PDF预览完整解决方案及各种兼容(VUE版)

news/2024/5/22 10:59:04/文章来源:https://blog.csdn.net/m0_48486615/article/details/128034797

PDF预览完整解决方案及各种兼容(VUE版)

PDF预览完整解决方案及各种兼容(VUE版) - 掘金

前端学习使者正在上传…重新上传取消

2021年11月12日 16:57 ·  阅读 2547

一、利用iframe

就一行代码就够了,只能满足最基本的浏览,且会出现很多问题。

<iframe src="Url" style="width:100%;height:100%" frameborder="0"></iframe>
复制代码

**问题一缓存问题:**利用iframe打开pdf后,当再次利用iframe打开另一个pdf时会显示第一份pdf,原因是浏览器对url的缓存处理。

**解决办法:**给url加时间戳或随机数,这样就没有缓存问题了。

    const fresh=new Date().getTime();//时间戳    this.url = this.url+'?'+ fresh; // 初始化查看pdf应用地址
复制代码

**问题二使用base64url问题:**有些pdf的url采用base64格式,直接将base64格式url放进src中可能会报错导致显示不了。原因是base64地址太长,浏览器不支持。

**解决办法:**利用Blob转base64url成文件路径.

  var bstr = window.atob(_this.baseUrl); //解码  var n = bstr.length;  var u8arr = new Uint8Array(n);  while (n--) {  u8arr[n] = bstr.charCodeAt(n); //转二进制  }  let blob = new Blob([u8arr], { type: 'application/pdf' }); //用blob生成pdf文件,返回PDF文件  this.url = window.URL.createObjectURL(blob); //得到的文件路径url
复制代码

**问题三特殊字体和水印无法显示:**这里采用插件的形式解决

二、利用vue-pdf插件

这里以VUE框架为例。vue-pdf是基于pdfjs-dist插件的vue封装。不是vue框架可以去找pdfjs-dist对应的封装或者直接用pdfjs-dist,不过pdfjs-dist使用稍微复杂些。

