STM Урок 72. Touch panel FT5336. Часть 1



 

Урок 72

 

Часть 1

 

Touch panel FT5336

 

Продолжаем работу с отладочной платой STM32F746G-DISCO и изучать её интересные элементы. Мы уже изрядно изучили её дисплей LCD, теперь настало время изучить панель Toush Screen, установленную на данном дисплее. Тем более без этого экран теряет свою интерактивность, и становится, как говорится, доступным «только для чтения». Нам это не подходит, так как мы хотим управлять процессами, поэтому обойти тему ввода информации через Touch Screen нам никак не получится.

Контроллер у данной панели представлен компанией FocalTech и маркируется FT5336. К сожелению, найти подробную техническую документацию к данному контроллеру (или драйверу) мне не удалось, только краткую, которую я, разумеется, прикреплю внизу страницы. В данной документации представлен протокол передачи данных, которая происходит посредством шины I2C, также даны все электические и временные характеристики. Но здесь нет не то что идентификаторов, а даже адреса устройства, по которому мы к нему сможем обращаться. Мало того, данный контроллер является полноправным, то есть присутствует масса регистров, и описание данных регистров здесь не представлено.

Но, к счастью, мне в разборе этой темы помог исходный код из примеров Cube, а также техническая документация на подобные контроллеры TS, и мне удалось всё-таки научить данный Toushscreen откликаться и давать нам информацию о наших действиях и координатах. Данная панель является полноправным тачскрином, то есть поддерживается мультитач, отслеживаются действия одновременно пяти пальцев рук. Есть также регистры для хранения событий жестов, из которых почему-то читается постоянно ноль — нет жеста. Возможно, жесты не поддерживаются данным контроллером и регистры туда добавлены из соображений совместимости. Может это, конечно, и не так, но, во всяком случае, мне не удалось данные жесты идентифицировать. Если в последствии всё же как-то жесты откликнутся, то я обязательно этим с вами поделюсь и дам отдельный урок. А пока и без этого с данным устройством предстоит очень много работы, так что наберитесь терпения. Начнём.

Также скажу, что Toushscreen наш является емкостным, что придаёт нашему дисплею удобство в интерактивности.

Так как нам потребуются все функции нашего дисплея, то проект, соответственно, мы сотворим из проекта урока 70 по выводу текста на экран LTDC_TEXT и назовём его TOUCH_FT5336.

Запустим проект в Cube MX и включим в нём шину I2C

 

image00

 

Ножку SCL переопределим на PH7, после этого ножки I2C будут у нас на ножках портов PH7 и PH8

 

image01

 

Сделано это согласно схемы на нашу плату

 

image02

 

Также включим ножку порта PI11 на вход. Это синяя кнопка на плате

 

image05

 

Зайдём в I2C в разделе Configuration и настроим там сразу адрес Slave

 

image03

 

Адрес также указан в схеме

 

image04

 

Двоичное 01110000 равно шестнадцатеричному 70h и десятичному 112. Также всё равно потом в коде мы будем оперировать адресом явно.

Теперь генерируем проект для System WorkBench и открываем его там, перед этим на всякий случай удалив оттуда все проекты. После добавления проекта также удалим из секции Run/Debug Settings настроек все пункты. Откроем файл main.c и попытаемся собрать наш проект.

Также попробуем проект прошить через отладку и запустить его. Если нормально работает старый код на плате, то останавливаем отладку и запустим проект обычным штатным образом через Run.

Теперь начнём сочинять свою библиотеку по работе с тачскрином, соответственно добавив для этой цели новый модуль. Создадим пару файлов ft5336.h и ft5336.c со стандартным содержимым

 

ft5336.h:

 

#ifndef __FT5336_H

#define __FT5336_H

//------------------------------------------

#include "stm32f7xx_hal.h"

#include <string.h>

#include <stdlib.h>

//------------------------------------------

//------------------------------------------

#endif /* __FT5336_H */

 

ft5336.c:

 

#include "ft5336.h"

//----------------------------------------

 

 

В файл ft5336.c подключим библиотеку ltdc и напишем функцию обработки ошибок

 

#include "ft5336.h"

#include "ltdc.h"

//----------------------------------------

void Error(void)

{

  TFT_FillScreen(LCD_COLOR_RED);

}

//----------------------------------------

 

То есть при вызове обраотчика ошибок экран будет светиться красным цветом (это вместо красного светодиода).

Далее добавим функцию инициализации нашего тачскрина

 

//----------------------------------------

void Touch_Ini(void)

{

  uint8_t regValue = 0;

  HAL_Delay(200);

}

//----------------------------------------

 

