Skip to content

Commit

Permalink
org selector #1127
Browse files Browse the repository at this point in the history
  • Loading branch information
syjer committed Dec 15, 2022
1 parent 5a6b24c commit 855cce3
Show file tree
Hide file tree
Showing 10 changed files with 81 additions and 10 deletions.
8 changes: 7 additions & 1 deletion frontend-admin/src/app/app.component.html
Expand Up @@ -2,8 +2,14 @@
<header class="navbar navbar-dark sticky-top bg-dark flex-md-nowrap p-0">
<span class="navbar-brand col-md-3 col-lg-2 me-0 px-3 fs-6">
<img src="assets/alfio-logo.svg" height="48">
<span>
<button class="btn btn-light" (click)="openOrgSelector()">
<svg-icon key="organization" size="lg"></svg-icon>
{{(currentOrganization$ | async)?.name}}
<svg-icon key="arrowdropdown"></svg-icon>
</button>
</span>
</span>
<span style="color: white;">org: {{(currentOrganization$ | async)?.name}}</span>
<span style="color: white;">user: {{(currentUser$ | async)?.username}}</span>
<!-- <input class="form-control form-control-dark w-100 rounded-0 border-0" type="text" placeholder="Search"
aria-label="Search">
Expand Down
15 changes: 14 additions & 1 deletion frontend-admin/src/app/app.component.ts
@@ -1,9 +1,11 @@
import { Component, OnInit } from '@angular/core';
import { ActivationEnd, Router } from '@angular/router';
import { NgbModal } from '@ng-bootstrap/ng-bootstrap';
import { TranslateService } from '@ngx-translate/core';
import { filter, map, Observable, zip } from 'rxjs';
import { filter, map, Observable, of, tap, zip } from 'rxjs';
import { Organization } from './model/organization';
import { UserInfo } from './model/user';
import { OrgSelectorComponent } from './org-selector/org-selector.component';
import { OrganizationService } from './shared/organization.service';
import { UserService } from './shared/user.service';

Expand All @@ -24,6 +26,7 @@ export class AppComponent implements OnInit {
private readonly organizationService: OrganizationService,
private readonly userService: UserService,
private readonly router: Router,
private readonly modalService: NgbModal,
) {
}

Expand All @@ -39,4 +42,14 @@ export class AppComponent implements OnInit {
this.currentOrganization$ = zip(this.organizationId$, this.organizations$)
.pipe(map(([id, orgs]) => orgs.find(o => id !== null && o.id === Number.parseInt(id))));
}

public openOrgSelector(): void {
const modalRef = this.modalService.open(OrgSelectorComponent);
const selector: OrgSelectorComponent = modalRef.componentInstance
selector.organizations$ = this.organizations$;
selector.organizationId$ = this.organizationId$;
modalRef.result.then((res: Organization) => {
this.router.navigate(['/organization', res.id]).then(r => {if (r) {this.currentOrganization$ = of(res)}});
});
}
}
2 changes: 2 additions & 0 deletions frontend-admin/src/app/app.module.ts
Expand Up @@ -15,6 +15,7 @@ import {MissingOrgComponent} from './missing-org/missing-org.component';
import { ICON_CONFIG } from './shared/icons';
import {TranslateLoader, TranslateModule} from '@ngx-translate/core';
import {CustomLoader} from './shared/i18n.service';
import { OrgSelectorComponent } from './org-selector/org-selector.component';

