PDF.js专题

Stella981
• 阅读 854

前言

    英文是github上的原文,找不到中文资料,我根据自己理解翻译的,有些词意思拿不准就直接把单词留在原地了,看这个文档应该可以凑合着用了。

PDF.js是什么

    PDF.js is a Portable Document Format(PDF) viewer that is built with HTML5.PDF.js is community-driven and supportedby Mozilla Labs. Our goal is to create a general-purpose, web standards-basedplatform for parsing and rendering PDFs.

    PDF.js是一个由Html5建立的PDF阅读器。依托开源社区驱动和Mozilla实验室的技术支持。目标是建立一个通用的,基于web的解析和渲染PDF文件的平台。https://github.com/ChineseDron/pdf.js# 是从Mozilla原版中fork出来的一个版本,原版的链接在这里https://github.com/mozilla/pdf.js 原版的版次新一些,我们用原版。

PDF.js怎么用

    首先看一个demo:http://mozilla.github.io/pdf.js/web/viewer.html

    这个viewer我觉得就是PDF.js的最终UI。根据以往经验,网上能下载的demo,从来就没有见过能正常运行的,不过我还是抱着侥幸试了一下,PDF.js果然也不例外。从github上面我们可以下载PDF.js项目源代码,examples里有几个demo示例,helloworld运行就报错,此处省略研究过程1W字,大家只用看结论就可以了:IE9报错就升级的IE10,我也是试出来的,这个时候还不知道原因。其他的demo示例运行不是页面全黑就是全白,可以直接删了。

    Mozilla有一个比较简单的Pre-built版demo程序,改造一下就可以用了。

2.1 demo程序的结构翻译

build/

pdf.js

display layer

显示层采用核心层并且暴露了一个更容易使用的API来渲染PDF文件,并获得其他的资料出文件。该API基于不同的版本号而不同。

pdf.worker.js

core layer

core层是PDF解析和解释核心功能,是所有其它层的基础

web/

cmaps/

character maps(required by core)

字符映射(core层需要的资源)

compatibility.js

polyfills for missing features

Polyfilling 是由 RemySharp提出的一个术语,它是用来描述复制缺少的 API和API功能的行为。

09.pdf

test pdf

测试用的pdf文件

debugger.js

helpful pdf debugging features

images/

images for the viewer and annotation icons

viewer界面的图标

l10n.js

localization

locale/

translation files

翻译文件,包含所有支持语言的翻译资源

viewer.css

viewer style sheet

viewer界面的css

viewer.html

viewer html

viewer主界面

viewer.js

viewer layer

viewer界面的js,页面参数包括加载的PDF文件路径都在这里设置

2.2 我想只要满足下面两个要求就算大家可以用了

1.打开任意想打开的pdf文件(这就是github上的FAQ的第一个问题)

2.能够通过.net后台动态的控制与打开pdf有关的参数

第一个问题:

我们只用修改viewer.js文件中的pdf路径参数即可:

var DEFAULT_URL = '09.pdf';

如果pdf文件与viewer.html不在一层目录中,改成相对路径即可:

var DEFAULT_URL = ' ../doc/ 09.pdf';

第二个问题:

viewer.html可以通过页面参数传值的方式加载pdf文件,比如我们想打开09.pdf文件的话,只需要这样:

先把viewer.js中的参数修改为空:

var DEFAULT_URL = '';

然后把url改写为参数传值:

http://localhost:54175/PDFJSInNet/web/viewer.html?file=09.pdf

如果pdf文件与viewer.html不在一层目录中,改成相对路径即可:

http://localhost:54175/PDFJSInNet/web/viewer.html?file=../doc/09.pdf

非常容易通过Visual Studio控制后台代码动态拼出这样一个url字符串。

2.3 补充

viewer的demo程序示例的toolbar工具比较全,第二个是打印第三个是下载,如果我们只想做在线阅读,不许用户打印或者下载文档的话,把这两个按钮隐藏掉或者删掉即可,在viewer.html源码第180行186行