Создадим на данную функцию прототип, затем подключим нашу библиотеку в файле main.c

 

#include "MT48LC4M32B2.h"

#include "ft5336.h"

/* USER CODE END Includes */

 

Затем вызовем нашу функцию инициализации в main()

 

TFT_FillScreen(LCD_COLOR_BLACK);

Touch_Ini();

if(f_mount(&SDFatFs, (TCHAR const*)SD_Path, 0) != FR_OK)

 

Вернёмся в ft5336.c и добавим указатель на периферию I2C

 

#include "ltdc.h"

//----------------------------------------

extern I2C_HandleTypeDef hi2c3;

//----------------------------------------

 

Немного выше функции инициализации добавим функцию чтения байта из шины I2C

 

//----------------------------------------

uint8_t TS_IO_Read(uint8_t Addr, uint8_t Reg)

{

  uint8_t read_value = 0;

  HAL_I2C_Mem_Read(&hi2c3, Addr, (uint16_t)Reg, I2C_MEMADD_SIZE_8BIT, &read_value, 1, 0x1000);

  return read_value;

}

//----------------------------------------

 

Функция эта простейшая и в объяснении не нуждается.

 

 

Теперь нам потребуются некоторые макросы для удобного обращения к регистрам, адресам, битам нашей микросхемы-драйвера тачскрина. Я уже заранее это всё подготовил, поэтому добавим их сразу все в заголовочный файл  ft5336.h

 

Макросы ft5336.h

#define TS_SWAP_NONE ((uint8_t) 0x01)

#define TS_SWAP_X ((uint8_t) 0x02)

#define TS_SWAP_Y ((uint8_t) 0x04)

#define TS_SWAP_XY ((uint8_t) 0x08)

//------------------------------------------

#define TS_I2C_ADDRESS ((uint16_t)0x70)

#define FT5336_ID_VALUE ((uint8_t)0x51)

#define FT5336_TD_STAT_REG ((uint8_t)0x02)

#define FT5336_GMODE_REG ((uint8_t)0xA4)

#define FT5336_CHIP_ID_REG ((uint8_t)0xA8)

#define FT5336_G_MODE_INTERRUPT_POLLING ((uint8_t)0x00)

#define FT5336_G_MODE_INTERRUPT_MASK ((uint8_t)0x03)

#define FT5336_TD_STAT_MASK ((uint8_t)0x0F)

#define FT5336_G_MODE_INTERRUPT_SHIFT ((uint8_t)0x00)

#define FT5336_GEST_ID_REG ((uint8_t)0x01)

//------------------------------------------

/* Possible values of FT5336_GEST_ID_REG */

#define FT5336_GEST_ID_NO_GESTURE ((uint8_t)0x00)

#define FT5336_GEST_ID_MOVE_UP ((uint8_t)0x10)

#define FT5336_GEST_ID_MOVE_RIGHT ((uint8_t)0x14)

#define FT5336_GEST_ID_MOVE_DOWN ((uint8_t)0x18)

#define FT5336_GEST_ID_MOVE_LEFT ((uint8_t)0x1C)

#define FT5336_GEST_ID_SINGLE_CLICK ((uint8_t)0x20)

#define FT5336_GEST_ID_DOUBLE_CLICK ((uint8_t)0x22)

#define FT5336_GEST_ID_ROTATE_CLOCKWISE ((uint8_t)0x28)

#define FT5336_GEST_ID_ROTATE_C_CLOCKWISE ((uint8_t)0x29)

#define FT5336_GEST_ID_ZOOM_IN ((uint8_t)0x40)

#define FT5336_GEST_ID_ZOOM_OUT ((uint8_t)0x49)

#define FT5336_I2C_NOT_INITIALIZED ((uint8_t)0x00)

#define FT5336_I2C_INITIALIZED ((uint8_t)0x01)

#define FT5336_MAX_DETECTABLE_TOUCH ((uint8_t)0x05)

//------------------------------------------

#define FT5336_TOUCH_POS_MSB_MASK ((uint8_t)0x0F)

#define FT5336_TOUCH_POS_MSB_SHIFT ((uint8_t)0x00)

#define FT5336_TOUCH_POS_LSB_MASK ((uint8_t)0xFF)

#define FT5336_TOUCH_POS_LSB_SHIFT ((uint8_t)0x00)

//------------------------------------------

#define FT5336_P1_XH_REG ((uint8_t)0x03)

#define FT5336_P1_XL_REG ((uint8_t)0x04)

#define FT5336_P1_YH_REG ((uint8_t)0x05)

#define FT5336_P1_YL_REG ((uint8_t)0x06)

