hy-app 0.3.0 → 0.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +6 -3
- package/common/shakeService.ts +31 -29
- package/components/avatar.zip +0 -0
- package/components/hy-action-sheet/hy-action-sheet.vue +71 -46
- package/components/hy-address-picker/hy-address-picker.vue +94 -83
- package/components/hy-avatar/hy-avatar.vue +84 -85
- package/components/hy-back-top/hy-back-top.vue +8 -6
- package/components/hy-badge/hy-badge.vue +47 -46
- package/components/hy-button/hy-button.vue +117 -93
- package/components/hy-calendar/hy-calendar.vue +168 -160
- package/components/hy-card/hy-card.vue +50 -43
- package/components/hy-card/typing.d.ts +33 -32
- package/components/hy-cell/hy-cell.vue +73 -51
- package/components/hy-check-button/hy-check-button.vue +54 -47
- package/components/hy-checkbox/hy-checkbox.vue +97 -105
- package/components/hy-code-input/hy-code-input.vue +80 -89
- package/components/hy-config-provider/hy-config-provider.vue +20 -21
- package/components/hy-count-down/hy-count-down.vue +66 -67
- package/components/hy-count-to/hy-count-to.vue +105 -99
- package/components/hy-count-to/typing.d.ts +13 -12
- package/components/hy-datetime-picker/hy-datetime-picker.vue +261 -253
- package/components/hy-datetime-picker/typing.d.ts +42 -40
- package/components/hy-divider/hy-divider.vue +68 -73
- package/components/hy-dropdown/hy-dropdown.vue +20 -19
- package/components/hy-dropdown-item/hy-dropdown-item.vue +66 -61
- package/components/hy-dropdown-item/typing.d.ts +9 -9
- package/components/hy-empty/hy-empty.vue +42 -42
- package/components/hy-flex/hy-flex.vue +99 -0
- package/components/hy-flex/index.scss +8 -0
- package/components/hy-flex/typing.d.ts +23 -0
- package/components/hy-float-button/hy-float-button.vue +218 -210
- package/components/hy-folding-panel/hy-folding-panel.vue +32 -33
- package/components/hy-form/hy-form.vue +264 -252
- package/components/hy-form/typing.d.ts +4 -0
- package/components/hy-form-group/hy-form-group.vue +114 -183
- package/components/hy-form-item/hy-form-item.vue +12 -10
- package/components/hy-form-item/index.scss +2 -2
- package/components/hy-form-item/typing.d.ts +3 -6
- package/components/hy-grid/hy-grid.vue +44 -43
- package/components/hy-icon/hy-icon.vue +61 -67
- package/components/hy-image/hy-image.vue +112 -88
- package/components/hy-image/typing.d.ts +27 -23
- package/components/hy-input/hy-input.vue +157 -127
- package/components/hy-input/typing.d.ts +53 -47
- package/components/hy-line/hy-line.vue +26 -26
- package/components/hy-line-progress/hy-line-progress.vue +42 -35
- package/components/hy-list/hy-list.vue +76 -85
- package/components/hy-loading/hy-loading.vue +26 -23
- package/components/hy-login/TheUserLogin.vue +1 -1
- package/components/hy-menu/hy-menu.vue +48 -43
- package/components/hy-menu/typing.d.ts +18 -17
- package/components/hy-modal/hy-modal.vue +39 -35
- package/components/hy-navbar/hy-navbar.vue +25 -25
- package/components/hy-navbar/typing.d.ts +24 -22
- package/components/hy-notice-bar/hy-notice-bar.vue +26 -27
- package/components/hy-notify/hy-notify.vue +53 -53
- package/components/hy-number-step/hy-number-step.vue +134 -146
- package/components/hy-number-step/typing.d.ts +35 -35
- package/components/hy-overlay/hy-overlay.vue +23 -21
- package/components/hy-pagination/hy-pagination.vue +41 -36
- package/components/hy-picker/hy-picker.vue +184 -154
- package/components/hy-picker/typing.d.ts +39 -39
- package/components/hy-popover/hy-popover.vue +97 -77
- package/components/hy-popup/hy-popup.vue +107 -98
- package/components/hy-price/hy-price.vue +38 -34
- package/components/hy-qrcode/hy-qrcode.vue +50 -51
- package/components/hy-radio/hy-radio.vue +101 -113
- package/components/hy-rate/hy-rate.vue +107 -88
- package/components/hy-read-more/hy-read-more.vue +64 -49
- package/components/hy-scroll-list/hy-scroll-list.vue +45 -48
- package/components/hy-search/hy-search.vue +73 -66
- package/components/hy-search/typing.d.ts +36 -35
- package/components/hy-signature/hy-signature.vue +282 -240
- package/components/hy-slider/hy-slider.vue +195 -153
- package/components/hy-slider/typing.d.ts +21 -21
- package/components/hy-steps/hy-steps.vue +118 -90
- package/components/hy-steps/index.scss +31 -21
- package/components/hy-submit-bar/hy-submit-bar.vue +61 -70
- package/components/hy-subsection/hy-subsection.vue +99 -102
- package/components/hy-subsection/typing.d.ts +19 -19
- package/components/hy-swipe-action/hy-swipe-action.vue +131 -118
- package/components/hy-swiper/hy-swiper.vue +85 -71
- package/components/hy-switch/hy-switch.vue +67 -72
- package/components/hy-switch/typing.d.ts +21 -19
- package/components/hy-tabs/hy-tabs.vue +168 -113
- package/components/hy-tag/hy-tag.vue +90 -86
- package/components/hy-tag/typing.d.ts +26 -21
- package/components/hy-text/hy-text.vue +119 -111
- package/components/hy-textarea/hy-textarea.vue +100 -93
- package/components/hy-textarea/typing.d.ts +36 -31
- package/components/hy-toast/hy-toast.vue +77 -67
- package/components/hy-tooltip/hy-tooltip.vue +109 -91
- package/components/hy-transition/hy-transition.vue +62 -66
- package/components/hy-upload/hy-upload.vue +294 -152
- package/components/hy-upload/typing.d.ts +41 -36
- package/components/hy-warn/hy-warn.vue +34 -27
- package/components/hy-waterfall/hy-waterfall.vue +83 -74
- package/components/hy-watermark/hy-watermark.vue +134 -115
- package/components/index.ts +1 -1
- package/composables/usePopover.ts +236 -221
- package/composables/useQueue.ts +53 -52
- package/global.d.ts +1 -0
- package/package.json +2 -2
- package/store/index.ts +9 -1
- package/theme.scss +5 -5
- package/typing/index.ts +0 -1
- package/typing/modules/common.d.ts +0 -2
- package/web-types.json +1 -1
|
@@ -2,7 +2,11 @@
|
|
|
2
2
|
<view class="hy-upload" :style="[customStyle]">
|
|
3
3
|
<view class="hy-upload__wrap">
|
|
4
4
|
<template v-if="previewImage">
|
|
5
|
-
<view
|
|
5
|
+
<view
|
|
6
|
+
class="hy-upload__wrap__preview"
|
|
7
|
+
v-for="(item, index) in lists"
|
|
8
|
+
:key="index"
|
|
9
|
+
>
|
|
6
10
|
<image
|
|
7
11
|
v-if="item.isImage || (item.type && item.type === 'image')"
|
|
8
12
|
:src="item.thumb || item.url"
|
|
@@ -16,14 +20,26 @@
|
|
|
16
20
|
},
|
|
17
21
|
]"
|
|
18
22
|
/>
|
|
19
|
-
<view
|
|
23
|
+
<view
|
|
24
|
+
v-else
|
|
25
|
+
class="hy-upload__wrap__preview__other"
|
|
26
|
+
@tap="onClickPreview(item, index)"
|
|
27
|
+
>
|
|
20
28
|
<u-icon
|
|
21
29
|
color="#80CBF9"
|
|
22
30
|
size="26"
|
|
23
|
-
:name="
|
|
31
|
+
:name="
|
|
32
|
+
item.isVideo || (item.type && item.type === 'video')
|
|
33
|
+
? 'movie'
|
|
34
|
+
: 'folder'
|
|
35
|
+
"
|
|
24
36
|
></u-icon>
|
|
25
37
|
<text class="hy-upload__wrap__preview__other__text">
|
|
26
|
-
{{
|
|
38
|
+
{{
|
|
39
|
+
item.isVideo || (item.type && item.type === "video")
|
|
40
|
+
? "视频"
|
|
41
|
+
: "文件"
|
|
42
|
+
}}
|
|
27
43
|
</text>
|
|
28
44
|
</view>
|
|
29
45
|
|
|
@@ -46,7 +62,11 @@
|
|
|
46
62
|
@tap.stop="deleteItem(index)"
|
|
47
63
|
>
|
|
48
64
|
<view class="hy-upload__deletable__icon">
|
|
49
|
-
<HyIcon
|
|
65
|
+
<HyIcon
|
|
66
|
+
:name="IconConfig.CLOSE"
|
|
67
|
+
color="#ffffff"
|
|
68
|
+
size="14"
|
|
69
|
+
></HyIcon>
|
|
50
70
|
</view>
|
|
51
71
|
</view>
|
|
52
72
|
<!-- 删除图片图标 -->
|
|
@@ -55,7 +75,11 @@
|
|
|
55
75
|
<view class="hy-upload__success" v-if="item.status === 'success'">
|
|
56
76
|
<!-- #ifndef APP-NVUE -->
|
|
57
77
|
<view class="hy-upload__success__icon">
|
|
58
|
-
<HyIcon
|
|
78
|
+
<HyIcon
|
|
79
|
+
:name="IconConfig.CHECK_MASK"
|
|
80
|
+
color="#ffffff"
|
|
81
|
+
size="12"
|
|
82
|
+
></HyIcon>
|
|
59
83
|
</view>
|
|
60
84
|
<!-- #endif -->
|
|
61
85
|
</view>
|
|
@@ -87,8 +111,14 @@
|
|
|
87
111
|
},
|
|
88
112
|
]"
|
|
89
113
|
>
|
|
90
|
-
<HyIcon
|
|
91
|
-
|
|
114
|
+
<HyIcon
|
|
115
|
+
:name="uploadIcon"
|
|
116
|
+
size="26"
|
|
117
|
+
:color="uploadIconColor"
|
|
118
|
+
></HyIcon>
|
|
119
|
+
<text v-if="uploadText" class="hy-upload__button__text">{{
|
|
120
|
+
uploadText
|
|
121
|
+
}}</text>
|
|
92
122
|
</view>
|
|
93
123
|
</template>
|
|
94
124
|
</view>
|
|
@@ -97,141 +127,252 @@
|
|
|
97
127
|
|
|
98
128
|
<script lang="ts">
|
|
99
129
|
export default {
|
|
100
|
-
name:
|
|
130
|
+
name: "hy-upload",
|
|
101
131
|
options: {
|
|
102
132
|
addGlobalClass: true,
|
|
103
133
|
virtualHost: true,
|
|
104
|
-
styleIsolation:
|
|
134
|
+
styleIsolation: "shared",
|
|
105
135
|
},
|
|
106
|
-
}
|
|
136
|
+
};
|
|
107
137
|
</script>
|
|
108
138
|
|
|
109
139
|
<script setup lang="ts">
|
|
110
|
-
import { ref,
|
|
111
|
-
import
|
|
112
|
-
import type
|
|
113
|
-
import
|
|
114
|
-
import {
|
|
115
|
-
import { IconConfig } from '../../config'
|
|
140
|
+
import { ref, watch } from "vue";
|
|
141
|
+
import type { PropType, CSSProperties } from "vue";
|
|
142
|
+
import type { FileVo, ReadFunctionVo } from "./typing";
|
|
143
|
+
import { addUnit, chooseFile, isArray } from "../../utils";
|
|
144
|
+
import { IconConfig } from "../../config";
|
|
116
145
|
// 组件
|
|
117
|
-
import HyIcon from
|
|
146
|
+
import HyIcon from "../hy-icon/hy-icon.vue";
|
|
118
147
|
|
|
119
148
|
/**
|
|
120
149
|
* 该组件用于上传图片或者视频等场景
|
|
121
150
|
* @displayName hy-upload
|
|
122
151
|
*/
|
|
123
|
-
defineOptions({})
|
|
152
|
+
defineOptions({});
|
|
124
153
|
|
|
125
|
-
const props = withDefaults(defineProps<IProps>(), defaultProps)
|
|
126
|
-
const {
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
154
|
+
// const props = withDefaults(defineProps<IProps>(), defaultProps)
|
|
155
|
+
const props = defineProps({
|
|
156
|
+
/**
|
|
157
|
+
* 接受的文件类型
|
|
158
|
+
* @values all,media,image,file,video
|
|
159
|
+
* */
|
|
160
|
+
accept: {
|
|
161
|
+
type: String,
|
|
162
|
+
default: "image",
|
|
163
|
+
},
|
|
164
|
+
/** 根据文件拓展名过滤,每一项都不能是空字符串。默认不过滤。 */
|
|
165
|
+
extension: {
|
|
166
|
+
type: Array as PropType<string[]>,
|
|
167
|
+
default: () => [],
|
|
168
|
+
},
|
|
169
|
+
/** 图片或视频拾取模式,当accept为image类型时设置capture可选额外camera可以直接调起摄像头 */
|
|
170
|
+
capture: {
|
|
171
|
+
type: Array as PropType<("album" | "camera")[]>,
|
|
172
|
+
default: () => ["album", "camera"],
|
|
173
|
+
},
|
|
174
|
+
/** 当accept为video时生效,是否压缩视频 */
|
|
175
|
+
compressed: {
|
|
176
|
+
type: Boolean,
|
|
177
|
+
default: true,
|
|
178
|
+
},
|
|
179
|
+
/** 当accept为video时生效,可选值为back或front */
|
|
180
|
+
camera: {
|
|
181
|
+
type: String,
|
|
182
|
+
default: "back",
|
|
183
|
+
},
|
|
184
|
+
/** 当accept为video时生效,拍摄视频最长拍摄时间,单位秒 */
|
|
185
|
+
maxDuration: {
|
|
186
|
+
type: Number,
|
|
187
|
+
default: 60,
|
|
188
|
+
},
|
|
189
|
+
/** 上传区域的图标,只能内置图标 */
|
|
190
|
+
uploadIcon: {
|
|
191
|
+
type: String,
|
|
192
|
+
default: IconConfig.UPLOAD,
|
|
193
|
+
},
|
|
194
|
+
/** 上传区域的图标的字体颜色,只能内置图标 */
|
|
195
|
+
uploadIconColor: {
|
|
196
|
+
type: String,
|
|
197
|
+
default: "#D3D4D6",
|
|
198
|
+
},
|
|
199
|
+
/** 是否开启文件读取前事件 */
|
|
200
|
+
useBeforeRead: {
|
|
201
|
+
type: Boolean,
|
|
202
|
+
default: false,
|
|
203
|
+
},
|
|
204
|
+
/** 是否显示组件自带的图片预览功能 */
|
|
205
|
+
previewFullImage: {
|
|
206
|
+
type: Boolean,
|
|
207
|
+
default: true,
|
|
208
|
+
},
|
|
209
|
+
/** 最大上传数量 */
|
|
210
|
+
maxCount: {
|
|
211
|
+
type: Number,
|
|
212
|
+
default: 52,
|
|
213
|
+
},
|
|
214
|
+
/** 是否启用 */
|
|
215
|
+
disabled: {
|
|
216
|
+
type: Boolean,
|
|
217
|
+
default: false,
|
|
218
|
+
},
|
|
219
|
+
/**
|
|
220
|
+
* 预览上传的图片时的裁剪模式,和image组件mode属性一致
|
|
221
|
+
* @values scaleToFill,aspectFit,aspectFill,widthFix,heightFix,top,bottom,center,left,right,top left,top right,bottom left,bottom right
|
|
222
|
+
* */
|
|
223
|
+
imageMode: {
|
|
224
|
+
type: String,
|
|
225
|
+
default: "aspectFill",
|
|
226
|
+
},
|
|
227
|
+
/** 标识符,可以在回调函数的第二项参数中获取 */
|
|
228
|
+
name: {
|
|
229
|
+
type: String,
|
|
230
|
+
default: "",
|
|
231
|
+
},
|
|
232
|
+
/** 所选的图片的尺寸 */
|
|
233
|
+
sizeType: {
|
|
234
|
+
type: Array as PropType<("original" | "compressed")[]>,
|
|
235
|
+
default: ["original", "compressed"],
|
|
236
|
+
},
|
|
237
|
+
/** 是否开启图片多选,部分安卓机型不支持 */
|
|
238
|
+
multiple: {
|
|
239
|
+
type: Boolean,
|
|
240
|
+
default: false,
|
|
241
|
+
},
|
|
242
|
+
/** 是否展示删除按钮 */
|
|
243
|
+
deletable: {
|
|
244
|
+
type: Boolean,
|
|
245
|
+
default: true,
|
|
246
|
+
},
|
|
247
|
+
/** 文件大小限制,单位为byte */
|
|
248
|
+
maxSize: {
|
|
249
|
+
type: Number,
|
|
250
|
+
default: Number.MAX_VALUE,
|
|
251
|
+
},
|
|
252
|
+
/** 显示已上传的文件列表 */
|
|
253
|
+
fileList: {
|
|
254
|
+
type: Array as PropType<FileVo[]>,
|
|
255
|
+
default: () => [],
|
|
256
|
+
},
|
|
257
|
+
/** 上传区域的提示文字 */
|
|
258
|
+
uploadText: {
|
|
259
|
+
type: String,
|
|
260
|
+
default: "",
|
|
261
|
+
},
|
|
262
|
+
/** 内部预览图片区域和选择图片按钮的区域宽度 */
|
|
263
|
+
width: {
|
|
264
|
+
type: [String, Number],
|
|
265
|
+
default: 80,
|
|
266
|
+
},
|
|
267
|
+
/** 内部预览图片区域和选择图片按钮的区域高度 */
|
|
268
|
+
height: {
|
|
269
|
+
type: [String, Number],
|
|
270
|
+
default: 80,
|
|
271
|
+
},
|
|
272
|
+
/** 读取前的处理函数 */
|
|
273
|
+
beforeRead: Function as PropType<ReadFunctionVo>,
|
|
274
|
+
/** 读取后的处理函数 */
|
|
275
|
+
afterRead: Function as PropType<ReadFunctionVo>,
|
|
276
|
+
/** 定义需要用到的外部样式 */
|
|
277
|
+
customStyle: {
|
|
278
|
+
type: Object as PropType<CSSProperties>,
|
|
279
|
+
},
|
|
280
|
+
});
|
|
281
|
+
const emit = defineEmits([
|
|
282
|
+
"clickPreview",
|
|
283
|
+
"beforeRead",
|
|
284
|
+
"error",
|
|
285
|
+
"delete",
|
|
286
|
+
"afterRead",
|
|
287
|
+
"oversize",
|
|
288
|
+
]);
|
|
144
289
|
|
|
145
|
-
const lists = ref<FileVo[]>([])
|
|
146
|
-
|
|
147
|
-
const
|
|
290
|
+
const lists = ref<FileVo[]>([]);
|
|
291
|
+
// 上传按钮
|
|
292
|
+
const isInCount = ref<boolean>(true);
|
|
293
|
+
// 遮罩框
|
|
294
|
+
const previewImage = ref<boolean>(true);
|
|
148
295
|
|
|
149
296
|
const formatFileList = () => {
|
|
150
|
-
lists.value = fileList.
|
|
297
|
+
lists.value = props.fileList.map((item: FileVo) =>
|
|
151
298
|
Object.assign(Object.assign({}, item), {
|
|
152
299
|
// 如果item.url为本地选择的blob文件的话,无法判断其为video还是image,此处优先通过accept做判断处理
|
|
153
|
-
isImage: accept
|
|
154
|
-
isVideo: accept
|
|
155
|
-
deletable: item.deletable || deletable
|
|
300
|
+
isImage: props.accept === "image",
|
|
301
|
+
isVideo: props.accept === "video",
|
|
302
|
+
deletable: item.deletable || props.deletable,
|
|
156
303
|
}),
|
|
157
|
-
)
|
|
158
|
-
isInCount.value = lists.value.length < maxCount
|
|
159
|
-
}
|
|
304
|
+
);
|
|
305
|
+
isInCount.value = lists.value.length < props.maxCount;
|
|
306
|
+
};
|
|
160
307
|
|
|
161
308
|
watch(
|
|
162
|
-
() => fileList
|
|
309
|
+
() => props.fileList,
|
|
163
310
|
() => {
|
|
164
|
-
formatFileList()
|
|
311
|
+
formatFileList();
|
|
165
312
|
},
|
|
166
313
|
{ immediate: true, deep: true },
|
|
167
|
-
)
|
|
314
|
+
);
|
|
168
315
|
|
|
169
316
|
watch(
|
|
170
|
-
() => deletable
|
|
317
|
+
() => props.deletable,
|
|
171
318
|
() => {
|
|
172
|
-
formatFileList()
|
|
319
|
+
formatFileList();
|
|
173
320
|
},
|
|
174
|
-
)
|
|
321
|
+
);
|
|
175
322
|
|
|
176
323
|
watch(
|
|
177
|
-
() => maxCount
|
|
324
|
+
() => props.maxCount,
|
|
178
325
|
() => {
|
|
179
|
-
formatFileList()
|
|
326
|
+
formatFileList();
|
|
180
327
|
},
|
|
181
|
-
)
|
|
328
|
+
);
|
|
182
329
|
|
|
183
330
|
watch(
|
|
184
|
-
() => accept
|
|
331
|
+
() => props.accept,
|
|
185
332
|
() => {
|
|
186
|
-
formatFileList()
|
|
333
|
+
formatFileList();
|
|
187
334
|
},
|
|
188
|
-
)
|
|
335
|
+
);
|
|
189
336
|
|
|
190
337
|
const chooseFileFn = () => {
|
|
191
|
-
if (disabled
|
|
338
|
+
if (props.disabled) return;
|
|
192
339
|
// 如果用户传入的是字符串,需要格式化成数组
|
|
193
|
-
let capture
|
|
194
|
-
try {
|
|
195
|
-
capture = Array.isArray(capture) ? capture : capture!.split(',')
|
|
196
|
-
} catch (e) {
|
|
197
|
-
capture = []
|
|
198
|
-
}
|
|
199
340
|
chooseFile(
|
|
200
341
|
Object.assign(
|
|
201
342
|
{
|
|
202
|
-
accept: accept
|
|
203
|
-
extension: extension
|
|
204
|
-
multiple: multiple
|
|
205
|
-
capture: capture,
|
|
206
|
-
compressed: compressed
|
|
207
|
-
maxDuration: maxDuration
|
|
208
|
-
sizeType: sizeType
|
|
209
|
-
camera: camera
|
|
343
|
+
accept: props.accept,
|
|
344
|
+
extension: props.extension,
|
|
345
|
+
multiple: props.multiple,
|
|
346
|
+
capture: props.capture,
|
|
347
|
+
compressed: props.compressed,
|
|
348
|
+
maxDuration: props.maxDuration,
|
|
349
|
+
sizeType: props.sizeType,
|
|
350
|
+
camera: props.camera,
|
|
210
351
|
},
|
|
211
352
|
{
|
|
212
|
-
maxCount: maxCount
|
|
353
|
+
maxCount: props.maxCount - lists.value.length,
|
|
213
354
|
},
|
|
214
355
|
),
|
|
215
356
|
)
|
|
216
357
|
.then((res: any) => {
|
|
217
|
-
onBeforeRead(multiple
|
|
358
|
+
onBeforeRead(props.multiple ? res : res[0]);
|
|
218
359
|
})
|
|
219
360
|
.catch((error) => {
|
|
220
|
-
emit(
|
|
221
|
-
})
|
|
222
|
-
}
|
|
361
|
+
emit("error", error);
|
|
362
|
+
});
|
|
363
|
+
};
|
|
223
364
|
// 文件读取之前
|
|
224
365
|
const onBeforeRead = (file: FileVo) => {
|
|
225
|
-
let res: any = true
|
|
366
|
+
let res: any = true;
|
|
226
367
|
// beforeRead是否为一个方法
|
|
227
|
-
if (typeof props.beforeRead ===
|
|
368
|
+
if (typeof props.beforeRead === "function") {
|
|
228
369
|
// 如果用户定义了此方法,则去执行此方法,并传入读取的文件回调
|
|
229
|
-
res = props.beforeRead(file, getDetail())
|
|
370
|
+
res = props.beforeRead(file, getDetail());
|
|
230
371
|
}
|
|
231
|
-
if (useBeforeRead
|
|
372
|
+
if (props.useBeforeRead) {
|
|
232
373
|
res = new Promise((resolve, reject) => {
|
|
233
374
|
emit(
|
|
234
|
-
|
|
375
|
+
"beforeRead",
|
|
235
376
|
Object.assign(
|
|
236
377
|
Object.assign(
|
|
237
378
|
{
|
|
@@ -241,149 +382,150 @@ const onBeforeRead = (file: FileVo) => {
|
|
|
241
382
|
),
|
|
242
383
|
{
|
|
243
384
|
callback: (ok: any) => {
|
|
244
|
-
ok ? resolve(ok) : reject()
|
|
385
|
+
ok ? resolve(ok) : reject();
|
|
245
386
|
},
|
|
246
387
|
},
|
|
247
388
|
),
|
|
248
|
-
)
|
|
249
|
-
})
|
|
389
|
+
);
|
|
390
|
+
});
|
|
250
391
|
}
|
|
251
|
-
if (!res) return
|
|
252
|
-
if (typeof res ===
|
|
253
|
-
res.then((data: any) => onAfterRead(data || file))
|
|
392
|
+
if (!res) return;
|
|
393
|
+
if (typeof res === "function") {
|
|
394
|
+
res.then((data: any) => onAfterRead(data || file));
|
|
254
395
|
} else {
|
|
255
|
-
onAfterRead(file)
|
|
396
|
+
onAfterRead(file);
|
|
256
397
|
}
|
|
257
|
-
}
|
|
398
|
+
};
|
|
258
399
|
const getDetail = (index?: number) => {
|
|
259
400
|
return {
|
|
260
|
-
name: name
|
|
261
|
-
index: index == null ? fileList.
|
|
262
|
-
}
|
|
263
|
-
}
|
|
401
|
+
name: props.name,
|
|
402
|
+
index: index == null ? props.fileList.length : index,
|
|
403
|
+
};
|
|
404
|
+
};
|
|
264
405
|
const onAfterRead = (file: FileVo) => {
|
|
265
|
-
const oversize =
|
|
266
|
-
? file.some((item) => item.size > maxSize
|
|
267
|
-
: file.size > maxSize
|
|
406
|
+
const oversize = isArray(file)
|
|
407
|
+
? file.some((item) => item.size > props.maxSize)
|
|
408
|
+
: Number(file.size) > props.maxSize;
|
|
268
409
|
if (oversize) {
|
|
269
410
|
emit(
|
|
270
|
-
|
|
411
|
+
"oversize",
|
|
271
412
|
Object.assign(
|
|
272
413
|
{
|
|
273
414
|
file,
|
|
274
415
|
},
|
|
275
416
|
getDetail(),
|
|
276
417
|
),
|
|
277
|
-
)
|
|
278
|
-
return
|
|
418
|
+
);
|
|
419
|
+
return;
|
|
279
420
|
}
|
|
280
|
-
if (typeof props.afterRead ===
|
|
281
|
-
props.afterRead(file, getDetail())
|
|
421
|
+
if (typeof props.afterRead === "function") {
|
|
422
|
+
props.afterRead(file, getDetail());
|
|
282
423
|
}
|
|
283
424
|
emit(
|
|
284
|
-
|
|
425
|
+
"afterRead",
|
|
285
426
|
Object.assign(
|
|
286
427
|
{
|
|
287
428
|
file,
|
|
288
429
|
},
|
|
289
430
|
getDetail(),
|
|
290
431
|
),
|
|
291
|
-
)
|
|
292
|
-
}
|
|
432
|
+
);
|
|
433
|
+
};
|
|
293
434
|
|
|
294
435
|
/**
|
|
295
436
|
* @description 删除文件
|
|
296
437
|
* */
|
|
297
438
|
const deleteItem = (index: number) => {
|
|
298
|
-
fileList.
|
|
299
|
-
isInCount.value = lists.value.length < maxCount
|
|
439
|
+
props.fileList.splice(index, 1);
|
|
440
|
+
isInCount.value = lists.value.length < props.maxCount;
|
|
300
441
|
emit(
|
|
301
|
-
|
|
442
|
+
"delete",
|
|
302
443
|
Object.assign(Object.assign({}, getDetail(index)), {
|
|
303
|
-
file: fileList
|
|
444
|
+
file: props.fileList[index],
|
|
304
445
|
}),
|
|
305
|
-
)
|
|
306
|
-
}
|
|
446
|
+
);
|
|
447
|
+
};
|
|
307
448
|
|
|
308
449
|
/**
|
|
309
450
|
* @description 预览图片
|
|
310
451
|
* */
|
|
311
452
|
const onPreviewImage = (previewItem: FileVo, index: number) => {
|
|
312
|
-
if (!previewItem.isImage || !previewFullImage
|
|
313
|
-
let current = 0
|
|
314
|
-
const urls = []
|
|
315
|
-
let imageIndex = 0
|
|
316
|
-
for (
|
|
317
|
-
const item: FileVo = lists.value[i]
|
|
318
|
-
if (item.isImage || (item.type && item.type ===
|
|
319
|
-
urls.push(item.url || item.thumb)
|
|
453
|
+
if (!previewItem.isImage || !props.previewFullImage) return;
|
|
454
|
+
let current = 0;
|
|
455
|
+
const urls: string[] = [];
|
|
456
|
+
let imageIndex = 0;
|
|
457
|
+
for (let i = 0; i < lists.value.length; i++) {
|
|
458
|
+
const item: FileVo = lists.value[i];
|
|
459
|
+
if (item.isImage || (item.type && item.type === "image")) {
|
|
460
|
+
urls.push(item.url || (item.thumb as string));
|
|
320
461
|
if (i === index) {
|
|
321
|
-
current = imageIndex
|
|
462
|
+
current = imageIndex;
|
|
322
463
|
}
|
|
323
|
-
imageIndex += 1
|
|
464
|
+
imageIndex += 1;
|
|
324
465
|
}
|
|
325
466
|
}
|
|
326
|
-
if (urls.length < 1)
|
|
327
|
-
return
|
|
328
|
-
}
|
|
467
|
+
if (!urls || urls.length < 1) return;
|
|
329
468
|
uni.previewImage({
|
|
330
469
|
urls: urls,
|
|
331
470
|
current: current,
|
|
332
471
|
fail() {
|
|
333
|
-
uni.showToast({ title:
|
|
472
|
+
uni.showToast({ title: "预览图片失败" });
|
|
334
473
|
},
|
|
335
|
-
})
|
|
336
|
-
}
|
|
474
|
+
});
|
|
475
|
+
};
|
|
337
476
|
|
|
338
477
|
/**
|
|
339
478
|
* @description 预览视频
|
|
340
479
|
* */
|
|
341
480
|
const onPreviewVideo = (index: number) => {
|
|
342
|
-
if (!previewFullImage
|
|
343
|
-
let current = 0
|
|
344
|
-
const sources: any[] = []
|
|
345
|
-
let videoIndex = 0
|
|
481
|
+
if (!props.previewFullImage) return;
|
|
482
|
+
let current = 0;
|
|
483
|
+
const sources: any[] = [];
|
|
484
|
+
let videoIndex = 0;
|
|
346
485
|
for (let i = 0; i < lists.value.length; i++) {
|
|
347
|
-
const item: FileVo = lists.value[i]
|
|
348
|
-
if (item.isVideo || (item.type && item.type ===
|
|
486
|
+
const item: FileVo = lists.value[i];
|
|
487
|
+
if (item.isVideo || (item.type && item.type === "video")) {
|
|
349
488
|
sources.push(
|
|
350
489
|
Object.assign(Object.assign({}, item), {
|
|
351
|
-
type:
|
|
490
|
+
type: "video",
|
|
352
491
|
}),
|
|
353
|
-
)
|
|
492
|
+
);
|
|
354
493
|
if (i === index) {
|
|
355
|
-
current = videoIndex
|
|
494
|
+
current = videoIndex;
|
|
356
495
|
}
|
|
357
|
-
videoIndex += 1
|
|
496
|
+
videoIndex += 1;
|
|
358
497
|
}
|
|
359
498
|
}
|
|
360
499
|
if (sources.length < 1) {
|
|
361
|
-
return
|
|
500
|
+
return;
|
|
362
501
|
}
|
|
363
502
|
// #ifdef MP-WEIXIN
|
|
364
503
|
wx.previewMedia({
|
|
365
504
|
sources: sources,
|
|
366
505
|
current: current,
|
|
367
506
|
fail() {
|
|
368
|
-
uni.showToast({ title:
|
|
507
|
+
uni.showToast({ title: "预览视频失败" });
|
|
369
508
|
},
|
|
370
|
-
})
|
|
509
|
+
});
|
|
371
510
|
// #endif
|
|
372
|
-
}
|
|
511
|
+
};
|
|
373
512
|
|
|
374
513
|
const onClickPreview = (item: FileVo, index: number) => {
|
|
375
|
-
if (!previewFullImage
|
|
514
|
+
if (!props.previewFullImage) return;
|
|
376
515
|
switch (item.type) {
|
|
377
|
-
case
|
|
378
|
-
onPreviewVideo(index)
|
|
379
|
-
break
|
|
516
|
+
case "video":
|
|
517
|
+
onPreviewVideo(index);
|
|
518
|
+
break;
|
|
380
519
|
default:
|
|
381
|
-
break
|
|
520
|
+
break;
|
|
382
521
|
}
|
|
383
|
-
emit(
|
|
384
|
-
|
|
522
|
+
emit(
|
|
523
|
+
"clickPreview",
|
|
524
|
+
Object.assign(Object.assign({}, item), getDetail(index)),
|
|
525
|
+
);
|
|
526
|
+
};
|
|
385
527
|
</script>
|
|
386
528
|
|
|
387
529
|
<style lang="scss" scoped>
|
|
388
|
-
@import
|
|
530
|
+
@import "./index.scss";
|
|
389
531
|
</style>
|