store ids of sub-items directly in wxSubwindows instead of using a parallel data structure (patch 1865577)

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@51065 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Vadim Zeitlin 2008-01-07 01:54:33 +00:00
parent fb25206791
commit 52ca4ec419
5 changed files with 59 additions and 28 deletions

View File

@ -158,7 +158,9 @@ protected:
// the buttons we contain // the buttons we contain
wxSubwindows *m_radioButtons; wxSubwindows *m_radioButtons;
wxWindowIDRef *m_radioButtonIds;
// and the special dummy button used only as a tab group boundary
wxSubwindows *m_dummyButton;
// array of widths and heights of the buttons, may be wxDefaultCoord if the // array of widths and heights of the buttons, may be wxDefaultCoord if the
// corresponding quantity should be computed // corresponding quantity should be computed

View File

@ -118,7 +118,6 @@ protected:
// the labels windows, if any // the labels windows, if any
wxSubwindows *m_labels; wxSubwindows *m_labels;
wxWindowIDRef *m_labelIds;
int m_rangeMin; int m_rangeMin;
int m_rangeMax; int m_rangeMax;

View File

@ -32,6 +32,7 @@ public:
m_count = n; m_count = n;
m_hwnds = (HWND *)calloc(n, sizeof(HWND)); m_hwnds = (HWND *)calloc(n, sizeof(HWND));
m_ids = new wxWindowIDRef[n];
} }
// non-virtual dtor, this class is not supposed to be used polymorphically // non-virtual dtor, this class is not supposed to be used polymorphically
@ -43,6 +44,7 @@ public:
} }
free(m_hwnds); free(m_hwnds);
delete [] m_ids;
} }
// get the number of subwindows // get the number of subwindows
@ -56,12 +58,21 @@ public:
return m_hwnds[n]; return m_hwnds[n];
} }
HWND& operator[](size_t n) { return Get(n); }
HWND operator[](size_t n) const HWND operator[](size_t n) const
{ {
return wx_const_cast(wxSubwindows *, this)->Get(n); return wx_const_cast(wxSubwindows *, this)->Get(n);
} }
// initialize the given window: id will be stored in wxWindowIDRef ensuring
// that it is not reused while this object exists
void Set(size_t n, HWND hwnd, wxWindowID id)
{
wxASSERT_MSG( n < m_count, _T("subwindow index out of range") );
m_hwnds[n] = hwnd;
m_ids[n] = id;
}
// check if we have this window // check if we have this window
bool HasWindow(HWND hwnd) bool HasWindow(HWND hwnd)
{ {
@ -140,6 +151,9 @@ private:
// the HWNDs we contain // the HWNDs we contain
HWND *m_hwnds; HWND *m_hwnds;
// the IDs of the windows
wxWindowIDRef *m_ids;
DECLARE_NO_COPY_CLASS(wxSubwindows) DECLARE_NO_COPY_CLASS(wxSubwindows)
}; };

View File

