0
点赞
收藏
分享

微信扫一扫

Unity UGUI无限列表(Infinite List)


更新日期:2020年10月16日。
Github源码:​​​[点我获取源码]​​

索引

  • ​​InfiniteList​​
  • ​​使用​​
  • ​​创建InfiniteListScrollRect​​
  • ​​InfiniteListScrollRect参数详解​​
  • ​​重写数据类​​
  • ​​重写元素类​​
  • ​​编辑元素模板​​
  • ​​添加数据​​
  • ​​移除数据​​
  • ​​清空数据​​

InfiniteList

InfiniteList为基于UGUI的ScrollRect无限滚动列表的一种实现,很多时候当我们的ScrollRect的视图中包含的数据无限多时,而同时可见的数据往往只有几条,大量不可见数据被Mask组件排除在肉眼可见范围之外,但他们依然存在,内存与DrawCall的消耗仍旧同时进行着,这是相当不明智的,所以,消灭这一部分隐藏数据的真身就是InfiniteList做的主要工作。

使用

创建InfiniteListScrollRect

Hierarchy视图点击右键,选择菜单​​UI​​​ -> ​​ScrollView - InfiniteList​​,在场景中创建一个无限滚动视野的默认对象:

Unity UGUI无限列表(Infinite List)_无限列表

InfiniteListScrollRect参数详解

Unity UGUI无限列表(Infinite List)_数据_02


1.​​Element Template​​为无限列表元素的模板,你需要根据你的情况修改此模板。

2.​​Listing Direction​​列表的排列方向,支持水平垂直方向,但不支持同时水平+垂直布局。

3.​​Height​​垂直布局时,单个元素高度,水平布局时,单个元素宽度。

4.​​Interval​​列表布局时,元素之间的间隔距离。

5.其余参数为继承至ScrollRect的参数。

重写数据类

首先,你需要新建一个数据类型,继承至​​InfiniteListData​​无限列表数据基类,比如下方的InfiniteListTestData

/// <summary>
/// 无限列表测试数据
/// </summary>
public class InfiniteListTestData : InfiniteListData
{
public string Name;
}

需注意,一个数据对象对应一个无限列表中显示的元素,数据 <=> 元素,为一对一的关系。

重写元素类

然后,你需要新建一个元素类型,继承至​​InfiniteListElement​​无限列表元素基类,比如下方的InfiniteListTestElement

/// <summary>
/// 无限列表测试元素
/// </summary>
public class InfiniteListTestElement : InfiniteListElement
{
public Text Name;
public Button RemoveButton;

//元素属于的无限列表对象
private InfiniteListScrollRect _scrollRect;
//元素持有的数据
private InfiniteListTestData _data;

public override void UpdateData(InfiniteListScrollRect scrollRect, InfiniteListData data)
{
base.UpdateData(scrollRect, data);

_scrollRect = scrollRect;
_data = data as InfiniteListTestData;
Name.text = _data.Name;
RemoveButton.onClick.AddListener(() => { _scrollRect.RemoveData(_data); });
}

public override void ClearData()
{
base.ClearData();

_scrollRect = null;
_data = null;
RemoveButton.onClick.RemoveAllListeners();
}
}

需注意,​​UpdateData​​​方法为此元素在无限列表中可见时被调用,参数1为无限列表对象,参数2为此元素对应的数据。
​​​ClearData​​方法为此元素在无限列表中隐藏时被调用。

编辑元素模板

然后,需要用我们自己的元素类,替换掉元素模板​​ElementTemplate​​上的元素类:

Unity UGUI无限列表(Infinite List)_Unity_03


我们继续编辑元素模板,在其中添加一个Text用于显示文本,添加一个按钮用于点击后移除此元素(也即是从列表中移除此元素对应的数据),元素的高度我们设定为​​20​​​,在垂直排列时,无限列表只认​​高度​​​、和元素​​y​​​坐标值,​​x​​坐标值会始终被设置为0,水平排列同理。

Unity UGUI无限列表(Infinite List)_Unity_04


同时,我们要将我们设定的高度​​20​​设置到InfiniteListScrollRect的面板,元素间的间隔我们设置为​​5​​:

Unity UGUI无限列表(Infinite List)_无限列表_05

添加数据

目前无限列表只支持动态添加数据:

//无限列表对象
public InfiniteListScrollRect InfiniteList;

private string[] _surnames = new string[] { "张", "李", "王", "赵", "刘", "胡", "霍", "江", "唐", "欧阳", "司徒", "慕容", "轩辕", "皇甫", "西门" };
private string[] _names = new string[] { "三", "四", "五", "明", "强", "磊", "龙", "虎", "玉清", "博", "成", "航", "逸", "建国", "建军", "建党" };

private void Start()
{
List<InfiniteListTestData> datas = new List<InfiniteListTestData>();
for (int i = 0; i < 1000; i++)
{
InfiniteListTestData data = new InfiniteListTestData();
data.Name = (i + 1) + "." + RandomName();
datas.Add(data);
}

//添加多条数据到无限列表,当然也支持单条添加
InfiniteList.AddDatas(datas);
}

/// <summary>
/// 随机组合一个姓名
/// </summary>
private string RandomName()
{
int surname = Random.Range(0, _surnames.Length);
int name = Random.Range(0, _names.Length);

return _surnames[surname] + _names[name];
}

运行场景,可以看到1000条数据的视图中,无论怎么滚动,真实存在的元素对象只有可见区域中的几个,视图滚动时,他们轮番被对象池提取回收

Unity UGUI无限列表(Infinite List)_InfiniteList_06


水平排列模式类似:

Unity UGUI无限列表(Infinite List)_UGUI_07

移除数据

目前无限列表只支持动态移除数据,在元素类中有一句代码将移除数据的逻辑绑定到​​移除​​按钮上,当有数据被移除时,列表会自动刷新位置:

RemoveButton.onClick.AddListener(() => { _scrollRect.RemoveData(_data); });

清空数据

使用如下方式清空所有数据:

InfiniteList.ClearData();


举报

相关推荐

0 条评论