Agnular's ng-click triggers twice when i click label which has input inside in it. I've tried $event.stopPropagation();
but didn't work, how to solve this :?
I've checked this question also:
Angular.js ng-click events on labels are firing twice
<div class="list-group-item" ng-repeat="item in model.data">
<form role="form" name="selectForm" novalidate>
<label ng-click="$event.stopPropagation(); updateSelected();">
<input type="checkbox" ng-model="chechkedSkins[item.id]" />
<span>{{item.name}}</span>
</label>
</form>
</div>
Use ng-change="updateSelected"
Use this only on the input since the change is triggered even if you click the label.
Well thats because label
is the parent or container for the checkbox
, so the click
handler is attached to the complete container in your case, thereby whenever either label
or checkbox
is clicked, event is triggered.
Whats wrong with your approach:
- Firstly never insert the input tags inside the label, thats not a good way to construct markup in html.In
Angular.js
this behaviour causes the click event to be triggered for both the tags. so to add a binding between input
tag & label
use the for
attribute of label.
- Using
$event.stopPropagation()
inside label actually stops all events from propagating/boiling to the top of the DOM from the label. this will not serve any purpose because the event would still propagate to the input with in the label.
I hope you can visualise what i'm saying.
What I have done:
- Use
for
attribute to bind the input
to the label & add a click
event to prevent the default functionality.
Add the click handler to the respective input
tag & not the label
<label for="username" ng-click="$event.preventDefault();">Click me</label>
<input type="text" id="username" ng-click="updateSelected();">
Live Demo @ JSFiddle
This way you don't have to worry about any conflicts in event handling,also its neat way to maintain the HTML code :)
I'm using the latest version of Angular Material 1.0.3 and still having this issue when clicking on labels that are configured as buttons on Android. I don't have the problem on IOS or the browser (cordova app). The following resolved it for me.
my html:
<label class="btn btn-primary" ng-click="vm.goAbout()">About</label>
my controller:
vm.goAbout = debounceFn(function(){
//show dialog here, and now it only pops up once
}, 250, false);
The debounce function:
function debounceFn(func, wait, immediate){
var timeout;
var deferred = $q.defer();
return function() {
var context = this, args = arguments;
var later = function() {
timeout = null;
if(!immediate) {
deferred.resolve(func.apply(context, args));
deferred = $q.defer();
}
};
var callNow = immediate && !timeout;
if ( timeout ) {
$timeout.cancel(timeout);
}
timeout = $timeout(later, wait);
if (callNow) {
deferred.resolve(func.apply(context,args));
deferred = $q.defer();
}
return deferred.promise;
}
}