html2canvas-pro 2.3.6 → 2.3.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/html2canvas-pro.cjs +76 -4
- package/dist/html2canvas-pro.cjs.map +1 -1
- package/dist/html2canvas-pro.esm.js +76 -4
- package/dist/html2canvas-pro.esm.js.map +1 -1
- package/dist/html2canvas-pro.js +76 -4
- package/dist/html2canvas-pro.js.map +1 -1
- package/dist/html2canvas-pro.min.js +5 -4
- package/dist/lib/core/cache-storage.js +16 -1
- package/dist/lib/css/index.js +2 -0
- package/dist/lib/css/property-descriptors/white-space.js +32 -0
- package/dist/lib/dom/element-container.js +10 -1
- package/dist/lib/render/canvas/content-renderer.js +54 -1
- package/dist/types/css/index.d.ts +2 -0
- package/dist/types/css/property-descriptors/white-space.d.ts +9 -0
- package/dist/types/render/canvas/content-renderer.d.ts +7 -0
- package/package.json +1 -1
package/dist/html2canvas-pro.cjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/*!
|
|
2
|
-
* html2canvas-pro 2.3.
|
|
2
|
+
* html2canvas-pro 2.3.8 <https://yorickshan.github.io/html2canvas-pro/>
|
|
3
3
|
* Copyright (c) 2024-present yorickshan and html2canvas-pro contributors
|
|
4
4
|
* Released under MIT License
|
|
5
5
|
*/
|
|
@@ -5164,6 +5164,23 @@ const wordBreak = {
|
|
|
5164
5164
|
}
|
|
5165
5165
|
};
|
|
5166
5166
|
//#endregion
|
|
5167
|
+
//#region src/css/property-descriptors/white-space.ts
|
|
5168
|
+
const whiteSpace = {
|
|
5169
|
+
name: "white-space",
|
|
5170
|
+
initialValue: "normal",
|
|
5171
|
+
prefix: false,
|
|
5172
|
+
type: 2,
|
|
5173
|
+
parse: (_context, value) => {
|
|
5174
|
+
switch (value) {
|
|
5175
|
+
case "pre": return "pre";
|
|
5176
|
+
case "nowrap": return "nowrap";
|
|
5177
|
+
case "pre-wrap": return "pre-wrap";
|
|
5178
|
+
case "pre-line": return "pre-line";
|
|
5179
|
+
default: return "normal";
|
|
5180
|
+
}
|
|
5181
|
+
}
|
|
5182
|
+
};
|
|
5183
|
+
//#endregion
|
|
5167
5184
|
//#region src/css/property-descriptors/writing-mode.ts
|
|
5168
5185
|
const isVerticalWritingMode = (writingMode) => writingMode !== 0;
|
|
5169
5186
|
const isSidewaysWritingMode = (writingMode) => writingMode === 3 || writingMode === 4;
|
|
@@ -6604,6 +6621,11 @@ var CSSParsedDeclaration = class CSSParsedDeclaration {
|
|
|
6604
6621
|
wordBreak,
|
|
6605
6622
|
"wordBreak"
|
|
6606
6623
|
],
|
|
6624
|
+
[
|
|
6625
|
+
"whiteSpace",
|
|
6626
|
+
whiteSpace,
|
|
6627
|
+
"whiteSpace"
|
|
6628
|
+
],
|
|
6607
6629
|
[
|
|
6608
6630
|
"writingMode",
|
|
6609
6631
|
writingMode,
|
|
@@ -7449,7 +7471,12 @@ var ElementContainer = class {
|
|
|
7449
7471
|
this.bounds = parseBounds(this.context, element);
|
|
7450
7472
|
if (element.tagName === "FIELDSET") {
|
|
7451
7473
|
const legend = element.querySelector(":scope > legend");
|
|
7452
|
-
if (legend)
|
|
7474
|
+
if (legend) {
|
|
7475
|
+
const legendBounds = parseBounds(this.context, legend);
|
|
7476
|
+
this.legendBounds = legendBounds;
|
|
7477
|
+
const borderBoxTop = legendBounds.top + legendBounds.height / 2 - this.styles.borderTopWidth / 2;
|
|
7478
|
+
this.bounds = new Bounds(this.bounds.left, borderBoxTop, this.bounds.width, this.bounds.height - (borderBoxTop - this.bounds.top));
|
|
7479
|
+
}
|
|
7453
7480
|
}
|
|
7454
7481
|
if (isDebugging(element, 4)) this.debugRender = true;
|
|
7455
7482
|
}
|
|
@@ -10357,13 +10384,57 @@ function renderFormElements(ctx, textRenderer, pathFn, container, styles) {
|
|
|
10357
10384
|
new Vector(bounds.left, bounds.top + bounds.height)
|
|
10358
10385
|
]);
|
|
10359
10386
|
ctx.clip();
|
|
10360
|
-
|
|
10387
|
+
const lines = wrapTextToWidth(ctx, container.value, bounds.width, styles.whiteSpace === "pre" || styles.whiteSpace === "nowrap");
|
|
10388
|
+
const fontSizeValue = getAbsoluteValue(styles.fontSize, 0);
|
|
10389
|
+
const lineHeight = computeLineHeight(styles.lineHeight, fontSizeValue);
|
|
10390
|
+
lines.forEach((line, index) => {
|
|
10391
|
+
let lineX = textBounds.left;
|
|
10392
|
+
const lineWidth = ctx.measureText(line).width;
|
|
10393
|
+
switch (styles.textAlign) {
|
|
10394
|
+
case 1:
|
|
10395
|
+
lineX += (bounds.width - lineWidth) / 2;
|
|
10396
|
+
break;
|
|
10397
|
+
case 2:
|
|
10398
|
+
lineX += bounds.width - lineWidth;
|
|
10399
|
+
break;
|
|
10400
|
+
}
|
|
10401
|
+
const lineBounds = new Bounds(lineX, textBounds.top + index * lineHeight, 0, 0);
|
|
10402
|
+
textRenderer.renderTextWithLetterSpacing(new TextBounds(line, lineBounds), styles.letterSpacing, baseline, styles.writingMode);
|
|
10403
|
+
});
|
|
10361
10404
|
ctx.restore();
|
|
10362
10405
|
ctx.textBaseline = "alphabetic";
|
|
10363
10406
|
ctx.textAlign = "left";
|
|
10364
10407
|
}
|
|
10365
10408
|
}
|
|
10366
10409
|
/**
|
|
10410
|
+
* Split text into lines that fit the given pixel width, preserving hard line
|
|
10411
|
+
* breaks and (when wrapping is enabled) breaking at word boundaries — mirroring
|
|
10412
|
+
* how a <textarea> lays out its value.
|
|
10413
|
+
* @internal exported for testing
|
|
10414
|
+
*/
|
|
10415
|
+
const wrapTextToWidth = (ctx, text, maxWidth, noWrap) => {
|
|
10416
|
+
const lines = [];
|
|
10417
|
+
const paragraphs = text.split("\n");
|
|
10418
|
+
for (const paragraph of paragraphs) {
|
|
10419
|
+
if (noWrap) {
|
|
10420
|
+
lines.push(paragraph);
|
|
10421
|
+
continue;
|
|
10422
|
+
}
|
|
10423
|
+
const words = paragraph.split(/(\s+)/);
|
|
10424
|
+
let line = "";
|
|
10425
|
+
for (const word of words) {
|
|
10426
|
+
const candidate = line + word;
|
|
10427
|
+
if (ctx.measureText(candidate).width <= maxWidth || line === "") line = candidate;
|
|
10428
|
+
else {
|
|
10429
|
+
lines.push(line);
|
|
10430
|
+
line = word;
|
|
10431
|
+
}
|
|
10432
|
+
}
|
|
10433
|
+
lines.push(line);
|
|
10434
|
+
}
|
|
10435
|
+
return lines;
|
|
10436
|
+
};
|
|
10437
|
+
/**
|
|
10367
10438
|
* Render list-item marker (image or text).
|
|
10368
10439
|
*/
|
|
10369
10440
|
async function renderListMarker(ctx, context, textRenderer, paint, container, styles) {
|
|
@@ -10961,7 +11032,8 @@ var Cache = class {
|
|
|
10961
11032
|
const originChecker = this.context.originChecker;
|
|
10962
11033
|
const defaultIsSameOrigin = (src) => originChecker.isSameOrigin(src);
|
|
10963
11034
|
const isSameOrigin = typeof this._options.customIsSameOrigin === "function" ? await this._options.customIsSameOrigin(key, defaultIsSameOrigin) : defaultIsSameOrigin(key);
|
|
10964
|
-
const
|
|
11035
|
+
const canAttemptCors = !isSameOrigin && this._options.allowTaint === false && !isInlineImage(key) && !isBlobImage(key) && typeof this._options.proxy !== "string";
|
|
11036
|
+
const useCORS = !isInlineImage(key) && (this._options.useCORS === true || canAttemptCors) && FEATURES.SUPPORT_CORS_IMAGES && !isSameOrigin;
|
|
10965
11037
|
const useProxy = !isInlineImage(key) && !isSameOrigin && !isBlobImage(key) && typeof this._options.proxy === "string" && FEATURES.SUPPORT_CORS_XHR && !useCORS;
|
|
10966
11038
|
if (!isSameOrigin && this._options.allowTaint === false && !isInlineImage(key) && !isBlobImage(key) && !useProxy && !useCORS) return;
|
|
10967
11039
|
let src = key;
|