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 #include <sal/config.h>
21
22 #include <comphelper/processfactory.hxx>
23 #include <tools/datetime.hxx>
24 #include <unotools/datetime.hxx>
25 #include <vcl/commandevent.hxx>
26 #include <vcl/event.hxx>
27 #include <vcl/settings.hxx>
28 #include <vcl/svapp.hxx>
29 #include <vcl/weld.hxx>
30 #include <ucbhelper/content.hxx>
31 #include <com/sun/star/ucb/ContentCreationException.hpp>
32 #include <sfx2/app.hxx>
33 #include <helpids.h>
34 #include <svx/gallery1.hxx>
35 #include <svx/galtheme.hxx>
36 #include <svx/galmisc.hxx>
37 #include "galbrws1.hxx"
38 #include <com/sun/star/util/DateTime.hpp>
39 #include <svx/strings.hrc>
40 #include <algorithm>
41 #include <svx/dialmgr.hxx>
42
43 #include <svx/svxdlg.hxx>
44 #include <memory>
45 #include <bitmaps.hlst>
46
47 using namespace ::com::sun::star;
48
49
GalleryButton(GalleryBrowser1 * pParent,WinBits nWinBits)50 GalleryButton::GalleryButton( GalleryBrowser1* pParent, WinBits nWinBits ) :
51 PushButton( pParent, nWinBits )
52 {
53 }
54
KeyInput(const KeyEvent & rKEvt)55 void GalleryButton::KeyInput( const KeyEvent& rKEvt )
56 {
57 if( !static_cast< GalleryBrowser1* >( GetParent() )->KeyInput( rKEvt, this ) )
58 PushButton::KeyInput( rKEvt );
59 }
60
61
GalleryThemeListBox(GalleryBrowser1 * pParent,WinBits nWinBits)62 GalleryThemeListBox::GalleryThemeListBox( GalleryBrowser1* pParent, WinBits nWinBits ) :
63 ListBox( pParent, nWinBits )
64 {
65 InitSettings();
66 }
67
InitSettings()68 void GalleryThemeListBox::InitSettings()
69 {
70 SetBackground( Wallpaper( GALLERY_BG_COLOR ) );
71 SetControlBackground( GALLERY_BG_COLOR );
72 SetControlForeground( GALLERY_FG_COLOR );
73 }
74
DataChanged(const DataChangedEvent & rDCEvt)75 void GalleryThemeListBox::DataChanged( const DataChangedEvent& rDCEvt )
76 {
77 if ( ( rDCEvt.GetType() == DataChangedEventType::SETTINGS ) && ( rDCEvt.GetFlags() & AllSettingsFlags::STYLE ) )
78 InitSettings();
79 else
80 ListBox::DataChanged( rDCEvt );
81 }
82
PreNotify(NotifyEvent & rNEvt)83 bool GalleryThemeListBox::PreNotify( NotifyEvent& rNEvt )
84 {
85 bool bDone = false;
86
87 if( rNEvt.GetType() == MouseNotifyEvent::COMMAND )
88 {
89 const CommandEvent* pCEvt = rNEvt.GetCommandEvent();
90
91 if( pCEvt && pCEvt->GetCommand() == CommandEventId::ContextMenu )
92 static_cast< GalleryBrowser1* >( GetParent() )->ShowContextMenu();
93 }
94 else if( rNEvt.GetType() == MouseNotifyEvent::KEYINPUT )
95 {
96 const KeyEvent* pKEvt = rNEvt.GetKeyEvent();
97
98 if( pKEvt )
99 bDone = static_cast< GalleryBrowser1* >( GetParent() )->KeyInput( *pKEvt, this );
100 }
101
102 return( bDone || ListBox::PreNotify( rNEvt ) );
103 }
104
105
GalleryBrowser1(vcl::Window * pParent,Gallery * pGallery,const std::function<sal_Bool (const KeyEvent &,Window *)> & rKeyInputHandler,const std::function<void ()> & rThemeSlectionHandler)106 GalleryBrowser1::GalleryBrowser1(
107 vcl::Window* pParent,
108 Gallery* pGallery,
109 const std::function<sal_Bool (const KeyEvent&,Window*)>& rKeyInputHandler,
110 const std::function<void ()>& rThemeSlectionHandler)
111 :
112 Control ( pParent, WB_TABSTOP ),
113 maNewTheme ( VclPtr<GalleryButton>::Create(this, WB_3DLOOK) ),
114 mpThemes ( VclPtr<GalleryThemeListBox>::Create( this, WB_TABSTOP | WB_3DLOOK | WB_BORDER | WB_HSCROLL | WB_VSCROLL | WB_AUTOHSCROLL | WB_SORT ) ),
115 mpGallery ( pGallery ),
116 mpExchangeData ( new ExchangeData ),
117 aImgNormal ( GalleryResGetBitmapEx( RID_SVXBMP_THEME_NORMAL ) ),
118 aImgDefault ( GalleryResGetBitmapEx( RID_SVXBMP_THEME_DEFAULT ) ),
119 aImgReadOnly ( GalleryResGetBitmapEx( RID_SVXBMP_THEME_READONLY ) ),
120 maKeyInputHandler(rKeyInputHandler),
121 maThemeSlectionHandler(rThemeSlectionHandler)
122 {
123 StartListening( *mpGallery );
124
125 maNewTheme->SetHelpId( HID_GALLERY_NEWTHEME );
126 maNewTheme->SetText( SvxResId(RID_SVXSTR_GALLERY_CREATETHEME));
127 maNewTheme->SetClickHdl( LINK( this, GalleryBrowser1, ClickNewThemeHdl ) );
128
129 // disable creation of new themes if a writable directory is not available
130 if( mpGallery->GetUserURL().GetProtocol() == INetProtocol::NotValid )
131 maNewTheme->Disable();
132
133 mpThemes->SetHelpId( HID_GALLERY_THEMELIST );
134 mpThemes->SetSelectHdl( LINK( this, GalleryBrowser1, SelectThemeHdl ) );
135 mpThemes->SetAccessibleName(SvxResId(RID_SVXSTR_GALLERYPROPS_GALTHEME));
136
137 for( sal_uIntPtr i = 0, nCount = mpGallery->GetThemeCount(); i < nCount; i++ )
138 ImplInsertThemeEntry( mpGallery->GetThemeInfo( i ) );
139
140 ImplAdjustControls();
141 maNewTheme->Show();
142 mpThemes->Show();
143 }
144
~GalleryBrowser1()145 GalleryBrowser1::~GalleryBrowser1()
146 {
147 disposeOnce();
148 }
149
dispose()150 void GalleryBrowser1::dispose()
151 {
152 EndListening( *mpGallery );
153 mpThemePropertiesDialog.clear();
154 mpThemes.disposeAndClear();
155 mpExchangeData.reset();
156 maNewTheme.disposeAndClear();
157 Control::dispose();
158 }
159
ImplInsertThemeEntry(const GalleryThemeEntry * pEntry)160 sal_uIntPtr GalleryBrowser1::ImplInsertThemeEntry( const GalleryThemeEntry* pEntry )
161 {
162 static const bool bShowHiddenThemes = ( getenv( "GALLERY_SHOW_HIDDEN_THEMES" ) != nullptr );
163
164 sal_uIntPtr nRet = LISTBOX_ENTRY_NOTFOUND;
165
166 if( pEntry && ( !pEntry->IsHidden() || bShowHiddenThemes ) )
167 {
168 const Image* pImage;
169
170 if( pEntry->IsReadOnly() )
171 pImage = &aImgReadOnly;
172 else if( pEntry->IsDefault() )
173 pImage = &aImgDefault;
174 else
175 pImage = &aImgNormal;
176
177 nRet = mpThemes->InsertEntry( pEntry->GetThemeName(), *pImage );
178 }
179
180 return nRet;
181 }
182
ImplAdjustControls()183 void GalleryBrowser1::ImplAdjustControls()
184 {
185 const Size aOutSize( GetOutputSizePixel() );
186 const long nNewThemeHeight = LogicToPixel(Size(0, 14), MapMode(MapUnit::MapAppFont)).Height();
187 const long nStartY = nNewThemeHeight + 4;
188
189 maNewTheme->SetPosSizePixel( Point(),
190 Size( aOutSize.Width(), nNewThemeHeight ) );
191
192 mpThemes->SetPosSizePixel( Point( 0, nStartY ),
193 Size( aOutSize.Width(), aOutSize.Height() - nStartY ) );
194 }
195
ImplFillExchangeData(const GalleryTheme * pThm,ExchangeData & rData)196 void GalleryBrowser1::ImplFillExchangeData( const GalleryTheme* pThm, ExchangeData& rData )
197 {
198 rData.pTheme = const_cast<GalleryTheme*>(pThm);
199 rData.aEditedTitle = pThm->GetName();
200
201 try
202 {
203 ::ucbhelper::Content aCnt( pThm->GetThmURL().GetMainURL( INetURLObject::DecodeMechanism::NONE ), uno::Reference< ucb::XCommandEnvironment >(), comphelper::getProcessComponentContext() );
204 util::DateTime aDateTimeModified;
205 DateTime aDateTime( DateTime::EMPTY );
206
207 aCnt.getPropertyValue("DateModified") >>= aDateTimeModified;
208 ::utl::typeConvert( aDateTimeModified, aDateTime );
209 rData.aThemeChangeDate = aDateTime;
210 rData.aThemeChangeTime = aDateTime;
211 }
212 catch( const ucb::ContentCreationException& )
213 {
214 }
215 catch( const uno::RuntimeException& )
216 {
217 }
218 catch( const uno::Exception& )
219 {
220 }
221 }
222
ImplGetExecuteVector(std::vector<OString> & o_aExec)223 void GalleryBrowser1::ImplGetExecuteVector(std::vector<OString>& o_aExec)
224 {
225 GalleryTheme* pTheme = mpGallery->AcquireTheme( GetSelectedTheme(), *this );
226
227 if( pTheme )
228 {
229 bool bUpdateAllowed, bRenameAllowed, bRemoveAllowed;
230 static const bool bIdDialog = ( getenv( "GALLERY_ENABLE_ID_DIALOG" ) != nullptr );
231
232 if( pTheme->IsReadOnly() )
233 bUpdateAllowed = bRenameAllowed = bRemoveAllowed = false;
234 else if( pTheme->IsDefault() )
235 {
236 bUpdateAllowed = bRenameAllowed = true;
237 bRemoveAllowed = false;
238 }
239 else
240 bUpdateAllowed = bRenameAllowed = bRemoveAllowed = true;
241
242 if( bUpdateAllowed && pTheme->GetObjectCount() )
243 o_aExec.emplace_back("update");
244
245 if( bRenameAllowed )
246 o_aExec.emplace_back("rename");
247
248 if( bRemoveAllowed )
249 o_aExec.emplace_back("delete");
250
251 if( bIdDialog && !pTheme->IsReadOnly() )
252 o_aExec.emplace_back("assign");
253
254 o_aExec.emplace_back("properties");
255
256 mpGallery->ReleaseTheme( pTheme, *this );
257 }
258 }
259
ImplGalleryThemeProperties(const OUString & rThemeName,bool bCreateNew)260 void GalleryBrowser1::ImplGalleryThemeProperties( const OUString & rThemeName, bool bCreateNew )
261 {
262 DBG_ASSERT(!mpThemePropsDlgItemSet, "mpThemePropsDlgItemSet already set!");
263 mpThemePropsDlgItemSet.reset(new SfxItemSet( SfxGetpApp()->GetPool() ));
264 GalleryTheme* pTheme = mpGallery->AcquireTheme( rThemeName, *this );
265
266 ImplFillExchangeData( pTheme, *mpExchangeData );
267
268 SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
269 mpThemePropertiesDialog = pFact->CreateGalleryThemePropertiesDialog(GetFrameWeld(), mpExchangeData.get(), mpThemePropsDlgItemSet.get());
270
271 if ( bCreateNew )
272 {
273 mpThemePropertiesDialog->StartExecuteAsync([this](sal_Int32 nResult){
274 EndNewThemePropertiesDlgHdl(nResult);
275 });
276 }
277 else
278 {
279 mpThemePropertiesDialog->StartExecuteAsync([this](sal_Int32 nResult){
280 EndThemePropertiesDlgHdl(nResult);
281 });
282 }
283 }
284
ImplEndGalleryThemeProperties(bool bCreateNew,sal_Int32 nRet)285 void GalleryBrowser1::ImplEndGalleryThemeProperties(bool bCreateNew, sal_Int32 nRet)
286 {
287 if( nRet == RET_OK )
288 {
289 OUString aName( mpExchangeData->pTheme->GetName() );
290
291 if( !mpExchangeData->aEditedTitle.isEmpty() && aName != mpExchangeData->aEditedTitle )
292 {
293 OUString aTitle( mpExchangeData->aEditedTitle );
294 sal_uInt16 nCount = 0;
295
296 while( mpGallery->HasTheme( aTitle ) && ( nCount++ < 16000 ) )
297 {
298 aTitle = mpExchangeData->aEditedTitle + " " + OUString::number( nCount );
299 }
300
301 mpGallery->RenameTheme( aName, aTitle );
302 }
303
304 if ( bCreateNew )
305 {
306 mpThemes->SelectEntry( mpExchangeData->pTheme->GetName() );
307 SelectThemeHdl( *mpThemes );
308 }
309 }
310
311 OUString aThemeName( mpExchangeData->pTheme->GetName() );
312 mpGallery->ReleaseTheme( mpExchangeData->pTheme, *this );
313
314 if ( bCreateNew && ( nRet != RET_OK ) )
315 {
316 mpGallery->RemoveTheme( aThemeName );
317 }
318
319 // destroy mpThemeProps asynchronously
320 Application::PostUserEvent( LINK( this, GalleryBrowser1, DestroyThemePropertiesDlgHdl ), nullptr, true );
321 }
322
EndNewThemePropertiesDlgHdl(sal_Int32 nResult)323 void GalleryBrowser1::EndNewThemePropertiesDlgHdl(sal_Int32 nResult)
324 {
325 ImplEndGalleryThemeProperties(true, nResult);
326 }
327
EndThemePropertiesDlgHdl(sal_Int32 nResult)328 void GalleryBrowser1::EndThemePropertiesDlgHdl(sal_Int32 nResult)
329 {
330 ImplEndGalleryThemeProperties(false, nResult);
331 }
332
333 IMPL_LINK( GalleryBrowser1, DestroyThemePropertiesDlgHdl, void*, /*p*/, void )
334 {
335 mpThemePropertiesDialog.disposeAndClear();
336 mpThemePropsDlgItemSet.reset();
337 }
338
ImplExecute(const OString & rIdent)339 void GalleryBrowser1::ImplExecute(const OString &rIdent)
340 {
341 if (rIdent == "update")
342 {
343 GalleryTheme* pTheme = mpGallery->AcquireTheme( GetSelectedTheme(), *this );
344
345 SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
346 ScopedVclPtr<VclAbstractDialog> aActualizeProgress(pFact->CreateActualizeProgressDialog(GetFrameWeld(), pTheme));
347
348 aActualizeProgress->Execute();
349 mpGallery->ReleaseTheme( pTheme, *this );
350 }
351 else if (rIdent == "delete")
352 {
353 std::unique_ptr<weld::Builder> xBuilder(Application::CreateBuilder(GetFrameWeld(), "svx/ui/querydeletethemedialog.ui"));
354 std::unique_ptr<weld::MessageDialog> xQuery(xBuilder->weld_message_dialog("QueryDeleteThemeDialog"));
355 if (xQuery->run() == RET_YES)
356 mpGallery->RemoveTheme( mpThemes->GetSelectedEntry() );
357 }
358 else if (rIdent == "rename")
359 {
360 GalleryTheme* pTheme = mpGallery->AcquireTheme( GetSelectedTheme(), *this );
361 const OUString aOldName( pTheme->GetName() );
362
363 SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
364 ScopedVclPtr<AbstractTitleDialog> aDlg(pFact->CreateTitleDialog(GetFrameWeld(), aOldName));
365
366 if( aDlg->Execute() == RET_OK )
367 {
368 const OUString aNewName( aDlg->GetTitle() );
369
370 if( !aNewName.isEmpty() && ( aNewName != aOldName ) )
371 {
372 OUString aName( aNewName );
373 sal_uInt16 nCount = 0;
374
375 while( mpGallery->HasTheme( aName ) && ( nCount++ < 16000 ) )
376 {
377 aName = aNewName + " " + OUString::number( nCount );
378 }
379
380 mpGallery->RenameTheme( aOldName, aName );
381 }
382 }
383 mpGallery->ReleaseTheme( pTheme, *this );
384 }
385 else if (rIdent == "assign")
386 {
387 GalleryTheme* pTheme = mpGallery->AcquireTheme( GetSelectedTheme(), *this );
388
389 if (pTheme && !pTheme->IsReadOnly())
390 {
391
392 SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
393 ScopedVclPtr<AbstractGalleryIdDialog> aDlg(pFact->CreateGalleryIdDialog(GetFrameWeld(), pTheme));
394 if( aDlg->Execute() == RET_OK )
395 pTheme->SetId( aDlg->GetId(), true );
396 }
397
398 mpGallery->ReleaseTheme( pTheme, *this );
399 }
400 else if (rIdent == "properties")
401 {
402 ImplGalleryThemeProperties( GetSelectedTheme(), false );
403 }
404 }
405
Resize()406 void GalleryBrowser1::Resize()
407 {
408 Control::Resize();
409 ImplAdjustControls();
410 }
411
GetFocus()412 void GalleryBrowser1::GetFocus()
413 {
414 Control::GetFocus();
415 if( maNewTheme->IsEnabled() )
416 maNewTheme->GrabFocus();
417 else
418 mpThemes->GrabFocus();
419 }
420
Notify(SfxBroadcaster &,const SfxHint & rHint)421 void GalleryBrowser1::Notify( SfxBroadcaster&, const SfxHint& rHint )
422 {
423 const GalleryHint& rGalleryHint = static_cast<const GalleryHint&>(rHint);
424
425 switch( rGalleryHint.GetType() )
426 {
427 case GalleryHintType::THEME_CREATED:
428 ImplInsertThemeEntry( mpGallery->GetThemeInfo( rGalleryHint.GetThemeName() ) );
429 break;
430
431 case GalleryHintType::THEME_RENAMED:
432 {
433 const sal_Int32 nCurSelectPos = mpThemes->GetSelectedEntryPos();
434 const sal_Int32 nRenameEntryPos = mpThemes->GetEntryPos( rGalleryHint.GetThemeName() );
435
436 mpThemes->RemoveEntry( rGalleryHint.GetThemeName() );
437 ImplInsertThemeEntry( mpGallery->GetThemeInfo( rGalleryHint.GetStringData() ) );
438
439 if( nCurSelectPos == nRenameEntryPos )
440 {
441 mpThemes->SelectEntry( rGalleryHint.GetStringData() );
442 SelectThemeHdl( *mpThemes );
443 }
444 }
445 break;
446
447 case GalleryHintType::THEME_REMOVED:
448 {
449 mpThemes->RemoveEntry( rGalleryHint.GetThemeName() );
450 }
451 break;
452
453 case GalleryHintType::CLOSE_THEME:
454 {
455 const sal_Int32 nCurSelectPos = mpThemes->GetSelectedEntryPos();
456 const sal_Int32 nCloseEntryPos = mpThemes->GetEntryPos( rGalleryHint.GetThemeName() );
457
458 if( nCurSelectPos == nCloseEntryPos )
459 {
460 if( nCurSelectPos < ( mpThemes->GetEntryCount() - 1 ) )
461 mpThemes->SelectEntryPos( nCurSelectPos + 1 );
462 else if( nCurSelectPos )
463 mpThemes->SelectEntryPos( nCurSelectPos - 1 );
464 else
465 mpThemes->SetNoSelection();
466
467 SelectThemeHdl( *mpThemes );
468 }
469 }
470 break;
471
472 default:
473 break;
474 }
475 }
476
ShowContextMenu()477 void GalleryBrowser1::ShowContextMenu()
478 {
479 Application::PostUserEvent( LINK( this, GalleryBrowser1, ShowContextMenuHdl ), this, true );
480 }
481
KeyInput(const KeyEvent & rKEvt,vcl::Window * pWindow)482 bool GalleryBrowser1::KeyInput( const KeyEvent& rKEvt, vcl::Window* pWindow )
483 {
484 bool bRet = false;
485 if (maKeyInputHandler)
486 bRet = maKeyInputHandler(rKEvt, pWindow);
487
488 if( !bRet )
489 {
490 std::vector<OString> aExecVector;
491 ImplGetExecuteVector(aExecVector);
492 OString sExecuteIdent;
493 bool bMod1 = rKEvt.GetKeyCode().IsMod1();
494
495 switch( rKEvt.GetKeyCode().GetCode() )
496 {
497 case KEY_INSERT:
498 ClickNewThemeHdl( nullptr );
499 break;
500
501 case KEY_I:
502 {
503 if( bMod1 )
504 ClickNewThemeHdl( nullptr );
505 }
506 break;
507
508 case KEY_U:
509 {
510 if( bMod1 )
511 sExecuteIdent = "update";
512 }
513 break;
514
515 case KEY_DELETE:
516 sExecuteIdent = "delete";
517 break;
518
519 case KEY_D:
520 {
521 if( bMod1 )
522 sExecuteIdent = "delete";
523 }
524 break;
525
526 case KEY_R:
527 {
528 if( bMod1 )
529 sExecuteIdent = "rename";
530 }
531 break;
532
533 case KEY_RETURN:
534 {
535 if( bMod1 )
536 sExecuteIdent = "properties";
537 }
538 break;
539 }
540
541 if (!sExecuteIdent.isEmpty() && (std::find( aExecVector.begin(), aExecVector.end(), sExecuteIdent) != aExecVector.end()))
542 {
543 ImplExecute(sExecuteIdent);
544 bRet = true;
545 }
546 }
547
548 return bRet;
549 }
550
IMPL_LINK_NOARG(GalleryBrowser1,ShowContextMenuHdl,void *,void)551 IMPL_LINK_NOARG(GalleryBrowser1, ShowContextMenuHdl, void*, void)
552 {
553 std::vector<OString> aExecVector;
554 ImplGetExecuteVector(aExecVector);
555
556 if( aExecVector.empty() )
557 return;
558
559 VclBuilder aBuilder(nullptr, VclBuilderContainer::getUIRootDir(), "svx/ui/gallerymenu1.ui", "");
560 VclPtr<PopupMenu> aMenu(aBuilder.get_menu("menu"));
561
562 aMenu->EnableItem( aMenu->GetItemId("update"), std::find( aExecVector.begin(), aExecVector.end(), "update" ) != aExecVector.end() );
563 aMenu->EnableItem( aMenu->GetItemId("rename"), std::find( aExecVector.begin(), aExecVector.end(), "rename" ) != aExecVector.end() );
564 aMenu->EnableItem( aMenu->GetItemId("delete"), std::find( aExecVector.begin(), aExecVector.end(), "delete" ) != aExecVector.end() );
565 aMenu->EnableItem( aMenu->GetItemId("assign"), std::find( aExecVector.begin(), aExecVector.end(), "assign" ) != aExecVector.end() );
566 aMenu->EnableItem( aMenu->GetItemId("properties"), std::find( aExecVector.begin(), aExecVector.end(), "properties" ) != aExecVector.end() );
567 aMenu->SetSelectHdl( LINK( this, GalleryBrowser1, PopupMenuHdl ) );
568 aMenu->RemoveDisabledEntries();
569
570 const tools::Rectangle aThemesRect( mpThemes->GetPosPixel(), mpThemes->GetOutputSizePixel() );
571 Point aSelPos( mpThemes->GetBoundingRectangle( mpThemes->GetSelectedEntryPos() ).Center() );
572
573 aSelPos.setX( std::max( std::min( aSelPos.X(), aThemesRect.Right() ), aThemesRect.Left() ) );
574 aSelPos.setY( std::max( std::min( aSelPos.Y(), aThemesRect.Bottom() ), aThemesRect.Top() ) );
575
576 aMenu->Execute( this, aSelPos );
577 }
578
IMPL_LINK(GalleryBrowser1,PopupMenuHdl,Menu *,pMenu,bool)579 IMPL_LINK( GalleryBrowser1, PopupMenuHdl, Menu*, pMenu, bool )
580 {
581 ImplExecute(pMenu->GetCurItemIdent());
582 return false;
583 }
584
IMPL_LINK_NOARG(GalleryBrowser1,SelectThemeHdl,ListBox &,void)585 IMPL_LINK_NOARG(GalleryBrowser1, SelectThemeHdl, ListBox&, void)
586 {
587 if (maThemeSlectionHandler)
588 maThemeSlectionHandler();
589 }
590
IMPL_LINK_NOARG(GalleryBrowser1,ClickNewThemeHdl,Button *,void)591 IMPL_LINK_NOARG(GalleryBrowser1, ClickNewThemeHdl, Button*, void)
592 {
593 OUString aNewTheme( SvxResId(RID_SVXSTR_GALLERY_NEWTHEME) );
594 OUString aName( aNewTheme );
595 sal_uIntPtr nCount = 0;
596
597 while( mpGallery->HasTheme( aName ) && ( nCount++ < 16000 ) )
598 {
599 aName = aNewTheme + " " + OUString::number( nCount );
600 }
601
602 if( !mpGallery->HasTheme( aName ) && mpGallery->CreateTheme( aName ) )
603 {
604 ImplGalleryThemeProperties( aName, true );
605 }
606 }
607
608 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
609