是否可以在 Angular 应用程序中内省/反映模型,您可以在其中更改范围并遍历它?像batarang这样的东西有,但这将允许改变价值观。
如果不是,是否可以对 Angular 代码进行猴子补丁(通过在页面上包含另一个脚本)使其成为可能?
是否可以在 Angular 应用程序中内省/反映模型,您可以在其中更改范围并遍历它?像batarang这样的东西有,但这将允许改变价值观。
如果不是,是否可以对 Angular 代码进行猴子补丁(通过在页面上包含另一个脚本)使其成为可能?
1.访问/修改范围属性
Angular 的$scope
对象是普通的旧 JS 对象,因此可以通过标准方式进行操作。
例如someScope.someProp
,检索属性的值,同时someScope.someProp = someValue
设置属性的值。
2. 让 Angular 知道
修改对象的属性是一回事——让 Angular 意识到变化是另一回事。Angular 在运行一个循环
之前不会知道我们的修改。$digest
如果我们想立即应用更改,我们可以显式地触发一个$digest
循环,使用someScope.$apply()
.
3. 把握范围
为了获得对与 DOM 元素关联的范围的引用,我们需要对相应的 DOM Node 对象具有引用,将其包装angular.element
并执行其scope()
方法。
像这样的东西:
<body class="ng-scope">
var someScope = angular.element(document.body).scope();
此外,如果我们想访问$rootScope
(所有作用域的父作用域),我们可以使用注入器来注入$rootScope
服务:
<html ng-app="myApp">
var injector = angular.element(document.documentElement).injector();
var rootScope = injector.get('$rootScope');
4. 遍历范围树
一旦我们掌握了一个作用域对象,我们可能想要遍历作用域树。每个范围都具有以下属性(除其他外):
$parent
:此范围的父范围(如果有)。$$nextSibling
:此范围的下一个兄弟范围(如果有)。$parent
)$$childHead
:此范围的第一个子范围(如果有)。为了以someScope
根为根遍历范围树的分支:
var scopes = [someScope];
while (scopes.length) {
var scope = scopes.shift();
console.log(scope);
if (scope.$$nextSibling) { scopes.unshift(scope.$$nextSibling); }
if (scope.$$childHead) { scopes.unshift(scope.$$childHead); }
}
例如,要遍历整个作用域树,您可以使用以下代码段:
var injector = angular.element(document.body).injector();
var rootScope = injector.get('$rootScope');
var scopes = [rootScope];
while (scopes.length) {
var scope = scopes.shift();
report(scope);
if (scope.$$nextSibling) { scopes.unshift(scope.$$nextSibling); }
if (scope.$$childHead) { scopes.unshift(scope.$$childHead); }
}
function report(scope) {
var str = '' + scope.$id;
while (scope.$parent) {
str = scope.$parent.$id + ' => ' + str;
scope = scope.$parent;
}
console.log(str);
}
找到了方法,这是一个更改 Angular 之外范围的代码:
var $scope = angular.element($('.section:eq(0)')).scope();
$scope.$apply(function() {
scope.color = "blue";
});
将angular.element().scope()
返回范围并且可以进行调查。不确定如何遍历范围树,但这是一个很好的起点。如果没有范围遍历,您可以只遍历 DOM 并检查该 DOM 元素上是否有新的范围。
您可以通过调用由(或者,如果您还使用 jQuery)scope()
返回的对象上的方法来获取范围,例如. 没有直接访问子作用域的方法。但是知道所有具有与其关联的新范围的元素都具有该类,您可以改为遍历元素树。angular.element()
$()
angular.element(".foo").scope()
ng-scope
$(".foo").find(".ng-scope").each(function() {
var scope = $(this).scope();
});
然而,这可能有点棘手,因为find()
将在下面找到所有节点.foo
,无论它们的深度如何。您可以children()
改用,但它可能不会产生任何结果,因为 的直接后代.foo
可能不会创建新范围。