export function RedirectToLoginIfNeeded(userService: UserService, router: Router): () => Promise<boolean> {
return async () => {
Expand All @@ -35,6 +36,7 @@ export function HttpLoaderFactory(http: HttpClient) {
declarations: [
AppComponent,
MissingOrgComponent,
OrgSelectorComponent,
],
imports: [
BrowserModule,
Expand Down
4 changes: 2 additions & 2 deletions frontend-admin/src/app/dashboard/dashboard.component.html
@@ -1,6 +1,6 @@
<h1 translate="admin.dashboard.my-events"></h1>
<app-filter-button text="Active" [checked]="activeFilter" (toggleFilter)="toggleActiveFilter($event)"></app-filter-button>
<app-filter-button text="Inactive" [checked]="inactiveFilter" (toggleFilter)="toggleInactiveFilter($event)"></app-filter-button>
<app-filter-button text="Past" [checked]="inactiveFilter" (toggleFilter)="toggleInactiveFilter($event)"></app-filter-button>
<ng-container *ngIf="activeFilter">
<h2>Active</h2>
<ul>
Expand All @@ -10,7 +10,7 @@ <h2>Active</h2>
</ul>
</ng-container>
<ng-container *ngIf="inactiveFilter">
<h2>Expired</h2>
<h2>Past</h2>
<ul>
<li *ngFor="let ev of expiredEvents$ | async">
<a [routerLink]="['./event', ev.id]">{{ev.displayName}} {{ev.formattedBegin}} {{ev.formattedEnd}}</a>
Expand Down
20 changes: 14 additions & 6 deletions frontend-admin/src/app/dashboard/dashboard.component.ts
@@ -1,6 +1,6 @@
import {Component, OnInit} from "@angular/core";
import {ActivatedRoute} from "@angular/router";
import { Observable, of } from "rxjs";
import { map, mergeMap, Observable, of } from "rxjs";
import { EventInfo } from "../model/event";
import { EventService } from "../shared/event.service";

Expand All @@ -9,24 +9,32 @@ import { EventService } from "../shared/event.service";
})
export class DashboardComponent implements OnInit {

public readonly organizationId: string;
public organizationId$: Observable<string | null> = of();
public activeEvents$: Observable<EventInfo[]> = of();
public expiredEvents$: Observable<EventInfo[]> = of();
public activeFilter: boolean = true;
public inactiveFilter: boolean = false;

constructor(route: ActivatedRoute, private readonly eventService: EventService) {
this.organizationId = route.snapshot.paramMap.get('organizationId') as string;
this.organizationId$ = route.paramMap.pipe(map((pm) => pm.get('organizationId')))
}

public ngOnInit(): void {
this.activeEvents$ = this.eventService.getActiveEvents(this.organizationId); // default
this.activeEvents$ = this.loadActiveEvents(); // default
}

private loadActiveEvents() {
return this.organizationId$.pipe(mergeMap(orgId => orgId != null ? this.eventService.getActiveEvents(orgId) : []));
}

private loadInactiveEvents() {
return this.organizationId$.pipe(mergeMap(orgId => orgId != null ? this.eventService.getExpiredEvents(orgId) : []));
}

public toggleActiveFilter(toggle: boolean): void {
this.activeFilter = toggle;
if (toggle) {
this.activeEvents$ = this.eventService.getActiveEvents(this.organizationId);
this.activeEvents$ = this.loadActiveEvents();
} else {
this.activeEvents$ = of();
}
Expand All @@ -35,7 +43,7 @@ export class DashboardComponent implements OnInit {
public toggleInactiveFilter(toggle: boolean): void {
this.inactiveFilter = toggle;
if (toggle) {
this.expiredEvents$ = this.eventService.getExpiredEvents(this.organizationId);
this.expiredEvents$ = this.loadInactiveEvents();
} else {
this.expiredEvents$ = of();
}
Expand Down
14 changes: 14 additions & 0 deletions frontend-admin/src/app/org-selector/org-selector.component.html
@@ -0,0 +1,14 @@
<div class="modal-header">
<h4 class="modal-title">Select organization</h4>
<button type="button" class="btn-close" aria-label="Close" (click)="activeModal.dismiss('Cross click')"></button>
</div>
<div class="modal-body">
<ul>
<li *ngFor="let org of organizations$ | async">
<button class="btn btn-link" (click)="selectOrganization(org)">{{org.name}}</button>
</li>
</ul>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-outline-dark" (click)="activeModal.close('Close click')">Close</button>
</div>
Empty file.
25 changes: 25 additions & 0 deletions frontend-admin/src/app/org-selector/org-selector.component.ts
@@ -0,0 +1,25 @@
import { Component, OnInit } from '@angular/core';
import { NgbActiveModal } from '@ng-bootstrap/ng-bootstrap';
import { Observable } from 'rxjs';
import { Organization } from '../model/organization';

@Component({
selector: 'app-org-selector',
templateUrl: './org-selector.component.html',
styleUrls: ['./org-selector.component.scss']
})
export class OrgSelectorComponent implements OnInit {

public organizations$?: Observable<Organization[]>;
public organizationId$?: Observable<string | null>;

constructor(public activeModal: NgbActiveModal) { }

ngOnInit(): void {
}

public selectOrganization(org: Organization): void {
this.activeModal.close(org);
}

}
2 changes: 2 additions & 0 deletions frontend-admin/src/app/shared/icons.ts
@@ -1,4 +1,5 @@
import { addIcon } from '../svg/add';
import { arrowdropdownIcon } from '../svg/arrowdropdown';
import {checkIcon} from '../svg/check';
import {homeIcon} from '../svg/home';
import { organizationIcon } from '../svg/organization';
Expand All @@ -11,6 +12,7 @@ const ICONS = [
addIcon,
organizationIcon,
settingsIcon,
arrowdropdownIcon,
];
export const ICON_CONFIG = {
sizes: {
Expand Down
1 change: 1 addition & 0 deletions frontend-admin/src/assets/svg/arrowdropdown.svg
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.

0 comments on commit 855cce3

Please sign in to comment.