前言
使用过echart插件开发小程序的同学,应该都会遇到这个问题。尤其常见的是需求是:顶部固定,其他内容可以滚动 ,这时你会发现绘制的图形是会穿透所固定的顶部,并且无论你怎么给顶部区域设置css的z-index都是无效的。
来看下案发现场例子:
其实微信官方有写到,诸如canvas,video等组件是使用客户端创建的原生组件,而原生组件的层级是最高的,所以页面中的其他组件无论设置 z-index 为多少,都无法盖在原生组件上。为了解决这个问题,官方提供了cover-view 与 cover-image这两个组件,这两个组件其实也是使用原生组件进行渲染,所以可以在显示层级上覆盖其他原生组件,但是也有一些明显使用限制:
我从实际开发来看,最棘手的限制就是cover-view能嵌套的组件太少,内部只能嵌套cover-view,cover-image及button,样式上不支持单边border,单边radius,及shadow阴影。
实战踩坑分享(基于taro框架开发)
头部实现
其实这里只需要将普通的view组件换成cover-view即可,fixed定位于顶部
画线
既然无法实现单边border,那要怎么画单条线呢?
聪明的你可能想到了利用移动端1px线条的画法,例如:
background-size: 100% 1px;
background-repeat: no-repeat;
background-position: bottom left;
background-image: linear-gradient(0, #ededed, #ededed 50%, transparent 50%);
遗憾的是经过测试,该写法无效;
需要注意的是,很多情况下开发者工具模拟器可以达到正常想要效果,真机就不能,所以开发时一定要用真机调试
这边就利用一个空壳cover-view实现,例如底部线条:
.cover-border-b{
position: absolute;
bottom: 0;
left: 0;
width: 100%;
height: 2px; // 这边开发用了taro框架,实际高度相当于小程序2rpx单位
background-color: #ededed; // 边框颜色
}
使用:放置直接父元素下面,并将其父元素设置position:relative属性;
<CoverView className='cover-border-b'></CoverView>
弹出层选择器
穿透问题
同理,将弹出层实现全部换成cover-view,上面提到过cover-view能嵌套的组件只有cover-view,cover-image及button,这样有个很大的问题就是无法使用picker组件了。
遇到的坑
正常情况下,弹出层都会以一个单独的组件抽离出来。这边实践发现,抽离出来后,却无法直接在组件中通过this.props.children获取到数据进行渲染:
<FloatLayoutCover>
<CoverView>test text</CoverView>
<CoverView>test text</CoverView>
<CoverView>test text</CoverView>
</FloatLayoutCover>
以上写法真机中是无法渲染出数据的,测试发现只传文字时才会进行渲染:
<FloatLayoutCover>
test text
test text
test text
</FloatLayoutCover>
但这个写法是毫无意义的,都无法对其设置样式。最后是以数据形式传入,在组件内部对数据进行处理:
<FloatLayoutCover
title='选择时间'
isOpened={panelShow}
onConfirm={this.handleResult.bind(this)}
showCloseIcon={false}
contentHeight={400}
data={data}
activeIndex={activeIndex}
>
</FloatLayoutCover>
<CoverView className='layout-body' style={{height: contentHeight + 'rpx'}}>
{
data.map((item, index) => {
return
<CoverView
className={`${index === activeIndex && 'active'} option-item`}
onClick={() => this.props.onConfirm(index)}>
{item}
</CoverView>
})
}
</CoverView>
最后实现效果:
最后
如果你也是基于taro框架进行echart开发的话,在初始编译完成打开项目运行的时候(npm run dev:weapp),应该也会遇到下面这个报错。
被这个问题坑了很长一段时间,最后发现是每次重新编译时,taro框架不仅仅是将我存放echart.js文件移动到dist对应目录下,还对它进行了某种处理,导致实际运行的dist目录下的echart.js文件被破坏了,只能每次冷编译完成后,手动将开发目录下的echart.js替换掉dist目录下编译生成的。
如果你对此问题有更好的办法,欢迎留言,谢谢。