Ng-init如果尚未创建数组

时间:2013-08-30 16:53:23

标签: javascript arrays angularjs angularjs-ng-repeat

我正在尝试为应用程序构建模板,并希望显示带有名称的动态列表。所以我得到这个代码来显示列表并添加/删除行;

<table ng-init="page.businessRows = []">
<thead>
    <tr>
        <th>Company</th>
        <th>Contact</th>
        <th>Phone</th>
    </tr>
</thead>
    <tr ng-repeat="row in page.businessRows">
        <td>
            <input type="text" ng-model="row.name" />
        </td>
        <td>
            <input type="text" ng-model="row.contact" />
        </td>
        <td>
            <input type="text" ng-model="row.phone" />
        </td>
        <td>
            <button ng-click="page.businessRows.splice($index,1)">
                Remove
            </button>
        </td>
    </tr>
</table>
<button class="btn" ng-click="page.businessRows.push({})">addRow</button>

当加载此模板时,page.busnessRows很可能会加载行,因此我想将ng-init更改为仅在未初始化businessRows时创建空数组。

我尝试了ng-init="page.businessRows = page.businessRows.length < 1 ? [] : page.businessRows但是没有用。我打算如何在jsangular表达式中做条件?

所有帮助表示赞赏。提前致谢

3 个答案:

答案 0 :(得分:25)

您可以这样做:

<table ng-init="page.businessRows = page.businessRows || []">

更新

我查看AngularJS的解析器代码,注意版本1.2(当前RC)支持三元表达式。因此,如果你使用AngularJS 1.2,这也会起作用(虽然比上面的代码更冗长):

<table ng-init="page.businessRows = page.businessRows == null ? [] : page.businessRows">

请在此处查看demo

但是,如果page.businessRowsnull,原始代码可能无效,因为解析器无法取消引用length的{​​{1}}属性。所以在那里要小心。

答案 1 :(得分:3)

我认为ng-init不会正确评估条件语句。但是您可以将条件重构为控制器函数并从ng-init调用该函数。

<table ng-init="initializeBusinessRows(page.businessRows)">

将条件评估放在控制器范围的函数中。

答案 2 :(得分:1)

我认为你正试图解决错误的问题。

问题是您允许在加载或准备好数据之前执行操作。第二个问题是你在ng-click中使用了一个表达式函数或控制器函数的表达式。

因此...

  1. 如果表单尚未就绪,请禁用该按钮。
  2. 使用您的控制器控制这些互动。
  3. 所以这是控制器的一个例子。添加了$ timeout以模拟延迟的数据加载到$ scope.page变量中。

    app.controller('MyCtrl', function($scope, $timeout, $window) { 
      //Timeout to simulate the asynchronous load
      //of the page object on the $scope
      $timeout(function(){
        $scope.page = {
          businessRows: []
        };
      }, 2000);
    
    
      //scope method to add a row.
      $scope.addRow = function (){
        //for safety's sake, check to see if the businessRows array is there.
        if($scope.page && angular.isArray($scope.page.businessRows)) {
          $scope.page.businessRows.push({});
        }
      };
    
      //scope method to remove a row
      $scope.removeRow = function(index, row) {
        if($window.confirm('Are you sure you want to delete this row?')) {
          $scope.page.businessRows.splice(index, 1);
        }
      };
    });
    

    ...和HTML视图(注意ng-disabled和ng-click)(以及缺少ng-init):

      <div ng-controller="MyCtrl">
        <table>
          <thead>
            <tr>
                <th>Company</th>
                <th>Contact</th>
                <th>Phone</th>
            </tr>
          </thead>
          <tbody>
            <tr ng-repeat="row in page.businessRows">
                <td>
                    <input type="text" ng-model="row.name" />
                </td>
                <td>
                    <input type="text" ng-model="row.contact" />
                </td>
                <td>
                    <input type="text" ng-model="row.phone" />
                </td>
                <td>
                    <button ng-click="removeRow($index, row)">
                        Remove
                    </button>
                </td>
            </tr>
          </tbody>
        </table>
        <button class="btn" ng-disabled="!page" ng-click="addRow()">addRow</button>
      </div>
    

    另外,here's the obligatory Plunker for you to see this in action