Browse Source

物料管理

master
songguoqiang 1 year ago
parent
commit
80bf28e6ed
  1. 77
      src/api/spc/itembasic/index.ts
  2. 160
      src/components/BasicForm/src/BasicForm.vue
  3. 71
      src/components/Detail/src/Detail.vue
  4. 75
      src/components/Form/src/Form.vue
  5. 34
      src/components/ImportForm/src/ImportForm.vue
  6. 56
      src/components/SearchHigh/src/SearchHigh.vue
  7. 67
      src/components/SearchTable/src/SearchTable.vue
  8. 9
      src/components/TableForm/src/TableForm.vue
  9. 49
      src/components/TableHead/src/TableHead.vue
  10. 119
      src/components/XButton/src/ButtonBase.vue
  11. 69
      src/components/rowDrop/index.vue
  12. 228
      src/views/spc/itembasic/index.vue
  13. 355
      src/views/spc/itembasic/itembasic.data.ts

77
src/api/spc/itembasic/index.ts

@ -0,0 +1,77 @@
import request from '@/config/axios'
export interface ItembasicVO {
code: string
name: string
desc1: string
desc2: string
status: string
uom: string
altUom: string
isStdPack: string
enableBuy: string
enableMake: string
enableOutsourcing: string
isRecycled: string
isPhantom: string
abcClass: string
type: string
category: string
itemGroup: string
color: string
configuration: string
project: string
eqLevel: string
validityDays: number
userGroupCode: string
available: string
activeTime: Date
expireTime: Date
remark: string
deletionTime: Date
deleterId: string
extraProperties: string
concurrencyStamp: string
siteId: string
}
// 查询物品基本信息列表
export const getItembasicPage = async (params) => {
if (params.isSearch) {
delete params.isSearch
const data = {...params}
return await request.post({ url: '/spc/itembasic/senior', data })
} else {
return await request.get({ url: `/spc/itembasic/page`, params })
}
}
// 查询物品基本信息详情
export const getItembasic = async (id: number) => {
return await request.get({ url: `/spc/itembasic/get?id=` + id })
}
// 新增物品基本信息
export const createItembasic = async (data: ItembasicVO) => {
return await request.post({ url: `/spc/itembasic/create`, data })
}
// 修改物品基本信息
export const updateItembasic = async (data: ItembasicVO) => {
return await request.put({ url: `/spc/itembasic/update`, data })
}
// 删除物品基本信息
export const deleteItembasic = async (id: number) => {
return await request.delete({ url: `/spc/itembasic/delete?id=` + id })
}
// 导出物品基本信息 Excel
export const exportItembasic = async (params) => {
return await request.download({ url: `/spc/itembasic/export-excel`, params })
}
// 下载导入模板
export const importTemplate = () => {
return request.download({ url: '/spc/itembasic/get-import-template' })
}

160
src/components/BasicForm/src/BasicForm.vue