#define FT5336_P2_XH_REG ((uint8_t)0x09)

#define FT5336_P2_XL_REG ((uint8_t)0x0A)

#define FT5336_P2_YH_REG ((uint8_t)0x0B)

#define FT5336_P2_YL_REG ((uint8_t)0x0C)

#define FT5336_P3_XH_REG ((uint8_t)0x0F)

#define FT5336_P3_XL_REG ((uint8_t)0x10)

#define FT5336_P3_YH_REG ((uint8_t)0x11)

#define FT5336_P3_YL_REG ((uint8_t)0x12)

#define FT5336_P4_XH_REG ((uint8_t)0x15)

#define FT5336_P4_XL_REG ((uint8_t)0x16)

#define FT5336_P4_YH_REG ((uint8_t)0x17)

#define FT5336_P4_YL_REG ((uint8_t)0x18)

#define FT5336_P5_XH_REG ((uint8_t)0x1B)

#define FT5336_P5_XL_REG ((uint8_t)0x1C)

#define FT5336_P5_YH_REG ((uint8_t)0x1D)

#define FT5336_P5_YL_REG ((uint8_t)0x1E)

#define FT5336_P6_XH_REG ((uint8_t)0x21)

#define FT5336_P6_XL_REG ((uint8_t)0x22)

#define FT5336_P6_YH_REG ((uint8_t)0x23)

#define FT5336_P6_YL_REG ((uint8_t)0x24)

#define FT5336_P7_XH_REG ((uint8_t)0x27)

#define FT5336_P7_XL_REG ((uint8_t)0x28)

#define FT5336_P7_YH_REG ((uint8_t)0x29)

#define FT5336_P7_YL_REG ((uint8_t)0x2A)

#define FT5336_P8_XH_REG ((uint8_t)0x2D)

#define FT5336_P8_XL_REG ((uint8_t)0x2E)

#define FT5336_P8_YH_REG ((uint8_t)0x2F)

#define FT5336_P8_YL_REG ((uint8_t)0x30)

#define FT5336_P9_XH_REG ((uint8_t)0x33)

#define FT5336_P9_XL_REG ((uint8_t)0x34)

#define FT5336_P9_YH_REG ((uint8_t)0x35)

#define FT5336_P9_YL_REG ((uint8_t)0x36)

#define FT5336_P10_XH_REG ((uint8_t)0x39)

#define FT5336_P10_XL_REG ((uint8_t)0x3A)

#define FT5336_P10_YH_REG ((uint8_t)0x3B)

#define FT5336_P10_YL_REG ((uint8_t)0x3C)

//------------------------------------------

#define FT5336_P1_WEIGHT_REG ((uint8_t)0x07)

#define FT5336_P1_MISC_REG ((uint8_t)0x08)

#define FT5336_P2_WEIGHT_REG ((uint8_t)0x0D)

#define FT5336_P2_MISC_REG ((uint8_t)0x0E)

#define FT5336_P3_WEIGHT_REG ((uint8_t)0x13)

#define FT5336_P3_MISC_REG ((uint8_t)0x14)

#define FT5336_P4_WEIGHT_REG ((uint8_t)0x19)

#define FT5336_P4_MISC_REG ((uint8_t)0x1A)

#define FT5336_P5_WEIGHT_REG ((uint8_t)0x1F)

#define FT5336_P5_MISC_REG ((uint8_t)0x20)

#define FT5336_P6_WEIGHT_REG ((uint8_t)0x25)

#define FT5336_P6_MISC_REG ((uint8_t)0x26)

#define FT5336_P7_WEIGHT_REG ((uint8_t)0x2B)

#define FT5336_P7_MISC_REG ((uint8_t)0x2C)

#define FT5336_P8_WEIGHT_REG ((uint8_t)0x31)

#define FT5336_P8_MISC_REG ((uint8_t)0x32)

#define FT5336_P9_WEIGHT_REG ((uint8_t)0x37)

#define FT5336_P9_MISC_REG ((uint8_t)0x38)

#define FT5336_P10_WEIGHT_REG ((uint8_t)0x3D)

#define FT5336_P10_MISC_REG ((uint8_t)0x3E)

//------------------------------------------

#define FT5336_TOUCH_EVT_FLAG_PRESS_DOWN ((uint8_t)0x00)

#define FT5336_TOUCH_EVT_FLAG_LIFT_UP ((uint8_t)0x01)

#define FT5336_TOUCH_EVT_FLAG_CONTACT ((uint8_t)0x02)

#define FT5336_TOUCH_EVT_FLAG_NO_EVENT ((uint8_t)0x03)

//------------------------------------------

