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

📄 desktop.c

📁 这是一个介绍 linux 编程知识的文章。
💻 C
📖 第 1 页 / 共 5 页
字号:
        pWin->dwStyle |= WS_VISIBLE;

        SendAsyncMessage ((HWND)pWin, MSG_NCPAINT, 0, 0);
    
        InvalidateRect ((HWND)pWin, NULL, TRUE);
    }
    else {
        SendAsyncMessage ((HWND)pWin, MSG_NCPAINT, 0, 0);

        if (pWin->dwExStyle & WS_EX_TOPMOST)
            dskUpdateGCRInfoOnChangeTopMostEx (pWin);
        else
            dskUpdateGCRInfoOnChangeTopMost (pWin);

        // then update Z Order.
        if (pWin->dwExStyle & WS_EX_TOPMOST) {
            pNode = TopMostWinZOrder.pTopMost;
            if (pNode->hWnd != (HWND)pWin) {
                while(pNode->pNext)
                {
                    if( pNode->pNext->hWnd == (HWND)pWin )
                    {
                       pTemp = pNode->pNext;
                       pNode->pNext = pNode->pNext->pNext;

                       pTemp->pNext = TopMostWinZOrder.pTopMost;
                       TopMostWinZOrder.pTopMost = pTemp;

                       break;
                    }
                    pNode = pNode->pNext;
                }
            }
        }
        else {
            pNode = MainWinZOrder.pTopMost;
            if (pNode->hWnd != (HWND)pWin) {
                while (pNode->pNext)
                {
                    if (pNode->pNext->hWnd == (HWND)pWin)
                    {
                       pTemp = pNode->pNext;
                       pNode->pNext = pNode->pNext->pNext;
    
                       pTemp->pNext = MainWinZOrder.pTopMost;
                       MainWinZOrder.pTopMost = pTemp;

                       break;
                    }
                    pNode = pNode->pNext;
                }
            }
        }
    }
    
    return dskChangActiveWindow (pWin);
}

