Browse Source

优化货源页面布局和图片显示

Boss3
Default User 1 month ago
parent
commit
b8b15150c1
  1. 687
      supply.html

687
supply.html

@ -27,13 +27,14 @@
.title-bar { .title-bar {
background-color: #1677ff; background-color: #1677ff;
color: white; color: white;
padding: 15px; padding: 15px 20px;
position: sticky; position: sticky;
top: 0; top: 0;
z-index: 100; z-index: 100;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
gap: 10px; gap: 12px;
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
} }
.title-bar-top { .title-bar-top {
@ -44,8 +45,8 @@
.title-bar h1 { .title-bar h1 {
margin: 0; margin: 0;
font-size: 18px; font-size: 20px;
font-weight: 500; font-weight: 600;
} }
.title-bar-bottom { .title-bar-bottom {
@ -53,7 +54,7 @@
justify-content: space-between; justify-content: space-between;
align-items: center; align-items: center;
flex-wrap: nowrap; flex-wrap: nowrap;
gap: 10px; gap: 12px;
} }
.title-bar-left { .title-bar-left {
@ -104,7 +105,7 @@
/* 搜索框样式优化 */ /* 搜索框样式优化 */
.search-container { .search-container {
padding: 15px; padding: 20px;
background-color: white; background-color: white;
border-bottom: 1px solid #f0f0f0; border-bottom: 1px solid #f0f0f0;
} }
@ -119,13 +120,21 @@
background-color: #07c160; background-color: #07c160;
color: white; color: white;
border: none; border: none;
padding: 14px 40px; padding: 16px 48px;
border-radius: 25px; border-radius: 28px;
font-size: 16px; font-size: 16px;
font-weight: 500;
cursor: pointer; cursor: pointer;
transition: background-color 0.3s; transition: all 0.3s;
width: 100%; width: 100%;
max-width: 300px; max-width: 300px;
box-shadow: 0 4px 12px rgba(7, 193, 96, 0.3);
}
.create-supply-btn button:hover {
background-color: #08d16a;
transform: translateY(-2px);
box-shadow: 0 6px 16px rgba(7, 193, 96, 0.4);
} }
/* 货源列表样式优化 */ /* 货源列表样式优化 */
@ -181,11 +190,44 @@
padding: 15px; padding: 15px;
flex-direction: column; flex-direction: column;
gap: 15px; gap: 15px;
margin: 8px 0;
}
.supply-name {
font-size: 16px;
gap: 8px;
overflow-x: auto;
-webkit-overflow-scrolling: touch;
scrollbar-width: none;
}
.supply-name::-webkit-scrollbar {
display: none;
} }
.supply-images { .image-slider {
width: 100% !important;
height: 250px !important;
}
.image-slider img {
width: 100%; width: 100%;
height: 150px; height: 100%;
object-fit: cover;
}
.supply-details {
padding: 12px;
gap: 8px;
}
.supply-actions {
gap: 10px;
}
.supply-actions button {
padding: 6px 14px;
font-size: 12px;
} }
} }
@ -211,17 +253,18 @@
.search-box { .search-box {
position: relative; position: relative;
background-color: #f5f5f5; background-color: #f5f5f5;
border-radius: 20px; border-radius: 25px;
padding: 0 15px; padding: 0 20px;
box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.05);
} }
.search-input { .search-input {
width: 100%; width: 100%;
height: 40px; height: 44px;
border: none; border: none;
background: transparent; background: transparent;
font-size: 14px; font-size: 14px;
padding-right: 30px; padding-right: 35px;
} }
.search-input:focus { .search-input:focus {
@ -235,6 +278,15 @@
transform: translateY(-50%); transform: translateY(-50%);
color: #999; color: #999;
cursor: pointer; cursor: pointer;
font-size: 16px;
padding: 4px;
border-radius: 50%;
transition: all 0.3s;
}
.clear-icon:hover {
background-color: rgba(0, 0, 0, 0.05);
color: #666;
} }
.section-header { .section-header {
@ -287,10 +339,16 @@
gap: 20px; gap: 20px;
align-items: flex-start; align-items: flex-start;
transition: all 0.3s; transition: all 0.3s;
background-color: white;
border-radius: 8px;
margin: 10px 0;
box-shadow: 0 1px 3px rgba(0, 0, 0, 0.05);
} }
.supply-item:hover { .supply-item:hover {
background-color: #fafafa; background-color: #fafafa;
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
transform: translateY(-2px);
} }
.supply-item:last-child { .supply-item:last-child {
@ -299,20 +357,27 @@
/* 图片区域 */ /* 图片区域 */
.supply-images { .supply-images {
width: 120px; width: 250px;
height: 120px; height: 250px;
position: relative; position: relative;
background-color: #f5f5f5; background-color: #f5f5f5;
border-radius: 8px; border-radius: 8px;
overflow: hidden; overflow: hidden;
flex-shrink: 0; flex-shrink: 0;
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1); box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
border: 1px solid #e0e0e0;
display: flex;
align-items: center;
justify-content: center;
} }
.image-slider { .image-slider {
width: 100%; width: 100%;
height: 100%; height: 100%;
position: relative; position: relative;
display: flex;
align-items: center;
justify-content: center;
} }
.image-slider img { .image-slider img {
@ -320,6 +385,7 @@
height: 100%; height: 100%;
object-fit: cover; object-fit: cover;
transition: transform 0.3s; transition: transform 0.3s;
display: block;
} }
.supply-images:hover .image-slider img { .supply-images:hover .image-slider img {
@ -346,12 +412,20 @@
} }
.supply-name { .supply-name {
font-size: 16px; font-size: 18px;
font-weight: 600; font-weight: 600;
display: flex; display: flex;
align-items: center; align-items: center;
gap: 10px; gap: 12px;
color: #333; color: #333;
margin-bottom: 4px;
flex-wrap: nowrap;
white-space: nowrap;
}
.supply-name > * {
flex-shrink: 0;
white-space: nowrap;
} }
.supply-status { .supply-status {
@ -360,6 +434,17 @@
border-radius: 12px; border-radius: 12px;
color: white; color: white;
font-weight: 500; font-weight: 500;
flex-shrink: 0;
}
.countdown-badge {
flex-shrink: 0;
white-space: nowrap;
}
.copy-supply-btn {
flex-shrink: 0;
white-space: nowrap;
} }
.status-published { .status-published {
@ -396,9 +481,13 @@
} }
.supply-details { .supply-details {
display: grid; display: flex;
grid-template-columns: repeat(2, 1fr); flex-direction: column;
gap: 10px; gap: 10px;
background-color: #fafafa;
padding: 16px;
border-radius: 8px;
border: 1px solid #f0f0f0;
} }
.detail-item { .detail-item {
@ -406,27 +495,42 @@
color: #666; color: #666;
display: flex; display: flex;
align-items: center; align-items: center;
gap: 6px; gap: 8px;
flex-wrap: nowrap;
white-space: normal;
overflow: visible;
text-overflow: clip;
} }
.detail-item::before { .detail-item::before {
content: "•"; content: "";
color: #1677ff; width: 6px;
font-size: 16px; height: 6px;
border-radius: 50%;
background-color: #1677ff;
margin-top: 2px;
} }
.supply-actions { .supply-actions {
display: flex; display: flex;
gap: 10px; gap: 12px;
margin-top: 8px;
} }
.supply-actions button { .supply-actions button {
padding: 6px 15px; padding: 8px 18px;
border: none; border: none;
border-radius: 4px; border-radius: 6px;
font-size: 12px; font-size: 13px;
font-weight: 500;
cursor: pointer; cursor: pointer;
transition: all 0.3s; transition: all 0.3s;
box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}
.supply-actions button:hover {
transform: translateY(-1px);
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.15);
} }
.btn-primary { .btn-primary {
@ -449,18 +553,19 @@
color: white; color: white;
} }
/* 模态框 - 改为全屏样式 */ /* 模态框 - 改为正常弹窗样式 */
.modal { .modal {
position: fixed; position: fixed;
top: 0; top: 0;
left: 0; left: 0;
right: 0; right: 0;
bottom: 0; bottom: 0;
background-color: white; background-color: rgba(0, 0, 0, 0.5);
display: none; display: none;
flex-direction: column; justify-content: center;
align-items: center;
z-index: 1000; z-index: 1000;
overflow: hidden; overflow: auto;
} }
.modal.active { .modal.active {
@ -469,13 +574,12 @@
.modal-content { .modal-content {
background-color: white; background-color: white;
width: 100%; width: 90%;
height: 100%; max-width: 800px;
max-width: none; max-height: 90vh;
max-height: none; border-radius: 12px;
border-radius: 0;
overflow: hidden; overflow: hidden;
box-shadow: none; box-shadow: 0 4px 24px rgba(0, 0, 0, 0.15);
display: flex; display: flex;
flex-direction: column; flex-direction: column;
} }
@ -487,12 +591,13 @@
justify-content: space-between; justify-content: space-between;
align-items: center; align-items: center;
background-color: white; background-color: white;
box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
} }
.modal-title { .modal-title {
margin: 0; margin: 0;
font-size: 18px; font-size: 18px;
font-weight: 500; font-weight: 600;
color: #333; color: #333;
} }
@ -503,25 +608,120 @@
cursor: pointer; cursor: pointer;
color: #999; color: #999;
transition: color 0.3s; transition: color 0.3s;
padding: 4px;
border-radius: 4px;
} }
.close-btn:hover { .close-btn:hover {
color: #333; color: #333;
background: #f0f0f0;
} }
.modal-body { .modal-body {
padding: 20px; padding: 20px;
overflow-y: auto; overflow-y: auto;
max-height: none;
flex: 1; flex: 1;
} }
.modal-footer {
padding: 16px 20px;
border-top: 1px solid #f0f0f0;
display: flex;
justify-content: flex-end;
gap: 10px;
background-color: white;
box-shadow: 0 -2px 4px rgba(0, 0, 0, 0.1);
}
/* 修复select下拉框向上显示问题 */ /* 修复select下拉框向上显示问题 */
select.form-select { select.form-select {
position: relative; position: relative;
z-index: 1; z-index: 1;
} }
/* 手机端响应式样式 */
@media (max-width: 768px) {
.modal-content {
width: 95%;
max-height: 95vh;
}
.modal-header {
padding: 16px;
}
.modal-title {
font-size: 16px;
}
.modal-body {
padding: 16px;
}
.modal-footer {
padding: 12px 16px;
}
/* 详情弹窗内容响应式调整 */
#supplyDetailContent {
font-size: 14px;
}
#supplyDetailContent > div {
gap: 16px !important;
}
#supplyDetailContent > div > div {
padding: 16px !important;
}
#supplyDetailContent .spec-quantity-box {
font-size: 12px !important;
padding: 8px !important;
}
/* 详情弹窗媒体文件响应式调整 */
#supplyDetailContent div[style*="display: flex; gap: 10px; margin-bottom: 20px; overflow-x: auto; padding: 10px 0;"] {
gap: 8px !important;
margin-bottom: 16px !important;
padding: 8px 0 !important;
}
#supplyDetailContent div[style*="flex-shrink: 0; width: 100px; height: 100px;"] {
width: 80px !important;
height: 80px !important;
}
/* 详情弹窗基本信息网格响应式调整 */
#supplyDetailContent div[style*="display: grid; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); gap: 15px;"] {
grid-template-columns: 1fr !important;
gap: 12px !important;
}
/* 详情弹窗基本信息卡片响应式调整 */
#supplyDetailContent div[style*="padding: 15px; border: 1px solid #f0f0f0; border-radius: 8px; background-color: #fafafa;"] {
padding: 12px !important;
}
/* 详情弹窗基本信息标题响应式调整 */
#supplyDetailContent div[style*="font-weight: 600; margin-bottom: 8px; color: #333;"] {
font-size: 14px !important;
margin-bottom: 6px !important;
}
/* 详情弹窗基本信息内容响应式调整 */
#supplyDetailContent div[style*="margin-bottom: 5px;"] {
font-size: 13px !important;
margin-bottom: 4px !important;
}
/* 详情弹窗规格信息响应式调整 */
#supplyDetailContent div[style*="margin-bottom: 12px; color: #333;"] {
font-size: 14px !important;
margin-bottom: 8px !important;
}
}
/* 表单样式 */ /* 表单样式 */
.form-group { .form-group {
margin-bottom: 20px; margin-bottom: 20px;
@ -1189,7 +1389,7 @@
} }
.image-slider { .image-slider {
height: 150px; height: 200px;
} }
/* 调整手机端规格-件数-价格对的布局 */ /* 调整手机端规格-件数-价格对的布局 */
@ -2241,6 +2441,24 @@
</div> </div>
</div> </div>
<!-- 货源详情弹窗 -->
<div id="supplyDetailModal" class="modal">
<div class="modal-content">
<div class="modal-header">
<h2 class="modal-title">货源详情</h2>
<button class="close-btn" onclick="hideSupplyDetailModal()">×</button>
</div>
<div class="modal-body">
<div id="supplyDetailContent">
<!-- 详情内容将通过JavaScript动态生成 -->
</div>
</div>
<div class="modal-footer">
<button class="modal-btn modal-btn-primary" onclick="hideSupplyDetailModal()">关闭</button>
</div>
</div>
</div>
<script> <script>
// 全局变量 // 全局变量
let supplyData = { let supplyData = {
@ -4324,6 +4542,195 @@
regionSelectModal.classList.remove('active'); regionSelectModal.classList.remove('active');
} }
// 显示货源详情弹窗
function showSupplyDetail(supplyId) {
// 查找对应的货源
let supply = null;
// 1. 首先尝试直接从所有货源数组中查找
if (supplyData.supplies && supplyData.supplies.length > 0) {
supply = supplyData.supplies.find(item => {
return String(item.id) === String(supplyId) || String(item.productId) === String(supplyId) || String(item._id) === String(supplyId);
});
}
// 2. 如果没找到,遍历所有状态的货源列表查找
if (!supply) {
const allSupplies = [
...supplyData.publishedSupplies,
...supplyData.pendingSupplies,
...supplyData.rejectedSupplies,
...supplyData.draftSupplies
];
supply = allSupplies.find(item => {
return String(item.id) === String(supplyId) || String(item.productId) === String(supplyId) || String(item._id) === String(supplyId);
});
}
if (!supply) {
alert('未找到对应的货源信息');
return;
}
// 生成详情内容
let detailContent = '';
// 处理媒体文件(图片和视频)
let mediaHTML = '';
const imageUrls = Array.isArray(supply.imageUrls) ? supply.imageUrls :
(typeof supply.imageUrls === 'string' ? [supply.imageUrls] :
(supply.imageUrls ? [supply.imageUrls] : []));
if (imageUrls.length > 0) {
mediaHTML = '<div style="display: flex; gap: 10px; margin-bottom: 20px; overflow-x: auto; padding: 10px 0;">';
imageUrls.forEach((url, index) => {
if (url.startsWith('data:video/') ||
url.match(/\.(mp4|mov|avi|wmv|flv|webm|mkv)$/i)) {
mediaHTML += `
<div style="flex-shrink: 0; width: 100px; height: 100px; position: relative; border-radius: 8px; overflow: hidden;">
<video src="${url}" style="width: 100%; height: 100%; object-fit: cover;" muted></video>
<div style="position: absolute; top: 50%; left: 50%; transform: translate(-50%, -50%); color: white; font-size: 24px; background-color: rgba(0, 0, 0, 0.5); border-radius: 50%; width: 40px; height: 40px; display: flex; align-items: center; justify-content: center;"></div>
</div>
`;
} else {
mediaHTML += `
<div style="flex-shrink: 0; width: 100px; height: 100px; border-radius: 8px; overflow: hidden;">
<img src="${url}" alt="图片${index + 1}" style="width: 100%; height: 100%; object-fit: cover; cursor: pointer;" onclick="previewImage('${url}', ${JSON.stringify(imageUrls || []).replace(/\"/g, '&quot;')})"></img>
</div>
`;
}
});
mediaHTML += '</div>';
}
// 解析规格和件数为数组
let specifications = [];
let quantities = [];
let costprices = [];
let specStatuses = [];
try {
if (supply.specification) {
if (typeof supply.specification === 'string') {
specifications = supply.specification.split(',').filter(spec => spec.trim());
} else if (Array.isArray(supply.specification)) {
specifications = supply.specification;
} else {
specifications = [supply.specification];
}
} else if (supply.spec) {
specifications = [supply.spec];
}
} catch (e) {
specifications = [supply.specification || supply.spec || '无'];
}
try {
if (supply.quantity) {
if (typeof supply.quantity === 'string') {
quantities = supply.quantity.split(',').filter(qty => qty.trim());
} else if (Array.isArray(supply.quantity)) {
quantities = supply.quantity;
} else {
quantities = [supply.quantity];
}
}
} catch (e) {
quantities = [supply.quantity || '0'];
}
try {
if (supply.costprice) {
if (typeof supply.costprice === 'string') {
costprices = supply.costprice.split(',').filter(cp => cp.trim());
} else if (Array.isArray(supply.costprice)) {
costprices = supply.costprice;
} else {
costprices = [supply.costprice];
}
}
} catch (e) {
costprices = [supply.costprice || '0'];
}
try {
if (supply.spec_status) {
if (typeof supply.spec_status === 'string') {
specStatuses = supply.spec_status.split(',').map(s => s.trim());
} else if (Array.isArray(supply.spec_status)) {
specStatuses = supply.spec_status;
} else {
specStatuses = [supply.spec_status];
}
}
} catch (e) {
specStatuses = [];
}
// 生成规格信息
let specHTML = '';
const maxLength = Math.max(specifications.length, quantities.length, costprices.length);
for (let i = 0; i < maxLength; i++) {
const spec = specifications[i] || '无';
const quantity = quantities[i] || '0';
const costprice = costprices[i] || '0';
const specStatus = specStatuses[i] || '0';
const soldOutTag = specStatus === '1' ? '<span style="color: #f5222d; font-size: 12px; font-weight: 600; margin-left: 10px;">已售空</span>' : '';
specHTML += `<div style="margin-bottom: 10px; padding: 10px; border: 1px solid #f0f0f0; border-radius: 8px; background-color: #fafafa;">• 规格${i + 1}: ${spec} | ${quantity}件 | ¥${costprice}${soldOutTag}</div>`;
}
// 生成详情内容
detailContent = `
<div style="display: flex; flex-direction: column; gap: 20px;">
<!-- 媒体文件 -->
${mediaHTML}
<!-- 基本信息 -->
<div style="display: grid; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); gap: 15px;">
<div style="padding: 15px; border: 1px solid #f0f0f0; border-radius: 8px; background-color: #fafafa;">
<div style="font-weight: 600; margin-bottom: 8px; color: #333;">基本信息</div>
<div style="margin-bottom: 5px;">商品名称: ${supply.productName || '无'}</div>
<div style="margin-bottom: 5px;">货源类型: ${supply.sourceType || '无'}</div>
<div style="margin-bottom: 5px;">种类: ${supply.category || '无'}</div>
<div style="margin-bottom: 5px;">蛋黄类型: ${supply.yolk || '无'}</div>
<div style="margin-bottom: 5px;">产品包装: ${supply.producting || '无'}</div>
<div style="margin-bottom: 5px;">新鲜程度: ${supply.freshness || '无'}</div>
<div style="margin-bottom: 5px;">地区: ${supply.region || '无'}</div>
</div>
<div style="padding: 15px; border: 1px solid #f0f0f0; border-radius: 8px; background-color: #fafafa;">
<div style="font-weight: 600; margin-bottom: 8px; color: #333;">其他信息</div>
<div style="margin-bottom: 5px;">货源状态: ${supply.supplyStatus || '无'}</div>
<div style="margin-bottom: 5px;">货源描述: ${supply.description || '无'}</div>
<div style="margin-bottom: 5px;">创建时间: ${formatDate(supply.created_at)}</div>
<div style="margin-bottom: 5px;">更新时间: ${formatDate(supply.updated_at)}</div>
${supply.autoOfflineHours ? `<div style="margin-bottom: 5px;">自动下架时间: ${supply.autoOfflineHours}小时</div>` : ''}
</div>
</div>
<!-- 规格信息 -->
<div style="padding: 15px; border: 1px solid #f0f0f0; border-radius: 8px; background-color: #fafafa;">
<div style="font-weight: 600; margin-bottom: 12px; color: #333;">规格信息</div>
${specHTML}
</div>
</div>
`;
// 填充详情内容
document.getElementById('supplyDetailContent').innerHTML = detailContent;
// 显示弹窗
document.getElementById('supplyDetailModal').classList.add('active');
}
// 隐藏货源详情弹窗
function hideSupplyDetailModal() {
document.getElementById('supplyDetailModal').classList.remove('active');
}
// 生成地区选项 // 生成地区选项
function generateRegionOptions() { function generateRegionOptions() {
const provinceList = document.getElementById('provinceList'); const provinceList = document.getElementById('provinceList');
@ -4882,7 +5289,7 @@
<img <img
src="${firstMediaUrl}" src="${firstMediaUrl}"
alt="${supply.productName}" alt="${supply.productName}"
style="width: 100%; height: 100%; object-fit: cover; border-radius: 8px;" style="width: 100%; height: 100%; object-fit: cover;"
onclick="previewImage('${firstMediaUrl}', ${JSON.stringify(imageUrls || []).replace(/\"/g, '&quot;')})" onclick="previewImage('${firstMediaUrl}', ${JSON.stringify(imageUrls || []).replace(/\"/g, '&quot;')})"
> >
`; `;
@ -4899,22 +5306,25 @@
// 处理操作按钮 // 处理操作按钮
let actionsHTML = ''; let actionsHTML = '';
if (supply.status === 'published') { if (supply.status === 'published') {
actionsHTML = `<button class="btn-primary" onclick="unpublishSupply('${supply.id}')">下架</button> <button class="btn-warning" onclick="showEditSupply('${supply.id}')">编辑</button>`; actionsHTML = `<button class="btn-primary" onclick="unpublishSupply('${supply.id}')">下架</button> <button class="btn-warning" onclick="showEditSupply('${supply.id}')">编辑</button> <button class="btn-default" onclick="showSupplyDetail('${supply.id}')">查看详情</button>`;
} else if (supply.status === 'pending_review') { } else if (supply.status === 'pending_review') {
actionsHTML = ` actionsHTML = `
<button class="btn-warning" onclick="showEditSupply('${supply.id}')">编辑</button> <button class="btn-warning" onclick="showEditSupply('${supply.id}')">编辑</button>
<button class="btn-danger" onclick="deleteSupply('${supply.id}')">删除</button> <button class="btn-danger" onclick="deleteSupply('${supply.id}')">删除</button>
<button class="btn-default" onclick="showSupplyDetail('${supply.id}')">查看详情</button>
`; `;
} else if (supply.status === 'rejected') { } else if (supply.status === 'rejected') {
actionsHTML = ` actionsHTML = `
<button class="${supply.label === 1 ? 'btn-disabled' : 'btn-primary'}" ${supply.label === 1 ? '' : `onclick="preparePublishSupply('${supply.id}')"`}>上架</button> <button class="${supply.label === 1 ? 'btn-disabled' : 'btn-primary'}" ${supply.label === 1 ? '' : `onclick="preparePublishSupply('${supply.id}')"`}>上架</button>
<button class="btn-danger" onclick="deleteSupply('${supply.id}')">删除</button> <button class="btn-danger" onclick="deleteSupply('${supply.id}')">删除</button>
<button class="btn-primary" onclick="showRejectReason('${supply.id}')">查看原因</button> <button class="btn-primary" onclick="showRejectReason('${supply.id}')">查看原因</button>
<button class="btn-default" onclick="showSupplyDetail('${supply.id}')">查看详情</button>
`; `;
} else if (supply.status === 'hidden' || supply.status === 'sold_out') { } else if (supply.status === 'hidden' || supply.status === 'sold_out') {
actionsHTML = ` actionsHTML = `
<button class="${supply.label === 1 ? 'btn-disabled' : 'btn-primary'}" ${supply.label === 1 ? '' : `onclick="preparePublishSupply('${supply.id}')"`}>上架</button> <button class="${supply.label === 1 ? 'btn-disabled' : 'btn-primary'}" ${supply.label === 1 ? '' : `onclick="preparePublishSupply('${supply.id}')"`}>上架</button>
<button class="btn-danger" onclick="deleteSupply('${supply.id}')">删除</button> <button class="btn-danger" onclick="deleteSupply('${supply.id}')">删除</button>
<button class="btn-default" onclick="showSupplyDetail('${supply.id}')">查看详情</button>
`; `;
} }
@ -5000,48 +5410,36 @@
// 添加售空标识 // 添加售空标识
const soldOutTag = specStatus === '1' ? '<span style="color: #f5222d; font-size: 12px; font-weight: 600; margin-left: 10px;">已售空</span>' : ''; const soldOutTag = specStatus === '1' ? '<span style="color: #f5222d; font-size: 12px; font-weight: 600; margin-left: 10px;">已售空</span>' : '';
specQuantityBoxes += `<div class="spec-quantity-box" style="border: 1px solid #f0f0f0; padding: 10px; border-radius: 8px; background-color: #fafafa; margin-bottom: 10px;">• 规格${i + 1}: ${spec} - 件数: ${quantity}件 - 采购价: ¥${costprice}${soldOutTag}</div>`; specQuantityBoxes += `<div class="spec-quantity-box" style="border: 1px solid #f0f0f0; padding: 10px; border-radius: 8px; background-color: #fafafa; margin-bottom: 10px;">• 规格${i + 1}: ${spec} | ${quantity}件 | ¥${costprice}${soldOutTag}</div>`;
} }
return ` return `
<div class="supply-item" data-id="${supply.id}"> <div class="supply-item" data-id="${supply.id}">
<div class="supply-images"> <div class="image-slider" style="position: relative; width: 250px; height: 250px; border-radius: 8px; overflow: hidden; flex-shrink: 0; box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1); border: 1px solid #e0e0e0; display: flex; align-items: center; justify-content: center;">
<div class="image-slider" style="position: relative;"> ${mediaPreviewHTML}
${mediaPreviewHTML}
</div>
</div> </div>
<div class="supply-info"> <div class="supply-info">
<!-- 产品名称和规格-件数对在同一行 --> <!-- 产品名称 -->
<div style="display: flex; gap: 20px; align-items: flex-start;"> <div class="supply-name">
<!-- 左侧产品名称 --> ${supply.productName}
<div style="flex: 1;"> ${(supply.status === 'hidden' || supply.status === 'sold_out') ? '' : `<span class="supply-status ${status.class}">${status.text}</span>`}
<div class="supply-name"> ${supply.status === 'published' && supply.autoOfflineHours && supply.autoOfflineHours !== '' && supply.autoOfflineHours !== null ? `<span class="countdown-badge" data-id="${supply.id}" style="margin-left: 8px; padding: 4px 12px; background: linear-gradient(135deg, #ff6b6b, #ee5a6f); color: white; border-radius: 16px; font-size: 12px; font-weight: 500; box-shadow: 0 2px 4px rgba(255, 107, 107, 0.3); display: inline-flex; align-items: center; gap: 4px;">⏰ 计算中...</span>` : ''}
${supply.productName} <button class="copy-supply-btn" onclick="copySupply('${supply.id}')">复制</button>
${(supply.status === 'hidden' || supply.status === 'sold_out') ? '' : `<span class="supply-status ${status.class}">${status.text}</span>`} </div>
${supply.status === 'published' && supply.autoOfflineHours && supply.autoOfflineHours !== '' && supply.autoOfflineHours !== null ? `<span class="countdown-badge" data-id="${supply.id}" style="margin-left: 8px; padding: 4px 12px; background: linear-gradient(135deg, #ff6b6b, #ee5a6f); color: white; border-radius: 16px; font-size: 12px; font-weight: 500; box-shadow: 0 2px 4px rgba(255, 107, 107, 0.3); display: inline-flex; align-items: center; gap: 4px;">⏰ 计算中...</span>` : ''}
<button class="copy-supply-btn" onclick="copySupply('${supply.id}')">复制</button> <!-- 精简基本信息 -->
</div> <div class="supply-details" style="margin: 12px 0; padding: 12px; background: #f8f9fa; border-radius: 8px;">
<!-- 基本信息 --> <div class="detail-item">品种: ${supply.category || '无'}</div>
<div class="supply-details"> <div class="detail-item">地区: ${supply.region || '未设置'}</div>
<div class="detail-item">货源类型: ${supply.sourceType || '无'}</div> <div class="detail-item">包装: ${supply.producting || '无'}</div>
<div class="detail-item">品种: ${supply.category || '无'}</div>
<div class="detail-item">蛋黄: ${supply.yolk || '无'}</div> <!-- 规格和件数信息 - 简化显示 -->
<div class="detail-item">包装: ${supply.producting || '无'}</div> <div style="margin-top: 12px; font-size: 13px; font-weight: 500; color: #333; margin-bottom: 8px;">规格信息</div>
<div class="detail-item">新鲜程度: ${supply.freshness || '无'}</div> ${specQuantityBoxes}
<div class="detail-item">货源状态: ${supply.supplyStatus || '未设置'}</div>
<div class="detail-item">货源描述: ${supply.description || '无'}</div>
<div class="detail-item">地区: ${supply.region || '未设置'}</div>
<!-- 隐藏独立价格字段,因为每个规格-件数对都有自己的采购价 -->
<div class="detail-item" style="font-size: 12px; color: #999;">创建时间: ${formatDate(supply.created_at)}</div>
${supply.status === 'published' ? `<div class="detail-item" style="color: #faad14;">上架时间: ${formatDate(getPublishTime(supply))}</div>` : ''}
</div>
</div>
<!-- 右侧规格-件数对 -->
<div class="spec-quantity-container" style="display: block; gap: 15px; flex: 1;">
${specQuantityBoxes}
</div>
</div> </div>
<div class="supply-actions">
<!-- 操作按钮 -->
<div class="supply-actions" style="margin-top: 16px;">
${actionsHTML} ${actionsHTML}
</div> </div>
</div> </div>
@ -8888,5 +9286,134 @@
} }
}; };
</script> </script>
</body> <!-- 货源详情弹窗 -->
<div id="supplyDetailModal" class="modal">
<div class="modal-content">
<div class="modal-header">
<h2 class="modal-title">货源详情</h2>
<button class="close-btn" onclick="hideSupplyDetailModal()">×</button>
</div>
<div class="modal-body" id="supplyDetailContent">
<!-- 详情内容将通过JavaScript动态填充 -->
</div>
<div class="modal-footer">
<button class="btn-default" onclick="hideSupplyDetailModal()">关闭</button>
</div>
</div>
</div>
<script>
// 显示货源详情弹窗
function showSupplyDetail(supplyId) {
const supply = supplyData.supplies.find(s => String(s.id) === String(supplyId));
if (!supply) return;
// 构建详情HTML
let detailHTML = `
<div style="display: flex; flex-direction: column; gap: 20px;">
<!-- 基本信息 -->
<div style="padding: 20px; background: linear-gradient(135deg, #f8f9fa 0%, #e9ecef 100%); border-radius: 12px;">
<h3 style="font-size: 18px; font-weight: 600; margin-bottom: 16px; color: #333;">基本信息</h3>
<div style="display: grid; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); gap: 12px;">
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">产品名称</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.productName || '未知'}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">货源类型</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.sourceType || '未知'}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">品种</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.category || '未知'}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">蛋黄</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.yolk || '未知'}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">包装</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.producting || '未知'}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">新鲜程度</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.freshness || '未知'}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">货源状态</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.supplyStatus || '未设置'}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">地区</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${supply.region || '未设置'}</div>
</div>
</div>
</div>
<!-- 规格和价格信息 -->
<div style="padding: 20px; background: linear-gradient(135deg, #f8f9fa 0%, #e9ecef 100%); border-radius: 12px;">
<h3 style="font-size: 18px; font-weight: 600; margin-bottom: 16px; color: #333;">规格和价格</h3>
<div style="display: flex; flex-direction: column; gap: 12px;">
`;
// 添加规格-件数-价格信息
if (supply.spec && supply.quantity && supply.costprice) {
const specs = Array.isArray(supply.spec) ? supply.spec : supply.spec.split(',');
const quantities = Array.isArray(supply.quantity) ? supply.quantity : supply.quantity.split(',');
const costprices = Array.isArray(supply.costprice) ? supply.costprice : supply.costprice.split(',');
specs.forEach((spec, index) => {
const quantity = quantities[index] || '';
const costprice = costprices[index] || '';
detailHTML += `
<div style="padding: 16px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 14px; font-weight: 500; color: #333;">规格 ${index + 1}</div>
<div style="font-size: 13px; color: #666; margin-top: 8px;">• 规格: ${spec || '未知'}</div>
<div style="font-size: 13px; color: #666;">• 件数: ${quantity || '未知'}件</div>
<div style="font-size: 13px; color: #666;">• 采购价: ¥${costprice || '未知'}</div>
</div>
`;
});
}
detailHTML += `
</div>
</div>
<!-- 时间信息 -->
<div style="padding: 20px; background: linear-gradient(135deg, #f8f9fa 0%, #e9ecef 100%); border-radius: 12px;">
<h3 style="font-size: 18px; font-weight: 600; margin-bottom: 16px; color: #333;">时间信息</h3>
<div style="display: grid; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); gap: 12px;">
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">创建时间</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${formatDate(supply.created_at)}</div>
</div>
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">更新时间</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${formatDate(supply.updated_at)}</div>
</div>
${supply.status === 'published' ? `
<div style="padding: 12px; background: white; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);">
<div style="font-size: 12px; color: #666; margin-bottom: 4px;">上架时间</div>
<div style="font-size: 14px; font-weight: 500; color: #333;">${formatDate(getPublishTime(supply))}</div>
</div>
` : ''}
</div>
</div>
</div>
`;
// 填充详情内容
document.getElementById('supplyDetailContent').innerHTML = detailHTML;
// 显示弹窗
document.getElementById('supplyDetailModal').classList.add('active');
}
// 隐藏货源详情弹窗
function hideSupplyDetailModal() {
document.getElementById('supplyDetailModal').classList.remove('active');
}
</script>
</body>
</html> </html>
Loading…
Cancel
Save