Give the segment table room, and size its text columns by content
The page was capped at max-w-4xl. Eleven columns in 896px meant something was always smashed, and the previous fix just moved which one -- w-full on the note cell let it claim the slack, and w-48 on label is only a hint in an auto-layout table, so the browser shrank the label input to min-content. The cap is gone; the blocks that read better narrow keep their own. label, note and counts-toward are now measured off the longest value in the log, in ch, with floors so an empty table keeps its headers and ceilings so one long note cannot push the numbers off the side. The note's one-line clip moved onto its inner div: a max-width on a table cell is only a hint too, so pinning it to the cell could collapse the column to min-content or let it grow past the measurement. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
98f7bbef34
commit
602effde73
@ -165,6 +165,19 @@ export default function Baseline({ sources = [], sourceId, versions = [], versio
|
|||||||
} catch (err) { flash(err.message, 'error') }
|
} catch (err) { flash(err.message, 'error') }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Column widths read off the content rather than guessed. ch is the width of a
|
||||||
|
// '0', so for proportional text it runs slightly generous -- which is what is
|
||||||
|
// wanted for an input you are about to type a longer name into. The floors keep
|
||||||
|
// an empty table from collapsing its headers; the ceilings keep one long note
|
||||||
|
// from pushing the numbers off the side.
|
||||||
|
function widthCh(values, min, max) {
|
||||||
|
const longest = values.reduce((n, v) => Math.max(n, String(v || '').length), 0)
|
||||||
|
return `${Math.min(max, Math.max(min, longest + 2))}ch`
|
||||||
|
}
|
||||||
|
const labelW = widthCh(log.map(e => e.label || e.tag || e.note), 18, 40)
|
||||||
|
const bucketW = widthCh(log.map(e => e.bucket), 16, 28)
|
||||||
|
const noteW = widthCh(log.map(e => e.note), 24, 60)
|
||||||
|
|
||||||
function loadLog() {
|
function loadLog() {
|
||||||
fetch(`/api/versions/${versionId}/log`).then(r => r.json()).then(data => {
|
fetch(`/api/versions/${versionId}/log`).then(r => r.json()).then(data => {
|
||||||
setLog(data.filter(e => e.operation === 'baseline' || e.operation === 'reference'))
|
setLog(data.filter(e => e.operation === 'baseline' || e.operation === 'reference'))
|
||||||
@ -341,7 +354,10 @@ export default function Baseline({ sources = [], sourceId, versions = [], versio
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="h-full overflow-y-auto bg-gray-50">
|
<div className="h-full overflow-y-auto bg-gray-50">
|
||||||
<div className="p-4 flex flex-col gap-4 max-w-4xl">
|
{/* Uncapped: the segment table is eleven columns, and at max-w-4xl (896px)
|
||||||
|
something always got smashed no matter how the widths were divided. The
|
||||||
|
blocks that read better narrow keep their own caps. */}
|
||||||
|
<div className="p-4 flex flex-col gap-4">
|
||||||
|
|
||||||
{msg && (
|
{msg && (
|
||||||
<div className={`px-3 py-2 text-xs rounded font-medium ${msg.type === 'error' ? 'bg-red-50 text-red-700' : 'bg-green-50 text-green-700'}`}>
|
<div className={`px-3 py-2 text-xs rounded font-medium ${msg.type === 'error' ? 'bg-red-50 text-red-700' : 'bg-green-50 text-green-700'}`}>
|
||||||
@ -408,9 +424,9 @@ export default function Baseline({ sources = [], sourceId, versions = [], versio
|
|||||||
<th className="px-3 py-1.5 font-medium w-6"></th>
|
<th className="px-3 py-1.5 font-medium w-6"></th>
|
||||||
<th className="px-3 py-1.5 font-medium">#</th>
|
<th className="px-3 py-1.5 font-medium">#</th>
|
||||||
<th className="px-3 py-1.5 font-medium w-20">kind</th>
|
<th className="px-3 py-1.5 font-medium w-20">kind</th>
|
||||||
<th className="px-3 py-1.5 font-medium w-48">label</th>
|
<th className="px-3 py-1.5 font-medium" style={{ width: labelW }}>label</th>
|
||||||
<th className="px-3 py-1.5 font-medium w-full max-w-0">note</th>
|
<th className="px-3 py-1.5 font-medium" style={{ width: noteW }}>note</th>
|
||||||
<th className="px-3 py-1.5 font-medium w-36">counts toward</th>
|
<th className="px-3 py-1.5 font-medium" style={{ width: bucketW }}>counts toward</th>
|
||||||
<th className="px-3 py-1.5 font-medium text-right">rows</th>
|
<th className="px-3 py-1.5 font-medium text-right">rows</th>
|
||||||
<th className="px-3 py-1.5 font-medium text-right">{log[0]?.value_col || 'value'}</th>
|
<th className="px-3 py-1.5 font-medium text-right">{log[0]?.value_col || 'value'}</th>
|
||||||
<th className="px-3 py-1.5 font-medium">by</th>
|
<th className="px-3 py-1.5 font-medium">by</th>
|
||||||
@ -464,16 +480,16 @@ export default function Baseline({ sources = [], sourceId, versions = [], versio
|
|||||||
focus:border-blue-400 rounded px-1 py-0.5 text-xs
|
focus:border-blue-400 rounded px-1 py-0.5 text-xs
|
||||||
focus:outline-none bg-transparent" />
|
focus:outline-none bg-transparent" />
|
||||||
</td>
|
</td>
|
||||||
{/* One line, clipped. The note is provenance -- it can run
|
{/* One line, clipped against the measured width above. The
|
||||||
long -- and this row is eleven columns wide, so it used
|
note is provenance and can run long, so left to itself it
|
||||||
to wrap and push every row to two or three lines. w-full
|
wrapped and pushed every row to two or three lines.
|
||||||
plus max-w-0 is what lets a cell in an auto-layout table
|
Expanding the row shows it in full. The cap is on the div,
|
||||||
absorb the slack and still clip: without the max-w-0 the
|
not the cell: a max-width on a cell in an auto-layout table
|
||||||
column simply grows to fit the text. Expanding the row
|
is only a hint, and the column can still collapse to
|
||||||
shows it in full. */}
|
min-content or grow past it. */}
|
||||||
<td className="px-3 py-2 w-full max-w-0">
|
<td className="px-3 py-2">
|
||||||
{entry.note
|
{entry.note
|
||||||
? <div className="truncate" title={entry.note}>{entry.note}</div>
|
? <div className="truncate" style={{ maxWidth: noteW }} title={entry.note}>{entry.note}</div>
|
||||||
: <span className="text-gray-300">—</span>}
|
: <span className="text-gray-300">—</span>}
|
||||||
</td>
|
</td>
|
||||||
<td className="px-3 py-2" onClick={e => e.stopPropagation()}>
|
<td className="px-3 py-2" onClick={e => e.stopPropagation()}>
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user