java-mall-admin/src/views/product/goodsImg/imgEdit.vue
2025-11-28 10:26:20 +08:00

356 lines
9.6 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<el-dialog
title="编辑商品图片"
:visible.sync="visible"
width="800px"
:close-on-click-modal="false"
@close="handleClose"
>
<div class="edit-tip">
正在编辑商品: <strong>{{ formData.name }}</strong>
(条码: {{ formData.barcode || '无条码' }})
</div>
<el-form ref="editForm" :model="formData" label-width="100px" label-position="right">
<!-- 主图编辑 -->
<!-- <el-form-item label="当前主图">
<el-image
v-if="formData.thumb"
:src="formData.thumb"
style="width: 100px; height: 100px; object-fit: cover; border: 1px solid #eee;"
:preview-src-list="[formData.thumb, ...getSubImages(formData.product_image_list)]"
/>
<span v-else class="text-gray-500">暂无主图</span>
</el-form-item> -->
<el-form-item
label="上传新主图"
prop="newThumb"
:rules="[
{ required: true, message: '请上传新的商品主图', trigger: 'change' }
]"
>
<upload
height="100px"
:image="formData.newThumb"
width="100px"
@upImage="handleMainImageUpload"
/>
<div class="el-form-item__error" style="padding-top: 10px;">
<span>支持 JPG, PNG 格式,建议尺寸 800x800px</span>
</div>
</el-form-item>
<!-- 副图编辑 -->
<!-- <el-form-item label="商品副图">
<div class="sub-images-container">
<div v-for="(item, index) in formData.product_image_list" :key="item.id || index" class="sub-image-item">
<upload
v-if="item.uploadNew"
height="80px"
:image="item.newImageUrl || item.imageUrl"
width="80px"
@upImage="(url) => handleSubImageUpload(url, index)"
/>
<el-image
v-else
:src="item.imageUrl"
style="width: 80px; height: 80px; object-fit: cover; border: 1px solid #eee;"
:preview-src-list="[formData.thumb, ...getSubImages(formData.product_image_list)]"
:preview-index="index + 1"
/>
<div class="sub-img-actions">
<el-button
size="mini"
type="text"
icon="el-icon-edit"
@click="toggleEditSubImage(index)"
/>
<el-button
size="mini"
type="text"
icon="el-icon-delete"
@click="deleteSubImage(index)"
/>
</div>
</div>
<div class="add-sub-image" @click="addSubImage">
<i class="el-icon-plus" />
<span>添加副图</span>
</div>
</div>
</el-form-item> -->
</el-form>
<template #footer>
<el-button @click="handleClose">{{ __('取消') }}</el-button>
<el-button type="primary" @click="handleSubmit">{{ __('提交修改') }}</el-button>
</template>
</el-dialog>
</template>
<script>
import upload from '@/components/upload'
import { URL } from '@/config'
import { saveBatchBarcode } from '@/api/goodsTool';
export default {
name: 'ImgEdit',
components: {
upload
},
data() {
return {
visible: false,
formData: {
id: '',
name: '',
barcode: '', // 条码
thumb: '',
newThumb: '',
product_image_list: [],
original_product_image_list: [], // 保存原始副图数据
original_thumb: '' // 保存原始主图数据
},
}
},
methods: {
// 获取副图URL列表用于预览
getSubImages(imageList) {
return (imageList || []).map(item => item.imageUrl).filter(url => url);
},
// 子组件open方法
open(row) {
if (!row || !row.id) {
this.$message.error('无效的商品数据');
return;
}
// 保存原始数据
const originalProductImages = JSON.parse(JSON.stringify(row.product_image_list || []));
const originalThumb = row.thumb || '';
// 初始化表单数据添加barcode
this.formData = {
id: row.id,
name: row.name || '未知名称',
barcode: row.barcode || '', // 新增条码字段
thumb: originalThumb,
newThumb: originalThumb,
original_thumb: originalThumb,
product_image_list: originalProductImages.map(item => ({
...item,
uploadNew: false,
newImageUrl: ''
})),
original_product_image_list: originalProductImages
};
this.visible = true;
this.$nextTick(() => {
this.$refs.editForm?.clearValidate();
});
},
handleClose() {
this.visible = false;
this.formData = {
id: '',
name: '',
thumb: '',
newThumb: '',
product_image_list: [],
original_product_image_list: [],
original_thumb: ''
};
this.$refs.editForm?.clearValidate();
},
// 主图上传
handleMainImageUpload(imageUrl) {
this.formData.newThumb = imageUrl;
},
//副图上传
handleSubImageUpload(imageUrl, index) {
if (this.formData.product_image_list[index]) {
const item = this.formData.product_image_list[index];
item.newImageUrl = imageUrl;
item.imageUrl = imageUrl; // 更新最终显示URL
item.uploadNew = false; // 退出编辑状态
item.tmpUrl = ''; // 清空临时URL
}
},
// 切换编辑副图状态
toggleEditSubImage(idx) {
const item = this.formData.product_image_list[idx];
if (item.uploadNew) {
// 取消编辑恢复原始URL
if (item.tmpUrl) {
item.imageUrl = item.tmpUrl;
item.tmpUrl = ''; // 清空临时URL
}
item.newImageUrl = '';
} else {
// 进入编辑保存当前URL到临时变量
item.tmpUrl = item.imageUrl;
}
item.uploadNew = !item.uploadNew;
},
// 删除副图
deleteSubImage(index) {
this.formData.product_image_list.splice(index, 1);
},
addSubImage() {
const max = this.formData.product_image_list.reduce((p, c) => Math.max(p, c.seq || 0), 0);
this.formData.product_image_list.push({
id: null,
productId: this.formData.id,
imageUrl: '',
newImageUrl: '',
uploadNew: true, // 默认进入编辑状态
tmpUrl: '', // 初始化临时URL
isMain: false,
seq: max + 1,
status: 1
});
},
async handleSubmit() {
try {
await this.$refs.editForm.validate();
// 准备提交数据 - 保持不变的字段使用原始数据
const submitData = [
{
id: this.formData.id,
name: this.formData.name,
// 主图:使用新上传的或原始的
thumb: this.formData.newThumb || this.formData.original_thumb,
// 副图:如果没有修改则使用原始数据,否则使用修改后的数据
product_image_list: this.hasSubImagesChanged()
? this.formData.product_image_list.filter(item => item.imageUrl).map((item, index) => ({
id: item.id,
productId: this.formData.id,
imageUrl: item.imageUrl,
isMain: false,
seq: index + 1,
status: 1
}))
: this.formData.original_product_image_list
}
];
console.log('提交更新商品图片请求:', submitData);
const response = await saveBatchBarcode(submitData);
if (response.status === 200) {
this.$message.success('商品图片修改成功!');
this.handleClose();
this.$emit('success');
} else {
this.$message.error('修改失败: ' + (response.msg || '未知错误'));
}
} catch (error) {
console.error('提交修改失败:', error);
if (error.name !== 'ValidateError') {
this.$message.error('修改失败,请稍后重试');
}
}
},
// 判断副图是否有修改
hasSubImagesChanged() {
// 如果副图数量不同,说明有修改
if (this.formData.product_image_list.length !== this.formData.original_product_image_list.length) {
return true;
}
// 检查每张图片是否有修改
for (let i = 0; i < this.formData.product_image_list.length; i++) {
const newItem = this.formData.product_image_list[i];
const originalItem = this.formData.original_product_image_list[i];
if (!originalItem || newItem.imageUrl !== originalItem.imageUrl) {
return true;
}
}
return false;
}
}
}
</script>
<style lang="scss" scoped>
.edit-tip {
color: #666;
padding: 8px 12px;
background-color: #f5f7fa;
border-radius: 4px;
margin-bottom: 16px;
font-size: 13px;
}
.sub-images-container {
display: flex;
flex-wrap: wrap;
gap: 15px;
padding: 10px 0;
.sub-image-item {
display: flex;
flex-direction: column;
align-items: center;
gap: 5px;
.sub-img-actions {
display: flex;
gap: 5px;
.el-button {
color: #666;
padding: 0;
&:hover {
color: #409eff;
}
}
.el-button:nth-child(2):hover {
color: #f56c6c;
}
}
}
.add-sub-image {
width: 80px;
height: 80px;
border: 1px dashed #ccc;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
cursor: pointer;
color: #999;
.el-icon-plus {
font-size: 20px;
margin-bottom: 5px;
}
&:hover {
border-color: #409eff;
color: #409eff;
}
}
}
::v-deep .el-form-item {
margin-bottom: 20px;
}
</style>