位置:首页 > web前端 > vue

vue实现录屏功能

dearweb 发布:2021-10-26 10:09:55阅读:

vue实现录屏功能分享学习使用。

<!--录屏-->
<template>
  <div class="container">
    <section class="item">
      <span class="type-name">文件名称:</span>
      <input type="text"
             v-model.trim="fileName" />
      <span>.mp4</span>
    </section>
    <section class="item">
      <span class="type-name">录制时长</span>
      <span>{{timeLong}}s</span>
    </section>
    <section>
      <button class="media-btn"
              @click="clicks()"
              title="点击开始录制">{{txt}}</button>
    </section>
  </div>
</template>

<script>
export default {
  data() {
    return {
      timeout: 0,
      recordedBlobs: [],
      fileName: '',
      txt: '开始录制',
      status: false,
      stream: null,
      options: {
        audioBitsPerSecond: 128000,
        videoBitsPerSecond: 4500000,
        mimeType: 'video/webm'
      },
      startTime: 0,
      timeLong: 0,
      timeLongs: null,
      endTime: 0
    }
  },
  watch: {
    status(a) {
      if (a) {
        this.txt = '停止录制'
      } else {
        this.txt = '开始录制'
      }
    }
  },
  methods: {
    clicks() {
      if (this.status) {
        this.stopReset()
        this.status = false
        clearInterval(this.timesLongs)
      } else {
        this.startScreen()
      }
    },
    cauTime() {
      this.timeLongs = setInterval(() => {
        this.timeLong = (new Date().getTime() - this.startTime) / 1000
      }, 200)
    },
    stopReset() {
      this.stream.getTracks().forEach(track => track.stop())
      this.recordedBlobs = []
    },
    startScreen() {
      //注意,加上 audio: true 之后底部可以拖动的停止就失效了,正在fixing
      navigator.mediaDevices.getDisplayMedia({ video: true, audio: true }).then(
        stream => {
          this.status = !this.status
          console.log('开始录制')
          this.startTime = new Date().getTime()
          this.cauTime()

          this.stream = stream
          const mediaRecorder = new MediaRecorder(stream, this.options)
          mediaRecorder.ondataavailable = event => {
            if (event.data.size > 0) {
              this.status = false
              clearInterval(this.timeLongs)
              console.log('结束录制,录制时长:' + this.timeLong + 's')
              this.recordedBlobs.push(event.data)
              this.download()
              this.stopReset()
            }
          }
          mediaRecorder.start()
        },
        error => console.log(error)
      )
    },
    download() {
      const blob = new Blob(this.recordedBlobs, { type: 'video/mp4' })
      const url = URL.createObjectURL(blob)
      const a = document.createElement('a')
      document.body.appendChild(a)
      a.style.display = 'none'
      a.href = url
      if (this.fileName) {
        a.download = this.fileName + '.mp4'
      } else {
        a.download = new Date() + '.mp4'
      }
      a.click()
      window.URL.revokeObjectURL(url)
    }
  }
}
</script>

<style scoped>
.container {
  width: 450px;
  height: 250px;
  border: 1px solid;
}
.item {
  display: flex;
  align-items: center;
  margin: 25px 0;
  font-size: 20px;
}
.item .unit {
  margin-left: 10px;
}
.item input {
  height: 30px;
  padding: 1px;
  padding-left: 5px;
}
.item input[type='text'] {
  width: 180px;
}
.item input[type='number'] {
  width: 80px;
}
.type-name {
  width: 30%;
}
.media-btn {
  background: rgb(146, 224, 214);
  border: none;
  padding: 8px;
  border-radius: 5px;
  cursor: pointer;
  font-weight: 800;
  outline: none;
}
.media-btn:hover {
  background: rgb(155, 235, 224);
}

.tip {
  background-color: rgb(248, 243, 172);
  display: inline-block;
  padding: 19px;
  font-size: 25px;
  font-weight: 900;
  border-radius: 3px;
  margin-top: 19px;
}
</style>


24人点赞 返回栏目 提问 分享一波

小礼物走一波,支持作者

还没有人赞赏,支持一波吧

留言(问题紧急可添加微信 xxl18963067593) 评论仅代表网友个人 留言列表

暂无留言,快来抢沙发吧!

本刊热文
网友在读
手机扫码查看 手机扫码查看