@ -1,110 +1,13 @@
<template> <template>
<Dialog :title="dialogTitle" v-model="dialogVisible" :width="isBusiness?'60%':'40%'"> <Dialog :title="dialogTitle" v-model="dialogVisible" :width="isBusiness?'60%':'40%'">
<Form ref="formRef" v-loading="formLoading" :rules="rules" :schema="formSchema" :is-col="true" > <Form
<!-- <template #productItemCode="form"> ref="formRef"
<slot name="productItemCode" :param="form"></slot> v-loading="formLoading"
</template> --> :rules="rules"
<template #itemCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'itemCode'))"> :schema="formSchema"
<div class="w-[100%] flex"> :is-col="true"
<el-input v-model="form['itemCode']" :placeholder="'请选择物料代码'" @click="opensearchTable('itemCode', 'code')" /> @opensearchTable="opensearchTable"
</div> />
</template>
<template #productItemCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'productItemCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['productItemCode']" :placeholder="'请选择物料代码'" @click="opensearchTable('productItemCode', 'code')" />
</div>
</template>
<template #componentItemCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'componentItemCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['componentItemCode']" :placeholder="'请选择物料代码'" @click="opensearchTable('componentItemCode', 'code')" />
</div>
</template>
<template #supplierCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'supplierCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['supplierCode']" :placeholder="'请选择供应商代码'" @click="opensearchTable('supplierCode', 'code')" />
</div>
</template>
<template #productionLineCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'productionLineCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['productionLineCode']" :placeholder="'请选择生产线代码'" @click="opensearchTable('productionLineCode', 'code')" />
</div>
</template>
<template #fgLocationCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'fgLocationCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['fgLocationCode']" :placeholder="'请选择库位代码'" @click="opensearchTable('fgLocationCode', 'code')" />
</div>
</template>
<template #defaultWarehouseCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'defaultWarehouseCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['defaultWarehouseCode']" :placeholder="'请选择仓库代码'" @click="opensearchTable('defaultWarehouseCode', 'code')" />
</div>
</template>
<template #defaultLocationCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'defaultLocationCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['defaultLocationCode']" :placeholder="'请选择库位代码'" @click="opensearchTable('defaultLocationCode', 'code')" />
</div>
</template>
<template #customerCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'customerCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['customerCode']" :placeholder="'请选择客户代码'" @click="opensearchTable('customerCode', 'code')" />
</div>
</template>
<template #warehouseCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'warehouseCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['warehouseCode']" :placeholder="'请选择仓库代码'" @click="opensearchTable('warehouseCode', 'code')" />
</div>
</template>
<template #areaCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'areaCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['areaCode']" :placeholder="'请选择库区代码'" @click="opensearchTable('areaCode', 'code')" />
</div>
</template>
<template #locationGroupCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'locationGroupCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['locationGroupCode']" :placeholder="'请选择库位组代码'" @click="opensearchTable('locationGroupCode', 'code')" />
</div>
</template>
<template #rawLocationCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'rawLocationCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['rawLocationCode']" :placeholder="'请选择库位代码'" @click="opensearchTable('rawLocationCode', 'code')" />
</div>
</template>
<template #workshopCode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'workshopCode'))">
<div class="w-[100%] flex">
<el-input v-model="form['workshopCode']" :placeholder="'请选择车间代码'" @click="opensearchTable('workshopCode', 'code')" />
</div>
</template>
<template #outAreaCodes="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'outAreaCodes'))">
<div class="w-[100%] flex">
<el-input v-model="form['outAreaCodes']" :placeholder="'请选择库区代码'" @click="opensearchTable('outAreaCodes', 'code')" />
</div>
</template>
<template #inAreaCodes="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'inAreaCodes'))">
<div class="w-[100%] flex">
<el-input v-model="form['inAreaCodes']" :placeholder="'请选择库区代码'" @click="opensearchTable('inAreaCodes', 'code')" />
</div>
</template>
<template #customercode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'customercode'))">
<div class="w-[100%] flex">
<el-input v-model="form['customercode']" :placeholder="'请选择客户代码'" @click="opensearchTable('customercode', 'code')" />
</div>
</template>
<template #itemcode="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'itemcode'))">
<div class="w-[100%] flex">
<el-input v-model="form['itemcode']" :placeholder="'请选择物料代码'" @click="opensearchTable('itemcode', 'code')" />
</div>
</template>
<template #asnNumber="form" v-if="props.searchTableParams?.find((item:any) => (item.formField == 'asnNumber'))">
<div class="w-[100%] flex">
<el-input v-model="form['asnNumber']" :placeholder="'请选择发货单号'" @click="opensearchTable('asnNumber', 'asnNumber')" />
</div>
</template>
<template #poNumber="form" v-if="props.searchTableParams?.find((item: any) => (item.formField == 'poNumber'))">
<div class="w-[100%] flex">
<el-input v-model="form['poNumber']" :placeholder="'请选择发货单号'" @click="opensearchTable('poNumber', 'poNumber')" />
</div>
</template>
</Form>
<div class="table" v-if="isBusiness && formType == 'create'"> <div class="table" v-if="isBusiness && formType == 'create'">
<TableForm ref="tableFormRef" <TableForm ref="tableFormRef"
class="w-[100%]" class="w-[100%]"
@ -132,7 +35,6 @@ import { SearchTable } from '@/components/SearchTable';
import * as defaultButtons from '@/utils/disposition/defaultButtons' import * as defaultButtons from '@/utils/disposition/defaultButtons'
import ButtonBase from '@/components/XButton/src/ButtonBase.vue' import ButtonBase from '@/components/XButton/src/ButtonBase.vue'
import TableForm from '@/components/TableForm/src/TableForm.vue' import TableForm from '@/components/TableForm/src/TableForm.vue'
import { string } from 'vue-types';
const props = defineProps({ const props = defineProps({
// rules // rules
@ -165,11 +67,11 @@ const props = defineProps({
default: null default: null
}, },
// //
searchTableParams: { // searchTableParams: {
type: Array, // type: Array,
required: false, // required: false,
default: null // default: null
}, // },
// APIVo // APIVo
apiVo: { apiVo: {
type: Object, type: Object,
@ -219,18 +121,29 @@ const formType = ref('') // 表单的类型:create - 新增;update - 修改
const formRef = ref() // Ref const formRef = ref() // Ref
const formSchema = ref(props.formAllSchemas?.formSchema) const formSchema = ref(props.formAllSchemas?.formSchema)
/** 弹层操作 */ /** 弹层操作 */
// formField form // formField form
// searchField // searchField
// type type=tableForm // type type=tableForm
// searchCondition
const searchTableRef = ref() const searchTableRef = ref()
const opensearchTable = (formField, searchField, type, row) => { const opensearchTable = (formField, searchField, searchTitle, searchAllSchemas, searchPage, type, row, searchCondition) => {
const _searchTableParamsObject:any = props.searchTableParams.find((item:any) => (item.formField == formField)) const _searchCondition = {}
const _searchTableTitle = _searchTableParamsObject.searchTableTitle //
const _searchTableAllSchemas = _searchTableParamsObject.searchTableAllSchemas if (searchCondition && searchCondition.length > 0) {
const _searchTablePage = _searchTableParamsObject.searchTablePage searchCondition.forEach(item => {
searchTableRef.value.open(_searchTableTitle, _searchTableAllSchemas, _searchTablePage, formField, searchField, type, row) //
if (item.isMainValue) {
_searchCondition[item.key] = formRef.value.formModel[item.value]
} else {
_searchCondition[item.key] = item.value
}
})
}
const _searchTableTitle = searchTitle
const _searchTableAllSchemas = searchAllSchemas
const _searchTablePage = searchPage
searchTableRef.value.open(_searchTableTitle, _searchTableAllSchemas, _searchTablePage, formField, searchField, type, row, _searchCondition)
} }
// //
// val row // val row
@ -394,7 +307,16 @@ const handleAddTable = () => {
} }
// //
const inpuFocus = (headerItem, row, index) => { const inpuFocus = (headerItem, row, index) => {
opensearchTable(headerItem.field, 'poNumber', 'tableForm', row) opensearchTable(
headerItem.field,
headerItem.tableForm.searchField,
headerItem.tableForm.searchTitle,
headerItem.tableForm.searchAllSchemas,
headerItem.tableForm.searchPage,
'tableForm',
row,
headerItem.tableForm.searchCondition
)
} }
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>

71
src/components/Detail/src/Detail.vue

@ -35,7 +35,7 @@
v-model:pageSize="tableObject.pageSize" v-model:pageSize="tableObject.pageSize"
v-model:currentPage="tableObject.currentPage" > v-model:currentPage="tableObject.currentPage" >
<template #action="{ row }"> <template #action="{ row }">
<ButtonBase :Butttondata="buttondata(row)" @button-base-click="buttonTableClick($event, row)" /> <ButtonBase :Butttondata="buttondata" @button-base-click="buttonTableClick($event, row)" />
</template> </template>
</Table> </Table>
</ContentWrap> </ContentWrap>
@ -56,7 +56,6 @@
@success="getList" @success="getList"
:rules="detailAllSchemasRules" :rules="detailAllSchemasRules"
:formAllSchemas="detailAllSchemas" :formAllSchemas="detailAllSchemas"
:searchTableParams="searchTableParams"
:isBusiness="false" :isBusiness="false"
:apiUpdate="apiUpdate" :apiUpdate="apiUpdate"
:apiCreate="apiCreate" :apiCreate="apiCreate"
@ -116,12 +115,6 @@ const props = defineProps({
type: Object, type: Object,
required: true, required: true,
default: null default: null
},
//
searchTableParams: {
type: Array,
required: true,
default: null
}, },
// API // API
apiCreate: { apiCreate: {
@ -221,6 +214,11 @@ const masterParmas=ref({
status: '',// status: '',//
}) })
//
const HeadButttondata = ref()
// -
const buttondata = ref()
/** 打开弹窗 */ /** 打开弹窗 */
const titleNameRef = ref() const titleNameRef = ref()
const titleValueRef = ref() const titleValueRef = ref()
@ -250,7 +248,16 @@ const openDetail = async (row: any, titleName: any, titleValue: any, tableName:
getRemarkList() getRemarkList()
getFileList() getFileList()
getChangeRecordList() getChangeRecordList()
//
HeadButttondata.value = [
defaultButtons.defaultAddBtn({hide:isShowMainButton(row,['1','1','PLAN_PURCHASE_READY','1'])}), //
defaultButtons.defaultFilterBtn(null), //
]
//
buttondata.value = [
defaultButtons.mainListEditBtn({hide:isShowMainButton(row,['1','1','PLAN_PURCHASE_READY','1'])}), //
defaultButtons.mainListDeleteBtn({hide:isShowMainButton(row,['1','1','PLAN_PURCHASE_READY','1'])}), //
]
} finally { } finally {
detailLoading.value = false detailLoading.value = false
} }
@ -281,13 +288,20 @@ const getChangeRecordList = async () => {
const { tableObject, tableMethods } = useTable({ const { tableObject, tableMethods } = useTable({
getListApi: props.apiPage // getListApi: props.apiPage //
}) })
//
const isShowMainButton = (row,val) => {
if (val.indexOf(row.status) > -1) {
return false
} else {
return true
}
}
// //
const { getList } = tableMethods const { getList } = tableMethods
//
const HeadButttondata = ref([
defaultButtons.defaultAddBtn(null), //
defaultButtons.defaultFilterBtn(null), //
])
// //
const buttonBaseClick = (val, item) => { const buttonBaseClick = (val, item) => {
if (val == 'add') { // if (val == 'add') { //
@ -308,13 +322,7 @@ const buttonBaseClick = (val, item) => {
// const updataTableColumns = (val) => { // const updataTableColumns = (val) => {
// detailAllSchemas.tableColumns.value = val // detailAllSchemas.tableColumns.value = val
// } // }
// -
const buttondata = (row) => {
return [
defaultButtons.mainListEditBtn({ hide: masterParmas.value.status=='REQUEST_NEW'?false:true, hasPermi: 'wms:purchaseclaim-request-main:update' }), //
defaultButtons.mainListDeleteBtn({ hide: masterParmas.value.status=='REQUEST_NEW'?false:true, hasPermi: 'wms:purchaseclaim-request-main:delete' }), //
]
}
// - // -
const buttonTableClick = async (val, row) => { const buttonTableClick = async (val, row) => {
if (val == 'edit') { // if (val == 'edit') { //
@ -329,20 +337,13 @@ const openForm = async (type: string, row?: number) => {
formRef.value.open(type, row, masterParmas.value) formRef.value.open(type, row, masterParmas.value)
} }
// //
const searchTableSuccess = (formField, searchField, val, formRef, type, row) => { const searchTableSuccess = (formField, searchField, val, formRef) => {
nextTick(() => { emit('searchTableSuccessDetail', formField, searchField, val, formRef)
if (type == 'tableForm') {
} else {
const setV = {}
setV[formField] = val[0][searchField]
console.log(formField);
props.Echo.forEach((item)=>{
setV[item] = val[0][item]
})
formRef.setValues(setV)
}
})
} }
//
const emit = defineEmits([
'searchTableSuccessDetail',
])
/** 删除按钮操作 */ /** 删除按钮操作 */
const handleDelete = async (id: number) => { const handleDelete = async (id: number) => {
try { try {
@ -359,7 +360,7 @@ const handleDelete = async (id: number) => {
const searchFormClick = (searchData) => { const searchFormClick = (searchData) => {
tableObject.params = { tableObject.params = {
isSearch: true, isSearch: true,
filters: searchData.filters filters: searchData.filters?searchData.filters:[{column: "masterId", action: "==", value: masterParmas.value.masterId}]
} }
getList() // getList() //
} }

75
src/components/Form/src/Form.vue

@ -1,6 +1,6 @@
<script lang="tsx"> <script lang="tsx">
import { computed, defineComponent, onMounted, PropType, ref, unref, watch } from 'vue' import { computed, defineComponent, onMounted, PropType, ref, unref, watch } from 'vue'
import { ElCol, ElForm, ElFormItem, ElRow, ElTooltip } from 'element-plus' import { ElButton, ElCol, ElForm, ElFormItem, ElInput, ElRow, ElTooltip } from 'element-plus'
import { componentMap } from './componentMap' import { componentMap } from './componentMap'
import { propTypes } from '@/utils/propTypes' import { propTypes } from '@/utils/propTypes'
import { getSlot } from '@/utils/tsxHelper' import { getSlot } from '@/utils/tsxHelper'
@ -21,6 +21,7 @@ import { set } from 'lodash-es'
import { FormProps } from './types' import { FormProps } from './types'
import { Icon } from '@/components/Icon' import { Icon } from '@/components/Icon'
import { FormSchema, FormSetPropsType } from '@/types/form' import { FormSchema, FormSetPropsType } from '@/types/form'
import { Search } from '@element-plus/icons-vue'
const { getPrefixCls } = useDesign() const { getPrefixCls } = useDesign()
@ -53,7 +54,7 @@ export default defineComponent({
vLoading: propTypes.bool.def(false), vLoading: propTypes.bool.def(false),
labelPosition: propTypes.string.def('left'), labelPosition: propTypes.string.def('left'),
}, },
emits: ['register'], emits: ['register','opensearchTable'],
setup(props, { slots, expose, emit }) { setup(props, { slots, expose, emit }) {
// element form // element form
const elFormRef = ref<ComponentRef<typeof ElForm>>() const elFormRef = ref<ComponentRef<typeof ElForm>>()
@ -119,6 +120,10 @@ export default defineComponent({
return unref(elFormRef) as ComponentRef<typeof ElForm> return unref(elFormRef) as ComponentRef<typeof ElForm>
} }
const opensearchTable = (field, searchField,searchTitle,searchAllSchemas, searchPage, searchCondition) => {
emit('opensearchTable',field, searchField, searchTitle, searchAllSchemas, searchPage, searchCondition)
}
expose({ expose({
setValues, setValues,
formModel, formModel,
@ -126,7 +131,8 @@ export default defineComponent({
delSchema, delSchema,
addSchema, addSchema,
setSchema, setSchema,
getElFormRef getElFormRef,
opensearchTable
}) })
// formModel // formModel
@ -213,6 +219,26 @@ export default defineComponent({
) )
} }
} }
// isSearchList: true 使
const formItemSlotsSearchList: Recordable = setFormItemSlots(slots, item.field)
if (item?.componentProps?.isSearchList) {
formItemSlotsSearchList[item.field] = () => {
return (
<>
<ElInput class={'myInput'} v-model={formModel.value[item.field]} placeholder={item?.componentProps?.searchListPlaceholder} disabled={true} />
<ElButton icon={Search} onClick={()=>{
opensearchTable(
item.field, item?.componentProps?.searchField,
item?.componentProps?.searchTitle,
item?.componentProps?.searchAllSchemas,
item?.componentProps?.searchPage,
item?.componentProps?.searchCondition
)}}/>
</>
)
}
}
return ( return (
<ElFormItem {...(item.formItemProps || {})} prop={item.field} label={item.label || ''}> <ElFormItem {...(item.formItemProps || {})} prop={item.field} label={item.label || ''}>
{{ {{
@ -221,26 +247,27 @@ export default defineComponent({
const Com = componentMap[item.component as string] as ReturnType< const Com = componentMap[item.component as string] as ReturnType<
typeof defineComponent typeof defineComponent
> >
const { autoSetPlaceholder } = unref(getProps) const { autoSetPlaceholder } = unref(getProps)
//
return slots[item.field] ? ( return formItemSlotsSearchList[item.field] ?
getSlot(slots, item.field, formModel.value) (getSlot(formItemSlotsSearchList, item.field, formModel.value)) :
) : ( slots[item.field] ? (
<Com getSlot(slots, item.field, formModel.value)
vModel={formModel.value[item.field]} ) : (
{...(autoSetPlaceholder && setTextPlaceholder(item))} <Com
{...setComponentProps(item)} vModel={formModel.value[item.field]}
style={item.componentProps?.style} {...(autoSetPlaceholder && setTextPlaceholder(item))}
{...(notRenderOptions.includes(item?.component as string) && {...setComponentProps(item)}
item?.componentProps?.options style={item.componentProps?.style}
? { options: item?.componentProps?.options || [] } {...(notRenderOptions.includes(item?.component as string) &&
: {})} item?.componentProps?.options
> ? { options: item?.componentProps?.options || [] }
{{ ...slotsMap }} : {})}
</Com> >
) {{ ...slotsMap }}
} </Com>
)
},
}} }}
</ElFormItem> </ElFormItem>
) )
@ -296,12 +323,16 @@ export default defineComponent({
} }
}} }}
</ElForm> </ElForm>
) )
} }
}) })
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>
.myInput{
width: calc(100% - 46px);
}
.#{$elNamespace}-form.#{$namespace}-form .#{$elNamespace}-row { .#{$elNamespace}-form.#{$namespace}-form .#{$elNamespace}-row {
margin-right: 0 !important; margin-right: 0 !important;
margin-left: 0 !important; margin-left: 0 !important;

34
src/components/ImportForm/src/ImportForm.vue

@ -1,16 +1,16 @@
<!-- 导入组件 --> <!-- 导入组件 -->
<template> <template>
<Dialog v-model="dialogVisible" title="导入" width="600"> <Dialog v-model="dialogVisible" title="导入" width="600">
<el-upload ref="uploadRef" v-model:file-list="fileList" :action="importUrl + '?mode=' + mode + '&file=' + file + '&updatePart=' + updatePart" <el-upload ref="uploadRef" v-model:file-list="fileList" :action="importUrl + '?mode=' + mode + '&file=' + file + '&updatePart=' + updatePart + '&outFile=' + outFile"
:auto-upload="false" :disabled="formLoading" :headers="uploadHeaders" :limit="1" :on-error="submitFormError" :auto-upload="false" :disabled="formLoading" :headers="uploadHeaders" :limit="1" :on-error="submitFormError"
:on-exceed="handleExceed" :on-success="submitFormSuccess" :accept="accept" drag :on-exceed="handleExceed" :on-success="submitFormSuccess" :accept="accept" drag
style="width:300px;margin:0 auto"> style="width:300px;margin:0 auto">
<Icon icon="ep:upload-filled" color="#c0c4cc" size="60" /> <Icon icon="ep:upload-filled" color="#c0c4cc" size="60" />
<div class="el-upload__text">将文件拖到此处<em>点击上传</em></div> <div class="el-upload__text">将文件拖到此处<em>点击上传</em></div>
<template #tip> <template #tip>
<div class="el-upload__tip ml--80px mr--80px"> <div class="el-upload__tip ml--126px mr--80px">
<div class="flex"> <div class="flex">
<div class="label h-32px mr-26px color-#acaeb3 font-size-14px" style="line-height:32px">导入模式</div> <div class="label h-32px mr-26px color-#acaeb3 font-size-14px w-100px text-right" style="line-height:32px">导入模式</div>
<div class=""> <div class="">
<div class="radio"> <div class="radio">
<el-radio-group v-model="mode"> <el-radio-group v-model="mode">
@ -28,18 +28,25 @@
</div> </div>
</div> </div>
<div class="flex mt-16px"> <div class="flex mt-16px">
<div class="label h-32px mr-26px color-#acaeb3 font-size-14px" style="line-height:32px">部分保存</div> <div class="label h-32px mr-26px color-#acaeb3 font-size-14px w-100px text-right" style="line-height:32px">部分保存</div>
<div class=""> <div class="">
<div class="switch"> <div class="switch">
<el-switch v-model="updatePart" /> <el-switch v-model="updatePart" />
</div> </div>
<div class="tips color-#acaeb3 font-size-14px"> <div class="tips color-#acaeb3 font-size-14px">
<div class="mt-2">部分保存如存在错误数据正确数据正常导入</div> <div class="mt-2">部分保存如存在错误数据正确数据正常导入</div>
<div class="mt-2">全部保存全部数据正确才能导入</div> <div class="mt-2">全部保存全部数据正确才能导入</div>
</div> </div>
</div> </div>
</div> </div>
<div class="flex mt-16px" v-if="isShowOut">
<div class="label h-32px mr-26px color-#acaeb3 font-size-14px w-100px text-right" style="line-height:32px">是否外部资源</div>
<div class="">
<div class="switch">
<el-switch v-model="outFile" />
</div>
</div>
</div>
</div> </div>
</template> </template>
</el-upload> </el-upload>
@ -54,7 +61,6 @@
<el-button :disabled="formLoading" type="primary" @click="submitForm"> </el-button> <el-button :disabled="formLoading" type="primary" @click="submitForm"> </el-button>
<el-button @click="dialogVisible = false"> </el-button> <el-button @click="dialogVisible = false"> </el-button>
</div> </div>
</template> </template>
</Dialog> </Dialog>
</template> </template>
@ -114,12 +120,23 @@ const file = ref('')
updatePart: { updatePart: {
type: Boolean, type: Boolean,
required: false, required: false,
default: true default: false
}, },
url:{ url:{
type: String, type: String,
required: false, required: false,
} },
//
isShowOut: {
type: Boolean,
required: false,
default: false
},
outFile: {
type: Boolean,
required: false,
default: false
},
}) })
const importTemplateData= ref(props.importTemplateData) const importTemplateData= ref(props.importTemplateData)
const accept= ref(props.accept) const accept= ref(props.accept)
@ -128,6 +145,7 @@ const updateIsDisable = ref(props.updateIsDisable)//更新是否禁用,默认值
const appendIsDisable = ref(props.appendIsDisable)//, const appendIsDisable = ref(props.appendIsDisable)//,
const coverIsDisable = ref(props.coverIsDisable)//, const coverIsDisable = ref(props.coverIsDisable)//,
const updatePart = ref(props.updatePart)// const updatePart = ref(props.updatePart)//
const outFile = ref(props.outFile)//
const importUrl = const importUrl =
import.meta.env.VITE_BASE_URL + import.meta.env.VITE_API_URL + props.url import.meta.env.VITE_BASE_URL + import.meta.env.VITE_API_URL + props.url

56
src/components/SearchHigh/src/SearchHigh.vue

@ -23,20 +23,20 @@
<!-- 数字输入框 --> <!-- 数字输入框 -->
<el-input-number v-else-if="getInputType(item.column) == 'inputNumber'" v-model="item.value" :precision="6" :disabled="item.disabled"/> <el-input-number v-else-if="getInputType(item.column) == 'inputNumber'" v-model="item.value" :precision="6" :disabled="item.disabled"/>
<!-- 下拉框 --> <!-- 下拉框 -->
<el-select v-else-if="getInputType(item.column) == 'select'" v-model="item.value" placeholder="请选择内容" :filterable="true" clearable :disabled="item.disabled"> <el-select v-else-if="getInputType(item.column) == 'select'" v-model="item.value1" placeholder="请选择内容" :filterable="true" clearable :disabled="item.disabled" :multiple="item.action=='in' || item.action=='notIn' ? true : false" collapse-tags collapse-tags-tooltip :key="item.action">
<el-option v-for="dict in initSelectOptions(item.column)" :key="dict.value" :label="dict.label" <el-option v-for="dict in initSelectOptions(item.column)" :key="dict.value" :label="dict.label"
:value="dict.value" /> :value="dict.value" />
<!-- <el-option v-for="(op, index) in initSelectOptions(item.column)" :label="op[item.optionsLabel] || op.label" <!-- <el-option v-for="(op, index) in initSelectOptions(item.column)" :label="op[item.optionsLabel] || op.label"
:value="op[item.optionsValue] || op.value" :key="index" /> --> :value="op[item.optionsValue] || op.value" :key="index" /> -->
</el-select> </el-select>
<!-- 时间 --> <!-- 时间 -->
<el-time-picker v-else-if="getInputType(item.column) == 'time'" range-separator="-" start-placeholder="开始时间" end-placeholder="结束时间" v-model="item.time" style="width: 340px;margin-right: 20px;" :disabled="item.disabled"/> <el-time-picker v-else-if="getInputType(item.column) == 'time'" range-separator="-" start-placeholder="开始时间" end-placeholder="结束时间" v-model="item.value1" style="width: calc(100% - 20px);margin-right: 10px;" :disabled="item.disabled"/>
<!-- 日期 --> <!-- 日期 -->
<el-date-picker v-else-if="getInputType(item.column) == 'date'" v-model="item.time" type="daterange" <el-date-picker v-else-if="getInputType(item.column) == 'date'" v-model="item.value1" type="daterange"
range-separator="-" start-placeholder="开始日期" end-placeholder="结束日期" style="width: 340px;margin-right: 20px;" @change="changeDateTimePicker($event, item,'daterange')" value-format="YYYY-MM-DD" format="YYYY/MM/DD" :disabled="item.disabled"/> range-separator="-" start-placeholder="开始日期" end-placeholder="结束日期" style="width: calc(100% - 20px);margin-right: 10px;" @change="changeDateTimePicker($event, item,'daterange')" value-format="YYYY-MM-DD" format="YYYY/MM/DD" :disabled="item.disabled"/>
<!-- 日期时间 --> <!-- 日期时间 -->
<el-date-picker v-else-if="getInputType(item.column) == 'datePicker'" v-model="item.time" type="datetimerange" <el-date-picker v-else-if="getInputType(item.column) == 'datePicker'" v-model="item.value1" type="datetimerange"
range-separator="-" start-placeholder="开始时间" end-placeholder="结束时间" style="width: 340px;" @change="changeDateTimePicker($event, item, 'datetimerange')" value-format="x" format="YYYY/MM/DD HH:mm:ss" :disabled="item.disabled"/> range-separator="-" start-placeholder="开始时间" end-placeholder="结束时间" style="width: calc(100% - 20px);margin-right: 10px;" @change="changeDateTimePicker($event, item, 'datetimerange')" value-format="x" format="YYYY/MM/DD HH:mm:ss" :disabled="item.disabled"/>
</div> </div>
<!-- 删除条件按钮 --> <!-- 删除条件按钮 -->
<el-button type="danger" :icon="Minus" circle size="small" <el-button type="danger" :icon="Minus" circle size="small"
@ -178,7 +178,7 @@ const moreListPush = () => {
column: '', column: '',
action: "==", action: "==",
value: "", value: "",
time:'' value1 :""
} }
moreListData.value.filters.push(data) moreListData.value.filters.push(data)
} }
@ -187,13 +187,13 @@ const moreListPush = () => {
const resetSelect = (val) => { const resetSelect = (val) => {
if (getInputType(val.column) == 'datePicker' || getInputType(val.column) == 'date') { if (getInputType(val.column) == 'datePicker' || getInputType(val.column) == 'date') {
val.action = 'betweeen' val.action = 'betweeen'
val.value = ""
val.disabled = false val.disabled = false
}else{ }else{
val.action = '==' val.action = '=='
val.value = ""
val.disabled = false val.disabled = false
} }
val.value1 = ""
val.value = ""
} }
// //
const actionSelect = (val)=>{ const actionSelect = (val)=>{
@ -202,6 +202,12 @@ const actionSelect = (val)=>{
}else{ }else{
val.disabled = false val.disabled = false
} }
val.value1 = undefined
nextTick(()=>{
val.value1 =[]
val.value = ''
})
} }
// //
@ -209,11 +215,21 @@ const buttonBaseClick = (val) => {
if (val == 'search') { // if (val == 'search') { //
let data = [] let data = []
moreListData.value.filters.forEach(item => { moreListData.value.filters.forEach(item => {
let obj = { let obj = {}
column: item.column, if(item.value1&&item.value1.length>0){
action: item.action, obj = {
value: item.value, column: item.column,
action: item.action,
value:Array.isArray(item.value1)?item.value1.join(','):item.value1,
}
}else{
obj = {
column: item.column,
action: item.action,
value:item.value,
}
} }
data.push(obj) data.push(obj)
}) })
if (props.masterId){ if (props.masterId){
@ -229,6 +245,8 @@ const buttonBaseClick = (val) => {
} else if (val == 'searchReset') { // } else if (val == 'searchReset') { //
moreListData.value = {filters:[]} moreListData.value = {filters:[]}
moreListPush() moreListPush()
//
emit('searchFormClick', {})
} }
} }
@ -281,19 +299,19 @@ defineExpose({
} }
.rowInnerItem { .rowInnerItem {
margin-right: 20px; margin-right: 10px;
width: 220px; width: 20%;
.el-input__wrapper { .el-input__wrapper {
width: 220px; width:100%;
} }
} }
.rowInnerItem1{ .rowInnerItem1{
margin-right: 20px; margin-right: 10px;
width: 360px; width: 50%;
.el-input__wrapper { .el-input__wrapper {
width: 340px; width:100%;
} }
} }
.moreListBaseBts { .moreListBaseBts {

67
src/components/SearchTable/src/SearchTable.vue

@ -1,20 +1,30 @@
<template> <template>
<Dialog :title="dialogTitle" v-model="searchDialogVisible" :width="'80%'"> <Dialog :title="dialogTitle" v-model="searchDialogVisible" :width="'80%'">
<!-- 搜索工作栏 --> <!-- 搜索工作栏 -->
<Search :schema="searchSchema" @search="setSearchParamsRef" @reset="setSearchParamsRef" /> <!-- <Search :schema="searchSchema" @search="setSearchParamsRef" @reset="setSearchParamsRef" /> -->
<Table
ref="searchTableRef" <!-- 列表头部 -->
:columns="tableColumns" <TableHead
:data="tableObjectRef.tableList" :HeadButttondata="HeadButttondata"
:loading="tableObjectRef.loading" :routeName="routeName"
:pagination="{ @searchFormClick="searchFormClick"
total: tableObjectRef.total :allSchemas="allSchemasRef"
}"
v-model:pageSize="tableObjectRef.pageSize"
v-model:currentPage="tableObjectRef.currentPage"
v-model:sort="tableObjectRef.sort"
:selection="true"
/> />
<ContentWrap>
<Table
ref="searchTableRef"
:columns="tableColumns"
:data="tableObjectRef.tableList"
:loading="tableObjectRef.loading"
:pagination="{
total: tableObjectRef.total
}"
v-model:pageSize="tableObjectRef.pageSize"
v-model:currentPage="tableObjectRef.currentPage"
v-model:sort="tableObjectRef.sort"
:selection="true"
/>
</ContentWrap>
<template #footer> <template #footer>
<div class="flex items-center"> <div class="flex items-center">
<el-button @click="submitForm" type="primary" :disabled="formLoading"> </el-button> <el-button @click="submitForm" type="primary" :disabled="formLoading"> </el-button>
@ -24,14 +34,26 @@
</Dialog> </Dialog>
</template> </template>
<script setup lang="ts"> <script setup lang="ts">
import * as defaultButtons from '@/utils/disposition/defaultButtons'
// const { t } = useI18n() // // const { t } = useI18n() //
const message = useMessage() // const message = useMessage() //
const route = useRoute() //
const routeName = ref()
routeName.value = route.name
const searchDialogVisible = ref(false) // const searchDialogVisible = ref(false) //
const dialogTitle = ref('') // const dialogTitle = ref('') //
const formLoading = ref(false) // 12 const formLoading = ref(false) // 12
//
const HeadButttondata = [
defaultButtons.defaultFilterBtn(null), //
]
/** 打开弹窗 */ /** 打开弹窗 */
const getListRef = ref()
const setSearchParamsRef = ref() const setSearchParamsRef = ref()
const tableObjectRef = ref() const tableObjectRef = ref()
const getPage:any = ref() const getPage:any = ref()
@ -41,12 +63,14 @@ const formFieldRef = ref()
const searchFieldRef = ref() const searchFieldRef = ref()
const typeRef = ref() const typeRef = ref()
const rowRef = ref() const rowRef = ref()
const open = (titleName: any, allSchemas: any,getApiPage: any, formField: any, searchField: any, type: any, row: any ) => { const allSchemasRef = ref()
const open = (titleName: any, allSchemas: any,getApiPage: any, formField: any, searchField: any, type: any, row: any, searchCondition:any ) => {
searchDialogVisible.value = true searchDialogVisible.value = true
formFieldRef.value = formField formFieldRef.value = formField
searchFieldRef.value = searchField searchFieldRef.value = searchField
allSchemasRef.value = allSchemas
searchSchema.value = allSchemas.searchSchema searchSchema.value = allSchemas.searchSchema
tableColumns.value = allSchemas.tableColumns tableColumns.value = allSchemas.tableColumns.filter(item => (item.field !== 'action'))
getPage.value = getApiPage getPage.value = getApiPage
typeRef.value = type typeRef.value = type
rowRef.value = row rowRef.value = row
@ -56,12 +80,23 @@ const open = (titleName: any, allSchemas: any,getApiPage: any, formField: any, s
getListApi: getPage.value // getListApi: getPage.value //
}) })
tableObjectRef.value = tableObject tableObjectRef.value = tableObject
if (searchCondition) tableObjectRef.value.params = searchCondition
// //
const { getList, setSearchParams } = tableMethods const { getList, setSearchParams } = tableMethods
setSearchParamsRef.value = setSearchParams setSearchParamsRef.value = setSearchParams
getListRef.value = getList
getList() getList()
} }
//
const searchFormClick = (searchData) => {
tableObjectRef.value.params = {
isSearch: true,
filters: searchData.filters
}
getListRef.value() //
}
defineExpose({ open }) // open defineExpose({ open }) // open
// Table ref // Table ref

