AngularJS是否具有在div中对属性进行别名的语法?

Ken*_*ows 10 javascript alias angularjs

这是一个奇怪的问题,但这里的想法是:

假设我有一个复杂的JSON对象从HTTP调用返回并附加到$scope.像这样的东西:

$scope.obj = {
    user: {
        id: 10,
        name: { first: 'Joe', last: 'Smith' },
        contact: {
            home: {
                street: '101 First St.',
                city: 'Myville',
                state: 'Jokelahoma',
                zip: '98765'
            },
            email: 'joeshmoe@gmail.com',
            phone: '+12345678901'
        }
    },
    purchase_hist: [
        { item_id: 11004, date: 'Thu, 06 Aug 2015 13:51:17 GMT' },
        { item_id: 97020, date: 'Fri, 31 Jul 2015 18:57:57 GMT' }
    ]
}
Run Code Online (Sandbox Code Playgroud)

现在,如果我想在AngularJS partial中显示购买历史的概述,我可以这样做:

<table>
    <tr ng-repeat="p in obj.purchase_hist">
        <td>{{p.item_id}}</td>
        <td>{{p.date}}</td>
    </tr>
</table>
Run Code Online (Sandbox Code Playgroud)

关于这种格式真正方便的事情(尽管这里的道具并不是很明显),所描述的购买是别名的p.我不必这样做obj.purchase_hist[0].item_id,我可以做p.item_id.

但是当我去显示用户的家庭住址时呢?我真的必须这样做吗?:

<div>
    <p>{{obj.user.contact.home.street}}</p>
    <p>{{obj.user.contact.home.city}}</p>
    <p>{{obj.user.contact.home.state}}</p>
    <p>{{obj.user.contact.home.zip}}</p>
</div>
Run Code Online (Sandbox Code Playgroud)

这真的很冗长.我宁愿使用类似于controller as ...语法的东西,如下所示:

<div ng-alias="obj.user.contact.home as uhome">
    <p>{{uhome.street}}</p>
    <p>{{uhome.city}}</p>
    <p>{{uhome.state}}</p>
    <p>{{uhome.zip}}</p>
</div>
Run Code Online (Sandbox Code Playgroud)

AngularJS中是否存在这样的东西?不幸的是我不能在我的环境中使用插件,所以我特意寻找一种可以这种方式工作的角度核心部分.

谢谢!

Pau*_*tes 8

我写了这个小指令,它允许你执行你想要的:

指令ngAlias

(function(){

  function ngAlias($compile) {
    return {
        restrict: "A",
        link: function(scope, element, attrs) {
          var args = attrs.ngAlias.split('as').map(function(elm){return elm.replace(/ /g,'')});

          scope[args[0]] = '';

          var dot = args[1].split('.');

          var object = {};

          dot.forEach(function(value, index){
            index === 0
            ? object = scope[value]
            : object = object[value] === null ? object[value] = {} : object[value];
          });

          console.log(object)

          scope[args[0]] = object;
        }
    };
  }

angular
  .module('app')
  .directive('ngAlias', ngAlias);


})();
Run Code Online (Sandbox Code Playgroud)

例如,在控制器中设置对象

调节器

(function(){

function Controller($scope) {


  $scope.obj = {
    toto: {
      nom: 'toto',
      prenom: 'tata'
    }
  };

}

angular
.module('app', [])
.controller('ctrl', Controller);

})();
Run Code Online (Sandbox Code Playgroud)

你可以使用它:

HTML

  <body ng-app="app" ng-controller="ctrl">

    <div ng-alias="toto as obj.toto">
      {{toto.nom}}
    </div>

  </body>
Run Code Online (Sandbox Code Playgroud)

  • ngInit half 解决了这个问题,但它是一次性的。如果我使用`ng-init="uhome = obj.user.contact.home"` 那么`obj.user.contact.home` 的值在视图加载后会发生变化,则没有2 路绑定会更新该值`uhome`。该指令将使这项工作发挥作用。 (2认同)

Ken*_*ows 6

@PaulBoutes提供了我需要的答案,他应该得到信用; 我只是想根据他的答案添加我所确定的指令版本.

app.directive('alias', function() {
    return {
        restrict: 'A',
        link: function(scope, element, attrs) {
            var splits = attrs['alias'].trim().split(/\s+as\s+/);
            scope.$watch(splits[0], function(val) {
                scope.$eval(splits[1]+'=('+splits[0]+')');
            });
        }
    };
});
Run Code Online (Sandbox Code Playgroud)

和Paul一样基本的想法,只是清理了一点,并在空白等方面做了一点灵活.

用法示例:

<div data-alias="obj.user.contact.home as uhome">
    <p>{{uhome.street}}</p>
    <p>{{uhome.city}}</p>
    <p>{{uhome.state}}</p>
    <p>{{uhome.zip}}</p>
</div>
Run Code Online (Sandbox Code Playgroud)


小智 5

我刚刚遇到了这个问题并测试了 ngAlias 指令,它可能会也可能不会正常工作,我不知道,因为我遇到了问题,可能是由于其他一些不相关的错误,我决定采用这种更简单的方法:

<div ng-repeat="uhome in [obj.user.contact.home]">
    <p>{{uhome.street}}</p>
    <p>{{uhome.city}}</p>
    <p>{{uhome.state}}</p>
    <p>{{uhome.zip}}</p>
</div>
Run Code Online (Sandbox Code Playgroud)

多田!“obj.user.contact.home”现在别名为“uhome”。我相信这个解决方案实际上也正是您提出这个问题时想要的,因为它确实使用了 ng-repeat,因此具有 ng-repeat 内置别名机制的所有好处。