diff --git a/src/app/app.component.ts b/src/app/app.component.ts index e0c06b61e..a0f9799d5 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -2,7 +2,11 @@ * Created by vadimdez on 21/06/16. */ import { Component, ViewChild } from '@angular/core'; -import { PDFProgressData, PDFDocumentProxy, PDFSource } from './pdf-viewer/pdf-viewer.module'; +import { + PDFProgressData, + PDFDocumentProxy, + PDFSource +} from './pdf-viewer/pdf-viewer.module'; import { PdfViewerComponent } from './pdf-viewer/pdf-viewer.component'; @@ -12,9 +16,7 @@ import { PdfViewerComponent } from './pdf-viewer/pdf-viewer.component'; templateUrl: './app.component.html', styleUrls: ['./app.component.css'] }) - export class AppComponent { - pdfSrc: string | PDFSource | ArrayBuffer = './assets/pdf-test.pdf'; // or pass options as object @@ -54,7 +56,7 @@ export class AppComponent { xhr.onload = (e: any) => { console.log(xhr); if (xhr.status === 200) { - const blob = new Blob([xhr.response], {type: 'application/pdf'}); + const blob = new Blob([xhr.response], { type: 'application/pdf' }); this.pdfSrc = URL.createObjectURL(blob); } }; @@ -87,7 +89,7 @@ export class AppComponent { onFileSelected() { const $pdf: any = document.querySelector('#file'); - if (typeof (FileReader) !== 'undefined') { + if (typeof FileReader !== 'undefined') { const reader = new FileReader(); reader.onload = (e: any) => { @@ -127,7 +129,9 @@ export class AppComponent { this.error = error; // set error if (error.name === 'PasswordException') { - const password = prompt('This document is password protected. Enter the password:'); + const password = prompt( + 'This document is password protected. Enter the password:' + ); if (password) { this.error = null; @@ -140,11 +144,11 @@ export class AppComponent { let newSrc; if (this.pdfSrc instanceof ArrayBuffer) { - newSrc = {data: this.pdfSrc}; + newSrc = { data: this.pdfSrc }; } else if (typeof this.pdfSrc === 'string') { - newSrc = {url: this.pdfSrc}; + newSrc = { url: this.pdfSrc }; } else { - newSrc = {...this.pdfSrc}; + newSrc = { ...this.pdfSrc }; } newSrc.password = password; diff --git a/src/app/pdf-viewer/pdf-viewer.component.spec.ts b/src/app/pdf-viewer/pdf-viewer.component.spec.ts index 8328f49ee..f33a1855c 100644 --- a/src/app/pdf-viewer/pdf-viewer.component.spec.ts +++ b/src/app/pdf-viewer/pdf-viewer.component.spec.ts @@ -5,7 +5,9 @@ import { PdfViewerComponent } from './pdf-viewer.component'; import { PdfViewerModule } from './pdf-viewer.module'; @Component({ - template: `` + template: ` + + ` }) class TestComponent {} @@ -24,20 +26,17 @@ describe('AppComponent', () => { beforeEach(async(() => { TestBed.configureTestingModule({ - declarations: [ - TestComponent - ], - imports: [ - PdfViewerModule - ] - }).compileComponents() - .then(() => { - testFixture = TestBed.createComponent(TestComponent); - testApp = testFixture.debugElement.componentInstance; - - pdfViewerFixture = TestBed.createComponent(PdfViewerComponent); - pdfViewer = pdfViewerFixture.debugElement.componentInstance; - }); + declarations: [TestComponent], + imports: [PdfViewerModule] + }) + .compileComponents() + .then(() => { + testFixture = TestBed.createComponent(TestComponent); + testApp = testFixture.debugElement.componentInstance; + + pdfViewerFixture = TestBed.createComponent(PdfViewerComponent); + pdfViewer = pdfViewerFixture.debugElement.componentInstance; + }); })); it('should create test component', () => { @@ -50,7 +49,10 @@ describe('AppComponent', () => { setPdf(10); [1, 3, 7, 10].forEach((page: number) => { - expect((pdfViewer as any).getValidPageNumber(page)).toBe(page, `page: ${ page }`); + expect((pdfViewer as any).getValidPageNumber(page)).toBe( + page, + `page: ${page}` + ); }); }); @@ -61,7 +63,7 @@ describe('AppComponent', () => { expect((pdfViewer as any).getValidPageNumber(pages + 2)).toBe(pages); }); - it('should return first page when page is less then 1', function () { + it('should return first page when page is less then 1', function() { setPdf(10); expect((pdfViewer as any).getValidPageNumber(0)).toBe(1); expect((pdfViewer as any).getValidPageNumber(-1)).toBe(1); @@ -69,8 +71,12 @@ describe('AppComponent', () => { }); describe('getScale', () => { - it('should get scale 1 with offsetWidth = 0', function () { - let spy = spyOnProperty((pdfViewer as any).element.nativeElement, 'offsetWidth', 'get').and.returnValue(0); + it('should get scale 1 with offsetWidth = 0', function() { + let spy = spyOnProperty( + (pdfViewer as any).element.nativeElement, + 'offsetWidth', + 'get' + ).and.returnValue(0); expect((pdfViewer as any).getScale(0)).toBe(1); expect(spy).toHaveBeenCalled(); @@ -84,7 +90,9 @@ describe('AppComponent', () => { it('should check default url', () => { const PDFJS = require('pdfjs-dist/build/pdf'); - expect((pdfViewer)._cMapsUrl).toBe(`https://unpkg.com/pdfjs-dist@${ (PDFJS as any).version }/cmaps/`); + expect((pdfViewer)._cMapsUrl).toBe( + `https://unpkg.com/pdfjs-dist@${(PDFJS as any).version}/cmaps/` + ); }); it('should return src', () => { @@ -98,14 +106,22 @@ describe('AppComponent', () => { pdfViewer.src = src; pdfViewer.cMapsUrl = cMapUrl; - expect((pdfViewer).getDocumentParams()).toEqual({ url: src, cMapUrl, cMapPacked: true }); + expect((pdfViewer).getDocumentParams()).toEqual({ + url: src, + cMapUrl, + cMapPacked: true + }); }); it('should return object when src is an object', () => { pdfViewer.src = { url: src }; pdfViewer.cMapsUrl = cMapUrl; - expect((pdfViewer).getDocumentParams()).toEqual({ url: src, cMapUrl, cMapPacked: true }); + expect((pdfViewer).getDocumentParams()).toEqual({ + url: src, + cMapUrl, + cMapPacked: true + }); }); it('should return object when src is an object with byte array', () => { @@ -113,7 +129,11 @@ describe('AppComponent', () => { pdfViewer.src = { url: src as any }; pdfViewer.cMapsUrl = cMapUrl; - expect((pdfViewer).getDocumentParams()).toEqual({ url: src, cMapUrl, cMapPacked: true }); + expect((pdfViewer).getDocumentParams()).toEqual({ + url: src, + cMapUrl, + cMapPacked: true + }); }); }); -}); \ No newline at end of file +}); diff --git a/src/app/pdf-viewer/pdf-viewer.component.ts b/src/app/pdf-viewer/pdf-viewer.component.ts index 50925b275..c1c893b71 100644 --- a/src/app/pdf-viewer/pdf-viewer.component.ts +++ b/src/app/pdf-viewer/pdf-viewer.component.ts @@ -2,9 +2,25 @@ * Created by vadimdez on 21/06/16. */ import { - Component, Input, Output, ElementRef, EventEmitter, OnChanges, SimpleChanges, OnInit, HostListener, OnDestroy + Component, + Input, + Output, + ElementRef, + EventEmitter, + OnChanges, + SimpleChanges, + OnInit, + HostListener, + OnDestroy } from '@angular/core'; -import { PDFDocumentProxy, PDFViewerParams, PDFPageProxy, PDFSource, PDFProgressData, PDFPromise } from 'pdfjs-dist'; +import { + PDFDocumentProxy, + PDFViewerParams, + PDFPageProxy, + PDFSource, + PDFProgressData, + PDFPromise +} from 'pdfjs-dist'; import { createEventBus } from '../utils/event-bus-utils'; @@ -31,12 +47,10 @@ export enum RenderTextMode { @Component({ selector: 'pdf-viewer', template: ` -
-
-
`, +
+ `, styleUrls: ['./pdf-viewer.component.scss'] }) - export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { static CSS_UNITS: number = 96.0 / 72.0; @@ -48,7 +62,10 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { private pdfSinglePageLinkService: any; private pdfSinglePageFindController: any; - private _cMapsUrl = typeof PDFJS !== 'undefined' ? `https://unpkg.com/pdfjs-dist@${ (PDFJS as any).version }/cmaps/` : null; + private _cMapsUrl = + typeof PDFJS !== 'undefined' + ? `https://unpkg.com/pdfjs-dist@${(PDFJS as any).version}/cmaps/` + : null; private _renderText = true; private _renderTextMode: RenderTextMode = RenderTextMode.ENABLED; private _stickToPage = false; @@ -65,9 +82,13 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { private resizeTimeout: NodeJS.Timer; - @Output('after-load-complete') afterLoadComplete = new EventEmitter(); + @Output('after-load-complete') afterLoadComplete = new EventEmitter< + PDFDocumentProxy + >(); @Output('page-rendered') pageRendered = new EventEmitter(); - @Output('text-layer-rendered') textLayerRendered = new EventEmitter(); + @Output('text-layer-rendered') textLayerRendered = new EventEmitter< + CustomEvent + >(); @Output('error') onError = new EventEmitter(); @Output('on-progress') onProgress = new EventEmitter(); @Output() pageChange: EventEmitter = new EventEmitter(true); @@ -186,14 +207,19 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { let pdfWorkerSrc: string; - if (window.hasOwnProperty('pdfWorkerSrc') && typeof (window as any).pdfWorkerSrc === 'string' && (window as any).pdfWorkerSrc) { + if ( + window.hasOwnProperty('pdfWorkerSrc') && + typeof (window as any).pdfWorkerSrc === 'string' && + (window as any).pdfWorkerSrc + ) { pdfWorkerSrc = (window as any).pdfWorkerSrc; } else { - pdfWorkerSrc = `https://cdnjs.cloudflare.com/ajax/libs/pdf.js/${ (PDFJS as any).version }/pdf.worker.min.js`; + pdfWorkerSrc = `https://cdnjs.cloudflare.com/ajax/libs/pdf.js/${ + (PDFJS as any).version + }/pdf.worker.min.js`; } (PDFJS as any).GlobalWorkerOptions.workerSrc = pdfWorkerSrc; - } ngOnInit() { @@ -230,7 +256,9 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { } get pdfLinkService(): any { - return this._showAll ? this.pdfMultiPageLinkService : this.pdfSinglePageLinkService; + return this._showAll + ? this.pdfMultiPageLinkService + : this.pdfSinglePageLinkService; } get pdfViewer(): any { @@ -238,7 +266,9 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { } get pdfFindController(): any { - return this._showAll ? this.pdfMultiPageFindController : this.pdfSinglePageFindController; + return this._showAll + ? this.pdfMultiPageFindController + : this.pdfSinglePageFindController; } ngOnChanges(changes: SimpleChanges) { @@ -250,7 +280,9 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { this.loadPDF(); } else if (this._pdf) { if ('renderText' in changes) { - this.getCurrentViewer().textLayerMode = this._renderText ? this._renderTextMode : RenderTextMode.DISABLED; + this.getCurrentViewer().textLayerMode = this._renderText + ? this._renderTextMode + : RenderTextMode.DISABLED; this.resetPdfDocument(); } else if ('showAll' in changes) { this.resetPdfDocument(); @@ -258,7 +290,7 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { if ('page' in changes) { // New form of page changing: The viewer will now jump to the specified page when it is changed. // This behavior is introducedby using the PDFSinglePageViewer - this.getCurrentViewer().scrollPageIntoView({pageNumber: this._page}); + this.getCurrentViewer().scrollPageIntoView({ pageNumber: this._page }); } this.update(); @@ -267,19 +299,25 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { public updateSize() { const currentViewer = this.getCurrentViewer(); - this._pdf.getPage(currentViewer.currentPageNumber).then((page: PDFPageProxy) => { - const viewport = page.getViewport(this._zoom, this._rotation); - let scale = this._zoom; - let stickToPage = true; - - // Scale the document when it shouldn't be in original size or doesn't fit into the viewport - if (!this._originalSize || (this._fitToPage && viewport.width > this.element.nativeElement.offsetWidth)) { - scale = this.getScale(page.getViewport(1).width); - stickToPage = !this._stickToPage; - } + this._pdf + .getPage(currentViewer.currentPageNumber) + .then((page: PDFPageProxy) => { + const viewport = page.getViewport(this._zoom, this._rotation); + let scale = this._zoom; + let stickToPage = true; + + // Scale the document when it shouldn't be in original size or doesn't fit into the viewport + if ( + !this._originalSize || + (this._fitToPage && + viewport.width > this.element.nativeElement.offsetWidth) + ) { + scale = this.getScale(page.getViewport(1).width); + stickToPage = !this._stickToPage; + } - currentViewer._setScale(scale, stickToPage); - }); + currentViewer._setScale(scale, stickToPage); + }); } private setupMultiPageViewer() { @@ -289,20 +327,25 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { const eventBus = createEventBus(PDFJSViewer); - eventBus.on('pagerendered', (e) => { + eventBus.on('pagerendered', e => { this.pageRendered.emit(e); }); - this.pdfMultiPageLinkService = new PDFJSViewer.PDFLinkService({eventBus}); - this.pdfMultiPageFindController = new PDFJSViewer.PDFFindController({linkService: this.pdfMultiPageLinkService, eventBus}); + this.pdfMultiPageLinkService = new PDFJSViewer.PDFLinkService({ eventBus }); + this.pdfMultiPageFindController = new PDFJSViewer.PDFFindController({ + linkService: this.pdfMultiPageLinkService, + eventBus + }); const pdfOptions: PDFViewerParams | any = { eventBus: eventBus, container: this.element.nativeElement.querySelector('div'), removePageBorders: true, linkService: this.pdfMultiPageLinkService, - textLayerMode: this._renderText ? this._renderTextMode : RenderTextMode.DISABLED, - findController: this.pdfMultiPageFindController, + textLayerMode: this._renderText + ? this._renderTextMode + : RenderTextMode.DISABLED, + findController: this.pdfMultiPageFindController }; this.pdfMultiPageViewer = new PDFJSViewer.PDFViewer(pdfOptions); @@ -317,20 +360,27 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { const eventBus = createEventBus(PDFJSViewer); - eventBus.on('pagerendered', (e) => { + eventBus.on('pagerendered', e => { this.pageRendered.emit(e); }); - this.pdfSinglePageLinkService = new PDFJSViewer.PDFLinkService({eventBus}); - this.pdfSinglePageFindController = new PDFJSViewer.PDFFindController({linkService: this.pdfSinglePageLinkService, eventBus}); + this.pdfSinglePageLinkService = new PDFJSViewer.PDFLinkService({ + eventBus + }); + this.pdfSinglePageFindController = new PDFJSViewer.PDFFindController({ + linkService: this.pdfSinglePageLinkService, + eventBus + }); const pdfOptions: PDFViewerParams | any = { eventBus: eventBus, container: this.element.nativeElement.querySelector('div'), removePageBorders: true, linkService: this.pdfSinglePageLinkService, - textLayerMode: this._renderText ? this._renderTextMode : RenderTextMode.DISABLED, - findController: this.pdfSinglePageFindController, + textLayerMode: this._renderText + ? this._renderTextMode + : RenderTextMode.DISABLED, + findController: this.pdfSinglePageFindController }; this.pdfSinglePageViewer = new PDFJSViewer.PDFSinglePageViewer(pdfOptions); @@ -353,7 +403,7 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { } private getDocumentParams() { - const srcType = typeof(this.src); + const srcType = typeof this.src; if (!this._cMapsUrl) { return this.src; @@ -387,15 +437,17 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { return; } - const loadingTask: any = (PDFJS as any).getDocument(this.getDocumentParams()); + const loadingTask: any = (PDFJS as any).getDocument( + this.getDocumentParams() + ); loadingTask.onProgress = (progressData: PDFProgressData) => { this.onProgress.emit(progressData); }; const src = this.src; - (>loadingTask.promise) - .then((pdf: PDFDocumentProxy) => { + (>loadingTask.promise).then( + (pdf: PDFDocumentProxy) => { if (this._pdf) { this._pdf.destroy(); } @@ -412,9 +464,11 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { this.resetPdfDocument(); this.update(); - }, (error: any) => { + }, + (error: any) => { this.onError.emit(error); - }); + } + ); } private update() { @@ -427,7 +481,10 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { this._page = this.getValidPageNumber(this._page); const currentViewer = this.getCurrentViewer(); - if (this._rotation !== 0 || currentViewer.pagesRotation !== this._rotation) { + if ( + this._rotation !== 0 || + currentViewer.pagesRotation !== this._rotation + ) { setTimeout(() => { currentViewer.pagesRotation = this._rotation; }); @@ -449,7 +506,10 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { return 1; } - return this._zoom * (offsetWidth / viewportWidth) / PdfViewerComponent.CSS_UNITS; + return ( + (this._zoom * (offsetWidth / viewportWidth)) / + PdfViewerComponent.CSS_UNITS + ); } private getCurrentViewer(): any { @@ -472,7 +532,5 @@ export class PdfViewerComponent implements OnChanges, OnInit, OnDestroy { this.pdfSinglePageViewer.setDocument(this._pdf); this.pdfSinglePageLinkService.setDocument(this._pdf, null); } - } - }