第一步 安装 npm install --save vue-pdf
第二部引入注册 
import VuePdf from "vue-pdf";
export default {
components: {
VuePdf,
},
第三步 使用
<VuePdf  src="PDFurl" : />
上面是最简单的使用方式,只能显示第一页的pdf,满足不了大部分需求,现在增加功能模板里
<VuePdf  v-for="i in numPages" :key="i" :src="url" :page="i" />
下面方法在mounted里面使用// PDF初始化    getNumPages() {      let loadingTask = VuePdf.createLoadingTask(this.url,      );      loadingTask.promise.then(pdf => {        this.numPages = pdf.numPages;      }).catch(err => {        console.error('pdf 加载失败', err);      })    },numPages、url在data里面定义为空,在getNumPages()调用前将路径赋值给this.url
复制代码

这样就可以得到一个可以pdf的全部内容,pdf放大缩小翻页就不赘述了百度很多

PDF下载

<div @click="down(pdfName)">下载</div>
//需要两个参数 pdfName 和 pdf的base64地址。
在调用方法前将pdf的base64地址赋值给this.baseUrl就可以调用方法下载。down(pdfName){      
const fileName = pdfName;      
let byteCharacters = atob(this.baseUrl);      
let byteNumbers = new Array (byteCharacters.length);      
for (var i = 0; i < byteCharacters.length; i++) {        
byteNumbers[i] = byteCharacters.charCodeAt(i);      
}      
let byteArray = new Uint8Array ( byteNumbers);       
let blob = new Blob([byteArray], { type:"application/pdf"});      
if (navigator.msSaveOrOpenBlob) {         
navigator.msSaveBlob(blob,fileName);      
}else{        
let link = document.createElement("a");        
link.href = window.URL.createObjectURL(blob);        
link.download = fileName;        
document.body.appendChild(link);        
link.click();        
document.body.removeChild(link);        
window.URL.revokeObjectURL(link.href);      
}    
},
复制代码

VUE-PDF出现问题一:部分pdf水印不显示

解决办法
+ 步骤一 在node_modules/pdfjs-dist/build/pdf.worker.js注释掉一行代码
+ if (data.fieldType === "Sig") {
+      data.fieldValue = null;+      // 注释掉底下这行 就可以显示电子签章
+      // this.setFlags(_util.AnnotationFlag.HIDDEN);+ }
+ 步骤二 在node_modules/pdfjs-dist/es5/build/pdf.worker.js注释掉一行代码
+ if (data.fieldType === "Sig") {+    data.fieldValue = null;
+      // 注释掉底下这行 就可以显示电子签章+      // _this4.setFlags(_util.AnnotationFlag.HIDDEN);
+  }
复制代码

问题又来了,在node_modules里面改动文件下一次打包或者项目上线就行不通了。

这里采用把vue-pdf项目文件放在服务器tomcat的一个文件夹下。项目里用iframe来直接跳转的形式来显示

<iframe  :src="iframeUrl" frameborder="0"></iframe>    
const fresh=new Date().getTime();//时间戳    
this.iframeUrl = location.origin + "/pdf/index.html"+'?'+ fresh; // 初始化查看pdf应用地址
复制代码

那么在服务器下的vue-pdf文件如何得到项目上传过来的PDF信息呢,这里采用indexDB数据库。这里不推荐使用cookies和localStorage的形式存储数据,因为PDF数据可能会很大,另外两种形式容量不够。

IndexDB存储PDF需要的信息

     在上线项目里使用/**          *@param url pdf地址          
*@param baseUrl pdfbase64地址          
* @param fileName 文件名          
**/        
setIndexDB(url,baseUrl,fileName){            
// 创建indexDB数据库          //pdfDB          
var request = window.indexedDB.open('pdfData');          
request.onerror = function() {                  
console.log('数据库打开失败');          };            
request.onsuccess = function(e) {              
var pdfDB= e.target.result;              
var store = pdfDB.transaction('workers','readwrite').objectStore('workers');               
store.put({ id: 1, pdfUrl: url,baseUrl:baseUrl,pdfName:fileName});            
};            
request.onupgradeneeded =  function(e){                
// 在数据库中创建该对象空间,workers相当于表的名字                
e.target.result.createObjectStore('workers', {keyPath:'id'});            
}          
},
复制代码

在vue-pdf里面获取存储的数据

    getPdfUrl() {      const _this = this;      const request = window.indexedDB.open("pdfData");      request.onerror = function () {        console.log("数据库打开失败");      };      request.onsuccess = function (e) {        //  var store = e.target.result.transaction('workers','readwrite').objectStore('workers');        //  store.put({id:1,pdfUrl:"2.pdf",pdfName:"",baseUrl:"",pathType:"路径形式"})       const readPDF = e.target.result          .transaction(["workers"])          .objectStore("workers")          .get(1);        readPDF.onsuccess = () => {          if (readPDF.result) {            _this.url = readPDF.result.pdfUrl;            _this.baseUrl = readPDF.result.baseUrl;            _this.pdfName = readPDF.result.pdfName;              var bstr = window.atob(_this.baseUrl); //解码              var n = bstr.length;              var u8arr = new Uint8Array(n);              while (n--) {              u8arr[n] = bstr.charCodeAt(n); //转二进制              }              let blob = new Blob([u8arr], { type: 'application/pdf' }); //用blob生成pdf文件,返回PDF文件              let path = window.URL.createObjectURL(blob);              _this.iframeUrl = path; // 初始化查看pdf应用地址              _this.getNumPages();                      } else {            console.log("未获得数据记录");          }        };      };      request.onupgradeneeded = function (e) {        // 在数据库中创建该对象空间,workers相当于表的名字,表名不可随意更改        e.target.result.createObjectStore("workers", { keyPath: "id" });      };    },
复制代码

具体indexDB看文档www.ruanyifeng.com/blog/2018/0…

vue-pdf项目例子看gitee.com/tianguai/vu…

问题二:字体缺失

VUE-PDF会有一些特殊字体显示不了,这是由于node_modules/pdfjs-dist/cmaps路径下没有对应的字体文件

解决方法:在vue-pdf项目例子中加入以下代码,这里引入外部字体库。

    computed: {pdfSrc(){//处理pdfUrl返回let src =  pdf.createLoadingTask({url: this.pdfUrl,//引入pdf.js字体,templcMapUrl: 'https://cdn.jsdelivr.net/npm/pdfjs-dist@2.5.207/cmaps/',cMapPacked: true})return src ;}}
复制代码

但我们公司项目包含了非常多的不同字体,还是满足不了需求,我采用了浏览器默认查看pdf方式和插件方式两种同时使用,可以解决99%的需求啦。不过使用插件形式的pdf不要超过200页,不然会加载时间过长导致打不开。

效果图,哈哈有跟没有一样

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.luyixian.cn/news_show_36539.aspx

如若内容造成侵权/违法违规/事实不符,请联系dt猫网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

ThinkPHP5目录结构

文章目录一、TP5的框架的下载1、[采用fastAdmin安装](https://www.fastadmin.net/download.html)2、Composer安装2.1 Composer提供的服务3、Git安装二、使用Composer安装后目录结构2.1 补充获取 Git 仓库git的工作机制一、TP5的框架的下载 1、采用fastAdmin安装 FastAdmin是一…

运营版uniapp多商户商城小程序+H5+APP+商家入驻短视频社区种草直播阶梯拼团

运营版uniapp多商户商城小程序H5APP商家入驻短视频社区种草直播阶梯拼团 前后端全套源码&#xff0c; 支持二次开发&#xff0c;代码无加密&#xff01; 独立商家后台 用于店铺商品管理订单管理发货管理等 多类经营模式 多商家B2B2C、自营B2C运营模式 私有化部署 前端Uni…

JVM类加载(类加载过程、双亲委派模型)

系列文章目录 JVM的内存区域划分_crazy_xieyi的博客-CSDN博客 文章目录 一、类加载过程二、关于类加载的典型试题三、双亲委派模型一、类加载过程 对于一个类来说&#xff0c;它的生命周期是这样的&#xff1a;1.加载 “加载”&#xff08;Loading&#xff09;阶段是整个“类加…

spring 如何解决循环依赖

什么是循环依赖 A 类中有一个属性 B &#xff0c;也就是说 A 依赖 B&#xff0c;同时 B 类中有一个属性 A, 也就是说 B 依赖 A. 他们之间的依赖关系形成了环。就是我们说的循环依赖&#xff0c;如下图&#xff1a; 循环依赖示例 public class CircularDependenciesDemo {publ…

SSM基于上述环境实现简单CUDA操作

目录 1. 结构 2. 环境&#xff1a; 3. controller 4. mapper 5. service 6. serviceImpl 7. mapper.xml 8. emplist.html 9. update 1. 结构 2. 环境&#xff1a; SSM整合 Spring SprintMVC Mybatishttps://blog.csdn.net/qq_41950447/article/details/128033971 3.…

Android -- 每日一问:Activity的启动模式(launchMode)有哪些,有什么区别?

经典回答 这应该是一道很虐人的面试题&#xff0c;很多人都答不上来&#xff0c;很多人根本就没有用过。当我发现在被我面试的人中有80%的比例对它不了解时&#xff0c;我找过一些同事讨论是否还有在面试中考查这个问题的必要&#xff0c;得到的回答是“程序员何苦为难程序员”…

2020-RKT

2020-RKT&#xff1a;Relation-Aware Self-Attention for Knowledge Tracing 有代码&#xff1a;https://github.com/shalini1194/RKT 摘要 学生在解决练习的过程中获得技能&#xff0c;每一次这样的互动都对学生解决未来练习的能力有明显的影响。 这种影响表现为:1)互动中涉…

电脑c盘满了怎么清理,快速清理,用这5招

​新买的电脑没用多久&#xff0c;突然发现系统提示磁盘空间不足。点击一看&#xff0c;电脑c盘空间已经爆满变红。当出现这种情况时&#xff0c;很多电脑的运行速度会大大降低&#xff0c;甚至导致部分应用无法正常运行。那么电脑c盘满了怎么清理&#xff1f;如何释放电脑c盘空…

C语言:关键字----switch、case、default(开关语句)

C语言&#xff1a;基础开发----目录 C语言&#xff1a;关键字—32个(分类说明) 有32个关键字详细说明&#xff0c;还有跳转链接&#xff01; 一、开关语句----介绍 开关语句&#xff0c;包括以下四种关键字&#xff1a; switch&#xff1a;开关语句case&#xff1a; 开关语句…

【vim】系统剪切板、vim寄存器之间的复制粘贴操作命令?系统剪切板中的内容复制粘贴到命令行?vim文本中复制粘贴到命令行

一、系统剪切板和文本内容的复制粘贴 1.1 从系统剪切板复制粘贴到文本中 需要操作3次&#xff1a; 分别是英文双引号、一个加号或梅花号&#xff0c;最后是一个p 也即"p 或者直接使用组合键【Shift insert】 1.2 从文本复制粘贴到系统剪切板 也需要操作3次&#xff…

java EE初阶 — 计算机工作原理

文章目录1.操作系统2.操作系统的定位3.进程3.1 进程的基本了解3.2 操作系统内核是如何管理软件资源的3.3 PCB里描述了进程的哪些特征3.3.1 三个较为简单的特征3.3.2 进程的调度属性4.内存管理1.操作系统 操作系统是一个搞管理的软件。 对上要给软件提供稳定的运行环境。对下要…

基于JAVA的鲜花店商城平台【数据库设计、源码、开题报告】

数据库脚本下载地址&#xff1a; https://download.csdn.net/download/itrjxxs_com/86427660 摘要 在互联网不断发展的时代之下&#xff0c;鲜花软件可以为鲜花企业带来更多的发展机会&#xff0c;让企业可以挖掘到更多的潜在用户&#xff0c;同时结合企业的优势就能够为用户…

Swin Transformer目标检测实验——环境配置的步骤和避坑

Swin Transformer1. 网上基础教程&#xff08;带视频讲解&#xff09;2. 配置虚拟环境时遇到的一些问题&#xff08;按操作顺序排列&#xff09;1. 网上基础教程&#xff08;带视频讲解&#xff09; 大家是不是都从b站来的呀&#xff0c;先给你们基础环境的配置和搭配的视频教…

黑马点评--Redis消息队列

Redis消息队列 Redis消息队列实现异步秒杀 消息队列&#xff08;Message Queue&#xff09;&#xff0c;字面意思就是存放消息的队列。最简单的消息队列模型包括3个角色&#xff1a; 消息队列&#xff1a;存储和管理消息&#xff0c;也被称为消息代理&#xff08;Message Br…

【附源码】计算机毕业设计JAVA疫情下的居民管理系统

【附源码】计算机毕业设计JAVA疫情下的居民管理系统 目运行 环境项配置&#xff1a; Jdk1.8 Tomcat8.5 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; JAVA…

蒙泰转债上市价格预测

蒙泰转债基本信息转债名称&#xff1a;蒙泰转债&#xff0c;评级&#xff1a;A&#xff0c;发行规模&#xff1a;3.0亿元。正股名称&#xff1a;蒙泰高新&#xff0c;今日收盘价&#xff1a;31.3&#xff0c;转股价格&#xff1a;26.15。当前转股价值 转债面值 / 转股价格 * 正…

有没有把语音转为文字的软件?这几个转换软件你值得收藏

我们在日常的工作和生活中&#xff0c;应该经常会遇到需要将音频转换成文字的情况吧。相信大部分的小伙伴都会选择直接使用转换软件进行音频转文字的操作&#xff0c;但在使用的过程中就会发现&#xff0c;有些软件会在使用次数、音频时长上面有所限制&#xff0c;导致我们会转…

《从零开始:机器学习的数学原理和算法实践》chap1

《从零开始&#xff1a;机器学习的数学原理和算法实践》chap1 学习笔记 文章目录《从零开始&#xff1a;机器学习的数学原理和算法实践》chap1 学习笔记chap1 补基础&#xff1a;不怕学不懂微积分1.1 深入理解导数的本质直观理解复合函数求导1.2 理解多元函数偏导1.3 理解微积分…

【附源码】计算机毕业设计JAVA疫情下智慧社区系统

【附源码】计算机毕业设计JAVA疫情下智慧社区系统 目运行 环境项配置&#xff1a; Jdk1.8 Tomcat8.5 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; JAVA …

CorelDRAW2023最新版矢量设计软件

CorelDRAW2023最新版是我比较用的比较好的一款软件&#xff0c;因为其作为一款优秀的矢量设计软件&#xff0c;兼具功能和性能&#xff0c;它是由Corel公司出品的矢量设计工具&#xff0c;被广泛应用于排版印刷、矢量图形编辑、网页设计等行业。CDR软件的优势在于&#xff1a;易…