components: MdInput doesn't set required asterisk when the validator is set in reactive forms
Bug, feature request, or proposal:
The placeholder
from the MdInput does not show the asterisk (*) when we use Validators.required
in the FormControl
.
What is the expected behavior?
The asterisk should be shown as it is when setting the required
attribute.
What are the steps to reproduce?
http://plnkr.co/edit/XqkOmF502Q8RFj8qcUwp?p=preview or take a look at the input-container-demo
What is the use-case or motivation for changing an existing behavior?
To be not dependet on the template to visually indicate that the input is required.
Which versions of Angular, Material, OS, browsers are affected?
all (to my knowlege it never worked)
About this issue
- Original URL
- State: closed
- Created 7 years ago
- Reactions: 114
- Comments: 59 (10 by maintainers)
Commits related to this issue
- fix(material/input): show required asterisk when using required validator Resolves the long-standing issue where the required asterisk wasn't being shown in the form field label when using the `requi... — committed to crisbeto/material2 by crisbeto 3 years ago
- fix(material/input): show required asterisk when using required validator Resolves the long-standing issue where the required asterisk wasn't being shown in the form field label when using the `requi... — committed to crisbeto/material2 by crisbeto 3 years ago
- fix(material/input): show required asterisk when using required validator (#23362) Resolves the long-standing issue where the required asterisk wasn't being shown in the form field label when using t... — committed to angular/components by crisbeto 3 years ago
- fix(material/input): show required asterisk when using required validator (#23362) Resolves the long-standing issue where the required asterisk wasn't being shown in the form field label when using t... — committed to angular/components by crisbeto 3 years ago
I’m using this solution:
<input formControlName="name" [required]="formGroup.get('name').errors !== null && formGroup.get('name').errors.required">
Any ETA ??
I implemented a Monkey Patch for this for now, based on the proposed PR from Alexandre (https://github.com/angular/material2/pull/14795)
Any intent to fix this? Or should we settle with hacks/patches provided in this thread? 😃
Now that https://github.com/angular/angular/pull/42838 has landed we should be able to implement this
I needed more functional directive than applying a class to required to mat-form-field. I was needing to display the asterisk from reactive form validator to prevent duplicate management (and conflicts) by template + reactive form.
The directive matches only MatFormFields that have MatInput or MatSelect that don’t have [required] attribute. When elligible, the required status (determined as described by @Khaldor48) updates the MatFormControl.required status, updating the template and the showing/hiding the required asterisk.
Usage
Directive
hey guys, is there any update on this?
@ajaysattikar That would be template-driven forms. This whole discussion is about reactive forms.
well… no pretty solution… but you can add an additional directive to force the asterisk: https://stackblitz.com/edit/angular-material2-issue-qdqb1n?file=app%2Fmat-form-field-required.directive.ts
Below solution works for me:
@donacross But we don’t need this “workaround”. Manually adding required to reactive form is already adding the asterisk. The entire point of this thread is that it should also be added when the proper validator is set.
Any update on this?
Knowing if the required validation was added or not doesn’t seems like something that core angular is going to support, because validators are just functions. It is even possible to write a custom validation function that conditionally checks required, such as
if (something) return Validators.required(control) else null
. So, I would like to suggest adding a new attribute such asmatRequired
, which just visually add the asterisk, but doesn’t touch the validators. To be honest, this is the only solution I can think on this case, given that angular is unlike to support the requirement. This was proposed in #4090, but it was closed as a dupe of the current issue, but they are, in fact, different things. I’m suggesting in this one because it is the currently open issue.@daankets Thanks. Your Monkey Patch still works in Angular 9 and is also applicable to MatSelect: https://stackblitz.com/edit/angular9-reactive-form-required
I spent many hours to find a working non-all-performance-consuming solution. This is my solution (which is composed from other solutions found here and on stackoverflow). So thank you guys for helping me with this.
Note: I had implemented conditional required fields, which are not affected by this solution. If I found something useful I will post it here afterwards.
Note2: It requires typescript >= 3.7.0 because of optional chaining, but this can be easily workarounded with
Just a question: This one has been open for 2 years already… Is there still an intent to fix this one?
@bboehm86 that’s a great solution, but there’s a small bug that causes an error if
validator(new FormControl())
isnull
, which is the case when a control only has validators that are valid.This stackblitz shows the error occurring where the validators are valid (i.e. return
null
). Check the console to see them.The fix is to check if running the validator on an empty FormControl returns not null. The fix is in this stackblitz. Here’s the diff:
Unfortunately FelipeCarriel solution is not related to this issue. This issue is specifically about reactive form, but that solution is for template driven form.
Monkey patching still seems to be the best workaround available.
@isherwood Yes, sorry. Edited to avoid confusion.
Yeah but the underlying problem seems to be the same, only checking the existence of the
required
input, instead of checking whether required validator exists(which I think will be a little tricky).For future reference, https://github.com/angular/angular/issues/22422 is the issue blocking this one.
This solution proposed by @bboehm86 works for me, adding the fix that @kwkelly commented bellow, but I found other bug in lines 21, 22, because for access the first case you always need that
this._control.ngControl['form']
exists, so we need to remove thethis._control.ngControl.validator
conditionFor me, it’s a great solution while we wait for an official solution
Any solution for this?
Is there any update on this?
Using the required attribute doesn’t work well if the input is inside an ngIf I have found. The core forms automatically adds the required validator to the control when the required attribute is used on the input but it doesn’t go away once the input is no longer in the dom. Maybe that’s a separate issue for the core side not cleaning up when an element is removed from the dom. This leads to a form appearing invalid when it shouldn’t be.