⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lhtouch.cpp

📁 完整的触摸屏驱动源程序
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/*--------------------------------------------------------------------------*/
// touch.cpp
//
//      Touch Driver for Sharp LH79524 using on-board ADC controller.
//  
// Author: Kenneth G. Maxwell
//
// Notes:
//
// This driver runs in Polled mode. The high-level application software
// must do these things to use this touch driver:
//
// 1) Instantiate TouchDevice instance.
// 2) Call TouchDevice::Calibrate to calibrate the touch screen.
// 3) Periodically call TouchDevice::Poll to poll for touch input changes.
//
//
//  Example:
//
//      #include "touch.hpp"
//
//      void main(int argc, char **argv)
//      {
//          TouchDevice *pTouch = new TouchDevice();
//          pTouch->Calibrate();
//
//          while(1)
//          {
//              pTouch->Poll();
//          }
//      }
//
//
//
/*--------------------------------------------------------------------------*/

#include "peg.hpp"
#include "touch.hpp"
#include "lh795_8.hpp"      // for register addresses

/*--------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------*/
TouchDevice::TouchDevice()
{
    PEGINT iLoop;
    PEGULONG lVal;
    PEGULONG *pReg;
    ADC_REGS *pADC = (ADC_REGS *) ADC_REG_BASE;

    // program GPIO pins as analog input pins:

    pReg = (PEGULONG *) (IOCON_REG_BASE + 0xc0);    // mux ctrl 25
    *pReg = 0;

    // unlock clock control:
    pReg = (PEGULONG *) RCPC_REG_BASE;
    lVal = *pReg;
    lVal |= 0x200;  // set bit 9 to unlock
    *pReg = lVal;

    pReg = (PEGULONG *) (RCPC_REG_BASE + 0x48); // adc clock divisor
    *pReg = 0x10;   // div by 32. With 192 MHz HCLK, this is
                    // a 6 MHz ADC clock

    pReg = (PEGULONG *) (RCPC_REG_BASE + 0x28); // peripheral clock 1
    lVal = *pReg;
    lVal &= ~0x04;   // enable ADC clock
    *pReg = lVal;    


    // program all writable ADC registers to zero:

    pADC->IntClear = 0x03;
    pADC->IntClear = 0;
    pADC->IntMask = 0;
    pADC->PowerConfig = 0;
    pADC->GeneralConfig = 0;

    for (iLoop = 0; iLoop < 16; iLoop++)
    {
        pADC->HiWordBank[iLoop] = 0;
        pADC->LoWordBank[iLoop] = 0;
    }
    pADC->IdleHiWord = 0;
    pADC->IdleLoWord = 0;

    // Read FIFO until empty:

    while((pADC->FifoStatus & 0x04) == 0)
    {
        lVal = pADC->Results;
    }

    pReg = (PEGULONG *) INT_ENABLE_CLEAR; // IntEnableClear
    *pReg = 0x10000;        // set bit 16

    // setup ADC Regs

    pADC->IntMask = 0;  // Polled Mode
    pADC->PowerConfig = (ADC_CLOCK_SEL << 8) | 0x6b;
    pADC->GeneralConfig = 0x02;     // SSB starts conversions

    pADC->HiWordBank[0] = ADC_SETTLE_TIME;
    pADC->HiWordBank[1] = ADC_SETTLE_TIME;
    pADC->HiWordBank[2] = ADC_SETTLE_TIME | 0x11;
    pADC->HiWordBank[3] = ADC_SETTLE_TIME | 0x11;
    pADC->HiWordBank[4] = ADC_SETTLE_TIME | 0x11;
    pADC->HiWordBank[5] = ADC_SETTLE_TIME | 0x11;
    pADC->HiWordBank[6] = ADC_SETTLE_TIME | 0x02;
    pADC->HiWordBank[7] = ADC_SETTLE_TIME | 0x02;
    pADC->HiWordBank[8] = ADC_SETTLE_TIME | 0x02;
    pADC->HiWordBank[9] = ADC_SETTLE_TIME | 0x02;
    pADC->HiWordBank[10] = ADC_SETTLE_TIME;
    pADC->HiWordBank[11] = ADC_SETTLE_TIME;

    pADC->LoWordBank[0] =  0x0004;        
    pADC->LoWordBank[1] =  0x1080;        
    pADC->LoWordBank[2] =  0x0015;        
    pADC->LoWordBank[3] =  0x0015;        
    pADC->LoWordBank[4] =  0x0015;        
    pADC->LoWordBank[5] =  0x0015;        
    pADC->LoWordBank[6] =  0x00a2;        
    pADC->LoWordBank[7] =  0x00a2;        
    pADC->LoWordBank[8] =  0x00a2;        
    pADC->LoWordBank[9] =  0x00a2;        
    pADC->LoWordBank[10] = 0x0004;        
    pADC->LoWordBank[11] = 0x1080;        

    mDummy = 0;
    mLastTouched = 0;
    mLastPos.x = mLastPos.y = 0;
    TouchCal.CenterX = TouchCal.CenterY = 0;
    TouchCal.IsCalibrated = FALSE;
    TouchCal.SwapAxis = FALSE;
}

/*--------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------*/
// Scan
//
// Called during calibration or normal operation to do one polled read.
//
// Return:
//
// Boolean touched or not
// If touched, passes back raw x and rawy values.
/*--------------------------------------------------------------------------*/
PEGBOOL TouchDevice::Scan(PEGINT *pRawX, PEGINT *pRawY)
{
    ADC_REGS *pADC = (ADC_REGS *) ADC_REG_BASE;
    PEGULONG lVal;
    PEGINT loop;
    PEGBOOL Touched = FALSE;

    PEGINT xVal;
    PEGINT yVal;

    pADC->IntClear = 0x01;  // write EOSINTC bit

    Sleep(100);
    pADC->GeneralConfig = 0x06;     // trigger conversion

    // poll end-of-sequence interrupt status:

    while((pADC->IntStatus & 0x04) == 0)
    {
        mDummy++;
    }

    lVal = pADC->Results;   // pre-bias
    lVal = pADC->Results >> 6;   // touch detect

    if (lVal > TOUCH_DETECT_VAL)
    {
        for (loop = 0; loop < 10; loop++)
        {
            lVal = pADC->Results;
        }
        Touched = FALSE;
    }
    else
    {
        xVal =  pADC->Results >> 6;
        xVal += pADC->Results >> 6;
        xVal += pADC->Results >> 6;
        xVal += pADC->Results >> 6;
        xVal /= 4;

        yVal = pADC->Results >> 6;
        yVal += pADC->Results >> 6;
        yVal += pADC->Results >> 6;
        yVal += pADC->Results >> 6;
        yVal /= 4;

        lVal = pADC->Results;   // pre-bias
        lVal = pADC->Results >> 6;   // touch detect

        if (lVal > TOUCH_DETECT_VAL)
        {
            Touched = FALSE;
        }
        else
        {
            if (TouchCal.SwapAxis)
            {
                *pRawX = yVal;
                *pRawY = xVal;
            }
            else
            {
                *pRawX = xVal;
                *pRawY = yVal;
            }

            Touched = TRUE;
        }
    }
    return Touched;
}


/*--------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------*/
PEGBOOL TouchDevice::Poll(void)
{
    PegMessage TouchMessage;
    PEGBOOL ReturnVal = FALSE;
    PEGINT  RawX;
    PEGINT  RawY;
    PegPoint CurPos;

    PEGBOOL Touched = Scan(&RawX, &RawY);
    
    if (Touched)                // am I touched now?
    {
        CurPos = ScaleRawVals(RawX, RawY);
        
        if (mLastTouched)       // was I touched last time?
        {
            if (CurPos.x != mLastPos.x ||
                CurPos.y != mLastPos.y)
            {
                // position changed, report new position:

                TouchMessage.pTarget = TouchMessage.pSource = NULL;
                TouchMessage.wType = PM_POINTER_MOVE;
                TouchMessage.Point = CurPos;
                PegThing::MessageQueue()->Push(TouchMessage);
                ReturnVal = TRUE;
            }
        }
        else
        {
            // here for new touch

            TouchMessage.pTarget = TouchMessage.pSource = NULL;
            TouchMessage.wType = PM_LBUTTONDOWN;
            TouchMessage.Point = CurPos;
            PegThing::MessageQueue()->Push(TouchMessage);
            ReturnVal = TRUE;
        }
        mLastPos = CurPos;
    }
    else
    {
        if (mLastTouched)
        {
            // here for LBUTTONUP:
            TouchMessage.pTarget = TouchMessage.pSource = NULL;
            TouchMessage.wType = PM_LBUTTONUP;
            TouchMessage.Point = mLastPos;
            PegThing::MessageQueue()->Push(TouchMessage);
            ReturnVal = TRUE;
        }
    }
    mLastTouched = Touched;
    return ReturnVal;
}

/*--------------------------------------------------------------------------*/
void TouchDevice::Sleep(PEGINT Time)
{
    PEGINT iLoop;

    while(Time >= 0)
    {
        for (iLoop = 0; iLoop < 100; iLoop++)
        {
            mDummy++;
        }
        Time--;
    }
}

/*--------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------*/
PegPoint TouchDevice::ScaleRawVals(PEGINT RawX, PEGINT RawY)
{
    PegPoint Pos;

    Pos.x = (RawX - TouchCal.xRawMin) * 

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -