Conversation
m_1secTimer->start(100) started the timer with a 100ms interval despite its name and its handler, on_1secTimerTick(), being written for a once-per-second cadence: it toggles the graph hint popups' visibility based on cursor position every tick. At 10Hz instead of 1Hz this causes visibly flickering popups during normal use.
analyzer/ble_analyzer.h includes "screeninfo.h" and declares a setScreenInfo(ScreenInfo&) signal; screeninfo.h does not exist anywhere in this repository at any commit reachable from master, and setScreenInfo is never defined or called anywhere either. This breaks any build on any platform.
…dback loop MainWindow::event() reacted to every single WindowActivate/WindowDeactivate by showing/hiding two always-on-top Qt::Tool popups (the graph 'Hint' and 'BriefHint' hints, and the markers popup). On some Wayland compositors (observed on COSMIC/cosmic-comp), unmapping/remapping those Qt::Tool surfaces itself triggers a spurious WindowActivate/WindowDeactivate on the parent window - which re-fires the same show/hide logic, creating a self-sustaining feedback loop that reads as rapidly flickering popups and a flickering main window title bar. Two changes, together: - MainWindow now debounces WindowActivate/WindowDeactivate symmetrically: neither is acted on immediately: only once the window's activation state has held steady for 300ms is focus() actually emitted, and only if it differs from the last emitted state. - PopUp::focusShow()/focusHide() and MarkersPopUp::focusShow()/focusHide() no longer map/unmap the underlying window at all; they move it on/off-screen instead. This keeps the Wayland surface continuously mapped, so showing/hiding these popups can no longer perturb the parent window's activation state, breaking the feedback loop at its root rather than just slowing it down. Also adds Qt::WindowDoesNotAcceptFocus to both classes' window flags as defense in depth. Separately, mainwindow.cpp already had m_1secTimer - a timer whose handler toggles the same hint popups based on cursor position - started with a 100ms interval despite its name and intent; that is a distinct, already-fixed bug (see previous commit) that made the same popups flash on every mouse-cursor check instead of once a second.
label.setStyleSheet("QLabel { color : " + m_textColor + "margin-top: ...")
concatenates the text color directly onto the next CSS property with no
separating semicolon, producing an invalid declaration like
'color : whitemargin-top: 6px' - the color is silently dropped by Qt's
stylesheet parser. PopUp::setTextColor() already builds the equivalent
string correctly (with a ';' after the color); this makes the default
built in init() match it, so any PopUp that never calls setTextColor()
still gets a valid, visible label color instead of relying on it being
overwritten later.
PopUp and MarkersPopUp were always separate Qt::Tool top-level windows. The previous fix (park off-screen instead of unmapping) stopped them causing flicker, but left them permanently registered as real windows with the window manager/task switcher, since they are never truly unmapped once shown. Add an 'embedded' constructor parameter: when true, the widget is a plain child of its parent instead of a separate top-level window, so there is no window for a window manager/compositor to ever see - no flicker risk, and nothing to show up in any window/task list either. All existing position-tracking code (setName/setPosition/ MainWindowPos/mouseMoveEvent) keeps computing m_x/m_y as global screen coordinates exactly as before; only the final geometry application (a new applyGeometry() helper) translates through parentWidget()->mapFromGlobal() when embedded, so none of that math needed to change. m_graphHint, m_graphBriefHint (Measurements) and m_markersHint (Markers) are now constructed embedded, parented to MainWindow.
Both were declared but never initialized, and only ever assigned inside on_focus(bool). Previously the first WindowActivate at startup emitted focus(true) essentially immediately, setting it before anything read it. The new debounced focus() emission (see the previous commit on this branch fixing the WindowActivate/Deactivate feedback loop) can now legitimately not emit at all during startup if the window starts active, leaving m_focus read before it is ever written - undefined behavior. Default-initialize both to true, matching the normal case of an app that starts with the main window focused.
Same bug as db3c4ae (popup.cpp): the color declaration runs straight into the next CSS property with no separating semicolon ('color : #RRGGBBmargin-top: 6px'), silently dropping the color. The class's own setTextColor() builds the equivalent string correctly.
on_selectDeviceDialog() runs a nested event loop via dlg.exec(). A pending QTimer::singleShot call to the same slot (e.g. from on_refreshConnection()) would still fire while that nested loop is running, stacking a second real top-level SelectDeviceDialog on top of the first. No live path currently re-enters it, but the pattern is fragile against future changes and costs nothing to guard directly.
Open
5 tasks
archlinux-github
pushed a commit
to archlinux/aur
that referenced
this pull request
Aug 31, 2026
Upstream has moved from 1.2.6 (Qt5) to 2.0.3 (Qt6, Bluetooth support,
UI redesign) with no tags or releases for Linux, so the head commit is
pinned as of packaging (bc7b74d). Reworks the package around that:
- depends on qt6-base/qt6-serialport/qt6-connectivity/libusb instead
of qt5-base/qt5-serialport/glibc/gcc-libs
- license now lists both MIT (upstream's own code) and
GPL-3.0-or-later (the vendored qcustomplot.cpp), previously just MIT
- install layout simplified to a normal /usr/bin/AntScope2 binary
instead of /usr/share/antscope2/AntScope2 plus a symlink
- fixes real bugs in the old PKGBUILD: LICENSE.txt installed to a
nonstandard location, a broken .icns icon reference in the desktop
file (Linux icon themes don't resolve macOS icon files), a udev rule
numbered after 73-seat-late.rules so its TAG+="uaccess" never
actually took effect, and a self-conflicting conflicts=('antscope2'
'antscope2-git') plus a typo'd provide=() that pacman silently
ignored
- adds the two known upstream Linux defects as patches: a build-
breaking reference to a nonexistent screeninfo.h, and
Settings::localDataPath() resolving data files relative to the
binary's own directory rather than a real install path
Also adds 13 patches for a flickering-popups/title-bar bug (a
WindowActivate/WindowDeactivate feedback loop against certain Wayland
compositors) and its underlying defects, plus five out-of-bounds
reads in device/network parsing and disabled TLS certificate
verification - found and fixed while chasing the flicker bug, and
submitted upstream as:
rigexpert/AntScope2#29
rigexpert/AntScope2#30
Not yet merged as of packaging; applied here in the meantime.
archlinux-github
pushed a commit
to archlinux/aur
that referenced
this pull request
Sep 2, 2026
Long-neglected package that had drifted far from what it actually builds:
- Qt5 deps (qt5-base/qt5-serialport/glibc/gcc-libs) for a project that
moved to Qt6 with Bluetooth support; switched to
qt6-base/qt6-serialport/qt6-connectivity/libusb, matching the antscope2
package's own (tested) dependency list.
- Pinned to a stale commit (19323af) despite being a "-git" package that
should track the live tip; replaced with a proper pkgver() deriving a
monotonic version from ANTSCOPE2VER plus commit count/hash, and a VCS
source with no commit pin.
- Fixed two real bugs that would have broken every build: a missing path
separator ("${pkgdir}"usr/share/... instead of "${pkgdir}"/usr/share/...)
and an unterminated string literal in the LICENSE.txt install line.
- Fixed provides=('antcsope2-git') (transposed letters) to
provides=('antscope2') - a -git package should provide the versioned
package's name, not a typo of its own.
- Removed a stray conflicts=('antscop2') (another typo, a third
nonexistent package name) and an unused .INSTALL hook whose symlink
approach the modernized install layout below no longer needs.
- Modernized the install layout to match the antscope2 package: binary
installs straight to /usr/bin (no /usr/share/antscope2-git/AntScope2 +
symlink), the actually-current udev rule (0483:a1de and 0483:a1da, uaccess
tag, correctly numbered - the old 99-rigexpert.rules used a blanket
MODE="0666") and desktop file (the old one pointed its icon at a
Windows-only .icns file that was never installed anywhere on Linux).
Source now points at a maintainer fork branch (linux-packaging) that merges
two sets of fixes - flickering popups/title bar, and out-of-bounds reads
plus a completed firmware-update fix - submitted upstream as
rigexpert/AntScope2#29 and #30 but not yet merged.
This -git package tracks that branch directly (no patch files needed,
unlike the versioned antscope2 package, which pins a commit and applies
patches); once the PRs merge, this should point back at upstream directly.
Verified: a fresh clone of the fork branch, with the one remaining
Linux-packaging-only patch (linux-fixed-system-data-path.patch) applied,
builds cleanly with qmake6/make and produces a working binary.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_013EAiXVpAbBuCAxWNA3mzJY
3 tasks
dc0sk
force-pushed
the
fix/1sec-timer-flicker
branch
from
September 2, 2026 13:05
9fb2af8 to
6f8486a
Compare
This was referenced Sep 8, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Fixes a real usability bug: popups in the main window flicker rapidly (several times a second), and the main window's title bar flickers along with them, starting specifically after alt-tabbing away from and back to the app. Reproduced and fixed live on Linux (COSMIC desktop / cosmic-comp Wayland compositor) with a real analyzer (Stick 500) connected.
Root cause
MainWindow::event()emits afocus(bool)signal on every singleQEvent::WindowActivate/WindowDeactivate, which drivesMeasurements/Markersto show/hide two always-on-topQt::Toolpopups ("Hint"/"BriefHint" graph hints and the markers popup) via realQWidget::show()/hide(). On some Wayland compositors, mapping/unmapping thoseQt::Toolsurfaces itself triggers a spuriousWindowActivate/WindowDeactivateback on the parent window — a self-sustaining feedback loop entirely internal to the app.What changed
m_1secTimerwas started with a 100ms interval despite its name and its handler being written for a once-per-second cadence — a separate, smaller flicker source, fixed first.MainWindownow debouncesWindowActivate/WindowDeactivatesymmetrically — neither is acted on immediately, only once the window's activation state has held steady for 300ms. And more importantly,PopUp/MarkersPopUpare now converted to plain embedded child widgets instead of separateQt::Tooltop-level windows, so there is no window for a compositor to ever see, no window-manager interaction that can perturb activation state, and nothing left in any window/task list either. All existing screen-coordinate positioning logic is untouched; only the final geometry application translates throughmapFromGlobal()when embedded.#include "screeninfo.h"/ unused signal declaration inble_analyzer.h—screeninfo.hdoesn't exist anywhere in this repository at any commit reachable from master, which breaks the build on any platform.;in two places (popup.cpp,onefqwidget.cpp) where a label's default stylesheet concatenates the text color straight into the next CSS property (color : whitemargin-top: 6px), silently dropping the color.Measurements::m_focus/Markers::m_focusnever being initialized (only ever assigned insideon_focus()) — the new debouncedfocus()emission can legitimately not fire at all during a normal startup, so this was being read as undefined behavior.on_selectDeviceDialog(): it runs a nested event loop viadlg.exec(), during which a pendingQTimer::singleShotcall to the same slot could in principle stack a second dialog on top of the first.Test plan