Skip to content
This repository has been archived by the owner on Jul 1, 2020. It is now read-only.

Can i setup a validation that is conditional ? #52

Closed
rluiten opened this issue Jul 23, 2015 · 18 comments
Closed

Can i setup a validation that is conditional ? #52

rluiten opened this issue Jul 23, 2015 · 18 comments

Comments

@rluiten
Copy link

rluiten commented Jul 23, 2015

I've tried to use addValidator() and removeValidator() and have it working but its pretty awful IMO.
Going in I had almost expected that validation rules on a field would be disabled if ng-required was false. But then maybe that was an unreasonable expectation.

Maybe I am just missing something obvious.

We have quiet a few forms were some fields appear and are required to have a value if a checkbox is selected.

Thanks for reading,
Rob.

@ghiscoding
Copy link
Owner

The function of removeValidator() is made to completely remove it, it's not made for what you want to do.

If you want to validate a field only after your checkbox is selected, then you should add the validation on your input but make your input disabled with ngDisabled and only make it enable once the checkbox is clicked. Angular-Validation does not validate a field that is disabled, but will validate if it becomes enable. You can see that in the demo I made on the Live Plunker Demo the last field.

This is the code from the demo with a radio button, just change the radio to a checkbox and you are good to go

<div class="form-group">
            <label for="input4">ngDisabled =></label>
            ON <input type="radio" id="radioDisableInput4_on" ng-model="vm.disableInput4" value="on" ng-init="vm.disableInput4 = 'on'">
            OFF <input type="radio" id="radioDisableInput4_off" ng-model="vm.disableInput4" value="off">
            <input type="text" class="form-control" name="input4" placeholder="alpha_dash|min_len:2|required" ng-model="vm.input4" validation="alpha_dash|min_len:2|required" ng-disabled="vm.disableInput4 == 'on'" />
        </div>

@rluiten
Copy link
Author

rluiten commented Jul 23, 2015

That makes perfect sense [it was something I was missing], all the code here currently uses conditional on ng-required - which works but isn't as intention revealing. We still have a fair bit of not using angular-validation yet.

One further question, I have modified this form to use ng-disabled and it works and gets rid of the mess I had made before.

However one further hiccup, by using ng-disabled with the right condition the field appears correctly and is required correctly but it is marked in red with validation message on first appearance. The state of enabled field shows up with $pristine true and $valid false, now this is the same as the other fields that were never disabled to start with, but the other field do not show the validation markings until after being dirty, or submit has run which executes checkFormValidity() to flag all fields for the user.

Extra bit of info, before the control is enabled $valid is true, maybe the transition to false of being enabled is causing the marking ?

@ghiscoding
Copy link
Owner

I believe that is normal behavior to have the red border, because the field is really invalid since it's required. What you have to do is to change your CSS to only show red border on dirty.

This is part of my CSS to do that

/* invalid & (dirty or touched) => red -- CSS3 only */
.ng-invalid.ng-dirty:not(:focus),
.ng-invalid.ng-touched:not(:focus) {
    border-color: #e74c3c;
}

/* valid & dirty => green */
.ng-valid.ng-dirty.ng-touched {
    border-color: #2ecc71;
}

If you have no more questions and this fixes your problem, please close this issue. Thanks

@rluiten
Copy link
Author

rluiten commented Jul 23, 2015

Ill restate my comment, maybe I did not express myself sufficiently.

The other fields all have validation="required", and are not showing the validation when they are shown. It is common to not show it if the control is still pristine$ I believe this is why you provide the checkFormValidity() to force them to be visible if for example if someone wants them all to appear if someone presses submit button.

Its just the enabled form field is shown differently from other fields that also required on the form, it is shown invalid when others are not yet.

@rluiten
Copy link
Author

rluiten commented Jul 23, 2015

Hmm interesting, this field that has been enabled is marked $touched is true.

@ghiscoding
Copy link
Owner

Ah now I think I know what you mean. Yes that is how I coded it, when you enable it, I validate and touch the item, if it's required then the error message will show right away. You can see that in the live demo.

