123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229 |
- <template>
- <div class="select-table">
- <div class="select-table-box">
- <page-layout-list class="dialog-table">
- <template #filter v-if="searchFieldList.length > 0">
- <cip-search-form v-model:model="searchFilter" :field-list="searchFieldList" @search="handleSearch"></cip-search-form>
- </template>
- <cip-table v-if="checkType === 'radio'"
- :data="itemList"
- :columns="tableColumns"
- :offset="offset"
- ref="tableRef"
- size="small"
- :select-type="checkType"
- :select-radio="selectRadio"
- :select-label="optionProps.value"
- @current-change="currentChange"
- v-loading="listLoading">
- </cip-table>
- <cip-table v-if="checkType === 'checkbox'"
- :data="itemList"
- :columns="tableColumns"
- :offset="offset"
- ref="tableRef"
- size="small"
- :select-type="checkType"
- @select="onSelect"
- @select-all="onSelectAll"
- :selectable="selectable"
- v-loading="listLoading">
- </cip-table>
- <template #pagination v-if="withPagination">
- <cip-pagination v-model:offset="offset"
- v-model:limit="limit"
- :total="total"
- :current-page="currentPage"
- @refresh="getItemList"></cip-pagination>
- </template>
- </page-layout-list>
- <slot name="group"></slot>
- <tags v-if="!$slots.group && withTags" class="dialog-tags" :options="checkOptions" :keyProp="optionProps" @update:options="changeOptions"></tags>
- </div>
- </div>
- </template>
- <script>
- import { useCurd } from '@cip/hooks/use-curd'
- import { useTableCacheSelect } from '@cip/components/hooks/table-cache-select'
- import { ref, computed, nextTick, watch, watchEffect } from 'vue'
- import { ElLoading } from 'element-plus'
- import PageLayoutList from '@cip/components/page-layout/list'
- import CipSearchForm from '@cip/components/cip-search-form'
- import CipTable from '@cip/components/cip-table'
- import CipPagination from '@cip/components/cip-pagination'
- import { useFormInput, useOptions } from '@cip/components/hooks/form-input'
- import { formInputProps } from '../../form-input-props'
- import Tags from './tags'
- export default {
- components: { Tags, PageLayoutList, CipSearchForm, CipTable, CipPagination },
- directives: {
- loading: ElLoading.directive
- },
- props: formInputProps,
- emits: ['update:modelValue'],
- setup (props, context) {
- const { emitInput, ...formInput } = useFormInput(props, context)
- const { optionProps } = useOptions(props, false, formInput.emitInput)
- const checkOptions = computed(() => {
- return cacheSelectedList.value.length === 0 ? props.modelValue : cacheSelectedList.value
- })
- // 类型
- const checkType = computed(() => {
- return props.config?.checkType ?? 'radio'
- })
- // 列表头
- const tableColumns = computed(() => {
- return props.config?.tableColumns ?? []
- })
- // 搜索头
- const searchFieldList = computed(() => {
- return props.config?.searchFieldList ?? []
- })
- // 是否显示分页
- const withPagination = computed(() => {
- return props.config?.withPagination ?? true
- })
- // 是否显示选中tag
- const withTags = computed(() => {
- return props.config?.withTags ?? true
- })
- // 表格行是否可选,这里整个表格行为一致, selectable为function
- const selectable = computed(() => {
- return props.config?.selectable ?? (() => true)
- })
- // 右侧数据改变
- const changeOptions = (item) => {
- cacheSelectedList.value = item
- emitInput(item)
- handleSelectShow()
- }
- const tableRef = ref()
- const CURD = useCurd(props.config.entity, { ...props.config.curdFn, itemType: props.config.itemType })
- const { itemList, getItemList, searchFilter, search } = CURD
- watch(() => props.config?.defaultSearchFilter, val => {
- getTableList(val)
- })
- // 外层触发请求
- const getTableList = (item = {}) => {
- searchFilter.value = { ...props.config.defaultSearchFilter, ...searchFilter.value, ...item }
- getItemList()
- }
- getTableList()
- const { cacheSelectedList, onSelect, onSelectAll } = useTableCacheSelect(itemList, optionProps.value.value, val => {
- emitInput(val)
- })
- // 已选择的radio
- const selectRadio = computed(() => {
- if (props.modelValue && props.modelValue[optionProps.value.value]) {
- return props.modelValue[optionProps.value.value]
- }
- return radioCache.value
- })
- // radio类型时的缓存
- const radioCache = computed(() => {
- const cache = itemList.value?.find(v => v[optionProps.value.value] === props.modelValue)
- return cache ? cache[optionProps.value.value] : undefined
- })
- const currentChange = (currentRow, oldCurrentRow) => {
- // 单选不能取消,只能有值时才填入
- if (currentRow) {
- emitInput(currentRow[optionProps.value.value])
- }
- }
- // checkbox类型更新选中视图
- const showSelectedView = (rows, select) => {
- nextTick(() => {
- rows.forEach(row => {
- tableRef.value.cipTableRef.value.toggleRowSelection(row, select)
- })
- })
- }
- // tag组件传入值需要更新table选中视图
- const handleSelectShow = () => {
- const selectedPropsCode = cacheSelectedList.value.map(button => button[optionProps.value.value])
- const rows = itemList.value.filter(item => {
- return !selectedPropsCode.includes(item[optionProps.value.value])
- })
- showSelectedView(rows, false)
- }
- if (checkType.value === 'checkbox') {
- // 分页切换时缓存数据处理
- watch(() => [itemList.value, props.modelValue], list => {
- cacheHandle()
- })
- } else {
- const unWatch = watchEffect(() => {
- if (props.modelValue && props.modelValue[optionProps.value.value]) {
- const checkItem = itemList.value.filter(item => item[optionProps.value.value] === props.modelValue[optionProps.value.value])[0]
- if (checkItem) {
- emitInput(checkItem)
- unWatch()
- }
- }
- })
- }
- // 缓存数据处理
- const cacheHandle = () => {
- if (cacheSelectedList.value.length === 0) {
- cacheSelectedList.value = props.modelValue ?? []
- }
- const cacheSelectButtonCode = cacheSelectedList.value.map(button => button[optionProps.value.value])
- const rows = itemList.value.filter(item => {
- const selectList = props.modelValue || (cacheSelectButtonCode.includes(item[optionProps.value.value]) ? cacheSelectButtonCode : [])
- return selectList.findIndex(v => v[optionProps.value.value] === item[optionProps.value.value]) !== -1
- })
- showSelectedView(rows, true)
- }
- // 搜索
- const handleSearch = () => {
- search()
- }
- return {
- changeOptions,
- checkOptions,
- getTableList,
- handleSearch,
- optionProps,
- checkType,
- tableColumns,
- searchFieldList,
- withPagination,
- withTags,
- ...CURD,
- tableRef,
- selectable,
- selectRadio,
- currentChange,
- onSelect,
- onSelectAll,
- cacheSelectedList
- }
- }
- }
- </script>
- <style lang="less" scoped>
- .select-table{
- flex: 1;
- .select-table-box{
- display: flex;
- }
- .dialog-table{
- flex: 1;
- margin: 0 15px 15px 0;
- padding: 0;
- }
- .dialog-tags{
- padding: 8px 0;
- flex-basis: 220px;
- }
- }
- </style>
|