[0.4.9][WIN32SS] Fix scrollbar bug CORE-15557 & CORE-13986

Fixes CORE-13986 "Wise Installer draws scrollbars enabled while they should be drawn disabled"
by porting back 0.4.11-dev-586-g 929a2c6 (the mentioned CORE-ID in that commit was wrong due to typo)

which requires to pick also 0.4.14-dev-1167-g 8bb9434 to prevent the first fix introducing regression
CORE-16721 "Scrolling by pressing the scrollbar arrows does not draw the arrows as pressed"

and finally port back 0.4.14-dev-243-g 19fbdda to fix
CORE-15557 "disabled scrollbars being clickable"

In sum this brings the scrollbar code to the state of 0.4.13-release-0-g 4ee3778
This commit is contained in:
Joachim Henze 2020-12-01 16:42:32 +01:00
parent e124688789
commit e187d8d998
2 changed files with 75 additions and 13 deletions

View file

@ -58,6 +58,10 @@ DBG_DEFAULT_CHANNEL(UserScrollbar);
/* FUNCTIONS *****************************************************************/
BOOL APIENTRY
IntEnableScrollBar(BOOL Horz, PSCROLLBARINFO Info, UINT wArrows);
/* Ported from WINE20020904 */
/* Compute the scroll bar rectangle, in drawing coordinates (i.e. client coords for SB_CTL, window coords for SB_VERT and
* SB_HORZ). 'arrowSize' returns the width or height of an arrow (depending on * the orientation of the scrollbar),
@ -203,6 +207,14 @@ IntCalculateThumb(PWND Wnd, LONG idObject, PSCROLLBARINFO psbi, PSBDATA pSBData)
psbi->xyThumbBottom = 0;
ThumbPos = Thumb;
}
else if (psbi->rgstate[SBRG_TOPRIGHTBTN] == STATE_SYSTEM_UNAVAILABLE &&
psbi->rgstate[SBRG_BOTTOMLEFTBTN] == STATE_SYSTEM_UNAVAILABLE &&
pSBData->posMin >= (int)(pSBData->posMax - max(pSBData->page - 1, 0)))
{
/* Nothing to scroll */
psbi->xyThumbTop = 0;
psbi->xyThumbBottom = 0;
}
else
{
ThumbBox = pSBData->page ? MINTRACKTHUMB : UserGetSystemMetrics(SM_CXHTHUMB);
@ -525,7 +537,6 @@ co_IntSetScrollInfo(PWND Window, INT nBar, LPCSCROLLINFO lpsi, BOOL bRedraw)
OldPos = Info->nPos;
Info->nPos = lpsi->nPos;
pSBData->pos = lpsi->nPos;
bChangeParams = TRUE;
}
}
@ -599,11 +610,15 @@ co_IntSetScrollInfo(PWND Window, INT nBar, LPCSCROLLINFO lpsi, BOOL bRedraw)
else /* Show and enable scroll-bar only if no page only changed. */
if (lpsi->fMask != SIF_PAGE)
{
new_flags = ESB_ENABLE_BOTH;
if ((nBar != SB_CTL) && bChangeParams)
{
new_flags = ESB_ENABLE_BOTH;
action |= SA_SSI_SHOW;
}
else if (nBar == SB_CTL)
{
new_flags = ESB_ENABLE_BOTH;
}
}
if (Window->pSBInfo->WSBflags != new_flags) /* Check arrow flags */
@ -642,6 +657,12 @@ co_IntSetScrollInfo(PWND Window, INT nBar, LPCSCROLLINFO lpsi, BOOL bRedraw)
co_UserRedrawWindow(Window, &UpdateRect, 0, RDW_INVALIDATE | RDW_FRAME);
}
*/ }
if (bChangeParams && (nBar == SB_HORZ || nBar == SB_VERT) && (lpsi->fMask & SIF_DISABLENOSCROLL))
{
IntEnableScrollBar(nBar == SB_HORZ, psbi, Window->pSBInfo->WSBflags);
}
/* Return current position */
return lpsi->fMask & SIF_PREVIOUSPOS ? OldPos : pSBData->pos;
}

View file

@ -318,6 +318,26 @@ IntGetScrollBarInfo(HWND Wnd, INT Bar, PSCROLLBARINFO ScrollBarInfo)
return NtUserGetScrollBarInfo(Wnd, IntScrollGetObjectId(Bar), ScrollBarInfo);
}
static VOID FASTCALL
IntUpdateScrollArrows(HWND Wnd, HDC hDC, PSCROLLBARINFO ScrollBarInfo,
SETSCROLLBARINFO *info, INT SBType, INT Arrow,
BOOL Vertical, BOOL Pressed)
{
if (Pressed)
{
ScrollBarInfo->rgstate[Arrow] |= STATE_SYSTEM_PRESSED;
}
else
{
ScrollBarInfo->rgstate[Arrow] &= ~STATE_SYSTEM_PRESSED;
}
/* Update arrow state */
info->rgstate[Arrow] = ScrollBarInfo->rgstate[Arrow];
NtUserSetScrollBarInfo(Wnd, IntScrollGetObjectId(SBType), info);
IntDrawScrollArrows(hDC, ScrollBarInfo, Vertical);
}
void
IntDrawScrollBar(HWND Wnd, HDC DC, INT Bar)
{
@ -831,9 +851,11 @@ IntScrollHandleScrollEvent(HWND Wnd, INT SBType, UINT Msg, POINT Pt)
PrevPt = Pt;
if (SBType == SB_CTL && (GetWindowLongPtrW(Wnd, GWL_STYLE) & WS_TABSTOP)) SetFocus(Wnd);
SetCapture(Wnd);
ScrollBarInfo.rgstate[ScrollTrackHitTest] |= STATE_SYSTEM_PRESSED;
NewInfo.rgstate[ScrollTrackHitTest] = ScrollBarInfo.rgstate[ScrollTrackHitTest];
NtUserSetScrollBarInfo(Wnd, IntScrollGetObjectId(SBType), &NewInfo);
/* Don't update scrollbar if disabled. */
if (ScrollBarInfo.rgstate[ScrollTrackHitTest] != STATE_SYSTEM_UNAVAILABLE)
{
IntUpdateScrollArrows (Wnd, Dc, &ScrollBarInfo, &NewInfo, SBType, ScrollTrackHitTest, Vertical, TRUE);
}
break;
case WM_MOUSEMOVE:
@ -846,13 +868,12 @@ IntScrollHandleScrollEvent(HWND Wnd, INT SBType, UINT Msg, POINT Pt)
ReleaseCapture();
/* if scrollbar has focus, show back caret */
if (Wnd == GetFocus()) ShowCaret(Wnd);
ScrollBarInfo.rgstate[ScrollTrackHitTest] &= ~STATE_SYSTEM_PRESSED;
NewInfo.rgstate[ScrollTrackHitTest] = ScrollBarInfo.rgstate[ScrollTrackHitTest];
NtUserSetScrollBarInfo(Wnd, IntScrollGetObjectId(SBType), &NewInfo);
IntDrawScrollInterior(Wnd,Dc,SBType,Vertical,&ScrollBarInfo);
IntDrawScrollArrows(Dc, &ScrollBarInfo, Vertical);
/* Don't update scrollbar if disabled. */
if (ScrollBarInfo.rgstate[ScrollTrackHitTest] != STATE_SYSTEM_UNAVAILABLE)
{
IntUpdateScrollArrows (Wnd, Dc, &ScrollBarInfo, &NewInfo, SBType, ScrollTrackHitTest, Vertical, FALSE);
IntDrawScrollInterior(Wnd,Dc,SBType,Vertical,&ScrollBarInfo);
}
break;
case WM_SYSTIMER:
@ -883,9 +904,17 @@ IntScrollHandleScrollEvent(HWND Wnd, INT SBType, UINT Msg, POINT Pt)
SetSystemTimer(Wnd, SCROLL_TIMER, (WM_LBUTTONDOWN == Msg) ?
SCROLL_FIRST_DELAY : SCROLL_REPEAT_DELAY,
(TIMERPROC) NULL);
if (ScrollBarInfo.rgstate[ScrollTrackHitTest] != STATE_SYSTEM_UNAVAILABLE)
{
if (!(ScrollBarInfo.rgstate[ScrollTrackHitTest] &= STATE_SYSTEM_PRESSED))
{
IntUpdateScrollArrows (Wnd, Dc, &ScrollBarInfo, &NewInfo, SBType, ScrollTrackHitTest, Vertical, TRUE);
}
}
}
else
{
IntUpdateScrollArrows (Wnd, Dc, &ScrollBarInfo, &NewInfo, SBType, ScrollTrackHitTest, Vertical, FALSE);
KillSystemTimer(Wnd, SCROLL_TIMER);
}
break;
@ -985,8 +1014,20 @@ IntScrollHandleScrollEvent(HWND Wnd, INT SBType, UINT Msg, POINT Pt)
SetSystemTimer(Wnd, SCROLL_TIMER, (WM_LBUTTONDOWN == Msg) ?
SCROLL_FIRST_DELAY : SCROLL_REPEAT_DELAY,
(TIMERPROC) NULL);
if (ScrollBarInfo.rgstate[ScrollTrackHitTest] != STATE_SYSTEM_UNAVAILABLE)
{
if (!(ScrollBarInfo.rgstate[ScrollTrackHitTest] &= STATE_SYSTEM_PRESSED))
{
TRACE("Set Arrow\n");
IntUpdateScrollArrows (Wnd, Dc, &ScrollBarInfo, &NewInfo, SBType, ScrollTrackHitTest, Vertical, TRUE);
}
}
}
else KillSystemTimer(Wnd, SCROLL_TIMER);
else
{
IntUpdateScrollArrows (Wnd, Dc, &ScrollBarInfo, &NewInfo, SBType, ScrollTrackHitTest, Vertical, FALSE);
KillSystemTimer(Wnd, SCROLL_TIMER);
}
break;
}