v0.10.8 首页 H6 宣言条 + H7 四列图标卡 1:1:section 根 padding/列 gap 默认 populated padding(10px 全向)/WidgetNode 双层 el-w-auto 修复 width:100% 强推;EAEL 取证改以原站实际加载的 eael-18.css 为准(icon/content 默认 block、title width:max-content maxW100%);H2~H7 全量 computed 归零(仅 0.8px 页级漂移),清理被取代的 scoped 补丁
This commit is contained in:
@@ -282,18 +282,20 @@ function collectResponsiveCss(elements: ElElement[]): string {
|
||||
return css;
|
||||
}
|
||||
|
||||
/** # 组件 单个元素节点分发(section/column/container/widget) */
|
||||
function ElementNode({ el }: { el: ElElement }) {
|
||||
/** # 组件 单个元素节点分发(section/column/container/widget)
|
||||
* 参数 gapPad 所属 section 的默认列内边距(Elementor gap 档位,仅 column 消费)
|
||||
*/
|
||||
function ElementNode({ el, gapPad }: { el: ElElement; gapPad?: string }) {
|
||||
const type = s(el.elType);
|
||||
if (type === "widget") return <WidgetNode el={el} />;
|
||||
if (type === "section" || type === "container") return <SectionNode el={el} />;
|
||||
if (type === "column") return <ColumnNode el={el} />;
|
||||
if (type === "column") return <ColumnNode el={el} gapPad={gapPad} />;
|
||||
// 未知结构:有子元素则递归,否则忽略
|
||||
if (el.elements?.length) {
|
||||
return (
|
||||
<>
|
||||
{el.elements.map((c, i) => (
|
||||
<ElementNode key={c.id || i} el={c} />
|
||||
<ElementNode key={c.id || i} el={c} gapPad={gapPad} />
|
||||
))}
|
||||
</>
|
||||
);
|
||||
@@ -303,23 +305,29 @@ function ElementNode({ el }: { el: ElElement }) {
|
||||
|
||||
/** # 组件 section / container:背景 + 内部布局
|
||||
* 取证(原站实测/post CSS):boxed 内容容器 = margin auto + flex wrap 的定宽行;
|
||||
* 内容宽度 content_width 优先,否则沿用 Elementor kit 默认 1140px;
|
||||
* 自带 padding 只取 settings.padding(不再叠加通用 px/py)。
|
||||
* 内容宽度 content_width 优先,否则沿用 Elementor kit 默认 1140px。
|
||||
* padding 挂在 section 根(原站 computed padding 在 .elementor-section 上,行容器无 padding,
|
||||
* 根 padding 同时把行往内推:1436 视口 + 1.6px 侧 padding 时行仍为整宽 1360,实测一致)。
|
||||
* gap 档位决定子列的默认 populated padding(frontend.min.css:no 0 / narrow 5 / default 10 /
|
||||
* extended 15 / wide 20 / wider 30;settings 缺省 = default)。
|
||||
*/
|
||||
const GAP_PAD: Record<string, string> = {
|
||||
no: "0px", narrow: "5px", default: "10px", extended: "15px", wide: "20px", wider: "30px",
|
||||
};
|
||||
function SectionNode({ el }: { el: ElElement }) {
|
||||
const settings = resolveGlobals(el.settings || {});
|
||||
const style = sectionBgStyle(settings);
|
||||
const width = sizeCss(settings.content_width) || sizeCss((settings as Record<string, unknown>).width) || "1140px";
|
||||
const secPad = paddingCss(settings.padding);
|
||||
if (secPad) style.padding = secPad;
|
||||
const inner: CSSProperties = {};
|
||||
if (s(settings.layout) === "full_width") {
|
||||
// 通栏 section:内容不设上限、无内边距(如首页 hero 轮播)
|
||||
// 通栏 section:内容不设上限(如首页 hero 轮播)
|
||||
inner.maxWidth = "none";
|
||||
inner.padding = "0";
|
||||
} else {
|
||||
inner.maxWidth = width;
|
||||
const innerPad = paddingCss(settings.padding);
|
||||
if (innerPad) inner.padding = innerPad;
|
||||
}
|
||||
const gapPad = GAP_PAD[s(settings.gap) || "default"] || "10px";
|
||||
// section 高度模式(Elementor: min-height / full),配合 custom_height;
|
||||
// 取证(原站 09fe4b7 实测):height 未设置时 custom_height 不生效(min-height 0px),
|
||||
// 故仅在显式 height 模式下应用
|
||||
@@ -331,7 +339,7 @@ function SectionNode({ el }: { el: ElElement }) {
|
||||
<section style={style} data-el={el.id}>
|
||||
<div className="mx-auto flex flex-wrap" style={inner}>
|
||||
{(el.elements || []).map((c, i) => (
|
||||
<ElementNode key={c.id || i} el={c} />
|
||||
<ElementNode key={c.id || i} el={c} gapPad={gapPad} />
|
||||
))}
|
||||
</div>
|
||||
</section>
|
||||
@@ -342,8 +350,11 @@ function SectionNode({ el }: { el: ElElement }) {
|
||||
* 外层参与 flex 布局(按 _inline_size 百分比否则均分),不承载盒样式;
|
||||
* 内层承载 populated 的盒样式:_margin(margin,移动卡片间距且不影响 flex 宽度,与原站一致)、
|
||||
* padding、背景、边框、圆角。
|
||||
* padding:列自带 settings.padding 优先;否则用所属 section 的 gap 默认值
|
||||
* (frontend.min.css .elementor-column-gap-default > … > .elementor-element-populated{padding:10px},
|
||||
* 实测 H6 列 59bc2e1 四向 10px、H7 列 66de90a 设置覆盖为 8/16/16/0,两端一致)。
|
||||
*/
|
||||
function ColumnNode({ el }: { el: ElElement }) {
|
||||
function ColumnNode({ el, gapPad }: { el: ElElement; gapPad?: string }) {
|
||||
const settings = resolveGlobals(el.settings || {});
|
||||
const outer: CSSProperties = { minWidth: 0, flex: "1 1 0" };
|
||||
const inline = settings._inline_size;
|
||||
@@ -359,8 +370,7 @@ function ColumnNode({ el }: { el: ElElement }) {
|
||||
inner.width = "100%";
|
||||
inner.margin = mg;
|
||||
}
|
||||
const pad = paddingCss(settings.padding);
|
||||
if (pad) inner.padding = pad;
|
||||
inner.padding = paddingCss(settings.padding) || gapPad || "10px";
|
||||
const bg = sectionBgStyle(settings);
|
||||
Object.assign(inner, { backgroundColor: bg.backgroundColor, backgroundImage: bg.backgroundImage });
|
||||
const radius = paddingCss(settings.border_radius);
|
||||
@@ -375,9 +385,9 @@ function ColumnNode({ el }: { el: ElElement }) {
|
||||
}
|
||||
return (
|
||||
<div className="el-col min-w-0" style={outer} data-el={el.id}>
|
||||
<div className="px-2.5" style={inner}>
|
||||
<div style={{ display: "flex", flexWrap: "wrap", alignContent: "flex-start", width: "100%", ...inner }}>
|
||||
{(el.elements || []).map((c, i) => (
|
||||
<ElementNode key={c.id || i} el={c} />
|
||||
<ElementNode key={c.id || i} el={c} gapPad={gapPad} />
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
@@ -421,16 +431,22 @@ function WidgetNode({ el }: { el: ElElement }) {
|
||||
<WidgetNodeInner el={el} />
|
||||
</WidgetGuard>
|
||||
);
|
||||
// 原站 .elementor-widget-wrap > .elementor-element { width:100% }:
|
||||
// widget 默认满宽(flex wrap 中独占一行),_element_width=auto 时按内容宽(横排)
|
||||
const widthAuto = s(settings._element_width) === "auto";
|
||||
const cls = s(settings._css_classes) || undefined;
|
||||
const baseCls = cls ? (widthAuto ? cls + " el-w-auto" : cls) : widthAuto ? "el-w-auto" : undefined;
|
||||
const hasContainerStyle = Object.keys(style).length > 0;
|
||||
if (hasContainerStyle) {
|
||||
return (
|
||||
<div data-el={el.id}>
|
||||
<div className={cls} style={style}>{inner}</div>
|
||||
// 外层也要带 el-w-auto:列内基础规则按 :not(.el-w-auto) 放行 width:auto 的根,
|
||||
// 否则 width-auto widget(如图标)被 width:100% 强推成每行一个(H7 回归根因)
|
||||
<div className={widthAuto ? "el-w-auto" : undefined} data-el={el.id}>
|
||||
<div className={baseCls} style={{ width: widthAuto ? "auto" : "100%", ...style }}>{inner}</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
return <div className={cls} data-el={el.id}>{inner}</div>;
|
||||
return <div className={baseCls} style={{ width: widthAuto ? "auto" : "100%" }} data-el={el.id}>{inner}</div>;
|
||||
}
|
||||
|
||||
/** # 组件 单个 widget 渲染错误边界:异常 widget 降级为空,不拖垮整页 */
|
||||
|
||||
@@ -102,6 +102,8 @@ const SETTING_KEYS = new Set([
|
||||
"hover_animation",
|
||||
// widget 高级盒模型(如 eael-info-box 边框卡:_border_* + _padding/_margin)
|
||||
"_margin",
|
||||
// widget 宽度模式(auto → 按内容宽横排,如 H7 图标行)
|
||||
"_element_width",
|
||||
// widget 容器背景(如 H4 标题下的橙线图)
|
||||
"_background_image",
|
||||
"_background_position",
|
||||
|
||||
Reference in New Issue
Block a user