vue 实现调用摄像头进行拍照功能以及从图库中选择相片功能以及基于photoswipe的vue图片预览 组件

效果图

图一: vue 实现调用摄像头进行拍照功能以及从图库中选择相片功能以及基于photoswipe的vue图片预览 组件      图二:  vue 实现调用摄像头进行拍照功能以及从图库中选择相片功能以及基于photoswipe的vue图片预览 组件    

图三: vue 实现调用摄像头进行拍照功能以及从图库中选择相片功能以及基于photoswipe的vue图片预览 组件

图四: vue 实现调用摄像头进行拍照功能以及从图库中选择相片功能以及基于photoswipe的vue图片预览 组件

使用组件:

使用vue-photo-preview :https://github.com/826327700/vue-photo-preview

.ts

import photograph from "@/MobileApp/components/photograph";

@Component({
  components: { photograph }
})

.vue

<photograph></photograph>
<photograph showAlbum="false"></photograph> // 使用拍照功能
<photograph showPhoto="false"></photograph> // 使用拍照以及选择相片功能

组件:

.vue

<template>
  <div>
    <div>
      <div :style="{ height: picHeight-2 + 'px' ,width: picWidth-2 + 'px'}" ref="showPhoto" class="file" @click="showType">
        <span class="icon iconfont icon-uploadphoto camera"></span>
      </div>
      <div class="showImgDiv" v-for="(item, index) in photoLists" :key="index" ref="showPhoto">
        <img preview="0" ref="showImg" :style="{ height: picHeight + 'px' ,width: picWidth + 'px'}" :src="item">
        <span :style="{ width: picWidth + 'px'}" class="dele" @click="deleImg(index)">
          <span class="icon iconfont icon-delete deleIcon"></span>
        </span>
      </div>
    </div>
    <van-popup v-model="isShow" position="bottom" style="text-align: center;">
      <div ref="cameraRemove" class="van-hairline--bottom" @click="close" showPhoto>
        <input
          cameraDisable
           ref="inputCamera"
          class="inputPhoto"
          type="file"
          accept="image/*"
          capture="camera"
          @change="cameraChange"
        >
        <span :style="{ color: fontColorCamera}">拍照</span>
      </div>
      <div ref="multipleRemove" class="van-hairline--bottom" @click="close" showAlbum>
        <input
          multipleDisable
          ref="inputMultiple" 
          class="inputPhoto"          
          type="file"
          accept="image/*"
          multiple
          @change="multipleChange"
        >
        <span :style="{ color: fontColorMultiple}">从相册中选择</span>
      </div>
    </van-popup>
  </div>
</template>

<style scoped>
.dele {
  height: 30px;
  background-color: #fff;
  opacity: 0.8;
  text-align: center;
  line-height: 30px;
  position: absolute;
  bottom: 0;
  left: 0;
}

.deleIcon {
  color: #3fcc8e;
}

.showImgDiv {
  position: relative;
  display: inline-block;
  padding-right: 2px;
  padding-top: 5px;
}

.van-hairline--bottom {
  height: 60px;
  line-height: 60px;
}

.vanRow {
  background-color: #fff;
}

.camera {
  color: #3fcc8e;
  font-size: 26px;
}

.file {
  position: relative;
  border: 1px dashed #3fcc8e;
  display: inline-block;
  overflow: hidden;
  line-height: 88px;
  text-align: center;
  margin-right: 5px;
  margin-top: 5px;
}

.inputPhoto {
  position: absolute;
  font-size: 100px;
  right: 0;
  top: 0;
  opacity: 0;
}
</style>

<script>
import Photograph from "./photograph.ts";
export default Photograph;
</script>

.ts 

/**
 * @module MobileApp\components\photograph
 */

import Vue from "vue";
import { Component, Prop, Watch, Emit } from "vue-property-decorator";
import { IndexObject } from "@/types";
import common from "@/MobileApp/utils/common";

@Component
export default class Photograph extends Vue {
  [x: string]: any;
  private isShow = false;
  private photoLists = [];
  private picWidth = 75;
  private picHeight = 90;

  @Prop({ default: "true" }) showAlbum!: string;
  @Prop({ default: "true" }) showPhoto!: string;

  mounted() {}

  private close() {
    this.isShow = false;
  }

  private showType() {
    this.isShow = true;
    this.$nextTick(function() {
      let cameraRemove = this.$refs.cameraRemove as IndexObject;
      let multipleRemove = this.$refs.multipleRemove as IndexObject;
      if (!cameraRemove.parentNode || !multipleRemove.parentNode) {
        return;
      }
      if (this.showAlbum === "false") {
        multipleRemove.parentNode.removeChild(multipleRemove);
      }
      if (this.showPhoto === "false") {
        cameraRemove.parentNode.removeChild(cameraRemove);
      }
    });
  }

    private cameraChange() {
      let inputCameraFile = this.$refs.inputCamera as IndexObject;
      let url;
      if (inputCameraFile.files[0]) {
        url = URL.createObjectURL(inputCameraFile.files[0]);
        (this as any).photoLists.push(url);
      }
      this.$previewRefresh();
    }

    private multipleChange() {
      let url;
      let inputMultiple = this.$refs.inputMultiple as IndexObject;
      if (inputMultiple.files) {
        for (let file of inputMultiple.files) {
          url = URL.createObjectURL(file);
          (this as any).photoLists.push(url);
        }
      }
      this.$previewRefresh();
    }

  private deleImg(index) {
    common
      .dialogConfirm("温馨提示", "请确认要删除此照片?")
      .then(() => {
        // on confirm
        (this as any).photoLists.splice(index, 1);
      })
      .catch(() => {
        // on cancel
      });
  }
}