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_sd.hxx"
26
27 #include "ToolBarManager.hxx"
28
29 #include "DrawViewShell.hxx"
30 #include "EventMultiplexer.hxx"
31 #include "ViewShellBase.hxx"
32 #include "ViewShellManager.hxx"
33 #include <com/sun/star/beans/XPropertySet.hpp>
34 #include <com/sun/star/frame/XLayoutManager.hpp>
35 #include <com/sun/star/ui/UIElementType.hpp>
36
37 #include <cppuhelper/implbase1.hxx>
38 #include <osl/mutex.hxx>
39 #include <rtl/ref.hxx>
40 #include <sfx2/app.hxx>
41 #include <sfx2/docfile.hxx>
42 #include <sfx2/objsh.hxx>
43 #include <sfx2/request.hxx>
44 #include <sfx2/viewfrm.hxx>
45 #include <svl/eitem.hxx>
46 #include <svx/dialogs.hrc>
47 #include <svx/extrusionbar.hxx>
48 #include <svx/fontworkbar.hxx>
49 #ifndef _TOOLKIT_HELPER_VCLUNOHELPER_HXX_
50 #include <toolkit/helper/vclunohelper.hxx>
51 #endif
52 #include <tools/link.hxx>
53
54 #include <map>
55 #include <vector>
56 #include <iterator>
57
58 using namespace ::com::sun::star;
59 using namespace ::com::sun::star::uno;
60
61 #undef VERBOSE
62
63 #undef OUSTRING // Remove definition made in the SFX
64 #define OUSTRING(s) (::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(s)))
65
66 namespace {
67
68 using namespace sd;
69
70 class ToolBarRules;
71
72 /** Lock of the frame::XLayoutManager.
73 */
74 class LayouterLock
75 {
76 public:
77 LayouterLock (const Reference<frame::XLayoutManager>& rxLayouter);
78 ~LayouterLock (void);
79 private:
80 Reference<frame::XLayoutManager> mxLayouter;
81 };
82
83
84 typedef ::std::vector<rtl::OUString> NameList;
85
86 /** Store a list of tool bars for each of the tool bar groups. From
87 this the list of requested tool bars is built.
88 */
89 class ToolBarList
90 {
91 public:
92 ToolBarList (void);
93
94 void ClearGroup (sd::ToolBarManager::ToolBarGroup eGroup);
95 void AddToolBar (sd::ToolBarManager::ToolBarGroup eGroup, const ::rtl::OUString& rsName);
96 bool RemoveToolBar (sd::ToolBarManager::ToolBarGroup eGroup, const ::rtl::OUString& rsName);
97
98 void GetToolBarsToActivate (NameList& rToolBars) const;
99 void GetToolBarsToDeactivate (NameList& rToolBars) const;
100
101 void MarkToolBarAsActive (const ::rtl::OUString& rsName);
102 void MarkToolBarAsNotActive (const ::rtl::OUString& rsName);
103 void MarkAllToolBarsAsNotActive (void);
104
105 private:
106 typedef ::std::map<sd::ToolBarManager::ToolBarGroup,NameList> Groups;
107 Groups maGroups;
108 NameList maActiveToolBars;
109
110 void MakeRequestedToolBarList (NameList& rToolBars) const;
111 };
112
113
114
115
116 /** Manage tool bars that are implemented as sub shells of a view shell.
117 The typical procedure of updating the sub shells of a view shell is to
118 rebuild a list of sub shells that the caller would like to have active.
119 The methods ClearGroup() and AddShellId() allow the caller to do that. A
120 final call to UpdateShells() activates the requested shells that are not
121 active and deactivates the active shells that are not requested .
122
123 This is done by maintaining two lists. One (the current list)
124 reflects the current state. The other (the requested list) contains the
125 currently requested shells. UpdateShells() makes the requested
126 list the current list and clears the current list.
127
128 Each shell belongs to one group. Different groups can be modified
129 separately.
130 */
131 class ToolBarShellList
132 {
133 public:
134 /** Create a new object with an empty current list and an empty
135 requested list.
136 */
137 ToolBarShellList (void);
138
139 /** Remove all shells from a group. Calling this method should normally
140 not be necessary because after the construction or after a call to
141 UpdateShells() the requested list is empty.
142 @param eGroup
143 The group to clear. Shells in other groups are not modified.
144 */
145 void ClearGroup (sd::ToolBarManager::ToolBarGroup eGroup);
146
147 /** Add a shell. When the specified shell has already been requested
148 for another group then it is moved to this group.
149 @param eGroup
150 The group to which to add the shell.
151 @param nId
152 The id of the shell to add.
153 */
154 void AddShellId (sd::ToolBarManager::ToolBarGroup eGroup, sd::ShellId nId);
155
156 /** Releasing all shells means that the given ToolBarRules object is
157 informed that every shell managed by the called ToolBarShellList is
158 about to be removed and that the associated framework tool bars can
159 be removed as well. The caller still has to call UpdateShells().
160 */
161 void ReleaseAllShells (ToolBarRules& rRules);
162
163 /** The requested list is made the current list by activating all
164 shells in the requested list and by deactivating the shells in the
165 current list that are not in the requested list.
166 @param pMainViewShell
167 The shells that are activated or deactivated are sub shells of
168 this view shell.
169 @param rManager
170 This ViewShellManager is used to activate or deactivate shells.
171 */
172 void UpdateShells (
173 const ::boost::shared_ptr<ViewShell>& rpMainViewShell,
174 const ::boost::shared_ptr<ViewShellManager>& rpManager);
175
176 private:
177 class ShellDescriptor
178 {public:
179 ShellDescriptor (ShellId nId,sd::ToolBarManager::ToolBarGroup eGroup);
180 ShellId mnId;
181 sd::ToolBarManager::ToolBarGroup meGroup;
operator <(const ShellDescriptor & r1,const ShellDescriptor & r2)182 friend bool operator<(const ShellDescriptor& r1, const ShellDescriptor& r2)
183 { return r1.mnId < r2.mnId; }
184 };
185
186 /** The requested list of tool bar shells that will be active after the
187 next call to UpdateShells().
188 */
189 typedef ::std::set<ShellDescriptor> GroupedShellList;
190 GroupedShellList maNewList;
191
192 /** The list of tool bar shells that are currently on the shell stack.
193 Using a GroupedShellList is not strictly necessary but it makes
194 things easier and does not waste too much memory.
195 */
196 GroupedShellList maCurrentList;
197 };
198
199
200
201
202 /** This class concentrates the knowledge about when to show what tool bars
203 in one place.
204 */
205 class ToolBarRules
206 {
207 public:
208 ToolBarRules (
209 const ::boost::shared_ptr<ToolBarManager>& rpToolBarManager,
210 const ::boost::shared_ptr<ViewShellManager>& rpViewShellManager);
211
212 /** This method calls MainViewShellChanged() and SelectionHasChanged()
213 for the current main view shell and its view.
214 */
215 void Update (ViewShellBase& rBase);
216
217 /** Reset all tool bars in all groups and add tool bars and tool bar
218 shells to the TBG_PERMANENT group for the specified ViewShell type.
219 */
220 void MainViewShellChanged (ViewShell::ShellType nShellType);
221
222 /** Reset all tool bars in all groups and add tool bars and tool bar
223 shells to the TBG_PERMANENT group for the specified ViewShell.
224 */
225 void MainViewShellChanged (const ViewShell& rMainViewShell);
226
227 /** Reset all tool bars in the TBG_FUNCTION group and add tool bars and tool bar
228 shells to this group for the current selection.
229 */
230 void SelectionHasChanged (
231 const ::sd::ViewShell& rViewShell,
232 const SdrView& rView);
233
234 /** Add a tool bar for the specified tool bar shell.
235 */
236 void SubShellAdded (
237 ::sd::ToolBarManager::ToolBarGroup eGroup,
238 sd::ShellId nShellId);
239
240 /** Remove a tool bar for the specified tool bar shell.
241 */
242 void SubShellRemoved (
243 ::sd::ToolBarManager::ToolBarGroup eGroup,
244 sd::ShellId nShellId);
245
246 private:
247 ::boost::shared_ptr<ToolBarManager> mpToolBarManager;
248 ::boost::shared_ptr<ViewShellManager> mpViewShellManager;
249 };
250
251 } // end of anonymous namespace
252
253
254
255
256 namespace sd {
257
258 //===== ToolBarManager::Implementation ========================================
259
260 class ToolBarManager::Implementation
261 {
262 public:
263 /** This constructor takes three arguments even though the
264 ToolBarManager could be taken from the ViewShellBase. This is so to
265 state explicitly which information has to be present when this
266 constructor is called. The ViewShellBase may not have been fully
267 initialized at this point and must not be asked for this values.
268 */
269 Implementation (
270 ViewShellBase& rBase,
271 const ::boost::shared_ptr<sd::tools::EventMultiplexer>& rpMultiplexer,
272 const ::boost::shared_ptr<ViewShellManager>& rpViewShellManager,
273 const ::boost::shared_ptr<ToolBarManager>& rpToolBarManager);
274 ~Implementation (void);
275
276 void SetValid (bool bValid);
277
278 void ResetToolBars (ToolBarGroup eGroup);
279 void ResetAllToolBars (void);
280 void AddToolBar (ToolBarGroup eGroup, const ::rtl::OUString& rsToolBarName);
281 void AddToolBarShell (ToolBarGroup eGroup, ShellId nToolBarId);
282 void RemoveToolBar (ToolBarGroup eGroup, const ::rtl::OUString& rsToolBarName);
283
284 /** Release all tool bar shells and the associated framework tool bars.
285 Typically called when the main view shell is being replaced by
286 another, all tool bar shells are released. In that process the
287 shells are destroyed anyway and without calling this method they
288 would still be referenced.
289 */
290 void ReleaseAllToolBarShells (void);
291
292 void ToolBarsDestroyed(void);
293
294 void RequestUpdate (void);
295
296 void PreUpdate (void);
297 void PostUpdate (void);
298 /** Tell the XLayoutManager about the tool bars that we would like to be
299 shown.
300 @param rpLayouterLock
301 This typically is the mpSynchronousLayouterLock that is used in
302 this method and that is either released at its end or assigned
303 to mpAsynchronousLock in order to be unlocked later.
304 */
305 void Update (::std::auto_ptr<LayouterLock> pLayouterLock);
306
307 class UpdateLockImplementation
308 {
309 public:
UpdateLockImplementation(Implementation & rImplementation)310 UpdateLockImplementation (Implementation& rImplementation)
311 : mrImplementation(rImplementation) { mrImplementation.LockUpdate(); }
~UpdateLockImplementation(void)312 ~UpdateLockImplementation (void) { mrImplementation.UnlockUpdate(); }
313 private:
314 Implementation& mrImplementation;
315 };
316
317 void LockViewShellManager (void);
318 void LockUpdate (void);
319 void UnlockUpdate (void);
320
321 ToolBarRules& GetToolBarRules (void);
322
323 private:
324 const static ::rtl::OUString msToolBarResourcePrefix;
325
326 mutable ::osl::Mutex maMutex;
327 ViewShellBase& mrBase;
328 ::boost::shared_ptr<sd::tools::EventMultiplexer> mpEventMultiplexer;
329 bool mbIsValid;
330 ToolBarList maToolBarList;
331 ToolBarShellList maToolBarShellList;
332 Reference<frame::XLayoutManager> mxLayouter;
333 sal_Int32 mnLockCount;
334 bool mbPreUpdatePending;
335 bool mbPostUpdatePending;
336 /** The layouter locks manage the locking of the XLayoutManager. The
337 lock() and unlock() functions are not called directly because the
338 (final) unlocking is usually done asynchronously *after* the
339 list of requested toolbars is updated.
340 */
341 ::std::auto_ptr<LayouterLock> mpSynchronousLayouterLock;
342 ::std::auto_ptr<LayouterLock> mpAsynchronousLayouterLock;
343 ::std::auto_ptr<ViewShellManager::UpdateLock> mpViewShellManagerLock;
344 sal_uLong mnPendingUpdateCall;
345 sal_uLong mnPendingSetValidCall;
346 ToolBarRules maToolBarRules;
347
348 ::rtl::OUString GetToolBarResourceName (const ::rtl::OUString& rsBaseName) const;
349 bool CheckPlugInMode (const ::rtl::OUString& rsName) const;
350
351 DECL_LINK(UpdateCallback,bool*);
352 DECL_LINK(EventMultiplexerCallback, sd::tools::EventMultiplexerEvent*);
353 DECL_LINK(SetValidCallback,void*);
354 };
355
356
357
358 //===== ToolBarManager ========================================================
359
360 const ::rtl::OUString ToolBarManager::msToolBar(OUSTRING("toolbar"));
361 const ::rtl::OUString ToolBarManager::msOptionsToolBar(OUSTRING("optionsbar"));
362 const ::rtl::OUString ToolBarManager::msCommonTaskToolBar(OUSTRING("commontaskbar"));
363 const ::rtl::OUString ToolBarManager::msViewerToolBar(OUSTRING("viewerbar"));
364 const ::rtl::OUString ToolBarManager::msSlideSorterToolBar(OUSTRING("slideviewtoolbar"));
365 const ::rtl::OUString ToolBarManager::msSlideSorterObjectBar(OUSTRING("slideviewobjectbar"));
366 const ::rtl::OUString ToolBarManager::msOutlineToolBar(OUSTRING("outlinetoolbar"));
367 const ::rtl::OUString ToolBarManager::msMasterViewToolBar(OUSTRING("masterviewtoolbar"));
368 const ::rtl::OUString ToolBarManager::msDrawingObjectToolBar(OUSTRING("drawingobjectbar"));
369 const ::rtl::OUString ToolBarManager::msGluePointsToolBar(OUSTRING("gluepointsobjectbar"));
370 const ::rtl::OUString ToolBarManager::msTextObjectBar(OUSTRING("textobjectbar"));
371 const ::rtl::OUString ToolBarManager::msBezierObjectBar(OUSTRING("bezierobjectbar"));
372 const ::rtl::OUString ToolBarManager::msGraphicObjectBar(OUSTRING("graphicobjectbar"));
373 const ::rtl::OUString ToolBarManager::msMediaObjectBar(OUSTRING("mediaobjectbar"));
374 const ::rtl::OUString ToolBarManager::msTableObjectBar(OUSTRING("tableobjectbar"));
375
376
Create(ViewShellBase & rBase,const::boost::shared_ptr<sd::tools::EventMultiplexer> & rpMultiplexer,const::boost::shared_ptr<ViewShellManager> & rpViewShellManager)377 ::boost::shared_ptr<ToolBarManager> ToolBarManager::Create (
378 ViewShellBase& rBase,
379 const ::boost::shared_ptr<sd::tools::EventMultiplexer>& rpMultiplexer,
380 const ::boost::shared_ptr<ViewShellManager>& rpViewShellManager)
381 {
382 ::boost::shared_ptr<ToolBarManager> pManager (new ToolBarManager());
383 pManager->mpImpl.reset(
384 new Implementation(rBase,rpMultiplexer,rpViewShellManager,pManager));
385 return pManager;
386 }
387
388
389
390
ToolBarManager(void)391 ToolBarManager::ToolBarManager (void)
392 : mpImpl()
393 {
394 }
395
396
397
398
~ToolBarManager(void)399 ToolBarManager::~ToolBarManager (void)
400 {
401 }
402
403
404
405
Shutdown(void)406 void ToolBarManager::Shutdown (void)
407 {
408 if (mpImpl.get() != NULL)
409 mpImpl.reset();
410 }
411
412
413
414
ResetToolBars(ToolBarGroup eGroup)415 void ToolBarManager::ResetToolBars (ToolBarGroup eGroup)
416 {
417 if (mpImpl.get() != NULL)
418 {
419 UpdateLock aLock (shared_from_this());
420 mpImpl->ResetToolBars(eGroup);
421 }
422 }
423
424
425
426
ResetAllToolBars(void)427 void ToolBarManager::ResetAllToolBars (void)
428 {
429 if (mpImpl.get() != NULL)
430 {
431 UpdateLock aLock (shared_from_this());
432 mpImpl->ResetAllToolBars();
433 }
434 }
435
436
437
438
AddToolBar(ToolBarGroup eGroup,const::rtl::OUString & rsToolBarName)439 void ToolBarManager::AddToolBar (
440 ToolBarGroup eGroup,
441 const ::rtl::OUString& rsToolBarName)
442 {
443 if (mpImpl.get() != NULL)
444 {
445 UpdateLock aLock (shared_from_this());
446 mpImpl->AddToolBar(eGroup,rsToolBarName);
447 }
448 }
449
450
451
452
AddToolBarShell(ToolBarGroup eGroup,ShellId nToolBarId)453 void ToolBarManager::AddToolBarShell (
454 ToolBarGroup eGroup,
455 ShellId nToolBarId)
456 {
457 if (mpImpl.get() != NULL)
458 {
459 UpdateLock aLock (shared_from_this());
460 mpImpl->AddToolBarShell(eGroup,nToolBarId);
461 }
462 }
463
464
465
466
RemoveToolBar(ToolBarGroup eGroup,const::rtl::OUString & rsToolBarName)467 void ToolBarManager::RemoveToolBar (
468 ToolBarGroup eGroup,
469 const ::rtl::OUString& rsToolBarName)
470 {
471 if (mpImpl.get() != NULL)
472 {
473 UpdateLock aLock (shared_from_this());
474 mpImpl->RemoveToolBar(eGroup,rsToolBarName);
475 }
476 }
477
478
479
480
SetToolBar(ToolBarGroup eGroup,const::rtl::OUString & rsToolBarName)481 void ToolBarManager::SetToolBar (
482 ToolBarGroup eGroup,
483 const ::rtl::OUString& rsToolBarName)
484 {
485 if (mpImpl.get() != NULL)
486 {
487 UpdateLock aLock (shared_from_this());
488 mpImpl->ResetToolBars(eGroup);
489 mpImpl->AddToolBar(eGroup,rsToolBarName);
490 }
491 }
492
493
494
495
SetToolBarShell(ToolBarGroup eGroup,ShellId nToolBarId)496 void ToolBarManager::SetToolBarShell (
497 ToolBarGroup eGroup,
498 ShellId nToolBarId)
499 {
500 if (mpImpl.get() != NULL)
501 {
502 UpdateLock aLock (shared_from_this());
503 mpImpl->ResetToolBars(eGroup);
504 mpImpl->AddToolBarShell(eGroup,nToolBarId);
505 }
506 }
507
508
509
510
PreUpdate(void)511 void ToolBarManager::PreUpdate (void)
512 {
513 if (mpImpl.get()!=NULL)
514 mpImpl->PreUpdate();
515 }
516
517
518
519
RequestUpdate(void)520 void ToolBarManager::RequestUpdate (void)
521 {
522 if (mpImpl.get()!=NULL)
523 mpImpl->RequestUpdate();
524 }
525
526
527
528
LockViewShellManager(void)529 void ToolBarManager::LockViewShellManager (void)
530 {
531 if (mpImpl.get() != NULL)
532 mpImpl->LockViewShellManager();
533 }
534
535
536
537
LockUpdate(void)538 void ToolBarManager::LockUpdate (void)
539 {
540 if (mpImpl.get()!=NULL)
541 mpImpl->LockUpdate();
542 }
543
544
545
546
UnlockUpdate(void)547 void ToolBarManager::UnlockUpdate (void)
548 {
549 if (mpImpl.get()!=NULL)
550 mpImpl->UnlockUpdate();
551 }
552
553
554
555
MainViewShellChanged(ViewShell::ShellType nShellType)556 void ToolBarManager::MainViewShellChanged (ViewShell::ShellType nShellType)
557 {
558 if (mpImpl.get() != NULL)
559 {
560 mpImpl->ReleaseAllToolBarShells();
561 mpImpl->GetToolBarRules().MainViewShellChanged(nShellType);
562 }
563 }
564
565
566
567
MainViewShellChanged(const ViewShell & rMainViewShell)568 void ToolBarManager::MainViewShellChanged (const ViewShell& rMainViewShell)
569 {
570 if (mpImpl.get() != NULL)
571 {
572 mpImpl->ReleaseAllToolBarShells();
573 mpImpl->GetToolBarRules().MainViewShellChanged(rMainViewShell);
574 }
575 }
576
577
578
579
SelectionHasChanged(const ViewShell & rViewShell,const SdrView & rView)580 void ToolBarManager::SelectionHasChanged (
581 const ViewShell& rViewShell,
582 const SdrView& rView)
583 {
584 if (mpImpl.get() != NULL)
585 mpImpl->GetToolBarRules().SelectionHasChanged(rViewShell,rView);
586 }
587
588
ToolBarsDestroyed(void)589 void ToolBarManager::ToolBarsDestroyed(void)
590 {
591 if (mpImpl.get() != NULL)
592 mpImpl->ToolBarsDestroyed();
593 }
594
595
596 //===== ToolBarManager::Implementation =======================================
597
598 const ::rtl::OUString ToolBarManager::Implementation::msToolBarResourcePrefix(
599 OUSTRING("private:resource/toolbar/"));
600
Implementation(ViewShellBase & rBase,const::boost::shared_ptr<sd::tools::EventMultiplexer> & rpMultiplexer,const::boost::shared_ptr<ViewShellManager> & rpViewShellManager,const::boost::shared_ptr<ToolBarManager> & rpToolBarManager)601 ToolBarManager::Implementation::Implementation (
602 ViewShellBase& rBase,
603 const ::boost::shared_ptr<sd::tools::EventMultiplexer>& rpMultiplexer,
604 const ::boost::shared_ptr<ViewShellManager>& rpViewShellManager,
605 const ::boost::shared_ptr<ToolBarManager>& rpToolBarManager)
606 : maMutex(),
607 mrBase(rBase),
608 mpEventMultiplexer(rpMultiplexer),
609 mbIsValid(false),
610 maToolBarList(),
611 maToolBarShellList(),
612 mxLayouter(NULL),
613 mnLockCount(0),
614 mbPreUpdatePending(false),
615 mbPostUpdatePending(false),
616 mpSynchronousLayouterLock(),
617 mpAsynchronousLayouterLock(),
618 mpViewShellManagerLock(),
619 mnPendingUpdateCall(0),
620 mnPendingSetValidCall(0),
621 maToolBarRules(rpToolBarManager,rpViewShellManager)
622 {
623 Link aLink (LINK(this,ToolBarManager::Implementation,EventMultiplexerCallback));
624 mpEventMultiplexer->AddEventListener(
625 aLink,
626 tools::EventMultiplexerEvent::EID_CONTROLLER_ATTACHED
627 | tools::EventMultiplexerEvent::EID_CONTROLLER_DETACHED
628 | tools::EventMultiplexerEvent::EID_PANE_MANAGER_DYING);
629 }
630
631
632
633 /** The order of statements is important.
634 First unregister listeners, which may post user events.
635 Then remove pending user events.
636 */
~Implementation(void)637 ToolBarManager::Implementation::~Implementation (void)
638 {
639 // Unregister at broadcasters.
640 Link aLink (LINK(this,ToolBarManager::Implementation,EventMultiplexerCallback));
641 mpEventMultiplexer->RemoveEventListener(aLink);
642
643 // Abort pending user calls.
644 if (mnPendingUpdateCall != 0)
645 Application::RemoveUserEvent(mnPendingUpdateCall);
646 if (mnPendingSetValidCall != 0)
647 Application::RemoveUserEvent(mnPendingSetValidCall);
648 }
649
650
ToolBarsDestroyed(void)651 void ToolBarManager::Implementation::ToolBarsDestroyed(void)
652 {
653 maToolBarList.MarkAllToolBarsAsNotActive();
654 }
655
656
SetValid(bool bValid)657 void ToolBarManager::Implementation::SetValid (bool bValid)
658 {
659 ::osl::MutexGuard aGuard(maMutex);
660
661 if (mbIsValid != bValid)
662 {
663 UpdateLockImplementation aUpdateLock (*this);
664
665 mbIsValid = bValid;
666 if (mbIsValid)
667 {
668 Reference<frame::XFrame> xFrame;
669 if (mrBase.GetViewFrame() != NULL)
670 xFrame = mrBase.GetViewFrame()->GetFrame().GetFrameInterface();
671 try
672 {
673 Reference<beans::XPropertySet> xFrameProperties (xFrame, UNO_QUERY_THROW);
674 Any aValue (xFrameProperties->getPropertyValue(OUSTRING("LayoutManager")));
675 aValue >>= mxLayouter;
676 }
677 catch (RuntimeException aException)
678 {
679 }
680
681 GetToolBarRules().Update(mrBase);
682 }
683 else
684 {
685 ResetAllToolBars();
686 mxLayouter = NULL;
687 }
688 }
689 }
690
691
692
693
ResetToolBars(ToolBarGroup eGroup)694 void ToolBarManager::Implementation::ResetToolBars (ToolBarGroup eGroup)
695 {
696 ::osl::MutexGuard aGuard(maMutex);
697
698 maToolBarList.ClearGroup(eGroup);
699 maToolBarShellList.ClearGroup(eGroup);
700
701 mbPreUpdatePending = true;
702 }
703
704
705
706
ResetAllToolBars(void)707 void ToolBarManager::Implementation::ResetAllToolBars (void)
708 {
709 #ifdef VERBOSE
710 OSL_TRACE("resetting all tool bars\n");
711 #endif
712 for (int i=TBG__FIRST; i<=TBG__LAST; ++i)
713 ResetToolBars((ToolBarGroup)i);
714 }
715
716
717
718
AddToolBar(ToolBarGroup eGroup,const::rtl::OUString & rsToolBarName)719 void ToolBarManager::Implementation::AddToolBar (
720 ToolBarGroup eGroup,
721 const ::rtl::OUString& rsToolBarName)
722 {
723 ::osl::MutexGuard aGuard(maMutex);
724
725 if (CheckPlugInMode(rsToolBarName))
726 {
727 maToolBarList.AddToolBar(eGroup,rsToolBarName);
728
729 mbPostUpdatePending = true;
730 if (mnLockCount == 0)
731 PostUpdate();
732 }
733 }
734
735
736
737
RemoveToolBar(ToolBarGroup eGroup,const::rtl::OUString & rsToolBarName)738 void ToolBarManager::Implementation::RemoveToolBar (
739 ToolBarGroup eGroup,
740 const ::rtl::OUString& rsToolBarName)
741 {
742 ::osl::MutexGuard aGuard(maMutex);
743
744 if (maToolBarList.RemoveToolBar(eGroup,rsToolBarName))
745 {
746 mbPreUpdatePending = true;
747 if (mnLockCount == 0)
748 PreUpdate();
749 }
750 }
751
752
753
754
AddToolBarShell(ToolBarGroup eGroup,ShellId nToolBarId)755 void ToolBarManager::Implementation::AddToolBarShell (
756 ToolBarGroup eGroup,
757 ShellId nToolBarId)
758 {
759 ViewShell* pMainViewShell = mrBase.GetMainViewShell().get();
760 if (pMainViewShell != NULL)
761 {
762 maToolBarShellList.AddShellId(eGroup,nToolBarId);
763 GetToolBarRules().SubShellAdded(eGroup, nToolBarId);
764 }
765 }
766
767
768
769
ReleaseAllToolBarShells(void)770 void ToolBarManager::Implementation::ReleaseAllToolBarShells (void)
771 {
772 maToolBarShellList.ReleaseAllShells(GetToolBarRules());
773 maToolBarShellList.UpdateShells(mrBase.GetMainViewShell(), mrBase.GetViewShellManager());
774 }
775
776
777
778
RequestUpdate(void)779 void ToolBarManager::Implementation::RequestUpdate (void)
780 {
781 if (mnPendingUpdateCall == 0)
782 {
783 mnPendingUpdateCall = Application::PostUserEvent(
784 LINK(this,ToolBarManager::Implementation,UpdateCallback));
785 }
786 }
787
788
789
790
PreUpdate(void)791 void ToolBarManager::Implementation::PreUpdate (void)
792 {
793 ::osl::MutexGuard aGuard(maMutex);
794
795 if (mbIsValid
796 && mbPreUpdatePending
797 && mxLayouter.is())
798 {
799 mbPreUpdatePending = false;
800
801 #ifdef VERBOSE
802 OSL_TRACE("ToolBarManager::PreUpdate [");
803 #endif
804
805 // Get the list of tool bars that are not used anymore and are to be
806 // deactivated.
807 NameList aToolBars;
808 maToolBarList.GetToolBarsToDeactivate(aToolBars);
809
810 // Turn off the tool bars.
811 NameList::const_iterator iToolBar;
812 for (iToolBar=aToolBars.begin(); iToolBar!=aToolBars.end(); ++iToolBar)
813 {
814 ::rtl::OUString sFullName (GetToolBarResourceName(*iToolBar));
815 #ifdef VERBOSE
816 OSL_TRACE(" turning off tool bar %s",
817 ::rtl::OUStringToOString(sFullName, RTL_TEXTENCODING_UTF8).getStr());
818 #endif
819 mxLayouter->destroyElement(sFullName);
820 maToolBarList.MarkToolBarAsNotActive(*iToolBar);
821 }
822
823 #ifdef VERBOSE
824 OSL_TRACE("ToolBarManager::PreUpdate ]\n");
825 #endif
826 }
827 }
828
829
830
831
PostUpdate(void)832 void ToolBarManager::Implementation::PostUpdate (void)
833 {
834 ::osl::MutexGuard aGuard(maMutex);
835
836 if (mbIsValid
837 && mbPostUpdatePending
838 && mxLayouter.is())
839 {
840 mbPostUpdatePending = false;
841
842 // Create the list of requested tool bars.
843 NameList aToolBars;
844 maToolBarList.GetToolBarsToActivate(aToolBars);
845
846 #ifdef VERBOSE
847 OSL_TRACE("ToolBarManager::PostUpdate [");
848 #endif
849
850 // Turn on the tool bars that are visible in the new context.
851 NameList::const_iterator iToolBar;
852 for (iToolBar=aToolBars.begin(); iToolBar!=aToolBars.end(); ++iToolBar)
853 {
854 ::rtl::OUString sFullName (GetToolBarResourceName(*iToolBar));
855 #ifdef VERBOSE
856 OSL_TRACE(" turning on tool bar %s",
857 ::rtl::OUStringToOString(sFullName, RTL_TEXTENCODING_UTF8).getStr());
858 #endif
859 mxLayouter->requestElement(sFullName);
860 maToolBarList.MarkToolBarAsActive(*iToolBar);
861 }
862
863 #ifdef VERBOSE
864 OSL_TRACE("ToolBarManager::PostUpdate ]\n");
865 #endif
866 }
867 }
868
869
870
871
LockViewShellManager(void)872 void ToolBarManager::Implementation::LockViewShellManager (void)
873 {
874 if (mpViewShellManagerLock.get() == NULL)
875 mpViewShellManagerLock.reset(
876 new ViewShellManager::UpdateLock(mrBase.GetViewShellManager()));
877 }
878
879
880
881
LockUpdate(void)882 void ToolBarManager::Implementation::LockUpdate (void)
883 {
884 #ifdef VERBOSE
885 OSL_TRACE("LockUpdate %d\n", mnLockCount);
886 #endif
887 ::osl::MutexGuard aGuard(maMutex);
888
889 DBG_ASSERT(mnLockCount<100, "ToolBarManager lock count unusually high");
890 if (mnLockCount == 0)
891 {
892 OSL_ASSERT(mpSynchronousLayouterLock.get()==NULL);
893
894 mpSynchronousLayouterLock.reset(new LayouterLock(mxLayouter));
895 }
896 ++mnLockCount;
897 }
898
899
900
901
UnlockUpdate(void)902 void ToolBarManager::Implementation::UnlockUpdate (void)
903 {
904 #ifdef VERBOSE
905 OSL_TRACE("UnlockUpdate %d\n", mnLockCount);
906 #endif
907 ::osl::MutexGuard aGuard(maMutex);
908
909 OSL_ASSERT(mnLockCount>0);
910 --mnLockCount;
911 if (mnLockCount == 0)
912 {
913 Update(mpSynchronousLayouterLock);
914 }
915 }
916
917
918
919
Update(::std::auto_ptr<LayouterLock> pLocalLayouterLock)920 void ToolBarManager::Implementation::Update (
921 ::std::auto_ptr<LayouterLock> pLocalLayouterLock)
922 {
923 // When the lock is released and there are pending changes to the set of
924 // tool bars then update this set now.
925 if (mnLockCount == 0)
926 {
927 // During ceation of ViewShellBase we may have the situation that
928 // the controller has already been created and attached to the frame
929 // but that the ToolBarManager has not yet completed its
930 // initialization (by initializing the mxLayouter member.) We do
931 // this here so that we do not have to wait for the next Update()
932 // call to show the tool bars.
933 if (mnPendingSetValidCall != 0)
934 {
935 Application::RemoveUserEvent(mnPendingSetValidCall);
936 mnPendingSetValidCall = 0;
937 SetValid(true);
938 }
939
940 if (mbIsValid && mxLayouter.is() && (mbPreUpdatePending || mbPostUpdatePending))
941 {
942 // 1) Release UNO tool bars that are not longer used. Do this
943 // now so that they are not updated when the SFX shell stack is
944 // modified.
945 if (mbPreUpdatePending)
946 PreUpdate();
947
948 // 2) Update the requested shells that represent tool bar
949 // functionality. Those that are not used anymore are
950 // deactivated now. Those that are missing are activated in the
951 // next step together with the view shells.
952 if (mpViewShellManagerLock.get() == NULL)
953 mpViewShellManagerLock.reset(
954 new ViewShellManager::UpdateLock(mrBase.GetViewShellManager()));
955 maToolBarShellList.UpdateShells(
956 mrBase.GetMainViewShell(),
957 mrBase.GetViewShellManager());
958
959 // 3) Unlock the ViewShellManager::UpdateLock. This updates the
960 // shell stack. We have to be careful here. The deletion of
961 // the lock may end in a synchronous call to LockUpdate(). When
962 // at this time the lock has been deleted but the auto_ptr has
963 // not yet been reset then the lock is deleted a second time.
964 ViewShellManager::UpdateLock* pLock = mpViewShellManagerLock.release();
965 delete pLock;
966
967 // 4) Make the UNO tool bars visible. The outstanding call to
968 // PostUpdate() is done via PostUserEvent() so that it is
969 // guaranteed to be executed when the SFX shell stack has been
970 // updated (under the assumption that our lock to the
971 // ViewShellManager was the only one open. If that is not the
972 // case then all should still be well but not as fast.)
973 //
974 // Note that the lock count may have been increased since
975 // entering this method. In that case one of the next
976 // UnlockUpdate() calls will post the UpdateCallback.
977 if (mnPendingUpdateCall==0 && mnLockCount==0)
978 {
979 mpAsynchronousLayouterLock = pLocalLayouterLock;
980 mnPendingUpdateCall = Application::PostUserEvent(
981 LINK(this,ToolBarManager::Implementation,UpdateCallback));
982 }
983 }
984 else
985 {
986 mpViewShellManagerLock.reset();
987 pLocalLayouterLock.reset();
988 }
989 }
990 }
991
992
993
994
GetToolBarRules(void)995 ToolBarRules& ToolBarManager::Implementation::GetToolBarRules (void)
996 {
997 return maToolBarRules;
998 }
999
1000
1001
1002
IMPL_LINK(ToolBarManager::Implementation,UpdateCallback,bool *,EMPTYARG)1003 IMPL_LINK(ToolBarManager::Implementation,UpdateCallback,bool*,EMPTYARG)
1004 {
1005 mnPendingUpdateCall = 0;
1006 if (mnLockCount == 0)
1007 {
1008 if (mbPreUpdatePending)
1009 PreUpdate();
1010 if (mbPostUpdatePending)
1011 PostUpdate();
1012 if (mbIsValid && mxLayouter.is())
1013 mpAsynchronousLayouterLock.reset();
1014 }
1015 return 0;
1016 }
1017
1018
1019
1020
IMPL_LINK(ToolBarManager::Implementation,EventMultiplexerCallback,sd::tools::EventMultiplexerEvent *,pEvent)1021 IMPL_LINK(ToolBarManager::Implementation,EventMultiplexerCallback,
1022 sd::tools::EventMultiplexerEvent*,pEvent)
1023 {
1024 if (pEvent != NULL)
1025 {
1026 switch (pEvent->meEventId)
1027 {
1028 case tools::EventMultiplexerEvent::EID_CONTROLLER_ATTACHED:
1029 if (mnPendingSetValidCall == 0)
1030 mnPendingSetValidCall
1031 = Application::PostUserEvent(LINK(this,Implementation,SetValidCallback));
1032 break;
1033
1034 case tools::EventMultiplexerEvent::EID_CONTROLLER_DETACHED:
1035 SetValid(false);
1036 break;
1037
1038 case tools::EventMultiplexerEvent::EID_PANE_MANAGER_DYING:
1039 SetValid(false);
1040 break;
1041 }
1042 }
1043 return 0;
1044 }
1045
1046
1047
1048
IMPL_LINK(ToolBarManager::Implementation,SetValidCallback,void *,EMPTYARG)1049 IMPL_LINK(ToolBarManager::Implementation, SetValidCallback,void*,EMPTYARG)
1050 {
1051 mnPendingSetValidCall = 0;
1052 SetValid(true);
1053 return 0;
1054 }
1055
1056
1057
1058
1059
GetToolBarResourceName(const::rtl::OUString & rsBaseName) const1060 ::rtl::OUString ToolBarManager::Implementation::GetToolBarResourceName (
1061 const ::rtl::OUString& rsBaseName) const
1062 {
1063 ::rtl::OUString sToolBarName (msToolBarResourcePrefix);
1064 sToolBarName += rsBaseName;
1065 return sToolBarName;
1066 }
1067
1068
1069
1070
CheckPlugInMode(const::rtl::OUString & rsName) const1071 bool ToolBarManager::Implementation::CheckPlugInMode (const ::rtl::OUString& rsName) const
1072 {
1073 bool bValid (false);
1074
1075 // Determine the plug in mode.
1076 bool bIsPlugInMode (false);
1077 do
1078 {
1079 SfxObjectShell* pObjectShell = mrBase.GetObjectShell();
1080 if (pObjectShell == NULL)
1081 break;
1082
1083 SfxMedium* pMedium = pObjectShell->GetMedium();
1084 if (pMedium == NULL)
1085 break;
1086
1087 SFX_ITEMSET_ARG(pMedium->GetItemSet(),pViewOnlyItem,SfxBoolItem,SID_VIEWONLY,sal_False);
1088 if (pViewOnlyItem == NULL)
1089 break;
1090
1091 bIsPlugInMode = pViewOnlyItem->GetValue();
1092 }
1093 while (false);
1094
1095 if (rsName.equals(msViewerToolBar))
1096 bValid = bIsPlugInMode;
1097 else
1098 bValid = ! bIsPlugInMode;
1099
1100 return bValid;
1101 }
1102
1103
1104
1105
1106 } // end of namespace sd
1107
1108
1109
1110
1111 namespace {
1112
1113 using namespace ::sd;
1114
1115 //===== LayouterLock ==========================================================
1116
LayouterLock(const Reference<frame::XLayoutManager> & rxLayouter)1117 LayouterLock::LayouterLock (const Reference<frame::XLayoutManager>& rxLayouter)
1118 : mxLayouter(rxLayouter)
1119 {
1120 #ifdef VERBOSE
1121 OSL_TRACE("LayouterLock %d", mxLayouter.is() ? 1 :0);
1122 #endif
1123 if (mxLayouter.is())
1124 mxLayouter->lock();
1125 }
1126
1127
1128
1129
~LayouterLock(void)1130 LayouterLock::~LayouterLock (void)
1131 {
1132 #ifdef VERBOSE
1133 OSL_TRACE("~LayouterLock %d", mxLayouter.is() ? 1 :0);
1134 #endif
1135 if (mxLayouter.is())
1136 mxLayouter->unlock();
1137 }
1138
1139
1140
1141
1142 //===== ToolBarRules ==========================================================
1143
ToolBarRules(const::boost::shared_ptr<sd::ToolBarManager> & rpToolBarManager,const::boost::shared_ptr<sd::ViewShellManager> & rpViewShellManager)1144 ToolBarRules::ToolBarRules (
1145 const ::boost::shared_ptr<sd::ToolBarManager>& rpToolBarManager,
1146 const ::boost::shared_ptr<sd::ViewShellManager>& rpViewShellManager)
1147 : mpToolBarManager(rpToolBarManager),
1148 mpViewShellManager(rpViewShellManager)
1149 {
1150 }
1151
1152
1153
1154
Update(ViewShellBase & rBase)1155 void ToolBarRules::Update (ViewShellBase& rBase)
1156 {
1157 ViewShell* pMainViewShell = rBase.GetMainViewShell().get();
1158 if (pMainViewShell != NULL)
1159 {
1160 MainViewShellChanged(pMainViewShell->GetShellType());
1161 if (pMainViewShell->GetView())
1162 SelectionHasChanged (*pMainViewShell, *pMainViewShell->GetView());
1163 }
1164 else
1165 MainViewShellChanged(ViewShell::ST_NONE);
1166 }
1167
1168
1169
1170
MainViewShellChanged(ViewShell::ShellType nShellType)1171 void ToolBarRules::MainViewShellChanged (ViewShell::ShellType nShellType)
1172 {
1173 ::sd::ToolBarManager::UpdateLock aToolBarManagerLock (mpToolBarManager);
1174 ::sd::ViewShellManager::UpdateLock aViewShellManagerLock (mpViewShellManager);
1175
1176 mpToolBarManager->ResetAllToolBars();
1177
1178 switch(nShellType)
1179 {
1180 case ::sd::ViewShell::ST_IMPRESS:
1181 case ::sd::ViewShell::ST_NOTES:
1182 case ::sd::ViewShell::ST_HANDOUT:
1183 mpToolBarManager->AddToolBar(
1184 ToolBarManager::TBG_PERMANENT,
1185 ToolBarManager::msToolBar);
1186 mpToolBarManager->AddToolBar(
1187 ToolBarManager::TBG_PERMANENT,
1188 ToolBarManager::msOptionsToolBar);
1189 mpToolBarManager->AddToolBar(
1190 ToolBarManager::TBG_PERMANENT,
1191 ToolBarManager::msCommonTaskToolBar);
1192 mpToolBarManager->AddToolBar(
1193 ToolBarManager::TBG_PERMANENT,
1194 ToolBarManager::msViewerToolBar);
1195 break;
1196
1197 case ::sd::ViewShell::ST_DRAW:
1198 mpToolBarManager->AddToolBar(
1199 ToolBarManager::TBG_PERMANENT,
1200 ToolBarManager::msToolBar);
1201 mpToolBarManager->AddToolBar(
1202 ToolBarManager::TBG_PERMANENT,
1203 ToolBarManager::msOptionsToolBar);
1204 mpToolBarManager->AddToolBar(
1205 ToolBarManager::TBG_PERMANENT,
1206 ToolBarManager::msViewerToolBar);
1207 break;
1208
1209 case ViewShell::ST_OUTLINE:
1210 mpToolBarManager->AddToolBar(
1211 ToolBarManager::TBG_PERMANENT,
1212 ToolBarManager::msOutlineToolBar);
1213 mpToolBarManager->AddToolBar(
1214 ToolBarManager::TBG_PERMANENT,
1215 ToolBarManager::msViewerToolBar);
1216 mpToolBarManager->AddToolBarShell(
1217 ToolBarManager::TBG_PERMANENT, RID_DRAW_TEXT_TOOLBOX);
1218 break;
1219
1220 case ViewShell::ST_SLIDE_SORTER:
1221 mpToolBarManager->AddToolBar(
1222 ToolBarManager::TBG_PERMANENT,
1223 ToolBarManager::msViewerToolBar);
1224 mpToolBarManager->AddToolBar(
1225 ToolBarManager::TBG_PERMANENT,
1226 ToolBarManager::msSlideSorterToolBar);
1227 mpToolBarManager->AddToolBar(
1228 ToolBarManager::TBG_PERMANENT,
1229 ToolBarManager::msSlideSorterObjectBar);
1230 break;
1231
1232 case ViewShell::ST_NONE:
1233 case ViewShell::ST_PRESENTATION:
1234 case ViewShell::ST_SIDEBAR:
1235 default:
1236 break;
1237 }
1238 }
1239
1240
1241
1242
MainViewShellChanged(const ViewShell & rMainViewShell)1243 void ToolBarRules::MainViewShellChanged (const ViewShell& rMainViewShell)
1244 {
1245 ::sd::ToolBarManager::UpdateLock aToolBarManagerLock (mpToolBarManager);
1246 ::sd::ViewShellManager::UpdateLock aViewShellManagerLock (mpViewShellManager);
1247
1248 MainViewShellChanged(rMainViewShell.GetShellType());
1249 switch(rMainViewShell.GetShellType())
1250 {
1251 case ::sd::ViewShell::ST_IMPRESS:
1252 case ::sd::ViewShell::ST_DRAW:
1253 case ::sd::ViewShell::ST_NOTES:
1254 {
1255 const DrawViewShell* pDrawViewShell
1256 = dynamic_cast<const DrawViewShell*>(&rMainViewShell);
1257 if (pDrawViewShell != NULL)
1258 if (pDrawViewShell->GetEditMode() == EM_MASTERPAGE)
1259 mpToolBarManager->AddToolBar(
1260 ToolBarManager::TBG_MASTER_MODE,
1261 ToolBarManager::msMasterViewToolBar);
1262 break;
1263 }
1264
1265 default:
1266 break;
1267 }
1268 }
1269
1270
1271
1272
SelectionHasChanged(const::sd::ViewShell & rViewShell,const SdrView & rView)1273 void ToolBarRules::SelectionHasChanged (
1274 const ::sd::ViewShell& rViewShell,
1275 const SdrView& rView)
1276 {
1277 ::sd::ToolBarManager::UpdateLock aLock (mpToolBarManager);
1278 mpToolBarManager->LockViewShellManager();
1279 bool bTextEdit = rView.IsTextEdit();
1280
1281 mpToolBarManager->ResetToolBars(ToolBarManager::TBG_FUNCTION);
1282
1283 switch (rView.GetContext())
1284 {
1285 case SDRCONTEXT_GRAPHIC:
1286 if( !bTextEdit )
1287 mpToolBarManager->SetToolBarShell(ToolBarManager::TBG_FUNCTION, RID_DRAW_GRAF_TOOLBOX);
1288 break;
1289
1290 case SDRCONTEXT_MEDIA:
1291 if( !bTextEdit )
1292 mpToolBarManager->SetToolBarShell(ToolBarManager::TBG_FUNCTION, RID_DRAW_MEDIA_TOOLBOX);
1293 break;
1294
1295 case SDRCONTEXT_TABLE:
1296 mpToolBarManager->SetToolBarShell(ToolBarManager::TBG_FUNCTION, RID_DRAW_TABLE_TOOLBOX);
1297 bTextEdit = true;
1298 break;
1299
1300 case SDRCONTEXT_STANDARD:
1301 default:
1302 if( !bTextEdit )
1303 {
1304 switch(rViewShell.GetShellType())
1305 {
1306 case ::sd::ViewShell::ST_IMPRESS:
1307 case ::sd::ViewShell::ST_DRAW:
1308 case ::sd::ViewShell::ST_NOTES:
1309 case ::sd::ViewShell::ST_HANDOUT:
1310 mpToolBarManager->SetToolBar(
1311 ToolBarManager::TBG_FUNCTION,
1312 ToolBarManager::msDrawingObjectToolBar);
1313 break;
1314 default:
1315 break;
1316 }
1317 break;
1318 }
1319 }
1320
1321 if( bTextEdit )
1322 mpToolBarManager->AddToolBarShell(ToolBarManager::TBG_FUNCTION, RID_DRAW_TEXT_TOOLBOX);
1323
1324 SdrView* pView = &const_cast<SdrView&>(rView);
1325 // Check if the extrusion tool bar and the fontwork tool bar have to
1326 // be activated.
1327 if (svx::checkForSelectedCustomShapes(pView, true /* bOnlyExtruded */ ))
1328 mpToolBarManager->AddToolBarShell(ToolBarManager::TBG_FUNCTION, RID_SVX_EXTRUSION_BAR);
1329 sal_uInt32 nCheckStatus = 0;
1330 if (svx::checkForSelectedFontWork(pView, nCheckStatus))
1331 mpToolBarManager->AddToolBarShell(ToolBarManager::TBG_FUNCTION, RID_SVX_FONTWORK_BAR);
1332
1333 // Switch on additional context-sensitive tool bars.
1334 if (rView.GetContext() == SDRCONTEXT_POINTEDIT)
1335 mpToolBarManager->AddToolBarShell(ToolBarManager::TBG_FUNCTION, RID_BEZIER_TOOLBOX);
1336 }
1337
1338
1339
1340
SubShellAdded(::sd::ToolBarManager::ToolBarGroup eGroup,sd::ShellId nShellId)1341 void ToolBarRules::SubShellAdded (
1342 ::sd::ToolBarManager::ToolBarGroup eGroup,
1343 sd::ShellId nShellId)
1344 {
1345 // For some tool bar shells (those defined in sd) we have to add the
1346 // actual tool bar here.
1347 switch (nShellId)
1348 {
1349 case RID_DRAW_GRAF_TOOLBOX:
1350 mpToolBarManager->AddToolBar(eGroup, ToolBarManager::msGraphicObjectBar);
1351 break;
1352
1353 case RID_DRAW_MEDIA_TOOLBOX:
1354 mpToolBarManager->AddToolBar(eGroup, ToolBarManager::msMediaObjectBar);
1355 break;
1356
1357 case RID_DRAW_TEXT_TOOLBOX:
1358 mpToolBarManager->AddToolBar(eGroup, ToolBarManager::msTextObjectBar);
1359 break;
1360
1361 case RID_BEZIER_TOOLBOX:
1362 mpToolBarManager->AddToolBar(eGroup, ToolBarManager::msBezierObjectBar);
1363 break;
1364
1365 case RID_DRAW_TABLE_TOOLBOX:
1366 mpToolBarManager->AddToolBar(eGroup, ToolBarManager::msTableObjectBar);
1367 break;
1368 }
1369 }
1370
1371
1372
1373
SubShellRemoved(::sd::ToolBarManager::ToolBarGroup eGroup,sd::ShellId nShellId)1374 void ToolBarRules::SubShellRemoved (
1375 ::sd::ToolBarManager::ToolBarGroup eGroup,
1376 sd::ShellId nShellId)
1377 {
1378 // For some tool bar shells (those defined in sd) we have to add the
1379 // actual tool bar here.
1380 switch (nShellId)
1381 {
1382 case RID_DRAW_GRAF_TOOLBOX:
1383 mpToolBarManager->RemoveToolBar(eGroup, ToolBarManager::msGraphicObjectBar);
1384 break;
1385
1386 case RID_DRAW_MEDIA_TOOLBOX:
1387 mpToolBarManager->RemoveToolBar(eGroup, ToolBarManager::msMediaObjectBar);
1388 break;
1389
1390 case RID_DRAW_TEXT_TOOLBOX:
1391 mpToolBarManager->RemoveToolBar(eGroup, ToolBarManager::msTextObjectBar);
1392 break;
1393
1394 case RID_BEZIER_TOOLBOX:
1395 mpToolBarManager->RemoveToolBar(eGroup, ToolBarManager::msBezierObjectBar);
1396 break;
1397
1398 case RID_DRAW_TABLE_TOOLBOX:
1399 mpToolBarManager->RemoveToolBar(eGroup, ToolBarManager::msTableObjectBar);
1400 break;
1401 }
1402 }
1403
1404
1405
1406
1407 //===== ToolBarList ===========================================================
1408
ToolBarList(void)1409 ToolBarList::ToolBarList (void)
1410 : maGroups(),
1411 maActiveToolBars()
1412 {
1413 }
1414
1415
1416
1417
ClearGroup(sd::ToolBarManager::ToolBarGroup eGroup)1418 void ToolBarList::ClearGroup (sd::ToolBarManager::ToolBarGroup eGroup)
1419 {
1420 Groups::iterator iGroup (maGroups.find(eGroup));
1421 if (iGroup != maGroups.end())
1422 {
1423 if ( ! iGroup->second.empty())
1424 {
1425 iGroup->second.clear();
1426 }
1427 }
1428 }
1429
1430
1431
1432
AddToolBar(sd::ToolBarManager::ToolBarGroup eGroup,const::rtl::OUString & rsName)1433 void ToolBarList::AddToolBar (
1434 sd::ToolBarManager::ToolBarGroup eGroup,
1435 const ::rtl::OUString& rsName)
1436 {
1437 Groups::iterator iGroup (maGroups.find(eGroup));
1438 if (iGroup == maGroups.end())
1439 iGroup = maGroups.insert(Groups::value_type(eGroup,NameList())).first;
1440
1441 if (iGroup != maGroups.end())
1442 {
1443 NameList::const_iterator iBar (
1444 ::std::find(iGroup->second.begin(),iGroup->second.end(),rsName));
1445 if (iBar == iGroup->second.end())
1446 {
1447 iGroup->second.push_back(rsName);
1448 }
1449 }
1450 }
1451
1452
1453
1454
RemoveToolBar(sd::ToolBarManager::ToolBarGroup eGroup,const::rtl::OUString & rsName)1455 bool ToolBarList::RemoveToolBar (
1456 sd::ToolBarManager::ToolBarGroup eGroup,
1457 const ::rtl::OUString& rsName)
1458 {
1459 Groups::iterator iGroup (maGroups.find(eGroup));
1460 if (iGroup != maGroups.end())
1461 {
1462 NameList::iterator iBar (
1463 ::std::find(iGroup->second.begin(),iGroup->second.end(),rsName));
1464 if (iBar != iGroup->second.end())
1465 {
1466 iGroup->second.erase(iBar);
1467 return true;
1468 }
1469 }
1470 return false;
1471 }
1472
1473
1474
1475
MakeRequestedToolBarList(NameList & rRequestedToolBars) const1476 void ToolBarList::MakeRequestedToolBarList (NameList& rRequestedToolBars) const
1477 {
1478 for (int i=sd::ToolBarManager::TBG__FIRST; i<=sd::ToolBarManager::TBG__LAST; ++i)
1479 {
1480 ::sd::ToolBarManager::ToolBarGroup eGroup = (::sd::ToolBarManager::ToolBarGroup)i;
1481 Groups::const_iterator iGroup (maGroups.find(eGroup));
1482 if (iGroup != maGroups.end())
1483 ::std::copy(
1484 iGroup->second.begin(),
1485 iGroup->second.end(),
1486 ::std::inserter(rRequestedToolBars,rRequestedToolBars.end()));
1487 }
1488 }
1489
1490
1491
1492
GetToolBarsToActivate(NameList & rToolBars) const1493 void ToolBarList::GetToolBarsToActivate (NameList& rToolBars) const
1494 {
1495 NameList aRequestedToolBars;
1496 MakeRequestedToolBarList(aRequestedToolBars);
1497
1498 NameList::const_iterator iToolBar;
1499 for (iToolBar=aRequestedToolBars.begin(); iToolBar!=aRequestedToolBars.end(); ++iToolBar)
1500 {
1501 if (::std::find(maActiveToolBars.begin(),maActiveToolBars.end(),*iToolBar)
1502 == maActiveToolBars.end())
1503 {
1504 rToolBars.push_back(*iToolBar);
1505 }
1506 }
1507 }
1508
1509
1510
1511
GetToolBarsToDeactivate(NameList & rToolBars) const1512 void ToolBarList::GetToolBarsToDeactivate (NameList& rToolBars) const
1513 {
1514 NameList aRequestedToolBars;
1515 MakeRequestedToolBarList(aRequestedToolBars);
1516
1517 NameList::const_iterator iToolBar;
1518 for (iToolBar=maActiveToolBars.begin(); iToolBar!=maActiveToolBars.end(); ++iToolBar)
1519 {
1520 if (::std::find(aRequestedToolBars.begin(),aRequestedToolBars.end(),*iToolBar)
1521 == aRequestedToolBars.end())
1522 {
1523 rToolBars.push_back(*iToolBar);
1524 }
1525 }
1526 }
1527
1528
1529
1530
MarkToolBarAsActive(const::rtl::OUString & rsName)1531 void ToolBarList::MarkToolBarAsActive (const ::rtl::OUString& rsName)
1532 {
1533 maActiveToolBars.push_back(rsName);
1534 }
1535
1536
1537
1538
MarkToolBarAsNotActive(const::rtl::OUString & rsName)1539 void ToolBarList::MarkToolBarAsNotActive (const ::rtl::OUString& rsName)
1540 {
1541 maActiveToolBars.erase(
1542 ::std::find(maActiveToolBars.begin(),maActiveToolBars.end(), rsName));
1543 }
1544
1545
1546
1547
MarkAllToolBarsAsNotActive(void)1548 void ToolBarList::MarkAllToolBarsAsNotActive (void)
1549 {
1550 maActiveToolBars.clear();
1551 }
1552
1553
1554
1555
1556 //===== ToolBarShellList ======================================================
1557
ShellDescriptor(ShellId nId,sd::ToolBarManager::ToolBarGroup eGroup)1558 ToolBarShellList::ShellDescriptor::ShellDescriptor (
1559 ShellId nId,
1560 sd::ToolBarManager::ToolBarGroup eGroup)
1561 : mnId(nId),
1562 meGroup(eGroup)
1563 {
1564 }
1565
1566
1567
1568
ToolBarShellList(void)1569 ToolBarShellList::ToolBarShellList (void)
1570 : maNewList()
1571 , maCurrentList()
1572 {
1573 }
1574
1575
1576
1577
ClearGroup(sd::ToolBarManager::ToolBarGroup eGroup)1578 void ToolBarShellList::ClearGroup (sd::ToolBarManager::ToolBarGroup eGroup)
1579 {
1580 // In every loop we erase the first member of the specified group.
1581 // Because that invalidates the iterator another loop is started after
1582 // that. The loop is left only when no member of the group is found and
1583 // no element is erased
1584 bool bLoop;
1585 do
1586 {
1587 bLoop = false;
1588
1589 GroupedShellList::iterator iDescriptor;
1590 for (iDescriptor=maNewList.begin(); iDescriptor!=maNewList.end(); ++iDescriptor)
1591 if (iDescriptor->meGroup == eGroup)
1592 {
1593 maNewList.erase(iDescriptor);
1594 // Erasing the descriptor invalidated the iterator so we
1595 // have to exit the for loop and start anew to search for
1596 // further elements of the group.
1597 bLoop = true;
1598 break;
1599 }
1600 }
1601 while (bLoop);
1602 }
1603
1604
1605
1606
AddShellId(sd::ToolBarManager::ToolBarGroup eGroup,sd::ShellId nId)1607 void ToolBarShellList::AddShellId (sd::ToolBarManager::ToolBarGroup eGroup, sd::ShellId nId)
1608 {
1609 // Make sure that the shell is not added twice (and possibly in
1610 // different groups.)
1611 ShellDescriptor aDescriptor (nId,eGroup);
1612 GroupedShellList::iterator iDescriptor (maNewList.find(aDescriptor));
1613 if (iDescriptor != maNewList.end())
1614 {
1615 // The shell is already requested.
1616 if (iDescriptor->meGroup != eGroup)
1617 {
1618 // It is now being requested for another group.
1619 // (Is this an error?)
1620 // Move it to that group.
1621 maNewList.erase(iDescriptor);
1622 maNewList.insert(aDescriptor);
1623 }
1624 // else nothing to do.
1625 }
1626 else
1627 maNewList.insert(aDescriptor);
1628 }
1629
1630
1631
1632
ReleaseAllShells(ToolBarRules & rRules)1633 void ToolBarShellList::ReleaseAllShells (ToolBarRules& rRules)
1634 {
1635 // Release the currently active tool bars.
1636 GroupedShellList aList (maCurrentList);
1637 GroupedShellList::iterator iDescriptor;
1638 for (iDescriptor=aList.begin(); iDescriptor!=aList.end(); ++iDescriptor)
1639 {
1640 rRules.SubShellRemoved(iDescriptor->meGroup, iDescriptor->mnId);
1641 }
1642
1643 // Clear the list of requested tool bars.
1644 maNewList.clear();
1645 }
1646
1647
1648
1649
UpdateShells(const::boost::shared_ptr<ViewShell> & rpMainViewShell,const::boost::shared_ptr<ViewShellManager> & rpManager)1650 void ToolBarShellList::UpdateShells (
1651 const ::boost::shared_ptr<ViewShell>& rpMainViewShell,
1652 const ::boost::shared_ptr<ViewShellManager>& rpManager)
1653 {
1654 if (rpMainViewShell.get() != NULL)
1655 {
1656 GroupedShellList aList;
1657
1658 // Deactivate shells that are in maCurrentList, but not in
1659 // maNewList.
1660 ::std::set_difference(maCurrentList.begin(), maCurrentList.end(),
1661 maNewList.begin(), maNewList.end(),
1662 std::insert_iterator<GroupedShellList>(aList,aList.begin()));
1663 for (GroupedShellList::iterator iShell=aList.begin(); iShell!=aList.end(); ++iShell)
1664 {
1665 #ifdef VERBOSE
1666 OSL_TRACE("deactivating tool bar shell %d\n", iShell->mnId);
1667 #endif
1668 rpManager->DeactivateSubShell(*rpMainViewShell, iShell->mnId);
1669 }
1670
1671 // Activate shells that are in maNewList, but not in
1672 // maCurrentList.
1673 aList.clear();
1674 ::std::set_difference(maNewList.begin(), maNewList.end(),
1675 maCurrentList.begin(), maCurrentList.end(),
1676 std::insert_iterator<GroupedShellList>(aList,aList.begin()));
1677 for (GroupedShellList::iterator iShell=aList.begin(); iShell!=aList.end(); ++iShell)
1678 {
1679 #ifdef VERBOSE
1680 OSL_TRACE("activating tool bar shell %d\n", iShell->mnId);
1681 #endif
1682 rpManager->ActivateSubShell(*rpMainViewShell, iShell->mnId);
1683 }
1684
1685 // The maNewList now refelects the current state and thus is made
1686 // maCurrentList.
1687 maCurrentList = maNewList;
1688 }
1689 }
1690
1691
1692
1693
1694 } // end of anonymous namespace
1695