From b9048006a1dbbb9863eebb2a3e36d5cbfbb578d1 Mon Sep 17 00:00:00 2001 From: Leo_Ding <2405260743@qq.com> Date: Mon, 30 Jun 2025 11:06:31 +0800 Subject: [PATCH 1/2] =?UTF-8?q?=E4=BA=A7=E5=93=81=E4=B8=AD=E5=BF=83?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/locales/lang/zh-CN/menu.js | 1 + src/router/routes/product.js | 12 + src/views/product/components/EditDialog.vue | 359 +++++---------- .../productType/components/EditDialog.vue | 426 ++++++++++++++++++ src/views/productType/index.vue | 263 +++++++++++ .../contactUs/components/EditDialog.vue | 2 +- 6 files changed, 824 insertions(+), 239 deletions(-) create mode 100644 src/views/productType/components/EditDialog.vue create mode 100644 src/views/productType/index.vue diff --git a/src/locales/lang/zh-CN/menu.js b/src/locales/lang/zh-CN/menu.js index 2c1a183..4271195 100644 --- a/src/locales/lang/zh-CN/menu.js +++ b/src/locales/lang/zh-CN/menu.js @@ -51,4 +51,5 @@ export default { friendlyLinks:'友情链接', websiteStatement:'网站声明', contactUs:'联系我们', + productType:'产品分类' } diff --git a/src/router/routes/product.js b/src/router/routes/product.js index 1762640..1c8b7a0 100644 --- a/src/router/routes/product.js +++ b/src/router/routes/product.js @@ -13,4 +13,16 @@ export default [ permission: '*', }, }, + { + path: 'productType', + name: 'productType', + component: 'productType/index.vue', + meta: { + icon: ShoppingOutlined, + title: '产品分类', + isMenu: true, + keepAlive: true, + permission: '*', + }, + }, ] diff --git a/src/views/product/components/EditDialog.vue b/src/views/product/components/EditDialog.vue index ba87c93..fc443e9 100644 --- a/src/views/product/components/EditDialog.vue +++ b/src/views/product/components/EditDialog.vue @@ -1,137 +1,91 @@ @@ -221,7 +113,7 @@ import { cloneDeep } from 'lodash-es' import { ref, onBeforeMount } from 'vue' import { config } from '@/config' import apis from '@/apis' -import { useForm, useModal,useSpining } from '@/hooks' +import { useForm, useModal, useSpining } from '@/hooks' import { message } from 'ant-design-vue' import { useI18n } from 'vue-i18n' @@ -239,7 +131,7 @@ const emit = defineEmits(['ok']) const { t } = useI18n() // 解构出t方法 const { modal, showModal, hideModal, showLoading, hideLoading } = useModal() const { formRecord, formData, formRef, formRules, resetForm } = useForm() -const { spining,showSpining,hideSpining} = useSpining() +const { spining, showSpining, hideSpining } = useSpining() const cancelText = ref(t('button.cancel')) const okText = ref(t('button.confirm')) const rolesValue = ref([]) @@ -251,6 +143,7 @@ const mainImage = ref([]) const contentImage = ref([]) const childOpen = ref(false) const formArea = ref({ name: '', status: 'enabled' }) +const activeKey=ref('1') formRules.value = { title: { required: true, message: '请输入产品类别名称' }, code: { required: true, message: '请输入产品名称' }, @@ -264,6 +157,7 @@ formRules.value = { contentImage: { required: false, message: '请上传产品内容图片' }, sequence: [{ required: true, message: '请输入产品排序' }], status: [{ required: true, message: '请选择状态', trigger: 'change' }], + } const areaFormRules = { categoryIDName: [{ required: true, message: '请输入产品类别' }], @@ -283,7 +177,7 @@ const initDataBatch = async (configs) => { const mapped = data.map(item => { return { value: item.value, - children:item.children, + children: item.children, [resultKey]: item.label,// e.g. item['label'] } }) @@ -328,26 +222,24 @@ function handleCreate() { compose: '', target: '', feature: [{ - label:'功能特点', - data:[{ - msg:[''], - }] - }], + label: '功能特点', + data: [] + }], standard: [{ label: '', - val: '' , - fu_hoao: '' , - prx: '' , + val: '', + fu_hoao: '', + prx: '', }], images: [ ...(Array.isArray(formData.value.mainImage) - ? formData.value.mainImage - : [formData.value.mainImage] + ? formData.value.mainImage + : [formData.value.mainImage] ).filter(Boolean).map(item => String(item)), ...(Array.isArray(formData.value.contentImage) - ? formData.value.contentImage - : [formData.value.contentImage] + ? formData.value.contentImage + : [formData.value.contentImage] ).filter(Boolean).map(item => String(item)) ], @@ -406,26 +298,24 @@ async function handleEdit(record = {}) { } formData.value = { ...data, - standard:data.standard|| [{ + standard: data.standard || [{ label: '', - val: '' , - fu_hoao: '' , - prx: '' , + val: '', + fu_hoao: '', + prx: '', }], - feature:data.feature|| [{ - label:'功能特点', - data:[{ - msg:[''], - }] + feature: data.feature || [{ + label: '功能特点', + data: [] }], - // images:data.images || [''], - mainImage: data.images?[config('http.apiBasic')+data.images[0]]:[''], - contentImage:data.images?[config('http.apiBasic')+data.images[1]]:[''], + // images:data.images || [''], + mainImage: data.images ? [config('http.apiBasic') + data.images[0]] : [''], + contentImage: data.images ? [config('http.apiBasic') + data.images[1]] : [''], } // imgUrl.value = config('http.apiBasic') + data.img - mainImage.value = config('http.apiBasic') + data.images?.[0] , - contentImage.value = config('http.apiBasic') + data.images?.[1] , - console.log('编辑产品数据:',formData.value); + mainImage.value = config('http.apiBasic') + data.images?.[0], + contentImage.value = config('http.apiBasic') + data.images?.[1], + console.log('编辑产品数据:', formData.value); } /** @@ -438,28 +328,23 @@ function handleOk() { showLoading() const params = { ...values, - standard:formData.value.standard || + standard: formData.value.standard || [{ - label: '', - val: '' , - fu_hoao: '' , - prx: '' , + label: '', + val: '', + fu_hoao: '', + prx: '', }], - feature:formData.value.feature|| [{ - label:'功能特点', - data:[{ - msg:[''], - }] - }], + feature: formData.value.feature, images: [ ...(Array.isArray(formData.value.mainImage) - ? formData.value.mainImage - : [formData.value.mainImage] + ? formData.value.mainImage + : [formData.value.mainImage] ).filter(Boolean).map(item => spliceUrl(item)), ...(Array.isArray(formData.value.contentImage) - ? formData.value.contentImage - : [formData.value.contentImage] + ? formData.value.contentImage + : [formData.value.contentImage] ).filter(Boolean).map(item => spliceUrl(item)) ], } @@ -538,6 +423,4 @@ function removeFeature(index) { } - + diff --git a/src/views/productType/components/EditDialog.vue b/src/views/productType/components/EditDialog.vue new file mode 100644 index 0000000..fc443e9 --- /dev/null +++ b/src/views/productType/components/EditDialog.vue @@ -0,0 +1,426 @@ + + + + + diff --git a/src/views/productType/index.vue b/src/views/productType/index.vue new file mode 100644 index 0000000..80b11c2 --- /dev/null +++ b/src/views/productType/index.vue @@ -0,0 +1,263 @@ + + + + + diff --git a/src/views/websiteRelated/contactUs/components/EditDialog.vue b/src/views/websiteRelated/contactUs/components/EditDialog.vue index aea6b2c..46f2abe 100644 --- a/src/views/websiteRelated/contactUs/components/EditDialog.vue +++ b/src/views/websiteRelated/contactUs/components/EditDialog.vue @@ -67,7 +67,7 @@ import { useForm, useModal } from '@/hooks' import { message } from 'ant-design-vue' import { useI18n } from 'vue-i18n' import dayjs from 'dayjs' -import { createMenu, getMenu, updateMenu } from '@/apis/modules/webSite' + const emit = defineEmits(['ok']) const { t } = useI18n() // 解构出t方法 const { modal, showModal, hideModal, showLoading, hideLoading } = useModal() From a880d98f888aed2c253f69c7ff06116e22da49ac Mon Sep 17 00:00:00 2001 From: Leo_Ding <2405260743@qq.com> Date: Mon, 30 Jun 2025 18:35:16 +0800 Subject: [PATCH 2/2] =?UTF-8?q?=E4=BA=A7=E5=93=81=E4=B8=AD=E5=BF=83?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/apis/modules/categorys.js | 14 + src/views/imgMgt/homeBanner/index.vue | 3 +- src/views/imgMgt/researchHonor/index.vue | 3 +- src/views/product/components/Department.vue | 169 --------- .../components/EditDepartmentDialog.vue | 131 ------- src/views/product/components/EditDialog.vue | 135 ++++--- src/views/product/index.vue | 62 ++-- .../productType/components/EditDialog.vue | 348 ++---------------- src/views/productType/index.vue | 135 +------ 9 files changed, 155 insertions(+), 845 deletions(-) create mode 100644 src/apis/modules/categorys.js delete mode 100644 src/views/product/components/Department.vue delete mode 100644 src/views/product/components/EditDepartmentDialog.vue diff --git a/src/apis/modules/categorys.js b/src/apis/modules/categorys.js new file mode 100644 index 0000000..ca85edf --- /dev/null +++ b/src/apis/modules/categorys.js @@ -0,0 +1,14 @@ +/** + * 海邻动态接口 + */ +import request from '@/utils/request' +// 获取公司动态列表 +export const getDataList = (params) => request.basic.get('/api/v1/products/categorys', params) +// 获取单条数据 +export const getItem = (id) => request.basic.get(`/api/v1/products/categorys/${id}`) +// 添加动态 +export const createProductsItem = (params) => request.basic.post('/api/v1/products/categorys', params) +// 更新动态 +export const updateItem = (id, params) => request.basic.put(`/api/v1/products/categorys/${id}`, params) +// 删除动态 +export const delProductsItem = (id) => request.basic.delete(`/api/v1/products/categorys/${id}`) diff --git a/src/views/imgMgt/homeBanner/index.vue b/src/views/imgMgt/homeBanner/index.vue index be89eb1..5c7fdc9 100644 --- a/src/views/imgMgt/homeBanner/index.vue +++ b/src/views/imgMgt/homeBanner/index.vue @@ -121,6 +121,7 @@ async function getPageList() { .getDataList({ pageSize, page: current, + type:120, ...searchFormData.value, }) .catch(() => { @@ -129,7 +130,7 @@ async function getPageList() { hideLoading() if (config('http.code.success') === success) { //筛选type的值80对应about - listData.value = data.filter(item => item.type === 120) + listData.value = data paginationState.total = total } } catch (error) { diff --git a/src/views/imgMgt/researchHonor/index.vue b/src/views/imgMgt/researchHonor/index.vue index 0861c0e..d42784f 100644 --- a/src/views/imgMgt/researchHonor/index.vue +++ b/src/views/imgMgt/researchHonor/index.vue @@ -120,6 +120,7 @@ async function getPageList() { .getDataList({ pageSize, page: current, + type:110, ...searchFormData.value, }) .catch(() => { @@ -128,7 +129,7 @@ async function getPageList() { hideLoading() if (config('http.code.success') === success) { //筛选type的值110对应researchHonor - listData.value = data.filter(item => item.type===110) + // listData.value = data.filter(item => item.type===110) paginationState.total = total } } catch (error) { diff --git a/src/views/product/components/Department.vue b/src/views/product/components/Department.vue deleted file mode 100644 index efaefad..0000000 --- a/src/views/product/components/Department.vue +++ /dev/null @@ -1,169 +0,0 @@ - - - - - diff --git a/src/views/product/components/EditDepartmentDialog.vue b/src/views/product/components/EditDepartmentDialog.vue deleted file mode 100644 index e5a271f..0000000 --- a/src/views/product/components/EditDepartmentDialog.vue +++ /dev/null @@ -1,131 +0,0 @@ - - - - - diff --git a/src/views/product/components/EditDialog.vue b/src/views/product/components/EditDialog.vue index 58e292d..991c8da 100644 --- a/src/views/product/components/EditDialog.vue +++ b/src/views/product/components/EditDialog.vue @@ -13,13 +13,10 @@ - -
- - {{ - item.categoryIDName }} - -
+ +
@@ -34,7 +31,7 @@ - + - + @@ -140,15 +137,14 @@ const imgUrl = ref('') const categoryList = ref([]) const targetList = ref([]) const images = ref([]) -const mainImage = ref([]) const contentImage = ref([]) const childOpen = ref(false) -const formArea = ref({ name: '', status: 'enabled' }) -const activeKey=ref('1') + +const activeKey = ref('1') formRules.value = { title: { required: true, message: '请输入产品类别名称' }, code: { required: true, message: '请输入产品名称' }, - categoryID: { required: true, message: '请选择产品类别', trigger: 'change' }, + categoryIDs: { required: true, message: '请选择产品类别', trigger: 'change' }, compose: { required: true, message: '请选择产品适用对象', trigger: 'change' }, feature: [{ required: true, message: '请输入产品功能特点', trigger: 'change' }], // feature: [{ required: true, message: '请输入产品功能特点' }], @@ -158,21 +154,15 @@ formRules.value = { contentImage: { required: false, message: '请上传产品内容图片' }, sequence: [{ required: true, message: '请输入产品排序' }], status: [{ required: true, message: '请选择状态', trigger: 'change' }], - -} -const areaFormRules = { - categoryIDName: [{ required: true, message: '请输入产品类别' }], - targetName: [{ required: true, message: '请输入产品适用对象' }], - status: [{ required: true, message: '请选择状态', trigger: 'change' }], + } + const initData = async () => { try { showSpining(); - const { success: prodSuccess, data: prodData } = await apis.products.getProductObj({ pageSize: 999, page: 1 }); + const { success: prodSuccess, data: prodData } = await apis.categorys.getDataList({ pageSize: 999, page: 1 }); if (config('http.code.success') === prodSuccess) { - targetList.value = prodData - .filter(item => item.status === 'enabled') - .map(item => ({ code: item.id, name: item.name })); + categoryList.value = prodData } } catch (error) { @@ -193,7 +183,7 @@ function handleCreate() { // 初始化所有字段 formData.value = { title: '', - categoryID: '', + categoryIDs:'', compose: '', target: '', feature: [{ @@ -206,39 +196,13 @@ function handleCreate() { fu_hoao: '', prx: '', }], - images: [ - ...(Array.isArray(formData.value.mainImage) - ? formData.value.mainImage - : [formData.value.mainImage] - ).filter(Boolean).map(item => String(item)), - - ...(Array.isArray(formData.value.contentImage) - ? formData.value.contentImage - : [formData.value.contentImage] - ).filter(Boolean).map(item => String(item)) - ], - + images: [''], sequence: null, status: 'enabled', } initData() } -//新建产品类别 -const childHandleOk = async () => { - areaFormRef.value.validateFields().then(async (values) => { - try { - const params = { ...categoryForm.value } - const { success } = await apis.products.createProductCategory(params) - if (success) message.success('新增成功') - childOpen.value = false - categoryForm.value = { categoryIDName: '', status: 'enabled' } - initData() - } catch (error) { - message.error(error.message) - } - }) -} //新建产品适用对象 const childHandleObjOk = async () => { areaFormRef.value.validateFields().then(async (values) => { @@ -262,6 +226,7 @@ const handleCombinedOk = () => { * 编辑 */ async function handleEdit(record = {}) { + initData() showModal({ type: 'edit', title: t('pages.system.user.edit'), @@ -273,6 +238,7 @@ async function handleEdit(record = {}) { } formData.value = { ...data, + categoryIDs:data.categoryID, standard: data.standard || [{ label: '', val: '', @@ -284,13 +250,8 @@ async function handleEdit(record = {}) { data: [] }], // images:data.images || [''], - mainImage: data.images ? [config('http.apiBasic') + data.images[0]] : [''], - contentImage: data.images ? [config('http.apiBasic') + data.images[1]] : [''], + mainImage: data.images ? data.images.map(item=>config('http.apiBasic')+item):[''], } - // imgUrl.value = config('http.apiBasic') + data.img - mainImage.value = config('http.apiBasic') + data.images?.[0], - contentImage.value = config('http.apiBasic') + data.images?.[1], - console.log('编辑产品数据:', formData.value); } /** @@ -303,6 +264,8 @@ function handleOk() { showLoading() const params = { ...values, + categoryID:formData.value.categoryID, + categoryRootID:formData.value.categoryRootID, standard: formData.value.standard || [{ label: '', @@ -311,17 +274,7 @@ function handleOk() { prx: '', }], feature: formData.value.feature, - images: [ - ...(Array.isArray(formData.value.mainImage) - ? formData.value.mainImage - : [formData.value.mainImage] - ).filter(Boolean).map(item => spliceUrl(item)), - - ...(Array.isArray(formData.value.contentImage) - ? formData.value.contentImage - : [formData.value.contentImage] - ).filter(Boolean).map(item => spliceUrl(item)) - ], + images: formData.value.mainImage?formData.value.mainImage.map(item=>spliceUrl(item)):[''], } let result = null switch (modal.value.type) { @@ -396,6 +349,52 @@ function removeFeature(index) { formData.value.feature.splice(index, 1) } } +// 递归查找节点路径 +const findNodePath = (tree, value, path = []) => { + for (const node of tree) { + const currentPath = [...path, node.value]; + if (node.value === value) return currentPath; + if (node.children) { + const found = findNodePath(node.children, value, currentPath); + if (found) return found; + } + } + return null; +}; +// 获取节点是否是叶子节点 +const isLeafNode = (id) => { + const node = findNodeById(categoryList.value, id); + if(node.children.length>0) return false; + else return true +}; +// 根据ID查找节点 +const findNodeById = (tree, value) => { + for (const node of tree) { + if (node.value === value) return node; + if(node.children){ + const found=findNodeById(node.children,value) + if(found) return found; + } + } + return null; +}; +// 处理选择事件 +const handleTreeSelectChange = (value) => { + // 验证是否叶子节点 + if (!isLeafNode(value)) { + message.warning('只能选择最后一级节点'); + formData.value.categoryID = null; // 清除非叶子选择 + return; + } + if (!value) return; + const pathIds = findNodePath(categoryList.value, value); + if (pathIds) { + console.log('选中的路径ID数组:', pathIds); + // 实际使用中,此处可提交 pathIds 到后端或进行其他操作 + formData.value.categoryID=pathIds[1] + formData.value.categoryRootID=pathIds[0] + } +}; diff --git a/src/views/product/index.vue b/src/views/product/index.vue index 618f23c..a00102d 100644 --- a/src/views/product/index.vue +++ b/src/views/product/index.vue @@ -49,7 +49,6 @@