diff --git a/src/ui/windows/market_tab.cpp b/src/ui/windows/market_tab.cpp index ce90b55..7058bca 100644 --- a/src/ui/windows/market_tab.cpp +++ b/src/ui/windows/market_tab.cpp @@ -987,18 +987,34 @@ static void RenderPortfolioEditor(App* app) ImGui::SetNextItemWidth(-1); ImGui::InputTextWithHint("##pfSearch", TR("portfolio_search"), s_pf_search, sizeof(s_pf_search)); ImGui::Dummy(ImVec2(0, Layout::spacingXs())); - // Type filter — segmented control on its own row (compact). + // Filter + selection on one row: type-filter segmented (left) + Select all / Clear / + // Funded (right). Select-all is deferred so it applies to the freshly-filtered set below. + bool selAllClicked = false; { const char* flabels[3] = { TR("portfolio_select_all"), TR("shielded"), TR("transparent") }; + const char* selLbl = TR("portfolio_select_shown"); + const char* clrLbl = TR("portfolio_clear_sel"); + ImGuiStyle& st = ImGui::GetStyle(); + ImVec2 pillPad(Layout::spacingLg(), Layout::spacingSm()); // roomier text padding + float defFrameH = ImGui::GetFrameHeight(); + float fundedW = defFrameH + st.ItemInnerSpacing.x + ImGui::CalcTextSize(TR("portfolio_funded")).x; + float pillH = ImGui::GetTextLineHeight() + pillPad.y * 2.0f; + float selW = ImGui::CalcTextSize(selLbl).x + pillPad.x * 2.0f; + float clrW = ImGui::CalcTextSize(clrLbl).x + pillPad.x * 2.0f; + float groupW = selW + clrW + fundedW + st.ItemSpacing.x * 2.0f; float segH = 26.0f * dp; - float availW = ImGui::GetContentRegionAvail().x; - float segW = std::min(availW, 360.0f * dp); + float rowW = ImGui::GetContentRegionAvail().x; + float segW = std::min(360.0f * dp, std::max(160.0f * dp, rowW - groupW - Layout::spacingMd())); + float rowH = std::max(segH, pillH); + ImVec2 rowStart = ImGui::GetCursorScreenPos(); + // Segmented type filter (left), vertically centered in the row. + float segY = rowStart.y + (rowH - segH) * 0.5f; float cellW = segW / 3.0f; - ImVec2 sMin = ImGui::GetCursorScreenPos(); ImDrawList* fdl = ImGui::GetWindowDrawList(); - fdl->AddRectFilled(sMin, ImVec2(sMin.x + segW, sMin.y + segH), WithAlpha(OnSurface(), 20), segH * 0.5f); + fdl->AddRectFilled(ImVec2(rowStart.x, segY), ImVec2(rowStart.x + segW, segY + segH), + WithAlpha(OnSurface(), 20), segH * 0.5f); for (int f = 0; f < 3; f++) { - ImVec2 cMin(sMin.x + f * cellW, sMin.y), cMax(cMin.x + cellW, sMin.y + segH); + ImVec2 cMin(rowStart.x + f * cellW, segY), cMax(cMin.x + cellW, segY + segH); bool active = (s_pf_type_filter == f); bool hov = ImGui::IsMouseHoveringRect(cMin, cMax); if (active) @@ -1016,8 +1032,21 @@ static void RenderPortfolioEditor(App* app) if (ImGui::IsItemHovered()) ImGui::SetMouseCursor(ImGuiMouseCursor_Hand); ImGui::PopID(); } - ImGui::SetCursorScreenPos(ImVec2(sMin.x, sMin.y + segH)); - ImGui::Dummy(ImVec2(availW, 0)); + // Select all / Clear (rounded pills) + Funded toggle (right), vertically centered. + float grpX = rowStart.x + std::max(0.0f, rowW - groupW); + ImGui::PushStyleVar(ImGuiStyleVar_FrameRounding, 12.0f * dp); + ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, pillPad); + ImGui::SetCursorScreenPos(ImVec2(grpX, rowStart.y + (rowH - pillH) * 0.5f)); + if (ImGui::Button(selLbl)) selAllClicked = true; + ImGui::SameLine(); + if (ImGui::Button(clrLbl)) s_pf_addrs.clear(); + ImGui::PopStyleVar(2); + ImGui::SameLine(); + ImGui::SetCursorScreenPos(ImVec2(ImGui::GetCursorScreenPos().x, + rowStart.y + (rowH - defFrameH) * 0.5f)); // center vs. pills + ImGui::Checkbox(TR("portfolio_funded"), &s_pf_funded_only); + ImGui::SetCursorScreenPos(ImVec2(rowStart.x, rowStart.y + rowH)); + ImGui::Dummy(ImVec2(rowW, 0)); } ImGui::Dummy(ImVec2(0, Layout::spacingXs())); std::string search = s_pf_search; @@ -1038,36 +1067,8 @@ static void RenderPortfolioEditor(App* app) if (sx != sy) return sx; return x->balance > y->balance; }); - // Select all / Clear (rounded pills) + Funded toggle — one row, right-aligned. - { - const char* selLbl = TR("portfolio_select_shown"); - const char* clrLbl = TR("portfolio_clear_sel"); - ImGuiStyle& st = ImGui::GetStyle(); - ImVec2 pillPad(Layout::spacingLg(), Layout::spacingSm()); // roomier text padding - // Measure the checkbox at default padding and the pills at their (larger) padding, so - // the whole group can be right-aligned before it's drawn. - float defFrameH = ImGui::GetFrameHeight(); - float fundedW = defFrameH + st.ItemInnerSpacing.x + ImGui::CalcTextSize(TR("portfolio_funded")).x; - float pillH = ImGui::GetTextLineHeight() + pillPad.y * 2.0f; - float selW = ImGui::CalcTextSize(selLbl).x + pillPad.x * 2.0f; - float clrW = ImGui::CalcTextSize(clrLbl).x + pillPad.x * 2.0f; - float groupW = selW + clrW + fundedW + st.ItemSpacing.x * 2.0f; - float rowH = std::max(pillH, defFrameH); - float rowY = ImGui::GetCursorPosY(); - float availW = ImGui::GetContentRegionAvail().x; - if (availW > groupW) ImGui::SetCursorPosX(ImGui::GetCursorPosX() + availW - groupW); - ImGui::PushStyleVar(ImGuiStyleVar_FrameRounding, 12.0f * dp); - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, pillPad); - ImGui::SetCursorPosY(rowY + (rowH - pillH) * 0.5f); - if (ImGui::Button(selLbl)) - for (const AddressInfo* a : filtered) data::PortfolioEntryAdd(s_pf_addrs, a->address); - ImGui::SameLine(); - if (ImGui::Button(clrLbl)) s_pf_addrs.clear(); - ImGui::PopStyleVar(2); - ImGui::SameLine(); - ImGui::SetCursorPosY(rowY + (rowH - defFrameH) * 0.5f); // center vs. pills - ImGui::Checkbox(TR("portfolio_funded"), &s_pf_funded_only); - } + if (selAllClicked) + for (const AddressInfo* a : filtered) data::PortfolioEntryAdd(s_pf_addrs, a->address); ImGui::Dummy(ImVec2(0, Layout::spacingXs())); ImDrawList* ldl = pfBeginScrollChild("##pfAddrList", s_pf_addr_fade, ImVec2(Layout::spacingMd(), Layout::spacingSm()), dp);