workspace taskbars: Display windows in a consistent order
Use a vector instead of a map for for storing the workspace windows. This orders the windows by the time they were added to the workspace, instead of sorting by address (which is effectively a random order). The new ordering seems to match the wlr/taskbar module
This commit is contained in:
@ -27,6 +27,7 @@ namespace waybar::modules::hyprland {
|
|||||||
class Workspaces;
|
class Workspaces;
|
||||||
|
|
||||||
struct WindowRepr {
|
struct WindowRepr {
|
||||||
|
std::string address;
|
||||||
std::string window_class;
|
std::string window_class;
|
||||||
std::string window_title;
|
std::string window_title;
|
||||||
std::string repr_rewrite;
|
std::string repr_rewrite;
|
||||||
|
@ -54,9 +54,11 @@ class Workspace {
|
|||||||
void setWindows(uint value) { m_windows = value; };
|
void setWindows(uint value) { m_windows = value; };
|
||||||
void setName(std::string const& value) { m_name = value; };
|
void setName(std::string const& value) { m_name = value; };
|
||||||
void setOutput(std::string const& value) { m_output = value; };
|
void setOutput(std::string const& value) { m_output = value; };
|
||||||
bool containsWindow(WindowAddress const& addr) const { return m_windowMap.contains(addr); }
|
bool containsWindow(WindowAddress const& addr) const {
|
||||||
|
return std::ranges::any_of(m_windowMap,
|
||||||
|
[&addr](const auto& window) { return window.address == addr; });
|
||||||
|
};
|
||||||
void insertWindow(WindowCreationPayload create_window_paylod);
|
void insertWindow(WindowCreationPayload create_window_paylod);
|
||||||
WindowRepr removeWindow(WindowAddress const& addr);
|
|
||||||
void initializeWindowMap(const Json::Value& clients_data);
|
void initializeWindowMap(const Json::Value& clients_data);
|
||||||
|
|
||||||
bool onWindowOpened(WindowCreationPayload const& create_window_paylod);
|
bool onWindowOpened(WindowCreationPayload const& create_window_paylod);
|
||||||
@ -78,7 +80,7 @@ class Workspace {
|
|||||||
bool m_isUrgent = false;
|
bool m_isUrgent = false;
|
||||||
bool m_isVisible = false;
|
bool m_isVisible = false;
|
||||||
|
|
||||||
std::map<WindowAddress, WindowRepr, std::less<>> m_windowMap;
|
std::vector<WindowRepr> m_windowMap;
|
||||||
|
|
||||||
Gtk::Button m_button;
|
Gtk::Button m_button;
|
||||||
Gtk::Box m_content;
|
Gtk::Box m_content;
|
||||||
|
@ -98,7 +98,8 @@ WindowRepr WindowCreationPayload::repr(Workspaces &workspace_manager) {
|
|||||||
}
|
}
|
||||||
if (std::holds_alternative<ClassAndTitle>(m_window)) {
|
if (std::holds_alternative<ClassAndTitle>(m_window)) {
|
||||||
auto [window_class, window_title] = std::get<ClassAndTitle>(m_window);
|
auto [window_class, window_title] = std::get<ClassAndTitle>(m_window);
|
||||||
return {window_class, window_title, workspace_manager.getRewrite(window_class, window_title)};
|
return {m_windowAddress, window_class, window_title,
|
||||||
|
workspace_manager.getRewrite(window_class, window_title)};
|
||||||
}
|
}
|
||||||
// Unreachable
|
// Unreachable
|
||||||
spdlog::error("WorkspaceWindow::repr: Unreachable");
|
spdlog::error("WorkspaceWindow::repr: Unreachable");
|
||||||
|
@ -53,8 +53,13 @@ void addOrRemoveClass(const Glib::RefPtr<Gtk::StyleContext> &context, bool condi
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::optional<WindowRepr> Workspace::closeWindow(WindowAddress const &addr) {
|
std::optional<WindowRepr> Workspace::closeWindow(WindowAddress const &addr) {
|
||||||
if (m_windowMap.contains(addr)) {
|
auto it = std::ranges::find_if(m_windowMap,
|
||||||
return removeWindow(addr);
|
[&addr](const auto &window) { return window.address == addr; });
|
||||||
|
// If the vector contains the address, remove it and return the window representation
|
||||||
|
if (it != m_windowMap.end()) {
|
||||||
|
WindowRepr windowRepr = *it;
|
||||||
|
m_windowMap.erase(it);
|
||||||
|
return windowRepr;
|
||||||
}
|
}
|
||||||
return std::nullopt;
|
return std::nullopt;
|
||||||
}
|
}
|
||||||
@ -101,7 +106,15 @@ void Workspace::insertWindow(WindowCreationPayload create_window_paylod) {
|
|||||||
auto repr = create_window_paylod.repr(m_workspaceManager);
|
auto repr = create_window_paylod.repr(m_workspaceManager);
|
||||||
|
|
||||||
if (!repr.empty()) {
|
if (!repr.empty()) {
|
||||||
m_windowMap[create_window_paylod.getAddress()] = repr;
|
auto addr = create_window_paylod.getAddress();
|
||||||
|
auto it = std::ranges::find_if(
|
||||||
|
m_windowMap, [&addr](const auto &window) { return window.address == addr; });
|
||||||
|
// If the vector contains the address, update the window representation, otherwise insert it
|
||||||
|
if (it != m_windowMap.end()) {
|
||||||
|
*it = repr;
|
||||||
|
} else {
|
||||||
|
m_windowMap.emplace_back(repr);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@ -114,12 +127,6 @@ bool Workspace::onWindowOpened(WindowCreationPayload const &create_window_paylod
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
WindowRepr Workspace::removeWindow(WindowAddress const &addr) {
|
|
||||||
WindowRepr windowRepr = m_windowMap[addr];
|
|
||||||
m_windowMap.erase(addr);
|
|
||||||
return windowRepr;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string &Workspace::selectIcon(std::map<std::string, std::string> &icons_map) {
|
std::string &Workspace::selectIcon(std::map<std::string, std::string> &icons_map) {
|
||||||
spdlog::trace("Selecting icon for workspace {}", name());
|
spdlog::trace("Selecting icon for workspace {}", name());
|
||||||
if (isUrgent()) {
|
if (isUrgent()) {
|
||||||
@ -212,7 +219,7 @@ void Workspace::update(const std::string &workspace_icon) {
|
|||||||
|
|
||||||
bool isNotFirst = false;
|
bool isNotFirst = false;
|
||||||
|
|
||||||
for (const auto &[_pid, window_repr] : m_windowMap) {
|
for (const auto &window_repr : m_windowMap) {
|
||||||
if (isNotFirst) {
|
if (isNotFirst) {
|
||||||
windows.append(windowSeparator);
|
windows.append(windowSeparator);
|
||||||
}
|
}
|
||||||
@ -238,7 +245,7 @@ void Workspace::updateTaskbar(const std::string &workspace_icon) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const auto &[_addr, window_repr] : m_windowMap) {
|
for (const auto &window_repr : m_windowMap) {
|
||||||
auto window_box = Gtk::make_managed<Gtk::Box>(Gtk::ORIENTATION_HORIZONTAL);
|
auto window_box = Gtk::make_managed<Gtk::Box>(Gtk::ORIENTATION_HORIZONTAL);
|
||||||
window_box->set_tooltip_text(window_repr.window_title);
|
window_box->set_tooltip_text(window_repr.window_title);
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user