mirror of
https://github.com/paperless-ngx/paperless-ngx.git
synced 2025-07-28 18:24:38 -05:00
Feature: pngx PDF viewer with updated pdfjs (#4679)
This commit is contained in:
@@ -0,0 +1,3 @@
|
||||
<div #pdfViewerContainer class="pngx-pdf-viewer-container">
|
||||
<div class="pdfViewer"></div>
|
||||
</div>
|
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,599 @@
|
||||
/**
|
||||
* This file is taken and modified from https://github.com/VadimDez/ng2-pdf-viewer/blob/10.0.0/src/app/pdf-viewer/pdf-viewer.component.ts
|
||||
* Created by vadimdez on 21/06/16.
|
||||
*/
|
||||
import {
|
||||
Component,
|
||||
Input,
|
||||
Output,
|
||||
ElementRef,
|
||||
EventEmitter,
|
||||
OnChanges,
|
||||
SimpleChanges,
|
||||
OnInit,
|
||||
OnDestroy,
|
||||
ViewChild,
|
||||
AfterViewChecked,
|
||||
NgZone,
|
||||
} from '@angular/core'
|
||||
import { from, fromEvent, Subject } from 'rxjs'
|
||||
import { debounceTime, filter, takeUntil } from 'rxjs/operators'
|
||||
import * as PDFJS from 'pdfjs-dist'
|
||||
import * as PDFJSViewer from 'pdfjs-dist/web/pdf_viewer'
|
||||
|
||||
import { createEventBus } from './utils/event-bus-utils'
|
||||
|
||||
import type {
|
||||
PDFSource,
|
||||
PDFPageProxy,
|
||||
PDFProgressData,
|
||||
PDFDocumentProxy,
|
||||
PDFDocumentLoadingTask,
|
||||
PDFViewerOptions,
|
||||
ZoomScale,
|
||||
} from './typings'
|
||||
import { PDFSinglePageViewer } from 'pdfjs-dist/web/pdf_viewer'
|
||||
|
||||
PDFJS['verbosity'] = PDFJS.VerbosityLevel.ERRORS
|
||||
|
||||
// Yea this is a straight hack
|
||||
declare global {
|
||||
interface WeakKeyTypes {
|
||||
symbol: Object
|
||||
}
|
||||
|
||||
type WeakKey = WeakKeyTypes[keyof WeakKeyTypes]
|
||||
}
|
||||
|
||||
export enum RenderTextMode {
|
||||
DISABLED,
|
||||
ENABLED,
|
||||
ENHANCED,
|
||||
}
|
||||
|
||||
@Component({
|
||||
selector: 'pngx-pdf-viewer',
|
||||
templateUrl: './pdf-viewer.component.html',
|
||||
styleUrls: ['./pdf-viewer.component.scss'],
|
||||
})
|
||||
export class PdfViewerComponent
|
||||
implements OnChanges, OnInit, OnDestroy, AfterViewChecked
|
||||
{
|
||||
static CSS_UNITS = 96.0 / 72.0
|
||||
static BORDER_WIDTH = 9
|
||||
|
||||
@ViewChild('pdfViewerContainer')
|
||||
pdfViewerContainer!: ElementRef<HTMLDivElement>
|
||||
|
||||
public eventBus!: PDFJSViewer.EventBus
|
||||
public pdfLinkService!: PDFJSViewer.PDFLinkService
|
||||
public pdfViewer!: PDFJSViewer.PDFViewer | PDFSinglePageViewer
|
||||
|
||||
private isVisible = false
|
||||
|
||||
private _cMapsUrl =
|
||||
typeof PDFJS !== 'undefined'
|
||||
? `https://unpkg.com/pdfjs-dist@${(PDFJS as any).version}/cmaps/`
|
||||
: null
|
||||
private _imageResourcesPath =
|
||||
typeof PDFJS !== 'undefined'
|
||||
? `https://unpkg.com/pdfjs-dist@${(PDFJS as any).version}/web/images/`
|
||||
: undefined
|
||||
private _renderText = true
|
||||
private _renderTextMode: RenderTextMode = RenderTextMode.ENABLED
|
||||
private _stickToPage = false
|
||||
private _originalSize = true
|
||||
private _pdf: PDFDocumentProxy | undefined
|
||||
private _page = 1
|
||||
private _zoom = 1
|
||||
private _zoomScale: ZoomScale = 'page-width'
|
||||
private _rotation = 0
|
||||
private _showAll = true
|
||||
private _canAutoResize = true
|
||||
private _fitToPage = false
|
||||
private _externalLinkTarget = 'blank'
|
||||
private _showBorders = false
|
||||
private lastLoaded!: string | Uint8Array | PDFSource | null
|
||||
private _latestScrolledPage!: number
|
||||
|
||||
private resizeTimeout: number | null = null
|
||||
private pageScrollTimeout: number | null = null
|
||||
private isInitialized = false
|
||||
private loadingTask?: PDFDocumentLoadingTask | null
|
||||
private destroy$ = new Subject<void>()
|
||||
|
||||
@Output('after-load-complete') afterLoadComplete =
|
||||
new EventEmitter<PDFDocumentProxy>()
|
||||
@Output('page-rendered') pageRendered = new EventEmitter<CustomEvent>()
|
||||
@Output('pages-initialized') pageInitialized = new EventEmitter<CustomEvent>()
|
||||
@Output('text-layer-rendered') textLayerRendered =
|
||||
new EventEmitter<CustomEvent>()
|
||||
@Output('error') onError = new EventEmitter<any>()
|
||||
@Output('on-progress') onProgress = new EventEmitter<PDFProgressData>()
|
||||
@Output() pageChange: EventEmitter<number> = new EventEmitter<number>(true)
|
||||
@Input() src?: string | Uint8Array | PDFSource
|
||||
|
||||
@Input('c-maps-url')
|
||||
set cMapsUrl(cMapsUrl: string) {
|
||||
this._cMapsUrl = cMapsUrl
|
||||
}
|
||||
|
||||
@Input('page')
|
||||
set page(_page: number | string | any) {
|
||||
_page = parseInt(_page, 10) || 1
|
||||
const originalPage = _page
|
||||
|
||||
if (this._pdf) {
|
||||
_page = this.getValidPageNumber(_page)
|
||||
}
|
||||
|
||||
this._page = _page
|
||||
if (originalPage !== _page) {
|
||||
this.pageChange.emit(_page)
|
||||
}
|
||||
}
|
||||
|
||||
@Input('render-text')
|
||||
set renderText(renderText: boolean) {
|
||||
this._renderText = renderText
|
||||
}
|
||||
|
||||
@Input('render-text-mode')
|
||||
set renderTextMode(renderTextMode: RenderTextMode) {
|
||||
this._renderTextMode = renderTextMode
|
||||
}
|
||||
|
||||
@Input('original-size')
|
||||
set originalSize(originalSize: boolean) {
|
||||
this._originalSize = originalSize
|
||||
}
|
||||
|
||||
@Input('show-all')
|
||||
set showAll(value: boolean) {
|
||||
this._showAll = value
|
||||
}
|
||||
|
||||
@Input('stick-to-page')
|
||||
set stickToPage(value: boolean) {
|
||||
this._stickToPage = value
|
||||
}
|
||||
|
||||
@Input('zoom')
|
||||
set zoom(value: number) {
|
||||
if (value <= 0) {
|
||||
return
|
||||
}
|
||||
|
||||
this._zoom = value
|
||||
}
|
||||
|
||||
get zoom() {
|
||||
return this._zoom
|
||||
}
|
||||
|
||||
@Input('zoom-scale')
|
||||
set zoomScale(value: ZoomScale) {
|
||||
this._zoomScale = value
|
||||
}
|
||||
|
||||
get zoomScale() {
|
||||
return this._zoomScale
|
||||
}
|
||||
|
||||
@Input('rotation')
|
||||
set rotation(value: number) {
|
||||
if (!(typeof value === 'number' && value % 90 === 0)) {
|
||||
console.warn('Invalid pages rotation angle.')
|
||||
return
|
||||
}
|
||||
|
||||
this._rotation = value
|
||||
}
|
||||
|
||||
@Input('external-link-target')
|
||||
set externalLinkTarget(value: string) {
|
||||
this._externalLinkTarget = value
|
||||
}
|
||||
|
||||
@Input('autoresize')
|
||||
set autoresize(value: boolean) {
|
||||
this._canAutoResize = Boolean(value)
|
||||
}
|
||||
|
||||
@Input('fit-to-page')
|
||||
set fitToPage(value: boolean) {
|
||||
this._fitToPage = Boolean(value)
|
||||
}
|
||||
|
||||
@Input('show-borders')
|
||||
set showBorders(value: boolean) {
|
||||
this._showBorders = Boolean(value)
|
||||
}
|
||||
|
||||
static getLinkTarget(type: string) {
|
||||
switch (type) {
|
||||
case 'blank':
|
||||
return (PDFJSViewer as any).LinkTarget.BLANK
|
||||
case 'none':
|
||||
return (PDFJSViewer as any).LinkTarget.NONE
|
||||
case 'self':
|
||||
return (PDFJSViewer as any).LinkTarget.SELF
|
||||
case 'parent':
|
||||
return (PDFJSViewer as any).LinkTarget.PARENT
|
||||
case 'top':
|
||||
return (PDFJSViewer as any).LinkTarget.TOP
|
||||
}
|
||||
|
||||
return null
|
||||
}
|
||||
|
||||
constructor(
|
||||
private element: ElementRef<HTMLElement>,
|
||||
private ngZone: NgZone
|
||||
) {
|
||||
PDFJS.GlobalWorkerOptions['workerSrc'] = '/assets/js/pdf.worker.min.js'
|
||||
}
|
||||
|
||||
ngAfterViewChecked(): void {
|
||||
if (this.isInitialized) {
|
||||
return
|
||||
}
|
||||
|
||||
const offset = this.pdfViewerContainer.nativeElement.offsetParent
|
||||
|
||||
if (this.isVisible === true && offset == null) {
|
||||
this.isVisible = false
|
||||
return
|
||||
}
|
||||
|
||||
if (this.isVisible === false && offset != null) {
|
||||
this.isVisible = true
|
||||
|
||||
setTimeout(() => {
|
||||
this.initialize()
|
||||
this.ngOnChanges({ src: this.src } as any)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
ngOnInit() {
|
||||
this.initialize()
|
||||
this.setupResizeListener()
|
||||
}
|
||||
|
||||
ngOnDestroy() {
|
||||
this.clear()
|
||||
this.destroy$.next()
|
||||
this.loadingTask = null
|
||||
}
|
||||
|
||||
ngOnChanges(changes: SimpleChanges) {
|
||||
if (!this.isVisible) {
|
||||
return
|
||||
}
|
||||
|
||||
if ('src' in changes) {
|
||||
this.loadPDF()
|
||||
} else if (this._pdf) {
|
||||
if ('renderText' in changes || 'showAll' in changes) {
|
||||
this.setupViewer()
|
||||
this.resetPdfDocument()
|
||||
}
|
||||
if ('page' in changes) {
|
||||
const { page } = changes
|
||||
if (page.currentValue === this._latestScrolledPage) {
|
||||
return
|
||||
}
|
||||
|
||||
// New form of page changing: The viewer will now jump to the specified page when it is changed.
|
||||
// This behavior is introduced by using the PDFSinglePageViewer
|
||||
this.pdfViewer.scrollPageIntoView({ pageNumber: this._page })
|
||||
}
|
||||
|
||||
this.update()
|
||||
}
|
||||
}
|
||||
|
||||
public updateSize() {
|
||||
from(
|
||||
this._pdf!.getPage(
|
||||
this.pdfViewer.currentPageNumber
|
||||
) as unknown as Promise<PDFPageProxy>
|
||||
)
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe({
|
||||
next: (page: PDFPageProxy) => {
|
||||
const rotation = this._rotation + page.rotate
|
||||
const viewportWidth =
|
||||
(page as any).getViewport({
|
||||
scale: this._zoom,
|
||||
rotation,
|
||||
}).width * PdfViewerComponent.CSS_UNITS
|
||||
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 &&
|
||||
viewportWidth > this.pdfViewerContainer.nativeElement.clientWidth)
|
||||
) {
|
||||
const viewPort = (page as any).getViewport({ scale: 1, rotation })
|
||||
scale = this.getScale(viewPort.width, viewPort.height)
|
||||
stickToPage = !this._stickToPage
|
||||
}
|
||||
|
||||
setTimeout(() => {
|
||||
this.pdfViewer.currentScale = scale
|
||||
})
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
public clear() {
|
||||
if (this.loadingTask && !this.loadingTask.destroyed) {
|
||||
this.loadingTask.destroy()
|
||||
}
|
||||
|
||||
if (this._pdf) {
|
||||
this._latestScrolledPage = 0
|
||||
this._pdf.destroy()
|
||||
this._pdf = undefined
|
||||
}
|
||||
}
|
||||
|
||||
private getPDFLinkServiceConfig() {
|
||||
const linkTarget = PdfViewerComponent.getLinkTarget(
|
||||
this._externalLinkTarget
|
||||
)
|
||||
|
||||
if (linkTarget) {
|
||||
return { externalLinkTarget: linkTarget }
|
||||
}
|
||||
|
||||
return {}
|
||||
}
|
||||
|
||||
private initEventBus() {
|
||||
this.eventBus = createEventBus(PDFJSViewer, this.destroy$)
|
||||
|
||||
fromEvent<CustomEvent>(this.eventBus, 'pagerendered')
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe((event) => {
|
||||
this.pageRendered.emit(event)
|
||||
})
|
||||
|
||||
fromEvent<CustomEvent>(this.eventBus, 'pagesinit')
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe((event) => {
|
||||
this.pageInitialized.emit(event)
|
||||
})
|
||||
|
||||
fromEvent(this.eventBus, 'pagechanging')
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe(({ pageNumber }: any) => {
|
||||
if (this.pageScrollTimeout) {
|
||||
clearTimeout(this.pageScrollTimeout)
|
||||
}
|
||||
|
||||
this.pageScrollTimeout = window.setTimeout(() => {
|
||||
this._latestScrolledPage = pageNumber
|
||||
this.pageChange.emit(pageNumber)
|
||||
}, 100)
|
||||
})
|
||||
|
||||
fromEvent<CustomEvent>(this.eventBus, 'textlayerrendered')
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe((event) => {
|
||||
this.textLayerRendered.emit(event)
|
||||
})
|
||||
}
|
||||
|
||||
private initPDFServices() {
|
||||
this.pdfLinkService = new PDFJSViewer.PDFLinkService({
|
||||
eventBus: this.eventBus,
|
||||
...this.getPDFLinkServiceConfig(),
|
||||
})
|
||||
}
|
||||
|
||||
private getPDFOptions(): PDFViewerOptions {
|
||||
return {
|
||||
eventBus: this.eventBus,
|
||||
container: this.element.nativeElement.querySelector('div')!,
|
||||
removePageBorders: !this._showBorders,
|
||||
linkService: this.pdfLinkService,
|
||||
textLayerMode: this._renderText
|
||||
? this._renderTextMode
|
||||
: RenderTextMode.DISABLED,
|
||||
imageResourcesPath: this._imageResourcesPath,
|
||||
}
|
||||
}
|
||||
|
||||
private setupViewer() {
|
||||
PDFJS['disableTextLayer'] = !this._renderText
|
||||
|
||||
this.initPDFServices()
|
||||
|
||||
if (this._showAll) {
|
||||
this.pdfViewer = new PDFJSViewer.PDFViewer(this.getPDFOptions())
|
||||
} else {
|
||||
this.pdfViewer = new PDFJSViewer.PDFSinglePageViewer(this.getPDFOptions())
|
||||
}
|
||||
this.pdfLinkService.setViewer(this.pdfViewer)
|
||||
|
||||
this.pdfViewer._currentPageNumber = this._page
|
||||
}
|
||||
|
||||
private getValidPageNumber(page: number): number {
|
||||
if (page < 1) {
|
||||
return 1
|
||||
}
|
||||
|
||||
if (page > this._pdf!.numPages) {
|
||||
return this._pdf!.numPages
|
||||
}
|
||||
|
||||
return page
|
||||
}
|
||||
|
||||
private getDocumentParams() {
|
||||
const srcType = typeof this.src
|
||||
|
||||
if (!this._cMapsUrl) {
|
||||
return this.src
|
||||
}
|
||||
|
||||
const params: any = {
|
||||
cMapUrl: this._cMapsUrl,
|
||||
cMapPacked: true,
|
||||
enableXfa: true,
|
||||
}
|
||||
|
||||
if (srcType === 'string') {
|
||||
params.url = this.src
|
||||
} else if (srcType === 'object') {
|
||||
if ((this.src as any).byteLength !== undefined) {
|
||||
params.data = this.src
|
||||
} else {
|
||||
Object.assign(params, this.src)
|
||||
}
|
||||
}
|
||||
|
||||
return params
|
||||
}
|
||||
|
||||
private loadPDF() {
|
||||
if (!this.src) {
|
||||
return
|
||||
}
|
||||
|
||||
if (this.lastLoaded === this.src) {
|
||||
this.update()
|
||||
return
|
||||
}
|
||||
|
||||
this.clear()
|
||||
|
||||
this.setupViewer()
|
||||
|
||||
this.loadingTask = PDFJS.getDocument(this.getDocumentParams())
|
||||
|
||||
this.loadingTask!.onProgress = (progressData: PDFProgressData) => {
|
||||
this.onProgress.emit(progressData)
|
||||
}
|
||||
|
||||
const src = this.src
|
||||
|
||||
from(this.loadingTask!.promise as Promise<PDFDocumentProxy>)
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe({
|
||||
next: (pdf) => {
|
||||
this._pdf = pdf
|
||||
this.lastLoaded = src
|
||||
|
||||
this.afterLoadComplete.emit(pdf)
|
||||
this.resetPdfDocument()
|
||||
|
||||
this.update()
|
||||
},
|
||||
error: (error) => {
|
||||
this.lastLoaded = null
|
||||
this.onError.emit(error)
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
private update() {
|
||||
this.page = this._page
|
||||
|
||||
this.render()
|
||||
}
|
||||
|
||||
private render() {
|
||||
this._page = this.getValidPageNumber(this._page)
|
||||
|
||||
if (
|
||||
this._rotation !== 0 ||
|
||||
this.pdfViewer.pagesRotation !== this._rotation
|
||||
) {
|
||||
setTimeout(() => {
|
||||
this.pdfViewer.pagesRotation = this._rotation
|
||||
})
|
||||
}
|
||||
|
||||
if (this._stickToPage) {
|
||||
setTimeout(() => {
|
||||
this.pdfViewer.currentPageNumber = this._page
|
||||
})
|
||||
}
|
||||
|
||||
this.updateSize()
|
||||
}
|
||||
|
||||
private getScale(viewportWidth: number, viewportHeight: number) {
|
||||
const borderSize = this._showBorders
|
||||
? 2 * PdfViewerComponent.BORDER_WIDTH
|
||||
: 0
|
||||
const pdfContainerWidth =
|
||||
this.pdfViewerContainer.nativeElement.clientWidth - borderSize
|
||||
const pdfContainerHeight =
|
||||
this.pdfViewerContainer.nativeElement.clientHeight - borderSize
|
||||
|
||||
if (
|
||||
pdfContainerHeight === 0 ||
|
||||
viewportHeight === 0 ||
|
||||
pdfContainerWidth === 0 ||
|
||||
viewportWidth === 0
|
||||
) {
|
||||
return 1
|
||||
}
|
||||
|
||||
let ratio = 1
|
||||
switch (this._zoomScale) {
|
||||
case 'page-fit':
|
||||
ratio = Math.min(
|
||||
pdfContainerHeight / viewportHeight,
|
||||
pdfContainerWidth / viewportWidth
|
||||
)
|
||||
break
|
||||
case 'page-height':
|
||||
ratio = pdfContainerHeight / viewportHeight
|
||||
break
|
||||
case 'page-width':
|
||||
default:
|
||||
ratio = pdfContainerWidth / viewportWidth
|
||||
break
|
||||
}
|
||||
|
||||
return (this._zoom * ratio) / PdfViewerComponent.CSS_UNITS
|
||||
}
|
||||
|
||||
private resetPdfDocument() {
|
||||
this.pdfLinkService.setDocument(this._pdf, null)
|
||||
this.pdfViewer.setDocument(this._pdf!)
|
||||
}
|
||||
|
||||
private initialize(): void {
|
||||
if (!this.isVisible) {
|
||||
return
|
||||
}
|
||||
|
||||
this.isInitialized = true
|
||||
this.initEventBus()
|
||||
this.setupViewer()
|
||||
}
|
||||
|
||||
private setupResizeListener(): void {
|
||||
this.ngZone.runOutsideAngular(() => {
|
||||
fromEvent(window, 'resize')
|
||||
.pipe(
|
||||
debounceTime(100),
|
||||
filter(() => this._canAutoResize && !!this._pdf),
|
||||
takeUntil(this.destroy$)
|
||||
)
|
||||
.subscribe(() => {
|
||||
this.updateSize()
|
||||
})
|
||||
})
|
||||
}
|
||||
}
|
17
src-ui/src/app/components/common/pdf-viewer/typings.ts
Normal file
17
src-ui/src/app/components/common/pdf-viewer/typings.ts
Normal file
@@ -0,0 +1,17 @@
|
||||
export type PDFPageProxy =
|
||||
import('pdfjs-dist/types/src/display/api').PDFPageProxy
|
||||
export type PDFSource =
|
||||
import('pdfjs-dist/types/src/display/api').DocumentInitParameters
|
||||
export type PDFDocumentProxy =
|
||||
import('pdfjs-dist/types/src/display/api').PDFDocumentProxy
|
||||
export type PDFDocumentLoadingTask =
|
||||
import('pdfjs-dist/types/src/display/api').PDFDocumentLoadingTask
|
||||
export type PDFViewerOptions =
|
||||
import('pdfjs-dist/types/web/pdf_viewer').PDFViewerOptions
|
||||
|
||||
export interface PDFProgressData {
|
||||
loaded: number
|
||||
total: number
|
||||
}
|
||||
|
||||
export type ZoomScale = 'page-height' | 'page-fit' | 'page-width'
|
@@ -0,0 +1,182 @@
|
||||
/**
|
||||
* This file is taken and modified from https://github.com/VadimDez/ng2-pdf-viewer/blob/10.0.0/src/app/pdf-viewer/utils/event-bus-utils.ts
|
||||
* Created by vadimdez on 21/06/16.
|
||||
*/
|
||||
import { fromEvent, Subject } from 'rxjs'
|
||||
import { takeUntil } from 'rxjs/operators'
|
||||
|
||||
import type { EventBus } from 'pdfjs-dist/web/pdf_viewer'
|
||||
|
||||
// interface EventBus {
|
||||
// on(eventName: string, listener: Function): void;
|
||||
// off(eventName: string, listener: Function): void;
|
||||
// _listeners: any;
|
||||
// dispatch(eventName: string, data: Object): void;
|
||||
// _on(eventName: any, listener: any, options?: null): void;
|
||||
// _off(eventName: any, listener: any, options?: null): void;
|
||||
// }
|
||||
|
||||
export function createEventBus(pdfJsViewer: any, destroy$: Subject<void>) {
|
||||
const globalEventBus: EventBus = new pdfJsViewer.EventBus()
|
||||
attachDOMEventsToEventBus(globalEventBus, destroy$)
|
||||
return globalEventBus
|
||||
}
|
||||
|
||||
function attachDOMEventsToEventBus(
|
||||
eventBus: EventBus,
|
||||
destroy$: Subject<void>
|
||||
): void {
|
||||
fromEvent(eventBus, 'documentload')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(() => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('documentload', true, true, {})
|
||||
window.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'pagerendered')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ pageNumber, cssTransform, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('pagerendered', true, true, {
|
||||
pageNumber,
|
||||
cssTransform,
|
||||
})
|
||||
source.div.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'textlayerrendered')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ pageNumber, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('textlayerrendered', true, true, { pageNumber })
|
||||
source.textLayerDiv?.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'pagechanging')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ pageNumber, source }: any) => {
|
||||
const event = document.createEvent('UIEvents') as any
|
||||
event.initEvent('pagechanging', true, true)
|
||||
/* tslint:disable:no-string-literal */
|
||||
event['pageNumber'] = pageNumber
|
||||
source.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'pagesinit')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('pagesinit', true, true, null)
|
||||
source.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'pagesloaded')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ pagesCount, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('pagesloaded', true, true, { pagesCount })
|
||||
source.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'scalechange')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ scale, presetValue, source }: any) => {
|
||||
const event = document.createEvent('UIEvents') as any
|
||||
event.initEvent('scalechange', true, true)
|
||||
/* tslint:disable:no-string-literal */
|
||||
event['scale'] = scale
|
||||
/* tslint:disable:no-string-literal */
|
||||
event['presetValue'] = presetValue
|
||||
source.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'updateviewarea')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ location, source }: any) => {
|
||||
const event = document.createEvent('UIEvents') as any
|
||||
event.initEvent('updateviewarea', true, true)
|
||||
event['location'] = location
|
||||
source.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'find')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(
|
||||
({
|
||||
source,
|
||||
type,
|
||||
query,
|
||||
phraseSearch,
|
||||
caseSensitive,
|
||||
highlightAll,
|
||||
findPrevious,
|
||||
}: any) => {
|
||||
if (source === window) {
|
||||
return // event comes from FirefoxCom, no need to replicate
|
||||
}
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('find' + type, true, true, {
|
||||
query,
|
||||
phraseSearch,
|
||||
caseSensitive,
|
||||
highlightAll,
|
||||
findPrevious,
|
||||
})
|
||||
window.dispatchEvent(event)
|
||||
}
|
||||
)
|
||||
|
||||
fromEvent(eventBus, 'attachmentsloaded')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ attachmentsCount, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('attachmentsloaded', true, true, {
|
||||
attachmentsCount,
|
||||
})
|
||||
source.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'sidebarviewchanged')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ view, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('sidebarviewchanged', true, true, { view })
|
||||
source.outerContainer.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'pagemode')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ mode, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('pagemode', true, true, { mode })
|
||||
source.pdfViewer.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'namedaction')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ action, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('namedaction', true, true, { action })
|
||||
source.pdfViewer.container.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'presentationmodechanged')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ active, switchInProgress }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('presentationmodechanged', true, true, {
|
||||
active,
|
||||
switchInProgress,
|
||||
})
|
||||
window.dispatchEvent(event)
|
||||
})
|
||||
|
||||
fromEvent(eventBus, 'outlineloaded')
|
||||
.pipe(takeUntil(destroy$))
|
||||
.subscribe(({ outlineCount, source }: any) => {
|
||||
const event = document.createEvent('CustomEvent')
|
||||
event.initCustomEvent('outlineloaded', true, true, { outlineCount })
|
||||
source.container.dispatchEvent(event)
|
||||
})
|
||||
}
|
Reference in New Issue
Block a user