Add touch-to-logical coordinate mapping for UI
Implements tapToLogical() to convert normalized touch coordinates to orientation-aware logical screen coordinates. Adds TouchRegistry hit testing for interactive UI elements and header back button. Touch gestures now work correctly across all screen orientations (Portrait, Landscape, etc.) by inverting the rotateCoordinates transform.
This commit is contained in:
@@ -1296,6 +1296,38 @@ int GfxRenderer::getScreenHeight() const {
|
||||
return panelWidth;
|
||||
}
|
||||
|
||||
void GfxRenderer::tapToLogical(float nx, float ny, int& outX, int& outY) const {
|
||||
// Native panel pixel of the tap (wasTouchTap normalizes over the native panel).
|
||||
int phyX = static_cast<int>(nx * panelWidth);
|
||||
int phyY = static_cast<int>(ny * panelHeight);
|
||||
if (phyX < 0) phyX = 0;
|
||||
if (phyX > panelWidth - 1) phyX = panelWidth - 1;
|
||||
if (phyY < 0) phyY = 0;
|
||||
if (phyY > panelHeight - 1) phyY = panelHeight - 1;
|
||||
|
||||
// Inverse of rotateCoordinates() (see the forward transform above): map a
|
||||
// physical/native point back into the current orientation's logical frame.
|
||||
switch (orientation) {
|
||||
case Portrait: // forward: phyX=logY, phyY=panelHeight-1-logX
|
||||
outX = panelHeight - 1 - phyY;
|
||||
outY = phyX;
|
||||
break;
|
||||
case PortraitInverted: // forward: phyX=panelWidth-1-logY, phyY=logX
|
||||
outX = phyY;
|
||||
outY = panelWidth - 1 - phyX;
|
||||
break;
|
||||
case LandscapeClockwise: // forward: phyX=panelWidth-1-logX, phyY=panelHeight-1-logY
|
||||
outX = panelWidth - 1 - phyX;
|
||||
outY = panelHeight - 1 - phyY;
|
||||
break;
|
||||
case LandscapeCounterClockwise: // forward: identity
|
||||
default:
|
||||
outX = phyX;
|
||||
outY = phyY;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Translate a logical rect through rotateCoordinates and take the bounding
|
||||
// box of its four corners on the physical panel. Output coords are inclusive
|
||||
// and clamped. Returns false if the rect ends up fully off-panel.
|
||||
|
||||
@@ -135,6 +135,11 @@ class GfxRenderer {
|
||||
void clearScreen(uint8_t color = 0xFF) const;
|
||||
void getOrientedViewableTRBL(int* outTop, int* outRight, int* outBottom, int* outLeft) const;
|
||||
|
||||
// Map a touch tap (normalized 0..1 in panel-native orientation, from
|
||||
// InputManager::wasTouchTap) to logical screen coordinates matching the Rects the
|
||||
// UI draws in. Inverse of rotateCoordinates() for the current orientation.
|
||||
void tapToLogical(float nx, float ny, int& outX, int& outY) const;
|
||||
|
||||
// Tiled grayscale strip target. While active, drawPixel() and clearScreen()
|
||||
// operate on `scratch` (panelWidthBytes * stripRows bytes, holding physical
|
||||
// rows [stripY0, stripY0 + stripRows)) instead of the framebuffer; pixels
|
||||
|
||||
@@ -245,6 +245,8 @@ unsigned long HalGPIO::getPowerButtonHeldTime() const { return inputMgr.getPower
|
||||
|
||||
bool HalGPIO::wasTouchTap(float& nx, float& ny) const { return inputMgr.wasTouchTap(nx, ny); }
|
||||
|
||||
bool HalGPIO::hasTouch() const { return inputMgr.hasTouch(); }
|
||||
|
||||
void HalGPIO::startDeepSleep() {
|
||||
// Ensure that the power button has been released to avoid immediately turning back on if you're holding it
|
||||
while (inputMgr.isPressed(BTN_POWER)) {
|
||||
|
||||
@@ -77,6 +77,9 @@ class HalGPIO {
|
||||
// primitive; see MappedInputManager for the top-left = Back mapping.)
|
||||
bool wasTouchTap(float& nx, float& ny) const;
|
||||
|
||||
// True if a touch controller is present/active (runtime gate; false on the C3).
|
||||
bool hasTouch() const;
|
||||
|
||||
// Setup wake up GPIO and enter deep sleep
|
||||
void startDeepSleep();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user