@tscircuit/schematic-trace-solver 0.0.199 → 0.0.201
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 +92 -5
- package/lib/solvers/SameNetJunctionAlignmentSolver/SameNetJunctionAlignmentSolver.ts +6 -2
- package/lib/solvers/SameNetJunctionAlignmentSolver/shortenSameSideRailToLabelAnchor.ts +62 -0
- package/lib/solvers/UnroutedTraceRecoverySolver/UnroutedTraceRecoverySolver.ts +69 -0
- package/package.json +1 -1
- package/tests/bug-reports/bug-report-20260916T054012Z/__snapshots__/bug-report-20260916T054012Z.snap.svg +2 -2
- package/tests/bug-reports/bug-report-20260916T054012Z/bug-report-20260916T054012Z.test.ts +5 -1
- package/tests/repros/__snapshots__/repro-acoustic-tuner-parallel-vref-traces.snap.svg +585 -0
- package/tests/repros/assets/repro-acoustic-tuner-parallel-vref-traces.input.json +1484 -0
- package/tests/repros/repro-acoustic-tuner-parallel-vref-traces.test.ts +50 -0
- package/tests/solvers/UnroutedTraceRecoverySolver/skip-connected-pair.test.ts +80 -0
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import { expect, test } from "bun:test"
|
|
2
|
+
import { SchematicTracePipelineSolver } from "lib/solvers/SchematicTracePipelineSolver/SchematicTracePipelineSolver"
|
|
3
|
+
import type { InputProblem } from "lib/types/InputProblem"
|
|
4
|
+
import "tests/fixtures/matcher"
|
|
5
|
+
import inputProblem from "./assets/repro-acoustic-tuner-parallel-vref-traces.input.json"
|
|
6
|
+
|
|
7
|
+
// Captured from the merged Core repro188 acoustic tuner schematic. The VREF
|
|
8
|
+
// route contains two long vertical segments separated by only a small gap.
|
|
9
|
+
test("repro acoustic tuner near-parallel VREF traces", () => {
|
|
10
|
+
const solver = new SchematicTracePipelineSolver(
|
|
11
|
+
inputProblem as unknown as InputProblem,
|
|
12
|
+
)
|
|
13
|
+
|
|
14
|
+
solver.solve()
|
|
15
|
+
|
|
16
|
+
const vrefPins = new Set(
|
|
17
|
+
inputProblem.netConnections.find(({ netId }) => netId === "VREF")!.pinIds,
|
|
18
|
+
)
|
|
19
|
+
const verticalEdges = solver
|
|
20
|
+
.netLabelToTraceSolver!.getOutput()
|
|
21
|
+
.traces.filter(({ pinIds }) =>
|
|
22
|
+
pinIds?.every((pinId) => vrefPins.has(pinId)),
|
|
23
|
+
)
|
|
24
|
+
.flatMap(({ tracePath }) =>
|
|
25
|
+
tracePath.slice(0, -1).flatMap((from, index) => {
|
|
26
|
+
const to = tracePath[index + 1]!
|
|
27
|
+
return from.x === to.x ? [{ from, to }] : []
|
|
28
|
+
}),
|
|
29
|
+
)
|
|
30
|
+
|
|
31
|
+
const hasNearParallelOverlap = verticalEdges.some((edge, edgeIndex) =>
|
|
32
|
+
verticalEdges.slice(edgeIndex + 1).some((otherEdge) => {
|
|
33
|
+
const separation = Math.abs(edge.from.x - otherEdge.from.x)
|
|
34
|
+
const overlap =
|
|
35
|
+
Math.min(
|
|
36
|
+
Math.max(edge.from.y, edge.to.y),
|
|
37
|
+
Math.max(otherEdge.from.y, otherEdge.to.y),
|
|
38
|
+
) -
|
|
39
|
+
Math.max(
|
|
40
|
+
Math.min(edge.from.y, edge.to.y),
|
|
41
|
+
Math.min(otherEdge.from.y, otherEdge.to.y),
|
|
42
|
+
)
|
|
43
|
+
|
|
44
|
+
return separation > 0 && separation <= 0.05 && overlap > 1
|
|
45
|
+
}),
|
|
46
|
+
)
|
|
47
|
+
|
|
48
|
+
expect(hasNearParallelOverlap).toBe(false)
|
|
49
|
+
expect(solver).toMatchSolverSnapshot(import.meta.path)
|
|
50
|
+
})
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import { expect, test } from "bun:test"
|
|
2
|
+
import type { MspConnectionPair } from "lib/solvers/MspConnectionPairSolver/MspConnectionPairSolver"
|
|
3
|
+
import type { SolvedTracePath } from "lib/solvers/SchematicTraceLinesSolver/SchematicTraceLinesSolver"
|
|
4
|
+
import { UnroutedTraceRecoverySolver } from "lib/solvers/UnroutedTraceRecoverySolver/UnroutedTraceRecoverySolver"
|
|
5
|
+
import type { InputProblem } from "lib/types/InputProblem"
|
|
6
|
+
|
|
7
|
+
test("does not recover a pair already joined by intersecting same-net traces", () => {
|
|
8
|
+
const inputProblem: InputProblem = {
|
|
9
|
+
chips: [
|
|
10
|
+
{
|
|
11
|
+
chipId: "A",
|
|
12
|
+
center: { x: -0.1, y: 0 },
|
|
13
|
+
width: 0.2,
|
|
14
|
+
height: 0.2,
|
|
15
|
+
pins: [{ pinId: "A.1", x: 0, y: 0, _facingDirection: "x+" }],
|
|
16
|
+
},
|
|
17
|
+
{
|
|
18
|
+
chipId: "B",
|
|
19
|
+
center: { x: 1.1, y: 0 },
|
|
20
|
+
width: 0.2,
|
|
21
|
+
height: 0.2,
|
|
22
|
+
pins: [{ pinId: "B.1", x: 1, y: 0, _facingDirection: "x-" }],
|
|
23
|
+
},
|
|
24
|
+
{
|
|
25
|
+
chipId: "C",
|
|
26
|
+
center: { x: 0.5, y: -1.1 },
|
|
27
|
+
width: 0.2,
|
|
28
|
+
height: 0.2,
|
|
29
|
+
pins: [{ pinId: "C.1", x: 0.5, y: -1, _facingDirection: "y+" }],
|
|
30
|
+
},
|
|
31
|
+
{
|
|
32
|
+
chipId: "D",
|
|
33
|
+
center: { x: 0.5, y: 1.1 },
|
|
34
|
+
width: 0.2,
|
|
35
|
+
height: 0.2,
|
|
36
|
+
pins: [{ pinId: "D.1", x: 0.5, y: 1, _facingDirection: "y-" }],
|
|
37
|
+
},
|
|
38
|
+
],
|
|
39
|
+
directConnections: [],
|
|
40
|
+
netConnections: [{ netId: "SIGNAL", pinIds: ["A.1", "B.1", "C.1", "D.1"] }],
|
|
41
|
+
availableNetLabelOrientations: {},
|
|
42
|
+
maxMspPairDistance: 2,
|
|
43
|
+
}
|
|
44
|
+
const getPin = (chipId: string) => ({
|
|
45
|
+
...inputProblem.chips.find((chip) => chip.chipId === chipId)!.pins[0]!,
|
|
46
|
+
chipId,
|
|
47
|
+
})
|
|
48
|
+
const [a, b, c, d] = ["A", "B", "C", "D"].map(getPin)
|
|
49
|
+
const makeTrace = (
|
|
50
|
+
mspPairId: string,
|
|
51
|
+
pins: MspConnectionPair["pins"],
|
|
52
|
+
): SolvedTracePath => ({
|
|
53
|
+
mspPairId,
|
|
54
|
+
mspConnectionPairIds: [mspPairId],
|
|
55
|
+
dcConnNetId: "SIGNAL",
|
|
56
|
+
globalConnNetId: "SIGNAL",
|
|
57
|
+
pins,
|
|
58
|
+
pinIds: pins.map((pin) => pin.pinId),
|
|
59
|
+
tracePath: pins,
|
|
60
|
+
})
|
|
61
|
+
const connectionPair: MspConnectionPair = {
|
|
62
|
+
mspPairId: "A.1-D.1",
|
|
63
|
+
dcConnNetId: "SIGNAL",
|
|
64
|
+
globalConnNetId: "SIGNAL",
|
|
65
|
+
pins: [a!, d!],
|
|
66
|
+
}
|
|
67
|
+
const alreadySolvedTraces = [
|
|
68
|
+
makeTrace("A.1-B.1", [a!, b!]),
|
|
69
|
+
makeTrace("C.1-D.1", [c!, d!]),
|
|
70
|
+
]
|
|
71
|
+
|
|
72
|
+
const solver = new UnroutedTraceRecoverySolver({
|
|
73
|
+
inputProblem,
|
|
74
|
+
failedConnectionPairs: [connectionPair],
|
|
75
|
+
alreadySolvedTraces,
|
|
76
|
+
})
|
|
77
|
+
solver.solve()
|
|
78
|
+
|
|
79
|
+
expect(solver.solvedUnroutedTraces).toHaveLength(0)
|
|
80
|
+
})
|