自定义指令attr绑定不起作用

时间:2016-08-22 17:28:07

标签: javascript angularjs angularjs-directive

我在我正试图制作的标签/面板指令中遇到了问题。我需要能够为每个面板提供模板和控制器,可以是HTML中的字符串,也可以是要绑定的表达式。例如。我需要能够这样称呼它......

<tab-panel tab-id="tab1" 
    template="myTemplate.html" 
    controller="AdminController as adminController"
></tab-panel>

或者像这样

<tab-panel tab-id="tab1" 
    template="{{model.tabTemplate}}" 
    controller="{{model.tabController}}"
></tab-panel>

我在每个面板中使用ng-if来打开和关闭内容,使用ng-include和ng-controller来加载内容。这是我指令的简化测试用例。

// Tab Panel Directive Controller
.controller('TabPanelCtrl', function(){
    // removed for brevity
})

// Tab Panel Directive
.directive('s4pTabPanel', function($interpolate) {

    return {
        restrict: 'E',
        scope: {
            id: '@?tabId',
            template: '@?',
            controller: '@?',
        },
        controller: 'TabPanelCtrl as tabPanelCtrl',
        template: getTemplate
    };


    function getTemplate(element, attr) {


        // removed for brevity

        // Panel loads template and controller
        if(attr.template && attr.controller){
            return  '<tab-panel-inner ng-if="loadContent" ng-include="template" onload="onPanelLoaded()" ng-controller="controller"></tab-panel-inner>';
        }

        // removed for brevity

    }

});

因此,模板属性似乎没问题,评估表达式并将结果字符串插入到ng-include属性中。但是ng-controller属性由于某种原因不喜欢它,我得到以下控制台错误......

Error: ng:areq
Bad Argument
Argument 'controller' is not a function, got string

任何人帮助解决这个问题真的很感激。

修改

为了清楚,指令上的控制器很好,它是指令模板中的 ng-controller =“controller”位导致问题,因为它没有得到评估结果传入控制器名称的'@'绑定。

编辑2:

我很确定这与第一个答案有关。

AngularJS: dynamically assign controller from ng-repeat

特别是这一点:

“你的问题是ng-controller应该指向控制器本身,而不仅仅是控制器名称的字符串。”

控制器的名称包含在指令内的范围变量中,但它是一个字符串,如果我想保持这种动态,不知道它是如何以任何其他方式。

1 个答案:

答案 0 :(得分:0)

您似乎希望根据绑定的控制器动态设置控制器。

在你的代码中,ng-controller绑定到一个字符串&#34; controller&#34;。这与示波器绑定中的控制器不同。

// Panel loads template and controller
        if(attr.template && attr.controller){
            return  '<tab-panel-inner ng-if="loadContent" ng-include="template" onload="onPanelLoaded()" ng-controller="controller"></tab-panel-inner>';
        }

我认为你需要这样做:

...ng-controller="' + controller + '" ...

或者

...ng-controller="' + attr.controller + '" ...

这样您就可以访问控制器对象而不是字符串。