9
src/components/TableForm/src/TableForm.vue

@ -57,16 +57,16 @@
<!-- 字符串输入框 --> <!-- 字符串输入框 -->
<el-form-item <el-form-item
v-if="!headerItem?.tableForm?.type || headerItem?.tableForm?.type == 'InputString'" v-if="!headerItem?.tableForm?.type || headerItem?.tableForm?.type == 'InputString'"
:prop="headerItem.field"> :prop="headerItem.field" style="display: flex;align-items: center;">
<el-input <el-input
v-model="row[headerItem.field]" v-model="row[headerItem.field]"
clearable clearable
:type="headerItem?.tableForm?.inputType" :type="headerItem?.tableForm?.inputType"
:placeholder="headerItem?.tableForm?.placeholder || '请输入' + headerItem.label" :placeholder="headerItem?.tableForm?.placeholder || '请输入' + headerItem.label"
:disabled="itemIsDisabled(headerItem, row)" :disabled="headerItem?.tableForm?.disabled ? true: headerItem?.tableForm?.isInpuFocusShow ? true : false"
style="width: 100%;" style="flex:1"
@click="inpuFocus(headerItem,row,index)"
/> />
<el-button v-if="headerItem?.tableForm?.isInpuFocusShow" @click="inpuFocus(headerItem,row,index)"><Icon icon="ep:search" size="14"/></el-button>
</el-form-item> </el-form-item>
<!-- 金额输入框 --> <!-- 金额输入框 -->
<el-form-item <el-form-item
@ -91,6 +91,7 @@
v-model="row[headerItem.field]" v-model="row[headerItem.field]"
:max="headerItem?.tableForm?.max" :max="headerItem?.tableForm?.max"
:min="headerItem?.tableForm?.min" :min="headerItem?.tableForm?.min"
:precision="headerItem?.tableForm?.precision"
:disabled="itemIsDisabled(headerItem, row)" :disabled="itemIsDisabled(headerItem, row)"
/> />
</el-form-item> </el-form-item>

