mirror of
https://gitee.com/baidu/amis.git
synced 2024-11-29 18:48:45 +08:00
Merge pull request #3568 from gooolh/feat-input-image-event
feat: input-image 事件动作补充
This commit is contained in:
commit
e5b44cef2d
@ -1,3 +1,38 @@
|
||||
const getEventDesc = eventName => {
|
||||
return {
|
||||
actions: [
|
||||
{
|
||||
actionType: 'toast',
|
||||
msgType: 'info',
|
||||
msg: `派发${eventName}事件`
|
||||
}
|
||||
]
|
||||
};
|
||||
};
|
||||
|
||||
const change = {
|
||||
actions: [
|
||||
{
|
||||
actionType: 'dialog',
|
||||
args: {
|
||||
val: '${event.data.file}'
|
||||
},
|
||||
dialog: {
|
||||
title: `派发change事件`,
|
||||
data: {
|
||||
val: '${val}'
|
||||
},
|
||||
body: [
|
||||
{
|
||||
type: 'tpl',
|
||||
tpl: '${val|json}'
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
]
|
||||
};
|
||||
|
||||
export default {
|
||||
type: 'page',
|
||||
title: '上传类组件事件',
|
||||
@ -39,7 +74,55 @@ export default {
|
||||
type: 'input-file',
|
||||
id: 'clear-input-file',
|
||||
name: 'file',
|
||||
multiple: true
|
||||
multiple: true,
|
||||
onEvent: {
|
||||
change,
|
||||
remove: getEventDesc('remove'),
|
||||
success: getEventDesc('success'),
|
||||
fail: getEventDesc('fail')
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
type: 'form',
|
||||
debug: true,
|
||||
api: '/api/mock2/form/saveForm',
|
||||
body: [
|
||||
{
|
||||
type: 'group',
|
||||
body: [
|
||||
{
|
||||
name: 'trigger2',
|
||||
id: 'trigger2',
|
||||
type: 'action',
|
||||
label: 'clear触发器',
|
||||
level: 'primary',
|
||||
onEvent: {
|
||||
click: {
|
||||
actions: [
|
||||
{
|
||||
actionType: 'clear',
|
||||
componentId: 'clear-input-image',
|
||||
description: '点击清除数据'
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
type: 'input-image',
|
||||
id: 'clear-input-image',
|
||||
name: 'file',
|
||||
multiple: true,
|
||||
onEvent: {
|
||||
change,
|
||||
remove: getEventDesc('remove'),
|
||||
success: getEventDesc('success'),
|
||||
fail: getEventDesc('fail')
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
|
@ -5,7 +5,7 @@ import isPlainObject from 'lodash/isPlainObject';
|
||||
// @ts-ignore
|
||||
import mapLimit from 'async/mapLimit';
|
||||
import ImageControl from './InputImage';
|
||||
import {Payload, ApiObject, ApiString, Action} from '../../types';
|
||||
import {Payload, ApiObject, ApiString} from '../../types';
|
||||
import {filter} from '../../utils/tpl';
|
||||
import Alert from '../../components/Alert2';
|
||||
import {qsstringify, createObject, guid, isEmpty} from '../../utils/helper';
|
||||
@ -509,7 +509,6 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
}
|
||||
}
|
||||
);
|
||||
// 添加文件触发
|
||||
this.dispatchEvent('change');
|
||||
}
|
||||
|
||||
@ -711,7 +710,7 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
uploading: false
|
||||
},
|
||||
() => {
|
||||
this.onChange(!!this.resolve);
|
||||
this.onChange(!!this.resolve, false);
|
||||
|
||||
if (this.resolve) {
|
||||
this.resolve(
|
||||
@ -796,7 +795,7 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
},
|
||||
onProgress
|
||||
)
|
||||
.then(ret => {
|
||||
.then(async ret => {
|
||||
if ((ret.status && (ret as any).status !== '0') || !ret.data) {
|
||||
throw new Error(ret.msg || __('File.errorRetry'));
|
||||
}
|
||||
@ -805,7 +804,10 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
let value =
|
||||
(ret.data as any).value || (ret.data as any).url || ret.data;
|
||||
|
||||
this.dispatchEvent('success', file);
|
||||
const dispatcher = await this.dispatchEvent('success', file);
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
cb(null, file, {
|
||||
...(isPlainObject(ret.data) ? ret.data : null),
|
||||
value: value,
|
||||
@ -813,8 +815,11 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
id: file.id
|
||||
});
|
||||
})
|
||||
.catch(error => {
|
||||
this.dispatchEvent('fail', file);
|
||||
.catch(async error => {
|
||||
const dispatcher = await this.dispatchEvent('fail', {file, error});
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
cb(error.message || __('File.errorRetry'), file);
|
||||
});
|
||||
}
|
||||
@ -823,7 +828,10 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
const files = this.state.files.concat();
|
||||
const removeFile = files[index];
|
||||
// 触发移出文件事件
|
||||
await this.dispatchEvent('remove', removeFile);
|
||||
const dispatcher = await this.dispatchEvent('remove', removeFile);
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
this.removeFileCanelExecutor(file, true);
|
||||
files.splice(index, 1);
|
||||
|
||||
@ -838,7 +846,6 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
},
|
||||
isUploading ? this.tick : this.onChange
|
||||
);
|
||||
this.dispatchEvent('change');
|
||||
}
|
||||
|
||||
clearError() {
|
||||
@ -847,7 +854,7 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
});
|
||||
}
|
||||
|
||||
onChange(changeImmediately?: boolean) {
|
||||
async onChange(changeImmediately?: boolean, isFileChange = true) {
|
||||
const {
|
||||
multiple,
|
||||
onChange,
|
||||
@ -881,6 +888,12 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
} else {
|
||||
value = typeof resetValue === 'undefined' ? '' : resetValue;
|
||||
}
|
||||
if (isFileChange) {
|
||||
const dispatcher = await this.dispatchEvent('change');
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
onChange((this.emitValue = value), undefined, changeImmediately);
|
||||
this.syncAutoFill();
|
||||
@ -1188,19 +1201,15 @@ export default class FileControl extends React.Component<FileProps, FileState> {
|
||||
}
|
||||
}
|
||||
|
||||
async dispatchEvent(
|
||||
e: string,
|
||||
data?: Array<FileX | FileValue> | FileX | FileValue
|
||||
) {
|
||||
async dispatchEvent(e: string, data?: Record<string, any>) {
|
||||
const {dispatchEvent} = this.props;
|
||||
data = data ? data : this.state.files;
|
||||
return dispatchEvent(e, createObject(this.props.data, data));
|
||||
}
|
||||
|
||||
doAction(action: Action, data: object, throwErrors: boolean = false): any {
|
||||
if (action.actionType === 'clear') {
|
||||
this.setState({files: []});
|
||||
}
|
||||
data = data || this.state.files;
|
||||
return dispatchEvent(
|
||||
e,
|
||||
createObject(this.props.data, {
|
||||
file: data
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
render() {
|
||||
|
@ -689,7 +689,7 @@ export default class ImageControl extends React.Component<
|
||||
locked: false
|
||||
},
|
||||
() => {
|
||||
this.onChange(!!this.resolve);
|
||||
this.onChange(!!this.resolve, false);
|
||||
|
||||
if (this.resolve) {
|
||||
this.resolve(
|
||||
@ -704,9 +704,12 @@ export default class ImageControl extends React.Component<
|
||||
}
|
||||
}
|
||||
|
||||
removeFile(file: FileValue, index: number) {
|
||||
async removeFile(file: FileValue, index: number) {
|
||||
const files = this.files.concat();
|
||||
|
||||
const dispatcher = await this.dispatchEvent('remove', file);
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
this.removeFileCanelExecutor(file, true);
|
||||
files.splice(index, 1);
|
||||
|
||||
@ -756,7 +759,7 @@ export default class ImageControl extends React.Component<
|
||||
});
|
||||
}
|
||||
|
||||
onChange(changeImmediately?: boolean) {
|
||||
async onChange(changeImmediately?: boolean, isFileChange = true) {
|
||||
const {
|
||||
multiple,
|
||||
onChange,
|
||||
@ -789,6 +792,12 @@ export default class ImageControl extends React.Component<
|
||||
? newValue[valueField || 'value']
|
||||
: newValue;
|
||||
}
|
||||
if (isFileChange) {
|
||||
const dispatcher = await this.dispatchEvent('change');
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
onChange((this.emitValue = newValue || ''), undefined, changeImmediately);
|
||||
this.syncAutoFill();
|
||||
@ -973,6 +982,7 @@ export default class ImageControl extends React.Component<
|
||||
}
|
||||
}
|
||||
);
|
||||
this.dispatchEvent('change');
|
||||
}
|
||||
|
||||
sendFile(
|
||||
@ -987,7 +997,7 @@ export default class ImageControl extends React.Component<
|
||||
}
|
||||
|
||||
const image = new Image();
|
||||
image.onload = () => {
|
||||
image.onload = async () => {
|
||||
const width = image.width;
|
||||
const height = image.height;
|
||||
let error = '';
|
||||
@ -1024,6 +1034,10 @@ export default class ImageControl extends React.Component<
|
||||
|
||||
if (error) {
|
||||
file.state = 'invalid';
|
||||
const dispatcher = await this.dispatchEvent('fail', {file, error});
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
cb(error, file);
|
||||
} else {
|
||||
this._upload(file, cb, onProgress);
|
||||
@ -1033,13 +1047,13 @@ export default class ImageControl extends React.Component<
|
||||
}
|
||||
|
||||
_upload(
|
||||
file: Blob,
|
||||
file: FileX,
|
||||
cb: (error: null | string, file: Blob, obj?: FileValue) => void,
|
||||
onProgress: (progress: number) => void
|
||||
) {
|
||||
const __ = this.props.translate;
|
||||
this._send(file, this.props.receiver as string, {}, onProgress)
|
||||
.then((ret: Payload) => {
|
||||
.then(async (ret: Payload) => {
|
||||
if (ret.status && (ret as any).status !== '0') {
|
||||
throw new Error(ret.msg || __('File.errorRetry'));
|
||||
}
|
||||
@ -1050,9 +1064,22 @@ export default class ImageControl extends React.Component<
|
||||
};
|
||||
obj.value = obj.value || obj.url;
|
||||
|
||||
const dispatcher = await this.dispatchEvent('success', obj);
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
cb(null, file, obj);
|
||||
})
|
||||
.catch(error => cb(error.message || __('File.errorRetry'), file));
|
||||
.catch(async error => {
|
||||
const dispatcher = await this.dispatchEvent('fail', {
|
||||
file,
|
||||
error
|
||||
});
|
||||
if (dispatcher?.prevented) {
|
||||
return;
|
||||
}
|
||||
cb(error.message || __('File.errorRetry'), file);
|
||||
});
|
||||
}
|
||||
|
||||
async _send(
|
||||
@ -1206,6 +1233,12 @@ export default class ImageControl extends React.Component<
|
||||
}
|
||||
}
|
||||
|
||||
async dispatchEvent(e: string, data?: Record<string, any>) {
|
||||
const {dispatchEvent} = this.props;
|
||||
data = data ? data : this.state.files;
|
||||
return dispatchEvent(e, createObject(this.props.data, {file: data}));
|
||||
}
|
||||
|
||||
render() {
|
||||
const {
|
||||
className,
|
||||
|
Loading…
Reference in New Issue
Block a user