AngularJS + Bootstrap, datepicker is invalid with prepopulated data - angularjs

I have this form,
and on this form,
I have a control,
this control is a datepicker. It looks like this:
<div class="form-group" ng-class="{ 'has-error' : !orderLine.required.$pristine && orderLine.required.$invalid || !orderLine.required }">
<label class="control-label">Required date</label>
<div class="input-group">
<input class="form-control" type="text" name="required" ng-model="controller.orderLine.dates.required" datepicker-popup show-weeks="false" is-open="controller.calendar.open" required />
<span class="input-group-btn">
<button type="button" class="btn btn-default" ng-click="controller.openCalendar($event)"><span class="fa fa-calendar"></span></button>
</span>
</div>
valid: {{ !orderLine.required.$invalid }}
</div>
As you can see, this is a required field.
If I pull in some data from the server and populate this field with the value, the control is still marked as invalid.
Does anyone know why?

Related

Form validation not working in angular js

I have the following:
<form name="ctrl.form" class="form-horizontal" ng-class="{true: 'has-error'}[submitted && form.email.$invalid]"
novalidate>
<div class="form-group" ng-class="{'has-error' : ctrl.form.inputName.$dirty && ctrl.form.inputName.$invalid}">
<label for="inputName" class="col-sm-2 control-label">Name</label>
<div class="col-sm-8">
<input type="text" class="form-control" id="inputName" name="inputName" ng-model="ctrl.app.name"
placeholder="Enter stack name" ng-disabled="ctrl.editMode" ng-required='true'
ng-minlength='3' ng-maxlength='32' required/>
</div>
<span ng-show="ctrl.form.inputName.$error.required && !ctrl.form.inputName.$pristine" class="help-block">Name is required</span>
<span ng-show="ctrl.form.inputName.$error.minlength" class="help-block">Name is too short</span>
<span ng-show="ctrl.form.inputName.$error.maxlength" class="help-block">Name is too long</span>
<span ng-show="ctrl.form.inputName.$error.pattern" class="help-block">Name has invalid characters</span>
</div>
<div class="form-group" ng-class="{'has-error' : ctrl.hasServerErrors}">
<div class="col-sm-offset-2 col-sm-10">
<button type="submit" class="btn btn-primary" ng-disabled="ctrl.isCreating"
ng-click="ctrl.SubmitForm()">{{ctrl.editMode ? 'Update' :
ctrl.isCreating? 'Creating': 'Create'}}
</button>
<span ng-show="ctrl.hasServerErrors" class="help-block"
ng-repeat="serverError in ctrl.serverErrors">
{{serverError}}
</span>
</div>
</div>
<div class="alert alert-success" ng-show="ctrl.showUpdateSuccessAlert">
<strong>Successfully updated!</strong>
</div>
</form>
Now, the problem is, even though I have added the required tag to name, still when I click the submit button, the call goes to the backend service without showing that name is mandatory and has to be supplied.
What am I missing in this? Thanks!
<div class="" ng-show="ctrl.form.inputName.$dirty && ctrl.form.inputName.$invalid">
Message which you want to print.
</div>
Add this.
Hope this will help you.
You should check if the form is valid before submitting the form.
<button type="submit" class="btn btn-primary" ng-disabled="ctrl.form.$invalid"
ng-click="ctrl.SubmitForm()">{{ctrl.editMode ? 'Update' :
ctrl.isCreating? 'Creating': 'Create'}}
</button>
$invalid will be true, when the form is not valid.

Sharing controllers in angularjs

I have two date-pickers, one text field and a button in one form as below:
<div class="form-group">
<label class="control-label">Date End </label>
<div class="controls">
<p class="input-group" ng-controller="datePickerCtrl">
<input type="text" name="endDate" class="form-control" uib-datepicker-popup="{{format}}" ng-model="dt" is-open="popup1.opened" datepicker-options="dateOptions" ng-required="true" close-text="Close" alt-input-formats="altInputFormats" />
<span class="input-group-btn">
<button type="button" class="btn btn-default" ng-click="open1()"><i class="glyphicon glyphicon-calendar"></i></button>
</span>
</p>
</div>
</div>
<div class="form-group">
<label class="control-label">Staff </label>
<div class="controls">
<input type="text" name="name" class="form-control" ng-model="staff.name">
</div>
</div>
<div class="row">
<div class="col-md-4"></div>
<div class="col-md-4">
<div class="btn-group" role="group" aria-label="Close">
<button type="button" class="btn btn-primary" ng-click="userClickedCancel()">Filter</button>
</div>
</div>
<div class="col-md-4"></div>
</div>
As can be seen, each date-picker has the same controller: datePickerCtrl. I would like to have one controller attached to the whole form that will utilise the dates returned by the date-pickers and the text field. However, I'm not sure how to do it since both date-pickers are returning the date as ng-model=dt.
I do not want to copy paste the datePickerCtrl code in multiple places with a different variable to dt in each instance. I also don't want to create one controller and copy the datePickerCtrl into it since I would like to keep the code for date-picker separate. What's the best way to do this? Thanks.

