Show HN:uWrap.js – 一个更快、更精确的文本换行工具,大小小于 2KB
Show HN: uWrap.js – A faster and more accurate text wrapping util in < 2KB

原始链接: https://github.com/leeoniya/uWrap

uWrap是一个极小的(压缩后小于2KB),采用MIT许可证的文本换行工具,旨在优化虚拟列表和网格中的UI性能。它能够高效地预测可变的行高,这对于处理大型数据集至关重要。针对Canvas2D缺乏原生文本换行API以及`measureText()`和DOM操作的性能限制,uWrap准确地处理字体大小、变宽字体、字母间距和显式换行符(预换行策略)。 虽然目前针对拉丁字符集进行了优化,并且缺乏Windows风格的换行符支持,但uWrap在CPU和内存使用方面显著优于canvas-hypertxt等替代方案,同时保持更高的精度。该库提供函数来计算行数、测试换行以及根据给定宽度将文本拆分为多行,所有这些都针对指定的Canvas2D上下文和字体设置进行了调整。包含TypeScript定义,方便集成。

Hacker News 最新 | 过去 | 评论 | 提问 | 展示 | 招聘 | 提交 登录 Show HN: uWrap.js – 一个更快更准确的文本换行工具,大小小于 2KB (github.com/leeoniya) 12 分,来自 leeoniya,1 小时前 | 隐藏 | 过去 | 收藏 | 讨论 加入我们 6 月 16-17 日在旧金山举办的 AI 初创公司学校! 指南 | 常见问题 | 列表 | API | 安全 | 法律 | 申请 YC | 联系我们 搜索:
相关文章

原文

A 10x faster and more accurate text wrapping util in < 2KB (min) (MIT Licensed)


uWrap exists to efficiently predict varying row heights for list and grid virtualization, a technique for UI performance optimization when rendering large, scrollable datasets. Doing this both quickly and accurately turns out to be a non-trivial task since Canvas2D provides no API for text wrapping, and measureText() is quite expensive; measuring via DOM is also a non-starter due to poor performance. Additionally, font size, variable-width fonts, letter-spacing, explicit line breaks, and different white-space choices affect the number of wrapped lines.

Notes:

  • Today, works most accurately with Latin charsets
  • Does not yet handle Windows-style \r\n explicit line breaks
  • Only pre-line wrapping strategy is implemented so far

uWrap handily out-performs canvas-hypertxt in both CPU and memory usage by a wide margin while being significantly more accurate.

The benchmark below wraps 100,000 random sentences in boxes of random widths between 50px and 250px. You can see this live in DevTools console of the demo page.


or

<script src="./dist/uWrap.iife.min.js"></script>

A 10 LoC uWrap.d.ts TypeScript def.


// import util for wrapping variable-width fonts using pre-line strategy
import { varPreLine } from 'uwrap';

// create a Canvas2D context with desired font settings
let ctx = document.createElement('canvas').getContext('2d');
ctx.font = "14px Inter, sans-serif";
ctx.letterSpacing = '0.15px';

// init util fns
const { count, test, split } = varPreLine(ctx);

// example text
let text = 'The quick brown fox jumps over the lazy dog.';

// count lines
let numLines = count(text, width);

// test if text will wrap
let willWrap = test(text, width);

// split lines (with optional limit)
let lines = split(text, width, 3);
联系我们 contact @ memedata.com