Skip to content

Commit

Permalink
Add spinner when api call is not complete
Browse files Browse the repository at this point in the history
  • Loading branch information
minottic committed Mar 1, 2024
1 parent 3cb039c commit 096d09c
Show file tree
Hide file tree
Showing 11 changed files with 98 additions and 10 deletions.
15 changes: 15 additions & 0 deletions scilog/src/app/logbook/core/scroll-base.service.spec.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { TestBed } from '@angular/core/testing';

import { ScrollBaseService } from './scroll-base.service';
import { IDatasource } from 'ngx-ui-scroll';

describe('ScrollBaseService', () => {
let service: ScrollBaseService;
Expand All @@ -15,4 +16,18 @@ describe('ScrollBaseService', () => {
it('should be created', () => {
expect(service).toBeTruthy();
});

it('should decorate with isLoadedDecorator', async () => {
const toDecorate = async (index, count, config) => index + count + config;
const decorated = await service.isLoadedDecorator(toDecorate)(1, 2, 3);
expect(decorated).toEqual(6);
});

it('should reset isLoaded flag after reset', async () => {
service.datasource = { adapter: { reset: async () => ({}) } } as IDatasource;
service.isLoaded = true;
service.reset();
expect(service.isLoaded).toEqual(false);
});

});
24 changes: 23 additions & 1 deletion scilog/src/app/logbook/core/scroll-base.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,11 @@ export class ScrollBaseService {
datasource: IDatasource = null;
startIndex = 0;
config: WidgetItemConfig = null;
isLoaded = false;

constructor() { }
constructor() {
this.getDataBuffer = this.isLoadedDecorator(this.getDataBuffer.bind(this));
}

public async initialize(config: WidgetItemConfig) {
// console.log("Config: ", this.config);
Expand Down Expand Up @@ -64,6 +67,24 @@ export class ScrollBaseService {
throw new Error("Abstract method needs to be implemented in derived class.")
}

isLoadedDecorator(func: Function) {
const decorated = async (index: number, count: number, config: any) => {
this.isLoaded = false;
let data;
try {
data = await func(index, count, config);
}
catch {
console.log('scroller get data returned an error');
}
finally {
this.isLoaded = true;
return data;
}
}
return decorated;
}

async updateViewportEstimate() {
await this.datasource.adapter.relax();
this.datasource.adapter.check();
Expand All @@ -75,6 +96,7 @@ export class ScrollBaseService {

reset() {
if (this.datasource != null) {
this.isLoaded = false;
this.datasource.adapter.reset();
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -97,4 +97,12 @@
border: unset;
padding: 4px;
margin-left: 4px;
}
}

.spinner {
position: fixed;
z-index: 1031;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@
<div class="searchResults" *ngIf=showResults>
<div class="header">
Logbook view:
<mat-spinner *ngIf="!searchScrollService.isLoaded" [@spinner] class="spinner"></mat-spinner>
<div class="searchContainer">
<div *uiScroll="let snippet of searchScrollService.datasource; let i = index">
<snippet [snippet]="snippet" [updatedAt]="snippet.updatedAt" [index]=i+1 [config]="config"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { HttpClientTestingModule } from '@angular/common/http/testing';
import { ComponentFixture, TestBed, waitForAsync } from '@angular/core/testing';
import { ComponentFixture, TestBed, fakeAsync, tick, waitForAsync } from '@angular/core/testing';
import { MatDialog } from '@angular/material/dialog';
import { LogbookInfoService } from '@shared/logbook-info.service';
import { AppConfigService } from 'src/app/app-config.service';
Expand Down Expand Up @@ -34,4 +34,13 @@ describe('SearchWindowComponent', () => {
it('should create', () => {
expect(component).toBeTruthy();
});

it('should call _prepareConfig on searchString emission', fakeAsync(() => {
const prepareConfigSpy = spyOn<any>(component, '_prepareConfig');
component.searchString = '';
component.searchString = 'someSearch';
tick(501);
expect(prepareConfigSpy).toHaveBeenCalledTimes(1);
}));

});
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import { LogbookInfoService } from '@shared/logbook-info.service';
import { TagService } from '@shared/tag.service';
import { ScrollToElementService } from '@shared/scroll-to-element.service';
import { Hotkeys } from '@shared/hotkeys.service';
import { animate, style, transition, trigger } from '@angular/animations';

interface SearchResult {
location: string[],
Expand All @@ -23,7 +24,15 @@ interface SearchResult {
selector: 'search-window',
templateUrl: './search-window.component.html',
styleUrls: ['./search-window.component.css'],
providers: [SearchScrollService]
providers: [SearchScrollService],
animations: [
trigger('spinner', [
transition(':enter', [
style({opacity: 0}),
animate('1ms 0.2s ease-out', style({opacity: 1}))
])
]),
]
})
export class SearchWindowComponent implements OnInit {

Expand Down Expand Up @@ -65,13 +74,12 @@ export class SearchWindowComponent implements OnInit {
this.subscriptions.push(this.searchStringSubject.pipe(debounceTime(500)).subscribe(() => {
if (this._searchString.length > 0) {
this.showResults = !this.showHelp;
this.searchScrollService.config = this._prepareConfig();
this.searchScrollService.reset();
} else {
this.showHelp = true;
this.showResults = false;
}
this.searchScrollService.config = this._prepareConfig();
this.searchScrollService.reset();

}));
this._initialize_help();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,4 +28,11 @@ describe('LogbookIconScrollServiceService', () => {
expect(await service.getData(0, 10, {})).toEqual([[1, 2, 3], [4, 5, 6], [7]]);
});

it('should test getDataBuffer after decoration', async () => {
expect(service['isLoaded']).toEqual(false);
spyOn(service, 'getData').and.resolveTo([]);
await service.getDataBuffer(1, 2, 3);
expect(service['isLoaded']).toEqual(true);
});

});
8 changes: 8 additions & 0 deletions scilog/src/app/overview/overview.component.css
Original file line number Diff line number Diff line change
Expand Up @@ -38,3 +38,11 @@ mat-button-toggle-group {
transform: scale(75%) translate(18px, -50%);
margin-right: 0;
}

.spinner {
position: fixed;
z-index: 1031;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
1 change: 1 addition & 0 deletions scilog/src/app/overview/overview.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ <h1>Logbooks</h1>
<mat-button-toggle value="logbook-headline"><mat-icon>view_headline</mat-icon></mat-button-toggle>
</mat-button-toggle-group>
<button (click)='addCollectionLogbook("logbook")'>Add logbook</button><br>
<mat-spinner *ngIf="!logbookIconScrollService.isLoaded" [@spinner] class="spinner"></mat-spinner>
<div class="logbook-container" (resized)="onResized($event)" #logbookContainer>
<div *uiScroll="let logbookGroup of logbookIconScrollService.datasource">
<span *ngFor="let logbook of logbookGroup">
Expand Down
3 changes: 2 additions & 1 deletion scilog/src/app/overview/overview.component.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import { RouterTestingModule } from '@angular/router/testing';
import {Pipe, PipeTransform} from '@angular/core';
import { Logbooks } from '@model/logbooks';
import { ResizedEvent } from '@shared/directives/resized.directive';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';

@Pipe({name: 'logbookSearch'})
class LogbookSearchMockPipe implements PipeTransform {
Expand Down Expand Up @@ -47,7 +48,7 @@ describe('OverviewComponent', () => {
beforeEach(waitForAsync(() => {
TestBed.configureTestingModule({
declarations: [ OverviewComponent, LogbookSearchMockPipe],
imports: [MatDialogModule, RouterTestingModule],
imports: [MatDialogModule, RouterTestingModule, BrowserAnimationsModule],
providers: [
{ provide: MAT_DIALOG_DATA, useValue: {} },
{provide: LogbookInfoService, useValue: logbookInfoSpy},
Expand Down
12 changes: 10 additions & 2 deletions scilog/src/app/overview/overview.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import { LogbookDataService } from '@shared/remote-data.service';
import { LogbookIconScrollService } from './logbook-icon-scroll-service.service';
import { debounceTime } from 'rxjs/operators';
import { ResizedEvent } from '@shared/directives/resized.directive';
import { animate, style, transition, trigger } from '@angular/animations';

enum ContentType {
COLLECTION = 'collection',
Expand All @@ -24,8 +25,15 @@ export type MatCardType = 'logbook-module' | 'logbook-headline';
selector: 'app-overview',
templateUrl: './overview.component.html',
styleUrls: ['./overview.component.css'],
providers: [LogbookIconScrollService]

providers: [LogbookIconScrollService],
animations: [
trigger('spinner', [
transition(':enter', [
style({opacity: 0}),
animate('1ms 0.2s ease-out', style({opacity: 1}))
])
]),
]
})
export class OverviewComponent implements OnInit {

Expand Down

0 comments on commit 096d09c

Please sign in to comment.