Merge branch 'grid-uitests-gtk'
Fixes to wxUIActionSimulator allowing the tests using it to work for wxGrid in wxGTK. And some improvements and bug fixes to wxGrid itself. Closes https://github.com/wxWidgets/wxWidgets/pull/1609
This commit is contained in:
@@ -936,7 +936,7 @@ struct WXDLLIMPEXP_CORE wxGridSizesInfo
|
|||||||
// wxGrid
|
// wxGrid
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
class WXDLLIMPEXP_CORE wxGrid : public wxScrolledWindow
|
class WXDLLIMPEXP_CORE wxGrid : public wxScrolledCanvas
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
// possible selection modes
|
// possible selection modes
|
||||||
@@ -1937,9 +1937,8 @@ public:
|
|||||||
|
|
||||||
|
|
||||||
// override some base class functions
|
// override some base class functions
|
||||||
virtual wxWindow *GetMainWindowOfCompositeControl() wxOVERRIDE
|
|
||||||
{ return (wxWindow*)m_gridWin; }
|
|
||||||
virtual void Fit() wxOVERRIDE;
|
virtual void Fit() wxOVERRIDE;
|
||||||
|
virtual void SetFocus() wxOVERRIDE;
|
||||||
|
|
||||||
// implementation only
|
// implementation only
|
||||||
void CancelMouseCapture();
|
void CancelMouseCapture();
|
||||||
@@ -2277,7 +2276,7 @@ protected:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
// implement wxScrolledWindow method to return m_gridWin size
|
// implement wxScrolledCanvas method to return m_gridWin size
|
||||||
virtual wxSize GetSizeAvailableForScrollTarget(const wxSize& size) wxOVERRIDE;
|
virtual wxSize GetSizeAvailableForScrollTarget(const wxSize& size) wxOVERRIDE;
|
||||||
|
|
||||||
// depending on the values of m_numFrozenRows and m_numFrozenCols, it will
|
// depending on the values of m_numFrozenRows and m_numFrozenCols, it will
|
||||||
|
@@ -2866,8 +2866,14 @@ public:
|
|||||||
/**
|
/**
|
||||||
Enables or disables in-place editing of grid cell data.
|
Enables or disables in-place editing of grid cell data.
|
||||||
|
|
||||||
The grid will issue either a @c wxEVT_GRID_EDITOR_SHOWN or
|
Enabling in-place editing generates @c wxEVT_GRID_EDITOR_SHOWN and, if
|
||||||
@c wxEVT_GRID_EDITOR_HIDDEN event.
|
it isn't vetoed by the application, shows the in-place editor which
|
||||||
|
allows the user to change the cell value.
|
||||||
|
|
||||||
|
Disabling in-place editing does nothing if the in-place editor isn't
|
||||||
|
currently show, otherwise the @c wxEVT_GRID_EDITOR_HIDDEN event is
|
||||||
|
generated but, unlike the "shown" event, it can't be vetoed and the
|
||||||
|
in-place editor is dismissed unconditionally.
|
||||||
*/
|
*/
|
||||||
void EnableCellEditControl(bool enable = true);
|
void EnableCellEditControl(bool enable = true);
|
||||||
|
|
||||||
@@ -3249,7 +3255,11 @@ public:
|
|||||||
void SetReadOnly(int row, int col, bool isReadOnly = true);
|
void SetReadOnly(int row, int col, bool isReadOnly = true);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Displays the in-place cell edit control for the current cell.
|
Displays the active in-place cell edit control for the current cell
|
||||||
|
after it was hidden.
|
||||||
|
|
||||||
|
Note that this method does @em not start editing the cell, this is only
|
||||||
|
done by EnableCellEditControl().
|
||||||
*/
|
*/
|
||||||
void ShowCellEditControl();
|
void ShowCellEditControl();
|
||||||
|
|
||||||
|
@@ -183,6 +183,7 @@ wxBEGIN_EVENT_TABLE( GridFrame, wxFrame )
|
|||||||
EVT_MENU( ID_DELETEROW, GridFrame::DeleteSelectedRows )
|
EVT_MENU( ID_DELETEROW, GridFrame::DeleteSelectedRows )
|
||||||
EVT_MENU( ID_DELETECOL, GridFrame::DeleteSelectedCols )
|
EVT_MENU( ID_DELETECOL, GridFrame::DeleteSelectedCols )
|
||||||
EVT_MENU( ID_CLEARGRID, GridFrame::ClearGrid )
|
EVT_MENU( ID_CLEARGRID, GridFrame::ClearGrid )
|
||||||
|
EVT_MENU( ID_EDITCELL, GridFrame::EditCell )
|
||||||
EVT_MENU( ID_SETCORNERLABEL, GridFrame::SetCornerLabelValue )
|
EVT_MENU( ID_SETCORNERLABEL, GridFrame::SetCornerLabelValue )
|
||||||
EVT_MENU( ID_SHOWSEL, GridFrame::ShowSelection )
|
EVT_MENU( ID_SHOWSEL, GridFrame::ShowSelection )
|
||||||
EVT_MENU( ID_SELCELLS, GridFrame::SelectCells )
|
EVT_MENU( ID_SELCELLS, GridFrame::SelectCells )
|
||||||
@@ -372,6 +373,7 @@ GridFrame::GridFrame()
|
|||||||
editMenu->Append( ID_DELETEROW, "Delete selected ro&ws" );
|
editMenu->Append( ID_DELETEROW, "Delete selected ro&ws" );
|
||||||
editMenu->Append( ID_DELETECOL, "Delete selected co&ls" );
|
editMenu->Append( ID_DELETECOL, "Delete selected co&ls" );
|
||||||
editMenu->Append( ID_CLEARGRID, "Cl&ear grid cell contents" );
|
editMenu->Append( ID_CLEARGRID, "Cl&ear grid cell contents" );
|
||||||
|
editMenu->Append( ID_EDITCELL, "&Edit current cell" );
|
||||||
editMenu->Append( ID_SETCORNERLABEL, "&Set corner label..." );
|
editMenu->Append( ID_SETCORNERLABEL, "&Set corner label..." );
|
||||||
|
|
||||||
editMenu->AppendCheckItem( ID_FREEZE_OR_THAW, "Freeze up to cursor\tCtrl-F" );
|
editMenu->AppendCheckItem( ID_FREEZE_OR_THAW, "Freeze up to cursor\tCtrl-F" );
|
||||||
@@ -1161,6 +1163,11 @@ void GridFrame::ClearGrid( wxCommandEvent& WXUNUSED(ev) )
|
|||||||
grid->ClearGrid();
|
grid->ClearGrid();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void GridFrame::EditCell( wxCommandEvent& WXUNUSED(ev) )
|
||||||
|
{
|
||||||
|
grid->EnableCellEditControl();
|
||||||
|
}
|
||||||
|
|
||||||
void GridFrame::SetCornerLabelValue( wxCommandEvent& WXUNUSED(ev) )
|
void GridFrame::SetCornerLabelValue( wxCommandEvent& WXUNUSED(ev) )
|
||||||
{
|
{
|
||||||
wxTextEntryDialog dialog(this,
|
wxTextEntryDialog dialog(this,
|
||||||
|
@@ -69,6 +69,7 @@ class GridFrame : public wxFrame
|
|||||||
void DeleteSelectedRows( wxCommandEvent& );
|
void DeleteSelectedRows( wxCommandEvent& );
|
||||||
void DeleteSelectedCols( wxCommandEvent& );
|
void DeleteSelectedCols( wxCommandEvent& );
|
||||||
void ClearGrid( wxCommandEvent& );
|
void ClearGrid( wxCommandEvent& );
|
||||||
|
void EditCell( wxCommandEvent& );
|
||||||
void SetCornerLabelValue( wxCommandEvent& );
|
void SetCornerLabelValue( wxCommandEvent& );
|
||||||
void ShowSelection( wxCommandEvent& );
|
void ShowSelection( wxCommandEvent& );
|
||||||
void SelectCells( wxCommandEvent& );
|
void SelectCells( wxCommandEvent& );
|
||||||
@@ -179,6 +180,7 @@ public:
|
|||||||
ID_DELETEROW,
|
ID_DELETEROW,
|
||||||
ID_DELETECOL,
|
ID_DELETECOL,
|
||||||
ID_CLEARGRID,
|
ID_CLEARGRID,
|
||||||
|
ID_EDITCELL,
|
||||||
ID_SETCORNERLABEL,
|
ID_SETCORNERLABEL,
|
||||||
ID_SHOWSEL,
|
ID_SHOWSEL,
|
||||||
ID_CHANGESEL,
|
ID_CHANGESEL,
|
||||||
|
@@ -2257,7 +2257,7 @@ void wxGridWindow::OnFocus(wxFocusEvent& event)
|
|||||||
|
|
||||||
/////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
wxBEGIN_EVENT_TABLE( wxGrid, wxScrolledWindow )
|
wxBEGIN_EVENT_TABLE( wxGrid, wxScrolledCanvas )
|
||||||
EVT_PAINT( wxGrid::OnPaint )
|
EVT_PAINT( wxGrid::OnPaint )
|
||||||
EVT_SIZE( wxGrid::OnSize )
|
EVT_SIZE( wxGrid::OnSize )
|
||||||
EVT_KEY_DOWN( wxGrid::OnKeyDown )
|
EVT_KEY_DOWN( wxGrid::OnKeyDown )
|
||||||
@@ -2271,7 +2271,7 @@ bool wxGrid::Create(wxWindow *parent, wxWindowID id,
|
|||||||
const wxPoint& pos, const wxSize& size,
|
const wxPoint& pos, const wxSize& size,
|
||||||
long style, const wxString& name)
|
long style, const wxString& name)
|
||||||
{
|
{
|
||||||
if (!wxScrolledWindow::Create(parent, id, pos, size,
|
if (!wxScrolledCanvas::Create(parent, id, pos, size,
|
||||||
style | wxWANTS_CHARS, name))
|
style | wxWANTS_CHARS, name))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@@ -3390,7 +3390,7 @@ wxGridCellCoordsArray wxGrid::CalcCellsExposed( const wxRegion& reg,
|
|||||||
|
|
||||||
void wxGrid::PrepareDCFor(wxDC &dc, wxGridWindow *gridWindow)
|
void wxGrid::PrepareDCFor(wxDC &dc, wxGridWindow *gridWindow)
|
||||||
{
|
{
|
||||||
wxScrolledWindow::PrepareDC( dc );
|
wxScrolledCanvas::PrepareDC( dc );
|
||||||
|
|
||||||
wxPoint dcOrigin = dc.GetDeviceOrigin() - GetGridWindowOffset(gridWindow);
|
wxPoint dcOrigin = dc.GetDeviceOrigin() - GetGridWindowOffset(gridWindow);
|
||||||
|
|
||||||
@@ -5186,7 +5186,7 @@ void wxGrid::Refresh(bool eraseb, const wxRect* rect)
|
|||||||
if ( m_created && !GetBatchCount() )
|
if ( m_created && !GetBatchCount() )
|
||||||
{
|
{
|
||||||
// Refresh to get correct scrolled position:
|
// Refresh to get correct scrolled position:
|
||||||
wxScrolledWindow::Refresh(eraseb, rect);
|
wxScrolledCanvas::Refresh(eraseb, rect);
|
||||||
|
|
||||||
if (rect)
|
if (rect)
|
||||||
{
|
{
|
||||||
@@ -6824,7 +6824,7 @@ void wxGrid::ForceRefresh()
|
|||||||
|
|
||||||
void wxGrid::DoEnable(bool enable)
|
void wxGrid::DoEnable(bool enable)
|
||||||
{
|
{
|
||||||
wxScrolledWindow::DoEnable(enable);
|
wxScrolledCanvas::DoEnable(enable);
|
||||||
|
|
||||||
Refresh(false /* don't erase background */);
|
Refresh(false /* don't erase background */);
|
||||||
}
|
}
|
||||||
@@ -7908,7 +7908,7 @@ void wxGrid::SetRowLabelSize( int width )
|
|||||||
m_rowLabelWidth = width;
|
m_rowLabelWidth = width;
|
||||||
InvalidateBestSize();
|
InvalidateBestSize();
|
||||||
CalcWindowSizes();
|
CalcWindowSizes();
|
||||||
wxScrolledWindow::Refresh( true );
|
wxScrolledCanvas::Refresh( true );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -7938,7 +7938,7 @@ void wxGrid::SetColLabelSize( int height )
|
|||||||
m_colLabelHeight = height;
|
m_colLabelHeight = height;
|
||||||
InvalidateBestSize();
|
InvalidateBestSize();
|
||||||
CalcWindowSizes();
|
CalcWindowSizes();
|
||||||
wxScrolledWindow::Refresh( true );
|
wxScrolledCanvas::Refresh( true );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -9397,51 +9397,66 @@ wxGrid::AutoSizeColOrRow(int colOrRow, bool setAsMin, wxGridDirection direction)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// now also compare with the column label extent
|
// now also compare with the column label extent
|
||||||
wxCoord w, h;
|
wxCoord extentLabel;
|
||||||
dc.SetFont( GetLabelFont() );
|
dc.SetFont( GetLabelFont() );
|
||||||
|
|
||||||
bool addMargin = true;
|
// We add some margin around text for better readability.
|
||||||
|
const int margin = FromDIP(column ? 10 : 6);
|
||||||
|
|
||||||
if ( column )
|
if ( column )
|
||||||
{
|
{
|
||||||
if ( m_useNativeHeader )
|
if ( m_useNativeHeader )
|
||||||
{
|
{
|
||||||
w = GetGridColHeader()->GetColumnTitleWidth(colOrRow);
|
extentLabel = GetGridColHeader()->GetColumnTitleWidth(colOrRow);
|
||||||
|
|
||||||
// GetColumnTitleWidth already adds margins internally.
|
// Note that GetColumnTitleWidth already adds margins internally,
|
||||||
addMargin = false;
|
// so we don't need to add them here.
|
||||||
h = 0;
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
dc.GetMultiLineTextExtent( GetColLabelValue(colOrRow), &w, &h );
|
const wxSize
|
||||||
if ( GetColLabelTextOrientation() == wxVERTICAL )
|
size = dc.GetMultiLineTextExtent(GetColLabelValue(colOrRow));
|
||||||
w = h;
|
extentLabel = GetColLabelTextOrientation() == wxVERTICAL
|
||||||
|
? size.y
|
||||||
|
: size.x;
|
||||||
|
|
||||||
|
// Add some margins around text for better readability.
|
||||||
|
extentLabel += margin;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
dc.GetMultiLineTextExtent( GetRowLabelValue(colOrRow), &w, &h );
|
extentLabel = dc.GetMultiLineTextExtent(GetRowLabelValue(colOrRow)).y;
|
||||||
|
|
||||||
|
// As above, add some margins for readability, although a smaller one
|
||||||
|
// in vertical direction.
|
||||||
|
extentLabel += margin;
|
||||||
}
|
}
|
||||||
|
|
||||||
extent = column ? w : h;
|
|
||||||
if ( extent > extentMax )
|
|
||||||
extentMax = extent;
|
|
||||||
|
|
||||||
|
// Finally determine the suitable extent fitting both the cells contents
|
||||||
|
// and the label.
|
||||||
if ( !extentMax )
|
if ( !extentMax )
|
||||||
{
|
{
|
||||||
// empty column - give default extent (notice that if extentMax is less
|
// Special case: all the cells are empty, use the label extent.
|
||||||
// than default extent but != 0, it's OK)
|
extentMax = extentLabel;
|
||||||
|
if ( !extentMax )
|
||||||
|
{
|
||||||
|
// But if the label is empty too, use the default width/height.
|
||||||
extentMax = column ? m_defaultColWidth : m_defaultRowHeight;
|
extentMax = column ? m_defaultColWidth : m_defaultRowHeight;
|
||||||
}
|
}
|
||||||
else if ( addMargin )
|
|
||||||
{
|
|
||||||
// leave some space around text
|
|
||||||
if ( column )
|
|
||||||
extentMax += 10;
|
|
||||||
else
|
|
||||||
extentMax += 6;
|
|
||||||
}
|
}
|
||||||
|
else // We have some data in the column cells.
|
||||||
|
{
|
||||||
|
// Ensure we have the same margin around the cells text as we use
|
||||||
|
// around the label.
|
||||||
|
extentMax += margin;
|
||||||
|
|
||||||
|
// And increase it to fit the label if necessary.
|
||||||
|
if ( extentLabel > extentMax )
|
||||||
|
extentMax = extentLabel;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
if ( column )
|
if ( column )
|
||||||
{
|
{
|
||||||
@@ -9659,6 +9674,11 @@ void wxGrid::Fit()
|
|||||||
AutoSize();
|
AutoSize();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void wxGrid::SetFocus()
|
||||||
|
{
|
||||||
|
m_gridWin->SetFocus();
|
||||||
|
}
|
||||||
|
|
||||||
#if WXWIN_COMPATIBILITY_2_8
|
#if WXWIN_COMPATIBILITY_2_8
|
||||||
wxPen& wxGrid::GetDividerPen() const
|
wxPen& wxGrid::GetDividerPen() const
|
||||||
{
|
{
|
||||||
|
@@ -28,6 +28,8 @@
|
|||||||
#include "wx/unix/utilsx11.h"
|
#include "wx/unix/utilsx11.h"
|
||||||
|
|
||||||
#ifdef __WXGTK3__
|
#ifdef __WXGTK3__
|
||||||
|
#include "wx/utils.h"
|
||||||
|
|
||||||
#include "wx/gtk/private/wrapgtk.h"
|
#include "wx/gtk/private/wrapgtk.h"
|
||||||
GtkWidget* wxGetTopLevelGTK();
|
GtkWidget* wxGetTopLevelGTK();
|
||||||
#endif
|
#endif
|
||||||
@@ -108,7 +110,12 @@ bool wxUIActionSimulatorX11Impl::SendButtonEvent(int button, bool isDown)
|
|||||||
// all pending events, notably mouse moves.
|
// all pending events, notably mouse moves.
|
||||||
XSync(m_display, False /* don't discard */);
|
XSync(m_display, False /* don't discard */);
|
||||||
|
|
||||||
return DoX11Button(xbutton, isDown);
|
if ( !DoX11Button(xbutton, isDown) )
|
||||||
|
return false;
|
||||||
|
|
||||||
|
XFlush(m_display);
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if wxUSE_PLAINX_IMPL
|
#if wxUSE_PLAINX_IMPL
|
||||||
@@ -243,7 +250,7 @@ private:
|
|||||||
|
|
||||||
bool wxUIActionSimulatorXTestImpl::DoX11Button(int xbutton, bool isDown)
|
bool wxUIActionSimulatorXTestImpl::DoX11Button(int xbutton, bool isDown)
|
||||||
{
|
{
|
||||||
return XTestFakeButtonEvent(m_display, xbutton, isDown, 0) != 0;
|
return XTestFakeButtonEvent(m_display, xbutton, isDown, CurrentTime) != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool wxUIActionSimulatorXTestImpl::DoX11MouseMove(long x, long y)
|
bool wxUIActionSimulatorXTestImpl::DoX11MouseMove(long x, long y)
|
||||||
@@ -266,7 +273,7 @@ bool wxUIActionSimulatorXTestImpl::DoX11MouseMove(long x, long y)
|
|||||||
#endif // GTK+ 3.10+
|
#endif // GTK+ 3.10+
|
||||||
#endif // __WXGTK3__
|
#endif // __WXGTK3__
|
||||||
|
|
||||||
return XTestFakeMotionEvent(m_display, -1, x, y, 0) != 0;
|
return XTestFakeMotionEvent(m_display, -1, x, y, CurrentTime) != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
@@ -274,7 +281,7 @@ wxUIActionSimulatorXTestImpl::DoX11Key(KeyCode xkeycode,
|
|||||||
int WXUNUSED(modifiers),
|
int WXUNUSED(modifiers),
|
||||||
bool isDown)
|
bool isDown)
|
||||||
{
|
{
|
||||||
return XTestFakeKeyEvent(m_display, xkeycode, isDown, 0) != 0;
|
return XTestFakeKeyEvent(m_display, xkeycode, isDown, CurrentTime) != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif // wxUSE_XTEST
|
#endif // wxUSE_XTEST
|
||||||
@@ -328,6 +335,13 @@ bool wxUIActionSimulatorX11Impl::MouseMove(long x, long y)
|
|||||||
|
|
||||||
bool wxUIActionSimulatorX11Impl::MouseUp(int button)
|
bool wxUIActionSimulatorX11Impl::MouseUp(int button)
|
||||||
{
|
{
|
||||||
|
#ifdef __WXGTK3__
|
||||||
|
// This is a horrible hack, but some mouse click events are just lost
|
||||||
|
// without any apparent reason when using GTK 3 without this, i.e. they
|
||||||
|
// simply never reach GTK in some runs of the tests.
|
||||||
|
wxMilliSleep(10);
|
||||||
|
#endif
|
||||||
|
|
||||||
return SendButtonEvent(button, false);
|
return SendButtonEvent(button, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -341,7 +355,12 @@ bool wxUIActionSimulatorX11Impl::DoKey(int keycode, int modifiers, bool isDown)
|
|||||||
if ( xkeycode == NoSymbol )
|
if ( xkeycode == NoSymbol )
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
return DoX11Key(xkeycode, modifiers, isDown);
|
if ( !DoX11Key(xkeycode, modifiers, isDown) )
|
||||||
|
return false;
|
||||||
|
|
||||||
|
XFlush(m_display);
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
wxUIActionSimulator::wxUIActionSimulator()
|
wxUIActionSimulator::wxUIActionSimulator()
|
||||||
|
@@ -16,26 +16,20 @@
|
|||||||
|
|
||||||
#ifndef WX_PRECOMP
|
#ifndef WX_PRECOMP
|
||||||
#include "wx/app.h"
|
#include "wx/app.h"
|
||||||
|
#include "wx/dcclient.h"
|
||||||
#endif // WX_PRECOMP
|
#endif // WX_PRECOMP
|
||||||
|
|
||||||
#include "wx/grid.h"
|
#include "wx/grid.h"
|
||||||
|
#include "wx/headerctrl.h"
|
||||||
#include "testableframe.h"
|
#include "testableframe.h"
|
||||||
#include "asserthelper.h"
|
#include "asserthelper.h"
|
||||||
#include "wx/uiaction.h"
|
#include "wx/uiaction.h"
|
||||||
|
|
||||||
// FIXME: A lot of mouse-related tests sporadically fail in wxGTK. This happens
|
|
||||||
// almost all the time but sometimes the tests do pass and the failure
|
|
||||||
// doesn't happen when debugging so this looks like some kind of event
|
|
||||||
// dispatching/simulating problem rather than a real problem in wxGrid.
|
|
||||||
//
|
|
||||||
// Just disable these tests for now but it would be really great to
|
|
||||||
// really fix the problem.
|
|
||||||
#ifdef __WXGTK__
|
#ifdef __WXGTK__
|
||||||
#define NONGTK_TEST(test)
|
#include "wx/stopwatch.h"
|
||||||
#else
|
#endif // __WXGTK__
|
||||||
#define NONGTK_TEST(test) WXUISIM_TEST(test)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
#include "waitforpaint.h"
|
||||||
|
|
||||||
class GridTestCase : public CppUnit::TestCase
|
class GridTestCase : public CppUnit::TestCase
|
||||||
{
|
{
|
||||||
@@ -48,13 +42,13 @@ public:
|
|||||||
private:
|
private:
|
||||||
CPPUNIT_TEST_SUITE( GridTestCase );
|
CPPUNIT_TEST_SUITE( GridTestCase );
|
||||||
WXUISIM_TEST( CellEdit );
|
WXUISIM_TEST( CellEdit );
|
||||||
NONGTK_TEST( CellClick );
|
WXUISIM_TEST( CellClick );
|
||||||
NONGTK_TEST( ReorderedColumnsCellClick );
|
WXUISIM_TEST( ReorderedColumnsCellClick );
|
||||||
NONGTK_TEST( CellSelect );
|
WXUISIM_TEST( CellSelect );
|
||||||
NONGTK_TEST( LabelClick );
|
WXUISIM_TEST( LabelClick );
|
||||||
NONGTK_TEST( SortClick );
|
WXUISIM_TEST( SortClick );
|
||||||
WXUISIM_TEST( Size );
|
WXUISIM_TEST( Size );
|
||||||
NONGTK_TEST( RangeSelect );
|
WXUISIM_TEST( RangeSelect );
|
||||||
CPPUNIT_TEST( Cursor );
|
CPPUNIT_TEST( Cursor );
|
||||||
CPPUNIT_TEST( Selection );
|
CPPUNIT_TEST( Selection );
|
||||||
CPPUNIT_TEST( AddRowCol );
|
CPPUNIT_TEST( AddRowCol );
|
||||||
@@ -70,18 +64,21 @@ private:
|
|||||||
WXUISIM_TEST( ReadOnly );
|
WXUISIM_TEST( ReadOnly );
|
||||||
WXUISIM_TEST( ResizeScrolledHeader );
|
WXUISIM_TEST( ResizeScrolledHeader );
|
||||||
WXUISIM_TEST( ColumnMinWidth );
|
WXUISIM_TEST( ColumnMinWidth );
|
||||||
|
WXUISIM_TEST( AutoSizeColumn );
|
||||||
CPPUNIT_TEST( PseudoTest_NativeHeader );
|
CPPUNIT_TEST( PseudoTest_NativeHeader );
|
||||||
NONGTK_TEST( LabelClick );
|
WXUISIM_TEST( LabelClick );
|
||||||
NONGTK_TEST( SortClick );
|
WXUISIM_TEST( SortClick );
|
||||||
CPPUNIT_TEST( ColumnOrder );
|
CPPUNIT_TEST( ColumnOrder );
|
||||||
WXUISIM_TEST( ResizeScrolledHeader );
|
WXUISIM_TEST( ResizeScrolledHeader );
|
||||||
WXUISIM_TEST( ColumnMinWidth );
|
WXUISIM_TEST( ColumnMinWidth );
|
||||||
|
WXUISIM_TEST( AutoSizeColumn );
|
||||||
CPPUNIT_TEST( DeleteAndAddRowCol );
|
CPPUNIT_TEST( DeleteAndAddRowCol );
|
||||||
CPPUNIT_TEST( PseudoTest_NativeLabels );
|
CPPUNIT_TEST( PseudoTest_NativeLabels );
|
||||||
NONGTK_TEST( LabelClick );
|
WXUISIM_TEST( LabelClick );
|
||||||
NONGTK_TEST( SortClick );
|
WXUISIM_TEST( SortClick );
|
||||||
CPPUNIT_TEST( ColumnOrder );
|
CPPUNIT_TEST( ColumnOrder );
|
||||||
WXUISIM_TEST( WindowAsEditorControl );
|
WXUISIM_TEST( WindowAsEditorControl );
|
||||||
|
WXUISIM_TEST( AutoSizeColumn );
|
||||||
CPPUNIT_TEST_SUITE_END();
|
CPPUNIT_TEST_SUITE_END();
|
||||||
|
|
||||||
void CellEdit();
|
void CellEdit();
|
||||||
@@ -108,10 +105,25 @@ private:
|
|||||||
void WindowAsEditorControl();
|
void WindowAsEditorControl();
|
||||||
void ResizeScrolledHeader();
|
void ResizeScrolledHeader();
|
||||||
void ColumnMinWidth();
|
void ColumnMinWidth();
|
||||||
|
void AutoSizeColumn();
|
||||||
void PseudoTest_NativeHeader() { ms_nativeheader = true; }
|
void PseudoTest_NativeHeader() { ms_nativeheader = true; }
|
||||||
void PseudoTest_NativeLabels() { ms_nativeheader = false;
|
void PseudoTest_NativeLabels() { ms_nativeheader = false;
|
||||||
ms_nativelabels = true; }
|
ms_nativelabels = true; }
|
||||||
|
|
||||||
|
// The helper function to determine the width of the column label depending
|
||||||
|
// on whether the native column is used.
|
||||||
|
int GetColumnLabelWidth(wxClientDC& dc, int col, int margin) const
|
||||||
|
{
|
||||||
|
if (ms_nativeheader)
|
||||||
|
return m_grid->GetGridColHeader()->GetColumnTitleWidth(col);
|
||||||
|
|
||||||
|
int w, h;
|
||||||
|
dc.GetMultiLineTextExtent(m_grid->GetColLabelValue(col), &w, &h);
|
||||||
|
return w + margin;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CheckFirstColAutoSize(int expected);
|
||||||
|
|
||||||
static bool ms_nativeheader;
|
static bool ms_nativeheader;
|
||||||
static bool ms_nativelabels;
|
static bool ms_nativelabels;
|
||||||
|
|
||||||
@@ -142,8 +154,15 @@ void GridTestCase::setUp()
|
|||||||
if( ms_nativelabels )
|
if( ms_nativelabels )
|
||||||
m_grid->SetUseNativeColLabels();
|
m_grid->SetUseNativeColLabels();
|
||||||
|
|
||||||
|
WaitForPaint waitForPaint(m_grid->GetGridWindow());
|
||||||
|
|
||||||
m_grid->Refresh();
|
m_grid->Refresh();
|
||||||
m_grid->Update();
|
m_grid->Update();
|
||||||
|
|
||||||
|
if ( !waitForPaint.YieldUntilPainted() )
|
||||||
|
{
|
||||||
|
WARN("Grid not repainted until timeout expiration");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void GridTestCase::tearDown()
|
void GridTestCase::tearDown()
|
||||||
@@ -176,16 +195,48 @@ void GridTestCase::CellEdit()
|
|||||||
|
|
||||||
m_grid->SetFocus();
|
m_grid->SetFocus();
|
||||||
m_grid->SetGridCursor(1, 1);
|
m_grid->SetGridCursor(1, 1);
|
||||||
m_grid->ShowCellEditControl();
|
|
||||||
|
wxYield();
|
||||||
|
|
||||||
sim.Text("abab");
|
sim.Text("abab");
|
||||||
|
|
||||||
|
// We need to wait until the editor is really shown under GTK, consider
|
||||||
|
// that it happens once it gets focus.
|
||||||
|
#ifdef __WXGTK__
|
||||||
|
for ( wxStopWatch sw; wxWindow::FindFocus() == m_grid; )
|
||||||
|
{
|
||||||
|
if ( sw.Time() > 250 )
|
||||||
|
{
|
||||||
|
WARN("Editor control not shown until timeout expiration");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
wxYield();
|
||||||
|
}
|
||||||
|
#endif // __WXGTK__
|
||||||
|
|
||||||
sim.Char(WXK_RETURN);
|
sim.Char(WXK_RETURN);
|
||||||
|
|
||||||
wxYield();
|
wxYield();
|
||||||
|
|
||||||
CPPUNIT_ASSERT_EQUAL(1, created.GetCount());
|
#ifdef __WXGTK__
|
||||||
CPPUNIT_ASSERT_EQUAL(1, changing.GetCount());
|
for ( wxStopWatch sw; wxWindow::FindFocus() != m_grid; )
|
||||||
CPPUNIT_ASSERT_EQUAL(1, changed.GetCount());
|
{
|
||||||
|
if ( sw.Time() > 250 )
|
||||||
|
{
|
||||||
|
WARN("Editor control not hidden until timeout expiration");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
wxYield();
|
||||||
|
}
|
||||||
|
#endif // __WXGTK__
|
||||||
|
|
||||||
|
CHECK(m_grid->GetCellValue(1, 1) == "abab");
|
||||||
|
|
||||||
|
CHECK(created.GetCount() == 1);
|
||||||
|
CHECK(changing.GetCount() == 1);
|
||||||
|
CHECK(changed.GetCount() == 1);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -770,7 +821,6 @@ void GridTestCase::Editable()
|
|||||||
|
|
||||||
m_grid->SetFocus();
|
m_grid->SetFocus();
|
||||||
m_grid->SetGridCursor(1, 1);
|
m_grid->SetGridCursor(1, 1);
|
||||||
m_grid->ShowCellEditControl();
|
|
||||||
|
|
||||||
sim.Text("abab");
|
sim.Text("abab");
|
||||||
wxYield();
|
wxYield();
|
||||||
@@ -797,12 +847,20 @@ void GridTestCase::ReadOnly()
|
|||||||
CPPUNIT_ASSERT(m_grid->IsReadOnly(1, 1));
|
CPPUNIT_ASSERT(m_grid->IsReadOnly(1, 1));
|
||||||
|
|
||||||
m_grid->SetFocus();
|
m_grid->SetFocus();
|
||||||
|
|
||||||
|
#ifdef __WXGTK__
|
||||||
|
// This is a mystery, but we somehow get WXK_RETURN generated by the
|
||||||
|
// previous test (Editable) in this one. In spite of wxYield() in that
|
||||||
|
// test, the key doesn't get dispatched there and we have to consume it
|
||||||
|
// here before setting the current grid cell, as getting WXK_RETURN later
|
||||||
|
// would move the selection down, to a non read-only cell.
|
||||||
|
wxYield();
|
||||||
|
#endif // __WXGTK__
|
||||||
|
|
||||||
m_grid->SetGridCursor(1, 1);
|
m_grid->SetGridCursor(1, 1);
|
||||||
|
|
||||||
CPPUNIT_ASSERT(m_grid->IsCurrentCellReadOnly());
|
CPPUNIT_ASSERT(m_grid->IsCurrentCellReadOnly());
|
||||||
|
|
||||||
m_grid->ShowCellEditControl();
|
|
||||||
|
|
||||||
sim.Text("abab");
|
sim.Text("abab");
|
||||||
wxYield();
|
wxYield();
|
||||||
|
|
||||||
@@ -950,4 +1008,94 @@ void GridTestCase::ColumnMinWidth()
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void GridTestCase::CheckFirstColAutoSize(int expected)
|
||||||
|
{
|
||||||
|
m_grid->AutoSizeColumn(0);
|
||||||
|
|
||||||
|
wxYield();
|
||||||
|
CHECK(m_grid->GetColSize(0) == expected);
|
||||||
|
}
|
||||||
|
|
||||||
|
void GridTestCase::AutoSizeColumn()
|
||||||
|
{
|
||||||
|
// Hardcoded extra margin for the columns used in grid.cpp.
|
||||||
|
const int margin = m_grid->FromDIP(10);
|
||||||
|
|
||||||
|
wxGridCellAttr *attr = m_grid->GetOrCreateCellAttr(0, 0);
|
||||||
|
wxGridCellRenderer *renderer = attr->GetRenderer(m_grid, 0, 0);
|
||||||
|
REQUIRE(renderer != NULL);
|
||||||
|
|
||||||
|
wxClientDC dcCell(m_grid->GetGridWindow());
|
||||||
|
|
||||||
|
wxClientDC dcLabel(m_grid->GetGridWindow());
|
||||||
|
dcLabel.SetFont(m_grid->GetLabelFont());
|
||||||
|
|
||||||
|
const wxString shortStr = "W";
|
||||||
|
const wxString mediumStr = "WWWW";
|
||||||
|
const wxString longStr = "WWWWWWWW";
|
||||||
|
const wxString multilineStr = mediumStr + "\n" + longStr;
|
||||||
|
|
||||||
|
SECTION("Empty column and label")
|
||||||
|
{
|
||||||
|
m_grid->SetColLabelValue(0, wxString());
|
||||||
|
CheckFirstColAutoSize( m_grid->GetDefaultColSize() );
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Empty column with label")
|
||||||
|
{
|
||||||
|
m_grid->SetColLabelValue(0, mediumStr);
|
||||||
|
CheckFirstColAutoSize( GetColumnLabelWidth(dcLabel, 0, margin) );
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Column with empty label")
|
||||||
|
{
|
||||||
|
m_grid->SetColLabelValue(0, wxString());
|
||||||
|
m_grid->SetCellValue(0, 0, mediumStr);
|
||||||
|
m_grid->SetCellValue(1, 0, shortStr);
|
||||||
|
m_grid->SetCellValue(3, 0, longStr);
|
||||||
|
|
||||||
|
CheckFirstColAutoSize(
|
||||||
|
renderer->GetBestWidth(*m_grid, *attr, dcCell, 3, 0,
|
||||||
|
m_grid->GetRowHeight(3)) + margin );
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Column with label longer than contents")
|
||||||
|
{
|
||||||
|
m_grid->SetColLabelValue(0, multilineStr);
|
||||||
|
m_grid->SetCellValue(0, 0, mediumStr);
|
||||||
|
m_grid->SetCellValue(1, 0, shortStr);
|
||||||
|
CheckFirstColAutoSize( GetColumnLabelWidth(dcLabel, 0, margin) );
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Column with contents longer than label")
|
||||||
|
{
|
||||||
|
m_grid->SetColLabelValue(0, mediumStr);
|
||||||
|
m_grid->SetCellValue(0, 0, mediumStr);
|
||||||
|
m_grid->SetCellValue(1, 0, shortStr);
|
||||||
|
m_grid->SetCellValue(3, 0, multilineStr);
|
||||||
|
CheckFirstColAutoSize(
|
||||||
|
renderer->GetBestWidth(*m_grid, *attr, dcCell, 3, 0,
|
||||||
|
m_grid->GetRowHeight(3)) + margin );
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Column with equally sized contents and label")
|
||||||
|
{
|
||||||
|
m_grid->SetColLabelValue(0, mediumStr);
|
||||||
|
m_grid->SetCellValue(0, 0, mediumStr);
|
||||||
|
m_grid->SetCellValue(1, 0, mediumStr);
|
||||||
|
m_grid->SetCellValue(3, 0, mediumStr);
|
||||||
|
|
||||||
|
const int labelWidth = GetColumnLabelWidth(dcLabel, 0, margin);
|
||||||
|
|
||||||
|
const int cellWidth =
|
||||||
|
renderer->GetBestWidth(*m_grid, *attr, dcCell, 3, 0,
|
||||||
|
m_grid->GetRowHeight(3))
|
||||||
|
+ margin;
|
||||||
|
|
||||||
|
// We can't be sure which size will be greater because of different fonts
|
||||||
|
// so just calculate the maximum width.
|
||||||
|
CheckFirstColAutoSize( wxMax(labelWidth, cellWidth) );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#endif //wxUSE_GRID
|
#endif //wxUSE_GRID
|
||||||
|
@@ -577,11 +577,11 @@ bool TestApp::ProcessEvent(wxEvent& event)
|
|||||||
int TestApp::RunTests()
|
int TestApp::RunTests()
|
||||||
{
|
{
|
||||||
#if wxUSE_LOG
|
#if wxUSE_LOG
|
||||||
// Switch off logging unless --verbose
|
// Switch off logging to avoid interfering with the tests output unless
|
||||||
bool verbose = wxLog::GetVerbose();
|
// WXTRACE is set, as otherwise setting it would have no effect while
|
||||||
wxLog::EnableLogging(verbose);
|
// running the tests.
|
||||||
#else
|
if ( !wxGetEnv("WXTRACE", NULL) )
|
||||||
bool verbose = false;
|
wxLog::EnableLogging(false);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// Cast is needed under MSW where Catch also provides an overload taking
|
// Cast is needed under MSW where Catch also provides an overload taking
|
||||||
|
96
tests/waitforpaint.h
Normal file
96
tests/waitforpaint.h
Normal file
@@ -0,0 +1,96 @@
|
|||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
// Name: tests/waitforpaint.h
|
||||||
|
// Purpose: Helper WaitForPaint class
|
||||||
|
// Author: Vadim Zeitlin
|
||||||
|
// Created: 2019-10-17 (extracted from tests/window/setsize.cpp)
|
||||||
|
// Copyright: (c) 2019 Vadim Zeitlin <vadim@wxwidgets.org>
|
||||||
|
///////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
#ifndef _WX_TESTS_WAITFORPAINT_H_
|
||||||
|
#define _WX_TESTS_WAITFORPAINT_H_
|
||||||
|
|
||||||
|
#include "wx/stopwatch.h"
|
||||||
|
#include "wx/window.h"
|
||||||
|
|
||||||
|
// Class used to check if we received the (first) paint event: this is
|
||||||
|
// currently used under GTK only, as MSW doesn't seem to need to wait for the
|
||||||
|
// things to work, while under Mac nothing works anyhow.
|
||||||
|
#ifdef __WXGTK__
|
||||||
|
|
||||||
|
class WaitForPaint
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
explicit WaitForPaint(wxWindow* win)
|
||||||
|
: m_win(*win),
|
||||||
|
m_painted(false),
|
||||||
|
m_handler(&m_painted)
|
||||||
|
{
|
||||||
|
m_win.Bind(wxEVT_PAINT, m_handler);
|
||||||
|
}
|
||||||
|
|
||||||
|
// This function waits up to the given number of milliseconds for the paint
|
||||||
|
// event to come and returns true if we did get it or false otherwise.
|
||||||
|
bool YieldUntilPainted(int timeoutInMS = 250) const
|
||||||
|
{
|
||||||
|
wxStopWatch sw;
|
||||||
|
for ( ;; )
|
||||||
|
{
|
||||||
|
wxYield();
|
||||||
|
|
||||||
|
if ( m_painted )
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if ( sw.Time() > timeoutInMS )
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
~WaitForPaint()
|
||||||
|
{
|
||||||
|
m_win.Unbind(wxEVT_PAINT, m_handler);
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
wxWindow& m_win;
|
||||||
|
bool m_painted;
|
||||||
|
|
||||||
|
class PaintHandler
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Note that we have to use a pointer here, i.e. we can't just store
|
||||||
|
// the flag inside the class itself because it's going to be cloned
|
||||||
|
// inside wx and querying the flag of the original copy wouldtn' work.
|
||||||
|
explicit PaintHandler(bool* painted)
|
||||||
|
: m_painted(*painted)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator()(wxPaintEvent& event)
|
||||||
|
{
|
||||||
|
event.Skip();
|
||||||
|
m_painted = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
bool& m_painted;
|
||||||
|
} m_handler;
|
||||||
|
};
|
||||||
|
|
||||||
|
#else // !__WXGTK__
|
||||||
|
|
||||||
|
class WaitForPaint
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
explicit WaitForPaint(wxWindow* WXUNUSED(win))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
bool YieldUntilPainted(int WXUNUSED(timeoutInMS) = 250) const
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // __WXGTK__/!__WXGTK__
|
||||||
|
|
||||||
|
#endif // _WX_TESTS_WAITFORPAINT_H_
|
@@ -23,9 +23,9 @@
|
|||||||
#endif // WX_PRECOMP
|
#endif // WX_PRECOMP
|
||||||
|
|
||||||
#include "wx/scopedptr.h"
|
#include "wx/scopedptr.h"
|
||||||
#include "wx/stopwatch.h"
|
|
||||||
|
|
||||||
#include "asserthelper.h"
|
#include "asserthelper.h"
|
||||||
|
#include "waitforpaint.h"
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// tests helpers
|
// tests helpers
|
||||||
@@ -47,57 +47,6 @@ protected:
|
|||||||
virtual wxSize DoGetBestSize() const wxOVERRIDE { return wxSize(50, 250); }
|
virtual wxSize DoGetBestSize() const wxOVERRIDE { return wxSize(50, 250); }
|
||||||
};
|
};
|
||||||
|
|
||||||
// Class used to check if we received the (first) paint event.
|
|
||||||
class WaitForPaint
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
// Note that we have to use a pointer here, i.e. we can't just store the
|
|
||||||
// flag inside the class itself because it's going to be cloned inside wx
|
|
||||||
// and querying the flag of the original copy is not going to work.
|
|
||||||
explicit WaitForPaint(bool* painted)
|
|
||||||
: m_painted(*painted)
|
|
||||||
{
|
|
||||||
m_painted = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void operator()(wxPaintEvent& event)
|
|
||||||
{
|
|
||||||
event.Skip();
|
|
||||||
m_painted = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
bool& m_painted;
|
|
||||||
};
|
|
||||||
|
|
||||||
// This function should be used to show the window and wait until we can get
|
|
||||||
// its real geometry.
|
|
||||||
void ShowAndWaitForPaint(wxWindow* w)
|
|
||||||
{
|
|
||||||
// Unfortunately showing the window is asynchronous, at least when using
|
|
||||||
// X11, so we have to wait for some time before retrieving its true
|
|
||||||
// geometry. And it's not clear how long should we wait, so we do it until
|
|
||||||
// we get the first paint event -- by then the window really should have
|
|
||||||
// its final size.
|
|
||||||
bool painted;
|
|
||||||
WaitForPaint waitForPaint(&painted);
|
|
||||||
w->Bind(wxEVT_PAINT, waitForPaint);
|
|
||||||
|
|
||||||
w->Show();
|
|
||||||
|
|
||||||
wxStopWatch sw;
|
|
||||||
while ( !painted )
|
|
||||||
{
|
|
||||||
wxYield();
|
|
||||||
|
|
||||||
if ( sw.Time() > 250 )
|
|
||||||
{
|
|
||||||
WARN("Didn't get a paint event until timeout expiration");
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} // anonymous namespace
|
} // anonymous namespace
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
@@ -143,7 +92,19 @@ TEST_CASE("wxWindow::MovePreservesSize", "[window][size][move]")
|
|||||||
wxScopedPtr<wxWindow>
|
wxScopedPtr<wxWindow>
|
||||||
w(new wxFrame(wxTheApp->GetTopWindow(), wxID_ANY, "Test child frame"));
|
w(new wxFrame(wxTheApp->GetTopWindow(), wxID_ANY, "Test child frame"));
|
||||||
|
|
||||||
ShowAndWaitForPaint(w.get());
|
// Unfortunately showing the window is asynchronous, at least when using
|
||||||
|
// X11, so we have to wait for some time before retrieving its true
|
||||||
|
// geometry. And it's not clear how long should we wait, so we do it until
|
||||||
|
// we get the first paint event -- by then the window really should have
|
||||||
|
// its final size.
|
||||||
|
WaitForPaint waitForPaint(w.get());
|
||||||
|
|
||||||
|
w->Show();
|
||||||
|
|
||||||
|
if ( !waitForPaint.YieldUntilPainted() )
|
||||||
|
{
|
||||||
|
WARN("Didn't get a paint event until timeout expiration");
|
||||||
|
}
|
||||||
|
|
||||||
const wxRect rectOrig = w->GetRect();
|
const wxRect rectOrig = w->GetRect();
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user