49
src/components/TableHead/src/TableHead.vue

@ -8,27 +8,19 @@
/> />
</div> </div>
<div class="tableNavRightBtns"> <div class="tableNavRightBtns">
<!-- 快速搜索 -->
<!-- <SearchNormal
ref="quicklySearchDom_Ref"
:vueName="vueName"
:quicklySearchOption="quicklySearchOption"
@searchNormalClick="quicklySearchClick"
@searchNormalClear="quicklySearchClear"
style="margin-right: 15px;"
></SearchNormal> -->
<!-- 右侧按钮 --> <!-- 右侧按钮 -->
<ButtonBase :Butttondata="buttonsRight" @button-base-click="buttonBaseClick" /> <ButtonBase :Butttondata="buttonsRight" @button-base-click="buttonBaseClick" @updata-table-columns="updataTableColumns"
:allSchemas="allSchemas" ref="rowDropRef"/>
</div> </div>
</div> </div>
<slot></slot> <slot></slot>
</div> </div>
<!-- 字段设置弹窗 --> <!-- 字段设置弹窗 -->
<rowDrop <!-- <rowDrop
ref="rowDropRef" ref="rowDropRef"
@updata-table-columns="updataTableColumns" @updata-table-columns="updataTableColumns"
:allSchemas="allSchemas" :allSchemas="allSchemas"
/> /> -->
<!-- 高级筛选 --> <!-- 高级筛选 -->
<SearchHigh <SearchHigh
ref="searchHigh_Ref" ref="searchHigh_Ref"
@ -83,6 +75,8 @@ import rowDrop from "@/components/rowDrop/index.vue"
// const defaultButtons = inject('global').defaultButtons // const defaultButtons = inject('global').defaultButtons
// //
const buttonsLeftOrRight = () => { const buttonsLeftOrRight = () => {
buttonsRight.value = []
buttonsLeft.value = []
// () // ()
// let _primarySearchOption = primarySearch[props.vueName] // let _primarySearchOption = primarySearch[props.vueName]
// let _highSearchOption = highSearch[props.vueName] // let _highSearchOption = highSearch[props.vueName]
@ -100,12 +94,17 @@ import rowDrop from "@/components/rowDrop/index.vue"
} }
buttonsLeftOrRight() buttonsLeftOrRight()
watch(
() => props.HeadButttondata,
() => {
buttonsLeftOrRight()
}
)
// //
const emit = defineEmits([ const emit = defineEmits([
'buttonBaseClick', 'buttonBaseClick',
'quicklySearchClick',
'quicklySearchClear',
'updataTableColumns', 'updataTableColumns',
'searchFormClick' 'searchFormClick'
]) ])
@ -117,7 +116,7 @@ import rowDrop from "@/components/rowDrop/index.vue"
const buttonBaseClick = (val, item) => { const buttonBaseClick = (val, item) => {
// //
if (val == 'set') { if (val == 'set') {
rowDropRef.value.popoverVisible = true rowDropRef.value.popoverVisible = !rowDropRef.value.popoverVisible
} else if (val == 'filtrate') { } else if (val == 'filtrate') {
searchHigh_Ref.value.popoverVisible = true searchHigh_Ref.value.popoverVisible = true
} else { } else {
@ -125,16 +124,6 @@ import rowDrop from "@/components/rowDrop/index.vue"
} }
} }
//
const quicklySearchClick = (val, option) => {
emit('quicklySearchClick', val, option)
}
//
const quicklySearchClear = (val, option) => {
emit('quicklySearchClear', val, option)
}
const quicklySearchDom_Ref = ref() const quicklySearchDom_Ref = ref()
// //
@ -158,13 +147,15 @@ import rowDrop from "@/components/rowDrop/index.vue"
display: flex; display: flex;
justify-content: space-between; justify-content: space-between;
} }
.tableNavLeftBtns{
display: flex;
margin-left: -5px;
}
.tableNavRightBtns{ .tableNavRightBtns{
display: flex; display: flex;
margin-left: 10px; margin-left: 10px;
.currenButton .el-button { margin-right: -5px;
margin-left: 10px !important;
}
} }
} }
</style> </style>

