yangg há 2 meses atrás
pai
commit
019f9ffed4

+ 156 - 1
pages/identity-verify/identity-verify.vue

@@ -117,6 +117,11 @@
         重新上传
       </button>
     </div>
+
+    <!-- 在模板部分添加录制时长显示 -->
+    <!-- <div class="recording-timer" v-if="isRecording">
+      <span class="timer-text">{{ recordingTimeDisplay || '00:00' }}</span>
+    </div> -->
   </div>
 </template>
 
@@ -212,6 +217,9 @@ export default {
       showStartRecordingButton: false,
       showRetryButton: false, // 控制重试按钮显示
       lastVideoToRetry: null, // 存储上次失败的视频URL,用于重试
+      recordingStartTime: null, // 录制开始时间
+      recordingTimerCount: 0, // 录制计时器计数
+      recordingTimeDisplay: '00:00', // 格式化的录制时间显示
     }
   },
   mounted() {
@@ -789,6 +797,18 @@ export default {
       console.log('开始录制用户回答');
       this.isRecording = true;
       
+      // 记录录制开始时间
+      this.recordingStartTime = Date.now();
+      this.recordingTimerCount = 0;
+      
+      // 启动计时器,每秒更新计时
+      this.recordingTimer = setInterval(() => {
+        this.recordingTimerCount++;
+        
+        // 可以在这里更新UI显示录制时长
+        // 例如:this.recordingTimeDisplay = this.formatTime(this.recordingTimerCount);
+      }, 1000);
+      
       // 显示录制中的提示
       // uni.showLoading({
       //   title: '正在录制...',
@@ -1197,6 +1217,112 @@ export default {
     // 添加新方法:停止录制用户回答
     stopRecordingAnswer() {
       console.log('停止录制用户回答');
+      
+      // 检查录制时长
+      const recordingDuration = this.getRecordingDuration();
+      const minimumDuration = 3; // 最小录制时长(秒)
+      
+      if (recordingDuration < minimumDuration) {
+        // 录制时间过短,显示提示
+        uni.showModal({
+          title: '录制时间过短',
+          content: '您的回答时间过短,请至少录制' + minimumDuration + '秒。是否重新录制?',
+          confirmText: '重新录制',
+          cancelText: '仍然提交',
+          success: (res) => {
+            if (res.confirm) {
+              // 用户选择重新录制
+              console.log('用户选择重新录制');
+              // 重置录制状态但不停止当前录制
+              this.resetRecording();
+              return;
+            } else {
+              // 用户选择仍然提交,继续执行停止录制逻辑
+              console.log('用户选择继续提交短视频');
+              this.completeRecordingStop();
+            }
+          }
+        });
+      } else {
+        // 录制时长足够,直接停止
+        this.completeRecordingStop();
+      }
+    },
+
+    // 添加新方法:获取录制时长
+    getRecordingDuration() {
+      // 如果有明确的录制开始时间,计算实际录制时长
+      if (this.recordingStartTime) {
+        return (Date.now() - this.recordingStartTime) / 1000;
+      }
+      
+      // 如果没有明确记录开始时间,尝试从视频元素获取
+      if (this.mediaRecorder && this.$refs.userCameraVideo) {
+        return this.$refs.userCameraVideo.currentTime || 0;
+      }
+      
+      // 如果无法获取准确时长,返回估计值(如果有计时器)
+      if (this.recordingTimerCount) {
+        return this.recordingTimerCount;
+      }
+      
+      // 默认返回0
+      return 0;
+    },
+
+    // 添加新方法:重置录制
+    resetRecording() {
+      // 保持录制状态,但重置计时器
+      if (this.recordingTimer) {
+        clearTimeout(this.recordingTimer);
+      }
+      
+      // 重置录制开始时间
+      this.recordingStartTime = Date.now();
+      this.recordingTimerCount = 0;
+      
+      // 如果是浏览器环境,需要重置MediaRecorder
+      if (this.mediaRecorder && this.mediaRecorder.state !== 'inactive') {
+        // 停止当前录制
+        this.mediaRecorder.stop();
+        
+        // 清空已录制的数据块
+        this.recordedChunks = [];
+        
+        // 短暂延迟后重新开始录制
+        setTimeout(() => {
+          this.startBrowserRecording();
+        }, 500);
+      } 
+      // 如果是小程序环境,需要重置相机录制
+      else if (this.cameraContext) {
+        // 停止当前录制
+        this.cameraContext.stopRecord({
+          success: () => {
+            console.log('重置录制:停止当前录制成功');
+            // 短暂延迟后重新开始录制
+            setTimeout(() => {
+              this.startMiniProgramRecording();
+            }, 500);
+          },
+          fail: (err) => {
+            console.error('重置录制:停止当前录制失败', err);
+            // 尝试直接重新开始录制
+            this.startMiniProgramRecording();
+          }
+        });
+      }
+      
+      // 显示提示
+      uni.showToast({
+        title: '请重新开始回答',
+        icon: 'none',
+        duration: 2000
+      });
+    },
+
+    // 添加新方法:完成录制停止流程
+    completeRecordingStop() {
       this.isRecording = false;
       
       // 清除定时器
@@ -1711,6 +1837,11 @@ export default {
       // 获取当前视频播放时间
       const currentTime = e.target.currentTime;
       
+      // 如果正在录制,更新录制时间显示
+      if (this.isRecording && this.recordingTimerCount) {
+        this.recordingTimeDisplay = this.formatTime(this.recordingTimerCount);
+      }
+      
       // 根据当前播放的视频索引选择对应的字幕数组
       let currentSubtitles;
       if (this.currentVideoIndex === 0) {
@@ -2080,7 +2211,14 @@ export default {
       } catch (e) {
         console.log('防御性检查异常:', e);
       }
-    }
+    },
+
+    // 添加格式化时间的辅助方法
+    formatTime(seconds) {
+      const minutes = Math.floor(seconds / 60);
+      const remainingSeconds = seconds % 60;
+      return `${minutes.toString().padStart(2, '0')}:${remainingSeconds.toString().padStart(2, '0')}`;
+    },
   }
 }
 </script>
@@ -2406,4 +2544,21 @@ video::-webkit-media-controls-fullscreen-button {
 .retry-button:hover {
   background-color: #2980b9;
 }
+
+/* 录制时长显示 */
+.recording-timer {
+  position: absolute;
+  top: 20px;
+  left: 130px; /* 放在录制指示器旁边 */
+  background-color: rgba(0, 0, 0, 0.6);
+  padding: 5px 10px;
+  border-radius: 15px;
+  z-index: 20;
+}
+
+.timer-text {
+  color: white;
+  font-size: 14px;
+  font-family: monospace; /* 使用等宽字体,使时间显示更稳定 */
+}
 </style>

+ 92 - 1
unpackage/dist/dev/mp-weixin/pages/identity-verify/identity-verify.js

@@ -105,8 +105,14 @@ const _sfc_main = {
       showStartRecordingButton: false,
       showRetryButton: false,
       // 控制重试按钮显示
-      lastVideoToRetry: null
+      lastVideoToRetry: null,
       // 存储上次失败的视频URL,用于重试
+      recordingStartTime: null,
+      // 录制开始时间
+      recordingTimerCount: 0,
+      // 录制计时器计数
+      recordingTimeDisplay: "00:00"
+      // 格式化的录制时间显示
     };
   },
   mounted() {
@@ -534,6 +540,11 @@ const _sfc_main = {
     startRecordingAnswer() {
       console.log("开始录制用户回答");
       this.isRecording = true;
+      this.recordingStartTime = Date.now();
+      this.recordingTimerCount = 0;
+      this.recordingTimer = setInterval(() => {
+        this.recordingTimerCount++;
+      }, 1e3);
       const systemInfo = common_vendor.index.getSystemInfoSync();
       const isMiniProgram = systemInfo.uniPlatform && systemInfo.uniPlatform.startsWith("mp-");
       if (isMiniProgram) {
@@ -837,6 +848,77 @@ const _sfc_main = {
     // 添加新方法:停止录制用户回答
     stopRecordingAnswer() {
       console.log("停止录制用户回答");
+      const recordingDuration = this.getRecordingDuration();
+      const minimumDuration = 3;
+      if (recordingDuration < minimumDuration) {
+        common_vendor.index.showModal({
+          title: "录制时间过短",
+          content: "您的回答时间过短,请至少录制" + minimumDuration + "秒。是否重新录制?",
+          confirmText: "重新录制",
+          cancelText: "仍然提交",
+          success: (res) => {
+            if (res.confirm) {
+              console.log("用户选择重新录制");
+              this.resetRecording();
+              return;
+            } else {
+              console.log("用户选择继续提交短视频");
+              this.completeRecordingStop();
+            }
+          }
+        });
+      } else {
+        this.completeRecordingStop();
+      }
+    },
+    // 添加新方法:获取录制时长
+    getRecordingDuration() {
+      if (this.recordingStartTime) {
+        return (Date.now() - this.recordingStartTime) / 1e3;
+      }
+      if (this.mediaRecorder && this.$refs.userCameraVideo) {
+        return this.$refs.userCameraVideo.currentTime || 0;
+      }
+      if (this.recordingTimerCount) {
+        return this.recordingTimerCount;
+      }
+      return 0;
+    },
+    // 添加新方法:重置录制
+    resetRecording() {
+      if (this.recordingTimer) {
+        clearTimeout(this.recordingTimer);
+      }
+      this.recordingStartTime = Date.now();
+      this.recordingTimerCount = 0;
+      if (this.mediaRecorder && this.mediaRecorder.state !== "inactive") {
+        this.mediaRecorder.stop();
+        this.recordedChunks = [];
+        setTimeout(() => {
+          this.startBrowserRecording();
+        }, 500);
+      } else if (this.cameraContext) {
+        this.cameraContext.stopRecord({
+          success: () => {
+            console.log("重置录制:停止当前录制成功");
+            setTimeout(() => {
+              this.startMiniProgramRecording();
+            }, 500);
+          },
+          fail: (err) => {
+            console.error("重置录制:停止当前录制失败", err);
+            this.startMiniProgramRecording();
+          }
+        });
+      }
+      common_vendor.index.showToast({
+        title: "请重新开始回答",
+        icon: "none",
+        duration: 2e3
+      });
+    },
+    // 添加新方法:完成录制停止流程
+    completeRecordingStop() {
       this.isRecording = false;
       if (this.recordingTimer) {
         clearTimeout(this.recordingTimer);
@@ -1233,6 +1315,9 @@ const _sfc_main = {
     // 处理视频时间更新事件
     handleTimeUpdate(e) {
       const currentTime = e.target.currentTime;
+      if (this.isRecording && this.recordingTimerCount) {
+        this.recordingTimeDisplay = this.formatTime(this.recordingTimerCount);
+      }
       let currentSubtitles;
       if (this.currentVideoIndex === 0) {
         currentSubtitles = this.subtitles;
@@ -1515,6 +1600,12 @@ const _sfc_main = {
       } catch (e) {
         console.log("防御性检查异常:", e);
       }
+    },
+    // 添加格式化时间的辅助方法
+    formatTime(seconds) {
+      const minutes = Math.floor(seconds / 60);
+      const remainingSeconds = seconds % 60;
+      return `${minutes.toString().padStart(2, "0")}:${remainingSeconds.toString().padStart(2, "0")}`;
     }
   }
 };

+ 16 - 0
unpackage/dist/dev/mp-weixin/pages/identity-verify/identity-verify.wxss

@@ -289,3 +289,19 @@ video.data-v-464e78c6::-webkit-media-controls-fullscreen-button {
 .retry-button.data-v-464e78c6:hover {
   background-color: #2980b9;
 }
+
+/* 录制时长显示 */
+.recording-timer.data-v-464e78c6 {
+  position: absolute;
+  top: 20px;
+  left: 130px; /* 放在录制指示器旁边 */
+  background-color: rgba(0, 0, 0, 0.6);
+  padding: 5px 10px;
+  border-radius: 15px;
+  z-index: 20;
+}
+.timer-text.data-v-464e78c6 {
+  color: white;
+  font-size: 14px;
+  font-family: monospace; /* 使用等宽字体,使时间显示更稳定 */
+}