How to trigger ngModelChange with a button in Angular 2 - html

I use *ngFor to populate my table.
<tr *ngFor= "stu in students">
<td>{{stu.name}}</td>
<td><input type="checkbox" ngModel="isChecked"
(ngModelChange)="addID(stu.id)</td>
</tr>
Then I have a button outside the table.
<button (click)="selectAllID()">select all</button>
Then I have my component as:
studentID=[];
isChecked=false;
addID(id:number){
this.student.push (id);
//I do other thing with id
}
selectAllID (){
If (this.isChecked)
this isChecked = false;
else this isChecked = true
}
The problem is:
if I check individual checkbox, the addID() function is executed. But if I click on the select all button, the checkboxes get selected. But the addID() function is not called.
How can I trigger the ngModelChange function when I use the select all button so I get all selected id's

You have only one way binding of the input control with ngModelChange directive. But to update the view you should bind the control to ngModel.
<input type="checkbox" [ngModel]="isChecked"
(ngModelChange)="addID(stu.id)">

Thank you everyone. i finally resolved the issue. This is what i did:
I used the selectAll() function to automatically load all id's (this id i get from the source loading my tables) to an array. and
i set the value of isChecked to true or false.

Related

Fire ng change on change of checkbox checked value in angular 8

Changed the value but change event is not getting triggered.I want to trigger the change when ischecked is changed
in html
<input class="inputStyle" type="checkbox" [checked]="isChecked" id="actA" tabindex="0" (change)="onAct($event)">
have another function(in ts)
onChangeoption(lang) {
this.isChecked = true; `enter code here`
}
What you are trying to do is trigger a change event after you have programatically changed the value of the input first and this is not going to work.
I can suggest two approaches:
Approach 1:
From what you have shown in those snippets, it seems easy to call onAct inside the onChangeoption. If you don't really need the change event object, you can call onAct immediately after you change the value of isChecked.
Approach 2:
If you need the change event object, create a reference of the input element and programatically dispatch a change event
In your TypeScript code:
#ViewChild('myCheckbox') myCheckbox;
onChangeoption() {
this.isChecked = true; `enter code here`
this.myCheckbox.nativeElement.dispatchEvent(new Event('change'));
}
And update your template:
<input #myCheckbox class="inputStyle" type="checkbox" [checked]="isChecked"
id="actA" tabindex="0" (change)="onAct($event)">

How can I check a Material Checkbox in Angular with a single click?