2.4 再补充

    viewer在解析和渲染pdf的时候有点耗费系统资源,尤其是cpu资源,不知道是不是因为我的本子配置较低的缘故,在页面加载等待的过程中,IE进程消耗掉了CPU资源的50-60%。点击翻页操作,或者改变IE的窗口大小会触发viewer对pdf进行重新解析和渲染。有时把IE前端的某个挡住他的程序窗口(比如一个txt)移开也会导致重新渲染,但是并不是每次都会触发,原因不详。

    如果在viewer解析和渲染的过程中尝试用adobe reader之类的工具打开那个pdf文件,系统会出现第二个iexplore.exe *32的进程,有时是AcroRd32.exe *32进程,两个进程加一起几乎耗去了100%的CPU资源,此时机器已经显得比较卡了。多点两下就会出现页面未响应,但是一般情况下是假死,等几秒就会活过来,我试了很多次还没有遇到真死的情况。

    我用一个7M大的PDF测试了一下速度,能感觉出解析和渲染的时间变长了,但是时间还没有长到不能忍受(FAQ里的最后一个问题有提到)

官方上的FAQ

我只选取了我认为可以用得到的问题。

Can Ispecify a different PDF in the default viewer?可以指定一个不同的PDF文件给viewer打开吗?

You canmodify the DEFAULT_URL variable in the web/viewer.js file or you can append the ?file= query string to the viewer URL, e.g.http://mozilla.github.com/pdf.js/web/viewer.html?file=compressed.tracemonkey-pldi-09.pdf.

在2.2章节已经回答了。

Can I load a PDF fromanother server (cross domain request)?能否从其它服务器读取pdf文件(跨域访问)?

Notby default, but it is possible. PDF.js runs with the same permissions as anyother JavaScript code, which means it cannot do cross origin requests (see Same origin policy and an example).There are some possible ways to get around this such as using CORS (seealso unsafeheaders issue and Access-Control-Expose-Headersissue) or setting up a proxy on your server thatwill feed PDF.js the PDF file. Both workarounds are out of the scope of thePDF.js project and we will not provide code to do either.

不默认,但它是可能的。 PDF.js运行具有相同权限的任何其他JavaScript代码,这意味着它不能跨出自身请求(见同根同源的政策和示例) 。有一些可能的方法来解决这个问题,如使用CORS (seealso unsafe headers issue and Access-Control-Expose-Headersissue),或者设置你的服务器上的代理,将PDF文件提供给PDF.js。这两种解决方法都出了PDF.js项目的范围,我们将不提供代码,请执行。

What browsers are supported?支持哪些浏览器?

The goal is to support all HTML5 compliant browsers, but sincefeature support varies per browser/version our support for all PDF featuresvaries as well. If you want to support more browsers than Firefox you'll needto include compatibility.jswhich has polyfills for missing features. Find the list offeatures needed for PDF.js to properly work and browser tests for thosefeatures at RequiredBrowser Features. In general, the support is below:

我们的目标是支持所有HTML5兼容的浏览器,但是每个浏览器/版本对PDF的所有特性的支持是不同的。如果你想支持除了Firefox以外的更多种浏览器,你需要有compatibility.js文件,它有polyfills丢失的功能。想查找PDF.js正常工作所需的浏览器的测试要求,请参考如下浏览器特性的列表:

Browser

Supported

Automated Testing

Notes

Firefox Stable

yes

Windows and Linux

Chrome Stable

yes

Windows and Linux

Opera Stable

yes

none

Android

limited

none

Android's Web Browser version 4.0 or below lacks a number of features or has defects, e.g. in typed arrays or HTTP range requests

Safari

limited

none

Safari (desktop and mobile) lacks a number of features or has defects, e.g. in typed arrays or HTTP range requests

IE9

limited

none

IE9 lacks a number of features and most notably typed arrays which causes subpar performance.

IE9缺少了一些功能和最显着的类型化数组,支持性表现欠佳,我想到了之前运行出错的helloworld....

<=IE8

NO

none

IE8 and below are missing too many features to be supported.