How to validate two form in one submit button in AngularJS?

I am beginner in AngularJS. So I faced little bit confusion this language. Please check my code:
<form class="form-horizontal" ng-submit="productFormForm.$valid && submitProductForm()" novalidate="" name="productFormForm">
<label for="from_id_dropdown">Templates</label>
<select class="form-control" name="from_id_dropdown" id="from_id_dropdown" ng-model="formData.form_id" ng-change="getDropdownOptions(formData.form_id)" ng-options="option.id as option.name for option in forms_dropdown.availableOptions" required="">
<option value="">Select Template</option>
</select>
<div ng-show="productFormForm.$submitted || productFormForm.from_id_dropdown.$touched" class="">
<span style="color:red;" ng-show="productFormForm.from_id_dropdown.$error.required">Template is required.</span>
</div>
</form>
<form class="form-horizontal" ng-submit="attributeForm.$valid && submitForm()" novalidate="" name="attributeForm">
<label class="tooltip-demo">Label</label>
<input type="text" name="attribute_lebel" ng-model="attr_value.label" class="form-control" placeholder="Label Name" required="">
<div ng-show="attributeForm.$submitted || attributeForm.attribute_lebel.$touched" class="">
<span class="text-danger" ng-show="attributeForm.attribute_lebel.$error.required">Label is required.</span>
</div>
<button class="btn btn-w-m btn-success" type="submit">Save</button>
</form>
Here is two form productFormForm and attributeForm But one submit button which is 2nd form. I want to validate both form those fields are blank.
You can validate both forms using js - example
or in html add <span> after your button -
<span ng-show="attributeForm.attribute_lebel.$error.required || productFormForm.from_id_dropdown.$error.required"> Form not valid</span>

Toggle class on input depending on input's value

I am still new to Angular but I have an existing application that uses Angular 1.5 pretty heavily.
I have a basic form that I need to add a class to depending on the following criteria:
The form can only have an End Date value or an Active for value. It cannot have both. I was thinking I need to disable the input box of the input not being used.
Ex. If a user inputs a date into the End Date input, then the Active for input will become disabled.
I looked into ng-if but every example I came across was for checking if the entered input variable was empty or equal to a value in a .js controller, not checking if the current entered variable was equal to another entered variable in the form.
<div class="form-group">
<label>End date:</label>
<div class="input-group">
<input type="text" class="form-control" is-open="endDateOpened" uib-datepicker-popup="MM/dd/yyyy" ng-model="updatePatientLabel.active_end_date"/>
<span class="input-group-btn">
<button type="button" class="btn btn-search" ng-click="openEndDate($event)"><i class="fa fa-calendar"></i></button>
</span>
</div>
</div>
<div class="form-group">
<label>Or will be active for:</label>
<input name="expirationTimeNumber" type="number" class="form-control time" ng-model="updatePatientLabel.expiration_time_number"/>
</div>
Here is a screenshot of my modal where this happens. Ignore the other inputs as they are not affected by the conditions I've laid out.
Thanks
Form Screen Shot
You can use ng-disabled.
//initialize your dates with null
$scope.updatePatientLabel = {};
$scope.updatePatientLabel.active_end_date = null;
$scope.updatePatientLabel.expiration_time_number = null;
HTML:
<input id="endDate" ng-disabled="updatePatientLabel.expiration_time_number !== null" ng-model="updatePatientLabel.active_end_date" />
<input id="activeDate" ng-disabled="updatePatientLabel.active_end_date !== null" ng-model="updatePatientLabel.expiration_time_number" />
You have a few options. Classes, as you mentioned, or ng-if. The ng-if seems more elegant, like so:
<div class="form-group" ng-if="updatePatientLabel.active_end_date != ''">
<label>End date:</label>
<div class="input-group">
<input type="text" class="form-control" is-open="endDateOpened" uib-datepicker-popup="MM/dd/yyyy" ng-model="updatePatientLabel.active_end_date"/>
<span class="input-group-btn">
<button type="button" class="btn btn-search" ng-click="openEndDate($event)"><i class="fa fa-calendar"></i></button>
</span>
</div>
</div>
<div class="form-group" ng-if="updatePatientLabel.expiration_time_number > 0">
<label>Or will be active for:</label>
<input name="expirationTimeNumber" type="number" class="form-control time" ng-model="updatePatientLabel.expiration_time_number"/>
</div>
Otherwise, you could do an inline conditional outputting "hidden" inside the class attribute only if the value is not present. Something like this:
<div class="form-group {{updatePatientLabel.active_end_date != '' ? '' : 'hidden'}}">
<label>End date:</label>
<div class="input-group">
<input type="text" class="form-control" is-open="endDateOpened" uib-datepicker-popup="MM/dd/yyyy" ng-model="updatePatientLabel.active_end_date"/>
<span class="input-group-btn">
<button type="button" class="btn btn-search" ng-click="openEndDate($event)"><i class="fa fa-calendar"></i></button>
</span>
</div>
</div>
<div class="form-group {{updatePatientLabel.expiration_time_number > 0 ? '' : 'hidden'}}">
<label>Or will be active for:</label>
<input name="expirationTimeNumber" type="number" class="form-control time" ng-model="updatePatientLabel.expiration_time_number"/>
</div>
I use both in my projects, and either way is perfectly acceptable. Though, ng-if does seem more elegant and a bit more suited for this scenario.

