问题描述:做一个音乐播放器的UI,想要使用slider做歌曲进度条,能拖动那种。为了使进度条自动向前,设置了一个interval,每500ms更新一次,用audioctx.currentTime更新,有拖动的时候用拖动值更新。拖动进度条的时候发现:从B点拖到A点,小圆圈回先退回B点,然后弹回A点。声音播放没有回退现象,就是进度条piaji一下看得不爽。
解决方案:经过一系列尝试,最后在三个地方log:seek后的currentTime,拖动值,以及用来更新的currentTime:
slider(e:any){ let value=Number(e.detail.value); audioctx.seek(value); console.log("0:"+audioctx.currentTime);this.setData({ isChanging:false, timeId:setInterval(()=>{ if(this.data.isPlaying&&!this.data.isChanging){ this.update(); } },500) }) }, update(newVal?:Number){ let value=newVal?newVal:audioctx.currentTime; console.log("1:"+value); console.log("2:"+audioctx.currentTime); let max=audioctx.duration; ...... },
log结果如下:
可以发现是seek后currentTime并没有立即更新导致的回退。但不知道为什么setTimeout并没有用,于是只能自己算时间了,拖动时清除上一个interval,拖动结束重新定时,反正误差不大:
slider(e:any){ let value=Number(e.detail.value); audioctx.seek(value); console.log("0:"+audioctx.currentTime); let i=0; this.setData({ isChanging:false, timeId:setInterval(()=>{ if(this.data.isPlaying&&!this.data.isChanging){ this.update(value+0.5*i); i++; } },500) }) }, update(newVal?:Number){ let value=newVal?newVal:audioctx.currentTime; console.log("1:"+value); console.log("2:"+audioctx.currentTime); let max=audioctx.duration; while(value>lyricTime[lyricIndex]&&value>lyricTime[lyricIndex+1]){ lyricIndex++; if(lyricIndex===lyricTime.length) break; } while(value<lyricTime[lyricIndex]&&value<lyricTime[lyricIndex-1]){ lyricIndex--; if(lyricIndex===0) break; } this.setData({ max:max, value:value, currentTop:lyricPos[lyricIndex]-lyricPos[0], currentIndex:lyricIndex }); },
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?