From ca6760047c94bd1106cde8ab6e736aee1783db01 Mon Sep 17 00:00:00 2001 From: Gunar Schorcht Date: Wed, 9 Aug 2023 10:40:51 +0200 Subject: [PATCH 1/3] drivers/ft5x06: introduce coordinate conversions To obtain coordinates from the touch panel that correspond to the display coordinates, it is often necessary to convert the coordinates from the touch display by swapping and mirroring. For the sake of simplicity, possible rotations are additionally defined. --- dist/tools/doccheck/exclude_simple | 1 + drivers/ft5x06/ft5x06.c | 27 ++++++++++++++++-- drivers/ft5x06/include/ft5x06_params.h | 4 +++ drivers/include/ft5x06.h | 38 ++++++++++++++++++++++---- 4 files changed, 61 insertions(+), 9 deletions(-) diff --git a/dist/tools/doccheck/exclude_simple b/dist/tools/doccheck/exclude_simple index 5f415b5a31ee..ecdc91e14b51 100644 --- a/dist/tools/doccheck/exclude_simple +++ b/dist/tools/doccheck/exclude_simple @@ -2307,6 +2307,7 @@ warning: Member FT5X06_PARAMS (macro definition) of file ft5x06_params.h is not warning: Member FT5X06_PARAM_TYPE (macro definition) of file ft5x06_params.h is not documented. warning: Member FT5X06_PARAM_XMAX (macro definition) of file ft5x06_params.h is not documented. warning: Member FT5X06_PARAM_YMAX (macro definition) of file ft5x06_params.h is not documented. +warning: Member FT5X06_PARAM_XYCONV (macro definition) of file ft5x06_params.h is not documented. warning: Member FT5X06_TD_STATUS_MASK (macro definition) of file ft5x06_constants.h is not documented. warning: Member FT5X06_TD_STATUS_REG (macro definition) of file ft5x06_constants.h is not documented. warning: Member FT5X06_TOUCH1_XH_REG (macro definition) of file ft5x06_constants.h is not documented. diff --git a/drivers/ft5x06/ft5x06.c b/drivers/ft5x06/ft5x06.c index 889e430cd19f..8fac64dbb2d1 100644 --- a/drivers/ft5x06/ft5x06.c +++ b/drivers/ft5x06/ft5x06.c @@ -111,9 +111,30 @@ int ft5x06_read_touch_positions(const ft5x06_t *dev, ft5x06_touch_position_t *po i2c_read_regs(FT5X06_BUS, FT5X06_ADDR, touch_reg_map[touch], ®s, 4, 0); pos_x = (uint16_t)((regs[1] & FT5X06_TOUCH_POS_LSB_MASK) | (uint16_t)(regs[0] & FT5X06_TOUCH_POS_MSB_MASK) << 8); pos_y = (uint16_t)((regs[3] & FT5X06_TOUCH_POS_LSB_MASK) | (uint16_t)(regs[2] & FT5X06_TOUCH_POS_MSB_MASK) << 8); - /* X and Y positions are swapped compared to the display */ - positions[touch].x = pos_y; - positions[touch].y = pos_x; + + if (dev->params->xyconv & FT5X06_SWAP_XY) { + positions[touch].x = pos_y; + positions[touch].y = pos_x; + } + else { + positions[touch].x = pos_x; + positions[touch].y = pos_y; + } + + if (dev->params->xyconv & FT5X06_MIRROR_X) { + /* X position is mirrored */ + assert(positions[touch].x <= dev->params->xmax); + positions[touch].x = dev->params->xmax - positions[touch].x; + } + + if (dev->params->xyconv & FT5X06_MIRROR_Y) { + /* Y position is mirrored */ + assert(positions[touch].y <= dev->params->ymax); + positions[touch].y = dev->params->ymax - positions[touch].y; + } + + DEBUG("[ft5x06] read position X=%u y=%u'\n", + positions[touch].x, positions[touch].y); } i2c_release(FT5X06_BUS); diff --git a/drivers/ft5x06/include/ft5x06_params.h b/drivers/ft5x06/include/ft5x06_params.h index fae9d1a194fd..b580067aa13c 100644 --- a/drivers/ft5x06/include/ft5x06_params.h +++ b/drivers/ft5x06/include/ft5x06_params.h @@ -49,6 +49,9 @@ extern "C" { #ifndef FT5X06_PARAM_YMAX #define FT5X06_PARAM_YMAX (272U) #endif +#ifndef FT5X06_PARAM_XYCONV +#define FT5X06_PARAM_XYCONV FT5X06_SWAP_XY +#endif #ifndef FT5X06_PARAM_TYPE #define FT5X06_PARAM_TYPE FT5X06_TYPE_FT5336 #endif @@ -59,6 +62,7 @@ extern "C" { .int_pin = FT5X06_PARAM_INT_PIN, \ .xmax = FT5X06_PARAM_XMAX, \ .ymax = FT5X06_PARAM_YMAX, \ + .xyconv = FT5X06_PARAM_XYCONV, \ .type = FT5X06_PARAM_TYPE \ } /**@}*/ diff --git a/drivers/include/ft5x06.h b/drivers/include/ft5x06.h index eb079cfb4241..5e075a500a7a 100644 --- a/drivers/include/ft5x06.h +++ b/drivers/include/ft5x06.h @@ -77,6 +77,26 @@ typedef enum { FT5X06_TYPE_FT5X46, /**< FT5X46 */ } ft5x06_type_t; +/** + * @brief Touch screen coordinate conversions + * + * Normally the coordinates of the touch device must be converted to the + * screen coordinates by swapping and/or mirroring. The flags defined by + * this enumeration can be ORed for a combined conversion. In this case, + * the swapping is performed before the mirroring. + * + * @note The maximum X and Y screen coordinates defined by + * @ref ft5x06_params_t::xmax and @ref ft5x06_params_t::ymax + * define the dimension of the touch device in screen coordinates, + * i.e. after conversion. + */ +typedef enum { + FT5X06_NO_CONV = 0x00, /**< No conversion */ + FT5X06_MIRROR_X = 0x01, /**< Mirror X, applied after optional swapping */ + FT5X06_MIRROR_Y = 0x02, /**< Mirror Y, applied after optional swapping */ + FT5X06_SWAP_XY = 0x04, /**< Swap XY, applied before optional mirroring */ +} ft5x06_touch_conv_t; + /** * @brief Signature of the touch event callback triggered from interrupt * @@ -86,14 +106,20 @@ typedef void (*ft5x06_event_cb_t)(void *arg); /** * @brief Device initialization parameters + * + * @note ft5x06_params_t::xmax and ft5x06_params_t::ymax define the + * maximum X and Y values in screen coordinates after the optional + * conversion defined by ft5x06_params_t::xmax. */ typedef struct { - i2c_t i2c; /**< I2C device which is used */ - uint8_t addr; /**< Device I2C address */ - gpio_t int_pin; /**< Touch screen interrupt pin */ - uint16_t xmax; /**< Touch screen max X position */ - uint16_t ymax; /**< Touch screen max Y position */ - ft5x06_type_t type; /**< Device type */ + i2c_t i2c; /**< I2C device which is used */ + uint8_t addr; /**< Device I2C address */ + gpio_t int_pin; /**< Touch screen interrupt pin */ + uint16_t xmax; /**< Touch screen max X position */ + uint16_t ymax; /**< Touch screen max Y position */ + ft5x06_touch_conv_t xyconv; /**< Touch screen coordinates conversion, + swapping is performed before mirroring */ + ft5x06_type_t type; /**< Device type */ } ft5x06_params_t; /** From a61d4be36aa055b4ddbee230f9a962df3a4c20a0 Mon Sep 17 00:00:00 2001 From: Gunar Schorcht Date: Wed, 9 Aug 2023 10:42:40 +0200 Subject: [PATCH 2/3] boards/stm32f746g-disco: add touch panel conversion config --- boards/stm32f746g-disco/include/board.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/boards/stm32f746g-disco/include/board.h b/boards/stm32f746g-disco/include/board.h index 9ecef1eb7424..e87c09913baf 100644 --- a/boards/stm32f746g-disco/include/board.h +++ b/boards/stm32f746g-disco/include/board.h @@ -79,8 +79,9 @@ extern "C" { */ #define FT5X06_PARAM_I2C_DEV I2C_DEV(1) /**< I2C device */ #define FT5X06_PARAM_INT_PIN GPIO_PIN(PORT_I, 13) /**< Interrupt pin */ -#define FT5X06_PARAM_XMAX (480) /**< Max width */ -#define FT5X06_PARAM_YMAX (272) /**< Max height */ +#define FT5X06_PARAM_XMAX LCD_SCREEN_WIDTH /**< Max width */ +#define FT5X06_PARAM_YMAX LCD_SCREEN_HEIGHT /**< Max height */ +#define FT5X06_PARAM_XYCONV FT5X06_SWAP_XY /**< Swap X and Y */ #define FT5X06_PARAM_TYPE FT5X06_TYPE_FT5336 /**< Device type */ /** @} */ From 26ed7e6955efcf28ee4afa1ee637e0a385f58280 Mon Sep 17 00:00:00 2001 From: Gunar Schorcht Date: Wed, 9 Aug 2023 11:28:04 +0200 Subject: [PATCH 3/3] boards/stm32f723e-disco: add touch panel conversion config --- boards/stm32f723e-disco/include/board.h | 1 + 1 file changed, 1 insertion(+) diff --git a/boards/stm32f723e-disco/include/board.h b/boards/stm32f723e-disco/include/board.h index 9e710af42844..3b9f72070c76 100644 --- a/boards/stm32f723e-disco/include/board.h +++ b/boards/stm32f723e-disco/include/board.h @@ -56,6 +56,7 @@ extern "C" { #define FT5X06_PARAM_INT_PIN GPIO_PIN(PORT_I, 9) /**< Interrupt pin */ #define FT5X06_PARAM_XMAX (240) /**< Max width */ #define FT5X06_PARAM_YMAX (240) /**< Max height */ +#define FT5X06_PARAM_XYCONV FT5X06_NO_CONV /**< No coordinate conversion */ #define FT5X06_PARAM_TYPE FT5X06_TYPE_FT6X06 /**< Device type */ /** @} */