📄 rangeslider.c
字号:
w = rc.right;
h = rc.bottom;
#if 1
if ( !lpr->hCompDC )
lpr->hCompDC = CreateCompatibleDC( hDC );
hCompDC = lpr->hCompDC;
if ( !lpr->hBmp )
lpr->hBmp = CreateCompatibleBitmap( hDC, w, h );
hBmp = lpr->hBmp;
#else
hCompDC = CreateCompatibleDC( hDC );
hBmp = CreateCompatibleBitmap( hDC, w, h );
#endif
SelectObject( hCompDC, hBmp );
FillRect( hCompDC, &rc, lpr->hBackground );
// Draw the tic marks
SelectObject( hCompDC, lpr->hBlackPen );
for( i = 0; i < lpr->numTics; i++ )
{
xOfs = ((w - 7) * lpr->tic[i] / (lpr->max - lpr->min)) + 3;
pt[0].x = xOfs; pt[0].y = 15;
pt[1].x = xOfs; pt[1].y = 19;
Polyline( hCompDC, pt, 2 );
pt[0].y = 24 + HEIGHTSLIDER;
pt[1].y = 20 + HEIGHTSLIDER;
Polyline( hCompDC, pt, 2 );
}
#if 0
pt[0].x = w - 4; pt[0].y = 15;
pt[1].x = w - 4; pt[1].y = 19;
Polyline( hCompDC, pt, 2 );
pt[0].x = w - 4; pt[0].y = 24 + HEIGHTSLIDER;
pt[1].x = w - 4; pt[1].y = 20 + HEIGHTSLIDER;
Polyline( hCompDC, pt, 2 );
#endif
rc.left = 1;
rc.right = w - 1;
rc.top = 20;
rc.bottom = rc.top + HEIGHTSLIDER;
FillRect( hCompDC, &rc, (HBRUSH)GetStockObject( WHITE_BRUSH ) );
// draw 3-d edge
SelectObject( hCompDC, lpr->hDkGreyPen );
pt[0].x = rc.left; pt[0].y = rc.top + HEIGHTSLIDER - 2;
pt[1].x = rc.left; pt[1].y = rc.top;
pt[2].x = rc.right - 1; pt[2].y = rc.top;
Polyline( hCompDC, pt, 3 );
SelectObject( hCompDC, lpr->hBlackPen );
pt[0].x++; pt[0].y--;
pt[1].x++; pt[1].y++;
pt[2].x--; pt[2].y++;
Polyline( hCompDC, pt, 3 );
SelectObject( hCompDC, lpr->hLtGreyPen );
pt[0].y++;
pt[1].x = rc.right-2; pt[1].y = pt[0].y;
pt[2].x = rc.right-2; pt[2].y--;
Polyline( hCompDC, pt, 3 );
rc.top += 2;
rc.bottom -= 2;
rc.left = ((w - 7) * lpr->start / (lpr->max - lpr->min)) + 3;
// we have to increment the right corner, since FillRect fills up to, but
// not including the right and bottom edges.
rc.right = ((w - 7) * lpr->finish / (lpr->max - lpr->min)) + 4;
FillRect( hCompDC, &rc, lpr->hGreenBrush );
BitBlt( hDC, 0, 0, w, h, hCompDC, 0, 0, SRCCOPY );
rc.left = 3;
rc.right = w - 4;
rc.top = 20;
rc.bottom = rc.top + HEIGHTSLIDER;
//xOfs = (rc.right - rc.left) * lpr->start / (lpr->max - lpr->min);
xOfs = (w-7) * lpr->start / (lpr->max - lpr->min);
SelectObject( hCompDC, lpr->hTop );
BitBlt( hDC, xOfs, 0, 7, 14, hCompDC, 0, 0, SRCCOPY );
xOfs = (w-7) * lpr->finish / (lpr->max - lpr->min);
SelectObject( hCompDC, lpr->hBottom );
BitBlt( hDC, xOfs, 25 + HEIGHTSLIDER, 7, 14, hCompDC, 0, 0, SRCCOPY );
//DeleteDC( hCompDC );
//DeleteObject( hBmp );
EndPaint( hWnd, &p );
}
BOOL sliderHandleLButtonDown( HWND hWnd, LPRANGESLIDERSTRUCT lpr,
LPARAM lParam )
{
POINTS pt = MAKEPOINTS( lParam );
if ( !lpr->bInDrag )
{
if ( SliderHitTest( hWnd, TOPSLIDER, lParam, lpr ) )
{
SetCapture( hWnd );
lpr->bInDrag = TRUE;
lpr->which = TOPSLIDER;
}
else if ( SliderHitTest( hWnd, BOTTOMSLIDER, lParam, lpr ) )
{
SetCapture( hWnd );
lpr->bInDrag = TRUE;
lpr->which = BOTTOMSLIDER;
lpr->xOfsStart = (lpr->rc.right - 7) * lpr->finish / (lpr->max - lpr->min) + 3;
}
else if ( SliderLeftHitTest( hWnd, TOPSLIDER, lParam, lpr ) )
{
SendMessage( hWnd, RSB_SNAP, TOPSLIDER, 0 );
return TRUE;
}
else if ( SliderLeftHitTest( hWnd, BOTTOMSLIDER, lParam, lpr ) )
{
SendMessage( hWnd, RSB_SNAP, BOTTOMSLIDER, 0 );
return TRUE;
}
else if ( SliderRightHitTest( hWnd, TOPSLIDER, lParam, lpr ) )
{
SendMessage( hWnd, RSB_SNAP, TOPSLIDER, 1 );
return TRUE;
}
else if ( SliderRightHitTest( hWnd, BOTTOMSLIDER, lParam, lpr ) )
{
SendMessage( hWnd, RSB_SNAP, BOTTOMSLIDER, 1 );
return TRUE;
}
if ( lpr->bInDrag )
{
lpr->xStart = pt.x;
lpr->yStart = pt.y;
}
}
return FALSE;
}
BOOL sliderHandleLButtonUp( HWND hWnd, LPRANGESLIDERSTRUCT lpr, LPARAM lParam )
{
if ( lpr->bInDrag )
{
ReleaseCapture();
lpr->bInDrag = FALSE;
SendSliderNotifyChanged( hWnd, lpr );
}
return FALSE;
}
#if 0
rc.left = ((w - 7) * lpr->start / (lpr->max - lpr->min)) + 3;
rc.right = ((w - 7) * lpr->finish / (lpr->max - lpr->min)) + 3;
#endif
BOOL sliderHandleMouseMove( HWND hWnd, LPRANGESLIDERSTRUCT lpr, LPARAM lParam )
{
int xOfs;
POINTS pt;
DWORD dwNewValue;
pt = MAKEPOINTS( lParam );
if ( lpr->bInDrag )
{
xOfs = pt.x - 3;
if ( xOfs < 0 )
xOfs = 0;
else if ( xOfs > (lpr->rc.right - 7) )
xOfs = lpr->rc.right - 7;
switch( lpr->which )
{
case TOPSLIDER:
dwNewValue = xOfs * (lpr->max - lpr->min) / (lpr->rc.right - 7);
if ( SendSliderNotifyChanging( hWnd, lpr, dwNewValue ) )
{
lpr->start = dwNewValue;
//SendSliderNotifyChanged( hWnd, lpr );
}
return TRUE;
case BOTTOMSLIDER:
dwNewValue = xOfs * (lpr->max - lpr->min) / (lpr->rc.right - 7);
if ( SendSliderNotifyChanging( hWnd, lpr, dwNewValue ) )
{
lpr->finish = dwNewValue;
//SendSliderNotifyChanged( hWnd, lpr );
}
return TRUE;
}
}
return FALSE;
}
/*
* "Snaps" a slider either left or right to the nearest tic mark.
*
* wParam: which slider (TOPSLIDER or BOTTOMSLIDER)
* lParam: left (0) or right (1)
*/
BOOL sliderHandleSnap( HWND hWnd, WPARAM wParam, BOOL bRight, LPRANGESLIDERSTRUCT lpr )
{
int i;
DWORD dwPos;
DWORD dwCurrent;
if ( (wParam != TOPSLIDER) && (wParam != BOTTOMSLIDER) )
return FALSE;
if ( lpr->numTics == 0 )
return FALSE;
if ( bRight )
dwPos = lpr->min;
else
dwPos = lpr->max;
lpr->which = (int)wParam;
// find the leftmost or rightmost tic mark
for( i = 0; i < lpr->numTics; i++ )
{
if ( bRight )
{
if ( lpr->tic[i] > dwPos )
dwPos = lpr->tic[i];
}
else
{
if ( lpr->tic[i] < dwPos )
dwPos = lpr->tic[i];
}
}
dwCurrent = (wParam == TOPSLIDER)?lpr->start:lpr->finish;
for( i = 0; i < lpr->numTics; i++ )
{
if ( bRight )
{
if ( (lpr->tic[i] > dwCurrent) && (lpr->tic[i] < dwPos) )
dwPos = lpr->tic[i];
}
else
{
if ( (lpr->tic[i] < dwCurrent) && (lpr->tic[i] > dwPos) )
dwPos = lpr->tic[i];
}
}
lpr->which = (int)wParam;
if ( wParam == TOPSLIDER )
{
if ( SendSliderNotifyChanging( hWnd, lpr, dwPos ) )
lpr->start = dwPos;
}
else
{
if ( SendSliderNotifyChanging( hWnd, lpr, dwPos ) )
lpr->finish = dwPos;
}
SendSliderNotifyChanged( hWnd, lpr );
return TRUE;
}
BOOL SendSliderNotifyChanging( HWND hWnd, LPRANGESLIDERSTRUCT lpr, DWORD dwNew )
{
RSBNOTIFY rsb;
ZeroMemory( &rsb, sizeof(rsb) );
rsb.hdr.hwndFrom = hWnd;
rsb.hdr.idFrom = (UINT)GetWindowLong( hWnd, GWL_ID );
rsb.which = lpr->which;
if ( lpr->which == TOPSLIDER )
{
rsb.hdr.code = RSBN_STARTCHANGING;
rsb.newStart = dwNew;
rsb.newFinish = lpr->finish;
}
else
{
rsb.hdr.code = RSBN_FINISHCHANGING;
rsb.newStart = lpr->start;
rsb.newFinish = dwNew;
}
rsb.start = lpr->start;
rsb.finish = lpr->finish;
if ( SendMessage( GetParent( hWnd ), WM_NOTIFY, (WPARAM)rsb.hdr.idFrom,
(LPARAM)&rsb ) )
return TRUE;
return FALSE;
}
BOOL SendSliderNotifyChanged( HWND hWnd, LPRANGESLIDERSTRUCT lpr )
{
RSBNOTIFY rsb;
ZeroMemory( &rsb, sizeof(rsb) );
rsb.hdr.hwndFrom = hWnd;
rsb.hdr.idFrom = (UINT)GetWindowLong( hWnd, GWL_ID );
rsb.which = lpr->which;
if ( lpr->which == TOPSLIDER )
{
rsb.hdr.code = RSBN_STARTCHANGED;
}
else
{
rsb.hdr.code = RSBN_FINISHCHANGED;
}
rsb.start = lpr->start;
rsb.finish = lpr->finish;
rsb.newStart = lpr->start;
rsb.newFinish = lpr->finish;
SendMessage( GetParent( hWnd ), WM_NOTIFY, (WPARAM)rsb.hdr.idFrom,
(LPARAM)&rsb );
return TRUE;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -