Javascript AngularJS-如何从promise中呈现模板和数据

Javascript AngularJS-如何从promise中呈现模板和数据,javascript,angularjs,ajax,Javascript,Angularjs,Ajax,好吧,我对Angular是个新手,我花了两天的时间试图找到一个好方法来做这件事,但是失败了。我也不确定标题是否好 我正在尝试制作一个带有菜单的简单页面。这个人会点击一个菜单链接,然后菜单下面的视图会相应地呈现出来(当然不会刷新整个页面)。听起来很简单 但问题是,将会有一个管理员菜单和一个普通用户菜单,所以菜单是通过ajax加载的。这是我得到的一个例子: [ { name: "Manage games", templateUrl: "/view/mygame

好吧,我对Angular是个新手,我花了两天的时间试图找到一个好方法来做这件事,但是失败了。我也不确定标题是否好

我正在尝试制作一个带有菜单的简单页面。这个人会点击一个菜单链接,然后菜单下面的视图会相应地呈现出来(当然不会刷新整个页面)。听起来很简单

但问题是,将会有一个管理员菜单和一个普通用户菜单,所以菜单是通过ajax加载的。这是我得到的一个例子:

[
    {
        name: "Manage games",
        templateUrl: "/view/mygames.html",
        url: "/games",
    },
    {
        name: "Weekly Reports",
        templateUrl: "/view/myreports.html",
        url: "/reports"
    },
    {
        name: "Manage Users",
        templateUrl: "/view/users.html",
        url: "/users",
        adminRequired: true
    }
];
加载菜单后,当单击菜单元素时,我想获取对
url
属性进行ajax调用的数据,获取该数据的模板也将是对
templateUrl
属性的ajax调用

那么,这是如何实现的呢?基本上我想要的是有一个指令/组件/任何东西,默认情况下它将是空的,不显示或呈现。但是,当我从菜单中单击一个元素时,我将$broadcast一个带有dataUrl/templateUrl的事件到指令/component/which,它将进行两个ajax调用,一个两个获取数据,另一个获取模板,在两个都完成后,它将呈现并显示在页面上

对此,我们将不胜感激

顺便说一下,我正在使用Angular 1.5.7

您应该使用路由(在我的示例中是)来实现这一点。
ui路由器有一个属性,允许您解析控制器依赖项,然后将它们注入控制器以使用它们

下面是我制作的一个完整示例(很抱歉ui太差):

HTML:


JS:

var-app=angular.module('app',['ui.router']);
应用控制器('gamesCtrl',功能(数据){
this.title=data.title;
}).
控制器('reportsCtrl',功能(数据){
this.title=data.title;
}).
控制器('usersCtrl',函数(数据,adminData){
this.title=data.title;
this.removedUsers=adminData.removedUsers;
}).
控制器('homeCtrl',函数(){
此项。项目=[{
名称:“管理游戏”,
国家:“游戏”
}, {
名称:'每周报告',
声明:“报告”
}, {
名称:“管理用户”,
声明:“用户”,
adminRequired:true
}];
});
应用程序组件('菜单'{
绑定:{
项目:“=”
},
模板:“{item.name}}”,
控制器:函数($state){
this.goToState=函数(项){
console.log('重定向到状态:'+item.state);
$state.go(item.state);
}
}
});
app.config(函数($stateProvider,$urlRouterProvider){
$stateProvider。
州(“运动会”{
url:“/游戏”,
模板:{{vm.title}}',//使用templateUrl。。
决心:{
数据:函数($q){
返回$q.when({
标题:“游戏”
})
}
},//返回返回承诺并将其注入到ctrl中的可注入项
控制器:“gamesCtrl作为虚拟机”
}).
陈述(“报告”{
url:“/reports”,
模板:{{vm.title}}',//使用templateUrl。。
决心:{
数据:函数($q){
返回$q.when({
标题:“报告”
})
}
},//返回返回承诺并将其注入到ctrl中的可注入项
控制器:“作为vm报告SCTRL”
}).
状态('用户'{
url:“/users”,
模板:{{vm.title}}删除的用户:{{user}}',//使用templateUrl。。
//返回承诺并将其注入到ctrl中的可注入者
决心:{
数据:函数($q){
返回$q.when({
标题:“用户”
})
},
adminData:函数($q){
返回$q.when({
removedUsers:['user1','user2','user3']
})
}
},
控制器:“usersCtrl作为虚拟机”
}).
状态('默认'{
url:“/default”,
模板:“这是默认状态”
});
$urlRouterProvider。否则('/default');
});

备注

  • 在配置状态时,应该使用templateUrl而不是template
  • 我使用了
    $q.when
    来演示承诺的回报。您可能会改用
    $http.get\pos
    t

或者您可以使用ngRoute。我尝试过使用ngRoute,但没有正确使用。比如,我有MenuController,在它里面我调用它来获取我显示的JSON。在获取对象后,我尝试使用app.config传递$rootProvider来定义路由,但由于某些原因,该函数永远不会被调用,并且还看到其他人有类似的问题。不确定是否可以从promise/Controllery内部调用app.config无法在controller中设置路由。您需要在配置阶段执行此操作。为此,您需要使用全局注入器$http服务发出ajax请求。我可以为你安排一切,但我现在有点懒。。但一旦你装载了路线,这就很容易了。关于
url
:最好将解析指令与一些辅助服务一起使用。要获取全局$http:
angular.injector(['ng'])。获取('$http')
查看此演示以了解如何动态加载路由:下一步是设置解析以加载数据。
<div ng-app="app">
  <div ng-controller="homeCtrl as vm">
    <menu items="vm.items"></menu>
  </div>
  <div>
    <ui-view></ui-view>
  </div>
</div>
var app = angular.module('app', ['ui.router']);

app.controller('gamesCtrl', function(data) {
  this.title = data.title;
}).
controller('reportsCtrl', function(data) {
  this.title = data.title;
}).
controller('usersCtrl', function(data, adminData) {
  this.title = data.title;
  this.removedUsers = adminData.removedUsers;
}).
controller('homeCtrl', function() {
  this.items = [{
    name: 'Manage games',
    state: 'games'
  }, {
    name: 'Weekly Reports',
    state: 'reports'
  }, {
    name: 'Manage Users',
    state: 'users',
    adminRequired: true
  }];
});

app.component('menu', {
  bindings: {
    items: "="
  },
  template: '<div ng-repeat="item in  $ctrl.items"><span ng-click="$ctrl.goToState(item)">{{item.name}}</span></div>',
  controller: function($state) {
    this.goToState = function(item) {
      console.log('redirecting to state:' + item.state);
      $state.go(item.state);
    }
  }
});

app.config(function($stateProvider, $urlRouterProvider) {
  $stateProvider.
  state('games', {
    url: '/games',
    template: '<div><h1>{{vm.title}}</h1></div>', // use templateUrl..
    resolve: {
      data: function($q) {
        return $q.when({
          title: 'games'
        })
      }
    }, // return injectables who return promises and inject them into your ctrl
    controller: 'gamesCtrl as vm'
  }).
  state('reports', {
    url: '/reports',
    template: '<div><h1>{{vm.title}}</h1></div>', // use templateUrl..
    resolve: {
      data: function($q) {
        return $q.when({
          title: 'reports'
        })
      }
    }, // return injectables who return promises and inject them into your ctrl
    controller: 'reportsCtrl as vm'
  }).
  state('users', {
    url: '/users',
    template: '<div><h1>{{vm.title}}</h1><div>Removed Users:</div><div ng-repeat="user in vm.removedUsers">{{user}}</div></div>', // use templateUrl..
    // return injectables who return promises and inject them into your ctrl
    resolve: {
      data: function($q) {
        return $q.when({
          title: 'users'
        })
      },
      adminData: function($q) {
        return $q.when({
          removedUsers: ['user1', 'user2', 'user3']
        })
      }
    },
    controller: 'usersCtrl as vm'
  }).
  state('default', {
    url: '/default',
    template: '<h1>This is the default state</h1>'
  });

  $urlRouterProvider.otherwise('/default');
});