internal: new shared_ptr and weak_ptr implementation (#5883)

moves std::shared_ptrs to a new implementation

Advantages:
- you can dereference a weak_ptr directly. This will obviously segfault on a nullptr deref if it's expired.
   - this is useful to avoid the .lock() hell where we are 100% sure the pointer _should_ be valid. (and if it isn't, it should throw.)
- weak_ptrs are still valid while the SP is being destroyed.
   - reasoning: while an object (e.g. CWindow) is being destroyed, its `weak_ptr self` should be accessible (the sp is still alive, and so is CWindow), but it's not because by stl it's already expired (to prevent resurrection)
   - this impl solves it differently. w_p is expired, but can still be dereferenced and used. Creating `s_p`s is not possible anymore, though.
   - this is useful in destructors and callbacks.
This commit is contained in:
Vaxry 2024-05-05 17:16:00 +01:00 committed by GitHub
parent 589f758d94
commit 1ed1ce9506
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
88 changed files with 899 additions and 414 deletions

View file

@ -5,11 +5,11 @@
void CInputManager::newIdleInhibitor(std::any inhibitor) {
const auto PINHIBIT = m_vIdleInhibitors.emplace_back(std::make_unique<SIdleInhibitor>()).get();
PINHIBIT->inhibitor = std::any_cast<std::shared_ptr<CIdleInhibitor>>(inhibitor);
PINHIBIT->inhibitor = std::any_cast<SP<CIdleInhibitor>>(inhibitor);
Debug::log(LOG, "New idle inhibitor registered for surface {:x}", (uintptr_t)PINHIBIT->inhibitor->surface);
PINHIBIT->inhibitor->listeners.destroy = PINHIBIT->inhibitor->resource.lock()->events.destroy.registerListener([this, PINHIBIT](std::any data) {
PINHIBIT->inhibitor->listeners.destroy = PINHIBIT->inhibitor->resource->events.destroy.registerListener([this, PINHIBIT](std::any data) {
std::erase_if(m_vIdleInhibitors, [PINHIBIT](const auto& other) { return other.get() == PINHIBIT; });
recheckIdleInhibitorStatus();
});

View file

@ -250,7 +250,7 @@ void CInputManager::mouseMoveUnified(uint32_t time, bool refocus) {
if (!PSLS)
return;
foundSurface = PSLS->surface.lock()->surface();
foundSurface = PSLS->surface->surface();
surfacePos = PMONITOR->vecPosition;
}
@ -408,7 +408,7 @@ void CInputManager::mouseMoveUnified(uint32_t time, bool refocus) {
m_pFoundSurfaceToFocus = foundSurface;
}
if (currentlyDraggedWindow.lock() && pFoundWindow != currentlyDraggedWindow.lock()) {
if (currentlyDraggedWindow.lock() && pFoundWindow != currentlyDraggedWindow) {
wlr_seat_pointer_notify_enter(g_pCompositor->m_sSeat.seat, foundSurface, surfaceLocal.x, surfaceLocal.y);
wlr_seat_pointer_notify_motion(g_pCompositor->m_sSeat.seat, time, surfaceLocal.x, surfaceLocal.y);
return;
@ -434,8 +434,7 @@ void CInputManager::mouseMoveUnified(uint32_t time, bool refocus) {
if (FOLLOWMOUSE != 1 && !refocus) {
if (pFoundWindow != g_pCompositor->m_pLastWindow.lock() && g_pCompositor->m_pLastWindow.lock() &&
((pFoundWindow->m_bIsFloating && *PFLOATBEHAVIOR == 2) ||
(g_pCompositor->m_pLastWindow.lock()->m_bIsFloating != pFoundWindow->m_bIsFloating && *PFLOATBEHAVIOR != 0))) {
((pFoundWindow->m_bIsFloating && *PFLOATBEHAVIOR == 2) || (g_pCompositor->m_pLastWindow->m_bIsFloating != pFoundWindow->m_bIsFloating && *PFLOATBEHAVIOR != 0))) {
// enter if change floating style
if (FOLLOWMOUSE != 3 && allowKeyboardRefocus)
g_pCompositor->focusWindow(pFoundWindow, foundSurface);
@ -446,12 +445,12 @@ void CInputManager::mouseMoveUnified(uint32_t time, bool refocus) {
wlr_seat_pointer_notify_enter(g_pCompositor->m_sSeat.seat, foundSurface, surfaceLocal.x, surfaceLocal.y);
}
if (pFoundWindow == g_pCompositor->m_pLastWindow.lock()) {
if (pFoundWindow == g_pCompositor->m_pLastWindow) {
m_pLastMouseSurface = foundSurface;
wlr_seat_pointer_notify_enter(g_pCompositor->m_sSeat.seat, foundSurface, surfaceLocal.x, surfaceLocal.y);
}
if (FOLLOWMOUSE != 0 || pFoundWindow == g_pCompositor->m_pLastWindow.lock())
if (FOLLOWMOUSE != 0 || pFoundWindow == g_pCompositor->m_pLastWindow)
wlr_seat_pointer_notify_motion(g_pCompositor->m_sSeat.seat, time, surfaceLocal.x, surfaceLocal.y);
m_bLastFocusOnLS = false;
@ -671,7 +670,7 @@ void CInputManager::processMouseDownNormal(wlr_pointer_button_event* e) {
}
// if clicked on a floating window make it top
if (g_pCompositor->m_pLastWindow.lock() && g_pCompositor->m_pLastWindow.lock()->m_bIsFloating)
if (g_pCompositor->m_pLastWindow.lock() && g_pCompositor->m_pLastWindow->m_bIsFloating)
g_pCompositor->changeWindowZOrder(g_pCompositor->m_pLastWindow.lock(), true);
break;
@ -1172,9 +1171,9 @@ void CInputManager::destroyKeyboard(SP<IKeyboard> pKeyboard) {
std::erase_if(m_vKeyboards, [pKeyboard](const auto& other) { return other == pKeyboard; });
if (m_vKeyboards.size() > 0) {
g_pCompositor->m_sSeat.keyboard = m_vKeyboards.back();
g_pCompositor->m_sSeat.keyboard.lock()->active = true;
wlr_seat_set_keyboard(g_pCompositor->m_sSeat.seat, g_pCompositor->m_sSeat.keyboard.lock()->wlr());
g_pCompositor->m_sSeat.keyboard = m_vKeyboards.back();
g_pCompositor->m_sSeat.keyboard->active = true;
wlr_seat_set_keyboard(g_pCompositor->m_sSeat.seat, g_pCompositor->m_sSeat.keyboard->wlr());
} else {
g_pCompositor->m_sSeat.keyboard.reset();
wlr_seat_set_keyboard(g_pCompositor->m_sSeat.seat, nullptr);
@ -1278,7 +1277,7 @@ bool CInputManager::shouldIgnoreVirtualKeyboard(SP<IKeyboard> pKeyboard) {
CVirtualKeyboard* vk = (CVirtualKeyboard*)pKeyboard.get();
return !pKeyboard || (!m_sIMERelay.m_pIME.expired() && m_sIMERelay.m_pIME.lock()->grabClient() == vk->getClient());
return !pKeyboard || (!m_sIMERelay.m_pIME.expired() && m_sIMERelay.m_pIME->grabClient() == vk->getClient());
}
void CInputManager::refocus() {

View file

@ -144,7 +144,7 @@ class CInputManager {
std::deque<PHLLSREF> m_dExclusiveLSes;
// constraints
std::vector<std::weak_ptr<CPointerConstraint>> m_vConstraints;
std::vector<WP<CPointerConstraint>> m_vConstraints;
//
void newTabletTool(wlr_input_device*);
@ -241,9 +241,9 @@ class CInputManager {
// idle inhibitors
struct SIdleInhibitor {
std::shared_ptr<CIdleInhibitor> inhibitor;
bool nonDesktop = false;
CHyprSignalListener surfaceDestroyListener;
SP<CIdleInhibitor> inhibitor;
bool nonDesktop = false;
CHyprSignalListener surfaceDestroyListener;
};
std::vector<std::unique_ptr<SIdleInhibitor>> m_vIdleInhibitors;

View file

@ -73,7 +73,7 @@ void CInputPopup::damageSurface() {
}
void CInputPopup::updateBox() {
if (!popup.lock()->mapped)
if (!popup->mapped)
return;
const auto OWNER = queryOwner();
@ -114,7 +114,7 @@ void CInputPopup::updateBox() {
popupOffset.x -= popupOverflow;
CBox cursorBoxLocal({-popupOffset.x, -popupOffset.y}, cursorBoxParent.size());
popup.lock()->sendInputRectangle(cursorBoxLocal);
popup->sendInputRectangle(cursorBoxLocal);
CBox popupBoxParent(cursorBoxParent.pos() + popupOffset, currentPopupSize);
if (popupBoxParent != lastBoxLocal) {

View file

@ -85,7 +85,7 @@ CTextInput* CInputMethodRelay::getFocusedTextInput() {
}
void CInputMethodRelay::onNewTextInput(std::any tiv3) {
m_vTextInputs.emplace_back(std::make_unique<CTextInput>(std::any_cast<std::weak_ptr<CTextInputV3>>(tiv3)));
m_vTextInputs.emplace_back(std::make_unique<CTextInput>(std::any_cast<WP<CTextInputV3>>(tiv3)));
}
void CInputMethodRelay::onNewTextInput(STextInputV1* pTIV1) {
@ -106,7 +106,7 @@ void CInputMethodRelay::activateIME(CTextInput* pInput) {
if (m_pIME.expired())
return;
m_pIME.lock()->activate();
m_pIME->activate();
commitIMEState(pInput);
}
@ -114,7 +114,7 @@ void CInputMethodRelay::deactivateIME(CTextInput* pInput) {
if (m_pIME.expired())
return;
m_pIME.lock()->deactivate();
m_pIME->deactivate();
commitIMEState(pInput);
}

View file

@ -11,7 +11,7 @@ CTextInput::CTextInput(STextInputV1* ti) : pV1Input(ti) {
initCallbacks();
}
CTextInput::CTextInput(std::weak_ptr<CTextInputV3> ti) : pV3Input(ti) {
CTextInput::CTextInput(WP<CTextInputV3> ti) : pV3Input(ti) {
initCallbacks();
}
@ -109,7 +109,7 @@ void CTextInput::onCommit() {
return;
}
if (!(isV3() ? pV3Input.lock()->current.enabled : pV1Input->active)) {
if (!(isV3() ? pV3Input->current.enabled : pV1Input->active)) {
Debug::log(WARN, "Disabled TextInput commit?");
return;
}
@ -180,7 +180,7 @@ void CTextInput::enter(wlr_surface* pSurface) {
}
if (isV3())
pV3Input.lock()->enter(pSurface);
pV3Input->enter(pSurface);
else {
zwp_text_input_v1_send_enter(pV1Input->resourceImpl, pSurface->resource);
pV1Input->active = true;
@ -200,7 +200,7 @@ void CTextInput::leave() {
}
if (isV3() && focusedSurface())
pV3Input.lock()->leave(focusedSurface());
pV3Input->leave(focusedSurface());
else if (focusedSurface() && pV1Input) {
zwp_text_input_v1_send_leave(pV1Input->resourceImpl);
pV1Input->active = false;
@ -216,7 +216,7 @@ wlr_surface* CTextInput::focusedSurface() {
}
wl_client* CTextInput::client() {
return isV3() ? pV3Input.lock()->client() : pV1Input->client;
return isV3() ? pV3Input->client() : pV1Input->client;
}
void CTextInput::commitStateToIME(SP<CInputMethodV2> ime) {
@ -284,9 +284,9 @@ void CTextInput::updateIMEState(SP<CInputMethodV2> ime) {
}
bool CTextInput::hasCursorRectangle() {
return !isV3() || pV3Input.lock()->current.box.updated;
return !isV3() || pV3Input->current.box.updated;
}
CBox CTextInput::cursorBox() {
return CBox{isV3() ? pV3Input.lock()->current.box.cursorBox : pV1Input->cursorRectangle};
return CBox{isV3() ? pV3Input->current.box.cursorBox : pV1Input->cursorRectangle};
}

View file

@ -15,7 +15,7 @@ class CInputMethodV2;
class CTextInput {
public:
CTextInput(std::weak_ptr<CTextInputV3> ti);
CTextInput(WP<CTextInputV3> ti);
CTextInput(STextInputV1* ti);
~CTextInput();
@ -37,13 +37,13 @@ class CTextInput {
wlr_surface* focusedSurface();
private:
void setFocusedSurface(wlr_surface* pSurface);
void initCallbacks();
void setFocusedSurface(wlr_surface* pSurface);
void initCallbacks();
wlr_surface* pFocusedSurface = nullptr;
int enterLocks = 0;
std::weak_ptr<CTextInputV3> pV3Input;
STextInputV1* pV1Input = nullptr;
wlr_surface* pFocusedSurface = nullptr;
int enterLocks = 0;
WP<CTextInputV3> pV3Input;
STextInputV1* pV1Input = nullptr;
DYNLISTENER(textInputEnable);
DYNLISTENER(textInputDisable);

View file

@ -38,7 +38,7 @@ void CInputManager::onTouchDown(wlr_touch_down_event* e) {
if (m_sActiveSwipe.pWorkspaceBegin) {
return;
// TODO: Don't swipe if you touched a floating window.
} else if (*PSWIPETOUCH && (m_pFoundLSToFocus.expired() || m_pFoundLSToFocus.lock()->layer <= ZWLR_LAYER_SHELL_V1_LAYER_BOTTOM)) {
} else if (*PSWIPETOUCH && (m_pFoundLSToFocus.expired() || m_pFoundLSToFocus->layer <= ZWLR_LAYER_SHELL_V1_LAYER_BOTTOM)) {
const auto PWORKSPACE = PMONITOR->activeWorkspace;
const bool VERTANIMS = PWORKSPACE->m_vRenderOffset.getConfig()->pValues->internalStyle == "slidevert" ||
PWORKSPACE->m_vRenderOffset.getConfig()->pValues->internalStyle.starts_with("slidefadevert");
@ -67,16 +67,15 @@ void CInputManager::onTouchDown(wlr_touch_down_event* e) {
Vector2D local;
if (!m_sTouchData.touchFocusWindow.expired()) {
if (m_sTouchData.touchFocusWindow.lock()->m_bIsX11) {
local = (g_pInputManager->getMouseCoordsInternal() - m_sTouchData.touchFocusWindow.lock()->m_vRealPosition.goal()) *
m_sTouchData.touchFocusWindow.lock()->m_fX11SurfaceScaledBy;
m_sTouchData.touchSurfaceOrigin = m_sTouchData.touchFocusWindow.lock()->m_vRealPosition.goal();
if (m_sTouchData.touchFocusWindow->m_bIsX11) {
local = (g_pInputManager->getMouseCoordsInternal() - m_sTouchData.touchFocusWindow->m_vRealPosition.goal()) * m_sTouchData.touchFocusWindow->m_fX11SurfaceScaledBy;
m_sTouchData.touchSurfaceOrigin = m_sTouchData.touchFocusWindow->m_vRealPosition.goal();
} else {
g_pCompositor->vectorWindowToSurface(g_pInputManager->getMouseCoordsInternal(), m_sTouchData.touchFocusWindow.lock(), local);
m_sTouchData.touchSurfaceOrigin = g_pInputManager->getMouseCoordsInternal() - local;
}
} else if (!m_sTouchData.touchFocusLS.expired()) {
local = g_pInputManager->getMouseCoordsInternal() - m_sTouchData.touchFocusLS.lock()->geometry.pos();
local = g_pInputManager->getMouseCoordsInternal() - m_sTouchData.touchFocusLS->geometry.pos();
m_sTouchData.touchSurfaceOrigin = g_pInputManager->getMouseCoordsInternal() - local;
} else {
@ -130,18 +129,18 @@ void CInputManager::onTouchMove(wlr_touch_motion_event* e) {
return;
}
if (validMapped(m_sTouchData.touchFocusWindow)) {
const auto PMONITOR = g_pCompositor->getMonitorFromID(m_sTouchData.touchFocusWindow.lock()->m_iMonitorID);
const auto PMONITOR = g_pCompositor->getMonitorFromID(m_sTouchData.touchFocusWindow->m_iMonitorID);
wlr_cursor_warp(g_pCompositor->m_sWLRCursor, nullptr, PMONITOR->vecPosition.x + e->x * PMONITOR->vecSize.x, PMONITOR->vecPosition.y + e->y * PMONITOR->vecSize.y);
auto local = g_pInputManager->getMouseCoordsInternal() - m_sTouchData.touchSurfaceOrigin;
if (m_sTouchData.touchFocusWindow.lock()->m_bIsX11)
local = local * m_sTouchData.touchFocusWindow.lock()->m_fX11SurfaceScaledBy;
if (m_sTouchData.touchFocusWindow->m_bIsX11)
local = local * m_sTouchData.touchFocusWindow->m_fX11SurfaceScaledBy;
wlr_seat_touch_notify_motion(g_pCompositor->m_sSeat.seat, e->time_msec, e->touch_id, local.x, local.y);
// wlr_seat_pointer_notify_motion(g_pCompositor->m_sSeat.seat, e->time_msec, local.x, local.y);
} else if (!m_sTouchData.touchFocusLS.expired()) {
const auto PMONITOR = g_pCompositor->getMonitorFromID(m_sTouchData.touchFocusLS.lock()->monitorID);
const auto PMONITOR = g_pCompositor->getMonitorFromID(m_sTouchData.touchFocusLS->monitorID);
wlr_cursor_warp(g_pCompositor->m_sWLRCursor, nullptr, PMONITOR->vecPosition.x + e->x * PMONITOR->vecSize.x, PMONITOR->vecPosition.y + e->y * PMONITOR->vecSize.y);