Angular 写入嵌套范围属性
Angular write into nested scope properties
我的应用程序中有多个 "input field and a button" 对。
该按钮会打开一个对话框,用于在文本字段中写入内容。
[ input ] [ button ] ---> [ dialog ( ok ) ( cancel ) ]
我用过 Bootstrap.UI.Modal ( https://angular-ui.github.io/bootstrap/#/modal ) 所以我保证会处理它:
//html
<input ng-model="foo"/>
<button ng-click="dialog('foo')"> Open </button>
//controller
modalInstance.result.then(
function ( selectedItem ) {
$scope[ arg ] = selectedItem;
},
...
);
一切正常。 ( Demo )
当我必须访问范围对象的嵌套属性时,问题就来了:
...
<input ng-model="foo"/>
<button ng-click="dialog('foo')"> Open </button>
...
<li ng-repeat="thing in model.nested.properties.of.unknown.level">
...
<input ng-model="thing.foo"/>
<button ng-click="dialog( '???' )"> Open </button>
...
我想知道的是:实现该目标的最佳方法是什么?
到目前为止,我尝试过:
将范围变量传递给返回的回调,但它只得到值,没有引用;所以该字段不会更新。
resolve: {
field: function() {
return $scope[ field ];
}
}
传递字符串数组以重新创建范围层次结构
dialog( ["a","b","c"] ) --> $scope[ "a" ][ "b" ][ "c" ] = output.value;
正在准备回调对象,例如
object = {
"one": function(){ $scope.a.b.c = ... },
"two": function(){ $scope.d.e.f = ... },
...
// but this requires that I know in advance
// how many level I will nest into the $scope
}
使用输入字段的id,所以你可以直接写入DOM(但据我所知,这在angularjs中不是一个好方法)
$("#input-abc...").val( ... )
使用 eval (uungh...)
我认为第一个解决方案是最好的解决方案,但如何将嵌套范围元素的引用传递给我的 promise 回调?
有一些最佳实践可以实现这一目标吗?
有什么建议吗?
我建议您尽可能考虑所有具有相同结构的数据,这样您就不必在模态内处理条件。
连第一个和第二个:
$scope.first = {label:'first',value:'initial value'};
$scope.second = {label:'second ', value:'initial value'};
我找到了让它工作的方法:
我创建了一个指令来直接在元素的 val( ) 上设置您从承诺中获得的值。
.directive("external", function( $modal ){
return {
restrict: "A",
link: function (scope, element) {
element.bind("mousedown", function () {
var modalInstance = $modal.open({
templateUrl: 'myModalContent.html',
controller: 'ModalInstanceCtrl',
resolve: {
field: function() {
return "";
}
}
});
modalInstance.result.then(function( output ) {
element.val( output.selection );
}, function() {
$log.info('Modal dismissed at: ' + new Date());
});
});
}
};
});
这样您就可以在事先不知道任何事情的情况下访问您的元素。
工作演示(link)
要处理嵌套结构,您可以简单地将容器与字段名称一起传递:
resolve: {
container: function () {
return thing; // thing would come from edit() parameter
},
field: function () {
return fieldName;
}
}
然后从容器而不是范围访问您的数据。这将是穷人双向绑定。
--
另一种方法,从您离开指令的地方开始,如下所示:
步骤 1) 当您使用 ngModel
时,将其添加到指令范围以获得双向绑定:
scope: {
ngModel: '='
},
步骤 2) 将 attr
参数添加到 link
link: function (scope, element, attr)
步骤 3) 将字段解析为视图中传递的数据
resolve: {
field: function () {
return attr.external;
}
步骤 4) 模态完成后将新数据分配给 ngModel
scope.ngModel = output.selection;
第 5 步)像这样改变你的观点:
<input type='text' ng-model='thing.value' external="{{thing.label}}"/> Value: {{thing.value}}
我的应用程序中有多个 "input field and a button" 对。 该按钮会打开一个对话框,用于在文本字段中写入内容。
[ input ] [ button ] ---> [ dialog ( ok ) ( cancel ) ]
我用过 Bootstrap.UI.Modal ( https://angular-ui.github.io/bootstrap/#/modal ) 所以我保证会处理它:
//html
<input ng-model="foo"/>
<button ng-click="dialog('foo')"> Open </button>
//controller
modalInstance.result.then(
function ( selectedItem ) {
$scope[ arg ] = selectedItem;
},
...
);
一切正常。 ( Demo ) 当我必须访问范围对象的嵌套属性时,问题就来了:
...
<input ng-model="foo"/>
<button ng-click="dialog('foo')"> Open </button>
...
<li ng-repeat="thing in model.nested.properties.of.unknown.level">
...
<input ng-model="thing.foo"/>
<button ng-click="dialog( '???' )"> Open </button>
...
我想知道的是:实现该目标的最佳方法是什么?
到目前为止,我尝试过:
将范围变量传递给返回的回调,但它只得到值,没有引用;所以该字段不会更新。
resolve: { field: function() { return $scope[ field ]; } }
传递字符串数组以重新创建范围层次结构
dialog( ["a","b","c"] ) --> $scope[ "a" ][ "b" ][ "c" ] = output.value;
正在准备回调对象,例如
object = { "one": function(){ $scope.a.b.c = ... }, "two": function(){ $scope.d.e.f = ... }, ... // but this requires that I know in advance // how many level I will nest into the $scope }
使用输入字段的id,所以你可以直接写入DOM(但据我所知,这在angularjs中不是一个好方法)
$("#input-abc...").val( ... )
使用 eval (uungh...)
我认为第一个解决方案是最好的解决方案,但如何将嵌套范围元素的引用传递给我的 promise 回调? 有一些最佳实践可以实现这一目标吗? 有什么建议吗?
我建议您尽可能考虑所有具有相同结构的数据,这样您就不必在模态内处理条件。
连第一个和第二个:
$scope.first = {label:'first',value:'initial value'};
$scope.second = {label:'second ', value:'initial value'};
我找到了让它工作的方法:
我创建了一个指令来直接在元素的 val( ) 上设置您从承诺中获得的值。
.directive("external", function( $modal ){
return {
restrict: "A",
link: function (scope, element) {
element.bind("mousedown", function () {
var modalInstance = $modal.open({
templateUrl: 'myModalContent.html',
controller: 'ModalInstanceCtrl',
resolve: {
field: function() {
return "";
}
}
});
modalInstance.result.then(function( output ) {
element.val( output.selection );
}, function() {
$log.info('Modal dismissed at: ' + new Date());
});
});
}
};
});
这样您就可以在事先不知道任何事情的情况下访问您的元素。
工作演示(link)
要处理嵌套结构,您可以简单地将容器与字段名称一起传递:
resolve: {
container: function () {
return thing; // thing would come from edit() parameter
},
field: function () {
return fieldName;
}
}
然后从容器而不是范围访问您的数据。这将是穷人双向绑定。
--
另一种方法,从您离开指令的地方开始,如下所示:
步骤 1) 当您使用 ngModel
时,将其添加到指令范围以获得双向绑定:
scope: {
ngModel: '='
},
步骤 2) 将 attr
参数添加到 link
link: function (scope, element, attr)
步骤 3) 将字段解析为视图中传递的数据
resolve: {
field: function () {
return attr.external;
}
步骤 4) 模态完成后将新数据分配给 ngModel
scope.ngModel = output.selection;
第 5 步)像这样改变你的观点:
<input type='text' ng-model='thing.value' external="{{thing.label}}"/> Value: {{thing.value}}