I should maybe change that and only show it right if the global option of preValidateFormElements is True. Looks like I'm never done with this library :'(

@ghiscoding
Copy link
Owner

When a field get re-enable, I run the validation on it and I also mark it as $touched, which is what you found out.

I found the code where it does that, I'll have to change to few things to do as said in my previous comment:
I should maybe change that and only show it right if the global option of preValidateFormElements is True.

I will have to modify my Protractor tests also, since it changes a few things and it will fail. I will see if I can push that in the next couple hours or tomorrow.

@rluiten
Copy link
Author

rluiten commented Jul 23, 2015

Don't do it on my account we are weeks from next deployment at moment.

Extra note, as a test I added an ng-disabled="false" to one of my normal form fields and it also gets the validation shown immediately. Which make sense in the light of your comments.

@rluiten
Copy link
Author

rluiten commented Jul 23, 2015

My colleague just asked me a related question, he is aware of a few forms where a field that is normally optional becomes a required field when a checkbox is set to true. Does this scenario require the use of the addValidator() removeValidator() methods ?

As a side note, i think making removeValidator() not crash if there isnt a validator allready there would be a good thing.

@ghiscoding
Copy link
Owner

I already got something close to working, but I want to take a break now, it will not validate automatically anymore (unless you have the global options preValidateFormElements is True). Which is how I should have coded it at first, it makes more sense that way.

What do you mean by removeValidator() crash? What are your function arguments?

The removeValidator() was created to completely remove all validators to the field. You could use the addValidator() to add it back, but playing with those 2 functions might not always be the best. If you want to dynamically add validation, you could also do it yourself through Angular interpolation, you could probably do something like this: <input type="text" name="field2" validation="{{vm.isRequired}}" /> where the vm.isRequired is set somewhere in your controller or in your view by another field, up to you. You just need to be creative and find a solution, there is multiple ways to do it, just think about it and have fun finding a solution...

I can't put everything into Angular-Validation, it's already doing a lot, I don't want to over complicate it, with extra features that are not always necessary.

@rluiten
Copy link
Author

rluiten commented Jul 24, 2015

Ahh i feel stupid now :), while I've used angular a bit now, still not always doing things the easy way.

@rluiten
Copy link
Author

rluiten commented Jul 24, 2015

I have tried out the interpolation to validation.
It sort of works, field 1 defaults to required field 2 is the inverse.
Then i can toggle the required validation between the two with the checkbox in the example

http://plnkr.co/edit/XLhq6Cxf9d53vUfpvJJ1?p=preview

I get to see field 1 get the validation message, and it toggles on and off with the check box, but field 2 never produces the validation field even if i go into it and out of it or type something in and then remove the content toggling check box before and after the operation to try and see the validation message

Maybe its a just a bug ?

ghiscoding added a commit that referenced this issue Jul 29, 2015
- Fixed issue #52, Changed default behavior of `ngDisabled` which was
displaying error message right after an element became enabled, it will
still pre-validate but not directly show the error message unless
`preValidateFormElements` is set to True.
- Look into the folder /more-examples/interpolate/
- Fixed issue #53,  To support `ngIf` (add a trigger on element
`$destroy`).
- Look into the folder /more-examples/ngIfShowHideDisabled/
@ghiscoding
Copy link
Owner

I used your plunker demo to test it out and you were correct, the interpolation wasn't working correctly, but now it does :)
You can find a demo under the folder angular-validation/more-examples/interpolateValidation which is based on the plunker demo you did.
I also fixed your plunker if you want to see it there.

And finally, I also fixed the red border that was showing at the beginning, the behavior is now to still pre-validate the field but without showing the error message right away (unless you defined the global option of preValidateFormElements to True).

So please use the new version v.1.3.38

Thank you for the great feedback!
You should hire me, you find the bugs and I fix the bugs..lol

@rluiten
Copy link
Author

rluiten commented Jul 29, 2015

This looks good so far.
I can't hire you :) I am a contractor, and the project I am on might well be imploding due to political reasons in the near future. Though the software is finished enough to be useful thankfully.

@ghiscoding
Copy link
Owner

Oh well, good luck with your project. Hopefully you'll use my library for all future projects ;)

@ghiscoding
Copy link
Owner

Just so you know, another person raised a small issue just after my previous version, so v.1.3.39 was pushed 2min ago, so 1.3.38 is already outdated. I hope it's the last one for long time though.

@rluiten
Copy link
Author

rluiten commented Jul 29, 2015

I noticed the 1.3.39 update and laughed, but sounds like a good fix to.
If your library gets popular i am sure more corner cases and such will be discovered.

I have the v1.3.39 installed in our project now, and the validation behaviour is much nicer now don't get the warnings till after submit is pressed which I think is a nice. Also the conditional validation with interpolation in two of our forms has made them markedly simpler.

One of the reasons your library IMO is better than the other 5 I had looked at is yours reduces the markup complexity and the coding complexity. Some of the libraries I looked at I had to do as much work as if I was handling it all myself anyway.

@ghiscoding
Copy link
Owner

My end goal was simplicity :)

Having more people using it, is great also for the fact that lot of features came from suggestions of others. You brought up ControllerAs, some persons even took the time to add new locale translation as well. For a first open source tool, I think it's a success :)

Alright time to sleep in Canada, it's pass midnight. Cheers from the other end ;)

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants