v0.10.32: 产品 hero 残差收口(+58→-4):图廊数据源改 products.gallery 列(3 缩略)、主图/缩略 #C7CBDA 边框、meta 去顶距+分类链接橙、短描述 p 包裹+行高 24/列表 32、价格/购物车 widget 空渲染、按钮 paddingCss 空串=fallback 12px 24px+file-alt 图标
This commit is contained in:
+1
-1
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "dusuniot-rebuild",
|
"name": "dusuniot-rebuild",
|
||||||
"version": "0.10.31",
|
"version": "0.10.32",
|
||||||
"private": true,
|
"private": true,
|
||||||
"type": "module",
|
"type": "module",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
|
|||||||
@@ -145,7 +145,8 @@ function paddingCss(v: unknown): string | undefined {
|
|||||||
if (typeof v === "object") {
|
if (typeof v === "object") {
|
||||||
const o = v as Record<string, unknown>;
|
const o = v as Record<string, unknown>;
|
||||||
const unit = s(o.unit) || "px";
|
const unit = s(o.unit) || "px";
|
||||||
const t = o.top, r = o.right, b = o.bottom, l = o.left;
|
// Elementor 语义:空串 = 未设置(继承默认值),显式 "0" 才是 0(产品 hero 按钮 text_padding 全空 → 12px 24px 默认)
|
||||||
|
const t = o.top === "" ? null : o.top, r = o.right === "" ? null : o.right, b = o.bottom === "" ? null : o.bottom, l = o.left === "" ? null : o.left;
|
||||||
if (t == null && r == null && b == null && l == null) return undefined;
|
if (t == null && r == null && b == null && l == null) return undefined;
|
||||||
const px = (x: unknown) => `${x ?? 0}${unit}`;
|
const px = (x: unknown) => `${x ?? 0}${unit}`;
|
||||||
return collapseBoxValues(`${px(t)} ${px(r)} ${px(b)} ${px(l)}`);
|
return collapseBoxValues(`${px(t)} ${px(r)} ${px(b)} ${px(l)}`);
|
||||||
@@ -818,6 +819,11 @@ function WidgetNodeInner({ el }: { el: ElElement }) {
|
|||||||
return <WooProductDataTabs />;
|
return <WooProductDataTabs />;
|
||||||
case "woocommerce-products":
|
case "woocommerce-products":
|
||||||
return <WooProductsWidget />;
|
return <WooProductsWidget />;
|
||||||
|
/* 原站这两类 widget 在 hero 渲染为空(询价型商品无价格/购物车,取证 dsgw-210-a-1
|
||||||
|
* 叶子扫描仅 7 个 widget);渲染非空会把 hero 撑高(Add to Cart 占位 +42px) */
|
||||||
|
case "woocommerce-product-price":
|
||||||
|
case "wc-add-to-cart":
|
||||||
|
return null;
|
||||||
case "video":
|
case "video":
|
||||||
return <VideoWidget settings={settings} />;
|
return <VideoWidget settings={settings} />;
|
||||||
case "counter":
|
case "counter":
|
||||||
@@ -2148,7 +2154,16 @@ function WooProductMeta() {
|
|||||||
function WooProductShortDescription() {
|
function WooProductShortDescription() {
|
||||||
const woo = useContext(WooContext);
|
const woo = useContext(WooContext);
|
||||||
if (!woo?.shortDescription) return null;
|
if (!woo?.shortDescription) return null;
|
||||||
return <div className="woo-short-desc" dangerouslySetInnerHTML={{ __html: localSiteUrl(woo.shortDescription) }} />;
|
return <div className="woo-short-desc" dangerouslySetInnerHTML={{ __html: localSiteUrl(wpautopLite(woo.shortDescription)) }} />;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** # 函数 WP wpautop 简化版:把首个块级标签(ul/ol/table/hN/p)之前的裸文本包进 <p>
|
||||||
|
* dump 的 short_description 与 WP 库存一致(裸文本 + \r\n<ul>),原站经 the_content 输出时
|
||||||
|
* 首段被包成 <p>(取证 dsgw-210-a-1:P h=96 + mb 14.4);不包则匿名文本行盒与 ul 缝距不齐
|
||||||
|
*/
|
||||||
|
function wpautopLite(html: string): string {
|
||||||
|
const m = /^([^<]+)(<[\s\S]*)$/.exec(html.trim());
|
||||||
|
return m ? `<p>${m[1].trim()}</p>${m[2]}` : html;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** # 组件 Woo 产品数据标签页(woocommerce-product-data-tabs)
|
/** # 组件 Woo 产品数据标签页(woocommerce-product-data-tabs)
|
||||||
@@ -2211,18 +2226,23 @@ function WooProductsWidget() {
|
|||||||
/** # 常量 Woo 产品组件样式(取证 2026-11-03 dsgw-210-a-1 @1440) */
|
/** # 常量 Woo 产品组件样式(取证 2026-11-03 dsgw-210-a-1 @1440) */
|
||||||
const WOO_CSS = `
|
const WOO_CSS = `
|
||||||
.woo-gallery { margin: 0 0 32px; }
|
.woo-gallery { margin: 0 0 32px; }
|
||||||
|
/* 取证(dsgw-210-a-1,2026-11-03):主图框 .flex-viewport border 1px #C7CBDA(484 宽)、缩略图 img 115×115 同色边框 */
|
||||||
|
.woo-gallery .woo-gallery-image { border: 1px solid #C7CBDA; }
|
||||||
.woo-gallery .woo-gallery-image img { display: block; width: 100%; height: auto; }
|
.woo-gallery .woo-gallery-image img { display: block; width: 100%; height: auto; }
|
||||||
.woo-gallery .woo-thumbs { list-style: none; display: flex; flex-wrap: wrap; margin: 6px -4px 0; padding: 0; }
|
.woo-gallery .woo-thumbs { list-style: none; display: flex; flex-wrap: wrap; margin: 6px -4px 0; padding: 0; }
|
||||||
.woo-gallery .woo-thumbs li { width: 25%; padding: 4px; box-sizing: border-box; list-style: none; }
|
.woo-gallery .woo-thumbs li { width: 25%; padding: 4px; box-sizing: border-box; list-style: none; }
|
||||||
.woo-gallery .woo-thumbs img { display: block; width: 100%; height: auto; border-radius: 3px; cursor: pointer; opacity: 0.85; }
|
.woo-gallery .woo-thumbs img { display: block; width: 100%; height: auto; border: 1px solid #C7CBDA; cursor: pointer; }
|
||||||
.woo-title { margin: 0; font-size: 24px; font-weight: 600; line-height: 24px; color: #333; }
|
.woo-title { margin: 0; font-size: 24px; font-weight: 600; line-height: 24px; color: #333; }
|
||||||
.woo-meta { display: flex; flex-wrap: wrap; margin: 16px -10px 0; font-size: 16px; line-height: 24px; color: #333; }
|
.woo-meta { display: flex; flex-wrap: wrap; margin: 0 -10px; font-size: 16px; line-height: 24px; color: #333; }
|
||||||
.woo-meta .woo-meta-item { padding: 0 10px; }
|
.woo-meta .woo-meta-item { padding: 0 10px; }
|
||||||
.woo-meta .woo-meta-label { font-weight: 700; }
|
.woo-meta .woo-meta-label { font-weight: 700; }
|
||||||
.woo-meta .woo-meta-value a { color: #333; text-decoration: none; }
|
.woo-meta .woo-meta-value a { color: #ED6C00; text-decoration: none; }
|
||||||
.woo-meta .woo-meta-value a:hover { color: #ED6C00; }
|
.woo-meta .woo-meta-value a:hover { color: #FFA11B; }
|
||||||
.woo-short-desc { margin-top: 20px; font-size: 16px; line-height: 32px; color: #333; }
|
/* 取证(dsgw-210-a-1,2026-11-03):正文 p/匿名文本行高 24(P h=96/4 行)、列表项 32(UL 224/7 项)、p 底距 14.4 */
|
||||||
.woo-short-desc p { margin: 0 0 10px; }
|
.woo-short-desc { margin-top: 0; font-size: 16px; line-height: 24px; color: #333; }
|
||||||
|
.woo-short-desc li { line-height: 32px; }
|
||||||
|
.woo-short-desc p { margin: 0 0 14.4px; }
|
||||||
|
.woo-short-desc ul { margin: 0; }
|
||||||
.woo-tabs-list { list-style: none; display: none; margin: 0; padding: 0; }
|
.woo-tabs-list { list-style: none; display: none; margin: 0; padding: 0; }
|
||||||
.woo-tabs-list li { display: inline-block; }
|
.woo-tabs-list li { display: inline-block; }
|
||||||
.woo-tabs-list li a { display: inline-block; padding: 12.8px 19.2px; font-size: 16px; font-weight: 700; line-height: 16px; color: #515151; }
|
.woo-tabs-list li a { display: inline-block; padding: 12.8px 19.2px; font-size: 16px; font-weight: 700; line-height: 16px; color: #515151; }
|
||||||
|
|||||||
+5
-2
@@ -287,6 +287,7 @@ export async function getProductDetail(slug: string) {
|
|||||||
description: products.description,
|
description: products.description,
|
||||||
price: products.price,
|
price: products.price,
|
||||||
regularPrice: products.regularPrice,
|
regularPrice: products.regularPrice,
|
||||||
|
gallery: products.gallery,
|
||||||
stockStatus: products.stockStatus,
|
stockStatus: products.stockStatus,
|
||||||
stock: products.stock,
|
stock: products.stock,
|
||||||
specUrl: products.specUrl,
|
specUrl: products.specUrl,
|
||||||
@@ -302,8 +303,10 @@ export async function getProductDetail(slug: string) {
|
|||||||
.leftJoin(media, eq(media.id, products.featuredMediaId))
|
.leftJoin(media, eq(media.id, products.featuredMediaId))
|
||||||
.where(and(eq(products.slug, slug), eq(products.status, "published")));
|
.where(and(eq(products.slug, slug), eq(products.status, "published")));
|
||||||
if (!row) return null;
|
if (!row) return null;
|
||||||
const galleryUrls = row.meta && Array.isArray((row.meta as any).gallery)
|
// 图廊 ID 存 products.gallery 列(JSON 数组,如 [3785,3784];meta.gallery 不存在)
|
||||||
? await db.select({ url: media.url, alt: media.altText }).from(media).where(inArray(media.id, (row.meta as any).gallery))
|
const galleryIds: unknown = (row as unknown as { gallery?: unknown }).gallery;
|
||||||
|
const galleryUrls = Array.isArray(galleryIds) && galleryIds.length
|
||||||
|
? await db.select({ url: media.url, alt: media.altText }).from(media).where(inArray(media.id, galleryIds as number[]))
|
||||||
: [];
|
: [];
|
||||||
const attributes = await db
|
const attributes = await db
|
||||||
.select({ attr: productAttributes.name, attrSlug: productAttributes.slug, value: productAttributeValues.value, valueSlug: productAttributeValues.slug })
|
.select({ attr: productAttributes.name, attrSlug: productAttributes.slug, value: productAttributeValues.value, valueSlug: productAttributeValues.slug })
|
||||||
|
|||||||
@@ -83,6 +83,8 @@
|
|||||||
}
|
}
|
||||||
.fa-chevron-up::before { content: "\f077"; }
|
.fa-chevron-up::before { content: "\f077"; }
|
||||||
.fa-comment-dots::before { content: "\f4ad"; }
|
.fa-comment-dots::before { content: "\f4ad"; }
|
||||||
|
/* 产品 hero「Specification」按钮右图标(模板 2741 b267c2a selected_icon far fa-file-alt) */
|
||||||
|
.fa-file-alt::before { content: "\f15c"; }
|
||||||
.fa-check-circle::before { content: "\f058"; }
|
.fa-check-circle::before { content: "\f058"; }
|
||||||
/* 联系页地址列(icon-list 38bf7c7/cbf19d1 等):信封与地图钉(FA Solid 码位) */
|
/* 联系页地址列(icon-list 38bf7c7/cbf19d1 等):信封与地图钉(FA Solid 码位) */
|
||||||
.fa-envelope::before { content: "\f0e0"; }
|
.fa-envelope::before { content: "\f0e0"; }
|
||||||
|
|||||||
Reference in New Issue
Block a user