@tscircuit/schematic-trace-solver 0.0.167 → 0.0.168
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 +41 -28
- package/lib/solvers/InlineNetLabelSolver/InlineNetLabelSolver.ts +3 -8
- package/lib/solvers/InlineNetLabelSolver/getAnchoredNetLabelRenderedBounds.ts +34 -0
- package/lib/solvers/InlineNetLabelSolver/pushAnchoredNetLabelsAwayFromInlineLabels.ts +15 -16
- package/lib/solvers/InlineNetLabelSolver/pushInlineTerminalLabelsAwayFromAnchoredLabels.ts +9 -11
- package/package.json +1 -1
- package/tests/repros/__snapshots__/repro-core-ground-inline-label-fallback.snap.svg +151 -187
- package/tests/repros/repro-core-ground-inline-label-fallback.test.ts +6 -7
- package/tests/solvers/InlineNetLabelSolver/__snapshots__/inline-net-label-anchored-label-clearance.snap.svg +24 -24
- package/tests/solvers/InlineNetLabelSolver/get-anchored-net-label-rendered-bounds.test.ts +39 -0
|
@@ -8,9 +8,10 @@ const signalNetIds = new Set(["step", "direction", "enable"])
|
|
|
8
8
|
|
|
9
9
|
// Captured from @tscircuit/core's
|
|
10
10
|
// ground-net-label-preserves-solver-orientation test. These three two-pin
|
|
11
|
-
// signal nets opt into inline labels
|
|
12
|
-
//
|
|
13
|
-
|
|
11
|
+
// signal nets opt into inline labels. Neighboring shared LOGIC_3V3 and GND
|
|
12
|
+
// labels must not make post-processing mistake their terminal stubs for
|
|
13
|
+
// collisions with vertically encoded rail-label bounds.
|
|
14
|
+
test("keeps core inline signal labels near shared rail labels", () => {
|
|
14
15
|
const inputProblem: InputProblem = JSON.parse(
|
|
15
16
|
JSON.stringify(inputProblemJson),
|
|
16
17
|
)
|
|
@@ -26,9 +27,7 @@ test("repro: core inline signal labels fall back near shared rail labels", () =>
|
|
|
26
27
|
(placement) => signalNetIds.has(placement.netId ?? ""),
|
|
27
28
|
)
|
|
28
29
|
|
|
29
|
-
expect(signalInlineLabels).toHaveLength(
|
|
30
|
-
expect(
|
|
31
|
-
signalAnchoredLabels.map((placement) => placement.netId).sort(),
|
|
32
|
-
).toEqual(["direction", "direction", "enable", "enable", "step", "step"])
|
|
30
|
+
expect(signalInlineLabels).toHaveLength(6)
|
|
31
|
+
expect(signalAnchoredLabels).toHaveLength(0)
|
|
33
32
|
expect(solver).toMatchSolverSnapshot(import.meta.path)
|
|
34
33
|
})
|
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
<svg width="1200" height="2016" viewBox="0 0 1200 2016" xmlns="http://www.w3.org/2000/svg" role="img" aria-label="Solver debug visualization on top and Circuit JSON schematic on the bottom">
|
|
2
2
|
<g transform="translate(0, 0) scale(1.875, 1.875) translate(0, 0)">
|
|
3
|
-
<rect width="100%" height="100%" fill="white"/><g><polyline data-points="-0.7,0.2 -1.
|
|
4
|
-
globalConnNetId: connectivity_net0" data-x="-1.
|
|
5
|
-
globalConnNetId: connectivity_net1" data-x="-1.
|
|
3
|
+
<rect width="100%" height="100%" fill="white"/><g><polyline data-points="-0.7,0.2 -1.33,0.2" data-type="line" data-label="" points="337.880307589435,320 219.92644600468068,320" fill="none" stroke="purple" stroke-width="1px"/></g><g><polyline data-points="-0.7,0.4 -1.33,0.4" data-type="line" data-label="" points="337.880307589435,282.5543296556335 219.92644600468068,282.5543296556335" fill="none" stroke="purple" stroke-width="1px"/></g><g><polyline data-points="-0.7,0 -1.38,0" data-type="line" data-label="" points="337.880307589435,357.4456703443664 210.56502841858912,357.4456703443664" fill="none" stroke="purple" stroke-width="1px"/></g><g><rect data-type="rect" data-label="U1" data-x="0" data-y="0.2" x="337.880307589435" y="226.38582413908392" width="262.119692410565" height="187.22835172183218" fill="hsl(164, 100%, 50%, 0.8)" stroke="black" stroke-width="0.005341071428571428"/></g><g><rect data-type="rect" data-label="netId: D_MINUS
|
|
4
|
+
globalConnNetId: connectivity_net0" data-x="-1.811" data-y="0.4" x="39.99999999999997" y="263.83149448345034" width="179.73921765295887" height="37.44567034436642" fill="hsl(40, 100%, 50%, 0.35)" stroke="black" stroke-width="0.005341071428571428"/></g><g><rect data-type="rect" data-label="netId: D_PLUS
|
|
5
|
+
globalConnNetId: connectivity_net1" data-x="-1.751" data-y="0.2" x="62.46740220661985" y="301.2771648278168" width="157.27181544633902" height="37.44567034436642" fill="hsl(40, 100%, 50%, 0.35)" stroke="black" stroke-width="0.005341071428571428"/></g><g><rect data-type="rect" data-label="INLINE netId: SWCLK
|
|
6
6
|
axis: x
|
|
7
|
-
side: y+" data-x="-1.04" data-y="0.11" x="229.
|
|
8
|
-
x-" data-x="-0.7" data-y="0.4" cx="337.
|
|
9
|
-
x-" data-x="-0.7" data-y="0.2" cx="337.
|
|
10
|
-
x-" data-x="-0.7" data-y="0" cx="337.
|
|
11
|
-
orientation: x-" data-x="-1.
|
|
12
|
-
orientation: x-" data-x="-1.
|
|
13
|
-
SWCLK" data-x="-1.04" data-y="0" cx="274.
|
|
7
|
+
side: y+" data-x="-1.04" data-y="0.11" x="229.2878635907723" y="325.6168505516549" width="89.8696088264794" height="22.46740220661985" fill="hsl(40, 100%, 50%, 0.35)" stroke="black" stroke-width="0.005341071428571428"/></g><text data-type="text" data-label="SWCLK" data-x="-0.8" data-y="0.11" x="319.1574724172517" y="336.8505516549649" fill="green" font-size="22.467402206619862" font-family="sans-serif" text-anchor="end" dominant-baseline="central">SWCLK</text><g><circle data-type="point" data-label="U1.minus
|
|
8
|
+
x-" data-x="-0.7" data-y="0.4" cx="337.880307589435" cy="282.5543296556335" r="3" fill="hsl(166, 100%, 50%, 0.8)"/></g><g><circle data-type="point" data-label="U1.plus
|
|
9
|
+
x-" data-x="-0.7" data-y="0.2" cx="337.880307589435" cy="320" r="3" fill="hsl(92, 100%, 50%, 0.8)"/></g><g><circle data-type="point" data-label="U1.swclk
|
|
10
|
+
x-" data-x="-0.7" data-y="0" cx="337.880307589435" cy="357.4456703443664" r="3" fill="hsl(308, 100%, 50%, 0.8)"/></g><g><circle data-type="point" data-label="anchorPoint
|
|
11
|
+
orientation: x-" data-x="-1.33" data-y="0.4" cx="219.92644600468068" cy="282.5543296556335" r="3" fill="hsl(40, 100%, 50%, 0.9)"/></g><g><circle data-type="point" data-label="anchorPoint
|
|
12
|
+
orientation: x-" data-x="-1.33" data-y="0.2" cx="219.92644600468068" cy="320" r="3" fill="hsl(40, 100%, 50%, 0.9)"/></g><g><circle data-type="point" data-label="inline anchor
|
|
13
|
+
SWCLK" data-x="-1.04" data-y="0" cx="274.222668004012" cy="357.4456703443664" r="3" fill="green"/></g><g id="crosshair" style="display: none"><line id="crosshair-h" y1="0" y2="640" stroke="#666" stroke-width="0.5"/><line id="crosshair-v" x1="0" x2="640" stroke="#666" stroke-width="0.5"/><text id="coordinates" font-family="monospace" font-size="12" fill="#666"></text></g><script><![CDATA[
|
|
14
14
|
document.currentScript.parentElement.addEventListener('mousemove', (e) => {
|
|
15
15
|
const svg = e.currentTarget;
|
|
16
16
|
const rect = svg.getBoundingClientRect();
|
|
@@ -32,7 +32,7 @@ SWCLK" data-x="-1.04" data-y="0" cx="274.11371237458195" cy="357.4581939799331"
|
|
|
32
32
|
v.setAttribute('y2', '640');
|
|
33
33
|
|
|
34
34
|
// Calculate real coordinates using inverse transformation
|
|
35
|
-
const matrix = {"a":187.
|
|
35
|
+
const matrix = {"a":187.22835172183218,"c":0,"e":468.9401537947175,"b":0,"d":-187.22835172183218,"f":357.4456703443664};
|
|
36
36
|
// Manually invert and apply the affine transform
|
|
37
37
|
// Since we only use translate and scale, we can directly compute:
|
|
38
38
|
// x' = (x - tx) / sx
|
|
@@ -67,20 +67,20 @@ SWCLK" data-x="-1.04" data-y="0" cx="274.11371237458195" cy="357.4581939799331"
|
|
|
67
67
|
.port-label { fill: rgb(0, 100, 100); }
|
|
68
68
|
.component-name { fill: rgb(0, 100, 100); }
|
|
69
69
|
|
|
70
|
-
</style><rect class="boundary" x="0" y="0" width="1200" height="800"/><g class="trace sch-trace" data-layer="base" data-circuit-json-type="schematic_trace" data-schematic-trace-id="schematic_trace_0__stack1"><path d="M 701.
|
|
71
|
-
M 492.
|
|
72
|
-
L
|
|
73
|
-
L 166.
|
|
74
|
-
L 166.
|
|
75
|
-
L
|
|
70
|
+
</style><rect class="boundary" x="0" y="0" width="1200" height="800"/><g class="trace sch-trace" data-layer="base" data-circuit-json-type="schematic_trace" data-schematic-trace-id="schematic_trace_0__stack1"><path d="M 701.97365994024 400.00000000004 L 492.802597115166 400.00000000004" class="trace-invisible-hover-outline sch-trace-hitbox" stroke="rgb(0, 150, 0)" fill="none" stroke-width="53.122809606368px" stroke-linecap="round" opacity="0" stroke-linejoin="round"/><path class="sch-trace-path" d="M 701.97365994024 400.00000000004 L 492.802597115166 400.00000000004" stroke="rgb(0, 150, 0)" fill="none" stroke-width="6.640351200796px" stroke-linecap="round" stroke-linejoin="round"/></g><g class="trace sch-trace" data-layer="base" data-circuit-json-type="schematic_trace" data-schematic-trace-id="schematic_trace_1__stack1"><path d="M 701.97365994024 333.59648799208003 L 492.802597115166 333.59648799208003" class="trace-invisible-hover-outline sch-trace-hitbox" stroke="rgb(0, 150, 0)" fill="none" stroke-width="53.122809606368px" stroke-linecap="round" opacity="0" stroke-linejoin="round"/><path class="sch-trace-path" d="M 701.97365994024 333.59648799208003 L 492.802597115166 333.59648799208003" stroke="rgb(0, 150, 0)" fill="none" stroke-width="6.640351200796px" stroke-linecap="round" stroke-linejoin="round"/></g><g class="trace sch-trace" data-layer="base" data-circuit-json-type="schematic_trace" data-schematic-trace-id="schematic_trace_2__stack1"><path d="M 701.97365994024 466.403512008 L 476.20171911317607 466.403512008" class="trace-invisible-hover-outline sch-trace-hitbox" stroke="rgb(0, 150, 0)" fill="none" stroke-width="53.122809606368px" stroke-linecap="round" opacity="0" stroke-linejoin="round"/><path class="sch-trace-path" d="M 701.97365994024 466.403512008 L 476.20171911317607 466.403512008" stroke="rgb(0, 150, 0)" fill="none" stroke-width="6.640351200796px" stroke-linecap="round" stroke-linejoin="round"/></g><g class="trace-overlays sch-trace-overlays" data-layer="overlay" data-circuit-json-type="schematic_trace" data-schematic-trace-id="schematic_trace_0__stack1"/><g class="trace-overlays sch-trace-overlays" data-layer="overlay" data-circuit-json-type="schematic_trace" data-schematic-trace-id="schematic_trace_1__stack1"/><g class="trace-overlays sch-trace-overlays" data-layer="overlay" data-circuit-json-type="schematic_trace" data-schematic-trace-id="schematic_trace_2__stack1"/><g class="sch-component" data-circuit-json-type="schematic_component" data-schematic-component-id="schematic_component_0__stack1"><rect class="component chip sch-component-body" x="834.78068395616" y="233.99121998014002" width="199.21053602388008" height="332.01756003979995" stroke-width="6.640351200796px" fill="rgb(255, 255, 194)" stroke="rgb(132, 0, 0)"/><rect class="component-overlay sch-component-overlay" x="834.78068395616" y="233.99121998014002" width="199.21053602388008" height="332.01756003979995" fill="transparent"/><text class="sch-text" x="934.3859519681" y="400.00000000004" fill="#0f172a" text-anchor="middle" dominant-baseline="middle" font-family="sans-serif" font-size="59.763160807164px" transform="rotate(0, 934.3859519681, 400.00000000004)">U1</text><line class="component-pin sch-component-pin sch-port-line" x1="834.78068395616" y1="333.59648799208003" x2="701.97365994024" y2="333.59648799208003" stroke-width="6.640351200796px"/><g class="sch-port" data-schematic-port-id="source_port_0_0__stack1"><rect x="695.3333087394441" y="326.95613679128405" width="13.280702401592" height="13.280702401592" opacity="0"/></g><text class="pin-number sch-pin-number" x="768.3771719482" y="326.956136791284" style="font-family: sans-serif;" fill="rgb(169, 0, 0)" text-anchor="middle" dominant-baseline="auto" font-size="49.80263400597px" transform=""></text><text class="pin-number sch-pin-label" x="867.98243996014" y="333.59648799208003" style="font-family: sans-serif;" fill="rgb(169, 0, 0)" text-anchor="start" dominant-baseline="middle" font-size="49.80263400597px" transform="">minus</text><line class="component-pin sch-component-pin sch-port-line" x1="834.78068395616" y1="400.00000000004" x2="701.97365994024" y2="400.00000000004" stroke-width="6.640351200796px"/><g class="sch-port" data-schematic-port-id="source_port_0_1__stack1"><rect x="695.3333087394441" y="393.35964879924404" width="13.280702401592" height="13.280702401592" opacity="0"/></g><text class="pin-number sch-pin-number" x="768.3771719482" y="393.359648799244" style="font-family: sans-serif;" fill="rgb(169, 0, 0)" text-anchor="middle" dominant-baseline="auto" font-size="49.80263400597px" transform=""></text><text class="pin-number sch-pin-label" x="867.98243996014" y="400.00000000004" style="font-family: sans-serif;" fill="rgb(169, 0, 0)" text-anchor="start" dominant-baseline="middle" font-size="49.80263400597px" transform="">plus</text><line class="component-pin sch-component-pin sch-port-line" x1="834.78068395616" y1="466.403512008" x2="701.97365994024" y2="466.403512008" stroke-width="6.640351200796px"/><g class="sch-port" data-schematic-port-id="source_port_0_2__stack1"><rect x="695.3333087394441" y="459.76316080720403" width="13.280702401592" height="13.280702401592" opacity="0"/></g><text class="pin-number sch-pin-number" x="768.3771719482" y="459.76316080720403" style="font-family: sans-serif;" fill="rgb(169, 0, 0)" text-anchor="middle" dominant-baseline="auto" font-size="49.80263400597px" transform=""></text><text class="pin-number sch-pin-label" x="867.98243996014" y="466.403512008" style="font-family: sans-serif;" fill="rgb(169, 0, 0)" text-anchor="start" dominant-baseline="middle" font-size="49.80263400597px" transform="">swclk</text></g><g class="schematic-port-hover sch-port-hover" data-schematic-port-id="source_port_0_0__stack1"><circle cx="701.97365994024" cy="333.59648799208003" r="13.280702401592" fill="red" opacity="0"/></g><g class="schematic-port-hover sch-port-hover" data-schematic-port-id="source_port_0_1__stack1"><circle cx="701.97365994024" cy="400.00000000004" r="13.280702401592" fill="red" opacity="0"/></g><g class="schematic-port-hover sch-port-hover" data-schematic-port-id="source_port_0_2__stack1"><circle cx="701.97365994024" cy="466.403512008" r="13.280702401592" fill="red" opacity="0"/></g><path class="net-label sch-net-label" data-circuit-json-type="schematic_net_label" data-schematic-net-label-id="schematic_net_label_0__stack1" d="
|
|
71
|
+
M 492.802597115166,333.59648799208003
|
|
72
|
+
L 474.8736488730168,366.79824399606
|
|
73
|
+
L 166.00878001999223,366.79824399605997
|
|
74
|
+
L 166.00878001999223,300.3947319881
|
|
75
|
+
L 474.8736488730168,300.39473198810003
|
|
76
76
|
Z
|
|
77
|
-
" fill="rgba(255, 255, 255, 0.6)" stroke="rgb(132, 0, 0)" stroke-width="6.
|
|
78
|
-
M 492.
|
|
79
|
-
L
|
|
80
|
-
L 205.
|
|
81
|
-
L 205.
|
|
82
|
-
L
|
|
77
|
+
" fill="rgba(255, 255, 255, 0.6)" stroke="rgb(132, 0, 0)" stroke-width="6.640351200796px"/><text class="net-label-text sch-net-label-text" data-circuit-json-type="schematic_net_label" data-schematic-net-label-id="schematic_net_label_0__stack1" x="462.921016711584" y="333.59648799208003" fill="rgb(132, 0, 0)" text-anchor="end" dominant-baseline="central" font-family="sans-serif" font-variant-numeric="tabular-nums" font-size="59.763160807164px" transform="">XXXXXXX</text><path class="net-label sch-net-label" data-circuit-json-type="schematic_net_label" data-schematic-net-label-id="schematic_net_label_1__stack1" d="
|
|
78
|
+
M 492.802597115166,400.00000000004
|
|
79
|
+
L 474.8736488730168,433.20175600402
|
|
80
|
+
L 205.00977607266742,433.20175600402
|
|
81
|
+
L 205.00977607266742,366.79824399605997
|
|
82
|
+
L 474.8736488730168,366.79824399606
|
|
83
83
|
Z
|
|
84
|
-
" fill="rgba(255, 255, 255, 0.6)" stroke="rgb(132, 0, 0)" stroke-width="6.
|
|
84
|
+
" fill="rgba(255, 255, 255, 0.6)" stroke="rgb(132, 0, 0)" stroke-width="6.640351200796px"/><text class="net-label-text sch-net-label-text" data-circuit-json-type="schematic_net_label" data-schematic-net-label-id="schematic_net_label_1__stack1" x="462.921016711584" y="400.00000000004" fill="rgb(132, 0, 0)" text-anchor="end" dominant-baseline="central" font-family="sans-serif" font-variant-numeric="tabular-nums" font-size="59.763160807164px" transform="">XXXXXX</text><text class="sch-text" x="589.087689526708" y="429.881580403622" fill="#047857" text-anchor="middle" dominant-baseline="middle" font-family="sans-serif" font-size="39.842107204776px" transform="rotate(0, 589.087689526708, 429.881580403622)">XXXXX</text>
|
|
85
85
|
</g>
|
|
86
86
|
</svg>
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { expect, test } from "bun:test"
|
|
2
|
+
import { getAnchoredNetLabelRenderedBounds } from "lib/solvers/InlineNetLabelSolver/getAnchoredNetLabelRenderedBounds"
|
|
3
|
+
import type { NetLabelPlacement } from "lib/solvers/NetLabelPlacementSolver/NetLabelPlacementSolver"
|
|
4
|
+
|
|
5
|
+
const createPlacement = (
|
|
6
|
+
overrides: Partial<NetLabelPlacement>,
|
|
7
|
+
): NetLabelPlacement => ({
|
|
8
|
+
globalConnNetId: "connectivity_net0",
|
|
9
|
+
mspConnectionPairIds: [],
|
|
10
|
+
pinIds: ["U1.1"],
|
|
11
|
+
orientation: "x-",
|
|
12
|
+
anchorPoint: { x: 2, y: 3 },
|
|
13
|
+
width: 0.42,
|
|
14
|
+
height: 1.2,
|
|
15
|
+
center: { x: 1.79, y: 3 },
|
|
16
|
+
...overrides,
|
|
17
|
+
})
|
|
18
|
+
|
|
19
|
+
test("uses the horizontal renderer envelope for x-facing labels", () => {
|
|
20
|
+
const horizontalBounds = getAnchoredNetLabelRenderedBounds(
|
|
21
|
+
createPlacement({}),
|
|
22
|
+
)
|
|
23
|
+
expect(horizontalBounds.minX).toBeCloseTo(0.8)
|
|
24
|
+
expect(horizontalBounds.maxX).toBeCloseTo(2)
|
|
25
|
+
expect(horizontalBounds.minY).toBeCloseTo(2.9)
|
|
26
|
+
expect(horizontalBounds.maxY).toBeCloseTo(3.1)
|
|
27
|
+
|
|
28
|
+
const verticalBounds = getAnchoredNetLabelRenderedBounds(
|
|
29
|
+
createPlacement({
|
|
30
|
+
orientation: "y+",
|
|
31
|
+
anchorPoint: { x: 2, y: 3 },
|
|
32
|
+
center: { x: 2, y: 3.6 },
|
|
33
|
+
}),
|
|
34
|
+
)
|
|
35
|
+
expect(verticalBounds.minX).toBeCloseTo(1.79)
|
|
36
|
+
expect(verticalBounds.maxX).toBeCloseTo(2.21)
|
|
37
|
+
expect(verticalBounds.minY).toBeCloseTo(3)
|
|
38
|
+
expect(verticalBounds.maxY).toBeCloseTo(4.2)
|
|
39
|
+
})
|