@blocklet/ui-react 3.1.47 → 3.1.49
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.aigne/doc-smith/config.yaml +76 -0
- package/.aigne/doc-smith/history.yaml +9 -0
- package/.aigne/doc-smith/output/structure-plan.json +249 -0
- package/.aigne/doc-smith/upload-cache.yaml +528 -0
- package/docs/_sidebar.md +19 -0
- package/docs/components-component-management-blocklet-studio.ja.md +194 -0
- package/docs/components-component-management-blocklet-studio.md +194 -0
- package/docs/components-component-management-blocklet-studio.zh-TW.md +194 -0
- package/docs/components-component-management-blocklet-studio.zh.md +194 -0
- package/docs/components-component-management-component-installer.ja.md +256 -0
- package/docs/components-component-management-component-installer.md +256 -0
- package/docs/components-component-management-component-installer.zh-TW.md +256 -0
- package/docs/components-component-management-component-installer.zh.md +256 -0
- package/docs/components-component-management.ja.md +59 -0
- package/docs/components-component-management.md +59 -0
- package/docs/components-component-management.zh-TW.md +59 -0
- package/docs/components-component-management.zh.md +59 -0
- package/docs/components-layout-dashboard.ja.md +231 -0
- package/docs/components-layout-dashboard.md +231 -0
- package/docs/components-layout-dashboard.zh-TW.md +231 -0
- package/docs/components-layout-dashboard.zh.md +231 -0
- package/docs/components-layout-footer.ja.md +165 -0
- package/docs/components-layout-footer.md +165 -0
- package/docs/components-layout-footer.zh-TW.md +165 -0
- package/docs/components-layout-footer.zh.md +165 -0
- package/docs/components-layout-header.ja.md +233 -0
- package/docs/components-layout-header.md +233 -0
- package/docs/components-layout-header.zh-TW.md +233 -0
- package/docs/components-layout-header.zh.md +233 -0
- package/docs/components-layout.ja.md +50 -0
- package/docs/components-layout.md +50 -0
- package/docs/components-layout.zh-TW.md +50 -0
- package/docs/components-layout.zh.md +50 -0
- package/docs/components-notifications.ja.md +173 -0
- package/docs/components-notifications.md +173 -0
- package/docs/components-notifications.zh-TW.md +174 -0
- package/docs/components-notifications.zh.md +173 -0
- package/docs/components-user-management-user-center.ja.md +183 -0
- package/docs/components-user-management-user-center.md +183 -0
- package/docs/components-user-management-user-center.zh-TW.md +183 -0
- package/docs/components-user-management-user-center.zh.md +183 -0
- package/docs/components-user-management-user-sessions.ja.md +164 -0
- package/docs/components-user-management-user-sessions.md +164 -0
- package/docs/components-user-management-user-sessions.zh-TW.md +164 -0
- package/docs/components-user-management-user-sessions.zh.md +164 -0
- package/docs/components-user-management.ja.md +76 -0
- package/docs/components-user-management.md +76 -0
- package/docs/components-user-management.zh-TW.md +76 -0
- package/docs/components-user-management.zh.md +76 -0
- package/docs/components-utilities-icon.ja.md +106 -0
- package/docs/components-utilities-icon.md +106 -0
- package/docs/components-utilities-icon.zh-TW.md +106 -0
- package/docs/components-utilities-icon.zh.md +106 -0
- package/docs/components-utilities.ja.md +136 -0
- package/docs/components-utilities.md +136 -0
- package/docs/components-utilities.zh-TW.md +136 -0
- package/docs/components-utilities.zh.md +136 -0
- package/docs/components.ja.md +27 -0
- package/docs/components.md +27 -0
- package/docs/components.zh-TW.md +27 -0
- package/docs/components.zh.md +27 -0
- package/docs/core-concepts.ja.md +164 -0
- package/docs/core-concepts.md +164 -0
- package/docs/core-concepts.zh-TW.md +164 -0
- package/docs/core-concepts.zh.md +164 -0
- package/docs/getting-started.ja.md +132 -0
- package/docs/getting-started.md +132 -0
- package/docs/getting-started.zh-TW.md +132 -0
- package/docs/getting-started.zh.md +132 -0
- package/docs/hooks-api.ja.md +214 -0
- package/docs/hooks-api.md +214 -0
- package/docs/hooks-api.zh-TW.md +214 -0
- package/docs/hooks-api.zh.md +214 -0
- package/docs/how-to-guides.ja.md +413 -0
- package/docs/how-to-guides.md +413 -0
- package/docs/how-to-guides.zh-TW.md +413 -0
- package/docs/how-to-guides.zh.md +413 -0
- package/docs/overview.ja.md +91 -0
- package/docs/overview.md +91 -0
- package/docs/overview.zh-TW.md +91 -0
- package/docs/overview.zh.md +91 -0
- package/glossary.md +12 -0
- package/lib/Dashboard/index.js +46 -42
- package/lib/Footer/index.js +51 -36
- package/lib/Header/index.js +48 -44
- package/lib/UserCenter/components/settings.js +1 -0
- package/lib/UserCenter/components/user-center.js +133 -133
- package/lib/blocklets.d.ts +13 -2
- package/lib/blocklets.js +40 -40
- package/lib/common/header-addons.js +37 -33
- package/package.json +7 -7
- package/src/Dashboard/index.jsx +8 -3
- package/src/Footer/index.jsx +22 -4
- package/src/Header/index.tsx +7 -2
- package/src/UserCenter/components/settings.tsx +1 -0
- package/src/UserCenter/components/user-center.tsx +6 -6
- package/src/blocklets.js +18 -9
- package/src/common/header-addons.jsx +7 -2
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
# 概覽
|
|
2
|
+
|
|
3
|
+
`@blocklet/ui-react` 程式庫提供了一系列必要的 React 元件,旨在加速應用程式(稱為 Blocklet)的開發。它透過智慧地使用 blocklet 的元資料,簡化了通用使用者介面元素的建立過程,讓開發者能以最少的精力建構出一致且功能豐富的使用者介面。
|
|
4
|
+
|
|
5
|
+
此程式庫建構於 `@arcblock/ux` 之上,後者是 Material-UI 的主題化擴充。這個基礎確保了所有元件都堅固、易於存取且易於自訂,以符合您應用程式的品牌形象。
|
|
6
|
+
|
|
7
|
+
## 解決的問題
|
|
8
|
+
|
|
9
|
+
現代 Web 應用程式通常需要一套標準的 UI 元件來進行佈局、使用者管理和通知。為每個專案從頭開始實作這些元件既耗時又可能導致不一致。Blocklet UI React 程式庫透過提供預先建構的元件來解決此問題,這些元件會根據您的 blocklet 元資料(`blocklet.yml`)自動進行設定。
|
|
10
|
+
|
|
11
|
+
這種由元資料驅動的方法意味著,諸如您應用程式的名稱、標誌、導覽連結和主題顏色等元素會自動應用於所有元件,從而大幅減少樣板程式碼並確保品牌一致性。
|
|
12
|
+
|
|
13
|
+
## 核心架構
|
|
14
|
+
|
|
15
|
+
此程式庫的架構設計旨在簡潔與自動化。當 `Header` 或 `Footer` 等元件被渲染時,它會從 `window.blocklet` 物件中讀取設定資料,該物件由 Blocklet Server 從您的 `blocklet.yml` 檔案中填入。這讓您可以在一個中央設定檔中定義 UI 的結構和品牌,而元件會相應地進行調整。
|
|
16
|
+
|
|
17
|
+
```d2
|
|
18
|
+
direction: down
|
|
19
|
+
|
|
20
|
+
blocklet-yml: {
|
|
21
|
+
label: "blocklet.yml\n(元資料來源)"
|
|
22
|
+
shape: rectangle
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
blocklet-server: {
|
|
26
|
+
label: "Blocklet Server"
|
|
27
|
+
shape: rectangle
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
window-blocklet: {
|
|
31
|
+
label: "window.blocklet\n(執行期設定)"
|
|
32
|
+
shape: rectangle
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
your-app: {
|
|
36
|
+
label: "您的應用程式"
|
|
37
|
+
shape: rectangle
|
|
38
|
+
|
|
39
|
+
Header: {
|
|
40
|
+
label: "<Header />"
|
|
41
|
+
shape: rectangle
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
Footer: {
|
|
45
|
+
label: "<Footer />"
|
|
46
|
+
shape: rectangle
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
rendered-ui: {
|
|
51
|
+
label: "渲染後的 UI"
|
|
52
|
+
shape: rectangle
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
blocklet-yml -> blocklet-server: "1. 定義元資料"
|
|
56
|
+
blocklet-server -> window-blocklet: "2. 在執行期填入"
|
|
57
|
+
window-blocklet -> your-app: "3. 元件讀取設定"
|
|
58
|
+
your-app -> rendered-ui: "4. 渲染已設定的 UI"
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
## 主要特色
|
|
62
|
+
|
|
63
|
+
- **元資料驅動:** 使用您在 `blocklet.yml` 中定義的 blocklet 名稱、標誌和導覽結構,自動設定 `Header` 和 `Footer` 等元件。
|
|
64
|
+
- **整合式階段作業管理:** 元件與 DID Connect 階段作業無縫整合,自動顯示使用者個人資料資訊、階段作業控制,以及基於角色的導覽連結存取權限。
|
|
65
|
+
- **響應式佈局:** 包含強大的佈局元件,如 `Dashboard`,可立即為管理介面提供響應式結構。
|
|
66
|
+
- **元件管理:** 提供 `ComponentInstaller` 和 `BlockletStudio` 等工具,以協助在 Blocklet 生態系統中管理相依性和資源。
|
|
67
|
+
|
|
68
|
+
## 核心元件
|
|
69
|
+
|
|
70
|
+
此程式庫分為幾個關鍵模組,每個模組處理應用程式 UI 的特定領域。
|
|
71
|
+
|
|
72
|
+
<x-cards data-columns="2">
|
|
73
|
+
<x-card data-title="佈局" data-icon="lucide:layout-template" data-href="/components/layout">
|
|
74
|
+
構成 blocklet 應用程式主要結構的核心元件,如 Header、Footer 和 Dashboard。
|
|
75
|
+
</x-card>
|
|
76
|
+
<x-card data-title="使用者管理" data-icon="lucide:users" data-href="/components/user-management">
|
|
77
|
+
一套用於處理使用者個人資料、階段作業管理和組織切換的元件。
|
|
78
|
+
</x-card>
|
|
79
|
+
<x-card data-title="元件管理" data-icon="lucide:box" data-href="/components/component-management">
|
|
80
|
+
用於在應用程式內動態安裝、發布和管理 blocklet 元件的工具。
|
|
81
|
+
</x-card>
|
|
82
|
+
<x-card data-title="公用程式" data-icon="lucide:wrench" data-href="/components/utilities">
|
|
83
|
+
一系列輔助元件和公用程式,例如多功能的圖示元件和主題提供者。
|
|
84
|
+
</x-card>
|
|
85
|
+
</x-cards>
|
|
86
|
+
|
|
87
|
+
## 總結
|
|
88
|
+
|
|
89
|
+
透過利用 `@blocklet/ui-react` 程式庫,您可以大幅縮短開發時間,並專注於應用程式的獨特功能。由元資料驅動的方法確保了一致性,並簡化了通用 UI 元素的管理。
|
|
90
|
+
|
|
91
|
+
要開始建構您的應用程式,請參閱 [入門指南](./getting-started.md),以取得安裝程式庫和渲染第一個元件的逐步教學。
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
# 概述
|
|
2
|
+
|
|
3
|
+
`@blocklet/ui-react` 库提供了一系列核心 React 组件,旨在加速 Blocklet 应用程序的开发。它通过智能地利用 blocklet 的元数据来简化通用用户界面元素的创建,使开发人员能够以最少的工作量构建一致且功能丰富的 UI。
|
|
4
|
+
|
|
5
|
+
该库基于 `@arcblock/ux` 构建,后者是 Material-UI 的一个主题扩展。这一基础确保了所有组件都功能强大、易于访问,并且可以轻松定制以适应您的应用程序品牌。
|
|
6
|
+
|
|
7
|
+
## 它解决的问题
|
|
8
|
+
|
|
9
|
+
现代 Web 应用程序通常需要一套标准的 UI 组件用于布局、用户管理和通知。为每个项目从头开始实施这些组件非常耗时,并可能导致不一致性。Blocklet UI React 库通过提供预构建的组件来解决这个问题,这些组件会根据您的 blocklet 元数据(`blocklet.yml`)自动进行配置。
|
|
10
|
+
|
|
11
|
+
这种元数据驱动的方法意味着,诸如应用程序名称、徽标、导航链接和主题颜色等元素会自动应用于所有组件,从而极大地减少了样板代码并确保了品牌一致性。
|
|
12
|
+
|
|
13
|
+
## 核心架构
|
|
14
|
+
|
|
15
|
+
该库的架构设计旨在实现简洁和自动化。当渲染 `Header` 或 `Footer` 等组件时,它会从 `window.blocklet` 对象中读取配置数据,该对象由 Blocklet Server 从您的 `blocklet.yml` 文件中填充。这使您能够在一个中央配置文件中定义 UI 的结构和品牌,而组件会相应地进行调整。
|
|
16
|
+
|
|
17
|
+
```d2
|
|
18
|
+
direction: down
|
|
19
|
+
|
|
20
|
+
blocklet-yml: {
|
|
21
|
+
label: "blocklet.yml\n(元数据源)"
|
|
22
|
+
shape: rectangle
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
blocklet-server: {
|
|
26
|
+
label: "Blocklet Server"
|
|
27
|
+
shape: rectangle
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
window-blocklet: {
|
|
31
|
+
label: "window.blocklet\n(运行时配置)"
|
|
32
|
+
shape: rectangle
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
your-app: {
|
|
36
|
+
label: "您的应用程序"
|
|
37
|
+
shape: rectangle
|
|
38
|
+
|
|
39
|
+
Header: {
|
|
40
|
+
label: "<Header />"
|
|
41
|
+
shape: rectangle
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
Footer: {
|
|
45
|
+
label: "<Footer />"
|
|
46
|
+
shape: rectangle
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
rendered-ui: {
|
|
51
|
+
label: "渲染后的 UI"
|
|
52
|
+
shape: rectangle
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
blocklet-yml -> blocklet-server: "1. 定义元数据"
|
|
56
|
+
blocklet-server -> window-blocklet: "2. 在运行时填充"
|
|
57
|
+
window-blocklet -> your-app: "3. 组件读取配置"
|
|
58
|
+
your-app -> rendered-ui: "4. 渲染配置好的 UI"
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
## 主要特性
|
|
62
|
+
|
|
63
|
+
- **元数据驱动:** 使用您在 `blocklet.yml` 中定义的 blocklet 名称、徽标和导航结构,自动配置 `Header` 和 `Footer` 等组件。
|
|
64
|
+
- **集成会话管理:** 组件与 DID Connect 会话无缝集成,自动显示用户个人资料信息、会话控制以及基于角色的导航链接访问权限。
|
|
65
|
+
- **响应式布局:** 包含 `Dashboard` 等强大的布局组件,为管理界面提供开箱即用的响应式结构。
|
|
66
|
+
- **组件管理:** 提供 `ComponentInstaller` 和 `BlockletStudio` 等工具,帮助在 Blocklet 生态系统中管理依赖项和资源。
|
|
67
|
+
|
|
68
|
+
## 核心组件
|
|
69
|
+
|
|
70
|
+
该库分为几个关键模块,每个模块都针对应用程序 UI 的一个特定领域。
|
|
71
|
+
|
|
72
|
+
<x-cards data-columns="2">
|
|
73
|
+
<x-card data-title="布局" data-icon="lucide:layout-template" data-href="/components/layout">
|
|
74
|
+
构成 blocklet 应用程序主要结构的主要组件,如 Header、Footer 和 Dashboard。
|
|
75
|
+
</x-card>
|
|
76
|
+
<x-card data-title="用户管理" data-icon="lucide:users" data-href="/components/user-management">
|
|
77
|
+
一套用于处理用户个人资料、会话管理和组织切换的组件。
|
|
78
|
+
</x-card>
|
|
79
|
+
<x-card data-title="组件管理" data-icon="lucide:box" data-href="/components/component-management">
|
|
80
|
+
用于在应用程序内动态安装、发布和管理 blocklet 组件的工具。
|
|
81
|
+
</x-card>
|
|
82
|
+
<x-card data-title="实用工具" data-icon="lucide:wrench" data-href="/components/utilities">
|
|
83
|
+
一系列辅助组件和实用工具,例如通用的 Icon 组件和主题提供程序。
|
|
84
|
+
</x-card>
|
|
85
|
+
</x-cards>
|
|
86
|
+
|
|
87
|
+
## 总结
|
|
88
|
+
|
|
89
|
+
通过利用 `@blocklet/ui-react` 库,您可以显著减少开发时间,专注于应用程序的独特功能。元数据驱动的方法确保了一致性,并简化了常用 UI 元素的管理。
|
|
90
|
+
|
|
91
|
+
要开始构建您的应用程序,请参阅 [入门指南](./getting-started.md),其中提供了关于如何安装该库并渲染您的第一个组件的分步教程。
|
package/glossary.md
ADDED
package/lib/Dashboard/index.js
CHANGED
|
@@ -1,23 +1,23 @@
|
|
|
1
1
|
import { jsx as i } from "react/jsx-runtime";
|
|
2
2
|
import "iconify-icon";
|
|
3
|
-
import { use as
|
|
3
|
+
import { use as R, useMemo as w, useLayoutEffect as L } from "react";
|
|
4
4
|
import t from "prop-types";
|
|
5
|
-
import { SessionContext as
|
|
6
|
-
import { useLocaleContext as
|
|
7
|
-
import
|
|
8
|
-
import
|
|
9
|
-
import
|
|
10
|
-
import { SessionManagerProps as
|
|
11
|
-
import { mapRecursive as
|
|
12
|
-
import { formatBlockletInfo as
|
|
13
|
-
import
|
|
14
|
-
import { useWalletHiddenTopbar as
|
|
15
|
-
function
|
|
16
|
-
meta:
|
|
17
|
-
fallbackUrl:
|
|
5
|
+
import { SessionContext as T } from "@arcblock/did-connect-react/lib/Session";
|
|
6
|
+
import { useLocaleContext as z } from "@arcblock/ux/lib/Locale/context";
|
|
7
|
+
import A from "@arcblock/ux/lib/Img";
|
|
8
|
+
import C from "@arcblock/ux/lib/Layout/dashboard";
|
|
9
|
+
import D from "@arcblock/ux/lib/hooks/use-blocklet-logo";
|
|
10
|
+
import { SessionManagerProps as M, BlockletMetaProps as O } from "../types.js";
|
|
11
|
+
import { mapRecursive as j, flatRecursive as H, matchPaths as S } from "../utils.js";
|
|
12
|
+
import { formatBlockletInfo as _, getLocalizedNavigation as E, filterNavByRole as U, publicPath as m } from "../blocklets.js";
|
|
13
|
+
import q from "../common/header-addons.js";
|
|
14
|
+
import { useWalletHiddenTopbar as F } from "../common/wallet-hidden-topbar.js";
|
|
15
|
+
function G({
|
|
16
|
+
meta: a = {},
|
|
17
|
+
fallbackUrl: s = m,
|
|
18
18
|
invalidPathFallback: l = null,
|
|
19
19
|
headerAddons: k = void 0,
|
|
20
|
-
sessionManagerProps:
|
|
20
|
+
sessionManagerProps: N = {
|
|
21
21
|
showRole: !0,
|
|
22
22
|
// dashboard 默认退出登录行为: 跳转到 (root) blocklet 首页
|
|
23
23
|
onLogout: () => {
|
|
@@ -25,24 +25,28 @@ function F({
|
|
|
25
25
|
}
|
|
26
26
|
},
|
|
27
27
|
links: c = [],
|
|
28
|
-
showDomainWarningDialog:
|
|
28
|
+
showDomainWarningDialog: P = !0,
|
|
29
29
|
...h
|
|
30
30
|
}) {
|
|
31
|
-
|
|
32
|
-
const d =
|
|
33
|
-
const e = Object.assign({}, window.blocklet,
|
|
31
|
+
F();
|
|
32
|
+
const d = R(T)?.session?.user, g = d?.role, { locale: x, defaultLocale: y } = z() || {}, r = w(() => {
|
|
33
|
+
const e = Object.assign({}, window.blocklet, a);
|
|
34
34
|
try {
|
|
35
|
-
return
|
|
35
|
+
return _(e);
|
|
36
36
|
} catch (n) {
|
|
37
37
|
return console.error("Failed to format blocklet info", n, e), e;
|
|
38
38
|
}
|
|
39
|
-
}, [
|
|
40
|
-
let e =
|
|
41
|
-
|
|
39
|
+
}, [a]), { localizedNav: v, flattened: f, matchedIndex: b } = w(() => {
|
|
40
|
+
let e = E({
|
|
41
|
+
navigation: r?.navigation?.dashboard,
|
|
42
|
+
locale: x,
|
|
43
|
+
defaultLocale: y
|
|
44
|
+
}) || [];
|
|
45
|
+
e = U(e, g), e = j(
|
|
42
46
|
e,
|
|
43
47
|
(o) => {
|
|
44
48
|
let u = null;
|
|
45
|
-
return o.icon && (o.icon.startsWith("http") || o.icon.startsWith("data:") ? u = /* @__PURE__ */ i(
|
|
49
|
+
return o.icon && (o.icon.startsWith("http") || o.icon.startsWith("data:") ? u = /* @__PURE__ */ i(A, { src: o.icon }) : u = /* @__PURE__ */ i("iconify-icon", { height: "100%", width: "100%", icon: o.icon })), {
|
|
46
50
|
id: o.id,
|
|
47
51
|
title: o.title,
|
|
48
52
|
url: o.link,
|
|
@@ -54,37 +58,37 @@ function F({
|
|
|
54
58
|
},
|
|
55
59
|
"items"
|
|
56
60
|
);
|
|
57
|
-
const n =
|
|
61
|
+
const n = H(e).filter((o) => !!o.url), p = S(n.map((o) => o.url));
|
|
58
62
|
return p !== -1 && (n[p].active = !0), { localizedNav: e, flattened: n, matchedIndex: p };
|
|
59
|
-
}, [r, x, g]),
|
|
60
|
-
meta:
|
|
63
|
+
}, [r, x, y, g]), W = typeof c == "function" ? c(v) : [...v, ...c], B = D({
|
|
64
|
+
meta: a
|
|
61
65
|
});
|
|
62
|
-
if (
|
|
63
|
-
d && !f?.length &&
|
|
64
|
-
}, [
|
|
66
|
+
if (L(() => {
|
|
67
|
+
d && !f?.length && s && (window.location.href = s);
|
|
68
|
+
}, [s]), L(() => {
|
|
65
69
|
d && f?.length && b === -1 && l && l();
|
|
66
70
|
}, [l, f, b]), !r.appName)
|
|
67
71
|
return null;
|
|
68
|
-
const { appName:
|
|
72
|
+
const { appName: I } = r;
|
|
69
73
|
return /* @__PURE__ */ i(
|
|
70
|
-
|
|
74
|
+
C,
|
|
71
75
|
{
|
|
72
|
-
title:
|
|
76
|
+
title: I,
|
|
73
77
|
fullWidth: !0,
|
|
74
78
|
sidebarWidth: 128,
|
|
75
79
|
legacy: !1,
|
|
76
|
-
links:
|
|
80
|
+
links: W,
|
|
77
81
|
...h,
|
|
78
82
|
headerProps: {
|
|
79
83
|
homeLink: m,
|
|
80
|
-
logo: /* @__PURE__ */ i("img", { src:
|
|
84
|
+
logo: /* @__PURE__ */ i("img", { src: B, alt: "logo" }),
|
|
81
85
|
addons: /* @__PURE__ */ i(
|
|
82
|
-
|
|
86
|
+
q,
|
|
83
87
|
{
|
|
84
88
|
formattedBlocklet: r,
|
|
85
89
|
addons: k,
|
|
86
|
-
sessionManagerProps:
|
|
87
|
-
showDomainWarningDialog:
|
|
90
|
+
sessionManagerProps: N,
|
|
91
|
+
showDomainWarningDialog: P
|
|
88
92
|
}
|
|
89
93
|
),
|
|
90
94
|
...h.headerProps
|
|
@@ -92,17 +96,17 @@ function F({
|
|
|
92
96
|
}
|
|
93
97
|
);
|
|
94
98
|
}
|
|
95
|
-
|
|
96
|
-
meta:
|
|
99
|
+
G.propTypes = {
|
|
100
|
+
meta: O,
|
|
97
101
|
// 如果当前用户没有权限访问任何导航菜单, 则自动跳转到 fallbackUrl, 默认值为 publicPath, 设置为 null 表示禁用自动跳转
|
|
98
102
|
fallbackUrl: t.string,
|
|
99
103
|
// 当前路径未匹配任何 nav links 时的 fallback, 默认行为跳转到首个可用的 nav link
|
|
100
104
|
invalidPathFallback: t.func,
|
|
101
105
|
headerAddons: t.oneOfType([t.func, t.node]),
|
|
102
|
-
sessionManagerProps:
|
|
106
|
+
sessionManagerProps: M,
|
|
103
107
|
links: t.oneOfType([t.array, t.func]),
|
|
104
108
|
showDomainWarningDialog: t.bool
|
|
105
109
|
};
|
|
106
110
|
export {
|
|
107
|
-
|
|
111
|
+
G as default
|
|
108
112
|
};
|
package/lib/Footer/index.js
CHANGED
|
@@ -1,26 +1,26 @@
|
|
|
1
|
-
import { jsx as
|
|
2
|
-
import { useMemo as
|
|
3
|
-
import
|
|
4
|
-
import { styled as
|
|
1
|
+
import { jsx as s } from "react/jsx-runtime";
|
|
2
|
+
import { useMemo as d } from "react";
|
|
3
|
+
import F from "prop-types";
|
|
4
|
+
import { styled as x, useTheme as T, deepmerge as B, ThemeProvider as L } from "@arcblock/ux/lib/Theme";
|
|
5
5
|
import { withErrorBoundary as M } from "react-error-boundary";
|
|
6
6
|
import { useLocaleContext as N } from "@arcblock/ux/lib/Locale/context";
|
|
7
7
|
import { ErrorFallback as w } from "@arcblock/ux/lib/ErrorBoundary";
|
|
8
|
-
import
|
|
9
|
-
import
|
|
10
|
-
import
|
|
11
|
-
import { mapRecursive as
|
|
12
|
-
import { formatBlockletInfo as
|
|
13
|
-
import { BlockletMetaProps as
|
|
14
|
-
import
|
|
15
|
-
function
|
|
16
|
-
const { locale: i } = N() || {},
|
|
8
|
+
import j from "@arcblock/ux/lib/hooks/use-blocklet-logo";
|
|
9
|
+
import C from "lodash/omit";
|
|
10
|
+
import E from "./internal-footer.js";
|
|
11
|
+
import { mapRecursive as I } from "../utils.js";
|
|
12
|
+
import { formatBlockletInfo as P, getLocalizedNavigation as l } from "../blocklets.js";
|
|
13
|
+
import { BlockletMetaProps as z } from "../types.js";
|
|
14
|
+
import D from "../libs/with-hide-when-embed.js";
|
|
15
|
+
function f({ meta: o = {}, theme: t = {}, ...c }) {
|
|
16
|
+
const { locale: i, defaultLocale: a } = N() || {}, m = T(), r = d(() => {
|
|
17
17
|
const e = Object.assign({}, window.blocklet, o);
|
|
18
18
|
try {
|
|
19
|
-
return
|
|
20
|
-
} catch (
|
|
21
|
-
return console.error("Failed to format blocklet info",
|
|
19
|
+
return P(e);
|
|
20
|
+
} catch ($) {
|
|
21
|
+
return console.error("Failed to format blocklet info", $, e), e;
|
|
22
22
|
}
|
|
23
|
-
}, [o]),
|
|
23
|
+
}, [o]), p = d(() => B(m, t), [m, t]), b = j({
|
|
24
24
|
key: "xs",
|
|
25
25
|
// 始终优先长 logo
|
|
26
26
|
meta: o,
|
|
@@ -28,18 +28,33 @@ function d({ meta: o = {}, theme: t = {}, ...n }) {
|
|
|
28
28
|
});
|
|
29
29
|
if (!r.appName)
|
|
30
30
|
return null;
|
|
31
|
-
const { appName:
|
|
32
|
-
footerNav: l(
|
|
33
|
-
|
|
34
|
-
|
|
31
|
+
const { appName: g, appDescription: k, description: u, copyright: h } = r, v = p.palette.background.default, n = {
|
|
32
|
+
footerNav: l({
|
|
33
|
+
navigation: r?.navigation?.footer,
|
|
34
|
+
locale: i,
|
|
35
|
+
defaultLocale: a,
|
|
36
|
+
section: "footer"
|
|
37
|
+
}) || [],
|
|
38
|
+
socialMedia: l({
|
|
39
|
+
navigation: r?.navigation?.social,
|
|
40
|
+
locale: i,
|
|
41
|
+
defaultLocale: a,
|
|
42
|
+
section: "footer"
|
|
43
|
+
}) || [],
|
|
44
|
+
links: l({
|
|
45
|
+
navigation: r?.navigation?.bottom,
|
|
46
|
+
locale: i,
|
|
47
|
+
defaultLocale: a,
|
|
48
|
+
section: "footer"
|
|
49
|
+
}) || []
|
|
35
50
|
}, y = {
|
|
36
51
|
brand: {
|
|
37
|
-
name:
|
|
38
|
-
description: k ||
|
|
39
|
-
logo:
|
|
52
|
+
name: g,
|
|
53
|
+
description: k || u,
|
|
54
|
+
logo: b
|
|
40
55
|
},
|
|
41
|
-
navigation:
|
|
42
|
-
|
|
56
|
+
navigation: I(
|
|
57
|
+
n.footerNav,
|
|
43
58
|
(e) => ({
|
|
44
59
|
...e,
|
|
45
60
|
label: e.title,
|
|
@@ -47,24 +62,24 @@ function d({ meta: o = {}, theme: t = {}, ...n }) {
|
|
|
47
62
|
}),
|
|
48
63
|
"items"
|
|
49
64
|
),
|
|
50
|
-
copyright:
|
|
51
|
-
socialMedia:
|
|
52
|
-
links:
|
|
65
|
+
copyright: h,
|
|
66
|
+
socialMedia: n.socialMedia,
|
|
67
|
+
links: n.links.map((e) => ({ ...e, label: e.title }))
|
|
53
68
|
};
|
|
54
|
-
return /* @__PURE__ */
|
|
69
|
+
return /* @__PURE__ */ s(L, { theme: p, children: /* @__PURE__ */ s(H, { ...y, ...C(c, ["bordered"]), $bordered: c?.bordered, $bgcolor: v }) });
|
|
55
70
|
}
|
|
56
|
-
|
|
57
|
-
meta:
|
|
71
|
+
f.propTypes = {
|
|
72
|
+
meta: z,
|
|
58
73
|
// 允许覆盖 footer 内置的 theme
|
|
59
|
-
theme:
|
|
74
|
+
theme: F.object
|
|
60
75
|
};
|
|
61
|
-
const
|
|
76
|
+
const H = x(E)`
|
|
62
77
|
${({ $bordered: o, theme: t }) => `border-top: 1px solid ${o && t.palette.divider};`}
|
|
63
78
|
color: ${({ theme: o }) => o.palette.text.secondary};
|
|
64
79
|
${({ $bgcolor: o }) => o && `background-color: ${o};`}
|
|
65
|
-
`,
|
|
80
|
+
`, _ = M(D(f), {
|
|
66
81
|
FallbackComponent: w
|
|
67
82
|
});
|
|
68
83
|
export {
|
|
69
|
-
|
|
84
|
+
_ as default
|
|
70
85
|
};
|
package/lib/Header/index.js
CHANGED
|
@@ -1,25 +1,25 @@
|
|
|
1
1
|
import { jsx as a } from "react/jsx-runtime";
|
|
2
2
|
import { useMemo as f } from "react";
|
|
3
|
-
import { useMemoizedFn as
|
|
4
|
-
import { withErrorBoundary as
|
|
5
|
-
import { ErrorFallback as
|
|
6
|
-
import { styled as
|
|
3
|
+
import { useMemoizedFn as $ } from "ahooks";
|
|
4
|
+
import { withErrorBoundary as C } from "react-error-boundary";
|
|
5
|
+
import { ErrorFallback as H } from "@arcblock/ux/lib/ErrorBoundary";
|
|
6
|
+
import { styled as _, useTheme as w, deepmerge as A, ThemeProvider as L } from "@arcblock/ux/lib/Theme";
|
|
7
7
|
import { ResponsiveHeader as B } from "@arcblock/ux/lib/Header";
|
|
8
|
-
import
|
|
9
|
-
import { useLocaleContext as
|
|
10
|
-
import { translate as
|
|
11
|
-
import
|
|
12
|
-
import
|
|
8
|
+
import M, { Products as R } from "@arcblock/ux/lib/NavMenu";
|
|
9
|
+
import { useLocaleContext as z } from "@arcblock/ux/lib/Locale/context";
|
|
10
|
+
import { translate as F } from "@arcblock/ux/lib/Locale/util";
|
|
11
|
+
import O from "@arcblock/ux/lib/hooks/use-blocklet-logo";
|
|
12
|
+
import P from "lodash/omit";
|
|
13
13
|
import I from "lodash/isFinite";
|
|
14
|
-
import
|
|
15
|
-
import { getUTMUrl as
|
|
16
|
-
import
|
|
17
|
-
import { mapRecursive as
|
|
18
|
-
import { formatBlockletInfo as
|
|
19
|
-
import
|
|
20
|
-
import { useWalletHiddenTopbar as
|
|
21
|
-
import
|
|
22
|
-
const
|
|
14
|
+
import U from "clsx";
|
|
15
|
+
import { getUTMUrl as W } from "@arcblock/ux/lib/withTracker/libs/utm";
|
|
16
|
+
import j from "../Icon/index.js";
|
|
17
|
+
import { mapRecursive as S, flatRecursive as G, matchPaths as K } from "../utils.js";
|
|
18
|
+
import { formatBlockletInfo as q, getLocalizedNavigation as D, publicPath as J } from "../blocklets.js";
|
|
19
|
+
import Q from "../common/header-addons.js";
|
|
20
|
+
import { useWalletHiddenTopbar as V } from "../common/wallet-hidden-topbar.js";
|
|
21
|
+
import X from "../libs/with-hide-when-embed.js";
|
|
22
|
+
const Y = {
|
|
23
23
|
en: {
|
|
24
24
|
products: "Products"
|
|
25
25
|
},
|
|
@@ -32,12 +32,12 @@ const X = {
|
|
|
32
32
|
ja: {
|
|
33
33
|
products: "製品"
|
|
34
34
|
}
|
|
35
|
-
},
|
|
35
|
+
}, Z = (r) => {
|
|
36
36
|
if (!r?.length)
|
|
37
37
|
return { navItems: [], activeId: null };
|
|
38
38
|
let t = 1;
|
|
39
|
-
const c =
|
|
40
|
-
const i = e.icon ? /* @__PURE__ */ a(
|
|
39
|
+
const c = S(r, (e) => {
|
|
40
|
+
const i = e.icon ? /* @__PURE__ */ a(j, { icon: e.icon }) : null;
|
|
41
41
|
if (e.items)
|
|
42
42
|
return {
|
|
43
43
|
id: `${t++}`,
|
|
@@ -51,35 +51,35 @@ const X = {
|
|
|
51
51
|
rel: "noreferrer"
|
|
52
52
|
}), {
|
|
53
53
|
id: `${t++}`,
|
|
54
|
-
label: /* @__PURE__ */ a("a", { href:
|
|
54
|
+
label: /* @__PURE__ */ a("a", { href: W(e.link, "header"), ...s, children: e.title }),
|
|
55
55
|
icon: i,
|
|
56
56
|
description: e.description,
|
|
57
57
|
link: e.link
|
|
58
58
|
};
|
|
59
|
-
}, "items"), l =
|
|
59
|
+
}, "items"), l = G(c), p = K(l.map((e) => e.link));
|
|
60
60
|
return { navItems: c, activeId: p >= 0 ? l[p].id : null };
|
|
61
61
|
};
|
|
62
|
-
function
|
|
62
|
+
function ee({
|
|
63
63
|
meta: r = {},
|
|
64
64
|
addons: t = void 0,
|
|
65
65
|
sessionManagerProps: h = {
|
|
66
66
|
showRole: !0
|
|
67
67
|
},
|
|
68
|
-
homeLink: c =
|
|
68
|
+
homeLink: c = J,
|
|
69
69
|
theme: l = {},
|
|
70
70
|
hideNavMenu: p = !1,
|
|
71
71
|
showDomainWarningDialog: e = !0,
|
|
72
72
|
...i
|
|
73
73
|
}) {
|
|
74
|
-
|
|
75
|
-
const s =
|
|
74
|
+
V();
|
|
75
|
+
const s = w(), { locale: g, defaultLocale: T } = z() || {}, x = $((o, n = {}) => F(Y, o, g, "en", n)), d = f(() => {
|
|
76
76
|
const o = Object.assign({}, window.blocklet, r);
|
|
77
77
|
try {
|
|
78
|
-
return
|
|
78
|
+
return q(o);
|
|
79
79
|
} catch (n) {
|
|
80
80
|
return console.error("Failed to format blocklet info", n, o), o;
|
|
81
81
|
}
|
|
82
|
-
}, [r]), m = f(() =>
|
|
82
|
+
}, [r]), m = f(() => A(s, l), [s, l]), y = O({
|
|
83
83
|
meta: r,
|
|
84
84
|
theme: l
|
|
85
85
|
}), { productsOrder: b, productsType: k } = f(() => {
|
|
@@ -97,20 +97,24 @@ function Z({
|
|
|
97
97
|
}, [d]);
|
|
98
98
|
if (!d.appName)
|
|
99
99
|
return null;
|
|
100
|
-
const
|
|
100
|
+
const E = D({
|
|
101
|
+
navigation: d?.navigation?.header,
|
|
102
|
+
locale: g,
|
|
103
|
+
defaultLocale: T
|
|
104
|
+
}), v = Z(E), { navItems: u, activeId: N } = v;
|
|
101
105
|
return k && Number.isInteger(b) && u.splice(b, 0, {
|
|
102
|
-
label:
|
|
106
|
+
label: x("products"),
|
|
103
107
|
// eslint-disable-next-line react/no-unstable-nested-components
|
|
104
|
-
children: () => /* @__PURE__ */ a(
|
|
105
|
-
}), /* @__PURE__ */ a(
|
|
106
|
-
|
|
108
|
+
children: () => /* @__PURE__ */ a(R, { type: k })
|
|
109
|
+
}), /* @__PURE__ */ a(L, { theme: m, children: /* @__PURE__ */ a(
|
|
110
|
+
oe,
|
|
107
111
|
{
|
|
108
112
|
homeLink: c,
|
|
109
|
-
logo: /* @__PURE__ */ a("img", { src:
|
|
113
|
+
logo: /* @__PURE__ */ a("img", { src: y, alt: "logo" }),
|
|
110
114
|
addons: (
|
|
111
115
|
// @ts-ignore
|
|
112
116
|
/* @__PURE__ */ a(
|
|
113
|
-
|
|
117
|
+
Q,
|
|
114
118
|
{
|
|
115
119
|
formattedBlocklet: d,
|
|
116
120
|
addons: typeof t == "function" ? (o) => t(o, { navigation: v }) : t,
|
|
@@ -119,17 +123,17 @@ function Z({
|
|
|
119
123
|
}
|
|
120
124
|
)
|
|
121
125
|
),
|
|
122
|
-
...
|
|
126
|
+
...P(i, ["bordered"]),
|
|
123
127
|
$bordered: i?.bordered,
|
|
124
128
|
$bgcolor: m.palette.background.default,
|
|
125
|
-
className:
|
|
129
|
+
className: U("blocklet__header", i.className),
|
|
126
130
|
children: p || !u?.length ? null : ({ isMobile: o }) => (
|
|
127
131
|
// @ts-ignore
|
|
128
132
|
/* @__PURE__ */ a(
|
|
129
|
-
|
|
133
|
+
M,
|
|
130
134
|
{
|
|
131
135
|
mode: o ? "inline" : "horizontal",
|
|
132
|
-
activeId:
|
|
136
|
+
activeId: N,
|
|
133
137
|
items: u,
|
|
134
138
|
className: "header-nav",
|
|
135
139
|
bgColor: "transparent",
|
|
@@ -141,7 +145,7 @@ function Z({
|
|
|
141
145
|
}
|
|
142
146
|
) });
|
|
143
147
|
}
|
|
144
|
-
const
|
|
148
|
+
const oe = _(B)`
|
|
145
149
|
${({ $bgcolor: r }) => `background-color: ${r || "#fff"};`}
|
|
146
150
|
.header-logo {
|
|
147
151
|
min-width: 44px;
|
|
@@ -152,9 +156,9 @@ const ee = H(B)`
|
|
|
152
156
|
min-width: 32px;
|
|
153
157
|
}
|
|
154
158
|
}
|
|
155
|
-
`,
|
|
156
|
-
FallbackComponent:
|
|
159
|
+
`, Ne = C(X(ee), {
|
|
160
|
+
FallbackComponent: H
|
|
157
161
|
});
|
|
158
162
|
export {
|
|
159
|
-
|
|
163
|
+
Ne as default
|
|
160
164
|
};
|