Vue2——基于vue-cropper封装一个视频封面裁剪组件

Vue2——基于vue-cropper封装一个视频封面裁剪组件

前言

如题基于vue-cropper封装一个自动裁剪符合标准的封面裁剪组件;

内容

子组件:CropperCoverDialog

为了保证裁剪的图片符合标准,所以要先控制容器尺寸,为容器添加一个动态的style,其次配置autoCropWidthautoCropHeightfixedNumberenlarge

竖版视频封面尺寸:宽高比9:16,720*1280≤尺寸≤1440*2560

横版视频封面尺寸:宽高比16:9,1280*720≤尺寸≤2560*1440

为了保证在web界面上好展示,所以我们先将尺寸大小缩小4倍,然后再将enlarge设置为4,这样就能保证裁剪的图片是我们想要的咯;

整体预览如下:
2024-09-10T03:52:19.png

<template>
  <el-dialog
    title="裁剪封面"
    :visible.sync="dialogVisible"
    append-to-body
    width="30%"
  >
    <div class="cropper-container">
      <VueCropper
        ref="cropper"
        :style="dynamicStyle"
        :img="option.img"
        :auto-crop="option.autoCrop"
        :auto-crop-width="option.autoCropWidth"
        :auto-crop-height="option.autoCropHeight"
        :fixed="option.fixed"
        :fixed-number="option.fixedNumber"
        :full="option.full"
        :fixed-box="option.fixedBox"
        :center-box="option.centerBox"
        :enlarge="option.enlarge"
        :info-true="option.infoTrue"
      />
    </div>
    <div class="text-gray margin-top text">
      调整图片时,请保证图片符合以下要求:
      <br>
      {{ text }}
    </div>
    <span slot="footer">
      <el-button @click="dialogVisible = false">取 消</el-button>
      <el-button
        type="primary"
        @click="handleConfirm"
      >确 定</el-button>
    </span>
  </el-dialog>
</template>
<script>
import { VueCropper } from 'vue-cropper'
export default {
  name: 'CoverDialog',
  components: {
    VueCropper
  },
  data() {
    return {
      dynamicStyle: { width: '180px', height: '320px' },
      dialogVisible: false,
      // https://www.npmjs.com/package/vue-cropper
      option: {
        img: '', // 裁剪图片的地址
        autoCrop: true, // 是否默认生成截图框
        enlarge: 4, // 图片根据截图框输出比例倍数
        centerBox: false, // 截图框是否被限制在图片里面
        autoCropWidth: 180, // 默认生成截图框宽度
        autoCropHeight: 320, // 默认生成截图框高度
        fixed: true, // 是否开启截图框宽高固定比例
        fixedNumber: [180, 320], // 截图框的宽高比例
        full: true, // 按原比例裁切图片,不失真
        fixedBox: true, // 固定截图框大小,不允许改变
        infoTrue: true // true为展示真实输出图片宽高,false展示看到的截图框宽高
      },
      imageInfo: {},
      file: null
    }
  },
  methods: {
    handleSetOptions(data) {
      const { video_cover_url, image_mode } = data
      this.dialogVisible = true
      this.imageInfo = data
      this.option.img = video_cover_url
      const cropStrategy = {
        CREATIVE_IMAGE_MODE_VIDEO_VERTICAL: () => {
          this.option.fixedNumber = [180, 320]
          this.option.autoCropWidth = 180
          this.option.autoCropHeight = 320
          this.dynamicStyle = { width: '180px', height: '320px' }
          this.text = '宽高比9:16,720*1280≤尺寸≤1440*2560'
        },
        CREATIVE_IMAGE_MODE_VIDEO: () => {
          this.option.fixedNumber = [320, 180]
          this.option.autoCropWidth = 320
          this.option.autoCropHeight = 180
          this.dynamicStyle = { width: '320px', height: '180px' }
          this.text = '宽高比16:9,1280*720≤尺寸≤2560*1440'
        }
      }
      cropStrategy[image_mode]()
    },
    handleConfirm() {
      this.$refs.cropper.getCropBlob(data => {
        const res = new File([data], `cover_${(new Date()).getTime()}.jpeg`, { type: 'image/jpeg', lastModified: Date.now() })
        this.$emit('data', res, this.imageInfo)
      })
    }
  }
}
</script>
<style lang="scss" scoped>
.cropper-container {
  display: flex;
  justify-content: center;
}

.text {
  font-size: 12px;
  line-height: 18px;
  text-align: center;
}
</style>

父组件

<template>
    <cropper-cover-dialog
      ref="cropperDialog"
      @data="handleUploadCoverData"
    />
</template>
<script>
  export default {
    methods: {
      handleChooseProductVideo(item) {
        this.$refs.cropperDialog.handleSetOptions(item)
      },
      handleUploadCoverData(data, image) {
        const formData = new FormData()
        formData.append('file', data)
        // 进行上传和数据组装
        this.$refs.cropperDialog.dialogVisible = false
      },
    }
  }
posted @ 2024-09-10 11:52:00 王洋 阅读(49) 评论(0)
发表评论
昵称
邮箱
网址