2 Things:
When getting access to a DOM Element in react you should always use useRef
It appears that .html method is async and requires a callback
A working example would be something like this:
import { useRef } from 'react';
import { jsPDF } from 'jspdf';
export default function PDF() {
const pdfRef = useRef(null);
const handleDownload = () => {
const content = pdfRef.current;
const doc = new jsPDF();
doc.html(content, {
callback: function (doc) {
doc.save('sample.pdf');
}
});
};
return (
<div>
<header ref={pdfRef}>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
</header>
<footer>
<button onClick={handleDownload}>Download</button>
</footer>
</div>
);
}
Update
If you need to control the size you can add additional properties as per documentation cited above:
Option 1 - use the html2canvas option and control the scale:
const handleDownload = () => {
const content = pdfRef.current;
const doc = new jsPDF();
doc.html(content, {
callback: function (doc) {
doc.save('sample.pdf');
},
html2canvas: { scale: 0.5 } // change the scale to whatever number you need
});
};
Option 2 - use width and windowWidth:
const handleDownload = () => {
const content = pdfRef.current;
const doc = new jsPDF();
doc.html(content, {
callback: function (doc) {
doc.save('sample.pdf');
},
width: 200, // <- here
windowWidth: 200 // <- here
});
};
Answer from SakoBu on Stack Overflow
» npm install jspdf
Videos
2 Things:
When getting access to a DOM Element in react you should always use useRef
It appears that .html method is async and requires a callback
A working example would be something like this:
import { useRef } from 'react';
import { jsPDF } from 'jspdf';
export default function PDF() {
const pdfRef = useRef(null);
const handleDownload = () => {
const content = pdfRef.current;
const doc = new jsPDF();
doc.html(content, {
callback: function (doc) {
doc.save('sample.pdf');
}
});
};
return (
<div>
<header ref={pdfRef}>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
<div>l kldfjlkasjfld asjflkajf ljfasd'flksdasjf lsdasjfsadf</div>
</header>
<footer>
<button onClick={handleDownload}>Download</button>
</footer>
</div>
);
}
Update
If you need to control the size you can add additional properties as per documentation cited above:
Option 1 - use the html2canvas option and control the scale:
const handleDownload = () => {
const content = pdfRef.current;
const doc = new jsPDF();
doc.html(content, {
callback: function (doc) {
doc.save('sample.pdf');
},
html2canvas: { scale: 0.5 } // change the scale to whatever number you need
});
};
Option 2 - use width and windowWidth:
const handleDownload = () => {
const content = pdfRef.current;
const doc = new jsPDF();
doc.html(content, {
callback: function (doc) {
doc.save('sample.pdf');
},
width: 200, // <- here
windowWidth: 200 // <- here
});
};
// use can you ReactDOMServer.renderToString(element)
import { renderToString } from "react-dom/server";
import { jsPDF } from "jspdf";
export const dow = () => {
let htmlElement = <div>Hello </div>
let elementAsString = renderToString(htmlElement);
var doc = new jsPDF();
doc.html(elementAsString, {
callback: function (doc) {
doc.save("test.pdf");
},
x: 10,
y: 10,
});
};
// use can use this code as function to handle an event
» npm install jspdf-react
Step1:
Package.json dependencies
"jspdf": "git://github.com/MrRio/jsPDF/#76edb3387cda3d5292e212765134b06150030364",
This is due to jspdf for npm is not working.
Step2:
Add print function:
onPrint() {
const { vehicleData } = this.props.parkedVehicle;
const {
plate_no,
max_time,
entry_date_time,
exit_date_time,
expiry_time,
address1,
address2,
city,
state,
zip,
country,
parking_status
} = vehicleData;
var pdfConverter = require('jspdf');
//var converter = new pdfConverter();
//var doc = converter.jsPDF('p', 'pt');
var doc = new pdfConverter('p','pt','c6');
doc.setFontSize(22);
doc.text(20, 50, 'Park Entry Ticket');
doc.setFontSize(16);
doc.text(20, 80, 'Address1: ' + address1);
doc.text(20, 100, 'Address2: ' + address2);
doc.text(20, 120, 'Entry Date & time: ' + entry_date_time);
doc.text(20, 140, 'Expiry date & time: ' + exit_date_time);
doc.save("test.pdf");
}
And It worked fine to me.
We can now also convert React components directly to pdf.
The idea is to pass the react-rendered through following transformation: DOM -> CANVAS -> PNG -> PDF
For DOM to Canvas, we can use the html2canvas library. Canvas to PNG is straight forward. From PNG to PDF, we can use jsDom.
I've posted an answer explaining the same with more details and code samples here.