使用md-virtual-repeat实现无限滚动

还在jQuery时代,就看到那种无限滚动按需加载效果,后来用ngInfiniteScroll实现了一个。最近深度使用material时,发现框架自带的md-virtual-repeat-container结合md-virtual-repeat也能很好地实现无限滚动。

一、md-virtual-repeat-container

md-virtual-repeat-container是md-virtual-repeat组件的滚动容器。它有以下属性:

  • md-top-index:将滚动容器顶部项索引绑定到$scope。它可以读取和设置滚动位置;
  • md-orient-horizontal:确定容器是否应水平滚动 (默认为方向是垂直滚动);
  • md-auto-shrink:当该数值小于原始尺寸时, 容器将收缩以适合项目数量;
  • md-auto-shrink-min:md-auto-shrink将收缩到的最小项目数(默认值: 0)。

二、md-virtual-repeat

md-virtual-repeat替换ng-repeat只呈现足够的html元素来填充容器并在用户滚动时重用它们。它有以下属性:

  • md-item-size:重复元素的高度或宽度 (每个元素必须相同)。这是可选的。如果丢失, 则尝试从dom读取大小, 但仍假定所有重复的节点具有相同的高度或宽度;
  • md-extra-name:为重复作用域上可以分配当前迭代项计算其他名称(needed for use in md-autocomplete);
  • md-on-demand:如果设置,将md-virtual-repeat参数视为可以获取行的对象而不是数组。此对象必须使用两个方法实现以下接口。

1) getItemAtIndex − function(index) [object]:尚未加载时该索引对应的项或null(应在该情况下开始下载该项目)。
2) getLength − function() [number]:md-virtual-repeat-container调整大小后的数据长度。理想情况下, 当计数已知时, 此方法应返回它。否则, 返回比当前加载的项更高的数字以生成无限滚动行为。

三、示例

angular
  .module('myApp', ['ngMaterial'])
  .controller('AppCtrl', function($timeout, $filter) {
    this.infiniteItems = {
      loaded: 0,
      toLoad: 0,
      items: [],
      getItemAtIndex: function(index) {
        if (index > this.loaded) {
          this.fetchMore(index);
          return null;
        }
        return this.items[index];
      },

      getLength: function() {
        return this.loaded + 5;
      },

      fetchMore: function(index) {
        if (this.toLoad < index) {
          this.toLoad += 20;
          $timeout(function() {
            var arr = [];
            for (var i = 1; i < 21; i++) {
              arr.push({
                name: 'file' + (i + this.loaded).toString(),
                size: 1000 + Math.ceil(1000 * Math.random()),
                createTime: new Date().getTime() - Math.ceil(3600000 * 24 * 30 * Math.random())
              });
            }
            this.items = this.items.concat(arr);
            this.loaded = this.toLoad;
          }.bind(this), 300);
        }
      }
    }
  })

本实例中,由于使用了md-on-demand属性,所以必须getItemAtIndex和getLength两个方法。其中getLength返回this.loaded + 5,比当前加载的项更高,这样才能生成无限滚动行为。

为了演示方便我们用的异步模拟数据,我们在真实环境中应该是调用Service来实现。点击此处查看最终效果

发表评论

电子邮件地址不会被公开。 必填项已用*标注