xref: /aoo42x/main/vcl/source/window/btndlg.cxx (revision ad3a95a3)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_vcl.hxx"
26 
27 #include <tools/ref.hxx>
28 #include <tools/debug.hxx>
29 #include <tools/rc.h>
30 
31 #include <svdata.hxx>
32 
33 #include <vcl/button.hxx>
34 #include <vcl/btndlg.hxx>
35 
36 
37 
38 // =======================================================================
39 
40 struct ImplBtnDlgItem
41 {
42 	sal_uInt16				mnId;
43 	sal_Bool				mbOwnButton;
44 	sal_Bool				mbDummyAlign;
45 	long				mnSepSize;
46 	PushButton* 		mpPushButton;
47 };
48 
49 DECLARE_LIST( ImplBtnDlgItemList, ImplBtnDlgItem* )
50 
51 // =======================================================================
52 
53 void ButtonDialog::ImplInitButtonDialogData()
54 {
55 	mpItemList				= new ImplBtnDlgItemList( 8, 8 );
56 	mnButtonSize			= 0;
57 	mnCurButtonId			= 0;
58 	mnFocusButtonId 		= BUTTONDIALOG_BUTTON_NOTFOUND;
59 	mbFormat				= sal_True;
60 }
61 
62 // -----------------------------------------------------------------------
63 
64 ButtonDialog::ButtonDialog( WindowType nType ) :
65 	Dialog( nType )
66 {
67 	ImplInitButtonDialogData();
68 }
69 
70 // -----------------------------------------------------------------------
71 
72 ButtonDialog::ButtonDialog( Window* pParent, WinBits nStyle ) :
73 	Dialog( WINDOW_BUTTONDIALOG )
74 {
75 	ImplInitButtonDialogData();
76 	ImplInit( pParent, nStyle );
77 }
78 
79 // -----------------------------------------------------------------------
80 
81 ButtonDialog::ButtonDialog( Window* pParent, const ResId& rResId ) :
82 	Dialog( WINDOW_BUTTONDIALOG )
83 {
84 	ImplInitButtonDialogData();
85 	rResId.SetRT( RSC_DIALOG ); 	// !!!!!!!!!! RSC_BUTTONDIALOG !!!!!!!!
86 	ImplInit( pParent, ImplInitRes( rResId ) );
87 	ImplLoadRes( rResId );
88 }
89 
90 // -----------------------------------------------------------------------
91 
92 ButtonDialog::~ButtonDialog()
93 {
94 	ImplBtnDlgItem* pItem = mpItemList->First();
95 	while ( pItem )
96 	{
97 		if ( pItem->mpPushButton && pItem->mbOwnButton )
98 			delete pItem->mpPushButton;
99 		delete pItem;
100 		pItem = mpItemList->Next();
101 	}
102 
103 	delete mpItemList;
104 }
105 
106 // -----------------------------------------------------------------------
107 
108 PushButton* ButtonDialog::ImplCreatePushButton( sal_uInt16 nBtnFlags )
109 {
110 	PushButton* pBtn;
111 	WinBits 	nStyle = 0;
112 
113 	if ( nBtnFlags & BUTTONDIALOG_DEFBUTTON )
114 		nStyle |= WB_DEFBUTTON;
115 	if ( nBtnFlags & BUTTONDIALOG_CANCELBUTTON )
116 		pBtn = new CancelButton( this, nStyle );
117 	else if ( nBtnFlags & BUTTONDIALOG_OKBUTTON )
118 		pBtn = new OKButton( this, nStyle );
119 	else if ( nBtnFlags & BUTTONDIALOG_HELPBUTTON )
120 		pBtn = new HelpButton( this, nStyle );
121 	else
122 		pBtn = new PushButton( this, nStyle );
123 
124 	if ( !(nBtnFlags & BUTTONDIALOG_HELPBUTTON) )
125 		pBtn->SetClickHdl( LINK( this, ButtonDialog, ImplClickHdl ) );
126 
127 	return pBtn;
128 }
129 
130 // -----------------------------------------------------------------------
131 
132 ImplBtnDlgItem* ButtonDialog::ImplGetItem( sal_uInt16 nId ) const
133 {
134 	ImplBtnDlgItem* pItem = mpItemList->First();
135 	while ( pItem )
136 	{
137 		if ( pItem->mnId == nId )
138 			return pItem;
139 
140 		pItem = mpItemList->Next();
141 	}
142 
143 	return NULL;
144 }
145 
146 // -----------------------------------------------------------------------
147 
148 long ButtonDialog::ImplGetButtonSize()
149 {
150 	if ( !mbFormat )
151 		return mnButtonSize;
152 
153 	// Calculate ButtonSize
154 	long	nLastSepSize = 0;
155 	long	nSepSize = 0;
156 	long	nButtonCount = 0;
157 	maCtrlSize = Size( IMPL_MINSIZE_BUTTON_WIDTH, IMPL_MINSIZE_BUTTON_HEIGHT );
158 	ImplBtnDlgItem* pItem = mpItemList->First();
159 	while ( pItem )
160 	{
161 		nSepSize += nLastSepSize;
162 
163 		long nTxtWidth = pItem->mpPushButton->GetCtrlTextWidth( pItem->mpPushButton->GetText() );
164 		nTxtWidth += IMPL_EXTRA_BUTTON_WIDTH;
165 		if ( nTxtWidth > maCtrlSize.Width() )
166 			maCtrlSize.Width() = nTxtWidth;
167 		long nTxtHeight = pItem->mpPushButton->GetTextHeight();
168 		nTxtHeight += IMPL_EXTRA_BUTTON_HEIGHT;
169 		if ( nTxtHeight > maCtrlSize.Height() )
170 			maCtrlSize.Height() = nTxtHeight;
171 
172 		nSepSize += pItem->mnSepSize;
173 
174 		if ( GetStyle() & WB_HORZ )
175 			nLastSepSize = IMPL_SEP_BUTTON_X;
176 		else
177 			nLastSepSize = IMPL_SEP_BUTTON_Y;
178 
179 		nButtonCount++;
180 
181 		pItem = mpItemList->Next();
182 	}
183 
184 	if ( GetStyle() & WB_HORZ )
185 		mnButtonSize  = nSepSize + (nButtonCount*maCtrlSize.Width());
186 	else
187 		mnButtonSize = nSepSize + (nButtonCount*maCtrlSize.Height());
188 
189 	return mnButtonSize;
190 }
191 
192 // -----------------------------------------------------------------------
193 
194 void ButtonDialog::ImplPosControls()
195 {
196 	if ( !mbFormat )
197 		return;
198 
199 	// Create PushButtons and determine Sizes
200 	ImplGetButtonSize();
201 
202 	// determine dialog size
203 	ImplBtnDlgItem* pItem;
204 	Size			aDlgSize = maPageSize;
205 	long			nX;
206 	long			nY;
207 	if ( GetStyle() & WB_HORZ )
208 	{
209 		if ( mnButtonSize+(IMPL_DIALOG_OFFSET*2) > aDlgSize.Width() )
210 			aDlgSize.Width() = mnButtonSize+(IMPL_DIALOG_OFFSET*2);
211 		if ( GetStyle() & WB_LEFT )
212 			nX = IMPL_DIALOG_OFFSET;
213 		else if ( GetStyle() & WB_RIGHT )
214 			nX = aDlgSize.Width()-mnButtonSize-IMPL_DIALOG_OFFSET;
215 		else
216 			nX = (aDlgSize.Width()-mnButtonSize)/2;
217 
218 		aDlgSize.Height() += IMPL_DIALOG_OFFSET+maCtrlSize.Height();
219 		nY = aDlgSize.Height()-maCtrlSize.Height()-IMPL_DIALOG_OFFSET;
220 	}
221 	else
222 	{
223 		if ( mnButtonSize+(IMPL_DIALOG_OFFSET*2) > aDlgSize.Height() )
224 			aDlgSize.Height() = mnButtonSize+(IMPL_DIALOG_OFFSET*2);
225 		if ( GetStyle() & WB_BOTTOM )
226 			nY = aDlgSize.Height()-mnButtonSize-IMPL_DIALOG_OFFSET;
227 		else if ( GetStyle() & WB_VCENTER )
228 			nY = (aDlgSize.Height()-mnButtonSize)/2;
229 		else
230 			nY = IMPL_DIALOG_OFFSET;
231 
232 		aDlgSize.Width() += IMPL_DIALOG_OFFSET+maCtrlSize.Width();
233 		nX = aDlgSize.Width()-maCtrlSize.Width()-IMPL_DIALOG_OFFSET;
234 	}
235 
236 	// Arrange PushButtons
237 	pItem = mpItemList->First();
238 	while ( pItem )
239 	{
240 		if ( GetStyle() & WB_HORZ )
241 			nX += pItem->mnSepSize;
242 		else
243 			nY += pItem->mnSepSize;
244 		pItem->mpPushButton->SetPosSizePixel( Point( nX, nY ), maCtrlSize );
245 		pItem->mpPushButton->Show();
246 		if ( GetStyle() & WB_HORZ )
247 			nX += maCtrlSize.Width()+IMPL_SEP_BUTTON_X;
248 		else
249 			nY += maCtrlSize.Height()+IMPL_SEP_BUTTON_Y;
250 
251 		pItem = mpItemList->Next();
252 	}
253 
254 	SetOutputSizePixel( aDlgSize );
255 
256 	mbFormat = sal_False;
257 }
258 
259 // -----------------------------------------------------------------------
260 
261 IMPL_LINK( ButtonDialog, ImplClickHdl, PushButton*, pBtn )
262 {
263 	ImplBtnDlgItem* pItem = mpItemList->First();
264 	while ( pItem )
265 	{
266 		if ( pItem->mpPushButton == pBtn )
267 		{
268 			mnCurButtonId = pItem->mnId;
269 			Click();
270 			break;
271 		}
272 
273 		pItem = mpItemList->Next();
274 	}
275 
276 	return 0;
277 }
278 
279 // -----------------------------------------------------------------------
280 
281 void ButtonDialog::Resize()
282 {
283 }
284 
285 // -----------------------------------------------------------------------
286 
287 void ButtonDialog::StateChanged( StateChangedType nType )
288 {
289 	if ( nType == STATE_CHANGE_INITSHOW )
290 	{
291 		ImplPosControls();
292 //IAccessibility2 Implementation 2009-----
293 		ImplBtnDlgItem* pItem = mpItemList->First();
294 		while ( pItem )
295 		{
296 			if ( pItem->mpPushButton && pItem->mbOwnButton )
297 				pItem->mpPushButton->SetZOrder(0, WINDOW_ZORDER_LAST);
298 			pItem = mpItemList->Next();
299 		}
300 //-----IAccessibility2 Implementation 2009
301 
302 		// Focus evt. auf den entsprechenden Button setzen
303 		if ( mnFocusButtonId != BUTTONDIALOG_BUTTON_NOTFOUND )
304 		{
305 			ImplBtnDlgItem* pItem = mpItemList->First();
306 			while ( pItem )
307 			{
308 				if ( pItem->mnId == mnFocusButtonId )
309 				{
310 					if ( pItem->mpPushButton->IsVisible() )
311 						pItem->mpPushButton->GrabFocus();
312 					break;
313 				}
314 
315 				pItem = mpItemList->Next();
316 			}
317 		}
318 	}
319 
320 	Dialog::StateChanged( nType );
321 }
322 
323 // -----------------------------------------------------------------------
324 
325 void ButtonDialog::Click()
326 {
327 	if ( !maClickHdl )
328 	{
329 		if ( IsInExecute() )
330 			EndDialog( GetCurButtonId() );
331 	}
332 	else
333 		maClickHdl.Call( this );
334 }
335 
336 // -----------------------------------------------------------------------
337 
338 void ButtonDialog::AddButton( const XubString& rText, sal_uInt16 nId,
339 							  sal_uInt16 nBtnFlags, long nSepPixel )
340 {
341 	// PageItem anlegen
342 	ImplBtnDlgItem* pItem	= new ImplBtnDlgItem;
343 	pItem->mnId 			= nId;
344 	pItem->mbOwnButton		= sal_True;
345 	pItem->mnSepSize		= nSepPixel;
346 	pItem->mpPushButton 	= ImplCreatePushButton( nBtnFlags );
347 	if ( rText.Len() )
348 		pItem->mpPushButton->SetText( rText );
349 
350 	// In die Liste eintragen
351 	mpItemList->Insert( pItem, LIST_APPEND );
352 
353 	if ( nBtnFlags & BUTTONDIALOG_FOCUSBUTTON )
354 		mnFocusButtonId = nId;
355 
356 	mbFormat = sal_True;
357 }
358 
359 // -----------------------------------------------------------------------
360 
361 void ButtonDialog::AddButton( StandardButtonType eType, sal_uInt16 nId,
362 							  sal_uInt16 nBtnFlags, long nSepPixel )
363 {
364 	// PageItem anlegen
365 	ImplBtnDlgItem* pItem	= new ImplBtnDlgItem;
366 	pItem->mnId 			= nId;
367 	pItem->mbOwnButton		= sal_True;
368 	pItem->mnSepSize		= nSepPixel;
369 
370 	if ( eType == BUTTON_OK )
371 		nBtnFlags |= BUTTONDIALOG_OKBUTTON;
372 	else if ( eType == BUTTON_HELP )
373 		nBtnFlags |= BUTTONDIALOG_HELPBUTTON;
374 	else if ( (eType == BUTTON_CANCEL) || (eType == BUTTON_CLOSE) )
375 		nBtnFlags |= BUTTONDIALOG_CANCELBUTTON;
376 	pItem->mpPushButton = ImplCreatePushButton( nBtnFlags );
377 
378 	// Standard-Buttons have the right text already
379 	if ( !((eType == BUTTON_OK) 	&& (pItem->mpPushButton->GetType() == WINDOW_OKBUTTON)) ||
380 		 !((eType == BUTTON_CANCEL) && (pItem->mpPushButton->GetType() == WINDOW_CANCELBUTTON)) ||
381 		 !((eType == BUTTON_HELP)	&& (pItem->mpPushButton->GetType() == WINDOW_HELPBUTTON)) )
382 	{
383 		pItem->mpPushButton->SetText( Button::GetStandardText( eType ) );
384 		pItem->mpPushButton->SetHelpText( Button::GetStandardHelpText( eType ) );
385 	}
386 
387 	if ( nBtnFlags & BUTTONDIALOG_FOCUSBUTTON )
388 		mnFocusButtonId = nId;
389 
390 	// In die Liste eintragen
391 	mpItemList->Insert( pItem, LIST_APPEND );
392 
393 	mbFormat = sal_True;
394 }
395 
396 // -----------------------------------------------------------------------
397 
398 void ButtonDialog::AddButton( PushButton* pBtn, sal_uInt16 nId,
399 							  sal_uInt16 nBtnFlags, long nSepPixel )
400 {
401 	// PageItem anlegen
402 	ImplBtnDlgItem* pItem	= new ImplBtnDlgItem;
403 	pItem->mnId 			= nId;
404 	pItem->mbOwnButton		= sal_False;
405 	pItem->mnSepSize		= nSepPixel;
406 	pItem->mpPushButton 	= pBtn;
407 
408 	if ( nBtnFlags & BUTTONDIALOG_FOCUSBUTTON )
409 		mnFocusButtonId = nId;
410 
411 	// In die View-Liste eintragen
412 	mpItemList->Insert( pItem, LIST_APPEND );
413 
414 	mbFormat = sal_True;
415 }
416 
417 // -----------------------------------------------------------------------
418 
419 void ButtonDialog::RemoveButton( sal_uInt16 nId )
420 {
421 	ImplBtnDlgItem* pItem = mpItemList->First();
422 	while ( pItem )
423 	{
424 		if ( pItem->mnId == nId )
425 		{
426 			pItem->mpPushButton->Hide();
427 			if ( pItem->mbOwnButton )
428 				delete pItem->mpPushButton;
429 			delete pItem;
430 			mpItemList->Remove();
431 			mbFormat = sal_True;
432 			break;
433 		}
434 
435 		pItem = mpItemList->Next();
436 	}
437 
438 	DBG_ERRORFILE( "ButtonDialog::RemoveButton(): ButtonId invalid" );
439 }
440 
441 // -----------------------------------------------------------------------
442 
443 void ButtonDialog::Clear()
444 {
445 	ImplBtnDlgItem* pItem = mpItemList->First();
446 	while ( pItem )
447 	{
448 		pItem->mpPushButton->Hide();
449 		if ( pItem->mbOwnButton )
450 			delete pItem->mpPushButton;
451 		delete pItem;
452 		pItem = mpItemList->Next();
453 	}
454 
455 	mpItemList->Clear();
456 	mbFormat = sal_True;
457 }
458 
459 // -----------------------------------------------------------------------
460 
461 sal_uInt16 ButtonDialog::GetButtonCount() const
462 {
463 	return (sal_uInt16)mpItemList->Count();
464 }
465 
466 // -----------------------------------------------------------------------
467 
468 sal_uInt16 ButtonDialog::GetButtonId( sal_uInt16 nButton ) const
469 {
470 	if ( nButton < mpItemList->Count() )
471 		return (sal_uInt16)mpItemList->GetObject( nButton )->mnId;
472 	else
473 		return BUTTONDIALOG_BUTTON_NOTFOUND;
474 }
475 
476 // -----------------------------------------------------------------------
477 
478 PushButton* ButtonDialog::GetPushButton( sal_uInt16 nId ) const
479 {
480 	ImplBtnDlgItem* pItem = ImplGetItem( nId );
481 
482 	if ( pItem )
483 		return pItem->mpPushButton;
484 	else
485 		return NULL;
486 }
487 
488 // -----------------------------------------------------------------------
489 
490 void ButtonDialog::SetButtonText( sal_uInt16 nId, const XubString& rText )
491 {
492 	ImplBtnDlgItem* pItem = ImplGetItem( nId );
493 
494 	if ( pItem )
495 	{
496 		pItem->mpPushButton->SetText( rText );
497 		mbFormat = sal_True;
498 	}
499 }
500 
501 // -----------------------------------------------------------------------
502 
503 XubString ButtonDialog::GetButtonText( sal_uInt16 nId ) const
504 {
505 	ImplBtnDlgItem* pItem = ImplGetItem( nId );
506 
507 	if ( pItem )
508 		return pItem->mpPushButton->GetText();
509 	else
510 		return ImplGetSVEmptyStr();
511 }
512 
513 // -----------------------------------------------------------------------
514 
515 void ButtonDialog::SetButtonHelpText( sal_uInt16 nId, const XubString& rText )
516 {
517 	ImplBtnDlgItem* pItem = ImplGetItem( nId );
518 
519 	if ( pItem )
520 		pItem->mpPushButton->SetHelpText( rText );
521 }
522 
523 // -----------------------------------------------------------------------
524 
525 XubString ButtonDialog::GetButtonHelpText( sal_uInt16 nId ) const
526 {
527 	ImplBtnDlgItem* pItem = ImplGetItem( nId );
528 
529 	if ( pItem )
530 		return pItem->mpPushButton->GetHelpText();
531 	else
532 		return ImplGetSVEmptyStr();
533 }
534 
535 // -----------------------------------------------------------------------
536 
537 void ButtonDialog::SetButtonHelpId( sal_uInt16 nId, const rtl::OString& rHelpId )
538 {
539 	ImplBtnDlgItem* pItem = ImplGetItem( nId );
540 
541 	if ( pItem )
542 		pItem->mpPushButton->SetHelpId( rHelpId );
543 }
544 
545 // -----------------------------------------------------------------------
546 
547 rtl::OString ButtonDialog::GetButtonHelpId( sal_uInt16 nId ) const
548 {
549 	ImplBtnDlgItem* pItem = ImplGetItem( nId );
550 
551 	return pItem ? rtl::OString( pItem->mpPushButton->GetHelpId() ) : rtl::OString();
552 }
553