?? wm.c
字號(hào):
r.x0 = ClipContext.CurRect.x1+1; r.y0 = ClipContext.CurRect.y0; if (r.x0 > ClipContext.ClientRect.x1) {NextStripe: /* go down to next stripe */ r.x0 = ClipContext.ClientRect.x0; r.y0 = ClipContext.CurRect.y1+1; } } /* STEP 2: Check if we are done completely. */ if (r.y0 >ClipContext.ClientRect.y1) return 0; /* STEP 3: Find out the max. height (r.y1) if we are at the left border. Since we are using the same height for all IVRs at the same y0, we do this only for the leftmost one. */ pAWin = WM_H2P(GUI_Context.hAWin); if (r.x0 == ClipContext.ClientRect.x0) { r.y1 = ClipContext.ClientRect.y1; r.x1 = ClipContext.ClientRect.x1; /* Iterate over all windows which are above */ /* Check all siblings above (Iterate over Parents and top siblings (hNext) */ for (hParent = GUI_Context.hAWin; hParent; hParent = pParent->hParent) { pParent = WM_H2P(hParent); for (iWin= pParent->hNext; iWin !=0; iWin = pWin->hNext) { Status = (pWin = WM_H2P(iWin))->Status; /* Check if this window affects us at all */ if ((Status & WM_SF_ISVIS) && (!(Status & WM_SF_HASTRANS)) && GUI_RectsIntersect(&r, &pWin->Rect)) { if (pWin->Rect.y0 > r.y0) { ASSIGN_IF_LESS(r.y1, pWin->Rect.y0-1); /* Check upper border of window */ } else { ASSIGN_IF_LESS(r.y1, pWin->Rect.y1); /* Check lower border of window */ } } } } /* Check all children */ for (iWin= pAWin->hFirstChild; iWin !=0; iWin = pWin->hNext) { Status = (pWin = WM_H2P(iWin))->Status; /* Check if this window affects us at all */ if ((Status & WM_SF_ISVIS) && (!(Status & WM_SF_HASTRANS)) && GUI_RectsIntersect(&r, &pWin->Rect)) { if (pWin->Rect.y0 > r.y0) { ASSIGN_IF_LESS(r.y1, pWin->Rect.y0-1); /* Check upper border of window */ } else { ASSIGN_IF_LESS(r.y1, pWin->Rect.y1); /* Check lower border of window */ } } } } /* STEP 4 Find out x0 for the given y0, y1 by iterating over windows above. if we find one that intersects, adjust x0 to the right. */Find_x0: r.x1 = r.x0; /* Iterate over all windows which are above */ /* Check all siblings above */ for (hParent = GUI_Context.hAWin; hParent; hParent = pParent->hParent) { pParent = WM_H2P(hParent); for (iWin= pParent->hNext; iWin !=0; iWin = pWin->hNext) { Status = (pWin = WM_H2P(iWin))->Status; if ( (Status & WM_SF_ISVIS) && (!(Status & WM_SF_HASTRANS)) && GUI_RectsIntersect(&r, &pWin->Rect)) { /* Check if this window affects us at all */ r.x0 = pWin->Rect.x1+1; goto Find_x0; } } } /* Check all children */ for (iWin= pAWin->hFirstChild; iWin !=0; iWin = pWin->hNext) { Status = (pWin = WM_H2P(iWin))->Status; if ( (Status & WM_SF_ISVIS) && (!(Status & WM_SF_HASTRANS)) && GUI_RectsIntersect(&r, &pWin->Rect)) { /* Check if this window affects us at all */ r.x0 = pWin->Rect.x1+1; goto Find_x0; } } /* STEP 5: If r.x0 out of right border, this stripe is done. Set next stripe and goto STEP 2 Find out x1 for the given x0, y0, y1 */ r.x1 = ClipContext.ClientRect.x1; if (r.x1 < r.x0) {/* horizontal border reached ? */ ClipContext.CurRect = r; goto NextStripe; } /* STEP 6: Find r.x1. We have to Iterate over all windows which are above */ /* Check all siblings above (Iterate over Parents and top siblings (hNext) */ for (hParent = GUI_Context.hAWin; hParent; hParent = pParent->hParent) { pParent = WM_H2P(hParent); for (iWin= pParent->hNext; iWin !=0; iWin = pWin->hNext) { Status = (pWin = WM_H2P(iWin))->Status; if ( (Status & WM_SF_ISVIS) && (!(Status & WM_SF_HASTRANS)) && GUI_RectsIntersect(&r, &pWin->Rect)) { /* Check if this window affects us at all */ r.x1 = pWin->Rect.x0-1; } } } /* Check all children */ for (iWin= pAWin->hFirstChild; iWin !=0; iWin = pWin->hNext) { Status = (pWin = WM_H2P(iWin))->Status; if ( (Status & WM_SF_ISVIS) && (!(Status & WM_SF_HASTRANS)) && GUI_RectsIntersect(&r, &pWin->Rect)) { /* Check if this window affects us at all */ r.x1 = pWin->Rect.x0-1; } } /* We are done. Return the rectangle we found in the ClipContext. */ if (ClipContext.Cnt >200) { return 0; /* error !!! This should not happen !*/ } ClipContext.CurRect = r; return 1; /* IVR is valid ! */}#elsestatic int FindNext_IVR(void) { if (ClipContext.Cnt ==0) { ClipContext.CurRect = GUI_Context.pAWin->Rect; return 1; /* IVR is valid ! */ } return 0; /* Nothing left to draw */}#endif/*********************************************************************** Get next IVR Sets the next clipping rectangle. If a valid one has been found (and set), 1 is returned in order to indicate that the drawing operation needs to be executed. Returning 0 signals that we have iterated over all rectangles. Returns: 0 if no valid rectangle is found 1 if rectangle has been found*/int WM__GetNextIVR (void) { #if GUI_SUPPORT_CURSOR static char _CursorHidden; #endif /* If WM is not active, we have no rectangles to return */ if (WM_IsActive==0) return 0; if (ClipContext.EntranceCnt > 1) { ClipContext.EntranceCnt--; return 0; } #if GUI_SUPPORT_CURSOR if (_CursorHidden) { _CursorHidden = 0; (*GUI_CURSOR_pfTempUnhide) ( &ClipContext.CurRect); } #endif ++ClipContext.Cnt; /* Find next rectangle and use it as ClipRect */ if (!FindNext_IVR()) { ClipContext.EntranceCnt--; /* This search is over ! */ return 0; /* Could not find an other one ! */ } /* Hide cursor if necessary */ LCD_SetClipRectEx(&ClipContext.CurRect); #if GUI_SUPPORT_CURSOR if (GUI_CURSOR_pfTempHide) { _CursorHidden = 1; (*GUI_CURSOR_pfTempHide) ( &ClipContext.CurRect); } #endif return 1;}/*********************************************************************** Init IVR search This routine is called from the clipping level (the WM_ITERATE_START macro) when starting an iteration over the visible rectangles. Return value: 0 : There is no valid rectangle (nothing to do ...) 1 : There is a valid rectangle*/int WM__InitIVRSearch(const GUI_RECT* pMaxRect) { GUI_RECT r; WM_Obj* pAWin; /* If WM is not active -> nothing to do, leave cliprect alone */ if (WM_IsActive==0) return 1; /* If we entered multiple times, leave Cliprect alone */ if (++ClipContext.EntranceCnt > 1) return 1; pAWin = WM_H2P(GUI_Context.hAWin); ClipContext.Cnt = -1; /* When using callback mechanism, it is legal to reduce drawing area to the invalid area ! */ if (IsInCallback) { WM__GetInvalidRectAbs(pAWin, &r); } else { /* Not using callback mechanism, therefor allow entire rectangle */ if (pAWin->Status & WM_SF_ISVIS) { r = pAWin->Rect; } else { --ClipContext.EntranceCnt; return 0; /* window is not even visible ! */ } } /* If the drawing routine has specified a rectangle, use it to reduce the rectangle */ if (pMaxRect) { GUI__IntersectRect(&r, pMaxRect); } /* If user has reduced the cliprect size, reduce the rectangle */ if (GUI_Context.WM__pUserClipRect) { GUI_RECT rUser = *(GUI_Context.WM__pUserClipRect); WM__Client2Screen(pAWin, &rUser); GUI__IntersectRect(&r, &rUser); } /* Iterate over all ancestors and clip at their borders */ _ClipAtParentBorders(&r, pAWin); /* Store the rectangle and find the first rectangle of the area */ ClipContext.ClientRect = r; return WM__GetNextIVR();}/* ******************************************** * * * Set default * * * ******************************************** This routine sets the defaults for WM and the layers below. It is used before a drawing routine is called in order to make sure that defaults are set (in case the default settings had been altered before by the application)*/void WM_SetDefault(void) { GL_SetDefault(); GUI_Context.WM__pUserClipRect = NULL; /* No add. clipping */}/* ******************************************** * * Callback for Paint message * ******************************************** This callback is used by the window manger in conjunction with banding memory devices. A pointer to this routine is given to the banding memory device. This callback in turn will send the paint message to the window.*/#if GUI_SUPPORT_MEMDEVstatic void cbPaint(void* pMsg) { WM_SendMessage(((WM_MESSAGE*)pMsg)->hWin, (WM_MESSAGE*) pMsg);}#endif/* ******************************************** * * * Draw next window * * * *********************************************/static void _DrawNext(void) { int UpdateRem = 1; WM_HWIN iWin = (NextDrawWin == WM_HWIN_NULL) ? WM__FirstWin : NextDrawWin; GUI_CONTEXT ContextOld; GUI_SaveContext(&ContextOld); /* Make sure the next window to redraw is valid */ for (; (iWin!=WM_HWIN_NULL) && UpdateRem; ) { WM_Obj* pWin = WM_H2P(iWin); if (pWin->Status & WM_SF_INVALID) { U8 Status = (pWin->Status &= ~WM_SF_INVALID); /* Clear invalid flag */ WM__NumInvalidWindows--; /* Send WM_PAINT if window is visible and a callback is defined */ if ((pWin->cb != NULL) && (Status & WM_SF_ISVIS)) { WM_MESSAGE Msg; Msg.hWin = iWin; Msg.MsgId = WM_PAINT; Msg.Data.p = (GUI_RECT*)&pWin->InvalidRect; WM_SelectWindow(iWin); WM_SetDefault(); #if GUI_SUPPORT_MEMDEV if (Status & WM_SF_MEMDEV) { GUI_RECT r = pWin->InvalidRect; GUI_MoveRect (&r, pWin->Rect.x0, pWin->Rect.y0); GUI_MEMDEV_Draw(&r, cbPaint, &Msg, 0, (Status & WM_SF_HASTRANS) ? GUI_MEMDEV_HASTRANS : 0); } else #endif WM_SendMessage(iWin, &Msg); UpdateRem--; /* Only the given number of windows at a time ... */ } } iWin = pWin->hNextLin; } NextDrawWin = iWin; /* Remember the window */ GUI_RestoreContext(&ContextOld);}/* ***************************************************************** * * * Idle loop * * * ******************************************************************/int WM_Exec1(void) { if (WM_pfHandleHID) { if (WM_pfHandleHID()) return 1; /* We have done something ... */ } if (GUI_PollKeyMsg()) { return 1; /* We have done something ... */ } if (WM_IsActive && WM__NumInvalidWindows) { WM_LOCK(); _DrawNext(); WM_UNLOCK(); return 1; /* We have done something ... */ } return 0; /* There was nothing to do ... */}int WM_Exec(void) { int r = 0; while (WM_Exec1()) { r = 1; /* We have done something */ } return r;}/***************************************************************** ** Callback for background window ** *******************************************************************/static WM_RESULT cbBackWin( WM_MESSAGE* pMsg) { WM_KEY_INFO* pKeyInfo; switch (pMsg->MsgId) { case WM_KEY: pKeyInfo = (WM_KEY_INFO*)pMsg->Data.p; if (pKeyInfo->PressedCnt == 0) { GUI_StoreKey(pKeyInfo->Key); } break; case WM_PAINT: if (WM__BkColor != GUI_INVALID_COLOR) { GUI_SetBkColor(WM__BkColor); GUI_Clear(); } default: WM_DefaultProc(pMsg); }}/****************************************************************** WM_Activate / WM_Deactivate*******************************************************************/void WM_Activate(void) { WM_IsActive = 1; /* Running */}void WM_Deactivate(void) { WM_IsActive = 0; /* No clipping performed by WM */ WM__SetMaxClipRect(WM_H2P(WM_HBKWIN));}/* ***************************************************************** * * * WM_Init * * * ******************************************************************/void WM_Init(void) { if (!_IsInited) { WM_HWIN hWin; NextDrawWin = WM__FirstWin = WM_HWIN_NULL; GUI_Context.WM__pUserClipRect = NULL; WM__NumWindows = WM__NumInvalidWindows =0; /* Make sure we have at least one window. This greatly simplifies the drawing routines as they do not have to check if the window is valid. */ hWin = WM_CreateWindow(0, 0, GUI_XMAX, GUI_YMAX, WM_CF_SHOW, cbBackWin, 0); WM_SelectWindow(hWin); WM_Activate(); _IsInited =1; }}/* ****************************************************** * * * Default procedure * * * *******************************************************/WM_RESULT WM_DefaultProc(WM_MESSAGE* pMsg) { WM_HWIN hWin = pMsg->hWin; void *p = pMsg->Data.p; WM_Obj* pWin = WM_H2P(hWin); /* Exec message */ switch (pMsg->MsgId) { case WM_GETORG: ((GUI_POINT*)p)->x = pWin->Rect.x0; ((GUI_POINT*)p)->y = pWin->Rect.y0; break; case WM_GETCLIENTRECT: /* return client window in window coordinates */ WM__GetClientRectWin(pWin, (GUI_RECT*)p); break; case WM_GETCLIENTRECT_ABS: /* return client window in absolute (screen) coordinates */ WM__GetClientRectWin(pWin, (GUI_RECT*)p); GUI_MoveRect((GUI_RECT*)p, pWin->Rect.x0, pWin->Rect.y0); break; case WM_GET_CLIENT_WINDOW: /* return handle to client window. For most windows, there is no seperate client window, so it is the same handle */ pMsg->Data.v = hWin; return; /* Message handled */ case WM_KEY: WM_SendToParent(hWin, pMsg); return; /* Message handled */ case WM_GET_BKCOLOR: pMsg->Data.Color = GUI_INVALID_COLOR; return; /* Message handled */ } /* Message not handled. If it queries something, we return 0 to be on the safe side. */ pMsg->Data.v = 0; pMsg->Data.p = 0;}#elsevoid WM(void) {} /* avoid empty object files */#endif /* WM_MAX_WINDOW */
?? 快捷鍵說(shuō)明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -