diff options
| author | Adam Soltys <[email protected]> | 2026-08-30 16:20:57 -0700 |
|---|---|---|
| committer | Adam Soltys <[email protected]> | 2026-08-30 16:20:57 -0700 |
| commit | fbcb96a9ee16d44e5da6a39aa6b5cb16e4da24d5 (patch) | |
| tree | 396dd500328950297411cb8d13a78401e622a982 /src | |
| parent | 431907c9959e6d414fe13e05f76d1a1a45f7828e (diff) | |
| download | coinosv3-fbcb96a9ee16d44e5da6a39aa6b5cb16e4da24d5.tar.gz coinosv3-fbcb96a9ee16d44e5da6a39aa6b5cb16e4da24d5.zip | |
The coins table stops wrapping into confetti on a phone: each coin is now a two-line row — the amount, then 'expires 26d · depth 6 · exit fee 1,844 · renew 117' riding inline — so there is no header row and no five-column horizontal budget to blow; the column-header strings retire
Co-Authored-By: Claude Fable 5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01MrkLsNScXe9b6BviUSdmMr
Diffstat (limited to 'src')
| -rw-r--r-- | src/features/ark.js | 27 | ||||
| -rw-r--r-- | src/i18n.js | 6 |
2 files changed, 16 insertions, 17 deletions
diff --git a/src/features/ark.js b/src/features/ark.js index df08e35..805701a 100644 --- a/src/features/ark.js +++ b/src/features/ark.js @@ -1634,8 +1634,6 @@ export function arkFeature(ctx) { ui.arkCoinsSel = null; back(); }; - const cell = (s, extra = '') => h('span', { class: 'small', style: 'flex:1;' + extra }, s); - const head = (s, extra = '') => h('span', { class: 'small faint', style: 'flex:1;' + extra }, s); const tick = (checked, onChange, title) => h('input', { type: 'checkbox', checked, title, style: 'flex:0 0 auto;margin:0', onChange, }); @@ -1644,29 +1642,34 @@ export function arkFeature(ctx) { h('h3', { style: 'margin:0' }, t('arkCoinsTitle')), h('p', { class: 'small muted', style: 'margin:0' }, t('arkCoinsIntro', { n: spend.length, total: fmtAmount(totalSat) + ' ' + unitLabel() })), - h('div', { class: 'col', style: 'gap:4px;margin-top:4px' }, + // One coin per row, two lines: the amount, then a terse meta line. + // Five flexed columns fit a laptop but wrap into confetti on a phone + // — labels riding inline with each value need no header row and no + // horizontal budget at all. + h('div', { class: 'col', style: 'gap:8px;margin-top:4px' }, h('div', { class: 'row gap6', style: 'align-items:center' }, tick(sel.size === ids.size, (e) => { ui.arkCoinsSel = e.target.checked ? new Set(ids) : new Set(); render(); }, t('arkCoinsSelectAll')), - head(t('arkCoinsColAmount')), head(t('arkCoinsColExpires'), 'text-align:center'), - head(t('arkCoinsColDepth'), 'text-align:center'), head(t('arkCoinsColExitFee'), 'text-align:center'), - head(t('arkCoinsColFee'), 'text-align:right')), + h('span', { class: 'small faint' }, t('arkCoinsSelectAll'))), ...spend.map((v) => { const d = depthOf(v); const f = feeNowOf(v); const xf = exitFeeOf(v); - return h('div', { class: 'row gap6', style: 'align-items:center' }, + return h('div', { class: 'row gap6', style: 'align-items:flex-start' }, tick(sel.has(v.id), (e) => { e.target.checked ? sel.add(v.id) : sel.delete(v.id); render(); }), - cell(fmtAmount(v.amountSat) + ' ' + unitLabel()), - cell(expiresOf(v), 'text-align:center'), - cell(d == null ? '—' : String(d), 'text-align:center'), - cell(xf == null ? '—' : fmtAmount(xf), 'text-align:center'), - cell(f > 0 ? fmtAmount(f) : t('arkDepthFree'), 'text-align:right')); + h('div', { class: 'col grow', style: 'gap:1px;min-width:0' }, + h('span', { class: 'small' }, fmtAmount(v.amountSat) + ' ' + unitLabel()), + h('span', { class: 'small faint' }, t('arkCoinsRowMeta', { + exp: expiresOf(v), + d: d == null ? '—' : String(d), + exit: xf == null ? '—' : fmtAmount(xf), + renew: f > 0 ? fmtAmount(f) : t('arkDepthFree'), + })))); })), h('p', { class: 'small faint', style: 'margin:4px 0 0' }, t('arkCoinsExpiryNote'))), h('div', { class: 'card col', style: 'gap:8px' }, diff --git a/src/i18n.js b/src/i18n.js index 680b83e..ac2cf27 100644 --- a/src/i18n.js +++ b/src/i18n.js @@ -210,10 +210,7 @@ const STR = { arkSpentElsewhereN: '{n} coins', arkCoinsTitle: 'Spending coins', arkCoinsIntro: 'Your Spending balance lives in {n} coins totalling {total}. Each can be pulled on-chain without the server’s help — at a cost that grows with the coin’s history.', - arkCoinsColAmount: 'Amount', - arkCoinsColExpires: 'Expires', - arkCoinsColDepth: 'Depth', - arkCoinsColExitFee: 'Exit fee', + arkCoinsRowMeta: 'expires {exp} · depth {d} · exit fee {exit} · renew {renew}', arkCoinsExpiryNote: 'Past its expiry a coin can be reclaimed by the server — the wallet renews on its own well before that.', arkCoinsExitTitle: 'Uncooperative exit', arkCoinsExitDesc: 'If the server vanished today, publishing every transaction in each coin’s history would cost about {fee} sats in mining fees. After a renewal it would be one fresh coin, one hop: about {after} sats.', @@ -224,7 +221,6 @@ const STR = { arkCoinsRenewSome: 'Renew {n} selected for {fee}', arkCoinsRenewNone: 'Select coins to renew', arkCoinsSelectAll: 'Select all', - arkCoinsColFee: 'Renew fee', arkCoinsSpanDay: '1 day', arkCoinsSpanDays: '{n} days', arkCoinsSpanHour: '1 hour', |
