circuit-to-canvas 0.0.51 → 0.0.53

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.
Files changed (35) hide show
  1. package/dist/index.d.ts +5 -2
  2. package/dist/index.js +1748 -1743
  3. package/lib/drawer/CircuitToCanvasDrawer.ts +61 -60
  4. package/lib/drawer/elements/pcb-board.ts +26 -21
  5. package/lib/drawer/elements/pcb-plated-hole.ts +3 -3
  6. package/lib/drawer/elements/pcb-soldermask/hole.ts +4 -4
  7. package/lib/drawer/elements/pcb-soldermask/index.ts +9 -9
  8. package/lib/drawer/elements/pcb-soldermask/plated-hole.ts +4 -4
  9. package/lib/drawer/elements/pcb-soldermask/smt-pad.ts +4 -4
  10. package/lib/drawer/shapes/text/getTextStartPosition.ts +10 -4
  11. package/package.json +1 -1
  12. package/tests/board-snapshot/usb-c-flashlight-board.test.ts +1 -1
  13. package/tests/elements/__snapshots__/board-with-elements.snap.png +0 -0
  14. package/tests/elements/__snapshots__/brep-copper-pours.snap.png +0 -0
  15. package/tests/elements/__snapshots__/oval-plated-hole.snap.png +0 -0
  16. package/tests/elements/__snapshots__/pcb-fabrication-note-dimension.snap.png +0 -0
  17. package/tests/elements/__snapshots__/pcb-keepout-layer-filter.snap.png +0 -0
  18. package/tests/elements/__snapshots__/pcb-keepout-multiple-layers.snap.png +0 -0
  19. package/tests/elements/__snapshots__/pcb-keepout-rect-and-circle.snap.png +0 -0
  20. package/tests/elements/__snapshots__/pcb-no-soldermask.snap.png +0 -0
  21. package/tests/elements/__snapshots__/pcb-plated-hole.snap.png +0 -0
  22. package/tests/elements/__snapshots__/pcb-silkscreen-oval.snap.png +0 -0
  23. package/tests/elements/__snapshots__/pcb-silkscreen-text-anchor-alignment.snap.png +0 -0
  24. package/tests/elements/__snapshots__/pill-plated-hole.snap.png +0 -0
  25. package/tests/elements/pcb-board.test.ts +2 -2
  26. package/tests/elements/pcb-comprehensive-soldermask-margin.test.ts +1 -1
  27. package/tests/elements/pcb-hole-soldermask-margin.test.ts +1 -1
  28. package/tests/elements/pcb-keepout-with-group-id.test.ts +1 -1
  29. package/tests/elements/pcb-plated-hole-soldermask-margin.test.ts +1 -1
  30. package/tests/elements/pcb-plated-hole.test.ts +3 -3
  31. package/tests/elements/pcb-silkscreen-text-anchor-alignment.test.ts +221 -0
  32. package/tests/elements/pcb-smtpad-asymmetric-soldermask-margin.test.ts +1 -1
  33. package/tests/elements/pcb-smtpad-soldermask-coverage.test.ts +1 -1
  34. package/tests/elements/pcb-smtpad-soldermask-margin.test.ts +1 -1
  35. package/tests/fixtures/getStackedPngSvgComparison.ts +5 -5
