我在使用 Angular 的 JQM 库时遇到了问题。特别是,我正在尝试使用 jqmFlip 指令来创建过滤器按钮。
当我向指令添加 ng-model 属性时,数据绑定在 DOM 中工作正常。但是当我尝试从控制器记录 ng-model 的值时,它会显示为一个空白字符串(因为我必须像这样定义 ng-model:
$scope.search = {
includeTags:"",
includeKeywords:""
};
否则变量出现未定义。
但是,我可以通过在 log 语句之前调用 $scope.$apply() 来记录正确的值。
据我了解,这不是检索值的最佳方法,因为我收到此错误:$digest 已经在进行中。
关于为什么会发生这种情况的任何想法?如有必要,我可以发布更多代码。
更新:指令代码
jqmModule.directive('jqmFlip', [function () {
return {
restrict: 'E',
transclude: true,
replace: true,
templateUrl: 'templates/jqmFlip.html',
scope: {
onLabel: '@',
onValue: '@',
offLabel: '@',
offValue: '@',
mini: '@',
disabled: '@',
defaultValue: '@'
},
require: ['?ngModel', '^?jqmControlgroup'],
link: function (scope, element, attr, ctrls) {
console.log(ctrls);
var ngModelCtrl = ctrls[0];
var jqmControlGroupCtrl = ctrls[1];
var parsedOn;
var parsedOff;
scope.theme = scope.$theme || 'c';
scope.isMini = isMini;
scope.onValue = angular.isDefined(attr.onValue) ? scope.onValue : true;
scope.offValue = angular.isDefined(attr.offValue) ? scope.offValue : false;
scope.defaultValue = attr.defaultValue;
initToggleState();
bindClick();
function initToggleState () {
ngModelCtrl.$parsers.push(parseBoolean);
parsedOn = parseBoolean(scope.onValue);
parsedOff = parseBoolean(scope.offValue);
ngModelCtrl.$render = updateToggleStyle;
ngModelCtrl.$viewChangeListeners.push(updateToggleStyle);
}
function updateToggleStyle () {
updateNaNAsOffValue(scope.defaultValue);
var toggled = isToggled();
scope.toggleLabel = toggled ? scope.onLabel : scope.offLabel;
scope.onStyle = toggled ? 100 : 0;
scope.offStyle = toggled ? 0 : 100;
}
// this has to be done in the change listener,
// otherwise the potential scope value would be overwritten with the off value
function updateNaNAsOffValue (defaultValue) {
if (!ngModelCtrl.$viewValue) {
ngModelCtrl.$setViewValue(defaultValue);
}
}
function bindClick () {
scope.toggle = function () {
ngModelCtrl.$setViewValue(isToggled() ? parsedOff : parsedOn);
};
}
function isToggled () {
return ngModelCtrl.$viewValue === parsedOn;
}
function isMini() {
return scope.mini || (jqmControlGroupCtrl && jqmControlGroupCtrl.$scope.mini);
}
function parseBoolean(value) {
if (value === 'true') {
return true;
} else if (value === 'false') {
return false;
}
return value;
}
}
};
}]);
jqmFlip 指令所需的 JQMcontrolGroup 指令:
jqmModule.directive('jqmControlgroup', function() {
return {
restrict: 'A',
replace: true,
transclude: true,
templateUrl: 'templates/jqmControlgroup.html',
scope: {
mini: '@',
iconpos: '@',
type: '@',
shadow: '@',
corners: '@',
legend: '@'
},
controller: ['$scope', JqmControlGroupCtrl]
};
function JqmControlGroupCtrl($scope) {
this.$scope = $scope;
}
});
jqmFlip 模板网址:
angular.module("templates/jqmFlip.html", []).run(["$templateCache", function($templateCache) {
$templateCache.put("templates/jqmFlip.html",
"<div jqm-scope-as=\"jqmFlip\">\n" +
" <label class=\"ui-slider\" ng-transclude></label>\n" +
" <div class=\"ui-slider ui-slider-switch ui-btn-down-{{$scopeAs.jqmFlip.theme}} ui-btn-corner-all\"\n" +
" jqm-class=\"{'ui-disabled': $scopeAs.jqmFlip.disabled,\n" +
" 'ui-mini': $scopeAs.jqmFlip.isMini()}\"\n" +
" ng-click=\"$scopeAs.jqmFlip.toggle()\">\n" +
" <span class=\"ui-slider-label ui-slider-label-a ui-btn-active ui-btn-corner-all\" ng-style=\"{width: $scopeAs.jqmFlip.onStyle + '%'}\">{{$scopeAs.jqmFlip.onLabel}}</span>\n" +
" <span class=\"ui-slider-label ui-slider-label-b ui-btn-down-{{$scopeAs.jqmFlip.theme}} ui-btn-corner-all\" ng-style=\"{width: $scopeAs.jqmFlip.offStyle + '%'}\">{{$scopeAs.jqmFlip.offLabel}}</span>\n" +
" <div class=\"ui-slider-inneroffset\">\n" +
" <a class=\"ui-slider-handle ui-slider-handle-snapping ui-btn ui-btn-corner-all ui-btn-up-{{$scopeAs.jqmFlip.theme}} ui-shadow\"\n" +
" title=\"{{$scopeAs.jqmFlip.toggleLabel}}\"\n" +
" ng-style=\"{left: $scopeAs.jqmFlip.onStyle + '%'}\">\n" +
" <span class=\"ui-btn-inner\"><span class=\"ui-btn-text\"></span></span>\n" +
" </a>\n" +
" </div>\n" +
" </div>\n" +
"</div>\n" +
"");
}]);
jqmControlGroup 模板网址:
angular.module("templates/jqmControlgroup.html", []).run(["$templateCache", function($templateCache) {
$templateCache.put("templates/jqmControlgroup.html",
"<fieldset class=\"ui-controlgroup\"\n" +
" jqm-class=\"{'ui-mini': mini, 'ui-shadow': shadow, 'ui-corner-all': corners!='false',\n" +
" 'ui-controlgroup-vertical': type!='horizontal', 'ui-controlgroup-horizontal': type=='horizontal'}\">\n" +
" <div ng-if=\"legend\" class=\"ui-controlgroup-label\">\n" +
" <legend>{{legend}}</legend>\n" +
" </div>\n" +
" <div class=\"ui-controlgroup-controls\" ng-transclude jqm-position-anchor></div>\n" +
"</fieldset>\n" +
"");
}]);
HTML中的参考:
<jqm-flip mini="true" jqm-theme="d" ng-model="search.includeTags" on-label="On" on-value="1" off-label="Off"
off-value="0" default-value="1"></jqm-flip>
{{search.includeTags}}