[feat](trx-frontend-http): centre the radio controls, split off the mode row
The controls every rig has — mode, wheel, tune step, transmit — now sit as a centred block rather than packed against the left edge. What the current mode adds moves out from among them: WFM's six controls stretched the row sideways whenever it was active, pushing the wheel and the step pickers off centre, and SAM did the same on a smaller scale. They get a row of their own below a divider, which appears and leaves with them — an empty one would still take a track and a gap in the tray and draw its divider under controls it has nothing to do with. Signed-off-by: Stan Grams <sjg@haxx.space>
This commit is contained in:
@@ -6201,6 +6201,7 @@ var wfmCciValEl = document.getElementById("wfm-cci-val");
|
||||
var wfmAciFillEl = document.getElementById("wfm-aci-fill");
|
||||
var wfmAciValEl = document.getElementById("wfm-aci-val");
|
||||
var samControlsCol = document.getElementById("sam-controls-col");
|
||||
var modeControlsRow = document.getElementById("mode-controls-row");
|
||||
var samStereoWidthEl = document.getElementById("sam-stereo-width");
|
||||
var samCarrierSyncEl = document.getElementById("sam-carrier-sync");
|
||||
var sdrSquelchWrapEl = document.getElementById("sdr-squelch-wrap");
|
||||
@@ -6508,6 +6509,7 @@ function updateWfmControls() {
|
||||
const mode = (modeEl && modeEl.value ? modeEl.value : "").toUpperCase();
|
||||
if (wfmControlsCol) wfmControlsCol.style.display = mode === "WFM" ? "" : "none";
|
||||
if (samControlsCol) samControlsCol.style.display = mode === "SAM" ? "" : "none";
|
||||
if (modeControlsRow) modeControlsRow.style.display = mode === "WFM" || mode === "SAM" ? "" : "none";
|
||||
}
|
||||
if (!hasWebCodecs) {
|
||||
rxAudioBtn.disabled = true;
|
||||
|
||||
@@ -256,6 +256,16 @@ SPDX-License-Identifier: GPL-2.0-or-later
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="controls-col controls-col-power label-below-col" id="tx-power-col">
|
||||
<div class="label"><span>Transmit / Power</span></div>
|
||||
<div class="btn-grid">
|
||||
<button id="ptt-btn" type="button" aria-pressed="false">Start TX</button>
|
||||
<button id="power-btn" type="button" aria-pressed="false">Power On</button>
|
||||
<button id="lock-btn" type="button" aria-pressed="false">Lock Tuning</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="controls-row controls-row-mode full-row" id="mode-controls-row" style="display:none">
|
||||
<div class="controls-col controls-col-wfm label-below-col" id="wfm-controls-col" style="display:none;">
|
||||
<div class="inline wfm-controls-inline">
|
||||
<label class="wfm-control">
|
||||
@@ -313,14 +323,6 @@ SPDX-License-Identifier: GPL-2.0-or-later
|
||||
</div>
|
||||
<div class="label"><span>SAM</span></div>
|
||||
</div>
|
||||
<div class="controls-col controls-col-power label-below-col" id="tx-power-col">
|
||||
<div class="label"><span>Transmit / Power</span></div>
|
||||
<div class="btn-grid">
|
||||
<button id="ptt-btn" type="button" aria-pressed="false">Start TX</button>
|
||||
<button id="power-btn" type="button" aria-pressed="false">Power On</button>
|
||||
<button id="lock-btn" type="button" aria-pressed="false">Lock Tuning</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="full-row label-below-row" id="vfo-row">
|
||||
<div class="label"><span>VFO</span></div>
|
||||
|
||||
@@ -278,9 +278,17 @@ input.status-input, select.status-input { width: 100%; padding: 0.45rem 0.5rem;
|
||||
.controls-row {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
justify-content: center;
|
||||
gap: 1rem 1.25rem;
|
||||
align-items: flex-start;
|
||||
}
|
||||
/* Whatever the current mode adds — WFM's deemphasis and interference meters,
|
||||
SAM's carrier sync — sits on its own line under the controls every rig has,
|
||||
instead of stretching the row sideways when one mode happens to be active. */
|
||||
.controls-row-mode {
|
||||
padding-top: 0.85rem;
|
||||
border-top: 1px solid color-mix(in srgb, var(--border-light) 45%, transparent);
|
||||
}
|
||||
.controls-col {
|
||||
min-width: 0;
|
||||
display: flex;
|
||||
|
||||
@@ -5145,6 +5145,7 @@ const wfmCciValEl = document.getElementById("wfm-cci-val");
|
||||
const wfmAciFillEl = document.getElementById("wfm-aci-fill");
|
||||
const wfmAciValEl = document.getElementById("wfm-aci-val");
|
||||
const samControlsCol = document.getElementById("sam-controls-col");
|
||||
const modeControlsRow = document.getElementById("mode-controls-row");
|
||||
const samStereoWidthEl = document.getElementById("sam-stereo-width") as HTMLInputElement | null;
|
||||
const samCarrierSyncEl = document.getElementById("sam-carrier-sync") as HTMLSelectElement | null;
|
||||
const sdrSquelchWrapEl = document.getElementById("sdr-squelch-wrap");
|
||||
@@ -5463,6 +5464,9 @@ function updateWfmControls() {
|
||||
const mode = (modeEl && modeEl.value ? modeEl.value : "").toUpperCase();
|
||||
if (wfmControlsCol) wfmControlsCol.style.display = mode === "WFM" ? "" : "none";
|
||||
if (samControlsCol) samControlsCol.style.display = mode === "SAM" ? "" : "none";
|
||||
// The row holds only these two, so it goes with them — an empty one would
|
||||
// still take a track and a gap in the tray, and draw its divider.
|
||||
if (modeControlsRow) modeControlsRow.style.display = (mode === "WFM" || mode === "SAM") ? "" : "none";
|
||||
}
|
||||
|
||||
// Show compatibility warning for non-Chromium browsers
|
||||
|
||||
@@ -49,6 +49,23 @@ try {
|
||||
assert.equal(modeAfter.active, target, "the clicked mode is not the marked one");
|
||||
assert.ok(modeAfter.selectWidth <= 2, `the hidden select still occupies ${modeAfter.selectWidth}px`);
|
||||
|
||||
// Mode-specific controls live on their own row, which has to leave with them:
|
||||
// an empty one would still take a track and a gap in the tray and draw its
|
||||
// divider under the controls every rig has.
|
||||
const modeRowState = async () => page.evaluate(() => {
|
||||
const row = document.getElementById("mode-controls-row");
|
||||
return { display: getComputedStyle(row).display, height: Math.round(row.getBoundingClientRect().height) };
|
||||
});
|
||||
await page.locator('#mode-picker button[data-mode="WFM"]').click();
|
||||
await page.waitForTimeout(250);
|
||||
const withWfm = await modeRowState();
|
||||
assert.notEqual(withWfm.display, "none", "WFM controls did not bring their row up");
|
||||
assert.ok(withWfm.height > 0, `WFM row has no height (${withWfm.height}px)`);
|
||||
await page.locator('#mode-picker button[data-mode="FM"]').click();
|
||||
await page.waitForTimeout(250);
|
||||
const withoutWfm = await modeRowState();
|
||||
assert.equal(withoutWfm.display, "none", "the mode row stayed behind with nothing in it");
|
||||
|
||||
// Scheduler controls read left to right: step, hand back, then the entry on
|
||||
// air. The separator is drawn by the current-entry block, so it can only sit
|
||||
// in the right place if that block is last.
|
||||
|
||||
Reference in New Issue
Block a user