Skip to content
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
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,8 @@
<td>defaultValue: string</td>
<td></td>
<td>
Default value given to the textarea when is uncontrolled and also maintains the uncontrolled behaviour.
Default value given to the textarea when is uncontrolled and also
maintains the uncontrolled behaviour.
</td>
</tr>
<tr>
Expand Down Expand Up @@ -59,8 +60,9 @@
</td>
<td>
If true, the input will be optional, showing <code>(Optional)</code>
next to the label. Otherwise, the field will be considered required and an error
will be passed as a parameter to the OnBlur and onChange functions when it has not been filled.
next to the label. Otherwise, the field will be considered required and an
error will be passed as a parameter to the OnBlur and onChange functions
when it has not been filled.
</td>
</tr>
<tr>
Expand Down Expand Up @@ -94,9 +96,12 @@
<td>error: string</td>
<td></td>
<td>
If it is defined, the component will change its appearance, showing the
error below the textarea component. If it is not defined, the error
messages will be created and managed internally.
If it is a defined value and also a truthy string, the component will
change its appearance, showing the error below the textarea. If the
defined value is an empty string, it will reserve a space below the
component for a future error, but it would not change its look. In case of
being undefined or null, both the appearance and the space for the error
message would not be modified.
</td>
</tr>
<tr>
Expand Down Expand Up @@ -198,4 +203,4 @@
...
</td>
</tr>
</dxc-table>
</dxc-table>
Original file line number Diff line number Diff line change
Expand Up @@ -7,20 +7,24 @@
[pattern]="pattern"
(onBlur)="onBlur($event)"
tabIndexValue="3"
margin="xsmall"
>
</dxc-textarea>
<dxc-textarea
label="default value"
[pattern]="pattern"
defaultValue="Default"
margin="xsmall"
>
</dxc-textarea>
</tbuilder-component-mode>
<tbuilder-component-mode text="Invalid">
<dxc-textarea label="Test" error="error"> </dxc-textarea>
<dxc-textarea label="Test" error="error" margin="xsmall"> </dxc-textarea>
<dxc-textarea label="Test" error="" margin="xsmall"> </dxc-textarea>
</tbuilder-component-mode>
<tbuilder-component-mode text="Disabled">
<dxc-textarea label="Test" value="test" disabled="true"> </dxc-textarea>
<dxc-textarea label="Test" value="test" disabled="true" margin="xsmall">
</dxc-textarea>
</tbuilder-component-mode>
</background-provider>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,4 +19,8 @@
(focus)="handleOnFocus()"
[attr.autocomplete]="autocomplete"
></textarea>
<span *ngIf="error && !disabled" class="textareaErrorMessage">{{ error }}</span>
<span
*ngIf="(error || error === '') && !disabled"
class="textareaErrorMessage"
>{{ error }}</span
>
Original file line number Diff line number Diff line change
Expand Up @@ -131,9 +131,15 @@ describe("DxcTextareaComponent", () => {
expect(textarea).toHaveFocus();
fireEvent.click(textarea);
fireEvent.input(textarea, { target: { value: "pattern4&" } });
expect(onChange).toHaveBeenCalledWith({ error: null, value: "pattern4&" });
expect(onChange).toHaveBeenCalledWith({
error: undefined,
value: "pattern4&",
});
fireEvent.blur(textarea);
expect(onBlur).toHaveBeenCalledWith({ error: null, value: "pattern4&" });
expect(onBlur).toHaveBeenCalledWith({
error: undefined,
value: "pattern4&",
});
expect(screen.getByDisplayValue("pattern4&"));
});
test("Strict mode - Length constraint", async () => {
Expand Down Expand Up @@ -176,7 +182,10 @@ describe("DxcTextareaComponent", () => {
fireEvent.input(textarea, { target: { value: "test 2" } });
fireEvent.blur(textarea);
await waitFor(() => {
expect(onBlur).toHaveBeenCalledWith({ error: null, value: "test 2" });
expect(onBlur).toHaveBeenCalledWith({
error: undefined,
value: "test 2",
});
});
});
test("Strict mode - Pattern and length constraints", async () => {
Expand Down Expand Up @@ -227,7 +236,7 @@ describe("DxcTextareaComponent", () => {
fireEvent.click(textarea);
fireEvent.input(textarea, { target: { value: "test 4" } });
fireEvent.blur(textarea);
expect(onBlur).toHaveBeenCalledWith({ error: null, value: "test 4" });
expect(onBlur).toHaveBeenCalledWith({ error: undefined, value: "test 4" });
});
test("Non Strict mode - Pattern constraint", async () => {
const onChange = jest.fn((value) => {
Expand Down Expand Up @@ -351,7 +360,10 @@ describe("DxcTextareaComponent", () => {
fireEvent.input(textarea, { target: { value: "Blur test" } });
fireEvent.blur(textarea);
expect(onBlur).toHaveBeenCalled();
expect(onBlur).toHaveBeenCalledWith({ value: "Blur test", error: null });
expect(onBlur).toHaveBeenCalledWith({
value: "Blur test",
error: undefined,
});
});
test("Controlled textarea", async () => {
const onChange = jest.fn();
Expand Down Expand Up @@ -382,13 +394,13 @@ describe("DxcTextareaComponent", () => {
expect(screen.getByDisplayValue("test"));
expect(onChange).toHaveBeenCalledWith({
value: "Controlled test",
error: null,
error: undefined,
});
});
fireEvent.blur(textarea);
await waitFor(() => {
expect(onBlur).toHaveBeenCalled();
expect(onBlur).toHaveBeenCalledWith({ value: "test", error: null });
expect(onBlur).toHaveBeenCalledWith({ value: "test", error: undefined });
});
});
test("Uncontrolled input", async () => {
Expand All @@ -415,7 +427,7 @@ describe("DxcTextareaComponent", () => {
expect(onChange).toHaveBeenCalled();
expect(onChange).toHaveBeenCalledWith({
value: "Uncontrolled test",
error: null,
error: undefined,
});
expect(textarea.value).toBe("Uncontrolled test");
});
Expand Down
46 changes: 25 additions & 21 deletions projects/dxc-ngx-cdk/src/lib/dxc-textarea/dxc-textarea.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ export class DxcTextareaComponent implements OnInit {
}
private _disabled = false;
/**
* If true, the textarea will be optional, showing (Optional) next to the label.
* If true, the textarea will be optional, showing (Optional) next to the label.
* Otherwise, the field will be considered required and an error will be passed as a parameter to the OnBlur and onChange functions when it has not been filled.
*/
@Input()
Expand Down Expand Up @@ -99,8 +99,12 @@ export class DxcTextareaComponent implements OnInit {
@Input()
verticalGrow: "auto" | "manual" | "none" = "auto";
/**
* If it is defined, the component will change its appearance, showing the error below the textarea component.
* If it is not defined, the error messages will be created and managed internally.
* If it is a defined value and also a truthy string, the component will
* change its appearance, showing the error below the textarea. If the defined
* value is an empty string, it will reserve a space below the component for a
* future error, but it would not change its look. In case of being undefined
* or null, both the appearance and the space for the error message would not
* be modified.
*/
@Input()
error = undefined;
Expand All @@ -110,34 +114,34 @@ export class DxcTextareaComponent implements OnInit {
@Input()
placeholder = "";
/**
* Regular expression that defines the valid format allowed by the textarea.
* This will be checked when the textarea loses the focus.
* If the value entered does not match the pattern, the onBlur function will be called with the value
* entered and the error informing that the value does not match the pattern as parameters. If the pattern is accomplished,
* Regular expression that defines the valid format allowed by the textarea.
* This will be checked when the textarea loses the focus.
* If the value entered does not match the pattern, the onBlur function will be called with the value
* entered and the error informing that the value does not match the pattern as parameters. If the pattern is accomplished,
* the error parameter will be null.
*/
@Input()
pattern = "";
/**
* Specifies the minimun length allowed by the textarea.
* This will be checked both when the input element loses the focus and while typing within it.
* If the string entered does not comply the minimum length, the onBlur and onChange functions will be called
* with the current value and an internal error informing that the value length does not comply the specified range.
* Specifies the minimun length allowed by the textarea.
* This will be checked both when the input element loses the focus and while typing within it.
* If the string entered does not comply the minimum length, the onBlur and onChange functions will be called
* with the current value and an internal error informing that the value length does not comply the specified range.
* If a valid length is reached, the error parameter of both events will be null.
*/
@Input()
minLength: number;
/**
* Specifies the maximum length allowed by the textarea.
* This will be checked both when the input element loses the focus and while typing within it.
* If the string entered does not comply the maximum length, the onBlur and onChange functions will be called
* with the current value and an internal error informing that the value length does not comply the specified range.
* Specifies the maximum length allowed by the textarea.
* This will be checked both when the input element loses the focus and while typing within it.
* If the string entered does not comply the maximum length, the onBlur and onChange functions will be called
* with the current value and an internal error informing that the value length does not comply the specified range.
* If a valid length is reached, the error parameter of both events will be null.
*/
@Input()
maxLength: number;
/**
* Size of the margin to be applied to the component ('xxsmall' | 'xsmall' | 'small' | 'medium' | 'large' | 'xlarge' | 'xxlarge').
* Size of the margin to be applied to the component ('xxsmall' | 'xsmall' | 'small' | 'medium' | 'large' | 'xlarge' | 'xxlarge').
* You can pass an object with 'top', 'bottom', 'left' and 'right' properties in order to specify different margin sizes.
*/
@Input()
Expand All @@ -161,7 +165,7 @@ export class DxcTextareaComponent implements OnInit {
private controlled: boolean;
defaultInputs = new BehaviorSubject<TextareaProperties>({
placeholder: "",
error: "",
error: undefined,
optional: false,
disabled: false,
helperText: "",
Expand All @@ -175,13 +179,13 @@ export class DxcTextareaComponent implements OnInit {
verticalGrow: "auto",
});
/**
* This event will emit when the user types within the textarea. An object including the new value and the error will be passed to this function.
* This event will emit when the user types within the textarea. An object including the new value and the error will be passed to this function.
* An example of this object is: { value: value, error: error }. If there is no error, error will be null.
*/
@Output()
onChange = new EventEmitter<EmittedValue>();
/**
* This event will emit when the textarea loses the focus. An object including the textarea value and the error will be passed to this function.
* This event will emit when the textarea loses the focus. An object including the textarea value and the error will be passed to this function.
* An example of this object is: { value: value, error: error }. If there is no error, error will be null.
*/
@Output()
Expand Down Expand Up @@ -275,7 +279,7 @@ export class DxcTextareaComponent implements OnInit {
return `Min length ${this.minLength}, Max length ${this.maxLength}`;
if (value && !this.patternMatch(this.pattern, value))
return `Please use a valid pattern`;
return null;
return undefined;
}
private handleValidationError() {
const validationError = this.validateValue(this.value);
Expand Down Expand Up @@ -315,4 +319,4 @@ export class DxcTextareaComponent implements OnInit {
}
}
}
}
}