30

PDF.JSを使用して、PDFページをさまざまなキャンバス要素にレンダリングしています。私の要件は、キャンバスの出力をキャプチャし、それを画像として表示することです。キャンバスでのPDFページのレンダリングが終了したかどうかを知るためのイベントはありますか?キャンバスの出力をキャプチャしようとすると空白になるためです。ただし、PDFページは正しくレンダリングされます。pdf.jsがレンダリングプロセスを完了する前に、キャプチャイベントが呼び出されているようです。

これが私のコードです:

page.render(renderContext);
var myImage = new Image();
myImage.src = document.getElementById('my-canvas-id').toDataURL();
$('body').append(myImage);

FireFoxのコンソールで同じコードを実行すると、これは正常に機能します。したがって、このコードには何の問題もありません。

私がすでにdocument.readyイベントとwindow.loadイベントを試したことを人々に知らせるためだけに。

4

16 に答える 16

22

私もこの問題に苦しんでいました..私が使用した解決策は次のとおりです:

//Step 1: store a refer to the renderer
var pageRendering = page.render(renderContext);
//Step : hook into the pdf render complete event
var completeCallback = pageRendering.internalRenderTask.callback;
pageRendering.internalRenderTask.callback = function (error) {
  //Step 2: what you want to do before calling the complete method                  
  completeCallback.call(this, error);
  //Step 3: do some more stuff
};
于 2013-09-03T05:03:24.163 に答える
18

<script type="text/javascript">
  document.addEventListener("pagesloaded", function(e) {
   //do sth..
  });
</script>

私のために働いた

于 2015-03-31T22:37:44.493 に答える
16

これを書いている時点では、これはうまくいきました。それでもそうなるかどうかはわかりません。

PDFJSはを利用しPromisesます。最も簡単な方法は次のとおりです。

page.render(renderContext).promise.then(function(){
  document.body.appendChild(canvas);
});
于 2013-07-13T13:52:24.537 に答える
7

イベントの使用はtextlayerrendered私のために働いた:

document.addEventListener('textlayerrendered', function (event) {
  // was this the last page?
  if (event.detail.pageNumber === PDFViewerApplication.page) {
    console.log('Finished rendering!');
  }
}, true);
于 2015-09-15T17:21:18.850 に答える
4

より堅牢なリヨンのソリューション。しかし、これは私が見つけることができる最も簡単な解決策です。

var renderTask = pdfPage.render(renderContext);
renderTask.promise.then(
  function pdfPageRenderCallback() {
    pageViewDrawCallback(null);
  },
  function pdfPageRenderError(error) {
    pageViewDrawCallback(error);
  }
);
于 2014-02-10T17:52:01.667 に答える
3

これらの解決策を検討しているときに、を取得する際に問題が発生したrenderContextため、次のことを聞いてこのアプローチを使用することになりましたpagerendered

document.addEventListener("pagerendered", function(e){

});

私の場合、最小限の労力で、ページがレンダリングされた後に外部関数を呼び出したかっただけです。

お役に立てれば。乾杯!

