@tscircuit/pcb-viewer 1.11.273 → 1.11.275

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/index.js CHANGED
@@ -9386,52 +9386,97 @@ import { lineAlphabet, svgAlphabet } from "@tscircuit/alphabet";
9386
9386
  // src/lib/convert-text-to-lines.ts
9387
9387
  var LETTER_HEIGHT_TO_WIDTH_RATIO = 0.6;
9388
9388
  var LETTER_HEIGHT_TO_SPACE_RATIO = 0.2;
9389
- var getTextWidth = (text) => {
9390
- if (text.text.length === 0) return 0;
9389
+ var LOWERCASE_BASELINE_OFFSET = (() => {
9390
+ const referenceLetters = ["a", "c", "e", "m", "n", "o", "r", "s", "u", "x"];
9391
+ const offsets = referenceLetters.map((letter) => lineAlphabet[letter]).filter((lines) => lines && lines.length > 0).map(
9392
+ (lines) => Math.min(...lines.map((line) => Math.min(line.y1, line.y2)))
9393
+ );
9394
+ return offsets.length > 0 ? Math.min(...offsets) : 0;
9395
+ })();
9396
+ var getBaselineOffsetForLetter = (letter) => letter >= "a" && letter <= "z" ? LOWERCASE_BASELINE_OFFSET : 0;
9397
+ var getTextGeometry = (text) => {
9391
9398
  const target_height = text.size * 0.7;
9392
9399
  const target_width_char = target_height * LETTER_HEIGHT_TO_WIDTH_RATIO;
9393
9400
  const space_between_chars = target_height * LETTER_HEIGHT_TO_SPACE_RATIO;
9394
- return text.text.length * target_width_char + (text.text.length - 1) * space_between_chars;
9401
+ const space_between_lines = target_height * LETTER_HEIGHT_TO_SPACE_RATIO;
9402
+ const text_lines = text.text.split(/\r?\n/);
9403
+ const has_text = text.text.length > 0 && target_height > 0;
9404
+ const line_count = has_text ? text_lines.length : 0;
9405
+ const line_widths = has_text ? text_lines.map((line) => {
9406
+ if (line.length === 0) return 0;
9407
+ return line.length * target_width_char + (line.length - 1) * space_between_chars;
9408
+ }) : [];
9409
+ const width = line_widths.length > 0 ? Math.max(...line_widths) : 0;
9410
+ const hasLowercase = /[a-z]/.test(text.text);
9411
+ const baselineOffset = hasLowercase ? LOWERCASE_BASELINE_OFFSET * target_height : 0;
9412
+ const height = line_count > 0 ? line_count * target_height + (line_count - 1) * space_between_lines + baselineOffset : 0;
9413
+ return {
9414
+ text_lines,
9415
+ line_count,
9416
+ target_height,
9417
+ target_width_char,
9418
+ space_between_chars,
9419
+ space_between_lines,
9420
+ width,
9421
+ height
9422
+ };
9423
+ };
9424
+ var getTextMetrics = (text) => {
9425
+ const geometry = getTextGeometry(text);
9426
+ return {
9427
+ width: geometry.width,
9428
+ height: geometry.height,
9429
+ lineHeight: geometry.target_height,
9430
+ lineSpacing: geometry.space_between_lines,
9431
+ lineCount: geometry.line_count
9432
+ };
9395
9433
  };
9396
9434
  var convertTextToLines = (text) => {
9397
- const target_height = text.size * 0.7;
9398
- if (target_height <= 0 || text.text.length === 0) return [];
9435
+ const {
9436
+ text_lines,
9437
+ line_count,
9438
+ target_height,
9439
+ target_width_char,
9440
+ space_between_chars,
9441
+ space_between_lines
9442
+ } = getTextGeometry(text);
9443
+ if (target_height <= 0 || line_count === 0) return [];
9399
9444
  const strokeWidth = target_height / 12;
9400
- const centerline_span_y = Math.max(0, target_height - strokeWidth);
9401
- const y_baseline_offset = strokeWidth / 2;
9402
- const target_width_char = target_height * LETTER_HEIGHT_TO_WIDTH_RATIO;
9403
- const centerline_span_x = Math.max(0, target_width_char - strokeWidth);
9404
- const x_char_start_offset = strokeWidth / 2;
9405
- const space_between_chars = target_height * LETTER_HEIGHT_TO_SPACE_RATIO;
9406
9445
  const lines = [];
9407
- let current_x_origin_for_char_box = text.x;
9408
- for (let letterIndex = 0; letterIndex < text.text.length; letterIndex++) {
9409
- const letter = text.text[letterIndex];
9410
- const letterLines = lineAlphabet[letter] ?? lineAlphabet[letter.toUpperCase()];
9411
- if (!letterLines) {
9446
+ for (let lineIndex = 0; lineIndex < line_count; lineIndex++) {
9447
+ const lineYOffset = lineIndex * (target_height + space_between_lines);
9448
+ let current_x_origin_for_char_box = text.x;
9449
+ for (let letterIndex = 0; letterIndex < text_lines[lineIndex].length; letterIndex++) {
9450
+ const letter = text_lines[lineIndex][letterIndex];
9451
+ const letterLines = lineAlphabet[letter] ?? lineAlphabet[letter.toUpperCase()];
9452
+ const baselineOffset = getBaselineOffsetForLetter(letter);
9453
+ if (!letterLines) {
9454
+ current_x_origin_for_char_box += target_width_char + space_between_chars;
9455
+ continue;
9456
+ }
9457
+ for (const {
9458
+ x1: norm_x1,
9459
+ y1: norm_y1,
9460
+ x2: norm_x2,
9461
+ y2: norm_y2
9462
+ } of letterLines) {
9463
+ const adjusted_y1 = norm_y1 - baselineOffset;
9464
+ const adjusted_y2 = norm_y2 - baselineOffset;
9465
+ lines.push({
9466
+ _pcb_drawing_object_id: getNewPcbDrawingObjectId("line"),
9467
+ pcb_drawing_type: "line",
9468
+ x1: current_x_origin_for_char_box + target_width_char * norm_x1,
9469
+ y1: text.y + lineYOffset + target_height * adjusted_y1,
9470
+ x2: current_x_origin_for_char_box + target_width_char * norm_x2,
9471
+ y2: text.y + lineYOffset + target_height * adjusted_y2,
9472
+ width: strokeWidth,
9473
+ layer: text.layer,
9474
+ unit: text.unit,
9475
+ color: text.color
9476
+ });
9477
+ }
9412
9478
  current_x_origin_for_char_box += target_width_char + space_between_chars;
9413
- continue;
9414
- }
9415
- for (const {
9416
- x1: norm_x1,
9417
- y1: norm_y1,
9418
- x2: norm_x2,
9419
- y2: norm_y2
9420
- } of letterLines) {
9421
- lines.push({
9422
- _pcb_drawing_object_id: getNewPcbDrawingObjectId("line"),
9423
- pcb_drawing_type: "line",
9424
- x1: current_x_origin_for_char_box + x_char_start_offset + centerline_span_x * norm_x1,
9425
- y1: text.y + y_baseline_offset + centerline_span_y * norm_y1,
9426
- x2: current_x_origin_for_char_box + x_char_start_offset + centerline_span_x * norm_x2,
9427
- y2: text.y + y_baseline_offset + centerline_span_y * norm_y2,
9428
- width: strokeWidth,
9429
- layer: text.layer,
9430
- unit: text.unit,
9431
- color: text.color
9432
- });
9433
9479
  }
9434
- current_x_origin_for_char_box += target_width_char + space_between_chars;
9435
9480
  }
9436
9481
  return lines;
9437
9482
  };
@@ -9467,8 +9512,7 @@ var drawText = (drawer, text) => {
9467
9512
  layer: text.layer
9468
9513
  });
9469
9514
  let alignOffset = { x: 0, y: 0 };
9470
- const textWidth = getTextWidth(text);
9471
- const textHeight = text.size;
9515
+ const { width: textWidth, height: textHeight } = getTextMetrics(text);
9472
9516
  switch (text.align) {
9473
9517
  case "top_left":
9474
9518
  alignOffset.x = 0;
@@ -13261,7 +13305,7 @@ import { css as css3 } from "@emotion/css";
13261
13305
  // package.json
13262
13306
  var package_default = {
13263
13307
  name: "@tscircuit/pcb-viewer",
13264
- version: "1.11.272",
13308
+ version: "1.11.274",
13265
13309
  main: "dist/index.js",
13266
13310
  type: "module",
13267
13311
  repository: "tscircuit/pcb-viewer",