pdf.js open or generate pdf from Uint8Array - javascript

I have the below base64 encoded string which contains the pdf file.
I want to convert the base64 string to a Uint8Array as Uint8Array is supported from IE9 forward, and than I want to open pdf using pdf.js
I am using following code,
var BASE64_MARKER = ';base64,';
function convertDataURIToBinary(dataURI) {
var base64Index = dataURI.indexOf(BASE64_MARKER) + BASE64_MARKER.length;
var base64 = dataURI.substring(base64Index);
var raw = window.atob(base64);
var rawLength = raw.length;
var array = new Uint8Array(new ArrayBuffer(rawLength));
for(i = 0; i < rawLength; i++) {
array[i] = raw.charCodeAt(i);
}
return array;
}
var pdfAsDataUri = "data:application/pdf;base64," + base64encodedString;
var pdfAsArray = convertDataURIToBinary(pdfAsDataUri);
PDFJS.getDocument(pdfAsArray)
base64encodedString = JVBERi0xLjQKJeLjz9MKMyAwIG9iago8PC9MZW5ndGggMTE1My9GaWx0ZXIvRmxhdGVEZWNvZGU+PnN0cmVhbQp4nI2XbW/bNhDH3/tT8NXQAavCJ1HigAF17SRI29hNrHR7y1lsp8CWXYne5m+/k2R5NcVTgiKok//97o6n4+n8ffI+mwhFkiQhWT6h5C1n/adEnT4w2n+Scf8nJZtP19nkYfK9/eHkAwi3ExrF5J9JmkaCJIoSRmWkCPis7GR1EpnmkW5VwUSUemqHSjGGgoqjXI2hoOIo1WMoqCiqNB9BGxVHk3gMBRVH43QMBRVHJRtDQcVRLsdQUHGUJmMoqCga67FuatRL9KFpbUYo/GNE07YfoX23k6ub5uQk+zp588WW+a4iC7O1v/6cPTf9/APEtGz71KemZE5WT1m2XJCfyGq5WA3RLp5Mw/Fmu9KZtcNDDsAPtiyP5JPZYqEEC4e63ppigwcaYM9NoHf1YW8rV4GLonSbaL1D4zIZjjvN88rWNR55AHJKfr9eZUSIRyhv9nh9nSFBlU489gaquauO4w9yiN1+WmZ3U3I/XTzdTGfZ0+Pd4pbMlvefscApRQK/9ESHpDHmXV7XI7VVSnjMXVnv7doVuxICbvemPOIBB/D7Q2XNgXyxVeFMjcWUym/2Q17AEfFAA+LfNeaca8/00e53lSOLw/ZPOxJiwOEhGMdrNjdupDsGJKNXTF9xymIkWKwHk6EpFsmOezzOEJrP3pKbojQb0uInEH2rxvDykyyNZHBIwvCVLEpB1BdDUtAIbhwqJyzSaSszHkcx93SuE/gflSUXEeWtrngEe4Mnp3GUdN45jbRPd4mzc2Y0lDgmnxJn/2dGA4ljcp84OydOQ4mzc+I08G7hiYpSBs/FH9rZzsFDfXBHrH/EuRVUC3xeksUu0DiCtzXwzVfuuLFhIhFtWcLE3Nbrqtg3d2KIcq2bivnk3O5N5ba2dENEQmmbKvrMbGPqwKCRadJWNZhcY+4bdtf/zUghmbp0pRVLtcQr6dvHPOXT2RSthm9fHjYbvA6vtD6dbphLrF6aAVLBniN0JGGbUhf9zsFpgutCJREf4TvvsTirccg7pvfeMb3zLtJx75jee8f0zjt/IXdM771jeuedvpA7pvfeh/pwTZXJaVeAecPblgj0ZQKNDPGS8xaVnl6osE/ALc1tHu5PJYbQdO0OJtChXTZxemn9VBauJqfXaigM1wzOPOA4pYGUBLwTk4Axlo0UoWzuzTPsnHP7FVIKJKR0pNSQ3cCCStxfpiQA/wZTG8/PR9H8eLBa90X5ivx81s8vMND6/HwUzY95B1k54w6BIc3BPA3Y38DXiVAaQec/GKOjTKjxC9voPEkjLUaujFDe+WftLXD1S9FhvpNtH6r5ZeNf2c4ipiryDXpKNAa9tegshinCrbic86fFmqyKbyU8g8oOyyqgMXgAbRZZ3Fp51v13FFi24SsZVMW44m87Fpdz3Z3sVXFZs4zGAPkHXJvcbo9k1ez4NTFlTpYHl+92VaDfGJOtE+Y5eYDJVLgjmdb1oTLl2pLM1q4ov5EZnMRWYU8wN2Fvv/TEUkrJAkZFDV8FHvNfyEcDfrM/SJJIqU9+/gN7fC5TCmVuZHN0cmVhbQplbmRvYmoKNSAwIG9iago8PC9QYXJlbnQgNCAwIFIvQ29udGVudHMgMyAwIFIvVHlwZS9QYWdlL1Jlc291cmNlczw8L1Byb2NTZXQgWy9QREYgL1RleHQgL0ltYWdlQiAvSW1hZ2VDIC9JbWFnZUldL0ZvbnQ8PC9GMSAxIDAgUi9GMiAyIDAgUj4+Pj4vTWVkaWFCb3hbMCAwIDU5NSA4NDJdPj4KZW5kb2JqCjEgMCBvYmoKPDwvQmFzZUZvbnQvVGltZXMtQm9sZC9UeXBlL0ZvbnQvRW5jb2RpbmcvV2luQW5zaUVuY29kaW5nL1N1YnR5cGUvVHlwZTE+PgplbmRvYmoKMiAwIG9iago8PC9CYXNlRm9udC9IZWx2ZXRpY2EvVHlwZS9Gb250L0VuY29kaW5nL1dpbkFuc2lFbmNvZGluZy9TdWJ0eXBlL1R5cGUxPj4KZW5kb2JqCjQgMCBvYmoKPDwvSVRYVCg1LjIuMSkvVHlwZS9QYWdlcy9Db3VudCAxL0tpZHNbNSAwIFJdPj4KZW5kb2JqCjYgMCBvYmoKPDwvVHlwZS9DYXRhbG9nL1BhZ2VzIDQgMCBSPj4KZW5kb2JqCjcgMCBvYmoKPDwvQ3JlYXRvcihDbGVhcnRyYWNrKS9Qcm9kdWNlcihpVGV4dK4gNS4yLjEgqTIwMDAtMjAxMiAxVDNYVCBCVkJBKS9UaXRsZShBY2FkZW15IE9yZGVyIEluc3BlY3Rpb24gUERGKS9Nb2REYXRlKEQ6MjAxNTEyMDMwOTI5NTItMDUnMDAnKS9BdXRob3IoQ2xlYXJ0cmFjaykvQ3JlYXRpb25EYXRlKEQ6MjAxNTEyMDMwOTI5NTItMDUnMDAnKT4+CmVuZG9iagp4cmVmCjAgOAowMDAwMDAwMDAwIDY1NTM1IGYgCjAwMDAwMDE0MDIgMDAwMDAgbiAKMDAwMDAwMTQ5MSAwMDAwMCBuIAowMDAwMDAwMDE1IDAwMDAwIG4gCjAwMDAwMDE1NzkgMDAwMDAgbiAKMDAwMDAwMTIzNiAwMDAwMCBuIAowMDAwMDAxNjQyIDAwMDAwIG4gCjAwMDAwMDE2ODcgMDAwMDAgbiAKdHJhaWxlcgo8PC9Sb290IDYgMCBSL0lEIFs8Y2RmYjYwYjE2YjY0YTM5MGZiNGQ1ZTI1ZGU4ZmNkMTg+PGQ2OWY0NzdkZTUxZGQ0YjVhMzZkZGEwZjJmMDMzZGJiPl0vSW5mbyA3IDAgUi9TaXplIDg+PgpzdGFydHhyZWYKMTg5OAolJUVPRgo=
But pdf is not getting generated or open in browser, any kind of suggestions or help will be appreciated.

