stop hovering when the cursor points at no tile

A cursor resting on a panel or outside the window kept whatever it last
pointed at: the ghost, the tunnel preview, the deconstruct tint all stayed
put, because "not hovering" was not a state the build mode could hold. Make
both ghost tiles optional, clear the hover with them, and re-derive it when
the cursor comes back or a mode is entered.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Ne3mejABZoLWKLh8fgpM3x
This commit is contained in:
2026-08-17 15:19:22 +02:00
parent 9490a96e12
commit b2148f00ac
7 changed files with 167 additions and 31 deletions

View File

@@ -226,6 +226,15 @@ private:
// which is the only case that goes on to start a box drag.
bool selectAtPoint(QPoint tile, QVector2D worldPos, bool additive);
void selectInBox(bool additive);
// Whether the cursor points at the game world at all: it does while it is over
// this widget, and while a belt or box drag holds the button, which goes on
// following the cursor onto the floating panels and past the window edge.
bool isHoverLive() const;
// Re-derives the hover from wherever the cursor is now, or drops it when the
// cursor points at nothing (REQ-BLD-GHOST). The entry point for everything a
// mouse move does not cover: a scrolling view, a cursor crossing onto a panel or
// out of the window, and a mode just entered under a cursor that has not moved.
void refreshHover();
// Re-resolves everything that follows from where the cursor points into the world:
// the ghost tile and its validity, the tunnel ends, a running belt or box drag, the
// deconstruct hover. Called for every mouse move, and once per frame while the view
@@ -320,6 +329,11 @@ private:
// end tile closest to the cursor when snapping to a building (REQ-BLD-BELT-DRAG)
// and to resolve the tunnel ghost sub-tile (REQ-BLD-TUNNEL-MODE).
QVector2D m_cursorWorldPos;
// Whether the hover state currently stands for a cursor pointing at the world,
// so that losing it is noticed once rather than every frame. Kept here rather
// than asked of Qt per reader: it has to agree with what was last written to the
// build mode controller, not with where the cursor happens to be mid-frame.
bool m_hoverLive = false;
bool m_debugDraw;