// When hide a main win, all main win which is covered by
// this hidding main win will be regenerated.
//
// Functions which lead to call this function:
//  ShowWindow: hide a visible window with SW_HIDE parameters.
//  DestroyWindow: destroy a visible window.
//
static void dskUpdateGCRInfoOnHideMainWin(MAINWIN* pWin)
{
    PZORDERNODE pNode, pAffected;
    PGCRINFO pGCRInfo;
    RECT     rcWin, rcTemp;
    PMAINWIN pTemp;
    
    // where is the hidding main window?
    pNode = MainWinZOrder.pTopMost;
    while (pNode)
    {
        if (pNode->hWnd == (HWND)pWin)
            break;
        pNode = pNode->pNext;
    }
    
    // update this main window's status.
    pWin->dwStyle &= ~WS_VISIBLE;

    // this main window's rect.
    memcpy (&rcWin, &pWin->left, sizeof(RECT));

    // the first affected main window
    pAffected = pNode->pNext;
    while (pAffected){
        pTemp = (PMAINWIN)(pAffected->hWnd);

        if (pTemp->dwStyle & WS_VISIBLE) {

            pGCRInfo = &pTemp->GCRInfo;
            pthread_mutex_lock (&pGCRInfo->lock);
            IntersectRect (&rcTemp, (PRECT)(&pTemp->left), &sg_rcScr);
            SetClipRgn (&pGCRInfo->crgn, &rcTemp);

            // clip by all top most windows.
            pNode = TopMostWinZOrder.pTopMost;
            while (pNode) {

                pTemp = (PMAINWIN)(pNode->hWnd);
                if (pTemp->dwStyle & WS_VISIBLE)
                    SubtractClipRect (&pGCRInfo->crgn, (PRECT)(&pTemp->left));

                pNode = pNode->pNext;
            }
           
            pNode = MainWinZOrder.pTopMost;
            while (pNode != pAffected) {

                pTemp = (PMAINWIN)(pNode->hWnd);
                if (pTemp->dwStyle & WS_VISIBLE)
                    SubtractClipRect (&pGCRInfo->crgn, (PRECT)(&pTemp->left));

                pNode = pNode->pNext;
            }
            pGCRInfo->age ++;
            pthread_mutex_unlock (&pGCRInfo->lock);

            pTemp = (PMAINWIN)(pAffected->hWnd);

            IntersectRect (&rcTemp, &rcWin, &rcTemp);
            SendAsyncMessage ((HWND)pTemp,
                MSG_NCPAINT, 0, 0);

            rcTemp.left -= pTemp->cl;
            rcTemp.top -= pTemp->ct;
            rcTemp.right -= pTemp->cl;
            rcTemp.bottom -= pTemp->ct;
            InvalidateRect ((HWND)pTemp, &rcTemp, TRUE);
        }

           pAffected = pAffected->pNext;
    }

    // update desktop's global clip region.
    pthread_mutex_lock (&sg_ScrGCRInfo.lock);
    SetClipRgn (&sg_ScrGCRInfo.crgn, &sg_rcScr);
    
    pNode = TopMostWinZOrder.pTopMost;
    while (pNode) {
    
        pTemp = (PMAINWIN)(pNode->hWnd);
        if (pTemp->dwStyle & WS_VISIBLE)
            SubtractClipRect (&sg_ScrGCRInfo.crgn, (PRECT)(&pTemp->left));

        pNode = pNode->pNext;
    }
    
    pNode = MainWinZOrder.pTopMost;
    while (pNode) {
    
        pTemp = (PMAINWIN)(pNode->hWnd);
        if (pTemp->dwStyle & WS_VISIBLE)
            SubtractClipRect (&sg_ScrGCRInfo.crgn, (PRECT)(&pTemp->left));

        pNode = pNode->pNext;
    }

    sg_ScrGCRInfo.age ++;
    pthread_mutex_unlock (&sg_ScrGCRInfo.lock);

    // Erase invalid rect.
    IntersectRect (&rcTemp, &rcWin, &sg_rcScr);
    DesktopProc (HWND_DESKTOP, MSG_ERASEDESKTOP, 0, (LPARAM)(&rcTemp));
}

// this is a top most window
static void dskUpdateGCRInfoOnHideMainWinEx(MAINWIN* pWin)
{
    PZORDERNODE pNode, pAffected;
    PGCRINFO pGCRInfo;
    RECT     rcWin, rcTemp;
    PMAINWIN pTemp;
    
    // where is the hidding main window?
    pNode = TopMostWinZOrder.pTopMost;
    while (pNode)
    {
        if (pNode->hWnd == (HWND)pWin)
            break;
        pNode = pNode->pNext;
    }
    
    // update this main window's status.
    pWin->dwStyle &= ~WS_VISIBLE;

    // this main window's rect.
    memcpy (&rcWin, &pWin->left, sizeof(RECT));

    // the first affected main window
    pAffected = pNode->pNext;
    while (pAffected){
        pTemp = (PMAINWIN)(pAffected->hWnd);

        if (pTemp->dwStyle & WS_VISIBLE) {

            pGCRInfo = &pTemp->GCRInfo;
            pthread_mutex_lock (&pGCRInfo->lock);
            IntersectRect (&rcTemp, (PRECT)(&pTemp->left), &sg_rcScr);
            SetClipRgn (&pGCRInfo->crgn, &rcTemp);

            pNode = TopMostWinZOrder.pTopMost;
            while (pNode != pAffected) {

                pTemp = (PMAINWIN)(pNode->hWnd);
                if (pTemp->dwStyle & WS_VISIBLE)
                    SubtractClipRect (&pGCRInfo->crgn, (PRECT)(&pTemp->left));

                pNode = pNode->pNext;
            }
            pGCRInfo->age ++;
            pthread_mutex_unlock (&pGCRInfo->lock);

            pTemp = (PMAINWIN)(pAffected->hWnd);

            IntersectRect (&rcTemp, &rcWin, &rcTemp);
            SendAsyncMessage ((HWND)pTemp,
                MSG_NCPAINT, 0, 0);

            rcTemp.left -= pTemp->cl;
            rcTemp.top -= pTemp->ct;
            rcTemp.right -= pTemp->cl;
            rcTemp.bottom -= pTemp->ct;
            InvalidateRect ((HWND)pTemp, &rcTemp, TRUE);
        }

           pAffected = pAffected->pNext;
    }

    // update all main windows global clip region.
    // the first affected main window
    pAffected = MainWinZOrder.pTopMost;
    while (pAffected){
        pTemp = (PMAINWIN)(pAffected->hWnd);

        if (pTemp->dwStyle & WS_VISIBLE) {

            pGCRInfo = &pTemp->GCRInfo;
            pthread_mutex_lock (&pGCRInfo->lock);
            IntersectRect (&rcTemp, (PRECT)(&pTemp->left), &sg_rcScr);
            SetClipRgn (&pGCRInfo->crgn, &rcTemp);

            // clip by all top most windows.
            pNode = TopMostWinZOrder.pTopMost;
            while (pNode) {

                pTemp = (PMAINWIN)(pNode->hWnd);
                if (pTemp->dwStyle & WS_VISIBLE)
                    SubtractClipRect (&pGCRInfo->crgn, (PRECT)(&pTemp->left));

                pNode = pNode->pNext;
            }
           
            pNode = MainWinZOrder.pTopMost;
            while (pNode != pAffected) {

                pTemp = (PMAINWIN)(pNode->hWnd);
                if (pTemp->dwStyle & WS_VISIBLE)
                    SubtractClipRect (&pGCRInfo->crgn, (PRECT)(&pTemp->left));

                pNode = pNode->pNext;
            }
            pGCRInfo->age ++;
            pthread_mutex_unlock (&pGCRInfo->lock);

            pTemp = (PMAINWIN)(pAffected->hWnd);

            IntersectRect (&rcTemp, &rcWin, &rcTemp);
            SendAsyncMessage ((HWND)pTemp,
                MSG_NCPAINT, 0, 0);

            rcTemp.left -= pTemp->cl;
            rcTemp.top -= pTemp->ct;
            rcTemp.right -= pTemp->cl;
            rcTemp.bottom -= pTemp->ct;
            InvalidateRect ((HWND)pTemp, &rcTemp, TRUE);
        }

           pAffected = pAffected->pNext;
    }

    // update desktop's global clip region.
    pthread_mutex_lock (&sg_ScrGCRInfo.lock);
    SetClipRgn (&sg_ScrGCRInfo.crgn, &sg_rcScr);
    
    pNode = TopMostWinZOrder.pTopMost;
    while (pNode) {
    
        pTemp = (PMAINWIN)(pNode->hWnd);
        if (pTemp->dwStyle & WS_VISIBLE)
            SubtractClipRect (&sg_ScrGCRInfo.crgn, (PRECT)(&pTemp->left));

        pNode = pNode->pNext;
    }
    
    pNode = MainWinZOrder.pTopMost;
    while (pNode) {
    
        pTemp = (PMAINWIN)(pNode->hWnd);

        if (pTemp->dwStyle & WS_VISIBLE)
            SubtractClipRect (&sg_ScrGCRInfo.crgn, (PRECT)(&pTemp->left));

        pNode = pNode->pNext;
    }
    sg_ScrGCRInfo.age ++;
    pthread_mutex_unlock (&sg_ScrGCRInfo.lock);

    // Erase invalid rect.
    IntersectRect (&rcTemp, &rcWin, &sg_rcScr);
    DesktopProc (HWND_DESKTOP, MSG_ERASEDESKTOP, 0, (LPARAM)(&rcTemp));
}

static PMAINWIN dskGetFirstVisibleWindow ()
{
    PZORDERNODE pNode;
    PMAINWIN pTemp;

    pNode = MainWinZOrder.pTopMost;
    while (pNode) {
    
        pTemp = (PMAINWIN)(pNode->hWnd);

        if (pTemp->dwStyle & WS_VISIBLE)
            return pTemp;

        pNode = pNode->pNext;
    }
    
    pNode = TopMostWinZOrder.pTopMost;
    while (pNode) {
    
        pTemp = (PMAINWIN)(pNode->hWnd);

        if (pTemp->dwStyle & WS_VISIBLE)
            return pTemp;

        pNode = pNode->pNext;
    }

    return NULL;
    
}

static PMAINWIN dskGetNextVisibleWindow (PMAINWIN pWin)
{
    PZORDERNODE pNode;
    PMAINWIN pTemp;

    if (pWin)
        pNode = pWin->pZOrderNode->pNext;
    else
        pNode = MainWinZOrder.pTopMost;

    while (pNode) {

        pTemp = (PMAINWIN)(pNode->hWnd);

        if (pTemp->dwStyle & WS_VISIBLE && !(pTemp->dwStyle & WS_DISABLED))
            return pTemp;

        pNode = pNode->pNext;
    }
    
    return NULL;
}

static PMAINWIN dskHideMainWindow(PMAINWIN pWin)
{
    if (!(pWin->dwStyle & WS_VISIBLE))
        return NULL;

    // Update all affected windows' GCR info.
    if (pWin->dwExStyle & WS_EX_TOPMOST)
        dskUpdateGCRInfoOnHideMainWinEx (pWin);
    else
        dskUpdateGCRInfoOnHideMainWin (pWin);

    // if this is the avtive window,
    // must choose another window as the active one. 
    if (pActiveMainWnd == pWin)
        dskChangActiveWindow (dskGetFirstVisibleWindow ());

    return pActiveMainWnd;
}

// When destroy a main win, all main win which is covered by
// this destroying main win will be redraw.
//
// Functions which lead to call this function:
//  DestroyWindow: destroy a visible window.
//
// return: the new active window.
static PMAINWIN dskRemoveMainWindow(PMAINWIN pWin)
{
    PZORDERNODE pNode, pTemp;

    // Handle main window hosting.
    if (pWin->pHosting)
        dskRemoveHostedMainWindow (pWin->pHosting, pWin);
        
    // Update all affected windows' GCR info.
    if (pWin->dwStyle & WS_VISIBLE) {
        if (pWin->dwExStyle & WS_EX_TOPMOST)
            dskUpdateGCRInfoOnHideMainWinEx (pWin);
        else
            dskUpdateGCRInfoOnHideMainWin (pWin);

        if (pActiveMainWnd == pWin)
            dskChangActiveWindow (dskGetFirstVisibleWindow ());

        if (pActiveMainWnd == pWin)
            pActiveMainWnd = NULL;
    }

    // Update window Z order list.

    if (pWin->dwExStyle & WS_EX_TOPMOST) {
        pNode = TopMostWinZOrder.pTopMost;
        if (pNode->hWnd == (HWND)pWin) {
            TopMostWinZOrder.pTopMost = pNode->pNext;
            free (pNode);
        }
        else {
            while (pNode->pNext) {
                if (pNode->pNext->hWnd == (HWND)pWin) {
                   pTemp = pNode->pNext->pNext;
                   free (pNode->pNext);
                   pNode->pNext = pTemp;
           
                   break;
                }
                pNode = pNode->pNext;
            }
        }
        TopMostWinZOrder.nNumber--;
    }
    else {
        pNode = MainWinZOrder.pTopMost;
        if (pNode->hWnd == (HWND)pWin) {
            MainWinZOrder.pTopMost = pNode->pNext;

⌨️ 快捷键说明

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