119
src/components/XButton/src/ButtonBase.vue

@ -1,38 +1,95 @@
<template> <template>
<el-button <div v-for="(item, index) in Butttondata" :key="index" class="btn-div">
v-for="(item, index) in Butttondata" :key="index" <el-button
v-show="!item.hide" v-show="!item.hide"
:type="item.type" :type="item.type"
:color="item.color" :color="item.color"
:link = "item.link ? item.link : false" :link="item.link ? item.link : false"
v-hasPermi="[item.hasPermi] || []" v-hasPermi="[item.hasPermi] || []"
@click="buttonBaseClick(item.name,item,$event)" v-if="item.name != 'set'"
> @click="buttonBaseClick(item.name, item, $event)"
<Icon v-if="item.icon" :icon="item.icon" class="mr-1px" /> >
{{ item.label }} <Icon v-if="item.icon" :icon="item.icon" class="mr-1px" />
</el-button> {{ item.label }}
</el-button>
<!-- 设置按钮 -->
<el-popover
:visible="popoverVisible"
placement="bottom"
:width="300"
trigger="click"
v-if="item.name == 'set'&&!item.hide"
>
<rowDrop
ref="rowDropRef"
@updata-table-columns="updataTableColumns"
:allSchemas="allSchemas"
@closeRowDrop="closeRowDrop"
@updataTableColumns="updataTableColumns"
/>
<template #reference>
<el-button
v-show="!item.hide"
:type="item.type"
:color="item.color"
:link="item.link ? item.link : false"
v-hasPermi="[item.hasPermi] || []"
@click="buttonBaseClick(item.name, item, $event)"
>
<Icon v-if="item.icon" :icon="item.icon" class="mr-1px" />
{{ item.label }}
</el-button>
</template>
</el-popover>
</div>
<slot></slot> <slot></slot>
</template> </template>
<script setup> <script setup>
import { Plus } from '@element-plus/icons-vue' import { Plus } from '@element-plus/icons-vue'
import { clearButtonBlurHandle } from '@/utils/index' import { clearButtonBlurHandle } from '@/utils/index'
const props = defineProps({ import rowDrop from '@/components/rowDrop/index.vue'
Butttondata: { const props = defineProps({
type: Array, Butttondata: {
default: () => { type: Array,
return [] default: () => {
} return []
}, }
}) },
allSchemas: {
type: Object,
default: null
}
})
//
const emit = defineEmits(['buttonBaseClick', 'updataTableColumns'])
// const buttonBaseClick = (val, item, $event) => {
const emit = defineEmits([ clearButtonBlurHandle($event) //el-button
'buttonBaseClick', emit('buttonBaseClick', val, item, $event)
]) }
const popoverVisible = ref(false)
//
const closeRowDrop = () => {
popoverVisible.value = false
}
defineExpose({
popoverVisible
})
//
const updataTableColumns = (val) => {
emit('updataTableColumns', val)
}
</script>
<style scoped lang="scss">
.btn-div{
display: inline;
const buttonBaseClick = (val, item, $event) => { ::v-deep(.el-button){
clearButtonBlurHandle($event)//el-button margin: 0px 5px;
emit('buttonBaseClick', val, item, $event) }
::v-deep(.el-button.is-link){
margin: 0px;
} }
}
</script> </style>