@@ -0,0 +1,221 @@
1
+ import { expect, test } from "bun:test"
2
+ import { createCanvas } from "@napi-rs/canvas"
3
+ import type { PcbSilkscreenText } from "circuit-json"
4
+ import { CircuitToCanvasDrawer } from "../../lib/drawer"
5
+
6
+ test("draw silkscreen text with different anchor alignments on top and bottom layers", async () => {
7
+ const SCALE = 4
8
+ const canvas = createCanvas(400 * SCALE, 300 * SCALE)
9
+ const ctx = canvas.getContext("2d")
10
+ ctx.scale(SCALE, SCALE)
11
+ const drawer = new CircuitToCanvasDrawer(ctx)
12
+
13
+ ctx.fillStyle = "#1a1a1a"
14
+ ctx.fillRect(0, 0, canvas.width / SCALE, canvas.height / SCALE)
15
+
16
+ // Draw reference lines
17
+ ctx.strokeStyle = "#444444"
18
+ ctx.lineWidth = 0.5
19
+ // Horizontal lines
20
+ ctx.beginPath()
21
+ ctx.moveTo(10, 50)
22
+ ctx.lineTo(390, 50)
23
+ ctx.stroke()
24
+ ctx.beginPath()
25
+ ctx.moveTo(10, 150)
26
+ ctx.lineTo(390, 150)
27
+ ctx.stroke()
28
+ ctx.beginPath()
29
+ ctx.moveTo(10, 250)
30
+ ctx.lineTo(390, 250)
31
+ ctx.stroke()
32
+ // Vertical lines
33
+ ctx.beginPath()
34
+ ctx.moveTo(100, 10)
35
+ ctx.lineTo(100, 290)
36
+ ctx.stroke()
37
+ ctx.beginPath()
38
+ ctx.moveTo(200, 10)
39
+ ctx.lineTo(200, 290)
40
+ ctx.stroke()
41
+ ctx.beginPath()
42
+ ctx.moveTo(300, 10)
43
+ ctx.lineTo(300, 290)
44
+ ctx.stroke()
45
+
46
+ const elements: PcbSilkscreenText[] = [
47
+ // Top layer tests
48
+ {
49
+ type: "pcb_silkscreen_text",
50
+ pcb_silkscreen_text_id: "top-top-left",
51
+ pcb_component_id: "component1",
52
+ layer: "top",
53
+ text: "TL",
54
+ anchor_position: { x: 100, y: 50 },
55
+ anchor_alignment: "top_left",
56
+ font: "tscircuit2024",
57
+ font_size: 12,
58
+ },
59
+ {
60
+ type: "pcb_silkscreen_text",
61
+ pcb_silkscreen_text_id: "top-center",
62
+ pcb_component_id: "component1",
63
+ layer: "top",
64
+ text: "TC",
65
+ anchor_position: { x: 200, y: 50 },
66
+ anchor_alignment: "top_center",
67
+ font: "tscircuit2024",
68
+ font_size: 12,
69
+ },
70
+ {
71
+ type: "pcb_silkscreen_text",
72
+ pcb_silkscreen_text_id: "top-top-right",
73
+ pcb_component_id: "component1",
74
+ layer: "top",
75
+ text: "TR",
76
+ anchor_position: { x: 300, y: 50 },
77
+ anchor_alignment: "top_right",
78
+ font: "tscircuit2024",
79
+ font_size: 12,
80
+ },
81
+ {
82
+ type: "pcb_silkscreen_text",
83
+ pcb_silkscreen_text_id: "top-center-left",
84
+ pcb_component_id: "component1",
85
+ layer: "top",
86
+ text: "CL",
87
+ anchor_position: { x: 100, y: 150 },
88
+ anchor_alignment: "center_left",
89
+ font: "tscircuit2024",
90
+ font_size: 12,
91
+ },
92
+ {
93
+ type: "pcb_silkscreen_text",
94
+ pcb_silkscreen_text_id: "top-center",
95
+ pcb_component_id: "component1",
96
+ layer: "top",
97
+ text: "C",
98
+ anchor_position: { x: 200, y: 150 },
99
+ anchor_alignment: "center",
100
+ font: "tscircuit2024",
101
+ font_size: 12,
102
+ },
103
+ {
104
+ type: "pcb_silkscreen_text",
105
+ pcb_silkscreen_text_id: "top-center-right",
106
+ pcb_component_id: "component1",
107
+ layer: "top",
108
+ text: "CR",
109
+ anchor_position: { x: 300, y: 150 },
110
+ anchor_alignment: "center_right",
111
+ font: "tscircuit2024",
112
+ font_size: 12,
113
+ },
114
+ {
115
+ type: "pcb_silkscreen_text",
116
+ pcb_silkscreen_text_id: "top-bottom-left",
117
+ pcb_component_id: "component1",
118
+ layer: "top",
119
+ text: "BL",
120
+ anchor_position: { x: 100, y: 250 },
121
+ anchor_alignment: "bottom_left",
122
+ font: "tscircuit2024",
123
+ font_size: 12,
124
+ },
125
+ {
126
+ type: "pcb_silkscreen_text",
127
+ pcb_silkscreen_text_id: "top-bottom-center",
128
+ pcb_component_id: "component1",
129
+ layer: "top",
130
+ text: "BC",
131
+ anchor_position: { x: 200, y: 250 },
132
+ anchor_alignment: "bottom_center",
133
+ font: "tscircuit2024",
134
+ font_size: 12,
135
+ },
136
+ {
137
+ type: "pcb_silkscreen_text",
138
+ pcb_silkscreen_text_id: "top-bottom-right",
139
+ pcb_component_id: "component1",
140
+ layer: "top",
141
+ text: "BR",
142
+ anchor_position: { x: 300, y: 250 },
143
+ anchor_alignment: "bottom_right",
144
+ font: "tscircuit2024",
145
+ font_size: 12,
146
+ },
147
+ // Bottom layer tests (should appear mirrored horizontally)
148
+ {
149
+ type: "pcb_silkscreen_text",
150
+ pcb_silkscreen_text_id: "bottom-top-left",
151
+ pcb_component_id: "component1",
152
+ layer: "bottom",
153
+ text: "BL-TL",
154
+ anchor_position: { x: 50, y: 50 },
155
+ anchor_alignment: "top_left",
156
+ font: "tscircuit2024",
157
+ font_size: 10,
158
+ },
159
+ {
160
+ type: "pcb_silkscreen_text",
161
+ pcb_silkscreen_text_id: "bottom-top-right",
162
+ pcb_component_id: "component1",
163
+ layer: "bottom",
164
+ text: "BL-TR",
165
+ anchor_position: { x: 350, y: 50 },
166
+ anchor_alignment: "top_right",
167
+ font: "tscircuit2024",
168
+ font_size: 10,
169
+ },
170
+ {
171
+ type: "pcb_silkscreen_text",
172
+ pcb_silkscreen_text_id: "bottom-center-left",
173
+ pcb_component_id: "component1",
174
+ layer: "bottom",
175
+ text: "BL-CL",
176
+ anchor_position: { x: 50, y: 150 },
177
+ anchor_alignment: "center_left",
178
+ font: "tscircuit2024",
179
+ font_size: 10,
180
+ },
181
+ {
182
+ type: "pcb_silkscreen_text",
183
+ pcb_silkscreen_text_id: "bottom-center-right",
184
+ pcb_component_id: "component1",
185
+ layer: "bottom",
186
+ text: "BL-CR",
187
+ anchor_position: { x: 350, y: 150 },
188
+ anchor_alignment: "center_right",
189
+ font: "tscircuit2024",
190
+ font_size: 10,
191
+ },
192
+ {
193
+ type: "pcb_silkscreen_text",
194
+ pcb_silkscreen_text_id: "bottom-bottom-left",
195
+ pcb_component_id: "component1",
196
+ layer: "bottom",
197
+ text: "BL-BL",
198
+ anchor_position: { x: 50, y: 250 },
199
+ anchor_alignment: "bottom_left",
200
+ font: "tscircuit2024",
201
+ font_size: 10,
202
+ },
203
+ {
204
+ type: "pcb_silkscreen_text",
205
+ pcb_silkscreen_text_id: "bottom-bottom-right",
206
+ pcb_component_id: "component1",
207
+ layer: "bottom",
208
+ text: "BL-BR",
209
+ anchor_position: { x: 350, y: 250 },
210
+ anchor_alignment: "bottom_right",
211
+ font: "tscircuit2024",
212
+ font_size: 10,
213
+ },
214
+ ]
215
+
216
+ drawer.drawElements(elements)
217
+
218
+ await expect(canvas.toBuffer("image/png")).toMatchPngSnapshot(
219
+ import.meta.path,
220
+ )
221
+ })
@@ -132,7 +132,7 @@ test("draw smt pads with asymmetric soldermask margins", async () => {
132
132
  ]
133
133
 
134
134
  drawer.setCameraBounds({ minX: -7, maxX: 7, minY: -5, maxY: 5 })
135
- drawer.drawElements(circuit, { showSoldermask: true })
135
+ drawer.drawElements(circuit, { drawSoldermask: true })
136
136
 
137
137
  await expect(canvas.toBuffer("image/png")).toMatchPngSnapshot(
138
138
  import.meta.path,
@@ -154,7 +154,7 @@ test("draw smt pads fully covered with soldermask and board with soldermask", as
154
154
  ]
155
155
 
156
156
  drawer.setCameraBounds({ minX: -7, maxX: 7, minY: -5, maxY: 5 })
157
- drawer.drawElements(circuit, { showSoldermask: true })
157
+ drawer.drawElements(circuit, { drawSoldermask: true })
158
158
 
159
159
  await expect(canvas.toBuffer("image/png")).toMatchPngSnapshot(
160
160
  import.meta.path,
@@ -165,7 +165,7 @@ test("draw smt pads with positive and negative soldermask margins", async () =>
165
165
  ]
166
166
 
167
167
  drawer.setCameraBounds({ minX: -7, maxX: 7, minY: -5, maxY: 5 })
168
- drawer.drawElements(circuit, { showSoldermask: true })
168
+ drawer.drawElements(circuit, { drawSoldermask: true })
169
169
 
170
170
  await expect(canvas.toBuffer("image/png")).toMatchPngSnapshot(
171
171
  import.meta.path,
@@ -1,16 +1,16 @@
1
1
  import { createCanvas } from "@napi-rs/canvas"
2
+ import { getBoundsOfPcbElements } from "@tscircuit/circuit-json-util"
3
+ import type { Bounds } from "@tscircuit/math-utils"
2
4
  import type { AnyCircuitElement } from "circuit-json"
3
5
  import { convertCircuitJsonToPcbSvg } from "circuit-to-svg"
4
- import type { Bounds } from "@tscircuit/math-utils"
5
6
  import { CircuitToCanvasDrawer } from "../../lib/drawer"
6
7
  import { stackPngsVertically, svgToPng } from "./stackPngsVertically"
7
- import { getBoundsOfPcbElements } from "@tscircuit/circuit-json-util"
8
8
 
9
9
  export interface StackedPngSvgComparisonOptions {
10
10
  width?: number
11
11
  height?: number
12
12
  padding?: number
13
- showSoldermask?: boolean
13
+ drawSoldermask?: boolean
14
14
  }
15
15
 
16
16
  /**
@@ -28,7 +28,7 @@ export async function getStackedPngSvgComparison(
28
28
  width = 400,
29
29
  height = 800,
30
30
  padding = 4,
31
- showSoldermask = false,
31
+ drawSoldermask = false,
32
32
  } = options
33
33
 
34
34
  const bounds = getBoundsOfPcbElements(circuitJson)
@@ -47,7 +47,7 @@ export async function getStackedPngSvgComparison(
47
47
  minY: bounds.minY,
48
48
  maxY: bounds.maxY,
49
49
  })
50
- drawer.drawElements(circuitJson, { showSoldermask })
50
+ drawer.drawElements(circuitJson, { drawSoldermask })
51
51
 
52
52
  const canvasPng = canvas.toBuffer("image/png")
53
53