Issue with angular radio input not populating the model when clicked

I have a strange issue with a radio input not populating the model of an angular form.
All fields populate the model except for the radio input...
The radio input is given at the beginning of the form below. I use ng-inspector and I can see that signupForm.member.role does not get populated when I click one of the radio values.
Can someone please help?
<form name="formCtrl" ng-submit="signup(formCtrl)" class="col-xs-12" novalidate role="form">
<h4>{{'SIGNUP_FORM_ROLE_PREFIX' | translate}}</h4>
<div class="btn-group Choix col-xs-12 text-center" data-toggle="buttons" ng-class="getCssClasses(formCtrl, formCtrl.signupRole)">
<label class="btn StateButton col-xs-6">
<img class="img-responsive" src="assets/media/img/parents.svg" />
<input type="radio" name="signupRole" ng-model="signupForm.member.role" value="ROLE_BASIC_PARENTS" ng-required="true" />
<span class="help-block">{{'DOMAIN_ENUM_' + 'ROLE_BASIC_PARENTS' | translate}}</span>
</label>
<label class="btn StateButton col-xs-6">
<img class="img-responsive" src="assets/media/img/professionel.svg" />
<input type="radio" name="signupRole" ng-model="signupForm.member.role" value="ROLE_BASIC_CHILDCARE_WORKER" ng-required="true" />
<span class="help-block">{{'DOMAIN_ENUM_' + 'ROLE_BASIC_CHILDCARE_WORKER' | translate}}</span>
</label>
<div ng-messages="formCtrl.signupRole.$error" ng-if="formCtrl.$submitted">
<div ng-message="required" class="control-label">{{'SIGNUP_FORM_ROLE_REQUIRED'| translate}}</div>
</div>
</div>
<hr>
<div class="form-group" ng-class="getCssClasses(formCtrl, formCtrl.firstName)">
<div class="input-group">
<span class="input-group-addon">
<span class="glyphicon icon-Prenom" aria-hidden="true"></span>
</span>
<input type="text" name="firstName" ng-minlength="2" placeholder="{{'SIGNUP_FORM_FIRST_NAME' | translate}}" ng-model="signupForm.member.firstName" ng-required="true" class="form-control" />
<span ng-if="isSuccessFeedback(formCtrl, formCtrl.firstName)" class="form-control-feedback" aria-hidden="true"><span class="glyphicon icon-Valid" aria-hidden="true"></span></span>
<span ng-if="isErrorFeedback(formCtrl, formCtrl.firstName)" class="form-control-feedback" aria-hidden="true"><span class="glyphicon icon-Erreur" aria-hidden="true"></span></span>
</div>
<div ng-messages="formCtrl.firstName.$error" ng-if="formCtrl.$submitted">
<div ng-message="required" class="control-label">{{'SIGNUP_FORM_FIRST_NAME_REQUIRED' | translate}}</div>
<div ng-message="minlength" class="control-label">{{'SIGNUP_FORM_FIRST_NAME_REQUIRED' | translate }}</div>
</div>
</div>
</form>
Here is a working plunker: http://plnkr.co/edit/lsaevbL0mBRku7zcrGDJ
One can notice that the radio is not taken into account when the form is submitted even if one of the radios is selected...
Simply use value instead of ng-value. Please see this working demo: http://plnkr.co/edit/2EB4NvTO1StN50NIXOyn?p=preview.
You should not use ng-value, which is looking for $scope.ROLE_BASIC_PARENTS.
Check AngularJS.org, the example there use:
<input type="radio" ng-model="color.name" ng-value="specialValue">
And in the controller:
$scope.specialValue = {
"id": "12345",
"value": "green"
};

Resources