1

我正在尝试编写一个指令,该指令从其子指令的输入构建一个对象并将其推送到作为参数提供的数组中。就像是:

<aggregate-input on="SiteContent.data.objList">
    <p aggregate-question>Question text</p>
    <input aggregate-answer ng-model="answer" type="text" />
</aggregate-input>
<aggregate-input on="SiteContent.data.objList">
    <p aggregate-question>Question text 2</p>
    <input aggregate-answer ng-model="answer" type="text" />
</aggregate-input>

我希望收集如下数据:

SiteContent.data.objList === [
    {question: 'Quesion text', answer: 'user input'},
    {question: 'Quesion text 2', answer: 'user input 2'},
];

这是带有代码的 plunker

  • 更新 1:@jrsala 包括范围和 bindToController 语法更改

我无法弄清楚这些指令的通信方式。我期望input 链接中定义的对象将在每个指令的范围内隔离并推送到on提供的对象。结果是input对象在所有实例之间共享,并且只有一个对象被推送到数组中。

我猜嵌入的范围规则让我感到困惑,但我真的不知道在哪里。有任何想法吗?谢谢!

4

1 回答 1

1

第一个问题:您的aggregate-input指令指定了一个没有绑定属性的隔离范围,但您仍然on在元素上使用带有指令的属性:

<aggregate-input on="SiteContent.data.objList">

但在你的 JS 中,

{
    restrict: 'E',
    scope: {},
    controller: aggregateInputController,
    controllerAs: 'Aggregate',
    bindToController: { on: '=' },
    /* */
}

而你需要的是

{
    restrict: 'E',
    scope: { on: '=' },
    controller: aggregateInputController,
    controllerAs: 'Aggregate',
    bindToController: true // BOOLEAN REQUIRED HERE, NO OBJECT
}

根据规范的段落bindToController

当一个组件使用隔离作用域(见上文)并且使用了 controllerAs 时,bindToController: true 将允许组件将其属性绑定到控制器,而不是作用域。实例化控制器时,隔离范围绑定的初始值已经可用。

然后你不需要将on属性分配给你的控制器,它是由 Angular 为你完成的(我也不明白你为什么这样做this.on = this.on || [],这this.on ||部分对我来说看起来没有必要)。

我想您可以将其应用于其余代码,这应该是一个开始。我要寻找更多的问题。

编辑:我发现的更多问题:

  • 如果 的范围siteContent是孤立的,则在SiteContent编译指令时控制器不可访问,并且 Angular 在评估SiteContent.data.objList将其传递给子指令时会默默地失败(就像总是......)。scope: {}我通过从其定义中删除来解决这个问题。

  • 有必要将 over to 的功能aggregateInputLink移到,aggregateInputController因为像往常一样,子控制器在链接函数之前执行,并且由于指令在其控制器aggregateQuestion中进行调用,因此父指令中的分配到后链接函数还不存在.InputCtrl.changeValue('question', elem.text());scope.input

function aggregateInputController($scope) {
    $scope.input = {};
    this.on.push($scope.input);

    this.changeValue = function changeValue(field, value) {
        $scope.input[field] = value;
    };
}

提醒一下:在遍历指令树期间,控制器以前序方式执行,并以后序方式链接功能。

  • 最后,在那之后,SiteContent控制器的数据没有得到渲染属性,因为用于迭代的集合ng-repeat错误地SiteContent.objList而不是SiteContent.data.objList.

链接到最终的 plunker

于 2015-09-18T19:05:10.043 回答