diff --git a/npm/ng-packs/apps/dev-app/src/app/app-routing.module.ts b/npm/ng-packs/apps/dev-app/src/app/app-routing.module.ts index 0d9f82ea25..6588538b28 100644 --- a/npm/ng-packs/apps/dev-app/src/app/app-routing.module.ts +++ b/npm/ng-packs/apps/dev-app/src/app/app-routing.module.ts @@ -31,4 +31,4 @@ const routes: Routes = [ imports: [RouterModule.forRoot(routes, {})], exports: [RouterModule], }) -export class AppRoutingModule {} +export class AppRoutingModule { } diff --git a/npm/ng-packs/apps/dev-app/src/favicon.ico b/npm/ng-packs/apps/dev-app/src/favicon.ico index 39695854d2..3a4e8ddfcc 100644 Binary files a/npm/ng-packs/apps/dev-app/src/favicon.ico and b/npm/ng-packs/apps/dev-app/src/favicon.ico differ diff --git a/npm/ng-packs/packages/account/src/lib/account-routing.module.ts b/npm/ng-packs/packages/account/src/lib/account-routing.module.ts index a10bde7009..6803444712 100644 --- a/npm/ng-packs/packages/account/src/lib/account-routing.module.ts +++ b/npm/ng-packs/packages/account/src/lib/account-routing.module.ts @@ -35,6 +35,7 @@ const routes: Routes = [ defaultComponent: LoginComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpAccount::Login', }, { path: 'register', @@ -46,6 +47,7 @@ const routes: Routes = [ defaultComponent: RegisterComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpAccount::Register', }, { path: 'forgot-password', @@ -58,6 +60,7 @@ const routes: Routes = [ defaultComponent: ForgotPasswordComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpAccount::ForgotPassword', }, { path: 'reset-password', @@ -70,6 +73,7 @@ const routes: Routes = [ defaultComponent: ResetPasswordComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpAccount::ResetPassword', }, { path: 'manage', @@ -82,6 +86,7 @@ const routes: Routes = [ defaultComponent: ManageProfileComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpAccount::Menu:Account', }, ], }, @@ -91,4 +96,4 @@ const routes: Routes = [ imports: [RouterModule.forChild(routes)], exports: [RouterModule], }) -export class AccountRoutingModule {} +export class AccountRoutingModule { } diff --git a/npm/ng-packs/packages/core/src/lib/core.module.ts b/npm/ng-packs/packages/core/src/lib/core.module.ts index 7c8f450cda..e236fb50bf 100644 --- a/npm/ng-packs/packages/core/src/lib/core.module.ts +++ b/npm/ng-packs/packages/core/src/lib/core.module.ts @@ -2,7 +2,7 @@ import { CommonModule } from '@angular/common'; import { HttpClientModule, HttpClientXsrfModule } from '@angular/common/http'; import { APP_INITIALIZER, Injector, ModuleWithProviders, NgModule } from '@angular/core'; import { FormsModule, ReactiveFormsModule } from '@angular/forms'; -import { RouterModule } from '@angular/router'; +import { RouterModule, TitleStrategy } from '@angular/router'; import { AbstractNgModelComponent } from './abstracts/ng-model.component'; import { DynamicLayoutComponent } from './components/dynamic-layout.component'; import { ReplaceableRouteContainerComponent } from './components/replaceable-route-container.component'; @@ -42,6 +42,7 @@ import { SORT_COMPARE_FUNC, compareFuncFactory } from './tokens/compare-func.tok import { AuthErrorFilterService } from './abstracts'; import { DYNAMIC_LAYOUTS_TOKEN } from "./tokens/dynamic-layout.token"; import { DEFAULT_DYNAMIC_LAYOUTS } from "./constants"; +import { CustomTitleStrategy } from './services/title-strategy.service'; const standaloneDirectives = [ @@ -194,6 +195,10 @@ export class CoreModule { { provide: DYNAMIC_LAYOUTS_TOKEN, useValue: options.dynamicLayouts || DEFAULT_DYNAMIC_LAYOUTS + }, + { + provide: TitleStrategy, + useExisting: CustomTitleStrategy } ], }; diff --git a/npm/ng-packs/packages/core/src/lib/services/title-strategy.service.ts b/npm/ng-packs/packages/core/src/lib/services/title-strategy.service.ts new file mode 100644 index 0000000000..e25bac5fa5 --- /dev/null +++ b/npm/ng-packs/packages/core/src/lib/services/title-strategy.service.ts @@ -0,0 +1,42 @@ +import { Injectable, effect, inject, signal } from "@angular/core"; +import { Title } from "@angular/platform-browser"; +import { TitleStrategy, RouterStateSnapshot } from "@angular/router"; +import { ConfigStateService } from "./config-state.service"; +import { LocalizationService } from "./localization.service"; +import { tap } from "rxjs"; +import { toSignal } from "@angular/core/rxjs-interop"; + +@Injectable({ + providedIn: 'root' +}) +export class CustomTitleStrategy extends TitleStrategy { + protected readonly title = inject(Title); + protected readonly configState = inject(ConfigStateService); + protected readonly localizationService = inject(LocalizationService); + routerState: RouterStateSnapshot; + projectName = toSignal(this.configState.getDeep$("localization.defaultResourceName"), { initialValue: "MyProjectName" }); + langugageChange = toSignal(this.localizationService.languageChange$); + + override updateTitle(routerState: RouterStateSnapshot) { + let title = this.buildTitle(routerState); + this.routerState = routerState; + + if (title === undefined) { + this.title.setTitle(`${this.projectName()}`); + return; + } + + const localizedTitle = this.localizationService.instant({ key: title, defaultValue: title }); + this.title.setTitle(`${localizedTitle} | ${this.projectName()}`); + } + + constructor() { + super(); + effect(() => { + if (this.langugageChange()) { + this.updateTitle(this.routerState); + } + }); + } +} +// .pipe(tap(() => this.updateTitle(this.routerState))).subscribe(); \ No newline at end of file diff --git a/npm/ng-packs/packages/identity/src/lib/identity-routing.module.ts b/npm/ng-packs/packages/identity/src/lib/identity-routing.module.ts index 93ac912d97..985e075200 100644 --- a/npm/ng-packs/packages/identity/src/lib/identity-routing.module.ts +++ b/npm/ng-packs/packages/identity/src/lib/identity-routing.module.ts @@ -32,6 +32,7 @@ const routes: Routes = [ defaultComponent: RolesComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpIdentity::Roles', }, { path: 'users', @@ -43,6 +44,7 @@ const routes: Routes = [ defaultComponent: UsersComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpIdentity::Users', }, ], }, diff --git a/npm/ng-packs/packages/setting-management/src/lib/setting-management-routing.module.ts b/npm/ng-packs/packages/setting-management/src/lib/setting-management-routing.module.ts index b642bc176e..98d3a2cb30 100644 --- a/npm/ng-packs/packages/setting-management/src/lib/setting-management-routing.module.ts +++ b/npm/ng-packs/packages/setting-management/src/lib/setting-management-routing.module.ts @@ -27,6 +27,7 @@ const routes: Routes = [ }, }, ], + title: 'AbpSettingManagement::Settings', }, ]; @@ -34,4 +35,4 @@ const routes: Routes = [ imports: [RouterModule.forChild(routes)], exports: [RouterModule], }) -export class SettingManagementRoutingModule {} +export class SettingManagementRoutingModule { } diff --git a/npm/ng-packs/packages/tenant-management/src/lib/tenant-management-routing.module.ts b/npm/ng-packs/packages/tenant-management/src/lib/tenant-management-routing.module.ts index 2fcce5e108..187e60e184 100644 --- a/npm/ng-packs/packages/tenant-management/src/lib/tenant-management-routing.module.ts +++ b/npm/ng-packs/packages/tenant-management/src/lib/tenant-management-routing.module.ts @@ -31,6 +31,7 @@ const routes: Routes = [ defaultComponent: TenantsComponent, } as ReplaceableComponents.RouteData, }, + title: 'AbpTenantManagement::Tenants', }, ], }, @@ -40,4 +41,4 @@ const routes: Routes = [ imports: [RouterModule.forChild(routes)], exports: [RouterModule], }) -export class TenantManagementRoutingModule {} +export class TenantManagementRoutingModule { }