IE8及以下缺失太多的功能特性以至于无法得到支持。

Is it possible to add annotations to aPDF?是否可以向pdf文件添加注解?

PDF.js is mainly written for reading PDF files, not editing them. Becauseof that we don't yet support adding any kind of annotations. We do howeversupport rendering a number of annotation types for viewing.

PDF.js主要是写阅读PDF文件,而不是编辑它们。正因为如此,我们还不支持添加任何注释。然而,我们也支持渲染一些注释类型以供查看。

The PDF.js files are too big. Can you provide minified versions ofJS files?PDF.js文件太大,可以提供缩小版的js文件吗files?

仅为google编译器(GoogleClosure Compiler)提供

I know that my PDFs arecorrupted.Will PDF.js attempt to display it?

Yes. PDF.js will attempt to recover usable PDF data (pages,content or fonts) and display the document. Please report the issue (see above)and we will take a look.

是。PDF.js将尝试恢复可用的PDF数据(页,内容或字体),并显示文档。

What types of PDF files are slow in PDF.js? Can I optimize a PDFfile to make PDF.js faster?什么样的pdf文件会导致PDF.js运行速度减慢,是否可以优化pdf文件使PDF.js速度变快?

Typically, PDFs with a smaller filesize will be rendered faster and it depends on how big a single page is. Theamount of pages does not affect the performance. It's essential that youoptimize your documents for the web. See Optimize a PDFfromAdobe's website for more information. There are more improvement techniquesthat we can suggest:

  1. Avoid using high resolution images -- 150 dpi resolution for scanned images shall be enough for screens, especially for low powered devices;
  2. Try to use JPEG encoding for color images/photos inRGB colorspacewhen possible;
  3. Avoid using expensive compositions/effects such as transitions/masking --flatten transparency;
  4. Avoid using PDF generators (or don't create content) that produce ineffective PDF output (e.g. LibreOffice creates a lots of tiny images for vector elements/pictures it does not understand);
  5. If there is such a setting, use web-optimized PDF output / linearization;
  6. Fix or don't produce corrupted PDFs that do not conform to the PDF32000 specification.

通常情况下, PDF文件以更小的文件大小将变得更快,这取决于单页(数据量?)有多大。还有更多的改进技术,我们可以建议:
1.避免使用高清晰度的图像- 建议不超过150dpi的分辨率的扫描图像,尤其是对于低功率设备;
2.如果可能的话,尝试使用JPEG编码的彩色图像或者是RGB色彩的照片;
3.避免使用华丽的成分/效果,如转换/屏蔽- 拼合透明度;
4.避免使用PDF生成器(或者不创造内容)产生无效的PDF输出(如LibreOffice中创建大量的微小的图像,矢量元素/图片);
5.使用的网络优化格式的PDF;
6.修复或不产生不符合PDF32000规范的PDF文件。

回答网友提问  2015-1-19

chrome是可以通过参数传值方式打开PDF的,我用的版本是39.0.2171.95 m

PDF.js专题

回答网友提问  2015-7-28

因为好多人问能不能显示中文的问题,我总结大致分为两类问题:

1.能否显示中文?2.能否读取远程服务器上的PDF(包括中文文件名)

第一个问题:能否显示中文?

首先,显示中文肯定是可以的,不论是文件名还是文件的正文,见下图:

PDF.js专题

如果你说显示不出中文,我想是不是下面这种情况:

PDF.js专题

这属于js中文乱码问题,你看中文文件名完全没有识别出来,看一下你的viewer.html文件在标记是不是有这句:

换成:  就可以啦!说白了就是charset换成gb2312

第一个问题over。

第二个问题:能否读取远程服务器上的PDF(包括中文文件名)

我们哆嗦一点,从头说起,首先用mozilla的example证明读取远程服务器上的pdf绝对没有问题,见下图

读取http://mozilla.github.io/pdf.js/web/compressed.tracemonkey-pldi-09.pdf

PDF.js专题

然后我换成公司服务器上的pdf文件地址,运行,如下图所示,我想大多数人遇到的都是这个问题。

PDF.js专题

这个问题简单说就是跨域访问,其实mozilla的example里有一段声明提到了这个问题,只是这个声明不那么显眼,在helloworld.html中,见下图

PDF.js专题

(CORS) - most servers don't support cross-origin browser requests.  

CORS就是跨域访问,大多数服务器都不支持跨域访问。

要解决跨域访问问题,有很多解决方案,由于能力有限,那些好复杂的处理办法我还完全不懂,不过我百度的水平还是一流的,下面这个链接就是处理这个问题的简单方法,无奈中文资料太少。http://www.webdavsystem.com/ajax/programming/cross\_origin\_requests

如果看不懂英文,我翻译过来就是一张图

PDF.js专题

设置完毕后再运行:成功,跨域访问问题顺利解决,见下图。第二个问题OVER。

PDF.js专题

关于7.28第二个问题的延伸,同事帮助解决了一个小细节 2015-11-17

同事使用的时候发现一个小问题,跨域访问按照我所说的问题2设置了还是不行(IE浏览器),但是用搜狗浏览器极速模式就可以,于是采取了如下办法问题解决:在页面添加  

demo程序下载链接

http://download.csdn.net/detail/xiangcns/8946311

点赞
收藏
评论区
推荐文章
blmius blmius
3年前
MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1
文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s
皕杰报表之UUID
​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为
待兔 待兔
5个月前
手写Java HashMap源码
HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22
Jacquelyn38 Jacquelyn38
3年前
2020年前端实用代码段,为你的工作保驾护航
有空的时候,自己总结了几个代码段,在开发中也经常使用,谢谢。1、使用解构获取json数据let jsonData  id: 1,status: "OK",data: 'a', 'b';let  id, status, data: number   jsonData;console.log(id, status, number )
Easter79 Easter79
3年前
Twitter的分布式自增ID算法snowflake (Java版)
概述分布式系统中,有一些需要使用全局唯一ID的场景,这种时候为了防止ID冲突可以使用36位的UUID,但是UUID有一些缺点,首先他相对比较长,另外UUID一般是无序的。有些时候我们希望能使用一种简单一些的ID,并且希望ID能够按照时间有序生成。而twitter的snowflake解决了这种需求,最初Twitter把存储系统从MySQL迁移
Wesley13 Wesley13
3年前
mysql设置时区
mysql设置时区mysql\_query("SETtime\_zone'8:00'")ordie('时区设置失败,请联系管理员!');中国在东8区所以加8方法二:selectcount(user\_id)asdevice,CONVERT\_TZ(FROM\_UNIXTIME(reg\_time),'08:00','0
Wesley13 Wesley13
3年前
00:Java简单了解
浅谈Java之概述Java是SUN(StanfordUniversityNetwork),斯坦福大学网络公司)1995年推出的一门高级编程语言。Java是一种面向Internet的编程语言。随着Java技术在web方面的不断成熟,已经成为Web应用程序的首选开发语言。Java是简单易学,完全面向对象,安全可靠,与平台无关的编程语言。
Stella981 Stella981
3年前
Django中Admin中的一些参数配置
设置在列表中显示的字段,id为django模型默认的主键list_display('id','name','sex','profession','email','qq','phone','status','create_time')设置在列表可编辑字段list_editable
Wesley13 Wesley13
3年前
MySQL部分从库上面因为大量的临时表tmp_table造成慢查询
背景描述Time:20190124T00:08:14.70572408:00User@Host:@Id:Schema:sentrymetaLast_errno:0Killed:0Query_time:0.315758Lock_
Python进阶者 Python进阶者
11个月前
Excel中这日期老是出来00:00:00,怎么用Pandas把这个去除
大家好,我是皮皮。一、前言前几天在Python白银交流群【上海新年人】问了一个Pandas数据筛选的问题。问题如下:这日期老是出来00:00:00,怎么把这个去除。二、实现过程后来【论草莓如何成为冻干莓】给了一个思路和代码如下:pd.toexcel之前把这