This question already has answers here:
Adding multiple class using ng-class
(12 answers)
Closed 6 years ago.
suppose i am showing product information. i want if price less than 50 then item color should be red. if price more than 50 then item color should be yellow and if price more than (50+(50*60/100)) then item color should be green. now tell me how could i achieve it best way. guide me with best approach to complete it.
this way i tried but i came to know there will be more iteration due to dirty check when work with ng-repeat. see my code and tell me how could i put multiple condition in ng-class to set class dynamically.
<div ng-app="myApp">
<ul ng-controller="MyController">
<li ng-class="setColor(item.price)" ng-repeat="item in products">{{item.name}} — {{item.price}}</li>
</ul>
</div>
var myApp = angular.module('myApp', []);
myApp.controller('MyController', function MyController($scope) {
$scope.setColor = function(price) {
alert(price);
}
$scope.products = [
{
'name' : 'Xbox',
'clearance' : true,
'price' : 30.99,
},
{
'name' : 'Xbox 360',
'clearance' : false,
'salesStatus' : 'old',
'price' : 99.99,
},
{
'name' : 'Xbox One',
'salesStatus' : 'new',
'price' : 50,
},
{
'name' : 'PS2',
'clearance' : true,
'price' : 79.99,
},
{
'name' : 'PS3',
'salesStatus' : 'old',
'price' : 99.99,
},
{
'name' : 'PS4',
'salesStatus' : 'new',
'price' : 20.99,
}
]
})
tell me without calling function from ng-class how could i place multiple if else condition in ng-class?
if price > 50
return "css-class-yello"
else if price < 50
return "css-class-red"
else if price > (50+(50*60/100))
return "css-class-green"
if possible please guide me with code. thanks
try like this.
var app = angular.module("app",[]);
app.controller("ctrl" , function($scope){
$scope.products = [{
'name': 'Xbox',
'clearance': true,
'price': 30.99,
}, {
'name': 'Xbox 360',
'clearance': false,
'salesStatus': 'old',
'price': 99.99,
}, {
'name': 'Xbox One',
'salesStatus': 'new',
'price': 50,
}, {
'name': 'PS2',
'clearance': true,
'price': 79.99,
}, {
'name': 'PS3',
'salesStatus': 'old',
'price': 99.99,
}, {
'name': 'PS4',
'salesStatus': 'new',
'price': 20.99,
}];
});
.css-class-yellow{
background-color: yellow;
}
.css-class-red{
background-color: red;
}
.css-class-green{
background-color: green;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="ctrl" class="panel-group" id="accordion">
<ul class="nav nav-pills" ng-init="catVal = 1">
<li ng-repeat="item in products" ng-class="{'css-class-yellow' : item.price > 50,'css-class-red' : item.price <50, 'css-class-green' : item.price > 50+50*60/100}">
{{item.name}}
</li>
</ul>
</div>
You could set ng-class to call a function in your controller and pass the object.
Example: https://jsfiddle.net/5hgLshhz/
<ul>
<li ng-repeat="p in ctrl.products" ng-class="ctrl.setClass(p)">{{p.name}}</li>
</ul>
function Controller() {
var vm = this;
vm.products = [{
'name': 'Xbox',
'clearance': true,
'price': 30.99,
}, {
'name': 'Xbox 360',
'clearance': false,
'salesStatus': 'old',
'price': 99.99,
}, {
'name': 'Xbox One',
'salesStatus': 'new',
'price': 50,
}, {
'name': 'PS2',
'clearance': true,
'price': 79.99,
}, {
'name': 'PS3',
'salesStatus': 'old',
'price': 99.99,
}, {
'name': 'PS4',
'salesStatus': 'new',
'price': 20.99,
}];
vm.setClass = setClass;
function setClass(p) {
if (p.price > 50) {
return 'css-class-yellow';
}
if (p.price < 50) {
return 'css-class-red';
}
if (p.price > (50 + (50 * 60 / 100))) {
return 'css-class-green';
}
}
}
There are several different ways to use ng-classthe way I most commonly use this directive is by setting your css class to a boolean $scope variable... something like:
HTML:
ng-class="{your-css-class:$scope.myVariable}"
Angular controller:
//to add class
$scope.myVariable = true
//to remove class
$scope.myVariable = false
To use multiple classes simply seperate them by commas something like:
ng-class="{your-css-class:$scope.myVariable, my-other-class:$scope.myOtherVariable}"
fiddle here
Related
I am learning Angularjs and Dragular.
I have a data set, and on drop I have to insert the data into another container's data set value. For example:
This is the data set
$scope.items1 = [
{
'name' : 'x',
'age' : '4'
},
{
'name' : 'y',
'age' : '5'
},
{
'name' : 'z',
'age' : '6'
}
];
And I want to drop each element of items1 into items2 values. items2 looks like:
$scope.items2 = [
{
'key' : 'aaa',
'value' :""
},
{
'key' : 'bbb',
'value' : ""
},
{
'key' : 'ccc',
'value' : ""
},
{
'key' : 'ddd',
'value' : ""
}
];
Once it's dropped, items2 should look like:
{
name:'aaa',
value: [{
'key' : 'aaa',
'value' :""
}]
}
for each one. How do I do this?
Here is on of possible solutions:
angular.module('myApp', ['dragularModule']).controller('MyCtrl', function(dragularService, $element, $scope, $timeout) {
$scope.items1 = [{
name: 'x',
age: '4'
}, {
name: 'y',
age: '5'
}, {
name: 'z',
age: '6'
}];
$scope.items2 = [
{
'key': 'info',
'value': []
}, {
'key': 'info',
'value': []
}, {
'key': 'info',
'value': []
},
];
// timeout due to document not ready, jsfiddle settings issue?
$timeout(function() {
dragularService('#items1');
dragularService('.items2');
});
});
div {
border: 1px solid blue;
min-width: 200px;
padding: 10px
}
.can-be-empty {
min-height: 10px;
min-width: 200px;
}
<link href="https://rawgit.com/luckylooke/dragular/master/dist/dragular.css" rel="stylesheet" />
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<script src="https://rawgit.com/luckylooke/dragular/master/dist/dragular.js"></script>
<div class='app' ng-app="myApp" ng-controller="MyCtrl">
<h2>items1</h2>
<div id="items1" class="can-be-empty">
<div ng-repeat="item in items1">item {{item.name + ' age:' + item.age}}</div>
</div>
<h2>items2</h2>
<div ng-repeat="container in items2" class="items2">
<div class="can-be-empty" ng-repeat="item in container.value">
<div>item {{item.name + ' age:' + item.age}}</div>
</div>
</div>
</div>
Link to codepen: https://codepen.io/luckylooke/pen/LyoWzR
I have a function in controller in which I am calling it from ng-class directive. My code is working but I am not getting right output. Something is wrong but I am not being able to capture it because I am new in AngularJS. So anyone please have a look at my code and tell me what mistake I made and if possible discuss with rectified code.
My code
<div ng-app="myApp">
<ul ng-controller="MyController">
<li ng-class="setColor(item.businessTime,item.name)" ng-repeat="item in products">{{item.name}} — {{item.price}} — {{clsName}} — {{diff}}</li>
</ul>
</div>
var myApp = angular.module('myApp', []);
myApp.controller('MyController', function MyController($scope) {
$scope.dbTime='02/09/2013 15:00:00';
$scope.diff='';
$scope.clsName='';
$scope.setColor = function(businessTime,name) {
//alert('businessTime '+businessTime);
//alert('dbtime '+$scope.dbTime);
//var diff =$scope.dbTime.diff(businessTime, 'minutes')
//alert(diff);
var _diff=0;
var ms = moment($scope.dbTime,"DD/MM/YYYY HH:mm:ss").diff(moment(businessTime,"DD/MM/YYYY HH:mm:ss"));
var d = moment.duration(ms);
//alert(d.asMinutes());
_diff=Math.round(d.asMinutes());
if(_diff.between(-2000, -6000))
{
//alert(name+' clsRed '+_diff);
$scope.diff=Math.round(d.asMinutes());
$scope.clsName="clsRed";
return "clsRed";
}
else if(_diff.between(-6001, -8000))
{
//alert(name+' clsGreen '+diff);
$scope.diff=Math.round(d.asMinutes());
$scope.clsName="clsYello";
return "clsYello";
}
else if(_diff.between(1000, 2000))
{
//alert(name+' clsYello '+_diff);
$scope.diff=Math.round(d.asMinutes());
$scope.clsName="clsGreen";
return "clsGreen";
}
}
$scope.products = [
{
'name' : 'Xbox',
'clearance' : true,
'price' : 30.99,
'businessTime':'05/09/2013 15:00:00'
},
{
'name' : 'Xbox 360',
'clearance' : false,
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':'04/09/2013 14:20:00'
},
{
'name' : 'Xbox One',
'salesStatus' : 'new',
'price' : 50,
'businessTime':'06/09/2013 18:12:10'
},
{
'name' : 'PS2',
'clearance' : true,
'price' : 79.99,
'businessTime':'07/09/2013 19:22:00'
},
{
'name' : 'PS3',
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':'01/09/2013 09:00:00'
},
{
'name' : 'PS4',
'salesStatus' : 'new',
'price' : 20.99,
'businessTime':'10/09/2013 07:00:00'
}
]
})
Number.prototype.between = function(a, b) {
var min = Math.min.apply(Math, [a, b]),
max = Math.max.apply(Math, [a, b]);
return this > min && this < max;
};
css
.clsRed {
font-weight: bold;
color: red;
}
.clsYello {
font-weight: bold;
color: yellow;
}
.clsGreen {
font-weight: bold;
color: green;
}
within if else logic i am setting class name $scope.clsName="clsYello"; but in output i have notice some time wrong class name in showing in html.
here is screen shot
now see the first data where class name is showing clsGreen but in output clsRed is applied. right output would be clsRed and also clsRed should be applied. clsRed has applied but clsGreen is showing as class name in output which is not right.
so please guide me where i made the mistake. please guide me with rectified code.
js fiddle https://jsfiddle.net/tridip/czjo9f1m/8/
thanks
see this. if you use $scope.diff as array probably you find out what is your problem.
var myApp = angular.module('myApp', []);
myApp.controller('MyController', function MyController($scope) {
$scope.dbTime='02/09/2013 15:00:00';
$scope.diff=[];
$scope.clsName=[];
$scope.setColor = function(businessTime,name) {
var _diff=0;
var ms = moment($scope.dbTime,"DD/MM/YYYY HH:mm:ss").diff(moment(businessTime,"DD/MM/YYYY HH:mm:ss"));
var d = moment.duration(ms);
_diff=Math.round(d.asMinutes());
if(_diff.between(-2000, -6000))
{
$scope.diff.push(Math.round(d.asMinutes()));
$scope.clsName.push("clsRed");
console.log($scope.diff);
return "clsRed";
}
else if(_diff.between(-6001, -8000))
{
$scope.diff.push(Math.round(d.asMinutes()));
$scope.clsName.push("clsYello");
console.log($scope.diff);
return "clsYello";
}
else if(_diff.between(1000, 2000))
{
$scope.diff.push(Math.round(d.asMinutes()));
$scope.clsName.push("clsGreen");
console.log($scope.diff);
return "clsGreen";
}
}
$scope.products = [
{
'name' : 'Xbox',
'clearance' : true,
'price' : 30.99,
'businessTime':'05/09/2013 15:00:00'
},
{
'name' : 'Xbox 360',
'clearance' : false,
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':'04/09/2013 14:20:00'
},
{
'name' : 'Xbox One',
'salesStatus' : 'new',
'price' : 50,
'businessTime':'06/09/2013 18:12:10'
},
{
'name' : 'PS2',
'clearance' : true,
'price' : 79.99,
'businessTime':'07/09/2013 19:22:00'
},
{
'name' : 'PS3',
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':'01/09/2013 09:00:00'
}
];
})
Number.prototype.between = function(a, b) {
var min = Math.min.apply(Math, [a, b]),
max = Math.max.apply(Math, [a, b]);
return this > min && this < max;
};
.clsRed {
font-weight: bold;
color: red;
}
.clsYello {
font-weight: bold;
color: yellow;
}
.clsGreen {
font-weight: bold;
color: green;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.12.0/moment.js"></script>
<div ng-app="myApp">
<ul ng-controller="MyController">
<li ng-repeat="item in products track by $index"><span ng-class="setColor(item.businessTime,item.name)">{{$index}} — {{item.price}} — {{clsName[$index]}} — {{diff[$index]}}</span></li>
</ul>
</div>
i think that this is better solution.
var myApp = angular.module('myApp', []);
myApp.controller('MyController', function MyController($scope) {
$scope.dbTime='02/09/2013 15:00:00';
$scope.diff=[];
$scope.clsName=[];
$scope.products = [
{
'name' : 'Xbox',
'clearance' : true,
'price' : 30.99,
'businessTime':'05/09/2013 15:00:00'
},
{
'name' : 'Xbox 360',
'clearance' : false,
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':'04/09/2013 14:20:00'
},
{
'name' : 'Xbox One',
'salesStatus' : 'new',
'price' : 50,
'businessTime':'06/09/2013 18:12:10'
},
{
'name' : 'PS2',
'clearance' : true,
'price' : 79.99,
'businessTime':'07/09/2013 19:22:00'
},
{
'name' : 'PS3',
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':'01/09/2013 09:00:00'
},
{
'name' : 'PS4',
'salesStatus' : 'new',
'price' : 20.99,
'businessTime':'10/09/2013 07:00:00'
}
];
angular.forEach( $scope.products,function(product,i){
var _diff=0;
var ms = moment($scope.dbTime,"DD/MM/YYYY HH:mm:ss").diff(moment(product.businessTime,"DD/MM/YYYY HH:mm:ss"));
var d = moment.duration(ms);
_diff=Math.round(d.asMinutes());
$scope.products[i].diff = _diff;
});
console.log($scope.products);
})
.clsRed {
font-weight: bold;
color: red;
}
.clsYello {
font-weight: bold;
color: yellow;
}
.clsGreen {
font-weight: bold;
color: green;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.12.0/moment.js"></script>
<div ng-app="myApp">
<ul ng-controller="MyController">
<li ng-repeat="item in products track by $index">
<span ng-class="{'clsYello':-6000>item.diff,'clsRed':-2000>item.diff,'clsGreen':item.diff > 1000}">{{$index}} — {{item.price}} — {{clsName[$index]}} — {{item.diff}}</span></li>
</ul>
</div>
i am comparing time time and based on that i am setting css class name but i made some mistake and that is why code is not working. please anyone see my code and tell me where i made the mistake.
<div ng-app="app" ng-controller="ctrl" class="panel-group" id="accordion">
<ul class="nav nav-pills" ng-init="catVal = 1">
<li ng-repeat="item in products" ng-class="{'css-class-yellow' : moment($scope.dbTime, 'HH:mm:ss').diff(moment(item.businessTime, 'HH:mm:ss'), 'minutes') > 60,'css-class-red' : moment($scope.dbTime, 'HH:mm:ss').diff(moment(item.businessTime, 'HH:mm:ss'), 'minutes') > 200, 'css-class-green' : moment($scope.dbTime, 'HH:mm:ss').diff(moment(item.businessTime, 'HH:mm:ss'), 'minutes') > 300 }">
{{item.name}}
</li>
</ul>
</div>
var app = angular.module("app",[]);
app.controller("ctrl" , function($scope){
$scope.dbTime='12:05:05';
$scope.products = [{
'name': 'Xbox',
'clearance': true,
'price': 30.99,
'businessTime':'04:15:22'
}, {
'name': 'Xbox 360',
'clearance': false,
'salesStatus': 'old',
'price': 99.99,
'businessTime':'12:10:22'
}, {
'name': 'Xbox One',
'salesStatus': 'new',
'price': 50,
'businessTime':'06:25:22'
}, {
'name': 'PS2',
'clearance': true,
'price': 79.99,
'businessTime':'08:11:22'
}, {
'name': 'PS3',
'salesStatus': 'old',
'price': 99.99,
'businessTime':'17:41:22'
}, {
'name': 'PS4',
'salesStatus': 'new',
'price': 20.99,
'businessTime':'21:05:22'
}];
});
.css-class-yellow{
background-color: yellow;
}
.css-class-red{
background-color: red;
}
.css-class-green{
background-color: green;
}
I would propose to move such a complex comparison back to controller:
//template
<li ng-repeat="item in products" ng-class="{'css-class-yellow' : isYellowLess() }">
//controller
$scope.isYellowLess = function(){
return moment($scope.dbTime, 'HH:mm:ss').diff(moment(item.businessTime, 'HH:mm:ss'), 'minutes') > 60;
}
Then you can debug it easier.
UPD
Check the updated fiddle: https://jsfiddle.net/4jz8uh2y/3/
The problem was that you need to do the moment parsing in the controller, not in the template. Since you use plain version of momentjs (not angular-moment), your controller knows nothing about the momentjs functions hence could not evaluate the time comparison properly.
i am new in angular. so i am tying to set class dynamically from my controller class. my program is working but right class is not getting attached. i am not being able to capture where is the problem in code. please see my code and js fiddle and tell me where is the problem for which right class is not getting attached with html element.
<div ng-app="myApp">
<ul ng-controller="MyController">
<li ng-class="setColor(item.businessTime,item.name)" ng-repeat="item in products">{{item.name}} — {{item.price}} — {{clsName}} — {{diff}}</li>
</ul>
</div>
the problem list in setColor() function
var myApp = angular.module('myApp', []);
myApp.controller('MyController', function MyController($scope) {
$scope.dbTime=moment('12:05:05','HH:mm:ss');
$scope.diff='';
$scope.clsName='';
$scope.setColor = function(businessTime,name) {
//alert('businessTime '+businessTime);
//alert('dbtime '+$scope.dbTime);
var diff =$scope.dbTime.diff(businessTime, 'minutes')
//alert(diff);
$scope.diff=diff;
if(diff < 60)
{
alert(name+' clsRed '+diff);
$scope.clsName="clsRed";
return "clsRed";
}
else if(diff > 60 )
{
alert(name+' clsYello '+diff);
$scope.clsName="clsYello";
return "clsYello";
}
else if(diff > 200)
{
alert(name+' clsGreen '+diff);
$scope.clsName="clsGreen";
return "clsGreen";
}
}
$scope.products = [
{
'name' : 'Xbox',
'clearance' : true,
'price' : 30.99,
'businessTime':moment('06:05:05','HH:mm:ss')
},
{
'name' : 'Xbox 360',
'clearance' : false,
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':moment('04:15:22','HH:mm:ss')
},
{
'name' : 'Xbox One',
'salesStatus' : 'new',
'price' : 50,
'businessTime':moment('12:10:22','HH:mm:ss')
},
{
'name' : 'PS2',
'clearance' : true,
'price' : 79.99,
'businessTime':moment('06:25:22','HH:mm:ss')
},
{
'name' : 'PS3',
'salesStatus' : 'old',
'price' : 99.99,
'businessTime':moment('08:11:22','HH:mm:ss')
},
{
'name' : 'PS4',
'salesStatus' : 'new',
'price' : 20.99,
'businessTime':moment('19:41:22','HH:mm:ss')
}
]
})
js fiddle https://jsfiddle.net/tridip/czjo9f1m/1/
please help me to capture the problem. alert is showing setcolor function return right class name but different class is getting attached with html element.......why? thanks
i am using select2 multi select dropdown, and it works perfectly but my problem is, i want to categorise the drop down list of the same. Here is my code
<script src="/static/select2.js"></script>
<input type="hidden" id="test" value=""/>
and js
$(test).select2({
data:data,
multiple: true,
width: "100%",
placeholder:"None Selected",
closeOnSelect:false,
});
This should work:
$(test).select2({
data:
[
{
text: 'GREETINGS',
children:
[
{ 'id': 1, text: 'hai' },
{ 'id': 2, text: 'hellow'},
]
},
{
text: 'QUESTIONS',
children:
[
{ 'id': 3, 'text': 'yes' },
{ 'id': 4, 'text': 'no' }
]
}
],
multiple: true,
width: "100%",
placeholder: "None Selected",
closeOnSelect: false,
});