Gallery在不可见情况下,onscroll造成的空指针异常

原本是做个listview,然后listView.addHeaderView(Gallery)

而且header的Gallery要一直循环轮播

这是轮播关键代码

// gallery设置spacing(间隙)后,需scroll比spacing距离稍大的位置,才能onkeydown,否则onkeydown不生效。
gallery.onScroll(null, null, 1, 0);
gallery.onKeyDown(KeyEvent.KEYCODE_DPAD_RIGHT, null);


补充下:因为gallery图片间会有叠加出现,所以要在xml中设置下spacing间隙距离。但是设置了spacing,由于有间隙,所以onkeydown方法无法使用,需要先滚动到比spacing距离稍大点位置,才能播放下一张。


在滚动listView的时候,当gallery完全不可见后,会报错


Gallery.onScroll这个方法报错,起初以为是gallery空了,但是测试发现并不是。

错误指向1008行,所以去看了下源码


源码中child已经进行了判断,所以哪里报空指针成了我心底的谜。

后来,看源码看到了。Gallery的一个方法,isShown();看见这方法,顿时乐开了。功能如其名。判断gallery当前是否显示

这是解决方法

if (gallery != null && gallery.isShown()) {
                            // gallery设置spacing(间隙)后,需scoll比spacing距离稍大的位置,才能onkeydown,否则onkeydown不生效。
                            gallery.onScroll(null, null, 1, 0);
                            gallery.onKeyDown(KeyEvent.KEYCODE_DPAD_RIGHT, null);
                        }


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,我可以为您提供一个基于 Vue 3 的虚拟滚动列表实现。 首先,我们需要通过 Vue 3 提供的 `reactive` 函数创建响应式数据。我们需要保存以下信息: - 每个列表项的高度 - 可视区域高度 - 滚动区域高度 - 当前滚动位置 代码如下: ```javascript import { reactive } from 'vue'; export default { setup() { const state = reactive({ itemHeight: 50, visibleHeight: 0, contentHeight: 0, scrollTop: 0, }); return { state, }; }, }; ``` 接着,我们需要在模板中添加一个虚拟列表容器,并根据列表项数量和高度计算出容器的高度。我们可以使用 `v-on:scroll` 监听滚动事件,并更新 `scrollTop` 的值。 ```html <template> <div class="virtual-list" ref="container" :style="{ height: `${state.contentHeight}px` }" v-on:scroll="onScroll"> <!-- 渲染列表项 --> </div> </template> ``` ```javascript export default { setup() { const state = reactive({ itemHeight: 50, visibleHeight: 0, contentHeight: 0, scrollTop: 0, }); const container = ref(null); onMounted(() => { state.visibleHeight = container.value.clientHeight; }); const onScroll = () => { state.scrollTop = container.value.scrollTop; }; return { state, container, onScroll, }; }, }; ``` 接下来,我们需要计算出当前可见的列表项的范围,并只渲染这些列表项。我们可以使用计算属性来实现这个功能。 ```html <template> <div class="virtual-list" ref="container" :style="{ height: `${state.contentHeight}px` }" v-on:scroll="onScroll"> <div :style="{ height: `${state.itemHeight * itemLength}px`, paddingTop: `${state.itemHeight * start}px` }"> <div v-for="i in end - start + 1" :key="start + i - 1" :style="{ height: `${state.itemHeight}px` }"> <!-- 渲染列表项 --> </div> </div> </div> </template> ``` ```javascript export default { setup() { const state = reactive({ itemHeight: 50, visibleHeight: 0, contentHeight: 0, scrollTop: 0, }); const container = ref(null); const items = computed(() => { const start = Math.floor(state.scrollTop / state.itemHeight); const end = Math.min(start + Math.ceil(state.visibleHeight / state.itemHeight), itemLength); return { start, end }; }); onMounted(() => { state.visibleHeight = container.value.clientHeight; state.contentHeight = state.itemHeight * itemLength; }); const onScroll = () => { state.scrollTop = container.value.scrollTop; }; return { state, container, items, onScroll, }; }, }; ``` 最后,我们需要在列表项中使用 `v-show` 来根据当前列表项的索引判断是否需要显示。由于只渲染可见的列表项,这可以有效提高性能。 ```html <template> <div class="virtual-list" ref="container" :style="{ height: `${state.contentHeight}px` }" v-on:scroll="onScroll"> <div :style="{ height: `${state.itemHeight * itemLength}px`, paddingTop: `${state.itemHeight * items.start}px` }"> <div v-for="i in items.end - items.start + 1" :key="items.start + i - 1" :style="{ height: `${state.itemHeight}px` }"> <div v-show="items.start <= i && i <= items.end"> <!-- 渲染列表项 --> </div> </div> </div> </div> </template> ``` 这样,一个基于 Vue 3 的虚拟滚动列表就完成了。完整代码如下: ```javascript <template> <div class="virtual-list" ref="container" :style="{ height: `${state.contentHeight}px` }" v-on:scroll="onScroll"> <div :style="{ height: `${state.itemHeight * itemLength}px`, paddingTop: `${state.itemHeight * items.start}px` }"> <div v-for="i in items.end - items.start + 1" :key="items.start + i - 1" :style="{ height: `${state.itemHeight}px` }"> <div v-show="items.start <= i && i <= items.end"> <!-- 渲染列表项 --> </div> </div> </div> </div> </template> <script> import { computed, reactive, ref, onMounted } from 'vue'; export default { props: { itemLength: { type: Number, required: true, }, }, setup(props) { const state = reactive({ itemHeight: 50, visibleHeight: 0, contentHeight: 0, scrollTop: 0, }); const container = ref(null); const items = computed(() => { const start = Math.floor(state.scrollTop / state.itemHeight); const end = Math.min(start + Math.ceil(state.visibleHeight / state.itemHeight), props.itemLength); return { start, end }; }); onMounted(() => { state.visibleHeight = container.value.clientHeight; state.contentHeight = state.itemHeight * props.itemLength; }); const onScroll = () => { state.scrollTop = container.value.scrollTop; }; return { state, container, items, onScroll, }; }, }; </script> ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值