]>
Commit | Line | Data |
---|---|---|
1 | ///////////////////////////////////////////////////////////////////////////// | |
2 | // Name: src/osx/choice_osx.cpp | |
3 | // Purpose: wxChoice | |
4 | // Author: Stefan Csomor | |
5 | // Modified by: | |
6 | // Created: 1998-01-01 | |
7 | // Copyright: (c) Stefan Csomor | |
8 | // Licence: wxWindows licence | |
9 | ///////////////////////////////////////////////////////////////////////////// | |
10 | ||
11 | #include "wx/wxprec.h" | |
12 | ||
13 | #if wxUSE_CHOICE | |
14 | ||
15 | #include "wx/choice.h" | |
16 | ||
17 | #ifndef WX_PRECOMP | |
18 | #include "wx/menu.h" | |
19 | #include "wx/dcclient.h" | |
20 | #endif | |
21 | ||
22 | #include "wx/osx/private.h" | |
23 | ||
24 | wxChoice::~wxChoice() | |
25 | { | |
26 | if ( HasClientObjectData() ) | |
27 | { | |
28 | unsigned int i, max = GetCount(); | |
29 | ||
30 | for ( i = 0; i < max; ++i ) | |
31 | delete GetClientObject( i ); | |
32 | } | |
33 | delete m_popUpMenu; | |
34 | } | |
35 | ||
36 | bool wxChoice::Create(wxWindow *parent, | |
37 | wxWindowID id, | |
38 | const wxPoint& pos, | |
39 | const wxSize& size, | |
40 | const wxArrayString& choices, | |
41 | long style, | |
42 | const wxValidator& validator, | |
43 | const wxString& name ) | |
44 | { | |
45 | if ( !Create( parent, id, pos, size, 0, NULL, style, validator, name ) ) | |
46 | return false; | |
47 | ||
48 | Append( choices ); | |
49 | ||
50 | if ( !choices.empty() ) | |
51 | SetSelection( 0 ); | |
52 | ||
53 | SetInitialSize( size ); | |
54 | ||
55 | return true; | |
56 | } | |
57 | ||
58 | bool wxChoice::Create(wxWindow *parent, | |
59 | wxWindowID id, | |
60 | const wxPoint& pos, | |
61 | const wxSize& size, | |
62 | int n, | |
63 | const wxString choices[], | |
64 | long style, | |
65 | const wxValidator& validator, | |
66 | const wxString& name ) | |
67 | { | |
68 | DontCreatePeer(); | |
69 | ||
70 | if ( !wxChoiceBase::Create( parent, id, pos, size, style, validator, name ) ) | |
71 | return false; | |
72 | ||
73 | m_popUpMenu = new wxMenu(); | |
74 | m_popUpMenu->SetNoEventsMode(true); | |
75 | ||
76 | SetPeer(wxWidgetImpl::CreateChoice( this, parent, id, m_popUpMenu, pos, size, style, GetExtraStyle() )); | |
77 | ||
78 | MacPostControlCreate( pos, size ); | |
79 | ||
80 | #if !wxUSE_STD_CONTAINERS | |
81 | if ( style & wxCB_SORT ) | |
82 | // autosort | |
83 | m_strings = wxArrayString( 1 ); | |
84 | #endif | |
85 | ||
86 | Append(n, choices); | |
87 | ||
88 | // Set the first item as being selected | |
89 | if (n > 0) | |
90 | SetSelection( 0 ); | |
91 | ||
92 | // Needed because it is a wxControlWithItems | |
93 | SetInitialSize( size ); | |
94 | ||
95 | return true; | |
96 | } | |
97 | ||
98 | // ---------------------------------------------------------------------------- | |
99 | // adding/deleting items to/from the list | |
100 | // ---------------------------------------------------------------------------- | |
101 | ||
102 | void wxChoice::DoAfterItemCountChange() | |
103 | { | |
104 | InvalidateBestSize(); | |
105 | ||
106 | GetPeer()->SetMaximum( GetCount() ); | |
107 | } | |
108 | ||
109 | int wxChoice::DoInsertItems(const wxArrayStringsAdapter & items, | |
110 | unsigned int pos, | |
111 | void **clientData, wxClientDataType type) | |
112 | { | |
113 | const unsigned int numItems = items.GetCount(); | |
114 | for( unsigned int i = 0; i < numItems; ++i, ++pos ) | |
115 | { | |
116 | unsigned int idx; | |
117 | ||
118 | #if wxUSE_STD_CONTAINERS | |
119 | if ( IsSorted() ) | |
120 | { | |
121 | wxArrayString::iterator | |
122 | insertPoint = std::lower_bound( m_strings.begin(), m_strings.end(), items[i] ); | |
123 | idx = insertPoint - m_strings.begin(); | |
124 | m_strings.insert( insertPoint, items[i] ); | |
125 | } | |
126 | else | |
127 | #endif // wxUSE_STD_CONTAINERS | |
128 | { | |
129 | idx = pos; | |
130 | m_strings.Insert( items[i], idx ); | |
131 | } | |
132 | ||
133 | wxString text = items[i]; | |
134 | if (text == wxEmptyString) | |
135 | text = " "; // menu items can't have empty labels | |
136 | m_popUpMenu->Insert( idx, i+1, text ); | |
137 | m_datas.Insert( NULL, idx ); | |
138 | AssignNewItemClientData(idx, clientData, i, type); | |
139 | } | |
140 | ||
141 | DoAfterItemCountChange(); | |
142 | ||
143 | return pos - 1; | |
144 | } | |
145 | ||
146 | void wxChoice::DoDeleteOneItem(unsigned int n) | |
147 | { | |
148 | wxCHECK_RET( IsValid(n) , wxT("wxChoice::Delete: invalid index") ); | |
149 | ||
150 | if ( HasClientObjectData() ) | |
151 | delete GetClientObject( n ); | |
152 | ||
153 | m_popUpMenu->Delete( m_popUpMenu->FindItemByPosition( n ) ); | |
154 | ||
155 | m_strings.RemoveAt( n ) ; | |
156 | m_datas.RemoveAt( n ) ; | |
157 | ||
158 | DoAfterItemCountChange(); | |
159 | } | |
160 | ||
161 | void wxChoice::DoClear() | |
162 | { | |
163 | for ( unsigned int i = 0 ; i < GetCount() ; i++ ) | |
164 | { | |
165 | m_popUpMenu->Delete( m_popUpMenu->FindItemByPosition( 0 ) ); | |
166 | } | |
167 | ||
168 | m_strings.Empty() ; | |
169 | m_datas.Empty() ; | |
170 | ||
171 | DoAfterItemCountChange(); | |
172 | } | |
173 | ||
174 | // ---------------------------------------------------------------------------- | |
175 | // selection | |
176 | // ---------------------------------------------------------------------------- | |
177 | int wxChoice::GetSelection() const | |
178 | { | |
179 | return GetPeer()->GetValue(); | |
180 | } | |
181 | ||
182 | void wxChoice::SetSelection( int n ) | |
183 | { | |
184 | GetPeer()->SetValue( n ); | |
185 | } | |
186 | ||
187 | // ---------------------------------------------------------------------------- | |
188 | // string list functions | |
189 | // ---------------------------------------------------------------------------- | |
190 | ||
191 | unsigned int wxChoice::GetCount() const | |
192 | { | |
193 | return m_strings.GetCount() ; | |
194 | } | |
195 | ||
196 | int wxChoice::FindString( const wxString& s, bool bCase ) const | |
197 | { | |
198 | #if !wxUSE_STD_CONTAINERS | |
199 | // Avoid assert for non-default args passed to sorted array Index | |
200 | if ( IsSorted() ) | |
201 | bCase = true; | |
202 | #endif | |
203 | ||
204 | return m_strings.Index( s , bCase ) ; | |
205 | } | |
206 | ||
207 | void wxChoice::SetString(unsigned int n, const wxString& s) | |
208 | { | |
209 | wxCHECK_RET( IsValid(n), wxT("wxChoice::SetString(): invalid index") ); | |
210 | ||
211 | m_strings[n] = s ; | |
212 | ||
213 | m_popUpMenu->FindItemByPosition( n )->SetItemLabel( s ) ; | |
214 | } | |
215 | ||
216 | wxString wxChoice::GetString(unsigned int n) const | |
217 | { | |
218 | wxCHECK_MSG( IsValid(n), wxEmptyString, wxT("wxChoice::GetString(): invalid index") ); | |
219 | ||
220 | return m_strings[n] ; | |
221 | } | |
222 | ||
223 | // ---------------------------------------------------------------------------- | |
224 | // client data | |
225 | // ---------------------------------------------------------------------------- | |
226 | void wxChoice::DoSetItemClientData(unsigned int n, void* clientData) | |
227 | { | |
228 | m_datas[n] = (char*)clientData ; | |
229 | } | |
230 | ||
231 | void * wxChoice::DoGetItemClientData(unsigned int n) const | |
232 | { | |
233 | return (void *)m_datas[n]; | |
234 | } | |
235 | ||
236 | bool wxChoice::OSXHandleClicked( double WXUNUSED(timestampsec) ) | |
237 | { | |
238 | SendSelectionChangedEvent(wxEVT_CHOICE); | |
239 | ||
240 | return true ; | |
241 | } | |
242 | ||
243 | wxSize wxChoice::DoGetBestSize() const | |
244 | { | |
245 | // We use the base window size for the height (which is wrong as it doesn't | |
246 | // take the font into account -- TODO) and add some margins to the width | |
247 | // computed by the base class method to account for the arrow. | |
248 | const int lbHeight = wxWindow::DoGetBestSize().y; | |
249 | ||
250 | return wxSize(wxChoiceBase::DoGetBestSize().x + 2*lbHeight + GetCharWidth(), | |
251 | lbHeight); | |
252 | } | |
253 | ||
254 | #endif // wxUSE_CHOICE |