@ -129,7 +129,7 @@ void wxRadioBox::Init()
{ {
m_selectedButton = wxNOT_FOUND; m_selectedButton = wxNOT_FOUND;
m_radioButtons = NULL; m_radioButtons = NULL;
m_radioButtonIds = NULL; m_dummyButton = NULL;
m_radioWidth = NULL; m_radioWidth = NULL;
m_radioHeight = NULL; m_radioHeight = NULL;
} }
@ -156,8 +156,17 @@ bool wxRadioBox::Create(wxWindow *parent,
wxUnusedVar(val); wxUnusedVar(val);
#endif // wxUSE_VALIDATORS/!wxUSE_VALIDATORS #endif // wxUSE_VALIDATORS/!wxUSE_VALIDATORS
// We need an extra one to keep track of the 'dummy' item we
// create to end the radio group, so it will be destroyed and
// it's id will be released. But we want it separate from the
// other buttons since the wxSubwindows will operate on it as
// well and we just want to ignore it until destroying it.
// For instance, we don't want the bounding box of the radio
// buttons to include the dummy button
m_radioButtons = new wxSubwindows(n); m_radioButtons = new wxSubwindows(n);
m_radioButtonIds = new wxWindowIDRef[n + 1]; m_dummyButton = new wxSubwindows(1);
m_radioWidth = new int[n]; m_radioWidth = new int[n];
m_radioHeight = new int[n]; m_radioHeight = new int[n];
@ -169,14 +178,14 @@ bool wxRadioBox::Create(wxWindow *parent,
if ( i == 0 ) if ( i == 0 )
styleBtn |= WS_GROUP; styleBtn |= WS_GROUP;
m_radioButtonIds[i] = NewControlId(); wxWindowIDRef subid = NewControlId();
HWND hwndBtn = ::CreateWindow(_T("BUTTON"), HWND hwndBtn = ::CreateWindow(_T("BUTTON"),
choices[i].wx_str(), choices[i].wx_str(),
styleBtn, styleBtn,
0, 0, 0, 0, // will be set in SetSize() 0, 0, 0, 0, // will be set in SetSize()
GetHwndOf(parent), GetHwndOf(parent),
(HMENU)(wxWindowID)m_radioButtonIds[i], (HMENU)subid.GetValue(),
wxGetInstance(), wxGetInstance(),
NULL); NULL);
@ -187,21 +196,29 @@ bool wxRadioBox::Create(wxWindow *parent,
return false; return false;
} }
(*m_radioButtons)[i] = hwndBtn; // Keep track of the subwindow
m_radioButtons->Set(i, hwndBtn, subid);
SubclassRadioButton((WXHWND)hwndBtn); SubclassRadioButton((WXHWND)hwndBtn);
m_subControls.Add(m_radioButtonIds[i]); // Also, make it a subcontrol of this control
m_subControls.Add(subid);
} }
// Create a dummy radio control to end the group. // Create a dummy radio control to end the group.
m_radioButtonIds[n] = NewControlId(); wxWindowIDRef subid = NewControlId();
(void)::CreateWindow(_T("BUTTON"), HWND dummy = ::CreateWindow(_T("BUTTON"),
wxEmptyString, wxEmptyString,
WS_GROUP | BS_AUTORADIOBUTTON | WS_CHILD, WS_GROUP | BS_AUTORADIOBUTTON | WS_CHILD,
0, 0, 0, 0, GetHwndOf(parent), 0, 0, 0, 0, GetHwndOf(parent),
(HMENU)(wxWindowID)m_radioButtonIds[n], wxGetInstance(), NULL); (HMENU)subid.GetValue(), wxGetInstance(), NULL);
// Keep track of the subwindow so it will be destroyed when the radio
// box is and it's id will be freed.
// Also, do we need to consider this dummy item a subcontrol and add it
// to m_subControls
m_dummyButton->Set(0, dummy, subid);
m_radioButtons->SetFont(GetFont()); m_radioButtons->SetFont(GetFont());
@ -241,7 +258,7 @@ wxRadioBox::~wxRadioBox()
m_isBeingDeleted = true; m_isBeingDeleted = true;
delete m_radioButtons; delete m_radioButtons;
delete[] m_radioButtonIds; delete m_dummyButton;
delete[] m_radioWidth; delete[] m_radioWidth;
delete[] m_radioHeight; delete[] m_radioHeight;
} }

View File

@ -135,7 +135,6 @@ IMPLEMENT_DYNAMIC_CLASS(wxSlider, wxControl)
void wxSlider::Init() void wxSlider::Init()
{ {
m_labels = NULL; m_labels = NULL;
m_labelIds = NULL;
m_pageSize = 1; m_pageSize = 1;
m_lineSize = 1; m_lineSize = 1;
@ -205,24 +204,25 @@ wxSlider::Create(wxWindow *parent,
if ( m_windowStyle & wxSL_LABELS ) if ( m_windowStyle & wxSL_LABELS )
{ {
m_labels = new wxSubwindows(SliderLabel_Last); m_labels = new wxSubwindows(SliderLabel_Last);
m_labelIds = new wxWindowIDRef[SliderLabel_Last];
HWND hwndParent = GetHwndOf(parent); HWND hwndParent = GetHwndOf(parent);
for ( size_t n = 0; n < SliderLabel_Last; n++ ) for ( size_t n = 0; n < SliderLabel_Last; n++ )
{ {
m_labelIds[n] = NewControlId(); wxWindowIDRef lblid = NewControlId();
(*m_labels)[n] = ::CreateWindow HWND wnd = ::CreateWindow
( (
wxT("STATIC"), wxT("STATIC"),
NULL, NULL,
WS_CHILD | WS_VISIBLE | SS_CENTER, WS_CHILD | WS_VISIBLE | SS_CENTER,
0, 0, 0, 0, 0, 0, 0, 0,
hwndParent, hwndParent,
(HMENU)(wxWindowID)m_labelIds[n], (HMENU)lblid.GetValue(),
wxGetInstance(), wxGetInstance(),
NULL NULL
); );
m_labels->Set(n, wnd, lblid);
} }
m_labels->SetFont(GetFont()); m_labels->SetFont(GetFont());
@ -286,7 +286,6 @@ WXDWORD wxSlider::MSWGetStyle(long style, WXDWORD *exstyle) const
wxSlider::~wxSlider() wxSlider::~wxSlider()
{ {
delete m_labels; delete m_labels;
delete[] m_labelIds;
} }
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------