Browse Source

UI: continue new-menu rollout — home-links page, dashboard view toolbar, breadcrumb/user-menu polish

pull/15888/head
Igor Kulikov 3 months ago
parent
commit
f587052369
  1. 6
      ui-ngx/src/app/modules/home/components/dashboard-page/dashboard-page.component.html
  2. 2
      ui-ngx/src/app/modules/home/components/dashboard-page/dashboard-page.component.scss
  3. 9
      ui-ngx/src/app/modules/home/components/dashboard-page/dashboard-toolbar.component.scss
  4. 6
      ui-ngx/src/app/modules/home/components/dashboard-page/states/default-state-controller.component.html
  5. 14
      ui-ngx/src/app/modules/home/components/dashboard-page/states/default-state-controller.component.scss
  6. 6
      ui-ngx/src/app/modules/home/components/dashboard-page/states/default-state-controller.component.ts
  7. 7
      ui-ngx/src/app/modules/home/components/dashboard-page/states/entity-state-controller.component.html
  8. 3
      ui-ngx/src/app/modules/home/components/dashboard-page/states/entity-state-controller.component.scss
  9. 2
      ui-ngx/src/app/modules/home/components/dashboard-view/dashboard-view.component.html
  10. 26
      ui-ngx/src/app/modules/home/components/dashboard-view/dashboard-view.component.ts
  11. 1
      ui-ngx/src/app/modules/home/pages/home-links/home-links-routing.module.ts
  12. 2
      ui-ngx/src/app/modules/home/pages/home-links/home-links.component.html
  13. 44
      ui-ngx/src/app/modules/home/pages/home-links/home-links.component.ts
  14. 65
      ui-ngx/src/app/shared/components/breadcrumb.component.html
  15. 11
      ui-ngx/src/app/shared/components/user-menu.component.html
  16. 13
      ui-ngx/src/app/shared/components/user-menu.component.scss
  17. 1
      ui-ngx/src/app/shared/models/dashboard.models.ts

6
ui-ngx/src/app/modules/home/components/dashboard-page/dashboard-page.component.html

@ -75,7 +75,9 @@
[states]="dashboardConfiguration.states">
</tb-states-component>
} @else {
<tb-notification-bell class="gt-sm:!hidden"></tb-notification-bell>
@if (!isPublicUser()) {
<tb-notification-bell class="gt-sm:!hidden"></tb-notification-bell>
}
<tb-breadcrumb class="lt-md:flex-1"
[componentBreadcrumbsTpl]="dashboardBreadcrumbsTpl">
</tb-breadcrumb>
@ -124,7 +126,7 @@
<mat-icon>{{isRightLayoutOpened ? 'arrow_back' : 'menu'}}</mat-icon>
</button>
<div class="flex flex-row-reverse items-center lt-md:!hidden">
@if (!isEdit) {
@if (!isEdit && !isPublicUser()) {
<tb-notification-bell></tb-notification-bell>
}
<button [class.!hidden]="hideFullscreenButton()" mat-icon-button

2
ui-ngx/src/app/modules/home/components/dashboard-page/dashboard-page.component.scss

@ -18,7 +18,7 @@
$toolbar-height: 56px !default;
$fullscreen-toolbar-height: 56px !default;
$mobile-toolbar-height: 96px !default;
$mobile-app-toolbar-height: 40px !default;
$mobile-app-toolbar-height: 48px !default;
tb-dashboard-page {
display: flex;

9
ui-ngx/src/app/modules/home/components/dashboard-page/dashboard-toolbar.component.scss

@ -21,7 +21,7 @@ $mobile-toolbar-height: 96px !default;
$half-mobile-toolbar-height: 48px !default;
$mobile-toolbar-height-total: 96px !default;
$mobile-app-toolbar-height: 40px !default;
$mobile-app-toolbar-height: 48px !default;
div.tb-dashboard-page.mobile-app {
tb-dashboard-toolbar {
@ -95,9 +95,14 @@ tb-dashboard-toolbar {
}
}
&.mat-is-open {
.mat-fab-toolbar-wrapper {
border-bottom: 1px solid rgba(0, 0, 0, 0.12);
}
}
.mat-fab-toolbar-wrapper {
height: $mobile-toolbar-height-total;
border-bottom: 1px solid rgba(0, 0, 0, 0.12);
@media #{$mat-gt-sm} {
height: $toolbar-height;

6
ui-ngx/src/app/modules/home/components/dashboard-page/states/default-state-controller.component.html

@ -15,8 +15,10 @@
limitations under the License.
-->
<div class="flex flex-row items-center justify-start gap-2">
<span class='state-divider'> > </span>
<div class="flex flex-row items-center justify-start gap-2" [class.tb-mobile]="isMobile">
@if ((breadcrumbs$ | async).length > 1) {
<span class='state-divider'> > </span>
}
<mat-select class="default-state-controller" [class.!hidden]="!displayStateSelection()"
[(ngModel)]="stateObject[0].id" (ngModelChange)="selectedStateIdChanged()">
@for (stateKv of states | keyvalue; track stateKv) {

14
ui-ngx/src/app/modules/home/components/dashboard-page/states/default-state-controller.component.scss

@ -33,6 +33,11 @@
.state-divider {
display: block;
}
.tb-mobile {
.state-divider {
display: none;
}
}
}
}
@ -44,6 +49,15 @@
--mat-select-enabled-trigger-text-color: rgba(0, 0, 0, 0.76);
}
}
.tb-mobile {
::ng-deep {
.mat-mdc-select.default-state-controller {
--mat-select-trigger-text-size: 24px;
--mat-select-trigger-text-line-height: 32px;
--mat-select-trigger-text-weight: 400;
}
}
}
}
:host ::ng-deep {

6
ui-ngx/src/app/modules/home/components/dashboard-page/states/default-state-controller.component.ts

@ -27,6 +27,7 @@ import { base64toObj, objToBase64 } from '@app/core/utils';
import { DashboardUtilsService } from '@core/services/dashboard-utils.service';
import { EntityService } from '@core/http/entity.service';
import { MobileService } from '@core/services/mobile.service';
import { BreadcrumbService } from '@core/services/breadcrumb.service';
@Component({
selector: 'tb-default-state-controller',
@ -36,6 +37,8 @@ import { MobileService } from '@core/services/mobile.service';
})
export class DefaultStateControllerComponent extends StateControllerComponent implements OnInit, OnDestroy {
breadcrumbs$ = this.breadcrumbService.breadcrumbs$;
constructor(protected router: Router,
protected route: ActivatedRoute,
protected ngZone: NgZone,
@ -43,7 +46,8 @@ export class DefaultStateControllerComponent extends StateControllerComponent im
private utils: UtilsService,
private entityService: EntityService,
private mobileService: MobileService,
private dashboardUtils: DashboardUtilsService) {
private dashboardUtils: DashboardUtilsService,
private breadcrumbService: BreadcrumbService) {
super(router, route, ngZone, statesControllerService);
}

7
ui-ngx/src/app/modules/home/components/dashboard-page/states/entity-state-controller.component.html

@ -18,7 +18,7 @@
<div class="entity-state-controller">
@if (!isMobile) {
<div class="flex flex-row items-center justify-start gap-2">
@for (state of stateObject; track state; let i = $index; let isLast = $last;) {
@for (state of stateObject; track state.id; let i = $index; let isLast = $last;) {
@if ((breadcrumbs$ | async).length > 1 || i > 0) {
<span class='state-divider' [class.last-divider]="isLast"> > </span>
}
@ -29,12 +29,11 @@
</span>
}
</div>
}
@if (isMobile) {
} @else {
@if (stateObject.length > 1) {
<mat-select
[(ngModel)]="selectedStateIndex" (ngModelChange)="selectedStateIndexChanged()">
@for (state of stateObject; track state; let i = $index) {
@for (state of stateObject; track state.id; let i = $index) {
<mat-option [value]="i">
{{getStateName(i)}}
</mat-option>

3
ui-ngx/src/app/modules/home/components/dashboard-page/states/entity-state-controller.component.scss

@ -73,9 +73,6 @@
--mat-select-trigger-text-line-height: 32px;
--mat-select-trigger-text-weight: 400;
--mat-select-enabled-trigger-text-color: rgba(0,0,0,0.76);
.mat-mdc-select-value {
max-width: 200px;
}
.mat-mdc-select-arrow {
width: 24px;
}

2
ui-ngx/src/app/modules/home/components/dashboard-view/dashboard-view.component.html

@ -15,4 +15,4 @@
limitations under the License.
-->
<tb-dashboard-page [embedded]="true" [dashboard]="dashboard"></tb-dashboard-page>
<tb-dashboard-page #dashboardPage [embedded]="true" [dashboard]="dashboard"></tb-dashboard-page>

26
ui-ngx/src/app/modules/home/components/dashboard-view/dashboard-view.component.ts

@ -14,12 +14,15 @@
/// limitations under the License.
///
import { Component } from '@angular/core';
import { Component, DestroyRef, effect, EventEmitter, viewChild } from '@angular/core';
import { Store } from '@ngrx/store';
import { AppState } from '@core/core.state';
import { PageComponent } from '@shared/components/page.component';
import { Dashboard } from '@shared/models/dashboard.models';
import { ActivatedRoute } from '@angular/router';
import { MainToolbarComponent } from '@home/models/main-toolbar.models';
import { DashboardPageComponent } from '@home/components/dashboard-page/dashboard-page.component';
import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
@Component({
selector: 'tb-dashboard-view',
@ -27,12 +30,29 @@ import { ActivatedRoute } from '@angular/router';
styleUrls: ['./dashboard-view.component.scss'],
standalone: false
})
export class DashboardViewComponent extends PageComponent {
export class DashboardViewComponent extends PageComponent implements MainToolbarComponent {
dashboard: Dashboard = this.route.snapshot.data.dashboard;
hideMainToolbar = true;
toggleSideBar = new EventEmitter<void>();
private dashboardPage = viewChild<DashboardPageComponent>('dashboardPage');
constructor(protected store: Store<AppState>,
private route: ActivatedRoute) {
private route: ActivatedRoute,
private destroyRef: DestroyRef) {
super(store);
effect(() => {
const dashboardPage = this.dashboardPage();
if (dashboardPage) {
dashboardPage.toggleSideBar.pipe(
takeUntilDestroyed(this.destroyRef)
).subscribe(() => {
this.toggleSideBar.emit();
});
}
});
}
}

1
ui-ngx/src/app/modules/home/pages/home-links/home-links-routing.module.ts

@ -96,6 +96,7 @@ const applySystemParametersToHomeDashboard = (store: Store<AppState>,
}
}
dashboard.hideDashboardToolbar = true;
dashboard.isSystemDashboard = true;
return dashboard;
})
))

2
ui-ngx/src/app/modules/home/pages/home-links/home-links.component.html

@ -16,7 +16,7 @@
-->
@if (homeDashboard) {
<tb-dashboard-page [embedded]="true" [dashboard]="homeDashboard" [hideToolbar]="homeDashboard.hideDashboardToolbar"></tb-dashboard-page>
<tb-dashboard-page #dashboardPage [embedded]="true" [dashboard]="homeDashboard" [hideToolbar]="homeDashboard.hideDashboardToolbar"></tb-dashboard-page>
} @else {
<mat-grid-list class="tb-home-links" [cols]="cols" rowHeight="280px">
@for (section of homeSections$| async; track section) {

44
ui-ngx/src/app/modules/home/pages/home-links/home-links.component.ts

@ -14,22 +14,35 @@
/// limitations under the License.
///
import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnInit } from '@angular/core';
import {
ChangeDetectionStrategy,
ChangeDetectorRef,
Component, DestroyRef,
effect,
EventEmitter,
OnInit,
viewChild
} from '@angular/core';
import { MenuService } from '@core/services/menu.service';
import { BreakpointObserver, BreakpointState } from '@angular/cdk/layout';
import { MediaBreakpoints } from '@shared/models/constants';
import { HomeSection } from '@core/services/menu.models';
import { ActivatedRoute } from '@angular/router';
import { HomeDashboard } from '@shared/models/dashboard.models';
import { MainToolbarComponent } from '@home/models/main-toolbar.models';
import { DashboardPageComponent } from '@home/components/dashboard-page/dashboard-page.component';
import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
@Component({
selector: 'tb-home-links',
templateUrl: './home-links.component.html',
styleUrls: ['./home-links.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush,
standalone: false
selector: 'tb-home-links',
templateUrl: './home-links.component.html',
styleUrls: ['./home-links.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush,
standalone: false
})
export class HomeLinksComponent implements OnInit {
export class HomeLinksComponent implements MainToolbarComponent, OnInit {
private dashboardPage = viewChild<DashboardPageComponent>('dashboardPage');
homeSections$ = this.menuService.homeSections();
@ -37,10 +50,25 @@ export class HomeLinksComponent implements OnInit {
homeDashboard: HomeDashboard = this.route.snapshot.data.homeDashboard;
hideMainToolbar = false;
toggleSideBar = new EventEmitter<void>();
constructor(private menuService: MenuService,
public breakpointObserver: BreakpointObserver,
private cd: ChangeDetectorRef,
private route: ActivatedRoute) {
private route: ActivatedRoute,
private destroyRef: DestroyRef) {
effect(() => {
const dashboardPage = this.dashboardPage();
if (dashboardPage) {
dashboardPage.toggleSideBar.pipe(
takeUntilDestroyed(this.destroyRef)
).subscribe(() => {
this.toggleSideBar.emit();
});
}
});
this.hideMainToolbar = (!!this.homeDashboard && !this.homeDashboard.isSystemDashboard);
}
ngOnInit() {

65
ui-ngx/src/app/shared/components/breadcrumb.component.html

@ -16,28 +16,16 @@
-->
<div class="tb-breadcrumb flex flex-1 flex-row gap-2">
@if (componentBreadcrumbsTpl && (lastBreadcrumb$ | async) === null) {
<div class="min-w-0 flex-1">
<ng-container
*ngTemplateOutlet="componentBreadcrumbsTpl">
</ng-container>
</div>
} @else {
@if (lastBreadcrumb$ | async; as breadcrumb) {
@if (componentBreadcrumbsTpl) {
<div class="flex-1 gt-sm:!hidden">
<ng-container
*ngTemplateOutlet="componentBreadcrumbsTpl">
</ng-container>
</div>
} @else {
<h1 class="flex-1 gt-sm:!hidden">
<ng-container
*ngTemplateOutlet="breadcrumbTpl;context:{breadcrumb: breadcrumb}">
</ng-container>
</h1>
}
@if (lastBreadcrumb$ | async; as breadcrumb) {
@if (!componentBreadcrumbsTpl) {
<h1 class="flex-1 gt-sm:!hidden">
<ng-container
*ngTemplateOutlet="breadcrumbTpl;context:{breadcrumb: breadcrumb}">
</ng-container>
</h1>
}
}
@if (!componentBreadcrumbsTpl || (breadcrumbs$ | async).length > 1) {
<div class="flex flex-1 flex-row items-center gap-2 overflow-hidden lt-md:!hidden">
@for (breadcrumb of breadcrumbs$ | async; track breadcrumb.id; let isLast = $last; let i = $index;) {
@switch (isLast) {
@ -46,35 +34,36 @@
<span class="divider"> > </span>
}
<span class="flex flex-row gap-2">
<a [routerLink]="breadcrumb.link" [queryParams]="breadcrumb.queryParams">
<ng-container
*ngTemplateOutlet="breadcrumbTpl;context:{breadcrumb: breadcrumb}">
</ng-container>
</a>
</span>
<a [routerLink]="breadcrumb.link" [queryParams]="breadcrumb.queryParams">
<ng-container
*ngTemplateOutlet="breadcrumbTpl;context:{breadcrumb: breadcrumb}">
</ng-container>
</a>
</span>
}
@case (true) {
@if (componentBreadcrumbsTpl) {
<span>
<ng-container
*ngTemplateOutlet="componentBreadcrumbsTpl">
</ng-container>
</span>
} @else {
@if (!componentBreadcrumbsTpl) {
@if (i > 0) {
<span class="divider last-divider"> > </span>
}
<span>
<ng-container
*ngTemplateOutlet="breadcrumbTpl;context:{breadcrumb: breadcrumb}">
</ng-container>
</span>
<ng-container
*ngTemplateOutlet="breadcrumbTpl;context:{breadcrumb: breadcrumb}">
</ng-container>
</span>
}
}
}
}
</div>
}
@if (componentBreadcrumbsTpl) {
<span>
<ng-container
*ngTemplateOutlet="componentBreadcrumbsTpl">
</ng-container>
</span>
}
</div>
<ng-template #breadcrumbTpl let-breadcrumb="breadcrumb">
{{ breadcrumb.labelFunction ? breadcrumb.labelFunction() : (breadcrumb.customTranslate ? (breadcrumb.label | customTranslate) : (breadcrumb.label | translate)) }}

11
ui-ngx/src/app/shared/components/user-menu.component.html

@ -33,9 +33,18 @@
}
</div>
</button>
<button #menuPopover="tbPopover" mat-icon-button class="tb-user-menu-icon"
(click)="$event.stopPropagation();"
tb-popover
tbPopoverTrigger="click"
[tbPopoverMenu]="true"
[tbPopoverContent]="userMenuTpl"
[tbPopoverPlacement]="'bottomRight'">
<tb-icon class="material-icons tb-mini-avatar">mdi:account-circle-outline</tb-icon>
</button>
<ng-template #userMenuTpl>
@if (authority$ | async; as authority) {
<div class="tb-menu-content tb-user-menu-items" [style.width.px]="!collapsed ? menuButton._elementRef.nativeElement.offsetWidth : ''">
<div class="tb-menu-content tb-user-menu-items" [style.width.px]="!collapsed ? menuButton?._elementRef?.nativeElement?.offsetWidth : ''">
<button mat-button (click)="menuPopover?.hide(); openAccount()">
<tb-icon matButtonIcon>mdi:account-circle-outline</tb-icon>
<span translate>account.account</span>

13
ui-ngx/src/app/shared/components/user-menu.component.scss

@ -22,12 +22,22 @@
button.mat-mdc-button:not(.mat-mdc-icon-button).tb-user-menu {
padding: 12px 16px;
}
@media #{$mat-lt-lg} {
button.mat-mdc-button:not(.mat-mdc-icon-button).tb-user-menu {
display: none;
}
.tb-user-menu-icon {
display: block;
}
}
}
}
tb-user-menu {
width: 100%;
.tb-user-menu-icon {
display: none;
}
button.mat-mdc-button:not(.mat-mdc-icon-button).tb-user-menu {
width: 100%;
height: 100%;
@ -81,7 +91,6 @@ tb-user-menu {
height: 20px;
font-size: 20px;
}
.tb-user-info {
opacity: 0;
}

1
ui-ngx/src/app/shared/models/dashboard.models.ts

@ -199,6 +199,7 @@ export interface Dashboard extends DashboardInfo {
export interface HomeDashboard extends Dashboard {
hideDashboardToolbar: boolean;
isSystemDashboard?: boolean;
}
export interface HomeDashboardInfo {

Loading…
Cancel
Save