大家好,今天要做的是捕捉ListView里面显示在萤幕上的是哪一个Item,今天会用到NotificationListener、HitTestResult、MetaData、ShaderMask
先为ListView
添加监听的NotificationListener
onNotification
会传出很多滚动的讯息,例如在列表的ScrollStartNotification
开始滚动、ScrollUpdateNotification
滚动更新、ScrollEndNotification
滚动结束的状态等
NotificationListener(
onNotification: (noti) {
return true;
},
child: ListView.builder(
itemCount: 10,
itemBuilder: (BuildContext context, index) {
return _buildItem(index);
},
),
),
要找到在列表的什麽位置是简单的事情,因为可以透过ScrollController.offset
取得,但是单纯位置不足以判断现在显示的哪一个Widget。除非知道每一个Item的高度,去算现在是第几个。不过,今天我使用的方法是用MetaData。
元数据,用MetaData
可以把一些讯息放在渲染树中,让用户交互的时候可以提供讯息
HitTestBehavior
是一个枚举类,具体请参阅这里
_buildItem(int index) {
return MetaData(
metaData: index, //这边希望放入的是index资讯
behavior: HitTestBehavior.translucent,
child: _buildComingSoonItem(index),
);
}
T getMeta<T>(double x, double y) {
//这两行主要目的是找出一个Offset,要取得讯息的位置
var renderBox = context.findRenderObject() as RenderBox;
var offset = renderBox.localToGlobal(Offset(x, y));
//这两行是对这个位置做点击测试
HitTestResult result = HitTestResult();
WidgetsBinding.instance.hitTest(result, offset);
//从测试结果取出metaData讯息
for (var i in result.path) {
if (i.target is RenderMetaData) {
var d = i.target as RenderMetaData;
if (d.metaData is T) {
return d.metaData as T;
}
}
}
return null;
}
在onNotification
里面调用getMeta,取得讯息就可以对其他UI做控制了
Future.microtask
onNotification: (noti) {
Future.microtask(() {
var info = getMeta(0, MediaQuery.of(context).size.height * .5);
print("scrolling to ${info}");
if (info != null) {
setState(() {
visibleIndex = info;
});
}
});
if (noti is ScrollEndNotification) {
print('开始播放');
}
return true;
},
直接将原本的每个Item包起来,可以透过LinearGradient快速定义shader
LinearGradient(colors: [_color, _color]).createShader(rect)
_buildComingSoonItem(int index) {
//判断是否是中间正在显示的Widget,来使用遮罩
Color _color = Colors.white.withOpacity(visibleIndex != index ? 0.4 : 1.0);
return ShaderMask(
shaderCallback: (rect) {
return LinearGradient(colors: [_color, _color]).createShader(rect);
},
child: Padding(...),
);
}
今日完成的效果,可以看到除了正中间的正常显示,其他的都是被遮住的
<<: Day 26:ELK stack for observation system
嗨大家!昨天跟大家分享一个 library 叫做 SWR,文章在这里~ 今天用 SWR 新增了小功能...
Sometimes PST files exceed the storage limit, whic...
哈罗大家好,我是黄奇昌 我就读岭东科技大学视觉传达设计系 今年是第一次参加13th铁人赛,想跟大家好...
前情提要 我是 siriuskoan,在这三十天内会把一些关於 flask 的知识写成文章,以供自己...
昨天介绍了什麽是IDE,今天就要介绍我常用的IDE了 IDE大比较 1. Visual Studio...