在主题编辑器中集成 sections

当用户通过 theme editor 自定义 sections 时,这些 sections 的 HTML 会动态地直接添加、移除或者重新渲染到现有的 DOM 上,而不会重新加载整个页面。不过,任何在页面加载时运行的 JavaScript 不会再次自动运行。

另外,你需要确保当一个 section 或 block 被选中时,它能出现在可视区域内,并且在选中期间一直保持可见。比如说,如果是一个 slideshow section,当这个 section 被选中时应该滚动到视口内,切换到选中的 block(slide),并且在选中期间暂停播放。

为了帮助识别像 section 和 block 选中、重新排序这些 theme editor 的动作,你可以使用 theme editor 触发的 JavaScript events

有时候你可能想要在 theme editor 里阻止一些特定的代码运行。你可以通过 Liquid 和 JavaScript 变量来 检测是否在 theme editor 中

Tip

Section 文件必须在它们的 schema 里定义 presets,这样才能支持通过 theme editor 添加到 JSON 模板中。没有 presets 的 section 文件必须手动包含在 JSON 文件里,而且无法通过 theme editor 删除。

想了解更多让你的主题兼容 theme editor preview inspector 的方法,可以参考 Theme editor preview inspector 最佳实践

JavaScript events

为了识别 sections 和 blocks,theme editor 会在相关 section 或 block 的父元素上查找特定的 data attributes。Sections 默认会被 Shopify 生成的元素包裹,并自带这个 attribute。但 blocks 需要手动通过 block objectshopify_attributes 属性加上去。

Theme editor 会触发 section 和 block 的 JavaScript events,这些事件是可以冒泡的,但不可取消。每个 event 都有一个 target(event.target),是基于上面提到的 data attribute 找到的 section 或 block 元素。

除了 section 和 block 的事件,theme editor 也会在 theme editor preview inspector 激活或关闭时触发事件。

下面这张表列出了 theme editor 触发的事件:

type target detail 触发时机 预期操作
shopify:inspector:activate theme editor preview inspector 被激活了
shopify:inspector:deactivate theme editor preview inspector 被关闭了
shopify:section:load section {sectionId} 某个 section 被添加或重新渲染了 重新执行让这个 section 正常工作和显示所需要的任何 JavaScript,就像页面刚加载时一样
shopify:section:unload section {sectionId} 某个 section 被删除或正在重新渲染 清理事件监听器、变量等,避免交互时报错或出现内存泄露
shopify:section:select section {sectionId, load} 用户在 sidebar 里选中了某个 section Theme editor 会自动滚动到这个 section,确保它在视口中并且一直保持可见
shopify:section:deselect section {sectionId} 用户取消选中了某个 section
shopify:section:reorder section {sectionId} 某个 section 被重新排序了
shopify:block:select block {blockId, sectionId, load} 用户在 sidebar 里选中了某个 block Theme editor 会自动滚动到这个 block,确保它在视口中并且一直保持可见
shopify:block:deselect block {blockId, sectionId} 用户取消选中了某个 block

表格里的 blockId 是指 block IDsectionId 是指 section ID,而 load 表示事件是因为 section 重新渲染触发的,还是用户主动选择触发的。load 的值是 truefalse

Tip

想看 theme editor JavaScript events 的实际使用例子,可以参考 Dawn 主题里的 theme-editor.js asset

检测 theme editor

你可以在 LiquidJavaScript 里检测当前是否在 theme editor 里。

Liquid

Liquid 的 request object 有一个 design_mode 属性,如果当前在 theme editor 里,会返回 true,否则返回 false。例如:

  1. {% if request.design_mode %}
  2. <!-- 只有在 theme editor 里才渲染 -->
  3. {% endif %}

JavaScript

在 JavaScript 里,全局变量 Shopify.designMode 如果在 theme editor 里,会返回 true,否则是 undefined。例如:

  1. if (Shopify.designMode) {
  2. // 只有在 theme editor 里才执行
  3. }

检测 theme editor preview inspector

除了在 JavaScript events 里监听 theme editor preview inspector 被激活或关闭外,你还可以直接用全局变量 Shopify.inspectMode。如果 preview inspector 被激活,返回 true,否则返回 false。例如:

  1. if (Shopify.inspectMode) {
  2. // 只有在 preview inspector 激活时才执行
  3. }

检测 theme editor visual preview

你可以在 LiquidJavaScript 里检测是否在 theme editor 的 visual preview 模式。

Liquid

Liquid 的 request object 有一个 visual_preview_mode 属性,如果当前在 visual preview 模式,会返回 true,否则返回 false。例如:

  1. {% if request.visual_preview_mode %}
  2. <!-- 只有在 theme editor visual preview 里才渲染 -->
  3. {% endif %}

JavaScript

全局变量 Shopify.visualPreviewMode 如果当前在 theme editor 的 visual preview 模式,会返回 true,否则是 undefined

例如:

  1. if (Shopify.visualPreviewMode) {
  2. // 只有在 visual preview 模式里才执行
  3. }