alfresco-ng2-components/lib/core/viewer/components/img-viewer.component.spec.ts
Eugenio Romano c8688bf0bf
[ACA-4382 ] About Page refactoring to use it across all the platform (#7365)
* about page refactor for global usage

* Development About

* add storybook

* fix build

* fix

* fix

* fix imports

* fix

* fix lint

* fix

* fix

* fix

* fix
2021-11-23 10:30:10 +00:00

356 lines
13 KiB
TypeScript

/*!
* @license
* Copyright 2019 Alfresco Software, Ltd.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import { SimpleChange } from '@angular/core';
import { ComponentFixture, fakeAsync, TestBed, tick } from '@angular/core/testing';
import { ContentService } from '../../services/content.service';
import { ImgViewerComponent } from './img-viewer.component';
import { setupTestBed, CoreTestingModule } from '../../testing';
import { AppConfigService } from '../../app-config/app-config.service';
import { TranslateModule } from '@ngx-translate/core';
import { By } from '@angular/platform-browser';
describe('Test Img viewer component ', () => {
let component: ImgViewerComponent;
let service: ContentService;
let fixture: ComponentFixture<ImgViewerComponent>;
let element: HTMLElement;
function createFakeBlob() {
const data = atob('iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mNk+M9QDwADhgGAWjR9awAAAABJRU5ErkJggg==');
return new Blob([data], { type: 'image/png' });
}
setupTestBed({
imports: [
TranslateModule.forRoot(),
CoreTestingModule
]
});
describe('Url', () => {
beforeEach(() => {
service = TestBed.inject(ContentService);
fixture = TestBed.createComponent(ImgViewerComponent);
element = fixture.nativeElement;
component = fixture.componentInstance;
component.urlFile = 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAUAAAAFCAYAAACNbyblAAAAHElEQVQI12P4//8/w38GIAXDIBKE0DHxgljNBAAO9TXL0Y4OHwAAAABJRU5ErkJggg==';
fixture.detectChanges();
fixture.componentInstance.ngAfterViewInit();
component.ngAfterViewInit();
fixture.detectChanges();
});
it('should display current scale as percent string', () => {
component.scale = 0.5;
expect(component.currentScaleText).toBe('50%');
component.scale = 1.0;
expect(component.currentScaleText).toBe('100%');
});
it('should define cropper after init', () => {
fixture.componentInstance.ngAfterViewInit();
expect(component.cropper).toBeDefined();
});
});
describe('Blob', () => {
beforeEach(() => {
service = TestBed.inject(ContentService);
fixture = TestBed.createComponent(ImgViewerComponent);
element = fixture.nativeElement;
component = fixture.componentInstance;
fixture.detectChanges();
});
it('If no url or blob are passed should thrown an error', () => {
const change = new SimpleChange(null, null, true);
expect(() => {
component.ngOnChanges({ 'blobFile': change });
}).toThrow(new Error('Attribute urlFile or blobFile is required'));
});
it('If url is passed should not thrown an error', () => {
component.urlFile = 'fake-url';
expect(() => {
component.ngOnChanges(null);
}).not.toThrow(new Error('Attribute urlFile or blobFile is required'));
});
it('The file Name should be present in the alt attribute', () => {
component.nameFile = 'fake-name';
fixture.detectChanges();
expect(element.querySelector('#viewer-image').getAttribute('alt')).toEqual('fake-name');
});
it('If blob is passed should not thrown an error', () => {
const blob = createFakeBlob();
spyOn(service, 'createTrustedUrl').and.returnValue('fake-blob-url');
const change = new SimpleChange(null, blob, true);
expect(() => {
component.ngOnChanges({ 'blobFile': change });
}).not.toThrow(new Error('Attribute urlFile or blobFile is required'));
expect(component.urlFile).toEqual('fake-blob-url');
});
});
describe('Zoom customization', () => {
beforeEach(() => {
service = TestBed.inject(ContentService);
fixture = TestBed.createComponent(ImgViewerComponent);
element = fixture.nativeElement;
component = fixture.componentInstance;
component.urlFile = 'fake-url-file.png';
fixture.detectChanges();
});
describe('default value', () => {
it('should use default zoom if is not present a custom zoom in the app.config', () => {
fixture.detectChanges();
expect(component.scale).toBe(1.0);
});
});
describe('custom value', () => {
beforeEach(() => {
const appConfig: AppConfigService = TestBed.inject(AppConfigService);
appConfig.config['adf-viewer.image-viewer-scaling'] = 70;
component.initializeScaling();
});
it('should use the custom zoom if it is present in the app.config', (done) => {
fixture.detectChanges();
fixture.whenStable().then(() => {
expect(component.scale).toBe(0.70);
done();
});
});
});
});
describe('toolbar actions', () => {
beforeEach(() => {
fixture = TestBed.createComponent(ImgViewerComponent);
element = fixture.nativeElement;
component = fixture.componentInstance;
component.blobFile = createFakeBlob();
const change = new SimpleChange(null, component.blobFile, true);
component.ngOnChanges({ 'blobFile': change });
fixture.detectChanges();
});
it('should update scales on zoom in', fakeAsync(() => {
spyOn(component, 'zoomIn').and.callThrough();
spyOn(component.cropper, 'zoom');
component.scale = 1.0;
tick();
component.zoomIn();
expect(component.scale).toBe(1.2);
expect(component.cropper.zoom).toHaveBeenCalledWith(0.2);
component.zoomIn();
expect(component.scale).toBe(1.4);
expect(component.cropper.zoom).toHaveBeenCalledWith(0.2);
}));
it('should update scales on zoom out', fakeAsync(() => {
spyOn(component, 'zoomOut').and.callThrough();
spyOn(component.cropper, 'zoom');
component.scale = 1.0;
tick();
component.zoomOut();
expect(component.scale).toBe(0.8);
expect(component.cropper.zoom).toHaveBeenCalledWith(-0.2);
component.zoomOut();
expect(component.scale).toBe(0.6);
expect(component.cropper.zoom).toHaveBeenCalledWith(-0.2);
}));
it('should not zoom out past 20%', fakeAsync(() => {
component.scale = 0.2;
tick();
component.zoomOut();
component.zoomOut();
component.zoomOut();
expect(component.scale).toBe(0.2);
}));
it('should show rotate button if not in read only mode', () => {
component.readOnly = false;
fixture.detectChanges();
const rotateButtonElement = element.querySelector('#viewer-rotate-button');
expect(rotateButtonElement).not.toEqual(null);
});
it('should not show rotate button by default', () => {
const rotateButtonElement = element.querySelector('#viewer-rotate-button');
expect(rotateButtonElement).toEqual(null);
});
it('should not show crop button by default', () => {
const rotateButtonElement = element.querySelector('#viewer-crop-button');
expect(rotateButtonElement).toEqual(null);
});
it('should start cropping when clicking the crop button', fakeAsync(() => {
component.readOnly = false;
spyOn(component, 'cropImage').and.callThrough();
spyOn(component.cropper, 'crop');
spyOn(component.cropper, 'setDragMode');
fixture.detectChanges();
const cropButtonElement = fixture.debugElement.query(By.css('#viewer-crop-button'));
cropButtonElement.triggerEventHandler('click', null);
tick();
expect(component.cropImage).toHaveBeenCalled();
expect(component.cropper.crop).toHaveBeenCalled();
expect(component.cropper.setDragMode).toHaveBeenCalledWith('crop');
}));
it('should rotate image by -90 degrees on button click', fakeAsync(() => {
component.readOnly = false;
spyOn(component, 'rotateImage').and.callThrough();
spyOn(component.cropper, 'rotate');
fixture.detectChanges();
const rotateButtonElement = fixture.debugElement.query(By.css('#viewer-rotate-button'));
rotateButtonElement.triggerEventHandler('click', null);
tick();
expect(component.rotateImage).toHaveBeenCalled();
expect(component.cropper.rotate).toHaveBeenCalledWith(-90);
}));
it('should display the second toolbar when in editing and not in read only mode', fakeAsync(() => {
component.readOnly = false;
component.isEditing = true;
fixture.detectChanges();
const secondaryToolbar = document.querySelector('.adf-secondary-toolbar');
expect(secondaryToolbar).not.toEqual(null);
}));
it('should not display the second toolbar when in read only mode', () => {
component.readOnly = true;
fixture.detectChanges();
const secondaryToolbar = document.querySelector('.adf-secondary-toolbar');
expect(secondaryToolbar).toEqual(null);
});
it('should not display the second toolbar when not in editing', () => {
component.readOnly = true;
component.isEditing = false;
fixture.detectChanges();
const secondaryToolbar = document.querySelector('.adf-secondary-toolbar');
expect(secondaryToolbar).toEqual(null);
});
it('should display second toolbar in edit mode', fakeAsync(() => {
component.readOnly = false;
component.isEditing = true;
fixture.detectChanges();
const secondaryToolbar = document.querySelector('.adf-secondary-toolbar');
const resetButton = document.querySelector('#viewer-cancel-button');
const saveButton = document.querySelector('#viewer-save-button');
expect(secondaryToolbar).not.toEqual(null);
expect(resetButton).not.toEqual(null);
expect(saveButton).not.toEqual(null);
}));
it('should not be in editing mode by default', () => {
component.readOnly = false;
expect(component.isEditing).toEqual(false);
});
it('should get in editing mode when the image gets rotated', () => {
component.readOnly = false;
component.rotateImage();
expect(component.isEditing).toEqual(true);
});
it('should get in editing mode when the image gets cropped', () => {
component.readOnly = false;
component.cropImage();
expect(component.isEditing).toEqual(true);
});
it('should reset the scale and hide second toolbar', fakeAsync(() => {
component.readOnly = false;
component.isEditing = true;
spyOn(component, 'reset').and.callThrough();
spyOn(component, 'updateCanvasContainer');
spyOn(component.cropper, 'reset');
spyOn(component.cropper, 'clear');
spyOn(component.cropper, 'zoomTo');
fixture.detectChanges();
const cancelButtonElement = fixture.debugElement.query(By.css('#viewer-cancel-button'));
cancelButtonElement.triggerEventHandler('click', null);
tick();
expect(component.reset).toHaveBeenCalled();
expect(component.scale).toEqual(1.0);
expect(component.isEditing).toEqual(false);
expect(component.cropper.reset).toHaveBeenCalled();
expect(component.cropper.clear).toHaveBeenCalled();
expect(component.updateCanvasContainer).toHaveBeenCalled();
}));
it('should save when clicked on toolbar button', fakeAsync(() => {
component.readOnly = false;
component.isEditing = true;
spyOn(component, 'save');
fixture.detectChanges();
const saveButtonElement = fixture.debugElement.query(By.css('#viewer-save-button'));
saveButtonElement.triggerEventHandler('click', null);
tick();
expect(component.save).toHaveBeenCalled();
}));
});
});