如何在使用ng-repeat时仅在字段发生变化时显示?

How to display a field only when it changes when using ng-repeat?

我运行通过collection条报价记录ng-repeat是这样的:

<div ng-repeat="quote in quotes">
    <h3>{{quote.chaptertitle}}</h3>
    <div>"{{quote.body}}"</div>
</div>

每一章都有很多引用,当然我只想在显示记录时第一次出现时显示章节标题。

执行此操作的最佳方法是什么,例如在范围内创建一个保持变量,然后使用 ng-if 来检查它,或者有另一种更简单的方法来使用 ng-repeat?

您可以更改引号数组,如果标题相同,则将其设置为未定义:

var chapterTitle;
for (var i = 0; i < $scope.quotes.length; i++) {
    var quote = $scope.quotes[i];
    if (quote.chaptertitle !== chapterTitle) {
      chapterTitle = quote.chaptertitle
    }
    else {
      quote.chaptertitle = undefined;
    }
}

然后在您看来您可以在 h3 上使用 ng-if:

<div ng-repeat="quote in quotes">
  <h3 ng-if="quote.chaptertitle != undefined">{{quote.chaptertitle}}</h3>
  <div>"{{quote.body}}"</div>
</div>

Plunkr

但通常我会更改我的数据结构(在后端),所以它会是这样的:

$scope.chapters = [
    {
        title: 'one',
        quotes: [
            {
                body: 'body1'
            },
            {
                body: 'body2'
            }
        ]
    },
    {
        title: 'two',
        quotes: [
            {
                body: 'body3'
            },
            {
                body: 'body4'
            }
        ]
    }
];

那么你将使用嵌套重复:

<div>
  <h3 ng-repeat-start="chapter in chapters">{{chapter.title}}</h3>
  <div ng-repeat="quote in chapter.quotes" ng-repeat-end>"{{quote.body}}"</div>
</div>

您可以使用当前索引并与之前的记录进行比较。使用您的 html

<div ng-controller="MyCtrl">
    <div ng-repeat="quote in quotes">
         <h3 ng-hide="equalPrevious($index)">{{quote.chaptertitle}}</h3>
        <div>"{{quote.body}}"</div>
    </div>
</div>

使用以下控制器

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

function MyCtrl($scope) {
    $scope.quotes = [
      { chaptertitle: 'Hello', body: '1' },
      { chaptertitle: 'Hello', body: '2' },
      { chaptertitle: 'Hello1', body: '3' }
    ];

    $scope.equalPrevious = function(index) {
        return index != 0 &&
            $scope.quotes[index].chaptertitle == $scope.quotes[index -1].chaptertitle;
    };
}

当运行(和jsfiddle

时会显示如下结果

你好
“1”
“2”
你好1
“3”

您可能希望按 chaptertitle

对报价进行分组
<div ng-repeat="(key, value) in quotes | groupBy: 'chaptertitle'">
    <h3>{{ key }}</h3>
    <div ng-repeat="quote in value">
        "{{quote.body}}"
    </div>
</div>

更新: groupBy 过滤器来自 https://github.com/a8m/angular-filter, hosted here http://cdnjs.com/libraries/angular-filter

Plunker

你确实可以使用 ng-if:

<h3 ng-if="quote.chaptertitle != quotes[$index-1].chaptertitle">{{quote.chaptertitle}}</h3>

我个人更愿意首先使用嵌套结构(章节 -> 引用)。其他人建议的现有分组解决方案也很好。