{"id":14973184,"url":"https://github.com/vadimdez/ng2-pdf-viewer","last_synced_at":"2025-05-13T15:09:10.458Z","repository":{"id":9358422,"uuid":"61661161","full_name":"VadimDez/ng2-pdf-viewer","owner":"VadimDez","description":"📄 PDF Viewer Component for Angular","archived":false,"fork":false,"pushed_at":"2025-04-16T15:26:19.000Z","size":104821,"stargazers_count":1325,"open_issues_count":96,"forks_count":427,"subscribers_count":30,"default_branch":"master","last_synced_at":"2025-05-08T20:18:42.017Z","etag":null,"topics":["angular","angular12","angular2","pdf","pdf-viewer","pdf-viewer-component"],"latest_commit_sha":null,"homepage":"https://vadimdez.github.io/ng2-pdf-viewer/","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/VadimDez.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":".github/FUNDING.yml","license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null},"funding":{"custom":["https://paypal.me/vadimdez"]}},"created_at":"2016-06-21T19:27:57.000Z","updated_at":"2025-05-07T14:07:06.000Z","dependencies_parsed_at":"2024-05-07T23:29:34.057Z","dependency_job_id":"31e86c1d-7690-4630-beef-50d17fec8afe","html_url":"https://github.com/VadimDez/ng2-pdf-viewer","commit_stats":{"total_commits":875,"total_committers":57,"mean_commits":"15.350877192982455","dds":"0.21942857142857142","last_synced_commit":"039184176404df62ee725ad97cf6b2fef371e498"},"previous_names":[],"tags_count":103,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/VadimDez%2Fng2-pdf-viewer","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/VadimDez%2Fng2-pdf-viewer/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/VadimDez%2Fng2-pdf-viewer/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/VadimDez%2Fng2-pdf-viewer/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/VadimDez","download_url":"https://codeload.github.com/VadimDez/ng2-pdf-viewer/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":253969238,"owners_count":21992262,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["angular","angular12","angular2","pdf","pdf-viewer","pdf-viewer-component"],"created_at":"2024-09-24T13:48:18.080Z","updated_at":"2025-05-13T15:09:05.439Z","avatar_url":"https://github.com/VadimDez.png","language":"TypeScript","funding_links":["https://paypal.me/vadimdez","https://www.paypal.me/vadimdez"],"categories":[],"sub_categories":[],"readme":"\u003ch1 align=\"center\"\u003eAngular PDF Viewer\u003c/h1\u003e\n\u003cp align=\"center\"\u003e\n  \u003ca href=\"https://www.npmjs.com/package/ng2-pdf-viewer\"\u003e\n    \u003cimg src=\"https://img.shields.io/npm/dm/ng2-pdf-viewer.svg?style=flat\" alt=\"downloads\"\u003e\n  \u003c/a\u003e\n  \u003ca href=\"https://badge.fury.io/js/ng2-pdf-viewer\"\u003e\n    \u003cimg src=\"https://badge.fury.io/js/ng2-pdf-viewer.svg\" alt=\"npm version\"\u003e\n  \u003c/a\u003e\n  \u003ca href=\"https://gitter.im/ngx-pdf-viewer/Lobby\" title=\"Gitter\"\u003e\n    \u003cimg src=\"https://img.shields.io/gitter/room/nwjs/nw.js.svg\" alt=\"Gitter\"/\u003e\n  \u003c/a\u003e\n  \u003ca href=\"https://www.paypal.me/vadimdez\" title=\"Donate to this project using Paypal\"\u003e\n    \u003cimg src=\"https://img.shields.io/badge/paypal-donate-yellow.svg\" alt=\"PayPal donate button\" /\u003e\n  \u003c/a\u003e\n\u003c/p\u003e\n\n\u003e PDF Viewer Component for Angular 5+\n\n### Demo page\n\n[https://vadimdez.github.io/ng2-pdf-viewer/](https://vadimdez.github.io/ng2-pdf-viewer/)\n\n#### Stackblitz Example\n\n[https://stackblitz.com/edit/ng2-pdf-viewer](https://stackblitz.com/edit/ng2-pdf-viewer)\n\n### Blog post\n\n[https://medium.com/@vadimdez/render-pdf-in-angular-4-927e31da9c76](https://medium.com/@vadimdez/render-pdf-in-angular-4-927e31da9c76)\n\n## Overview\n\n* [Install](#install)\n* [Usage](#usage)\n* [Options](#options)\n* [Render local PDF file](#render-local-pdf-file)\n* [Set custom path to the worker](#set-custom-path-to-the-worker)\n* [Search in the PDF](#search-in-the-pdf)\n* [Contribute](#contribute)\n\n## Install\n\n### Angular \u003e= 12\n```\nnpm install ng2-pdf-viewer\n```\n\u003e Partial Ivy compilated library bundles.\n\n### Angular \u003e= 4\n```\nnpm install ng2-pdf-viewer@^7.0.0\n```\n\n### Angular \u003c 4\n```\nnpm install ng2-pdf-viewer@~3.0.8\n```\n\n## Usage\n\n*In case you're using ```systemjs``` see configuration [here](https://github.com/VadimDez/ng2-pdf-viewer/blob/master/SYSTEMJS.md).*\n\nAdd ```PdfViewerModule``` to your module's ```imports```\n\n```typescript\nimport { NgModule } from '@angular/core';\nimport { BrowserModule } from '@angular/platform-browser';\nimport { AppComponent } from './app/app.component';\n\nimport { PdfViewerModule } from 'ng2-pdf-viewer';\n\n@NgModule({\n  imports: [BrowserModule, PdfViewerModule],\n  declarations: [AppComponent],\n  bootstrap: [AppComponent]\n})\n\nclass AppModule {}\n\nplatformBrowserDynamic().bootstrapModule(AppModule);\n```\n\nAnd then use it in your component\n\n```typescript\nimport { Component } from '@angular/core';\n\n@Component({\n  selector: 'example-app',\n  template: `\n  \u003cpdf-viewer [src]=\"pdfSrc\"\n              [render-text]=\"true\"\n              [original-size]=\"false\"\n              style=\"width: 400px; height: 500px\"\n  \u003e\u003c/pdf-viewer\u003e\n  `\n})\nexport class AppComponent {\n  pdfSrc = \"https://vadimdez.github.io/ng2-pdf-viewer/assets/pdf-test.pdf\";\n}\n```\n\n## Options\n\n* [[src]](#src)\n* [[(page)]](#page)\n* [[stick-to-page]](#stick-to-page)\n* [[external-link-target]](#external-link-target)\n* [[render-text]](#render-text)\n* [[render-text-mode]](#render-text-mode)\n* [[rotation]](#rotation)\n* [[zoom]](#zoom)\n* [[zoom-scale]](#zoom-scale)\n* [[original-size]](#original-size)\n* [[fit-to-page]](#fit-to-page)\n* [[show-all]](#show-all)\n* [[autoresize]](#autoresize)\n* [[c-maps-url]](#c-maps-url)\n* [[show-borders]](#show-borders)\n* [(after-load-complete)](#after-load-complete)\n* [(page-rendered)](#page-rendered)\n* [(text-layer-rendered)](#text-layer-rendered)\n* [(error)](#error)\n* [(on-progress)](#on-progress)\n\n#### [src]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [src] | *string, object, UInt8Array* | Required |\n\nPass pdf location\n\n```\n[src]=\"'https://vadimdez.github.io/ng2-pdf-viewer/assets/pdf-test.pdf'\"\n```\n\nFor more control you can pass options object to ```[src]```. [See other attributes for the object here](https://github.com/mozilla/pdf.js/blob/master/src/display/api.js#L130-L222).\n\nOptions object for loading protected PDF would be:\n\n ```js\n {\n  url: 'https://vadimdez.github.io/ng2-pdf-viewer/assets/pdf-test.pdf',\n  withCredentials: true\n }\n ```\n\n#### [page]\n\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [page] or [(page)] | *number* | *Required* with [show-all]=\"false\" or *Optional* with [show-all]=\"true\" |\n\nPage number\n\n```\n[page]=\"1\"\n```\nsupports two way data binding as well\n```\n[(page)]=\"pageVariable\"\n```\n\nIf you want that the `two way data binding` actually updates your `page` variable on page change/scroll - you have to be sure that you define the height of the container, for example:\n```css\npdf-viewer {\n    height: 100vh;\n}\n```\n\n#### [stick-to-page]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [stick-to-page] | *boolean* | *Optional* |\n\nSticks view to the page. Works in combination with `[show-all]=\"true\"` and `page`.\n\n```\n[stick-to-page]=\"true\"\n```\n\n#### [render-text]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [render-text] | *boolean* | *Optional* |\n\nEnable text rendering, allows to select text\n```\n[render-text]=\"true\"\n```\n\n#### [render-text-mode]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [render-text-mode] | *RenderTextMode* | *Optional* |\n\nUsed in combination with `[render-text]=\"true\"`\n\nControls if the text layer is enabled, and the selection mode that is used.\n\n`0 = RenderTextMode.DISABLED` - disable the text selection layer\n\n`1 = RenderTextMode.ENABLED` - enables the text selection layer\n\n`2 = RenderTextMode.ENHANCED` - enables enhanced text selection\n\n```\n[render-text-mode]=\"1\"\n```\n\n#### [external-link-target]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [external-link-target] | *string* | *Optional* |\n\nUsed in combination with `[render-text]=\"true\"`\n\nLink target\n* `blank`\n* `none`\n* `self`\n* `parent`\n* `top`\n```\n[external-link-target]=\"'blank'\"\n```\n\n#### [rotation]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [rotation] | *number* | *Optional* |\n\nRotate PDF\n\n*Allowed step is 90 degree, ex. 0, 90, 180*\n```\n[rotation]=\"90\"\n```\n\n#### [zoom]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [zoom] | *number* | *Optional* |\n\nZoom pdf\n```\n[zoom]=\"0.5\"\n```\n\n#### [zoom-scale]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [zoom-scale] | *'page-width'\\|'page-fit'\\|'page-height'* | *Optional* |\n\nDefines how the Zoom scale is computed when  `[original-size]=\"false\"`, by default set to 'page-width'.\n\n- *'page-width'* with zoom of 1 will display a page width that take all the possible horizontal space in the container\n\n- *'page-height'* with zoom of 1 will display a page height that take all the possible vertical space in the container\n\n- *'page-fit'* with zoom of 1 will display a page that will be scaled to either width or height to fit completely in the container\n\n```\n[zoom-scale]=\"'page-width'\"\n```\n\n#### [original-size]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [original-size] | *boolean* | *Optional* |\n\n* if set to *true* - size will be as same as original document\n* if set to *false* - size will be as same as container block\n\n```\n[original-size]=\"true\"\n```\n\n#### [fit-to-page]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [fit-to-page] | *boolean* | *Optional* |\n\nWorks in combination with `[original-size]=\"true\"`. You can show your document in original size, and make sure that it's not bigger then container block.\n\n```\n[fit-to-page]=\"false\"\n```\n\n#### [show-all]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [show-all] | *boolean* | *Optional* |\n\nShow single or all pages altogether\n\n```\n[show-all]=\"true\"\n```\n\n#### [autoresize]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [autoresize] | *boolean* | *Optional* |\n\nTurn on or off auto resize.\n\n**!Important** To make `[autoresize]` work - make sure that `[original-size]=\"false\"` and `pdf-viewer` tag has `max-width` or `display` are set.\n\n```\n[autoresize]=\"true\"\n```\n\n#### [c-maps-url]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [c-maps-url] | *string* | Optional |\n\nUrl for non-latin characters source maps.\n```\n[c-maps-url]=\"'assets/cmaps/'\"\n```\n\nDefault url is: [https://unpkg.com/pdfjs-dist@2.0.550/cmaps/](https://unpkg.com/pdfjs-dist@2.0.550/cmaps/)\n\nTo serve cmaps on your own you need to copy ```node_modules/pdfjs-dist/cmaps``` to ```assets/cmaps```.\n\n### [show-borders]\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| [show-borders] | *boolean* | Optional |\n\nShow page borders\n```\n[show-borders]=\"true\"\n```\n\n#### (after-load-complete)\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| (after-load-complete) | *callback* | *Optional* |\n\nGet PDF information with callback\n\nFirst define callback function \"callBackFn\" in your controller,\n```typescript\ncallBackFn(pdf: PDFDocumentProxy) {\n   // do anything with \"pdf\"\n}\n```\n\nAnd then use it in your template:\n```\n(after-load-complete)=\"callBackFn($event)\"\n```\n\n#### (page-rendered)\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| (page-rendered) | *callback* | *Optional* |\n\nGet event when a page is rendered. Called for every page rendered.\n\nDefine callback in your component:\n\n```typescript\npageRendered(e: CustomEvent) {\n  console.log('(page-rendered)', e);\n}\n```\n\nAnd then bind it to `\u003cpdf-viewer\u003e`:\n\n```angular2html\n(page-rendered)=\"pageRendered($event)\"\n```\n\n#### (pages-initialized)\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| (pages-initialized) | *callback* | *Optional* |\n\nGet event when the pages are initialized.\n\nDefine callback in your component:\n\n```typescript\npageInitialized(e: CustomEvent) {\n  console.log('(pages-initialized)', e);\n}\n```\n\nAnd then bind it to `\u003cpdf-viewer\u003e`:\n\n```angular2html\n(pages-initialized)=\"pageInitialized($event)\"\n```\n\n#### (text-layer-rendered)\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| (text-layer-rendered) | *callback* | *Optional* |\n\nGet event when a text layer is rendered.\n\nDefine callback in your component:\n\n```typescript\ntextLayerRendered(e: CustomEvent) {\n  console.log('(text-layer-rendered)', e);\n}\n```\n\nAnd then bind it to `\u003cpdf-viewer\u003e`:\n\n```angular2html\n(text-layer-rendered)=\"textLayerRendered($event)\"\n```\n\n#### (error)\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| (error) | *callback* | *Optional* |\n\nError handling callback\n\nDefine callback in your component's class\n\n```typescript\nonError(error: any) {\n  // do anything\n}\n```\n\nThen add it to `pdf-component` in component's template\n\n```html\n(error)=\"onError($event)\"\n```\n\n#### (on-progress)\n\n| Property | Type | Required |\n| --- | ---- | --- |\n| (on-progress) | *callback* | *Optional* |\n\nLoading progress callback - provides progress information `total` and `loaded` bytes. Is called several times during pdf loading phase.\n\nDefine callback in your component's class\n\n```typescript\nonProgress(progressData: PDFProgressData) {\n  // do anything with progress data. For example progress indicator\n}\n```\n\nThen add it to `pdf-component` in component's template\n\n```html\n(on-progress)=\"onProgress($event)\"\n```\n\n## Render local PDF file\n\nIn your `html` template add `input`:\n\n```html\n\u003cinput (change)=\"onFileSelected()\" type=\"file\" id=\"file\"\u003e\n```\n\nand then add `onFileSelected` method to your component:\n\n```typescript\nonFileSelected() {\n  let $img: any = document.querySelector('#file');\n\n  if (typeof (FileReader) !== 'undefined') {\n    let reader = new FileReader();\n\n    reader.onload = (e: any) =\u003e {\n      this.pdfSrc = e.target.result;\n    };\n\n    reader.readAsArrayBuffer($img.files[0]);\n  }\n}\n```\n\n\n## Set custom path to the worker\n\nBy default the `worker` is loaded from `cdn.jsdelivr.net`.\n\nIn your code update `path` to the worker to be for example `/pdf.worker.mjs`\n```typescript\n(window as any).pdfWorkerSrc = '/pdf.worker.mjs';\n```\n\n*This should be set before `pdf-viewer` component is rendered.*\n\nIf you ever have a (super rare) edge case where you run in an environment that multiple\ncomponents are somehow loaded within the same web page, sharing the same window,\nbut using different versions of pdf.worker, support has been added.  You can do the\nabove, except that you can append the specific version of pdfjs required and override the\ncustom path *just for that version*.  This way setting the global window var won't conflict.\n```typescript\n(window as any)[\"pdfWorkerSrc2.14.305\"] = '/pdf.worker.mjs';\n```\n\n## Search in the PDF\n\nUse `eventBus` for the search functionality.\n\nIn your component's ts file:\n\n* Add reference to `pdf-viewer` component,\n* then when needed execute `search()` like this:\n\n```typescript\n@ViewChild(PdfViewerComponent) private pdfComponent: PdfViewerComponent;\n\nsearch(stringToSearch: string) {\n  this.pdfComponent.eventBus.dispatch('find', {\n    query: stringToSearch, type: 'again', caseSensitive: false, findPrevious: undefined, highlightAll: true, phraseSearch: true\n  });\n}\n```\n\n## Contribute\n[See CONTRIBUTING.md](CONTRIBUTING.md)\n\n## Donation\nIf this project help you reduce time to develop, you can give me a cup of tea :)\n\n[![paypal](https://www.paypalobjects.com/en_US/i/btn/btn_donateCC_LG.gif)](https://www.paypal.me/vadimdez)\n\n## License\n\n[MIT](https://tldrlegal.com/license/mit-license) © [Vadym Yatsyuk](https://github.com/vadimdez)\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fvadimdez%2Fng2-pdf-viewer","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fvadimdez%2Fng2-pdf-viewer","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fvadimdez%2Fng2-pdf-viewer/lists"}