I use this in my projects and it works fine.
HTML
<div id="myCanvasContainer"></div>
JS
function renderPDF( pdfBase64 ) {
var pdfUint8Array = base64ToUint8Array( pdfBase64 );
var canvasContainer = document.getElementById('myCanvasContainer');
var options = options || { scale: 1.5 };
function renderPage(page) {
var viewport = page.getViewport(options.scale);
var canvas = document.createElement('canvas');
var ctx = canvas.getContext('2d');
var renderContext = {
canvasContext: ctx,
viewport: viewport
};
canvas.height = viewport.height;
canvas.width = viewport.width;
canvasContainer.appendChild(canvas);
page.render(renderContext);
}
function renderPages(pdfDoc) {
for(var num = 1; num <= pdfDoc.numPages; num++)
pdfDoc.getPage(num).then(renderPage);
}
function base64ToUint8Array(base64) {
var raw = atob(base64);
var uint8Array = new Uint8Array(raw.length);
for (var i = 0; i < raw.length; i++) {
uint8Array[i] = raw.charCodeAt(i);
}
return uint8Array;
}
PDFJS.disableWorker = true;
PDFJS.getDocument(pdfUint8Array).then(renderPages);
}
Hope it helps.

Related

Writing to A4 pdf giving wrong size image

I am trying to write to an A4 PDF
form = document.querySelector("#theform");
html2canvas(form).then(function(canvas) {
doc = new jsPDF({
unit: 'pt',
format: 'a4',
});
for (var i = 0; i <= form.clientHeight/842; i++) {
//! This is all just html2canvas stuff
var srcImg = canvas;
var sX = 0;
var sY = 842*i;
var sWidth = 595;
var sHeight = 842;
var dX = 0;
var dY = 0;
var dWidth = 595;
var dHeight = 842;
window.onePageCanvas = document.createElement("canvas");
onePageCanvas.setAttribute('width', 595);
onePageCanvas.setAttribute('height', 842);
var ctx = onePageCanvas.getContext('2d');
ctx.drawImage(srcImg,sX,sY,sWidth,sHeight,dX,dY,dWidth,dHeight);
var canvasDataURL = onePageCanvas.toDataURL("image/png", wid = canvas.width, hgt = canvas.height);
var hratio = hgt/wid
const pdfWidth = doc.internal.pageSize.width;
const TheHeight = doc.internal.pageSize.width;
const pdfHeight = TheHeight
if (i > 0) {
doc.addPage(595, 842);
}
//! now we declare that we're working on that page
doc.setPage(i+1);
doc.addImage(canvasDataURL, 'PNG', 10, 10, pdfWidth, pdfHeight);
}
doc.autoPrint();
window.open(doc.output('bloburl'), '_blank');
}
But the it is only creating a PDF for part of the left hand side and I can't see anything wrong.. It is as though what it is writing to the PDF is twice the size it should be.

How to fix "TypeError: Failed to execute 'drawImage' on 'CanvasRenderingContext2D'"?

I am a beginner JavaScript programmer and I am following a book called "Create with < code >" and I am having trouble with the code. I have been following along with the book but when I have tried running it, I get this error:
Uncaught TypeError: Failed to execute 'drawImage' on 'CanvasRenderingContext2D': The provided value is not of type '(CSSImageValue or HTMLImageElement or SVGImageElement or HTMLVideoElement or HTMLCanvasElement or ImageBitmap or OffscreenCanvas)
I have been typing the code into a plain-text editor and viewing it on Chrome. How do I fix this error?
If you run the snippet you should be able to see the error.
//CONSTANTS
var CANVAS_WIDTH = 800;
var CANVAS_HEIGHT = 600;
var GROUND_Y = 540;
//SETUP
var canvas = document.createElement('canvas');
var c = canvas.getContext('2d');
canvas.width = CANVAS_WIDTH;
canvas.height = CANVAS_HEIGHT;
document.body.appendChild(canvas);
var cameraX = 0;
var bushData = generateBushes();
var bush1Image = new Image();
bush1Image.src = 'bush1.png';
var bush2Image = new Image();
bush2Image.src = 'bush2.png';
window.addEventListener('load', start);
function start() {
window.requestAnimationFrame(mainLoop);
}
function generateBushes() {
var generatedBushData = [];
var bushX = 0;
while (bushX < (2 * CANVAS_WIDTH)) {
var bushImage;
if (Math.random() >= 0.5) {
bushImage = bush1Image;
} else {
bushImage = bush2Image
}
generatedBushData.push({
x: bushX,
y: 80 + Math.random() * 20,
image: bushImage
});
bushX += 150 + Math.random() * 200;
}
return generatedBushData;
}
//MAIN LOOP
function mainLoop() {
update();
draw();
window.requestAnimationFrame(mainLoop);
}
//UPDATING
function update() {
//Update bushes.
for (var i = 0; i < bushData.length; i++) {
if ((bushData[i].x - cameraX) < -CANVAS_WIDTH) {
bushData[i].x += (2 * CANVAS_WIDTH) + 150;
}
}
}
//DRAWING
function draw() {
//Draw the bushes
for (var i = 0; i < bushData.length; i++) {
c.drawImage(
bushData[i].image,
bushData[i].x,
GROUND_Y - bushData[i].y);
}
}
DanieleAlessandra put his finger on the error in a comment: image in the objects in bushData is undefined, because you're calling generateBushes too soon. You have:
var bushData = generateBushes();
var bush1Image = new Image();
bush1Image.src = 'bush1.png';
var bush2Image = new Image();
bush2Image.src = 'bush2.png';
but you need to initialize bush1Image and bush2Image before calling generateBushes. Just moving var bushData = generateBushes(); to after bush2Image.src = 'bush2.png'; fixes it.

Compare multiple part of an image through canvas using resemble.js

I am trying to compare different blocks of an image(filled.png) with a specific block of another image(blank.png).
So far I have tried this :-
var canvas = document.createElement('canvas');
var context = canvas.getContext('2d');
canvas.width = 20;
canvas.height = 20;
var img = new Image();
img.onload = function(){
context.drawImage(img,53,61,20,20,0,0,20,20);
};
img.src ='blank.png';
var imgResult = new Image();
var image1,image2;
var canvasResult = document.createElement('canvas');
canvasResult.width = 20;
canvasResult.height = 20;
var contextResult = canvasResult.getContext('2d');
function compare(){
image1=new Image();
image1.onload= function(){
imgResult.onload = function(){
var x = 53;
for (var i = 1; i <= 20; i++) {
contextResult.clearRect(0, 0, 20, 20);
contextResult.drawImage(imgResult,x,61,20,20,0,0,20,20);
x += 23;
image2 = new Image();
image2.onload = function(){
resemble(image1.src).compareTo(image2.src).onComplete(function(data){
$('p').append('Diffrence : ' + data.misMatchPercentage+ '%</br>');
});
};
image2.src = canvasResult.toDataURL();
}
};
imgResult.src = 'filled.png';
}
image1.src=canvas.toDataURL();
}
But it is not working, getting same result on each iteration of for loop. So please help me find, where I am going wrong.
.onComplete - sounds asynchronous, and image2.onload DEFINITELY IS - but in the meantime you're changing contextResult ... asynchronous code strikes again
If you create a function which recursively calls itself when each iteration completes, you should have better results:
e.g. with minimal code changes to what you have:
imgResult.onload = function(){
var x = 53, i = 1;
var compare = function() {
contextResult.clearRect(0, 0, 20, 20);
contextResult.drawImage(imgResult,x,61,20,20,0,0,20,20);
x += 23;
image2 = new Image();
image2.onload = function(){
resemble(image1.src).compareTo(image2.src).onComplete(function (data) {
$('p').append('Diffrence : ' + data.misMatchPercentage+ '%</br>');
i += 1;
if (i <= 20) {
compare();
}
});
};
image2.src = canvasResult.toDataURL();
};
compare();
}

Not getting data in kinetic js throught JSON

i am stuck in passing data from php to kineticjs throught json below is the code
$arrParams = array('images' =>$images, 'captions' => $content);
init({"container":"slider","data":<?php echo json_encode($arrParams); ?>});
i want to pass the above Json array in my below given coded kineticjs code
var data;
var canvasWidth;
var canvasHeight;
var stage;
var layer = new Kinetic.Layer();
var imageNodes = [];
var imageObjects = [];
var imageBox = [];
var captionBox = [];
var textNodes = [];
var totalObjects = 0;
var objectLoaded = 0;
var currentSlide = false;
var defaultPosition = [];
var rightCardPosition = [];
var leftCardPosition = [];
function init(config) {
canvasWidth = config.width | 600;
canvasHeight = config.height | 300;
defaultPosition["x"] = canvasWidth / 4;
defaultPosition["y"] = canvasHeight + 5;
leftCardPosition["start"] = [];
leftCardPosition["end"] = [];
leftCardPosition["start"]["x"] = (canvasWidth / 3) - 180;
leftCardPosition["start"]["y"] = canvasHeight - 260;
leftCardPosition["end"]["x"] = (canvasWidth + 100);
leftCardPosition["end"]["y"] = -250;
rightCardPosition["start"] = [];
rightCardPosition["end"] = [];
rightCardPosition["start"]["x"] = (canvasWidth / 3) + 160;
rightCardPosition["start"]["y"] = canvasHeight - 300;
rightCardPosition["end"]["x"] = (canvasWidth + 100);
rightCardPosition["end"]["y"] = -250;
stage = new Kinetic.Stage({
container: config.container,
width: canvasWidth,
height: canvasHeight
});
totalObjects = data.images.length;
for (var i = 0; i < data.images.length; i++) {
totalObjects += data.captions[i].length;
}
for (var i = 0; i < data.images.length; i++) {
loadImage(data.images[i]);
loadCaption(data.captions[i]);
}
}
I am getting error like in the line
totalObjects = data.images.length;
data is undefine... which means images is not pass from the json array
You're encoding the JSON with PHP, now you just need to parse it with JavaScript and store it in your data variable.
data = JSON.parse(config.data);
Put this at the start of your init function and it should work for you.

When dynamically creating images, why is the image array empty?

What I am trying to do is load images dynamically and then draw them on the screen. However, when I call console.log(images), it is empty.
Here is the code:
if (canvas.getContext)
{
var ctx = canvas.getContext("2d");
var images = new Array();
for (i = 0; i < mattes_array.length; i++)
{
var imgsrc = mattes_array[i]["imgsrc"];
var total_size = mattes_array[i]["total_size"];
var cpu = mattes_array[i]["cpu"];
var cid = mattes_array[i]["cid"];
var imageObj = new Image();
imageObj.onload = function() {
images[i] = imageObj;
console.log(images[i]);
};
imageObj.id = "matte_" + cid;
imageObj.src = imgsrc;
}
console.log(images); //this is empty
for (i = 0; i < mattes_array.length; i++)
{
var imgsrc = mattes_array[i]["imgsrc"];
var total_size = mattes_array[i]["total_size"];
var cpu = mattes_array[i]["cpu"];
var cid = mattes_array[i]["cid"];
var pattern = ctx.createPattern(images[i], 'repeat');
ctx.strokeStyle = pattern;
ctx.lineWidth = width - opening_width - (total_size * 2);
ctx.strokeRect(0, 0, width, height);
}
}
I have also tried doing it in one loop, but it seems to only draw the last image:
if (canvas.getContext)
{
var ctx = canvas.getContext("2d");
var images = new Array();
for (i = 0; i < mattes_array.length; i++)
{
var imgsrc = mattes_array[i]["imgsrc"];
var total_size = mattes_array[i]["total_size"];
var cpu = mattes_array[i]["cpu"];
var cid = mattes_array[i]["cid"];
var imageObj = new Image();
imageObj.onload = function() {
var pattern = ctx.createPattern(imageObj, 'repeat');
ctx.strokeStyle = pattern;
ctx.lineWidth = width - opening_width - (total_size * 2);
ctx.strokeRect(0, 0, width, height);
};
imageObj.id = "matte_" + cid;
imageObj.src = imgsrc;
}
}
Here is an image of what I am trying to do:
Images load asynchronously. You're trying to draw them before they are loaded. Give this a try:
if (canvas.getContext)
{
var ctx = canvas.getContext("2d");
var images = new Array();
var loaded = 0;
for (i = 0; i < mattes_array.length; i++)
{
var imgsrc = mattes_array[i]["imgsrc"];
var total_size = mattes_array[i]["total_size"];
var cpu = mattes_array[i]["cpu"];
var cid = mattes_array[i]["cid"];
var imageObj = new Image();
imageObj.onload = function() {
images[i] = imageObj;
console.log(images[i]);
if ( ++loaded === mattes_array.length ) onloaded();
};
imageObj.id = "matte_" + cid;
imageObj.src = imgsrc;
}
function onloaded() {
console.log(images); //this is won't be empty anymore
for (i = 0; i < mattes_array.length; i++)
{
var imgsrc = mattes_array[i]["imgsrc"];
var total_size = mattes_array[i]["total_size"];
var cpu = mattes_array[i]["cpu"];
var cid = mattes_array[i]["cid"];
var pattern = ctx.createPattern(images[i], 'repeat');
ctx.strokeStyle = pattern;
ctx.lineWidth = width - opening_width - (total_size * 2);
ctx.strokeRect(0, 0, width, height);
}
}
}

Categories