Bootstrap buttons-checkbox with Angular

by luisfarzati

HTML

<link rel="stylesheet" href="//netdna.bootstrapcdn.com/twitter-bootstrap/2.1.1/css/bootstrap.no-icons.min.css">
<script src="http://code.jquery.com/jquery-1.8.2.min.js"></script>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.0.2/angular.min.js"></script>
<script src="http://netdna.bootstrapcdn.com/twitter-bootstrap/2.1.1/js/bootstrap.min.js"></script>
<div ng-app="sample" ng-controller="SampleController">
<ul>
    <li>myModel.optionA:{{myModel.optionA}}</li>
    <li>myModel.optionA: {{myModel.optionB}}</li>
</ul>
<form class="form-inline">
    <label class="checkbox">                
        <input type="checkbox" ng-model="myModel.optionA"> A
    </label>
    <label class="checkbox">                
        <input type="checkbox" ng-model="myModel.optionB"> B
    </label>
</form>
<div class="btn-group" data-toggle="buttons-checkbox">
    <button type="button" ng-model="myModel.optionA" class="btn">A</button>
    <button type="button" ng-model="myModel.optionB" class="btn">B</button>
</div>
</div>

JavaScript

// Bootstrap module
// here you should keep adding more directives leading to a
// better Bootstrap-AngularJS integration :)
angular.module('bootstrap', []).directive('button', function() {
    return {
        restrict: 'E',
        require: 'ngModel',
        link: function($scope, element, attr, ctrl) {

            // ignore other kind of button groups (e.g. buttons-radio)
            if (!element.parent('[data-toggle="buttons-checkbox"].btn-group').length) {
                return;
            }

            // set/unset 'active' class when model changes
            $scope.$watch(attr.ngModel, function(newValue, oldValue) {
                element.toggleClass('active', ctrl.$viewValue);
            });

            // update model when button is clicked
            element.bind('click', function(e) {
                $scope.$apply(function(scope) {
                    ctrl.$setViewValue(!ctrl.$viewValue);
                });

                // don't let Bootstrap.js catch this event,
                // as we are overriding its data-toggle behavior.
                e.stopPropagation();
            });
        }
    };
});

angular.module('sample', ['bootstrap']);

function SampleController($scope) {
    console.log('model');
    $scope.myModel = {
        optionA: false,
        optionB: true
    };
}