Disable or enable button per item in angularjs - angularjs

I have a list of participants. Each participant have dial and mute buttons. I want to disable mute button at first and enable it only after dial button is clicked. Currently, if I click on dial button of say Participant 1, all the mute buttons of other participants enables. But I want to enable mute button of only Participant 1.
HTML:
<body ng-controller="MainCtrl">
<table>
<tr ng-model="participant.partName" ng-repeat="participant in participants">
<td>{{participant.partName}}</td>
<td>
<button ng-click="mutePart(participant.partName);">Mute</button>
</td>
<td>
<button ng-click="dial(participant.partName)">Dial</button>
</td>
</tr>
</table>
</body>
JS:
$scope.participants = [
{
partName: 'abc',
partId: '123'
},
{
partName: 'def',
partId: '1234'
},
{
partName: 'xyz',
partId: '12345'
},
]
$scope.mutePart = function(item){
}
$scope.dial = function(item){
}

<body ng-controller="MainCtrl">
<table>
<tr ng-model="participant.partName" ng-repeat="participant in participants">
<td>{{participant.partName}}</td>
<td>
<button ng-disabled="!callSessions[$index]" ng-click="mutePart(participant.partName);">Mute</button>
</td>
<td>
<button ng-click="dial(participant.partName, $index)">Dial</button>
</td>
</tr>
</table>
</body>
controller:
$scope.callSessions= {};
$scope.dial = function(name, index){
$scope.callSessions[index] = true;
}

Since ngRepeat will create its own child scope per each iterated item, you can set a variable in the view that will be limited to that scope:
<tr ng-repeat="participant in participants">
<td>{{participant.partName}}</td>
<td>
<button ng-disabled="!isDialing" ng-click="mutePart(participant.partName);">Mute</button>
</td>
<td>
<button ng-click="isDialing = true; dial(participant.partName)">Dial</button>
</td>
</tr>
Also, the ngModel on the tr is useless. Remove it. If you need more control over the variable (like to re-enable it when it's done calling, you should add a property to your model and toggle it):
{
partName: 'abc',
partId: '123',
isDialing: false //Added property, now toggle this
}

Related

AngularJS table stop sorting when in edit mode

I have AngularJS table with CRUD operations and sortable header. When I add the new row to table the lines are jumping and the table is getting sorted while in edit mode.
I want to stop sorting while in the edit mode and should sort only after saving the new row. I searched online for fixing this issue but nothing helped yet.
Here is the HTML file:
<thead>
<tr>
<td><input type="text" ng-model="main.search.Data1" id="myInput" placeholder="search for Data1..."/></td>
<td><input type="text" ng-model="main.search.Data2" id="myInput" placeholder="search for Data2..."/></td>
</tr>
<tr class="table_header" style="background-color: blue;">
<th><a href="#" ng-click="orderByField='data1'; reverseSort = !reverseSort"> Data1 <span ng-show ="!reverseSort">^</span><span ng-show="reverseSort">v</span></th>
<th><a href="#" ng-click="orderByField='data2'; reverseSort = !reverseSort"> Data2</th>
</tr>
</thead>
<tbody>
<tr ng-repeat=" code in main.Table | orderBy: Predicate | orderByField:reverseSort | filter:main.search"></tr>
<script type="text/ng-template" id="dispay">
<td>{{code.data1}}</td>
<td>{{code.data2}}</td>
</script>
<script type="text/ng-template" id="edit">
<td><input type="text" ng-model="code.data1" class"form-control input-sm"/></td>
<td><input type="text" ng-model="code.data2" class"form-control input-sm"/></td>
</script>
</tbody>
Here is the JS code:
//add new row
$scope.addNew = function(data) {
$scope.Table.unshift({
data1: "",
data2: ""
});
console.log($scope.table);
};
//Edit the row
$scope.edit = function(data){
$scope.selected = angular.copy(data);
$scope.backuplist = angular.copy($scope.table);
};
The behaviour is correct because on addNew you add 1 empty record in apply cycle which then will reorder again the list.
You have 2 ways to go :
1) When Adding new Item, create sperate object and upon submit add it in the list:
$scope.addNew = function(data) {
$scope.newItem ={
data1: "",
data2: ""
};
};
$scope.save = function() {
$scope.table.push($scope.newItem);
};
Like this there is speration of concerns and not to mingle the main list.
Or if you still want to add it in main list directly which i dont recommend you can implement your custom filter which keeps always the empty data at the top - In your predicate Method.
<tr class="table_header" style="background-color: blue;">
<th><a href="#" ng-click="orderByField='data1'; reverseSort = !reverseSort" ng-disabled="setTrueFalse"> Data1 <span ng-show ="!reverseSort">^</span><span ng-show="reverseSort">v</span></th>
<th><a href="#" ng-click="orderByField='data2'; reverseSort = !reverseSort" ng-disabled="setTrueFalse"> Data2</th>
</tr>
$scope.setTrueFalse = true/false
MAke use of ng-disabled.. Set it to true when you do not want to sort the values and vice versa

