fix(user): align badge entry with medal settings
This commit is contained in:
@@ -7,7 +7,63 @@
|
|||||||
* 加载条件与 user-badges.js 一致(badge surface 页面)。
|
* 加载条件与 user-badges.js 一致(badge surface 页面)。
|
||||||
* ============================================================ */
|
* ============================================================ */
|
||||||
|
|
||||||
/* ---------- 分类分组(zibll .medal-cat-box / .medal-cat-name) ---------- */
|
/* ---------- 顶部资料卡入口(zibll user-medal-info parity) ---------- */
|
||||||
|
.aksrt-medal-entry {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 4px;
|
||||||
|
min-width: 0;
|
||||||
|
margin: 2px 8px 2px 0;
|
||||||
|
padding: 2px 0;
|
||||||
|
border: 0;
|
||||||
|
background: transparent;
|
||||||
|
color: var(--muted-2-color, var(--color-ink-4));
|
||||||
|
font: inherit;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 1.4;
|
||||||
|
cursor: pointer;
|
||||||
|
white-space: nowrap;
|
||||||
|
transition: color .15s ease, opacity .15s ease;
|
||||||
|
}
|
||||||
|
.aksrt-medal-entry:hover,
|
||||||
|
.aksrt-medal-entry:focus-visible {
|
||||||
|
color: var(--focus-color);
|
||||||
|
opacity: 1;
|
||||||
|
}
|
||||||
|
.aksrt-medal-entry:focus-visible {
|
||||||
|
outline: 2px solid var(--focus-color);
|
||||||
|
outline-offset: 2px;
|
||||||
|
border-radius: var(--mini-radius, 6px);
|
||||||
|
}
|
||||||
|
.aksrt-medal-entry__icons {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
flex: none;
|
||||||
|
min-width: 0;
|
||||||
|
}
|
||||||
|
.aksrt-medal-entry__icon {
|
||||||
|
width: auto;
|
||||||
|
height: 1.45em;
|
||||||
|
max-width: 2.2em;
|
||||||
|
margin: 0 1px;
|
||||||
|
object-fit: contain;
|
||||||
|
vertical-align: middle;
|
||||||
|
}
|
||||||
|
.aksrt-medal-entry__icon + .aksrt-medal-entry__icon { margin-left: -1px; }
|
||||||
|
.aksrt-medal-entry__fallback {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
width: 1.6em;
|
||||||
|
height: 1.6em;
|
||||||
|
color: var(--focus-color);
|
||||||
|
background: var(--focus-color-opacity1);
|
||||||
|
border-radius: 50%;
|
||||||
|
}
|
||||||
|
.aksrt-medal-entry__count { margin-left: 2px; }
|
||||||
|
.aksrt-medal-entry__arrow { margin-left: 1px; font-size: .9em; }
|
||||||
|
|
||||||
|
|
||||||
.medal-cat-box {
|
.medal-cat-box {
|
||||||
position: relative;
|
position: relative;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
|
|||||||
@@ -738,8 +738,7 @@
|
|||||||
}
|
}
|
||||||
.aksrt-author-card__badge img { border-radius: 50%; }
|
.aksrt-author-card__badge img { border-radius: 50%; }
|
||||||
|
|
||||||
/* 徽章远程弹窗样式已迁至 assets/css/frontend/medal.css(zibll medal 风格)。 */
|
/* 徽章入口与弹窗样式统一由 assets/css/frontend/medal.css 提供。 */
|
||||||
.aksrt-author-hero__badges { margin-top: 8px; }
|
|
||||||
|
|
||||||
/* Forum tab topics (batch6) */
|
/* Forum tab topics (batch6) */
|
||||||
.aksrt-ftab__nav {
|
.aksrt-ftab__nav {
|
||||||
|
|||||||
@@ -234,6 +234,63 @@ if (!function_exists('aksrt_get_user_name')) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!function_exists('aksrt_render_user_medal_entry')) {
|
||||||
|
/**
|
||||||
|
* Render the compact Zibll-style badge overview entry.
|
||||||
|
*
|
||||||
|
* The configured limit controls preview icons only; the count remains
|
||||||
|
* the complete owned badge count returned by the privacy-aware DTO.
|
||||||
|
*
|
||||||
|
* @param int $user_id
|
||||||
|
* @param string $context user-center|user-home
|
||||||
|
* @param bool $can_wear Whether the viewer may initially wear a badge.
|
||||||
|
*/
|
||||||
|
function aksrt_render_user_medal_entry(int $user_id, string $context = 'user-home', bool $can_wear = false): string {
|
||||||
|
if ($user_id <= 0 || !class_exists('AKSRT\\User\\Badges') || !class_exists('AKSRT\\Settings\\Settings')) {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
|
||||||
|
$settings = \AKSRT\Settings\Settings::get_user_identity_settings();
|
||||||
|
$medal = is_array($settings['medal'] ?? null) ? $settings['medal'] : [];
|
||||||
|
if (empty($medal['enabled']) || ($context === 'user-home' && empty($medal['public_display']))) {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
|
||||||
|
$data = \AKSRT\User\Badges::list_for_user($user_id);
|
||||||
|
if (empty($data['enabled']) || ($context === 'user-home' && empty($data['public_display']))) {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
|
||||||
|
$limit = max(1, min(8, (int) ($medal['limit'] ?? 3)));
|
||||||
|
$icons = [];
|
||||||
|
foreach ((array) ($data['categories'] ?? []) as $category) {
|
||||||
|
foreach ((array) ($category['items'] ?? []) as $item) {
|
||||||
|
if (empty($item['owned'])) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
$icon_url = esc_url((string) ($item['icon_url'] ?? ''));
|
||||||
|
if ($icon_url === '') {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
$label = sanitize_text_field((string) ($item['label'] ?? __('徽章', 'aksrt')));
|
||||||
|
$icons[] = '<img class="img-icon medal-icon aksrt-medal-entry__icon" src="' . $icon_url . '" alt="' . esc_attr($label) . '" title="' . esc_attr($label) . '" loading="lazy" decoding="async" />';
|
||||||
|
if (count($icons) >= $limit) {
|
||||||
|
break 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$count = max(0, (int) ($data['count'] ?? 0));
|
||||||
|
$label = $count > 0 ? sprintf(_n('%d枚徽章', '%d枚徽章', $count, 'aksrt'), $count) : __('获取徽章', 'aksrt');
|
||||||
|
$icons_html = implode('', $icons);
|
||||||
|
if ($icons_html === '') {
|
||||||
|
$icons_html = '<span class="aksrt-medal-entry__fallback" aria-hidden="true"><i class="fas fa-award"></i></span>';
|
||||||
|
}
|
||||||
|
$classes = 'aksrt-medal-entry aksrt-medal-entry--' . sanitize_html_class($context);
|
||||||
|
return '<button type="button" class="' . esc_attr($classes) . '" data-aksrt-badges-open data-aksrt-badges-user-id="' . (int) $user_id . '" data-aksrt-badges-can-wear="' . ($can_wear ? '1' : '0') . '" aria-label="' . esc_attr($label) . '"><span class="aksrt-medal-entry__icons">' . $icons_html . '</span><span class="aksrt-medal-entry__count">' . esc_html($label) . '</span><i class="fas fa-angle-right aksrt-medal-entry__arrow" aria-hidden="true"></i></button>';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (!function_exists('aksrt_user_has_visible_badges')) {
|
if (!function_exists('aksrt_user_has_visible_badges')) {
|
||||||
/**
|
/**
|
||||||
* Whether a user owns at least one badge that exists in the current catalog.
|
* Whether a user owns at least one badge that exists in the current catalog.
|
||||||
|
|||||||
@@ -41,6 +41,9 @@ extract($context, EXTR_SKIP); // phpcs:ignore WordPress.PHP.DontExtract.extract_
|
|||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
</h1>
|
</h1>
|
||||||
<div class="uc-header__meta desc user-identity flex ac hh">
|
<div class="uc-header__meta desc user-identity flex ac hh">
|
||||||
|
<?php if (function_exists('aksrt_render_user_medal_entry')) : ?>
|
||||||
|
<?php echo aksrt_render_user_medal_entry((int) $user_id, 'user-center', true); // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped ?>
|
||||||
|
<?php endif; ?>
|
||||||
<span class="uc-header__meta-item" title="<?php esc_attr_e('用户名', 'aksrt'); ?>">
|
<span class="uc-header__meta-item" title="<?php esc_attr_e('用户名', 'aksrt'); ?>">
|
||||||
<i class="fas fa-user" aria-hidden="true"></i> <?php echo esc_html($target_user->user_login); ?>
|
<i class="fas fa-user" aria-hidden="true"></i> <?php echo esc_html($target_user->user_login); ?>
|
||||||
</span>
|
</span>
|
||||||
@@ -61,12 +64,6 @@ extract($context, EXTR_SKIP); // phpcs:ignore WordPress.PHP.DontExtract.extract_
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="uc-header__actions">
|
<div class="uc-header__actions">
|
||||||
<?php if (class_exists('\AKSRT\User\Badges') && \AKSRT\User\Badges::enabled()) : ?>
|
|
||||||
<button type="button" class="btn-ghost btn-sm" data-aksrt-badges-open data-aksrt-badges-user-id="<?php echo (int) $user_id; ?>" data-aksrt-badges-can-wear="1">
|
|
||||||
<i class="fas fa-award" aria-hidden="true"></i> <?php esc_html_e('我的徽章', 'aksrt'); ?>
|
|
||||||
</button>
|
|
||||||
<?php endif; ?>
|
|
||||||
|
|
||||||
<?php if (!empty($messages_url)) : ?>
|
<?php if (!empty($messages_url)) : ?>
|
||||||
<a href="<?php echo esc_url($messages_url); ?>" class="btn-ghost btn-sm">
|
<a href="<?php echo esc_url($messages_url); ?>" class="btn-ghost btn-sm">
|
||||||
<i class="fas fa-bell" aria-hidden="true"></i> <?php esc_html_e('消息通知', 'aksrt'); ?>
|
<i class="fas fa-bell" aria-hidden="true"></i> <?php esc_html_e('消息通知', 'aksrt'); ?>
|
||||||
|
|||||||
+16
-3
@@ -168,7 +168,7 @@ class Badges {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
$settings = \AKSRT\Settings\Settings::get_user_identity_settings();
|
$settings = \AKSRT\Settings\Settings::get_user_identity_settings();
|
||||||
return !empty($settings['badge']['enabled']);
|
return !empty($settings['medal']['enabled']);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static function public_display(): bool {
|
public static function public_display(): bool {
|
||||||
@@ -176,7 +176,7 @@ class Badges {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
$settings = \AKSRT\Settings\Settings::get_user_identity_settings();
|
$settings = \AKSRT\Settings\Settings::get_user_identity_settings();
|
||||||
return !empty($settings['badge']['enabled']) && !empty($settings['badge']['public_display']);
|
return !empty($settings['medal']['enabled']) && !empty($settings['medal']['public_display']);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -190,7 +190,20 @@ class Badges {
|
|||||||
return self::$dictionary_cache = [];
|
return self::$dictionary_cache = [];
|
||||||
}
|
}
|
||||||
$settings = \AKSRT\Settings\Settings::get_user_identity_settings();
|
$settings = \AKSRT\Settings\Settings::get_user_identity_settings();
|
||||||
$dict = is_array($settings['badge']['dictionary'] ?? null) ? $settings['badge']['dictionary'] : [];
|
$medal = is_array($settings['medal'] ?? null) ? $settings['medal'] : [];
|
||||||
|
$dict = [];
|
||||||
|
foreach ((array) ($medal['items_by_slug'] ?? []) as $item) {
|
||||||
|
if (!is_array($item)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
$dict[] = [
|
||||||
|
'slug' => sanitize_key((string) ($item['slug'] ?? '')),
|
||||||
|
'label' => (string) ($item['name'] ?? $item['slug'] ?? ''),
|
||||||
|
'tone' => 'neutral',
|
||||||
|
'desc' => (string) ($item['desc'] ?? ''),
|
||||||
|
'icon_url' => (string) ($item['icon'] ?? ''),
|
||||||
|
];
|
||||||
|
}
|
||||||
$out = [];
|
$out = [];
|
||||||
foreach ($dict as $item) {
|
foreach ($dict as $item) {
|
||||||
$slug = sanitize_key((string) ($item['slug'] ?? ''));
|
$slug = sanitize_key((string) ($item['slug'] ?? ''));
|
||||||
|
|||||||
+2
-2
@@ -161,8 +161,8 @@ class Home {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!empty($settings['badge']['enabled']) && !empty($settings['badge']['public_display'])) {
|
if (!empty($settings['medal']['enabled']) && !empty($settings['medal']['public_display'])) {
|
||||||
$limit = max(1, (int) ($settings['badge']['limit'] ?? 3));
|
$limit = max(1, (int) ($settings['medal']['limit'] ?? 3));
|
||||||
if (class_exists('AKSRT\\User\\Badges')) {
|
if (class_exists('AKSRT\\User\\Badges')) {
|
||||||
$list = Badges::list_for_user($user_id);
|
$list = Badges::list_for_user($user_id);
|
||||||
$badge_count = 0;
|
$badge_count = 0;
|
||||||
|
|||||||
@@ -100,22 +100,18 @@ $pm_url = ($pm_enabled && $messages_url !== '')
|
|||||||
</h1>
|
</h1>
|
||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
|
|
||||||
<?php if (class_exists('\AKSRT\User\Badges') && \AKSRT\User\Badges::enabled() && \AKSRT\User\Badges::public_display()) : ?>
|
|
||||||
<div class="aksrt-author-hero__badges">
|
|
||||||
<button type="button" class="but but-sm jb-blue mt6" data-aksrt-badges-open data-aksrt-badges-user-id="<?php echo (int) $user_id; ?>" data-aksrt-badges-can-wear="<?php echo $is_own ? '1' : '0'; ?>">
|
|
||||||
<i class="fas fa-award" aria-hidden="true"></i> <?php esc_html_e('徽章明细', 'aksrt'); ?>
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
<?php endif; ?>
|
|
||||||
|
|
||||||
<?php
|
<?php
|
||||||
// IP 归属地 (zibll author_header_identity / user_city_s).
|
// Zibll parity: the badge overview leads the identity row.
|
||||||
$city_badge = function_exists('aksrt_get_user_city_badge_html')
|
$city_badge = function_exists('aksrt_get_user_city_badge_html')
|
||||||
? aksrt_get_user_city_badge_html($user_id, 'user_home', 'badg')
|
? aksrt_get_user_city_badge_html($user_id, 'user_home', 'badg')
|
||||||
: '';
|
: '';
|
||||||
|
$medal_entry = function_exists('aksrt_render_user_medal_entry')
|
||||||
|
? aksrt_render_user_medal_entry($user_id, 'user-home', $is_own)
|
||||||
|
: '';
|
||||||
?>
|
?>
|
||||||
<?php if ($city_badge !== '') : ?>
|
<?php if ($medal_entry !== '' || $city_badge !== '') : ?>
|
||||||
<div class="aksrt-author-hero__identity user-identity flex ac hh">
|
<div class="aksrt-author-hero__identity user-identity flex ac hh">
|
||||||
|
<?php echo $medal_entry; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped ?>
|
||||||
<?php echo $city_badge; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped ?>
|
<?php echo $city_badge; // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped ?>
|
||||||
</div>
|
</div>
|
||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
|
|||||||
Reference in New Issue
Block a user