added workspaces

This commit is contained in:
vaxerski 2022-03-20 15:55:47 +01:00
parent 45addfb31d
commit 50370e4216
10 changed files with 136 additions and 12 deletions

View file

@ -203,10 +203,10 @@ bool CCompositor::windowExists(CWindow* pWindow) {
}
CWindow* CCompositor::vectorToWindow(const Vector2D& pos) {
const auto PMONITOR = getMonitorFromCursor();
const auto PMONITOR = getMonitorFromVector(pos);
for (auto& w : m_lWindows) {
wlr_box box = {w.m_vRealPosition.x, w.m_vRealPosition.y, w.m_vRealSize.x, w.m_vRealSize.y};
if (wlr_box_contains_point(&box, pos.x, pos.y)) // TODO: workspaces
if (wlr_box_contains_point(&box, pos.x, pos.y) && w.m_iWorkspaceID == PMONITOR->activeWorkspace)
return &w;
}
@ -214,18 +214,18 @@ CWindow* CCompositor::vectorToWindow(const Vector2D& pos) {
}
CWindow* CCompositor::vectorToWindowIdeal(const Vector2D& pos) {
const auto PMONITOR = getMonitorFromCursor();
const auto PMONITOR = getMonitorFromVector(pos);
// first loop over floating cuz they're above
// TODO: make an actual Z-system
for (auto& w : m_lWindows) {
wlr_box box = {w.m_vRealPosition.x, w.m_vRealPosition.y, w.m_vRealSize.x, w.m_vRealSize.y};
if (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_bIsFloating) // TODO: workspaces
if (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_bIsFloating && w.m_iWorkspaceID == PMONITOR->activeWorkspace)
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 (wlr_box_contains_point(&box, pos.x, pos.y)) // TODO: workspaces
if (wlr_box_contains_point(&box, pos.x, pos.y) && w.m_iWorkspaceID == PMONITOR->activeWorkspace)
return &w;
}
@ -239,13 +239,13 @@ CWindow* CCompositor::windowFromCursor() {
// TODO: make an actual Z-system
for (auto& w : m_lWindows) {
wlr_box box = {w.m_vRealPosition.x, w.m_vRealPosition.y, w.m_vRealSize.x, w.m_vRealSize.y};
if (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_bIsFloating) // TODO: workspaces
if (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_bIsFloating && w.m_iWorkspaceID == PMONITOR->activeWorkspace)
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 (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y)) // TODO: workspaces
if (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_iWorkspaceID == PMONITOR->activeWorkspace)
return &w;
}
@ -256,7 +256,7 @@ CWindow* CCompositor::windowFloatingFromCursor() {
const auto PMONITOR = getMonitorFromCursor();
for (auto& w : m_lWindows) {
wlr_box box = {w.m_vRealPosition.x, w.m_vRealPosition.y, w.m_vRealSize.x, w.m_vRealSize.y};
if (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_bIsFloating) // TODO: workspaces
if (wlr_box_contains_point(&box, m_sWLRCursor->x, m_sWLRCursor->y) && w.m_bIsFloating && w.m_iWorkspaceID == PMONITOR->activeWorkspace)
return &w;
}
@ -359,5 +359,49 @@ CWindow* CCompositor::getWindowFromSurface(wlr_surface* pSurface) {
return &w;
}
return nullptr;
}
bool CCompositor::isWorkspaceVisible(const int& w) {
for (auto& m : m_lMonitors) {
if (m.activeWorkspace == w)
return true;
}
return false;
}
SWorkspace* CCompositor::getWorkspaceByID(const int& id) {
for (auto& w : m_lWorkspaces) {
if (w.ID == id)
return &w;
}
return nullptr;
}
void CCompositor::sanityCheckWorkspaces() {
for (auto it = m_lWorkspaces.begin(); it != m_lWorkspaces.end(); ++it) {
if (getWindowsOnWorkspace(it->ID) == 0 && !isWorkspaceVisible(it->ID))
it = m_lWorkspaces.erase(it);
}
}
int CCompositor::getWindowsOnWorkspace(const int& id) {
int no = 0;
for (auto& w : m_lWindows) {
if (w.m_iWorkspaceID == id)
no++;
}
return no;
}
CWindow* CCompositor::getFirstWindowOnWorkspace(const int& id) {
for (auto& w : m_lWindows) {
if (w.m_iWorkspaceID == id)
return &w;
}
return nullptr;
}

View file

@ -14,8 +14,10 @@
#include "managers/LayoutManager.hpp"
#include "managers/KeybindManager.hpp"
#include "helpers/Monitor.hpp"
#include "helpers/Workspace.hpp"
#include "Window.hpp"
#include "render/Renderer.hpp"
class CCompositor {
public:
CCompositor();
@ -50,6 +52,7 @@ public:
std::list<CWindow> m_lWindows;
std::list<SLayerPopup> m_lLayerPopups;
std::list<SXDGPopup> m_lXDGPopups;
std::list<SWorkspace> m_lWorkspaces;
void startCompositor();
@ -75,6 +78,11 @@ public:
SLayerSurface* getLayerForPopup(SLayerPopup*);
CWindow* getWindowForPopup(wlr_xdg_popup*);
CWindow* getWindowFromSurface(wlr_surface*);
bool isWorkspaceVisible(const int&);
SWorkspace* getWorkspaceByID(const int&);
void sanityCheckWorkspaces();
int getWindowsOnWorkspace(const int&);
CWindow* getFirstWindowOnWorkspace(const int&);
private:
void initAllSignals();

View file

@ -39,6 +39,7 @@ public:
bool m_bIsFullscreen = false;
uint64_t m_iMonitorID = -1;
std::string m_szTitle = "";
int m_iWorkspaceID = -1;
// XWayland stuff
bool m_bIsX11 = false;

View file

@ -67,6 +67,16 @@ void Events::listener_newOutput(wl_listener* listener, void* data) {
newMonitor.vecPosition = monitorRule.offset;
newMonitor.vecSize = monitorRule.resolution;
newMonitor.refreshRate = monitorRule.refreshRate;
// Workspace
g_pCompositor->m_lWorkspaces.push_back(SWorkspace());
const auto PNEWWORKSPACE = &g_pCompositor->m_lWorkspaces.back();
PNEWWORKSPACE->ID = g_pCompositor->m_lWorkspaces.size();
PNEWWORKSPACE->monitorID = newMonitor.ID;
newMonitor.activeWorkspace = PNEWWORKSPACE->ID;
g_pCompositor->m_lMonitors.push_back(newMonitor);
//
@ -106,6 +116,13 @@ void Events::listener_monitorFrame(wl_listener* listener, void* data) {
wlr_renderer_end(g_pCompositor->m_sWLRRenderer);
wlr_output_commit(PMONITOR->output);
// Sanity check the workspaces.
// Hack: only check when monitor number 1 refreshes, saves a bit of resources.
if (PMONITOR->ID == 0) {
g_pCompositor->sanityCheckWorkspaces();
}
}
void Events::listener_monitorDestroy(wl_listener* listener, void* data) {
@ -485,6 +502,7 @@ void Events::listener_mapWindow(wl_listener* listener, void* data) {
const auto PMONITOR = g_pCompositor->getMonitorFromCursor();
PWINDOW->m_iMonitorID = PMONITOR->ID;
PWINDOW->m_bMappedX11 = true;
PWINDOW->m_iWorkspaceID = PMONITOR->activeWorkspace;
if (g_pXWaylandManager->shouldBeFloated(PWINDOW))
g_pLayoutManager->getCurrentLayout()->onWindowCreatedFloating(PWINDOW);

View file

@ -13,6 +13,7 @@ struct SMonitor {
bool primary = false;
uint64_t ID = -1;
int activeWorkspace = -1;
std::string szName = "";

View file

@ -0,0 +1,9 @@
#pragma once
#include "../defines.hpp"
struct SWorkspace {
int ID = -1;
uint64_t monitorID = -1;
bool hasFullscreenWindow = false;
};

View file

@ -301,8 +301,10 @@ void CHyprDwindleLayout::onMouseMove(const Vector2D& mousePos) {
// and check its monitor
const auto PMONITOR = g_pCompositor->getMonitorFromVector(middle);
if (PMONITOR)
if (PMONITOR) {
DRAGGINGWINDOW->m_iMonitorID = PMONITOR->ID;
DRAGGINGWINDOW->m_iWorkspaceID = PMONITOR->activeWorkspace;
}
}
void CHyprDwindleLayout::onWindowCreatedFloating(CWindow* pWindow) {

View file

@ -43,6 +43,7 @@ bool CKeybindManager::handleKeybinds(const uint32_t& modmask, const xkb_keysym_t
if (k.handler == "exec") { spawn(k.arg); }
else if (k.handler == "killactive") { killActive(k.arg); }
else if (k.handler == "togglefloating") { toggleActiveFloating(k.arg); }
else if (k.handler == "workspace") { changeworkspace(k.arg); }
found = true;
}
@ -84,4 +85,44 @@ void CKeybindManager::toggleActiveFloating(std::string args) {
g_pLayoutManager->getCurrentLayout()->changeWindowFloatingMode(ACTIVEWINDOW);
}
}
void CKeybindManager::changeworkspace(std::string args) {
int workspaceToChangeTo = 0;
try {
workspaceToChangeTo = stoi(args);
} catch (...) {
Debug::log(ERR, "Invalid arg \"%s\" in changeWorkspace!", args.c_str());
}
// if it exists, we warp to it
if (g_pCompositor->getWorkspaceByID(workspaceToChangeTo)) {
const auto PMONITOR = g_pCompositor->getMonitorFromID(g_pCompositor->getWorkspaceByID(workspaceToChangeTo)->monitorID);
// if it's not visible, make it visible.
if (!g_pCompositor->isWorkspaceVisible(workspaceToChangeTo))
PMONITOR->activeWorkspace = workspaceToChangeTo;
// If the monitor is not the one our cursor's at, warp to it.
if (PMONITOR != g_pCompositor->getMonitorFromCursor()) {
Vector2D middle = PMONITOR->vecPosition + PMONITOR->vecSize / 2.f;
wlr_cursor_warp(g_pCompositor->m_sWLRCursor, nullptr, middle.x, middle.y);
}
// focus the first window
g_pCompositor->focusWindow(g_pCompositor->getFirstWindowOnWorkspace(workspaceToChangeTo));
return;
}
// Workspace doesn't exist, create and switch
const auto PMONITOR = g_pCompositor->getMonitorFromCursor();
g_pCompositor->m_lWorkspaces.push_back(SWorkspace());
const auto PWORKSPACE = &g_pCompositor->m_lWorkspaces.back();
PWORKSPACE->ID = workspaceToChangeTo;
PWORKSPACE->monitorID = PMONITOR->ID;
PMONITOR->activeWorkspace = workspaceToChangeTo;
}

View file

@ -26,7 +26,7 @@ private:
void killActive(std::string);
void spawn(std::string);
void toggleActiveFloating(std::string);
void changeworkspace(std::string);
};
inline std::unique_ptr<CKeybindManager> g_pKeybindManager;

View file

@ -50,7 +50,7 @@ void CHyprRenderer::renderAllClientsForMonitor(const int& ID, timespec* time) {
for (auto& w : g_pCompositor->m_lWindows) {
if (w.m_bIsX11)
if (w.m_bIsX11 || w.m_iWorkspaceID != PMONITOR->activeWorkspace)
continue;
wlr_box geometry = { w.m_vRealPosition.x, w.m_vRealPosition.y, w.m_vRealSize.x, w.m_vRealSize.y };
@ -71,7 +71,7 @@ void CHyprRenderer::renderAllClientsForMonitor(const int& ID, timespec* time) {
for (auto& w : g_pCompositor->m_lWindows) {
if (!w.m_bIsX11)
if (!w.m_bIsX11 || w.m_iWorkspaceID != PMONITOR->activeWorkspace)
continue;
if (!g_pCompositor->windowValidMapped(&w))