Using service and ng-class on checkboxes click - javascript

var app = angular.module('myApp', []);
app.controller('checkCtrl', ['$scope','sharedService', function($scope, sharedService) {
$scope.isCutScore = function() {
if($scope.cc) {
alert('Checked');
$scope.val = true;
} else {
alert('Unchecked');
}
};
}]);
app.controller('divCtrl', ['$scope', 'sharedService', function($scope, sharedService) {
$scope.addClass = function() {
if(flag == true) {
return EL;
} else {
return EP;
}
};
}]);
app.service('sharedService', function() {
var flag = false;
if(angular.element('#cutScoreCheck').is(':checked')) {
flag = true;
} else {
flag = false;
}
});
Add and remove class to a div using ng-class on click of checkbox. But challenge is checkbox and div to which we need to apply and remove class are in different controllers. And compulsion here is to use a service which is shared by both the controllers.
In the following example if we check the checkbox, 'EL' class should be applied and if we uncheck the box, this class will be removed and 'EP' should be applied.
Code

you can use this. Works here.
I have added function to service, it will be called when user check the checkbox and I used $rootScope to reach AddClass method in different controller.
your body html
<body ng-app="myApp">
<div class="row">
<div class="col-sm-4 checkDiv" ng-controller="checkCtrl">
<input type="checkbox" id="cutScoreCheck" ng-model="cc" ng-change="checkDiv()"/>
</div>
</div>
<div class="row">
<div class="col-sm-4 container" ng-controller="divCtrl" ng-class="flag ? 'EL' : 'EP'">500</div>
</div>
<script src="CtrlCheck.js"></script>
</body>
Js part:
var app = angular.module('myApp', []);
app.controller('checkCtrl', ['$scope','sharedService', '$rootScope',function($scope, sharedService,$rootScope) {
$scope.checkDiv = function(){
var flag = sharedService.CheckDiv($scope.cc);
$rootScope.addClass(flag);
}
}]);
app.controller('divCtrl', ['$scope', 'sharedService', '$rootScope',function($scope, sharedService,$rootScope,$apply) {
$scope.flag = false;
$rootScope.addClass = function(flag) {
if(flag == 'true') {
$scope.divClass = "EL";
} else {
$scope.divClass = "EP";
}
console.log(flag)
$scope.flag = flag;
};
}]);
app.service('sharedService', function() {
var flag = false;
this.CheckDiv = function (isChecked) {
if(isChecked) {
flag = true;
} else {
flag = false;
}
return flag;
}
});

Related

How to use $document in a Modal

I am having trouble using $document in the modals controller. Is there a correct way of passing it in? I cant use just document as our angular project rules do not allow it
Calling the modal
var modalInstance = $uibModal.open({
templateUrl: "errorsModal.html",
controller: ["$uibModalInstance", "data","vm", modalController],
controllerAs: "vm",
size:"md",
resolve: {
data: function () {
return referenceDataService.getErrors().$loaded();
},
vm: function (){
return vm;
}
}
});
}
Modals Function I am trying to use $document in
function isTrueOrFalse(elementId,tickBoxElement,newData){
console.log(vm.check);
var checkBox = $document.getElementById(tickBoxElement);
checkBox.checked = !checkBox.checked;
updateErrors(newData,parentVm,true);
if(checkBox.checked === true){
checkBox.checked = false;
updateErrors(newData,parentVm,true);
}
else if(checkBox.checked ===false){
checkBox.checked = true;
updateErrors(newData,parentVm,false);
}
else{
checkBox.checked = true;
}
}
I have found my own workaround using angular.element("elementId")

angularjs show with animation on true and hide after delay

