This is a simple library for the STMPE610 touchscreen controller used by the Adafruit 2.8" TFT LCD shield

Dependents:   EasyCAT_LAB

SPI_STMPE610.cpp

Committer:
EasyCAT
Date:
2021-05-26
Revision:
0:b5211f22867b

File content as of revision 0:b5211f22867b:

//********************************************************************************************    
//                                                                                           *
// This software is distributed as an example, "AS IS", in the hope that it could            *
// be useful, WITHOUT ANY WARRANTY of any kind, express or implied, included, but            *
// not limited,  to the warranties of merchantability, fitness for a particular              *
// purpose, and non infringiment. In no event shall the authors be liable for any            *    
// claim, damages or other liability, arising from, or in connection with this software.     *
//                                                                                           *
//********************************************************************************************/ 

#include "SPI_STMPE610.h"


#define REG_SYS_CTRL1       0x03    // reset control

#define REG_SYS_CTRL2       0x04    // clock control 

#define REG_SPI_CFG         0x08    // SPI interface configuration

#define REG_CFG             0x41    // touchscreen controller configuration
                                    //
#define CFG_1SAMPLE         0x00    //
#define CFG_2SAMPLE         0x40    //
#define CFG_4SAMPLE         0x80    //
#define CFG_8SAMPLE         0xC0    //
                                    //
#define CFG_DELAY_10US      0x00    //
#define CFG_DELAY_50US      0x08    //
#define CFG_DELAY_100US     0x10    //
#define CFG_DELAY_500US     0x18    //
#define CFG_DELAY_1MS       0x20    //
#define CFG_DELAY_5MS       0x28    //
#define CFG_DELAY_10MS      0x30    //
#define CFG_DELAY_50MS      0x38    //
                                    //
#define CFG_SETTLE_10US     0x00    //
#define CFG_SETTLE_100US    0x01    //
#define CFG_SETTLE_500US    0x02    //
#define CFG_SETTLE_1MS      0x03    //
#define CFG_SETTLE_5MS      0x04    //
#define CFG_SETTLE_10MS     0x05    //
#define CFG_SETTLE_50MS     0x06    //
#define CFG_SETTLE_100MS    0x07    //

#define REG_CTRL            0x40    // touchscreen controller control
                                    //
#define CTRL_EN             0x01    //
#define CTRL_XY             0x02    //

#define REG_FIFO_SIZE       0x4C    // FIFO size 

#define REG_FIFO_STA        0x4B    // FIFO control/status

#define REG_DATA_X          0x4D    // X point value
#define REG_DATA_Y          0x4F    // Y point value

                                    

#define X_OFFSET    180
#define X_GAIN      0.090

#define Y_OFFSET    207
#define Y_GAIN      0.066


SPI_STMPE610::SPI_STMPE610(PinName mosi, PinName miso, PinName sclk, PinName cs) :
                           m_spi(mosi, miso, sclk), m_cs(cs, 1) 
{

    m_spi.frequency(1000000) ;                      // SPI mode 0 - 8 bit - 1MHz
    m_spi.format(8, 0);                             //

    Write8(REG_SYS_CTRL1, 0x02) ;                   // soft reset
    #if (MBED_MAJOR_VERSION != 2)                   //
        ThisThread::sleep_for(10ms);                //
    #else                                           //
        wait_ms(10);                                //
    #endif                                          //
 
    Write8(REG_SYS_CTRL2, 0x00) ;                   // turn on clocks
    
    Write8(REG_SPI_CFG, 0x04);                      // autoincrement on
    
                                                    // touchscreen parameters
    Write8(REG_CFG, CFG_8SAMPLE | CFG_DELAY_1MS | CFG_SETTLE_5MS ) ;
        
    Write8(REG_CTRL, CTRL_XY | CTRL_EN);            // enable the touchscreen
                                                    // we don't use pressure reporting        
}


                                            //--- write an 8 bits register -----
                                            //
void SPI_STMPE610::Write8(uint8_t Addr, uint8_t Data)
{
    m_cs = 0;
    m_spi.write(0x7F & Addr);
    m_spi.write(Data);    
    m_cs = 1;
}


                                            //--- read an 8 bits register ------ 
                                            //
uint8_t SPI_STMPE610::Read8(uint8_t Addr)
{
    uint8_t Data;
    
    m_cs = 0;
    m_spi.write(0x80 | Addr);
    Data = m_spi.write(0x00);    
    m_cs = 1;   

    return(Data);
}

                                            //--- read a 16 bits register ------ 
                                            //
uint16_t SPI_STMPE610::Read16(uint8_t Addr)
{
    uint16_t Data;
    
    m_cs = 0;
    m_spi.write(0x80 | Addr);
    Data = m_spi.write(0x80); 
    Data = (Data << 8) & 0xFF00;   
    Data |= m_spi.write(0x00);     
    m_cs = 1;   

    return(Data);    
}


                                            //--- get a raw point -------------- 
                                            //
bool SPI_STMPE610::GetRawPoint(uint16_t *X, uint16_t *Y)
{                                                
    if(Read8(REG_FIFO_SIZE))                // if some data is available in the fifo 
    {                                    
        *Y = Read16(REG_DATA_X);            // read X value
        *X = Read16(REG_DATA_Y);            // read Y value
                                            // X and Y are exchanged because the display is horizontal
                                          
        Write8(REG_FIFO_STA, 0x01);         // reset the fifo
        Write8(REG_FIFO_STA, 0x00);         //  "       "
                                          
        //printf("X raw %d\n", *X);           
        //printf("Y raw %d\n\n", *Y);       
                                         
        return true;                        // exit with a valid point
    }  
     
    else                                   
    {                                       
        return false;                       // exit with no valid point
    }                                       
}


                                            //--- get a normalized point ------- 
                                            //
bool SPI_STMPE610::GetPoint(uint16_t *X, uint16_t *Y)
{
    uint16_t RawX, RawY;
    
    if(GetRawPoint (&RawX, &RawY))          // if a point is available
    {                    
        RawX = RawX - X_OFFSET;             // remove the offset 
        if ((int16_t)RawX < 0)              //
            RawX = 0;                       //
                                            //
        RawY = RawY - Y_OFFSET;             //
        if ((int16_t)RawY < 0)              //
            RawY = 0;                       //                           
     
        *X = X_GAIN * (float)RawX;          // apply the gain factor
        *Y = Y_GAIN * (float)RawY;          //
        
        *Y = 240 - *Y;                      // we want the 0,0 point in the upper left corner
        if ((int16_t)*Y < 0)                // so Y must be inverted
            *Y = 0;                         //
        
        //printf("X %d\n", *X);
        //printf("Y %d\n\n", *Y);  
                      
        return true;                        // exit with a valid point
    }
        
    else
    {
        return false;                       // exit with no valid point
    }           
}