diff --git a/assets/css/routes/user-center/shell.css b/assets/css/routes/user-center/shell.css index 8ebf5ef4..0a767a0f 100644 --- a/assets/css/routes/user-center/shell.css +++ b/assets/css/routes/user-center/shell.css @@ -622,25 +622,6 @@ body.aksrt-user-center .uc-content, } } -.uc-service-grid__icon small { - position: absolute; - top: -5px; - right: -7px; - display: grid; - place-items: center; - min-width: 17px; - height: 17px; - padding: 0 4px; - border: 2px solid var(--surface-1); - border-radius: 99px; - background: var(--color-error, #ef4444); - color: #fff; - font-size: 9px; - font-style: normal; - font-weight: 700; - line-height: 1; -} - .uc-sidebar__pair { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); @@ -684,7 +665,8 @@ body.aksrt-user-center .uc-content, text-overflow: ellipsis; } -.uc-summary-card__body > i { +.uc-summary-card__body > i, +.uc-summary-card__body > svg { font-size: 18px; } @@ -716,14 +698,26 @@ body.aksrt-user-center .uc-content, .uc-center-card strong { font-size: 13px; } .uc-center-card small { margin-top: 3px; color: var(--color-ink-4); font-size: 10px; } -.uc-center-card > i { color: var(--color-ink-4); font-size: 11px; } +.uc-center-card > i, +.uc-center-card > svg { color: var(--color-ink-4); font-size: 11px; } .uc-center-card--creation .uc-center-card__icon { color: #6650c7; background: rgba(124, 92, 220, 0.12); } .uc-center-card--revenue .uc-center-card__icon { color: #ce6b35; background: rgba(234, 112, 55, 0.12); } -.uc-service-grid { - display: grid; - grid-template-columns: repeat(3, minmax(0, 1fr)); - gap: 8px; +/* Services / settings grids, ported from the reference theme sidebar: + four per row, no tinted tile behind the icon. */ +.user-icon-but-box > a { + width: calc(25% - 10px); + margin: 5px; + min-width: 50px; + max-width: 100px; + color: var(--color-ink-3); + text-align: center; + text-decoration: none; +} + +.user-icon-but-box > a:hover, +.user-icon-but-box > a.is-active { + color: var(--color-primary); } .uc-follow-management__list { display: grid; gap: 10px; margin-top: 16px; } @@ -735,44 +729,3 @@ body.aksrt-user-center .uc-content, .uc-follow-management__actions { display: flex; flex-wrap: wrap; gap: 8px; margin-left: auto; } @media (max-width: 560px) { .uc-follow-management__item { align-items: flex-start; flex-wrap: wrap; } .uc-follow-management__actions { width: 100%; margin-left: 60px; } } -.uc-service-grid__item { - display: flex; - flex-direction: column; - align-items: center; - gap: 7px; - min-width: 0; - padding: 4px 2px; - color: var(--color-ink-3); - font-size: 11px; - text-align: center; - text-decoration: none; -} - -.uc-service-grid__icon { - position: relative; - display: grid; - place-items: center; - width: 38px; - height: 38px; - border-radius: 14px; - background: var(--surface-2); - font-size: 16px; -} - -.uc-service-grid__item--cart .uc-service-grid__icon { color: #dd6941; background: rgba(238, 109, 61, 0.12); } -.uc-service-grid__item--level .uc-service-grid__icon { color: #9b6b0a; background: rgba(234, 179, 8, 0.13); } -.uc-service-grid__item--revenue .uc-service-grid__icon { color: #b8377d; background: rgba(219, 39, 119, 0.12); } -.uc-service-grid__item--auth .uc-service-grid__icon { color: #287bc4; background: rgba(14, 165, 233, 0.12); } -.uc-service-grid__item--orders .uc-service-grid__icon { color: #c05621; background: rgba(234, 88, 12, 0.12); } -.uc-service-grid__item--notice .uc-service-grid__icon { color: #d04b65; background: rgba(244, 63, 94, 0.11); } -.uc-service-grid__item--profile .uc-service-grid__icon { color: #6550c7; background: rgba(124, 92, 220, 0.12); } -.uc-service-grid__item--security .uc-service-grid__icon { color: #16816c; background: rgba(16, 185, 129, 0.12); } - -.uc-service-grid__item:hover, -.uc-service-grid__item.is-active { - color: var(--color-primary); -} - -.uc-service-grid__item.is-active .uc-service-grid__icon { - box-shadow: 0 0 0 2px var(--color-primary-soft), 0 5px 14px rgba(15, 23, 42, 0.08); -} diff --git a/inc/helpers/user-center-renderers/profile-sidebar.php b/inc/helpers/user-center-renderers/profile-sidebar.php index 1c0d67a6..b81fbcbb 100644 --- a/inc/helpers/user-center-renderers/profile-sidebar.php +++ b/inc/helpers/user-center-renderers/profile-sidebar.php @@ -15,7 +15,8 @@ require __DIR__ . '/sidebar-vip.php'; require __DIR__ . '/sidebar-commerce.php'; require __DIR__ . '/sidebar-creator.php'; require __DIR__ . '/sidebar-nav.php'; +$drawer_trigger_icon = aksrt_icon_markup('zibsvg-menu'); ?> diff --git a/inc/helpers/user-center-renderers/sidebar-commerce.php b/inc/helpers/user-center-renderers/sidebar-commerce.php index 4b7dc508..8d32fd2d 100644 --- a/inc/helpers/user-center-renderers/sidebar-commerce.php +++ b/inc/helpers/user-center-renderers/sidebar-commerce.php @@ -20,23 +20,26 @@ try { $wallet = '0.00'; } $points = max(0, (int) ($credit_balance ?? 0)); +$wallet_icon = aksrt_icon_markup('zibsvg-money-color-2'); +$points_icon = aksrt_icon_markup('zibsvg-points-color'); +$arrow_icon = aksrt_icon_markup('zibsvg-right'); ?>
- + - + - + - + diff --git a/inc/helpers/user-center-renderers/sidebar-creator.php b/inc/helpers/user-center-renderers/sidebar-creator.php index c3ce50ec..209d9e8c 100644 --- a/inc/helpers/user-center-renderers/sidebar-creator.php +++ b/inc/helpers/user-center-renderers/sidebar-creator.php @@ -13,20 +13,23 @@ $revenue_url = isset($dashboard_tabs['revenue']) ? aksrt_get_user_center_tab_url if ($creation_url === '' && $revenue_url === '') { return; } +$creation_icon = aksrt_icon_markup('zibsvg-merchant-color'); +$revenue_icon = aksrt_icon_markup('zibsvg-money-color'); +$arrow_icon = aksrt_icon_markup('zibsvg-right'); ?>
- + - + - + - +
diff --git a/inc/helpers/user-center-renderers/sidebar-nav.php b/inc/helpers/user-center-renderers/sidebar-nav.php index be6f5800..9fdbe7c4 100644 --- a/inc/helpers/user-center-renderers/sidebar-nav.php +++ b/inc/helpers/user-center-renderers/sidebar-nav.php @@ -2,6 +2,9 @@ /** * User center sidebar: services and account settings. * + * Icon set mirrors the reference theme user-center sidebar: every entry renders + * an inline SVG from the theme sprite through aksrt_icon_markup(). + * * @package AKSRT */ @@ -17,22 +20,20 @@ $orders_url = $orders_available ? (string) ($orders_url ?? '') : ''; $services = array_values(array_filter([ [ 'label' => __('我的等级', 'aksrt'), - 'icon' => 'chart-line', - 'tone' => 'level', + 'icon' => 'trend-color', 'url' => $level_url, + 'tab' => 'level', ], [ 'label' => __('官方认证', 'aksrt'), - 'icon' => 'id-badge', - 'tone' => 'auth', + 'icon' => 'user-auth', 'url' => $auth_url, 'tab' => 'auth', ], [ 'label' => __('我的订单', 'aksrt'), - 'icon' => 'receipt', - 'tone' => 'orders', + 'icon' => 'order-color', 'url' => $orders_url, 'tab' => 'orders', ], @@ -41,35 +42,38 @@ $services = array_values(array_filter([ $settings = array_values(array_filter([ [ 'label' => __('消息通知', 'aksrt'), - 'icon' => 'bell', - 'tone' => 'notice', + 'icon' => 'msg-color', 'url' => isset($dashboard_tabs['msg']) ? aksrt_get_user_center_tab_url('msg') : '', 'tab' => 'msg', ], [ 'label' => __('个人资料', 'aksrt'), - 'icon' => 'user-edit', - 'tone' => 'profile', + 'icon' => 'user-color', 'url' => isset($dashboard_tabs['profile']) ? aksrt_get_user_center_tab_url('profile') : '', + 'tab' => 'profile', ], [ 'label' => __('账户安全', 'aksrt'), - 'icon' => 'shield-alt', - 'tone' => 'security', + 'icon' => 'security-color', 'url' => isset($dashboard_tabs['settings']) ? aksrt_get_user_center_tab_url('settings') : '', + 'tab' => 'settings', ], ], static fn(array $item): bool => (string) $item['url'] !== '')); $render_grid = static function (array $items): void { ?> -
- - data-tab=""> - - - - - + diff --git a/inc/helpers/user-center-renderers/sidebar-vip.php b/inc/helpers/user-center-renderers/sidebar-vip.php index f1df9538..43ec5176 100644 --- a/inc/helpers/user-center-renderers/sidebar-vip.php +++ b/inc/helpers/user-center-renderers/sidebar-vip.php @@ -49,7 +49,8 @@ $sidebar_level = $vip_level > 0 ? $vip_level : $expired_level; $sidebar_icon_url = esc_url((string) ($vip_levels[$sidebar_level]['img_icon'] ?? '')); $sidebar_icon = $sidebar_icon_url !== '' ? '' - : ''; + : aksrt_icon_markup('zibsvg-vip_1'); +$sidebar_arrow = aksrt_icon_markup('zibsvg-right', 'uc-sidebar-vip__arrow'); ?> @@ -57,5 +58,5 @@ $sidebar_icon = $sidebar_icon_url !== '' - + diff --git a/tests/widget-system/user-center-sidebar-icons-contract.test.cjs b/tests/widget-system/user-center-sidebar-icons-contract.test.cjs new file mode 100644 index 00000000..a668748f --- /dev/null +++ b/tests/widget-system/user-center-sidebar-icons-contract.test.cjs @@ -0,0 +1,117 @@ +/** + * 用户中心左侧栏图标契约(参考主题 1:1 对齐)。 + * + * 硬约束: + * 1) 「我的服务 / 功能设置」两个网格使用参考主题的 icon-but-box / user-icon-but-box + * 外壳,图标全部来自主题内置 SVG sprite(aksrt_icon_markup('zibsvg-*')), + * 不再出现 Font Awesome 字形。 + * 2) 侧栏其余部件(余额/积分卡、创作/推广卡、VIP 入口、抽屉触发器)同样只使用 + * sprite 图标,箭头统一为 zibsvg-right,保证侧栏只剩一种图标族。 + * 3) 旧的 uc-service-grid 外壳、色调底色与计数角标必须已彻底移除,不得残留。 + */ +'use strict'; + +const assert = require('node:assert/strict'); +const fs = require('node:fs'); +const path = require('node:path'); +const test = require('node:test'); + +const root = path.resolve(__dirname, '..', '..'); +const read = (file) => fs.readFileSync(path.join(root, file), 'utf8'); + +const sidebarDir = 'inc/helpers/user-center-renderers/'; +const sidebarFiles = [ + 'sidebar-nav.php', + 'sidebar-commerce.php', + 'sidebar-creator.php', + 'sidebar-vip.php', + 'profile-sidebar.php', +]; + +test('服务/设置网格使用参考主题 icon-but-box 外壳与 sprite 图标', () => { + const nav = read(sidebarDir + 'sidebar-nav.php'); + + assert.match(nav, /class="flex ac hh text-center icon-but-box user-icon-but-box"/); + assert.match(nav, /
<\?php echo \$icon_html;/); + assert.match(nav, /
/); + assert.match(nav, /aksrt_icon_markup\('zibsvg-' \. \(string\) \$item\['icon'\]\)/); + + // 参考主题选型:我的服务 = trend-color / user-auth / order-color。 + assert.match(nav, /'icon'\s+=>\s+'trend-color'/); + assert.match(nav, /'icon'\s+=>\s+'user-auth'/); + assert.match(nav, /'icon'\s+=>\s+'order-color'/); + // 功能设置 = msg-color / user-color / security-color。 + assert.match(nav, /'icon'\s+=>\s+'msg-color'/); + assert.match(nav, /'icon'\s+=>\s+'user-color'/); + assert.match(nav, /'icon'\s+=>\s+'security-color'/); + + // 每项都带 tab,保证 icon-but-* 类名完整且选中态可同步。 + for (const tab of ['level', 'auth', 'orders', 'msg', 'profile', 'settings']) { + assert.match(nav, new RegExp(`'tab'\\s+=>\\s+'${tab}'`), `missing tab key: ${tab}`); + } + + // AKSRT 的跳转契约保留 + data-tab,不搬参考主题的 。 + assert.match(nav, //); + assert.doesNotMatch(nav, /data-onclick/); +}); + +test('侧栏五个部件均不再出现 Font Awesome 字形', () => { + for (const file of sidebarFiles) { + const source = read(sidebarDir + file); + assert.doesNotMatch(source, /fa\s+fas\s+fa-/, `${file} still renders a Font Awesome glyph`); + assert.doesNotMatch(source, /