The first thing you notice is the Product ID Registers (0x8140–0x814E). You read 0x39, 0x33, 0x31, 0x31. Magic. It whispers "GT911" back at you. It’s alive.
The genius move? The Gesture ID at 0x814F. You swipe left? The register spits out 0x01. Swipe right? 0x02. This isn't just a touch controller; it’s a lazy programmer’s dream for UI navigation. No gesture math. No vector analysis. Just read one byte. Chef's kiss.
Then there's 0x814E (Buffer Status). Bit 7 is the "Large Detect" flag (fat-finger protection), and Bit 0 is the "Buffer Ready" flag. This is the heartbeat of the device. Poll it, read the 5 touch points (each taking 8 bytes at 0x8150), and clear it by writing 0x00 back. It’s a clean, simple dance.
This is almost always a threshold (0x8105) issue. If set too low (e.g., <30), environmental noise triggers false touches. Increase to 120 and test. gt911 register map
Each touch point occupies 8 consecutive bytes. Point 1 starts at 0x8150.
| Offset | Description | |--------|-------------| | +0 | Track ID (changes on each new touch) | | +1 | X coordinate (low byte) | | +2 | X coordinate (high byte) | | +3 | Y coordinate (low byte) | | +4 | Y coordinate (high byte) | | +5 | Touch size (pressure/area) | | +6 | Reserved | | +7 | Reserved |
Address mapping for each point:
Need the full 200+ register guide? Download the GT911 Programming Guide (Goodix official).
Have you run into any GT911 quirks in your projects? Share below 👇
Let’s walk through a minimal read sequence on an ESP32 or Arduino: The first thing you notice is the Product
// Read number of touch points uint8_t touch_count = 0; i2c_read(0x5D, 0x8101, &touch_count, 1);
if(touch_count > 0) touch_data[3]; uint8_t track_id = touch_data[0]; uint8_t size = touch_data[5]; printf("Touch %d: X=%d Y=%d Size=%d\n", track_id, x, y, size);