Implement wxListBox::EnsureVisible() for wxMSW.

Manually check whether the item is currently visible and scroll the listbox
just enough if it isn't.

Closes #3224.

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@77653 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Vadim Zeitlin 2014-09-10 16:51:17 +00:00
parent ed1e48b1ed
commit 9a377ec117
4 changed files with 37 additions and 6 deletions

View File

@ -102,6 +102,7 @@ wxMSW:
- Add wxThread::MSWGetHandle() (troelsk).
- Allow using sizers for laying out wxMDIClientWindow (Artur Wieczorek).
- Fix updating wxSlider background when its parent background changes.
- Implement wxListBox::EnsureVisible() (RIVDSL).
wxOSX/Cocoa:

View File

@ -93,6 +93,8 @@ public:
int HitTest(const wxPoint& pt) const { return DoHitTestList(pt); }
int HitTest(wxCoord x, wxCoord y) const { return DoHitTestList(wxPoint(x, y)); }
virtual void EnsureVisible(int n);
// ownerdrawn wxListBox and wxCheckListBox support
#if wxUSE_OWNER_DRAWN
// override base class virtuals

View File

@ -285,12 +285,8 @@ public:
/**
Ensure that the item with the given index is currently shown.
Scroll the listbox if necessary.
This method is currently only implemented in wxGTK and wxOSX and does
nothing in other ports.
@see SetFirstItem()
This method scrolls the listbox only if necessary and doesn't do
anything if this item is already shown, unlike SetFirstItem().
*/
virtual void EnsureVisible(int n);

View File

@ -221,6 +221,38 @@ void wxListBox::MSWOnItemsChanged()
// implementation of wxListBoxBase methods
// ----------------------------------------------------------------------------
void wxListBox::EnsureVisible(int n)
{
wxCHECK_RET( IsValid(n),
wxT("invalid index in wxListBox::EnsureVisible") );
// when item is before the first visible item, make the item the first visible item
const int firstItem = SendMessage(GetHwnd(), LB_GETTOPINDEX, 0, 0);
if ( n <= firstItem )
{
DoSetFirstItem(n);
return;
}
// retrieve item height in order to compute last visible item and scroll amount
const int itemHeight = SendMessage(GetHwnd(), LB_GETITEMHEIGHT, 0, 0);
if ( itemHeight == LB_ERR || itemHeight == 0)
return;
// compute the amount of fully visible items
int countVisible = GetClientSize().y / itemHeight;
if ( !countVisible )
countVisible = 1;
// when item is before the last fully visible item, it is already visible
const int lastItem = firstItem + countVisible - 1;
if ( n <= lastItem )
return;
// make the item the last visible item by setting the first visible item accordingly
DoSetFirstItem(n - countVisible + 1);
}
void wxListBox::DoSetFirstItem(int N)
{
wxCHECK_RET( IsValid(N),