根据功能需求,花了好长时间,终于完成了自己第一个小程序自定义组件开发,用于音频播放与暂停控制,同时用按钮外面的圆环表进播放进度。效果图如下:
第一个图标是待播放状态,第二个图标是播放中,圆环按百分比显示进度。由于是自己开发的第一个自定义组件,还是遇到很多坑,记录如下:
一、自定义组件
进度圆环组件,主要有两种思路,第一种是用canvas在图框上绘制,另一种用CSS生成,两种组件都试过,还是觉得用canvas好控制一些。小程序自定义件四个文件分别如下。
1.1 wxml文件
先根据调用组件上传来的会制圆环box大小
第一个组件是图中play与pause按钮,根据状态动态显示。根据画线宽度(2),反复测试后,size比box框小10显示比较协调。
在这理特别注用,经过反复对比全用的是cover-image,用image在地图上显示图标有问题,但cover-image会影响有些参数传递,要特别注意。
另外注意一下,图片文件名的大小写,在开发工具调试时,大小写不敏感可以正常显示,但在真机环境下大小写是敏感的,导致我在真机时显示不正常,pause按钮不显示,前面一直以为父子组件参数传递不正常,或且子给件没有动态刷新,或都cover-image阻止了参数传递,导致解决这个问题起了好多弯路。
第二个组件是圆环背景,为浅色,在js文件中定义
第三个组件是根据播放进度比例显示,为明亮色或彩色,具体在js文件中定义
在wxml文件中还一个draw参数,是由调用组件传递过来,以便在同一页面有多个圆环时用ID区别开,以便于后观通过父组件,对不同子组件的控制。
<!-- components/circle/circle.wxml -->
<view class="circle_box" style="width:{
{size}}px;height:{
{size}}px">
<cover-image class='audioImg' style="width:{
{size-10}}px;height:{
{size-10}}px" src="{
{isPlay?'/icon/pause.png':'/icon/play.png'}}"></cover-image>
<canvas class="circle_bg" canvas-id="{
{draw}}bg" style="width:{
{size}}px;height:{
{size}}px"></canvas>
<canvas class="circle_draw" canvas-id="{
{draw}}" style="width:{
{size}}px;height:{
{size}}px"></canvas>
</view>
1.2 wxss文件
样式文件不多,分别定义如下。
.circle_box,.circle_draw{
position: relative; }
.circle_bg{
position: absolute;}
.circle_box{
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
}
.audioImg{
position: absolute;
}
1.3 json文件
一定要将自己定义为组件,能便后面利用。
{
"component": true,
"usingComponents": {
}
}
1.4 js文件
程序文件注意事项:
1、组件有properties和data,data只有lifetimes生命周期的atached加载一次,用properties可以根据父组件参数修改而改变,本子组件有4个properties参数,分别是画板元素代码draw,显示比例per,半径r,缺省为30px,是否处于播放状态。
子组件data数据不会随父组件直接修改,要修改需要获取到子给件id,通过init方法修改。
2、圆环动态修改,在本子组件定义了一个updateCircle函数,用来更新圆环显示的比例。
/* components/circle/circle.js */
Component({
options: {
multipleSlots: true // 在组件定义时的选项中启用多slot支持
},
properties: {
draw: {
//画板元素名称id
type: String,
value: 'draw'
},
per:{
//百分比 通过此值转换成step
type: String,
value: '0'
},
r:{
//半径
type: String,
value: '30'
},
isPlay:{
//是否播放状态
type: Boolean,
value: false,
},
},
data: {
/* 私有数据,可用于模版渲染 */
step: 1, //用来算圆的弧度0-2
size:0, //画板大小
screenWidth:750, //实际设备的宽度
txt:0,
},
methods: {
/**
* el:画圆的元素
* r:圆的半径
* w:圆的宽度
* 功能:画背景
*/
drawCircleBg: function (el, r, w) {
const ctx = wx.createCanvasContext(el,this