How to send data from a table generated with a form inside a ng-repeat

I have a table generated with a ng-repeat directive.
Each cell can be editable and each row has a submit button.
The submit button must send only the data of the affected row to the controller instead of sending the complete table. Then the controller will send it to a database. So if my table is huge and has a lot of rows, I prefer to just send one row to the database instead of the complete table.
Most of the time I use <form name="myForm" ng-submit="sendMyData()"> to send data from the view to the controller but in this case I have multiple forms (one per each row).
My problem is that I have no idea how to identify each row generated by the ng-repeat.
I am using AngularJS Material.
You don't need forms to do this. I'll demonstrate how to achieve this using sample data:
Controller:
app.controller("MyController", function($scope) {
$scope.persons = [
{ id: 1, name: "Bob" },
{ id: 2, name: "Alice" }
];
$scope.submitPerson = function(person) {
// do something to person - send to backend etc...
};
});
View:
<div ng-controller="MyController">
<table>
<tr ng-repeat="person in persons">
<td>{{person.name}}</td>
<td><button ng-click="submitPerson(person)">Submit</button></td>
</tr>
</table>
</div>
By clicking the submit button within each row - the individual person object will be passed to the submitPerson function in your controller where you can send it to the backend or do anything else.
You can try something like below just to submit one row at a time and also change in any number of rows and tick box which rows to be updated at once by clicking Submit ALL button.
var app = angular.module('app',[]);
app.controller('noduesaccountsmodalcontroller',function($scope){
$scope.nodueaccountassets = [{'name':'x'},{'name':'a'},
{'name':'b'},{'name':'c'},{'name':'d'}];
$scope.init= function(){
};
$scope.selectedItems =[];
$scope.rowSubmit = function(row){
$scope.submittedRow = row;
};
$scope.submit = function(acc){
angular.forEach($scope.nodueaccountassets,function(emp){
if(emp.selected){
$scope.selectedItems.push(emp.name);
}
});
};
});
<script data-require="jquery#*" data-semver="3.0.0" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.0.0/jquery.js"></script>
<script data-require="angularjs#1.5.8" data-semver="1.5.8" src="https://opensource.keycdn.com/angularjs/1.5.8/angular.min.js"></script>
<body ng-app="app" ng-controller="noduesaccountsmodalcontroller" ng-init="init()">
<table class="table">
<thead>
<tr>
<th>item</th>
<th>received</th>
</tr>
</thead>
<tbody ng-repeat="emp in nodueaccountassets track by $index">
<tr>
<td><input type="text" ng-model="emp.name"/></td>
<td>
<input type="checkbox" ng-model="emp.selected" value="{{emp.name}}" />
</td>
<td> <button type="button" value="submit" ng-click="rowSubmit(emp)">Submit</button></td>
</tr>
</tbody>
</table>
{{selectedItems}}
Submitted row --- {{submittedRow}}
<button type="button" ng-click="submit()" value="submit">Submit ALL</button>
</body>

Angular loop through table row and check for checked checbox

I have a table that has a list from database with checkbox on each row, checkbox will used for ex. during deletion of the record.
So what i am trying to achieve is that when i clicked the delete button, angular will loop each row in table and check the checkbox whether is checked, if yes the please proceed to delete. Dont have any idea how to do this. Someone please give some related example.
Here is my code
index.html
<button class="ui red labeled icon button right floated" type="button" data-content="Delete selected item(s)" id="delete" ng-click="deleteSeleted()"><i class="trash icon"></i>Delete</button>
<div class='container-table'>
<table class="ui fixed single line celled table striped sortable compact" style="width:2000px" id="mytable">
<thead>
<tr>
<th class="width-checkbox"><input type="checkbox" ng-model="matin.selectedAll" /></th>
<th class="width-120">Item</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="x in data">
<td><input type="checkbox" ng-checked="matin.selectedAll"></td>
<td>{{x.item}}</td>
</tr>
</tbody>
</table>
</div>
<tr ng-repeat="x in data">
<td><input type="checkbox" ng-model="x.selected"></td>
<td>{{x.item}}</td>
</tr>
Angular Js Code
for (var k = 0; k < $scope.data.length; k++)
{
if($scope.data[k].selected==true)
{
//Perform your desired thing over here
var val=$scope.data[k].item //to getData
}
}
Please find the fiddler link which i have created to select all the items in the table and on delete print which ever is checked https://jsfiddle.net/dfL1L944/3/
var appModule = angular.module('Module', []);
appModule.controller("DataController", function($scope) {
$scope.data = [{"name":"Alex"},{"name":"Juni"}]
$scope.deleteAll = false;
$scope.deleteSeleted = function(){
$scope.data.forEach(function(x) {
console.log(x.name);
});
}
$scope.selectedAll = function(){
$scope.data.forEach(function(x) {
if($scope.deleteAll){
x.deleted = true;
}
else{
x.deleted = false;
}
});
}
});
HTML Code
<div ng-app="Module"> <div ng-controller="DataController">
<button class="ui red labeled icon button right floated" type="button" data-content="Delete selected item(s)" id="delete" ng-click="deleteSeleted()"> <i class="trash icon"></i>Delete</button> <div class='container-table'> <table class="ui fixed single line celled table striped sortable compact" style="width:200px" id="mytable"> <thead>
<tr>
<th width="20px">
<input type="checkbox" ng-model="deleteAll" ng-click="selectedAll()" /></th>
<th>Item</th>
</tr> </thead> <tbody>
<tr ng-repeat="x in data">
<td width="2px"><input type="checkbox" ng-checked="x.deleted"></td>
<td>{{x.name}}</td>
</tr> </tbody> </table> </div>
</div> </div>
You could use $filter (you would need to insert $filter as a dependency)
$scope.data: [ // assuming your model looks like this
{
Id: "my_id",
Name: "my_name",
checked: true
}
];
var myFilteredValues = $filter('filter')($scope.data, { $: true });
And in your HTML
<tr ng-repeat="x in data">
<td><input type="checkbox" ng-model="x.checked"></td>
<td>{{x.Name}}</td>
</tr>
You can add a .toDelete property to every x in your data array, for example, and bind the checkboxes like this:
<input type="checkbox" ng-model="x.toDelete">
Afterwards you can create a button under the table:
<input type="button" ng-click="deleteRows();" value="Delete rows">
...And then create a function on your controller's scope (a newbie-friendly function):
$scope.deleteRows = function(){
var i=0;
for(i=0; i<data.length; i++){
if(data[i].toDelete){
//send your server requests here and do
//your stuff with the element if needed
data.splice(i, 1); //remove the element from the array
i--; //decrement the value of i so it stays the same
//(array is now shorter than it used to be)
}
}
}
You can also keep the information on what row is to be deleted in a separate array on the same scope but this solution seems simpler to me.
Regarding the "Check All" checkbox at the top, you can create a function and bind it with ng-click to a button or any other element and use that function to simply iterate through all the elements and set the .toDelete property to true for each one of them.

