Element开发笔记
前言
官网 https://element.eleme.cn/#/zh-CN/component/upload
其它项目网站
https://www.cnblogs.com/qq2806933146xiaobai/p/17180878.html
表格
序号列添加
vue
<el-table-column type="index" :index="handleIndexCalc" label="#" align="center" />
handleIndexCalc是计算分页中的ID,否则序号不准确。
javascript
// 自动计算分页 Id
handleIndexCalc(index) {
return (
(this.queryParams.pageIndex - 1) * this.queryParams.pageSize + index + 1
)
},
选择列添加
vue
<el-table-column sortable type="selection" align="center" />
注意:同时拥有 序号列、选择列,序号必须在 选择列前面
表格高度统一,防止数据量少时,页脚上升
表格设置height
属性,根据浏览器界面大小自动计算高度,留页脚面板高度。
html
<el-table ref="dataResult"
v-loading="loading"
:data="dataResult.dataSource"
:height="tableHeight"
:default-sort="{ prop: queryParams.orderby, order: queryParams.sort }"
row-key="id"
stripe
border
style="width: 100%;height=250"
@sort-change="handleSortable">
Data:
javascript
// 表格高度
tableHeight: window.innerHeight - 280,
项目实例:
vue
<!-- 表格数据展示 -->
<el-row>
<el-table ref="dataResult"
v-loading="loading"
:data="dataResult.dataSource"
:height="tableHeight"
:default-sort="{ prop: queryParams.orderby, order: queryParams.sort }"
row-key="id"
stripe
border
style="width: 100%;height=250"
@sort-change="handleSortable">
<el-table-column type="index" :index="handleIndexCalc" label="#" align="center" />
<el-table-column sortable type="selection" align="center" />
<el-table-column sortable prop="title" :show-overflow-tooltip="true" align="center" label="标题" width="200px" />
<el-table-column sortable prop="fileName" :show-overflow-tooltip="true" align="left" label="文档名称" width="200px" />
<el-table-column sortable prop="fileType" :show-overflow-tooltip="true" align="left" label="文档格式" width="100px" />
<el-table-column sortable prop="securityLevel" align="left" label="密级" width="80px" />
<el-table-column prop="keyWords" :show-overflow-tooltip="true" align="left" label="关键字" width="200px" />
<el-table-column sortable prop="fileSource" :show-overflow-tooltip="true" align="left" label="资料来源" width="100px" />
<el-table-column sortable prop="createName" align="left" label="创建人" width="100px" />
<el-table-column sortable prop="createTime" :show-overflow-tooltip="true" align="left" label="创建时间" width="200px" />
<el-table-column sortable prop="downloadCount" :show-overflow-tooltip="true" align="left" label="下载次数" width="100px" />
<el-table-column sortable prop="status_dictText" :show-overflow-tooltip="true" align="left" label="审核状态" width="100px" />
<el-table-column prop="failReason" align="left" :show-overflow-tooltip="true" label="不通过原因" width="250px" />
<el-table-column prop="remarks" align="left" :show-overflow-tooltip="true" label="备注" width="300px" />
<el-table-column label="操作" align="center" fixed="right" width="300px">
<template slot-scope="scope">
<el-button v-permission="['PRIV_DOC_PREVIEW']" type="text" size="mini" @click="handlePreview(scope.row)">预览</el-button>
<el-button v-permission="['PRIV_DOC_EDIT']" type="text" size="mini" @click="handleEdit(scope.row)">修改</el-button>
<el-button v-permission="['PRIV_DOC_DOWNLOAD']" type="text" size="mini" @click="handleDownLoad(scope.row)">下载</el-button>
<el-button v-if="scope.row.status !='3'" v-permission="['PRIV_DOC_APPROVED']" type="text" size="small" @click="handleApproved(scope.row)">审批</el-button>
<el-button v-if="scope.row.status !='4'" v-permission="['PRIV_DOC_APPROVEDFAILED']" type="text" size="small" @click="handleApprovedFail(scope.row)">驳回</el-button>
</template>
</el-table-column>
</el-table>
<pagination v-show="total > 0" :total="total" :page.sync="queryParams.pageIndex" :limit.sync="queryParams.pageSize" @pagination="getList" />
</el-row>
Select选择器
vue
<template>
<el-select v-model="value" clearable placeholder="请选择">
<el-option
v-for="item in options"
:key="item.value"
:label="item.label"
:value="item.value">
</el-option>
</el-select>
</template>
<script>
export default {
data() {
return {
options: [{
value: '选项1',
label: '黄金糕'
}, {
value: '选项2',
label: '双皮奶'
}, {
value: '选项3',
label: '蚵仔煎'
}, {
value: '选项4',
label: '龙须面'
}, {
value: '选项5',
label: '北京烤鸭'
}],
value: ''
}
}
}
</script>
参数 | 说明 | 类型 | 可选值 | 默认值 |
---|---|---|---|---|
value / v-model | 绑定值 | boolean / string / number | --- | --- |
multiple | 是否多选 | boolean | --- | false |
disabled | 是否禁用 | boolean | --- | false |
value-key | 作为 value 唯一标识的键名,绑定值为对象类型时必填 | string | --- | value |
size | 输入框尺寸 | string | medium/small/mini | --- |
clearable | 是否可以清空选项 | boolean | --- | false |
collapse-tags | 多选时是否将选中值按文字的形式展示 | boolean | --- | false |
multiple-limit | 多选时用户最多可以选择的项目数,为 0 则不限制 | number | --- | 0 |
name | select input 的 name 属性 | string | --- | --- |
autocomplete | select input 的 autocomplete 属性 | string | --- | off |
auto-complete | 下个主版本弃用 | string | --- | off |
placeholder | 占位符 | string | --- | 请选择 |
filterable | 是否可搜索 | boolean | --- | false |
allow-create | 是否允许用户创建新条目,需配合 filterable 使用 |
boolean | --- | false |
filter-method | 自定义搜索方法 | function | --- | --- |
remote | 是否为远程搜索 | boolean | --- | false |
remote-method | 远程搜索方法 | function | --- | --- |
loading | 是否正在从远程获取数据 | boolean | --- | false |
loading-text | 远程加载时显示的文字 | string | --- | 加载中 |
no-match-text | 搜索条件无匹配时显示的文字,也可以使用slot="empty" 设置 |
string | --- | 无匹配数据 |
no-data-text | 选项为空时显示的文字,也可以使用slot="empty" 设置 |
string | --- | 无数据 |
popper-class | Select 下拉框的类名 | string | --- | --- |
reserve-keyword | 多选且可搜索时,是否在选中一个选项后保留当前的搜索关键词 | boolean | --- | false |
default-first-option | 在输入框按下回车,选择第一个匹配项。需配合 filterable 或 remote 使用 |
boolean | - | false |
popper-append-to-body | 是否将弹出框插入至 body 元素。在弹出框的定位出现问题时,可将该属性设置为 false | boolean | - | true |
automatic-dropdown | 对于不可搜索的 Select,是否在输入框获得焦点后自动弹出选项菜单 | boolean | - | false |
项目实例
vue
<el-select v-model="queryParams.queryStatus" placeholder="请选择文档状态" filterable clearable @change="handleSelectSearchStatus">
<el-option v-for="item in statusOptions" :key="item.value" :label="item.label" :value="item.value" />
</el-select>
javascript
// 搜索框-文档状态
statusOptions: [],
// 创建时
created() {
getOption('SYSTEM_STATUS').then((response) => {
this.statusOptions = response.data
}),
this.getList()
},
// 选择文档状态(搜索框)
handleSelectSearchStatus(e) {
this.queryParams.queryStatus = e
},
el-select
使用 multiple
多选属性时,数据定义必须符合规范,并且返回的是 字符串数组
,一开始需要定义好,否则数据无法显示。
vue
<el-select
v-model="keyWordsList"
multiple
filterable
allow-create
default-first-option
placeholder="请填写关键字(可多选,可手填按回车键)">
<el-option
v-for="item in keyWordsOptions"
:key="item.wordName"
:label="item.wordName"
:value="item.wordName" />
</el-select>
javascript
// 控件绑定的
keyWordsList: [],
/** 编辑按钮操作 */
handleEdit(row) {
this.reset()
this.postForm = { ...row }
this.keyWordsList = row.keyWords.split(',') //数据库取出来是字符串,转数组
this.bOpenForm = true
this.title = '编辑文档'
},
dialog弹出框
需要注意浅拷贝
和 深拷贝
问题,row是Object对象类型,如果直接赋值,就变成了 浅拷贝
,相当于我们的引用传递。
javascript
//方法一
this.form = JSON.parse(JSON.stringify(row));
//方法二
this.form = {...row}
javascript
/** 新增按钮操作 */
handleCreate() {
this.reset()
this.open = true
this.title = '添加关键字'
},
/** 修改按钮操作 */
handleUpdate(row) {
this.reset()
this.form = { ...row }
this.open = true
this.title = '修改关键字'
},
每次窗体打开,并不会清除上一次验证规则
,需要手动调用clearValidate()
方法清除,与C#一样。
javascript
watch: {
// 打开弹窗,清空上一次验证规则
bOpenForm: {
handler(newVal) {
if (newVal) {
this.$nextTick(() => {
this.$refs['postForm'].clearValidate()
})
}
},
},
},
el-upload上传组件
:action是执行上传动作的后台接口,el-button是触发上传的按钮。
multiple 设置是否可以同时选中多个文件上传
accept 设置限制上传文件的格式
html
<el-upload
:action="uploadActionUrl"
accept="image/jpeg,image/gif,image/png"
:before-upload="onBeforeUpload"
multiple
:limit="3"
:on-exceed="handleExceed">
<el-button size="small" type="primary">点击上传</el-button>
<div slot="tip" class="el-upload__tip">请上传图片格式文件</div>
</el-upload>
...
onBeforeUpload(file)
{
const isIMAGE = file.type === 'image/jpeg'||'image/gif'||'image/png';
const isLt1M = file.size / 1024 / 1024 < 1;
if (!isIMAGE) {
this.$message.error('上传文件只能是图片格式!');
}
if (!isLt1M) {
this.$message.error('上传文件大小不能超过 1MB!');
}
return isIMAGE && isLt1M;
}
属性
参数 | 说明dd | 类型 | 可选值 | 默认值 |
---|---|---|---|---|
action | 必选参数,上传的地址 | string | --- | --- |
headers | 设置上传的请求头部 | object | --- | --- |
multiple | 是否支持多选文件 | boolean | --- | --- |
data | 上传时附带的额外参数 | object | --- | --- |
name | 上传的文件字段名 | string | --- | file |
with-credentials | 支持发送 cookie 凭证信息 | boolean | --- | false |
show-file-list | 是否显示已上传文件列表 | boolean | --- | true |
drag | 是否启用拖拽上传 | boolean | --- | false |
accept | 接受上传的文件类型(thumbnail-mode 模式下此参数无效) | string | --- | --- |
on-preview | 点击文件列表中已上传的文件时的钩子 | function(file) | --- | --- |
on-remove | 文件列表移除文件时的钩子 | function(file, fileList) | --- | --- |
on-success | 文件上传成功时的钩子 | function(response, file, fileList) | --- | --- |
on-error | 文件上传失败时的钩子 | function(err, file, fileList) | --- | --- |
on-progress | 文件上传时的钩子 | function(event, file, fileList) | --- | --- |
on-change | 文件状态改变时的钩子,添加文件、上传成功和上传失败时都会被调用 | function(file, fileList) | --- | --- |
before-upload | 上传文件之前的钩子,参数为上传的文件,若返回 false 或者返回 Promise 且被 reject,则停止上传。 | function(file) | --- | --- |
before-remove | 删除文件之前的钩子,参数为上传的文件和文件列表,若返回 false 或者返回 Promise 且被 reject,则停止删除。 | function(file, fileList) | --- | --- |
list-type | 文件列表的类型 | string | text/picture/picture-card | text |
auto-upload | 是否在选取文件后立即进行上传 | boolean | --- | true |
file-list | 上传的文件列表, 例如: [{name: 'food.jpg', url: 'https://xxx.cdn.com/xxx.jpg'}] | array | --- | [] |
http-request | 覆盖默认的上传行为,可以自定义上传的实现 | function | --- | --- |
disabled | 是否禁用 | boolean | --- | false |
limit | 最大允许上传个数 | number | --- | --- |
on-exceed | 文件超出个数限制时的钩子 | function(files, fileList) | --- | - |
项目实例
这里使用了,父组件向子组件传参,子组件向父组件传参
。
vue
<el-form-item label="上传附件" prop="fileName">
<file-upload v-model="postForm.fileName" :uploadlimit="filelimit" :accept="fileAccept" :listType="filelistType" @fileList="getFileList" :actionUrl="fileActionUrl" :tips="filetips" />
</el-form-item>
父组件传参数
javascript
// 上传附件
fileActionUrl: CONFIG_URL.PUBLIC_CONFIG.baseURL + '/api/doc/UpLoadFile',
fileAccept: '.doc, .docx, .xls, .xlsx, .ppt, .pptx, .pdf',
filelimit: 1,
filelistType: 'file',
filetips: '只能上传办公文档,其它类型建议不要上传',
子组件接收参数,在props
中定义
vue
// 接收父组件传递的值
props: {
// 动作action
actionUrl: {
type: String,
required: true,
default: '/api/doc/UpLoadFile'
},
// 接受上传的文件类型
accept: {
type: String,
required: true
},
// 最大允许上传个数
uploadlimit: {
type: Number,
required: true,
default: 1
},
/** 文件列表的类型
* drag是否启用拖拽上传
* list-type 可选值 text/picture/picture-card
**/
listType: {
type: String,
required: true,
default: 'text'
},
// 上传提示语
tips: {
type: String,
required: false
}
},
子组件向父组件回传数据
vue
// $emit() 向外触发父组件中方法,fileList由父组件传递过来
this.$emit("fileList", this.ret_fileList)
父组件接收子组件回传的数据,需要在watch
监听器中实现,能够感知数据变化。
javascript
watch: {
// 监听文件列表变化
fileList: {
handler() {
this.$emit('fileList', this.ret_fileList)
}
}
},
子组件代码
vue
<!-- 文件上传通用组件(支持拖拽上传,打开本地资源管理器) -->
<template>
<div class="content">
<el-upload
:action="actionUrl"
:accept="accept"
:on-preview="handlePreview"
:before-remove="beforeRemove"
:on-remove="handleRemove"
:on-exceed="handleExceed"
:on-success="handleSuccess"
:drag="listType!=='picture'"
:limit="uploadlimit"
:headers="header"
:file-list="fileList"
:list-type="listType">
<el-button v-if="listType==='picture'" size="small" type="primary">点击上传</el-button>
<i v-if="listType!=='picture'" class="el-icon-upload" />
<div v-if="listType!=='picture'" class="el-upload__text">
将文件拖到此处,或
<em>点击上传</em>
</div>
<!-- 附件提示信息 -->
<div v-if="tips" slot="tip" class="el-upload__tip">{{ tips }}</div>
</el-upload>
</div>
</template>
<script>
import { getToken } from '@/utils/auth'
export default {
name: 'FileUpload',
// 接收父组件传递的值
props: {
// 动作action
actionUrl: {
type: String,
required: true,
default: '/api/doc/UpLoadFile'
},
// 接受上传的文件类型
accept: {
type: String,
required: true
},
// 最大允许上传个数
uploadlimit: {
type: Number,
required: true,
default: 1
},
/** 文件列表的类型
* drag是否启用拖拽上传
* list-type 可选值 text/picture/picture-card
**/
listType: {
type: String,
required: true,
default: 'text'
},
// 上传提示语
tips: {
type: String,
required: false
}
},
data() {
return {
// 界面绑定的文件列表,参数不可更改,否则底层无法识别
// 上传的文件列表,例如: [{name: 'food.jpg', url: 'https://xxx.cdn.com/xxx.jpg'}]
fileList: [],
// 服务器返回的文件列表
ret_fileList: [],
header: {}
}
},
/**
* watch侦听器
* 侦听父组件传递的值,实现动态传递数据
*/
// watch: {
// },
created() {
this.header = { token: getToken() }
},
methods: {
// 文件列表重置
reset() {
this.ret_fileList = [
{
fileName: undefined,
fileType: undefined,
fileUrl: undefined,
viewUrl: undefined,
cover: ''
}
]
},
// 文件超出个数限制时的钩子
handleExceed() {
this.$message.warning(`每次只能上传 ${this.uploadlimit} 个文件`)
},
// 点击的文件列表元素
handlePreview(file) {
console.log("你点击了 " + file.name)
this.$message.warning("你点击了 " + file.name)
},
// 删除文件之前的钩子
beforeRemove(file) {
return this.$confirm(`确定移除 ${ file.name }文件?`)
},
// 文件列表移除文件时的钩子
handleRemove(file, fileList) {
console.log(file, fileList);
this.fileList = this.fileList.filter((item) => {
return item.name !== file.name
})
},
// 文件上传成功时的钩子
handleSuccess(response) {
if (response.statusCode === 200) {
this.$message({
message: '上传成功',
type: 'success'
})
this.ret_fileList = response.data
}else{
this.$message({
type: 'error',
message: response.msg
})
this.reset()
}
// $emit() 向外触发父组件中方法,fileList由父组件传递过来
this.$emit("fileList", this.ret_fileList)
}
}
}
</script>