Move Re-Capture and Insert Conform from the panel top bar to the overflow menu; re-pin action_bar width test to the new 4-button top bar.
This commit is contained in:
+33
-47
@@ -30,15 +30,13 @@ static int g_fail = 0;
|
||||
#define CHECK(cond) do { if(!(cond)) { \
|
||||
std::printf("FAIL line %d: %s\n", __LINE__, #cond); ++g_fail; } } while(0)
|
||||
|
||||
// The panel's real inventory shape: 2 capture, 1 maintenance (Re-capture), 3 placement
|
||||
// (Insert / Insert Conform / Insert as FX) = 6 buttons. Cluster order:
|
||||
// Capture -> Maintenance -> Placement (Re-capture sits between the two capture verbs and the
|
||||
// placement verbs).
|
||||
// The panel's real inventory shape: 2 capture, 2 placement (Insert / Insert as FX) = 4
|
||||
// buttons. Re-capture and Insert Conform moved to the overflow menu, so the top bar's
|
||||
// Maintenance cluster is now empty. Cluster order: Capture -> Placement.
|
||||
static std::vector<ClusterSpec> inventory() {
|
||||
return {
|
||||
{ActionCluster::Capture, 2},
|
||||
{ActionCluster::Maintenance, 1},
|
||||
{ActionCluster::Placement, 3},
|
||||
{ActionCluster::Placement, 2},
|
||||
};
|
||||
}
|
||||
|
||||
@@ -55,28 +53,26 @@ static ActionBarSpec roundSpec() {
|
||||
|
||||
// --- Layout: all fit, correct rects + gaps ------------------------------------
|
||||
|
||||
// A wide bar fits all 6 buttons. Verify the first few rects, the intra-cluster gap, and the
|
||||
// (wider) inter-cluster gap between button 1 (last capture) and button 2 (maintenance).
|
||||
// A wide bar fits all 4 buttons. Verify the first few rects, the intra-cluster gap, and the
|
||||
// (wider) inter-cluster gap between button 1 (last capture) and button 2 (first placement).
|
||||
//
|
||||
// Pixel walk with roundSpec and bar at (0,40):
|
||||
// btn0 (Capture): x=8, right=108
|
||||
// btn1 (Capture): x=112, right=212 (intraGap = 4 after btn0's right)
|
||||
// btn2 (Maintenance): x=228, right=328 (clusterGap = 16 after btn1's right)
|
||||
// btn3 (Placement): x=344, right=444 (clusterGap = 16 after btn2's right)
|
||||
// btn4 (Placement): x=448, right=548 (intraGap = 4 after btn3's right)
|
||||
// btn5 (Placement): x=552, right=652 (intraGap = 4 after btn4's right)
|
||||
// Minimum bar width: 652 + sidePad(8) = 660. Give it 700.
|
||||
// btn0 (Capture): x=8, right=108
|
||||
// btn1 (Capture): x=112, right=212 (intraGap = 4 after btn0's right)
|
||||
// btn2 (Placement): x=228, right=328 (clusterGap = 16 after btn1's right)
|
||||
// btn3 (Placement): x=332, right=432 (intraGap = 4 after btn2's right)
|
||||
// Minimum bar width: 432 + sidePad(8) = 440. Give it 500.
|
||||
static void testAllFitRectsAndGaps() {
|
||||
const auto clusters = inventory();
|
||||
const ActionBarSpec spec = roundSpec();
|
||||
ActionBarRect bar{0, 40, 700, 34};
|
||||
ActionBarRect bar{0, 40, 500, 34};
|
||||
|
||||
BarFit fit = computeBarFit(bar, clusters, spec);
|
||||
CHECK(fit.visibleCount == 6);
|
||||
CHECK(fit.visibleCount == 4);
|
||||
CHECK(fit.hiddenCount == 0);
|
||||
|
||||
auto slots = computeBarSlots(bar, clusters, spec);
|
||||
CHECK(slots.size() == 6);
|
||||
CHECK(slots.size() == 4);
|
||||
|
||||
// Button 0: at sidePad, top = y + verticalInset, height = barH - 2*inset.
|
||||
CHECK(slots[0].x == 8);
|
||||
@@ -90,27 +86,17 @@ static void testAllFitRectsAndGaps() {
|
||||
CHECK(slots[1].x == 112);
|
||||
CHECK(slots[1].cluster == ActionCluster::Capture);
|
||||
|
||||
// Button 2 (maintenance / Re-capture): cluster gap of 16 after 212 -> 228.
|
||||
// Button 2 (first placement): cluster gap of 16 after 212 -> 228.
|
||||
CHECK(slots[2].x == 228);
|
||||
CHECK(slots[2].cluster == ActionCluster::Maintenance);
|
||||
CHECK(slots[2].cluster == ActionCluster::Placement);
|
||||
CHECK(slots[2].index == 2);
|
||||
|
||||
// Button 3 (first placement): cluster gap of 16 after 328 -> 344.
|
||||
CHECK(slots[3].x == 344);
|
||||
// Button 3 (Insert as FX — second placement): intra-cluster gap of 4 after 328 -> 332.
|
||||
// It joins the Placement cluster, so no cluster gap opens before it.
|
||||
CHECK(slots[3].x == 332);
|
||||
CHECK(slots[3].cluster == ActionCluster::Placement);
|
||||
CHECK(slots[3].index == 3);
|
||||
|
||||
// Button 4 (second placement): intra-cluster gap of 4 after 444 -> 448.
|
||||
CHECK(slots[4].x == 448);
|
||||
CHECK(slots[4].cluster == ActionCluster::Placement);
|
||||
CHECK(slots[4].index == 4);
|
||||
|
||||
// Button 5 (Insert as FX — third placement): intra-cluster gap of 4 after 548 -> 552.
|
||||
// It joins the Placement cluster, so no cluster gap opens before it.
|
||||
CHECK(slots[5].x == 552);
|
||||
CHECK(slots[5].cluster == ActionCluster::Placement);
|
||||
CHECK(slots[5].index == 5);
|
||||
CHECK(slots[5].x - (slots[4].x + slots[4].width) == spec.buttonGap);
|
||||
CHECK(slots[3].x - (slots[2].x + slots[2].width) == spec.buttonGap);
|
||||
|
||||
// Inter-cluster gap (slot[2].x - slot[1].right = 228 - 212 = 16) is wider than the
|
||||
// intra-cluster gap (slot[1].x - slot[0].right = 112 - 108 = 4) — task grouping is
|
||||
@@ -159,14 +145,14 @@ static void testLabelFullHeightWhenShort() {
|
||||
// keep their full width (never clipped), and the frequent capture cluster survives.
|
||||
//
|
||||
// Exact fit for 2 capture buttons: sidePad(8) + 2*100 + 1*4 + sidePad(8) = 220.
|
||||
// A 3rd button (Maintenance) needs clusterGap(16)+100 = 116 more -> 336. So 220 fits exactly 2.
|
||||
// A 3rd button (Placement) needs clusterGap(16)+100 = 116 more -> 336. So 220 fits exactly 2.
|
||||
static void testOverflowDropsTrailingWhole() {
|
||||
const auto clusters = inventory();
|
||||
const ActionBarSpec spec = roundSpec();
|
||||
ActionBarRect bar{0, 0, 220, 34};
|
||||
BarFit fit = computeBarFit(bar, clusters, spec);
|
||||
CHECK(fit.visibleCount == 2);
|
||||
CHECK(fit.hiddenCount == 4);
|
||||
CHECK(fit.hiddenCount == 2);
|
||||
|
||||
auto slots = computeBarSlots(bar, clusters, spec);
|
||||
CHECK(slots.size() == 2);
|
||||
@@ -186,7 +172,7 @@ static void testTooNarrowForAny() {
|
||||
ActionBarRect bar{0, 0, 60, 34}; // sidePad*2 + one 100-wide button won't fit
|
||||
BarFit fit = computeBarFit(bar, clusters, spec);
|
||||
CHECK(fit.visibleCount == 0);
|
||||
CHECK(fit.hiddenCount == 6);
|
||||
CHECK(fit.hiddenCount == 4);
|
||||
CHECK(computeBarSlots(bar, clusters, spec).empty());
|
||||
}
|
||||
|
||||
@@ -246,9 +232,9 @@ static ActionBarSpec realBarSpec() {
|
||||
}
|
||||
|
||||
// At the real spec plus the real 40 px reserve (28 + 2*6, panel_state.h's kMenuBtnSpec --
|
||||
// all default-constructed here since its defaults already match), 764 is the narrowest
|
||||
// band that still shows all six buttons; one pixel narrower drops Insert as FX (flat index
|
||||
// 5, the trailing Placement button) alone into overflow, leaving its five neighbours intact.
|
||||
// all default-constructed here since its defaults already match), 520 is the narrowest
|
||||
// band that still shows all four buttons; one pixel narrower drops Insert as FX (flat index
|
||||
// 3, the trailing Placement button) alone into overflow, leaving its three neighbours intact.
|
||||
static void testReserveDropsInsertAsFxAtRealWidth() {
|
||||
const auto clusters = inventory();
|
||||
const ActionBarSpec spec = realBarSpec();
|
||||
@@ -256,18 +242,18 @@ static void testReserveDropsInsertAsFxAtRealWidth() {
|
||||
const int reserve = menuButtonReserve(MenuBarRect{0, 0, 900, 34}, menuSpec);
|
||||
CHECK(reserve == 40);
|
||||
|
||||
const int allSixWidth = 764;
|
||||
const int allFourWidth = 520;
|
||||
{
|
||||
ActionBarRect action{0, 0, allSixWidth - reserve, 34};
|
||||
ActionBarRect action{0, 0, allFourWidth - reserve, 34};
|
||||
const auto slots = computeBarSlots(action, clusters, spec);
|
||||
CHECK(slots.size() == 6);
|
||||
CHECK(slots.back().index == 5); // Insert as FX still visible
|
||||
CHECK(slots.size() == 4);
|
||||
CHECK(slots.back().index == 3); // Insert as FX still visible
|
||||
}
|
||||
{
|
||||
ActionBarRect action{0, 0, allSixWidth - 1 - reserve, 34};
|
||||
ActionBarRect action{0, 0, allFourWidth - 1 - reserve, 34};
|
||||
const auto slots = computeBarSlots(action, clusters, spec);
|
||||
CHECK(slots.size() == 5); // Insert as FX alone dropped
|
||||
CHECK(slots.back().index == 4); // Insert Conform is now the trailing visible button
|
||||
CHECK(slots.size() == 3); // Insert as FX alone dropped
|
||||
CHECK(slots.back().index == 2); // Insert is now the trailing visible button
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user