I've tried the answer mentioned here but no luck (I'm using angularjs 1.3). My problem is two part
1) Complex attributes are not being passed as objects despite using '=' (see code below) in scope
2) the function that should evaluate to provide one-way binding is also being passed as string instead
sample use,
<button type="button" class="btn btn-success" ng-click="RestEditCtrl.saveRestaurantDetails();">
    <smart-btn-label btn-state="RestEditCtrl.ajaxState(RestEditCtrl.restaurant.id)"
        when-normal="{label: 'Save', icon: 'glyphicon-floppy-disk' }"
        when-active="{label: 'Saving...', icon: 'glyphicon-refresh glyphicon-spin-animate'}"
        when-success="{label: 'Saved!',   icon: 'glyphicon glyphicon-floppy-saved'}"
        when-error="{label: 'Try saving again',  icon: 'glyphicon glyphicon-exclamation-sign'}"></smart-btn-label>
</button>
directive code,
angular.module("app")
    .directive('smartBtnLabel', function () {
        return {
            restrict: 'E',           
            scope: {
                btnState: '&', // not working, @ evaluates but that defeats my purpose
                whenActive: '=', //  not evaluating any which way, it always comes as string
                whenError: '=',
                whenSuccess: '=',
                whenNormal: '='
            },
            link: function (scope, elem, attrs) {
                console.log(attrs);
                var curState = "normal",
                    curLabel = attrs.whenNormal ? attrs.whenNormal.label : "",
                    curIcon = attrs.whenNormal ? attrs.whenNormal.icon : "";
                if (attrs.btnState) curState = attrs.btnState;
                if(curState == "active"){
                    curLabel = attrs.whenActive  ? attrs.whenActive.label : "";
                    curIcon = attrs.whenActive ? attrs.whenActive.icon : ""
                } else if(curState == "success"){
                    curLabel = attrs.whenSuccess ? attrs.whenSuccess.label : "";
                    curIcon = attrs.whenSuccess ? attrs.whenSuccess.icon : ""
                } else if(curState == "error"){
                    curLabel = attrs.whenError  ? attrs.whenError.label : "";
                    curIcon = attrs.whenError  ? attrs.whenError.icon : ""
                }
                scope.curLabel = curLabel;
                scope.curIcon = curIcon;
            },
            template: '<span aria-hidden="true" ng-show="curIcon" class="glyphicon {{curIcon}}" ></span>' +
                      '<span ng-show="curLabel"> {{curLabel}}</span>'
        };
    });
What am I doing wrong here? :-(
Solution
Thanks to PSL, here is what I ended up with:
angular.module("app")
    .directive('smartBtnLabel', function () {
        return {
            restrict: 'E',           
            scope: {
                btnState: '&', 
                whenActive: '&',
                whenError: '&',
                whenSuccess: '&',
                whenNormal: '&'
            },
            controller: ['$scope', function($scope){
                var vm = this;
                vm.props = {icon: "", label: ""};
                var _setProperties = function () {
                    var _btnState = "normal";
                    if ($scope.btnState) _btnState = $scope.btnState();
                    if (_btnState == "active" && $scope.whenActive) vm.props = $scope.whenActive();
                    else if (_btnState == "success" && $scope.whenSuccess) vm.props = $scope.whenSuccess();
                    else if (_btnState == "error" && $scope.whenError) vm.props = $scope.whenError();
                    else if ($scope.whenNormal) vm.props = $scope.whenNormal();
                };
                if($scope.btnState){
                    $scope.$watch($scope.btnState, function () {
                        _setProperties();
                    });
                }
                _setProperties();
            }],
            controllerAs : "smartBtnLabelCtrl",            
            template: '<span aria-hidden="true" ng-show="smartBtnLabelCtrl.props.icon" class="glyphicon {{smartBtnLabelCtrl.props.icon}}" ></span>' +
                      '<span ng-show="smartBtnLabelCtrl.props.label"> {{smartBtnLabelCtrl.props.label}}</span>'
        };
    });
 
     
    