📄 sizer.cpp
字号:
/////////////////////////////////////////////////////////////////////////////
// Name: sizer.cpp
// Purpose: provide new wxSizer class for layout
// Author: Robert Roebling and Robin Dunn, contributions by
// Dirk Holtwick, Ron Lee
// Modified by: Ron Lee
// Created:
// RCS-ID: $Id: sizer.cpp,v 1.125.2.2 2005/11/14 22:59:11 RR Exp $
// Copyright: (c) Robin Dunn, Robert Roebling
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
#if defined(__GNUG__) && !defined(NO_GCC_PRAGMA)
#pragma implementation "sizer.h"
#endif
// For compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
#pragma hdrstop
#endif
#ifndef WX_PRECOMP
#include "wx/string.h"
#include "wx/intl.h"
#endif // WX_PRECOMP
#include "wx/sizer.h"
#include "wx/utils.h"
#include "wx/statbox.h"
#include "wx/settings.h"
#include "wx/listimpl.cpp"
#include "wx/intl.h"
#if WXWIN_COMPATIBILITY_2_4
#include "wx/notebook.h"
#endif
//---------------------------------------------------------------------------
IMPLEMENT_CLASS(wxSizerItem, wxObject)
IMPLEMENT_CLASS(wxSizer, wxObject)
IMPLEMENT_CLASS(wxGridSizer, wxSizer)
IMPLEMENT_CLASS(wxFlexGridSizer, wxGridSizer)
IMPLEMENT_CLASS(wxBoxSizer, wxSizer)
#if wxUSE_STATBOX
IMPLEMENT_CLASS(wxStaticBoxSizer, wxBoxSizer)
#endif
#if wxUSE_BUTTON
IMPLEMENT_CLASS(wxStdDialogButtonSizer, wxBoxSizer)
#endif
WX_DEFINE_EXPORTED_LIST( wxSizerItemList );
/*
TODO PROPERTIES
sizeritem
object
object_ref
minsize
option
flag
border
spacer
option
flag
borfder
boxsizer
orient
staticboxsizer
orient
label
gridsizer
rows
cols
vgap
hgap
flexgridsizer
rows
cols
vgap
hgap
growablerows
growablecols
minsize
*/
// ----------------------------------------------------------------------------
// wxSizerItem
// ----------------------------------------------------------------------------
void wxSizerItem::Init(const wxSizerFlags& flags)
{
Init();
m_proportion = flags.GetProportion();
m_flag = flags.GetFlags();
m_border = flags.GetBorderInPixels();
}
wxSizerItem::wxSizerItem()
{
Init();
m_proportion = 0;
m_border = 0;
m_flag = 0;
m_kind = Item_None;
}
// window item
void wxSizerItem::SetWindow(wxWindow *window)
{
wxCHECK_RET( window, _T("NULL window in wxSizerItem::SetWindow()") );
m_kind = Item_Window;
m_window = window;
// window doesn't become smaller than its initial size, whatever happens
m_minSize = window->GetSize();
if ( m_flag & wxFIXED_MINSIZE )
window->SetMinSize(m_minSize);
// aspect ratio calculated from initial size
SetRatio(m_minSize);
}
wxSizerItem::wxSizerItem(wxWindow *window,
int proportion,
int flag,
int border,
wxObject* userData)
: m_proportion(proportion),
m_border(border),
m_flag(flag),
m_userData(userData)
{
m_kind = Item_None;
SetWindow(window);
}
// sizer item
void wxSizerItem::SetSizer(wxSizer *sizer)
{
m_kind = Item_Sizer;
m_sizer = sizer;
}
wxSizerItem::wxSizerItem(wxSizer *sizer,
int proportion,
int flag,
int border,
wxObject* userData)
: m_proportion(proportion),
m_border(border),
m_flag(flag),
m_ratio(0.0),
m_userData(userData)
{
SetSizer(sizer);
// m_minSize is set later
}
// spacer item
void wxSizerItem::SetSpacer(const wxSize& size)
{
m_kind = Item_Spacer;
m_spacer = new wxSizerSpacer(size);
m_minSize = size;
SetRatio(size);
}
wxSizerItem::wxSizerItem(int width,
int height,
int proportion,
int flag,
int border,
wxObject* userData)
: m_minSize(width, height), // minimal size is the initial size
m_proportion(proportion),
m_border(border),
m_flag(flag),
m_userData(userData)
{
SetSpacer(width, height);
}
wxSizerItem::~wxSizerItem()
{
delete m_userData;
switch ( m_kind )
{
case Item_None:
break;
case Item_Window:
m_window->SetContainingSizer(NULL);
break;
case Item_Sizer:
delete m_sizer;
break;
case Item_Spacer:
delete m_spacer;
break;
case Item_Max:
default:
wxFAIL_MSG( _T("unexpected wxSizerItem::m_kind") );
}
}
wxSize wxSizerItem::GetSpacer() const
{
wxSize size;
if ( m_kind == Item_Spacer )
size = m_spacer->GetSize();
return size;
}
wxSize wxSizerItem::GetSize() const
{
wxSize ret;
switch ( m_kind )
{
case Item_None:
break;
case Item_Window:
ret = m_window->GetSize();
break;
case Item_Sizer:
ret = m_sizer->GetSize();
break;
case Item_Spacer:
ret = m_spacer->GetSize();
break;
case Item_Max:
default:
wxFAIL_MSG( _T("unexpected wxSizerItem::m_kind") );
}
if (m_flag & wxWEST)
ret.x += m_border;
if (m_flag & wxEAST)
ret.x += m_border;
if (m_flag & wxNORTH)
ret.y += m_border;
if (m_flag & wxSOUTH)
ret.y += m_border;
return ret;
}
wxSize wxSizerItem::CalcMin()
{
if (IsSizer())
{
m_minSize = m_sizer->GetMinSize();
// if we have to preserve aspect ratio _AND_ this is
// the first-time calculation, consider ret to be initial size
if ((m_flag & wxSHAPED) && !m_ratio)
SetRatio(m_minSize);
}
else if ( IsWindow() )
{
// Since the size of the window may change during runtime, we
// should use the current minimal/best size.
m_minSize = m_window->GetBestFittingSize();
}
return GetMinSizeWithBorder();
}
wxSize wxSizerItem::GetMinSizeWithBorder() const
{
wxSize ret = m_minSize;
if (m_flag & wxWEST)
ret.x += m_border;
if (m_flag & wxEAST)
ret.x += m_border;
if (m_flag & wxNORTH)
ret.y += m_border;
if (m_flag & wxSOUTH)
ret.y += m_border;
return ret;
}
void wxSizerItem::SetDimension( wxPoint pos, wxSize size )
{
if (m_flag & wxSHAPED)
{
// adjust aspect ratio
int rwidth = (int) (size.y * m_ratio);
if (rwidth > size.x)
{
// fit horizontally
int rheight = (int) (size.x / m_ratio);
// add vertical space
if (m_flag & wxALIGN_CENTER_VERTICAL)
pos.y += (size.y - rheight) / 2;
else if (m_flag & wxALIGN_BOTTOM)
pos.y += (size.y - rheight);
// use reduced dimensions
size.y =rheight;
}
else if (rwidth < size.x)
{
// add horizontal space
if (m_flag & wxALIGN_CENTER_HORIZONTAL)
pos.x += (size.x - rwidth) / 2;
else if (m_flag & wxALIGN_RIGHT)
pos.x += (size.x - rwidth);
size.x = rwidth;
}
}
// This is what GetPosition() returns. Since we calculate
// borders afterwards, GetPosition() will be the left/top
// corner of the surrounding border.
m_pos = pos;
if (m_flag & wxWEST)
{
pos.x += m_border;
size.x -= m_border;
}
if (m_flag & wxEAST)
{
size.x -= m_border;
}
if (m_flag & wxNORTH)
{
pos.y += m_border;
size.y -= m_border;
}
if (m_flag & wxSOUTH)
{
size.y -= m_border;
}
m_rect = wxRect(pos, size);
switch ( m_kind )
{
case Item_None:
wxFAIL_MSG( _T("can't set size of uninitialized sizer item") );
break;
case Item_Window:
m_window->SetSize(pos.x, pos.y, size.x, size.y, wxSIZE_ALLOW_MINUS_ONE);
break;
case Item_Sizer:
m_sizer->SetDimension(pos.x, pos.y, size.x, size.y);
break;
case Item_Spacer:
m_spacer->SetSize(size);
break;
case Item_Max:
default:
wxFAIL_MSG( _T("unexpected wxSizerItem::m_kind") );
}
}
void wxSizerItem::DeleteWindows()
{
switch ( m_kind )
{
case Item_None:
case Item_Spacer:
break;
case Item_Window:
//We are deleting the window from this sizer - normally
//the window destroys the sizer associated with it,
//which might destroy this, which we don't want
m_window->SetContainingSizer(NULL);
m_window->Destroy();
//Putting this after the switch will result in a spacer
//not being deleted properly on destruction
m_kind = Item_None;
break;
case Item_Sizer:
m_sizer->DeleteWindows();
break;
case Item_Max:
default:
wxFAIL_MSG( _T("unexpected wxSizerItem::m_kind") );
}
}
void wxSizerItem::Show( bool show )
{
switch ( m_kind )
{
case Item_None:
wxFAIL_MSG( _T("can't show uninitialized sizer item") );
break;
case Item_Window:
m_window->Show(show);
break;
case Item_Sizer:
m_sizer->Show(show);
break;
case Item_Spacer:
m_spacer->Show(show);
break;
case Item_Max:
default:
wxFAIL_MSG( _T("unexpected wxSizerItem::m_kind") );
}
}
bool wxSizerItem::IsShown() const
{
switch ( m_kind )
{
case Item_None:
// we may be called from CalcMin(), just return false so that we're
// not used
break;
case Item_Window:
return m_window->IsShown();
case Item_Sizer:
return m_sizer->IsShown();
case Item_Spacer:
return m_spacer->IsShown();
case Item_Max:
default:
wxFAIL_MSG( _T("unexpected wxSizerItem::m_kind") );
}
return false;
}
void wxSizerItem::SetOption( int option )
{
SetProportion( option );
}
int wxSizerItem::GetOption() const
{
return GetProportion();
}
//---------------------------------------------------------------------------
// wxSizer
//---------------------------------------------------------------------------
wxSizer::wxSizer()
{
m_isShown = true;
}
wxSizer::~wxSizer()
{
WX_CLEAR_LIST(wxSizerItemList, m_children);
}
wxSizerItem* wxSizer::Insert( size_t index, wxSizerItem *item )
{
m_children.Insert( index, item );
if ( item->GetWindow() )
item->GetWindow()->SetContainingSizer( this );
return item;
}
bool wxSizer::Remove( wxWindow *window )
{
return Detach( window );
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -