# Touch Sensor FSM
The ESP32 touch sensor provides a convenient way to detect touch events. However, in environments with strong interference, the hardware judgment logic may fail. This component uses software solutions to provide a more flexible and reliable solution in such environments.
This component provides a finite state machine (FSM) for managing touch sensor data and states. It includes functions for creating, deleting, updating, and controlling the FSM, as well as handling events.
## Application Drivers Depends on this FSM
- [touch_proximity_sensor](https://components.espressif.com/components/espressif/touch_proximity_sensor)
- [touch_button_sensor](https://components.espressif.com/components/espressif/touch_button_sensor)
## Configuration
The FSM is configured using the `fsm_config_t` structure. Here are the key configuration parameters:
```c
typedef struct {
fsm_mode_t mode; // Touch sensor mode (polling or user push)
uint32_t channel_num; // Number of touch channels
uint32_t *channel_list; // List of touch channels
float smooth_coef; // Smoothing coefficient
float baseline_coef; // Baseline coefficient
float max_p; // Maximum effective positive change rate
float min_n; // Minimum effective negative change rate
float *threshold_p; // Positive threshold array
float *threshold_n; // Negative threshold array (optional)
float hysteresis_p; // Hysteresis for positive threshold
float noise_p; // Positive noise threshold
float noise_n; // Negative noise threshold
uint32_t debounce_p; // Debounce times for positive threshold
uint32_t debounce_n; // Debounce times for negative threshold
uint32_t reset_p; // Baseline reset positive threshold
uint32_t reset_n; // Baseline reset negative threshold
uint32_t raw_buf_size; // Size of raw data buffer
uint32_t polling_interval; // Polling interval in ms (for polling mode)
uint32_t *gold_value; // Gold values for baseline reset (optional)
uint32_t scale_factor; // Scale factor for calculations
fsm_state_cb_t state_cb; // State change callback
fsm_touch_polling_cb_t polling_cb; // Polling callback (for polling mode)
void *user_data; // User data passed to callbacks
} fsm_config_t;
```
Default configuration can be initialized using:
```c
fsm_config_t config = DEFAULTS_TOUCH_SENSOR_FSM_CONFIG();
```
## States
The FSM has three possible states:
```c
typedef enum {
FSM_STATE_INACTIVE = 0, // Touch sensor is inactive
FSM_STATE_ACTIVE, // Touch sensor is active
FSM_STATE_DEBOUNCE, // Touch sensor is in debounce state
} fsm_state_t;
```
## Data Types
When getting data from the FSM, three types of data are available:
```c
typedef enum {
FSM_DATA_RAW = 0, // Raw touch sensor data
FSM_DATA_SMOOTH, // Smoothed touch sensor data
FSM_DATA_BASELINE, // Baseline touch sensor data
FSM_DATA_MAX,
} fsm_data_t;
```
## Working Modes
### Polling Mode (`FSM_MODE_POLLING`)
In this mode, the FSM automatically polls touch sensor data using the registered callback function. The polling interval is configurable.
Example:
```c
void polling_callback(fsm_handle_t handle, uint32_t channel, uint32_t *raw_data, void *user_data) {
// Get raw data from touch sensor hardware
*raw_data = touch_pad_get_raw_data(channel);
}
fsm_config_t config = DEFAULTS_TOUCH_SENSOR_FSM_CONFIG();
config.mode = FSM_MODE_POLLING;
config.polling_cb = polling_callback;
config.polling_interval = 20; // 20ms polling interval
```
### User Push Mode (`FSM_MODE_USER_PUSH`)
In this mode, the application is responsible for pushing new touch sensor data to the FSM.
Example:
```c
fsm_config_t config = DEFAULTS_TOUCH_SENSOR_FSM_CONFIG();
config.mode = FSM_MODE_USER_PUSH;
// Later in your code:
uint32_t raw_data = touch_pad_get_raw_data(channel);
touch_sensor_fsm_update_data(handle, channel, raw_data, false);
```
## API Usage Examples
### Creating and Starting the FSM
```c
// Initialize configuration
fsm_config_t config = DEFAULTS_TOUCH_SENSOR_FSM_CONFIG();
config.channel_num = 1;
config.channel_list = (uint32_t[]){0};
config.threshold_p = (float[]){0.1};
// Create FSM
fsm_handle_t handle;
ESP_ERROR_CHECK(touch_sensor_fsm_create(&config, &handle));
// Start FSM
ESP_ERROR_CHECK(touch_sensor_fsm_control(handle, FSM_CTRL_START, NULL));
```
### Handling Events
```c
void touch_task(void *arg) {
fsm_handle_t handle = (fsm_handle_t)arg;
while (1) {
esp_err_t ret = touch_sensor_fsm_handle_events(handle);
if (ret != ESP_OK) {
break;
}
vTaskDelay(pdMS_TO_TICKS(20));
}
}
```
### Getting Data and State
```c
// Get processed data
uint32_t data[FSM_DATA_MAX];
ESP_ERROR_CHECK(touch_sensor_fsm_get_data(handle, channel, data));
printf("Raw: %lu, Smooth: %lu, Baseline: %lu\n",
data[FSM_DATA_RAW],
data[FSM_DATA_SMOOTH],
data[FSM_DATA_BASELINE]);
// Get current state
fsm_state_t state;
ESP_ERROR_CHECK(touch_sensor_fsm_get_state(handle, channel, &state));
printf("State: %d\n", state);
```
### Cleanup
```c
ESP_ERROR_CHECK(touch_sensor_fsm_control(handle, FSM_CTRL_STOP, NULL));
ESP_ERROR_CHECK(touch_sensor_fsm_delete(handle));
```
idf.py add-dependency "espressif/touch_sensor_fsm^0.5.0"