我正在創建一個服務,使用PDF.js和jQuery在pdf上加蓋一個影像。我設法用PDF.js創建了一個可拖動的物件,但這個物件在被拖動時留下了一個過去物件的痕跡。
我使用context.clearRect(0, 0, canvas.width, canvas.height);來清除過去的物件,但它也清除了canvas中的底層PDF。
我怎樣才能在不影響底層 PDF 的情況下拖動這個物件呢?
到目前為止,我所做的是這樣的。
我正在加載 PDF。
我正在使用以下代碼將 PDF 加載到畫布中。
function loadPdfPreview(base64pdf){
pdfjsLib.GlobalWorkerOptions.workerSrc = 'https://cdnjs.cloudflare.com/ajax/libs/pdf.js/2.0.943/pdf.worker.min.js'/span>。
var loadingTask = pdfjsLib.getDocument({data: base64pdf}) 。
loadingTask.promise.then(function (pdf) {
//獲取第一頁
pdf.getPage(1).then(function(page) {
var scale = 1.0;
var viewport = page.getViewport(scale)。
//使用PDF頁面尺寸準備畫布。
canvas = document.getElementById('pdf-canvas')。
context = canvas.getContext('2d')。
canvas.height = viewport.height。
canvas.width = viewport.width;
canvasOffset = $("#pdf-canvas"/span>).offset()。
offsetX = canvasOffset.left。
offsetY = canvasOffset.top。
//將PDF頁面渲染到畫布背景關系中。
var renderContext = {
canvasContext: context,
viewport: viewport
};
page.render(renderContext).then(function () {
///在成功時創建虛擬物件。
drawObjectFromBlueprint(blueprint)。
}, function (e) {
console.log(e)。
});
});
});
}
我使用下面的函式,在pdf加載到canvas后,在canvas上面畫出物件。
function drawObjectFromBlueprint(blueprint) {
//在畫布內繪制一個可拖動的元素。
context.strokeStyle = "lightgray"。
//清除之前的虛擬物件。
context.clearRect(0, 0, canvas.width, canvas.height) 。
//繪制假的物件。
context.beginPath()。
context.moveTo(blueprint.x, blueprint.y)。
context.lineTo(blueprint.right, blueprint.y)。
context.lineTo(blueprint.right, blueprint.bottom)。
context.lineTo(blueprint.x, blueprint.bottom)。
context.closePath()。
context.fillStyle = blueprint.fill;
context.fill()。
context.stroke()。
我使用以下代碼來處理滑鼠移動事件。
function handleMouseMove(e) {
var mouseX = parseInt(e.clientX - offsetX1)。
var mouseY = parseInt(e.clientY - offsetY1) 。
//總是更新全域藍圖。
blueprint.x = (mouseX - lastX)。
blueprint.y = (mouseY - lastY)。
blueprint.right = blueprint.x blueprint.width;
blueprint.bottom = blueprint.y blueprint.height。
lastX = mouseX;
lastY = mouseY;
drawObjectFromBlueprint(blueprint)。
我使用以下代碼來監聽滑鼠移動事件。
$("#drawable-canvas"/span>)。 mousemove(function (e) {
handleMouseMove(e)。
});
我想在不影響底層PDF的情況下重新繪制物件。我試著加載PDF并通過清除整個畫布來重新繪制物件,但這并不符合預期的效果。
uj5u.com熱心網友回復:
在page.render方法的回呼中,pdf頁面將被繪制在畫布上。你必須單獨保存繪制的圖片,這樣原始圖片才不會因為拖動而消失。
// maybe globalScope...?
const tempCanvas = document.createElement('canvas')。
const tempCtx = tempCanvas.getContext('2d')。
//您的代碼
page.render(renderContext).then(function (>) {
//span>保存原始頁面影像。
tempCanvas.width = canvas.width。
tempCanvas.height = canvas.height;
tempCtx.drawImage(canvas, 0, 0)。
//在成功時創建虛擬物件。
drawObjectFromBlueprint(blueprint)。
}, ...
接下來,請修改它,在drawObjectFromBlueprint中用原始的頁面影像進行繪制。
function drawObjectFromBlueprint(blueprint) {
//繪制原始頁面影像。
context.drawImage(tempCanvas, 0, 0)。
//在畫布內繪制一個可拖動的元素。
context.strokeStyle = "lightgray"。
...
}
uj5u.com熱心網友回復:
經過兩個小時的嘗試,我找到了這樣做的方法。我按照@Nikolaus的建議,使用了兩個畫布,并使用底部的畫布來加載PDF,頂部的畫布用于繪圖。
以下是我的 HTML:
<div class="col-md-12"/span> id="pdfDisplay" style="display: none;">
< div id="pageContainer"/span> class="pdfViewer nopadding"/span> style="background-color: transparent">
<canvas id="pdf-canvas"/span> style="border: 1px solid black"></canvas>>
<canvas id="drawable-canvas" style="border: 1px solid black"></canvas>>
</div>/span>
</div>
下面是我的CSS,將兩個畫布放在彼此的上面。
#pageContainer { position: relative; }
#drawable-canvas { position: absolute; top: 0; left: 0; }
以下是我的全域Javascript變數:
var isUploading = false;
var base64pdf = ""/span>;
var initX = 50;
var initY = 50;
var initWidth = 200;
var initHeight = 150;
//blueprint options are in pixels.
//此藍圖持有可拖動物件的最新值。
//在進行更改時,總是更新這個全域藍圖,以便它持有最新的值。
var blueprint = {
x: initX,
y: initY,
width: initWidth,
height: initHeight,
右: (initX initWidth), // x width: initX
bottom: (initY initHeight), // y height.
fill: "skyblue"
};
var context = null;
var canvas = null;
var drawableContext = null;
var drawableCanvas = null;
var canvasOffset = null;
var offsetX = 0;
var offsetY = 0;
var canvasOffset1 = null;
var offsetX1 = 0;
var offsetY1 = 0;
var lastX = 0;
var LastY = 0;
var mouseIsDown = false;
Javascript函式用于監聽滑鼠的上、下和移動,因為我只需要跟蹤使用滑鼠拖動物件時的滑鼠移動。
$("#drawable-canvas") 。 mousedown(function (e) {
var mouseX = parseInt(e.clientX - offsetX)。
var mouseY = parseInt(e.clientY - offsetY)。
lastX = mouseX;
lastY = mouseY;
mouseIsDown = true;
});
$("#drawable-canvas").mousemove(function (e) {
handleMouseMove(e)。
});
$("#drawable-canvas").mouseup(function (e) {
mouseIsDown = false;
});
Javascript函式將PDF加載到底部的畫布上。
function loadPdfPreview(base64pdf) {
pdfjsLib.GlobalWorkerOptions.workerSrc = 'https://cdnjs.cloudflare.com/ajax/libs/pdf.js/2.0.943/pdf.worker.min.js'/span>。
var loadingTask = pdfjsLib.getDocument({data: base64pdf}) 。
loadingTask.promise.then(function (pdf) {
//獲取第一頁
pdf.getPage(1).then(function(page) {
var scale = 1.0;
var viewport = page.getViewport(scale)。
//使用PDF頁面尺寸準備畫布。
canvas = document.getElementById('pdf-canvas')。
context = canvas.getContext('2d')。
canvas.height = viewport.height。
canvas.width = viewport.width;
canvasOffset = $("#pdf-canvas"/span>).offset()。
offsetX = canvasOffset.left。
offsetY = canvasOffset.top。
canvasOffset1 = $("#drawable-canvas"/span>).offset()。
offsetX1 = canvasOffset1.left。
offsetY1 = canvasOffset1.top;
//創建用于繪圖的可畫布,而不影響pdf-canvas。
//它有相同的寬度和高度以及X和Y值。
drawableCanvas = document.getElementById('drawable-canvas'); 。
drawableCanvas.height = viewport.height;
//使用z-index將可繪制的畫布調高。
drawableCanvas.style.zIndex = 1;
drawableCanvas.width = viewport.width;
drawableContext = drawableCanvas.getContext('2d')。
//將PDF頁面渲染到畫布背景關系中。
var renderContext = {
canvasContext: context,
viewport: viewport
};
page.render(renderContext).then(function () {
///在成功時創建虛擬物件。
drawObjectFromBlueprint(blueprint)。
}, function (e) {
console.log(e)。
});
});
});
}
處理滑鼠移動(拖動物件):
function handleMouseMove(e) {
if (! mouseIsDown) {
return;
}
var mouseX = parseInt(e.clientX - offsetX1) 。
var mouseY = parseInt(e.clientY - offsetY1) 。
//總是更新全域藍圖。
blueprint.x = (mouseX - lastX)。
blueprint.y = (mouseY - lastY)。
blueprint.right = blueprint.x blueprint.width;
blueprint.bottom = blueprint.y blueprint.height。
lastX = mouseX;
lastY = mouseY;
drawObjectFromBlueprint(blueprint)。
console.log(blueprint)。
}
在可畫布上繪制物件的Javascript函式,完全獨立于pdf-canvas.
function drawObjectFromBlueprint(blueprint) {
//在畫布內繪制一個可拖動的元素。
drawableContext.strokeStyle = "lightgray"。
//清除之前的虛擬物件 //清除之前的虛擬物件
drawableContext.clearRect(0, 0, drawableCanvas. width, drawableCanvas.height)。)
//繪制假的物件。
drawableContext.beginPath()。
drawableContext.moveTo(blueprint.x, blueprint.y) 。
drawableContext.lineTo(blueprint.right, blueprint.y) 。
drawableContext.lineTo(blueprint.right, blueprint.bottom)。
drawableContext.lineTo(blueprint.x, blueprint.bottom) 。
drawableContext.closePath()。
drawableContext.fillStyle = blueprint.fill;
drawableContext.fill()。
drawableContext.stroke()。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qianduan/333002.html
標籤:
