【问题标题】:Unable to update the rootScope in angular无法以角度更新 rootScope
【发布时间】:2016-01-27 15:57:08
【问题描述】:

我正在尝试从一个有角度的控制器向 php 文件发送请求并获得响应。我将响应存储在 rootScope 变量中,该变量在 controller.run() 方法中初始化为 0。

现在我尝试在另一个控制器中使用更新后的 rootScope 以显示来自 php 页面的响应。但是 rootScope 没有更新,仍然显示为 0。

这是我的代码。

下面是初始化rootScope的run方法

adminController.run(function ($rootScope) {
    $rootScope.n = 0;
});

以下是控制器 1 的代码,我在其中请求 php 页面的响应并更新 rootScope 变量。

adminController.controller('adminLoginController', function($scope,$rootScope,$http,$window) {

    $scope.loginCheck = function(event,user){
        var request = $http({
            method: "post",
            url: "../_/php/loginCheck.php",
            headers: { 'Content-Type': 'application/x-www-form-urlencoded'     }
        });
        request.success(function (data) {
            $rootScope.n=data;
            $rootScope.$apply();
            $window.location.href = 'admin.html#admin_home';       
        });
    }
});

这是我使用 rootScope 变量的第二个控制器的代码。问题来了,因为 rootScope 没有得到更新并且只向我显示它初始化的 0。

adminController.controller('adminHomeController', function($scope,$rootScope,$http,$window) {
    $scope.uname=$rootScope.n;
    alert($scope.uname);
});

谁能告诉我哪里出错了。

【问题讨论】:

  • $rootScope.$apply(); 不需要,摘要循环使用http 自动运行。任何控制台错误?尝试将控制台日志放入您的 .run 以查看它是否在导航上重新运行?
  • 我认为你的控制器首先加载然后 $rootScope 值更新。你能显示更多提示吗
  • @DylanWatt 我在控制器 1 的运行方法和成功方法中都尝试了日志。它没有显示控制器 1 的日志。是的,运行方法再次运行...跨度>
  • @BaradwajAryasomayajula :如果建议解决了您的问题,您可以将任何您认为最适合您要求的答案标记为已接受

标签: angularjs angularjs-scope angular-controller angularjs-rootscope


【解决方案1】:

您的问题听起来像是时间问题。要使用$rootScope 在控制器之间进行通信,您可以设置一个事件来监听变化。

更新根范围:

$rootScope.$broadcast('n', data);

监听变化:

$rootScope.$on('n', function (event, data) {
    //do something with new value 'data'
});

【讨论】:

  • 投反对票的原因?这不仅对我自己有帮助,对任何阅读此答案的人都有帮助
【解决方案2】:

HTML

<body ng-app="adminController">

<div ng-controller="adminLoginController">
        <button ng-click="loginCheck()">loginCheck</button>
    </div>

    <div ng-controller="adminHomeController">
    <button ng-click="getval()">getVal</button>
        rootscope val {{uname}}
    </div>
</body>

控制器

var app = angular.module('adminController', []);

app.run(function ($rootScope) {
    alert("run");
    $rootScope.n = 0;
});

adminController.controller('adminLoginController', function($scope,$rootScope,$http,$window) {

    $scope.loginCheck = function(){
        alert("Inside loginCheck");
        $rootScope.n = 1;      
    }
});

adminController.controller('adminHomeController', function($scope,$rootScope,$http,$window) {

    $scope.getval = function() {
        $scope.uname = $rootScope.n;
    } 
});

如果您的两个控制器同时实例化,那么您需要使用 @aw04 建议的使用 $broadcaste、$on 和 $emit 的基于偶数的通知。

【讨论】:

    【解决方案3】:

    在变量上添加$watch

    adminController.controller('adminHomeController', function($scope,$rootScope,$http,$window) {
        $scope.$watch(
            function watchFn(){ return $rootScope.n; },
            function listener(newValue, oldValue) {
                $scope.uname=newValue;
            }
        );
    });
    

    欲了解更多信息,请参阅AngularJS $watch API Reference


    请记住,将 $rootScope 与数据混为一谈是不明智的。持久性数据最好保存在服务中。

    app.factory("LoginCheck", function($http) {
        var n = 0;
        var request;
        function getN() { return n; };
        function setN(newN) { n = newN; return n; } 
        function getRequest { return request; };
        function check(user) { 
            request = $http({
                method: "post",
                url: "../_/php/loginCheck.php",
                headers: { 'Content-Type': 'application/x-www-form-urlencoded'     }
            });
            var derivedRequest = request.then(function (response) {
                setN(response.data);
                //return for chaining
                return response;
            });       
            request = derivedRequest;
            return request;
        };
        return {
            getN: getN,
            setN: setN,
            getRequest: getRequest,
            check: check
        };
    });
    

    然后在你的 LoginController 中:

    adminController.controller('adminLoginController', function($scope,$window,LoginCheck) {
    
        $scope.loginCheck = function(event,user){
            var req = LoginCheck.check(user);
            req.then(function (response) {
                $window.location.href = 'admin.html#admin_home';       
            }).catch(function (errorResponse) {
                console.log(errorResponse.status);
            });
        };
    });
    

    在您的 HomeController 中:

    adminController.controller('adminHomeController', function($scope,LoginCheck) {
        if ( LoginCheck.getN() ) {
            $scope.uname = LoginCheck.getN();
        } else {
            LoginCheck.getRequest().then( function() {
                $scope.uname = LoginCheck.getN();
            });
        }; 
    });
    

    【讨论】:

      猜你喜欢
      • 2021-06-19
      • 1970-01-01
      • 2021-07-21
      • 2020-01-21
      • 2020-11-03
      • 2021-03-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多