diff options
| author | Danilo M. <danix@danix.xyz> | 2026-09-30 19:56:48 +0200 |
|---|---|---|
| committer | Danilo M. <danix@danix.xyz> | 2026-09-30 19:56:48 +0200 |
| commit | 96ac1ee65da31055704e0a14cafacc33914d7e86 (patch) | |
| tree | 8a8fa33ec27607f40d6d23661a89681ffbaa4456 /widgets | |
| parent | e55896ce41d6165105671da5b6f33813106ef1b8 (diff) | |
| download | conky-theme-udt-96ac1ee65da31055704e0a14cafacc33914d7e86.tar.gz conky-theme-udt-96ac1ee65da31055704e0a14cafacc33914d7e86.zip | |
perf(dashboard): draw at 0.1s only while the dashboard is visible
Conky gives Lua no way to request one redraw, so a scroll showed up to
2s late. Pointer enter and leave, which Hyprland sends on every toggle
of the special workspace, now switch conky_set_update_interval between
0.1s and the config's 2s.
At that rate the CPU and network counters would sample over 0.1s
windows and the chart would fill 20x faster, so both now sample through
data.new_gate on the /proc/uptime clock, about every 2s, and redraw
their last values in between. The samplers move to texeci: execi runs
in the main loop and a 0.7s nvtable or an Immich download stalled the
scroll.
Measured: about 12% of one core while visible, 0.5% while hidden.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Diffstat (limited to 'widgets')
| -rw-r--r-- | widgets/immich.lua | 3 | ||||
| -rw-r--r-- | widgets/network.lua | 16 | ||||
| -rw-r--r-- | widgets/system.lua | 23 |
3 files changed, 27 insertions, 15 deletions
diff --git a/widgets/immich.lua b/widgets/immich.lua index 8590dbf..d700d8a 100644 --- a/widgets/immich.lua +++ b/widgets/immich.lua @@ -159,9 +159,6 @@ end -- Scroll steps through today's photos; a left click opens the one on screen -- in Immich and hides the dashboard, since the browser would otherwise open -- underneath the special workspace. --- --- ponytail: a scroll shows at the next draw, up to update_interval (2s) later. --- Conky offers Lua no way to request a redraw. function M.mouse(event) if event.type == 'mouse_scroll' then offset = offset + (event.direction == 'up' and -1 or 1) diff --git a/widgets/network.lua b/widgets/network.lua index 3a11521..20b0573 100644 --- a/widgets/network.lua +++ b/widgets/network.lua @@ -37,6 +37,11 @@ local rx_hist, tx_hist = {}, {} local hist_len = 0 local lan_addr = nil +-- Sampled every ~2s whatever the draw rate, so the chart keeps one point per +-- sample rather than per draw. 1.9 not 2: draws jitter by a few ms. +local gate = data.new_gate(1.9) +local down, up = nil, nil + -- Append to a fixed-length history, dropping the oldest. A plain array with -- table.remove(1) rather than a circular buffer with an index: the lengths -- here are a few hundred at most and the draw is every two seconds, so the @@ -73,8 +78,11 @@ function M.draw(cr, rect, colors) rx_counter = rx_counter or data.new_rate_counter(interval) tx_counter = tx_counter or data.new_rate_counter(interval) - local down = rx_counter:sample(read_counter('rx_bytes')) - local up = tx_counter:sample(read_counter('tx_bytes')) + local sampled, now = gate() + if sampled then + down = rx_counter:sample(read_counter('rx_bytes'), now) + up = tx_counter:sample(read_counter('tx_bytes'), now) + end -- Fluid type, as every other card does: one base size S drives everything, -- taken as the smaller of a height budget and a measured width fit. @@ -140,8 +148,8 @@ function M.draw(cr, rect, colors) while #rx_hist > hist_len do table.remove(rx_hist, 1) end while #tx_hist > hist_len do table.remove(tx_hist, 1) end end - if down then push(rx_hist, down, hist_len) end - if up then push(tx_hist, up, hist_len) end + if sampled and down then push(rx_hist, down, hist_len) end + if sampled and up then push(tx_hist, up, hist_len) end -- One ceiling for both series. Scaled independently they would lie about -- their relative size, which is the entire reason to draw them together. diff --git a/widgets/system.lua b/widgets/system.lua index 98e0ae1..c1cdf67 100644 --- a/widgets/system.lua +++ b/widgets/system.lua @@ -27,6 +27,11 @@ local TEMPS = { local counters = {} local total_counter = data.new_cpu_counter() +-- Sampled every ~2s whatever the draw rate; the values between samples are +-- the last ones read. 1.9 not 2: draws jitter by a few ms either way. +local gate = data.new_gate(1.9) +local load, pcts = nil, {} + -- Read once, not per frame. Neither can change without a reboot, and -- re-reading /proc/cpuinfo every two seconds for a constant is waste: the file -- repeats its model-name line once per thread. @@ -51,11 +56,15 @@ function M.draw(cr, rect, colors) local inner = card.card(cr, rect, colors) local function clamp(v, lo, hi) return math.max(lo, math.min(hi, v)) end - local stat = data.slurp('/proc/stat') - local agg_total, agg_idle = data.cpu_times(stat or '') - local load = total_counter:sample(agg_total, agg_idle) + if gate() then + local stat = data.slurp('/proc/stat') or '' + load = total_counter:sample(data.cpu_times(stat)) + for i, c in ipairs(data.per_cpu_times(stat)) do + counters[i] = counters[i] or data.new_cpu_counter() + pcts[i] = counters[i]:sample(c.total, c.idle) or 0 + end + end local load_txt = load and string.format('%d%%', math.floor(load + 0.5)) or '--' - local cores = data.per_cpu_times(stat or '') local temp_n = #TEMPS local cpu_txt, board_txt = hardware() @@ -137,16 +146,14 @@ function M.draw(cr, rect, colors) -- legitimate outcome: the guard below skips the band when it has no height. local eh = clamp((inner.y + inner.h) - eq_top - (S * 1.13 + temp_n * step), 0, math.huge) - local n = #cores + local n = #pcts if n > 0 and eh >= 8 then local gap = math.max(2, inner.w * 0.006) local bw = (inner.w - gap * (n - 1)) / n -- Below about 3px a row of sixteen bars is an illegible smear; drop to the -- aggregate bar instead of drawing one. if bw >= 3 then - for i, c in ipairs(cores) do - counters[i] = counters[i] or data.new_cpu_counter() - local pct = counters[i]:sample(c.total, c.idle) or 0 + for i, pct in ipairs(pcts) do card.vbar(cr, inner.x + (i - 1) * (bw + gap), eq_top + eh, bw, eh, pct / 100, card.threshold(pct, 25, 75, colors), colors) end |
