mirror of https://github.com/ElemeFE/element
add listType
parent
2f61998e78
commit
02a1f74022
|
@ -46,7 +46,6 @@
|
||||||
"row": "./packages/row/index.js",
|
"row": "./packages/row/index.js",
|
||||||
"col": "./packages/col/index.js",
|
"col": "./packages/col/index.js",
|
||||||
"upload": "./packages/upload/index.js",
|
"upload": "./packages/upload/index.js",
|
||||||
"upload-dragger": "./packages/upload/index.js",
|
|
||||||
"progress": "./packages/progress/index.js",
|
"progress": "./packages/progress/index.js",
|
||||||
"spinner": "./packages/spinner/index.js",
|
"spinner": "./packages/spinner/index.js",
|
||||||
"message": "./packages/message/index.js",
|
"message": "./packages/message/index.js",
|
||||||
|
|
|
@ -10,6 +10,32 @@
|
||||||
.upload-demo {
|
.upload-demo {
|
||||||
width: 360px;
|
width: 360px;
|
||||||
}
|
}
|
||||||
|
.avatar-uploader {
|
||||||
|
.el-upload {
|
||||||
|
border: 1px dashed #d9d9d9;
|
||||||
|
border-radius: 6px;
|
||||||
|
cursor: pointer;
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
border-color: #20a0ff;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.avatar-uploader-icon {
|
||||||
|
font-size: 28px;
|
||||||
|
color: #8c939d;
|
||||||
|
width: 178px;
|
||||||
|
height: @width;
|
||||||
|
line-height: @height;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
.avatar {
|
||||||
|
width: 178px;
|
||||||
|
height: @width;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
<script>
|
<script>
|
||||||
|
@ -24,7 +50,8 @@
|
||||||
name: 'food2.jpeg',
|
name: 'food2.jpeg',
|
||||||
url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100',
|
url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100',
|
||||||
status: 'finished'
|
status: 'finished'
|
||||||
}]
|
}],
|
||||||
|
imageUrl: ''
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
|
@ -52,6 +79,21 @@
|
||||||
},
|
},
|
||||||
submitUpload() {
|
submitUpload() {
|
||||||
this.$refs.upload.submit();
|
this.$refs.upload.submit();
|
||||||
|
},
|
||||||
|
handleAvatarScucess(res, file) {
|
||||||
|
this.imageUrl = URL.createObjectURL(file.raw);
|
||||||
|
},
|
||||||
|
beforeAvatarUpload(file) {
|
||||||
|
const isJPG = file.type === 'image/jpeg';
|
||||||
|
const isLt2M = file.size / 1024 / 1024 < 2;
|
||||||
|
|
||||||
|
if (!isJPG) {
|
||||||
|
this.$message.error('上传头像图片只能是 JPG 格式!');
|
||||||
|
}
|
||||||
|
if (!isLt2M) {
|
||||||
|
this.$message.error('上传头像图片大小不能超过 2MB!');
|
||||||
|
}
|
||||||
|
return isJPG && isLt2M;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -61,13 +103,13 @@
|
||||||
|
|
||||||
通过点击或者拖拽上传文件
|
通过点击或者拖拽上传文件
|
||||||
|
|
||||||
### 点击上传多个文件
|
### 点击上传
|
||||||
|
|
||||||
::: demo 通过 slot 你可以传入自定义的上传按钮类型和文字提示。
|
::: demo 通过 slot 你可以传入自定义的上传按钮类型和文字提示。
|
||||||
```html
|
```html
|
||||||
<el-upload
|
<el-upload
|
||||||
class="upload-demo"
|
class="upload-demo"
|
||||||
action="//jsonplaceholder.typicode.com/posts/"
|
action="http://localhost:9000/upload"
|
||||||
:on-preview="handlePreview"
|
:on-preview="handlePreview"
|
||||||
:on-remove="handleRemove"
|
:on-remove="handleRemove"
|
||||||
:file-list="fileList">
|
:file-list="fileList">
|
||||||
|
@ -94,18 +136,121 @@
|
||||||
```
|
```
|
||||||
:::
|
:::
|
||||||
|
|
||||||
::: demo 通过 slot 你可以传入自定义的上传按钮类型和文字提示。
|
### 用户头像上传
|
||||||
|
|
||||||
|
使用 beforeUpload 限制用户上传的图片格式和大小。
|
||||||
|
|
||||||
|
::: demo
|
||||||
|
```html
|
||||||
|
<el-upload
|
||||||
|
class="avatar-uploader"
|
||||||
|
action="http://localhost:9000/upload"
|
||||||
|
:show-file-list="false"
|
||||||
|
:on-success="handleAvatarScucess"
|
||||||
|
:before-upload="beforeAvatarUpload">
|
||||||
|
<img v-if="imageUrl" :src="imageUrl" class="avatar">
|
||||||
|
<i v-else class="el-icon-plus avatar-uploader-icon"></i>
|
||||||
|
</el-upload>
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
fileList: [{name: 'food.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}, {name: 'food2.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}]
|
||||||
|
};
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
handleRemove(file, fileList) {
|
||||||
|
console.log(file, fileList);
|
||||||
|
},
|
||||||
|
handlePreview(file) {
|
||||||
|
console.log(file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
```
|
||||||
|
:::
|
||||||
|
|
||||||
|
### 照片墙
|
||||||
|
|
||||||
|
使用 listType 属性来设置文件列表的样式。
|
||||||
|
|
||||||
|
::: demo
|
||||||
|
```html
|
||||||
|
<el-upload
|
||||||
|
action="http://localhost:9000/upload"
|
||||||
|
list-type="picture-card"
|
||||||
|
:on-preview="handlePreview">
|
||||||
|
<i class="el-icon-plus"></i>
|
||||||
|
</el-upload>
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
fileList: []
|
||||||
|
};
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
handleRemove(file, fileList) {
|
||||||
|
console.log(file, fileList);
|
||||||
|
},
|
||||||
|
handlePreview(file) {
|
||||||
|
console.log(file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
```
|
||||||
|
:::
|
||||||
|
|
||||||
|
### 图片列表缩略图
|
||||||
|
|
||||||
|
::: demo
|
||||||
```html
|
```html
|
||||||
<el-upload
|
<el-upload
|
||||||
class="upload-demo"
|
class="upload-demo"
|
||||||
draggable
|
action="http://localhost:9000/upload"
|
||||||
action="//jsonplaceholder.typicode.com/posts/"
|
|
||||||
:on-preview="handlePreview"
|
:on-preview="handlePreview"
|
||||||
:on-remove="handleRemove"
|
:on-remove="handleRemove"
|
||||||
:file-list="fileList"
|
:file-list="fileList"
|
||||||
thumbnail-mode>
|
list-type="picture">
|
||||||
|
<el-button size="small" type="primary">点击上传</el-button>
|
||||||
|
<div slot="tip" class="el-upload__tip">只能上传jpg/png文件,且不超过500kb</div>
|
||||||
|
</el-upload>
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
fileList: [{name: 'food.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}, {name: 'food2.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}]
|
||||||
|
};
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
handleRemove(file, fileList) {
|
||||||
|
console.log(file, fileList);
|
||||||
|
},
|
||||||
|
handlePreview(file) {
|
||||||
|
console.log(file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
```
|
||||||
|
:::
|
||||||
|
|
||||||
|
### 拖拽上传
|
||||||
|
|
||||||
|
::: demo
|
||||||
|
```html
|
||||||
|
<el-upload
|
||||||
|
class="upload-demo"
|
||||||
|
drag
|
||||||
|
action="http://localhost:9000/upload"
|
||||||
|
:on-preview="handlePreview"
|
||||||
|
:on-remove="handleRemove"
|
||||||
|
:file-list="fileList"
|
||||||
|
mutiple>
|
||||||
<i class="el-icon-upload"></i>
|
<i class="el-icon-upload"></i>
|
||||||
<div class="el-upload-dragger__text">将文件拖到此处,或<em>点击上传</em></div>
|
<div class="el-upload__text">将文件拖到此处,或<em>点击上传</em></div>
|
||||||
<div class="el-upload__tip" slot="tip">只能上传jpg/png文件,且不超过500kb</div>
|
<div class="el-upload__tip" slot="tip">只能上传jpg/png文件,且不超过500kb</div>
|
||||||
</el-upload>
|
</el-upload>
|
||||||
```
|
```
|
||||||
|
@ -118,7 +263,7 @@
|
||||||
<el-upload
|
<el-upload
|
||||||
class="upload-demo"
|
class="upload-demo"
|
||||||
ref="upload"
|
ref="upload"
|
||||||
action="//jsonplaceholder.typicode.com/posts/"
|
action="http://localhost:9000/upload"
|
||||||
:on-preview="handlePreview"
|
:on-preview="handlePreview"
|
||||||
:on-remove="handleRemove"
|
:on-remove="handleRemove"
|
||||||
:file-list="fileList"
|
:file-list="fileList"
|
||||||
|
@ -147,84 +292,6 @@
|
||||||
```
|
```
|
||||||
:::
|
:::
|
||||||
|
|
||||||
<!-- ### 拖拽上传
|
|
||||||
|
|
||||||
可将文件拖入指定区域进行上传。
|
|
||||||
|
|
||||||
::: demo 将 `type` 属性指定为 'drag' 可以将上传控件变为支持拖拽的形式,并且你可以通过 `multiple` 属性来控制是否支持多选,`on-preview` 和 `on-remove` 是一个钩子函数,分别在点击上传后的文件链接和点击移除上传后的文件后被调用。
|
|
||||||
```html
|
|
||||||
<el-upload
|
|
||||||
action="//jsonplaceholder.typicode.com/posts/"
|
|
||||||
type="drag"
|
|
||||||
:multiple="true"
|
|
||||||
:on-preview="handlePreview"
|
|
||||||
:on-remove="handleRemove"
|
|
||||||
:on-success="handleSuccess"
|
|
||||||
:on-error="handleError"
|
|
||||||
:file-list="fileList"
|
|
||||||
>
|
|
||||||
<i class="el-icon-upload"></i>
|
|
||||||
<div class="el-dragger__text">将文件拖到此处,或<em>点击上传</em></div>
|
|
||||||
<div class="el-upload__tip" slot="tip">只能上传jpg/png文件,且不超过500kb</div>
|
|
||||||
</el-upload>
|
|
||||||
<script>
|
|
||||||
export default {
|
|
||||||
data() {
|
|
||||||
return {
|
|
||||||
fileList: [{name: 'food.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}, {name: 'food2.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}]
|
|
||||||
};
|
|
||||||
},
|
|
||||||
methods: {
|
|
||||||
handleRemove(file, fileList) {
|
|
||||||
console.log(file, fileList);
|
|
||||||
},
|
|
||||||
handlePreview(file) {
|
|
||||||
console.log(file);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</script>
|
|
||||||
```
|
|
||||||
:::
|
|
||||||
|
|
||||||
### 上传单个图片
|
|
||||||
|
|
||||||
专门针对图片类型文件的上传,上传后在原位置显示缩略图。
|
|
||||||
|
|
||||||
::: demo `thumbnail-mode` 属性允许你将上传组件强制只允许图片上传,并支持展示上传文件的缩略图。
|
|
||||||
```html
|
|
||||||
<el-upload
|
|
||||||
action="//jsonplaceholder.typicode.com/posts/"
|
|
||||||
type="drag"
|
|
||||||
:thumbnail-mode="true"
|
|
||||||
:on-preview="handlePreview"
|
|
||||||
:on-remove="handleRemove"
|
|
||||||
:file-list="fileList"
|
|
||||||
>
|
|
||||||
<i class="el-icon-upload"></i>
|
|
||||||
<div class="el-dragger__text">将文件拖到此处,或<em>点击上传</em></div>
|
|
||||||
<div class="el-upload__tip" slot="tip">只能上传jpg/png文件,且不超过500kb</div>
|
|
||||||
</el-upload>
|
|
||||||
<script>
|
|
||||||
export default {
|
|
||||||
data() {
|
|
||||||
return {
|
|
||||||
fileList: [{name: 'food.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}, {name: 'food2.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}]
|
|
||||||
};
|
|
||||||
},
|
|
||||||
methods: {
|
|
||||||
handleRemove(file, fileList) {
|
|
||||||
console.log(file, fileList);
|
|
||||||
},
|
|
||||||
handlePreview(file) {
|
|
||||||
console.log(file);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</script>
|
|
||||||
```
|
|
||||||
::: -->
|
|
||||||
|
|
||||||
### Attribute
|
### Attribute
|
||||||
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|
||||||
|---------- |-------------- |---------- |-------------------------------- |-------- |
|
|---------- |-------------- |---------- |-------------------------------- |-------- |
|
||||||
|
@ -234,7 +301,7 @@
|
||||||
| data | 可选参数, 上传时附带的额外参数 | object | — | — |
|
| data | 可选参数, 上传时附带的额外参数 | object | — | — |
|
||||||
| name | 可选参数, 上传的文件字段名 | string | — | file |
|
| name | 可选参数, 上传的文件字段名 | string | — | file |
|
||||||
| with-credentials | 支持发送 cookie 凭证信息 | boolean | — | false |
|
| with-credentials | 支持发送 cookie 凭证信息 | boolean | — | false |
|
||||||
| show-upload-list | 是否显示已上传文件列表 | boolean | — | true |
|
| show-file-list | 是否显示已上传文件列表 | boolean | — | true |
|
||||||
| type | 上传控件类型 | string | select,drag | select |
|
| type | 上传控件类型 | string | select,drag | select |
|
||||||
| accept | 可选参数, 接受上传的[文件类型](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input#attr-accept)(thumbnail-mode 模式下此参数无效)| string | — | — |
|
| accept | 可选参数, 接受上传的[文件类型](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input#attr-accept)(thumbnail-mode 模式下此参数无效)| string | — | — |
|
||||||
| on-preview | 可选参数, 点击已上传的文件链接时的钩子, 可以通过 file.response 拿到服务端返回数据 | function(file) | — | — |
|
| on-preview | 可选参数, 点击已上传的文件链接时的钩子, 可以通过 file.response 拿到服务端返回数据 | function(file) | — | — |
|
||||||
|
@ -243,8 +310,9 @@
|
||||||
| on-error | 可选参数, 文件上传失败时的钩子 | function(err, response, file) | — | — |
|
| on-error | 可选参数, 文件上传失败时的钩子 | function(err, response, file) | — | — |
|
||||||
| on-progress | 可选参数, 文件上传时的钩子 | function(event, file, fileList) | — | — |
|
| on-progress | 可选参数, 文件上传时的钩子 | function(event, file, fileList) | — | — |
|
||||||
| before-upload | 可选参数, 上传文件之前的钩子,参数为上传的文件,若返回 false 或者 Promise 则停止上传。 | function(file) | — | — |
|
| before-upload | 可选参数, 上传文件之前的钩子,参数为上传的文件,若返回 false 或者 Promise 则停止上传。 | function(file) | — | — |
|
||||||
| thumbnail-mode | 是否设置为图片模式,该模式下会显示图片缩略图 | boolean | — | false |
|
| list-type | 文件列表的类型 | string | text/picture/picture-card | text |
|
||||||
| fileList | 默认已上传的文件列表, 例如: [{name: 'food.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}] | array | — | [] |
|
| auto-upload | 是否在选取文件后立即进行上传 | boolean | — | true |
|
||||||
|
| fileList | 上传的文件列表, 例如: [{name: 'food.jpeg', url: 'https://fuss10.elemecdn.com/3/63/4e7f3a15429bfda99bce42a18cdd1jpeg.jpeg?imageMogr2/thumbnail/360x360/format/webp/quality/100'}] | array | — | [] |
|
||||||
|
|
||||||
### Methods
|
### Methods
|
||||||
| 方法名 | 说明 | 参数 |
|
| 方法名 | 说明 | 参数 |
|
||||||
|
|
|
@ -59,3 +59,11 @@
|
||||||
.collapse-transition {
|
.collapse-transition {
|
||||||
transition: 0.3s height ease-in-out, 0.3s padding-top ease-in-out, 0.3s padding-bottom ease-in-out;
|
transition: 0.3s height ease-in-out, 0.3s padding-top ease-in-out, 0.3s padding-bottom ease-in-out;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.list-enter-active, .list-leave-active {
|
||||||
|
transition: all 1s;
|
||||||
|
}
|
||||||
|
.list-enter, .list-leave-active {
|
||||||
|
opacity: 0;
|
||||||
|
transform: translateY(-30px);
|
||||||
|
}
|
||||||
|
|
|
@ -5,14 +5,16 @@
|
||||||
@component-namespace el {
|
@component-namespace el {
|
||||||
@b upload {
|
@b upload {
|
||||||
display: inline-block;
|
display: inline-block;
|
||||||
|
text-align: center;
|
||||||
|
|
||||||
@e input {
|
@e input {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
@e inner {
|
@e tip {
|
||||||
display: inline-block;
|
font-size: 12px;
|
||||||
position: relative;
|
color: var(--color-base-silver);
|
||||||
|
margin-top: 7px;
|
||||||
|
}
|
||||||
& iframe {
|
& iframe {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
z-index: -1;
|
z-index: -1;
|
||||||
|
@ -21,25 +23,140 @@
|
||||||
opacity: 0;
|
opacity: 0;
|
||||||
filter: alpha(opacity=0);
|
filter: alpha(opacity=0);
|
||||||
}
|
}
|
||||||
|
/* 照片墙模式 */
|
||||||
|
@m picture-card {
|
||||||
|
background-color: #fbfdff;
|
||||||
|
border: 1px dashed #c0ccda;
|
||||||
|
border-radius: 6px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
width: 148px;
|
||||||
|
height: @width;
|
||||||
|
cursor: pointer;
|
||||||
|
line-height: calc(@height - 2);
|
||||||
|
|
||||||
|
i {
|
||||||
|
font-size: 28px;
|
||||||
|
color: #8c939d;
|
||||||
}
|
}
|
||||||
@e files {
|
|
||||||
|
&:hover {
|
||||||
|
border-color: var(--color-primary);
|
||||||
|
color: var(--color-primary);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@b upload-dragger {
|
||||||
|
background-color: #fff;
|
||||||
|
border: 1px dashed #d9d9d9;
|
||||||
|
border-radius: 6px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
width: 360px;
|
||||||
|
height: 180px;
|
||||||
|
text-align: center;
|
||||||
|
cursor: pointer;
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
|
|
||||||
|
& .el-icon-upload {
|
||||||
|
font-size: 67px;
|
||||||
|
color: var(--color-light-silver);
|
||||||
|
margin: 40px 0 16px;
|
||||||
|
line-height: 50px;
|
||||||
|
}
|
||||||
|
|
||||||
|
& + .el-upload__tip {
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
& ~ .el-upload__files {
|
||||||
|
border-top: 1px solid rgba(var(--color-extra-light-silver), .2);
|
||||||
|
margin-top: 7px;
|
||||||
|
padding-top: 5px;
|
||||||
|
}
|
||||||
|
.el-upload__text {
|
||||||
|
color: var(--color-light-silver);
|
||||||
|
font-size: 14px;
|
||||||
|
text-align: center;
|
||||||
|
|
||||||
|
& em {
|
||||||
|
color: var(--color-primary);
|
||||||
|
font-style: normal;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
border-color: var(--color-primary);
|
||||||
|
}
|
||||||
|
|
||||||
|
@when dragOver {
|
||||||
|
background-color: rgba(32, 159, 255, .06);
|
||||||
|
border: 2px dashed var(--color-primary);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@b upload-list {
|
||||||
margin: 0;
|
margin: 0;
|
||||||
padding: 0;
|
padding: 0;
|
||||||
list-style: none;
|
list-style: none;
|
||||||
margin-bottom: 10px;
|
|
||||||
}
|
@e item {
|
||||||
@e file {
|
|
||||||
transition: all .5s cubic-bezier(.55,0,.1,1);
|
transition: all .5s cubic-bezier(.55,0,.1,1);
|
||||||
font-size: 14px;
|
font-size: 14px;
|
||||||
color: var(--color-extra-light-black);
|
color: var(--color-extra-light-black);
|
||||||
line-height: 32px;
|
line-height: 1.8;
|
||||||
|
margin-top: 5px;
|
||||||
position: relative;
|
position: relative;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
position: relative;
|
position: relative;
|
||||||
|
|
||||||
@e name {
|
& .el-progress {
|
||||||
|
position: absolute;
|
||||||
|
bottom: -3px;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
& .el-progress__text {
|
||||||
|
position: absolute;
|
||||||
|
right: 0;
|
||||||
|
top: -10px;
|
||||||
|
right: 0;
|
||||||
|
}
|
||||||
|
.el-progress-bar {
|
||||||
|
margin-right: 0;
|
||||||
|
padding-right: 0;
|
||||||
|
}
|
||||||
|
&:first-child {
|
||||||
|
margin-top: 10px;
|
||||||
|
}
|
||||||
|
&:hover {
|
||||||
|
background-color: var(--color-extra-light-gray);
|
||||||
|
}
|
||||||
|
@when success {
|
||||||
|
.el-upload-list__item-name:hover {
|
||||||
|
color: var(--link-hover-color);
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
.el-icon-close {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
&:hover {
|
||||||
|
.el-icon-close {
|
||||||
|
display: inline-block;
|
||||||
|
cursor: pointer;
|
||||||
|
opacity: .75;
|
||||||
|
transform: scale(.7);
|
||||||
|
color: var(--color-extra-light-black);
|
||||||
|
&:hover {
|
||||||
|
opacity: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.el-icon-circle-check,
|
||||||
|
.el-icon-check {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@e item-name {
|
||||||
color: var(--color-extra-light-black);
|
color: var(--color-extra-light-black);
|
||||||
display: block;
|
display: block;
|
||||||
margin-right: 40px;
|
margin-right: 40px;
|
||||||
|
@ -56,118 +173,156 @@
|
||||||
line-height: inherit;
|
line-height: inherit;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@e icon {
|
@e item-status-label {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
right: 0;
|
right: 10px;
|
||||||
top: 0;
|
top: 0;
|
||||||
line-height: inherit;
|
line-height: inherit;
|
||||||
}
|
|
||||||
& .el-progress {
|
|
||||||
position: absolute;
|
|
||||||
bottom: -3px;
|
|
||||||
width: 100%;
|
|
||||||
}
|
|
||||||
& .el-progress__text {
|
|
||||||
position: absolute;
|
|
||||||
right: 0;
|
|
||||||
top: -10px;
|
|
||||||
right: 0;
|
|
||||||
}
|
|
||||||
.el-progress-bar {
|
|
||||||
margin-right: 0;
|
|
||||||
padding-right: 0;
|
|
||||||
}
|
|
||||||
&:hover {
|
|
||||||
background-color: var(--color-extra-light-gray);
|
|
||||||
}
|
|
||||||
@when success {
|
|
||||||
.el-upload__file__icon {
|
|
||||||
color: var(--color-success);
|
color: var(--color-success);
|
||||||
}
|
}
|
||||||
.el-upload__file__name:hover {
|
@e item-delete {
|
||||||
color: var(--link-hover-color);
|
|
||||||
cursor: pointer;
|
|
||||||
}
|
|
||||||
&:hover {
|
|
||||||
.el-upload__file__icon {
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
.el-upload__btn-delete {
|
|
||||||
display: block;
|
|
||||||
cursor: pointer;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@when fail {
|
|
||||||
.el-upload__file__icon {
|
|
||||||
color: var(--color-error);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@e tip {
|
|
||||||
font-size: 12px;
|
|
||||||
color: var(--color-base-silver);
|
|
||||||
margin-top: 7px;
|
|
||||||
}
|
|
||||||
@e btn-delete {
|
|
||||||
position: absolute;
|
position: absolute;
|
||||||
right: 15px;
|
right: 10px;
|
||||||
top: 0;
|
top: 0;
|
||||||
font-size: 12px;
|
font-size: 12px;
|
||||||
|
color: var(--color-extra-light-black);
|
||||||
|
display: none;
|
||||||
|
|
||||||
|
&: hover {
|
||||||
color: var(--color-primary);
|
color: var(--color-primary);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@m picture-card {
|
||||||
|
float: left;
|
||||||
|
margin: 0;
|
||||||
|
|
||||||
|
.el-upload-list__item {
|
||||||
|
overflow: hidden;
|
||||||
|
background-color: #fff;
|
||||||
|
border: 1px solid #c0ccda;
|
||||||
|
border-radius: 6px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
width: 148px;
|
||||||
|
height: @width;
|
||||||
|
margin: 0 8px 8px 0;
|
||||||
|
display: inline-block;
|
||||||
|
|
||||||
|
&:hover .el-upload-list__item-status-label {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
/* 拖拽模式 */
|
}
|
||||||
@m draggable {
|
.el-upload-list__item-name {
|
||||||
background-color: var(--color-dark-white);
|
display: none;
|
||||||
border: 1px solid var(--color-extra-light-silver);
|
}
|
||||||
box-sizing: border-box;
|
.el-upload-list__item-thumbnail {
|
||||||
width: 360px;
|
width: 100%;
|
||||||
height: 180px;
|
|
||||||
border-radius: 4px;
|
|
||||||
text-align: center;
|
|
||||||
cursor: pointer;
|
|
||||||
position: relative;
|
|
||||||
overflow: hidden;
|
|
||||||
|
|
||||||
& .el-upload__inner {
|
|
||||||
display: block;
|
|
||||||
height: 100%;
|
height: 100%;
|
||||||
}
|
}
|
||||||
& .el-icon-upload {
|
.el-upload-list__item-status-label {
|
||||||
font-size: 67px;
|
position: absolute;
|
||||||
color: var(--color-light-silver);
|
right: -15px;
|
||||||
margin: 40px 0 16px;
|
top: -6px;
|
||||||
line-height: 50px;
|
width: 40px;
|
||||||
}
|
height: 24px;
|
||||||
|
background: #13ce66;
|
||||||
& + .el-upload__tip {
|
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
transform: rotate(45deg);
|
||||||
& ~ .el-upload__files {
|
box-shadow: 0 0 1pc 1px rgba(0,0,0,0.2);
|
||||||
margin-top: 7px;
|
|
||||||
padding-top: 5px;
|
|
||||||
border-top: 1px solid rgba(var(--color-extra-light-silver), .2);
|
|
||||||
}
|
|
||||||
|
|
||||||
@e text {
|
i {
|
||||||
color: var(--color-light-silver);
|
font-size: 12px;
|
||||||
font-size: 14px;
|
margin-top: 11px;
|
||||||
|
transform: rotate(-45deg) scale(0.8);
|
||||||
|
color: #fff;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.el-upload-list__item-actions {
|
||||||
|
position: absolute;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
left: 0;
|
||||||
|
top: 0;
|
||||||
|
cursor: default;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
|
color: #fff;
|
||||||
|
opacity: 0;
|
||||||
|
font-size: 20px;
|
||||||
|
background-color: rgba(0, 0, 0, .5);
|
||||||
|
transition: opacity .3s;
|
||||||
|
@utils-vertical-center;
|
||||||
|
|
||||||
& em {
|
span {
|
||||||
color: var(--color-primary);
|
display: none;
|
||||||
font-style: normal;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
span + span {
|
||||||
|
margin-left: 15px;
|
||||||
}
|
}
|
||||||
|
|
||||||
&:not(.is-showCover):hover {
|
.el-upload-list__item-delete {
|
||||||
border-color: var(--color-primary);
|
position: static;
|
||||||
|
font-size: inherit;
|
||||||
|
color: inherit;
|
||||||
}
|
}
|
||||||
|
|
||||||
@when dragOver {
|
&:hover {
|
||||||
background-color: rgba(32, 159, 255, .06);
|
opacity: 1;
|
||||||
border: 2px dashed var(--color-primary);
|
span {
|
||||||
|
display: inline-block;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@m picture {
|
||||||
|
.el-upload-list__item {
|
||||||
|
overflow: hidden;
|
||||||
|
background-color: #fff;
|
||||||
|
border: 1px solid #c0ccda;
|
||||||
|
border-radius: 6px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
margin-top: 10px;
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
.el-upload-list__item-status-label {
|
||||||
|
background: transparent;
|
||||||
|
box-shadow: none;
|
||||||
|
top: -2px;
|
||||||
|
right: -12px;
|
||||||
|
|
||||||
|
.el-icon-close {
|
||||||
|
transform: rotate(45deg) scale(.7);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.el-upload-list__item-thumbnail {
|
||||||
|
vertical-align: middle;
|
||||||
|
display: inline-block;
|
||||||
|
width: 70px;
|
||||||
|
height: 70px;
|
||||||
|
margin: 10px;
|
||||||
|
}
|
||||||
|
.el-upload-list__item-name {
|
||||||
|
display: inline-block;
|
||||||
|
vertical-align: middle;
|
||||||
|
}
|
||||||
|
.el-upload-list__item-status-label {
|
||||||
|
position: absolute;
|
||||||
|
right: -17px;
|
||||||
|
top: -7px;
|
||||||
|
width: 46px;
|
||||||
|
height: 26px;
|
||||||
|
background: #13ce66;
|
||||||
|
text-align: center;
|
||||||
|
transform: rotate(45deg);
|
||||||
|
box-shadow: 0 1px 1px #ccc;
|
||||||
|
|
||||||
|
i {
|
||||||
|
font-size: 12px;
|
||||||
|
margin-top: 12px;
|
||||||
|
transform: rotate(-45deg) scale(0.8);
|
||||||
|
color: #fff;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,8 +0,0 @@
|
||||||
import UploadDragger from '../upload/src/upload-dragger';
|
|
||||||
|
|
||||||
/* istanbul ignore next */
|
|
||||||
UploadDragger.install = function(Vue) {
|
|
||||||
Vue.component(UploadDragger.name, UploadDragger);
|
|
||||||
};
|
|
||||||
|
|
||||||
export default UploadDragger;
|
|
|
@ -1,10 +0,0 @@
|
||||||
import Upload from './src';
|
|
||||||
import UploadDragger from './src/upload-dragger';
|
|
||||||
|
|
||||||
/* istanbul ignore next */
|
|
||||||
Upload.install = function(Vue) {
|
|
||||||
Vue.component(Upload.name, Upload);
|
|
||||||
Vue.component(UploadDragger.name, UploadDragger);
|
|
||||||
};
|
|
||||||
|
|
||||||
export default { Upload, UploadDragger };
|
|
|
@ -1,61 +0,0 @@
|
||||||
<template>
|
|
||||||
<div class="el-upload-cover" @click.stop v-if="image">
|
|
||||||
<transition name="el-fade-in">
|
|
||||||
<el-progress
|
|
||||||
class="el-upload-cover__progress"
|
|
||||||
v-if="image.status === 'uploading'"
|
|
||||||
:percentage="image.percentage"
|
|
||||||
:show-text="false"
|
|
||||||
>
|
|
||||||
</el-progress>
|
|
||||||
</transition>
|
|
||||||
<div
|
|
||||||
class="el-upload-cover__content"
|
|
||||||
v-if="image.status === 'success'"
|
|
||||||
@mouseenter="mouseover = true"
|
|
||||||
@mouseleave="mouseover = false"
|
|
||||||
>
|
|
||||||
<img :src="image.url">
|
|
||||||
<label class="el-upload-cover__label"><i class="el-icon-check"></i></label>
|
|
||||||
<transition name="el-fade-in">
|
|
||||||
<div v-show="mouseover" class="el-upload-cover__interact">
|
|
||||||
<div class="el-draggeer__cover__btns">
|
|
||||||
<span class="btn" @click="$parent.handleClick()"><i class="el-icon-upload2"></i><span>{{ t('el.upload.continue') }}</span></span>
|
|
||||||
<span class="btn" @click="$emit('preview', image)"><i class="el-icon-view"></i><span>{{ t('el.upload.preview') }}</span></span>
|
|
||||||
<span class="btn" @click="$emit('remove', image)"><i class="el-icon-delete2"></i><span>{{ t('el.upload.delete') }}</span></span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</transition>
|
|
||||||
<transition name="el-zoom-in-bottom">
|
|
||||||
<h4 v-show="mouseover" class="el-upload-cover__title">{{image.name}}</h4>
|
|
||||||
</transition>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
<script>
|
|
||||||
import Locale from 'element-ui/src/mixins/locale';
|
|
||||||
import ElProgress from 'element-ui/packages/progress';
|
|
||||||
|
|
||||||
export default {
|
|
||||||
mixins: [Locale],
|
|
||||||
|
|
||||||
components: { ElProgress },
|
|
||||||
|
|
||||||
props: {
|
|
||||||
image: {},
|
|
||||||
onPreview: {
|
|
||||||
type: Function,
|
|
||||||
default: function() {}
|
|
||||||
},
|
|
||||||
onRemove: {
|
|
||||||
type: Function,
|
|
||||||
default: function() {}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
data() {
|
|
||||||
return {
|
|
||||||
mouseover: false
|
|
||||||
};
|
|
||||||
}
|
|
||||||
};
|
|
||||||
</script>
|
|
|
@ -1,30 +0,0 @@
|
||||||
import Cover from './cover';
|
|
||||||
|
|
||||||
export default {
|
|
||||||
components: {
|
|
||||||
Cover
|
|
||||||
},
|
|
||||||
data() {
|
|
||||||
return {
|
|
||||||
dragOver: false
|
|
||||||
};
|
|
||||||
},
|
|
||||||
computed: {
|
|
||||||
lastestFile() {
|
|
||||||
return this.fileList[this.fileList.length - 1];
|
|
||||||
},
|
|
||||||
showCover() {
|
|
||||||
var file = this.lastestFile;
|
|
||||||
return this.thumbnailMode && file && file.status !== 'fail';
|
|
||||||
},
|
|
||||||
thumbnailMode() {
|
|
||||||
return this.$parent.thumbnailMode;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
methods: {
|
|
||||||
onDrop(e) {
|
|
||||||
this.dragOver = false;
|
|
||||||
this.uploadFiles(e.dataTransfer.files);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
|
@ -1,9 +1,9 @@
|
||||||
<script>
|
<script>
|
||||||
import Cover from './cover';
|
import UploadDragger from './upload-dragger.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
components: {
|
components: {
|
||||||
Cover
|
UploadDragger
|
||||||
},
|
},
|
||||||
props: {
|
props: {
|
||||||
type: String,
|
type: String,
|
||||||
|
@ -30,12 +30,13 @@ export default {
|
||||||
onRemove: {
|
onRemove: {
|
||||||
type: Function,
|
type: Function,
|
||||||
default: function() {}
|
default: function() {}
|
||||||
}
|
},
|
||||||
|
drag: Boolean,
|
||||||
|
listType: String
|
||||||
},
|
},
|
||||||
|
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
dragOver: false,
|
|
||||||
mouseover: false,
|
mouseover: false,
|
||||||
domain: '',
|
domain: '',
|
||||||
file: null,
|
file: null,
|
||||||
|
@ -43,31 +44,22 @@ export default {
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
|
|
||||||
computed: {
|
|
||||||
lastestFile() {
|
|
||||||
var fileList = this.$parent.fileList;
|
|
||||||
return fileList[fileList.length - 1];
|
|
||||||
},
|
|
||||||
showCover() {
|
|
||||||
var file = this.lastestFile;
|
|
||||||
return this.thumbnailMode && file && file.status !== 'fail';
|
|
||||||
},
|
|
||||||
thumbnailMode() {
|
|
||||||
return this.$parent.thumbnailMode;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
methods: {
|
methods: {
|
||||||
isImage(str) {
|
isImage(str) {
|
||||||
return str.indexOf('image') !== -1;
|
return str.indexOf('image') !== -1;
|
||||||
},
|
},
|
||||||
handleClick() {
|
handleClick() {
|
||||||
if (!this.disabled) {
|
|
||||||
this.$refs.input.click();
|
this.$refs.input.click();
|
||||||
}
|
|
||||||
},
|
},
|
||||||
handleChange(ev) {
|
handleChange(ev) {
|
||||||
const file = ev.target.files[0];
|
const file = ev.target.value;
|
||||||
|
if (file) {
|
||||||
|
this.uploadFiles(file);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
uploadFiles(file) {
|
||||||
|
if (this.disabled) return;
|
||||||
|
this.disabled = true;
|
||||||
this.file = file;
|
this.file = file;
|
||||||
this.onStart(file);
|
this.onStart(file);
|
||||||
|
|
||||||
|
@ -86,58 +78,49 @@ export default {
|
||||||
dataSpan.innerHTML = inputs.join('');
|
dataSpan.innerHTML = inputs.join('');
|
||||||
formNode.submit();
|
formNode.submit();
|
||||||
dataSpan.innerHTML = '';
|
dataSpan.innerHTML = '';
|
||||||
this.disabled = true;
|
|
||||||
},
|
},
|
||||||
getFormNode() {
|
getFormNode() {
|
||||||
return this.$refs.form;
|
return this.$refs.form;
|
||||||
},
|
},
|
||||||
getFormDataNode() {
|
getFormDataNode() {
|
||||||
return this.$refs.data;
|
return this.$refs.data;
|
||||||
},
|
|
||||||
onDrop(e) {
|
|
||||||
e.preventDefault();
|
|
||||||
this.dragOver = false;
|
|
||||||
this.uploadFiles(e.dataTransfer.files);
|
|
||||||
},
|
|
||||||
handleDragover(e) {
|
|
||||||
e.preventDefault();
|
|
||||||
this.onDrop = true;
|
|
||||||
},
|
|
||||||
handleDragleave(e) {
|
|
||||||
e.preventDefault();
|
|
||||||
this.onDrop = false;
|
|
||||||
},
|
|
||||||
onload(e) {
|
|
||||||
this.disabled = false;
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
created() {
|
||||||
|
this.frameName = 'frame-' + Date.now();
|
||||||
|
},
|
||||||
|
|
||||||
mounted() {
|
mounted() {
|
||||||
|
const self = this;
|
||||||
!this.$isServer && window.addEventListener('message', (event) => {
|
!this.$isServer && window.addEventListener('message', (event) => {
|
||||||
var targetOrigin = new URL(this.action).origin;
|
if (!self.file) return;
|
||||||
if (event.origin !== targetOrigin) {
|
var targetOrigin = new URL(self.action).origin;
|
||||||
return false;
|
if (event.origin !== targetOrigin) return;
|
||||||
}
|
|
||||||
var response = event.data;
|
var response = event.data;
|
||||||
if (response.result === 'success') {
|
if (response.result === 'success') {
|
||||||
this.onSuccess(response, this.file);
|
self.onSuccess(response, self.file);
|
||||||
} else if (response.result === 'failed') {
|
} else if (response.result === 'failed') {
|
||||||
this.onSuccess(response, this.file);
|
self.onError(response, self.file);
|
||||||
}
|
}
|
||||||
|
self.disabled = false;
|
||||||
|
self.file = null;
|
||||||
}, false);
|
}, false);
|
||||||
},
|
},
|
||||||
|
|
||||||
render(h) {
|
render(h) {
|
||||||
var cover = <cover image={this.lastestFile} onPreview={this.onPreview} onRemove={this.onRemove}></cover>;
|
const {
|
||||||
var frameName = 'frame-' + Date.now();
|
drag,
|
||||||
|
uploadFiles,
|
||||||
|
listType,
|
||||||
|
frameName
|
||||||
|
} = this;
|
||||||
|
const oClass = { 'el-upload': true };
|
||||||
|
oClass[`el-upload--${listType}`] = true;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
class={{
|
class={oClass}
|
||||||
'el-upload__inner': true,
|
|
||||||
'el-dragger': this.type === 'drag',
|
|
||||||
'is-dragOver': this.dragOver,
|
|
||||||
'is-showCover': this.showCover
|
|
||||||
}}
|
|
||||||
on-click={this.handleClick}
|
on-click={this.handleClick}
|
||||||
nativeOn-drop={this.onDrop}
|
nativeOn-drop={this.onDrop}
|
||||||
nativeOn-dragover={this.handleDragover}
|
nativeOn-dragover={this.handleDragover}
|
||||||
|
@ -161,7 +144,11 @@ export default {
|
||||||
<input type="hidden" name="documentDomain" value={ this.$isServer ? '' : document.domain } />
|
<input type="hidden" name="documentDomain" value={ this.$isServer ? '' : document.domain } />
|
||||||
<span ref="data"></span>
|
<span ref="data"></span>
|
||||||
</form>
|
</form>
|
||||||
{!this.showCover ? this.$slots.default : cover}
|
{
|
||||||
|
drag
|
||||||
|
? <upload-dragger on-file={uploadFiles}>{this.$slots.default}</upload-dragger>
|
||||||
|
: this.$slots.default
|
||||||
|
}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
<script>
|
<script>
|
||||||
import UploadList from './upload-list';
|
import UploadList from './upload-list';
|
||||||
import Upload from './upload';
|
import Upload from './upload';
|
||||||
import UploadDragger from './upload-dragger';
|
|
||||||
import IframeUpload from './iframe-upload';
|
import IframeUpload from './iframe-upload';
|
||||||
import ElProgress from 'element-ui/packages/progress';
|
import ElProgress from 'element-ui/packages/progress';
|
||||||
|
|
||||||
|
@ -14,7 +13,6 @@ export default {
|
||||||
ElProgress,
|
ElProgress,
|
||||||
UploadList,
|
UploadList,
|
||||||
Upload,
|
Upload,
|
||||||
UploadDragger,
|
|
||||||
IframeUpload
|
IframeUpload
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -35,11 +33,11 @@ export default {
|
||||||
type: String,
|
type: String,
|
||||||
default: 'file'
|
default: 'file'
|
||||||
},
|
},
|
||||||
draggable: Boolean,
|
drag: Boolean,
|
||||||
dragger: Boolean,
|
dragger: Boolean,
|
||||||
withCredentials: Boolean,
|
withCredentials: Boolean,
|
||||||
thumbnailMode: Boolean,
|
thumbnailMode: Boolean,
|
||||||
showUploadList: {
|
showFileList: {
|
||||||
type: Boolean,
|
type: Boolean,
|
||||||
default: true
|
default: true
|
||||||
},
|
},
|
||||||
|
@ -58,8 +56,7 @@ export default {
|
||||||
default: noop
|
default: noop
|
||||||
},
|
},
|
||||||
onPreview: {
|
onPreview: {
|
||||||
type: Function,
|
type: Function
|
||||||
default: noop
|
|
||||||
},
|
},
|
||||||
onSuccess: {
|
onSuccess: {
|
||||||
type: Function,
|
type: Function,
|
||||||
|
@ -82,6 +79,10 @@ export default {
|
||||||
autoUpload: {
|
autoUpload: {
|
||||||
type: Boolean,
|
type: Boolean,
|
||||||
default: true
|
default: true
|
||||||
|
},
|
||||||
|
listType: {
|
||||||
|
type: String,
|
||||||
|
default: 'text' // text,picture,picture-card
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -168,11 +169,6 @@ export default {
|
||||||
});
|
});
|
||||||
return target;
|
return target;
|
||||||
},
|
},
|
||||||
handlePreview(file) {
|
|
||||||
if (file.status === 'finished') {
|
|
||||||
this.onPreview(file);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
clearFiles() {
|
clearFiles() {
|
||||||
this.uploadFiles = [];
|
this.uploadFiles = [];
|
||||||
},
|
},
|
||||||
|
@ -188,12 +184,13 @@ export default {
|
||||||
render(h) {
|
render(h) {
|
||||||
var uploadList;
|
var uploadList;
|
||||||
|
|
||||||
if (this.showUploadList && this.uploadFiles.length) {
|
if (this.showFileList) {
|
||||||
uploadList = (
|
uploadList = (
|
||||||
<UploadList
|
<UploadList
|
||||||
|
listType={this.listType}
|
||||||
files={this.uploadFiles}
|
files={this.uploadFiles}
|
||||||
on-remove={this.handleRemove}
|
on-remove={this.handleRemove}
|
||||||
on-preview={this.handlePreview}>
|
handlePreview={this.onPreview}>
|
||||||
</UploadList>
|
</UploadList>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -201,7 +198,7 @@ export default {
|
||||||
var uploadData = {
|
var uploadData = {
|
||||||
props: {
|
props: {
|
||||||
type: this.type,
|
type: this.type,
|
||||||
draggable: this.draggable,
|
drag: this.drag,
|
||||||
action: this.action,
|
action: this.action,
|
||||||
multiple: this.multiple,
|
multiple: this.multiple,
|
||||||
'before-upload': this.beforeUpload,
|
'before-upload': this.beforeUpload,
|
||||||
|
@ -212,36 +209,31 @@ export default {
|
||||||
accept: this.thumbnailMode ? 'image/gif, image/png, image/jpeg, image/bmp, image/webp' : this.accept,
|
accept: this.thumbnailMode ? 'image/gif, image/png, image/jpeg, image/bmp, image/webp' : this.accept,
|
||||||
fileList: this.uploadFiles,
|
fileList: this.uploadFiles,
|
||||||
autoUpload: this.autoUpload,
|
autoUpload: this.autoUpload,
|
||||||
|
listType: this.listType,
|
||||||
'on-start': this.handleStart,
|
'on-start': this.handleStart,
|
||||||
'on-progress': this.handleProgress,
|
'on-progress': this.handleProgress,
|
||||||
'on-success': this.handleSuccess,
|
'on-success': this.handleSuccess,
|
||||||
'on-error': this.handleError,
|
'on-error': this.handleError,
|
||||||
'on-preview': this.handlePreview,
|
'on-preview': this.onPreview,
|
||||||
'on-remove': this.handleRemove
|
'on-remove': this.handleRemove
|
||||||
},
|
},
|
||||||
ref: 'upload-inner'
|
ref: 'upload-inner'
|
||||||
};
|
};
|
||||||
|
|
||||||
// var uploadComponent = (typeof FormData !== 'undefined' || this.$isServer)
|
const trigger = this.$slots.trigger || this.$slots.default;
|
||||||
// ? <upload {...props}>{this.$slots.default}</upload>
|
const uploadComponent = (typeof FormData !== 'undefined' || this.$isServer)
|
||||||
// : <iframeUpload {...props}>{this.$slots.default}</iframeUpload>;
|
? <upload {...uploadData}>{trigger}</upload>
|
||||||
|
: <iframeUpload {...uploadData}>{trigger}</iframeUpload>;
|
||||||
|
|
||||||
if (this.draggable) {
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<upload {...uploadData}>{this.$slots.trigger || this.$slots.default}</upload>
|
{
|
||||||
{this.$slots.tip}
|
this.$slots.trigger
|
||||||
{uploadList}
|
? [uploadComponent, this.$slots.default]
|
||||||
</div>
|
: uploadComponent
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return (
|
|
||||||
<div>
|
|
||||||
{uploadList}
|
|
||||||
<upload {...uploadData}>{this.$slots.trigger || this.$slots.default}</upload>
|
|
||||||
{this.$slots.default}
|
|
||||||
{this.$slots.tip}
|
{this.$slots.tip}
|
||||||
|
{uploadList}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,86 +2,29 @@
|
||||||
<div
|
<div
|
||||||
class="el-upload-dragger"
|
class="el-upload-dragger"
|
||||||
:class="{
|
:class="{
|
||||||
'is-dragOver': dragOver,
|
'is-dragOver': dragOver
|
||||||
'is-showCover': showCover
|
|
||||||
}"
|
}"
|
||||||
@click="handleClick"
|
|
||||||
@drop.prevent="onDrop"
|
@drop.prevent="onDrop"
|
||||||
@dragover.prevent="dragOver = true"
|
@dragover.prevent="dragOver = true"
|
||||||
@dragleave.prevent="dragOver = false"
|
@dragleave.prevent="dragOver = false"
|
||||||
>
|
>
|
||||||
<slot v-if="!showCover"></slot>
|
<slot></slot>
|
||||||
<cover :image="lastestFile" :on-preview="onPreview" :on-remove="onRemove" v-else></cover>
|
|
||||||
<input class="el-upload__input" type="file" ref="input" @change="handleChange" :multiple="multiple" :accept="accept">
|
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
<script>
|
<script>
|
||||||
import Upload from './upload';
|
|
||||||
import IframeUpload from './iframe-upload';
|
|
||||||
import Cover from './cover';
|
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
name: 'ElUploadDragger',
|
name: 'ElUploadDrag',
|
||||||
|
|
||||||
extends: Upload,
|
|
||||||
|
|
||||||
components: {
|
|
||||||
IframeUpload,
|
|
||||||
Cover
|
|
||||||
},
|
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
dragOver: false
|
dragOver: false
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
props: {
|
|
||||||
draggable: {
|
|
||||||
type: Boolean,
|
|
||||||
default: true
|
|
||||||
}
|
|
||||||
},
|
|
||||||
computed: {
|
|
||||||
lastestFile() {
|
|
||||||
var fileList = this.$parent.fileList;
|
|
||||||
return fileList[fileList.length - 1];
|
|
||||||
},
|
|
||||||
showCover() {
|
|
||||||
var file = this.lastestFile;
|
|
||||||
return this.thumbnailMode && file && file.status !== 'fail';
|
|
||||||
},
|
|
||||||
thumbnailMode() {
|
|
||||||
return this.$parent.thumbnailMode;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
methods: {
|
methods: {
|
||||||
onDrop(e) {
|
onDrop(e) {
|
||||||
this.dragOver = false;
|
this.dragOver = false;
|
||||||
this.uploadFiles(e.dataTransfer.files);
|
this.$emit('file', e.dataTransfer.files);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// render(h) {
|
|
||||||
// let {
|
|
||||||
// dragover
|
|
||||||
// } = this;
|
|
||||||
|
|
||||||
// let content = this.showCover
|
|
||||||
// ? <cover image={this.lastestFile} on-preview={this.onPreview} on-remove={this.onRemove}></cover>
|
|
||||||
// : this.$slots.default
|
|
||||||
// return (
|
|
||||||
// <div
|
|
||||||
// class={{
|
|
||||||
// 'el-upload-dragger': true,
|
|
||||||
// 'is-dragOver': this.dragOver,
|
|
||||||
// 'is-showCover': this.showCover
|
|
||||||
// }}
|
|
||||||
// @drop.prevent="onDrop"
|
|
||||||
// @dragover.prevent="dragOver = true"
|
|
||||||
// @dragleave.prevent="dragOver = false"
|
|
||||||
// >
|
|
||||||
// {content}
|
|
||||||
// <input class="el-upload__input" type="file" ref="input" on-change={this.handleChange} multiple={this.multiple} accept={this.accept} />
|
|
||||||
// </div>
|
|
||||||
// );
|
|
||||||
// }
|
|
||||||
};
|
};
|
||||||
</script>
|
</script>
|
|
@ -1,20 +1,48 @@
|
||||||
<template>
|
<template>
|
||||||
<transition-group tag="ul" class="el-upload__files" name="list">
|
<transition-group
|
||||||
|
tag="ul"
|
||||||
|
:class="['el-upload-list', 'el-upload-list--' + listType]"
|
||||||
|
name="list"
|
||||||
|
>
|
||||||
<li
|
<li
|
||||||
v-for="file in files"
|
v-for="file in files"
|
||||||
:class="['el-upload__file', 'is-' + file.status]"
|
:class="['el-upload-list__item', 'is-' + file.status]"
|
||||||
:key="file"
|
:key="file"
|
||||||
@click="$emit('clickFile', file)"
|
|
||||||
>
|
>
|
||||||
<a class="el-upload__file__name" @click="$emit('preview', file)">
|
<img class="el-upload-list__item-thumbnail" v-if="['picture-card', 'picture'].indexOf(listType) > -1" :src="file.url" alt="">
|
||||||
|
<a class="el-upload-list__item-name" @click="handleClick(file)">
|
||||||
<i class="el-icon-document"></i>{{file.name}}
|
<i class="el-icon-document"></i>{{file.name}}
|
||||||
</a>
|
</a>
|
||||||
|
<label v-show="file.status === 'success'" class="el-upload-list__item-status-label">
|
||||||
<i :class="{
|
<i :class="{
|
||||||
'el-upload__file__icon': true,
|
'el-icon-circle-check': listType === 'text',
|
||||||
'el-icon-circle-check': file.status === 'success',
|
'el-icon-check': ['picture-card', 'picture'].indexOf(listType) > -1
|
||||||
'el-icon-circle-cross': file.status === 'fail'
|
|
||||||
}"></i>
|
}"></i>
|
||||||
<span class="el-upload__btn-delete" @click="$emit('remove', file)" v-show="file.status === 'success'">{{ t('el.upload.delete') }}</span>
|
<i class="el-icon-close" @click="$emit('remove', file)"></i>
|
||||||
|
</label>
|
||||||
|
<span class="el-upload-list__item-actions"
|
||||||
|
v-if="
|
||||||
|
listType === 'picture-card' &&
|
||||||
|
file.status === 'success'
|
||||||
|
"
|
||||||
|
>
|
||||||
|
<span
|
||||||
|
v-if="
|
||||||
|
handlePreview &&
|
||||||
|
listType === 'picture-card'
|
||||||
|
"
|
||||||
|
@click="handlePreview(file)"
|
||||||
|
class="el-upload-list__item-preview"
|
||||||
|
>
|
||||||
|
<i class="el-icon-view"></i>
|
||||||
|
</span>
|
||||||
|
<span
|
||||||
|
class="el-upload-list__item-delete"
|
||||||
|
@click="$emit('remove', file)"
|
||||||
|
>
|
||||||
|
<i class="el-icon-delete2"></i>
|
||||||
|
</span>
|
||||||
|
</span>
|
||||||
<el-progress
|
<el-progress
|
||||||
v-if="file.status === 'uploading'"
|
v-if="file.status === 'uploading'"
|
||||||
:stroke-width="2"
|
:stroke-width="2"
|
||||||
|
@ -38,11 +66,16 @@
|
||||||
default() {
|
default() {
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
handlePreview: Function,
|
||||||
|
listType: String
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
parsePercentage(val) {
|
parsePercentage(val) {
|
||||||
return parseInt(val, 10);
|
return parseInt(val, 10);
|
||||||
|
},
|
||||||
|
handleClick(file) {
|
||||||
|
this.handlePreview && this.handlePreview(file);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
<script>
|
<script>
|
||||||
import merge from 'element-ui/src/utils/merge';
|
|
||||||
import ajax from './ajax';
|
import ajax from './ajax';
|
||||||
import dragger from './dragger';
|
import UploadDragger from './upload-dragger.vue';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
mixins: [dragger],
|
components: {
|
||||||
|
UploadDragger
|
||||||
|
},
|
||||||
props: {
|
props: {
|
||||||
type: String,
|
type: String,
|
||||||
action: {
|
action: {
|
||||||
|
@ -26,7 +26,7 @@ export default {
|
||||||
onSuccess: Function,
|
onSuccess: Function,
|
||||||
onError: Function,
|
onError: Function,
|
||||||
beforeUpload: Function,
|
beforeUpload: Function,
|
||||||
draggable: Boolean,
|
drag: Boolean,
|
||||||
onPreview: {
|
onPreview: {
|
||||||
type: Function,
|
type: Function,
|
||||||
default: function() {}
|
default: function() {}
|
||||||
|
@ -36,7 +36,8 @@ export default {
|
||||||
default: function() {}
|
default: function() {}
|
||||||
},
|
},
|
||||||
fileList: Array,
|
fileList: Array,
|
||||||
autoUpload: Boolean
|
autoUpload: Boolean,
|
||||||
|
listType: String
|
||||||
},
|
},
|
||||||
|
|
||||||
data() {
|
data() {
|
||||||
|
@ -118,15 +119,12 @@ export default {
|
||||||
render(h) {
|
render(h) {
|
||||||
let {
|
let {
|
||||||
handleClick,
|
handleClick,
|
||||||
draggable,
|
drag,
|
||||||
onDrop,
|
|
||||||
showCover,
|
|
||||||
onPreview,
|
|
||||||
onRemove,
|
|
||||||
handleChange,
|
handleChange,
|
||||||
multiple,
|
multiple,
|
||||||
accept,
|
accept,
|
||||||
lastestFile
|
listType,
|
||||||
|
uploadFiles
|
||||||
} = this;
|
} = this;
|
||||||
const data = {
|
const data = {
|
||||||
class: {
|
class: {
|
||||||
|
@ -136,32 +134,12 @@ export default {
|
||||||
click: handleClick
|
click: handleClick
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
if (draggable) {
|
data.class[`el-upload--${listType}`] = true;
|
||||||
merge(data.on, {
|
|
||||||
dragover: (ev) => {
|
|
||||||
ev.preventDefault();
|
|
||||||
this.dragOver = true;
|
|
||||||
},
|
|
||||||
dragleave: (ev) => {
|
|
||||||
ev.preventDefault();
|
|
||||||
this.dragOver = false;
|
|
||||||
},
|
|
||||||
drop: (ev) => {
|
|
||||||
ev.preventDefault();
|
|
||||||
onDrop(ev);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
merge(data.class, {
|
|
||||||
'el-upload--draggable': true,
|
|
||||||
'is-dragOver': this.dragOver,
|
|
||||||
'is-showCover': this.showCover
|
|
||||||
});
|
|
||||||
}
|
|
||||||
return (
|
return (
|
||||||
<div {...data}>
|
<div {...data}>
|
||||||
{
|
{
|
||||||
showCover
|
drag
|
||||||
? <cover image={lastestFile} on-preview={onPreview} on-remove={onRemove}></cover>
|
? <upload-dragger on-file={uploadFiles}>{this.$slots.default}</upload-dragger>
|
||||||
: this.$slots.default
|
: this.$slots.default
|
||||||
}
|
}
|
||||||
<input class="el-upload__input" type="file" ref="input" on-change={handleChange} multiple={multiple} accept={accept}></input>
|
<input class="el-upload__input" type="file" ref="input" on-change={handleChange} multiple={multiple} accept={accept}></input>
|
||||||
|
|
|
@ -47,7 +47,6 @@ import Icon from '../packages/icon';
|
||||||
import Row from '../packages/row';
|
import Row from '../packages/row';
|
||||||
import Col from '../packages/col';
|
import Col from '../packages/col';
|
||||||
import Upload from '../packages/upload';
|
import Upload from '../packages/upload';
|
||||||
import UploadDragger from '../packages/upload-dragger';
|
|
||||||
import Progress from '../packages/progress';
|
import Progress from '../packages/progress';
|
||||||
import Spinner from '../packages/spinner';
|
import Spinner from '../packages/spinner';
|
||||||
import Message from '../packages/message';
|
import Message from '../packages/message';
|
||||||
|
@ -109,7 +108,6 @@ const components = [
|
||||||
Row,
|
Row,
|
||||||
Col,
|
Col,
|
||||||
Upload,
|
Upload,
|
||||||
UploadDragger,
|
|
||||||
Progress,
|
Progress,
|
||||||
Spinner,
|
Spinner,
|
||||||
Badge,
|
Badge,
|
||||||
|
@ -203,7 +201,6 @@ module.exports = {
|
||||||
Row,
|
Row,
|
||||||
Col,
|
Col,
|
||||||
Upload,
|
Upload,
|
||||||
UploadDragger,
|
|
||||||
Progress,
|
Progress,
|
||||||
Spinner,
|
Spinner,
|
||||||
Message,
|
Message,
|
||||||
|
|
Loading…
Reference in New Issue