#define FT5336_TOUCH_EVT_FLAG_SHIFT ((uint8_t)0x06)

#define FT5336_TOUCH_EVT_FLAG_MASK ((uint8_t)(3 << FT5336_TOUCH_EVT_FLAG_SHIFT))

#define FT5336_TOUCH_WEIGHT_MASK ((uint8_t)0xFF)

#define FT5336_TOUCH_WEIGHT_SHIFT ((uint8_t)0x00)

#define FT5336_TOUCH_AREA_MASK ((uint8_t)(0x04 << 4))

#define FT5336_TOUCH_AREA_SHIFT ((uint8_t)0x04)

//------------------------------------------

#define TS_MAX_NB_TOUCH ((uint32_t) FT5336_MAX_DETECTABLE_TOUCH)

 

Теперь опять вернёмся в ft5336.c и добавим функцию чтения идентификатора микросхемы сразу после функции чтения байта из шины I2C

 

//----------------------------------------

uint16_t Touch_ReadID(uint16_t DeviceAddr)

{

  volatile uint8_t ucReadId = 0;

  uint8_t nbReadAttempts = 0;

  int8_t bFoundDevice = 0;

  for(nbReadAttempts = 0; ((nbReadAttempts < 3) && !(bFoundDevice)); nbReadAttempts++)

  {

    ucReadId = TS_IO_Read(DeviceAddr, FT5336_CHIP_ID_REG);

    if(ucReadId == FT5336_ID_VALUE)

    {

      bFoundDevice = 1;

    }

  }

  return (ucReadId);

}

//----------------------------------------

 

Идентификатор читаем с трёх попыток, а то вдруг сразу не считается.

Теперь вызовем эту функцию в функции инициализации тачскрина

 

  HAL_Delay(200);

  if(Touch_ReadID(TS_I2C_ADDRESS) != FT5336_ID_VALUE) Error();

}

 

Перейдём в файл main.c и в функции main() после вызова функции инициализации тачскрина добавим задержку в 1 секунду для того, чтобы, если будет ошибка и экран засветится красным цветом, мы успели это увидеть

 

Touch_Ini();

HAL_Delay(1000);

 

Также в этой же главной функции, а также в функции копирования файла Bmp в память исправим код закрашивания экрана в красный цвет, чтобы он действительно закрашивался в него

 

TFT_FillScreen(LCD_COLOR_RED); //в случае неудачи окрасим экран в красный цвет

 

Соберём код, прошьём контроллер для того, чтобы проверить, что идентификатор благополучно считан.

Перейдём в заголовочный файл ft5336.h и добавим там структуру

 

#define TS_MAX_NB_TOUCH ((uint32_t) FT5336_MAX_DETECTABLE_TOUCH)

//------------------------------------------

typedef struct

{

  uint8_t i2cInitialized;

  uint8_t currActiveTouchNb;

  uint8_t currActiveTouchIdx;

} ft5336_handle_TypeDef;

//------------------------------------------

void Touch_Ini(void);

 

Вернёмся в файл ft5336.c и добавим две глобальные переменные, одну из которых инициализируем сразу

 

extern I2C_HandleTypeDef hi2c3;

//----------------------------------------

static ft5336_handle_TypeDef ft5336_handle = {FT5336_I2C_NOT_INITIALIZED, 0, 0};

static uint8_t tsOrientation;

//----------------------------------------

 

После функции чтения из шины I2C добавим фукнцию записи в эту шину

 

//----------------------------------------

void TS_IO_Write(uint8_t Addr, uint8_t Reg, uint8_t Value)

{

  HAL_StatusTypeDef status = HAL_OK;

  HAL_I2C_Mem_Write(&hi2c3, Addr, (uint16_t)Reg, I2C_MEMADD_SIZE_8BIT, &Value, 1, 0x1000);

  if(status != HAL_OK) Error();

}

//----------------------------------------

 

Теперь продолжим писать функцию инициализации.

Установим горизонтальную ориентацию

 

  if(Touch_ReadID(TS_I2C_ADDRESS) != FT5336_ID_VALUE) Error();

  tsOrientation = TS_SWAP_XY;

}

 

На этом мы пока на сегодня закончим.

В следующей части занятия мы закончим писать функцию инициализации тачскрина, а также начнём писать код процесса отслеживания различных действий TS.

 

 

Предыдущий урок Программирование МК STM32 Следующая часть

 

 

Техническая документация на драйвер TS FT5336

 

 

Отладочную плату можно приобрести здесь 32F746G-DISCOVERY

 

 

Смотреть ВИДЕОУРОК (нажмите на картинку)

 

STM Touch panel FT5336

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *

*