| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107 |
- <script setup lang="ts">
- import type { UploadChangeParam } from 'ant-design-vue';
- import { ref, watchEffect } from 'vue';
- import { useRequest } from 'alova/client';
- import { Modal, Upload } from 'ant-design-vue';
- import { uploadFileMethod } from '#/api/method/common';
- interface UploadFile extends File {
- uid?: string;
- status: 'done' | 'error' | 'removed' | 'success' | 'uploading';
- thumbUrl: string;
- url: string;
- }
- defineOptions({
- inheritAttrs: false,
- });
- function getBase64(img: Blob, callback: (base64Url: string) => void) {
- const reader = new FileReader();
- reader.addEventListener('load', () => callback(reader.result as string), {
- once: true,
- });
- reader.readAsDataURL(img);
- }
- const { loading, send: upload } = useRequest(uploadFileMethod, {
- immediate: false,
- });
- const avatar = defineModel<string | void>('value', { default: void 0 });
- const fileList = ref<UploadFile[]>([]);
- watchEffect(() => {
- const url = avatar.value ?? '';
- if (url) {
- const name = url.split('/').pop() ?? 'avatar.png';
- fileList.value = [{ uid: '-1', status: 'done', name, url } as UploadFile];
- } else {
- fileList.value = [];
- }
- });
- const previewVisible = ref(false);
- const previewImage = ref('');
- const handleCancel = () => {
- previewVisible.value = false;
- };
- const onPreviewHandle = async (file: UploadFile) => {
- previewImage.value = file.url || file.thumbUrl;
- previewVisible.value = true;
- };
- const onChangeHandle = async (info: UploadChangeParam<UploadFile>) => {
- info.file.status ??= 'uploading';
- if (info.file.status === 'uploading') {
- getBase64(info.file, (thumbUrl) => {
- info.file.thumbUrl = thumbUrl;
- });
- try {
- const url = await upload(info.file);
- info.file.status = 'done';
- avatar.value = url;
- } catch {
- info.file.status = 'error';
- avatar.value = void 0;
- }
- }
- };
- const onRemoveHandle = () => {
- avatar.value = void 0;
- };
- </script>
- <template>
- <div>
- <Upload
- v-bind="$attrs"
- v-model:file-list="fileList"
- accept="image/*"
- :max-count="1"
- name="avatar"
- list-type="picture-card"
- class="avatar-uploader"
- :disabled="loading"
- :before-upload="() => false"
- @change="onChangeHandle"
- @remove="onRemoveHandle"
- @preview="onPreviewHandle"
- >
- <div v-if="!fileList?.length" class="ant-upload-text">上传</div>
- </Upload>
- <Modal
- :open="previewVisible"
- title="图片预览"
- :footer="null"
- @cancel="handleCancel"
- >
- <img alt="example" style="width: 100%" :src="previewImage" />
- </Modal>
- </div>
- </template>
- <style scoped></style>
|