@houser/edus-plugin 1.0.7 → 1.0.8

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/lib/client.js CHANGED
@@ -7046,27 +7046,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7046
7046
  });
7047
7047
  }
7048
7048
  //#endregion
7049
- //#region lib/types/client/MyWorksAction.js
7049
+ //#region lib/types/client/MyWorksPanel.js
7050
7050
  const PAGE_SIZE = 8;
7051
- let dialogOpen = false;
7052
- const dialogListeners = /* @__PURE__ */ new Set();
7053
- const dialog = {
7054
- getSnapshot: () => dialogOpen,
7055
- subscribe(listener) {
7056
- dialogListeners.add(listener);
7057
- return () => {
7058
- dialogListeners.delete(listener);
7059
- };
7060
- },
7061
- open() {
7062
- dialogOpen = true;
7063
- for (const listener of dialogListeners) listener();
7064
- },
7065
- close() {
7066
- dialogOpen = false;
7067
- for (const listener of dialogListeners) listener();
7068
- }
7069
- };
7070
7051
  function Icon({ name, size = 16 }) {
7071
7052
  return (0, react_jsx_runtime.jsx)("svg", {
7072
7053
  "aria-hidden": "true",
@@ -7079,7 +7060,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7079
7060
  strokeLinecap: "round",
7080
7061
  strokeLinejoin: "round",
7081
7062
  children: {
7082
- close: (0, react_jsx_runtime.jsx)(react_jsx_runtime.Fragment, { children: (0, react_jsx_runtime.jsx)("path", { d: "M3 3l10 10M13 3L3 13" }) }),
7083
7063
  copy: (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [(0, react_jsx_runtime.jsx)("rect", {
7084
7064
  x: "5.5",
7085
7065
  y: "5.5",
@@ -7112,72 +7092,15 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7112
7092
  }
7113
7093
  }
7114
7094
  const styles = {
7115
- triggerRow: {
7116
- width: "calc(100% + 4px)",
7117
- display: "flex",
7118
- alignItems: "center",
7119
- gap: 8,
7120
- flex: "none",
7121
- margin: "4px -2px"
7122
- },
7123
- triggerRowRail: {
7124
- width: 36,
7125
- margin: "8px 0 10px"
7126
- },
7127
- trigger: {
7128
- boxSizing: "border-box",
7129
- width: "auto",
7095
+ page: {
7130
7096
  minWidth: 0,
7131
- height: 42,
7132
- display: "flex",
7133
- alignItems: "center",
7134
- justifyContent: "flex-start",
7097
+ minHeight: 0,
7135
7098
  flex: 1,
7136
- gap: 8,
7137
- margin: 0,
7138
- padding: "0 10px 0 8px",
7139
- overflow: "hidden",
7140
- border: 0,
7141
- borderRadius: 12,
7142
- background: "transparent",
7143
- color: "var(--dsw-alias-label-primary)",
7144
- font: "inherit",
7145
- fontSize: 14,
7146
- lineHeight: "22px",
7147
- cursor: "pointer",
7148
- whiteSpace: "nowrap"
7149
- },
7150
- triggerRail: {
7151
- width: 36,
7152
- height: 36,
7153
- flex: "none",
7154
- gap: 0,
7155
- padding: 0,
7156
- borderRadius: "50%",
7157
- justifyContent: "center"
7158
- },
7159
- overlay: {
7160
- position: "fixed",
7161
- inset: 0,
7162
- zIndex: 1200,
7163
- display: "grid",
7164
- placeItems: "center",
7165
- padding: 24,
7166
- background: "var(--dsw-alias-bg-mask-1, rgb(0 0 0 / 32%))",
7167
- backdropFilter: "blur(5px)",
7168
- pointerEvents: "auto"
7169
- },
7170
- dialog: {
7171
- width: "min(960px, calc(100vw - 32px))",
7172
- height: "min(780px, calc(100vh - 32px))",
7173
7099
  display: "flex",
7174
7100
  flexDirection: "column",
7175
7101
  overflow: "hidden",
7176
- border: "1px solid var(--dsw-alias-border-inverted)",
7177
- borderRadius: 22,
7178
- background: "var(--dsw-alias-bg-layer-2)",
7179
- color: "var(--dsw-alias-label-primary)",
7180
- boxShadow: "var(--dsw-shadow-lv3, 0 28px 90px rgb(0 0 0 / 30%))"
7102
+ background: "var(--dsw-alias-bg-base)",
7103
+ color: "var(--dsw-alias-label-primary)"
7181
7104
  },
7182
7105
  header: {
7183
7106
  display: "flex",
@@ -7203,18 +7126,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7203
7126
  alignItems: "center",
7204
7127
  gap: 12
7205
7128
  },
7206
- close: {
7207
- width: 32,
7208
- height: 32,
7209
- display: "grid",
7210
- placeItems: "center",
7211
- flex: "none",
7212
- border: 0,
7213
- borderRadius: 9,
7214
- background: "transparent",
7215
- color: "var(--dsw-alias-label-secondary)",
7216
- cursor: "pointer"
7217
- },
7218
7129
  toolbar: {
7219
7130
  display: "flex",
7220
7131
  alignItems: "center",
@@ -7225,6 +7136,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7225
7136
  search: {
7226
7137
  minWidth: 0,
7227
7138
  flex: 1,
7139
+ maxWidth: 420,
7228
7140
  height: 36,
7229
7141
  boxSizing: "border-box",
7230
7142
  border: "1px solid var(--dsw-alias-border-l2)",
@@ -7272,7 +7184,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7272
7184
  overflow: "hidden",
7273
7185
  border: "1px solid var(--dsw-alias-border-l2)",
7274
7186
  borderRadius: 14,
7275
- background: "var(--dsw-alias-bg-base)"
7187
+ background: "var(--dsw-alias-bg-layer-2)"
7276
7188
  },
7277
7189
  thumb: {
7278
7190
  aspectRatio: "3 / 2",
@@ -7303,14 +7215,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7303
7215
  textOverflow: "ellipsis",
7304
7216
  whiteSpace: "nowrap"
7305
7217
  },
7306
- description: {
7307
- height: 38,
7308
- margin: "7px 0 11px",
7309
- overflow: "hidden",
7310
- color: "var(--dsw-alias-label-secondary)",
7311
- fontSize: 12,
7312
- lineHeight: 1.55
7313
- },
7314
7218
  meta: {
7315
7219
  display: "flex",
7316
7220
  alignItems: "center",
@@ -7399,7 +7303,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7399
7303
  border: 0,
7400
7304
  padding: 0,
7401
7305
  background: "transparent",
7402
- color: "var(--dsw-alias-label-tertiary)",
7306
+ color: "orange",
7403
7307
  font: "inherit",
7404
7308
  fontSize: 12,
7405
7309
  lineHeight: 1,
@@ -7440,37 +7344,21 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7440
7344
  if (status === 3) return "失败";
7441
7345
  return `状态 ${status}`;
7442
7346
  }
7443
- function MyWorksAction({ wide }) {
7444
- return (0, react_jsx_runtime.jsx)("div", {
7445
- style: {
7446
- ...styles.triggerRow,
7447
- ...!wide ? styles.triggerRowRail : {}
7448
- },
7449
- children: (0, react_jsx_runtime.jsxs)("button", {
7450
- type: "button",
7451
- "aria-label": "我的作品",
7452
- title: wide ? void 0 : "我的作品",
7453
- style: {
7454
- ...styles.trigger,
7455
- ...!wide ? styles.triggerRail : {}
7456
- },
7457
- onClick: dialog.open,
7458
- onMouseEnter: (event) => {
7459
- event.currentTarget.style.background = "var(--dsw-alias-interactive-bg-hover)";
7460
- },
7461
- onMouseLeave: (event) => {
7462
- event.currentTarget.style.background = "transparent";
7463
- },
7464
- children: [(0, react_jsx_runtime.jsx)(Icon, {
7465
- name: "folder",
7466
- size: wide ? 16 : 18
7467
- }), wide && (0, react_jsx_runtime.jsx)("span", { children: "我的作品" })]
7468
- })
7347
+ /**
7348
+ * 侧边栏「我的作品」行的图标。
7349
+ *
7350
+ * 按钮、标签、选中态都归 ui-sidebar 的 PanelRow:这里只按它要的尺寸画图形,
7351
+ * 并用 currentColor 让选中态的配色由外壳决定。
7352
+ */
7353
+ function MyWorksPanelIcon({ size }) {
7354
+ return (0, react_jsx_runtime.jsx)(Icon, {
7355
+ name: "folder",
7356
+ size
7469
7357
  });
7470
7358
  }
7471
- function MyWorksDialog({ remote }) {
7359
+ /** 主列的「我的作品」页:登录后按页展示当前账号发布过的网页作品。 */
7360
+ function MyWorksPanel({ remote }) {
7472
7361
  const account = useEdusLogin();
7473
- const open = (0, react.useSyncExternalStore)(dialog.subscribe, dialog.getSnapshot, () => false);
7474
7362
  const [list, setList] = (0, react.useState)([]);
7475
7363
  const [page, setPage] = (0, react.useState)(1);
7476
7364
  const [total, setTotal] = (0, react.useState)(0);
@@ -7503,7 +7391,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7503
7391
  setError("");
7504
7392
  await load(result.token, 1, "");
7505
7393
  }, [load]);
7506
- /** 退出后弹窗停留在登录面板,因此顺手把上一个账号的列表状态清干净。 */
7394
+ /** 退出后页面停留在登录面板,因此顺手把上一个账号的列表状态清干净。 */
7507
7395
  const logout = (0, react.useCallback)(() => {
7508
7396
  setConfirmLogout(false);
7509
7397
  EdusAuthStore.logout();
@@ -7539,298 +7427,281 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7539
7427
  setSharing(null);
7540
7428
  }
7541
7429
  };
7430
+ /**
7431
+ * 主列面板在切走时会被卸载,所以每次进入都从存储的登录态重新拉一次列表;
7432
+ * 这也顺带把过期 token 挡在渲染之前。
7433
+ */
7542
7434
  (0, react.useEffect)(() => {
7543
- if (!open) return;
7544
7435
  setError("");
7545
7436
  setNotice("");
7546
7437
  setConfirmLogout(false);
7547
7438
  const stored = EdusAuthStore.getSnapshot();
7548
- if (stored === null) setLoading(false);
7549
- if (stored !== null) {
7550
- setLoading(true);
7551
- remote.loginInfo(stored.token).then(async (refreshed) => {
7552
- EdusAuthStore.set(refreshed);
7553
- await load(refreshed.token, 1, "");
7554
- }).catch(() => {
7555
- EdusAuthStore.logout();
7556
- setError("登录状态已失效,请重新登录。");
7557
- setLoading(false);
7558
- });
7439
+ if (stored === null) {
7440
+ setLoading(false);
7441
+ return;
7559
7442
  }
7560
- const onKeyDown = (event) => {
7561
- if (event.key === "Escape") dialog.close();
7562
- };
7563
- document.addEventListener("keydown", onKeyDown);
7564
- return () => document.removeEventListener("keydown", onKeyDown);
7565
- }, [
7566
- load,
7567
- open,
7568
- remote
7569
- ]);
7570
- if (!open) return null;
7571
- return (0, react_jsx_runtime.jsx)("div", {
7572
- style: styles.overlay,
7573
- role: "presentation",
7574
- onMouseDown: dialog.close,
7575
- children: (0, react_jsx_runtime.jsxs)("section", {
7576
- style: styles.dialog,
7577
- role: "dialog",
7578
- "aria-modal": "true",
7579
- "aria-labelledby": "edus-my-works-title",
7580
- onMouseDown: (event) => event.stopPropagation(),
7581
- children: [
7582
- (0, react_jsx_runtime.jsxs)("header", {
7583
- style: styles.header,
7584
- children: [(0, react_jsx_runtime.jsxs)("div", {
7443
+ setLoading(true);
7444
+ remote.loginInfo(stored.token).then(async (refreshed) => {
7445
+ EdusAuthStore.set(refreshed);
7446
+ await load(refreshed.token, 1, "");
7447
+ }).catch(() => {
7448
+ EdusAuthStore.logout();
7449
+ setError("登录状态已失效,请重新登录。");
7450
+ setLoading(false);
7451
+ });
7452
+ }, [load, remote]);
7453
+ return (0, react_jsx_runtime.jsxs)("section", {
7454
+ style: styles.page,
7455
+ "aria-labelledby": "edus-my-works-title",
7456
+ children: [
7457
+ (0, react_jsx_runtime.jsx)("header", {
7458
+ style: styles.header,
7459
+ children: (0, react_jsx_runtime.jsxs)("div", {
7460
+ style: {
7461
+ minWidth: 0,
7462
+ flex: 1
7463
+ },
7464
+ children: [(0, react_jsx_runtime.jsx)("h2", {
7465
+ id: "edus-my-works-title",
7466
+ style: styles.title,
7467
+ children: "我的作品"
7468
+ }), (0, react_jsx_runtime.jsxs)("p", {
7585
7469
  style: {
7586
- minWidth: 0,
7587
- flex: 1
7470
+ ...styles.subtitle,
7471
+ ...styles.subtitleRow
7588
7472
  },
7589
- children: [(0, react_jsx_runtime.jsx)("h2", {
7590
- id: "edus-my-works-title",
7591
- style: styles.title,
7592
- children: "我的作品"
7593
- }), (0, react_jsx_runtime.jsxs)("p", {
7594
- style: {
7595
- ...styles.subtitle,
7596
- ...styles.subtitleRow
7597
- },
7598
- children: [(0, react_jsx_runtime.jsx)("span", {
7599
- style: {
7600
- minWidth: 0,
7601
- overflow: "hidden",
7602
- textOverflow: "ellipsis",
7603
- whiteSpace: "nowrap"
7604
- },
7605
- children: account === null ? "登录课成账号,查看你发布过的网页作品。" : `${account.title || account.phone} · 共 ${total} 个作品`
7606
- }), account !== null && (confirmLogout ? (0, react_jsx_runtime.jsxs)("span", {
7607
- style: styles.confirmRow,
7608
- children: [
7609
- (0, react_jsx_runtime.jsx)("span", { children: "确定退出登录?" }),
7610
- (0, react_jsx_runtime.jsx)("button", {
7611
- type: "button",
7612
- style: styles.danger,
7613
- onClick: logout,
7614
- children: "退出"
7615
- }),
7616
- (0, react_jsx_runtime.jsx)("button", {
7617
- type: "button",
7618
- style: styles.quiet,
7619
- onClick: () => setConfirmLogout(false),
7620
- children: "取消"
7621
- })
7622
- ]
7623
- }) : (0, react_jsx_runtime.jsxs)("button", {
7624
- type: "button",
7625
- title: "退出登录",
7626
- style: { ...styles.quiet },
7627
- onClick: () => setConfirmLogout(true),
7628
- children: [(0, react_jsx_runtime.jsx)(Icon, {
7629
- name: "logout",
7630
- size: 13
7631
- }), "退出登录"]
7632
- }))]
7633
- })]
7634
- }), (0, react_jsx_runtime.jsx)("button", {
7635
- type: "button",
7636
- "aria-label": "关闭我的作品",
7637
- style: styles.close,
7638
- onClick: dialog.close,
7639
- children: (0, react_jsx_runtime.jsx)(Icon, { name: "close" })
7640
- })]
7641
- }),
7642
- account !== null && (0, react_jsx_runtime.jsxs)("form", {
7643
- style: styles.toolbar,
7644
- onSubmit: (event) => {
7645
- event.preventDefault();
7646
- load(account.token, 1, searchInput.trim());
7647
- },
7648
- children: [
7649
- (0, react_jsx_runtime.jsx)("input", {
7650
- "aria-label": "搜索作品",
7651
- style: styles.search,
7652
- value: searchInput,
7653
- placeholder: "搜索标题或描述",
7654
- onChange: (event) => setSearchInput(event.target.value)
7655
- }),
7656
- (0, react_jsx_runtime.jsxs)("button", {
7657
- type: "submit",
7473
+ children: [(0, react_jsx_runtime.jsx)("span", {
7658
7474
  style: {
7659
- ...styles.button,
7660
- ...styles.primary
7475
+ minWidth: 0,
7476
+ flex: 1,
7477
+ overflow: "hidden",
7478
+ textOverflow: "ellipsis",
7479
+ whiteSpace: "nowrap"
7661
7480
  },
7662
- disabled: loading,
7663
- children: [(0, react_jsx_runtime.jsx)(Icon, {
7664
- name: "search",
7665
- size: 15
7666
- }), "搜索"]
7667
- }),
7668
- (0, react_jsx_runtime.jsxs)("button", {
7669
- type: "button",
7670
- style: styles.button,
7671
- disabled: loading,
7672
- onClick: () => void load(account.token, page, search),
7673
- children: [(0, react_jsx_runtime.jsx)(Icon, {
7674
- name: "refresh",
7675
- size: 15
7676
- }), "刷新"]
7677
- })
7678
- ]
7679
- }),
7680
- (0, react_jsx_runtime.jsxs)("div", {
7681
- style: styles.body,
7682
- children: [account === null ? (0, react_jsx_runtime.jsx)("div", {
7683
- style: styles.login,
7684
- children: (0, react_jsx_runtime.jsx)(EdusLoginPanel, {
7685
- remote,
7686
- intro: (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [(0, react_jsx_runtime.jsx)("strong", { children: "登录课成账号" }), (0, react_jsx_runtime.jsx)("p", {
7687
- style: {
7688
- ...styles.subtitle,
7689
- margin: "5px 0 0"
7690
- },
7691
- children: "作品列表仅展示当前账号创建的内容。"
7692
- })] }),
7693
- notice: error,
7694
- submitLabel: "登录并查看作品",
7695
- onSuccess: afterLogin,
7696
- theme: {
7697
- field: styles.field,
7698
- button: styles.button,
7699
- primary: {
7700
- ...styles.button,
7701
- ...styles.primary,
7702
- height: 40
7703
- },
7704
- error: styles.error
7705
- }
7706
- })
7707
- }) : loading ? (0, react_jsx_runtime.jsx)("div", {
7708
- style: styles.center,
7709
- children: "正在读取作品列表…"
7710
- }) : list.length === 0 ? (0, react_jsx_runtime.jsx)("div", {
7711
- style: styles.center,
7712
- children: (0, react_jsx_runtime.jsxs)("div", { children: [(0, react_jsx_runtime.jsx)(Icon, {
7713
- name: "folder",
7714
- size: 30
7715
- }), (0, react_jsx_runtime.jsx)("p", { children: search === "" ? "还没有发布过作品" : "没有找到匹配的作品" })] })
7716
- }) : (0, react_jsx_runtime.jsx)("div", {
7717
- style: styles.grid,
7718
- children: list.map((work) => (0, react_jsx_runtime.jsxs)("article", {
7719
- style: styles.card,
7481
+ children: account === null ? "登录课成账号,查看你发布过的网页作品。" : `${account.title || account.phone} · 共 ${total} 个作品`
7482
+ }), account !== null && (confirmLogout ? (0, react_jsx_runtime.jsxs)("span", {
7483
+ style: styles.confirmRow,
7720
7484
  children: [
7721
- work.thumb ? (0, react_jsx_runtime.jsx)("img", {
7722
- alt: "",
7723
- src: work.thumb,
7724
- style: styles.thumb
7725
- }) : (0, react_jsx_runtime.jsx)("div", {
7726
- style: styles.placeholder,
7727
- children: "暂无预览图"
7485
+ (0, react_jsx_runtime.jsx)("span", { children: "确定退出登录?" }),
7486
+ (0, react_jsx_runtime.jsx)("button", {
7487
+ type: "button",
7488
+ style: styles.danger,
7489
+ onClick: logout,
7490
+ children: "退出"
7728
7491
  }),
7729
- (0, react_jsx_runtime.jsxs)("div", {
7730
- style: styles.cardBody,
7731
- children: [(0, react_jsx_runtime.jsx)("h3", {
7732
- title: work.title,
7733
- style: styles.cardTitle,
7734
- children: work.title || "未命名作品"
7735
- }), (0, react_jsx_runtime.jsxs)("div", {
7736
- style: styles.meta,
7737
- children: [
7738
- (0, react_jsx_runtime.jsx)("span", {
7739
- style: styles.badge,
7740
- children: statusOf(work.status)
7741
- }),
7742
- (0, react_jsx_runtime.jsx)("span", { children: formatDate(work.updatedAt) }),
7743
- (0, react_jsx_runtime.jsxs)("span", {
7744
- style: { marginLeft: "auto" },
7745
- children: [work.views, " 次浏览"]
7746
- })
7747
- ]
7748
- })]
7749
- }),
7750
- (0, react_jsx_runtime.jsxs)("div", {
7751
- style: styles.cardActions,
7752
- children: [(0, react_jsx_runtime.jsxs)("button", {
7753
- type: "button",
7754
- style: styles.cardAction,
7755
- disabled: sharing === work.id || work.status !== 2,
7756
- onClick: () => void share(work, "open"),
7757
- children: [(0, react_jsx_runtime.jsx)(Icon, {
7758
- name: "open",
7759
- size: 14
7760
- }), "打开"]
7761
- }), (0, react_jsx_runtime.jsxs)("button", {
7762
- type: "button",
7763
- style: {
7764
- ...styles.cardAction,
7765
- borderRight: 0
7766
- },
7767
- disabled: sharing === work.id || work.status !== 2,
7768
- onClick: () => void share(work, "copy"),
7769
- children: [(0, react_jsx_runtime.jsx)(Icon, {
7770
- name: "copy",
7771
- size: 14
7772
- }), sharing === work.id ? "处理中…" : "复制链接"]
7773
- })]
7492
+ (0, react_jsx_runtime.jsx)("button", {
7493
+ type: "button",
7494
+ style: styles.quiet,
7495
+ onClick: () => setConfirmLogout(false),
7496
+ children: "取消"
7774
7497
  })
7775
7498
  ]
7776
- }, work.id))
7777
- }), account !== null && error !== "" && (0, react_jsx_runtime.jsx)("p", {
7499
+ }) : (0, react_jsx_runtime.jsxs)("button", {
7500
+ type: "button",
7501
+ title: "退出登录",
7502
+ style: { ...styles.quiet },
7503
+ onClick: () => setConfirmLogout(true),
7504
+ children: [(0, react_jsx_runtime.jsx)(Icon, {
7505
+ name: "logout",
7506
+ size: 13
7507
+ }), "退出登录"]
7508
+ }))]
7509
+ })]
7510
+ })
7511
+ }),
7512
+ account !== null && (0, react_jsx_runtime.jsxs)("form", {
7513
+ style: styles.toolbar,
7514
+ onSubmit: (event) => {
7515
+ event.preventDefault();
7516
+ load(account.token, 1, searchInput.trim());
7517
+ },
7518
+ children: [
7519
+ (0, react_jsx_runtime.jsx)("input", {
7520
+ "aria-label": "搜索作品",
7521
+ style: styles.search,
7522
+ value: searchInput,
7523
+ placeholder: "搜索标题或描述",
7524
+ onChange: (event) => setSearchInput(event.target.value)
7525
+ }),
7526
+ (0, react_jsx_runtime.jsxs)("button", {
7527
+ type: "submit",
7778
7528
  style: {
7779
- ...styles.error,
7780
- marginTop: 14
7529
+ ...styles.button,
7530
+ ...styles.primary
7781
7531
  },
7782
- children: error
7783
- })]
7784
- }),
7785
- account !== null && (0, react_jsx_runtime.jsxs)("footer", {
7786
- style: styles.footer,
7787
- children: [
7788
- (0, react_jsx_runtime.jsxs)("span", { children: [
7789
- "第 ",
7790
- page,
7791
- " / ",
7792
- pages,
7793
- " 页"
7794
- ] }),
7795
- notice !== "" && (0, react_jsx_runtime.jsx)("span", {
7796
- role: "status",
7797
- style: styles.toast,
7798
- children: notice
7799
- }),
7800
- (0, react_jsx_runtime.jsxs)("div", {
7532
+ disabled: loading,
7533
+ children: [(0, react_jsx_runtime.jsx)(Icon, {
7534
+ name: "search",
7535
+ size: 15
7536
+ }), "搜索"]
7537
+ }),
7538
+ (0, react_jsx_runtime.jsxs)("button", {
7539
+ type: "button",
7540
+ style: styles.button,
7541
+ disabled: loading,
7542
+ onClick: () => void load(account.token, page, search),
7543
+ children: [(0, react_jsx_runtime.jsx)(Icon, {
7544
+ name: "refresh",
7545
+ size: 15
7546
+ }), "刷新"]
7547
+ })
7548
+ ]
7549
+ }),
7550
+ (0, react_jsx_runtime.jsxs)("div", {
7551
+ style: styles.body,
7552
+ children: [account === null ? (0, react_jsx_runtime.jsx)("div", {
7553
+ style: styles.login,
7554
+ children: (0, react_jsx_runtime.jsx)(EdusLoginPanel, {
7555
+ remote,
7556
+ intro: (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [(0, react_jsx_runtime.jsx)("strong", { children: "登录课成账号" }), (0, react_jsx_runtime.jsx)("p", {
7801
7557
  style: {
7802
- display: "flex",
7803
- gap: 8
7558
+ ...styles.subtitle,
7559
+ margin: "5px 0 0"
7804
7560
  },
7805
- children: [(0, react_jsx_runtime.jsx)("button", {
7806
- type: "button",
7807
- style: styles.button,
7808
- disabled: loading || page <= 1,
7809
- onClick: () => void load(account.token, page - 1, search),
7810
- children: "上一页"
7811
- }), (0, react_jsx_runtime.jsx)("button", {
7812
- type: "button",
7813
- style: styles.button,
7814
- disabled: loading || page >= pages,
7815
- onClick: () => void load(account.token, page + 1, search),
7816
- children: "下一页"
7817
- })]
7818
- })
7819
- ]
7820
- })
7821
- ]
7822
- })
7561
+ children: "作品列表仅展示当前账号创建的内容。"
7562
+ })] }),
7563
+ notice: error,
7564
+ submitLabel: "登录并查看作品",
7565
+ onSuccess: afterLogin,
7566
+ theme: {
7567
+ field: styles.field,
7568
+ button: styles.button,
7569
+ primary: {
7570
+ ...styles.button,
7571
+ ...styles.primary,
7572
+ height: 40
7573
+ },
7574
+ error: styles.error
7575
+ }
7576
+ })
7577
+ }) : loading ? (0, react_jsx_runtime.jsx)("div", {
7578
+ style: styles.center,
7579
+ children: "正在读取作品列表…"
7580
+ }) : list.length === 0 ? (0, react_jsx_runtime.jsx)("div", {
7581
+ style: styles.center,
7582
+ children: (0, react_jsx_runtime.jsxs)("div", { children: [(0, react_jsx_runtime.jsx)(Icon, {
7583
+ name: "folder",
7584
+ size: 30
7585
+ }), (0, react_jsx_runtime.jsx)("p", { children: search === "" ? "还没有发布过作品" : "没有找到匹配的作品" })] })
7586
+ }) : (0, react_jsx_runtime.jsx)("div", {
7587
+ style: styles.grid,
7588
+ children: list.map((work) => (0, react_jsx_runtime.jsxs)("article", {
7589
+ style: styles.card,
7590
+ children: [
7591
+ work.thumb ? (0, react_jsx_runtime.jsx)("img", {
7592
+ alt: "",
7593
+ src: work.thumb,
7594
+ style: styles.thumb
7595
+ }) : (0, react_jsx_runtime.jsx)("div", {
7596
+ style: styles.placeholder,
7597
+ children: "暂无预览图"
7598
+ }),
7599
+ (0, react_jsx_runtime.jsxs)("div", {
7600
+ style: styles.cardBody,
7601
+ children: [(0, react_jsx_runtime.jsx)("h3", {
7602
+ title: work.title,
7603
+ style: styles.cardTitle,
7604
+ children: work.title || "未命名作品"
7605
+ }), (0, react_jsx_runtime.jsxs)("div", {
7606
+ style: styles.meta,
7607
+ children: [
7608
+ (0, react_jsx_runtime.jsx)("span", {
7609
+ style: styles.badge,
7610
+ children: statusOf(work.status)
7611
+ }),
7612
+ (0, react_jsx_runtime.jsx)("span", { children: formatDate(work.updatedAt) }),
7613
+ (0, react_jsx_runtime.jsxs)("span", {
7614
+ style: { marginLeft: "auto" },
7615
+ children: [work.views, " 次浏览"]
7616
+ })
7617
+ ]
7618
+ })]
7619
+ }),
7620
+ (0, react_jsx_runtime.jsxs)("div", {
7621
+ style: styles.cardActions,
7622
+ children: [(0, react_jsx_runtime.jsxs)("button", {
7623
+ type: "button",
7624
+ style: styles.cardAction,
7625
+ disabled: sharing === work.id || work.status !== 2,
7626
+ onClick: () => void share(work, "open"),
7627
+ children: [(0, react_jsx_runtime.jsx)(Icon, {
7628
+ name: "open",
7629
+ size: 14
7630
+ }), "打开"]
7631
+ }), (0, react_jsx_runtime.jsxs)("button", {
7632
+ type: "button",
7633
+ style: {
7634
+ ...styles.cardAction,
7635
+ borderRight: 0
7636
+ },
7637
+ disabled: sharing === work.id || work.status !== 2,
7638
+ onClick: () => void share(work, "copy"),
7639
+ children: [(0, react_jsx_runtime.jsx)(Icon, {
7640
+ name: "copy",
7641
+ size: 14
7642
+ }), sharing === work.id ? "处理中…" : "复制链接"]
7643
+ })]
7644
+ })
7645
+ ]
7646
+ }, work.id))
7647
+ }), account !== null && error !== "" && (0, react_jsx_runtime.jsx)("p", {
7648
+ style: {
7649
+ ...styles.error,
7650
+ marginTop: 14
7651
+ },
7652
+ children: error
7653
+ })]
7654
+ }),
7655
+ account !== null && (0, react_jsx_runtime.jsxs)("footer", {
7656
+ style: styles.footer,
7657
+ children: [
7658
+ (0, react_jsx_runtime.jsxs)("span", { children: [
7659
+ "第 ",
7660
+ page,
7661
+ " / ",
7662
+ pages,
7663
+ " 页"
7664
+ ] }),
7665
+ notice !== "" && (0, react_jsx_runtime.jsx)("span", {
7666
+ role: "status",
7667
+ style: styles.toast,
7668
+ children: notice
7669
+ }),
7670
+ (0, react_jsx_runtime.jsxs)("div", {
7671
+ style: {
7672
+ display: "flex",
7673
+ gap: 8
7674
+ },
7675
+ children: [(0, react_jsx_runtime.jsx)("button", {
7676
+ type: "button",
7677
+ style: styles.button,
7678
+ disabled: loading || page <= 1,
7679
+ onClick: () => void load(account.token, page - 1, search),
7680
+ children: "上一页"
7681
+ }), (0, react_jsx_runtime.jsx)("button", {
7682
+ type: "button",
7683
+ style: styles.button,
7684
+ disabled: loading || page >= pages,
7685
+ onClick: () => void load(account.token, page + 1, search),
7686
+ children: "下一页"
7687
+ })]
7688
+ })
7689
+ ]
7690
+ })
7691
+ ]
7823
7692
  });
7824
7693
  }
7825
7694
  //#endregion
7826
7695
  //#region lib/types/client/index.js
7827
7696
  const inject = ["slots", "remote"];
7697
+ /** 侧边栏行与它打开的主列面板共用这个 id;两者缺一,点击就会抛错。 */
7698
+ const WORKS_PANEL_ID = "edus-works";
7828
7699
  function unwrap(result) {
7829
7700
  if (!result.ok) throw new Error(result.error.message);
7830
7701
  return result.value;
7831
7702
  }
7832
7703
  /**
7833
- * Register the right-sidebar HTML publish extension and the works dialog.
7704
+ * Register the right-sidebar HTML publish extension and the works panel.
7834
7705
  *
7835
7706
  * 产品品牌不在这里:它属于产品外壳,由 dsh-desktop 的构建注入,业务插件
7836
7707
  * 不占用品牌槽位,也就不会因为换品牌而需要重新发版。
@@ -7887,16 +7758,18 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
7887
7758
  unwrap(await bridge.htmlVersionDelete(token, id));
7888
7759
  }
7889
7760
  };
7890
- ctx.slots.inject("sidebar.footer.action", () => ctx.slots.register({
7891
- name: "sidebar.footer.action",
7892
- id: "edus:my-works"
7893
- }, (props) => (0, react_jsx_runtime.jsx)(MyWorksAction, { ...props })));
7894
- const overlaySlots = ctx.slots;
7895
- overlaySlots.inject("shell.overlay", () => overlaySlots.register({
7896
- name: "shell.overlay",
7897
- id: "edus:my-works-dialog",
7761
+ const mainSlots = ctx.slots;
7762
+ mainSlots.inject("main", () => mainSlots.register({
7763
+ name: "main",
7764
+ key: WORKS_PANEL_ID,
7898
7765
  inject: () => ({ remote })
7899
- }, ({ remote: injectedRemote }) => (0, react_jsx_runtime.jsx)(MyWorksDialog, { remote: injectedRemote })));
7766
+ }, ({ remote: injectedRemote }) => (0, react_jsx_runtime.jsx)(MyWorksPanel, { remote: injectedRemote })));
7767
+ ctx.slots.inject("sidebar.panellist", () => ctx.slots.register({
7768
+ name: "sidebar.panellist",
7769
+ id: WORKS_PANEL_ID,
7770
+ order: -1,
7771
+ label: "我的作品"
7772
+ }, (props) => (0, react_jsx_runtime.jsx)(MyWorksPanelIcon, { ...props })));
7900
7773
  ctx.inject(["slots", "documentPreviews"], (child) => applyHtmlPublishPreview(child, remote));
7901
7774
  }
7902
7775
  function applyHtmlPublishPreview(ctx, remote) {
@@ -0,0 +1,14 @@
1
+ import type { SidebarPanelIconOwnerProps } from '@deepseek-ai/dsh-client-ui-sidebar/client';
2
+ import type { EdusRemote } from './HtmlWorkbench.tsx';
3
+ /**
4
+ * 侧边栏「我的作品」行的图标。
5
+ *
6
+ * 按钮、标签、选中态都归 ui-sidebar 的 PanelRow:这里只按它要的尺寸画图形,
7
+ * 并用 currentColor 让选中态的配色由外壳决定。
8
+ */
9
+ export declare function MyWorksPanelIcon({ size }: SidebarPanelIconOwnerProps): import("react").JSX.Element;
10
+ /** 主列的「我的作品」页:登录后按页展示当前账号发布过的网页作品。 */
11
+ export declare function MyWorksPanel({ remote }: {
12
+ readonly remote: EdusRemote;
13
+ }): import("react").JSX.Element;
14
+ //# sourceMappingURL=MyWorksPanel.d.ts.map
@@ -1,7 +1,7 @@
1
1
  import type { Context as ClientContext } from '@deepseek-ai/cordis';
2
2
  export declare const inject: string[];
3
3
  /**
4
- * Register the right-sidebar HTML publish extension and the works dialog.
4
+ * Register the right-sidebar HTML publish extension and the works panel.
5
5
  *
6
6
  * 产品品牌不在这里:它属于产品外壳,由 dsh-desktop 的构建注入,业务插件
7
7
  * 不占用品牌槽位,也就不会因为换品牌而需要重新发版。
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@houser/edus-plugin",
3
- "version": "1.0.7",
3
+ "version": "1.0.8",
4
4
  "description": "",
5
5
  "license": "ISC",
6
6
  "author": "",
@@ -1,7 +0,0 @@
1
- import type { SidebarFooterActionOwnerProps } from '@deepseek-ai/dsh-client-ui-sidebar/client';
2
- import type { EdusRemote } from './HtmlWorkbench.tsx';
3
- export declare function MyWorksAction({ wide }: SidebarFooterActionOwnerProps): import("react").JSX.Element;
4
- export declare function MyWorksDialog({ remote }: {
5
- readonly remote: EdusRemote;
6
- }): import("react").JSX.Element | null;
7
- //# sourceMappingURL=MyWorksAction.d.ts.map