feat(theme-basic): create nav-items component

pull/3851/head
mehmet-erim 5 years ago
parent 8e9050e6cd
commit 99fb9b6e59

@ -0,0 +1,80 @@
<ul class="navbar-nav">
<ng-container
*ngFor="let element of rightPartElements; trackBy: trackByFn"
[ngTemplateOutlet]="element"
></ng-container>
</ul>
<ng-template #language>
<li *ngIf="(dropdownLanguages$ | async)?.length > 0" class="nav-item">
<div class="dropdown" ngbDropdown #languageDropdown="ngbDropdown" display="static">
<a
ngbDropdownToggle
class="nav-link"
href="javascript:void(0)"
role="button"
id="dropdownMenuLink"
data-toggle="dropdown"
aria-haspopup="true"
aria-expanded="false"
>
{{ defaultLanguage$ | async }}
</a>
<div
class="dropdown-menu dropdown-menu-right border-0 shadow-sm"
aria-labelledby="dropdownMenuLink"
[class.d-block]="smallScreen && languageDropdown.isOpen()"
>
<a
*ngFor="let lang of dropdownLanguages$ | async"
href="javascript:void(0)"
class="dropdown-item"
(click)="onChangeLang(lang.cultureName)"
>{{ lang?.displayName }}</a
>
</div>
</div>
</li>
</ng-template>
<ng-template #currentUser>
<li class="nav-item">
<ng-template #loginBtn>
<a role="button" class="nav-link" routerLink="/account/login">{{
'AbpAccount::Login' | abpLocalization
}}</a>
</ng-template>
<div
*ngIf="(currentUser$ | async)?.isAuthenticated; else loginBtn"
ngbDropdown
class="dropdown"
#currentUserDropdown="ngbDropdown"
display="static"
>
<a
ngbDropdownToggle
class="nav-link"
href="javascript:void(0)"
role="button"
id="dropdownMenuLink"
data-toggle="dropdown"
aria-haspopup="true"
aria-expanded="false"
>
{{ (currentUser$ | async)?.userName }}
</a>
<div
class="dropdown-menu dropdown-menu-right border-0 shadow-sm"
aria-labelledby="dropdownMenuLink"
[class.d-block]="smallScreen && currentUserDropdown.isOpen()"
>
<a class="dropdown-item" routerLink="/account/manage-profile"
><i class="fa fa-cog mr-1"></i>{{ 'AbpAccount::ManageYourProfile' | abpLocalization }}</a
>
<a class="dropdown-item" href="javascript:void(0)" (click)="logout()"
><i class="fa fa-power-off mr-1"></i>{{ 'AbpUi::Logout' | abpLocalization }}</a
>
</div>
</div>
</li>
</ng-template>

@ -0,0 +1,125 @@
import {
Component,
AfterViewInit,
TrackByFunction,
TemplateRef,
ViewChild,
OnDestroy,
Input,
} from '@angular/core';
import {
ABP,
takeUntilDestroy,
SetLanguage,
AuthService,
ConfigState,
ApplicationConfiguration,
SessionState,
} from '@abp/ng.core';
import { LayoutState } from '../../states/layout.state';
import { Store, Select } from '@ngxs/store';
import { eNavigationElementNames } from '../../enums/navigation-element-names';
import { AddNavigationElement } from '../../actions/layout.actions';
import { map, filter } from 'rxjs/operators';
import { Observable } from 'rxjs';
import { Layout } from '../../models/layout';
import { Navigate, RouterState } from '@ngxs/router-plugin';
import snq from 'snq';
import compare from 'just-compare';
@Component({
selector: 'abp-nav-items',
templateUrl: 'nav-items.component.html',
})
export class NavItemsComponent implements AfterViewInit, OnDestroy {
@Select(LayoutState.getNavigationElements)
navElements$: Observable<Layout.NavigationElement[]>;
@Select(ConfigState.getOne('currentUser'))
currentUser$: Observable<ApplicationConfiguration.CurrentUser>;
@Select(ConfigState.getDeep('localization.languages'))
languages$: Observable<ApplicationConfiguration.Language[]>;
@ViewChild('currentUser', { static: false, read: TemplateRef })
currentUserRef: TemplateRef<any>;
@ViewChild('language', { static: false, read: TemplateRef })
languageRef: TemplateRef<any>;
@Input()
smallScreen: boolean;
rightPartElements: TemplateRef<any>[] = [];
trackByFn: TrackByFunction<ABP.FullRoute> = (_, element) => element;
get defaultLanguage$(): Observable<string> {
return this.languages$.pipe(
map(
languages =>
snq(
() => languages.find(lang => lang.cultureName === this.selectedLangCulture).displayName,
),
'',
),
);
}
get dropdownLanguages$(): Observable<ApplicationConfiguration.Language[]> {
return this.languages$.pipe(
map(
languages =>
snq(() => languages.filter(lang => lang.cultureName !== this.selectedLangCulture)),
[],
),
);
}
get selectedLangCulture(): string {
return this.store.selectSnapshot(SessionState.getLanguage);
}
constructor(private store: Store, private authService: AuthService) {}
ngAfterViewInit() {
const navigations = this.store
.selectSnapshot(LayoutState.getNavigationElements)
.map(({ name }) => name);
if (navigations.indexOf(eNavigationElementNames.Language) < 0) {
this.store.dispatch(
new AddNavigationElement([
{ element: this.languageRef, order: 4, name: eNavigationElementNames.Language },
{ element: this.currentUserRef, order: 5, name: eNavigationElementNames.User },
]),
);
}
this.navElements$
.pipe(
map(elements => elements.map(({ element }) => element)),
filter(elements => !compare(elements, this.rightPartElements)),
takeUntilDestroy(this),
)
.subscribe(elements => {
setTimeout(() => (this.rightPartElements = elements), 0);
});
}
ngOnDestroy() {}
onChangeLang(cultureName: string) {
this.store.dispatch(new SetLanguage(cultureName));
}
logout() {
this.authService.logout().subscribe(() => {
this.store.dispatch(
new Navigate(['/'], null, {
state: { redirectUrl: this.store.selectSnapshot(RouterState).state.url },
}),
);
});
}
}
Loading…
Cancel
Save