mirror of
https://github.com/hyprwm/Hyprland.git
synced 2025-08-01 12:41:55 -07:00
Compare commits
25 Commits
v0.1.3abet
...
v0.2.1beta
Author | SHA1 | Date | |
---|---|---|---|
|
0f8712ed64 | ||
|
3e28a8b690 | ||
|
8de7cc5a8d | ||
|
e73df80782 | ||
|
0d7131d30e | ||
|
d2e0b7c22a | ||
|
c1193ee483 | ||
|
042e79b888 | ||
|
0055efc4f1 | ||
|
df722cbb86 | ||
|
68f7e565e6 | ||
|
48a3b1c514 | ||
|
85128ebb7d | ||
|
ad98b96891 | ||
|
2e7586e841 | ||
|
f6ba9909d6 | ||
|
c9041bf5c9 | ||
|
b2474d406a | ||
|
eee9698ec9 | ||
|
1f4c938c67 | ||
|
c44c79abb2 | ||
|
1e096f6fcd | ||
|
b1c11f3d2e | ||
|
da63503d5f | ||
|
7167be9c48 |
3
.github/ISSUE_TEMPLATE/bug_report.md
vendored
3
.github/ISSUE_TEMPLATE/bug_report.md
vendored
@@ -3,6 +3,7 @@ name: Bug report
|
||||
about: Found a bug? Report it here!
|
||||
title: ''
|
||||
labels: bug
|
||||
assignees: ''
|
||||
|
||||
---
|
||||
|
||||
@@ -13,3 +14,5 @@ labels: bug
|
||||
|
||||
|
||||
Please attach a log (it's in /tmp/hypr/hyprland.log) and, if crashing, a crashdump (coredumpctl, then coredumpctl info <pid>)
|
||||
|
||||
*Please do NOT attach coredumps from any packaged version of Hyprland (AUR, etc.). Compile manually, and THEN attach a coredump of that.*
|
||||
|
1
.github/ISSUE_TEMPLATE/feature_request.md
vendored
1
.github/ISSUE_TEMPLATE/feature_request.md
vendored
@@ -3,6 +3,7 @@ name: Feature request
|
||||
about: Suggest a feature/change/idea
|
||||
title: ''
|
||||
labels: enhancement
|
||||
assignees: ''
|
||||
|
||||
---
|
||||
|
||||
|
2
.github/workflows/ci.yaml
vendored
2
.github/workflows/ci.yaml
vendored
@@ -30,6 +30,8 @@ jobs:
|
||||
|
||||
- name: Checkout Hyprland
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
submodules: recursive
|
||||
|
||||
- name: Build Hyprland With default settings
|
||||
run: |
|
||||
|
2
.github/workflows/nix-build.yaml
vendored
2
.github/workflows/nix-build.yaml
vendored
@@ -8,6 +8,8 @@ jobs:
|
||||
steps:
|
||||
- name: Clone repository
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
submodules: recursive
|
||||
- name: Install nix
|
||||
uses: cachix/install-nix-action@v17
|
||||
with:
|
||||
|
3
.gitmodules
vendored
Normal file
3
.gitmodules
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
[submodule "wlroots"]
|
||||
path = wlroots
|
||||
url = https://gitlab.freedesktop.org/wlroots/wlroots
|
15
Makefile
15
Makefile
@@ -89,6 +89,7 @@ clear:
|
||||
rm -rf build
|
||||
rm -f *.o *-protocol.h *-protocol.c
|
||||
rm -f ./hyprctl/hyprctl
|
||||
rm -rf ./wlroots/build
|
||||
|
||||
all:
|
||||
make config
|
||||
@@ -113,4 +114,16 @@ uninstall:
|
||||
rm -f ${PREFIX}/bin/hyprctl
|
||||
rm -rf ${PREFIX}/share/hyprland
|
||||
|
||||
config: xdg-shell-protocol.o wlr-layer-shell-unstable-v1-protocol.o wlr-screencopy-unstable-v1-protocol.o idle-protocol.o ext-workspace-unstable-v1-protocol.o pointer-constraints-unstable-v1-protocol.o
|
||||
protocols: xdg-shell-protocol.o wlr-layer-shell-unstable-v1-protocol.o wlr-screencopy-unstable-v1-protocol.o idle-protocol.o ext-workspace-unstable-v1-protocol.o pointer-constraints-unstable-v1-protocol.o
|
||||
|
||||
config:
|
||||
make protocols
|
||||
|
||||
sed -i -E 's/(soversion = 11)([^032]|$$)/soversion = 11032/g' ./wlroots/meson.build
|
||||
|
||||
rm -rf ./wlroots/build
|
||||
|
||||
cd wlroots && meson ./build --prefix=/usr --buildtype=release
|
||||
cd wlroots && ninja -C build/
|
||||
|
||||
cd wlroots && sudo ninja -C build/ install
|
||||
|
11
README.md
11
README.md
@@ -51,17 +51,18 @@ Try it out and report bugs / suggestions!
|
||||
|
||||
- Easily expandable and readable codebase
|
||||
- Config reloaded instantly upon saving
|
||||
- Bezier-curve window animations
|
||||
- Custom bezier curve based animations
|
||||
- Workspaces protocol support
|
||||
- wlr_ext workspaces protocol support
|
||||
- Dual Kawase blur
|
||||
- Window fade in / out
|
||||
- Fully dynamic workspaces
|
||||
- Window / layer fade in / out
|
||||
- Tiling / floating / fullscreen windows
|
||||
- Special Workspace (Scratchpad)
|
||||
- Window / monitor rules
|
||||
- Socket-based IPC
|
||||
- Event System for bash scripts
|
||||
- Rounded corners
|
||||
- Damage tracking ( *Experimental* )
|
||||
- Moving / resizing
|
||||
- Full Damage tracking
|
||||
- Docks support
|
||||
|
||||
<br>
|
||||
|
@@ -314,6 +314,15 @@ bool CCompositor::windowExists(CWindow* pWindow) {
|
||||
|
||||
CWindow* CCompositor::vectorToWindow(const Vector2D& pos) {
|
||||
const auto PMONITOR = getMonitorFromVector(pos);
|
||||
|
||||
if (PMONITOR->specialWorkspaceOpen) {
|
||||
for (auto& w : m_lWindows) {
|
||||
wlr_box box = {w.m_vRealPosition.vec().x, w.m_vRealPosition.vec().y, w.m_vRealSize.vec().x, w.m_vRealSize.vec().y};
|
||||
if (w.m_iWorkspaceID == SPECIAL_WORKSPACE_ID && wlr_box_contains_point(&box, pos.x, pos.y) && w.m_bIsMapped && !w.m_bIsFloating && !w.m_bHidden)
|
||||
return &w;
|
||||
}
|
||||
}
|
||||
|
||||
// first loop over floating cuz they're above, m_lWindows should be sorted bottom->top, for tiled it doesn't matter.
|
||||
for (auto w = m_lWindows.rbegin(); w != m_lWindows.rend(); w++) {
|
||||
wlr_box box = {w->m_vRealPosition.vec().x, w->m_vRealPosition.vec().y, w->m_vRealSize.vec().x, w->m_vRealSize.vec().y};
|
||||
@@ -332,6 +341,15 @@ CWindow* CCompositor::vectorToWindow(const Vector2D& pos) {
|
||||
|
||||
CWindow* CCompositor::vectorToWindowTiled(const Vector2D& pos) {
|
||||
const auto PMONITOR = getMonitorFromVector(pos);
|
||||
|
||||
if (PMONITOR->specialWorkspaceOpen) {
|
||||
for (auto& w : m_lWindows) {
|
||||
wlr_box box = {w.m_vPosition.x, w.m_vPosition.y, w.m_vSize.x, w.m_vSize.y};
|
||||
if (w.m_iWorkspaceID == SPECIAL_WORKSPACE_ID && wlr_box_contains_point(&box, pos.x, pos.y) && !w.m_bIsFloating && !w.m_bHidden)
|
||||
return &w;
|
||||
}
|
||||
}
|
||||
|
||||
for (auto& w : m_lWindows) {
|
||||
wlr_box box = {w.m_vPosition.x, w.m_vPosition.y, w.m_vSize.x, w.m_vSize.y};
|
||||
if (w.m_bIsMapped && wlr_box_contains_point(&box, pos.x, pos.y) && w.m_iWorkspaceID == PMONITOR->activeWorkspace && !w.m_bIsFloating && !w.m_bHidden)
|
||||
@@ -343,6 +361,16 @@ CWindow* CCompositor::vectorToWindowTiled(const Vector2D& pos) {
|
||||
|
||||
CWindow* CCompositor::vectorToWindowIdeal(const Vector2D& pos) {
|
||||
const auto PMONITOR = getMonitorFromVector(pos);
|
||||
|
||||
// special workspace
|
||||
if (PMONITOR->specialWorkspaceOpen) {
|
||||
for (auto& w : m_lWindows) {
|
||||
wlr_box box = {w.m_vPosition.x, w.m_vPosition.y, w.m_vSize.x, w.m_vSize.y};
|
||||
if (w.m_iWorkspaceID == SPECIAL_WORKSPACE_ID && w.m_bIsMapped && wlr_box_contains_point(&box, pos.x, pos.y) && !w.m_bHidden)
|
||||
return &w;
|
||||
}
|
||||
}
|
||||
|
||||
// first loop over floating cuz they're above, m_lWindows should be sorted bottom->top, for tiled it doesn't matter.
|
||||
for (auto w = m_lWindows.rbegin(); w != m_lWindows.rend(); w++) {
|
||||
wlr_box box = {w->m_vRealPosition.vec().x, w->m_vRealPosition.vec().y, w->m_vRealSize.vec().x, w->m_vRealSize.vec().y};
|
||||
@@ -362,6 +390,14 @@ CWindow* CCompositor::vectorToWindowIdeal(const Vector2D& pos) {
|
||||
CWindow* CCompositor::windowFromCursor() {
|
||||
const auto PMONITOR = getMonitorFromCursor();
|
||||
|
||||
if (PMONITOR->specialWorkspaceOpen) {
|
||||
for (auto& w : m_lWindows) {
|
||||
wlr_box box = {w.m_vPosition.x, w.m_vPosition.y, w.m_vSize.x, w.m_vSize.y};
|
||||
if (w.m_iWorkspaceID == SPECIAL_WORKSPACE_ID && wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_bIsMapped)
|
||||
return &w;
|
||||
}
|
||||
}
|
||||
|
||||
// first loop over floating cuz they're above, m_lWindows should be sorted bottom->top, for tiled it doesn't matter.
|
||||
for (auto w = m_lWindows.rbegin(); w != m_lWindows.rend(); w++) {
|
||||
wlr_box box = {w->m_vRealPosition.vec().x, w->m_vRealPosition.vec().y, w->m_vRealSize.vec().x, w->m_vRealSize.vec().y};
|
||||
@@ -576,6 +612,9 @@ bool CCompositor::isWorkspaceVisible(const int& w) {
|
||||
for (auto& m : m_lMonitors) {
|
||||
if (m.activeWorkspace == w)
|
||||
return true;
|
||||
|
||||
if (m.specialWorkspaceOpen && w == SPECIAL_WORKSPACE_ID)
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
@@ -592,7 +631,15 @@ CWorkspace* CCompositor::getWorkspaceByID(const int& id) {
|
||||
|
||||
void CCompositor::sanityCheckWorkspaces() {
|
||||
for (auto it = m_lWorkspaces.begin(); it != m_lWorkspaces.end(); ++it) {
|
||||
if (getWindowsOnWorkspace(it->m_iID) == 0 && !isWorkspaceVisible(it->m_iID)) {
|
||||
if ((getWindowsOnWorkspace(it->m_iID) == 0 && !isWorkspaceVisible(it->m_iID))) {
|
||||
it = m_lWorkspaces.erase(it);
|
||||
}
|
||||
|
||||
if (it->m_iID == SPECIAL_WORKSPACE_ID && getWindowsOnWorkspace(it->m_iID) == 0) {
|
||||
for (auto& m : m_lMonitors) {
|
||||
m.specialWorkspaceOpen = false;
|
||||
}
|
||||
|
||||
it = m_lWorkspaces.erase(it);
|
||||
}
|
||||
}
|
||||
@@ -622,6 +669,9 @@ void CCompositor::fixXWaylandWindowsOnWorkspace(const int& id) {
|
||||
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(id);
|
||||
|
||||
if (!PWORKSPACE)
|
||||
return;
|
||||
|
||||
for (auto& w : m_lWindows) {
|
||||
if (w.m_iWorkspaceID == id) {
|
||||
|
||||
@@ -820,8 +870,8 @@ CWorkspace* CCompositor::getWorkspaceByString(const std::string& str) {
|
||||
}
|
||||
|
||||
try {
|
||||
int id = std::stoi(str);
|
||||
return getWorkspaceByID(id);
|
||||
std::string name = "";
|
||||
return getWorkspaceByID(getWorkspaceIDFromString(str, name));
|
||||
} catch (std::exception& e) {
|
||||
Debug::log(ERR, "Error in getWorkspaceByString, invalid id");
|
||||
}
|
||||
@@ -936,4 +986,102 @@ void CCompositor::updateWindowBorderColor(CWindow* pWindow) {
|
||||
pWindow->m_cRealBorderColor = RENDERDATA.borderColor;
|
||||
else
|
||||
pWindow->m_cRealBorderColor = CColor(pWindow == m_pLastWindow ? *ACTIVECOL : *INACTIVECOL);
|
||||
}
|
||||
|
||||
void CCompositor::moveWindowToWorkspace(CWindow* pWindow, const std::string& work) {
|
||||
m_pLastWindow = pWindow;
|
||||
g_pKeybindManager->moveActiveToWorkspace(work);
|
||||
|
||||
g_pInputManager->refocus();
|
||||
}
|
||||
|
||||
int CCompositor::getNextAvailableMonitorID() {
|
||||
int64_t topID = -1;
|
||||
for (auto& m : m_lMonitors) {
|
||||
if ((int64_t)m.ID > topID)
|
||||
topID = m.ID;
|
||||
}
|
||||
|
||||
return topID + 1;
|
||||
}
|
||||
|
||||
void CCompositor::moveWorkspaceToMonitor(CWorkspace* pWorkspace, SMonitor* pMonitor) {
|
||||
|
||||
// We trust the workspace and monitor to be correct.
|
||||
|
||||
if (pWorkspace->m_iMonitorID == pMonitor->ID)
|
||||
return;
|
||||
|
||||
Debug::log(LOG, "moveWorkspaceToMonitor: Moving %d to monitor %d", pWorkspace->m_iID, pMonitor->ID);
|
||||
|
||||
const auto POLDMON = getMonitorFromID(pWorkspace->m_iMonitorID);
|
||||
|
||||
const bool SWITCHINGISACTIVE = POLDMON->activeWorkspace == pWorkspace->m_iID;
|
||||
|
||||
// fix old mon
|
||||
int nextWorkspaceOnMonitorID = -1;
|
||||
for (auto& w : m_lWorkspaces) {
|
||||
if (w.m_iMonitorID == POLDMON->ID && w.m_iID != pWorkspace->m_iID) {
|
||||
nextWorkspaceOnMonitorID = w.m_iID;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (nextWorkspaceOnMonitorID == -1) {
|
||||
nextWorkspaceOnMonitorID = 1;
|
||||
|
||||
while (getWorkspaceByID(nextWorkspaceOnMonitorID))
|
||||
nextWorkspaceOnMonitorID++;
|
||||
|
||||
Debug::log(LOG, "moveWorkspaceToMonitor: Plugging gap with new %d", nextWorkspaceOnMonitorID);
|
||||
}
|
||||
|
||||
Debug::log(LOG, "moveWorkspaceToMonitor: Plugging gap with existing %d", nextWorkspaceOnMonitorID);
|
||||
|
||||
g_pKeybindManager->focusMonitor(std::to_string(POLDMON->ID));
|
||||
g_pKeybindManager->changeworkspace(std::to_string(nextWorkspaceOnMonitorID));
|
||||
|
||||
// move the workspace
|
||||
|
||||
pWorkspace->m_iMonitorID = pMonitor->ID;
|
||||
pWorkspace->moveToMonitor(pMonitor->ID);
|
||||
|
||||
for (auto& w : m_lWindows) {
|
||||
if (w.m_iWorkspaceID == pWorkspace->m_iID)
|
||||
w.m_iMonitorID = pMonitor->ID;
|
||||
}
|
||||
|
||||
if (SWITCHINGISACTIVE) { // if it was active, preserve its' status. If it wasn't, don't.
|
||||
Debug::log(LOG, "moveWorkspaceToMonitor: SWITCHINGISACTIVE, active %d -> %d", pMonitor->activeWorkspace, pWorkspace->m_iID);
|
||||
|
||||
if (const auto PWORKSPACE = getWorkspaceByID(pMonitor->activeWorkspace); PWORKSPACE)
|
||||
getWorkspaceByID(pMonitor->activeWorkspace)->startAnim(false, false);
|
||||
|
||||
pMonitor->activeWorkspace = pWorkspace->m_iID;
|
||||
g_pLayoutManager->getCurrentLayout()->recalculateMonitor(pMonitor->ID);
|
||||
|
||||
pWorkspace->startAnim(true, true, true);
|
||||
|
||||
wlr_cursor_warp(m_sWLRCursor, m_sSeat.mouse->mouse, pMonitor->vecPosition.x + pMonitor->vecTransformedSize.x / 2, pMonitor->vecPosition.y + pMonitor->vecTransformedSize.y / 2);
|
||||
}
|
||||
|
||||
// finalize
|
||||
g_pLayoutManager->getCurrentLayout()->recalculateMonitor(POLDMON->ID);
|
||||
|
||||
g_pInputManager->refocus();
|
||||
}
|
||||
|
||||
bool CCompositor::workspaceIDOutOfBounds(const int& id) {
|
||||
int lowestID = 99999;
|
||||
int highestID = -99999;
|
||||
|
||||
for (auto& w : m_lWorkspaces) {
|
||||
if (w.m_iID < lowestID)
|
||||
lowestID = w.m_iID;
|
||||
|
||||
if (w.m_iID > highestID)
|
||||
highestID = w.m_iID;
|
||||
}
|
||||
|
||||
return std::clamp(id, lowestID, highestID) != id;
|
||||
}
|
@@ -126,6 +126,10 @@ public:
|
||||
SMonitor* getMonitorInDirection(const char&);
|
||||
void updateAllWindowsBorders();
|
||||
void updateWindowBorderColor(CWindow*);
|
||||
void moveWindowToWorkspace(CWindow*, const std::string&);
|
||||
int getNextAvailableMonitorID();
|
||||
void moveWorkspaceToMonitor(CWorkspace*, SMonitor*);
|
||||
bool workspaceIDOutOfBounds(const int&);
|
||||
|
||||
private:
|
||||
void initAllSignals();
|
||||
|
@@ -13,4 +13,34 @@ CWindow::~CWindow() {
|
||||
g_pCompositor->m_pLastFocus = nullptr;
|
||||
g_pCompositor->m_pLastWindow = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
wlr_box CWindow::getFullWindowBoundingBox() {
|
||||
|
||||
SWindowDecorationExtents maxExtents;
|
||||
|
||||
for (auto& wd : m_dWindowDecorations) {
|
||||
|
||||
const auto EXTENTS = wd->getWindowDecorationExtents();
|
||||
|
||||
if (EXTENTS.topLeft.x > maxExtents.topLeft.x)
|
||||
maxExtents.topLeft.x = EXTENTS.topLeft.x;
|
||||
|
||||
if (EXTENTS.topLeft.y > maxExtents.topLeft.y)
|
||||
maxExtents.topLeft.y = EXTENTS.topLeft.y;
|
||||
|
||||
if (EXTENTS.bottomRight.x > maxExtents.bottomRight.x)
|
||||
maxExtents.bottomRight.x = EXTENTS.bottomRight.x;
|
||||
|
||||
if (EXTENTS.bottomRight.y > maxExtents.bottomRight.y)
|
||||
maxExtents.bottomRight.y = EXTENTS.bottomRight.y;
|
||||
}
|
||||
|
||||
// Add extents to the real base BB and return
|
||||
wlr_box finalBox = {m_vRealPosition.vec().x - maxExtents.topLeft.x,
|
||||
m_vRealPosition.vec().y - maxExtents.topLeft.y,
|
||||
m_vRealSize.vec().x + maxExtents.topLeft.x + maxExtents.bottomRight.x,
|
||||
m_vRealSize.vec().y + maxExtents.topLeft.y + maxExtents.bottomRight.y};
|
||||
|
||||
return finalBox;
|
||||
}
|
@@ -9,6 +9,7 @@
|
||||
|
||||
struct SWindowSpecialRenderData {
|
||||
float alpha = 1.f;
|
||||
float alphaInactive = -1.f; // -1 means unset
|
||||
};
|
||||
|
||||
struct SWindowAdditionalConfigData {
|
||||
@@ -105,4 +106,7 @@ public:
|
||||
return m_uSurface.xdg == rhs.m_uSurface.xdg && m_uSurface.xwayland == rhs.m_uSurface.xwayland && m_vPosition == rhs.m_vPosition && m_vSize == rhs.m_vSize && m_bFadingOut == rhs.m_bFadingOut;
|
||||
}
|
||||
|
||||
// methods
|
||||
wlr_box getFullWindowBoundingBox();
|
||||
|
||||
};
|
@@ -26,8 +26,8 @@ std::string monitorsRequest() {
|
||||
std::string clientsRequest() {
|
||||
std::string result = "";
|
||||
for (auto& w : g_pCompositor->m_lWindows) {
|
||||
result += getFormat("Window %x -> %s:\n\tat: %i,%i\n\tsize: %i, %i\n\tworkspace: %i (%s)\n\tfloating: %i\n\n",
|
||||
&w, w.m_szTitle.c_str(), (int)w.m_vRealPosition.vec().x, (int)w.m_vRealPosition.vec().y, (int)w.m_vRealSize.vec().x, (int)w.m_vRealSize.vec().y, w.m_iWorkspaceID, (w.m_iWorkspaceID == -1 ? "" : g_pCompositor->getWorkspaceByID(w.m_iWorkspaceID)->m_szName.c_str()), (int)w.m_bIsFloating);
|
||||
result += getFormat("Window %x -> %s:\n\tat: %i,%i\n\tsize: %i,%i\n\tworkspace: %i (%s)\n\tfloating: %i\n\tmonitor: %i\n\n",
|
||||
&w, w.m_szTitle.c_str(), (int)w.m_vRealPosition.vec().x, (int)w.m_vRealPosition.vec().y, (int)w.m_vRealSize.vec().x, (int)w.m_vRealSize.vec().y, w.m_iWorkspaceID, (w.m_iWorkspaceID == -1 ? "" : g_pCompositor->getWorkspaceByID(w.m_iWorkspaceID)->m_szName.c_str()), (int)w.m_bIsFloating, w.m_iMonitorID);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
@@ -47,8 +47,8 @@ std::string activeWindowRequest() {
|
||||
if (!g_pCompositor->windowValidMapped(PWINDOW))
|
||||
return "Invalid";
|
||||
|
||||
return getFormat("Window %x -> %s:\n\tat: %i,%i\n\tsize: %i, %i\n\tworkspace: %i (%s)\n\tfloating: %i\n\n",
|
||||
PWINDOW, PWINDOW->m_szTitle.c_str(), (int)PWINDOW->m_vRealPosition.vec().x, (int)PWINDOW->m_vRealPosition.vec().y, (int)PWINDOW->m_vRealSize.vec().x, (int)PWINDOW->m_vRealSize.vec().y, PWINDOW->m_iWorkspaceID, (PWINDOW->m_iWorkspaceID == -1 ? "" : g_pCompositor->getWorkspaceByID(PWINDOW->m_iWorkspaceID)->m_szName.c_str()), (int)PWINDOW->m_bIsFloating);
|
||||
return getFormat("Window %x -> %s:\n\tat: %i,%i\n\tsize: %i,%i\n\tworkspace: %i (%s)\n\tfloating: %i\n\tmonitor: %i\n\n",
|
||||
PWINDOW, PWINDOW->m_szTitle.c_str(), (int)PWINDOW->m_vRealPosition.vec().x, (int)PWINDOW->m_vRealPosition.vec().y, (int)PWINDOW->m_vRealSize.vec().x, (int)PWINDOW->m_vRealSize.vec().y, PWINDOW->m_iWorkspaceID, (PWINDOW->m_iWorkspaceID == -1 ? "" : g_pCompositor->getWorkspaceByID(PWINDOW->m_iWorkspaceID)->m_szName.c_str()), (int)PWINDOW->m_bIsFloating, (int)PWINDOW->m_iMonitorID);
|
||||
}
|
||||
|
||||
std::string layersRequest() {
|
||||
|
@@ -64,4 +64,6 @@
|
||||
#endif
|
||||
#ifndef GIT_DIRTY
|
||||
#define GIT_DIRTY "?"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#define SPECIAL_WORKSPACE_ID -99
|
@@ -58,7 +58,12 @@ void Events::listener_destroyLayerSurface(void* owner, void* data) {
|
||||
|
||||
Debug::log(LOG, "LayerSurface %x destroyed", layersurface->layerSurface);
|
||||
|
||||
if (!layersurface->fadingOut) {
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromID(layersurface->monitorID);
|
||||
|
||||
if (!g_pCompositor->getMonitorFromID(layersurface->monitorID))
|
||||
Debug::log(WARN, "Layersurface destroyed on an invalid monitor (removed?)");
|
||||
|
||||
if (!layersurface->fadingOut && PMONITOR) {
|
||||
Debug::log(LOG, "Removing LayerSurface that wasn't mapped.");
|
||||
layersurface->alpha.setValueAndWarp(0.f);
|
||||
layersurface->fadingOut = true;
|
||||
@@ -70,8 +75,6 @@ void Events::listener_destroyLayerSurface(void* owner, void* data) {
|
||||
layersurface->hyprListener_unmapLayerSurface.removeCallback();
|
||||
layersurface->hyprListener_newPopup.removeCallback();
|
||||
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromID(layersurface->monitorID);
|
||||
|
||||
// rearrange to fix the reserved areas
|
||||
if (PMONITOR) {
|
||||
g_pHyprRenderer->arrangeLayersForMonitor(PMONITOR->ID);
|
||||
@@ -131,6 +134,11 @@ void Events::listener_unmapLayerSurface(void* owner, void* data) {
|
||||
|
||||
Debug::log(LOG, "LayerSurface %x unmapped", layersurface->layerSurface);
|
||||
|
||||
if (!g_pCompositor->getMonitorFromID(layersurface->monitorID)) {
|
||||
Debug::log(WARN, "Layersurface unmapping on invalid monitor (removed?) ignoring.");
|
||||
return;
|
||||
}
|
||||
|
||||
// make a snapshot and start fade
|
||||
g_pHyprOpenGL->makeLayerSnapshot(layersurface);
|
||||
layersurface->alpha = 0.f;
|
||||
|
@@ -70,7 +70,7 @@ void Events::listener_newOutput(wl_listener* listener, void* data) {
|
||||
|
||||
SMonitor newMonitor;
|
||||
newMonitor.output = OUTPUT;
|
||||
newMonitor.ID = g_pCompositor->m_lMonitors.size();
|
||||
newMonitor.ID = g_pCompositor->getNextAvailableMonitorID();
|
||||
newMonitor.szName = OUTPUT->name;
|
||||
|
||||
wlr_output_init_render(OUTPUT, g_pCompositor->m_sWLRAllocator, g_pCompositor->m_sWLRRenderer);
|
||||
@@ -111,17 +111,26 @@ void Events::listener_newOutput(wl_listener* listener, void* data) {
|
||||
|
||||
// Workspace
|
||||
const auto WORKSPACEID = monitorRule.defaultWorkspaceID == -1 ? g_pCompositor->m_lWorkspaces.size() + 1 /* Cuz workspaces doesnt have the new one yet and we start with 1 */ : monitorRule.defaultWorkspaceID;
|
||||
g_pCompositor->m_lWorkspaces.emplace_back(newMonitor.ID);
|
||||
const auto PNEWWORKSPACE = &g_pCompositor->m_lWorkspaces.back();
|
||||
|
||||
auto PNEWWORKSPACE = g_pCompositor->getWorkspaceByID(WORKSPACEID);
|
||||
|
||||
// We are required to set the name here immediately
|
||||
wlr_ext_workspace_handle_v1_set_name(PNEWWORKSPACE->m_pWlrHandle, std::to_string(WORKSPACEID).c_str());
|
||||
Debug::log(LOG, "New monitor: WORKSPACEID %d, exists: %d", WORKSPACEID, (int)(PNEWWORKSPACE != nullptr));
|
||||
|
||||
if (PNEWWORKSPACE) {
|
||||
// workspace exists, move it to the newly connected monitor
|
||||
g_pCompositor->moveWorkspaceToMonitor(PNEWWORKSPACE, PNEWMONITOR);
|
||||
} else {
|
||||
g_pCompositor->m_lWorkspaces.emplace_back(newMonitor.ID);
|
||||
PNEWWORKSPACE = &g_pCompositor->m_lWorkspaces.back();
|
||||
|
||||
PNEWWORKSPACE->m_iID = WORKSPACEID;
|
||||
PNEWWORKSPACE->m_szName = std::to_string(WORKSPACEID);
|
||||
// We are required to set the name here immediately
|
||||
wlr_ext_workspace_handle_v1_set_name(PNEWWORKSPACE->m_pWlrHandle, std::to_string(WORKSPACEID).c_str());
|
||||
|
||||
PNEWWORKSPACE->m_iID = WORKSPACEID;
|
||||
PNEWWORKSPACE->m_szName = std::to_string(WORKSPACEID);
|
||||
}
|
||||
|
||||
PNEWMONITOR->activeWorkspace = PNEWWORKSPACE->m_iID;
|
||||
|
||||
PNEWMONITOR->scale = monitorRule.scale;
|
||||
|
||||
g_pCompositor->deactivateAllWLRWorkspaces(PNEWWORKSPACE->m_pWlrHandle);
|
||||
@@ -132,7 +141,9 @@ void Events::listener_newOutput(wl_listener* listener, void* data) {
|
||||
//
|
||||
|
||||
if (!g_pCompositor->m_pLastMonitor) // set the last monitor if it isnt set yet
|
||||
g_pCompositor->m_pLastMonitor = PNEWMONITOR;
|
||||
g_pCompositor->m_pLastMonitor = PNEWMONITOR;
|
||||
|
||||
g_pEventManager->postEvent(SHyprIPCEvent("monitoradded", PNEWMONITOR->szName));
|
||||
|
||||
// ready to process cuz we have a monitor
|
||||
g_pCompositor->m_bReadyToProcess = true;
|
||||
@@ -296,7 +307,58 @@ void Events::listener_monitorDestroy(void* owner, void* data) {
|
||||
if (!pMonitor)
|
||||
return;
|
||||
|
||||
// Cleanup everything. Move windows back, snap cursor, shit.
|
||||
const auto BACKUPMON = &g_pCompositor->m_lMonitors.front();
|
||||
const auto BACKUPWORKSPACE = BACKUPMON->activeWorkspace > 0 ? std::to_string(BACKUPMON->activeWorkspace) : "name:" + g_pCompositor->getWorkspaceByID(BACKUPMON->activeWorkspace)->m_szName;
|
||||
|
||||
if (!BACKUPMON) {
|
||||
Debug::log(CRIT, "No monitors! Unplugged last! Exiting.");
|
||||
g_pCompositor->cleanupExit();
|
||||
return;
|
||||
}
|
||||
|
||||
// snap cursor
|
||||
wlr_cursor_warp(g_pCompositor->m_sWLRCursor, g_pCompositor->m_sSeat.mouse->mouse, BACKUPMON->vecPosition.x + BACKUPMON->vecTransformedSize.x / 2.f, BACKUPMON->vecPosition.y + BACKUPMON->vecTransformedSize.y / 2.f);
|
||||
|
||||
// move workspaces
|
||||
std::deque<CWorkspace*> wspToMove;
|
||||
for (auto& w : g_pCompositor->m_lWorkspaces) {
|
||||
if (w.m_iMonitorID == pMonitor->ID) {
|
||||
wspToMove.push_back(&w);
|
||||
}
|
||||
}
|
||||
|
||||
for (auto& w : wspToMove) {
|
||||
g_pCompositor->moveWorkspaceToMonitor(w, BACKUPMON);
|
||||
w->startAnim(true, true, true);
|
||||
}
|
||||
|
||||
pMonitor->activeWorkspace = -1;
|
||||
|
||||
for (auto it = g_pCompositor->m_lWorkspaces.begin(); it != g_pCompositor->m_lWorkspaces.end(); ++it) {
|
||||
if (it->m_iMonitorID == pMonitor->ID) {
|
||||
it = g_pCompositor->m_lWorkspaces.erase(it);
|
||||
}
|
||||
}
|
||||
|
||||
Debug::log(LOG, "Removed monitor %s!", pMonitor->szName.c_str());
|
||||
|
||||
g_pEventManager->postEvent(SHyprIPCEvent("monitorremoved", pMonitor->szName));
|
||||
|
||||
g_pCompositor->m_lMonitors.remove(*pMonitor);
|
||||
|
||||
// TODO: cleanup windows
|
||||
// update the pMostHzMonitor
|
||||
if (pMostHzMonitor == pMonitor) {
|
||||
int mostHz = 0;
|
||||
SMonitor* pMonitorMostHz = nullptr;
|
||||
|
||||
for (auto& m : g_pCompositor->m_lMonitors) {
|
||||
if (m.refreshRate > mostHz) {
|
||||
pMonitorMostHz = &m;
|
||||
mostHz = m.refreshRate;
|
||||
}
|
||||
}
|
||||
|
||||
pMostHzMonitor = pMonitorMostHz;
|
||||
}
|
||||
}
|
||||
|
@@ -25,10 +25,10 @@ void Events::listener_mapWindow(void* owner, void* data) {
|
||||
CWindow* PWINDOW = (CWindow*)owner;
|
||||
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromCursor();
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(PMONITOR->activeWorkspace);
|
||||
const auto PWORKSPACE = PMONITOR->specialWorkspaceOpen ? g_pCompositor->getWorkspaceByID(SPECIAL_WORKSPACE_ID) : g_pCompositor->getWorkspaceByID(PMONITOR->activeWorkspace);
|
||||
PWINDOW->m_iMonitorID = PMONITOR->ID;
|
||||
PWINDOW->m_bMappedX11 = true;
|
||||
PWINDOW->m_iWorkspaceID = PMONITOR->activeWorkspace;
|
||||
PWINDOW->m_iWorkspaceID = PMONITOR->specialWorkspaceOpen ? SPECIAL_WORKSPACE_ID : PMONITOR->activeWorkspace;
|
||||
PWINDOW->m_bIsMapped = true;
|
||||
PWINDOW->m_bReadyToDelete = false;
|
||||
PWINDOW->m_bFadingOut = false;
|
||||
@@ -114,7 +114,15 @@ void Events::listener_mapWindow(void* owner, void* data) {
|
||||
}
|
||||
} else if (r.szRule.find("opacity") == 0) {
|
||||
try {
|
||||
PWINDOW->m_sSpecialRenderData.alpha = std::stof(r.szRule.substr(r.szRule.find_first_of(' ') + 1));
|
||||
std::string alphaPart = r.szRule.substr(r.szRule.find_first_of(' ') + 1);
|
||||
|
||||
if (alphaPart.find_first_of(' ') != std::string::npos) {
|
||||
// we have a comma, 2 values
|
||||
PWINDOW->m_sSpecialRenderData.alpha = std::stof(alphaPart.substr(0, alphaPart.find_first_of(' ')));
|
||||
PWINDOW->m_sSpecialRenderData.alphaInactive = std::stof(alphaPart.substr(alphaPart.find_first_of(' ') + 1));
|
||||
} else {
|
||||
PWINDOW->m_sSpecialRenderData.alpha = std::stof(alphaPart);
|
||||
}
|
||||
} catch(std::exception& e) {
|
||||
Debug::log(ERR, "Opacity rule \"%s\" failed with: %s", r.szRule.c_str(), e.what());
|
||||
}
|
||||
|
@@ -149,8 +149,6 @@ public:
|
||||
return false; // unreachable
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
void warp() {
|
||||
switch (m_eVarType) {
|
||||
case AVARTYPE_FLOAT: {
|
||||
@@ -170,6 +168,8 @@ private:
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
Vector2D m_vValue = Vector2D(0,0);
|
||||
float m_fValue = 0;
|
||||
CColor m_cValue;
|
||||
|
@@ -125,7 +125,10 @@ bool isDirection(const std::string& arg) {
|
||||
|
||||
int getWorkspaceIDFromString(const std::string& in, std::string& outName) {
|
||||
int result = INT_MAX;
|
||||
if (in.find("name:") == 0) {
|
||||
if (in.find("special") == 0) {
|
||||
outName = "special";
|
||||
return SPECIAL_WORKSPACE_ID;
|
||||
} else if (in.find("name:") == 0) {
|
||||
const auto WORKSPACENAME = in.substr(in.find_first_of(':') + 1);
|
||||
const auto WORKSPACE = g_pCompositor->getWorkspaceByName(WORKSPACENAME);
|
||||
if (!WORKSPACE) {
|
||||
@@ -135,8 +138,59 @@ int getWorkspaceIDFromString(const std::string& in, std::string& outName) {
|
||||
}
|
||||
outName = WORKSPACENAME;
|
||||
} else {
|
||||
result = std::clamp((int)getPlusMinusKeywordResult(in, g_pCompositor->m_pLastMonitor->activeWorkspace), 1, INT_MAX);
|
||||
outName = std::to_string(result);
|
||||
if (in[0] == 'm') {
|
||||
// monitor relative
|
||||
result = (int)getPlusMinusKeywordResult(in.substr(1), 0);
|
||||
|
||||
// result now has +/- what we should move on mon
|
||||
int remains = (int)result;
|
||||
int currentID = g_pCompositor->m_pLastMonitor->activeWorkspace;
|
||||
int searchID = currentID;
|
||||
|
||||
while (remains != 0) {
|
||||
if (remains < 0)
|
||||
searchID--;
|
||||
else
|
||||
searchID++;
|
||||
|
||||
if (g_pCompositor->workspaceIDOutOfBounds(searchID)){
|
||||
// means we need to wrap around
|
||||
int lowestID = 99999;
|
||||
int highestID = -99999;
|
||||
|
||||
for (auto& w : g_pCompositor->m_lWorkspaces) {
|
||||
if (w.m_iID < lowestID)
|
||||
lowestID = w.m_iID;
|
||||
|
||||
if (w.m_iID > highestID)
|
||||
highestID = w.m_iID;
|
||||
}
|
||||
|
||||
if (remains < 0)
|
||||
searchID = highestID;
|
||||
else
|
||||
searchID = lowestID;
|
||||
}
|
||||
|
||||
if (const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(searchID); PWORKSPACE) {
|
||||
if (PWORKSPACE->m_iMonitorID == g_pCompositor->m_pLastMonitor->ID) {
|
||||
currentID = PWORKSPACE->m_iID;
|
||||
|
||||
if (remains < 0)
|
||||
remains++;
|
||||
else
|
||||
remains--;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
result = currentID;
|
||||
outName = g_pCompositor->getWorkspaceByID(currentID)->m_szName;
|
||||
|
||||
} else {
|
||||
result = std::clamp((int)getPlusMinusKeywordResult(in, g_pCompositor->m_pLastMonitor->activeWorkspace), 1, INT_MAX);
|
||||
outName = std::to_string(result);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
|
@@ -29,6 +29,9 @@ struct SMonitor {
|
||||
wlr_output_damage* damage = nullptr;
|
||||
bool needsFrameSkip = false;
|
||||
wl_output_transform transform = WL_OUTPUT_TRANSFORM_NORMAL;
|
||||
|
||||
// for the special workspace
|
||||
bool specialWorkspaceOpen = false;
|
||||
|
||||
// Double-linked list because we need to have constant mem addresses for signals
|
||||
// We have to store pointers and use raw new/delete because they might be moved between them
|
||||
|
@@ -1,7 +1,7 @@
|
||||
#include "Workspace.hpp"
|
||||
#include "../Compositor.hpp"
|
||||
|
||||
CWorkspace::CWorkspace(int monitorID) {
|
||||
CWorkspace::CWorkspace(int monitorID, bool special) {
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromID(monitorID);
|
||||
|
||||
if (!PMONITOR) {
|
||||
@@ -10,16 +10,20 @@ CWorkspace::CWorkspace(int monitorID) {
|
||||
}
|
||||
|
||||
m_iMonitorID = monitorID;
|
||||
|
||||
m_pWlrHandle = wlr_ext_workspace_handle_v1_create(PMONITOR->pWLRWorkspaceGroupHandle);
|
||||
|
||||
// set geometry here cuz we can
|
||||
wl_array_init(&m_wlrCoordinateArr);
|
||||
*reinterpret_cast<int*>(wl_array_add(&m_wlrCoordinateArr, sizeof(int))) = (int)PMONITOR->vecPosition.x;
|
||||
*reinterpret_cast<int*>(wl_array_add(&m_wlrCoordinateArr, sizeof(int))) = (int)PMONITOR->vecPosition.y;
|
||||
wlr_ext_workspace_handle_v1_set_coordinates(m_pWlrHandle, &m_wlrCoordinateArr);
|
||||
wlr_ext_workspace_handle_v1_set_hidden(m_pWlrHandle, false);
|
||||
wlr_ext_workspace_handle_v1_set_urgent(m_pWlrHandle, false);
|
||||
m_bIsSpecialWorkspace = special;
|
||||
|
||||
if (!special) {
|
||||
m_pWlrHandle = wlr_ext_workspace_handle_v1_create(PMONITOR->pWLRWorkspaceGroupHandle);
|
||||
|
||||
// set geometry here cuz we can
|
||||
wl_array_init(&m_wlrCoordinateArr);
|
||||
*reinterpret_cast<int*>(wl_array_add(&m_wlrCoordinateArr, sizeof(int))) = (int)PMONITOR->vecPosition.x;
|
||||
*reinterpret_cast<int*>(wl_array_add(&m_wlrCoordinateArr, sizeof(int))) = (int)PMONITOR->vecPosition.y;
|
||||
wlr_ext_workspace_handle_v1_set_coordinates(m_pWlrHandle, &m_wlrCoordinateArr);
|
||||
wlr_ext_workspace_handle_v1_set_hidden(m_pWlrHandle, false);
|
||||
wlr_ext_workspace_handle_v1_set_urgent(m_pWlrHandle, false);
|
||||
}
|
||||
|
||||
m_vRenderOffset.m_pWorkspace = this;
|
||||
m_vRenderOffset.create(AVARTYPE_VECTOR, &g_pConfigManager->getConfigValuePtr("animations:workspaces_speed")->floatValue, &g_pConfigManager->getConfigValuePtr("animations:workspaces")->intValue, &g_pConfigManager->getConfigValuePtr("animations:workspaces_curve")->strValue, nullptr, AVARDAMAGE_ENTIRE);
|
||||
@@ -31,6 +35,8 @@ CWorkspace::CWorkspace(int monitorID) {
|
||||
CWorkspace::~CWorkspace() {
|
||||
m_vRenderOffset.unregister();
|
||||
|
||||
Debug::log(LOG, "Destroying workspace ID %d", m_iID);
|
||||
|
||||
if (m_pWlrHandle) {
|
||||
wlr_ext_workspace_handle_v1_set_active(m_pWlrHandle, false);
|
||||
wlr_ext_workspace_handle_v1_destroy(m_pWlrHandle);
|
||||
@@ -38,7 +44,7 @@ CWorkspace::~CWorkspace() {
|
||||
}
|
||||
}
|
||||
|
||||
void CWorkspace::startAnim(bool in, bool left) {
|
||||
void CWorkspace::startAnim(bool in, bool left, bool instant) {
|
||||
const auto ANIMSTYLE = g_pConfigManager->getString("animations:workspaces_style");
|
||||
|
||||
if (ANIMSTYLE == "fade") {
|
||||
@@ -51,6 +57,18 @@ void CWorkspace::startAnim(bool in, bool left) {
|
||||
m_fAlpha.setValueAndWarp(255.f);
|
||||
m_fAlpha = 0.f;
|
||||
}
|
||||
} else if ("slidevert") {
|
||||
// fallback is slide
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromID(m_iMonitorID);
|
||||
|
||||
m_fAlpha.setValueAndWarp(255.f); // fix a bug, if switching from fade -> slide.
|
||||
|
||||
if (in) {
|
||||
m_vRenderOffset.setValueAndWarp(Vector2D(0, left ? PMONITOR->vecSize.y : -PMONITOR->vecSize.y));
|
||||
m_vRenderOffset = Vector2D(0, 0);
|
||||
} else {
|
||||
m_vRenderOffset = Vector2D(0, left ? -PMONITOR->vecSize.y : PMONITOR->vecSize.y);
|
||||
}
|
||||
} else {
|
||||
// fallback is slide
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromID(m_iMonitorID);
|
||||
@@ -64,10 +82,37 @@ void CWorkspace::startAnim(bool in, bool left) {
|
||||
m_vRenderOffset = Vector2D(left ? -PMONITOR->vecSize.x : PMONITOR->vecSize.x, 0);
|
||||
}
|
||||
}
|
||||
|
||||
if (instant) {
|
||||
m_vRenderOffset.warp();
|
||||
m_fAlpha.warp();
|
||||
}
|
||||
}
|
||||
|
||||
void CWorkspace::setActive(bool on) {
|
||||
if (m_pWlrHandle) {
|
||||
wlr_ext_workspace_handle_v1_set_active(m_pWlrHandle, on);
|
||||
}
|
||||
}
|
||||
|
||||
void CWorkspace::moveToMonitor(const int& id) {
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromID(id);
|
||||
|
||||
if (!PMONITOR || m_bIsSpecialWorkspace)
|
||||
return;
|
||||
|
||||
wlr_ext_workspace_handle_v1_set_active(m_pWlrHandle, false);
|
||||
wlr_ext_workspace_handle_v1_destroy(m_pWlrHandle);
|
||||
|
||||
m_pWlrHandle = wlr_ext_workspace_handle_v1_create(PMONITOR->pWLRWorkspaceGroupHandle);
|
||||
|
||||
// set geometry here cuz we can
|
||||
wl_array_init(&m_wlrCoordinateArr);
|
||||
*reinterpret_cast<int*>(wl_array_add(&m_wlrCoordinateArr, sizeof(int))) = (int)PMONITOR->vecPosition.x;
|
||||
*reinterpret_cast<int*>(wl_array_add(&m_wlrCoordinateArr, sizeof(int))) = (int)PMONITOR->vecPosition.y;
|
||||
wlr_ext_workspace_handle_v1_set_coordinates(m_pWlrHandle, &m_wlrCoordinateArr);
|
||||
wlr_ext_workspace_handle_v1_set_hidden(m_pWlrHandle, false);
|
||||
wlr_ext_workspace_handle_v1_set_urgent(m_pWlrHandle, false);
|
||||
|
||||
wlr_ext_workspace_handle_v1_set_name(m_pWlrHandle, m_szName.c_str());
|
||||
}
|
@@ -10,7 +10,7 @@ enum eFullscreenMode : uint8_t {
|
||||
|
||||
class CWorkspace {
|
||||
public:
|
||||
CWorkspace(int monitorID);
|
||||
CWorkspace(int monitorID, bool special = false);
|
||||
~CWorkspace();
|
||||
|
||||
// Workspaces ID-based have IDs > 0
|
||||
@@ -29,10 +29,15 @@ public:
|
||||
CAnimatedVariable m_vRenderOffset;
|
||||
CAnimatedVariable m_fAlpha;
|
||||
|
||||
// "scratchpad"
|
||||
bool m_bIsSpecialWorkspace = false;
|
||||
|
||||
// user-set
|
||||
bool m_bDefaultFloating = false;
|
||||
bool m_bDefaultPseudo = false;
|
||||
|
||||
void startAnim(bool in, bool left);
|
||||
void startAnim(bool in, bool left, bool instant = false);
|
||||
void setActive(bool on);
|
||||
|
||||
void moveToMonitor(const int&);
|
||||
};
|
@@ -34,56 +34,56 @@
|
||||
#define static
|
||||
|
||||
extern "C" {
|
||||
#include <wlr/backend.h>
|
||||
#include <wlr/backend/libinput.h>
|
||||
#include <wlr/render/allocator.h>
|
||||
#include <wlr/render/wlr_renderer.h>
|
||||
#include <wlr/types/wlr_compositor.h>
|
||||
#include <wlr/types/wlr_cursor.h>
|
||||
#include <wlr/types/wlr_data_control_v1.h>
|
||||
#include <wlr/types/wlr_data_device.h>
|
||||
#include <wlr/types/wlr_export_dmabuf_v1.h>
|
||||
#include <wlr/types/wlr_linux_dmabuf_v1.h>
|
||||
#include <wlr/types/wlr_gamma_control_v1.h>
|
||||
#include <wlr/types/wlr_idle.h>
|
||||
#include <wlr/types/wlr_input_device.h>
|
||||
#include <wlr/types/wlr_keyboard.h>
|
||||
#include <wlr/types/wlr_layer_shell_v1.h>
|
||||
#include <wlr/types/wlr_matrix.h>
|
||||
#include <wlr/types/wlr_output.h>
|
||||
#include <wlr/types/wlr_output_layout.h>
|
||||
#include <wlr/types/wlr_output_management_v1.h>
|
||||
#include <wlr/types/wlr_pointer.h>
|
||||
#include <wlr/types/wlr_presentation_time.h>
|
||||
#include <wlr/types/wlr_primary_selection.h>
|
||||
#include <wlr/types/wlr_primary_selection_v1.h>
|
||||
#include <wlr/types/wlr_screencopy_v1.h>
|
||||
#include <wlr/types/wlr_seat.h>
|
||||
#include <wlr/types/wlr_server_decoration.h>
|
||||
#include <wlr/types/wlr_viewporter.h>
|
||||
#include <wlr/types/wlr_virtual_keyboard_v1.h>
|
||||
#include <wlr/types/wlr_xcursor_manager.h>
|
||||
#include <wlr/types/wlr_xdg_activation_v1.h>
|
||||
#include <wlr/types/wlr_xdg_decoration_v1.h>
|
||||
#include <wlr/types/wlr_xdg_output_v1.h>
|
||||
#include <wlr/types/wlr_xdg_shell.h>
|
||||
#include <wlr/types/wlr_subcompositor.h>
|
||||
#include <wlr/types/wlr_scene.h>
|
||||
#include <wlr/types/wlr_output_damage.h>
|
||||
#include <wlr/types/wlr_input_inhibitor.h>
|
||||
#include <wlr/types/wlr_keyboard_shortcuts_inhibit_v1.h>
|
||||
#include <wlr/types/wlr_virtual_pointer_v1.h>
|
||||
#include <wlr/types/wlr_foreign_toplevel_management_v1.h>
|
||||
#include <wlr/util/log.h>
|
||||
#include <wlr/xwayland.h>
|
||||
#include <wlr/util/region.h>
|
||||
#include "../wlroots/include/wlr/backend.h"
|
||||
#include "../wlroots/include/wlr/backend/libinput.h"
|
||||
#include "../wlroots/include/wlr/render/allocator.h"
|
||||
#include "../wlroots/include/wlr/render/wlr_renderer.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_compositor.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_cursor.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_data_control_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_data_device.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_export_dmabuf_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_linux_dmabuf_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_gamma_control_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_idle.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_input_device.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_keyboard.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_layer_shell_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_matrix.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_output.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_output_layout.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_output_management_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_pointer.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_presentation_time.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_primary_selection.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_primary_selection_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_screencopy_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_seat.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_server_decoration.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_viewporter.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_virtual_keyboard_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_xcursor_manager.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_xdg_activation_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_xdg_decoration_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_xdg_output_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_xdg_shell.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_subcompositor.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_scene.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_output_damage.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_input_inhibitor.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_keyboard_shortcuts_inhibit_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_virtual_pointer_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_foreign_toplevel_management_v1.h"
|
||||
#include "../wlroots/include/wlr/util/log.h"
|
||||
#include "../wlroots/include/wlr/xwayland.h"
|
||||
#include "../wlroots/include/wlr/util/region.h"
|
||||
#include <xkbcommon/xkbcommon.h>
|
||||
#include <X11/Xproto.h>
|
||||
#include <wlr/render/egl.h>
|
||||
#include <wlr/render/gles2.h>
|
||||
#include <wlr/render/wlr_texture.h>
|
||||
#include <wlr/types/wlr_pointer_constraints_v1.h>
|
||||
#include <wlr/types/wlr_relative_pointer_v1.h>
|
||||
#include "../wlroots/include/wlr/render/egl.h"
|
||||
#include "../wlroots/include/wlr/render/gles2.h"
|
||||
#include "../wlroots/include/wlr/render/wlr_texture.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_pointer_constraints_v1.h"
|
||||
#include "../wlroots/include/wlr/types/wlr_relative_pointer_v1.h"
|
||||
}
|
||||
|
||||
#undef class
|
||||
|
@@ -160,10 +160,20 @@ void CHyprDwindleLayout::applyNodeDataToWindow(SDwindleNodeData* pNode) {
|
||||
}
|
||||
}
|
||||
|
||||
PWINDOW->m_vRealSize = calcSize;
|
||||
PWINDOW->m_vRealPosition = calcPos;
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(PWINDOW->m_iWorkspaceID);
|
||||
|
||||
g_pXWaylandManager->setWindowSize(PWINDOW, calcSize);
|
||||
if (PWORKSPACE->m_bIsSpecialWorkspace) {
|
||||
// if special, we adjust the coords a bit
|
||||
PWINDOW->m_vRealPosition = calcPos + (calcSize - calcSize * 0.8f) / 2.f;
|
||||
PWINDOW->m_vRealSize = calcSize * 0.8f;
|
||||
|
||||
g_pXWaylandManager->setWindowSize(PWINDOW, calcSize * 0.8f);
|
||||
} else {
|
||||
PWINDOW->m_vRealSize = calcSize;
|
||||
PWINDOW->m_vRealPosition = calcPos;
|
||||
|
||||
g_pXWaylandManager->setWindowSize(PWINDOW, calcSize);
|
||||
}
|
||||
}
|
||||
|
||||
void CHyprDwindleLayout::onWindowCreated(CWindow* pWindow) {
|
||||
@@ -184,7 +194,7 @@ void CHyprDwindleLayout::onWindowCreated(CWindow* pWindow) {
|
||||
SDwindleNodeData* OPENINGON;
|
||||
const auto MONFROMCURSOR = g_pCompositor->getMonitorFromCursor();
|
||||
|
||||
if (PMONITOR->ID == MONFROMCURSOR->ID && PNODE->workspaceID == PMONITOR->activeWorkspace) {
|
||||
if (PMONITOR->ID == MONFROMCURSOR->ID && (PNODE->workspaceID == PMONITOR->activeWorkspace || (PNODE->workspaceID == SPECIAL_WORKSPACE_ID && PMONITOR->specialWorkspaceOpen))) {
|
||||
OPENINGON = getNodeFromWindow(g_pCompositor->vectorToWindowTiled(g_pInputManager->getMouseCoordsInternal()));
|
||||
|
||||
// happens on reserved area
|
||||
@@ -196,6 +206,11 @@ void CHyprDwindleLayout::onWindowCreated(CWindow* pWindow) {
|
||||
|
||||
Debug::log(LOG, "OPENINGON: %x, Workspace: %i, Monitor: %i", OPENINGON, PNODE->workspaceID, PMONITOR->ID);
|
||||
|
||||
if (OPENINGON && OPENINGON->workspaceID != PNODE->workspaceID) {
|
||||
// special workspace handling
|
||||
OPENINGON = getFirstNodeOnWorkspace(PNODE->workspaceID);
|
||||
}
|
||||
|
||||
// if it's the first, it's easy. Make it fullscreen.
|
||||
if (!OPENINGON || OPENINGON->pWindow == pWindow) {
|
||||
PNODE->position = PMONITOR->vecPosition + PMONITOR->vecReservedTopLeft;
|
||||
@@ -356,6 +371,19 @@ void CHyprDwindleLayout::recalculateMonitor(const int& monid) {
|
||||
const auto PMONITOR = g_pCompositor->getMonitorFromID(monid);
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(PMONITOR->activeWorkspace);
|
||||
|
||||
if (!PWORKSPACE)
|
||||
return;
|
||||
|
||||
if (PMONITOR->specialWorkspaceOpen) {
|
||||
const auto TOPNODE = getMasterNodeOnWorkspace(SPECIAL_WORKSPACE_ID);
|
||||
|
||||
if (TOPNODE && PMONITOR) {
|
||||
TOPNODE->position = PMONITOR->vecPosition + PMONITOR->vecReservedTopLeft;
|
||||
TOPNODE->size = PMONITOR->vecSize - PMONITOR->vecReservedTopLeft - PMONITOR->vecReservedBottomRight;
|
||||
TOPNODE->recalcSizePosRecursive();
|
||||
}
|
||||
}
|
||||
|
||||
// Ignore any recalc events if we have a fullscreen window.
|
||||
if (PWORKSPACE->m_bHasFullscreenWindow)
|
||||
return;
|
||||
|
@@ -105,7 +105,7 @@ void CInputManager::mouseMoveUnified(uint32_t time, bool refocus) {
|
||||
|
||||
// then, we check if the workspace doesnt have a fullscreen window
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(PMONITOR->activeWorkspace);
|
||||
if (PWORKSPACE->m_bHasFullscreenWindow && !foundSurface) {
|
||||
if (PWORKSPACE->m_bHasFullscreenWindow && !foundSurface && PWORKSPACE->m_efFullscreenMode == FULLSCREEN_FULL) {
|
||||
pFoundWindow = g_pCompositor->getFullscreenWindowOnWorkspace(PWORKSPACE->m_iID);
|
||||
foundSurface = g_pXWaylandManager->getWindowSurface(pFoundWindow);
|
||||
surfacePos = pFoundWindow->m_vRealPosition.vec();
|
||||
@@ -113,7 +113,7 @@ void CInputManager::mouseMoveUnified(uint32_t time, bool refocus) {
|
||||
// only check floating because tiled cant be over fullscreen
|
||||
for (auto w = g_pCompositor->m_lWindows.rbegin(); w != g_pCompositor->m_lWindows.rend(); w++) {
|
||||
wlr_box box = {w->m_vRealPosition.vec().x, w->m_vRealPosition.vec().y, w->m_vRealSize.vec().x, w->m_vRealSize.vec().y};
|
||||
if (w->m_bIsFloating && w->m_bIsMapped && w->m_bCreatedOverFullscreen && wlr_box_contains_point(&box, mouseCoords.x, mouseCoords.y) && g_pCompositor->isWorkspaceVisible(w->m_iWorkspaceID) && !w->m_bHidden) {
|
||||
if (((w->m_bIsFloating && w->m_bIsMapped && w->m_bCreatedOverFullscreen) || (w->m_iWorkspaceID == SPECIAL_WORKSPACE_ID && PMONITOR->specialWorkspaceOpen)) && wlr_box_contains_point(&box, mouseCoords.x, mouseCoords.y) && g_pCompositor->isWorkspaceVisible(w->m_iWorkspaceID) && !w->m_bHidden) {
|
||||
pFoundWindow = &(*w);
|
||||
|
||||
if (!pFoundWindow->m_bIsX11) {
|
||||
|
@@ -21,6 +21,9 @@ CKeybindManager::CKeybindManager() {
|
||||
m_mDispatchers["movecursortocorner"] = moveCursorToCorner;
|
||||
m_mDispatchers["workspaceopt"] = workspaceOpt;
|
||||
m_mDispatchers["exit"] = exitHyprland;
|
||||
m_mDispatchers["movecurrentworkspacetomonitor"] = moveCurrentWorkspaceToMonitor;
|
||||
m_mDispatchers["moveworkspacetomonitor"] = moveWorkspaceToMonitor;
|
||||
m_mDispatchers["togglespecialworkspace"] = toggleSpecialWorkspace;
|
||||
}
|
||||
|
||||
void CKeybindManager::addKeybind(SKeybind kb) {
|
||||
@@ -151,6 +154,10 @@ void CKeybindManager::toggleActiveFloating(std::string args) {
|
||||
if (g_pCompositor->windowValidMapped(ACTIVEWINDOW)) {
|
||||
ACTIVEWINDOW->m_bIsFloating = !ACTIVEWINDOW->m_bIsFloating;
|
||||
|
||||
if (ACTIVEWINDOW->m_iWorkspaceID == SPECIAL_WORKSPACE_ID) {
|
||||
moveActiveToWorkspace(std::to_string(g_pCompositor->getMonitorFromID(ACTIVEWINDOW->m_iMonitorID)->activeWorkspace));
|
||||
}
|
||||
|
||||
ACTIVEWINDOW->m_vRealPosition.setValue(ACTIVEWINDOW->m_vRealPosition.vec() + Vector2D(5, 5));
|
||||
ACTIVEWINDOW->m_vSize = ACTIVEWINDOW->m_vRealPosition.vec() - Vector2D(10, 10);
|
||||
|
||||
@@ -189,12 +196,20 @@ void CKeybindManager::changeworkspace(std::string args) {
|
||||
|
||||
const auto PWORKSPACETOCHANGETO = g_pCompositor->getWorkspaceByID(workspaceToChangeTo);
|
||||
|
||||
if (workspaceToChangeTo == SPECIAL_WORKSPACE_ID)
|
||||
PWORKSPACETOCHANGETO->m_iMonitorID = PMONITOR->ID;
|
||||
|
||||
// if it's not visible, make it visible.
|
||||
if (!g_pCompositor->isWorkspaceVisible(workspaceToChangeTo)) {
|
||||
const auto OLDWORKSPACEID = PMONITOR->activeWorkspace;
|
||||
|
||||
// change it
|
||||
PMONITOR->activeWorkspace = workspaceToChangeTo;
|
||||
PMONITOR->specialWorkspaceOpen = false;
|
||||
|
||||
if (workspaceToChangeTo != SPECIAL_WORKSPACE_ID)
|
||||
PMONITOR->activeWorkspace = workspaceToChangeTo;
|
||||
else
|
||||
PMONITOR->specialWorkspaceOpen = true;
|
||||
|
||||
// we need to move XWayland windows to narnia or otherwise they will still process our cursor and shit
|
||||
// and that'd be annoying as hell
|
||||
@@ -217,7 +232,6 @@ void CKeybindManager::changeworkspace(std::string args) {
|
||||
if (!m_bSuppressWorkspaceChangeEvents)
|
||||
g_pEventManager->postEvent(SHyprIPCEvent("workspace", PWORKSPACETOCHANGETO->m_szName));
|
||||
}
|
||||
|
||||
|
||||
// If the monitor is not the one our cursor's at, warp to it.
|
||||
if (PMONITOR != g_pCompositor->getMonitorFromCursor()) {
|
||||
@@ -232,6 +246,9 @@ void CKeybindManager::changeworkspace(std::string args) {
|
||||
g_pCompositor->deactivateAllWLRWorkspaces(PWORKSPACETOCHANGETO->m_pWlrHandle);
|
||||
PWORKSPACETOCHANGETO->setActive(true);
|
||||
|
||||
// recalc layout
|
||||
g_pLayoutManager->getCurrentLayout()->recalculateMonitor(PWORKSPACETOCHANGETO->m_iMonitorID);
|
||||
|
||||
Debug::log(LOG, "Changed to workspace %i", workspaceToChangeTo);
|
||||
|
||||
// focus
|
||||
@@ -252,22 +269,29 @@ void CKeybindManager::changeworkspace(std::string args) {
|
||||
const auto ANIMTOLEFT = workspaceToChangeTo > OLDWORKSPACE;
|
||||
|
||||
// start anim on old workspace
|
||||
g_pCompositor->getWorkspaceByID(OLDWORKSPACE)->startAnim(false, ANIMTOLEFT);
|
||||
if (const auto POLDWORKSPACE = g_pCompositor->getWorkspaceByID(OLDWORKSPACE); POLDWORKSPACE)
|
||||
POLDWORKSPACE->startAnim(false, ANIMTOLEFT);
|
||||
|
||||
g_pCompositor->m_lWorkspaces.emplace_back(PMONITOR->ID);
|
||||
g_pCompositor->m_lWorkspaces.emplace_back(PMONITOR->ID, workspaceToChangeTo == SPECIAL_WORKSPACE_ID);
|
||||
const auto PWORKSPACE = &g_pCompositor->m_lWorkspaces.back();
|
||||
|
||||
// start anim on new workspace
|
||||
PWORKSPACE->startAnim(true, ANIMTOLEFT);
|
||||
|
||||
// We are required to set the name here immediately
|
||||
wlr_ext_workspace_handle_v1_set_name(PWORKSPACE->m_pWlrHandle, workspaceName.c_str());
|
||||
if (workspaceToChangeTo != SPECIAL_WORKSPACE_ID)
|
||||
wlr_ext_workspace_handle_v1_set_name(PWORKSPACE->m_pWlrHandle, workspaceName.c_str());
|
||||
|
||||
PWORKSPACE->m_iID = workspaceToChangeTo;
|
||||
PWORKSPACE->m_iMonitorID = PMONITOR->ID;
|
||||
PWORKSPACE->m_szName = workspaceName;
|
||||
|
||||
PMONITOR->activeWorkspace = workspaceToChangeTo;
|
||||
|
||||
PMONITOR->specialWorkspaceOpen = false;
|
||||
|
||||
if (workspaceToChangeTo != SPECIAL_WORKSPACE_ID)
|
||||
PMONITOR->activeWorkspace = workspaceToChangeTo;
|
||||
else
|
||||
PMONITOR->specialWorkspaceOpen = true;
|
||||
|
||||
// we need to move XWayland windows to narnia or otherwise they will still process our cursor and shit
|
||||
// and that'd be annoying as hell
|
||||
@@ -318,15 +342,23 @@ void CKeybindManager::moveActiveToWorkspace(std::string args) {
|
||||
const auto OLDWORKSPACE = g_pCompositor->getWorkspaceByID(PWINDOW->m_iWorkspaceID);
|
||||
|
||||
// hack
|
||||
std::string unusedName;
|
||||
const auto WORKSPACEID = getWorkspaceIDFromString(args, unusedName);
|
||||
|
||||
g_pKeybindManager->changeworkspace(args);
|
||||
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByString(args);
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(WORKSPACEID);
|
||||
|
||||
if (PWORKSPACE == OLDWORKSPACE) {
|
||||
Debug::log(LOG, "Not moving to workspace because it didn't change.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (!PWORKSPACE) {
|
||||
Debug::log(ERR, "Workspace null in moveActiveToWorkspace?");
|
||||
return;
|
||||
}
|
||||
|
||||
OLDWORKSPACE->m_bHasFullscreenWindow = false;
|
||||
|
||||
PWINDOW->m_iWorkspaceID = PWORKSPACE->m_iID;
|
||||
@@ -354,6 +386,17 @@ void CKeybindManager::moveActiveToWorkspace(std::string args) {
|
||||
PWINDOW->m_vRealPosition.setValue(PWINDOW->m_vRealPosition.vec() + g_pCompositor->getMonitorFromID(PWORKSPACE->m_iMonitorID)->vecPosition);
|
||||
PWINDOW->m_vPosition = PWINDOW->m_vRealPosition.vec();
|
||||
}
|
||||
|
||||
// undo the damage if we are moving to the special workspace
|
||||
if (WORKSPACEID == SPECIAL_WORKSPACE_ID) {
|
||||
changeworkspace(std::to_string(OLDWORKSPACE->m_iID));
|
||||
OLDWORKSPACE->startAnim(true, true, true);
|
||||
toggleSpecialWorkspace("");
|
||||
g_pCompositor->getWorkspaceByID(SPECIAL_WORKSPACE_ID)->startAnim(false, false, true);
|
||||
|
||||
for (auto& m : g_pCompositor->m_lMonitors)
|
||||
m.specialWorkspaceOpen = false;
|
||||
}
|
||||
}
|
||||
|
||||
void CKeybindManager::moveActiveToWorkspaceSilent(std::string args) {
|
||||
@@ -681,4 +724,101 @@ void CKeybindManager::workspaceOpt(std::string args) {
|
||||
void CKeybindManager::exitHyprland(std::string argz) {
|
||||
g_pCompositor->cleanupExit();
|
||||
exit(0);
|
||||
}
|
||||
|
||||
void CKeybindManager::moveCurrentWorkspaceToMonitor(std::string args) {
|
||||
if (!isNumber(args) && !isDirection(args)) {
|
||||
Debug::log(ERR, "moveCurrentWorkspaceToMonitor arg not a number or direction!");
|
||||
return;
|
||||
}
|
||||
|
||||
const auto PMONITOR = isDirection(args) ? g_pCompositor->getMonitorInDirection(args[0]) : g_pCompositor->getMonitorFromID(std::stoi(args));
|
||||
|
||||
if (!PMONITOR) {
|
||||
Debug::log(ERR, "Ignoring moveCurrentWorkspaceToMonitor: monitor doesnt exist");
|
||||
return;
|
||||
}
|
||||
|
||||
// get the current workspace
|
||||
const auto PCURRENTWORKSPACE = g_pCompositor->getWorkspaceByID(g_pCompositor->m_pLastMonitor->activeWorkspace);
|
||||
|
||||
if (!PCURRENTWORKSPACE)
|
||||
return;
|
||||
|
||||
g_pCompositor->moveWorkspaceToMonitor(PCURRENTWORKSPACE, PMONITOR);
|
||||
}
|
||||
|
||||
void CKeybindManager::moveWorkspaceToMonitor(std::string args) {
|
||||
|
||||
std::string workspace = args.substr(0, args.find_first_of(' '));
|
||||
std::string monitor = args.substr(args.find_first_of(' ') + 1);
|
||||
|
||||
if (!isNumber(monitor) && !isDirection(monitor)) {
|
||||
Debug::log(ERR, "moveWorkspaceToMonitor monitor arg not a number or direction!");
|
||||
return;
|
||||
}
|
||||
|
||||
const auto PMONITOR = isDirection(monitor) ? g_pCompositor->getMonitorInDirection(monitor[0]) : g_pCompositor->getMonitorFromID(std::stoi(monitor));
|
||||
|
||||
if (!PMONITOR){
|
||||
Debug::log(ERR, "Ignoring moveWorkspaceToMonitor: monitor doesnt exist");
|
||||
return;
|
||||
}
|
||||
|
||||
std::string workspaceName;
|
||||
const int WORKSPACEID = getWorkspaceIDFromString(workspace, workspaceName);
|
||||
|
||||
if (WORKSPACEID == INT_MAX) {
|
||||
Debug::log(ERR, "moveWorkspaceToMonitor invalid workspace!");
|
||||
return;
|
||||
}
|
||||
|
||||
const auto PWORKSPACE = g_pCompositor->getWorkspaceByID(WORKSPACEID);
|
||||
|
||||
if (!PWORKSPACE) {
|
||||
Debug::log(ERR, "moveWorkspaceToMonitor workspace doesn't exist!");
|
||||
return;
|
||||
}
|
||||
|
||||
g_pCompositor->moveWorkspaceToMonitor(PWORKSPACE, PMONITOR);
|
||||
}
|
||||
|
||||
void CKeybindManager::toggleSpecialWorkspace(std::string args) {
|
||||
|
||||
if (g_pCompositor->getWindowsOnWorkspace(SPECIAL_WORKSPACE_ID) == 0) {
|
||||
Debug::log(LOG, "Can't open empty special workspace!");
|
||||
return;
|
||||
}
|
||||
|
||||
bool open = false;
|
||||
|
||||
for (auto& m : g_pCompositor->m_lMonitors) {
|
||||
if (m.specialWorkspaceOpen) {
|
||||
open = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (open)
|
||||
Debug::log(LOG, "Toggling special workspace to closed");
|
||||
else
|
||||
Debug::log(LOG, "Toggling special workspace to open");
|
||||
|
||||
if (open) {
|
||||
for (auto& m : g_pCompositor->m_lMonitors) {
|
||||
if (m.specialWorkspaceOpen != !open) {
|
||||
m.specialWorkspaceOpen = !open;
|
||||
g_pLayoutManager->getCurrentLayout()->recalculateMonitor(m.ID);
|
||||
|
||||
g_pCompositor->getWorkspaceByID(SPECIAL_WORKSPACE_ID)->startAnim(false, false);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
g_pCompositor->m_pLastMonitor->specialWorkspaceOpen = true;
|
||||
g_pLayoutManager->getCurrentLayout()->recalculateMonitor(g_pCompositor->m_pLastMonitor->ID);
|
||||
|
||||
g_pCompositor->getWorkspaceByID(SPECIAL_WORKSPACE_ID)->startAnim(true, true);
|
||||
}
|
||||
|
||||
g_pInputManager->refocus();
|
||||
}
|
@@ -51,6 +51,11 @@ private:
|
||||
static void moveCursorToCorner(std::string);
|
||||
static void workspaceOpt(std::string);
|
||||
static void exitHyprland(std::string);
|
||||
static void moveCurrentWorkspaceToMonitor(std::string);
|
||||
static void moveWorkspaceToMonitor(std::string);
|
||||
static void toggleSpecialWorkspace(std::string);
|
||||
|
||||
friend class CCompositor;
|
||||
};
|
||||
|
||||
inline std::unique_ptr<CKeybindManager> g_pKeybindManager;
|
@@ -32,7 +32,7 @@ void renderSurface(struct wlr_surface* surface, int x, int y, void* data) {
|
||||
}
|
||||
|
||||
bool shouldRenderWindow(CWindow* pWindow, SMonitor* pMonitor) {
|
||||
wlr_box geometry = {pWindow->m_vRealPosition.vec().x, pWindow->m_vRealPosition.vec().y, pWindow->m_vRealSize.vec().x, pWindow->m_vRealSize.vec().y};
|
||||
wlr_box geometry = pWindow->getFullWindowBoundingBox();
|
||||
|
||||
if (!wlr_output_layout_intersects(g_pCompositor->m_sWLROutputLayout, pMonitor->output, &geometry))
|
||||
return false;
|
||||
@@ -46,6 +46,9 @@ bool shouldRenderWindow(CWindow* pWindow, SMonitor* pMonitor) {
|
||||
if (g_pCompositor->isWorkspaceVisible(pWindow->m_iWorkspaceID) || (PWORKSPACE && PWORKSPACE->m_iMonitorID == pMonitor->ID && (PWORKSPACE->m_vRenderOffset.isBeingAnimated() || PWORKSPACE->m_fAlpha.isBeingAnimated())))
|
||||
return true;
|
||||
|
||||
if (pMonitor->specialWorkspaceOpen && pWindow->m_iWorkspaceID == SPECIAL_WORKSPACE_ID)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -70,6 +73,21 @@ void CHyprRenderer::renderWorkspaceWithFullscreenWindow(SMonitor* pMonitor, CWor
|
||||
renderWindow(&w, pMonitor, time, true);
|
||||
}
|
||||
|
||||
// and then special windows
|
||||
for (auto& w : g_pCompositor->m_lWindows) {
|
||||
if (!g_pCompositor->windowValidMapped(&w) && !w.m_bFadingOut)
|
||||
continue;
|
||||
|
||||
if (w.m_iWorkspaceID != SPECIAL_WORKSPACE_ID)
|
||||
continue;
|
||||
|
||||
if (!shouldRenderWindow(&w, pMonitor))
|
||||
continue;
|
||||
|
||||
// render the bad boy
|
||||
renderWindow(&w, pMonitor, time, true);
|
||||
}
|
||||
|
||||
// and the overlay layers
|
||||
if (pWorkspace->m_efFullscreenMode != FULLSCREEN_FULL) {
|
||||
// on non-full we draw the bar and shit
|
||||
@@ -112,7 +130,10 @@ void CHyprRenderer::renderWindow(CWindow* pWindow, SMonitor* pMonitor, timespec*
|
||||
renderdata.rounding = pWindow->m_sAdditionalConfigData.rounding;
|
||||
|
||||
// apply window special data
|
||||
renderdata.alpha *= pWindow->m_sSpecialRenderData.alpha;
|
||||
if (pWindow->m_sSpecialRenderData.alphaInactive == -1)
|
||||
renderdata.alpha *= pWindow->m_sSpecialRenderData.alpha;
|
||||
else
|
||||
renderdata.alpha *= pWindow == g_pCompositor->m_pLastWindow ? pWindow->m_sSpecialRenderData.alpha : pWindow->m_sSpecialRenderData.alphaInactive;
|
||||
|
||||
g_pHyprOpenGL->m_pCurrentWindow = pWindow;
|
||||
|
||||
@@ -176,7 +197,10 @@ void CHyprRenderer::renderAllClientsForMonitor(const int& ID, timespec* time) {
|
||||
continue;
|
||||
|
||||
if (w.m_bIsFloating)
|
||||
continue; // floating are in second pass
|
||||
continue; // floating are in the second pass
|
||||
|
||||
if (w.m_iWorkspaceID == SPECIAL_WORKSPACE_ID)
|
||||
continue; // special are in the third pass
|
||||
|
||||
if (!shouldRenderWindow(&w, PMONITOR))
|
||||
continue;
|
||||
@@ -193,6 +217,24 @@ void CHyprRenderer::renderAllClientsForMonitor(const int& ID, timespec* time) {
|
||||
if (!w.m_bIsFloating)
|
||||
continue;
|
||||
|
||||
if (w.m_iWorkspaceID == SPECIAL_WORKSPACE_ID)
|
||||
continue;
|
||||
|
||||
if (!shouldRenderWindow(&w, PMONITOR))
|
||||
continue;
|
||||
|
||||
// render the bad boy
|
||||
renderWindow(&w, PMONITOR, time, true);
|
||||
}
|
||||
|
||||
// and then special
|
||||
for (auto& w : g_pCompositor->m_lWindows) {
|
||||
if (!g_pCompositor->windowValidMapped(&w) && !w.m_bFadingOut)
|
||||
continue;
|
||||
|
||||
if (w.m_iWorkspaceID != SPECIAL_WORKSPACE_ID)
|
||||
continue;
|
||||
|
||||
if (!shouldRenderWindow(&w, PMONITOR))
|
||||
continue;
|
||||
|
||||
|
1
wlroots
Submodule
1
wlroots
Submodule
Submodule wlroots added at 75d31509db
Reference in New Issue
Block a user