pretext

pretext で行折り返しを計算し、文字単位でマウスを避けるインタラクション。

textlayoutcanvas 2026-04
experiment
code
import { prepareWithSegments, layoutWithLines } from "@chenglou/pretext";

// 1. pretext で行折り返し位置を計算(DOM 計測なし)
const prepared = prepareWithSegments(text, font);
const { lines } = layoutWithLines(prepared, containerWidth, lineHeight);

// 2. 各文字の静止座標を確定
const chars = [];
for (const [i, line] of lines.entries()) {
  let x = 0;
  for (const ch of line.text) {
    const w = ctx.measureText(ch).width;
    chars.push({ ch, restX: x, restY: i * lineHeight, x, y, vx: 0, vy: 0 });
    x += w;
  }
}

// 3. フレームごとにスプリング + マウス反発
function tick() {
  for (const c of chars) {
    const dx = c.x - mouse.x, dy = c.y - mouse.y;
    const dist = Math.hypot(dx, dy);
    if (dist < RADIUS) {
      const force = (RADIUS - dist) / RADIUS * STRENGTH;
      c.vx += (dx / dist) * force;
      c.vy += (dy / dist) * force;
    }
    c.vx += (c.restX - c.x) * STIFFNESS;
    c.vy += (c.restY - c.y) * STIFFNESS;
    c.vx *= DAMPING; c.vy *= DAMPING;
    c.x += c.vx;   c.y += c.vy;
  }
}

chenglou/pretext で行折り返し位置を事前計算し、 文字ごとの静止座標を確定。あとは Canvas 上でスプリング物理だけで動かしている。 テキストエリアに入力すると文字が更新される。