How to apply css class to selected row in ng-repeat

I have a ng-repeate table. I need to toggleClass for each selected row. Here is my code:
<tr ng-repeat="expenses in Expensereports" ng-mouseenter='showpencil=true' ng-mouseleave='showpencil=false' ng-class="{'selectedrow':selectDelete}">
<td class="text-center">
<input type="checkbox" ng-model='expenses.isDelete' class='deletebox' ng-change='selectedDeleteRow(expenses.isDelete)'/>
</td>
<td class="text-center">{{expenses.date | parseDateFormat | date}}</td>
<td class="text-center">{{expenses.type}}</td>
</tr>
My JS Code:
$scope.selectedDeleteRow = function(selected){
if(selected==true){
$scope.selectDelete=true;
}else{
$scope.selectDelete=false;
}
}
What I want is that if user check the checkbox, I need to hightlight the whole row. but leave other unchecked row alone, simply says is let user know this row is selected, if they uncheck that row, the class will be gone.
ng-class="{'selectedrow': expenses.isDelete}" should work.
var app = angular.module('myApp', []);
app.controller('test', function($scope) {
$scope.Expensereports = [
{'test': 'Row 1'},
{'test': 'Row 2'},
{'test': 'Row 3'}
];
});
tr.selectedrow {
background-color: red;
}
<div ng-app="myApp">
<table ng-controller="test">
<tr ng-repeat="expenses in Expensereports" ng-class="{'selectedrow': expenses.isDelete}">
<td>
<input type="checkbox" ng-model="expenses.isDelete" ng-change="selectedDeleteRow(expenses.isDelete)"/>
</td>
<td class="text-center">{{expenses.test}}</td>
</tr>
</table>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
In Angular you can use [ngClass]:
<tr *ngFor="let expenses in Expensereports" [ngClass]="{'selectedrow': expenses.isDelete}">
...
</tr>

Click Table Row to Trigger a Checkbox Click in Angularjs

I have a simple table in an Angularjs app that contains a checkbox in each row.
<table>
<tr ng-repeat="obj in objList">
<td>
<input type="checkbox" ng-model="selectedObjs" value="{{obj}}"
ng-checked="obj.selected"
ng-click="toggleObjSelection(obj.description)">
{{obj.description}}
</input>
</td>
</tr>
</table>
Is there a way in Angularjs to allow the user to click any where within the row to trigger the checkbox click once?
If the user clicks in the checkbox, we don't want to trigger the click so that it appears that the checkbox click was triggered twice.
This article (http://www.learningjquery.com/2008/12/quick-tip-click-table-row-to-trigger-a-checkbox-click/) describes how to do this in jQuery, but is there a way to do this using Angularjs style?
You're pretty close you just need to stopPropagation on the $event object:
<table ng-controller="ctrl">
<tr ng-click="rowClicked(obj)" ng-repeat="obj in objList">
<td>
<input type="checkbox" ng-model="selectedObjs" value="{{obj}}"
ng-checked="obj.selected"
ng-click="toggleObjSelection($event, obj.description)">
{{obj.description}}
</input>
</td>
</tr>
</table>
And the JS:
angular.module('myApp', [])
.controller('ctrl', function($scope) {
$scope.objList = [{
description: 'a'
},{
description: 'b'
},{
description: 'c'
},{
description: 'd'
}];
$scope.toggleObjSelection = function($event, description) {
$event.stopPropagation();
console.log('checkbox clicked');
}
$scope.rowClicked = function(obj) {
console.log('row clicked');
obj.selected = !obj.selected;
};
});
http://jsfiddle.net/Ljwv0toh/7/
Related question: AngularJS ng-click stopPropagation

Resources