PDF.JS:使用 ArrayBuffer 或 Blob 而不是 URL 呈现 PDF [英] PDF.JS: Render PDF using an ArrayBuffer or Blob instead of URL

查看:76
本文介绍了PDF.JS:使用 ArrayBuffer 或 Blob 而不是 URL 呈现 PDF的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我知道一个与此类似的问题:Pdf.js:使用 base64 文件源而不是 url 呈现 pdf 文件.Codetoffel 很好地回答了这个问题,但我的问题不同,我的 PDF 是通过对 Web API 的 RESTful 调用检索的执行.让我解释一下...

I know of a similar question to this one: Pdf.js: rendering a pdf file using a base64 file source instead of url. That question was awesomely answered by Codetoffel but my question is different in that my PDF is retrieved via a RESTful call to my Web API implementation. Let me explain...

首先,这是使用 PDF.JS 通过 URL 打开 PDF 的基本方法:

First, here's a basic way to use PDF.JS to open a PDF via a URL:

PDFJS.getDocument("/api/path/to/my.pdf").then(function (pdf) {
  pdf.getPage(1).then(function (page) {
    var scale = 1;
    var viewport = page.getViewport(scale);
    var canvas = document.getElementById('the-canvas');
    var context = canvas.getContext('2d');
    canvas.height = viewport.height;
    canvas.width = viewport.width;
    page.render({canvasContext: context, viewport: viewport});
  });
});

这很好用,但我使用 Angular 及其 $resource 服务通过我的 RESTful Web API 请求 PDF.我确实知道 PDF.JS 允许我用一个 DocumentInitParams 对象(定义为 这里.使用 DocumentInitParams 对象的工作方式如下:

This works great, but I am using Angular and its $resource service to make the request for the PDF via my RESTful Web API. I do know that PDF.JS allows me to replace passing the URL as a string in the PDFJS.getDocument method (above) with a DocumentInitParams object, which is defined here. Using the DocumentInitParams object works as follows:

var docInitParams = {
    url: "/api/path/to/my.pdf",
    httpHeaders: getSecurityHeaders(), //as needed
    withCredentials: true
};
PDFJS.getDocument(docInitParams).then(function (pdf) {
    ...
});

这也有效,但它通过要求我构建 api URL 来解决我的 Angular $resource.但这没关系,因为 PDFJS 允许我直接给它 PDF 数据,而不是给它一个 PDF 的 URL,如下所示:

This also works, but it works around my Angular $resource by requiring me to construct the api URL. But that's OK because PDFJS allows me to give it the PDF data directly, instead of giving it a URL to the PDF, as follows:

var myPdf = myService.$getPdf({ Id: 123 });

//It's an Angular $resource, so there is a promise to be fulfilled...
myPdf.$promise.then(function() {
    var docInitParams = {
        data: myPdf
    };
    PDFJS.getDocument(docInitParams).then(function (pdf) {
        ...
    });
});

这是我似乎无法开始工作的地方.我可以告诉 myService.$gtPdf 方法将数据作为 blob 或作为 arraybuffer 返回,但两者都不起作用.我也尝试将 arraybuffer 返回的数据转换为 Uint8Array,但无济于事.

This is the one I can't seem to get to work. I can tell the myService.$gtPdf method to return the data as a blob or as an arraybuffer but neither works. I've tried to convert the arraybuffer returned data to an Uint8Array too, but to no avail.

我不知道还能尝试什么,真的可以使用小费.

I'm not sure what else to try and could really use a tip.

如何获取从我的服务返回的数据以使用 PDFJS?

提前致谢.

推荐答案

您不是将响应数据传递给 PDF.js,而是资源的一个实例:

You're not passing the response data to PDF.js, but an instance of the resource:

var myPdf = myService.$getPdf({ Id: 123 });
myPdf.$promise.then(function() {
    var docInitParams = {
        data: myPdf

您还没有显示 $getPdf 的代码,但我想它相当于

You haven't shown your code for $getPdf, but I guess that it is something equivalent to

var myService = $resource('/foo', {}, {$getPdf:{responseType: 'arraybuffer'}});
var myPdf = myService.$getPdf();

默认情况下,AngularJS $resource 将响应视为一个对象(从 JSON 反序列化)并将对象中的任何属性复制到资源实例(myPdf 在上一个片段).

By default, an AngularJS $resource treats the response as an object (deserialized from JSON) and copies any properties from the object to the resource instance (myPdf in the previous snippet).

显然,由于您的响应是一个数组缓冲区(或 Blob、类型化数组或其他任何内容),因此这是行不通的.获得所需响应的方法之一是使用 transformResponse 将响应对象包装在一个对象中:

Obviously, since your response is an array buffer (or Blob, typed array or whatever), this is not going to work. One of the ways to get the desired response is to use transformResponse to wrap the response object in an object:

var myService = $resource('/foo', {}, {
    $getPdf: {
        responseType: 'arraybuffer',
        transformResponse: function(data, headersGetter) {
            // Stores the ArrayBuffer object in a property called "data"
            return { data : data };
        }
    }
});
var myPdf = myService.$getPdf();
myPdf.$promise.then(function() {
    var docInitParams = {
        data: myPdf.data
    };

    PDFJS.getDocument(docInitParams).then(function (pdf) {
        // ...
    });
});

或者只是以下(避免不必要的局部变量):

Or simply the following (avoided unnecessary local variables):

myService.$getPdf().$promise.then(function(myPdf) {
    PDFJS.getDocument({
        data: myPdf.data
    }).then(function (pdf) {
        // ...
    });
});

这篇关于PDF.JS:使用 ArrayBuffer 或 Blob 而不是 URL 呈现 PDF的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