瀏覽代碼

在微信中运行的时候,微信没有开放自动加载资源的权限,所以要等播放之后才显示播放控制器

黄琪勇 11 月之前
父節點
當前提交
44707ed989
共有 2 個文件被更改,包括 74 次插入27 次删除
  1. 43 26
      src/views/creation/index-share.tsx
  2. 31 1
      src/views/creation/index.module.less

+ 43 - 26
src/views/creation/index-share.tsx

@@ -87,7 +87,8 @@ export default defineComponent({
       duration: 0,
       currentTime: 0,
       mediaTimeShow: false,
-      playIngShow: true
+      playIngShow: true,
+      loaded:false
     })
     // 点赞
     const onStarChange = async () => {
@@ -161,20 +162,22 @@ export default defineComponent({
       const player = state._plrl
         // 创建音波数据
       if(state.playType === "Audio"){
-        setTimeout(() => {
-          const audioDom = document.querySelector("#audioMediaSrc") as HTMLAudioElement
-          const canvasDom = document.querySelector("#audioVisualizer") as HTMLCanvasElement
-          const { pauseVisualDraw, playVisualDraw } = audioVisualDraw(audioDom, canvasDom)
-          player.on('play', () => {
-            lottieDom.value.play()
-            playVisualDraw()
-          });
-          player.on('pause', () => {
-            lottieDom.value.pause()
-            pauseVisualDraw()
-          });
-        }, 300); // 弹窗动画是0.25秒 这里用定时器 确保canvas 能获取到宽高
+        const audioDom = document.querySelector("#audioMediaSrc") as HTMLAudioElement
+        const canvasDom = document.querySelector("#audioVisualizer") as HTMLCanvasElement
+        const { pauseVisualDraw, playVisualDraw } = audioVisualDraw(audioDom, canvasDom)
+        player.on('play', () => {
+          lottieDom.value.play()
+          playVisualDraw()
+        });
+        player.on('pause', () => {
+          lottieDom.value.pause()
+          pauseVisualDraw()
+        });
       }
+      // 在微信中运行的时候,微信没有开放自动加载资源的权限,所以要等播放之后才显示播放控制器
+      player.on('loadedmetadata', () => {
+        plyrState.loaded = true
+      });
       player.on("timeupdate", ()=>{
         plyrState.currentTime = player.currentTime
       })
@@ -221,13 +224,10 @@ export default defineComponent({
       canvasDom.width = width
       canvasDom.height = height
       // audio
-      const audioCtx = new AudioContext()
-      const analyser = audioCtx.createAnalyser()
-      const source = audioCtx.createMediaElementSource(audioDom)
-      analyser.fftSize = fftSize
-      source.connect(analyser)
-      analyser.connect(audioCtx.destination)
-      const dataArray = new Uint8Array(analyser.frequencyBinCount)
+      let audioCtx : AudioContext | null = null
+      let analyser : AnalyserNode | null = null
+      let source : MediaElementAudioSourceNode | null = null
+      const dataArray = new Uint8Array(fftSize / 2)
       const draw = (data: Uint8Array, ctx: CanvasRenderingContext2D, { lineGap, canvWidth, canvHeight, canvFillColor, lineColor }: propsType) => {
         if (!ctx) return
         const w = canvWidth
@@ -235,7 +235,8 @@ export default defineComponent({
         fillCanvasBackground(ctx, w, h, canvFillColor)
           // 可视化
         const dataLen = data.length
-        const step = (w / 2 - lineGap * dataLen) / dataLen
+        let step = (w / 2 - lineGap * dataLen) / dataLen
+        step < 1 && (step = 1)
         const midX = w / 2
         const midY = h / 2
         let xLeft = midX
@@ -273,7 +274,7 @@ export default defineComponent({
       }
       const requestAnimationFrameFun = () => {
         requestAnimationFrame(() => {
-          analyser.getByteFrequencyData(dataArray)
+          analyser?.getByteFrequencyData(dataArray)
           draw(dataArray, canvasCtx, {
             lineGap: 2,
             canvWidth: width,
@@ -288,13 +289,23 @@ export default defineComponent({
       }
       let isPause = true
       const playVisualDraw = () => {
-        isPause = false
+        if (!audioCtx) {
+          audioCtx = new AudioContext()
+          source = audioCtx.createMediaElementSource(audioDom)
+        }
+        analyser = audioCtx.createAnalyser()
+        analyser.fftSize = fftSize
+        source?.connect(analyser)
+        analyser.connect(audioCtx.destination)
         audioCtx.resume()
+        isPause = false
         requestAnimationFrameFun()
       }
       const pauseVisualDraw = () => {
         isPause = true
-        audioCtx.suspend()
+        audioCtx?.suspend()
+        source?.disconnect()
+        analyser?.disconnect()
       }
       return {
         playVisualDraw,
@@ -381,6 +392,12 @@ export default defineComponent({
         path:"/transfer"
       })
     }
+    const pageVisibility = usePageVisibility();
+    watch(pageVisibility, value => {
+      if (value === 'hidden') {
+        state._plrl?.pause();
+      }
+    });
     onMounted(async () => {
       __init();
     });
@@ -438,7 +455,7 @@ export default defineComponent({
               </div>
             </div>
             <Sticky offsetTop={state.heightV - 1 + "px"}>
-              <div class={[styles.playSection, plyrState.mediaTimeShow && styles.mediaTimeShow]} id="playMediaSection" onClick={handlerClickPlay}>
+              <div class={[styles.playSection, plyrState.mediaTimeShow && styles.mediaTimeShow,!plyrState.loaded && styles.notLoaded]} id="playMediaSection" onClick={handlerClickPlay}>
                 {
                   state.playType &&
                   <>

+ 31 - 1
src/views/creation/index.module.less

@@ -110,7 +110,7 @@
     height: 48px;
     background: url("./images/midPlay.png") no-repeat;
     background-size: 100% 100%;
-    z-index: 1;
+    z-index: 12;
     display: none;
     &.playIngShow{
       display: initial;
@@ -126,6 +126,7 @@
     font-size: 14px;
     color: #FFFFFF;
     line-height: 20px;
+    z-index: 10;
     & div:first-child{
       width: 50px;
       text-align: right;
@@ -150,6 +151,28 @@
     background-size: 100% 100%;
     right: 10px;
     top: 10px;
+    z-index: 15;
+  }
+  .staffBox{
+    width: 100%;
+    height: var(--staffBoxHeight);
+    position: absolute;
+    bottom: 10px;
+    visibility: hidden;
+    &.staffBoxShow{
+      visibility: initial;
+    }
+    .staff{
+      width: 100%;
+      height: 100%;
+      padding-left: 10px;
+    }
+    .mask{
+      position: absolute;
+      z-index: 6;
+      width: 100%;
+      height: 100%;
+    }
   }
 }
 
@@ -394,6 +417,13 @@
   }
 }
 // 分享样式
+.playSection.notLoaded{
+  :global{
+    .plyr .plyr__controls {
+      display: none;
+    }
+  }
+}
 .logoDownload{
   display: flex;
   justify-content: space-between;