core: avoid having the toplevel mgr bound all the time

This commit is contained in:
Vaxry 2023-12-25 15:05:30 +01:00
parent f5c3576c3b
commit 24141c05c2
4 changed files with 57 additions and 11 deletions

View File

@ -235,8 +235,7 @@ void CPortalManager::onGlobal(void* data, struct wl_registry* registry, uint32_t
m_sWaylandConnection.shm = (wl_shm*)wl_registry_bind(registry, name, &wl_shm_interface, version);
else if (INTERFACE == zwlr_foreign_toplevel_manager_v1_interface.name)
m_sHelpers.toplevel =
std::make_unique<CToplevelManager>((zwlr_foreign_toplevel_manager_v1*)wl_registry_bind(registry, name, &zwlr_foreign_toplevel_manager_v1_interface, version));
m_sHelpers.toplevel = std::make_unique<CToplevelManager>(registry, name, version);
}
void CPortalManager::onGlobalRemoved(void* data, struct wl_registry* registry, uint32_t name) {

View File

@ -285,6 +285,8 @@ static const hyprland_toplevel_export_frame_v1_listener hyprlandFrameListener =
void CScreencopyPortal::onCreateSession(sdbus::MethodCall& call) {
sdbus::ObjectPath requestHandle, sessionHandle;
g_pPortalManager->m_sHelpers.toplevel->activate();
call >> requestHandle;
call >> sessionHandle;
@ -307,6 +309,9 @@ void CScreencopyPortal::onCreateSession(sdbus::MethodCall& call) {
}
PSESSION->session.release();
Debug::log(LOG, "[screencopy] Session destroyed");
// deactivate toplevel so it doesn't listen and waste battery
g_pPortalManager->m_sHelpers.toplevel->deactivate();
};
PSESSION->request = createDBusRequest(requestHandle);
PSESSION->request->onDestroy = [PSESSION]() { PSESSION->request.release(); };
@ -1085,7 +1090,7 @@ uint32_t CPipewireConnection::buildFormatsFor(spa_pod_builder* b[2], const spa_p
paramCount = 2;
params[0] = build_format(b[0], pwFromDrmFourcc(stream->pSession->sharingData.frameInfoDMA.fmt), stream->pSession->sharingData.frameInfoDMA.w,
stream->pSession->sharingData.frameInfoDMA.h, stream->pSession->sharingData.framerate, modifiers, modCount);
stream->pSession->sharingData.frameInfoDMA.h, stream->pSession->sharingData.framerate, modifiers, modCount);
assert(params[0] != NULL);
params[1] = build_format(b[1], pwFromDrmFourcc(stream->pSession->sharingData.frameInfoSHM.fmt), stream->pSession->sharingData.frameInfoSHM.w,
stream->pSession->sharingData.frameInfoSHM.h, stream->pSession->sharingData.framerate, NULL, 0);
@ -1095,7 +1100,7 @@ uint32_t CPipewireConnection::buildFormatsFor(spa_pod_builder* b[2], const spa_p
paramCount = 1;
params[0] = build_format(b[0], pwFromDrmFourcc(stream->pSession->sharingData.frameInfoSHM.fmt), stream->pSession->sharingData.frameInfoSHM.w,
stream->pSession->sharingData.frameInfoSHM.h, stream->pSession->sharingData.framerate, NULL, 0);
stream->pSession->sharingData.frameInfoSHM.h, stream->pSession->sharingData.framerate, NULL, 0);
}
if (modifiers)

View File

@ -1,5 +1,6 @@
#include "ToplevelManager.hpp"
#include "../helpers/Log.hpp"
#include "../core/PortalManager.hpp"
static void toplevelTitle(void* data, zwlr_foreign_toplevel_handle_v1* zwlr_foreign_toplevel_handle_v1, const char* title) {
const auto PTL = (SToplevelHandle*)data;
@ -81,11 +82,6 @@ inline const zwlr_foreign_toplevel_manager_v1_listener managerListener = {
.finished = managerFinished,
};
CToplevelManager::CToplevelManager(zwlr_foreign_toplevel_manager_v1* mgr) {
m_pManager = mgr;
zwlr_foreign_toplevel_manager_v1_add_listener(mgr, &managerListener, this);
}
bool CToplevelManager::exists(zwlr_foreign_toplevel_handle_v1* handle) {
for (auto& h : m_vToplevels) {
if (h->handle == handle)
@ -93,4 +89,39 @@ bool CToplevelManager::exists(zwlr_foreign_toplevel_handle_v1* handle) {
}
return false;
}
CToplevelManager::CToplevelManager(wl_registry* registry, uint32_t name, uint32_t version) {
m_sWaylandConnection = {registry, name, version};
}
void CToplevelManager::activate() {
m_iActivateLocks++;
Debug::log(LOG, "[toplevel] (activate) locks: {}", m_iActivateLocks);
if (m_pManager || m_iActivateLocks < 1)
return;
m_pManager = (zwlr_foreign_toplevel_manager_v1*)wl_registry_bind(m_sWaylandConnection.registry, m_sWaylandConnection.name, &zwlr_foreign_toplevel_manager_v1_interface,
m_sWaylandConnection.version);
zwlr_foreign_toplevel_manager_v1_add_listener(m_pManager, &managerListener, this);
wl_display_roundtrip(g_pPortalManager->m_sWaylandConnection.display);
Debug::log(LOG, "[toplevel] Activated, bound to {:x}, toplevels: {}", (uintptr_t)m_pManager, m_vToplevels.size());
}
void CToplevelManager::deactivate() {
m_iActivateLocks--;
Debug::log(LOG, "[toplevel] (deactivate) locks: {}", m_iActivateLocks);
if (!m_pManager || m_iActivateLocks > 0)
return;
zwlr_foreign_toplevel_manager_v1_destroy(m_pManager);
m_pManager = nullptr;
m_vToplevels.clear();
Debug::log(LOG, "[toplevel] unbound manager");
}

View File

@ -17,12 +17,23 @@ struct SToplevelHandle {
class CToplevelManager {
public:
CToplevelManager(zwlr_foreign_toplevel_manager_v1* mgr);
CToplevelManager(wl_registry* registry, uint32_t name, uint32_t version);
void activate();
void deactivate();
bool exists(zwlr_foreign_toplevel_handle_v1* handle);
std::vector<std::unique_ptr<SToplevelHandle>> m_vToplevels;
private:
zwlr_foreign_toplevel_manager_v1* m_pManager;
zwlr_foreign_toplevel_manager_v1* m_pManager = nullptr;
int64_t m_iActivateLocks = 0;
struct {
wl_registry* registry = nullptr;
uint32_t name = 0;
uint32_t version = 0;
} m_sWaylandConnection;
};