Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 :
21 : #include <limits.h>
22 : #include <stdlib.h>
23 : #include <algorithm>
24 : #include <vcl/builder.hxx>
25 : #include <vcl/msgbox.hxx>
26 : #include <unotools/viewoptions.hxx>
27 :
28 : #include "appdata.hxx"
29 : #include "sfxtypes.hxx"
30 : #include <sfx2/minarray.hxx>
31 : #include <sfx2/tabdlg.hxx>
32 : #include <sfx2/viewfrm.hxx>
33 : #include <sfx2/app.hxx>
34 : #include "sfx2/sfxresid.hxx"
35 : #include "sfx2/sfxhelp.hxx"
36 : #include <sfx2/ctrlitem.hxx>
37 : #include <sfx2/bindings.hxx>
38 : #include <sfx2/sfxdlg.hxx>
39 : #include <sfx2/itemconnect.hxx>
40 :
41 : #include "dialog.hrc"
42 : #include "helpid.hrc"
43 :
44 : using namespace ::com::sun::star::uno;
45 : using namespace ::rtl;
46 :
47 : #define USERITEM_NAME OUString("UserItem")
48 :
49 0 : TYPEINIT1(SfxTabDialogItem,SfxSetItem);
50 :
51 0 : struct TabPageImpl
52 : {
53 : sal_Bool mbStandard;
54 : sfx::ItemConnectionArray maItemConn;
55 : ::com::sun::star::uno::Reference< ::com::sun::star::frame::XFrame > mxFrame;
56 :
57 0 : TabPageImpl() : mbStandard( sal_False ) {}
58 : };
59 :
60 : struct Data_Impl
61 : {
62 : sal_uInt16 nId; // The ID
63 : CreateTabPage fnCreatePage; // Pointer to Factory
64 : GetTabPageRanges fnGetRanges; // Pointer to Ranges-Function
65 : SfxTabPage* pTabPage; // The TabPage itself
66 : sal_Bool bOnDemand; // Flag: ItemSet onDemand
67 : sal_Bool bRefresh; // Flag: Page must be re-initialized
68 :
69 : // Constructor
70 0 : Data_Impl( sal_uInt16 Id, CreateTabPage fnPage,
71 : GetTabPageRanges fnRanges, sal_Bool bDemand ) :
72 :
73 : nId ( Id ),
74 : fnCreatePage( fnPage ),
75 : fnGetRanges ( fnRanges ),
76 : pTabPage ( 0 ),
77 : bOnDemand ( bDemand ),
78 0 : bRefresh ( sal_False )
79 : {
80 0 : if ( !fnCreatePage )
81 : {
82 0 : SfxAbstractDialogFactory* pFact = SfxAbstractDialogFactory::Create();
83 0 : if ( pFact )
84 : {
85 0 : fnCreatePage = pFact->GetTabPageCreatorFunc( nId );
86 0 : fnGetRanges = pFact->GetTabPageRangesFunc( nId );
87 : }
88 : }
89 0 : }
90 : };
91 :
92 0 : SfxTabDialogItem::SfxTabDialogItem( const SfxTabDialogItem& rAttr, SfxItemPool* pItemPool )
93 0 : : SfxSetItem( rAttr, pItemPool )
94 : {
95 0 : }
96 :
97 0 : SfxTabDialogItem::SfxTabDialogItem( sal_uInt16 nId, const SfxItemSet& rItemSet )
98 0 : : SfxSetItem( nId, rItemSet )
99 : {
100 0 : }
101 :
102 0 : SfxPoolItem* SfxTabDialogItem::Clone(SfxItemPool* pToPool) const
103 : {
104 0 : return new SfxTabDialogItem( *this, pToPool );
105 : }
106 :
107 0 : SfxPoolItem* SfxTabDialogItem::Create(SvStream& /*rStream*/, sal_uInt16 /*nVersion*/) const
108 : {
109 : OSL_FAIL( "Use it only in UI!" );
110 0 : return NULL;
111 : }
112 :
113 : class SfxTabDialogController : public SfxControllerItem
114 : {
115 : SfxTabDialog* pDialog;
116 : const SfxItemSet* pSet;
117 : public:
118 : SfxTabDialogController( sal_uInt16 nSlotId, SfxBindings& rBindings, SfxTabDialog* pDlg )
119 : : SfxControllerItem( nSlotId, rBindings )
120 : , pDialog( pDlg )
121 : , pSet( NULL )
122 : {}
123 :
124 : ~SfxTabDialogController();
125 :
126 : virtual void StateChanged( sal_uInt16 nSID, SfxItemState eState, const SfxPoolItem* pState );
127 : };
128 :
129 0 : SfxTabDialogController::~SfxTabDialogController()
130 : {
131 0 : delete pSet;
132 0 : }
133 :
134 0 : void SfxTabDialogController::StateChanged( sal_uInt16 /*nSID*/, SfxItemState /*eState*/, const SfxPoolItem* pState )
135 : {
136 0 : const SfxSetItem* pSetItem = PTR_CAST( SfxSetItem, pState );
137 0 : if ( pSetItem )
138 : {
139 0 : pSet = pDialog->pSet = pSetItem->GetItemSet().Clone();
140 0 : sal_Bool bDialogStarted = sal_False;
141 0 : for ( sal_uInt16 n=0; n<pDialog->m_pTabCtrl->GetPageCount(); n++ )
142 : {
143 0 : sal_uInt16 nPageId = pDialog->m_pTabCtrl->GetPageId( n );
144 0 : SfxTabPage* pTabPage = dynamic_cast<SfxTabPage*> (pDialog->m_pTabCtrl->GetTabPage( nPageId ));
145 0 : if ( pTabPage )
146 : {
147 0 : pTabPage->Reset( pSetItem->GetItemSet() );
148 0 : bDialogStarted = sal_True;
149 : }
150 : }
151 :
152 0 : if ( bDialogStarted )
153 0 : pDialog->Show();
154 : }
155 : else
156 0 : pDialog->Hide();
157 0 : }
158 :
159 0 : DECL_PTRARRAY(SfxTabDlgData_Impl, Data_Impl *, 4,4)
160 :
161 : struct TabDlg_Impl
162 : {
163 : sal_Bool bModified : 1,
164 : bModal : 1,
165 : bInOK : 1,
166 : bHideResetBtn : 1;
167 : SfxTabDlgData_Impl* pData;
168 :
169 : SfxTabDialogController* pController;
170 :
171 0 : TabDlg_Impl( sal_uInt8 nCnt ) :
172 :
173 : bModified ( sal_False ),
174 : bModal ( sal_True ),
175 : bInOK ( sal_False ),
176 : bHideResetBtn ( sal_False ),
177 0 : pData ( new SfxTabDlgData_Impl( nCnt ) ),
178 0 : pController ( NULL )
179 0 : {}
180 : };
181 :
182 : Data_Impl* Find( SfxTabDlgData_Impl& rArr, sal_uInt16 nId, sal_uInt16* pPos = 0 );
183 :
184 0 : Data_Impl* Find( SfxTabDlgData_Impl& rArr, sal_uInt16 nId, sal_uInt16* pPos )
185 : {
186 0 : const sal_uInt16 nCount = rArr.Count();
187 :
188 0 : for ( sal_uInt16 i = 0; i < nCount; ++i )
189 : {
190 0 : Data_Impl* pObj = rArr[i];
191 :
192 0 : if ( pObj->nId == nId )
193 : {
194 0 : if ( pPos )
195 0 : *pPos = i;
196 0 : return pObj;
197 : }
198 : }
199 0 : return 0;
200 : }
201 :
202 0 : void SfxTabPage::SetFrame(const ::com::sun::star::uno::Reference< ::com::sun::star::frame::XFrame >& xFrame)
203 : {
204 0 : if (pImpl)
205 0 : pImpl->mxFrame = xFrame;
206 0 : }
207 :
208 0 : ::com::sun::star::uno::Reference< ::com::sun::star::frame::XFrame > SfxTabPage::GetFrame()
209 : {
210 0 : if (pImpl)
211 0 : return pImpl->mxFrame;
212 0 : return ::com::sun::star::uno::Reference< ::com::sun::star::frame::XFrame >();
213 : }
214 :
215 0 : SfxTabPage::SfxTabPage( Window *pParent,
216 : const ResId &rResId, const SfxItemSet &rAttrSet ) :
217 :
218 : /* [Description]
219 :
220 : Constructor
221 : */
222 :
223 : TabPage( pParent, rResId ),
224 :
225 : pSet ( &rAttrSet ),
226 : bHasExchangeSupport ( sal_False ),
227 : pTabDlg ( NULL ),
228 0 : pImpl ( new TabPageImpl )
229 :
230 : {
231 0 : }
232 :
233 :
234 0 : SfxTabPage::SfxTabPage(Window *pParent, const rtl::OString& rID, const rtl::OUString& rUIXMLDescription, const SfxItemSet &rAttrSet)
235 : : TabPage(pParent, rID, rUIXMLDescription)
236 : , pSet ( &rAttrSet )
237 : , bHasExchangeSupport ( sal_False )
238 : , pTabDlg ( NULL )
239 0 : , pImpl ( new TabPageImpl )
240 : {
241 0 : }
242 :
243 : // -----------------------------------------------------------------------
244 0 : SfxTabPage:: SfxTabPage( Window *pParent, WinBits nStyle, const SfxItemSet &rAttrSet ) :
245 : TabPage(pParent, nStyle),
246 : pSet ( &rAttrSet ),
247 : bHasExchangeSupport ( sal_False ),
248 : pTabDlg ( NULL ),
249 0 : pImpl ( new TabPageImpl )
250 : {
251 0 : }
252 : // -----------------------------------------------------------------------
253 :
254 0 : SfxTabPage::~SfxTabPage()
255 :
256 : /* [Description]
257 :
258 : Destructor
259 : */
260 :
261 : {
262 0 : delete pImpl;
263 0 : }
264 :
265 : // -----------------------------------------------------------------------
266 :
267 0 : sal_Bool SfxTabPage::FillItemSet( SfxItemSet& rSet )
268 : {
269 0 : return pImpl->maItemConn.DoFillItemSet( rSet, GetItemSet() );
270 : }
271 :
272 : // -----------------------------------------------------------------------
273 :
274 0 : void SfxTabPage::Reset( const SfxItemSet& rSet )
275 : {
276 0 : pImpl->maItemConn.DoApplyFlags( rSet );
277 0 : pImpl->maItemConn.DoReset( rSet );
278 0 : }
279 :
280 : // -----------------------------------------------------------------------
281 :
282 0 : void SfxTabPage::ActivatePage( const SfxItemSet& )
283 :
284 : /* [Description]
285 :
286 : Default implementation of the virtual ActivatePage method. This method is
287 : called when a page of dialogue supports the exchange of data between pages.
288 : <SfxTabPage::DeactivatePage(SfxItemSet *)>
289 : */
290 :
291 : {
292 0 : }
293 :
294 : // -----------------------------------------------------------------------
295 :
296 0 : int SfxTabPage::DeactivatePage( SfxItemSet* )
297 :
298 : /* [Description]
299 :
300 : Default implementation of the virtual DeactivatePage method. This method is
301 : called by Sfx when leaving a page; the application can, through the return
302 : value, control whether to leave the page. If the page is displayed through
303 : bHasExchangeSupport which supports data exchange between pages, then a
304 : pointer to the exchange set is passed as parameter. This takes on data for
305 : the exchange, then the set is available as a parameter in
306 : <SfxTabPage::ActivatePage(const SfxItemSet &)>.
307 :
308 : [Return value]
309 :
310 : LEAVE_PAGE; Allow leaving the page
311 : */
312 :
313 : {
314 0 : return LEAVE_PAGE;
315 : }
316 :
317 : // -----------------------------------------------------------------------
318 :
319 0 : void SfxTabPage::FillUserData()
320 :
321 : /* [Description]
322 :
323 : Virtual method is called by the base class in the destructor to save
324 : specific information of the TabPage in the ini-file. When overloading a
325 : string must be compiled, which is then flushed with the <SetUserData()>.
326 : */
327 :
328 : {
329 0 : }
330 :
331 : // -----------------------------------------------------------------------
332 :
333 0 : sal_Bool SfxTabPage::IsReadOnly() const
334 : {
335 0 : return sal_False;
336 : }
337 :
338 : // -----------------------------------------------------------------------
339 :
340 0 : const SfxPoolItem* SfxTabPage::GetItem( const SfxItemSet& rSet, sal_uInt16 nSlot, sal_Bool bDeep )
341 :
342 : /* [Description]
343 :
344 : static Method: hereby are the implementations of the TabPage code
345 : beeing simplified.
346 : */
347 :
348 : {
349 0 : const SfxItemPool* pPool = rSet.GetPool();
350 0 : sal_uInt16 nWh = pPool->GetWhich( nSlot, bDeep );
351 0 : const SfxPoolItem* pItem = 0;
352 0 : rSet.GetItemState( nWh, sal_True, &pItem );
353 :
354 0 : if ( !pItem && nWh != nSlot )
355 0 : pItem = &pPool->GetDefaultItem( nWh );
356 0 : return pItem;
357 : }
358 :
359 : // -----------------------------------------------------------------------
360 :
361 0 : const SfxPoolItem* SfxTabPage::GetOldItem( const SfxItemSet& rSet,
362 : sal_uInt16 nSlot, sal_Bool bDeep )
363 :
364 : /* [Description]
365 :
366 : This method returns an attribute for comparison of the old value.
367 : */
368 :
369 : {
370 0 : const SfxItemSet& rOldSet = GetItemSet();
371 0 : sal_uInt16 nWh = GetWhich( nSlot, bDeep );
372 0 : const SfxPoolItem* pItem = 0;
373 :
374 0 : if ( pImpl->mbStandard && rOldSet.GetParent() )
375 0 : pItem = GetItem( *rOldSet.GetParent(), nSlot );
376 0 : else if ( rSet.GetParent() &&
377 0 : SFX_ITEM_DONTCARE == rSet.GetItemState( nWh ) )
378 0 : pItem = GetItem( *rSet.GetParent(), nSlot );
379 : else
380 0 : pItem = GetItem( rOldSet, nSlot );
381 0 : return pItem;
382 : }
383 :
384 0 : void SfxTabPage::PageCreated( SfxAllItemSet /*aSet*/ )
385 : {
386 : DBG_ASSERT(0, "SfxTabPage::PageCreated should not be called");
387 0 : }
388 :
389 : // -----------------------------------------------------------------------
390 :
391 0 : void SfxTabPage::AddItemConnection( sfx::ItemConnectionBase* pConnection )
392 : {
393 0 : pImpl->maItemConn.AddConnection( pConnection );
394 0 : }
395 :
396 : #define INI_LIST(ItemSetPtr) \
397 : pSet(ItemSetPtr) \
398 : , pOutSet(0) \
399 : , pRanges(0) \
400 : , nResId(rResId.GetId()) \
401 : , nAppPageId(USHRT_MAX) \
402 : , bItemsReset(sal_False) \
403 : , bFmt(bEditFmt)\
404 : , pExampleSet(0)
405 :
406 : // -----------------------------------------------------------------------
407 :
408 0 : SfxTabDialog::SfxTabDialog
409 :
410 : /* [Description]
411 :
412 : Constructor
413 : */
414 :
415 : (
416 : SfxViewFrame* pViewFrame, // Frame, to which the Dialog belongs
417 : Window* pParent, // Parent Window
418 : const ResId& rResId, // ResourceId
419 : const SfxItemSet* pItemSet, // Itemset with the data;
420 : // can be NULL, when Pages are onDemand
421 : sal_Bool bEditFmt, // Flag: templates are processed
422 : // when yes -> additional Button for standard
423 : const String* pUserButtonText // Text for UserButton;
424 : // if != 0, the UserButton is created
425 : )
426 : : TabDialog(pParent, rResId)
427 : , pFrame(pViewFrame)
428 0 : , INI_LIST(pItemSet)
429 : {
430 0 : Init_Impl( bFmt, pUserButtonText, &rResId );
431 0 : }
432 :
433 0 : SfxTabDialog::SfxTabDialog
434 : (
435 : SfxViewFrame* pViewFrame, // Frame, to which the Dialog belongs
436 : Window* pParent, // Parent Window
437 : const rtl::OString& rID, const rtl::OUString& rUIXMLDescription, //Dialog Name, Dialog .ui path
438 : const SfxItemSet* pItemSet, // Itemset with the data;
439 : // can be NULL, when Pages are onDemand
440 : sal_Bool bEditFmt, // Flag: templates are processed
441 : // when yes -> additional Button for standard
442 : const String* pUserButtonText // Text for UserButton;
443 : // if != 0, the UserButton is created
444 : )
445 : : TabDialog(pParent, rID, rUIXMLDescription)
446 : , pFrame(pViewFrame)
447 : , pSet(pItemSet)
448 : , pOutSet(0)
449 : , pRanges(0)
450 : , nResId(0)
451 : , nAppPageId(USHRT_MAX)
452 : , bItemsReset(sal_False)
453 : , bFmt(bEditFmt)
454 0 : , pExampleSet(0)
455 : {
456 0 : Init_Impl( bFmt, pUserButtonText, NULL );
457 0 : }
458 :
459 : // -----------------------------------------------------------------------
460 :
461 0 : SfxTabDialog::SfxTabDialog
462 :
463 : /* [Description]
464 :
465 : Constructor, temporary without Frame
466 : */
467 :
468 : (
469 : Window* pParent, // Parent Window
470 : const ResId& rResId, // ResourceId
471 : const SfxItemSet* pItemSet, // Itemset with the data;
472 : // can be NULL, when Pages are onDemand
473 : sal_Bool bEditFmt, // Flag: templates are processed
474 : // when yes -> additional Button for standard
475 : const String* pUserButtonText // Text for UserButton;
476 : // if != 0, the UserButton is created
477 : )
478 : : TabDialog(pParent, rResId)
479 : , pFrame(0)
480 0 : , INI_LIST(pItemSet)
481 : {
482 0 : Init_Impl( bFmt, pUserButtonText, &rResId );
483 : DBG_WARNING( "Please use the Construtor with the ViewFrame" );
484 0 : }
485 :
486 : // -----------------------------------------------------------------------
487 :
488 0 : SfxTabDialog::~SfxTabDialog()
489 : {
490 0 : SavePosAndId();
491 :
492 0 : const sal_uInt16 nCount = pImpl->pData->Count();
493 0 : for ( sal_uInt16 i = 0; i < nCount; ++i )
494 : {
495 0 : Data_Impl* pDataObject = pImpl->pData->GetObject(i);
496 :
497 0 : if ( pDataObject->pTabPage )
498 : {
499 : // save settings of all pages (user data)
500 0 : pDataObject->pTabPage->FillUserData();
501 0 : String aPageData( pDataObject->pTabPage->GetUserData() );
502 0 : if ( aPageData.Len() )
503 : {
504 : // save settings of all pages (user data)
505 0 : SvtViewOptions aPageOpt( E_TABPAGE, String::CreateFromInt32( pDataObject->nId ) );
506 0 : aPageOpt.SetUserItem( USERITEM_NAME, makeAny( OUString( aPageData ) ) );
507 : }
508 :
509 0 : if ( pDataObject->bOnDemand )
510 0 : delete (SfxItemSet*)&pDataObject->pTabPage->GetItemSet();
511 0 : delete pDataObject->pTabPage;
512 : }
513 0 : delete pDataObject;
514 : }
515 :
516 0 : delete pImpl->pController;
517 0 : delete pImpl->pData;
518 0 : delete pImpl;
519 0 : delete pOutSet;
520 0 : delete pExampleSet;
521 0 : delete [] pRanges;
522 :
523 0 : if (m_bOwnsBaseFmtBtn)
524 0 : delete m_pBaseFmtBtn;
525 0 : if (m_bOwnsResetBtn)
526 0 : delete m_pResetBtn;
527 0 : if (m_bOwnsHelpBtn)
528 0 : delete m_pHelpBtn;
529 0 : if (m_bOwnsCancelBtn)
530 0 : delete m_pCancelBtn;
531 0 : if (m_bOwnsUserBtn)
532 0 : delete m_pUserBtn;
533 0 : if (m_bOwnsApplyBtn)
534 0 : delete m_pApplyBtn;
535 0 : if (m_bOwnsOKBtn)
536 0 : delete m_pOKBtn;
537 0 : if (m_bOwnsActionArea)
538 0 : delete m_pActionArea;
539 0 : if (m_bOwnsTabCtrl)
540 0 : delete m_pTabCtrl;
541 0 : if (m_bOwnsVBox)
542 0 : delete m_pBox;
543 0 : }
544 :
545 : // -----------------------------------------------------------------------
546 :
547 0 : void SfxTabDialog::Init_Impl( sal_Bool bFmtFlag, const String* pUserButtonText, const ResId *pResId )
548 :
549 : /* [Description]
550 :
551 : internal initialization of the dialogue
552 : */
553 :
554 : {
555 0 : m_pBox = get_content_area();
556 0 : m_bOwnsVBox = m_pBox == NULL;
557 0 : if (m_bOwnsVBox)
558 : {
559 0 : m_pBox = new VclVBox(this, false, 7);
560 0 : m_pBox->set_expand(true);
561 : }
562 :
563 0 : m_pTabCtrl = m_pUIBuilder ? m_pUIBuilder->get<TabControl>("tabcontrol") : NULL;
564 0 : m_bOwnsTabCtrl = m_pTabCtrl == NULL;
565 0 : if (m_bOwnsTabCtrl)
566 : {
567 0 : m_pTabCtrl = new TabControl(m_pBox, ResId(ID_TABCONTROL, *pResId->GetResMgr()));
568 0 : m_pTabCtrl->set_expand(true);
569 : }
570 :
571 0 : m_pActionArea = get_action_area();
572 0 : m_bOwnsActionArea = m_pActionArea == NULL;
573 0 : if (m_bOwnsActionArea)
574 0 : m_pActionArea = new VclHButtonBox(m_pBox);
575 :
576 0 : m_pOKBtn = m_pUIBuilder ? m_pUIBuilder->get<OKButton>("ok") : NULL;
577 0 : m_bOwnsOKBtn = m_pOKBtn == NULL;
578 0 : if (m_bOwnsOKBtn)
579 0 : m_pOKBtn = new OKButton(m_pActionArea);
580 :
581 0 : m_pApplyBtn = m_pUIBuilder ? m_pUIBuilder->get<PushButton>("apply") : NULL;
582 0 : m_bOwnsApplyBtn = m_pApplyBtn == NULL;
583 0 : if (m_bOwnsApplyBtn)
584 0 : m_pApplyBtn = NULL;
585 :
586 0 : m_pUserBtn = m_pUIBuilder ? m_pUIBuilder->get<PushButton>("user") : NULL;
587 0 : m_bOwnsUserBtn = m_pUserBtn == NULL;
588 0 : if (m_bOwnsUserBtn)
589 0 : m_pUserBtn = pUserButtonText ? new PushButton(m_pActionArea) : NULL;
590 :
591 0 : m_pCancelBtn = m_pUIBuilder ? m_pUIBuilder->get<CancelButton>("cancel") : NULL;
592 0 : m_bOwnsCancelBtn = m_pCancelBtn == NULL;
593 0 : if (m_bOwnsCancelBtn)
594 0 : m_pCancelBtn = new CancelButton(m_pActionArea);
595 :
596 0 : m_pHelpBtn = m_pUIBuilder ? m_pUIBuilder->get<HelpButton>("help") : NULL;
597 0 : m_bOwnsHelpBtn = m_pHelpBtn == NULL;
598 0 : if (m_bOwnsHelpBtn)
599 0 : m_pHelpBtn = new HelpButton(m_pActionArea);
600 :
601 0 : m_pResetBtn = m_pUIBuilder ? m_pUIBuilder->get<PushButton>("reset") : NULL;
602 0 : m_bOwnsResetBtn = m_pResetBtn == NULL;
603 0 : if (m_bOwnsResetBtn)
604 0 : m_pResetBtn = new PushButton(m_pActionArea);
605 :
606 0 : m_pBaseFmtBtn = m_pUIBuilder ? m_pUIBuilder->get<PushButton>("standard") : NULL;
607 0 : m_bOwnsBaseFmtBtn = m_pBaseFmtBtn == NULL;
608 0 : if (m_bOwnsBaseFmtBtn)
609 0 : m_pBaseFmtBtn = new PushButton(m_pActionArea);
610 :
611 0 : pImpl = new TabDlg_Impl(m_pTabCtrl->GetPageCount());
612 :
613 0 : m_pOKBtn->SetClickHdl( LINK( this, SfxTabDialog, OkHdl ) );
614 0 : m_pCancelBtn->SetClickHdl( LINK( this, SfxTabDialog, CancelHdl ) );
615 0 : m_pResetBtn->SetClickHdl( LINK( this, SfxTabDialog, ResetHdl ) );
616 0 : m_pResetBtn->SetText( SfxResId( STR_RESET ).toString() );
617 : m_pTabCtrl->SetActivatePageHdl(
618 0 : LINK( this, SfxTabDialog, ActivatePageHdl ) );
619 : m_pTabCtrl->SetDeactivatePageHdl(
620 0 : LINK( this, SfxTabDialog, DeactivatePageHdl ) );
621 0 : m_pActionArea->Show();
622 0 : m_pBox->Show();
623 0 : m_pTabCtrl->Show();
624 0 : m_pOKBtn->Show();
625 0 : m_pCancelBtn->Show();
626 0 : m_pHelpBtn->Show();
627 0 : m_pResetBtn->Show();
628 0 : m_pResetBtn->SetHelpId( HID_TABDLG_RESET_BTN );
629 :
630 0 : if ( m_pUserBtn )
631 : {
632 0 : m_pUserBtn->SetText( *pUserButtonText );
633 0 : m_pUserBtn->SetClickHdl( LINK( this, SfxTabDialog, UserHdl ) );
634 0 : m_pUserBtn->Show();
635 : }
636 :
637 : /* TODO: Check what is up with bFmt/bFmtFlag. Comment below suggests a
638 : different behavior than implemented!! */
639 0 : if ( bFmtFlag )
640 : {
641 0 : m_pBaseFmtBtn->SetText( SfxResId( STR_STANDARD_SHORTCUT ).toString() );
642 0 : m_pBaseFmtBtn->SetClickHdl( LINK( this, SfxTabDialog, BaseFmtHdl ) );
643 0 : m_pBaseFmtBtn->SetHelpId( HID_TABDLG_STANDARD_BTN );
644 :
645 : // bFmt = temporary Flag passed on in the Constructor(),
646 : // if bFmt == 2, then also sal_True,
647 : // additional suppression of the standard button,
648 : // after the Initializing set to sal_True again
649 0 : if ( bFmtFlag != 2 )
650 0 : m_pBaseFmtBtn->Show();
651 : else
652 0 : bFmtFlag = sal_True;
653 : }
654 :
655 0 : if ( pSet )
656 : {
657 0 : pExampleSet = new SfxItemSet( *pSet );
658 0 : pOutSet = new SfxItemSet( *pSet->GetPool(), pSet->GetRanges() );
659 : }
660 :
661 0 : m_pOKBtn->SetAccessibleRelationMemberOf( m_pOKBtn );
662 0 : m_pCancelBtn->SetAccessibleRelationMemberOf( m_pCancelBtn );
663 0 : m_pHelpBtn->SetAccessibleRelationMemberOf( m_pHelpBtn );
664 0 : m_pResetBtn->SetAccessibleRelationMemberOf( m_pResetBtn );
665 0 : }
666 :
667 : // -----------------------------------------------------------------------
668 :
669 0 : void SfxTabDialog::RemoveResetButton()
670 : {
671 0 : m_pResetBtn->Hide();
672 0 : pImpl->bHideResetBtn = sal_True;
673 0 : }
674 :
675 : // -----------------------------------------------------------------------
676 :
677 0 : short SfxTabDialog::Execute()
678 : {
679 0 : if ( !m_pTabCtrl->GetPageCount() )
680 0 : return RET_CANCEL;
681 0 : Start_Impl();
682 0 : return TabDialog::Execute();
683 : }
684 :
685 : // -----------------------------------------------------------------------
686 :
687 0 : void SfxTabDialog::StartExecuteModal( const Link& rEndDialogHdl )
688 : {
689 0 : if ( !m_pTabCtrl->GetPageCount() )
690 0 : return;
691 0 : Start_Impl();
692 0 : TabDialog::StartExecuteModal( rEndDialogHdl );
693 : }
694 :
695 : // -----------------------------------------------------------------------
696 :
697 0 : void SfxTabDialog::Start( sal_Bool bShow )
698 : {
699 0 : pImpl->bModal = sal_False;
700 0 : Start_Impl();
701 :
702 0 : if ( bShow )
703 0 : Show();
704 0 : }
705 :
706 : // -----------------------------------------------------------------------
707 :
708 0 : void SfxTabDialog::SetApplyHandler(const Link& _rHdl)
709 : {
710 : DBG_ASSERT( m_pApplyBtn, "SfxTabDialog::GetApplyHandler: no apply button enabled!" );
711 0 : if ( m_pApplyBtn )
712 0 : m_pApplyBtn->SetClickHdl( _rHdl );
713 0 : }
714 :
715 : // -----------------------------------------------------------------------
716 :
717 0 : void SfxTabDialog::EnableApplyButton(sal_Bool bEnable)
718 : {
719 0 : if ( IsApplyButtonEnabled() == bEnable )
720 : // nothing to do
721 0 : return;
722 :
723 : // create or remove the apply button
724 0 : if ( bEnable )
725 : {
726 0 : m_pApplyBtn = new PushButton(m_pActionArea);
727 : // in the z-order, the apply button should be behind the ok button, thus appearing at the right side of it
728 0 : m_pApplyBtn->SetZOrder(m_pOKBtn, WINDOW_ZORDER_BEHIND);
729 0 : m_pApplyBtn->SetText(SfxResId( STR_APPLY ).toString());
730 0 : m_pApplyBtn->Show();
731 :
732 0 : m_pApplyBtn->SetHelpId( HID_TABDLG_APPLY_BTN );
733 : }
734 : else
735 : {
736 0 : delete m_pApplyBtn;
737 0 : m_pApplyBtn = NULL;
738 : }
739 :
740 : // adjust the layout
741 0 : if (IsReallyShown())
742 0 : AdjustLayout();
743 : }
744 :
745 : // -----------------------------------------------------------------------
746 :
747 0 : sal_Bool SfxTabDialog::IsApplyButtonEnabled() const
748 : {
749 0 : return ( NULL != m_pApplyBtn );
750 : }
751 :
752 : // -----------------------------------------------------------------------
753 :
754 0 : void SfxTabDialog::Start_Impl()
755 : {
756 : DBG_ASSERT( pImpl->pData->Count() == m_pTabCtrl->GetPageCount(), "not all pages registered" );
757 0 : sal_uInt16 nActPage = m_pTabCtrl->GetPageId( 0 );
758 :
759 : // load old settings, when exists
760 0 : SvtViewOptions aDlgOpt( E_TABDIALOG, String::CreateFromInt32( nResId ) );
761 0 : if ( aDlgOpt.Exists() )
762 : {
763 0 : SetWindowState(rtl::OUStringToOString(aDlgOpt.GetWindowState().getStr(), RTL_TEXTENCODING_ASCII_US));
764 :
765 : // initial TabPage from Program/Help/config
766 0 : nActPage = (sal_uInt16)aDlgOpt.GetPageID();
767 :
768 0 : if ( USHRT_MAX != nAppPageId )
769 0 : nActPage = nAppPageId;
770 : else
771 : {
772 0 : sal_uInt16 nAutoTabPageId = SFX_APP()->Get_Impl()->nAutoTabPageId;
773 0 : if ( nAutoTabPageId )
774 0 : nActPage = nAutoTabPageId;
775 : }
776 :
777 0 : if ( TAB_PAGE_NOTFOUND == m_pTabCtrl->GetPagePos( nActPage ) )
778 0 : nActPage = m_pTabCtrl->GetPageId( 0 );
779 : }
780 0 : else if ( USHRT_MAX != nAppPageId && TAB_PAGE_NOTFOUND != m_pTabCtrl->GetPagePos( nAppPageId ) )
781 0 : nActPage = nAppPageId;
782 :
783 0 : m_pTabCtrl->SetCurPageId( nActPage );
784 0 : ActivatePageHdl( m_pTabCtrl );
785 0 : }
786 :
787 0 : void SfxTabDialog::AddTabPage( sal_uInt16 nId, sal_Bool bItemsOnDemand )
788 : {
789 0 : AddTabPage( nId, 0, 0, bItemsOnDemand );
790 0 : }
791 :
792 0 : void SfxTabDialog::AddTabPage( sal_uInt16 nId, const String &rRiderText, sal_Bool bItemsOnDemand, sal_uInt16 nPos )
793 : {
794 0 : AddTabPage( nId, rRiderText, 0, 0, bItemsOnDemand, nPos );
795 0 : }
796 :
797 : #ifdef SV_HAS_RIDERBITMAPS
798 :
799 : void SfxTabDialog::AddTabPage( sal_uInt16 nId, const Bitmap &rRiderBitmap, sal_Bool bItemsOnDemand, sal_uInt16 nPos )
800 : {
801 : AddTabPage( nId, rRiderBitmap, 0, 0, bItemsOnDemand, nPos );
802 : }
803 :
804 : #endif
805 :
806 : // -----------------------------------------------------------------------
807 :
808 0 : void SfxTabDialog::AddTabPage
809 :
810 : /* [Description]
811 :
812 : Adding a page to the dialogue. Must correspond to a entry in the
813 : TabControl in the resource of the dialogue.
814 : */
815 :
816 : (
817 : sal_uInt16 nId, // Page ID
818 : CreateTabPage pCreateFunc, // Pointer to the Factory Method
819 : GetTabPageRanges pRangesFunc, // Pointer to the Method for quering
820 : // Ranges onDemand
821 : sal_Bool bItemsOnDemand // indicates whether the set of this page is
822 : // requested when created
823 : )
824 : {
825 : pImpl->pData->Append(
826 0 : new Data_Impl( nId, pCreateFunc, pRangesFunc, bItemsOnDemand ) );
827 0 : }
828 :
829 0 : sal_uInt16 SfxTabDialog::AddTabPage
830 :
831 : /* [Description]
832 :
833 : Adding a page to the dialogue. Must correspond to a entry in the
834 : TabControl in the dialog .ui
835 : */
836 :
837 : (
838 : const OString &rName, // Page ID
839 : CreateTabPage pCreateFunc, // Pointer to the Factory Method
840 : GetTabPageRanges pRangesFunc, // Pointer to the Method for quering
841 : // Ranges onDemand
842 : sal_Bool bItemsOnDemand // indicates whether the set of this page is
843 : // requested when created
844 : )
845 : {
846 0 : sal_uInt16 nId = m_pTabCtrl->GetPageId(rName);
847 : pImpl->pData->Append(
848 0 : new Data_Impl( nId, pCreateFunc, pRangesFunc, bItemsOnDemand ) );
849 0 : return nId;
850 : }
851 :
852 : // -----------------------------------------------------------------------
853 :
854 0 : void SfxTabDialog::AddTabPage
855 :
856 : /* [Description]
857 :
858 : Add a page to the dialog. The Rider text is passed on, the page has no
859 : counterpart in the TabControl in the resource of the dialogue.
860 : */
861 :
862 : (
863 : sal_uInt16 nId,
864 : const String& rRiderText,
865 : CreateTabPage pCreateFunc,
866 : GetTabPageRanges pRangesFunc,
867 : sal_Bool bItemsOnDemand,
868 : sal_uInt16 nPos
869 : )
870 : {
871 : DBG_ASSERT( TAB_PAGE_NOTFOUND == m_pTabCtrl->GetPagePos( nId ),
872 : "Double Page-Ids in the Tabpage" );
873 0 : m_pTabCtrl->InsertPage( nId, rRiderText, nPos );
874 : pImpl->pData->Append(
875 0 : new Data_Impl( nId, pCreateFunc, pRangesFunc, bItemsOnDemand ) );
876 0 : }
877 :
878 : // -----------------------------------------------------------------------
879 : #ifdef SV_HAS_RIDERBITMAPS
880 :
881 : void SfxTabDialog::AddTabPage
882 :
883 : /* [Description]
884 :
885 : Add a page to the dialog. The riders bitmap is passed on, the page has no
886 : counterpart in the TabControl in the resource of the dialogue.
887 : */
888 :
889 : (
890 : sal_uInt16 nId,
891 : const Bitmap &rRiderBitmap,
892 : CreateTabPage pCreateFunc,
893 : GetTabPageRanges pRangesFunc,
894 : sal_Bool bItemsOnDemand,
895 : sal_uInt16 nPos
896 : )
897 : {
898 : DBG_ASSERT( TAB_PAGE_NOTFOUND == m_pTabCtrl->GetPagePos( nId ),
899 : "Duplicate Page-Ids in the Tabpage" );
900 : m_pTabCtrl->InsertPage( nId, rRiderBitmap, nPos );
901 : pImpl->pData->Append(
902 : new Data_Impl( nId, pCreateFunc, pRangesFunc, bItemsOnDemand ) );
903 : }
904 : #endif
905 :
906 : // -----------------------------------------------------------------------
907 :
908 0 : void SfxTabDialog::RemoveTabPage( sal_uInt16 nId )
909 :
910 : /* [Description]
911 :
912 : Delete the TabPage with ID nId
913 : */
914 :
915 : {
916 0 : sal_uInt16 nPos = 0;
917 0 : m_pTabCtrl->RemovePage( nId );
918 0 : Data_Impl* pDataObject = Find( *pImpl->pData, nId, &nPos );
919 :
920 0 : if ( pDataObject )
921 : {
922 0 : if ( pDataObject->pTabPage )
923 : {
924 0 : pDataObject->pTabPage->FillUserData();
925 0 : String aPageData( pDataObject->pTabPage->GetUserData() );
926 0 : if ( aPageData.Len() )
927 : {
928 : // save settings of this page (user data)
929 0 : SvtViewOptions aPageOpt( E_TABPAGE, String::CreateFromInt32( pDataObject->nId ) );
930 0 : aPageOpt.SetUserItem( USERITEM_NAME, makeAny( OUString( aPageData ) ) );
931 : }
932 :
933 0 : if ( pDataObject->bOnDemand )
934 0 : delete (SfxItemSet*)&pDataObject->pTabPage->GetItemSet();
935 0 : delete pDataObject->pTabPage;
936 : }
937 :
938 0 : delete pDataObject;
939 0 : pImpl->pData->Remove( nPos );
940 : }
941 : else
942 : {
943 : SAL_INFO( "sfx2.dialog", "TabPage-Id not known" );
944 : }
945 0 : }
946 :
947 : // -----------------------------------------------------------------------
948 :
949 0 : void SfxTabDialog::PageCreated
950 :
951 : /* [Description]
952 :
953 : Default implemetation of the virtual method. This is called immediately
954 : after creating a page. Here the dialogue can call the TabPage Method
955 : directly.
956 : */
957 :
958 : (
959 : sal_uInt16, // Id of the created page
960 : SfxTabPage& // Reference to the created page
961 : )
962 : {
963 0 : }
964 :
965 : // -----------------------------------------------------------------------
966 :
967 0 : SfxItemSet* SfxTabDialog::GetInputSetImpl()
968 :
969 : /* [Description]
970 :
971 : Derived classes may create new storage for the InputSet. This has to be
972 : released in the Destructor. To do this, this method must be called.
973 : */
974 :
975 : {
976 0 : return (SfxItemSet*)pSet;
977 : }
978 :
979 : // -----------------------------------------------------------------------
980 :
981 0 : SfxTabPage* SfxTabDialog::GetTabPage( sal_uInt16 nPageId ) const
982 :
983 : /* [Description]
984 :
985 : Return TabPage with the specified Id.
986 : */
987 :
988 : {
989 0 : sal_uInt16 nPos = 0;
990 0 : Data_Impl* pDataObject = Find( *pImpl->pData, nPageId, &nPos );
991 :
992 0 : if ( pDataObject )
993 0 : return pDataObject->pTabPage;
994 0 : return NULL;
995 : }
996 :
997 0 : void SfxTabDialog::SavePosAndId()
998 : {
999 : // save settings (screen position and current page)
1000 0 : SvtViewOptions aDlgOpt( E_TABDIALOG, String::CreateFromInt32( nResId ) );
1001 0 : aDlgOpt.SetWindowState(OStringToOUString(GetWindowState(WINDOWSTATE_MASK_POS),RTL_TEXTENCODING_ASCII_US));
1002 0 : aDlgOpt.SetPageID( m_pTabCtrl->GetCurPageId() );
1003 0 : }
1004 :
1005 : // -----------------------------------------------------------------------
1006 :
1007 0 : short SfxTabDialog::Ok()
1008 :
1009 : /* [Description]
1010 :
1011 : Ok handler for the Dialogue.
1012 :
1013 : Dialog's current location and current page are saved for the next time
1014 : the dialog is shown.
1015 :
1016 : The OutputSet is created and for each page this or the special OutputSet
1017 : is set by calling the method <SfxTabPage::FillItemSet(SfxItemSet &)>, to
1018 : insert the entered data by the user into the set.
1019 :
1020 : [Return value]
1021 :
1022 : RET_OK: if at least one page has returned from FillItemSet,
1023 : otherwise RET_CANCEL.
1024 : */
1025 :
1026 : {
1027 0 : SavePosAndId(); //See fdo#38828 "Apply" resetting window position
1028 :
1029 0 : pImpl->bInOK = sal_True;
1030 :
1031 0 : if ( !pOutSet )
1032 : {
1033 0 : if ( !pExampleSet && pSet )
1034 0 : pOutSet = pSet->Clone( sal_False ); // without Items
1035 0 : else if ( pExampleSet )
1036 0 : pOutSet = new SfxItemSet( *pExampleSet );
1037 : }
1038 0 : sal_Bool bModified = sal_False;
1039 :
1040 0 : const sal_uInt16 nCount = pImpl->pData->Count();
1041 :
1042 0 : for ( sal_uInt16 i = 0; i < nCount; ++i )
1043 : {
1044 0 : Data_Impl* pDataObject = pImpl->pData->GetObject(i);
1045 0 : SfxTabPage* pTabPage = pDataObject->pTabPage;
1046 :
1047 0 : if ( pTabPage )
1048 : {
1049 0 : if ( pDataObject->bOnDemand )
1050 : {
1051 0 : SfxItemSet& rSet = (SfxItemSet&)pTabPage->GetItemSet();
1052 0 : rSet.ClearItem();
1053 0 : bModified |= pTabPage->FillItemSet( rSet );
1054 : }
1055 0 : else if ( pSet && !pTabPage->HasExchangeSupport() )
1056 : {
1057 0 : SfxItemSet aTmp( *pSet->GetPool(), pSet->GetRanges() );
1058 :
1059 0 : if ( pTabPage->FillItemSet( aTmp ) )
1060 : {
1061 0 : bModified |= sal_True;
1062 0 : pExampleSet->Put( aTmp );
1063 0 : pOutSet->Put( aTmp );
1064 0 : }
1065 : }
1066 : }
1067 : }
1068 :
1069 0 : if ( pImpl->bModified || ( pOutSet && pOutSet->Count() > 0 ) )
1070 0 : bModified |= sal_True;
1071 :
1072 0 : if ( bFmt == 2 )
1073 0 : bModified |= sal_True;
1074 0 : return bModified ? RET_OK : RET_CANCEL;
1075 : }
1076 :
1077 : // -----------------------------------------------------------------------
1078 :
1079 0 : IMPL_LINK_NOARG(SfxTabDialog, CancelHdl)
1080 : {
1081 0 : EndDialog( RET_USER_CANCEL );
1082 0 : return 0;
1083 : }
1084 :
1085 : // -----------------------------------------------------------------------
1086 :
1087 0 : SfxItemSet* SfxTabDialog::CreateInputItemSet( sal_uInt16 )
1088 :
1089 : /* [Description]
1090 :
1091 : Default implemetation of the virtual Method.
1092 : This is called when pages create their sets onDenamd.
1093 : */
1094 :
1095 : {
1096 : SAL_WARN( "sfx2.dialog", "CreateInputItemSet not implemented" );
1097 0 : return new SfxAllItemSet( SFX_APP()->GetPool() );
1098 : }
1099 :
1100 : // -----------------------------------------------------------------------
1101 :
1102 0 : const SfxItemSet* SfxTabDialog::GetRefreshedSet()
1103 :
1104 : /* [Description]
1105 :
1106 : Default implemetation of the virtual Method.
1107 : This is called, when <SfxTabPage::DeactivatePage(SfxItemSet *)>
1108 : returns <SfxTabPage::REFRESH_SET>.
1109 : */
1110 :
1111 : {
1112 : SAL_INFO ( "sfx2.dialog", "GetRefreshedSet not implemented" );
1113 0 : return 0;
1114 : }
1115 :
1116 : // -----------------------------------------------------------------------
1117 :
1118 0 : IMPL_LINK_NOARG(SfxTabDialog, OkHdl)
1119 :
1120 : /* [Description]
1121 :
1122 : Handler of the Ok-Buttons
1123 : This calls the current page <SfxTabPage::DeactivatePage(SfxItemSet *)>.
1124 : Returns <SfxTabPage::LEAVE_PAGE>, <SfxTabDialog::Ok()> is called
1125 : and the Dialog is ended.
1126 : */
1127 :
1128 : {
1129 0 : pImpl->bInOK = sal_True;
1130 :
1131 0 : if ( OK_Impl() )
1132 : {
1133 0 : if ( pImpl->bModal )
1134 0 : EndDialog( Ok() );
1135 : else
1136 : {
1137 0 : Ok();
1138 0 : Close();
1139 : }
1140 : }
1141 0 : return 0;
1142 : }
1143 :
1144 : // -----------------------------------------------------------------------
1145 :
1146 0 : bool SfxTabDialog::PrepareLeaveCurrentPage()
1147 : {
1148 0 : sal_uInt16 const nId = m_pTabCtrl->GetCurPageId();
1149 0 : SfxTabPage* pPage = dynamic_cast<SfxTabPage*> (m_pTabCtrl->GetTabPage( nId ));
1150 0 : bool bEnd = !pPage;
1151 :
1152 0 : if ( pPage )
1153 : {
1154 0 : int nRet = SfxTabPage::LEAVE_PAGE;
1155 0 : if ( pSet )
1156 : {
1157 0 : SfxItemSet aTmp( *pSet->GetPool(), pSet->GetRanges() );
1158 :
1159 0 : if ( pPage->HasExchangeSupport() )
1160 0 : nRet = pPage->DeactivatePage( &aTmp );
1161 : else
1162 0 : nRet = pPage->DeactivatePage( NULL );
1163 :
1164 0 : if ( ( SfxTabPage::LEAVE_PAGE & nRet ) == SfxTabPage::LEAVE_PAGE
1165 0 : && aTmp.Count() )
1166 : {
1167 0 : pExampleSet->Put( aTmp );
1168 0 : pOutSet->Put( aTmp );
1169 0 : }
1170 : }
1171 : else
1172 0 : nRet = pPage->DeactivatePage( NULL );
1173 0 : bEnd = nRet;
1174 : }
1175 :
1176 0 : return bEnd;
1177 : }
1178 :
1179 :
1180 : // -----------------------------------------------------------------------
1181 :
1182 0 : IMPL_LINK_NOARG(SfxTabDialog, UserHdl)
1183 :
1184 : /* [Description]
1185 :
1186 : Handler of the User-Buttons
1187 : This calls the current page <SfxTabPage::DeactivatePage(SfxItemSet *)>.
1188 : returns this <SfxTabPage::LEAVE_PAGE> and <SfxTabDialog::Ok()> is called.
1189 : Then the Dialog is ended with the Return value <SfxTabDialog::Ok()>
1190 : */
1191 :
1192 : {
1193 0 : if ( PrepareLeaveCurrentPage () )
1194 : {
1195 0 : short nRet = Ok();
1196 :
1197 0 : if ( RET_OK == nRet )
1198 0 : nRet = RET_USER;
1199 : else
1200 0 : nRet = RET_USER_CANCEL;
1201 0 : EndDialog( nRet );
1202 : }
1203 0 : return 0;
1204 : }
1205 :
1206 : // -----------------------------------------------------------------------
1207 :
1208 0 : IMPL_LINK_NOARG(SfxTabDialog, ResetHdl)
1209 :
1210 : /* [Description]
1211 :
1212 : Handler behind the reset button.
1213 : The Current Page is new initialized with their initial data, all the
1214 : settings that the user has made on this page are repealed.
1215 : */
1216 :
1217 : {
1218 0 : const sal_uInt16 nId = m_pTabCtrl->GetCurPageId();
1219 0 : Data_Impl* pDataObject = Find( *pImpl->pData, nId );
1220 : DBG_ASSERT( pDataObject, "Id not known" );
1221 :
1222 0 : if ( pDataObject->bOnDemand )
1223 : {
1224 : // CSet on AIS has problems here, thus separated
1225 0 : const SfxItemSet* pItemSet = &pDataObject->pTabPage->GetItemSet();
1226 0 : pDataObject->pTabPage->Reset( *(SfxItemSet*)pItemSet );
1227 : }
1228 : else
1229 0 : pDataObject->pTabPage->Reset( *pSet );
1230 0 : return 0;
1231 : }
1232 :
1233 : // -----------------------------------------------------------------------
1234 :
1235 0 : IMPL_LINK_NOARG(SfxTabDialog, BaseFmtHdl)
1236 :
1237 : /* [Description]
1238 :
1239 : Handler behind the Standard-Button.
1240 : This button is available when editing style sheets. All the set attributes
1241 : in the edited stylesheet are deleted.
1242 : */
1243 :
1244 : {
1245 0 : const sal_uInt16 nId = m_pTabCtrl->GetCurPageId();
1246 0 : Data_Impl* pDataObject = Find( *pImpl->pData, nId );
1247 : DBG_ASSERT( pDataObject, "Id not known" );
1248 0 : bFmt = 2;
1249 :
1250 0 : if ( pDataObject->fnGetRanges )
1251 : {
1252 0 : if ( !pExampleSet )
1253 0 : pExampleSet = new SfxItemSet( *pSet );
1254 :
1255 0 : const SfxItemPool* pPool = pSet->GetPool();
1256 0 : const sal_uInt16* pTmpRanges = (pDataObject->fnGetRanges)();
1257 0 : SfxItemSet aTmpSet( *pExampleSet );
1258 :
1259 0 : while ( *pTmpRanges )
1260 : {
1261 0 : const sal_uInt16* pU = pTmpRanges + 1;
1262 :
1263 0 : if ( *pTmpRanges == *pU )
1264 : {
1265 : // Range which two identical values -> only set one Item
1266 0 : sal_uInt16 nWh = pPool->GetWhich( *pTmpRanges );
1267 0 : pExampleSet->ClearItem( nWh );
1268 0 : aTmpSet.ClearItem( nWh );
1269 : // At the Outset of InvalidateItem,
1270 : // so that the change takes effect
1271 0 : pOutSet->InvalidateItem( nWh );
1272 : }
1273 : else
1274 : {
1275 : // Correct Range with multiple values
1276 0 : sal_uInt16 nTmp = *pTmpRanges, nTmpEnd = *pU;
1277 : DBG_ASSERT( nTmp <= nTmpEnd, "Range is sorted the wrong way" );
1278 :
1279 0 : if ( nTmp > nTmpEnd )
1280 : {
1281 : // If really sorted wrongly, then set new
1282 0 : sal_uInt16 nTmp1 = nTmp;
1283 0 : nTmp = nTmpEnd;
1284 0 : nTmpEnd = nTmp1;
1285 : }
1286 :
1287 0 : while ( nTmp <= nTmpEnd )
1288 : {
1289 : // Iterate over the Range and set the Items
1290 0 : sal_uInt16 nWh = pPool->GetWhich( nTmp );
1291 0 : pExampleSet->ClearItem( nWh );
1292 0 : aTmpSet.ClearItem( nWh );
1293 : // At the Outset of InvalidateItem,
1294 : // so that the change takes effect
1295 0 : pOutSet->InvalidateItem( nWh );
1296 0 : nTmp++;
1297 : }
1298 : }
1299 : // Go to the next pair
1300 0 : pTmpRanges += 2;
1301 : }
1302 : // Set all Items as new -> the call the current Page Reset()
1303 : DBG_ASSERT( pDataObject->pTabPage, "the Page is gone" );
1304 0 : pDataObject->pTabPage->Reset( aTmpSet );
1305 0 : pDataObject->pTabPage->pImpl->mbStandard = sal_True;
1306 : }
1307 0 : return 1;
1308 : }
1309 :
1310 : // -----------------------------------------------------------------------
1311 :
1312 0 : IMPL_LINK( SfxTabDialog, ActivatePageHdl, TabControl *, pTabCtrl )
1313 :
1314 : /* [Description]
1315 :
1316 : Handler that is called by StarView for switching to a different page.
1317 : If the page not exist yet then it is created and the virtual Method
1318 : <SfxTabDialog::PageCreated( sal_uInt16, SfxTabPage &)> is called. If the page
1319 : exist, then the if possible the <SfxTabPage::Reset(const SfxItemSet &)> or
1320 : <SfxTabPage::ActivatePage(const SfxItemSet &)> is called.
1321 : */
1322 :
1323 : {
1324 0 : sal_uInt16 const nId = pTabCtrl->GetCurPageId();
1325 :
1326 : DBG_ASSERT( pImpl->pData->Count(), "no Pages registered" );
1327 0 : SFX_APP();
1328 :
1329 : // Tab Page schon da?
1330 0 : SfxTabPage* pTabPage = dynamic_cast<SfxTabPage*> (pTabCtrl->GetTabPage( nId ));
1331 0 : Data_Impl* pDataObject = Find( *pImpl->pData, nId );
1332 : DBG_ASSERT( pDataObject, "Id not known" );
1333 :
1334 : // Create TabPage if possible:
1335 0 : if ( !pTabPage )
1336 : {
1337 0 : const SfxItemSet* pTmpSet = 0;
1338 :
1339 0 : if ( pSet )
1340 : {
1341 0 : if ( bItemsReset && pSet->GetParent() )
1342 0 : pTmpSet = pSet->GetParent();
1343 : else
1344 0 : pTmpSet = pSet;
1345 : }
1346 :
1347 0 : if ( pTmpSet && !pDataObject->bOnDemand )
1348 0 : pTabPage = (pDataObject->fnCreatePage)( pTabCtrl, *pTmpSet );
1349 : else
1350 : pTabPage = (pDataObject->fnCreatePage)
1351 0 : ( pTabCtrl, *CreateInputItemSet( nId ) );
1352 : DBG_ASSERT( NULL == pDataObject->pTabPage, "create TabPage more than once" );
1353 0 : pDataObject->pTabPage = pTabPage;
1354 :
1355 0 : pDataObject->pTabPage->SetTabDialog( this );
1356 0 : SvtViewOptions aPageOpt( E_TABPAGE, String::CreateFromInt32( pDataObject->nId ) );
1357 0 : String sUserData;
1358 0 : Any aUserItem = aPageOpt.GetUserItem( USERITEM_NAME );
1359 0 : OUString aTemp;
1360 0 : if ( aUserItem >>= aTemp )
1361 0 : sUserData = String( aTemp );
1362 0 : pTabPage->SetUserData( sUserData );
1363 0 : Size aSiz = pTabPage->GetSizePixel();
1364 :
1365 0 : Size aCtrlSiz = pTabCtrl->GetTabPageSizePixel();
1366 : // Only set Size on TabControl when < as TabPage
1367 0 : if ( aCtrlSiz.Width() < aSiz.Width() ||
1368 0 : aCtrlSiz.Height() < aSiz.Height() )
1369 : {
1370 0 : pTabCtrl->SetTabPageSizePixel( aSiz );
1371 : }
1372 :
1373 0 : PageCreated( nId, *pTabPage );
1374 :
1375 0 : if ( pDataObject->bOnDemand )
1376 0 : pTabPage->Reset( (SfxItemSet &)pTabPage->GetItemSet() );
1377 : else
1378 0 : pTabPage->Reset( *pSet );
1379 :
1380 0 : pTabCtrl->SetTabPage( nId, pTabPage );
1381 : }
1382 0 : else if ( pDataObject->bRefresh )
1383 0 : pTabPage->Reset( *pSet );
1384 0 : pDataObject->bRefresh = sal_False;
1385 :
1386 0 : if ( pExampleSet )
1387 0 : pTabPage->ActivatePage( *pExampleSet );
1388 0 : sal_Bool bReadOnly = pTabPage->IsReadOnly();
1389 0 : ( bReadOnly || pImpl->bHideResetBtn ) ? m_pResetBtn->Hide() : m_pResetBtn->Show();
1390 0 : return 0;
1391 : }
1392 :
1393 : // -----------------------------------------------------------------------
1394 :
1395 0 : IMPL_LINK( SfxTabDialog, DeactivatePageHdl, TabControl *, pTabCtrl )
1396 :
1397 : /* [Description]
1398 :
1399 : Handler that is called by StarView before leaving a page.
1400 :
1401 : [Cross-reference]
1402 :
1403 : <SfxTabPage::DeactivatePage(SfxItemSet *)>
1404 : */
1405 :
1406 : {
1407 0 : sal_uInt16 nId = pTabCtrl->GetCurPageId();
1408 0 : SFX_APP();
1409 0 : SfxTabPage *pPage = dynamic_cast<SfxTabPage*> (pTabCtrl->GetTabPage( nId ));
1410 : DBG_ASSERT( pPage, "no active Page" );
1411 : #ifdef DBG_UTIL
1412 : Data_Impl* pDataObject = Find( *pImpl->pData, pTabCtrl->GetCurPageId() );
1413 : DBG_ASSERT( pDataObject, "no Data structur for current page" );
1414 : if ( pPage->HasExchangeSupport() && pDataObject->bOnDemand )
1415 : {
1416 : DBG_WARNING( "Data exchange in ItemsOnDemand is not desired!" );
1417 : }
1418 : #endif
1419 :
1420 0 : int nRet = SfxTabPage::LEAVE_PAGE;
1421 :
1422 0 : if ( !pExampleSet && pPage->HasExchangeSupport() && pSet )
1423 0 : pExampleSet = new SfxItemSet( *pSet->GetPool(), pSet->GetRanges() );
1424 :
1425 0 : if ( pSet )
1426 : {
1427 0 : SfxItemSet aTmp( *pSet->GetPool(), pSet->GetRanges() );
1428 :
1429 0 : if ( pPage->HasExchangeSupport() )
1430 0 : nRet = pPage->DeactivatePage( &aTmp );
1431 : else
1432 0 : nRet = pPage->DeactivatePage( NULL );
1433 0 : if ( ( SfxTabPage::LEAVE_PAGE & nRet ) == SfxTabPage::LEAVE_PAGE &&
1434 0 : aTmp.Count() )
1435 : {
1436 0 : pExampleSet->Put( aTmp );
1437 0 : pOutSet->Put( aTmp );
1438 0 : }
1439 : }
1440 : else
1441 : {
1442 0 : if ( pPage->HasExchangeSupport() ) //!!!
1443 : {
1444 0 : if ( !pExampleSet )
1445 : {
1446 0 : SfxItemPool* pPool = pPage->GetItemSet().GetPool();
1447 : pExampleSet =
1448 0 : new SfxItemSet( *pPool, GetInputRanges( *pPool ) );
1449 : }
1450 0 : nRet = pPage->DeactivatePage( pExampleSet );
1451 : }
1452 : else
1453 0 : nRet = pPage->DeactivatePage( NULL );
1454 : }
1455 :
1456 0 : if ( nRet & SfxTabPage::REFRESH_SET )
1457 : {
1458 0 : pSet = GetRefreshedSet();
1459 : DBG_ASSERT( pSet, "GetRefreshedSet() returns NULL" );
1460 : // Flag all Pages as to be initialized as new
1461 0 : const sal_uInt16 nCount = pImpl->pData->Count();
1462 :
1463 0 : for ( sal_uInt16 i = 0; i < nCount; ++i )
1464 : {
1465 0 : Data_Impl* pObj = (*pImpl->pData)[i];
1466 :
1467 0 : if ( pObj->pTabPage != pPage ) // Do not refresh own Page anymore
1468 0 : pObj->bRefresh = sal_True;
1469 : else
1470 0 : pObj->bRefresh = sal_False;
1471 : }
1472 : }
1473 0 : if ( nRet & SfxTabPage::LEAVE_PAGE )
1474 0 : return sal_True;
1475 : else
1476 0 : return sal_False;
1477 : }
1478 :
1479 : // -----------------------------------------------------------------------
1480 :
1481 0 : void SfxTabDialog::ShowPage( sal_uInt16 nId )
1482 :
1483 : /* [Description]
1484 :
1485 : The TabPage is activated with the specified Id.
1486 : */
1487 :
1488 : {
1489 0 : m_pTabCtrl->SetCurPageId( nId );
1490 0 : ActivatePageHdl( m_pTabCtrl );
1491 0 : }
1492 :
1493 : // -----------------------------------------------------------------------
1494 :
1495 0 : const sal_uInt16* SfxTabDialog::GetInputRanges( const SfxItemPool& rPool )
1496 :
1497 : /* [Description]
1498 :
1499 : Makes the set over the range of all pages of the dialogue. Pages have the
1500 : static method for querying their range in AddTabPage, ie deliver their
1501 : sets onDemand.
1502 :
1503 : [Return value]
1504 :
1505 : Pointer to a null-terminated array of sal_uInt16. This array belongs to the
1506 : dialog and is deleted when the dialogue is destroy.
1507 :
1508 : [Cross-reference]
1509 :
1510 : <SfxTabDialog::AddTabPage(sal_uInt16, CreateTabPage, GetTabPageRanges, sal_Bool)>
1511 : <SfxTabDialog::AddTabPage(sal_uInt16, const String &, CreateTabPage, GetTabPageRanges, sal_Bool, sal_uInt16)>
1512 : <SfxTabDialog::AddTabPage(sal_uInt16, const Bitmap &, CreateTabPage, GetTabPageRanges, sal_Bool, sal_uInt16)>
1513 : */
1514 :
1515 : {
1516 0 : if ( pSet )
1517 : {
1518 : SAL_WARN( "sfx2.dialog", "Set already exists!" );
1519 0 : return pSet->GetRanges();
1520 : }
1521 :
1522 0 : if ( pRanges )
1523 0 : return pRanges;
1524 0 : std::vector<sal_uInt16> aUS;
1525 0 : sal_uInt16 nCount = pImpl->pData->Count();
1526 :
1527 : sal_uInt16 i;
1528 0 : for ( i = 0; i < nCount; ++i )
1529 : {
1530 0 : Data_Impl* pDataObject = pImpl->pData->GetObject(i);
1531 :
1532 0 : if ( pDataObject->fnGetRanges )
1533 : {
1534 0 : const sal_uInt16* pTmpRanges = (pDataObject->fnGetRanges)();
1535 0 : const sal_uInt16* pIter = pTmpRanges;
1536 :
1537 : sal_uInt16 nLen;
1538 0 : for( nLen = 0; *pIter; ++nLen, ++pIter )
1539 : ;
1540 0 : aUS.insert( aUS.end(), pTmpRanges, pTmpRanges + nLen );
1541 : }
1542 : }
1543 :
1544 : //! Remove duplicated Ids?
1545 : {
1546 0 : nCount = aUS.size();
1547 :
1548 0 : for ( i = 0; i < nCount; ++i )
1549 0 : aUS[i] = rPool.GetWhich( aUS[i] );
1550 : }
1551 :
1552 : // sort
1553 0 : if ( aUS.size() > 1 )
1554 : {
1555 0 : std::sort( aUS.begin(), aUS.end() );
1556 : }
1557 :
1558 0 : pRanges = new sal_uInt16[aUS.size() + 1];
1559 0 : std::copy( aUS.begin(), aUS.end(), pRanges );
1560 0 : pRanges[aUS.size()] = 0;
1561 0 : return pRanges;
1562 : }
1563 :
1564 : // -----------------------------------------------------------------------
1565 :
1566 0 : void SfxTabDialog::SetInputSet( const SfxItemSet* pInSet )
1567 :
1568 : /* [Description]
1569 :
1570 : With this method the Input-Set can subsequently be set initally or re-set.
1571 : */
1572 :
1573 : {
1574 0 : bool bSet = ( pSet != NULL );
1575 :
1576 0 : pSet = pInSet;
1577 :
1578 0 : if ( !bSet && !pExampleSet && !pOutSet )
1579 : {
1580 0 : pExampleSet = new SfxItemSet( *pSet );
1581 0 : pOutSet = new SfxItemSet( *pSet->GetPool(), pSet->GetRanges() );
1582 : }
1583 0 : }
1584 :
1585 0 : long SfxTabDialog::Notify( NotifyEvent& rNEvt )
1586 : {
1587 0 : if ( rNEvt.GetType() == EVENT_GETFOCUS )
1588 : {
1589 0 : SfxViewFrame* pViewFrame = GetViewFrame() ? GetViewFrame() : SfxViewFrame::Current();
1590 0 : if ( pViewFrame )
1591 : {
1592 0 : Window* pWindow = rNEvt.GetWindow();
1593 0 : rtl::OString sHelpId;
1594 0 : while ( sHelpId.isEmpty() && pWindow )
1595 : {
1596 0 : sHelpId = pWindow->GetHelpId();
1597 0 : pWindow = pWindow->GetParent();
1598 : }
1599 :
1600 0 : if ( !sHelpId.isEmpty() )
1601 0 : SfxHelp::OpenHelpAgent( &pViewFrame->GetFrame(), sHelpId );
1602 : }
1603 : }
1604 :
1605 0 : return TabDialog::Notify( rNEvt );
1606 66 : }
1607 :
1608 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|