[PM-7176] Create appearance settings component (navigational changes) (#8911)
* Move about.component into tools ownership * Split out account security settings Move settings.component.ts to auth/popup/settings and rename to account-security.component.ts Move controls from settings.component.html and create account-security.component.html Move settings.component.html to tools/popup/settings.component.html Create settings.component.ts under tools/popup/settings Fixup module imports and routing Add new strings to en/message.json * Move vault-timeout-input.component to auth * Move await-desktop-dialog.component to auth * Add transition for account-security * Create appearance settings component * Add entry in settings to navigate to the appearance settings page * Add transition animation for settings to appearance and back * Remove settings from options that are now under appearance --------- Co-authored-by: Daniel James Smith <djsmith85@users.noreply.github.com>
This commit is contained in:
parent
350ad890de
commit
c2812fc21d
|
@ -3035,6 +3035,9 @@
|
|||
"accountSecurity": {
|
||||
"message": "Account security"
|
||||
},
|
||||
"appearance": {
|
||||
"message": "Appearance"
|
||||
},
|
||||
"errorAssigningTargetCollection": {
|
||||
"message": "Error assigning target collection."
|
||||
},
|
||||
|
|
|
@ -202,6 +202,10 @@ export const routerTransition = trigger("routerTransition", [
|
|||
transition("tabs => options", inSlideLeft),
|
||||
transition("options => tabs", outSlideRight),
|
||||
|
||||
// Appearance settings
|
||||
transition("tabs => appearance", inSlideLeft),
|
||||
transition("appearance => tabs", outSlideRight),
|
||||
|
||||
transition("tabs => premium", inSlideLeft),
|
||||
transition("premium => tabs", outSlideRight),
|
||||
|
||||
|
|
|
@ -48,6 +48,7 @@ import { VaultFilterComponent } from "../vault/popup/components/vault/vault-filt
|
|||
import { VaultItemsComponent } from "../vault/popup/components/vault/vault-items.component";
|
||||
import { VaultV2Component } from "../vault/popup/components/vault/vault-v2.component";
|
||||
import { ViewComponent } from "../vault/popup/components/vault/view.component";
|
||||
import { AppearanceComponent } from "../vault/popup/settings/appearance.component";
|
||||
import { FolderAddEditComponent } from "../vault/popup/settings/folder-add-edit.component";
|
||||
import { FoldersComponent } from "../vault/popup/settings/folders.component";
|
||||
import { SyncComponent } from "../vault/popup/settings/sync.component";
|
||||
|
@ -303,6 +304,12 @@ const routes: Routes = [
|
|||
canActivate: [AuthGuard],
|
||||
data: { state: "options" },
|
||||
},
|
||||
{
|
||||
path: "appearance",
|
||||
component: AppearanceComponent,
|
||||
canActivate: [AuthGuard],
|
||||
data: { state: "appearance" },
|
||||
},
|
||||
{
|
||||
path: "clone-cipher",
|
||||
component: AddEditComponent,
|
||||
|
|
|
@ -70,6 +70,7 @@ import { VaultSelectComponent } from "../vault/popup/components/vault/vault-sele
|
|||
import { VaultV2Component } from "../vault/popup/components/vault/vault-v2.component";
|
||||
import { ViewCustomFieldsComponent } from "../vault/popup/components/vault/view-custom-fields.component";
|
||||
import { ViewComponent } from "../vault/popup/components/vault/view.component";
|
||||
import { AppearanceComponent } from "../vault/popup/settings/appearance.component";
|
||||
import { FolderAddEditComponent } from "../vault/popup/settings/folder-add-edit.component";
|
||||
import { FoldersComponent } from "../vault/popup/settings/folders.component";
|
||||
import { SyncComponent } from "../vault/popup/settings/sync.component";
|
||||
|
@ -148,6 +149,7 @@ import "../platform/popup/locales";
|
|||
LoginViaAuthRequestComponent,
|
||||
LoginDecryptionOptionsComponent,
|
||||
OptionsComponent,
|
||||
AppearanceComponent,
|
||||
GeneratorComponent,
|
||||
PasswordGeneratorHistoryComponent,
|
||||
PasswordHistoryComponent,
|
||||
|
|
|
@ -192,56 +192,5 @@
|
|||
{{ "showIdentitiesCurrentTabDesc" | i18n }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="box">
|
||||
<div class="box-content">
|
||||
<div class="box-content-row box-content-row-checkbox" appBoxRow>
|
||||
<label for="favicon">{{ "enableFavicon" | i18n }}</label>
|
||||
<input
|
||||
id="favicon"
|
||||
type="checkbox"
|
||||
aria-describedby="faviconHelp"
|
||||
(change)="updateFavicon()"
|
||||
[(ngModel)]="enableFavicon"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div id="faviconHelp" class="box-footer">
|
||||
{{ accountSwitcherEnabled ? ("faviconDescAlt" | i18n) : ("faviconDesc" | i18n) }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="box">
|
||||
<div class="box-content">
|
||||
<div class="box-content-row box-content-row-checkbox" appBoxRow>
|
||||
<label for="badge">{{ "enableBadgeCounter" | i18n }}</label>
|
||||
<input
|
||||
id="badge"
|
||||
type="checkbox"
|
||||
aria-describedby="badgeHelp"
|
||||
(change)="updateBadgeCounter()"
|
||||
[(ngModel)]="enableBadgeCounter"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div id="badgeHelp" class="box-footer">{{ "badgeCounterDesc" | i18n }}</div>
|
||||
</div>
|
||||
<div class="box">
|
||||
<div class="box-content">
|
||||
<div class="box-content-row" appBoxRow>
|
||||
<label for="theme">{{ "theme" | i18n }}</label>
|
||||
<select
|
||||
id="theme"
|
||||
name="Theme"
|
||||
aria-describedby="themeHelp"
|
||||
[(ngModel)]="theme"
|
||||
(change)="saveTheme()"
|
||||
>
|
||||
<option *ngFor="let o of themeOptions" [ngValue]="o.value">{{ o.name }}</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div id="themeHelp" class="box-footer">
|
||||
{{ accountSwitcherEnabled ? ("themeDescAlt" | i18n) : ("themeDesc" | i18n) }}
|
||||
</div>
|
||||
</div>
|
||||
</ng-container>
|
||||
</main>
|
||||
|
|
|
@ -2,7 +2,6 @@ import { Component, OnInit } from "@angular/core";
|
|||
import { firstValueFrom } from "rxjs";
|
||||
|
||||
import { AutofillSettingsServiceAbstraction } from "@bitwarden/common/autofill/services/autofill-settings.service";
|
||||
import { BadgeSettingsServiceAbstraction } from "@bitwarden/common/autofill/services/badge-settings.service";
|
||||
import { DomainSettingsService } from "@bitwarden/common/autofill/services/domain-settings.service";
|
||||
import { UserNotificationSettingsServiceAbstraction } from "@bitwarden/common/autofill/services/user-notification-settings.service";
|
||||
import { ClearClipboardDelaySetting } from "@bitwarden/common/autofill/types";
|
||||
|
@ -12,8 +11,6 @@ import {
|
|||
} from "@bitwarden/common/models/domain/domain-service";
|
||||
import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service";
|
||||
import { MessagingService } from "@bitwarden/common/platform/abstractions/messaging.service";
|
||||
import { ThemeType } from "@bitwarden/common/platform/enums";
|
||||
import { ThemeStateService } from "@bitwarden/common/platform/theming/theme-state.service";
|
||||
import { VaultSettingsService } from "@bitwarden/common/vault/abstractions/vault-settings/vault-settings.service";
|
||||
|
||||
import { enableAccountSwitching } from "../../platform/flags";
|
||||
|
@ -23,8 +20,6 @@ import { enableAccountSwitching } from "../../platform/flags";
|
|||
templateUrl: "options.component.html",
|
||||
})
|
||||
export class OptionsComponent implements OnInit {
|
||||
enableFavicon = false;
|
||||
enableBadgeCounter = true;
|
||||
enableAutoFillOnPageLoad = false;
|
||||
autoFillOnPageLoadDefault = false;
|
||||
autoFillOnPageLoadOptions: any[];
|
||||
|
@ -36,8 +31,6 @@ export class OptionsComponent implements OnInit {
|
|||
showCardsCurrentTab = false;
|
||||
showIdentitiesCurrentTab = false;
|
||||
showClearClipboard = true;
|
||||
theme: ThemeType;
|
||||
themeOptions: any[];
|
||||
defaultUriMatch: UriMatchStrategySetting = UriMatchStrategy.Domain;
|
||||
uriMatchOptions: any[];
|
||||
clearClipboard: ClearClipboardDelaySetting;
|
||||
|
@ -52,18 +45,9 @@ export class OptionsComponent implements OnInit {
|
|||
private userNotificationSettingsService: UserNotificationSettingsServiceAbstraction,
|
||||
private autofillSettingsService: AutofillSettingsServiceAbstraction,
|
||||
private domainSettingsService: DomainSettingsService,
|
||||
private badgeSettingsService: BadgeSettingsServiceAbstraction,
|
||||
i18nService: I18nService,
|
||||
private themeStateService: ThemeStateService,
|
||||
private vaultSettingsService: VaultSettingsService,
|
||||
) {
|
||||
this.themeOptions = [
|
||||
{ name: i18nService.t("default"), value: ThemeType.System },
|
||||
{ name: i18nService.t("light"), value: ThemeType.Light },
|
||||
{ name: i18nService.t("dark"), value: ThemeType.Dark },
|
||||
{ name: "Nord", value: ThemeType.Nord },
|
||||
{ name: i18nService.t("solarizedDark"), value: ThemeType.SolarizedDark },
|
||||
];
|
||||
this.uriMatchOptions = [
|
||||
{ name: i18nService.t("baseDomain"), value: UriMatchStrategy.Domain },
|
||||
{ name: i18nService.t("host"), value: UriMatchStrategy.Host },
|
||||
|
@ -117,14 +101,8 @@ export class OptionsComponent implements OnInit {
|
|||
|
||||
this.enableAutoTotpCopy = await firstValueFrom(this.autofillSettingsService.autoCopyTotp$);
|
||||
|
||||
this.enableFavicon = await firstValueFrom(this.domainSettingsService.showFavicons$);
|
||||
|
||||
this.enableBadgeCounter = await firstValueFrom(this.badgeSettingsService.enableBadgeCounter$);
|
||||
|
||||
this.enablePasskeys = await firstValueFrom(this.vaultSettingsService.enablePasskeys$);
|
||||
|
||||
this.theme = await firstValueFrom(this.themeStateService.selectedTheme$);
|
||||
|
||||
const defaultUriMatch = await firstValueFrom(
|
||||
this.domainSettingsService.defaultUriMatchStrategy$,
|
||||
);
|
||||
|
@ -166,15 +144,6 @@ export class OptionsComponent implements OnInit {
|
|||
await this.autofillSettingsService.setAutofillOnPageLoadDefault(this.autoFillOnPageLoadDefault);
|
||||
}
|
||||
|
||||
async updateFavicon() {
|
||||
await this.domainSettingsService.setShowFavicons(this.enableFavicon);
|
||||
}
|
||||
|
||||
async updateBadgeCounter() {
|
||||
await this.badgeSettingsService.setEnableBadgeCounter(this.enableBadgeCounter);
|
||||
this.messagingService.send("bgUpdateContextMenu");
|
||||
}
|
||||
|
||||
async updateShowCardsCurrentTab() {
|
||||
await this.vaultSettingsService.setShowCardsCurrentTab(this.showCardsCurrentTab);
|
||||
}
|
||||
|
@ -183,10 +152,6 @@ export class OptionsComponent implements OnInit {
|
|||
await this.vaultSettingsService.setShowIdentitiesCurrentTab(this.showIdentitiesCurrentTab);
|
||||
}
|
||||
|
||||
async saveTheme() {
|
||||
await this.themeStateService.setSelectedTheme(this.theme);
|
||||
}
|
||||
|
||||
async saveClearClipboard() {
|
||||
await this.autofillSettingsService.setClearClipboardDelay(this.clearClipboard);
|
||||
}
|
||||
|
|
|
@ -86,6 +86,14 @@
|
|||
<div class="row-main">{{ "options" | i18n }}</div>
|
||||
<i class="bwi bwi-angle-right bwi-lg row-sub-icon" aria-hidden="true"></i>
|
||||
</button>
|
||||
<button
|
||||
type="button"
|
||||
class="box-content-row box-content-row-flex text-default"
|
||||
routerLink="/appearance"
|
||||
>
|
||||
<div class="row-main">{{ "appearance" | i18n }}</div>
|
||||
<i class="bwi bwi-angle-right bwi-lg row-sub-icon" aria-hidden="true"></i>
|
||||
</button>
|
||||
<button
|
||||
type="button"
|
||||
class="box-content-row box-content-row-flex text-default"
|
||||
|
|
|
@ -0,0 +1,67 @@
|
|||
<header>
|
||||
<div class="left">
|
||||
<button type="button" routerLink="/tabs/settings">
|
||||
<span class="header-icon"><i class="bwi bwi-angle-left" aria-hidden="true"></i></span>
|
||||
<span>{{ "back" | i18n }}</span>
|
||||
</button>
|
||||
</div>
|
||||
<h1 class="center">
|
||||
<span class="title">{{ "appearance" | i18n }}</span>
|
||||
</h1>
|
||||
<div class="right">
|
||||
<app-pop-out></app-pop-out>
|
||||
</div>
|
||||
</header>
|
||||
<main tabindex="-1">
|
||||
<div class="box">
|
||||
<div class="box-content">
|
||||
<div class="box-content-row" appBoxRow>
|
||||
<label for="theme">{{ "theme" | i18n }}</label>
|
||||
<select
|
||||
id="theme"
|
||||
name="Theme"
|
||||
aria-describedby="themeHelp"
|
||||
[(ngModel)]="theme"
|
||||
(change)="saveTheme()"
|
||||
>
|
||||
<option *ngFor="let o of themeOptions" [ngValue]="o.value">{{ o.name }}</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div id="themeHelp" class="box-footer">
|
||||
{{ accountSwitcherEnabled ? ("themeDescAlt" | i18n) : ("themeDesc" | i18n) }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="box">
|
||||
<div class="box-content">
|
||||
<div class="box-content-row box-content-row-checkbox" appBoxRow>
|
||||
<label for="badge">{{ "enableBadgeCounter" | i18n }}</label>
|
||||
<input
|
||||
id="badge"
|
||||
type="checkbox"
|
||||
aria-describedby="badgeHelp"
|
||||
(change)="updateBadgeCounter()"
|
||||
[(ngModel)]="enableBadgeCounter"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div id="badgeHelp" class="box-footer">{{ "badgeCounterDesc" | i18n }}</div>
|
||||
</div>
|
||||
<div class="box">
|
||||
<div class="box-content">
|
||||
<div class="box-content-row box-content-row-checkbox" appBoxRow>
|
||||
<label for="favicon">{{ "enableFavicon" | i18n }}</label>
|
||||
<input
|
||||
id="favicon"
|
||||
type="checkbox"
|
||||
aria-describedby="faviconHelp"
|
||||
(change)="updateFavicon()"
|
||||
[(ngModel)]="enableFavicon"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div id="faviconHelp" class="box-footer">
|
||||
{{ accountSwitcherEnabled ? ("faviconDescAlt" | i18n) : ("faviconDesc" | i18n) }}
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
|
@ -0,0 +1,62 @@
|
|||
import { Component, OnInit } from "@angular/core";
|
||||
import { firstValueFrom } from "rxjs";
|
||||
|
||||
import { BadgeSettingsServiceAbstraction } from "@bitwarden/common/autofill/services/badge-settings.service";
|
||||
import { DomainSettingsService } from "@bitwarden/common/autofill/services/domain-settings.service";
|
||||
import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service";
|
||||
import { MessagingService } from "@bitwarden/common/platform/abstractions/messaging.service";
|
||||
import { ThemeType } from "@bitwarden/common/platform/enums";
|
||||
import { ThemeStateService } from "@bitwarden/common/platform/theming/theme-state.service";
|
||||
|
||||
import { enableAccountSwitching } from "../../../platform/flags";
|
||||
|
||||
@Component({
|
||||
selector: "vault-appearance",
|
||||
templateUrl: "appearance.component.html",
|
||||
})
|
||||
export class AppearanceComponent implements OnInit {
|
||||
enableFavicon = false;
|
||||
enableBadgeCounter = true;
|
||||
theme: ThemeType;
|
||||
themeOptions: any[];
|
||||
accountSwitcherEnabled = false;
|
||||
|
||||
constructor(
|
||||
private messagingService: MessagingService,
|
||||
private domainSettingsService: DomainSettingsService,
|
||||
private badgeSettingsService: BadgeSettingsServiceAbstraction,
|
||||
i18nService: I18nService,
|
||||
private themeStateService: ThemeStateService,
|
||||
) {
|
||||
this.themeOptions = [
|
||||
{ name: i18nService.t("default"), value: ThemeType.System },
|
||||
{ name: i18nService.t("light"), value: ThemeType.Light },
|
||||
{ name: i18nService.t("dark"), value: ThemeType.Dark },
|
||||
{ name: "Nord", value: ThemeType.Nord },
|
||||
{ name: i18nService.t("solarizedDark"), value: ThemeType.SolarizedDark },
|
||||
];
|
||||
|
||||
this.accountSwitcherEnabled = enableAccountSwitching();
|
||||
}
|
||||
|
||||
async ngOnInit() {
|
||||
this.enableFavicon = await firstValueFrom(this.domainSettingsService.showFavicons$);
|
||||
|
||||
this.enableBadgeCounter = await firstValueFrom(this.badgeSettingsService.enableBadgeCounter$);
|
||||
|
||||
this.theme = await firstValueFrom(this.themeStateService.selectedTheme$);
|
||||
}
|
||||
|
||||
async updateFavicon() {
|
||||
await this.domainSettingsService.setShowFavicons(this.enableFavicon);
|
||||
}
|
||||
|
||||
async updateBadgeCounter() {
|
||||
await this.badgeSettingsService.setEnableBadgeCounter(this.enableBadgeCounter);
|
||||
this.messagingService.send("bgUpdateContextMenu");
|
||||
}
|
||||
|
||||
async saveTheme() {
|
||||
await this.themeStateService.setSelectedTheme(this.theme);
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue