diff --git a/CMakeLists.txt b/CMakeLists.txt index d886f50..e4e83ac 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -22,6 +22,12 @@ add_library(hy3 SHARED src/SelectionHook.cpp ) +option(HY3_NO_VERSION_CHECK "Disable hyprland version check" FALSE) + +if (HY3_NO_VERSION_CHECK) + target_compile_definitions(hy3 PRIVATE -DHY3_NO_VERSION_CHECK=TRUE) +endif() + target_include_directories(hy3 PRIVATE ${DEPS_INCLUDE_DIRS}) install(TARGETS hy3 LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}) diff --git a/compile_commands_bear.sh b/compile_commands_bear.sh index 8803482..83b4946 100755 --- a/compile_commands_bear.sh +++ b/compile_commands_bear.sh @@ -1,4 +1,4 @@ rm -rf build -cmake -DCMAKE_BUILD_TYPE=Debug -B build bear -- cmake --build build +cmake -DCMAKE_BUILD_TYPE=Debug -DHY3_NO_VERSION_CHECK=TRUE -B build sed -i 's/-std=gnu++23/-std=gnu++2b/g' compile_commands.json diff --git a/flake.lock b/flake.lock index 68e9cd2..d7a752d 100644 --- a/flake.lock +++ b/flake.lock @@ -9,11 +9,11 @@ "xdph": "xdph" }, "locked": { - "lastModified": 1699391198, - "narHash": "sha256-HrnlCdZBqqE37gFORapfSGEGcqhCyhX2aSMRnDEmR0k=", + "lastModified": 1702236723, + "narHash": "sha256-zIEnimM1vhsFkz+Kubb8kJ6YgHuLe56pALOSJc6CMVY=", "owner": "hyprwm", "repo": "Hyprland", - "rev": "751d2851cc270c3322ffe2eb83c156e4298a0c0e", + "rev": "167f2ed3b2bb18ceeabb831ac80b655ef8e16867", "type": "github" }, "original": { @@ -49,11 +49,11 @@ }, "nixpkgs": { "locked": { - "lastModified": 1698134075, - "narHash": "sha256-foCD+nuKzfh49bIoiCBur4+Fx1nozo+4C/6k8BYk4sg=", + "lastModified": 1700612854, + "narHash": "sha256-yrQ8osMD+vDLGFX7pcwsY/Qr5PUd6OmDMYJZzZi0+zc=", "owner": "NixOS", "repo": "nixpkgs", - "rev": "8efd5d1e283604f75a808a20e6cde0ef313d07d4", + "rev": "19cbff58383a4ae384dea4d1d0c823d72b49d614", "type": "github" }, "original": { @@ -87,18 +87,18 @@ "flake": false, "locked": { "host": "gitlab.freedesktop.org", - "lastModified": 1697909146, - "narHash": "sha256-jU0I6FoCKnj4zIBL4daosFWh81U1fM719Z6cae8PxSY=", + "lastModified": 1701368958, + "narHash": "sha256-7kvyoA91etzVEl9mkA/EJfB6z/PltxX7Xc4gcr7/xlo=", "owner": "wlroots", "repo": "wlroots", - "rev": "47bf87ade2bd32395615a385ebde1fefbcdf79a2", + "rev": "5d639394f3e83b01596dcd166a44a9a1a2583350", "type": "gitlab" }, "original": { "host": "gitlab.freedesktop.org", "owner": "wlroots", "repo": "wlroots", - "rev": "47bf87ade2bd32395615a385ebde1fefbcdf79a2", + "rev": "5d639394f3e83b01596dcd166a44a9a1a2583350", "type": "gitlab" } }, @@ -118,11 +118,11 @@ ] }, "locked": { - "lastModified": 1697981233, - "narHash": "sha256-y8q4XUwx+gVK7i2eLjfR32lVo7TYvEslyzrmzYEaPZU=", + "lastModified": 1700508250, + "narHash": "sha256-X4o/mifI7Nhu0UKYlxx53wIC+gYDo3pVM9L2u3PE2bE=", "owner": "hyprwm", "repo": "xdg-desktop-portal-hyprland", - "rev": "22e7a65ff9633e1dedfa5317fdffc49f68de2ff2", + "rev": "eb120ff25265ecacd0fc13d7dab12131b60d0f47", "type": "github" }, "original": { diff --git a/src/Hy3Layout.cpp b/src/Hy3Layout.cpp index 45a67b6..807d141 100644 --- a/src/Hy3Layout.cpp +++ b/src/Hy3Layout.cpp @@ -3,6 +3,7 @@ #include #include +#include #include "Hy3Layout.hpp" #include "SelectionHook.hpp" @@ -692,6 +693,24 @@ void Hy3Layout::alterSplitRatio(CWindow* pWindow, float delta, bool exact) { std::string Hy3Layout::getLayoutName() { return "hy3"; } CWindow* Hy3Layout::getNextWindowCandidate(CWindow* window) { + auto* workspace = g_pCompositor->getWorkspaceByID(window->m_iWorkspaceID); + + if (workspace->m_bHasFullscreenWindow) { + return g_pCompositor->getFullscreenWindowOnWorkspace(window->m_iWorkspaceID); + } + + // return the first floating window on the same workspace that has not asked not to be focused + if (window->m_bIsFloating) { + for (auto& w: g_pCompositor->m_vWindows | std::views::reverse) { + if (w->m_bIsMapped && !w->isHidden() && w->m_bIsFloating && w->m_iX11Type != 2 + && w->m_iWorkspaceID == window->m_iWorkspaceID && !w->m_bX11ShouldntFocus + && !w->m_bNoFocus && w.get() != window) + { + return w.get(); + } + } + } + auto* node = this->getWorkspaceFocusedNode(window->m_iWorkspaceID, true); if (node == nullptr) return nullptr; @@ -921,10 +940,31 @@ void Hy3Layout::shiftWindow(int workspace, ShiftDirection direction, bool once, } void Hy3Layout::shiftFocus(int workspace, ShiftDirection direction, bool visible) { + auto* current_window = g_pCompositor->m_pLastWindow; + + if (current_window != nullptr) { + auto* p_workspace = g_pCompositor->getWorkspaceByID(current_window->m_iWorkspaceID); + if (p_workspace->m_bHasFullscreenWindow) return; + + if (current_window->m_bIsFloating) { + auto* next_window = g_pCompositor->getWindowInDirection( + current_window, + direction == ShiftDirection::Left ? 'l' + : direction == ShiftDirection::Up ? 'u' + : direction == ShiftDirection::Down ? 'd' + : 'r' + ); + + if (next_window != nullptr) g_pCompositor->focusWindow(next_window); + return; + } + } + auto* node = this->getWorkspaceFocusedNode(workspace); if (node == nullptr) return; auto* target = this->shiftOrGetFocus(*node, direction, false, false, visible); + if (target != nullptr) { target->focus(); while (target->parent != nullptr) target = target->parent; @@ -1404,7 +1444,6 @@ void Hy3Layout::applyNodeDataToWindow(Hy3Node* node, bool no_animation) { } // clang-format off - static const auto* border_size = &HyprlandAPI::getConfigValue(PHANDLE, "general:border_size")->intValue; static const auto* gaps_in = &HyprlandAPI::getConfigValue(PHANDLE, "general:gaps_in")->intValue; static const auto* single_window_no_gaps = &HyprlandAPI::getConfigValue(PHANDLE, "plugin:hy3:no_gaps_when_only")->intValue; // clang-format on @@ -1425,9 +1464,6 @@ void Hy3Layout::applyNodeDataToWindow(Hy3Node* node, bool no_animation) { window->m_vSize = node->size; window->m_vPosition = node->position; - auto calcPos = window->m_vPosition + Vector2D(*border_size, *border_size); - auto calcSize = window->m_vSize - Vector2D(2 * *border_size, 2 * *border_size); - auto only_node = root_node->data.as_group.children.size() == 1 && root_node->data.as_group.children.front()->data.type == Hy3NodeType::Window; @@ -1454,6 +1490,9 @@ void Hy3Layout::applyNodeDataToWindow(Hy3Node* node, bool no_animation) { window->m_sSpecialRenderData.border = true; window->m_sSpecialRenderData.decorate = true; + auto calcPos = window->m_vPosition; + auto calcSize = window->m_vSize; + auto gaps_offset_topleft = Vector2D(*gaps_in, *gaps_in) + node->gap_topleft_offset; auto gaps_offset_bottomright = Vector2D(*gaps_in * 2, *gaps_in * 2) + node->gap_bottomright_offset + node->gap_topleft_offset; @@ -1463,7 +1502,7 @@ void Hy3Layout::applyNodeDataToWindow(Hy3Node* node, bool no_animation) { const auto reserved_area = window->getFullWindowReservedArea(); calcPos = calcPos + reserved_area.topLeft; - calcSize = calcSize - (reserved_area.topLeft - reserved_area.bottomRight); + calcSize = calcSize - (reserved_area.topLeft + reserved_area.bottomRight); if (g_pCompositor->isWorkspaceSpecial(window->m_iWorkspaceID)) { // adjust for special workspaces diff --git a/src/TabGroup.cpp b/src/TabGroup.cpp index 28ced1d..217b88e 100644 --- a/src/TabGroup.cpp +++ b/src/TabGroup.cpp @@ -142,7 +142,7 @@ void Hy3TabBarEntry::prepareTexture(float scale, CBox& box) { auto width = box.width; auto height = box.height; - auto rounding = std::min((double) *s_rounding, std::min(width * 0.5, height * 0.5)); + auto rounding = std::min((double) *s_rounding * scale, std::min(width * 0.5, height * 0.5)); if (this->texture.m_iTexID == 0 // clang-format off @@ -548,8 +548,9 @@ void Hy3TabGroup::renderTabBar() { auto scaled_size = Vector2D(std::round(size.x * scale), std::round(size.y * scale)); wlr_box box = {scaled_pos.x, scaled_pos.y, scaled_size.x, scaled_size.y}; - if (scaled_pos.x > monitor_size.x || scaled_pos.y > monitor_size.y - || scaled_pos.x + scaled_size.x < 0 || scaled_pos.y + scaled_size.y < 0) + // monitor size is not scaled + if (pos.x > monitor_size.x || pos.y > monitor_size.y || scaled_pos.x + scaled_size.x < 0 + || scaled_pos.y + scaled_size.y < 0) return; if (!this->bar.damaged) { diff --git a/src/main.cpp b/src/main.cpp index cbfb8ed..da76409 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,7 +1,9 @@ #include +#include #include #include +#include #include "SelectionHook.hpp" #include "dispatchers.hpp" @@ -12,6 +14,19 @@ APICALL EXPORT std::string PLUGIN_API_VERSION() { return HYPRLAND_API_VERSION; } APICALL EXPORT PLUGIN_DESCRIPTION_INFO PLUGIN_INIT(HANDLE handle) { PHANDLE = handle; +#ifndef HY3_NO_VERSION_CHECK + if (GIT_COMMIT_HASH != std::string(__hyprland_api_get_hash())) { + HyprlandAPI::addNotification( + PHANDLE, + "[hy3] Hy3 was compiled for a different version of hyprland; refusing to start.", + CColor {1.0, 0.2, 0.2, 1.0}, + 10000 + ); + + throw std::runtime_error("[hy3] target hyprland version mismatch"); + } +#endif + selection_hook::init(); #define CONF(NAME, TYPE, VALUE) \