Angular 2 html form validation - html

I've created a form using html validations with Angular 2.
I want to to check the sate of the inputs (no empty, correct format, etc) when the user click to a certain button. At the moment I'm doing it as following:
<form id="memberForm" #memberForm="ngForm" >
<input
type="text"
id="MemberName"
required
name="MemberName"
[(ngModel)]="newMember.name">
</form>
<div
[ngClass]="{'button_disabledButton' : !memberForm?.valid}"
(click)="onSubmit(memberForm?.valid, memberForm);">
<span>Next</span>
</div>
With this, I'm only evaluating the input once clicked and focus out. How can I make it hapens when the user click in the "Next" element?

You should make getter/setter solution for your ngModel input.
In the .ts file in the appropriate class put this:
savedVar:string = '';
get variable(): string {
return this.savedVar;
}
set variable(str: string) {
this.savedVar = str;
// do your validation
}
In template use ngModel=variable like this:
<input [(ngModel)]="variable">

Related

How to use submit button present outside the component and also needs validation

I have one form template driven i am handling it using id like #firstname and then using ngModel.so basically i want once the code gets validated it should let the button know to get enabled or diabled which is present outside the component.
Note: i am not using form tag here
Using form
If your component has a template variable
<form #form="ngForm">
...
</form>`
You can get it (and expose as public property of your component)
using ViewChild
#ViewChild('form') form:NgForm
Now in your parent, can access to the form if you access to the
child
<app-child #child ></app-child>
<button (click)="submit(child.form.form)">submit</button>
submit(form:FormGroup)
{
if (form.valid)
this.result=form.value;
else
this.result="Invalid form"
}
Using simple control
<input name="name" [(ngModel)]="name" #nameID="ngModel" required>
The ViewChild
#ViewChild('nameID') control:FormControl
Your parent like
<child-control #childControl></child-control>
<button (click)="submitControl(childControl.control)">submit</button>
submitControl(control:FormControl)
{
if (control.valid)
this.result=control.value;
else
this.result="Invalid control"
}
A stackblitz

Hiding and Showing Edit Input not working(Angular)

I'm trying to make an Edit button, with an input field that appears/disappears when the button is pressed. It was working previously, however when I tried to make a Display form, it doesn't seem to recognize the "title.value" This is very strange. I'm using Boolean for an "edit" variable combined with a *ngIf to show/hide the form. If I take the *ngIf="edit" off, it works normally as a form that displays what you're written. Am I missing something?
Here's the HTML:
<input type="text" #title *ngIf="edit"/>
<button (click)="edit = !edit">Edit</button>
<button (click)="getTitle(title.value)">Get Title</button>
<h2>{{groupTitle}}</h2>
and here's the .ts:
public edit = false;
public groupTitle = "";
getTitle(val) {
this.groupTitle = val;
}
You have a problem with implementing together the ngIf directive and a reference to your input element as #title. In that case you can use hidden instead of ngIf.
Here's your html:
<input type="text" #title [hidden]="!edit"/>
<button (click)="edit = !edit">Edit</button>
<button (click)="getTitle(title.value)">Get Title</button>
<h2>{{groupTitle}}</h2>
There are couple more elegant ways to bind a value and render it on a page.
The first one is to get rid of the Get title button and use (input) method directly on an input element.
In that case, Html looks like:
<input type="text" #title *ngIf="edit" (input)="getTitle(title.value)"/>
<button (click)="edit = !edit">Edit</button>
<h2>{{groupTitle}}</h2>
The second one is to use [(ngModel]) instead of the getTitle method and bind your input value directly to the groupTitle variable.
Html will look like:
<input type="text" #title *ngIf="edit" [(ngModel)]="groupTitle"/>
<button (click)="edit = !edit">Edit</button>
<h2>{{groupTitle}}</h2>
Your .ts file:
edit = false;
groupTitle = "";

Spring MVC - how to bind HTML checkbox value in a boolean variable

I am very new to spring mvc world. I am trying to send boolean value to from html form checkbox. When a user check the checkbox then it will send true, false otherwise.
<form class="attendanceBook" role="form" method="post" action="/attendances">
<div class="row">
<div class="form-group">
<div class="col-xs-4">
<label class="control-label">Check Here</label>
</div>
<div class="col-xs-4">
<input type="checkbox" name="i" id="i" value="true" />
</div>
<div class="col-xs-4">
<input type="submit" value="Click"/>
</div>
</div>
</div>
</form>
After some googilng I have found this so post, where it said standard behaviour is the value is only sent if the checkbox is checked. So what I have understand that is if the checkbox checked then the form will submit with the value of checkbox, otherwise it will not submit. When there is unchecked checkbox the initialization value in data class will be effective.
But in my case every time I am submitting the form it submitting true.
here is my rest controller for the bind html form submit.
#RestController
#RequestMapping("attendances")
class AttendanceRestController {
val logger = getLogger(AttendanceRestController::class.java)
#PostMapping
fun patchAttendance(#RequestBody attendanceJson: AttendanceJson): ResponseEntity<*> {
logger.info("attendanceJson {}", attendanceJson)
return responseOK(attendanceJson)
}
}
the data class(I am using kotlin)
data class AttendanceJson (
var i: Boolean = false,
var t: String = ""
)
So what will be the method to bind boolean data from a form submission with checkbox. I am also using Thymeleaf. Thanks in advance.
I'm working in Struts and don't know much about Spring. But I faced a similar situation.
What I did was I binded the checkbox with a boolean property in my From class. So for each checkbox, one boolean variable. And at the time of submitting in front end, I'll call a JS function code is below
function verifyCheckboxes() {
document.getElementById("researchPaper").value = document.getElementById("researchPaper").checked;
document.getElementById("researchPaperSeminarProceed").value = document.getElementById("researchPaperSeminarProceed").checked;
document.getElementById("extraActivities").value = document.getElementById("extraActivities").checked;
document.getElementById("studentAchivements").value = document.getElementById("studentAchivements").checked;
}
Here you can see I'm just assigning the value of checked property of that Checkbox just before submitting. It will be either true or false.
You should remove 'value' attribute from the input. If you want the checkbox checked when loading the page, add 'checked' attribute not 'value'.
Replace the input line with this:
<input type="checkbox" name="i" id="i" checked="checked"/>
This is the reason why you always get 'true' in code behind.
It's a bit of a hack, but if you change the type of the input tag from 'checkbox' to 'text' just before the form is posted, you will receive the value, whether it is checked or unchecked.
If you use jQuery:
$("input:checkbox").each(function(){this.type='text'})

Changing CSS property if no input is provided (Angular JS)

I am making a quiz using angular js.The first page of the quiz requires you to enter your name and doesn't allow you to go further if no input is provided.I want to animate input field more like the shake animation on this site (http://daneden.github.io/animate.css/) if the input field is empty and the user presses the start button.Please help me out.
CODE html :
<p>What's your name?</p>
<input type = "text" class = "playername" ng-model = "playername">
<h2>Welcome {{playername}}!</h2>
<p>Click start if you're ready!</p>
<p class = "btn" ng-click = "startQuiz()">START</p>
CODE angular :
$scope.presentQues = -1;
$scope.startQuiz = function(){
if ($scope.playername != null){
$scope.presentQues = 0;
}
}
PS. this is not the full code.
Building on #Chris's answer, if you wrap it in a form, you can also use the form.$submitted variable to check if the form has been submitted.
ng-class uses the following format: ng-class={'css-class':truthy-condition-to-evaluate
Try the following code (this will have to be changed if you already are wrapping everything in a form):
<div ng-controller="myCtrl as ctrl">
<form name="myForm">
<p>What's your name?</p>
<input type = "text" name="playername" class = "playername" ng-class="{'animated shake': !ctrl.playername && myForm.$submitted}" ng-model = "ctrl.playername">
<h2>Welcome {{ctrl.playername}}!</h2>
<p>Click start if you're ready!</p>
<input type="submit" class = "btn" ng-click = "startQuiz()" value="START">
</form>
</div>
Now, if the player submits the form without typing anything, angular will apply the animated and shake css classes to the text input.
Look at my plunker to view it in action.
There are many ways of doing this, one I can see is using ng-class.
<!-- add class 'bounceInUp' if the scope var 'isEmpty' is true -->
<input type="text" class="playername" ng-class={'bounceInUp':isEmpty,} ng-model="playername">

Refresh Angular output on input reset

I have several <input> fields within a <form>. Angular takes the value from those fields regardless of the <form> (which is actually there only for Bootstrap to apply the right styles to inner fields).
Now, I want to be able to reset the fields, and so get Angular update the output associated to them as well. However, a regular <input type="reset"/> button is not working. It resets the values of all the <input> fields, but Angular is not refreshing the output that is based on the fields after it.
Is there any way to tell Angular to refresh the outputs based on the current state of the fields? Something like a ng-click="refresh()"?
Let's say you have your model called address. You have this HTML form.
<input [...] ng-model="address.name" />
<input [...] ng-model="address.street" />
<input [...] ng-model="address.postalCode" />
<input [...] ng-model="address.town" />
<input [...] ng-model="address.country" />
And you have this in your angular controller.
$scope.reset = function() {
$scope.defaultAddress = {};
$scope.resetAddress = function() {
$scope.address = angular.copy($scope.defaultAddress);
}
};
JSFiddle available here.
You should have your values tied to a model.
<input ng-model="myvalue">
Output: {{myvalue}}
$scope.refresh = function(){
delete $scope.myvalue;
}
JSFiddle: http://jsfiddle.net/V2LAv/
Also check out an example usage of $pristine here:
http://plnkr.co/edit/815Bml?p=preview