将API添加到AngularJS指令

时间:2016-05-03 03:13:25

标签: angularjs angular-directive

注意:我已复制了我的代码here in JS Bin

我有一个指令,它将一系列项目打印到网页上。假设行' console.log("添加")'实际上是复杂的逻辑,而且无论控制器使用它,我们都希望每次都能执行该指令。它可以拨打AJX电话,表示已添加新记录。

所以我想象指令中会有一个函数来执行此操作。而不是使用" $ scope.items"要添加新项,控制器将在指令中调用此函数。除非有更好的方法,你能告诉我如何处理这个问题吗?

HTML:

<!DOCTYPE html>
<html>
<head>
<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.2.14/angular.min.js"></script>
  <meta charset="utf-8">
  <title>JS Bin</title>
</head>
<body ng-app="app">
  <div ng-controller="MyCtrl">
    <input type="text" ng-model="newitem.name"/>
    <button type="button" ng-click="addNewItem(newitem)">Add Item</button>
    <menu items="items"/>
  </div>
</body>
</html>

JavaScript的:

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

app.controller('MyCtrl', function($scope) {
  $scope.items = [
    {name: "item1"},
    {name: "item2"},
    {name: "item3"},
    {name: "item4"}
  ];

  $scope.addNewItem = function(newItem) {
    $scope.items.push(angular.copy(newItem));
    console.log("added");  //PRETEND THIS IS COMPLEX LOGIC WE WANT MOVED TO DIRECTIVE
  };
});

app.directive("menu", function(){
  return {
    restrict: "E",
    scope: {
      items: "=" 
    },
    template: "<div ng-repeat='item in items'>{{item.name}}</div>"
  };
});

1 个答案:

答案 0 :(得分:2)

通常你通过服务发出ajax请求。

假设您想通过REST API将添加的项目保存到数据库中,然后接收响应并将其解析到菜单列表,然后您将执行以下操作:

app.service('MenuService', function($http) {
  this.addItem = function(item) {
    return $http.post('/rest/menu', {menuItem: item});
  }
});

回到你的控制器:

app.controller('MyCtrl', function($scope, MenuService) {
  $scope.items = [
    {name: "item1"},
    {name: "item2"},
    {name: "item3"},
    {name: "item4"}
  ];

  $scope.addNewItem = function(newItem) {
    MenuService.addItem(newItem).then(function(itemFetchedFromWebService) {
      $scope.items.push(itemFetchedFromWebService);
    }, function(error) {console.log(error); });
  };
});

如果您不需要操作dom而不是ng-repeat指令,并且您也不需要通过属性接收其他数据,那么您并不需要这里的指令。控制器应该已经完成​​了工作。

修改

如果您更喜欢使用该指令,可以使用链接功能:

app.directive("menu", function(MenuService){ //Note the added dependency
  return {
    restrict: "E",
    scope: {
      items: "=" 
    },
    template: "<div ng-repeat='item in items'>{{item.name}}</div>",
    link: function(scope) {
      scope.addNewItem = function(newItem) {
       MenuService.addItem(newItem).then(function(itemFetchedFromWebService){
        scope.items.push(itemFetchedFromWebService);
       }, function(error) {console.log(error); });
      };
    }
  };
});

链接功能为您提供的内容:

  • 当前范围对象(在您的情况下为隔离范围)。
  • 该指令的元素(包含在angular.element对象中),您可以使用&#34;元素[0]&#34;
  • 访问dom元素
  • 包含元素属性的对象。

您可以在链接函数中使用另外两个参数:(超出问题范围)

第四个参数允许你在当前元素或父/兄弟元素中使用其他指向性的控制器。

第五个参数是transclude函数,它允许你操纵被转换的元素。