mirror of
https://github.com/openfrontio/OpenFrontIO.git
synced 2026-06-25 11:14:36 +00:00
Refactor & standardize modal tabs (#3864)
## Description: Refactors tab handling out of the individual modal components and into the base o-modal component. Tabs are now declared by passing tabs, activeTab, and onTabChange props, and a new named header slot pins consumer-supplied content above the tabs. This standardizes the modal tab look. <img width="1089" height="290" alt="Screenshot 2026-05-06 at 12 17 33 PM" src="https://github.com/user-attachments/assets/08d5a039-0aef-4aa7-b972-1e43b8723685" /> ## Please complete the following: - [x] I have added screenshots for all UI updates - [x] I process any text displayed to the user through translateText() and I've added it to the en.json file - [x] I have added relevant tests to the test directory - [x] I confirm I have thoroughly tested these changes and take full responsibility for any bugs introduced ## Please put your Discord username so you can be contacted if a bug or regression is found: evan
This commit is contained in:
+23
-53
@@ -41,43 +41,12 @@ export class StoreModal extends BaseModal {
|
||||
}
|
||||
|
||||
private renderHeader(): TemplateResult {
|
||||
return html`
|
||||
${modalHeader({
|
||||
title: translateText("store.title"),
|
||||
onBack: () => this.close(),
|
||||
ariaLabel: translateText("common.back"),
|
||||
rightContent: html`<not-logged-in-warning></not-logged-in-warning>`,
|
||||
})}
|
||||
<div class="flex items-center gap-2 justify-center pt-2">
|
||||
<button
|
||||
class="px-6 py-2 text-xs font-bold transition-all duration-200 rounded-lg uppercase tracking-widest ${this
|
||||
.activeTab === "packs"
|
||||
? "bg-malibu-blue/20 text-aquarius border border-malibu-blue/30 shadow-[var(--shadow-malibu-blue)]"
|
||||
: "text-white/40 hover:text-white hover:bg-white/5 border border-transparent"}"
|
||||
@click=${() => (this.activeTab = "packs")}
|
||||
>
|
||||
${translateText("store.packs")}
|
||||
</button>
|
||||
<button
|
||||
class="px-6 py-2 text-xs font-bold transition-all duration-200 rounded-lg uppercase tracking-widest ${this
|
||||
.activeTab === "patterns"
|
||||
? "bg-malibu-blue/20 text-aquarius border border-malibu-blue/30 shadow-[var(--shadow-malibu-blue)]"
|
||||
: "text-white/40 hover:text-white hover:bg-white/5 border border-transparent"}"
|
||||
@click=${() => (this.activeTab = "patterns")}
|
||||
>
|
||||
${translateText("store.patterns")}
|
||||
</button>
|
||||
<button
|
||||
class="px-6 py-2 text-xs font-bold transition-all duration-200 rounded-lg uppercase tracking-widest ${this
|
||||
.activeTab === "flags"
|
||||
? "bg-malibu-blue/20 text-aquarius border border-malibu-blue/30 shadow-[var(--shadow-malibu-blue)]"
|
||||
: "text-white/40 hover:text-white hover:bg-white/5 border border-transparent"}"
|
||||
@click=${() => (this.activeTab = "flags")}
|
||||
>
|
||||
${translateText("store.flags")}
|
||||
</button>
|
||||
</div>
|
||||
`;
|
||||
return modalHeader({
|
||||
title: translateText("store.title"),
|
||||
onBack: () => this.close(),
|
||||
ariaLabel: translateText("common.back"),
|
||||
rightContent: html`<not-logged-in-warning></not-logged-in-warning>`,
|
||||
});
|
||||
}
|
||||
|
||||
private renderPatternGrid(): TemplateResult {
|
||||
@@ -188,22 +157,18 @@ export class StoreModal extends BaseModal {
|
||||
render() {
|
||||
if (!this.isActive && !this.inline) return html``;
|
||||
|
||||
const content = html`
|
||||
<div class="${this.modalContainerClass}">
|
||||
${this.renderHeader()}
|
||||
<div class="overflow-y-auto pr-2 custom-scrollbar mr-1">
|
||||
${this.activeTab === "patterns"
|
||||
? this.renderPatternGrid()
|
||||
: this.activeTab === "flags"
|
||||
? this.renderFlagGrid()
|
||||
: this.renderPackGrid()}
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
const tabs = [
|
||||
{ key: "packs", label: translateText("store.packs") },
|
||||
{ key: "patterns", label: translateText("store.patterns") },
|
||||
{ key: "flags", label: translateText("store.flags") },
|
||||
];
|
||||
|
||||
if (this.inline) {
|
||||
return content;
|
||||
}
|
||||
const grid =
|
||||
this.activeTab === "patterns"
|
||||
? this.renderPatternGrid()
|
||||
: this.activeTab === "flags"
|
||||
? this.renderFlagGrid()
|
||||
: this.renderPackGrid();
|
||||
|
||||
return html`
|
||||
<o-modal
|
||||
@@ -212,8 +177,13 @@ export class StoreModal extends BaseModal {
|
||||
?inline=${this.inline}
|
||||
?hideHeader=${true}
|
||||
?hideCloseButton=${true}
|
||||
.tabs=${tabs}
|
||||
.activeTab=${this.activeTab}
|
||||
.onTabChange=${(key: string) =>
|
||||
(this.activeTab = key as "patterns" | "flags" | "packs")}
|
||||
>
|
||||
${content}
|
||||
<div slot="header">${this.renderHeader()}</div>
|
||||
${grid}
|
||||
</o-modal>
|
||||
`;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user