AngularJS - 在视图外操作变量

AngularJS - manipulate variables outside ng-view

我正在尝试提供一项服务,允许我在 ng-view 之外操作变量。我使用 factory 提供了一项服务,但我不知道如何将变量从子控制器传输到父控制器(至少,这是我通过阅读 SO 上的问答找到的方法)。

例如,我希望能够从我的 articleCtrl 控制器操纵 {{ siteName }},它位于 ng-view 之外。

这是我做的:

var blogApp = angular.module('blogApp', [
    'ngRoute',
    'ngSanitize',
    'blogCtrl'
]);

blogApp.config(['$routeProvider', '$locationProvider',
    function($routeProvider, $locationProvider) {
        $routeProvider.
            when('/page', {
                templateUrl: '/angular_blog/assets/templates/page.html',
                controller: 'pageCtrl'
            }).
            when('/page/:pagePermaLink', {
                templateUrl: '/angular_blog/assets/templates/page.html',
                controller: 'pageCtrl'
            }).
            when('/article/:articlePermaLink', {
                templateUrl: '/angular_blog/assets/templates/article.html',
                controller: 'articleCtrl'
            }).
            otherwise({
                redirectTo: '/page/404',
                templateUrl: '/angular_blog/assets/templates/404.html',
                controller: 'pageCtrl'
            });
        $locationProvider.html5Mode(true);
    }]);

blogApp.factory('templateService', function() {
    return {
        siteName:'',
        tagline:'',
        pageName:''
    };
});

function articleCtrl($scope, templateService) {
   $scope.template = templateService;
}

function templateCtrl($scope, templateService) {
   $scope.template = templateService;
}

var templateCtrl = angular.module('templateCtrl', []);
var blogCtrl = angular.module('blogCtrl', []);

blogCtrl.controller('articleCtrl', ['$scope', '$routeParams', '$http', 'templateService',
function($scope, $routeParams, $http, templateService) {
    $scope.siteName = "Something awesomediculous";
}]);

blogCtrl.controller('pageCtrl', ['$scope', '$routeParams', '$http',
function($scope, $routeParams, $http) {
    // ...
}]);

blogApp.controller('templateCtrl', function($scope, templateService) {
    // ...
});
<!DOCTYPE html>
<html lang="en" data-ng-app="blogApp" data-ng-controller="templateCtrl">
<head>
 <meta charset="UTF-8">
 <title>{{ pageName + " - " + siteName }}</title>

 <script src="//ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular.min.js"></script>
 <script src="//ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular-route.min.js"></script>
 <script src="//cdnjs.cloudflare.com/ajax/libs/angular.js/1.4.3/angular-sanitize.min.js"></script>

 <base href="/angular_blog/">

</head>
<body>

 <header>
  <h1>{{ siteName }}</h1>
  <p>{{ tagline }}</p>
 </header>

 <main id="content" data-ng-view></main>

</body>
</html>

您可以将 siteName 属性 移动到 templateCtrl ,然后它将在所有视图中可用。

blogApp.controller('templateCtrl', function($scope, templateService) {

   // this is important as updates from child will not take effect if done on primitives
   $scope.site = {};
   $scope.site.siteName = "Something awesomediculous";
});

您忘记在模板 Ctrl 中将服务绑定到您应该绑定的范围。

此外,如果你有 $scope.template.myname,你应该使用 {{template.name}}

请参阅下面的工作代码。

顺便说一句,您的代码中似乎有一些不必要的功能

var blogApp = angular.module('blogApp', [
    'ngRoute',
    'ngSanitize',
    'blogCtrl'
]);

blogApp.config(['$routeProvider', '$locationProvider',
    function($routeProvider, $locationProvider) {
        $routeProvider.
            when('/page', {
                templateUrl: '/angular_blog/assets/templates/page.html',
                controller: 'pageCtrl'
            }).
            when('/page/:pagePermaLink', {
                templateUrl: '/angular_blog/assets/templates/page.html',
                controller: 'pageCtrl'
            }).
            when('/article/:articlePermaLink', {
                templateUrl: '/angular_blog/assets/templates/article.html',
                controller: 'articleCtrl'
            }).
            otherwise({
                redirectTo: '/page/404',
                templateUrl: '/angular_blog/assets/templates/404.html',
                controller: 'pageCtrl'
            });
        $locationProvider.html5Mode(true);
    }]);

blogApp.factory('templateService', function() {
    return {
        siteName:'mysitename',
        tagline:'mytagline',
        pageName:'mypagename'
    };
});

function articleCtrl($scope, templateService) {
   $scope.template = templateService;
}

function templateCtrl($scope, templateService) {
   $scope.template = templateService;
}

var templateCtrl = angular.module('templateCtrl', []);
var blogCtrl = angular.module('blogCtrl', []);

blogCtrl.controller('articleCtrl', ['$scope', '$routeParams', '$http', 'templateService',
function($scope, $routeParams, $http, templateService) {
    $scope.siteName = "Something awesomediculous";
}]);

blogCtrl.controller('pageCtrl', ['$scope', '$routeParams', '$http',
function($scope, $routeParams, $http) {
    // ...
}]);

blogApp.controller('templateCtrl', function($scope, templateService) {
    // ...
// added this line:
   $scope.template = templateService;
});
<!DOCTYPE html>
<html lang="en" data-ng-app="blogApp" data-ng-controller="templateCtrl">
<head>
 <meta charset="UTF-8">
 <title>{{ pageName + " - " + siteName }}</title>

 <script src="//ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular.min.js"></script>
 <script src="//ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular-route.min.js"></script>
 <script src="//cdnjs.cloudflare.com/ajax/libs/angular.js/1.4.3/angular-sanitize.min.js"></script>

 <base href="/angular_blog/">

</head>
<body>

 <header>
  <h1>{{ template.siteName }}</h1>
  <p>{{ template.tagline }}</p>
 </header>

 <main id="content" data-ng-view></main>

</body>
</html>