我有一个简单的AngularJS项目,我从用户那里获取输入数据并根据该数据生成图表。我试图弄清楚如何组织代码,使其符合MVC design pattern。特别是,我很难搞清楚如何将表单的提交事件传播给自定义指令的父级。我正在寻找某种回叫机制。
似乎有几个选项,但我还没有让它们中的任何一个工作。我考虑过使用custom directives,ui-Router和服务(根据AngularJS: How can I pass variables between controllers?)
到目前为止,我一直试图让自定义指令的方法起作用。我有一个自定义指令<input-form>
,它是一个表单,在提交时应将其输入传递给另一个自定义指令<index-chart>
。我有三个控制器:一个用于主应用,NavigationController
,一个用于输入InputController
,它们与指令<input-form>
相关联,另一个用于输出OutputController
#39;绑定到<index-chart>
指令。
我认为NavigationController
应该知道如何从InputController
中提取输入数据并将其传递给OutputController
。 InputController
和OutputController
应保持不可知,以便可以重复使用。
我想我已经找到了除流量控制之外的所有东西。 <input-form>
包含<form ... ng-submit
,因此即使我希望它保持不可知,它也负责触发响应用户提交的输入的操作。然而,该行动的代码应该在OutputController
中InputController
不应该知道。
如何让NavigationController
回复控制器为<input-form>
的自定义指令InputController
中包含的提交事件?然后NavigationController
如何从InputController
的实例中提取数据并调用应该呈现图表的OutputController
中包含的代码(即下面代码中的renderChart()
) ?
以下代码也在Plunker上:http://plnkr.co/edit/wm4suXMcSUE6obYFk3hp?p=preview 的的index.html
<html ng-app="a3d">
<div ng-controller="NavigationController as navCtrl">
<input-form ng-show="navCtrl.shouldShowInputForm()"></input-form>
<index-chart ng-show="navCtrl.shouldShowOutputChart()"></index-chart>
</div>
</html>
a3j.js
(function(){
var app = angular.module('a3d', ['input-form', 'index-chart']);
app.controller('NavigationController', function(){
this.inputMode = true;
this.shouldShowInputForm = function(){
return this.inputMode;
};
this.shouldShowOutputChart = function(){
return !this.inputMode;
};
this.flipMode = function(){
this.inputMode = !this.inputMode;
}
});
})();
输入form.html
<form name="inputForm" ng-controller="InputController as inputCtrl"
ng-submit="inputForm.$valid && ???" novalidate>
<textarea name="topic1Data" ng-model="inputCtrl.inputValues.topic1Data" rows="10" cols="30" required></textarea>
<button type="submit" class="btn btn-info btn-lg" ng-disabled="!inputForm.$valid">Compare</button>
</form>
inputForm.js
(function(){
var app = angular.module('input-form', [ ]);
app.directive('inputForm', function(){
return {
restrict: 'E',
templateUrl: 'input-form.html',
};
});
app.controller('InputController', ['$window', '$log', function($window, $log, appData){
// ...
}]);
索引chart.html
<!-- I haven't really gotten to this part yet -->
<div id="indexchart" style="min-width: 310px; max-width: 800px; height: 900px; margin: 0 auto"></div>
indexChart.js
(function(){
var app = angular.module('index-chart', [ ]);
app.directive('indexChart', function(){
return {
restrict: 'E',
templateUrl: 'index-chart.html'
};
});
app.controller('OutputController', ['$window', '$log', function($window, $log, appData){
this.renderChart = function(){
// This is where the chart should get rendered
};
}]);
})();
答案 0 :(得分:1)
以下是一种方法 - Plunker。
a3j.js
app.controller('NavigationController', function(){
var navCtrl = this;
navCtrl.data = null;
});
的index.html
<div ng-controller="NavigationController as navCtrl">
<input-form data="navCtrl.data"></input-form>
<index-chart data="navCtrl.data"></index-chart>
</div>
inputForm.js
inputForm.directive('inputForm', function() {
return {
restrict: 'E',
templateUrl: 'input-form.html',
scope: {data: "="},
controllerAs: 'inputCtrl',
bindToController: true,
controller: function() {
var inputCtrl = this;
inputCtrl.inputValues = {topic1Data: 123456789};
inputCtrl.emitData = function() {
inputCtrl.data = inputCtrl.inputValues.topic1Data;
};
}
};
});
输入form.html
<form name="inputForm" ng-submit="inputForm.$valid && inputCtrl.emitData()" novalidate>
<textarea name="topic1Data" ng-model="inputCtrl.inputValues.topic1Data" rows="10" cols="30" required></textarea>
<button type="submit" class="btn btn-info btn-lg" ng-disabled="!inputForm.$valid">Compare</button>
</form>
indexChart.js
indexChart.directive('indexChart', function() {
return {
restrict: 'E',
templateUrl: 'index-chart.html',
scope: {data: "="},
controllerAs: 'chartCtrl',
bindToController: true,
controller: ['$scope', function($scope) {
var chartCtrl = this;
$scope.$watch('chartCtrl.data', function(newValue) {
if (angular.isDefined(newValue)) {
console.log(newValue);
}
});
}]
};
});
索引chart.html
{{chartCtrl.data}}
需要注意的要点是: