Skip to content

Commit 3e15808

Browse files
committed
[2.7.0] Added <Upload /> control
1 parent ae45b45 commit 3e15808

File tree

16 files changed

+441
-35
lines changed

16 files changed

+441
-35
lines changed

CHANGELOG.md

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,20 @@
1+
## 2.7.0
2+
3+
### Added
4+
5+
`<Upload />` control
6+
17
## 2.6.1
28

9+
### Fixed
10+
311
- Check `<Autocomplete />` initial value. If it's string — use it. If there is a default value for this control — use it.
412

513
## 2.6.0
614

7-
- Added `<Autocomplete />` control
15+
### Added
16+
17+
- `<Autocomplete />` control
818

919
## 2.5.11
1020

README.md

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -74,11 +74,13 @@ See demo at [https://detools.github.io/vue-form](https://detools.github.io/vue-f
7474
- [Slider](/VueForm/components/ConnectedSlider.js)
7575
- [Switch](/VueForm/components/ConnectedSwitch.js)
7676
- [TimePicker](/VueForm/components/ConnectedTimePicker.js)
77+
- [Upload](/VueForm/components/ConnectedUpload.js)
7778
- [FieldArray](/VueForm/components/ConnectedFieldArray.js)
7879
- [Form](/VueForm/components/Form/Form.vue)
7980

8081
## Changelog
8182

83+
- [2.7.0](/CHANGELOG.md#270)
8284
- [2.6.1](/CHANGELOG.md#261)
8385
- [2.6.0](/CHANGELOG.md#260)
8486
- [2.5.11](/CHANGELOG.md#2511)
@@ -107,12 +109,3 @@ See demo at [https://detools.github.io/vue-form](https://detools.github.io/vue-f
107109
- [1.4.2](/CHANGELOG.md#142)
108110
- [1.4.1](/CHANGELOG.md#141)
109111
- [1.4.0](/CHANGELOG.md#140)
110-
111-
## Roadmap
112-
113-
- Add remaining components
114-
- `<Upload />`
115-
- `<Rate />`
116-
- Add validation examples
117-
- [Field level sync/async validation](https://detools.github.io/vue-form/#/inline-validators-form)
118-
- [Form level sync validation](https://detools.github.io/vue-form/#/sync-validation-form)
Lines changed: 194 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,194 @@
1+
import { Upload } from 'element-ui'
2+
import noop from 'lodash/noop'
3+
import ConnectedControlMixin from '../mixins/ConnectedControl'
4+
5+
const defaultHandler = {
6+
type: Function,
7+
default: noop,
8+
}
9+
10+
const httpRequest = ({ headers, file, filename, action }) => {
11+
const method = 'POST'
12+
13+
const body = new FormData()
14+
15+
body.append(filename, file)
16+
17+
return fetch(action, {
18+
method,
19+
headers,
20+
body,
21+
}).then(response => response.json())
22+
}
23+
24+
const ConnectedInput = {
25+
props: {
26+
name: {
27+
type: String,
28+
required: true,
29+
},
30+
31+
endpoint: {
32+
type: String,
33+
required: true,
34+
},
35+
36+
headers: Object,
37+
multiple: Boolean,
38+
data: Object,
39+
40+
// name on element-ui
41+
prop: {
42+
type: String,
43+
default: 'file',
44+
},
45+
46+
withCredentials: Boolean,
47+
showFileList: Boolean,
48+
drag: Boolean,
49+
accept: String,
50+
51+
// hook function when clicking the uploaded files
52+
handlePreview: defaultHandler,
53+
54+
// hook function when files are removed
55+
handleRemove: defaultHandler,
56+
57+
// hook function when uploaded successfully
58+
handleSuccess: defaultHandler,
59+
60+
// hook function when some errors occurs
61+
handleError: defaultHandler,
62+
63+
// hook function when some progress occurs
64+
handleProgress: defaultHandler,
65+
66+
// hook function when select file or upload file success or upload file fail
67+
handleChange: defaultHandler,
68+
69+
// hook function before uploading with the file to be uploaded as its parameter.
70+
// If false is returned or a Promise is returned and then is rejected, uploading will be aborted
71+
beforeUpload: defaultHandler,
72+
73+
// hook function before removing a file with the file and file list as its parameters.
74+
// If false is returned or a Promise is returned and then is rejected, removing will be aborted
75+
beforeRemove: defaultHandler,
76+
77+
// hook function when limit is exceeded
78+
handleExceed: defaultHandler,
79+
80+
formatResponse: {
81+
type: Function,
82+
default: response => response,
83+
},
84+
85+
fileList: {
86+
type: Array,
87+
default: () => [],
88+
},
89+
listType: {
90+
type: String,
91+
default: 'text',
92+
},
93+
autoUpload: {
94+
type: Boolean,
95+
default: true,
96+
},
97+
httpRequest: {
98+
type: Function,
99+
default: httpRequest,
100+
},
101+
disabled: Boolean,
102+
limit: Number,
103+
104+
// Slots
105+
trigger: [Function, Object],
106+
tip: [Function, Object],
107+
108+
// FormItem Props
109+
label: [String, Boolean],
110+
formItem: Boolean,
111+
labelWidth: String,
112+
113+
// vue-form Props
114+
validators: Array,
115+
asyncValidators: Array,
116+
},
117+
118+
mixins: [ConnectedControlMixin],
119+
120+
computed: {
121+
callbacks() {
122+
return {
123+
props: {
124+
onPreview: this.handlePreview,
125+
onRemove: this.handleRemove,
126+
onSuccess: this.handleFieldSuccess,
127+
onError: this.handleError,
128+
onProgress: this.handleProgress,
129+
onChange: this.handleFieldChange,
130+
onExceed: this.handleExceed,
131+
},
132+
}
133+
},
134+
},
135+
136+
methods: {
137+
clearFiles() {
138+
return this.$refs.uiUpload.clearFiles()
139+
},
140+
141+
abort(...args) {
142+
return this.$refs.uiUpload.abort(...args)
143+
},
144+
145+
submit() {
146+
return this.refs.$uiUpload.submit()
147+
},
148+
149+
handleFieldRemove() {
150+
this.handleRemove()
151+
152+
const [, setValue] = this.state
153+
setValue([])
154+
},
155+
156+
handleFieldSuccess(response, file, filelist) {
157+
this.handleSuccess(response, file, filelist)
158+
159+
const [, setValue] = this.state
160+
setValue(this.formatResponse(response, file, filelist))
161+
},
162+
163+
renderComponent() {
164+
return (
165+
<Upload
166+
{...this.callbacks}
167+
ref="uiUpload"
168+
action={this.endpoint}
169+
headers={this.headers}
170+
multiple={this.multiple}
171+
data={this.data}
172+
name={this.prop}
173+
with-credentials={this.withCredentials}
174+
show-file-list={this.showFileList}
175+
drag={this.drag}
176+
accept={this.accept}
177+
before-upload={this.beforeUpload}
178+
before-remove={this.beforeRemove}
179+
file-list={this.fileList}
180+
list-type={this.listType}
181+
auto-upload={this.autoUpload}
182+
http-request={this.httpRequest}
183+
disabled={this.disabled}
184+
limit={this.limit}>
185+
{Boolean(this.trigger) && <template slot="trigger">{this.trigger}</template>}
186+
{Boolean(this.tip) && <template slot="tip">{this.tip}</template>}
187+
{this.$slots.default}
188+
</Upload>
189+
)
190+
},
191+
},
192+
}
193+
194+
export default ConnectedInput

VueForm/index.js

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import Slider from './components/ConnectedSlider'
1212
import TimePicker from './components/ConnectedTimePicker'
1313
import DatePicker from './components/ConnectedDatePicker'
1414
import ArrayField from './components/ConnectedArrayField'
15+
import Upload from './components/ConnectedUpload'
1516
import FormItem from './components/ConnectedFormItem'
1617

1718
import Notification from './components/Notification'
@@ -31,8 +32,9 @@ export {
3132
Slider,
3233
TimePicker,
3334
DatePicker,
34-
FormItem,
3535
ArrayField,
36+
Upload,
37+
FormItem,
3638
Notification,
3739
validators,
3840
}

docs/bundle.js

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

docs/main.css

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,34 +1,34 @@
11

2-
.root-container[data-v-a1275c98] {
2+
.root-container[data-v-d5068ce6] {
33
min-height: 100%;
44
}
5-
.title[data-v-a1275c98] {
5+
.title[data-v-d5068ce6] {
66
font-size: 40px;
77
margin: 10px 0 0;
88
font-weight: bold;
99
}
10-
.main-container[data-v-a1275c98] {
10+
.main-container[data-v-d5068ce6] {
1111
display: flex;
1212
flex-direction: row;
1313
justify-content: space-between;
1414
align-items: stretch;
1515
}
16-
.aside[data-v-a1275c98] {
16+
.aside[data-v-d5068ce6] {
1717
border-top: 1px solid rgba(0, 0, 0, 0.1);
1818
}
19-
.main[data-v-a1275c98] {
19+
.main[data-v-d5068ce6] {
2020
padding: 10px 40px 40px;
2121
border-top: 1px solid rgba(0, 0, 0, 0.1);
2222
border-left: 1px solid rgba(0, 0, 0, 0.1);
2323
}
24-
.link[data-v-a1275c98] {
24+
.link[data-v-d5068ce6] {
2525
display: block;
2626
line-height: 40px;
2727
padding-left: 30px;
2828
position: relative;
2929
color: #0a0a0a;
3030
}
31-
.link_active[data-v-a1275c98]:before {
31+
.link_active[data-v-d5068ce6]:before {
3232
content: '\261B';
3333
position: absolute;
3434
display: block;

docs/vendors~main.bundle.js

Lines changed: 4 additions & 4 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

example/src/App.vue

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ export default {
2121
'AllValidationsForm',
2222
'ArrayFieldForm',
2323
'AutocompleteForm',
24+
'UploadForm',
2425
],
2526
}
2627
},

example/src/forms/AutocompleteForm/AutocompleteForm.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ export default {
3232
render() {
3333
return (
3434
<div>
35-
<h1>Sync Validation Form</h1>
35+
<h1>Autocomplete Form</h1>
3636
<div class="wrapper">
3737
<div class="form">
3838
<Form
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
import Form, { Input, Upload, validators } from '@detools/vue-form'
2+
import { Button } from 'element-ui'
3+
4+
export default {
5+
data() {
6+
return {
7+
formValues: {},
8+
}
9+
},
10+
11+
methods: {
12+
handleSubmit(values) {
13+
this.formValues = values
14+
},
15+
},
16+
17+
render() {
18+
return (
19+
<div>
20+
<h1>Upload Form</h1>
21+
<div class="wrapper">
22+
<div class="form">
23+
<Form
24+
submit
25+
labelWidth="150px"
26+
labelPosition="left"
27+
labelSuffix=":"
28+
buttonsPosition="start"
29+
handleSubmit={this.handleSubmit}>
30+
<Input formItem label name="username" />
31+
<Upload
32+
formItem
33+
label
34+
endpoint="upload"
35+
name="files"
36+
validators={[validators.isRequired()]}
37+
formatResponse={({ items }) => items}>
38+
<Button>Upload</Button>
39+
</Upload>
40+
</Form>
41+
</div>
42+
<div class="values">
43+
<strong>Form Values</strong>
44+
<br />
45+
<br />
46+
<div>
47+
<pre>{JSON.stringify(this.formValues, null, 2)}</pre>
48+
</div>
49+
</div>
50+
</div>
51+
</div>
52+
)
53+
},
54+
}

0 commit comments

Comments
 (0)