spacr.qt.tooltip_policy

One rule for every tooltip in spaCR: when it appears and when it goes.

Qt’s own answer is a style hint, SH_ToolTip_WakeUpDelay, which most styles set to about 700 ms and which nothing in spaCR was choosing. Tooltips therefore arrived while the pointer was still travelling, and left the instant it moved off the widget – too fast to read, and impossible to reach if the text ran long.

This module installs ONE event filter on QApplication and takes the decision away from the style:

  • a tooltip appears after SHOW_DELAY_MS of hovering, not before;

  • it stays while the pointer is on the widget OR on the tooltip itself;

  • it leaves LINGER_MS after the pointer leaves both.

Because the filter sits on the application object, a widget written later obeys the rule without anyone remembering to ask for it: its ToolTip event travels to the application like every other one.

The filter shows the text itself, with QToolTip.showText and no owning widget, rather than letting Qt show it. Handing Qt the widget hands Qt the hiding as well – Qt hides on the widget’s Leave event, immediately, which is the one behaviour this module exists to change.

Two things follow from taking the event, and both are handled rather than accepted:

  • Qt PROPAGATES a tooltip event to the parent widget when the widget under the pointer has no tooltip of its own, which is how a card explains itself while the pointer is on the label written on it. The text is therefore resolved with tooltip_text_for(), up the parent chain, exactly as Qt would have.

  • A table, a header or a list answers from Qt::ToolTipRole inside its own event, not from a toolTip() any filter can read. When nothing in the parent chain has a tooltip, the event is SENT AGAIN after the wait, with the filter standing aside, so those still appear – and appear on the same two-second rule as everything else.

tooltips_enabled() is the preference switch, on by default. Cleared, the ToolTip event is swallowed and no tooltip is shown anywhere.

Functions

install_tooltip_policy(→ bool)

Install the application-wide tooltip filter. Idempotent.

invalidate_tooltip_policy(→ None)

Forget the cached preference, and hide anything already up.

tooltip_policy(→ Optional[_TooltipFilter])

The installed filter, or None. For tests and for diagnostics.

tooltip_text_for(→ str)

The tooltip a hover on widget would raise, parents included.

tooltips_enabled(→ bool)

Whether tooltips are shown at all. Cached; True by default.

uninstall_tooltip_policy(→ bool)

Remove the filter. True if there was one.

Module Contents

spacr.qt.tooltip_policy.install_tooltip_policy(app=None) → bool[source]

Install the application-wide tooltip filter. Idempotent.

Parameters:

app – the QApplication; defaults to the running instance.

Returns:

True if a filter was installed by this call.

spacr.qt.tooltip_policy.invalidate_tooltip_policy() → None[source]

Forget the cached preference, and hide anything already up.

spacr.qt.tooltip_policy.tooltip_policy() → _TooltipFilter | None[source]

The installed filter, or None. For tests and for diagnostics.

spacr.qt.tooltip_policy.tooltip_text_for(widget) → str[source]

The tooltip a hover on widget would raise, parents included.

This is not a convenience: it is the behaviour being preserved. Qt PROPAGATES a tooltip event up the parent chain, so a label with no tooltip of its own inside a card that has one shows the card’s. A filter that read widget.toolTip() alone and then swallowed the event would break every one of those – a card explains itself until the pointer lands on the text written on it, and then it stops.

Parameters:

widget – the hovered widget, or None; its toolTip() is read, then each parent’s up to and including its window (at most 64 levels).

Returns:

the first non-empty tooltip from the widget outwards, or "" if neither it nor any parent up to its window has one.

spacr.qt.tooltip_policy.tooltips_enabled() → bool[source]

Whether tooltips are shown at all. Cached; True by default.

Read on every ToolTip event, which is why the answer is cached rather than re-read from QSettings each time. invalidate_tooltip_policy() drops the cache, and spacr.qt.preferences.set_tooltips_enabled() calls it, so the switch and the screen can never disagree.

spacr.qt.tooltip_policy.uninstall_tooltip_policy(app=None) → bool[source]

Remove the filter. True if there was one.