<div ng-show="IsError">ERROR !!</div>
<button ng-click="validate()">Validate</button>
function MainController($scope, ) {
$scope.IsError = false;
$scope.validate = function (val) {
$scope.IsError = true;
setTimeout(function () {
$scope.IsError = false;
}, 1500);
}
}
On validate() div show but not hide.
How show div hide after 1.5 sec with angular (no DOM manipulate)?
How animate show and hide with transparent?
You can use $timeout service like below:
var app = angular.module('myApp', []);
app.controller('myCtrl', function($scope,$timeout) {
$scope.IsError = false;
$scope.validate = function (val) {
$scope.IsError = true;
$timeout(function () {
$scope.IsError = false;
}, 1500);
}
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="myApp" ng-controller="myCtrl">
<div ng-show="IsError">ERROR !!</div>
<button ng-click="validate()">Validate</button>
</div>

AngularJs Counter to count up to a specific target number

I am trying to create a counter using Angularjs which should count up to a number which is already present in that division. Here is my html snippet.
<div class="circle-home">
<span class="circle-home-score " id="counterofreviews" data-count="{{noReviews}}">{{noReviews}}</span> REVIEWS
</div>
Now when I am trying to get the value inside the span I get it as {{noReviews}} instead of its value.
Here is my AngularJs code.
var demoApp = angular.module(['demoApp','ngRoute','ui.bootstrap']);
demoApp.controller('SearchController',function ($scope, $http, $facebook, $interval){
$scope.noReviews=100;
$scope.childOnLoad = function() {
$scope.uppercount=$("#counterofreviews").text();
$scope.no_Reviews=0;
console.log($scope.uppercount);
var stop;
stop = $interval(function() {
if ($scope.uppercount >$scope.no_Reviews) {
$scope.noReviews=$scope.no_Reviews;
$scope.no_Reviews++;
console.log('Inside if statement');
} else {
$scope.stopFight();
}
}, 100);
};
$scope.stopFight = function() {
if (angular.isDefined(stop)) {
$interval.cancel(stop);
stop = undefined;
}
};
$scope.childOnLoad();
};
Output of console.log($scope.uppercount) is {{noReviews}}. I am unable to figure out a proper way to do it. Please suggest the correction or any other better method for the same perpose.
Not sure why do you use jQuery to get the #counterofreviews value. Is the value there because it's added from a server side script?
As mentioned in the comments, your code is probably not working because jQuery.text() is returning a string. Using parseInt(text) could work.
Please have a look at the demo below and here at jsfiddle.
It's more Angular and should help you getting started with your counter.
var demoApp = angular.module('demoApp', []); //'ngRoute','ui.bootstrap']);
demoApp.controller('SearchController', function ($scope, $http, $interval) { //$facebook,
$scope.noReviews = 100;
//$scope.childOnLoad = function () {
this.upperCount = 10; //$("#counterofreviews").text();
console.log(this.upperCount);
var stop;
this.startCounter = function () { // needed for re-run on change
//console.log(stop, this);
this.no_Reviews = 0;
if ( angular.isUndefined(stop) )
stop = $interval(checkCount.bind(this), 100);
};
this.startCounter();
//};
function checkCount() {
if (this.upperCount >= this.no_Reviews) {
this.noReviews = this.no_Reviews;
this.no_Reviews++;
//console.log('Inside if statement');
} else {
stopFight();
}
}
function stopFight() {
if (angular.isDefined(stop)) {
$interval.cancel(stop);
stop = undefined;
}
};
//$scope.childOnLoad();
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="demoApp" class="circle-home" ng-controller="SearchController as ctrl">Review max.:
<input ng-model="ctrl.upperCount" ng-change="ctrl.startCounter()"/> <span class="circle-home-score " id="counterofreviews" data-count="{{ctrl.upperCount}}">{{ctrl.noReviews}}</span> REVIEWS</div>

button can not be clicked with ng-click

When I run this plunker I press the arrow-down of the dropdown and I assume that the dropdown list pop ups now but it does not
In my browser console I have no error.
Why can the dropdown not be clicked?
http://plnkr.co/edit/WHswYfce44W6WWZR1T7y?p=preview
var app = angular.module('plunker', []);
app.controller('MainCtrl', function($scope) {
var schoolclassCodeColors = [
{background:'blue'},
{background:'red'}
];
var newSubject = "test";
var newSchoolclass = "11";
var newSchoolclassIdentifier = "xb";
$scope.activeStep = {};
$scope.activeStep.schoolclassCodeColors = schoolclassCodeColors;
$scope.activeStep.schoolclassCodeColorsIsOpen = false;
$scope.activeStep.selectedSchoolclassCodeColor = $scope.activeStep.schoolclassCodeColors[0];
$scope.activeStep.schoolclassCode = function () {
return newSubject + newSchoolclass + newSchoolclassIdentifier;
};
$scope.activeStep.setSchoolclassCodeColor = function(color){
$scope.activeStep.selectedSchoolclassCodeColor = color;
this.schoolclassCodeColorsIsOpen = false;
};
});
app
.constant('dropdownConfig', {
openClass: 'open'
})
.service('dropdownService', ['$document', function($document) {
var openScope = null;
this.open = function( dropdownScope ) {
if ( !openScope ) {
$document.bind('click', closeDropdown);
$document.bind('keydown', escapeKeyBind);
}
if ( openScope && openScope !== dropdownScope ) {
openScope.isOpen = false;
}
openScope = dropdownScope;
};
this.close = function( dropdownScope ) {
if ( openScope === dropdownScope ) {
openScope = null;
$document.unbind('click', closeDropdown);
$document.unbind('keydown', escapeKeyBind);
}
};
var closeDropdown = function( evt ) {
// This method may still be called during the same mouse event that
// unbound this event handler. So check openScope before proceeding.
if (!openScope) { return; }
var toggleElement = openScope.getToggleElement();
if ( evt && toggleElement && toggleElement[0].contains(evt.target) ) {
return;
}
openScope.$apply(function() {
openScope.isOpen = false;
});
};
var escapeKeyBind = function( evt ) {
if ( evt.which === 27 ) {
openScope.focusToggleElement();
closeDropdown();
}
};
}])
.controller('DropdownController', ['$scope', '$attrs', '$parse', 'dropdownConfig', 'dropdownService', '$animate', function($scope, $attrs, $parse, dropdownConfig, dropdownService, $animate) {
var self = this,
scope = $scope.$new(), // create a child scope so we are not polluting original one
openClass = dropdownConfig.openClass,
getIsOpen,
setIsOpen = angular.noop,
toggleInvoker = $attrs.onToggle ? $parse($attrs.onToggle) : angular.noop;
this.init = function( element ) {
self.$element = element;
if ( $attrs.isOpen ) {
getIsOpen = $parse($attrs.isOpen);
setIsOpen = getIsOpen.assign;
$scope.$watch(getIsOpen, function(value) {
scope.isOpen = !!value;
});
}
};
this.toggle = function( open ) {
return scope.isOpen = arguments.length ? !!open : !scope.isOpen;
};
// Allow other directives to watch status
this.isOpen = function() {
return scope.isOpen;
};
scope.getToggleElement = function() {
return self.toggleElement;
};
scope.focusToggleElement = function() {
if ( self.toggleElement ) {
self.toggleElement[0].focus();
}
};
scope.$watch('isOpen', function( isOpen, wasOpen ) {
$animate[isOpen ? 'addClass' : 'removeClass'](self.$element, openClass);
if ( isOpen ) {
scope.focusToggleElement();
dropdownService.open( scope );
} else {
dropdownService.close( scope );
}
setIsOpen($scope, isOpen);
if (angular.isDefined(isOpen) && isOpen !== wasOpen) {
toggleInvoker($scope, { open: !!isOpen });
}
});
$scope.$on('$locationChangeSuccess', function() {
scope.isOpen = false;
});
$scope.$on('$destroy', function() {
scope.$destroy();
});
}])
.directive('dropdown', function() {
return {
controller: 'DropdownController',
link: function(scope, element, attrs, dropdownCtrl) {
dropdownCtrl.init( element );
}
};
})
.directive('dropdownToggle', function() {
return {
require: '?^dropdown',
link: function(scope, element, attrs, dropdownCtrl) {
if ( !dropdownCtrl ) {
return;
}
dropdownCtrl.toggleElement = element;
var toggleDropdown = function(event) {
event.preventDefault();
if ( !element.hasClass('disabled') && !attrs.disabled ) {
scope.$apply(function() {
dropdownCtrl.toggle();
});
}
};
element.bind('click', toggleDropdown);
// WAI-ARIA
element.attr({ 'aria-haspopup': true, 'aria-expanded': false });
scope.$watch(dropdownCtrl.isOpen, function( isOpen ) {
element.attr('aria-expanded', !!isOpen);
});
scope.$on('$destroy', function() {
element.unbind('click', toggleDropdown);
});
}
};
});
HTML
</head>
<body ng-controller="MainCtrl">
<div class="col-md-6">
<div class="btn-group" dropdown is-open="activeStep.schoolclassCodeColorsIsOpen">
<button type="button" ng-style="{{activeStep.selectedSchoolclassCodeColor}}"
class="btn btn-primary dropdown-toggle" ng-disabled="disabled">
{{activeStep.schoolclassCode()}} <span class="caret"></span>
</button>
<ul class="dropdown-menu" role="menu">
<li ng-repeat="color in activeStep.schoolclassCodeColors">
<a ng-style="{{color}}"
ng-click="activeStep.setSchoolclassCodeColor(color)">{{activeStep.schoolclassCode()}}</a>
</li>
</ul>
</div>
</div>
</body>
</html>
In order to use the dropdownToggle directive inside the class attribute, you need to define the restrict permissions from the directive to include the C (Class). For example:
.directive('dropdownToggle', function() {
return {
restrict: 'AEC',
require: '?^dropdown',
// ...
});
From Angular's documentation:
The restrict option is typically set to:
'A' - only matches attribute name
'E' - only matches element name
'C' - only matches class name
Demo
<script src="//cdnjs.cloudflare.com/ajax/libs/jquery/2.1.1/jquery.js"></script>
<link rel="stylesheet" href="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css" />
<script data-require="angular.js#1.2.x" src="https://code.angularjs.org/1.2.25/angular.js" data-semver="1.2.25"></script>
<script src="app.js"></script>
<script src="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.min.js"></script>
you need to add bootstrap.min.js and jquery.js javascript files, and also you need to add, data-toggle="dropdown" attribute to button as below
<button type="button" ng-style="{{activeStep.selectedSchoolclassCodeColor}}"
class="btn btn-primary dropdown-toggle" ng-disabled="disabled" data-toggle="dropdown">
here is the plunker
demo
That seems like an awful lot of code for what you are trying to do. I can't tell if the answer below is what you are looking for. I'm assuming you are trying to create an angular-only version of the bootstrap toggle.
It seems like you have misunderstood the way that require and the controller attribute of the directive work. I think that the angular docs are probably the source of this confusion unfortunately:
When a directive requires a controller, it receives that controller as the fourth argument of its link function.
It says that the directive requires a controller, but it is actually the case that the directive requires another directive. And that required directive's controller is passed to the linking function.
The controller attribute should not be a string (controller: 'DropdownController',), but should be a constructor function for the controller. So I think you can solve your issue by moving your DropdownController into the directive.
For an example of something similar (but simpler) you can see this answer and the plnkr.

How to set ng-disabled inside directive

My directive has
link: function ($scope, $elm, $attrs) {
var status = $scope.item.status
if (status) {
var statusName = status.name,
item = $scope.item;
if (statusName === 'USED') {
$attrs.$set('ng-disabled', true); // this doesn't work
} else {
$elm.attr('ng-disabled', false);
}
}
}
So, my question is:
How to apply ng-disabled to element with this directive?
if (statusName === 'USED') {
$attrs.$set('disabled', 'disabled');
} else {
$elm.removeAttr('disabled');
}
Why invoke ng-disable at all? You're already once evaluating the condition yourself, so having ng-disable evaluating it again is redundant.
You would set ng-disabled to a scope variable, ex:
<input ng-disabled="isDisabled" />
And then inside your directive you can set that variable:
$scope.isDisabled = true;
//html
<div ng-app="miniapp" ng-controller="MainCtrl">
<input type="submit" mydir>
</div>
//js
'use strict';
var app = angular.module('miniapp', []);
app.directive('mydir', function ($compile) {
return {
priority:1001, // compiles first
terminal:true, // prevent lower priority directives to compile after it
compile: function(el) {
el.removeAttr('mydir'); // necessary to avoid infinite compile loop
return function(scope){
var status = scope.item.status
if (status === 'USED') {
el.attr('ng-disabled',true);
} else {
el.attr('ng-disabled',false);
}
var fn = $compile(el);
fn(scope);
};
}
};
});
app.controller('MainCtrl', function ($scope) {
$scope.item = {};
$scope.item.status = 'USED';
});
credit to Ilan Frumer

Categories

Resources