新增商品关联商品静态部分
This commit is contained in:
@@ -222,7 +222,6 @@
|
||||
<el-form-item label="库存数量">
|
||||
<el-input-number v-model="ruleForm.stockNumber" :min="0" />
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item label="打包费" prop="delivery">
|
||||
<div style="display: block;">
|
||||
<el-input-number v-model="ruleForm.packFee" controls-position="right"
|
||||
@@ -230,6 +229,41 @@
|
||||
<div style="color: #999;">单份商品打包费。注:店铺开启外卖模式下该数据才生效</div>
|
||||
</div>
|
||||
</el-form-item>
|
||||
<el-form-item label="关联推荐商品">
|
||||
<div class="column">
|
||||
<div class="row">
|
||||
<div class="center">
|
||||
<el-button type="primary" @click="selecProductDialogRef?.show()"
|
||||
:disabled="goodsList.length >= goodsListMax">添加商品</el-button>
|
||||
<div class="tips">设置商品后,用户可以在商品详情页中看到推荐商品可拖动调整顺序,最多设置{{ goodsListMax }}个商品</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row">
|
||||
<div id="goods_table_drag">
|
||||
<el-table :data="goodsList" border stripe style="width: 500px;" row-key="id">
|
||||
<!-- 拖拽列 -->
|
||||
<el-table-column label="排序" width="60">
|
||||
<template v-slot="scope">
|
||||
<div class="drag-handle">☰</div>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="商品图片" prop="coverImg" width="90">
|
||||
<template v-slot="scope">
|
||||
<el-image :src="scope.row.coverImg" style="width: 50px;height: 50px;border-radius: 4px;"
|
||||
fit="cover"></el-image>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="商品名称" prop="name"></el-table-column>
|
||||
<el-table-column label="操作" width="100">
|
||||
<template v-slot="scope">
|
||||
<el-button link type="danger" @click="goodsList.splice(scope.$index, 1)">删除</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</el-form-item>
|
||||
<el-form-item>
|
||||
<el-button type="primary" @click="submitForm(ruleFormRef)">确定</el-button>
|
||||
<el-button @click="resetForm(ruleFormRef)">取消</el-button>
|
||||
@@ -256,11 +290,13 @@
|
||||
</span>
|
||||
</template>
|
||||
</el-dialog>
|
||||
<!-- 选择商品弹窗 -->
|
||||
<selecProductDialog ref="selecProductDialogRef" @success="selecProductSuccess" />
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts" setup>
|
||||
import { reactive, ref } from "vue";
|
||||
import { reactive, ref, onMounted, nextTick } from "vue";
|
||||
import type { FormInstance, FormRules } from "element-plus";
|
||||
// 规格属性
|
||||
import SpecificationAttribute from "./SpecificationAttribute.vue";
|
||||
@@ -272,7 +308,65 @@ import UserAPI4 from "@/api/product/specificationsconfig";
|
||||
import shopList from "@/components/mycomponents/shopList.vue";
|
||||
import AddImg from "@/components/mycomponents/addImg.vue";
|
||||
import { useRouter } from "vue-router";
|
||||
import Sortable from "sortablejs";
|
||||
import { useTagsViewStore } from "@/store";
|
||||
import selecProductDialog from "@/views/marketing_center/group_booking/components/selecProductDialog.vue";
|
||||
|
||||
const selecProductDialogRef = ref(null)
|
||||
const goodsListMax = ref(9)
|
||||
const goodsList = ref<any[]>([]);
|
||||
|
||||
onMounted(() => {
|
||||
// Sortable 需要在 el-table 渲染 tbody 后初始化,尝试多次以确保 DOM 可用
|
||||
const initSortable = async () => {
|
||||
await nextTick();
|
||||
let attempts = 0;
|
||||
const maxAttempts = 8;
|
||||
const tryInit = () => {
|
||||
const el = document.querySelector("#goods_table_drag .el-table__body-wrapper tbody");
|
||||
if (!el) {
|
||||
attempts++;
|
||||
if (attempts < maxAttempts) {
|
||||
setTimeout(tryInit, 80);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// 已找到表体,初始化 Sortable
|
||||
new Sortable(el as HTMLElement, {
|
||||
animation: 150,
|
||||
handle: ".drag-handle",
|
||||
ghostClass: "sortable-ghost",
|
||||
chosenClass: "sortable-chosen",
|
||||
onEnd: (e) => {
|
||||
if (e.oldIndex == null || e.newIndex == null) return;
|
||||
if (e.oldIndex === e.newIndex) return;
|
||||
const from = e.oldIndex;
|
||||
const to = e.newIndex;
|
||||
const item = goodsList.value.splice(from, 1)[0];
|
||||
goodsList.value.splice(to, 0, item);
|
||||
// 触发响应式更新
|
||||
goodsList.value = goodsList.value.slice();
|
||||
console.log("排序后的数据", goodsList.value);
|
||||
},
|
||||
});
|
||||
};
|
||||
tryInit();
|
||||
};
|
||||
|
||||
initSortable();
|
||||
});
|
||||
|
||||
// 已选择的商品
|
||||
function selecProductSuccess(res: any) {
|
||||
let obj = goodsList.value.find((item) => item.id == res.id);
|
||||
if (obj && obj.id) {
|
||||
ElMessage.error("该商品已选择");
|
||||
return;
|
||||
}
|
||||
goodsList.value.push({ ...res });
|
||||
}
|
||||
|
||||
const tagsViewStore = useTagsViewStore();
|
||||
const router = useRouter();
|
||||
let list = ref<any[]>([
|
||||
@@ -915,6 +1009,27 @@ const resetForm = (formEl: FormInstance | undefined) => {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.drag-handle {
|
||||
cursor: move;
|
||||
display: inline-block;
|
||||
padding: 4px 8px;
|
||||
border-radius: 4px;
|
||||
background: #f0f0f0;
|
||||
}
|
||||
|
||||
/* SortableJS classes */
|
||||
.sortable-ghost {
|
||||
opacity: 0.6;
|
||||
}
|
||||
|
||||
.sortable-chosen {
|
||||
background: #f5f7ff !important;
|
||||
}
|
||||
|
||||
.el-table__body-wrapper tbody tr {
|
||||
transition: transform 150ms ease, background-color 150ms ease;
|
||||
}
|
||||
|
||||
.showStyle:hover>.buttonstyle {
|
||||
display: block;
|
||||
}
|
||||
@@ -942,4 +1057,26 @@ const resetForm = (formEl: FormInstance | undefined) => {
|
||||
top: -10px;
|
||||
z-index: 10;
|
||||
}
|
||||
</style>
|
||||
|
||||
.column {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
|
||||
.row {
|
||||
flex: 1;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
}
|
||||
|
||||
.center {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 10px;
|
||||
|
||||
.tips {
|
||||
color: #999;
|
||||
font-size: 14px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
Reference in New Issue
Block a user