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

📄 clv_listview.c

📁 VC++视频开发实例集锦(包括“远程视频监控”"语音识别系统"等13个经典例子)
💻 C
📖 第 1 页 / 共 5 页
字号:
    // No (horiz) scrollbar needed?
    if(pListData->m_iXScrollExtent <= iListRectWidth)
    {
        pListData->m_rList.bottom = pListData->m_rClient.bottom;
        if(pListData->m_bScrollBarVisible_Horiz == TRUE)
            CLV_InvalidateWindow(pListData);
        pListData->m_bScrollBarVisible_Horiz = FALSE;
        pListData->m_iXOrigin = 0;
        SetRect(&pListData->m_rScrollbar_Horiz, 0, 0, 0, 0);
    }
    else
    {
        int iTrackWidth;
        int iTrackThumbWidth;
        int iTrackThumbPos;
        int iTrackThumbWidth_Min;
        int iTrackThumbWidth_Max;

        pListData->m_rList.bottom = pListData->m_rClient.bottom - glb_pSkin->mpl_pHScrollBar_TrackUp->m_szSize.cy;

        // The presence of this scrollbar may require a vertical scrollbar - take this into account
        if(bCountedVScrollbar == FALSE)
        {
            iListRectHeight_Lines = CLV_GetListRect_Lines(pListData);
            if(iListRectHeight_Lines < pListData->m_iNumItems)
            {
                bCountedVScrollbar = TRUE;
                pListData->m_rList.right = pListData->m_rClient.right - glb_pSkin->mpl_pVScrollBar_TrackUp->m_szSize.cx;
                iListRectWidth -= glb_pSkin->mpl_pVScrollBar_TrackUp->m_szSize.cx;
            }
        }

        // Work out size of scroll track
        iTrackWidth = iListRectWidth - (glb_pSkin->mpl_pHScrollBar_Left->m_pImage->m_szSize.cx
                                        + glb_pSkin->mpl_pHScrollBar_Right->m_pImage->m_szSize.cx);

        // Setup scrollbar
        if(pListData->m_bScrollBarVisible_Horiz == FALSE)
            CLV_InvalidateWindow(pListData);
        pListData->m_bScrollBarVisible_Horiz = TRUE;
        pListData->m_rScrollbar_Horiz = pListData->m_rList;
        pListData->m_rScrollbar_Horiz.top = pListData->m_rList.bottom;
        pListData->m_rScrollbar_Horiz.bottom = pListData->m_rClient.bottom;

        // Limit scroll to fit into window
        if( (pListData->m_iXOrigin + iListRectWidth) > pListData->m_iXScrollExtent)
            pListData->m_iXOrigin = pListData->m_iXScrollExtent - iListRectWidth;

        // Setup track rect
        iTrackThumbWidth = (int)( (( (float)iListRectWidth / (float)pListData->m_iXScrollExtent ) * (float)iTrackWidth));
        iTrackThumbWidth_Min = glb_pSkin->mpl_rHScrollBar_Track_Tile.left
                               + (glb_pSkin->mpl_pHScrollBar_TrackUp->m_szSize.cx - glb_pSkin->mpl_rHScrollBar_Track_Tile.right);
        iTrackThumbWidth_Max = (pListData->m_rScrollbar_Horiz.right - pListData->m_rScrollbar_Horiz.left);
        if(iTrackThumbWidth < iTrackThumbWidth_Min)
            iTrackThumbWidth = iTrackThumbWidth_Min;
        if(iTrackThumbWidth > iTrackThumbWidth_Max)
            iTrackThumbWidth = iTrackThumbWidth_Max;
        pListData->m_rScrollbar_Horiz_Thumb = pListData->m_rScrollbar_Horiz;
        iTrackThumbPos = (int)( (  ((float)pListData->m_iXOrigin / (float)(pListData->m_iXScrollExtent - iListRectWidth)) * (float)(iTrackWidth-iTrackThumbWidth)));
        pListData->m_rScrollbar_Horiz_Thumb.left = iTrackThumbPos + glb_pSkin->mpl_pHScrollBar_Left->m_pImage->m_szSize.cx;
        pListData->m_rScrollbar_Horiz_Thumb.right = pListData->m_rScrollbar_Horiz_Thumb.left + iTrackThumbWidth;

        InvalidateRect(pListData->m_hWnd, &pListData->m_rScrollbar_Horiz, FALSE);
    }

    // Vertical scrollbar
    iListRectHeight_Lines = CLV_GetListRect_Lines(pListData);
    if(pListData->m_iNumItems <= iListRectHeight_Lines)
    {
        pListData->m_rList.right = pListData->m_rClient.right;
        pListData->m_rHeader.right = pListData->m_rList.right;
        if(pListData->m_bScrollBarVisible_Vert == TRUE)
            CLV_InvalidateWindow(pListData);
        pListData->m_bScrollBarVisible_Vert = FALSE;
        pListData->m_iFirstVisibleItem = 0;
        SetRect(&pListData->m_rScrollbar_Vert, 0, 0, 0, 0);
    }
    else
    {
        int iTrackHeight;
        int iTrackThumbHeight;
        int iTrackThumbPos;
        int iTrackThumbHeight_Min;
        int iTrackThumbHeight_Max;
        const int iListRectHeight = pListData->m_rList.bottom - pListData->m_rList.top;

        // Work out size of scroll track
        iTrackHeight = iListRectHeight - (glb_pSkin->mpl_pVScrollBar_Up->m_iStateHeight
                                          + glb_pSkin->mpl_pVScrollBar_Down->m_iStateHeight);

        // Setup scrollbar
        pListData->m_rList.right = pListData->m_rClient.right - glb_pSkin->mpl_pVScrollBar_TrackUp->m_szSize.cx;
        pListData->m_rHeader.right = pListData->m_rList.right;
        if(pListData->m_bScrollBarVisible_Vert == FALSE)
            CLV_InvalidateWindow(pListData);
        pListData->m_bScrollBarVisible_Vert = TRUE;
        pListData->m_rScrollbar_Vert = pListData->m_rList;
        pListData->m_rScrollbar_Vert.left = pListData->m_rList.right;
        pListData->m_rScrollbar_Vert.right = pListData->m_rClient.right;

        // Limit scroll to fit into window
        if( (pListData->m_iFirstVisibleItem + iListRectHeight_Lines) > pListData->m_iNumItems)
            pListData->m_iFirstVisibleItem = pListData->m_iNumItems - iListRectHeight_Lines;

        // Setup track rect
        iTrackThumbHeight = (int)( (( (float)iListRectHeight_Lines / (float)pListData->m_iNumItems ) * (float)iTrackHeight));
        iTrackThumbHeight_Min = glb_pSkin->mpl_rVScrollBar_Track_Tile.top
                                + (glb_pSkin->mpl_pVScrollBar_TrackUp->m_szSize.cy - glb_pSkin->mpl_rVScrollBar_Track_Tile.bottom);
        iTrackThumbHeight_Max = (pListData->m_rScrollbar_Vert.bottom - pListData->m_rScrollbar_Vert.top);
        if(iTrackThumbHeight < iTrackThumbHeight_Min)
            iTrackThumbHeight = iTrackThumbHeight_Min;
        if(iTrackThumbHeight > iTrackThumbHeight_Max)
            iTrackThumbHeight = iTrackThumbHeight_Max;
        pListData->m_rScrollbar_Vert_Thumb = pListData->m_rScrollbar_Vert;
        iTrackThumbPos = (int)( (  ((float)pListData->m_iFirstVisibleItem / (float)(pListData->m_iNumItems - iListRectHeight_Lines)) * (float)(iTrackHeight-iTrackThumbHeight)));
        pListData->m_rScrollbar_Vert_Thumb.top = iTrackThumbPos + pListData->m_rScrollbar_Vert.top + glb_pSkin->mpl_pVScrollBar_Up->m_iStateHeight;
        pListData->m_rScrollbar_Vert_Thumb.bottom = pListData->m_rScrollbar_Vert_Thumb.top + iTrackThumbHeight;

        InvalidateRect(pListData->m_hWnd, &pListData->m_rScrollbar_Horiz, FALSE);
    }
}
//
//
//
void CLV_BeginBatch(CP_HLISTVIEW _hListData)
{
    CIs_ListViewData* pListData = (CIs_ListViewData*)_hListData;
    CP_CHECKOBJECT(pListData);

    pListData->m_bInBatch = TRUE;
    pListData->m_iBatchNesting ++;
}
//
//
//
void CLV_EndBatch(CP_HLISTVIEW _hListData)
{
    CIs_ListViewData* pListData = (CIs_ListViewData*)_hListData;
    CP_CHECKOBJECT(pListData);

    pListData->m_iBatchNesting--;
    if(pListData->m_iBatchNesting == 0)
    {
        pListData->m_bInBatch = FALSE;
        CLV_InvalidateWindow(pListData);
        CLV_UpdateScrollBars(pListData);
    }
}
//
//
//
void CLV_Scroll_Horiz(CIs_ListViewData* pListData, const int iPixels)
{
    const int iListRectWidth = pListData->m_rList.right-pListData->m_rList.left;
    int iNewXOrigin;

    iNewXOrigin = pListData->m_iXOrigin + iPixels;

    // Ensure scoll is in range
    if(iNewXOrigin < 0)
        iNewXOrigin = 0;
    if( (iNewXOrigin + iListRectWidth) > pListData->m_iXScrollExtent)
        iNewXOrigin = pListData->m_iXScrollExtent - iListRectWidth;

    // Update only if we have changed the origin
    if(iNewXOrigin != pListData->m_iXOrigin)
    {
        pListData->m_iXOrigin = iNewXOrigin;

        // Update display
        CLV_UpdateScrollBars(pListData);
        CLV_InvalidateWindow(pListData);
    }
}
//
//
//
void CLV_Scroll_Vert(CIs_ListViewData* pListData, const int iLines)
{
    const int iListRectHeight_Lines = CLV_GetListRect_Lines(pListData);
    int iNewFirstVisibleItem;

    iNewFirstVisibleItem = pListData->m_iFirstVisibleItem + iLines;

    // Ensure scoll is in range
    if(iNewFirstVisibleItem < 0)
        iNewFirstVisibleItem = 0;
    if( (iNewFirstVisibleItem + iListRectHeight_Lines) > pListData->m_iNumItems)
        iNewFirstVisibleItem = pListData->m_iNumItems - iListRectHeight_Lines;

    // Update only if we have changed the first visible item
    if(iNewFirstVisibleItem != pListData->m_iFirstVisibleItem)
    {
        pListData->m_iFirstVisibleItem = iNewFirstVisibleItem;
        CLV_UpdateScrollBars(pListData);
        CLV_InvalidateWindow(pListData);
    }
}
//
//
//
void CLV_UpdateWindowDims(CIs_ListViewData* pListData, const int iCX, const int iCY)
{
    // Work out window parts
    pListData->m_rClient.top = 0;
    pListData->m_rClient.left = 0;
    pListData->m_rClient.right = iCX;
    pListData->m_rClient.bottom = iCY;

    pListData->m_rHeader.top = 0;
    pListData->m_rHeader.left = 0;
    pListData->m_rHeader.right = iCX;
    pListData->m_rHeader.bottom = pListData->m_iItemHeight;

    pListData->m_rList.top = pListData->m_rHeader.bottom;
    pListData->m_rList.left = 0;
    pListData->m_rList.right = iCX;
    pListData->m_rList.bottom = iCY;

    CLV_UpdateScrollBars(pListData);

    pListData->m_iNumItemsOnPage = (int)floor( (float)(pListData->m_rList.bottom-pListData->m_rList.top) / (float)pListData->m_iItemHeight);
}
//
//
//
void CLV_DrawBackgroundRect(CIs_ListViewData* pListData, CPs_DrawContext* pDC, const RECT* _prTarget)
{
    // Call the parent and get it to draw into this rect
    RECT rDraw;
    POINT ptParentOffset;
    CPs_DrawContext drawcontext;
    HRGN rgnClip;

    // Skip this draw if there is no handler registered
    if(!pListData->m_hndlr_DrawBackgroundRect)
        return;

    // Skip this draw if we are totally clipped
    if(_prTarget->right < pDC->m_rClip.left
            || _prTarget->bottom < pDC->m_rClip.top
            || _prTarget->left > pDC->m_rClip.right
            || _prTarget->top > pDC->m_rClip.bottom)
    {
        return;
    }

    // Get rect and clip relative to the parent's origin
    IntersectRect(&rDraw, _prTarget, &pDC->m_rClip);

    // Correct our draw context to bring it into our parent's domain
    ptParentOffset.x = 0;
    ptParentOffset.y = 0;
    ClientToScreen(pListData->m_hWnd, &ptParentOffset);
    ScreenToClient(GetParent(pListData->m_hWnd), &ptParentOffset);
    drawcontext = *pDC;
    drawcontext.m_ptOffset.x -= ptParentOffset.x;
    drawcontext.m_ptOffset.y -= ptParentOffset.y;
    drawcontext.m_rClip = rDraw;
    OffsetRect(&drawcontext.m_rClip, ptParentOffset.x, ptParentOffset.y);

    // Setup a GDI clip region
    rgnClip = CreateRectRgn(rDraw.left + pDC->m_ptOffset.x, rDraw.top + pDC->m_ptOffset.y,
                            rDraw.right + pDC->m_ptOffset.x, rDraw.bottom + pDC->m_ptOffset.y);
    SelectClipRgn(drawcontext.m_dcDraw, rgnClip);
    pListData->m_hndlr_DrawBackgroundRect(&drawcontext);
    SelectClipRgn(drawcontext.m_dcDraw, NULL);
}
//
//
//
void CLV_Handle_WM_PAINT(CIs_ListViewData* pListData)
{
    RECT rClient;
    PAINTSTRUCT ps;
    HDC dcPaint;
    HBITMAP hbmSurface, hbmSurface_Old;
    HFONT hfOld;
    CPs_DrawContext drawcontext;
    BOOL bAvoidFlicker;

    // Do some debug checking
    CP_ASSERT(pListData->m_iFocusItem == CPC_INVALIDITEM || (pListData->m_iFocusItem >= 0 && pListData->m_iFocusItem < pListData->m_iNumItems));

    // Prepare for draw
    dcPaint = BeginPaint(pListData->m_hWnd, &ps);
    rClient = pListData->m_rClient;
    GetClipBox(dcPaint, &drawcontext.m_rClip);

    // Null clip rgn?
    if(drawcontext.m_rClip.right == drawcontext.m_rClip.left
            || drawcontext.m_rClip.top == drawcontext.m_rClip.bottom)
    {
        EndPaint(pListData->m_hWnd, &ps);
        return;
    }

    bAvoidFlicker = TRUE;
    if(bAvoidFlicker == TRUE)
    {
        hbmSurface = CreateCompatibleBitmap(dcPaint, drawcontext.m_rClip.right-drawcontext.m_rClip.left, drawcontext.m_rClip.bottom-drawcontext.m_rClip.top);
        CP_ASSERT(hbmSurface);
        drawcontext.m_dcDraw = CreateCompatibleDC(dcPaint);
        CP_ASSERT(drawcontext.m_dcDraw);
        hbmSurface_Old = (HBITMAP)SelectObject(drawcontext.m_dcDraw, hbmSurface);

        drawcontext.m_ptOffset.x = -drawcontext.m_rClip.left;
        drawcontext.m_ptOffset.y = -drawcontext.m_rClip.top;
    }
    else
    {
        hbmSurface = NULL;
        drawcontext.m_dcDraw = dcPaint;
        drawcontext.m_ptOffset.x = 0;
        drawcontext.m_ptOffset.y = 0;
        hbmSurface_Old = NULL;
    }

    // Draw header
    hfOld = (HFONT)SelectObject(drawcontext.m_dcDraw, glb_pSkin->mpl_hfFont);
    {
        int iCursorX;
        unsigned int _iColIDX;
        RECT rHeaderItem;

        // Draw header items
        iCursorX = -pListData->m_iXOrigin;
        SetTextColor(drawcontext.m_dcDraw, glb_pSkin->mpl_ListHeaderColour);
        SetBkMode(drawcontext.m_dcDraw, TRANSPARENT);
        for(_iColIDX = 0; _iColIDX < pListData->m_iNumColumns; _iColIDX++)

⌨️ 快捷键说明

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