機(jī)電之家資源網(wǎng)
單片機(jī)首頁|單片機(jī)基礎(chǔ)|單片機(jī)應(yīng)用|單片機(jī)開發(fā)|單片機(jī)文案|軟件資料下載|音響制作|電路圖下載 |嵌入式開發(fā)
培訓(xùn)信息
贊助商
ucos II+ucGUI+s3c2410+LCD+觸摸屏整合
ucos II+ucGUI+s3c2410+LCD+觸摸屏整合
 更新時(shí)間:2008-8-18 14:57:54  點(diǎn)擊數(shù):240
【字體: 字體顏色
; Pt[i]=(0x3ff&rADCDAT0);
        }
        Pt[5]=(Pt[0]+Pt[1]+Pt[2]+Pt[3]+Pt[4])/5;//多次采樣取平均值
        TX = Pt[5];
        rADCTSC=(0<<8)|(0<<7)|(1<<6)|(1<<5)|(0<<4)|(1<<3)|(0<<2)|(2);
        for(i=0;i<LOOP;i++);            //delay to set up the next channel
        for(i=0;i<5;i++)                           //5 times
        {
            rADCCON|=0x1;               // Start Y-position conversion
            while(rADCCON & 0x1);       // Check if Enable_start is low
            while(!(0x8000&rADCCON));   // Check ECFLG
            Pt[i]=(0x3ff&rADCDAT1);
        }
        Pt[5]=(Pt[0]+Pt[1]+Pt[2]+Pt[3]+Pt[4])/5;// 多次采樣取平均值
 
        TY = Pt[5];
               rADCTSC=(1<<8)|(1<<7)|(1<<6)|(0<<5)|(1<<4)|(0<<3)|(0<<2)|(3);
}
    //cprintf("%d,%d\n",TX,TY);
       OSMboxPost(TouchMbox, 0);//向處理觸摸進(jìn)程發(fā)消息
    rSUBSRCPND |= BIT_SUB_TC;
    rINTSUBMSK &= ~(BIT_SUB_TC);         // Unmask sub interrupt (TC)    
    ClearPending(BIT_ADC);    
}
3) 需要的量:
#define LOOP 1
#define ADCPRS 0x27
int TX=0;//觸摸坐標(biāo)x
int TY=0;//觸摸坐標(biāo)y
extern OS_EVENT *TouchMbox;
int isDown;
 
4) 觸摸屏校準(zhǔn):
Ucgui390中,帶有一校準(zhǔn)程序(于TOUCH_Calibrate.c中),可以改寫為我所用(見下文)。
也可設(shè)置默認(rèn)值,測(cè)出左下最小坐標(biāo)minX,minY和右上最大坐標(biāo)maxX,maxY,注意是觸摸坐標(biāo),不是lcd坐標(biāo),如下填寫配置文件GUITouchConf.h:
#define GUI_TOUCH_AD_LEFT   minX
#define GUI_TOUCH_AD_TOP    maxY
#define GUI_TOUCH_AD_RIGHT maxX
#define GUI_TOUCH_AD_BOTTOM minY  
#define GUI_TOUCH_SWAP_XY   0
 #define GUI_TOUCH_MIRROR_X   1
#define GUI_TOUCH_MIRROR_Y 1
#define TOUCH_NEED_CALIBRATE 0
 
3、如下填寫GUIConf.h
       #define GUI_OS                    (1) /* Compile with multitasking support */
#define GUI_SUPPORT_TOUCH         (1) /* Support a touch screen (req. win-manager) */
#define GUI_SUPPORT_UNICODE       (1) /* Support mixed ASCII/UNICODE strings */
#define GUI_SUPPORT_CHINESE              (1)
#define GUI_DEFAULT_FONT          &GUI_Font6x8
#define GUI_ALLOC_SIZE            12500 /* Size of dynamic memory ... For WM and memory devices*/
#define GUI_WINSUPPORT            1 /* Window manager package available */
#define GUI_SUPPORT_MEMDEV        1 /* Memory devices available */
#define GUI_SUPPORT_AA            1 /* Anti aliasing available */
 
4、ucgui與lcd驅(qū)動(dòng)函數(shù)的連接,即修改LCDWin.c文件:
       在LCDWin.c中,去掉無用的頭文件包含。
#define SETPIXEL(x, y, c)   LCD2410_SetPixel(x, y, c, LCD_DISPLAY_INDEX)
#define GETPIXEL(x, y)    LCD2410_GetPixel(x,y, LCD_DISPLAY_INDEX)
即將“LCDSIM_XX”改成“LCD2410_XX”,這兩個(gè)函數(shù)位于lcd驅(qū)動(dòng)文件中。
       ……………………………
 #define SETPIXEL(x, y, c) \
    if (!_CheckBound(c)) { \
      LCD2410_SetPixel(x, y, c, LCD_DISPLAY_INDEX); \
    }
#else
 #define SETPIXEL(x, y, c) LCD2410_SetPixel(x, y, c, LCD_DISPLAY_INDEX)
#endif
#define GETPIXEL(x, y)    LCD2410_GetPixel(x,y,LCD_DISPLAY_INDEX)
……………………………
static void _XorPixel(int x, int y) {
 unsigned int Index = LCD_L0_GetPixelIndex(x,y);
  LCD2410_SetPixel(x, y, LCD_NUM_COLORS-1-Index, LCD_DISPLAY_INDEX);
}
……………………………
int LCD_L0_Init(void) {
    return LCD2410_Init();//調(diào)用lcd初始化函數(shù)
}
 
5、某些編譯器(如:ads1.2)不會(huì)初始化全局變量,因此做如下事:
1) 修改如下函數(shù)為:(位于GUICore.c
static void _InitContext(GUI_CONTEXT* pContext) {
   
    memset(pContext,0,sizeof(GUI_CONTEXT));//add
   
 #if GUI_SUPPORT_MEMDEV
    GUI_SelectLCD();
 #else
    LCD_SetClipRectMax();//LCD_L0_GetRect
 #endif
     pContext->pLCD_HL      = &LCD_HL_APIList;
     pContext->pAFont       = GUI_DEFAULT_FONT;
       pContext->pClipRect_HL = &GUI_Context.ClipRect;
     pContext->PenSize      = 1;
      pContext->DrawMode = GUI_DRAWMODE_NORMAL;//add
     pContext->TextMode = GUI_TEXTMODE_NORMAL;//add
     pContext->TextAlign = GUI_TA_LEFT|GUI_TA_TOP;//add
    pContext->AA_HiResEnable = 0;//add

    /* Variables in WM module */
       #if GUI_WINSUPPORT
           pContext->hAWin    = WM_GetDesktopWindow();
     #endif
     /* Variables in GUI_AA module */
     pContext->AA_Factor = 3;
     LCD_SetBkColor(GUI_DEFAULT_BKCOLOR);
     LCD_SetColor(GUI_DEFAULT_COLOR);
}
 
修改如下函數(shù)為:(位于GUIAlloc.c
void GUI_ALLOC_Init(void) {
........
     GUI_ALLOC.NumUsedBytes = 0;
   memset(&aBlock,0,sizeof(aBlock[0])*GUI_MAXBLOCKS);/////self
    aBlock[0].Size = (1<<GUI_BLOCK_ALIGN); /* occupy minimum for a block */
.......
}
 
 
修改如下函數(shù)為:(位于WM.c)(――――――――――New)
void WM_Init(void) {
       if (!_IsInited) {
       ……….
       memset(&_ClipContext,0,sizeof(WM_IVR_CONTEXT));//add
       NextDrawWin = WM__FirstWin = WM_HWIN_NULL;
        ……………….
    _IsInited =1;
       }
}
2)自己編寫如下函數(shù)(ads1.2):
void MyInit()
{
       IsInitialized = 0;//MemDev
     _IsInited = 0;//Win
     WM__CreateFlags = 0;
   GUI_CURSOR_pfTempHide = NULL;
 GUI_Context.hDevData = 0;
   WM__hCapture=0;
 WM__hWinFocus=0;
   WM_pfPollPID = 0;
 WM_pfHandlePID = 0;
   GUI_pfTimerExec = 0;
   _KeyMsgCnt = 0;
}
該函數(shù)應(yīng)在GUI_Init()調(diào)用之前調(diào)用。
 
6、改寫GUI_Init()函數(shù):
int GUI_Init(void) {
 int r;
 GUI_DEBUG_LOG("\nGUI_Init()");
 /* Init system wide globals first */
 GUI_DecChar = '.';
 
 /* Init context */
 _InitContext(&GUI_Context);
 GUITASK_INIT();
 r = LCD_Init();
 #if GUI_WINSUPPORT
    WM_Init();
 #endif
 GUITASK_COPY_CONTEXT();
 GUI_Clear();
  GUI_X_Init();
 GUI_CURSOR_Show();//啟動(dòng)即顯示鼠標(biāo)

 return r;
}
 
三、ucGUI與ucOS的整合,主要修改GUI_X.c文件:
       1、定義信號(hào)量及全局量:
              static OS_EVENT *DispSem;
static OS_EVENT *EventMbox;
static OS_EVENT *KeySem;
static int        KeyPressed;
static char       KeyIsInited;
       2、實(shí)現(xiàn)結(jié)合函數(shù):
              int GUI_X_GetTime(void)
{
 return ((int)OSTimeGet());
}
void GUI_X_Delay(int period)
{
    INT32U ticks;
    ticks = (period * 1000) / OS_TICKS_PER_SEC;
    OSTimeDly((INT16U)ticks);
}
void GUI_X_Unlock(void)
{
    OSSemPost(DispSem);
}
void GUI_X_Lock(void)
{
     U8 err;
     OSSemPend(DispSem, 0, &err);
}
U32 GUI_X_GetTaskId(void)
{
  return ((U32)(OSTCBCur->OSTCBPrio));
}
void GUI_X_WaitEvent (void)
{
    INT8U err;
    (void)OSMboxPend(EventMbox, 0, &err);
}
void GUI_X_SignalEvent (void)
{
    (void)OSMboxPost(EventMbox, (void *)1);
}
void GUI_X_InitOS(void)
{
    DispSem   = OSSemCreate(1);
    EventMbox = OSMboxCreate((void *)0);
}
void GUI_X_ExecIdle(void) {GUI_X_Delay(1);}
 
void GUI_X_Init(void) {
    SetTSInterrupt();//此處接入觸摸屏的中斷設(shè)置
    GUI_TOUCH_SetDefaultCalibration();//用默認(rèn)值校準(zhǔn)觸摸屏
}

 
四、與觸摸屏有關(guān)的函數(shù):
1、4個(gè)功能函數(shù):
void GUI_TOUCH_X_ActivateX(void) {//空}  
void GUI_TOUCH_X_ActivateY(void) {//空}
int GUI_TOUCH_X_MeasureX(void) {
    return TX;//返回觸摸坐標(biāo)x
}  
int  GUI_TOUCH_X_MeasureY(void){
    return TY; //返回觸摸坐標(biāo)y
}
 
2、觸摸屏校準(zhǔn)任務(wù)(進(jìn)程, 來自示例程序:TOUCH_Calibrate.c):
#if TOUCH_NEED_CALIBRATE
static const char * _acPos[] = {
 "(upper left position)",
 "(lower right position)"
};
static void _WaitForPressedState(int Pressed) {
 GUI_PID_STATE State;
 /* Wait until touch is pressed */
 do {
    GUI_TOUCH_GetState(&State);
    if (State.Pressed == Pressed) {
      break;
    }
    GUI_Delay (100);
 } while (1);
}
static void _DispStringCentered(const char * pString) {
 GUI_RECT Rect;
 Rect.x0 = Rect.y0 = 0;
 Rect.x1 = LCD_GetXSize() - 1;
 Rect.y1 = LCD_GetYSize() - 1;
 GUI_DispStringInRect(pString, &Rect, GUI_TA_HCENTER | GUI_TA_VCENTER);
}
static void _GetPhysValues(int LogX, int LogY, int * pPhysX, int * pPhysY, const char * pString) {
 char acText[] = "Press here";
 GUI_RECT Rect;
 int FontSizeY, Align;
 FontSizeY = GUI_GetFontSizeY();
 GUI_Clear();
 GUI_SetColor(GUI_BLACK);
 _DispStringCentered("Runtime calibration,\n"
                      "please touch the screen\n"
                      "at the center of the ring."); /* Ask user to press the touch */
 /* Calculate the rectangle for the string */
 Rect.y0 = LogY - FontSizeY;
 Rect.y1 = LogY + FontSizeY;
 if (LogX < LCD_GetXSize() / 2) {
    Rect.x0 = LogX + 15;
    Rect.x1 = LCD_GetXSize();
    Align = GUI_TA_LEFT;
 } else {
    Rect.x0 = 0;
   Rect.x1 = LogX - 15;
    Align = GUI_TA_RIGHT;
 }
 /* Show the text nearby the ring */
 GUI_DispStringInRect(acText, &Rect, Align | GUI_TA_TOP);
 GUI_DispStringInRect(pString, &Rect, Align | GUI_TA_BOTTOM);
 /* Draw the ring */
 GUI_FillCircle(LogX, LogY, 10);
 GUI_SetColor(GUI_WHITE);
 GUI_FillCircle(LogX, LogY, 5);
 GUI_SetColor(GUI_BLACK);
 /* Wait until touch is pressed */
 _WaitForPressedState(1);
 *pPhysX = GUI_TOUCH_GetxPhys();
 *pPhysY = GUI_TOUCH_GetyPhys();
 /* Wait until touch is released */
 _WaitForPressedState(0);
}
 
static void _Explain(void) {
 _DispStringCentered("This sample shows how\n"
                      "a touch screen can be\n"
                      "calibrated at run time.\n"
                      "Please press the touch\n"
                      "screen to continue...");
 GUI_DispStringHCenterAt("TOUCH_Calibrate", LCD_GetXSize() / 2, 5);
 _WaitForPressedState(1);
 _WaitForPressedState(0);
}
 
void CalibrateTask(void* pdata) {//觸摸屏校準(zhǔn)任務(wù)入口
 int aPhysX[2], aPhysY[2], aLogX[2], aLogY[2], i;
 GUI_SetBkColor(GUI_WHITE);
 GUI_Clear();
 GUI_SetColor(GUI_BLACK);
 GUI_SetFont(&GUI_Font13B_ASCII);
 _Explain();
 /* Set the logical values */
 aLogX[0] = 15;
 aLogY[0] = 15;
 aLogX[1] = LCD_GetXSize() - 20;
 aLogY[1] = LCD_GetYSize() - 20;
 /* Get the physical values of the AD converter for 2 positions */
 for (i = 0; i < 2; i++) {
    _GetPhysValues(aLogX[i], aLogY[i], &aPhysX[i], &aPhysY[i], _acPos[i]);
 }
 /* Use the physical values to calibrate the touch screen */
 GUI_TOUCH_Calibrate(0, aLogX[0], aLogX[1], aPhysX[0], aPhysX[1]); /* Calibrate X-axis */
 GUI_TOUCH_Calibrate(1, aLogY[0], aLogY[1], aPhysY[0], aPhysY[1]); /* Calibrate Y-axis */
 
 { /* calculate and display values for configuration file */
    int calX0, calX1;
    int calY0, calY1;
    GUI_Clear();
   
    GUI_TOUCH_GetCalData(GUI_COORD_X, &calX0, &calX1);
    GUI_TOUCH_GetCalData(GUI_COORD_Y, &calY0, &calY1);
   
    GUI_DispStringAt("calX0: ", 0, 0); GUI_DispDec(calX0, 4); GUI_DispNextLine();
    GUI_DispString ("calX1: ");       GUI_DispDec(calX1, 4); GUI_DispNextLine();
    GUI_DispString ("calY0: ");       GUI_DispDec(calY0, 4); GUI_DispNextLine();
    GUI_DispString ("calY1: ");       GUI_DispDec(calY1, 4);
     
    GUI_DispStringAt("lcdx0: ", 0, 200); GUI_DispDec(aLogX[0], 4); GUI_DispNextLine();
    GUI_DispString ("lcdx1: ");       GUI_DispDec(aLogX[1], 4); GUI_DispNextLine();
    GUI_DispString ("lcdy0: ");       GUI_DispDec(aLogY[0], 4); GUI_DispNextLine();
    GUI_DispString ("lcdy1: ");       GUI_DispDec(aLogY[1], 4); GUI_DispNextLine();
   
    GUI_DispString ("tscX0: ");       GUI_DispDec(aPhysX[0], 4); GUI_DispNextLine();
    GUI_DispString ("tscX1: ");       GUI_DispDec(aPhysX[1], 4); GUI_DispNextLine();
    GUI_DispString ("tscY0: ");       GUI_DispDec(aPhysY[0], 4); GUI_DispNextLine();
    GUI_DispString ("tscY1: ");       GUI_DispDec(aPhysY[1], 4); GUI_DispNextLine();
   
    GUI_DispString ("Please touch display to continue...");
    GUI_Delay(1000);
   
    _WaitForPressedState(1);
    _WaitForPressedState(0);
 }
 GUI_Clear();     
 SystemOn();
 OSTaskSuspend(OS_PRIO_SELF);
 
}
3、為了響應(yīng)觸摸屏,做如下事
       1)創(chuàng)建進(jìn)程處理觸摸事件,形式如下:
              void TouchTask(void* data) {
              INT8U err;
              while(1)
              {
                     CONSOL_Printf("Waiting for Touch......\n");
OSMboxPend(TouchMbox, 0, &err); /* Acquire semaphore to perform random numbers */
                     CONSOL_Printf("Got a message\n");
                     GUI_TOUCH_Exec();//
                     }
}
2) 如下修改函數(shù) GUI_TOUCH_Exec():
void GUI_TOUCH_Exec(void) {
 #ifndef WIN32
 static U8 ReadState;
 int x,y;
 /* calculate Min / Max values */
 if (xyMinMax[GUI_COORD_X].Min < xyMinMax[GUI_COORD_X].Max) {
    xMin = xyMinMax[GUI_COORD_X].Min;
    xMax = xyMinMax[GUI_COORD_X].Max;
 } else {
    xMax = xyMinMax[GUI_COORD_X].Min;
    xMin = xyMinMax[GUI_COORD_X].Max;
 }
 if (xyMinMax[GUI_COORD_Y].Min < xyMinMax[GUI_COORD_Y].Max) {
    yMin = xyMinMax[GUI_COORD_Y].Min;
    yMax = xyMinMax[GUI_COORD_Y].Max;
 } else {
    yMax = xyMinMax[GUI_COORD_Y].Min;
    yMin = xyMinMax[GUI_COORD_Y].Max;
 }
  /* Execute the state machine which reads the touch */
 //switch (ReadState) {
 //case 0:
    yPhys = TOUCH_X_MeasureY();
   // TOUCH_X_ActivateY(); /* Prepare X- measurement */
 // ReadState++;
 // break;
 //default:

    xPhys = TOUCH_X_MeasureX();
  // TOUCH_X_ActivateX(); /* Prepare Y- measurement */
    /* Convert values into logical values */
      #if !GUI_TOUCH_SWAP_XY   /* Is X/Y swapped ? */
        x = xPhys;
        y = yPhys;
      #else
        x = yPhys;
        y = xPhys;
      #endif
 
    if ((x <xMin) | (x>xMax) | (y <yMin) | (y>yMax)) {
      GUI_TOUCH_StoreUnstable(-1,-1);
    } else {
      x = AD2X(x);
      y = AD2Y(y);
      GUI_TOUCH_StoreUnstable(x,y);
    }
    /* Reset state machine */
    //ReadState=0;
  // break;
 //}

 #endif /* WIN32 */
}
 
五、     GUI多任務(wù)測(cè)試:
測(cè)試程序:MT_MultiTasking.c

歡迎來信交流:hongyhm@hotmail.com

<!--自定義字段-->
  • 上一篇: 基于ARM920T的IDE硬盤接口設(shè)計(jì)
  • 下一篇: uCOS II就緒表(Ready List)分析
  • 發(fā)表評(píng)論   告訴好友   打印此文  收藏此頁  關(guān)閉窗口  返回頂部
    熱點(diǎn)文章
     
    推薦文章
     
    相關(guān)文章
    網(wǎng)友評(píng)論:(只顯示最新5條。)
    關(guān)于我們 | 聯(lián)系我們 | 廣告合作 | 付款方式 | 使用幫助 | 機(jī)電之家 | 會(huì)員助手 | 免費(fèi)鏈接

    點(diǎn)擊這里給我發(fā)消息66821730(技術(shù)支持)點(diǎn)擊這里給我發(fā)消息66821730(廣告投放) 點(diǎn)擊這里給我發(fā)消息41031197(編輯) 點(diǎn)擊這里給我發(fā)消息58733127(審核)
    本站提供的機(jī)電設(shè)備,機(jī)電供求等信息由機(jī)電企業(yè)自行提供,該企業(yè)負(fù)責(zé)信息內(nèi)容的真實(shí)性、準(zhǔn)確性和合法性。
    機(jī)電之家對(duì)此不承擔(dān)任何保證責(zé)任,有侵犯您利益的地方請(qǐng)聯(lián)系機(jī)電之家,機(jī)電之家將及時(shí)作出處理。
    Copyright 2007 機(jī)電之家 Inc All Rights Reserved.機(jī)電之家-由機(jī)電一體化網(wǎng)更名-聲明
    電話:0571-87774297 傳真:0571-87774298
    杭州濱興科技有限公司提供技術(shù)支持

    主辦:杭州市高新區(qū)(濱江)機(jī)電一體化學(xué)會(huì)
    中國(guó)行業(yè)電子商務(wù)100強(qiáng)網(wǎng)站

    網(wǎng)站經(jīng)營(yíng)許可證:浙B2-20080178-1