image-preview.tsx 1.9 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62
import { useNamespace } from '@ibiz-template/vue-util';
import { defineComponent, PropType } from 'vue';
import '@ibiz-template/theme/style/components/common/image-preview/image-preview.scss';
import { RuntimeError, downloadFileFromBlob } from '@ibiz-template/core';

export const ImagePreview = defineComponent({
  name: 'ImagePreview',
  props: {
    file: {
      type: Object as PropType<{ name: string; url: string }>,
      required: true,
    },
  },
  setup(props) {
    const ns = useNamespace('image-preview');

    const onDownload = () => {
      // 发送get请求
      ibiz.net
        .request(props.file.url, {
          method: 'get',
          responseType: 'blob',
          baseURL: '', // 已经有baseURL了,这里无需再写
        })
        .then((response: IData) => {
          if (response.status !== 200) {
            throw new RuntimeError('下载文件失败');
          }
          // 请求成功,后台返回的是一个文件流
          if (!response.data) {
            throw new RuntimeError('文件流数据不存在');
          } else {
            // 获取文件名
            const fileName = props.file.name;
            downloadFileFromBlob(response.data, fileName);
          }
        });
    };

    return {
      ns,
      onDownload,
    };
  },
  render() {
    return (
      <div class={this.ns.b()}>
        <img class={this.ns.e('image')} src={this.file.url} />
        <div class={this.ns.e('toolbar')}>
          <div class={this.ns.e('zoom-bar')}>
            <i-icon class={this.ns.e('zoom-minus')} type='md-remove' />
            <span class={this.ns.e('zoom-percent')}>100%</span>
            <i-icon class={this.ns.e('zoom-plus')} type='md-add' />
          </div>
          <div onClick={this.onDownload} class={this.ns.e('download')}>
            <i-icon type='md-download' />
          </div>
        </div>
      </div>
    );
  },
});