parent
f1e4633c66
commit
a765e98b06
@ -0,0 +1,249 @@ |
||||
<template> |
||||
<a-modal |
||||
class="noborder" |
||||
:title="title" |
||||
:width="1020" |
||||
:visible="visible" |
||||
:isLoading="isLoading" |
||||
:maskClosable="false" |
||||
@ok="handleSubmit" |
||||
@cancel="handleCancel" |
||||
> |
||||
<s-table |
||||
ref="table" |
||||
:scroll="{ y: '420px', scrollToFirstRowOnChange: true }" |
||||
:rowKey="fieldName" |
||||
:loading="isLoading" |
||||
:columns="columns" |
||||
:data="loadData" |
||||
:rowSelection="rowSelection" |
||||
:pageSize="15" |
||||
> |
||||
<!-- 活动入口图片 --> |
||||
<span slot="index_image_url" slot-scope="text"> |
||||
<a title="点击查看原图" :href="text" target="_blank"> |
||||
<img height="50" :src="text" alt="活动入口图片" /> |
||||
</a> |
||||
</span> |
||||
<!-- Banner图 --> |
||||
<span slot="theme_image_url" slot-scope="text"> |
||||
<a title="点击查看原图" :href="text" target="_blank"> |
||||
<img height="50" :src="text" alt="活动主题图" /> |
||||
</a> |
||||
</span> |
||||
<!-- 状态 --> |
||||
<span slot="status" slot-scope="text"> |
||||
<a-tag :color="text == 1 ? 'green' : ''">{{ text ? '开启' : '关闭' }}</a-tag> |
||||
</span> |
||||
</s-table> |
||||
</a-modal> |
||||
</template> |
||||
|
||||
<script> |
||||
import PropTypes from 'ant-design-vue/es/_util/vue-types' |
||||
import cloneDeep from 'lodash.clonedeep' |
||||
import { filterModules } from '@/core/app' |
||||
import * as Api from '@/api/market/active' |
||||
import { STable } from '@/components/Table' |
||||
|
||||
// table表头 |
||||
const columns = filterModules([ |
||||
{ |
||||
title: '活动ID', |
||||
dataIndex: 'id' |
||||
}, |
||||
{ |
||||
title: '活动名称', |
||||
dataIndex: 'name' |
||||
}, |
||||
{ |
||||
title: '活动标题', |
||||
dataIndex: 'title' |
||||
}, |
||||
{ |
||||
title: '活动入口图片', |
||||
dataIndex: 'index_image_url', |
||||
scopedSlots: { customRender: 'index_image_url' } |
||||
}, |
||||
{ |
||||
title: '活动主题标题', |
||||
dataIndex: 'theme_title' |
||||
}, |
||||
{ |
||||
title: '活动主题图', |
||||
dataIndex: 'theme_image_url', |
||||
scopedSlots: { customRender: 'theme_image_url' } |
||||
}, |
||||
{ |
||||
title: '状态', |
||||
dataIndex: 'status', |
||||
scopedSlots: { customRender: 'status' } |
||||
} |
||||
]) |
||||
|
||||
export default { |
||||
name: 'ActiveModal', |
||||
props: { |
||||
// 多选模式, 如果false为单选 |
||||
multiple: PropTypes.bool.def(false), |
||||
// 最大选择的数量限制, multiple模式下有效 |
||||
maxNum: PropTypes.integer.def(100), |
||||
// 默认选中的列表记录 |
||||
defaultList: PropTypes.array.def([]) |
||||
}, |
||||
components: { |
||||
STable |
||||
}, |
||||
data () { |
||||
return { |
||||
// 对话框标题 |
||||
title: '选择活动', |
||||
// modal(对话框)是否可见 |
||||
visible: false, |
||||
// loading状态 |
||||
isLoading: false, |
||||
// 当前表单元素 |
||||
searchForm: this.$form.createForm(this), |
||||
// 查询参数 |
||||
queryParam: {}, |
||||
// table表头 |
||||
columns, |
||||
// 加载数据方法 必须为 Promise 对象 |
||||
loadData: param => { |
||||
return Api.list({ ...param, ...this.queryParam }) |
||||
.then(response => response.data.list) |
||||
}, |
||||
// 主键ID字段名 |
||||
fieldName: 'id', |
||||
// 已选择的元素 |
||||
selectedRowKeys: [], |
||||
// 已选择的列表记录 |
||||
selectedItems: [], |
||||
// 会员等级列表 |
||||
gradeList: [] |
||||
} |
||||
}, |
||||
computed: { |
||||
rowSelection () { |
||||
return { |
||||
selectedRowKeys: this.selectedRowKeys, |
||||
onChange: this.onSelectChange, |
||||
type: !this.multiple ? 'radio' : 'checkbox' |
||||
} |
||||
} |
||||
}, |
||||
created () { |
||||
}, |
||||
methods: { |
||||
|
||||
// 显示对话框 |
||||
handle () { |
||||
// 显示窗口 |
||||
this.visible = true |
||||
this.$nextTick(() => { |
||||
// 刷新列表数据 |
||||
// this.handleRefresh(true) |
||||
// 设置默认数据 |
||||
this.setDefaultValue() |
||||
}) |
||||
}, |
||||
|
||||
// 设置默认数据 |
||||
setDefaultValue () { |
||||
const { fieldName, defaultList } = this |
||||
if (defaultList.length) { |
||||
this.selectedItems = cloneDeep(defaultList) |
||||
this.selectedRowKeys = defaultList.map(item => item[fieldName]) |
||||
} |
||||
}, |
||||
|
||||
// 选中项发生变化时的回调 |
||||
onSelectChange (selectedRowKeys, newSelectedItems) { |
||||
const { selectedItems } = this |
||||
this.selectedRowKeys = selectedRowKeys |
||||
this.selectedItems = this.createSelectedItems(selectedRowKeys, selectedItems, newSelectedItems) |
||||
}, |
||||
|
||||
/** |
||||
* 生成已选中的元素列表 |
||||
* @param array selectedRowKeys 当前已选中的ID集 |
||||
* @param array oldSelectedItems 已选择的列表记录 (change前) |
||||
* @param array newSelectedItems 已选择的列表记录 (change后) |
||||
*/ |
||||
createSelectedItems (selectedRowKeys, oldSelectedItems, newSelectedItems) { |
||||
const { fieldName } = this |
||||
const selectedItems = [] |
||||
oldSelectedItems.forEach(item => { |
||||
if (selectedRowKeys.includes(item[fieldName])) { |
||||
selectedItems.push(item) |
||||
} |
||||
}) |
||||
const oldSelectedKeys = oldSelectedItems.map(item => item[fieldName]) |
||||
newSelectedItems.forEach(item => { |
||||
if (!oldSelectedKeys.includes(item[fieldName]) && selectedRowKeys.includes(item[fieldName])) { |
||||
selectedItems.push(item) |
||||
} |
||||
}) |
||||
return selectedItems |
||||
}, |
||||
|
||||
/** |
||||
* 刷新列表 |
||||
* @param Boolean bool 强制刷新到第一页 |
||||
*/ |
||||
handleRefresh (bool = false) { |
||||
this.$refs.table.refresh(true) |
||||
}, |
||||
|
||||
// 确认搜索 |
||||
handleSearch () { |
||||
this.searchForm.validateFields((error, values) => { |
||||
if (!error) { |
||||
this.queryParam = { ...this.queryParam, ...values } |
||||
this.handleRefresh(true) |
||||
} |
||||
}) |
||||
}, |
||||
|
||||
// 关闭对话框事件 |
||||
handleCancel () { |
||||
this.visible = false |
||||
this.queryParam = {} |
||||
this.searchForm.resetFields() |
||||
this.selectedRowKeys = [] |
||||
this.selectedItems = [] |
||||
}, |
||||
|
||||
// 确认按钮 |
||||
handleSubmit (e) { |
||||
e.preventDefault() |
||||
// 通知父端组件提交完成了 |
||||
this.$emit('handleSubmit', { |
||||
selectedItems: this.selectedItems, |
||||
selectedRowKeys: this.selectedRowKeys |
||||
}) |
||||
// 关闭对话框 |
||||
this.handleCancel() |
||||
} |
||||
|
||||
} |
||||
} |
||||
</script> |
||||
|
||||
<style lang="less" scoped> |
||||
.ant-modal-root { |
||||
background: #ccc; |
||||
/deep/.ant-modal-body { |
||||
padding-bottom: 8px; |
||||
} |
||||
/deep/.ant-modal-footer { |
||||
padding-top: 0; |
||||
} |
||||
} |
||||
// 搜索表单 |
||||
.search-form { |
||||
/deep/.ant-form-item-control-wrapper { |
||||
min-width: 180px; |
||||
} |
||||
} |
||||
</style> |
@ -0,0 +1,2 @@ |
||||
import ActiveModal from './ActiveModal' |
||||
export default ActiveModal |
@ -0,0 +1,184 @@ |
||||
<template> |
||||
<div> |
||||
<a-button @click="handleSelectActive">选择活动</a-button> |
||||
<a-table |
||||
v-show="selectedItems.length" |
||||
class="table-activeList" |
||||
rowKey="id" |
||||
:columns="columns" |
||||
:dataSource="selectedItems" |
||||
:pagination="false" |
||||
> |
||||
<!-- 活动入口图片 --> |
||||
<span slot="index_image_url" slot-scope="text"> |
||||
<a title="点击查看原图" :href="text" target="_blank"> |
||||
<img height="50" :src="text" alt="活动入口图片" /> |
||||
</a> |
||||
</span> |
||||
<!-- Banner图 --> |
||||
<span slot="theme_image_url" slot-scope="text"> |
||||
<a title="点击查看原图" :href="text" target="_blank"> |
||||
<img height="50" :src="text" alt="活动主题图" /> |
||||
</a> |
||||
</span> |
||||
<!-- 状态 --> |
||||
<span slot="status" slot-scope="text"> |
||||
<a-tag :color="text == 1 ? 'green' : ''">{{ text ? '开启' : '关闭' }}</a-tag> |
||||
</span> |
||||
<!-- 操作项 --> |
||||
<span slot="action" slot-scope="text, item, index"> |
||||
<a v-action:delete @click="handleDeleteItem(index)">删除</a> |
||||
</span> |
||||
</a-table> |
||||
<ActiveModal |
||||
ref="ActiveModal" |
||||
:multiple="multiple" |
||||
:maxNum="maxNum" |
||||
:defaultList="selectedItems" |
||||
@handleSubmit="handleSelectActiveSubmit" |
||||
/> |
||||
</div> |
||||
</template> |
||||
|
||||
<script> |
||||
import PropTypes from 'ant-design-vue/es/_util/vue-types' |
||||
import cloneDeep from 'lodash.clonedeep' |
||||
import { filterModules } from '@/core/app' |
||||
import { ActiveModal } from '@/components/Modal' |
||||
|
||||
// table表头 |
||||
const columns = filterModules([ |
||||
{ |
||||
title: '活动ID', |
||||
dataIndex: 'id' |
||||
}, |
||||
{ |
||||
title: '活动名称', |
||||
dataIndex: 'name' |
||||
}, |
||||
{ |
||||
title: '活动标题', |
||||
dataIndex: 'title' |
||||
}, |
||||
// { |
||||
// title: '活动入口图片', |
||||
// dataIndex: 'index_image_url', |
||||
// scopedSlots: { customRender: 'index_image_url' } |
||||
// }, |
||||
{ |
||||
title: '活动主题标题', |
||||
dataIndex: 'theme_title' |
||||
}, |
||||
// { |
||||
// title: '活动主题图', |
||||
// dataIndex: 'theme_image_url', |
||||
// scopedSlots: { customRender: 'theme_image_url' } |
||||
// }, |
||||
{ |
||||
title: '状态', |
||||
dataIndex: 'status', |
||||
scopedSlots: { customRender: 'status' } |
||||
}, |
||||
{ |
||||
title: '操作', |
||||
width: '180px', |
||||
dataIndex: 'action', |
||||
scopedSlots: { customRender: 'action' } |
||||
} |
||||
]) |
||||
|
||||
// 会员选择器组件 |
||||
export default { |
||||
name: 'SelectActive', |
||||
components: { |
||||
ActiveModal |
||||
}, |
||||
model: { |
||||
prop: 'value', |
||||
event: 'change' |
||||
}, |
||||
props: { |
||||
// 多选模式, 如果false为单选 |
||||
multiple: PropTypes.bool.def(false), |
||||
// 最大选择的数量限制, multiple模式下有效 |
||||
maxNum: PropTypes.integer.def(100), |
||||
// 默认选中的会员 |
||||
defaultList: PropTypes.array.def([]) |
||||
}, |
||||
data () { |
||||
return { |
||||
// table表头 |
||||
columns, |
||||
// 已选择的会员列表 |
||||
selectedItems: [], |
||||
// 已选择的会员ID集 |
||||
selectedActiveIds: [] |
||||
} |
||||
}, |
||||
watch: { |
||||
// 设置默认数据 |
||||
defaultList: { |
||||
// 首次加载的时候执行函数 |
||||
immediate: true, |
||||
handler (val) { |
||||
const { selectedItems } = this |
||||
if (val.length && !selectedItems.length) { |
||||
this.onUpdate(cloneDeep(val)) |
||||
} |
||||
} |
||||
} |
||||
}, |
||||
created () { |
||||
}, |
||||
methods: { |
||||
|
||||
// 更新数据 |
||||
onUpdate (selectedItems) { |
||||
if (this.multiple || !selectedItems.length) { |
||||
// 多选模式 |
||||
this.selectedItems = selectedItems |
||||
this.selectedActiveIds = selectedItems.map(item => item.id) |
||||
} else { |
||||
// 单选模式 |
||||
const single = selectedItems[selectedItems.length - 1] |
||||
this.selectedItems = [single] |
||||
this.selectedActiveIds = [single.id] |
||||
} |
||||
this.onChange() |
||||
}, |
||||
|
||||
// 打开会员选择器 |
||||
handleSelectActive () { |
||||
this.$refs.ActiveModal.handle() |
||||
}, |
||||
|
||||
// 会员库modal确认回调 |
||||
handleSelectActiveSubmit (result) { |
||||
const { selectedItems } = result |
||||
this.onUpdate(cloneDeep(selectedItems)) |
||||
}, |
||||
|
||||
// 删除会员 |
||||
handleDeleteItem (index) { |
||||
const { selectedItems } = this |
||||
selectedItems.splice(index, 1) |
||||
this.onUpdate(selectedItems) |
||||
}, |
||||
|
||||
// 触发change事件 |
||||
onChange () { |
||||
const { multiple, selectedActiveIds } = this |
||||
const sActiveIds = multiple ? selectedActiveIds : (selectedActiveIds.length ? selectedActiveIds[0] : undefined) |
||||
return this.$emit('change', sActiveIds) |
||||
} |
||||
|
||||
} |
||||
} |
||||
</script> |
||||
|
||||
<style lang="less" scoped> |
||||
.table-activeList { |
||||
margin-top: 10px; |
||||
min-width: 620px; |
||||
} |
||||
</style> |
@ -0,0 +1,2 @@ |
||||
import SelectActive from './SelectActive' |
||||
export default SelectActive |
Loading…
Reference in new issue