69
src/components/rowDrop/index.vue

@ -1,20 +1,22 @@
<template> <template>
<Dialog title="字段设置" width="270" v-model="popoverVisible" :scroll="true" :maxHeight="500"> <!-- <Dialog title="字段设置" width="270" v-model="popoverVisible" :scroll="true" :maxHeight="500"> -->
<div class="test_wrapper" @dragover="dragover($event)"> <div class="test_wrapper" @dragover="dragover($event)">
<el-checkbox :indeterminate="isIndeterminate" v-model="checkAll" @change="handlecheckallchange">全部</el-checkbox> <el-checkbox :indeterminate="isIndeterminate" v-model="checkAll" @change="handlecheckallchange">全部</el-checkbox>
<el-checkbox-group v-model="checkedDataList" @change="handlecheckedchange"> <el-checkbox-group v-model="checkedDataList" @change="handlecheckedchange">
<draggable :list="allData" :force-fallback="true" chosen-class="chosen" animation="300" @end="dragend" @update="dragenter" > <draggable :list="allData" :force-fallback="true" chosen-class="chosen" animation="300" @end="dragend" @update="dragenter" >
<template #item="{element}"> <template #item="{element}">
<div><el-checkbox :key="element" :label="element">{{element}}</el-checkbox></div> <div><el-checkbox :key="element" :label="element">{{element}}</el-checkbox></div>
</template> </template>
</draggable> </draggable>
</el-checkbox-group> </el-checkbox-group>
</div> </div>
<template #footer> <div class="footer">
<!-- <template #footer> -->
<el-button size="small" @click="reset">重置</el-button> <el-button size="small" @click="reset">重置</el-button>
<el-button size="small" @click="closeRowDrop">关闭</el-button> <el-button size="small" @click="closeRowDrop">关闭</el-button>
</template> <!-- </template> -->
</Dialog> </div>
<!-- </Dialog> -->
</template> </template>
<script setup lang="ts"> <script setup lang="ts">
import { ElMessageBox } from 'element-plus' import { ElMessageBox } from 'element-plus'
@ -68,7 +70,7 @@ const reset = () => {
// //
const closeRowDrop = () => { const closeRowDrop = () => {
popoverVisible.value = false emit('closeRowDrop')
} }
// //
@ -153,7 +155,20 @@ const initSelectSta = () => {
}) })
_showTableColumns.push(_myTableColumns[_myTableColumns.length-1]) _showTableColumns.push(_myTableColumns[_myTableColumns.length-1])
if(checkedDataList.value.length>0){
if(allData.value?.length != checkedDataList.value.length){
isIndeterminate.value = true
}else{
isIndeterminate.value = false
checkAll.value = true
}
}else{
isIndeterminate.value = false
checkAll.value = false
}
updataTableColumns(_showTableColumns) updataTableColumns(_showTableColumns)
} else { // } else { //
checkedDataList.value = [] checkedDataList.value = []
allData.value = [] allData.value = []
@ -182,7 +197,8 @@ const updataTableColumns = (val) => {
// //
const emit = defineEmits([ const emit = defineEmits([
'updataTableColumns' 'updataTableColumns',
'closeRowDrop'
]) ])
/** 初始化 **/ /** 初始化 **/
@ -196,10 +212,25 @@ defineExpose({
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>
// .buttonsBox { .test_wrapper{
// text-align: center; max-height: calc(100vh - 350px);
// margin: 0; overflow-y: auto;
// padding: 15px; }
// border-top: #eee solid 1px; .footer{
// } margin-top: 10px;
}
.el-checkbox-group ::v-deep(.el-checkbox .el-checkbox__inner){
background: url(../../assets/imgs/Eyes-closed.png) no-repeat 0px 0px;
background-size: 16px;
width: 16px;
height: 16px;
border: none;
}
.el-checkbox-group ::v-deep(.el-checkbox .is-checked .el-checkbox__inner){
background: url(../../assets/imgs/eye.png) no-repeat 0px 0px;
background-size: 16px;
width: 16px;
height: 16px;
border: none;
}
</style> </style>

228
src/views/spc/itembasic/index.vue

@ -0,0 +1,228 @@
<template>
<ContentWrap>
<!-- 搜索工作栏 -->
<Search :schema="Itembasic.allSchemas.searchSchema" @search="setSearchParams" @reset="setSearchParams" />
</ContentWrap>
<!-- 列表头部 -->
<TableHead
:HeadButttondata="HeadButttondata"
@button-base-click="buttonBaseClick"
:routeName="routeName"
@updataTableColumns="updataTableColumns"
@searchFormClick="searchFormClick"
:allSchemas="Itembasic.allSchemas"
/>
<!-- 列表 -->
<ContentWrap>
<Table
:columns="tableColumns"
:data="tableObject.tableList"
:loading="tableObject.loading"
:pagination="{
total: tableObject.total
}"
v-model:pageSize="tableObject.pageSize"
v-model:currentPage="tableObject.currentPage"
v-model:sort="tableObject.sort"
>
<template #code="{row}">
<el-button type="primary" link @click="openDetail(row, '代码', row.code)">
<span>{{ row.code }}</span>
</el-button>
</template>
<template #action="{ row }">
<ButtonBase :Butttondata="butttondata" @button-base-click="buttonTableClick($event,row)" />
</template>
</Table>
</ContentWrap>
<!-- 表单弹窗添加/修改 -->
<BasicForm
ref="basicFormRef"
@success="getList"
:rules="ItembasicRules"
:formAllSchemas="Itembasic.allSchemas"
:searchTableParams="searchTableParams"
:apiUpdate="ItembasicApi.updateItembasic"
:apiCreate="ItembasicApi.createItembasic"
@searchTableSuccess="searchTableSuccess"
:isBusiness="false"
/>
<!-- 详情 -->
<Detail ref="detailRef" :isBasic="true" :allSchemas="Itembasic.allSchemas" />
<!-- 导入 -->
<ImportForm ref="importFormRef" url="/spc/itembasic/import" :importTemplateData="importTemplateData" @success="importSuccess" />
</template>
<script setup lang="ts">
import download from '@/utils/download'
import { Itembasic,ItembasicRules } from './itembasic.data'
import * as ItembasicApi from '@/api/spc/itembasic'
import * as defaultButtons from '@/utils/disposition/defaultButtons'
defineOptions({ name: 'Itembasic' })
const message = useMessage() //
const { t } = useI18n() //
const route = useRoute() //
const routeName = ref()
routeName.value = route.name
const tableColumns = ref(Itembasic.allSchemas.tableColumns)
//
const updataTableColumns = (val) => {
tableColumns.value = val
}
//
const searchTableParams = ref([
//{
// formField: 'productItemCode',
// searchTableTitle: '',
// searchTableAllSchemas: Itembasic.allSchemas,
// searchTablePage: ItembasicApi.getItembasicPage
//}
])
const { tableObject, tableMethods } = useTable({
getListApi: ItembasicApi.getItembasicPage //
})
//
const { getList, setSearchParams } = tableMethods
//
const HeadButttondata = [
defaultButtons.defaultAddBtn({hasPermi:'wms:itembasic:create'}), //
defaultButtons.defaultImportBtn({hasPermi:'wms:itembasic:import'}), //
defaultButtons.defaultExportBtn({hasPermi:'wms:itembasic:export'}), //
defaultButtons.defaultFreshBtn(null), //
defaultButtons.defaultFilterBtn(null), //
defaultButtons.defaultSetBtn(null), //
// {
// label: '',
// name: 'zdy',
// hide: false,
// type: 'primary',
// icon: 'Select',
// color: ''
// },
]
//
const buttonBaseClick = (val, item) => {
if (val == 'add') { //
openForm('create')
} else if (val == 'import') { //
handleImport()
} else if (val == 'export') { //
handleExport()
} else if (val == 'refresh') { //
getList()
} else if (val == 'filtrate') { //
} else { //
console.log('其他按钮', item)
}
}
// -
const butttondata = [
defaultButtons.mainListEditBtn({hasPermi:'wms:itembasic:update'}), //
defaultButtons.mainListDeleteBtn({hasPermi:'wms:itembasic:delete'}), //
]
// -
const buttonTableClick = async (val, row) => {
if (val == 'edit') { //
openForm('update', row)
} else if (val == 'delete') { //
handleDelete(row.id)
}
}
/** 添加/修改操作 */
const basicFormRef = ref()
const openForm = (type: string, row?: any) => {
basicFormRef.value.open(type, row)
}
//
const searchTableSuccess = (formField, searchField, val, formRef) => {
nextTick(() => {
const setV = {}
setV[formField] = val[0][searchField]
formRef.setValues(setV)
})
}
/** 详情操作 */
const detailRef = ref()
const openDetail = (row: any, titleName: any, titleValue: any) => {
detailRef.value.openDetail(row, titleName, titleValue, 'basicItembasic')
}
/** 删除按钮操作 */
const handleDelete = async (id: number) => {
try {
//
await message.delConfirm()
//
await ItembasicApi.deleteItembasic(id)
message.success(t('common.delSuccess'))
//
await getList()
} catch {}
}
/** 导出按钮操作 */
const exportLoading = ref(false) //
const handleExport = async () => {
try {
//
await message.exportConfirm()
//
exportLoading.value = true
const data = await ItembasicApi.exportItembasic(setSearchParams)
download.excel(data, '物品基本信息.xls')
} catch {
} finally {
exportLoading.value = false
}
}
/** 导入 */
const importFormRef = ref()
const handleImport = () => {
importFormRef.value.open()
}
//
const importTemplateData = reactive({
templateUrl: '',
templateTitle: '物品基本信息导入模版.xls'
})
//
const importSuccess = () => {
getList()
}
//
const searchFormClick = (searchData) => {
tableObject.params = {
isSearch: true,
filters: searchData.filters
}
getList() //
}
/** 初始化 **/
onMounted(async () => {
getList()
importTemplateData.templateUrl = await ItembasicApi.importTemplate()
})
</script>

355
src/views/spc/itembasic/itembasic.data.ts

@ -0,0 +1,355 @@
import type { CrudSchema } from '@/hooks/web/useCrudSchemas'
import { dateFormatter } from '@/utils/formatTime'
// 表单校验
export const ItembasicRules = reactive({
code: [required],
status: [required],
uom: [required],
isStdPack: [required],
enableBuy: [required],
enableMake: [required],
enableOutsourcing: [required],
isRecycled: [required],
isPhantom: [required],
abcClass: [required],
type: [required],
validityDays: [required],
available: [required]
})
export const Itembasic = useCrudSchemas(reactive<CrudSchema[]>([
{
label: '代码',
field: 'code',
sort: 'custom',
isSearch: true
},
{
label: '名称',
field: 'name',
sort: 'custom',
isSearch: true
},
{
label: '描述1',
field: 'desc1',
sort: 'custom',
isSearch: true
},
{
label: '描述2',
field: 'desc2',
sort: 'custom',
isSearch: true
},
{
label: '状态',
field: 'status',
sort: 'custom',
dictType: DICT_TYPE.ITEM_STATUS,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '计量单位',
field: 'uom',
sort: 'custom',
dictType: DICT_TYPE.UOM,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '替代计量单位',
field: 'altUom',
sort: 'custom',
dictType: DICT_TYPE.UOM,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '是否标包',
field: 'isStdPack',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '可采购',
field: 'enableBuy',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '可制造',
field: 'enableMake',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '可委外加工',
field: 'enableOutsourcing',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '回收件',
field: 'isRecycled',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '虚零件',
field: 'isPhantom',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: 'ABC类',
field: 'abcClass',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '类型',
field: 'type',
sort: 'custom',
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '种类',
field: 'category',
sort: 'custom',
dictType: DICT_TYPE.ITEM_CATEGORY,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '分组',
field: 'itemGroup',
sort: 'custom',
dictType: DICT_TYPE.ITEM_GROUP,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '颜色',
field: 'color',
sort: 'custom',
dictType: DICT_TYPE.ITEM_COLOR,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '配置',
field: 'configuration',
sort: 'custom',
dictType: DICT_TYPE.ITEM_CONFIGURATION,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '项目',
field: 'project',
sort: 'custom',
isSearch: true
},
{
label: '质量等级',
field: 'eqLevel',
sort: 'custom',
dictType: DICT_TYPE.EQ_LEVEL,
dictClass: 'string', // 默认都是字符串类型其他暂不考虑
isSearch: true,
form: {
component: 'SelectV2'
}
},
{
label: '有效天数',
field: 'validityDays',
sort: 'custom',
isSearch: true,
form: {
component: 'InputNumber',
value: 0
}
},
{
label: '用户组代码',
field: 'userGroupCode',
sort: 'custom',
isSearch: true
},
{
label: '是否可用',
field: 'available',
sort: 'custom',
isSearch: true
},
{
label: '生效时间',
field: 'activeTime',
sort: 'custom',
formatter: dateFormatter,
isSearch: true,
search: {
component: 'DatePicker',
componentProps: {
valueFormat: 'YYYY-MM-DD HH:mm:ss',
type: 'daterange',
defaultTime: [new Date('1 00:00:00'), new Date('1 23:59:59')]
}
},
form: {
component: 'DatePicker',
componentProps: {
type: 'datetime',
valueFormat: 'x'
}
}
},
{
label: '失效时间',
field: 'expireTime',
sort: 'custom',
formatter: dateFormatter,
isSearch: true,
search: {
component: 'DatePicker',
componentProps: {
valueFormat: 'YYYY-MM-DD HH:mm:ss',
type: 'daterange',
defaultTime: [new Date('1 00:00:00'), new Date('1 23:59:59')]
}
},
form: {
component: 'DatePicker',
componentProps: {
type: 'datetime',
valueFormat: 'x'
}
}
},
{
label: '备注',
field: 'remark',
sort: 'custom',
isSearch: true
},
{
label: '创建时间',
field: 'createTime',
sort: 'custom',
formatter: dateFormatter,
isSearch: true,
search: {
component: 'DatePicker',
componentProps: {
valueFormat: 'YYYY-MM-DD HH:mm:ss',
type: 'daterange',
defaultTime: [new Date('1 00:00:00'), new Date('1 23:59:59')]
}
},
isForm: false
},
{
label: '删除时间',
field: 'deletionTime',
sort: 'custom',
formatter: dateFormatter,
isSearch: true,
search: {
component: 'DatePicker',
componentProps: {
valueFormat: 'YYYY-MM-DD HH:mm:ss',
type: 'daterange',
defaultTime: [new Date('1 00:00:00'), new Date('1 23:59:59')]
}
},
form: {
component: 'DatePicker',
componentProps: {
type: 'datetime',
valueFormat: 'x'
}
}
},
{
label: '删除者ID',
field: 'deleterId',
sort: 'custom',
isSearch: true
},
{
label: '扩展属性',
field: 'extraProperties',
sort: 'custom',
isSearch: true
},
{
label: '并发乐观锁',
field: 'concurrencyStamp',
sort: 'custom',
isSearch: true
},
{
label: '地点ID',
field: 'siteId',
sort: 'custom',
isSearch: true
},
{
label: '操作',
field: 'action',
isForm: false,
table: {
width: 150,
fixed: 'right'
}
}
]))
Loading…
Cancel
Save