Execution:
I have several Material Checkboxes in a Material Dialog Component. They represent a column filter for a table:
<h1 mat-dialog-title>Filter</h1>
<div mat-dialog-content>
<ng-container *ngFor="let column of allColumns; index as i; first as firstEntry ">
<mat-checkbox *ngIf="!firstEntry" class="checkbox" [checked]="checkedList[i]" [aria-label]="column" (click)=doToggle(i)>{{column}}</mat-checkbox>
</ng-container>
</div>
<div mat-dialog-actions>
<button mat-button (click)="onNoClick()">Abbrechen</button>
<button mat-button [mat-dialog-close]="allColumns" cdkFocusInitial>Reset</button>
<button id="ok-button" mat-button [mat-dialog-close]="displayedColumns" cdkFocusInitial>Ok</button>
</div>
When I click on a Checkbox I want to check it. All booleans of the Checkboxes are saved in a boolean array named checkedList. When I click on a Checkbox the method doToggle(i) gets executed.
doToggle(i: number){
if(this.checkedList[i]){
this.displayedColumns[i] = this.allColumns[i];
}
else{
this.displayedColumns[i] = null;
}
this.checkedList[i] = !this.checkedList[i];
}
The method also fills or empties the values at the appropriate position of the column list. At the end of the method it negates the boolean at the appropriate position in the checkedList.
Problem:
I always have to click twice on the Checkbox to check or uncheck it. The values are added or removed properly. But still I have to click two times on the checkbox. Why is that?
Try sending the value of checkbox in the click event.
Add template reference variable(#ck) to checkbox and get its value ck.checked
[checked]="checkedList[i]" [aria-label]="column" #ck (click)="doToggle(i,!ck.checked)"
and in doToggle function
doToggle(i,value){
this.checkedList[i] = value;
if(this.checkedList[i]){
this.displayedColumns[i] = this.allColumns[i];
}
else{
this.displayedColumns[i] = null;
}
}

Setting checkbox value in angular after initialization

So I have this checkbox, I have binded ngModel to it and based on the ngModel it properly sets the checkbox as checked or unchecked.
The problem is, if I change the checkbox, I check for some conditions and based on some that condition I make the ngModel binded to it false again, so technically it should go back to unchecked state if it was checked and the condition satisfied, but it's not. Although my ngModel shows a value of false.
Even tried with the [checked] attribute, but it's also not working.
Any inputs are highly appreciated
<input type="checkbox" [(ngModel)]="isChecked" [checked]="isChecked" (ngModelChange)="onChange('statusPush',$event)">
in Component
if(someCondition) {
this.isChecked = false
}
This code worked for me, just add a time out function before making the value of isChecked true or false in your onChange function
if(someCondition) {
setTimeout(()=>{
this.isChecked = false
});
}
Hope this helps.

Angularjs: Onchange event when the user hits enter

I have a HTML table in which one of the column is editable
<td ng-model="my.grade">
<div contenteditable>
{{list.grade}}
</div>
</td>
I have an angular function getInformation which does some calculation and connects to back end and then
makes the table. My goal is that when the user changes the value of above column and hits the enter I want to update the table and basically re-run the function getInformation.
I read that I should ng-model and ng-change but how should I update the table value on the enter?
You can do it like this:
<td ng-model="row.grade"
contenteditable ng-keypress='keyPressed($event)'></td>
So, ng-model and contenteditable must be on the same element.
Also, if you specify ng-model on a element, all of its content will be replaced by the value from a model. So it should be empty.
And
$scope.keyPressed = function (e){
var code = (e.keyCode ? e.keyCode : e.which);
if(code == 13) { // 'Enter' keycode
$scope.getInformation(); // your function here or some other code
e.preventDefault();
}
}
Here is working Plunkr:
http://plnkr.co/edit/sHHlqF
Why do you use contenteditable? Maybe you could use just <input ng-model...>?

How can I detect keydown or keypress event in angular.js?

I'm trying to get the value of a mobile number textbox to validate its input value using angular.js. I'm a newbie in using angular.js and not so sure how to implement those events and put some javascript to validate or manipulate the form inputs on my html code.
This is my HTML:
<div>
<label for="mobile_number">Mobile Number</label>
<input type="text" id="mobile_number" placeholder="+639178983214" required
ngcontroller="RegisterDataController" ng-keydown="keydown">
</div>
And my controller:
function RegisterDataController($scope, $element) {
console.log('register data controller');
console.log($element);
$scope.keydown = function(keyEvent) {
console.log('keydown -'+keyEvent);
};
}
I'm not sure how to use the keydown event in angular.js, I also searched how to properly use it. And can i validate my inputs on the directives? Or should I use a controller like what I've done to use the events like keydown or keypress?
Update:
ngKeypress, ngKeydown and ngKeyup are now part of AngularJS.
<!-- you can, for example, specify an expression to evaluate -->
<input ng-keypress="count = count + 1" ng-init="count=0">
<!-- or call a controller/directive method and pass $event as parameter.
With access to $event you can now do stuff like
finding which key was pressed -->
<input ng-keypress="changed($event)">
Read more here:
https://docs.angularjs.org/api/ng/directive/ngKeypress
https://docs.angularjs.org/api/ng/directive/ngKeydown
https://docs.angularjs.org/api/ng/directive/ngKeyup
Earlier solutions:
Solution 1: Use ng-change with ng-model
<input type="text" placeholder="+639178983214" ng-model="mobileNumber"
ng-controller="RegisterDataController" ng-change="keydown()">
JS:
function RegisterDataController($scope) {
$scope.keydown = function() {
/* validate $scope.mobileNumber here*/
};
}
Solution 2. Use $watch
<input type="text" placeholder="+639178983214" ng-model="mobileNumber"
ng-controller="RegisterDataController">
JS:
$scope.$watch("mobileNumber", function(newValue, oldValue) {
/* change noticed */
});
You were on the right track with your "ng-keydown" attribute on the input, but you missed a simple step. Just because you put the ng-keydown attribute there, doesn't mean angular knows what to do with it. That's where "directives" come into play. You used the attribute correctly, but you now need to write a directive that will tell angular what to do when it sees that attribute on an html element.
The following is an example of how you would do that. We'll rename the directive from ng-keydown to on-keydown (to avoid breaking the "best practice" found here):
var mod = angular.module('mydirectives');
mod.directive('onKeydown', function() {
return {
restrict: 'A',
link: function(scope, elem, attrs) {
// this next line will convert the string
// function name into an actual function
var functionToCall = scope.$eval(attrs.ngKeydown);
elem.on('keydown', function(e){
// on the keydown event, call my function
// and pass it the keycode of the key
// that was pressed
// ex: if ENTER was pressed, e.which == 13
functionToCall(e.which);
});
}
};
});
The directive simple tells angular that when it sees an HTML attribute called "ng-keydown", it should listen to the element that has that attribute and call whatever function is passed to it. In the html you would have the following:
<input type="text" on-keydown="onKeydown">
And then in your controller (just like you already had), you would add a function to your controller's scope that is called "onKeydown", like so:
$scope.onKeydown = function(keycode){
// do something with the keycode
}
Hopefully that helps either you or someone else who wants to know
You can checkout Angular UI # http://angular-ui.github.io/ui-utils/ which provide details event handle callback function for detecting keydown,keyup,keypress
(also Enter key, backspace key, alter key ,control key)
<textarea ui-keydown="{27:'keydownCallback($event)'}"></textarea>
<textarea ui-keypress="{13:'keypressCallback($event)'}"></textarea>
<textarea ui-keydown="{'enter alt-space':'keypressCallback($event)'}"> </textarea>
<textarea ui-keyup="{'enter':'keypressCallback($event)'}"> </textarea>
JavaScript code using ng-controller:
$scope.checkkey = function (event) {
alert(event.keyCode); //this will show the ASCII value of the key pressed
}
In HTML:
<input type="text" ng-keypress="checkkey($event)" />
You can now place your checks and other conditions using the keyCode method.