import 'reflect-metadata'; import { requiredMocks, } from './../../../test-mocks'; requiredMocks(jest); import { empty, of, timer, } from 'rxjs'; import { ChangeDetectorRef, SimpleChange, SimpleChanges, } from '@angular/core'; import { PIGService, } from './../../helpers/services/index'; import { ImageEditorWithDataComponent, } from './image-editor-with-data.component'; import { CoordsInterface, ImageEditorImageInterface, MaskImageMapInterface, PIGLayerImageInterface, } from '../../models'; const initImageEditorWithDataComponent = ( pigService?: PIGService, changeDetectorRef?: ChangeDetectorRef, ) => { return new ImageEditorWithDataComponent( pigService, changeDetectorRef, ); }; describe('get appliedColorOverlay', () => { // tslint:disable-next-line test('Returns null if the value of color_overlay from the pig layer components is false', () => { const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.layerComponents = { color_overlay: false, } as PIGLayerImageInterface; imageEditorWithDataComponent.colorOverlay = '#FFFFFF'; expect(imageEditorWithDataComponent.appliedColorOverlay) .toBeNull(); }); // tslint:disable-next-line test('Returns the colorOverlay input if the value of color_overlay from the pig layer components is true', () => { const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.layerComponents = { color_overlay: true, } as PIGLayerImageInterface; imageEditorWithDataComponent.colorOverlay = '#FFFFFF'; expect(imageEditorWithDataComponent.appliedColorOverlay) .toBe('#FFFFFF'); }); }); describe('ngOnChanges', () => { const callsInitaliseMasks = ( changes: SimpleChanges, ) => { const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.initaliseMasks = jest.fn(); imageEditorWithDataComponent.ngOnChanges(changes); expect(imageEditorWithDataComponent.initaliseMasks).toHaveBeenCalled(); }; test('If changes include imageEditorImages call initisaliseMasks', () => { callsInitaliseMasks({ imageEditorImages: {} as SimpleChange, }); }); test('If changes include showPrintArea call initisaliseMasks', () => { callsInitaliseMasks({ showPrintArea: {} as SimpleChange, }); }); test('If changes include guideAreaColor call initisaliseMasks', () => { callsInitaliseMasks({ guideAreaColor: {} as SimpleChange, }); }); test('If changes include showImageOverspill call initisaliseMasks', () => { callsInitaliseMasks({ showImageOverspill: {} as SimpleChange, }); }); const callsInitaliseLayerComponents = ( changes: SimpleChanges, ) => { const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.initaliseLayerComponents = jest.fn(); imageEditorWithDataComponent.ngOnChanges(changes); expect(imageEditorWithDataComponent.initaliseLayerComponents) .toHaveBeenCalled(); }; test('If changes include templateId call initaliseLayerComponents', () => { callsInitaliseLayerComponents({ templateId: {} as SimpleChange, }); }); // tslint:disable-next-line test('If changes include imageVariantName call initaliseLayerComponents', () => { callsInitaliseLayerComponents({ imageVariantName: {} as SimpleChange, }); }); }); describe('initaliseLayerComponents', () => { const initInitaliseLayerComponentsData = () => { const pigService = {} as PIGService; const getLayerComponentsResponse = {} as PIGLayerImageInterface; pigService.getLayerComponents$ = jest.fn().mockReturnValue( of(getLayerComponentsResponse), ); const imageEditorWithDataComponent = initImageEditorWithDataComponent( pigService, ); imageEditorWithDataComponent.templateId = 'templateId'; imageEditorWithDataComponent.imageVariantName = 'imageVariantName'; imageEditorWithDataComponent.initaliseMasks = jest.fn(); return { getLayerComponentsResponse, imageEditorWithDataComponent, pigService, }; }; // tslint:disable-next-line test('Does not call pigService.getLayerComponents$ if templateId is null', () => { const { imageEditorWithDataComponent, pigService, } = initInitaliseLayerComponentsData(); imageEditorWithDataComponent.templateId = null; imageEditorWithDataComponent.initaliseLayerComponents(); expect(pigService.getLayerComponents$).not.toHaveBeenCalled(); }); test('Sets isLoading to true', () => { const { imageEditorWithDataComponent, pigService, } = initInitaliseLayerComponentsData(); imageEditorWithDataComponent.isLoading = false; pigService.getLayerComponents$ = jest.fn().mockReturnValue( empty(), ); imageEditorWithDataComponent.initaliseLayerComponents(); expect(imageEditorWithDataComponent.isLoading).toBe(true); }); // tslint:disable-next-line test('Calls pigService.getLayerComponents$ with the correct arguments', () => { const { imageEditorWithDataComponent, pigService, } = initInitaliseLayerComponentsData(); imageEditorWithDataComponent.initaliseLayerComponents(); expect(pigService.getLayerComponents$).toHaveBeenCalledWith( 'templateId', 'imageVariantName', ); }); // tslint:disable-next-line test('Sets layerComponents to the result of pigService.getLayerComponents$', () => { const { getLayerComponentsResponse, imageEditorWithDataComponent, } = initInitaliseLayerComponentsData(); imageEditorWithDataComponent.layerComponents = null; imageEditorWithDataComponent.initaliseLayerComponents(); expect(imageEditorWithDataComponent.layerComponents).toBe( getLayerComponentsResponse, ); }); // tslint:disable-next-line test('Sets isLoading to false after pigService.getLayerComponents$ completes', () => { const { imageEditorWithDataComponent, pigService, } = initInitaliseLayerComponentsData(); imageEditorWithDataComponent.isLoading = true; imageEditorWithDataComponent.initaliseLayerComponents(); expect(imageEditorWithDataComponent.isLoading).toBe(false); }); // tslint:disable-next-line test('Calls initaliseMasks', () => { const { imageEditorWithDataComponent, } = initInitaliseLayerComponentsData(); imageEditorWithDataComponent.initaliseLayerComponents(); expect(imageEditorWithDataComponent.initaliseMasks).toHaveBeenCalled(); }); // tslint:disable-next-line test('If there is currently a http request in progress the result should only be called once', () => { const { imageEditorWithDataComponent, getLayerComponentsResponse, pigService, } = initInitaliseLayerComponentsData(); pigService.getLayerComponents$ = jest.fn().mockReturnValueOnce(timer(2000)) .mockReturnValueOnce(of(getLayerComponentsResponse)); imageEditorWithDataComponent.initaliseLayerComponents(); imageEditorWithDataComponent.initaliseLayerComponents(); expect(imageEditorWithDataComponent.initaliseMasks) .toHaveBeenCalledTimes(1); }); }); describe('initaliseMasks', () => { test('Does not throw if layerComponents is null', () => { const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.layerComponents = null; expect( imageEditorWithDataComponent.initaliseMasks.bind( imageEditorWithDataComponent, ), ).not.toThrow(); }); const initInitaliseMasks = () => { const mockUrlWithFilters1 = 'https://url-with-filters-1.com'; const mockUrlWithFilters2 = 'https://url-with-filters-2.com'; const pigService = {} as PIGService; pigService.getUrlWithFilters = jest.fn() .mockReturnValueOnce(mockUrlWithFilters1) .mockReturnValueOnce(mockUrlWithFilters2); const changeDetectorRef = {} as ChangeDetectorRef; changeDetectorRef.markForCheck = jest.fn(); const imageEditorWithDataComponent = initImageEditorWithDataComponent( pigService, changeDetectorRef, ); imageEditorWithDataComponent.layerComponents = { masks: [{ correction: 1, }, { correction: 2, }], } as PIGLayerImageInterface; imageEditorWithDataComponent.maskImageMap = null; imageEditorWithDataComponent.imageEditorImages = [{ scale: 5, }, { scale: 1, url_preview: 'testPreview', }] as ImageEditorImageInterface[]; return { changeDetectorRef, imageEditorWithDataComponent, mockUrlWithFilters1, mockUrlWithFilters2, pigService, }; }; test('Does not throw if imageEditorImages is undefined', () => { const { imageEditorWithDataComponent, } = initInitaliseMasks(); imageEditorWithDataComponent.imageEditorImages = undefined; expect((() => imageEditorWithDataComponent.initaliseMasks())) .not.toThrow(); }); test('Does not throw if there are no imageEditorImages', () => { const { imageEditorWithDataComponent, } = initInitaliseMasks(); imageEditorWithDataComponent.imageEditorImages = []; expect((() => imageEditorWithDataComponent.initaliseMasks())) .not.toThrow(); }); test('Correctly sets the maskImagesMap', () => { const { imageEditorWithDataComponent, mockUrlWithFilters1, mockUrlWithFilters2, } = initInitaliseMasks(); imageEditorWithDataComponent.initaliseMasks(); expect(imageEditorWithDataComponent.maskImageMap).toEqual([{ imageEditorImage: { ...imageEditorWithDataComponent.imageEditorImages[0], urlToRender: mockUrlWithFilters1, }, mask: imageEditorWithDataComponent.layerComponents.masks[0], }, { imageEditorImage: { ...imageEditorWithDataComponent.imageEditorImages[1], urlToRender: mockUrlWithFilters2, }, mask: imageEditorWithDataComponent.layerComponents.masks[1], }]); }); test('Gets the url with filters from the pig service', () => { const { imageEditorWithDataComponent, pigService, } = initInitaliseMasks(); imageEditorWithDataComponent.initaliseMasks(); expect(pigService.getUrlWithFilters).toHaveBeenCalledWith( imageEditorWithDataComponent.imageEditorImages[1].url_preview, imageEditorWithDataComponent.templateId, imageEditorWithDataComponent.imageEditorImages[1].filters, ); }); // tslint:disable-next-line test('Sets the foregroundBlendMode to undefined if there is no foreground in the layer components', () => { const { imageEditorWithDataComponent, } = initInitaliseMasks(); imageEditorWithDataComponent.layerComponents.foreground = undefined; imageEditorWithDataComponent.foregroundBlendMode = 'multiply'; imageEditorWithDataComponent.initaliseMasks(); expect(imageEditorWithDataComponent.foregroundBlendMode) .toBeUndefined(); }); // tslint:disable-next-line test('Sets the foregroundUrl to undefined if there is no foreground in the layer components', () => { const { imageEditorWithDataComponent, } = initInitaliseMasks(); imageEditorWithDataComponent.layerComponents.foreground = undefined; imageEditorWithDataComponent.foregroundUrl = 'https://foreground.com'; imageEditorWithDataComponent.initaliseMasks(); expect(imageEditorWithDataComponent.foregroundUrl) .toBeUndefined(); }); // tslint:disable-next-line test('Sets the foregroundBlendMode to the value from the layer components if it exists', () => { const { imageEditorWithDataComponent, } = initInitaliseMasks(); imageEditorWithDataComponent.layerComponents.foreground = { blend_mode: 'multiply', image: 'https://foreground.com', }; imageEditorWithDataComponent.initaliseMasks(); expect(imageEditorWithDataComponent.foregroundBlendMode) .toBe('multiply'); }); // tslint:disable-next-line test('Sets the foregroundUrl to the value from the layer components if it exists', () => { const { imageEditorWithDataComponent, } = initInitaliseMasks(); imageEditorWithDataComponent.layerComponents.foreground = { blend_mode: 'multiply', image: 'https://foreground.com', }; imageEditorWithDataComponent.initaliseMasks(); expect(imageEditorWithDataComponent.foregroundUrl) .toBe('https://foreground.com'); }); // tslint:disable-next-line test('Sets the urlToRender of the maskImageMap to the result of pigService.getUrlWithFilters', () => { const { imageEditorWithDataComponent, mockUrlWithFilters2, } = initInitaliseMasks(); imageEditorWithDataComponent.initaliseMasks(); expect( imageEditorWithDataComponent.maskImageMap.pop() .imageEditorImage.urlToRender, ).toBe(mockUrlWithFilters2); }); test('Calls changeDetectorRef.markForCheck', () => { const { changeDetectorRef, imageEditorWithDataComponent, } = initInitaliseMasks(); imageEditorWithDataComponent.initaliseMasks(); expect(changeDetectorRef.markForCheck).toHaveBeenCalled(); }); }); describe('onUpdateTranslations', () => { test('Emits an event to updateTranslations', () => { const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.updateTranslations.emit = jest.fn(); const event = [{}, {}] as [MaskImageMapInterface, CoordsInterface]; imageEditorWithDataComponent.onUpdateTranslations(event); expect(imageEditorWithDataComponent.updateTranslations.emit) .toHaveBeenCalledWith(event); }); }); describe('pinchRotateImage', () => { test('Emits an event to pinchRotateImage', () => { const event = [{}, 10] as [MaskImageMapInterface, number]; const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.onPinchRotateImage.emit = jest.fn(); imageEditorWithDataComponent.pinchRotateImage(event); expect(imageEditorWithDataComponent.onPinchRotateImage.emit) .toHaveBeenCalledWith(event); }); }); describe('pinchScaleImage', () => { test('Emits an event to pinchScaleImage', () => { const event = [{}, 10] as [MaskImageMapInterface, number]; const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.onPinchScaleImage.emit = jest.fn(); imageEditorWithDataComponent.pinchScaleImage(event); expect(imageEditorWithDataComponent.onPinchScaleImage.emit) .toHaveBeenCalledWith(event); }); }); describe('rotationControlRotate', () => { test('Emits an event to onRotationControlRotate', () => { const event = [{}, 10] as [MaskImageMapInterface, number]; const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.onRotationControlRotate.emit = jest.fn(); imageEditorWithDataComponent.rotationControlRotate(event); expect(imageEditorWithDataComponent.onRotationControlRotate.emit) .toHaveBeenCalledWith(event); }); }); describe('scaleControlScaleAndTranslate', () => { test('Emits an event to onScaleControlScaleAndTranslate', () => { const event = [{}, 10, {}] as [ MaskImageMapInterface, number, CoordsInterface ]; const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent .onScaleControlScaleAndTranslate.emit = jest.fn(); imageEditorWithDataComponent.scaleControlScaleAndTranslate(event); expect( imageEditorWithDataComponent.onScaleControlScaleAndTranslate.emit, ).toHaveBeenCalledWith(event); }); }); describe('deleteButtonClicked', () => { test('Emits an event to onDeleteButtonClicked', () => { const imageEditorWithDataComponent = initImageEditorWithDataComponent(); imageEditorWithDataComponent.onDeleteButtonClicked.emit = jest.fn(); const maskImageMap = {} as MaskImageMapInterface; imageEditorWithDataComponent.deleteButtonClicked(maskImageMap); expect(imageEditorWithDataComponent.onDeleteButtonClicked.emit) .toHaveBeenCalledWith(maskImageMap); }); });