fix(createCharacterComparison): change line break logic to ensure correct text wrap
All checks were successful
Workflow / build (pull_request) Successful in 1m14s
Workflow / publish (pull_request) Has been skipped

This commit is contained in:
Ilia Mashkov
2026-02-10 11:47:54 +03:00
parent 1fc9572f3d
commit faf9b8570b

View File

@@ -150,42 +150,63 @@ export function createCharacterComparison<
currentLineWords = []; currentLineWords = [];
} }
let remainingWord = word; const wordWidthA = measureText(
while (remainingWord.length > 0) { ctx,
let low = 1; word,
let high = remainingWord.length; Math.min(fontSize, controlledFontSize),
let bestBreak = 1; currentWeight,
fontA()?.name,
);
const wordWidthB = measureText(
ctx,
word,
Math.min(fontSize, controlledFontSize),
currentWeight,
fontB()?.name,
);
const wordAloneWidth = Math.max(wordWidthA, wordWidthB);
// Binary Search to find the maximum characters that fit if (wordAloneWidth <= availableWidth) {
while (low <= high) { // If word fits start new line with it
const mid = Math.floor((low + high) / 2); currentLineWords = [word];
const testFragment = remainingWord.slice(0, mid); } else {
let remainingWord = word;
while (remainingWord.length > 0) {
let low = 1;
let high = remainingWord.length;
let bestBreak = 1;
const wA = measureText( // Binary Search to find the maximum characters that fit
ctx, while (low <= high) {
testFragment, const mid = Math.floor((low + high) / 2);
fontSize, const testFragment = remainingWord.slice(0, mid);
currentWeight,
fontA()?.name,
);
const wB = measureText(
ctx,
testFragment,
fontSize,
currentWeight,
fontB()?.name,
);
if (Math.max(wA, wB) <= availableWidth) { const wA = measureText(
bestBreak = mid; ctx,
low = mid + 1; testFragment,
} else { fontSize,
high = mid - 1; currentWeight,
fontA()?.name,
);
const wB = measureText(
ctx,
testFragment,
fontSize,
currentWeight,
fontB()?.name,
);
if (Math.max(wA, wB) <= availableWidth) {
bestBreak = mid;
low = mid + 1;
} else {
high = mid - 1;
}
} }
}
pushLine([remainingWord.slice(0, bestBreak)]); pushLine([remainingWord.slice(0, bestBreak)]);
remainingWord = remainingWord.slice(bestBreak); remainingWord = remainingWord.slice(bestBreak);
}
} }
} else if (maxWidth > availableWidth && currentLineWords.length > 0) { } else if (maxWidth > availableWidth && currentLineWords.length > 0) {
pushLine(currentLineWords); pushLine(currentLineWords);