这个问题很老,但我挣扎了很长时间,试图找到一个适合我需要的问题的答案,但并不容易找到它。我相信我的以下解决方案比目前接受的解决方案要好得多,也许是因为 angular 自从这个问题最初提出以来就增加了功能。
简短的回答,使用 Module.value 方法允许您将数据传递到控制器构造函数中。
在这里看到我的 plunker
我创建了一个模型对象,然后将它与模块的控制器相关联,并用名称“模型”引用它
HTML / JS
<html>
<head>
<script>
var model = {"id": 1, "name":"foo"};
$(document).ready(function(){
var module = angular.module('myApp', []);
module.value('model', model);
module.controller('MyController', ['model', MyController]);
angular.bootstrap(document, ['myApp']);
});
function confirmModelEdited() {
alert("model name: " + model.name + "\nmodel id: " + model.id);
}
</script>
</head>
<body >
<div ng-controller="MyController as controller">
id: {{controller.model.id}} <br>
name: <input ng-model="controller.model.name"/>{{controller.model.name}}
<br><button ng-click="controller.incrementId()">increment ID</button>
<br><button onclick="confirmModelEdited()">confirm model was edited</button>
</div>
</body>
</html>
然后,我的控制器中的构造函数接受具有相同标识符“模型”的参数,然后它可以访问该参数。
控制器
function MyController (model) {
this.model = model;
}
MyController.prototype.incrementId = function() {
this.model.id = this.model.id + 1;
}
笔记:
我正在使用bootstrapping的手动初始化,它允许我在将模型发送到 Angular 之前对其进行初始化。这与现有代码配合得更好,因为您可以等待设置相关数据并仅在需要时按需编译应用程序的 Angular 子集。
在 plunker 中,我添加了一个按钮来提醒最初在 javascript 中定义并传递给 angular 的模型对象的值,只是为了确认 angular 真正引用了模型对象,而不是复制它并使用副本。
在这条线上:
module.controller('MyController', ['model', MyController]);
我将 MyController 对象传递给 Module.controller 函数,而不是声明为内联函数。我认为这使我们能够更清楚地定义我们的控制器对象,但是 Angular 文档倾向于内联,所以我认为它需要澄清。
我正在使用“controller as”语法并将值分配给 MyController 的“this”属性,而不是使用“$scope”变量。我相信使用 $scope 也可以正常工作,控制器分配看起来像这样:
module.controller('MyController', ['$scope', 'model', MyController]);
并且控制器构造函数将具有如下签名:
function MyController ($scope, model) {
如果出于任何原因,您还可以将此模型作为第二个模块的值附加,然后将其作为依赖项附加到主模块。
我相信他的解决方案比目前接受的解决方案要好得多,因为
- 传递给控制器的模型实际上是一个 javascript 对象,而不是被评估的字符串。它是对对象的真实引用,对它的更改会影响对该模型对象的其他引用。
- Angular 说,公认的答案对 ng-init 的使用是一种误用,而这个解决方案没有这样做。
在我见过的大多数其他示例中,Angular 的工作方式似乎是控制器定义了模型的数据,这对我来说从来没有意义,模型和控制器之间没有分离,这看起来并不像MVC 对我来说。该解决方案允许您真正拥有一个完全独立的模型对象,并将其传递给控制器。另外值得注意的是,如果您使用 ng-include 指令,您可以将所有 angular html 放在一个单独的文件中,将您的模型视图和控制器完全分离为单独的模块化部分。