于 2015-03-16T17:27:17.230 に答える
3
window.addEventListener('load', function () {
    PDFViewerApplication.eventBus.on('textlayerrendered', function () {
      console.log('textlayerrendered', arguments, PDFViewerApplication)
    })

イベント名textlayerrenderedには以下が含まれますPDFViewerApplication.eventBus._listeners

于 2020-10-21T14:04:02.210 に答える
2

結局のところ、最初の行は、次の3つのプロパティを持つオブジェクトをpage.render(renderContext);返します。RenderTask

  • internalRenderTask-InternalRenderTask当たり前
  • キャンセル-おそらくレンダリング作業をキャンセルできるようにする関数
  • promise -jQueryPromiseオブジェクト

約束はあなたが望むものです。それを利用するには、次のようになります。

 page.render(renderContext).promise.then(function() {

     //do something after the page is rendered here
 });

お役に立てば幸いです。

于 2014-06-13T21:21:17.107 に答える
2

PDF.jsのドキュメントによると。

2.2より前のバージョンの場合:
page.render(renderContext).then(function(){
var myImage = new Image();
myImage.src = document.getElementById('my-canvas-id').toDataURL();
$('body').append(myImage);
});

2.2以降のバージョンの場合: page.render(renderContext).promise.then(function(){
var myImage = new Image();
myImage.src = document.getElementById('my-canvas-id').toDataURL();
$('body').append(myImage);
});

于 2021-01-07T18:18:55.357 に答える
2

ビューアーアプリケーションでpdf.jsを使用している場合、初期化されるのを待つために私が見つけた最良の方法は次のとおりです。

// Wait for the PDFViewerApplication to initialize                                                                                                                         
PDFViewerApplication.initializedPromise.then(function() {
    // Do whatever startup code you need to here, now that the EventBus
    // is read. For example:
    PDFViewerApplication.eventBus.on('pagerendered', function (e) {
        annotationInterface.onPageRendered(e);
    });
});
于 2021-07-22T17:21:20.947 に答える
1

私はこのようにコードを変更しました、そしてそれは私がやりたいことを私に助けました:

pageRendering = page.render(renderContext);
pageRendering.onData(function(){
    var myImage = new Image();
    myImage.src = document.getElementById('my-canvas-id').toDataURL();
    $('body').append(myImage);
});

これは、特定のページのレンダリングが終了した場合にのみ役立ちます。すべてのページのレンダリングについては説明していません。

于 2012-10-04T09:30:47.697 に答える
1

pdfドキュメントのすべてのページを異なるキャンバスにレンダリングする場合は、すべてを1つずつ同期してレンダリングするのが一種の解決策です。

index.html

<!doctype html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>PDF Sample</title>
    <script type="text/javascript" src="jquery.js"></script>
    <script type="text/javascript" src="pdf.js"></script>
    <script type="text/javascript" src="main.js">
    </script>
    <link rel="stylesheet" type="text/css" href="main.css">
</head>
<body id="body">  
</body>
</html>

main.css

canvas {
    display: block;
}

main.js

$(function() {  
    var filePath = "document.pdf";

    function Num(num) {
        var num = num;

        return function () {
            return num;
        }
    };

    function renderPDF(url, canvasContainer, options) {
        var options = options || {
                scale: 1.5
            },          
            func,
            pdfDoc,
            def = $.Deferred(),
            promise = $.Deferred().resolve().promise(),         
            width, 
            height,
            makeRunner = function(func, args) {
                return function() {
                    return func.call(null, args);
                };
            };

        function renderPage(num) {          
            var def = $.Deferred(),
                currPageNum = new Num(num);
            pdfDoc.getPage(currPageNum()).then(function(page) {
                var viewport = page.getViewport(options.scale);
                var canvas = document.createElement('canvas');
                var ctx = canvas.getContext('2d');
                var renderContext = {
                    canvasContext: ctx,
                    viewport: viewport
                };

                if(currPageNum() === 1) {                   
                    height = viewport.height;
                    width = viewport.width;
                }

                canvas.height = height;
                canvas.width = width;

                canvasContainer.appendChild(canvas);

                page.render(renderContext).then(function() {                                        
                    def.resolve();
                });
            })

            return def.promise();
        }

        function renderPages(data) {
            pdfDoc = data;

            var pagesCount = pdfDoc.numPages;
            for (var i = 1; i <= pagesCount; i++) { 
                func = renderPage;
                promise = promise.then(makeRunner(func, i));
            }
        }

        PDFJS.disableWorker = true;
        PDFJS.getDocument(url).then(renderPages);       
    };

    var body = document.getElementById("body");
    renderPDF(filePath, body);
});
于 2014-06-06T00:17:45.270 に答える
1

使用しているPDF.jsのコンポーネント(およびバージョン)によっては、EventBusを使用することもできます。

PDF.jsの最も単純な実装を使用している場合、これは利用できない可能性がありますが、SimpleViewerまたはPageViewerの例を使用している場合は、次のことを試してください。

        eventBus.on("pagesloaded", function() {
            console.log('pagesloaded');
            // your code here
        });

eventBusはすでに定義されているはずですが、定義されていない場合は、次を使用して設定できます。

var eventBus = new pdfjsViewer.EventBus();

繰り返しますが、これはPDFビューアの複雑さのレベルによって異なります。PDF.js内には多くの異なるレイヤーがあることがわかりました。

すべてのページの読み込みをリッスンするには、eventBusイベントを使用します' pagerendered'

于 2020-07-02T16:39:32.787 に答える
0

page.renderは約束なので、以下のように成功の中で自分のことをしなければなりません。

page.render({
  canvasContext: context,
  viewport: viewport
}).then(function() {
//do your stuff here });
于 2016-11-18T15:04:45.080 に答える
0

これは、Viewer APIを使用して、レンダリングされたページをエラーなしで操作するために私が見つけた唯一の方法です。

onPagesLoaded = () => { 
    // do something, set zoom, current page, ...
};

window.PDFViewerApplication.eventBus.on('pagesloaded', onPagesLoaded);
于 2022-01-05T10:32:59.113 に答える
0

バックエンドでPDFを作成/変更する場合は、PDFファイルにpdfjavascriptを追加して、ロード時に印刷できます。

var pp = getPrintParams();  
pp.interactive=pp.constants.interactionLevel.full; 
print(pp);
于 2022-01-07T20:12:30.180 に答える