Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

✨(react) add TextArea component #199

Merged
merged 4 commits into from
Oct 24, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/ninety-eggs-cross.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@openfun/cunningham-react": minor
---

add TextArea component
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import { Select } from ":/components/Forms/Select";
import { FileUploader } from ":/components/Forms/FileUploader";
import { Switch } from ":/components/Forms/Switch";
import { Radio } from ":/components/Forms/Radio";
import { TextArea } from ":/components/Forms/TextArea";

export default {
title: "Components/Forms/Examples",
Expand Down Expand Up @@ -106,6 +107,9 @@ export const Application = () => {
accept="application/pdf"
/>
</div>
<div>
<TextArea label="Cover letter" fullWidth={true} rows={5} />
</div>
<div>
<Switch label="SMS Notification" fullWidth={true} />
<Switch label="Subscribe to newsletter" fullWidth={true} />
Expand Down
2 changes: 1 addition & 1 deletion packages/react/src/components/Forms/Input/index.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ You can use all the props of the native html `<input>` element props plus the fo

## Design tokens

Here are the custom design tokens defined by the button.
Here are the custom design tokens defined by the input.

| Token | Description |
|--------------- |----------------------------- |
Expand Down
2 changes: 1 addition & 1 deletion packages/react/src/components/Forms/Input/index.scss
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@
flex-grow: 1;
text-overflow: ellipsis;
background-color: transparent;
font-family: var(--c--theme--font--families--base);
@extend %text-style;

&__icon-left,
Expand Down Expand Up @@ -87,7 +88,6 @@

&--disabled {
cursor: default;

border-color: var(--c--theme--colors--greyscale-200);

.c__input {
Expand Down
126 changes: 126 additions & 0 deletions packages/react/src/components/Forms/TextArea/index.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
import { Canvas, Meta, Story, Source, ArgTypes } from '@storybook/blocks';
import * as Stories from './index.stories';
import { TextArea } from '.';

<Meta of={Stories}/>

# TextArea

Cunningham provides a versatile TextArea component that you can use in your forms.

<Canvas>
<Story id="components-forms-textarea--default"/>
</Canvas>

<Source
language='ts'
dark
format={false}
code={`import { TextArea } from "@openfun/cunningham-react";`}
/>

## States

You can use the following props to change the state of the TextArea component by using the `state` props.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--default"/>
</Canvas>

<Canvas sourceState="shown">
<Story id="components-forms-textarea--success"/>
</Canvas>

<Canvas sourceState="shown">
<Story id="components-forms-textarea--error"/>
</Canvas>

## Disabled

As a regular textarea, you can disable it by using the `disabled` props.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--disabled-empty"/>
<Story id="components-forms-textarea--disabled-filled"/>
</Canvas>

## Texts

You can define a text that will appear below the input by using the `text` props.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--with-text"/>
</Canvas>

You can also independently add a text on the right side by using the `rightText` props.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--with-both-texts"/>
</Canvas>

## Width

By default, the textarea has a default width, like all inputs. But you can force it to take the full width of its container by using the `fullWidth` props.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--full-width"/>
</Canvas>

## Chars Counter

You can display a counter of the number of characters entered in the textarea by using the `charsCounter` props. Please bare
in mind to also define `charCounterMax`.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--char-counter"/>
</Canvas>

## Controlled / Non Controlled

Like a native textarea, you can use the TextArea component in a controlled or non controlled way. You can see the example below
using the component in a controlled way.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--controlled"/>
</Canvas>

## Ref

You can use the `ref` props to get a reference to the textarea element.

<Canvas sourceState="shown">
<Story id="components-forms-textarea--with-ref"/>
</Canvas>

## Props

You can use all the props of the native html `<textarea>` element props plus the following.

<ArgTypes of={TextArea} />

## Design tokens

Here are the custom design tokens defined by the textarea.

| Token | Description |
|--------------- |----------------------------- |
| font-weight | Value font weight |
| font-size | Value font size |
| value-color | Value color |
| value-color--disabled | Value color when disabled |
| border-radius | Border radius of the textarea |
| border-radius--hover | Border radius of the textarea on mouse hover |
| border-radius--focus | Border radius of the textarea when focused |
| border-width | Border width of the textarea |
| border-color | Border color of the textarea |
| border-color--hover | Border color of the textarea on mouse hover |
| border-color--focus | Border color of the textarea when focus |
| border-style | Border style of the textarea |
| label-color--focus | Label color when focused |


## Form Example

<Canvas>
<Story id="components-forms-textarea--form-example"/>
</Canvas>
108 changes: 108 additions & 0 deletions packages/react/src/components/Forms/TextArea/index.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
.c__field--textarea {
width: inherit;
min-width: var(--c--components--forms-field--width);

&.c__field--full-width {
min-width: 100%;
}
}

.c__textarea__wrapper {
border-radius: var(--c--components--forms-textarea--border-radius);
border-width: var(--c--components--forms-textarea--border-width);
border-color: var(--c--components--forms-textarea--border-color);
border-style: var(--c--components--forms-textarea--border-style);
background-color: var(--c--components--forms-textarea--background-color);
transition: border var(--c--theme--transitions--duration) var(--c--theme--transitions--ease-out);
overflow: hidden;

.labelled-box__label {
padding: 0 1rem;
}

.c__textarea {
border: none;
background: none;
font-size: var(--c--components--forms-textarea--font-size);
font-weight: var(--c--components--forms-textarea--font-weight);
min-width: 100%;
padding: 0 1rem;
box-sizing: border-box;
font-family: var(--c--theme--font--families--base);

&:focus-visible {
outline: none;
}
}

&:hover {
border-radius: var(--c--components--forms-textarea--border-radius--hover);
border-color: var(--c--components--forms-textarea--border-color--hover);
}

&:focus-within {
border-radius: var(--c--components--forms-textarea--border-radius--focus);
border-color: var(--c--components--forms-textarea--border-color--focus) !important;
jbpenrath marked this conversation as resolved.
Show resolved Hide resolved

label {
color: var(--c--components--forms-textarea--label-color--focus);
}
}

&--disabled {
cursor: default;
border-color: var(--c--theme--colors--greyscale-200);

.c__textarea {
background-color: var(--c--components--forms-textarea--background-color);
}

.c__input {
color: var(--c--components--forms-textarea--value-color--disabled);
}

&:hover {
border-color: var(--c--theme--colors--greyscale-200);
}
}
}

.c__field {
&--success {
.c__textarea__wrapper {
border-color: var(--c--theme--colors--success-600);

.labelled-box label {
color: var(--c--theme--colors--success-600);
}

&:not(.c__input__wrapper--disabled) {
&:hover {
border-color: var(--c--theme--colors--success-800);
color: var(--c--theme--colors--success-800);

.labelled-box label {
color: var(--c--theme--colors--success-800);
}
}
}
}
}

&--error {
.c__textarea__wrapper {
border-color: var(--c--theme--colors--danger-600);

&:not(.c__input__wrapper--disabled) {
&:hover {
border-color: var(--c--theme--colors--danger-800);
color: var(--c--theme--colors--danger-800);

label {
color: var(--c--theme--colors--danger-800);
}
}
}
}
}
}
Loading