fix(ui): crowded pin headers escaped the inspector - draw those labels vertically
An SSD1306 has 8 pins along a 240px header. Horizontal labels need ~36px each = 288px, so they overflowed the art box and rendered outside the dialog, over the header and the canvas. Top/bottom labels are now vertical text - what printed pinout diagrams do - which needs only the side spacing, and the gutter grows to fit. The preview also clips, so nothing can escape again.
This commit is contained in:
parent
d4a42a4e75
commit
b02aab9a47
|
|
@ -127,6 +127,27 @@ describe('layoutInspectorPins — small parts', () => {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('layoutInspectorPins — a crowded header fits its edge', () => {
|
||||||
|
it('packs 8 top pins inside the art width (they are drawn as vertical text)', () => {
|
||||||
|
// The SSD1306's 8-pin header measured 240px wide in the dialog. With
|
||||||
|
// horizontal labels this demanded ~288px and the labels escaped the
|
||||||
|
// dialog; vertical labels use the side spacing instead.
|
||||||
|
const pins: InspectorPinInput[] = Array.from({ length: 8 }, (_, i) => ({
|
||||||
|
name: ['DATA', 'CLK', 'DC', 'RST', 'CS', '3V3', 'VIN', 'GND'][i],
|
||||||
|
x: 14 + i * 13,
|
||||||
|
y: 2,
|
||||||
|
}));
|
||||||
|
const r = layoutInspectorPins(pins, { width: 128, height: 119 });
|
||||||
|
for (const p of r.pins) expect(p.edge).toBe('top');
|
||||||
|
const xs = r.pins.map((p) => p.labelX).sort((a, b) => a - b);
|
||||||
|
expect(xs[0]).toBeGreaterThanOrEqual(0);
|
||||||
|
expect(xs[xs.length - 1]).toBeLessThanOrEqual(r.artWidth);
|
||||||
|
for (let i = 1; i < xs.length; i++) {
|
||||||
|
expect(xs[i] - xs[i - 1]).toBeGreaterThanOrEqual(16 - 1e-6);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('layoutInspectorPins — interior pins', () => {
|
describe('layoutInspectorPins — interior pins', () => {
|
||||||
it('detects a pin far from every edge and anchors its label on the dot', () => {
|
it('detects a pin far from every edge and anchors its label on the dot', () => {
|
||||||
const r = layoutInspectorPins(
|
const r = layoutInspectorPins(
|
||||||
|
|
|
||||||
|
|
@ -147,6 +147,9 @@
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
|
/* Labels are laid out inside the reserved gutters; clip anything that still
|
||||||
|
overshoots rather than letting it escape over the header or the canvas. */
|
||||||
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
.pid-preview-art {
|
.pid-preview-art {
|
||||||
|
|
@ -248,8 +251,16 @@
|
||||||
transform: translate(-100%, -50%);
|
transform: translate(-100%, -50%);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Top/bottom labels are VERTICAL, like a printed pinout diagram: a header row
|
||||||
|
packs pins every ~12px, where horizontal text would need ~36px and spill
|
||||||
|
out of the dialog (an 8-pin SSD1306 header is 240px wide). */
|
||||||
|
.pid-pin-label--top,
|
||||||
|
.pid-pin-label--bottom {
|
||||||
|
writing-mode: vertical-rl;
|
||||||
|
}
|
||||||
|
|
||||||
.pid-pin-label--top {
|
.pid-pin-label--top {
|
||||||
transform: translate(-50%, -100%);
|
transform: translate(-50%, -100%) rotate(180deg);
|
||||||
}
|
}
|
||||||
|
|
||||||
.pid-pin-label--bottom {
|
.pid-pin-label--bottom {
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1 @@
|
||||||
|
/home/dave/velxio-prod/pro/frontend/src/pro
|
||||||
|
|
@ -69,10 +69,14 @@ export interface PinLayoutOptions {
|
||||||
|
|
||||||
/** Horizontal gutter for left/right label columns (room for "GND2" etc.). */
|
/** Horizontal gutter for left/right label columns (room for "GND2" etc.). */
|
||||||
const SIDE_GUTTER = 72;
|
const SIDE_GUTTER = 72;
|
||||||
/** Vertical gutter for top/bottom labels (one text line + leader). */
|
/**
|
||||||
const CAP_GUTTER = 28;
|
* Vertical gutter for top/bottom labels. Those are drawn as VERTICAL text —
|
||||||
/** Top/bottom labels are horizontal text, so they need more room than 16px. */
|
* the way printed pinout diagrams do it — because horizontal ones do not fit:
|
||||||
const CAP_MIN_SPACING = 36;
|
* an SSD1306 has 8 pins along a 240px edge, and at the ~36px a horizontal
|
||||||
|
* "DATA" needs they demand 288px and spill out of the dialog. Vertical text
|
||||||
|
* needs only the same spacing as a side column, and the gutter grows instead.
|
||||||
|
*/
|
||||||
|
const CAP_GUTTER = 52;
|
||||||
/** Small parts (a resistor is 107x11) are upscaled, but only this far. */
|
/** Small parts (a resistor is 107x11) are upscaled, but only this far. */
|
||||||
const MAX_UPSCALE = 2;
|
const MAX_UPSCALE = 2;
|
||||||
|
|
||||||
|
|
@ -197,7 +201,7 @@ export function layoutInspectorPins(
|
||||||
const group = byEdge(edge);
|
const group = byEdge(edge);
|
||||||
const { out, nudged } = stackLabels(
|
const { out, nudged } = stackLabels(
|
||||||
group.map(([c]) => c.x),
|
group.map(([c]) => c.x),
|
||||||
Math.max(minSpacing, CAP_MIN_SPACING),
|
minSpacing,
|
||||||
W,
|
W,
|
||||||
);
|
);
|
||||||
group.forEach(([c, i], k) => {
|
group.forEach(([c, i], k) => {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue