当前位置: 首页 > 工具软件 > PDF Download > 使用案例 >

移动端和PC端的pdf预览与下载

艾意蕴
2023-12-01

34、移动端和PC端的pdf的预览与下载

1、预览

需求:在手机端实现pdf的文件与下载,主要是zlb_app中

实现过程:在研究了vue-pdf、pdfjs、pdfh5之后,选择了vue-pdf-signature,vue-pdf的升级版本

在vue-pdf和pdfjs中引入cmaps字体文件后,依旧显示不完整

技术安卓iOS选择
vue-pdf部分文字丢失,显示不完整部分文字丢失,显示不完整
pdf-js文字乱码文字乱码
vue-pdf-signature显示完整显示完整✔️

​ 表1:浙里办app预览方案对比

代码实现:pdf的预览

需要引入字体文件import CMapReaderFactory from ‘vue-pdf-signature/src/CMapReaderFactory’,在pdf创建时设置pdf.createLoadingTask

<!-- 页面引入vue-pdf-signature后,使用pdf组件 -->
<div>
    <p v-show="!show" style="position:absolute;top:0;left:0;text-align:center;width:100%;padding-top:0.2rem;">PDF加载中,请耐心等待...</p>
    <pdf
    v-show="show"
      v-for="i in numPages"
      :key="i"
      :src="src"
      :page="i"
      :rotate="rotate"
      class="pdf"
      :style="style"
    ></pdf>
  </div>
import pdf from 'vue-pdf-signature'
import CMapReaderFactory from 'vue-pdf-signature/src/CMapReaderFactory'
export default {
  components: {
    pdf
  },
  name: 'index',
  data () {
    return {
      numPages: "",
      src: "",
      pdfUrl: "",
      show:false,
      rotate:0,
      style:"width:100%",
      widt:100
    }
  },
  methods: {
    loadPdf (url) {
      console.log('uuurl', url)
      this.src = pdf.createLoadingTask({
        url: url,
        cMapPacked: true,
        CMapReaderFactory
      })
      this.src.promise.then((pdf) => {
        this.show = true
        this.numPages = pdf.numPages // 这里拿到当前pdf总页数
      })
    },
  },
   mounted () {
    //  可以是文件流,也可以是可访问地址
    this.pdfUrl = `url`
    this.loadPdf(this.pdfUrl)
  },
}

注意:

pdfUrl可以是后端接口返回的文件流,也可以是文件所在地址,若url中存在符号或中文,在encodeURIComponent之后再赋值,否则后端接收数据不完整

2、下载

需求:在移动端实现下载功能,适配安卓系统和iOS系统

实现过程:通过a标签的形式,点击后下载。

​ 后端配合:

  1. 后端配合,response header中返回

    // 强制下载
    content-disposition: attachment; filename=04702106000965.pdf
    content-type: application/pdf;charset=UTF-8
    

  2. 前端实现,request header设置

    //根据文件需求设置,我这里匹配了全部
    config.headers.Accept= '*/*'
    

代码实现:

down()
var e = document.createElement("a");
e.style.display = "none"
//ios系统中,没有xx.pdf不会显示下载按钮,且ios系统使用该方法会先打开预览,再次点击下载才可以
 e.href = "".concat(`${this.pdfUrl}`) + '&response-content-type=application/pdf&报告.pdf'
 // e.setAttribute("download", "t.pdf")
 e.setAttribute("target", "_blank")
 document.body.appendChild(e)
 console.log(e)
 e.click()
 document.body.removeChild(e)
}

注意:

e.href的赋值,需要用concat拼接一个空字符串,否则打不开浏览器,拼接

苹果下载:请求中加上xx.pdf才能实现打开预览界面中出现下载按钮

安卓下载:默认打开手机自带浏览器或阅读器,用于下载pdf

总结:下面是vue文件

<template>
  <div>
    <p v-show="!show" style="position:absolute;top:0;left:0;text-align:center;width:100%;padding-top:0.2rem;">{{text}}</p>
    <pdf
    v-show="show"
      v-for="i in numPages"
      :key="i"
      :src="src"
      :page="i"
      class="pdf"
      :style="style"
    ></pdf>
    <div v-show="show" @click="down" class="down"></div>
    <div v-show="show" @click="add" class="add" ></div>
    <div v-show="show" @click="reduce" class="reduce" ></div>
  </div>

</template>

<script>
import pdf from 'vue-pdf-signature'
import CMapReaderFactory from 'vue-pdf-signature/src/CMapReaderFactory'
import {aesCode,aesJM,changeTitle, getUserInfo} from '@/utils/index.js'

export default {
  components: {
    pdf
  },
  name: 'index',
  data () {
    return {
      numPages: "",
      src: "",
      pdfUrl: "",
      show:false,
      rotate:0,
      style:"width:100%",
      widt:100,
      text:'PDF加载中,请耐心等待...'
    }
  },
  methods: {
    loadPdf (url) {
      this.src = pdf.createLoadingTask({
        url: url,
        cMapPacked: true,
        CMapReaderFactory
      })
      this.src.promise.then((pdf) => {
        this.show = true
        this.numPages = pdf.numPages // 这里拿到当前pdf总页数
      }).catch(err=>{
        console.log(err)
        this.text = '暂未查到PDF,请稍后重试...'
      })
    },
    add(){
      // 放大
      this.widt +=20
      this.style = `width:${this.widt}%`
    },
    reduce(){
      // 缩小
      this.widt -=20
      this.style = `width:${this.widt}%`
    },
    down () {
      var e = document.createElement("a");
      e.style.display = "none"
      e.href = "".concat(`${this.pdfUrl}`) + '&response-content-type=application/pdf&报告.pdf'
      // e.setAttribute("download", "t.pdf")
      e.setAttribute("target", "_blank")
      document.body.appendChild(e)
      console.log(e)
      e.click()
      document.body.removeChild(e)
    },
  },
  mounted () {
    this.pdfUrl = `url`
    this.loadPdf(this.pdfUrl)
  },
}
</script>


<style scoped>
.down{
  width: 0.3rem;
  height: 0.3rem;
  position: fixed;
  right: 0.1rem;
  bottom: 1rem;
  background-image: url(./download2.png);
  background-size: 100% 100%;
  background-repeat: no-repeat;
}
.add{
  width: 0.3rem;
  height: 0.3rem;
  position: fixed;
  right: 0.1rem;
  bottom: 1.8rem;
  background-image: url(./add.png);
  background-size: 100% 100%;
  background-repeat: no-repeat;
}
.reduce{
  width: 0.3rem;
  height: 0.3rem;
  position: fixed;
  right: 0.1rem;
  bottom: 1.4rem;
  background-image: url(./reduce.png);
  background-size: 100% 100%;
  background-repeat: no-repeat;
}
</style>

该方法在pc端同样适用。

 类似资料: