mirror of
https://github.com/hyprwm/Hyprland.git
synced 2025-07-25 17:21:54 -07:00
@@ -102,25 +102,25 @@ void CEventLoopManager::enterLoop() {
|
||||
void CEventLoopManager::onTimerFire() {
|
||||
const auto CPY = m_timers.timers;
|
||||
for (auto const& t : CPY) {
|
||||
if (t.strongRef() > 1 /* if it's 1, it was lost. Don't call it. */ && t->passed() && !t->cancelled())
|
||||
if (t.strongRef() > 2 /* if it's 2, it was lost. Don't call it. */ && t->passed() && !t->cancelled())
|
||||
t->call(t);
|
||||
}
|
||||
|
||||
nudgeTimers();
|
||||
scheduleRecalc();
|
||||
}
|
||||
|
||||
void CEventLoopManager::addTimer(SP<CEventLoopTimer> timer) {
|
||||
if (std::ranges::contains(m_timers.timers, timer))
|
||||
return;
|
||||
m_timers.timers.emplace_back(timer);
|
||||
nudgeTimers();
|
||||
scheduleRecalc();
|
||||
}
|
||||
|
||||
void CEventLoopManager::removeTimer(SP<CEventLoopTimer> timer) {
|
||||
if (!std::ranges::contains(m_timers.timers, timer))
|
||||
return;
|
||||
std::erase_if(m_timers.timers, [timer](const auto& t) { return timer == t; });
|
||||
nudgeTimers();
|
||||
scheduleRecalc();
|
||||
}
|
||||
|
||||
static void timespecAddNs(timespec* pTimespec, int64_t delta) {
|
||||
@@ -136,7 +136,21 @@ static void timespecAddNs(timespec* pTimespec, int64_t delta) {
|
||||
}
|
||||
}
|
||||
|
||||
void CEventLoopManager::scheduleRecalc() {
|
||||
// do not do it instantly, do it later. Avoid recursive access to the timer
|
||||
// vector, it could be catastrophic if we modify it while iterating
|
||||
|
||||
if (m_timers.recalcScheduled)
|
||||
return;
|
||||
|
||||
m_timers.recalcScheduled = true;
|
||||
|
||||
doLater([this] { nudgeTimers(); });
|
||||
}
|
||||
|
||||
void CEventLoopManager::nudgeTimers() {
|
||||
m_timers.recalcScheduled = false;
|
||||
|
||||
// remove timers that have gone missing
|
||||
std::erase_if(m_timers.timers, [](const auto& t) { return t.strongRef() <= 1; });
|
||||
|
||||
|
@@ -27,8 +27,8 @@ class CEventLoopManager {
|
||||
|
||||
void onTimerFire();
|
||||
|
||||
// recalculates timers
|
||||
void nudgeTimers();
|
||||
// schedules a recalc of the timers
|
||||
void scheduleRecalc();
|
||||
|
||||
// schedules a function to run later, aka in a wayland idle event.
|
||||
void doLater(const std::function<void()>& fn);
|
||||
@@ -69,6 +69,7 @@ class CEventLoopManager {
|
||||
private:
|
||||
// Manages the event sources after AQ pollFDs change.
|
||||
void syncPollFDs();
|
||||
void nudgeTimers();
|
||||
|
||||
struct SEventSourceData {
|
||||
SP<Aquamarine::SPollFD> pollFD;
|
||||
@@ -84,6 +85,7 @@ class CEventLoopManager {
|
||||
struct {
|
||||
std::vector<SP<CEventLoopTimer>> timers;
|
||||
Hyprutils::OS::CFileDescriptor timerfd;
|
||||
bool recalcScheduled = false;
|
||||
} m_timers;
|
||||
|
||||
SIdleData m_idle;
|
||||
|
@@ -14,13 +14,13 @@ CEventLoopTimer::CEventLoopTimer(std::optional<Time::steady_dur> timeout, std::f
|
||||
void CEventLoopTimer::updateTimeout(std::optional<Time::steady_dur> timeout) {
|
||||
if (!timeout.has_value()) {
|
||||
m_expires.reset();
|
||||
g_pEventLoopManager->nudgeTimers();
|
||||
g_pEventLoopManager->scheduleRecalc();
|
||||
return;
|
||||
}
|
||||
|
||||
m_expires = Time::steadyNow() + *timeout;
|
||||
|
||||
g_pEventLoopManager->nudgeTimers();
|
||||
g_pEventLoopManager->scheduleRecalc();
|
||||
}
|
||||
|
||||
bool CEventLoopTimer::passed() {
|
||||
|
Reference in New Issue
Block a user