Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bounding box of form objects is incorrect for units other than 'pt' #3627

Open
HackbrettXXX opened this issue Aug 9, 2023 · 6 comments
Open

Comments

@HackbrettXXX
Copy link
Collaborator

Steps to reproduce

const doc = new jsPDF({ unit: 'mm', format: [200, 200], orientation: 'p' }) // with unit: 'pt' it works as expected

doc.advancedAPI()

doc.beginFormObject(-50, -50, 100, 100, doc.unitMatrix)
doc.rect(-50, -50, 100, 100).fill()
doc.endFormObject('0')

doc.doFormObject('0', new doc.Matrix(1, 0, 0, 1, 100, 100))

doc.setDrawColor(255, 0, 0)
doc.rect(50, 50, 100, 100).stroke()

doc.compatAPI()

Expected output

image

Actual output

image
actual.pdf
Form object:

24 0 obj
<<
/Type /XObject
/Subtype /Form
/BBox [-50. -50. -14.7222222222222285 -14.7222222222222285]
/Matrix [1. 0. 0. 1. 0. 0.]
/Length 24
>>
stream
-50. -50. 100. 100. re
f
endstream
endobj

Issue

The width and height of the bbox are scaled with the inverse scaling factor:

jsPDF/src/jspdf.js

Lines 5957 to 5964 in 5d09af9

var getPageWidth = (API.getPageWidth = function(pageNumber) {
pageNumber = pageNumber || currentPage;
return (
(pagesContext[pageNumber].mediaBox.topRightX -
pagesContext[pageNumber].mediaBox.bottomLeftX) /
scaleFactor
);
});

called by

jsPDF/src/jspdf.js

Lines 5707 to 5721 in 5d09af9

var RenderTarget = function() {
this.page = page;
this.currentPage = currentPage;
this.pages = pages.slice(0);
this.pagesContext = pagesContext.slice(0);
this.x = pageX;
this.y = pageY;
this.matrix = pageMatrix;
this.width = getPageWidth(currentPage);
this.height = getPageHeight(currentPage);
this.outputDestination = outputDestination;
this.id = ""; // set by endFormObject()
this.objectNumber = -1; // will be set by putXObject()
};

called by

jsPDF/src/jspdf.js

Lines 5751 to 5771 in 5d09af9

var endFormObject = function(key) {
// only add it if it is not already present (the keys provided by the user must be unique!)
if (renderTargetMap[key]) {
renderTargetStack.pop().restore();
return;
}
// save the created xObject
var newXObject = new RenderTarget();
var xObjectId = "Xo" + (Object.keys(renderTargets).length + 1).toString(10);
newXObject.id = xObjectId;
renderTargetMap[key] = xObjectId;
renderTargets[xObjectId] = newXObject;
events.publish("addFormObject", newXObject);
// restore state from stack
renderTargetStack.pop().restore();
};

x and y are not scaled.

The expected behavior is that x, y, with, height are all scaled by the normal (not inverse) scaling factor. This way the values passed to beginFormObject are actually interpreted with the correct unit.

This issue came up in yWorks/svg2pdf.js#244.

@Setha77
Copy link

Setha77 commented Sep 28, 2023

Hi, I would like to work on this issue. Can you assign it to me ?

@GiannyPontat
Copy link

Hi, I would like to work on this issue aswell. Can I be assigned to it too ?

@a6younes
Copy link

Hello, I would like to participate in the resolution of this issue. Can you assign it to me ?

@000-KunalPal
Copy link

hello, i would like to resolve this issue. Can you assign it to me.

@a6younes
Copy link

Hello,

There is an error in the code to reproduce the issue, it is not a const doc but a var doc. When you copy the code to reproduce the output in JsPDF, it doesn't do anything until you change the const to var.

@GiannyPontat
Copy link

Hello, this : #3682 will solve the issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants