xref: /AOO41X/main/cui/source/customize/cfg.cxx (revision 8809db7a87f97847b57a57f4cd2b0104b2b83182)
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_cui.hxx"
26 
27 #include <stdlib.h>
28 #include <time.h>
29 
30 #ifndef _HELP_HXX //autogen
31 #include <vcl/help.hxx>
32 #endif
33 #ifndef _MSGBOX_HXX //autogen
34 #include <vcl/msgbox.hxx>
35 #endif
36 #include <vcl/decoview.hxx>
37 #include <vcl/toolbox.hxx>
38 #include <vcl/scrbar.hxx>
39 
40 //added for issue73355
41 //#ifndef _SV_SVDATA_HXX
42 //#include <vcl/svdata.hxx>
43 //#endif
44 //issue73355 ends
45 
46 #include <sfx2/app.hxx>
47 #include <sfx2/sfxdlg.hxx>
48 #include <sfx2/viewfrm.hxx>
49 #include <sfx2/viewsh.hxx>
50 #include <sfx2/msg.hxx>
51 #include <sfx2/msgpool.hxx>
52 #include <sfx2/mnumgr.hxx>
53 #include <sfx2/minfitem.hxx>
54 #include <sfx2/objsh.hxx>
55 #include <sfx2/request.hxx>
56 #include <sfx2/filedlghelper.hxx>
57 #include <svl/stritem.hxx>
58 #include <svtools/miscopt.hxx>
59 #include <tools/diagnose_ex.h>
60 #include <toolkit/unohlp.hxx>
61 
62 #include <algorithm>
63 //add
64 #include <cuires.hrc>
65 #include "cfg.hrc"
66 #include "helpid.hrc"
67 
68 #include "acccfg.hxx"
69 #include "cfg.hxx"
70 #include "eventdlg.hxx"
71 #include <dialmgr.hxx>
72 
73 #include <comphelper/documentinfo.hxx>
74 #include <comphelper/processfactory.hxx>
75 #ifndef _UNOTOOLS_CONFIGMGR_HXX_
76 #include <unotools/configmgr.hxx>
77 #endif
78 #include <com/sun/star/ui/ItemType.hpp>
79 #include <com/sun/star/ui/ItemStyle.hpp>
80 #include <com/sun/star/ui/XModuleUIConfigurationManagerSupplier.hpp>
81 #include <com/sun/star/frame/XController.hpp>
82 #include <com/sun/star/frame/XDesktop.hpp>
83 #include <com/sun/star/ui/XUIConfiguration.hpp>
84 #include <com/sun/star/ui/XUIConfigurationListener.hpp>
85 #include <com/sun/star/ui/XUIConfigurationManagerSupplier.hpp>
86 #include <com/sun/star/ui/XUIConfigurationPersistence.hpp>
87 #include <com/sun/star/ui/XUIConfigurationStorage.hpp>
88 #include <com/sun/star/ui/XModuleUIConfigurationManager.hpp>
89 #include <com/sun/star/ui/XUIElement.hpp>
90 #ifndef _COM_SUN_STAR_UI_UIElementType_HPP_
91 #include <com/sun/star/ui/UIElementType.hpp>
92 #endif
93 #include <com/sun/star/ui/ImageType.hpp>
94 #include <com/sun/star/frame/XLayoutManager.hpp>
95 #include <com/sun/star/ui/dialogs/ExtendedFilePickerElementIds.hpp>
96 #include "com/sun/star/ui/dialogs/TemplateDescription.hpp"
97 #include <com/sun/star/ui/dialogs/XFilePickerControlAccess.hpp>
98 #include <com/sun/star/frame/XFramesSupplier.hpp>
99 #include <com/sun/star/frame/XFrames.hpp>
100 #include <com/sun/star/frame/FrameSearchFlag.hpp>
101 #include <com/sun/star/embed/ElementModes.hpp>
102 
103 #include "dlgname.hxx"
104 
105 #define PRTSTR(x) rtl::OUStringToOString(x, RTL_TEXTENCODING_ASCII_US).pData->buffer
106 
107 #define ENTRY_HEIGHT 16
108 
109 static const char ITEM_DESCRIPTOR_COMMANDURL[]  = "CommandURL";
110 static const char ITEM_DESCRIPTOR_CONTAINER[]   = "ItemDescriptorContainer";
111 static const char ITEM_DESCRIPTOR_LABEL[]       = "Label";
112 static const char ITEM_DESCRIPTOR_TYPE[]        = "Type";
113 static const char ITEM_DESCRIPTOR_STYLE[]       = "Style";
114 static const char ITEM_DESCRIPTOR_ISVISIBLE[]   = "IsVisible";
115 static const char ITEM_DESCRIPTOR_RESOURCEURL[] = "ResourceURL";
116 static const char ITEM_DESCRIPTOR_UINAME[]      = "UIName";
117 
118 static const char ITEM_MENUBAR_URL[] = "private:resource/menubar/menubar";
119 static const char ITEM_TOOLBAR_URL[] = "private:resource/toolbar/";
120 
121 static const char CUSTOM_TOOLBAR_STR[] = "custom_toolbar_";
122 static const char CUSTOM_MENU_STR[] = "vnd.openoffice.org:CustomMenu";
123 
124 static const char __FAR_DATA pSeparatorStr[] =
125     "----------------------------------";
126 static const char __FAR_DATA pMenuSeparatorStr[]    = " | ";
127 
128 #ifdef _MSC_VER
129 #pragma warning (disable:4355)
130 #endif
131 
132 using rtl::OUString;
133 namespace css = com::sun::star;
134 namespace uno = com::sun::star::uno;
135 namespace frame = com::sun::star::frame;
136 namespace lang = com::sun::star::lang;
137 namespace container = com::sun::star::container;
138 namespace beans = com::sun::star::beans;
139 namespace graphic = com::sun::star::graphic;
140 
141 #if OSL_DEBUG_LEVEL > 1
142 
143 void printPropertySet(
144     const OUString& prefix,
145     const uno::Reference< beans::XPropertySet >& xPropSet )
146 {
147     uno::Reference< beans::XPropertySetInfo > xPropSetInfo =
148         xPropSet->getPropertySetInfo();
149 
150     uno::Sequence< beans::Property > aPropDetails =
151         xPropSetInfo->getProperties();
152 
153     OSL_TRACE("printPropertySet: %d properties", aPropDetails.getLength());
154 
155     for ( sal_Int32 i = 0; i < aPropDetails.getLength(); i++ )
156     {
157         OUString tmp;
158         sal_Int32 ival;
159 
160         uno::Any a = xPropSet->getPropertyValue( aPropDetails[i].Name );
161 
162         if ( ( a >>= tmp ) /* && tmp.getLength() != 0 */ )
163         {
164             OSL_TRACE("%s: Got property: %s = %s",
165                 PRTSTR(prefix), PRTSTR(aPropDetails[i].Name), PRTSTR(tmp));
166         }
167         else if ( ( a >>= ival ) )
168         {
169             OSL_TRACE("%s: Got property: %s = %d",
170                 PRTSTR(prefix), PRTSTR(aPropDetails[i].Name), PRTSTR(tmp));
171         }
172         else
173         {
174             OSL_TRACE("%s: Got property: %s of type %s",
175                 PRTSTR(prefix), PRTSTR(aPropDetails[i].Name), PRTSTR(a.getValueTypeName()));
176         }
177     }
178 }
179 
180 void printProperties(
181     const OUString& prefix,
182     const uno::Sequence< beans::PropertyValue >& aProp )
183 {
184     for ( sal_Int32 i = 0; i < aProp.getLength(); i++ )
185     {
186         OUString tmp;
187 
188         aProp[i].Value >>= tmp;
189 
190         OSL_TRACE("%s: Got property: %s = %s",
191             PRTSTR(prefix), PRTSTR(aProp[i].Name), PRTSTR(tmp));
192     }
193 }
194 
195 void printEntries(SvxEntries* entries)
196 {
197     SvxEntries::const_iterator iter = entries->begin();
198 
199     for ( ; iter != entries->end(); iter++ )
200     {
201         SvxConfigEntry* entry = *iter;
202 
203         OSL_TRACE("printEntries: %s", PRTSTR(entry->GetName()));
204     }
205 }
206 
207 #endif
208 
209 OUString
210 stripHotKey( const OUString& str )
211 {
212     sal_Int32 index = str.indexOf( '~' );
213     if ( index == -1 )
214     {
215         return str;
216     }
217     else
218     {
219         return str.replaceAt( index, 1, OUString() );
220     }
221 }
222 
223 OUString replaceSaveInName(
224     const OUString& rMessage,
225     const OUString& rSaveInName )
226 {
227     OUString name;
228     OUString placeholder = OUString::createFromAscii( "%SAVE IN SELECTION%" );
229 
230     sal_Int32 pos = rMessage.indexOf( placeholder );
231 
232     if ( pos != -1 )
233     {
234         name = rMessage.replaceAt(
235             pos, placeholder.getLength(), rSaveInName );
236     }
237     else
238     {
239         // don't change the message
240     }
241 
242     return name;
243 }
244 
245 OUString
246 replaceSixteen( const OUString& str, sal_Int32 nReplacement )
247 {
248     OUString result( str );
249     OUString sixteen = OUString::valueOf( (sal_Int32)16 );
250     OUString expected = OUString::valueOf( nReplacement );
251 
252     sal_Int32 len = sixteen.getLength();
253     sal_Int32 index = result.indexOf( sixteen );
254 
255     while ( index != -1 )
256     {
257         result = result.replaceAt( index, len, expected );
258         index = result.indexOf( sixteen, index );
259     }
260 
261     return result;
262 }
263 
264 OUString
265 generateCustomName(
266     const OUString& prefix,
267     SvxEntries* entries,
268     sal_Int32 suffix = 1 )
269 {
270     // find and replace the %n placeholder in the prefix string
271     OUString name;
272     OUString placeholder = OUString::createFromAscii( "%n" );
273 
274     sal_Int32 pos = prefix.indexOf(
275         OUString::createFromAscii( "%n" ) );
276 
277     if ( pos != -1 )
278     {
279         name = prefix.replaceAt(
280             pos, placeholder.getLength(), OUString::valueOf( suffix ) );
281     }
282     else
283     {
284         // no placeholder found so just append the suffix
285         name = prefix + OUString::valueOf( suffix );
286     }
287 
288     // now check is there is an already existing entry with this name
289     SvxEntries::const_iterator iter = entries->begin();
290 
291     SvxConfigEntry* pEntry;
292     while ( iter != entries->end() )
293     {
294         pEntry = *iter;
295 
296         if ( name.equals( pEntry->GetName() ) )
297         {
298             break;
299         }
300         iter++;
301     }
302 
303     if ( iter != entries->end() )
304     {
305         // name already exists so try the next number up
306         return generateCustomName( prefix, entries, ++suffix );
307     }
308 
309     return name;
310 }
311 
312 sal_uInt32 generateRandomValue()
313 {
314     srand( unsigned( time( NULL ) ));
315     return sal_uInt32( rand() );
316 }
317 
318 OUString
319 generateCustomURL(
320     SvxEntries* entries )
321 {
322     OUString url = OUString::createFromAscii( ITEM_TOOLBAR_URL );
323     url += OUString::createFromAscii( CUSTOM_TOOLBAR_STR );
324 
325     // use a random number to minimize possible clash with existing custom toolbars
326     url += OUString::valueOf( sal_Int64( generateRandomValue() ), 16 );
327 
328     // now check is there is an already existing entry with this url
329     SvxEntries::const_iterator iter = entries->begin();
330 
331     SvxConfigEntry* pEntry;
332     while ( iter != entries->end() )
333     {
334         pEntry = *iter;
335 
336         if ( url.equals( pEntry->GetCommand() ) )
337         {
338             break;
339         }
340         iter++;
341     }
342 
343     if ( iter != entries->end() )
344     {
345         // url already exists so try the next number up
346         return generateCustomURL( entries );
347     }
348 
349     return url;
350 }
351 
352 OUString
353 generateCustomMenuURL(
354     SvxEntries* entries,
355     sal_Int32 suffix = 1 )
356 {
357     OUString url = OUString::createFromAscii( CUSTOM_MENU_STR );
358     url += OUString::valueOf( suffix );
359 
360     // now check is there is an already existing entry with this url
361     SvxEntries::const_iterator iter = entries->begin();
362 
363     SvxConfigEntry* pEntry;
364     while ( iter != entries->end() )
365     {
366         pEntry = *iter;
367 
368         if ( url.equals( pEntry->GetCommand() ) )
369         {
370             break;
371         }
372         iter++;
373     }
374 
375     if ( iter != entries->end() )
376     {
377         // url already exists so try the next number up
378         return generateCustomMenuURL( entries, ++suffix );
379     }
380 
381     return url;
382 }
383 
384 static sal_Int16 theImageType =
385     css::ui::ImageType::COLOR_NORMAL |
386     css::ui::ImageType::SIZE_DEFAULT;
387 
388 void InitImageType()
389 {
390     theImageType =
391         css::ui::ImageType::COLOR_NORMAL |
392         css::ui::ImageType::SIZE_DEFAULT;
393 
394     if ( SvtMiscOptions().AreCurrentSymbolsLarge() )
395     {
396         theImageType |= css::ui::ImageType::SIZE_LARGE;
397     }
398 
399     Window* topwin = Application::GetActiveTopWindow();
400     if ( topwin != NULL &&
401          topwin->GetSettings().GetStyleSettings().GetHighContrastMode() )
402     {
403         theImageType |= css::ui::ImageType::COLOR_HIGHCONTRAST;
404     }
405 }
406 
407 sal_Int16 GetImageType()
408 {
409     return theImageType;
410 }
411 
412 void RemoveEntry( SvxEntries* pEntries, SvxConfigEntry* pChildEntry )
413 {
414     SvxEntries::iterator iter = pEntries->begin();
415 
416     while ( iter != pEntries->end() )
417     {
418         if ( pChildEntry == *iter )
419         {
420             pEntries->erase( iter );
421             break;
422         }
423         iter++;
424     }
425 }
426 
427 bool
428 SvxConfigPage::CanConfig( const OUString& aModuleId )
429 {
430     OSL_TRACE("SupportsDocumentConfig: %s", PRTSTR(aModuleId));
431 
432     if  (  aModuleId.equalsAscii( "com.sun.star.script.BasicIDE" )
433         || aModuleId.equalsAscii( "com.sun.star.frame.Bibliography" )
434         )
435     {
436         return sal_False;
437     }
438     return sal_True;
439 }
440 
441 OUString GetModuleName( const OUString& aModuleId )
442 {
443     if ( aModuleId.equalsAscii( "com.sun.star.text.TextDocument" ) ||
444          aModuleId.equalsAscii( "com.sun.star.text.GlobalDocument" ) )
445         return OUString::createFromAscii("Writer");
446     else if ( aModuleId.equalsAscii( "com.sun.star.text.WebDocument" ) )
447         return OUString::createFromAscii("Writer/Web");
448     else if ( aModuleId.equalsAscii( "com.sun.star.drawing.DrawingDocument" ) )
449         return OUString::createFromAscii("Draw");
450     else if ( aModuleId.equalsAscii( "com.sun.star.presentation.PresentationDocument" ) )
451         return OUString::createFromAscii("Impress");
452     else if ( aModuleId.equalsAscii( "com.sun.star.sheet.SpreadsheetDocument" ) )
453         return OUString::createFromAscii("Calc");
454     else if ( aModuleId.equalsAscii( "com.sun.star.script.BasicIDE" ) )
455         return OUString::createFromAscii("Basic");
456     else if ( aModuleId.equalsAscii( "com.sun.star.formula.FormulaProperties" ) )
457         return OUString::createFromAscii("Math");
458     else if ( aModuleId.equalsAscii( "com.sun.star.sdb.RelationDesign" ) )
459         return OUString::createFromAscii("Relation Design");
460     else if ( aModuleId.equalsAscii( "com.sun.star.sdb.QueryDesign" ) )
461         return OUString::createFromAscii("Query Design");
462     else if ( aModuleId.equalsAscii( "com.sun.star.sdb.TableDesign" ) )
463         return OUString::createFromAscii("Table Design");
464     else if ( aModuleId.equalsAscii( "com.sun.star.sdb.DataSourceBrowser" ) )
465         return OUString::createFromAscii("Data Source Browser" );
466     else if ( aModuleId.equalsAscii( "com.sun.star.sdb.DatabaseDocument" ) )
467         return OUString::createFromAscii("Database" );
468 
469     return ::rtl::OUString();
470 }
471 
472 OUString GetUIModuleName( const OUString& aModuleId, const uno::Reference< css::frame::XModuleManager >& rModuleManager )
473 {
474     OUString aModuleUIName;
475 
476     if ( rModuleManager.is() )
477     {
478         uno::Reference< css::container::XNameAccess > xNameAccess( rModuleManager, uno::UNO_QUERY );
479         if ( xNameAccess.is() )
480         {
481             try
482             {
483                 uno::Any a = xNameAccess->getByName( aModuleId );
484                 uno::Sequence< beans::PropertyValue > aSeq;
485 
486                 if ( a >>= aSeq )
487                 {
488                     OUString aUIName;
489                     for ( sal_Int32 i = 0; i < aSeq.getLength(); i++ )
490                     {
491                         if ( aSeq[i].Name.equalsAscii( "ooSetupFactoryUIName" ))
492                         {
493                             aSeq[i].Value >>= aModuleUIName;
494                             break;
495                         }
496                     }
497                 }
498             }
499             catch ( uno::RuntimeException& e )
500             {
501                 throw e;
502             }
503             catch ( uno::Exception& )
504             {
505             }
506         }
507     }
508 
509     if ( aModuleUIName.getLength() == 0 )
510         aModuleUIName = GetModuleName( aModuleId );
511 
512     return aModuleUIName;
513 }
514 
515 bool GetMenuItemData(
516     const uno::Reference< container::XIndexAccess >& rItemContainer,
517     sal_Int32 nIndex,
518     OUString& rCommandURL,
519     OUString& rLabel,
520     sal_uInt16& rType,
521     uno::Reference< container::XIndexAccess >& rSubMenu )
522 {
523     try
524     {
525         uno::Sequence< beans::PropertyValue > aProp;
526         if ( rItemContainer->getByIndex( nIndex ) >>= aProp )
527         {
528             for ( sal_Int32 i = 0; i < aProp.getLength(); i++ )
529             {
530                 if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_COMMANDURL ))
531                 {
532                     aProp[i].Value >>= rCommandURL;
533                 }
534                 else if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_CONTAINER ))
535                 {
536                     aProp[i].Value >>= rSubMenu;
537                 }
538                 else if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_LABEL ))
539                 {
540                     aProp[i].Value >>= rLabel;
541                 }
542                 else if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_TYPE ))
543                 {
544                     aProp[i].Value >>= rType;
545                 }
546             }
547 
548             return sal_True;
549         }
550     }
551     catch ( ::com::sun::star::lang::IndexOutOfBoundsException& )
552     {
553     }
554 
555     return sal_False;
556 }
557 
558 bool GetToolbarItemData(
559     const uno::Reference< container::XIndexAccess >& rItemContainer,
560     sal_Int32 nIndex,
561     OUString& rCommandURL,
562     OUString& rLabel,
563     sal_uInt16& rType,
564     sal_Bool& rIsVisible,
565     sal_Int32& rStyle,
566     uno::Reference< container::XIndexAccess >& rSubMenu )
567 {
568     try
569     {
570         uno::Sequence< beans::PropertyValue > aProp;
571         if ( rItemContainer->getByIndex( nIndex ) >>= aProp )
572         {
573             for ( sal_Int32 i = 0; i < aProp.getLength(); i++ )
574             {
575                 if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_COMMANDURL ))
576                 {
577                     aProp[i].Value >>= rCommandURL;
578                 }
579                 if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_STYLE ))
580                 {
581                     aProp[i].Value >>= rStyle;
582                 }
583                 else if (aProp[i].Name.equalsAscii(ITEM_DESCRIPTOR_CONTAINER))
584                 {
585                     aProp[i].Value >>= rSubMenu;
586                 }
587                 else if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_LABEL ))
588                 {
589                     aProp[i].Value >>= rLabel;
590                 }
591                 else if ( aProp[i].Name.equalsAscii( ITEM_DESCRIPTOR_TYPE ))
592                 {
593                     aProp[i].Value >>= rType;
594                 }
595                 else if (aProp[i].Name.equalsAscii(ITEM_DESCRIPTOR_ISVISIBLE))
596                 {
597                     aProp[i].Value >>= rIsVisible;
598                 }
599             }
600 
601             return sal_True;
602         }
603     }
604     catch ( ::com::sun::star::lang::IndexOutOfBoundsException& )
605     {
606     }
607 
608     return sal_False;
609 }
610 
611 uno::Sequence< beans::PropertyValue >
612 ConvertSvxConfigEntry(
613     const uno::Reference< container::XNameAccess >& xCommandToLabelMap,
614     const SvxConfigEntry* pEntry )
615 {
616     static const OUString aDescriptorCommandURL (
617         RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_COMMANDURL ) );
618 
619     static const OUString aDescriptorType(
620             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_TYPE ) );
621 
622     static const OUString aDescriptorLabel(
623             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_LABEL ) );
624 
625     static const OUString aDescriptorContainer(
626             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_CONTAINER ) );
627 
628     uno::Sequence< beans::PropertyValue > aPropSeq( 3 );
629 
630     aPropSeq[0].Name = aDescriptorCommandURL;
631     aPropSeq[0].Value <<= rtl::OUString( pEntry->GetCommand() );
632 
633     aPropSeq[1].Name = aDescriptorType;
634     aPropSeq[1].Value <<= css::ui::ItemType::DEFAULT;
635 
636     // If the name has not been changed and the name is the same as
637     // in the default command to label map then the label can be stored
638     // as an empty string.
639     // It will be initialised again later using the command to label map.
640     aPropSeq[2].Name = aDescriptorLabel;
641     if ( pEntry->HasChangedName() == sal_False && pEntry->GetCommand().getLength() )
642     {
643         sal_Bool isDefaultName = sal_False;
644         try
645         {
646             uno::Any a( xCommandToLabelMap->getByName( pEntry->GetCommand() ) );
647             uno::Sequence< beans::PropertyValue > tmpPropSeq;
648             if ( a >>= tmpPropSeq )
649             {
650                 for ( sal_Int32 i = 0; i < tmpPropSeq.getLength(); i++ )
651                 {
652                     if ( tmpPropSeq[i].Name.equals( aDescriptorLabel ) )
653                     {
654                         OUString tmpLabel;
655                         tmpPropSeq[i].Value >>= tmpLabel;
656 
657                         if ( tmpLabel.equals( pEntry->GetName() ) )
658                         {
659                             isDefaultName = sal_True;
660                         }
661 
662                         break;
663                     }
664                 }
665             }
666         }
667         catch ( container::NoSuchElementException& )
668         {
669             // isDefaultName is left as FALSE
670         }
671 
672         if ( isDefaultName )
673         {
674             aPropSeq[2].Value <<= rtl::OUString();
675         }
676         else
677         {
678             aPropSeq[2].Value <<= rtl::OUString( pEntry->GetName() );
679         }
680     }
681     else
682     {
683         aPropSeq[2].Value <<= rtl::OUString( pEntry->GetName() );
684     }
685 
686     return aPropSeq;
687 }
688 
689 uno::Sequence< beans::PropertyValue >
690 ConvertToolbarEntry(
691     const uno::Reference< container::XNameAccess >& xCommandToLabelMap,
692     const SvxConfigEntry* pEntry )
693 {
694     static const OUString aDescriptorCommandURL (
695         RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_COMMANDURL ) );
696 
697     static const OUString aDescriptorType(
698             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_TYPE ) );
699 
700     static const OUString aDescriptorLabel(
701             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_LABEL ) );
702 
703     static const OUString aDescriptorContainer(
704             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_CONTAINER ) );
705 
706     static const OUString aIsVisible(
707             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_ISVISIBLE ) );
708 
709     uno::Sequence< beans::PropertyValue > aPropSeq( 4 );
710 
711     aPropSeq[0].Name = aDescriptorCommandURL;
712     aPropSeq[0].Value <<= rtl::OUString( pEntry->GetCommand() );
713 
714     aPropSeq[1].Name = aDescriptorType;
715     aPropSeq[1].Value <<= css::ui::ItemType::DEFAULT;
716 
717     // If the name has not been changed and the name is the same as
718     // in the default command to label map then the label can be stored
719     // as an empty string.
720     // It will be initialised again later using the command to label map.
721     aPropSeq[2].Name = aDescriptorLabel;
722     if ( pEntry->HasChangedName() == sal_False && pEntry->GetCommand().getLength() )
723     {
724         sal_Bool isDefaultName = sal_False;
725         try
726         {
727             uno::Any a( xCommandToLabelMap->getByName( pEntry->GetCommand() ) );
728             uno::Sequence< beans::PropertyValue > tmpPropSeq;
729             if ( a >>= tmpPropSeq )
730             {
731                 for ( sal_Int32 i = 0; i < tmpPropSeq.getLength(); i++ )
732                 {
733                     if ( tmpPropSeq[i].Name.equals( aDescriptorLabel ) )
734                     {
735                         OUString tmpLabel;
736                         tmpPropSeq[i].Value >>= tmpLabel;
737 
738                         if ( tmpLabel.equals( pEntry->GetName() ) )
739                         {
740                             isDefaultName = sal_True;
741                         }
742 
743                         break;
744                     }
745                 }
746             }
747         }
748         catch ( container::NoSuchElementException& )
749         {
750             // isDefaultName is left as FALSE
751         }
752 
753         if ( isDefaultName )
754         {
755             aPropSeq[2].Value <<= rtl::OUString();
756         }
757         else
758         {
759             aPropSeq[2].Value <<= rtl::OUString( pEntry->GetName() );
760         }
761     }
762     else
763     {
764         aPropSeq[2].Value <<= rtl::OUString( pEntry->GetName() );
765     }
766 
767     aPropSeq[3].Name = aIsVisible;
768     aPropSeq[3].Value <<= pEntry->IsVisible();
769 
770     return aPropSeq;
771 }
772 
773 SfxTabPage *CreateSvxMenuConfigPage( Window *pParent, const SfxItemSet& rSet )
774 {
775     return new SvxMenuConfigPage( pParent, rSet );
776 }
777 
778 SfxTabPage *CreateKeyboardConfigPage( Window *pParent, const SfxItemSet& rSet )
779 {
780     return new SfxAcceleratorConfigPage( pParent, rSet );
781 }
782 
783 SfxTabPage *CreateSvxToolbarConfigPage( Window *pParent, const SfxItemSet& rSet )
784 {
785     return new SvxToolbarConfigPage( pParent, rSet );
786 }
787 
788 SfxTabPage *CreateSvxEventConfigPage( Window *pParent, const SfxItemSet& rSet )
789 {
790     return new SvxEventConfigPage( pParent, rSet, SvxEventConfigPage::EarlyInit() );
791 }
792 
793 sal_Bool impl_showKeyConfigTabPage( const css::uno::Reference< css::frame::XFrame >& xFrame )
794 {
795     static ::rtl::OUString SERVICENAME_MODULEMANAGER = ::rtl::OUString::createFromAscii("com.sun.star.frame.ModuleManager");
796     static ::rtl::OUString SERVICENAME_DESKTOP       = ::rtl::OUString::createFromAscii("com.sun.star.frame.Desktop"             );
797     static ::rtl::OUString MODULEID_STARTMODULE      = ::rtl::OUString::createFromAscii("com.sun.star.frame.StartModule"         );
798 
799     try
800     {
801         css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR   = ::comphelper::getProcessServiceFactory();
802         css::uno::Reference< css::frame::XFramesSupplier >     xDesktop(xSMGR->createInstance(SERVICENAME_DESKTOP), css::uno::UNO_QUERY_THROW);
803         css::uno::Reference< css::frame::XModuleManager >     xMM     (xSMGR->createInstance(SERVICENAME_MODULEMANAGER), css::uno::UNO_QUERY_THROW);
804 
805         if (xMM.is() && xFrame.is())
806         {
807             ::rtl::OUString sModuleId = xMM->identify(xFrame);
808             if (
809                 ( sModuleId.getLength()                 ) &&
810                 (!sModuleId.equals(MODULEID_STARTMODULE))
811                )
812                return sal_True;
813         }
814     }
815     catch(const css::uno::Exception&)
816         {}
817 
818     return sal_False;
819 }
820 
821 /******************************************************************************
822  *
823  * SvxConfigDialog is the configuration dialog which is brought up from the
824  * Tools menu. It includes tabs for customizing menus, toolbars, events and
825  * key bindings.
826  *
827  *****************************************************************************/
828 SvxConfigDialog::SvxConfigDialog(
829     Window * pParent, const SfxItemSet* pSet_ )
830     :
831         SfxTabDialog( pParent,
832             CUI_RES( RID_SVXDLG_CUSTOMIZE ), pSet_ )
833 {
834     FreeResource();
835 
836     InitImageType();
837 
838     AddTabPage( RID_SVXPAGE_MENUS, CreateSvxMenuConfigPage, NULL );
839     AddTabPage( RID_SVXPAGE_KEYBOARD, CreateKeyboardConfigPage, NULL );
840     AddTabPage( RID_SVXPAGE_TOOLBARS, CreateSvxToolbarConfigPage, NULL );
841     AddTabPage( RID_SVXPAGE_EVENTS, CreateSvxEventConfigPage, NULL );
842 
843     const SfxPoolItem* pItem =
844         pSet_->GetItem( pSet_->GetPool()->GetWhich( SID_CONFIG ) );
845 
846     if ( pItem )
847     {
848         OUString text = ((const SfxStringItem*)pItem)->GetValue();
849 
850         if (text.indexOf(OUString::createFromAscii(ITEM_TOOLBAR_URL)) == 0)
851         {
852             SetCurPageId( RID_SVXPAGE_TOOLBARS );
853         }
854     }
855 }
856 
857 void SvxConfigDialog::SetFrame(const ::com::sun::star::uno::Reference< ::com::sun::star::frame::XFrame >& xFrame)
858 {
859     m_xFrame = xFrame;
860 
861     if (!impl_showKeyConfigTabPage( xFrame ))
862         RemoveTabPage( RID_SVXPAGE_KEYBOARD );
863 }
864 
865 SvxConfigDialog::~SvxConfigDialog()
866 {
867 }
868 
869 short SvxConfigDialog::Ok()
870 {
871     return SfxTabDialog::Ok();
872 }
873 
874 void SvxConfigDialog::PageCreated( sal_uInt16 nId, SfxTabPage& rPage )
875 {
876     (void)rPage;
877 
878     switch ( nId )
879     {
880         case RID_SVXPAGE_MENUS:
881         case RID_SVXPAGE_TOOLBARS:
882         case RID_SVXPAGE_KEYBOARD:
883             {
884                 rPage.SetFrame(m_xFrame);
885             }
886             break;
887         case RID_SVXPAGE_EVENTS:
888             {
889                 dynamic_cast< SvxEventConfigPage& >( rPage ).LateInit( m_xFrame );
890             };
891             break;
892         default:
893             break;
894     }
895 }
896 
897 /******************************************************************************
898  *
899  * The SaveInData class is used to hold data for entries in the Save In
900  * ListBox controls in the menu and toolbar tabs
901  *
902  ******************************************************************************/
903 
904 // Initialize static variable which holds default XImageManager
905 uno::Reference< css::ui::XImageManager>* SaveInData::xDefaultImgMgr = NULL;
906 
907 SaveInData::SaveInData(
908     const uno::Reference< css::ui::XUIConfigurationManager >& xCfgMgr,
909     const uno::Reference< css::ui::XUIConfigurationManager >& xParentCfgMgr,
910     const OUString& aModuleId,
911     bool isDocConfig )
912         :
913             bModified( sal_False ),
914             bDocConfig( isDocConfig ),
915             bReadOnly( sal_False ),
916             m_xCfgMgr( xCfgMgr ),
917             m_xParentCfgMgr( xParentCfgMgr )
918 {
919     uno::Reference< beans::XPropertySet > xProps(
920         ::comphelper::getProcessServiceFactory(), uno::UNO_QUERY );
921 
922     xProps->getPropertyValue(
923         OUString::createFromAscii( "DefaultContext" ))
924             >>= m_xComponentContext;
925 
926     m_aSeparatorSeq.realloc( 1 );
927     m_aSeparatorSeq[0].Name  = OUString(
928         RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_TYPE ) );
929     m_aSeparatorSeq[0].Value <<= css::ui::ItemType::SEPARATOR_LINE;
930 
931     if ( bDocConfig )
932     {
933         uno::Reference< css::ui::XUIConfigurationPersistence >
934             xDocPersistence( GetConfigManager(), uno::UNO_QUERY );
935 
936         bReadOnly = xDocPersistence->isReadOnly();
937     }
938 
939     m_xServiceManager = uno::Reference< lang::XMultiServiceFactory >(
940         ::comphelper::getProcessServiceFactory(), uno::UNO_QUERY_THROW );
941 
942     uno::Reference< container::XNameAccess > xNameAccess(
943         m_xServiceManager->createInstance(
944             OUString( RTL_CONSTASCII_USTRINGPARAM(
945                 "com.sun.star.frame.UICommandDescription" ) ) ),
946         uno::UNO_QUERY );
947 
948     if ( xNameAccess.is() )
949         xNameAccess->getByName( aModuleId ) >>= m_xCommandToLabelMap;
950 
951     if ( !m_xImgMgr.is() )
952     {
953         m_xImgMgr = uno::Reference< css::ui::XImageManager >(
954             GetConfigManager()->getImageManager(), uno::UNO_QUERY );
955     }
956 
957     if ( !IsDocConfig() )
958     {
959         // If this is not a document configuration then it is the settings
960         // for the module (writer, calc, impress etc.) Use this as the default
961         // XImageManager instance
962         xDefaultImgMgr = &m_xImgMgr;
963     }
964     else
965     {
966         // If this is a document configuration then use the module image manager
967         // as default.
968         if ( m_xParentCfgMgr.is() )
969         {
970             m_xParentImgMgr = uno::Reference< css::ui::XImageManager >(
971                 m_xParentCfgMgr->getImageManager(), uno::UNO_QUERY );
972             xDefaultImgMgr = &m_xParentImgMgr;
973         }
974     }
975 }
976 
977 uno::Reference< graphic::XGraphic > GetGraphic(
978     const uno::Reference< css::ui::XImageManager >& xImageManager,
979     const OUString& rCommandURL )
980 {
981     uno::Reference< graphic::XGraphic > result;
982 
983     if ( xImageManager.is() )
984     {
985         // TODO handle large and high contrast graphics
986         uno::Sequence< uno::Reference< graphic::XGraphic > > aGraphicSeq;
987 
988         uno::Sequence< OUString > aImageCmdSeq( 1 );
989         aImageCmdSeq[0] = rCommandURL;
990 
991         try
992         {
993             aGraphicSeq =
994                 xImageManager->getImages( GetImageType(), aImageCmdSeq );
995 
996             if ( aGraphicSeq.getLength() > 0 )
997             {
998                 result =  aGraphicSeq[0];
999             }
1000         }
1001         catch ( uno::Exception& )
1002         {
1003             // will return empty XGraphic
1004         }
1005     }
1006 
1007     return result;
1008 }
1009 
1010 Image SaveInData::GetImage( const OUString& rCommandURL )
1011 {
1012     Image aImage;
1013 
1014     uno::Reference< graphic::XGraphic > xGraphic =
1015         GetGraphic( m_xImgMgr, rCommandURL );
1016 
1017     if ( xGraphic.is() )
1018     {
1019         aImage = Image( xGraphic );
1020     }
1021     else if ( xDefaultImgMgr != NULL && (*xDefaultImgMgr).is() )
1022     {
1023         xGraphic = GetGraphic( (*xDefaultImgMgr), rCommandURL );
1024 
1025         if ( xGraphic.is() )
1026         {
1027             aImage = Image( xGraphic );
1028         }
1029     }
1030 
1031     return aImage;
1032 }
1033 
1034 bool SaveInData::PersistChanges(
1035     const uno::Reference< uno::XInterface >& xManager )
1036 {
1037     bool result = sal_True;
1038 
1039     try
1040     {
1041         if ( xManager.is() && !IsReadOnly() )
1042         {
1043             uno::Reference< css::ui::XUIConfigurationPersistence >
1044                 xConfigPersistence( xManager, uno::UNO_QUERY );
1045 
1046             if ( xConfigPersistence->isModified() )
1047             {
1048                 xConfigPersistence->store();
1049             }
1050         }
1051     }
1052     catch ( com::sun::star::io::IOException& )
1053     {
1054         result = sal_False;
1055     }
1056 
1057     return result;
1058 }
1059 
1060 /******************************************************************************
1061  *
1062  * The MenuSaveInData class extends SaveInData and provides menu specific
1063  * load and store functionality.
1064  *
1065  ******************************************************************************/
1066 
1067 // Initialize static variable which holds default Menu data
1068 MenuSaveInData* MenuSaveInData::pDefaultData = NULL;
1069 
1070 MenuSaveInData::MenuSaveInData(
1071     const uno::Reference< css::ui::XUIConfigurationManager >& cfgmgr,
1072     const uno::Reference< css::ui::XUIConfigurationManager >& xParentCfgMgr,
1073     const OUString& aModuleId,
1074     bool isDocConfig )
1075     :
1076         SaveInData( cfgmgr, xParentCfgMgr, aModuleId, isDocConfig ),
1077         m_aMenuResourceURL(
1078             RTL_CONSTASCII_USTRINGPARAM( ITEM_MENUBAR_URL ) ),
1079         m_aDescriptorContainer(
1080             RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_CONTAINER ) ),
1081         pRootEntry( 0 )
1082 {
1083     try
1084     {
1085         OUString url( RTL_CONSTASCII_USTRINGPARAM( ITEM_MENUBAR_URL ) );
1086         m_xMenuSettings = GetConfigManager()->getSettings( url, sal_False );
1087     }
1088     catch ( container::NoSuchElementException& )
1089     {
1090         // will use menu settings for the module
1091     }
1092 
1093     // If this is not a document configuration then it is the settings
1094     // for the module (writer, calc, impress etc.). These settings should
1095     // be set as the default to be used for SaveIn locations that do not
1096     // have custom settings
1097     if ( !IsDocConfig() )
1098     {
1099         SetDefaultData( this );
1100     }
1101 }
1102 
1103 MenuSaveInData::~MenuSaveInData()
1104 {
1105     if ( pRootEntry != NULL )
1106     {
1107         delete pRootEntry;
1108     }
1109 }
1110 
1111 SvxEntries*
1112 MenuSaveInData::GetEntries()
1113 {
1114     if ( pRootEntry == NULL )
1115     {
1116         pRootEntry = new SvxConfigEntry(
1117             String::CreateFromAscii("MainMenus"), String(), sal_True );
1118 
1119         if ( m_xMenuSettings.is() )
1120         {
1121             LoadSubMenus( m_xMenuSettings, String(), pRootEntry );
1122         }
1123         else if ( GetDefaultData() != NULL )
1124         {
1125             // If the doc has no config settings use module config settings
1126             LoadSubMenus( GetDefaultData()->m_xMenuSettings, String(), pRootEntry );
1127         }
1128     }
1129 
1130     return pRootEntry->GetEntries();
1131 }
1132 
1133 void
1134 MenuSaveInData::SetEntries( SvxEntries* pNewEntries )
1135 {
1136     // delete old menu hierarchy first
1137     if ( pRootEntry != NULL )
1138     {
1139         delete pRootEntry->GetEntries();
1140     }
1141 
1142     // now set new menu hierarchy
1143     pRootEntry->SetEntries( pNewEntries );
1144 }
1145 
1146 bool MenuSaveInData::LoadSubMenus(
1147     const uno::Reference< container::XIndexAccess >& xMenuSettings,
1148     const OUString& rBaseTitle,
1149     SvxConfigEntry* pParentData )
1150 {
1151     SvxEntries* pEntries = pParentData->GetEntries();
1152 
1153     // Don't access non existing menu configuration!
1154     if ( !xMenuSettings.is() )
1155         return true;
1156 
1157     for ( sal_Int32 nIndex = 0; nIndex < xMenuSettings->getCount(); nIndex++ )
1158     {
1159         uno::Reference< container::XIndexAccess >   xSubMenu;
1160         OUString                aCommandURL;
1161         OUString                aLabel;
1162         bool                    bIsUserDefined = sal_True;
1163 
1164         sal_uInt16 nType( css::ui::ItemType::DEFAULT );
1165 
1166         bool bItem = GetMenuItemData( xMenuSettings, nIndex,
1167             aCommandURL, aLabel, nType, xSubMenu );
1168 
1169         if ( bItem )
1170         {
1171             if ( nType == css::ui::ItemType::DEFAULT )
1172             {
1173                 uno::Any a;
1174                 try
1175                 {
1176                     a = m_xCommandToLabelMap->getByName( aCommandURL );
1177                     bIsUserDefined = sal_False;
1178                 }
1179                 catch ( container::NoSuchElementException& )
1180                 {
1181                     bIsUserDefined = sal_True;
1182                 }
1183 
1184                 // If custom label not set retrieve it from the command
1185                 // to info service
1186                 if ( aLabel.equals( OUString() ) )
1187                 {
1188                     uno::Sequence< beans::PropertyValue > aPropSeq;
1189                     if ( a >>= aPropSeq )
1190                     {
1191                         for ( sal_Int32 i = 0; i < aPropSeq.getLength(); i++ )
1192                         {
1193                             if ( aPropSeq[i].Name.equalsAscii( ITEM_DESCRIPTOR_LABEL ) )
1194                             {
1195                                 aPropSeq[i].Value >>= aLabel;
1196                                 break;
1197                             }
1198                         }
1199                     }
1200                 }
1201 
1202                 if ( xSubMenu.is() )
1203                 {
1204                     // popup menu
1205                     SvxConfigEntry* pEntry = new SvxConfigEntry(
1206                         aLabel, aCommandURL, sal_True );
1207 
1208                     pEntry->SetUserDefined( bIsUserDefined );
1209 
1210                     pEntries->push_back( pEntry );
1211 
1212                     OUString subMenuTitle( rBaseTitle );
1213 
1214                     if ( subMenuTitle.getLength() != 0 )
1215                     {
1216                         subMenuTitle +=
1217                             OUString::createFromAscii(pMenuSeparatorStr);
1218                     }
1219                     else
1220                     {
1221                         pEntry->SetMain( sal_True );
1222                     }
1223 
1224                     subMenuTitle += stripHotKey( aLabel );
1225 
1226                     LoadSubMenus( xSubMenu, subMenuTitle, pEntry );
1227                 }
1228                 else
1229                 {
1230                     SvxConfigEntry* pEntry = new SvxConfigEntry(
1231                         aLabel, aCommandURL, sal_False );
1232                     pEntry->SetUserDefined( bIsUserDefined );
1233                     pEntries->push_back( pEntry );
1234                 }
1235             }
1236             else
1237             {
1238                 SvxConfigEntry* pEntry = new SvxConfigEntry;
1239                 pEntry->SetUserDefined( bIsUserDefined );
1240                 pEntries->push_back( pEntry );
1241             }
1242         }
1243     }
1244     return true;
1245 }
1246 
1247 bool MenuSaveInData::Apply()
1248 {
1249     bool result = sal_False;
1250 
1251     if ( IsModified() )
1252     {
1253         // Apply new menu bar structure to our settings container
1254         m_xMenuSettings = uno::Reference< container::XIndexAccess >(
1255             GetConfigManager()->createSettings(), uno::UNO_QUERY );
1256 
1257         uno::Reference< container::XIndexContainer > xIndexContainer (
1258             m_xMenuSettings, uno::UNO_QUERY );
1259 
1260         uno::Reference< lang::XSingleComponentFactory > xFactory (
1261             m_xMenuSettings, uno::UNO_QUERY );
1262 
1263         Apply( pRootEntry, xIndexContainer, xFactory, NULL );
1264 
1265         try
1266         {
1267             if ( GetConfigManager()->hasSettings( m_aMenuResourceURL ) )
1268             {
1269                 GetConfigManager()->replaceSettings(
1270                     m_aMenuResourceURL, m_xMenuSettings );
1271             }
1272             else
1273             {
1274                 GetConfigManager()->insertSettings(
1275                     m_aMenuResourceURL, m_xMenuSettings );
1276             }
1277         }
1278         catch ( container::NoSuchElementException& )
1279         {
1280             OSL_TRACE("caught container::NoSuchElementException saving settings");
1281         }
1282         catch ( com::sun::star::io::IOException& )
1283         {
1284             OSL_TRACE("caught IOException saving settings");
1285         }
1286         catch ( com::sun::star::uno::Exception& )
1287         {
1288             OSL_TRACE("caught some other exception saving settings");
1289         }
1290 
1291         SetModified( sal_False );
1292 
1293         result = PersistChanges( GetConfigManager() );
1294     }
1295 
1296     return result;
1297 }
1298 
1299 void MenuSaveInData::Apply(
1300     SvxConfigEntry* pRootEntry_,
1301     uno::Reference< container::XIndexContainer >& rMenuBar,
1302     uno::Reference< lang::XSingleComponentFactory >& rFactory,
1303     SvLBoxEntry *pParentEntry )
1304 {
1305     (void)pRootEntry_;
1306     (void)pParentEntry;
1307 
1308     SvxEntries::const_iterator iter = GetEntries()->begin();
1309     SvxEntries::const_iterator end = GetEntries()->end();
1310 
1311     for ( ; iter != end; iter++ )
1312     {
1313         SvxConfigEntry* pEntryData = *iter;
1314 
1315         uno::Sequence< beans::PropertyValue > aPropValueSeq =
1316             ConvertSvxConfigEntry( m_xCommandToLabelMap, pEntryData );
1317 
1318         uno::Reference< container::XIndexContainer > xSubMenuBar(
1319             rFactory->createInstanceWithContext( m_xComponentContext ),
1320             uno::UNO_QUERY );
1321 
1322         sal_Int32 nIndex = aPropValueSeq.getLength();
1323         aPropValueSeq.realloc( nIndex + 1 );
1324         aPropValueSeq[nIndex].Name = m_aDescriptorContainer;
1325         aPropValueSeq[nIndex].Value <<= xSubMenuBar;
1326         rMenuBar->insertByIndex(
1327             rMenuBar->getCount(), uno::makeAny( aPropValueSeq ));
1328         ApplyMenu( xSubMenuBar, rFactory, pEntryData );
1329     }
1330 }
1331 
1332 void MenuSaveInData::ApplyMenu(
1333     uno::Reference< container::XIndexContainer >& rMenuBar,
1334     uno::Reference< lang::XSingleComponentFactory >& rFactory,
1335     SvxConfigEntry* pMenuData )
1336 {
1337     SvxEntries::const_iterator iter = pMenuData->GetEntries()->begin();
1338     SvxEntries::const_iterator end = pMenuData->GetEntries()->end();
1339 
1340     for ( ; iter != end; iter++ )
1341     {
1342         SvxConfigEntry* pEntry = *iter;
1343 
1344         if ( pEntry->IsPopup() )
1345         {
1346             uno::Sequence< beans::PropertyValue > aPropValueSeq =
1347                 ConvertSvxConfigEntry( m_xCommandToLabelMap, pEntry );
1348 
1349             uno::Reference< container::XIndexContainer > xSubMenuBar(
1350                 rFactory->createInstanceWithContext( m_xComponentContext ),
1351                     uno::UNO_QUERY );
1352 
1353             sal_Int32 nIndex = aPropValueSeq.getLength();
1354             aPropValueSeq.realloc( nIndex + 1 );
1355             aPropValueSeq[nIndex].Name = m_aDescriptorContainer;
1356             aPropValueSeq[nIndex].Value <<= xSubMenuBar;
1357 
1358             rMenuBar->insertByIndex(
1359                 rMenuBar->getCount(), uno::makeAny( aPropValueSeq ));
1360 
1361             ApplyMenu( xSubMenuBar, rFactory, pEntry );
1362         }
1363         else if ( pEntry->IsSeparator() )
1364         {
1365             rMenuBar->insertByIndex(
1366                 rMenuBar->getCount(), uno::makeAny( m_aSeparatorSeq ));
1367         }
1368         else
1369         {
1370             uno::Sequence< beans::PropertyValue > aPropValueSeq =
1371                 ConvertSvxConfigEntry( m_xCommandToLabelMap, pEntry );
1372             rMenuBar->insertByIndex(
1373                 rMenuBar->getCount(), uno::makeAny( aPropValueSeq ));
1374         }
1375     }
1376 }
1377 
1378 void
1379 MenuSaveInData::Reset()
1380 {
1381     GetConfigManager()->reset();
1382 
1383     delete pRootEntry;
1384     pRootEntry = NULL;
1385 
1386     try
1387     {
1388         m_xMenuSettings = GetConfigManager()->getSettings(
1389             m_aMenuResourceURL, sal_False );
1390     }
1391     catch ( container::NoSuchElementException& )
1392     {
1393         // will use default settings
1394     }
1395 }
1396 
1397 class PopupPainter : public SvLBoxString
1398 {
1399 public:
1400     PopupPainter( SvLBoxEntry* pEntry, const String& rStr )
1401         : SvLBoxString( pEntry, 0, rStr )
1402     { }
1403 
1404     ~PopupPainter() { }
1405 
1406     void Paint( const Point& rPos, SvLBox& rOutDev,
1407         sal_uInt16 nViewDataEntryFlags, SvLBoxEntry* pEntry )
1408     {
1409         SvLBoxString::Paint( rPos, rOutDev, nViewDataEntryFlags, pEntry );
1410 
1411         Color aOldFillColor = rOutDev.GetFillColor();
1412 
1413         SvTreeListBox* pTreeBox = static_cast< SvTreeListBox* >( &rOutDev );
1414         long nX = pTreeBox->GetSizePixel().Width();
1415 
1416         ScrollBar* pVScroll = pTreeBox->GetVScroll();
1417         if ( pVScroll->IsVisible() )
1418         {
1419             nX -= pVScroll->GetSizePixel().Width();
1420         }
1421 
1422         SvViewDataItem* pItem = rOutDev.GetViewDataItem( pEntry, this );
1423         nX -= pItem->aSize.Height();
1424 
1425         long nSize = pItem->aSize.Height() / 2;
1426         long nHalfSize = nSize / 2;
1427         long nY = rPos.Y() + nHalfSize;
1428 
1429         if ( aOldFillColor == COL_WHITE )
1430         {
1431             rOutDev.SetFillColor( Color( COL_BLACK ) );
1432         }
1433         else
1434         {
1435             rOutDev.SetFillColor( Color( COL_WHITE ) );
1436         }
1437 
1438         long n = 0;
1439         while ( n <= nHalfSize )
1440         {
1441             rOutDev.DrawRect( Rectangle( nX+n, nY+n, nX+n, nY+nSize-n ) );
1442             n++;
1443         }
1444 
1445         rOutDev.SetFillColor( aOldFillColor );
1446     }
1447 };
1448 
1449 /******************************************************************************
1450  *
1451  * SvxMenuEntriesListBox is the listbox in which the menu items for a
1452  * particular menu are shown. We have a custom listbox because we need
1453  * to add drag'n'drop support from the Macro Selector and within the
1454  * listbox
1455  *
1456  *****************************************************************************/
1457 SvxMenuEntriesListBox::SvxMenuEntriesListBox(
1458     Window* pParent, const ResId& rResId)
1459     : SvTreeListBox( pParent, rResId )
1460     , pPage( (SvxMenuConfigPage*) pParent )
1461     , m_bIsInternalDrag( sal_False )
1462 {
1463     SetStyle(
1464         GetStyle() | WB_CLIPCHILDREN | WB_HSCROLL | WB_HIDESELECTION );
1465 
1466     SetSpaceBetweenEntries( 3 );
1467     SetEntryHeight( ENTRY_HEIGHT );
1468 
1469     SetHighlightRange();
1470     SetSelectionMode(SINGLE_SELECTION);
1471 
1472     SetDragDropMode( SV_DRAGDROP_CTRL_MOVE  |
1473                      SV_DRAGDROP_APP_COPY   |
1474                      SV_DRAGDROP_ENABLE_TOP |
1475                      SV_DRAGDROP_APP_DROP);
1476 }
1477 
1478 SvxMenuEntriesListBox::~SvxMenuEntriesListBox()
1479 {
1480     // do nothing
1481 }
1482 
1483 // drag and drop support
1484 DragDropMode SvxMenuEntriesListBox::NotifyStartDrag(
1485     TransferDataContainer& aTransferDataContainer, SvLBoxEntry* pEntry )
1486 {
1487     (void)aTransferDataContainer;
1488     (void)pEntry;
1489 
1490     m_bIsInternalDrag = sal_True;
1491     return GetDragDropMode();
1492 }
1493 
1494 void SvxMenuEntriesListBox::DragFinished( sal_Int8 nDropAction )
1495 {
1496     (void)nDropAction;
1497     m_bIsInternalDrag = sal_False;
1498 }
1499 
1500 sal_Int8 SvxMenuEntriesListBox::AcceptDrop( const AcceptDropEvent& rEvt )
1501 {
1502     if ( m_bIsInternalDrag )
1503     {
1504         // internal copy isn't allowed!
1505         if ( rEvt.mnAction == DND_ACTION_COPY )
1506             return DND_ACTION_NONE;
1507         else
1508             return SvTreeListBox::AcceptDrop( rEvt );
1509     }
1510 
1511     // Always do COPY instead of MOVE if D&D comes from outside!
1512     AcceptDropEvent aNewAcceptDropEvent( rEvt );
1513     aNewAcceptDropEvent.mnAction = DND_ACTION_COPY;
1514     return SvTreeListBox::AcceptDrop( aNewAcceptDropEvent );
1515 }
1516 
1517 sal_Bool SvxMenuEntriesListBox::NotifyAcceptDrop( SvLBoxEntry* )
1518 {
1519     return sal_True;
1520 }
1521 
1522 sal_Bool SvxMenuEntriesListBox::NotifyMoving(
1523     SvLBoxEntry* pTarget, SvLBoxEntry* pSource,
1524     SvLBoxEntry*& rpNewParent, sal_uLong& rNewChildPos)
1525 {
1526     // only try to do a move if we are dragging within the list box
1527     if ( m_bIsInternalDrag )
1528     {
1529         if ( pPage->MoveEntryData( pSource, pTarget ) == sal_True )
1530         {
1531             SvTreeListBox::NotifyMoving(
1532                 pTarget, pSource, rpNewParent, rNewChildPos );
1533             return sal_True;
1534         }
1535         else
1536         {
1537             return sal_False;
1538         }
1539     }
1540     else
1541     {
1542         return NotifyCopying( pTarget, pSource, rpNewParent, rNewChildPos );
1543     }
1544 }
1545 
1546 sal_Bool SvxMenuEntriesListBox::NotifyCopying(
1547     SvLBoxEntry* pTarget, SvLBoxEntry* pSource,
1548     SvLBoxEntry*& rpNewParent, sal_uLong& rNewChildPos)
1549 {
1550     (void)pSource;
1551     (void)rpNewParent;
1552     (void)rNewChildPos;
1553 
1554     if ( !m_bIsInternalDrag )
1555     {
1556         // if the target is NULL then add function to the start of the list
1557         pPage->AddFunction( pTarget, pTarget == NULL );
1558 
1559         // AddFunction already adds the listbox entry so return FALSE
1560         // to stop another listbox entry being added
1561         return sal_False;
1562     }
1563 
1564     // Copying is only allowed from external controls, not within the listbox
1565     return sal_False;
1566 }
1567 
1568 void SvxMenuEntriesListBox::KeyInput( const KeyEvent& rKeyEvent )
1569 {
1570     KeyCode keycode = rKeyEvent.GetKeyCode();
1571 
1572     // support DELETE for removing the current entry
1573     if ( keycode == KEY_DELETE )
1574     {
1575         pPage->DeleteSelectedContent();
1576     }
1577     // support CTRL+UP and CTRL+DOWN for moving selected entries
1578     else if ( keycode.GetCode() == KEY_UP && keycode.IsMod1() )
1579     {
1580         pPage->MoveEntry( sal_True );
1581     }
1582     else if ( keycode.GetCode() == KEY_DOWN && keycode.IsMod1() )
1583     {
1584         pPage->MoveEntry( sal_False );
1585     }
1586     else
1587     {
1588         // pass on to superclass
1589         SvTreeListBox::KeyInput( rKeyEvent );
1590     }
1591 }
1592 
1593 // class SvxDescriptionEdit ----------------------------------------------
1594 
1595 SvxDescriptionEdit::SvxDescriptionEdit( Window* pParent, const ResId& _rId ) :
1596 
1597     ExtMultiLineEdit( pParent, _rId )
1598 
1599 {
1600     // calculate the available space for help text
1601     m_aRealRect = Rectangle( Point(), GetSizePixel() );
1602     if ( GetVScrollBar() )
1603         m_aRealRect.Right() -= ( GetVScrollBar()->GetSizePixel().Width() + 4 );
1604 
1605     SetLeftMargin(2);
1606     SetBorderStyle( WINDOW_BORDER_MONO );
1607 }
1608 
1609 // -----------------------------------------------------------------------
1610 
1611 void SvxDescriptionEdit::SetNewText( const String& _rText )
1612 {
1613     String sTemp( _rText );
1614     sal_Bool bShow = sal_False;
1615     if ( sTemp.Len() > 0 )
1616     {
1617         // detect if a scrollbar is necessary
1618         Rectangle aRect = GetTextRect( m_aRealRect, sTemp, TEXT_DRAW_WORDBREAK | TEXT_DRAW_MULTILINE );
1619         bShow = ( aRect.Bottom() > m_aRealRect.Bottom() );
1620     }
1621 
1622     if ( GetVScrollBar() )
1623         GetVScrollBar()->Show( bShow );
1624 
1625     if ( bShow )
1626         sTemp += '\n';
1627 
1628     SetText( sTemp );
1629 }
1630 
1631 /******************************************************************************
1632  *
1633  * SvxConfigPage is the abstract base class on which the Menu and Toolbar
1634  * configuration tabpages are based. It includes methods which are common to
1635  * both tabpages to add, delete, move and rename items etc.
1636  *
1637  *****************************************************************************/
1638 SvxConfigPage::SvxConfigPage(
1639     Window *pParent, const SfxItemSet& rSet )
1640     :
1641     SfxTabPage( pParent, CUI_RES( RID_SVXPAGE_MENUS ), rSet ),
1642     bInitialised( sal_False ),
1643     pCurrentSaveInData( 0 ),
1644     aTopLevelSeparator( this, CUI_RES( GRP_MENUS ) ),
1645     aTopLevelLabel( this, CUI_RES( FT_MENUS ) ),
1646     aTopLevelListBox( this, CUI_RES( LB_MENUS ) ),
1647     aNewTopLevelButton( this, CUI_RES( BTN_NEW ) ),
1648     aModifyTopLevelButton( this, CUI_RES( BTN_CHANGE ) ),
1649     aContentsSeparator( this, CUI_RES( GRP_MENU_SEPARATOR ) ),
1650     aContentsLabel( this, CUI_RES( GRP_MENU_ENTRIES ) ),
1651     aContentsListBox( 0 ),
1652     aAddCommandsButton( this, CUI_RES( BTN_ADD_COMMANDS ) ),
1653     aModifyCommandButton( this, CUI_RES( BTN_CHANGE_ENTRY ) ),
1654     aMoveUpButton( this, CUI_RES( BTN_UP ) ),
1655     aMoveDownButton( this, CUI_RES( BTN_DOWN ) ),
1656     aSaveInText( this, CUI_RES( TXT_SAVEIN ) ),
1657     aSaveInListBox( this, CUI_RES( LB_SAVEIN ) ),
1658     aDescriptionLabel( this, CUI_RES( FT_DESCRIPTION ) ),
1659     aDescriptionField( this, CUI_RES( ED_DESCRIPTION ) ),
1660     pSelectorDlg( 0 )
1661 {
1662     aDescriptionField.SetControlBackground( GetSettings().GetStyleSettings().GetDialogColor() );
1663     aDescriptionField.SetAutoScroll( sal_True );
1664     aDescriptionField.EnableCursor( sal_False );
1665 
1666     aMoveUpButton.SetAccessibleName(String(CUI_RES(BUTTON_STR_UP)));
1667     aMoveDownButton.SetAccessibleName(String(CUI_RES(BUTTON_STR_DOWN)));
1668     aMoveUpButton.SetAccessibleRelationMemberOf(&aContentsSeparator);
1669     aMoveDownButton.SetAccessibleRelationMemberOf(&aContentsSeparator);
1670     aNewTopLevelButton.SetAccessibleRelationMemberOf(&aTopLevelSeparator);
1671     aModifyTopLevelButton.SetAccessibleRelationMemberOf(&aTopLevelSeparator);
1672     aAddCommandsButton.SetAccessibleRelationMemberOf(&aContentsSeparator);
1673     aModifyCommandButton.SetAccessibleRelationMemberOf(&aContentsSeparator);
1674 }
1675 
1676 SvxConfigPage::~SvxConfigPage()
1677 {
1678 }
1679 
1680 void SvxConfigPage::Reset( const SfxItemSet& )
1681 {
1682     // If we haven't initialised our XMultiServiceFactory reference
1683     // then Reset is being called at the opening of the dialog.
1684     //
1685     // Load menu configuration data for the module of the currently
1686     // selected document, for the currently selected document, and for
1687     // all other open documents of the same module type
1688     if ( !bInitialised )
1689     {
1690         sal_uInt16 nPos = 0;
1691         uno::Reference < css::ui::XUIConfigurationManager > xCfgMgr;
1692         uno::Reference < css::ui::XUIConfigurationManager > xDocCfgMgr;
1693 
1694         uno::Reference< lang::XMultiServiceFactory > xServiceManager(
1695             ::comphelper::getProcessServiceFactory(), uno::UNO_QUERY_THROW );
1696 
1697         m_xFrame = GetFrame();
1698         OUString aModuleId = GetFrameWithDefaultAndIdentify( m_xFrame );
1699 
1700         // replace %MODULENAME in the label with the correct module name
1701         uno::Reference< css::frame::XModuleManager > xModuleManager(
1702             xServiceManager->createInstance(
1703                 OUString( RTL_CONSTASCII_USTRINGPARAM(
1704                     "com.sun.star.frame.ModuleManager" ) ) ),
1705             uno::UNO_QUERY_THROW );
1706         OUString aModuleName = GetUIModuleName( aModuleId, xModuleManager );
1707 
1708         OUString title = aTopLevelSeparator.GetText();
1709         OUString aSearchString = OUString::createFromAscii( "%MODULENAME" );
1710         sal_Int32 index = title.indexOf( aSearchString );
1711 
1712         if ( index != -1 )
1713         {
1714             title = title.replaceAt(
1715                 index, aSearchString.getLength(), aModuleName );
1716             aTopLevelSeparator.SetText( title );
1717         }
1718 
1719         uno::Reference< css::ui::XModuleUIConfigurationManagerSupplier >
1720             xModuleCfgSupplier( xServiceManager->createInstance(
1721                 OUString( RTL_CONSTASCII_USTRINGPARAM(
1722             "com.sun.star.ui.ModuleUIConfigurationManagerSupplier" ))),
1723             uno::UNO_QUERY );
1724 
1725         // Set up data for module specific menus
1726         SaveInData* pModuleData = NULL;
1727 
1728         try
1729         {
1730             xCfgMgr =
1731                 xModuleCfgSupplier->getUIConfigurationManager( aModuleId );
1732 
1733             pModuleData = CreateSaveInData( xCfgMgr,
1734                                             uno::Reference< css::ui::XUIConfigurationManager >(),
1735                                             aModuleId,
1736                                             sal_False );
1737         }
1738         catch ( container::NoSuchElementException& )
1739         {
1740         }
1741 
1742         if ( pModuleData != NULL )
1743         {
1744             OUString label;
1745             utl::ConfigManager::GetDirectConfigProperty(
1746                 utl::ConfigManager::PRODUCTNAME ) >>= label;
1747             label += OUString::createFromAscii( " " );
1748             label += aModuleName;
1749 
1750             nPos = aSaveInListBox.InsertEntry( label );
1751             aSaveInListBox.SetEntryData( nPos, pModuleData );
1752         }
1753 
1754         // try to retrieve the document based ui configuration manager
1755         OUString aTitle;
1756         uno::Reference< frame::XController > xController =
1757             m_xFrame->getController();
1758         if ( CanConfig( aModuleId ) && xController.is() )
1759         {
1760             uno::Reference< frame::XModel > xModel( xController->getModel() );
1761             if ( xModel.is() )
1762             {
1763                 uno::Reference< css::ui::XUIConfigurationManagerSupplier >
1764                     xCfgSupplier( xModel, uno::UNO_QUERY );
1765 
1766                 if ( xCfgSupplier.is() )
1767                 {
1768                     xDocCfgMgr = xCfgSupplier->getUIConfigurationManager();
1769                 }
1770                 aTitle = ::comphelper::DocumentInfo::getDocumentTitle( xModel );
1771             }
1772         }
1773 
1774         SaveInData* pDocData = NULL;
1775         if ( xDocCfgMgr.is() )
1776         {
1777             pDocData = CreateSaveInData( xDocCfgMgr, xCfgMgr, aModuleId, sal_True );
1778 
1779             if ( !pDocData->IsReadOnly() )
1780             {
1781                 nPos = aSaveInListBox.InsertEntry( aTitle );
1782                 aSaveInListBox.SetEntryData( nPos, pDocData );
1783             }
1784         }
1785 
1786         // if an item to select has been passed in (eg. the ResourceURL for a
1787         // toolbar) then try to select the SaveInData entry that has that item
1788         bool bURLToSelectFound = sal_False;
1789         if ( m_aURLToSelect.getLength() != 0 )
1790         {
1791             if ( pDocData != NULL && pDocData->HasURL( m_aURLToSelect ) )
1792             {
1793                 aSaveInListBox.SelectEntryPos( nPos, sal_True );
1794                 pCurrentSaveInData = pDocData;
1795                 bURLToSelectFound = sal_True;
1796             }
1797             else if ( pModuleData->HasURL( m_aURLToSelect ) )
1798             {
1799                 aSaveInListBox.SelectEntryPos( 0, sal_True );
1800                 pCurrentSaveInData = pModuleData;
1801                 bURLToSelectFound = sal_True;
1802             }
1803         }
1804 
1805         if ( bURLToSelectFound == sal_False )
1806         {
1807             // if the document has menu configuration settings select it
1808             // it the SaveIn listbox, otherwise select the module data
1809             if ( pDocData != NULL && pDocData->HasSettings() )
1810             {
1811                 aSaveInListBox.SelectEntryPos( nPos, sal_True );
1812                 pCurrentSaveInData = pDocData;
1813             }
1814             else
1815             {
1816                 aSaveInListBox.SelectEntryPos( 0, sal_True );
1817                 pCurrentSaveInData = pModuleData;
1818             }
1819         }
1820 
1821 #ifdef DBG_UTIL
1822         DBG_ASSERT( pCurrentSaveInData, "SvxConfigPage::Reset(): no SaveInData" );
1823 #endif
1824 
1825         if ( CanConfig( aModuleId ) )
1826         {
1827             // Load configuration for other open documents which have
1828             // same module type
1829             uno::Sequence< uno::Reference< frame::XFrame > > aFrameList;
1830             try
1831             {
1832                 uno::Reference< frame::XFramesSupplier > xFramesSupplier(
1833                     xServiceManager->createInstance(
1834                         OUString( RTL_CONSTASCII_USTRINGPARAM(
1835                             "com.sun.star.frame.Desktop" ) ) ),
1836                     uno::UNO_QUERY_THROW );
1837 
1838                 uno::Reference< frame::XFrames > xFrames =
1839                     xFramesSupplier->getFrames();
1840 
1841                 aFrameList = xFrames->queryFrames(
1842                     frame::FrameSearchFlag::ALL & ~frame::FrameSearchFlag::SELF );
1843 
1844             }
1845             catch( const uno::Exception& )
1846             {
1847                 DBG_UNHANDLED_EXCEPTION();
1848             }
1849 
1850             for ( sal_Int32 i = 0; i < aFrameList.getLength(); i++ )
1851             {
1852                 SaveInData* pData = NULL;
1853                 uno::Reference < frame::XFrame > xf = aFrameList[i];
1854 
1855                 if ( xf.is() && xf != m_xFrame )
1856                 {
1857                     OUString aCheckId;
1858                     try{
1859                         aCheckId = xModuleManager->identify( xf );
1860                     } catch(const uno::Exception&)
1861                         { aCheckId = ::rtl::OUString(); }
1862 
1863                     if ( aModuleId.equals( aCheckId ) )
1864                     {
1865                         // try to get the document based ui configuration manager
1866                         OUString aTitle2;
1867                         uno::Reference< frame::XController > xController_ =
1868                             xf->getController();
1869 
1870                         if ( xController_.is() )
1871                         {
1872                             uno::Reference< frame::XModel > xModel(
1873                                 xController_->getModel() );
1874 
1875                             if ( xModel.is() )
1876                             {
1877                                 uno::Reference<
1878                                     css::ui::XUIConfigurationManagerSupplier >
1879                                         xCfgSupplier( xModel, uno::UNO_QUERY );
1880 
1881                                 if ( xCfgSupplier.is() )
1882                                 {
1883                                     xDocCfgMgr =
1884                                         xCfgSupplier->getUIConfigurationManager();
1885                                 }
1886                                 aTitle2 = ::comphelper::DocumentInfo::getDocumentTitle( xModel );
1887                             }
1888                         }
1889 
1890                         if ( xDocCfgMgr.is() )
1891                         {
1892                             pData = CreateSaveInData( xDocCfgMgr, xCfgMgr, aModuleId, sal_True );
1893 
1894                             if ( pData && !pData->IsReadOnly() )
1895                             {
1896                                 nPos = aSaveInListBox.InsertEntry( aTitle2 );
1897                                 aSaveInListBox.SetEntryData( nPos, pData );
1898                             }
1899                         }
1900                     }
1901                 }
1902             }
1903         }
1904 
1905         aSaveInListBox.SetSelectHdl(
1906             LINK( this, SvxConfigPage, SelectSaveInLocation ) );
1907 
1908         bInitialised = sal_True;
1909 
1910         Init();
1911     }
1912     else
1913     {
1914         if ( QueryReset() == RET_YES )
1915         {
1916             // Reset menu configuration for currently selected SaveInData
1917             GetSaveInData()->Reset();
1918 
1919             Init();
1920         }
1921     }
1922 }
1923 
1924 ::rtl::OUString SvxConfigPage::GetFrameWithDefaultAndIdentify( uno::Reference< frame::XFrame >& _inout_rxFrame )
1925 {
1926     ::rtl::OUString sModuleID;
1927     try
1928     {
1929         uno::Reference< lang::XMultiServiceFactory > xServiceManager(
1930             ::comphelper::getProcessServiceFactory(), uno::UNO_QUERY_THROW );
1931 
1932         uno::Reference< frame::XFramesSupplier > xFramesSupplier(
1933             xServiceManager->createInstance(
1934                 OUString( RTL_CONSTASCII_USTRINGPARAM(
1935                     "com.sun.star.frame.Desktop" ) ) ),
1936             uno::UNO_QUERY_THROW );
1937 
1938         if ( !_inout_rxFrame.is() )
1939             _inout_rxFrame = xFramesSupplier->getActiveFrame();
1940 
1941         if ( !_inout_rxFrame.is() )
1942         {
1943             uno::Reference< frame::XDesktop > xDesktop( xFramesSupplier, uno::UNO_QUERY_THROW );
1944             _inout_rxFrame = xDesktop->getCurrentFrame();
1945         }
1946 
1947         if ( !_inout_rxFrame.is() && SfxViewFrame::Current() )
1948             _inout_rxFrame = SfxViewFrame::Current()->GetFrame().GetFrameInterface();
1949 
1950         if ( !_inout_rxFrame.is() )
1951         {
1952             DBG_ERRORFILE( "SvxConfigPage::GetFrameWithDefaultAndIdentify(): no frame found!" );
1953             return sModuleID;
1954         }
1955 
1956         uno::Reference< css::frame::XModuleManager > xModuleManager(
1957             xServiceManager->createInstance(
1958                 OUString( RTL_CONSTASCII_USTRINGPARAM(
1959                     "com.sun.star.frame.ModuleManager" ) ) ),
1960             uno::UNO_QUERY_THROW );
1961 
1962         try
1963         {
1964             sModuleID = xModuleManager->identify( _inout_rxFrame );
1965         }
1966         catch ( const frame::UnknownModuleException& )
1967         {
1968         }
1969 
1970     }
1971     catch( const uno::Exception& )
1972     {
1973         DBG_UNHANDLED_EXCEPTION();
1974     }
1975 
1976     return sModuleID;
1977 }
1978 
1979 sal_Bool SvxConfigPage::FillItemSet( SfxItemSet& )
1980 {
1981     bool result = sal_False;
1982 
1983     for ( sal_uInt16 i = 0 ; i < aSaveInListBox.GetEntryCount(); i++ )
1984     {
1985         SaveInData* pData =
1986             (SaveInData*) aSaveInListBox.GetEntryData( i );
1987 
1988         result = pData->Apply();
1989     }
1990     return result;
1991 }
1992 
1993 void SvxConfigPage::PositionContentsListBox()
1994 {
1995     if ( aContentsListBox == NULL )
1996     {
1997         return;
1998     }
1999 
2000     Point p, newp;
2001     Size s, news;
2002     long x, y, width, height;
2003 
2004     // x and width is same as aTopLevelListBox
2005     x = aTopLevelListBox.GetPosPixel().X();
2006     width = aTopLevelListBox.GetSizePixel().Width();
2007 
2008     // y is same as aAddCommandsButton
2009     y = aAddCommandsButton.GetPosPixel().Y();
2010 
2011     // get gap between aAddCommandsButton and aContentsSeparator
2012     p = aContentsSeparator.GetPosPixel();
2013     s = aContentsSeparator.GetSizePixel();
2014     long gap = y - ( p.Y() + s.Height() );
2015 
2016     height = aSaveInListBox.GetPosPixel().Y() - y - gap;
2017 
2018     aContentsListBox->SetPosPixel( Point( x, y ) );
2019     aContentsListBox->SetSizePixel( Size( width, height ) );
2020 }
2021 
2022 IMPL_LINK( SvxConfigPage, SelectSaveInLocation, ListBox *, pBox )
2023 {
2024     (void)pBox;
2025 
2026     pCurrentSaveInData = (SaveInData*) aSaveInListBox.GetEntryData(
2027             aSaveInListBox.GetSelectEntryPos());
2028 
2029     Init();
2030     return 1;
2031 }
2032 
2033 void SvxConfigPage::ReloadTopLevelListBox( SvxConfigEntry* pToSelect )
2034 {
2035     sal_uInt16 nSelectionPos = aTopLevelListBox.GetSelectEntryPos();
2036     aTopLevelListBox.Clear();
2037 
2038     if ( GetSaveInData() && GetSaveInData()->GetEntries() )
2039     {
2040         SvxEntries::const_iterator iter = GetSaveInData()->GetEntries()->begin();
2041         SvxEntries::const_iterator end = GetSaveInData()->GetEntries()->end();
2042 
2043         for ( ; iter != end; iter++ )
2044         {
2045             SvxConfigEntry* pEntryData = *iter;
2046             sal_uInt16 nPos = aTopLevelListBox.InsertEntry( stripHotKey( pEntryData->GetName() ) );
2047             aTopLevelListBox.SetEntryData( nPos, pEntryData );
2048 
2049             if ( pEntryData == pToSelect )
2050                 nSelectionPos = nPos;
2051 
2052             AddSubMenusToUI( stripHotKey( pEntryData->GetName() ), pEntryData );
2053         }
2054     }
2055 #ifdef DBG_UTIL
2056     else
2057     {
2058         DBG_ASSERT( GetSaveInData(), "SvxConfigPage::ReloadTopLevelListBox(): no SaveInData" );
2059         DBG_ASSERT( GetSaveInData()->GetEntries() ,
2060             "SvxConfigPage::ReloadTopLevelListBox(): no SaveInData entries" );
2061     }
2062 #endif
2063 
2064     nSelectionPos = nSelectionPos < aTopLevelListBox.GetEntryCount() ?
2065         nSelectionPos : aTopLevelListBox.GetEntryCount() - 1;
2066 
2067     aTopLevelListBox.SelectEntryPos( nSelectionPos, sal_True );
2068     aTopLevelListBox.GetSelectHdl().Call( this );
2069 }
2070 
2071 void SvxConfigPage::AddSubMenusToUI(
2072     const String& rBaseTitle, SvxConfigEntry* pParentData )
2073 {
2074     SvxEntries::const_iterator iter = pParentData->GetEntries()->begin();
2075     SvxEntries::const_iterator end = pParentData->GetEntries()->end();
2076 
2077     for ( ; iter != end; iter++ )
2078     {
2079         SvxConfigEntry* pEntryData = *iter;
2080 
2081         if ( pEntryData->IsPopup() )
2082         {
2083             OUString subMenuTitle( rBaseTitle );
2084             subMenuTitle += OUString::createFromAscii( pMenuSeparatorStr );
2085             subMenuTitle += stripHotKey( pEntryData->GetName() );
2086 
2087             sal_uInt16 nPos = aTopLevelListBox.InsertEntry( subMenuTitle );
2088             aTopLevelListBox.SetEntryData( nPos, pEntryData );
2089 
2090             AddSubMenusToUI( subMenuTitle, pEntryData );
2091         }
2092     }
2093 }
2094 
2095 SvxEntries* SvxConfigPage::FindParentForChild(
2096     SvxEntries* pRootEntries, SvxConfigEntry* pChildData )
2097 {
2098     SvxEntries::const_iterator iter = pRootEntries->begin();
2099     SvxEntries::const_iterator end = pRootEntries->end();
2100 
2101     for ( ; iter != end; iter++ )
2102     {
2103         SvxConfigEntry* pEntryData = *iter;
2104 
2105         if ( pEntryData == pChildData )
2106         {
2107             return pRootEntries;
2108         }
2109         else if ( pEntryData->IsPopup() )
2110         {
2111             SvxEntries* result =
2112                 FindParentForChild( pEntryData->GetEntries(), pChildData );
2113 
2114             if ( result != NULL )
2115             {
2116                 return result;
2117             }
2118         }
2119     }
2120     return NULL;
2121 }
2122 
2123 SvLBoxEntry* SvxConfigPage::AddFunction(
2124     SvLBoxEntry* pTarget, bool bFront, bool bAllowDuplicates )
2125 {
2126     String aDisplayName = pSelectorDlg->GetSelectedDisplayName();
2127     String aHelpText = pSelectorDlg->GetSelectedHelpText();
2128     String aURL = pSelectorDlg->GetScriptURL();
2129 
2130     if ( !aURL.Len() )
2131     {
2132         return NULL;
2133     }
2134 
2135     SvxConfigEntry* pNewEntryData =
2136         new SvxConfigEntry( aDisplayName, aURL, sal_False );
2137     pNewEntryData->SetUserDefined( sal_True );
2138 
2139     // check that this function is not already in the menu
2140     SvxConfigEntry* pParent = GetTopLevelSelection();
2141 
2142     SvxEntries::const_iterator iter = pParent->GetEntries()->begin();
2143     SvxEntries::const_iterator end = pParent->GetEntries()->end();
2144 
2145     if ( !bAllowDuplicates )
2146     {
2147         while ( iter != end )
2148         {
2149             SvxConfigEntry *pCurEntry = *iter;
2150 
2151             if ( pCurEntry->GetCommand() == pNewEntryData->GetCommand() )
2152             {
2153                 // asynchronous error message, because of MsgBoxes
2154                 PostUserEvent(
2155                     LINK( this, SvxConfigPage, AsyncInfoMsg ) );
2156                 return NULL;
2157             }
2158 
2159             iter++;
2160         }
2161     }
2162 
2163     return InsertEntry( pNewEntryData, pTarget, bFront );
2164 }
2165 
2166 SvLBoxEntry* SvxConfigPage::InsertEntry(
2167     SvxConfigEntry* pNewEntryData,
2168     SvLBoxEntry* pTarget,
2169     bool bFront )
2170 {
2171     // Grab the entries list for the currently selected menu
2172     SvxEntries* pEntries = GetTopLevelSelection()->GetEntries();
2173 
2174     SvLBoxEntry* pNewEntry = NULL;
2175     SvLBoxEntry* pCurEntry =
2176         pTarget != NULL ? pTarget : aContentsListBox->GetCurEntry();
2177 
2178     if ( bFront )
2179     {
2180         pEntries->insert( pEntries->begin(), pNewEntryData );
2181         pNewEntry = InsertEntryIntoUI( pNewEntryData, 0 );
2182     }
2183     else if ( pCurEntry == NULL || pCurEntry == aContentsListBox->Last() )
2184     {
2185         pEntries->push_back( pNewEntryData );
2186         pNewEntry = InsertEntryIntoUI( pNewEntryData );
2187     }
2188     else
2189     {
2190         SvxConfigEntry* pEntryData =
2191             (SvxConfigEntry*) pCurEntry->GetUserData();
2192 
2193         SvxEntries::iterator iter = pEntries->begin();
2194         SvxEntries::const_iterator end = pEntries->end();
2195 
2196         // Advance the iterator to the data for currently selected entry
2197         sal_uInt16 nPos = 0;
2198         while (*iter != pEntryData && ++iter != end)
2199         {
2200             nPos++;
2201         }
2202 
2203         // Now step past it to the entry after the currently selected one
2204         iter++;
2205         nPos++;
2206 
2207         // Now add the new entry to the UI and to the parent's list
2208         if ( iter != end )
2209         {
2210             pEntries->insert( iter, pNewEntryData );
2211             pNewEntry = InsertEntryIntoUI( pNewEntryData, nPos );
2212         }
2213     }
2214 
2215     if ( pNewEntry != NULL )
2216     {
2217         aContentsListBox->Select( pNewEntry );
2218         aContentsListBox->MakeVisible( pNewEntry );
2219 
2220         GetSaveInData()->SetModified( sal_True );
2221     }
2222 
2223     return pNewEntry;
2224 }
2225 
2226 SvLBoxEntry* SvxConfigPage::InsertEntryIntoUI(
2227     SvxConfigEntry* pNewEntryData, sal_uLong nPos )
2228 {
2229     SvLBoxEntry* pNewEntry = NULL;
2230 
2231     if (pNewEntryData->IsSeparator())
2232     {
2233         pNewEntry = aContentsListBox->InsertEntry(
2234             String::CreateFromAscii( pSeparatorStr ),
2235                 0, sal_False, nPos, pNewEntryData );
2236     }
2237     else
2238     {
2239         OUString aName = stripHotKey( pNewEntryData->GetName() );
2240 
2241         Image aImage = GetSaveInData()->GetImage(
2242             pNewEntryData->GetCommand());
2243 
2244         if ( !!aImage )
2245         {
2246             pNewEntry = aContentsListBox->InsertEntry(
2247                 aName, aImage, aImage, 0, sal_False, nPos, pNewEntryData );
2248         }
2249         else
2250         {
2251             pNewEntry = aContentsListBox->InsertEntry(
2252                 aName, 0, sal_False, nPos, pNewEntryData );
2253         }
2254 
2255         if ( pNewEntryData->IsPopup() ||
2256              pNewEntryData->GetStyle() & css::ui::ItemStyle::DROP_DOWN )
2257         {
2258             // add new popup painter, it gets destructed by the entry
2259             pNewEntry->ReplaceItem(
2260                 new PopupPainter( pNewEntry, aName ),
2261                 pNewEntry->ItemCount() - 1 );
2262         }
2263     }
2264 
2265     return pNewEntry;
2266 }
2267 
2268 IMPL_LINK( SvxConfigPage, AsyncInfoMsg, String*, pMsg )
2269 {
2270     (void)pMsg;
2271 
2272     // Asynchronous msg because of D&D
2273     InfoBox( this, CUI_RES(
2274         IBX_MNUCFG_ALREADY_INCLUDED ) ).Execute();
2275 
2276     return 0;
2277 }
2278 
2279 IMPL_LINK( SvxConfigPage, MoveHdl, Button *, pButton )
2280 {
2281     MoveEntry( pButton == &aMoveUpButton );
2282     return 0;
2283 }
2284 
2285 void SvxConfigPage::MoveEntry( bool bMoveUp )
2286 {
2287     SvLBoxEntry *pSourceEntry = aContentsListBox->FirstSelected();
2288     SvLBoxEntry *pTargetEntry = NULL;
2289     SvLBoxEntry *pToSelect = NULL;
2290 
2291     if ( !pSourceEntry )
2292     {
2293         return;
2294     }
2295 
2296     if ( bMoveUp )
2297     {
2298         // Move Up is just a Move Down with the source and target reversed
2299         pTargetEntry = pSourceEntry;
2300         pSourceEntry = aContentsListBox->PrevSibling( pTargetEntry );
2301         pToSelect = pTargetEntry;
2302     }
2303     else
2304     {
2305         pTargetEntry = aContentsListBox->NextSibling( pSourceEntry );
2306         pToSelect = pSourceEntry;
2307     }
2308 
2309     if ( MoveEntryData( pSourceEntry, pTargetEntry ) )
2310     {
2311         aContentsListBox->GetModel()->Move( pSourceEntry, pTargetEntry );
2312         aContentsListBox->Select( pToSelect );
2313         aContentsListBox->MakeVisible( pToSelect );
2314 
2315         UpdateButtonStates();
2316     }
2317 }
2318 
2319 bool SvxConfigPage::MoveEntryData(
2320     SvLBoxEntry* pSourceEntry, SvLBoxEntry* pTargetEntry )
2321 {
2322     //modified by shizhoubo for issue53677
2323     if ( NULL == pSourceEntry || NULL == pTargetEntry )
2324     {
2325         return sal_False;
2326     }
2327 
2328     // Grab the entries list for the currently selected menu
2329     SvxEntries* pEntries = GetTopLevelSelection()->GetEntries();
2330 
2331     SvxConfigEntry* pSourceData =
2332         (SvxConfigEntry*) pSourceEntry->GetUserData();
2333 
2334     if ( pTargetEntry == NULL )
2335     {
2336         RemoveEntry( pEntries, pSourceData );
2337         pEntries->insert(
2338             pEntries->begin(), pSourceData );
2339 
2340         GetSaveInData()->SetModified( sal_True );
2341 
2342         return sal_True;
2343     }
2344     else
2345     {
2346         SvxConfigEntry* pTargetData =
2347             (SvxConfigEntry*) pTargetEntry->GetUserData();
2348 
2349         if ( pSourceData != NULL && pTargetData != NULL )
2350         {
2351             // remove the source entry from our list
2352             RemoveEntry( pEntries, pSourceData );
2353 
2354             SvxEntries::iterator iter = pEntries->begin();
2355             SvxEntries::const_iterator end = pEntries->end();
2356 
2357             // advance the iterator to the position of the target entry
2358             while (*iter != pTargetData && ++iter != end) ;
2359 
2360             // insert the source entry at the position after the target
2361             pEntries->insert( ++iter, pSourceData );
2362 
2363             GetSaveInData()->SetModified( sal_True );
2364 
2365             return sal_True;
2366         }
2367     }
2368 
2369     return sal_False;
2370 }
2371 
2372 SvxMenuConfigPage::SvxMenuConfigPage(
2373     Window *pParent, const SfxItemSet& rSet )
2374     :
2375     SvxConfigPage( pParent, rSet )
2376 {
2377     aContentsListBox = new SvxMenuEntriesListBox( this, CUI_RES( BOX_ENTRIES ) );
2378     FreeResource();
2379 
2380     PositionContentsListBox();
2381     aContentsListBox->SetZOrder( &aAddCommandsButton, WINDOW_ZORDER_BEFOR );
2382 
2383     aTopLevelListBox.SetSelectHdl(
2384         LINK( this, SvxMenuConfigPage, SelectMenu ) );
2385 
2386     aContentsListBox->SetSelectHdl(
2387         LINK( this, SvxMenuConfigPage, SelectMenuEntry ) );
2388 
2389     aMoveUpButton.SetClickHdl ( LINK( this, SvxConfigPage, MoveHdl) );
2390     aMoveDownButton.SetClickHdl ( LINK( this, SvxConfigPage, MoveHdl) );
2391 
2392     aNewTopLevelButton.SetClickHdl  (
2393         LINK( this, SvxMenuConfigPage, NewMenuHdl ) );
2394 
2395     aAddCommandsButton.SetClickHdl  (
2396         LINK( this, SvxMenuConfigPage, AddCommandsHdl ) );
2397 
2398     PopupMenu* pMenu = new PopupMenu( CUI_RES( MODIFY_MENU ) );
2399     pMenu->SetMenuFlags(
2400         pMenu->GetMenuFlags() | MENU_FLAG_ALWAYSSHOWDISABLEDENTRIES );
2401 
2402     aModifyTopLevelButton.SetPopupMenu( pMenu );
2403     aModifyTopLevelButton.SetSelectHdl(
2404         LINK( this, SvxMenuConfigPage, MenuSelectHdl ) );
2405 
2406     PopupMenu* pEntry = new PopupMenu( CUI_RES( MODIFY_ENTRY ) );
2407     pEntry->SetMenuFlags(
2408         pEntry->GetMenuFlags() | MENU_FLAG_ALWAYSSHOWDISABLEDENTRIES );
2409 
2410     aModifyCommandButton.SetPopupMenu( pEntry );
2411     aModifyCommandButton.SetSelectHdl(
2412         LINK( this, SvxMenuConfigPage, EntrySelectHdl ) );
2413 }
2414 
2415 // Populates the Menu combo box
2416 void SvxMenuConfigPage::Init()
2417 {
2418     // ensure that the UI is cleared before populating it
2419     aTopLevelListBox.Clear();
2420     aContentsListBox->Clear();
2421 
2422     ReloadTopLevelListBox();
2423 
2424     aTopLevelListBox.SelectEntryPos(0, sal_True);
2425     aTopLevelListBox.GetSelectHdl().Call(this);
2426 }
2427 
2428 SvxMenuConfigPage::~SvxMenuConfigPage()
2429 {
2430     for ( sal_uInt16 i = 0 ; i < aSaveInListBox.GetEntryCount(); i++ )
2431     {
2432         MenuSaveInData* pData =
2433             (MenuSaveInData*) aSaveInListBox.GetEntryData( i );
2434 
2435         delete pData;
2436     }
2437 
2438     if ( pSelectorDlg != NULL )
2439     {
2440         delete pSelectorDlg;
2441     }
2442 
2443     delete aContentsListBox;
2444 }
2445 
2446 IMPL_LINK( SvxMenuConfigPage, SelectMenuEntry, Control *, pBox )
2447 {
2448     (void)pBox;
2449 
2450     UpdateButtonStates();
2451 
2452     return 1;
2453 }
2454 
2455 void SvxMenuConfigPage::UpdateButtonStates()
2456 {
2457     PopupMenu* pPopup = aModifyCommandButton.GetPopupMenu();
2458 
2459     // Disable Up and Down buttons depending on current selection
2460     SvLBoxEntry* selection = aContentsListBox->GetCurEntry();
2461 
2462     if ( aContentsListBox->GetEntryCount() == 0 || selection == NULL )
2463     {
2464         aMoveUpButton.Enable( sal_False );
2465         aMoveDownButton.Enable( sal_False );
2466 
2467         pPopup->EnableItem( ID_BEGIN_GROUP, sal_True );
2468         pPopup->EnableItem( ID_RENAME, sal_False );
2469         pPopup->EnableItem( ID_DELETE, sal_False );
2470 
2471         aDescriptionField.Clear();
2472 
2473         return;
2474     }
2475 
2476     SvLBoxEntry* first = aContentsListBox->First();
2477     SvLBoxEntry* last = aContentsListBox->Last();
2478 
2479     aMoveUpButton.Enable( selection != first );
2480     aMoveDownButton.Enable( selection != last );
2481 
2482     SvxConfigEntry* pEntryData =
2483         (SvxConfigEntry*) selection->GetUserData();
2484 
2485     if ( pEntryData->IsSeparator() )
2486     {
2487         pPopup->EnableItem( ID_DELETE, sal_True );
2488         pPopup->EnableItem( ID_BEGIN_GROUP, sal_False );
2489         pPopup->EnableItem( ID_RENAME, sal_False );
2490 
2491         aDescriptionField.Clear();
2492     }
2493     else
2494     {
2495         pPopup->EnableItem( ID_BEGIN_GROUP, sal_True );
2496         pPopup->EnableItem( ID_DELETE, sal_True );
2497         pPopup->EnableItem( ID_RENAME, sal_True );
2498 
2499         aDescriptionField.SetNewText( pEntryData->GetHelpText() );
2500     }
2501 }
2502 
2503 void SvxMenuConfigPage::DeleteSelectedTopLevel()
2504 {
2505     SvxConfigEntry* pMenuData = GetTopLevelSelection();
2506 
2507     SvxEntries* pParentEntries =
2508         FindParentForChild( GetSaveInData()->GetEntries(), pMenuData );
2509 
2510     RemoveEntry( pParentEntries, pMenuData );
2511     delete pMenuData;
2512 
2513     ReloadTopLevelListBox();
2514 
2515     GetSaveInData()->SetModified( sal_True );
2516 }
2517 
2518 bool SvxMenuConfigPage::DeleteSelectedContent()
2519 {
2520     SvLBoxEntry *pActEntry = aContentsListBox->FirstSelected();
2521 
2522     if ( pActEntry != NULL )
2523     {
2524         // get currently selected menu entry
2525         SvxConfigEntry* pMenuEntry =
2526             (SvxConfigEntry*) pActEntry->GetUserData();
2527 
2528         // get currently selected menu
2529         SvxConfigEntry* pMenu = GetTopLevelSelection();
2530 
2531         // remove menu entry from the list for this menu
2532         RemoveEntry( pMenu->GetEntries(), pMenuEntry );
2533 
2534         // remove menu entry from UI
2535         aContentsListBox->GetModel()->Remove( pActEntry );
2536 
2537         // if this is a submenu entry, redraw the menus list box
2538         if ( pMenuEntry->IsPopup() )
2539         {
2540             ReloadTopLevelListBox();
2541         }
2542 
2543         // delete data for menu entry
2544         delete pMenuEntry;
2545 
2546         GetSaveInData()->SetModified( sal_True );
2547 
2548         return sal_True;
2549     }
2550     return sal_False;
2551 }
2552 
2553 short SvxMenuConfigPage::QueryReset()
2554 {
2555     String msg =
2556         String( CUI_RES( RID_SVXSTR_CONFIRM_MENU_RESET ) );
2557 
2558     String saveInName = aSaveInListBox.GetEntry(
2559         aSaveInListBox.GetSelectEntryPos() );
2560 
2561     OUString label = replaceSaveInName( msg, saveInName );
2562 
2563     QueryBox qbox( this, WB_YES_NO, label );
2564 
2565     return qbox.Execute();
2566 }
2567 
2568 IMPL_LINK( SvxMenuConfigPage, SelectMenu, ListBox *, pBox )
2569 {
2570     (void)pBox;
2571 
2572     aContentsListBox->Clear();
2573 
2574     SvxConfigEntry* pMenuData = GetTopLevelSelection();
2575 
2576     PopupMenu* pPopup = aModifyTopLevelButton.GetPopupMenu();
2577     if ( pMenuData )
2578     {
2579         pPopup->EnableItem( ID_DELETE, pMenuData->IsDeletable() );
2580         pPopup->EnableItem( ID_RENAME, pMenuData->IsRenamable() );
2581         pPopup->EnableItem( ID_MOVE, pMenuData->IsMovable() );
2582 
2583         SvxEntries* pEntries = pMenuData->GetEntries();
2584         SvxEntries::const_iterator iter = pEntries->begin();
2585 
2586         for ( ; iter != pEntries->end(); iter++ )
2587         {
2588             SvxConfigEntry* pEntry = *iter;
2589             InsertEntryIntoUI( pEntry );
2590         }
2591     }
2592 
2593     UpdateButtonStates();
2594 
2595     return 0;
2596 }
2597 
2598 IMPL_LINK( SvxMenuConfigPage, MenuSelectHdl, MenuButton *, pButton )
2599 {
2600     switch( pButton->GetCurItemId() )
2601     {
2602         case ID_DELETE:
2603         {
2604             DeleteSelectedTopLevel();
2605             break;
2606         }
2607         case ID_RENAME:
2608         {
2609             SvxConfigEntry* pMenuData = GetTopLevelSelection();
2610 
2611             String aNewName( stripHotKey( pMenuData->GetName() ) );
2612             String aDesc = CUI_RESSSTR( RID_SVXSTR_LABEL_NEW_NAME );
2613 
2614             SvxNameDialog* pNameDialog = new SvxNameDialog( this, aNewName, aDesc );
2615             pNameDialog->SetHelpId( HID_SVX_CONFIG_RENAME_MENU );
2616             pNameDialog->SetText( CUI_RESSTR( RID_SVXSTR_RENAME_MENU ) );
2617 
2618             bool ret = pNameDialog->Execute();
2619 
2620             if ( ret == RET_OK ) {
2621                 pNameDialog->GetName( aNewName );
2622                 pMenuData->SetName( aNewName );
2623 
2624                 ReloadTopLevelListBox();
2625 
2626                 GetSaveInData()->SetModified( sal_True );
2627             }
2628 
2629             // #i68101# Moemory leak (!)
2630             delete pNameDialog;
2631 
2632             break;
2633         }
2634         case ID_MOVE:
2635         {
2636             SvxConfigEntry* pMenuData = GetTopLevelSelection();
2637 
2638             SvxMainMenuOrganizerDialog* pDialog =
2639                 new SvxMainMenuOrganizerDialog( this,
2640                     GetSaveInData()->GetEntries(), pMenuData );
2641 
2642             bool ret = pDialog->Execute();
2643 
2644             if ( ret == RET_OK )
2645             {
2646                 GetSaveInData()->SetEntries( pDialog->GetEntries() );
2647 
2648                 ReloadTopLevelListBox( pDialog->GetSelectedEntry() );
2649 
2650                 GetSaveInData()->SetModified( sal_True );
2651             }
2652 
2653             delete pDialog;
2654 
2655             break;
2656         }
2657         default:
2658             return sal_False;
2659     }
2660     return sal_True;
2661 }
2662 
2663 IMPL_LINK( SvxMenuConfigPage, EntrySelectHdl, MenuButton *, pButton )
2664 {
2665     switch( pButton->GetCurItemId() )
2666     {
2667         case ID_ADD_SUBMENU:
2668         {
2669             String aNewName;
2670             String aDesc = CUI_RESSSTR( RID_SVXSTR_SUBMENU_NAME );
2671 
2672             SvxNameDialog* pNameDialog = new SvxNameDialog( this, aNewName, aDesc );
2673             pNameDialog->SetHelpId( HID_SVX_CONFIG_NAME_SUBMENU );
2674             pNameDialog->SetText( CUI_RESSTR( RID_SVXSTR_ADD_SUBMENU ) );
2675 
2676             bool ret = pNameDialog->Execute();
2677 
2678             if ( ret == RET_OK ) {
2679                 pNameDialog->GetName(aNewName);
2680 
2681                 SvxConfigEntry* pNewEntryData =
2682                     new SvxConfigEntry( aNewName, aNewName, sal_True );
2683                 pNewEntryData->SetUserDefined( sal_True );
2684 
2685                 InsertEntry( pNewEntryData );
2686 
2687                 ReloadTopLevelListBox();
2688 
2689                 GetSaveInData()->SetModified( sal_True );
2690             }
2691 
2692             delete pNameDialog;
2693 
2694             break;
2695         }
2696         case ID_BEGIN_GROUP:
2697         {
2698             SvxConfigEntry* pNewEntryData = new SvxConfigEntry;
2699             pNewEntryData->SetUserDefined( sal_True );
2700             InsertEntry( pNewEntryData );
2701 
2702             break;
2703         }
2704         case ID_DELETE:
2705         {
2706             DeleteSelectedContent();
2707             break;
2708         }
2709         case ID_RENAME:
2710         {
2711             SvLBoxEntry* pActEntry = aContentsListBox->GetCurEntry();
2712             SvxConfigEntry* pEntry =
2713                 (SvxConfigEntry*) pActEntry->GetUserData();
2714 
2715             String aNewName( stripHotKey( pEntry->GetName() ) );
2716             String aDesc = CUI_RESSSTR( RID_SVXSTR_LABEL_NEW_NAME );
2717 
2718             SvxNameDialog* pNameDialog = new SvxNameDialog( this, aNewName, aDesc );
2719             pNameDialog->SetHelpId( HID_SVX_CONFIG_RENAME_MENU_ITEM );
2720             pNameDialog->SetText( CUI_RESSTR( RID_SVXSTR_RENAME_MENU ) );
2721 
2722             bool ret = pNameDialog->Execute();
2723 
2724             if ( ret == RET_OK ) {
2725                 pNameDialog->GetName(aNewName);
2726 
2727                 pEntry->SetName( aNewName );
2728                 aContentsListBox->SetEntryText( pActEntry, aNewName );
2729 
2730                 GetSaveInData()->SetModified( sal_True );
2731             }
2732 
2733             delete pNameDialog;
2734 
2735             break;
2736         }
2737         default:
2738         {
2739             return sal_False;
2740         }
2741     }
2742 
2743     if ( GetSaveInData()->IsModified() )
2744     {
2745         UpdateButtonStates();
2746     }
2747 
2748     return sal_True;
2749 }
2750 
2751 IMPL_LINK( SvxMenuConfigPage, AddFunctionHdl,
2752     SvxScriptSelectorDialog *, pDialog )
2753 {
2754     (void)pDialog;
2755 
2756     AddFunction();
2757 
2758     return 0;
2759 }
2760 
2761 IMPL_LINK( SvxMenuConfigPage, NewMenuHdl, Button *, pButton )
2762 {
2763     (void)pButton;
2764 
2765     SvxMainMenuOrganizerDialog* pDialog =
2766         new SvxMainMenuOrganizerDialog( 0,
2767             GetSaveInData()->GetEntries(), NULL, sal_True );
2768 
2769     bool ret = pDialog->Execute();
2770 
2771     if ( ret == RET_OK )
2772     {
2773         GetSaveInData()->SetEntries( pDialog->GetEntries() );
2774         ReloadTopLevelListBox( pDialog->GetSelectedEntry() );
2775         GetSaveInData()->SetModified( sal_True );
2776     }
2777 
2778     delete pDialog;
2779 
2780     return 0;
2781 }
2782 
2783 IMPL_LINK( SvxMenuConfigPage, AddCommandsHdl, Button *, pButton )
2784 {
2785     (void)pButton;
2786 
2787     if ( pSelectorDlg == NULL )
2788     {
2789         // Create Script Selector which also shows builtin commands
2790         pSelectorDlg = new SvxScriptSelectorDialog( this, sal_True, m_xFrame );
2791 
2792         pSelectorDlg->SetAddHdl(
2793             LINK( this, SvxMenuConfigPage, AddFunctionHdl ) );
2794 
2795         pSelectorDlg->SetDialogDescription( String(
2796             CUI_RES( RID_SVXSTR_MENU_ADDCOMMANDS_DESCRIPTION ) ) );
2797     }
2798 
2799     // Position the Script Selector over the Add button so it is
2800     // beside the menu contents list and does not obscure it
2801     pSelectorDlg->SetPosPixel( aAddCommandsButton.GetPosPixel() );
2802 
2803     pSelectorDlg->SetImageProvider(
2804         static_cast< ImageProvider* >( GetSaveInData() ) );
2805 
2806     pSelectorDlg->Show();
2807     return 1;
2808 }
2809 
2810 SaveInData* SvxMenuConfigPage::CreateSaveInData(
2811     const uno::Reference< css::ui::XUIConfigurationManager >& xCfgMgr,
2812     const uno::Reference< css::ui::XUIConfigurationManager >& xParentCfgMgr,
2813     const OUString& aModuleId,
2814     bool bDocConfig )
2815 {
2816     return static_cast< SaveInData* >(
2817         new MenuSaveInData( xCfgMgr, xParentCfgMgr, aModuleId, bDocConfig ));
2818 }
2819 
2820 SvxMainMenuOrganizerDialog::SvxMainMenuOrganizerDialog(
2821     Window* pParent, SvxEntries* entries,
2822     SvxConfigEntry* selection, bool bCreateMenu )
2823     :
2824     ModalDialog( pParent, CUI_RES( MD_MENU_ORGANISER ) ),
2825     aMenuNameText( this, CUI_RES( TXT_MENU_NAME ) ),
2826     aMenuNameEdit( this, CUI_RES( EDIT_MENU_NAME ) ),
2827     aMenuListText( this, CUI_RES( TXT_MENU ) ),
2828     aMenuListBox( this, CUI_RES( BOX_MAIN_MENUS ) ),
2829     aMoveUpButton( this, CUI_RES( BTN_MENU_UP ) ),
2830     aMoveDownButton( this, CUI_RES( BTN_MENU_DOWN ) ),
2831     aOKButton( this, CUI_RES( BTN_MENU_ADD ) ),
2832     aCloseButton( this, CUI_RES( BTN_MENU_CLOSE ) ),
2833     aHelpButton( this, CUI_RES( BTN_MENU_HELP ) ),
2834     bModified( sal_False )
2835 {
2836     FreeResource();
2837 
2838     // Copy the entries list passed in
2839     if ( entries != NULL )
2840     {
2841         SvxConfigEntry* pEntry;
2842         SvLBoxEntry* pLBEntry;
2843 
2844         pEntries = new SvxEntries();
2845         SvxEntries::const_iterator iter = entries->begin();
2846 
2847         while ( iter != entries->end() )
2848         {
2849             pEntry = *iter;
2850             pLBEntry =
2851                 aMenuListBox.InsertEntry( stripHotKey( pEntry->GetName() ) );
2852             pLBEntry->SetUserData( pEntry );
2853             pEntries->push_back( pEntry );
2854 
2855             if ( pEntry == selection )
2856             {
2857                 aMenuListBox.Select( pLBEntry );
2858             }
2859             iter++;
2860         }
2861     }
2862 
2863     if ( bCreateMenu )
2864     {
2865         // Generate custom name for new menu
2866         String prefix =
2867             String( CUI_RES( RID_SVXSTR_NEW_MENU ) );
2868 
2869         OUString newname = generateCustomName( prefix, entries );
2870         OUString newurl = generateCustomMenuURL( pEntries );
2871 
2872         SvxConfigEntry* pNewEntryData =
2873             new SvxConfigEntry( newname, newurl, sal_True );
2874         pNewEntryData->SetUserDefined( sal_True );
2875         pNewEntryData->SetMain( sal_True );
2876 
2877         pNewMenuEntry =
2878             aMenuListBox.InsertEntry( stripHotKey( pNewEntryData->GetName() ) );
2879         aMenuListBox.Select( pNewMenuEntry );
2880 
2881         pNewMenuEntry->SetUserData( pNewEntryData );
2882 
2883         pEntries->push_back( pNewEntryData );
2884 
2885         aMenuNameEdit.SetText( newname );
2886         aMenuNameEdit.SetModifyHdl(
2887             LINK( this, SvxMainMenuOrganizerDialog, ModifyHdl ) );
2888     }
2889     else
2890     {
2891         Point p, newp;
2892         Size s, news;
2893 
2894         // get offset to bottom of name textfield from top of dialog
2895         p = aMenuNameEdit.GetPosPixel();
2896         s = aMenuNameEdit.GetSizePixel();
2897         long offset = p.Y() + s.Height();
2898 
2899         // reposition menu list and label
2900         aMenuListText.SetPosPixel( aMenuNameText.GetPosPixel() );
2901         aMenuListBox.SetPosPixel( aMenuNameEdit.GetPosPixel() );
2902 
2903         // reposition up and down buttons
2904         p = aMoveUpButton.GetPosPixel();
2905         newp = Point( p.X(), p.Y() - offset );
2906         aMoveUpButton.SetPosPixel( newp );
2907 
2908         p = aMoveDownButton.GetPosPixel();
2909         newp = Point( p.X(), p.Y() - offset );
2910         aMoveDownButton.SetPosPixel( newp );
2911 
2912         // change size of dialog
2913         s = GetSizePixel();
2914         news = Size( s.Width(), s.Height() - offset );
2915         SetSizePixel( news );
2916 
2917         // hide name label and textfield
2918         aMenuNameText.Hide();
2919         aMenuNameEdit.Hide();
2920 
2921         // change the title
2922         SetText( CUI_RES( RID_SVXSTR_MOVE_MENU ) );
2923     }
2924 
2925     aMenuListBox.SetSelectHdl(
2926         LINK( this, SvxMainMenuOrganizerDialog, SelectHdl ) );
2927 
2928     aMoveUpButton.SetClickHdl (
2929         LINK( this, SvxMainMenuOrganizerDialog, MoveHdl) );
2930     aMoveDownButton.SetClickHdl (
2931         LINK( this, SvxMainMenuOrganizerDialog, MoveHdl) );
2932 
2933     aMoveUpButton.SetAccessibleName(String(CUI_RES(BUTTON_STR_UP)));
2934     aMoveDownButton.SetAccessibleName(String(CUI_RES(BUTTON_STR_DOWN)));
2935 }
2936 
2937 IMPL_LINK(SvxMainMenuOrganizerDialog, ModifyHdl, Edit*, pEdit)
2938 {
2939     (void)pEdit;
2940 
2941     // if the Edit control is empty do not change the name
2942     if ( aMenuNameEdit.GetText().Equals( String() ) )
2943     {
2944         return 0;
2945     }
2946 
2947     SvxConfigEntry* pNewEntryData =
2948         (SvxConfigEntry*) pNewMenuEntry->GetUserData();
2949 
2950     pNewEntryData->SetName( aMenuNameEdit.GetText() );
2951 
2952     aMenuListBox.SetEntryText( pNewMenuEntry, pNewEntryData->GetName() );
2953 
2954     return 0;
2955 }
2956 
2957 SvxMainMenuOrganizerDialog::~SvxMainMenuOrganizerDialog()
2958 {
2959 }
2960 
2961 IMPL_LINK( SvxMainMenuOrganizerDialog, SelectHdl, Control*, pCtrl )
2962 {
2963     (void)pCtrl;
2964     UpdateButtonStates();
2965     return 1;
2966 }
2967 
2968 void SvxMainMenuOrganizerDialog::UpdateButtonStates()
2969 {
2970     // Disable Up and Down buttons depending on current selection
2971     SvLBoxEntry* selection = aMenuListBox.GetCurEntry();
2972     SvLBoxEntry* first = aMenuListBox.First();
2973     SvLBoxEntry* last = aMenuListBox.Last();
2974 
2975     aMoveUpButton.Enable( selection != first );
2976     aMoveDownButton.Enable( selection != last );
2977 }
2978 
2979 IMPL_LINK( SvxMainMenuOrganizerDialog, MoveHdl, Button *, pButton )
2980 {
2981     SvLBoxEntry *pSourceEntry = aMenuListBox.FirstSelected();
2982     SvLBoxEntry *pTargetEntry = NULL;
2983 
2984     if ( !pSourceEntry )
2985     {
2986         return 0;
2987     }
2988 
2989     if ( pButton == &aMoveDownButton )
2990     {
2991         pTargetEntry = aMenuListBox.NextSibling( pSourceEntry );
2992     }
2993     else if ( pButton == &aMoveUpButton )
2994     {
2995         // Move Up is just a Move Down with the source and target reversed
2996         pTargetEntry = pSourceEntry;
2997         pSourceEntry = aMenuListBox.PrevSibling( pTargetEntry );
2998     }
2999 
3000     if ( pSourceEntry != NULL && pTargetEntry != NULL )
3001     {
3002         SvxConfigEntry* pSourceData =
3003             (SvxConfigEntry*) pSourceEntry->GetUserData();
3004         SvxConfigEntry* pTargetData =
3005             (SvxConfigEntry*) pTargetEntry->GetUserData();
3006 
3007         SvxEntries::iterator iter1 = GetEntries()->begin();
3008         SvxEntries::iterator iter2 = GetEntries()->begin();
3009         SvxEntries::const_iterator end = GetEntries()->end();
3010 
3011         // Advance the iterators to the positions of the source and target
3012         while (*iter1 != pSourceData && ++iter1 != end) ;
3013         while (*iter2 != pTargetData && ++iter2 != end) ;
3014 
3015         // Now swap the entries in the menu list and in the UI
3016         if ( iter1 != end && iter2 != end )
3017         {
3018             std::swap( *iter1, *iter2 );
3019             aMenuListBox.GetModel()->Move( pSourceEntry, pTargetEntry );
3020             aMenuListBox.MakeVisible( pSourceEntry );
3021 
3022             bModified = sal_True;
3023         }
3024     }
3025 
3026     if ( bModified )
3027     {
3028         UpdateButtonStates();
3029     }
3030 
3031     return 0;
3032 }
3033 
3034 SvxEntries* SvxMainMenuOrganizerDialog::GetEntries()
3035 {
3036     return pEntries;
3037 }
3038 
3039 SvxConfigEntry* SvxMainMenuOrganizerDialog::GetSelectedEntry()
3040 {
3041     return (SvxConfigEntry*)aMenuListBox.FirstSelected()->GetUserData();
3042 }
3043 
3044 const OUString&
3045 SvxConfigEntry::GetHelpText()
3046 {
3047     if ( aHelpText.getLength() == 0 )
3048     {
3049         if ( aCommand.getLength() )
3050         {
3051             aHelpText = Application::GetHelp()->GetHelpText( aCommand, NULL );
3052         }
3053     }
3054 
3055     return aHelpText;
3056 }
3057 
3058 SvxConfigEntry::SvxConfigEntry( const OUString& rDisplayName,
3059                                 const OUString& rCommandURL, bool bPopup, bool bParentData )
3060     : nId( 1 )
3061     , aLabel(rDisplayName)
3062     , aCommand(rCommandURL)
3063     , bPopUp(bPopup)
3064     , bStrEdited( sal_False )
3065     , bIsUserDefined( sal_False )
3066     , bIsMain( sal_False )
3067     , bIsParentData( bParentData )
3068     , bIsVisible( sal_True )
3069     , nStyle( 0 )
3070     , pEntries( 0 )
3071 {
3072     if (bPopUp)
3073     {
3074         pEntries = new SvxEntries();
3075     }
3076 }
3077 
3078 SvxConfigEntry::~SvxConfigEntry()
3079 {
3080     if ( pEntries != NULL )
3081     {
3082         SvxEntries::const_iterator iter = pEntries->begin();
3083 
3084         for ( ; iter != pEntries->end(); iter++ )
3085         {
3086             delete *iter;
3087         }
3088         delete pEntries;
3089     }
3090 }
3091 
3092 bool SvxConfigEntry::IsMovable()
3093 {
3094     if ( IsPopup() && !IsMain() )
3095     {
3096         return sal_False;
3097     }
3098     return sal_True;
3099 }
3100 
3101 bool SvxConfigEntry::IsDeletable()
3102 {
3103     if ( IsMain() && !IsUserDefined() )
3104     {
3105         return sal_False;
3106     }
3107     return sal_True;
3108 }
3109 
3110 bool SvxConfigEntry::IsRenamable()
3111 {
3112     if ( IsMain() && !IsUserDefined() )
3113     {
3114         return sal_False;
3115     }
3116     return sal_True;
3117 }
3118 
3119 SvxToolbarConfigPage::SvxToolbarConfigPage(
3120     Window *pParent, const SfxItemSet& rSet )
3121     :
3122     SvxConfigPage( pParent, rSet )
3123 {
3124     SetHelpId( HID_SVX_CONFIG_TOOLBAR );
3125 
3126     aContentsListBox = new SvxToolbarEntriesListBox(this, CUI_RES(BOX_ENTRIES));
3127     FreeResource();
3128     PositionContentsListBox();
3129     aContentsListBox->SetZOrder( &aAddCommandsButton, WINDOW_ZORDER_BEFOR );
3130 
3131     aContentsListBox->SetHelpId( HID_SVX_CONFIG_TOOLBAR_CONTENTS );
3132     aNewTopLevelButton.SetHelpId( HID_SVX_NEW_TOOLBAR );
3133     aModifyTopLevelButton.SetHelpId( HID_SVX_MODIFY_TOOLBAR );
3134     aAddCommandsButton.SetHelpId( HID_SVX_NEW_TOOLBAR_ITEM );
3135     aModifyCommandButton.SetHelpId( HID_SVX_MODIFY_TOOLBAR_ITEM );
3136     aSaveInListBox.SetHelpId( HID_SVX_SAVE_IN );
3137 
3138     aTopLevelSeparator.SetText(
3139         CUI_RES ( RID_SVXSTR_PRODUCTNAME_TOOLBARS ) );
3140 
3141     aTopLevelLabel.SetText( CUI_RES( RID_SVXSTR_TOOLBAR ) );
3142     aModifyTopLevelButton.SetText( CUI_RES( RID_SVXSTR_TOOLBAR ) );
3143     aContentsSeparator.SetText( CUI_RES( RID_SVXSTR_TOOLBAR_CONTENT ) );
3144     aContentsLabel.SetText( CUI_RES( RID_SVXSTR_COMMANDS ) );
3145 
3146     aTopLevelListBox.SetSelectHdl(
3147         LINK( this, SvxToolbarConfigPage, SelectToolbar ) );
3148     aContentsListBox->SetSelectHdl(
3149         LINK( this, SvxToolbarConfigPage, SelectToolbarEntry ) );
3150 
3151     aNewTopLevelButton.SetClickHdl  (
3152         LINK( this, SvxToolbarConfigPage, NewToolbarHdl ) );
3153 
3154     aAddCommandsButton.SetClickHdl  (
3155         LINK( this, SvxToolbarConfigPage, AddCommandsHdl ) );
3156 
3157     aMoveUpButton.SetClickHdl ( LINK( this, SvxToolbarConfigPage, MoveHdl) );
3158     aMoveDownButton.SetClickHdl ( LINK( this, SvxToolbarConfigPage, MoveHdl) );
3159     // Always enable Up and Down buttons
3160     // added for issue i53677 by shizhoubo
3161     aMoveDownButton.Enable( sal_True );
3162     aMoveUpButton.Enable( sal_True );
3163 
3164     PopupMenu* pMenu = new PopupMenu( CUI_RES( MODIFY_TOOLBAR ) );
3165     pMenu->SetMenuFlags(
3166         pMenu->GetMenuFlags() | MENU_FLAG_ALWAYSSHOWDISABLEDENTRIES );
3167 
3168     aModifyTopLevelButton.SetPopupMenu( pMenu );
3169     aModifyTopLevelButton.SetSelectHdl(
3170         LINK( this, SvxToolbarConfigPage, ToolbarSelectHdl ) );
3171 
3172     PopupMenu* pEntry = new PopupMenu(
3173         CUI_RES( MODIFY_TOOLBAR_CONTENT ) );
3174     pEntry->SetMenuFlags(
3175         pEntry->GetMenuFlags() | MENU_FLAG_ALWAYSSHOWDISABLEDENTRIES );
3176 
3177     aModifyCommandButton.SetPopupMenu( pEntry );
3178     aModifyCommandButton.SetSelectHdl(
3179         LINK( this, SvxToolbarConfigPage, EntrySelectHdl ) );
3180 
3181     // default toolbar to select is standardbar unless a different one
3182     // has been passed in
3183     m_aURLToSelect = OUString::createFromAscii( ITEM_TOOLBAR_URL );
3184     m_aURLToSelect += OUString::createFromAscii( "standardbar" );
3185 
3186     const SfxPoolItem* pItem =
3187         rSet.GetItem( rSet.GetPool()->GetWhich( SID_CONFIG ) );
3188 
3189     if ( pItem )
3190     {
3191         OUString text = ((const SfxStringItem*)pItem)->GetValue();
3192         if (text.indexOf(OUString::createFromAscii(ITEM_TOOLBAR_URL)) == 0)
3193         {
3194             m_aURLToSelect = text.copy( 0 );
3195         }
3196     }
3197 
3198     long nTxtW = aTopLevelLabel.GetCtrlTextWidth( aTopLevelLabel.GetText() );
3199     long nCtrlW = aTopLevelLabel.GetSizePixel().Width();
3200     if ( nTxtW >= nCtrlW )
3201     {
3202         long nDelta = Max( (long)10, nTxtW - nCtrlW );
3203         Size aNewSz = aTopLevelLabel.GetSizePixel();
3204         aNewSz.Width() += nDelta;
3205         aTopLevelLabel.SetSizePixel( aNewSz );
3206         aNewSz = aTopLevelListBox.GetSizePixel();
3207         aNewSz.Width() -= nDelta;
3208         Point aNewPt = aTopLevelListBox.GetPosPixel();
3209         aNewPt.X() += nDelta;
3210         aTopLevelListBox.SetPosSizePixel( aNewPt, aNewSz );
3211     }
3212 }
3213 
3214 SvxToolbarConfigPage::~SvxToolbarConfigPage()
3215 {
3216     for ( sal_uInt16 i = 0 ; i < aSaveInListBox.GetEntryCount(); i++ )
3217     {
3218         ToolbarSaveInData* pData =
3219             (ToolbarSaveInData*) aSaveInListBox.GetEntryData( i );
3220 
3221         delete pData;
3222     }
3223 
3224     if ( pSelectorDlg != NULL )
3225     {
3226         delete pSelectorDlg;
3227     }
3228 
3229 
3230     delete aContentsListBox;
3231 }
3232 
3233 void SvxToolbarConfigPage::DeleteSelectedTopLevel()
3234 {
3235     sal_uInt16 nSelectionPos = aTopLevelListBox.GetSelectEntryPos();
3236     ToolbarSaveInData* pSaveInData = (ToolbarSaveInData*) GetSaveInData();
3237     pSaveInData->RemoveToolbar( GetTopLevelSelection() );
3238 
3239     if ( aTopLevelListBox.GetEntryCount() > 1 )
3240     {
3241         // select next entry after the one being deleted
3242         // selection position is indexed from 0 so need to
3243         // subtract one from the entry count
3244         if ( nSelectionPos != aTopLevelListBox.GetEntryCount() - 1 )
3245         {
3246             aTopLevelListBox.SelectEntryPos( nSelectionPos + 1, sal_True );
3247         }
3248         else
3249         {
3250             aTopLevelListBox.SelectEntryPos( nSelectionPos - 1, sal_True );
3251         }
3252         aTopLevelListBox.GetSelectHdl().Call( this );
3253 
3254         // and now remove the entry
3255         aTopLevelListBox.RemoveEntry( nSelectionPos );
3256     }
3257     else
3258     {
3259         ReloadTopLevelListBox();
3260     }
3261 }
3262 
3263 bool SvxToolbarConfigPage::DeleteSelectedContent()
3264 {
3265     SvLBoxEntry *pActEntry = aContentsListBox->FirstSelected();
3266 
3267     if ( pActEntry != NULL )
3268     {
3269         // get currently selected entry
3270         SvxConfigEntry* pEntry =
3271             (SvxConfigEntry*) pActEntry->GetUserData();
3272 
3273         SvxConfigEntry* pToolbar = GetTopLevelSelection();
3274 
3275         // remove entry from the list for this toolbar
3276         RemoveEntry( pToolbar->GetEntries(), pEntry );
3277 
3278         // remove toolbar entry from UI
3279         aContentsListBox->GetModel()->Remove( pActEntry );
3280 
3281         // delete data for toolbar entry
3282         delete pEntry;
3283 
3284         (( ToolbarSaveInData* ) GetSaveInData())->ApplyToolbar( pToolbar );
3285         UpdateButtonStates();
3286 
3287         // if this is the last entry in the toolbar and it is a user
3288         // defined toolbar pop up a dialog asking the user if they
3289         // want to delete the toolbar
3290         if ( aContentsListBox->GetEntryCount() == 0 &&
3291              GetTopLevelSelection()->IsDeletable() )
3292         {
3293             QueryBox qbox( this,
3294                 CUI_RES( QBX_CONFIRM_DELETE_TOOLBAR ) );
3295 
3296             if ( qbox.Execute() == RET_YES )
3297             {
3298                 DeleteSelectedTopLevel();
3299             }
3300         }
3301 
3302         return sal_True;
3303     }
3304 
3305     return sal_False;
3306 }
3307 
3308 IMPL_LINK( SvxToolbarConfigPage, MoveHdl, Button *, pButton )
3309 {
3310     MoveEntry( pButton == &aMoveUpButton );
3311     return 0;
3312 }
3313 
3314 void SvxToolbarConfigPage::MoveEntry( bool bMoveUp )
3315 {
3316     SvxConfigPage::MoveEntry( bMoveUp );
3317 
3318     // Apply change to currently selected toolbar
3319     SvxConfigEntry* pToolbar = GetTopLevelSelection();
3320     if ( pToolbar )
3321         ((ToolbarSaveInData*)GetSaveInData())->ApplyToolbar( pToolbar );
3322     else
3323     {
3324         DBG_ERRORFILE( "SvxToolbarConfigPage::MoveEntry(): no entry" );
3325         UpdateButtonStates();
3326     }
3327 }
3328 
3329 IMPL_LINK( SvxToolbarConfigPage, ToolbarSelectHdl, MenuButton *, pButton )
3330 {
3331     sal_uInt16 nSelectionPos = aTopLevelListBox.GetSelectEntryPos();
3332 
3333     SvxConfigEntry* pToolbar =
3334         (SvxConfigEntry*)aTopLevelListBox.GetEntryData( nSelectionPos );
3335 
3336     ToolbarSaveInData* pSaveInData = (ToolbarSaveInData*) GetSaveInData();
3337 
3338     switch( pButton->GetCurItemId() )
3339     {
3340         case ID_DELETE:
3341         {
3342             DeleteSelectedTopLevel();
3343             UpdateButtonStates();
3344             break;
3345         }
3346         case ID_RENAME:
3347         {
3348             String aNewName( stripHotKey( pToolbar->GetName() ) );
3349             String aDesc = CUI_RESSSTR( RID_SVXSTR_LABEL_NEW_NAME );
3350 
3351             SvxNameDialog* pNameDialog = new SvxNameDialog( this, aNewName, aDesc );
3352             pNameDialog->SetHelpId( HID_SVX_CONFIG_RENAME_TOOLBAR );
3353             pNameDialog->SetText( CUI_RESSTR( RID_SVXSTR_RENAME_TOOLBAR ) );
3354 
3355             bool ret = pNameDialog->Execute();
3356 
3357             if ( ret == RET_OK )
3358             {
3359                 pNameDialog->GetName(aNewName);
3360 
3361                 pToolbar->SetName( aNewName );
3362                 pSaveInData->ApplyToolbar( pToolbar );
3363 
3364                 // have to use remove and insert to change the name
3365                 aTopLevelListBox.RemoveEntry( nSelectionPos );
3366                 nSelectionPos =
3367                     aTopLevelListBox.InsertEntry( aNewName, nSelectionPos );
3368                 aTopLevelListBox.SetEntryData( nSelectionPos, pToolbar );
3369                 aTopLevelListBox.SelectEntryPos( nSelectionPos );
3370             }
3371 
3372             delete pNameDialog;
3373 
3374             break;
3375         }
3376         case ID_DEFAULT_STYLE:
3377         {
3378             QueryBox qbox( this,
3379                 CUI_RES( QBX_CONFIRM_RESTORE_DEFAULT ) );
3380 
3381             if ( qbox.Execute() == RET_YES )
3382             {
3383                 ToolbarSaveInData* pSaveInData_ =
3384                     (ToolbarSaveInData*) GetSaveInData();
3385 
3386                 pSaveInData_->RestoreToolbar( pToolbar );
3387 
3388                 aTopLevelListBox.GetSelectHdl().Call( this );
3389             }
3390 
3391             break;
3392         }
3393         case ID_ICONS_ONLY:
3394         {
3395             pToolbar->SetStyle( 0 );
3396             pSaveInData->SetSystemStyle( m_xFrame, pToolbar->GetCommand(), 0 );
3397 
3398             aTopLevelListBox.GetSelectHdl().Call( this );
3399 
3400             break;
3401         }
3402         case ID_TEXT_ONLY:
3403         {
3404             pToolbar->SetStyle( 1 );
3405             pSaveInData->SetSystemStyle( m_xFrame, pToolbar->GetCommand(), 1 );
3406 
3407             aTopLevelListBox.GetSelectHdl().Call( this );
3408 
3409             break;
3410         }
3411         case ID_ICONS_AND_TEXT:
3412         {
3413             pToolbar->SetStyle( 2 );
3414             pSaveInData->SetSystemStyle( m_xFrame, pToolbar->GetCommand(), 2 );
3415 
3416             aTopLevelListBox.GetSelectHdl().Call( this );
3417 
3418             break;
3419         }
3420     }
3421     return 1;
3422 }
3423 
3424 IMPL_LINK( SvxToolbarConfigPage, EntrySelectHdl, MenuButton *, pButton )
3425 {
3426     bool bNeedsApply = sal_False;
3427 
3428     // get currently selected toolbar
3429     SvxConfigEntry* pToolbar = GetTopLevelSelection();
3430 
3431     switch( pButton->GetCurItemId() )
3432     {
3433         case ID_RENAME:
3434         {
3435             SvLBoxEntry* pActEntry = aContentsListBox->GetCurEntry();
3436             SvxConfigEntry* pEntry =
3437                 (SvxConfigEntry*) pActEntry->GetUserData();
3438 
3439             String aNewName( stripHotKey( pEntry->GetName() ) );
3440             String aDesc = CUI_RESSSTR( RID_SVXSTR_LABEL_NEW_NAME );
3441 
3442             SvxNameDialog* pNameDialog = new SvxNameDialog( this, aNewName, aDesc );
3443             pNameDialog->SetHelpId( HID_SVX_CONFIG_RENAME_TOOLBAR_ITEM );
3444             pNameDialog->SetText( CUI_RESSTR( RID_SVXSTR_RENAME_TOOLBAR ) );
3445 
3446             bool ret = pNameDialog->Execute();
3447 
3448             if ( ret == RET_OK ) {
3449                 pNameDialog->GetName(aNewName);
3450 
3451                 pEntry->SetName( aNewName );
3452                 aContentsListBox->SetEntryText( pActEntry, aNewName );
3453 
3454                 bNeedsApply = sal_True;
3455             }
3456 
3457             delete pNameDialog;
3458             break;
3459         }
3460         case ID_DEFAULT_COMMAND:
3461         {
3462             SvLBoxEntry* pActEntry = aContentsListBox->GetCurEntry();
3463             SvxConfigEntry* pEntry =
3464                 (SvxConfigEntry*) pActEntry->GetUserData();
3465 
3466             sal_uInt16 nSelectionPos = 0;
3467 
3468             // find position of entry within the list
3469             for ( sal_uInt16 i = 0; i < aContentsListBox->GetEntryCount(); i++ )
3470             {
3471                 if ( aContentsListBox->GetEntry( 0, i ) == pActEntry )
3472                 {
3473                     nSelectionPos = i;
3474                     break;
3475                 }
3476             }
3477 
3478             ToolbarSaveInData* pSaveInData =
3479                 (ToolbarSaveInData*) GetSaveInData();
3480 
3481             OUString aSystemName =
3482                 pSaveInData->GetSystemUIName( pEntry->GetCommand() );
3483 
3484             if ( !pEntry->GetName().equals( aSystemName ) )
3485             {
3486                 pEntry->SetName( aSystemName );
3487                 aContentsListBox->SetEntryText(
3488                     pActEntry, stripHotKey( aSystemName ) );
3489                 bNeedsApply = sal_True;
3490             }
3491 
3492             uno::Sequence< OUString > aURLSeq( 1 );
3493             aURLSeq[ 0 ] = pEntry->GetCommand();
3494 
3495             try
3496             {
3497                 GetSaveInData()->GetImageManager()->removeImages(
3498                     GetImageType(), aURLSeq );
3499 
3500                 // reset backup in entry
3501                 pEntry->SetBackupGraphic(
3502                     uno::Reference< graphic::XGraphic >() );
3503 
3504                 GetSaveInData()->PersistChanges(
3505                     GetSaveInData()->GetImageManager() );
3506 
3507                 aContentsListBox->GetModel()->Remove( pActEntry );
3508 
3509                 SvLBoxEntry* pNewLBEntry =
3510                     InsertEntryIntoUI( pEntry, nSelectionPos );
3511 
3512                 aContentsListBox->SetCheckButtonState( pNewLBEntry,
3513                     pEntry->IsVisible() ?
3514                         SV_BUTTON_CHECKED : SV_BUTTON_UNCHECKED );
3515 
3516                 aContentsListBox->Select( pNewLBEntry );
3517                 aContentsListBox->MakeVisible( pNewLBEntry );
3518 
3519                 bNeedsApply = sal_True;
3520             }
3521             catch ( uno::Exception& )
3522             {
3523                 OSL_TRACE("Error restoring image");
3524             }
3525             break;
3526         }
3527         case ID_BEGIN_GROUP:
3528         {
3529             SvxConfigEntry* pNewEntryData = new SvxConfigEntry;
3530             pNewEntryData->SetUserDefined( sal_True );
3531 
3532             SvLBoxEntry* pNewLBEntry = InsertEntry( pNewEntryData );
3533 
3534             aContentsListBox->SetCheckButtonState(
3535                 pNewLBEntry, SV_BUTTON_TRISTATE );
3536 
3537             bNeedsApply = sal_True;
3538             break;
3539         }
3540         case ID_DELETE:
3541         {
3542             DeleteSelectedContent();
3543             break;
3544         }
3545         case ID_ICON_ONLY:
3546         {
3547             break;
3548         }
3549         case ID_TEXT_ONLY:
3550         {
3551             break;
3552         }
3553         case ID_ICON_AND_TEXT:
3554         {
3555             break;
3556         }
3557         case ID_CHANGE_SYMBOL:
3558         {
3559             SvLBoxEntry* pActEntry = aContentsListBox->GetCurEntry();
3560             SvxConfigEntry* pEntry =
3561                 (SvxConfigEntry*) pActEntry->GetUserData();
3562 
3563             sal_uInt16 nSelectionPos = 0;
3564 
3565             // find position of entry within the list
3566             for ( sal_uInt16 i = 0; i < aContentsListBox->GetEntryCount(); i++ )
3567             {
3568                 if ( aContentsListBox->GetEntry( 0, i ) == pActEntry )
3569                 {
3570                     nSelectionPos = i;
3571                     break;
3572                 }
3573             }
3574 
3575             SvxIconSelectorDialog* pIconDialog =
3576                 new SvxIconSelectorDialog( 0,
3577                     GetSaveInData()->GetImageManager(),
3578                     GetSaveInData()->GetParentImageManager() );
3579 
3580             bool ret = pIconDialog->Execute();
3581 
3582             if ( ret == RET_OK )
3583             {
3584                 uno::Reference< graphic::XGraphic > newgraphic =
3585                     pIconDialog->GetSelectedIcon();
3586 
3587                 if ( newgraphic.is() )
3588                 {
3589                     uno::Sequence< uno::Reference< graphic::XGraphic > >
3590                         aGraphicSeq( 1 );
3591 
3592                     uno::Sequence< OUString > aURLSeq( 1 );
3593                     aURLSeq[ 0 ] = pEntry->GetCommand();
3594 
3595                     if ( !pEntry->GetBackupGraphic().is() )
3596                     {
3597                         uno::Reference< graphic::XGraphic > backup;
3598                         backup = GetGraphic(
3599                             GetSaveInData()->GetImageManager(), aURLSeq[ 0 ] );
3600 
3601                         if ( backup.is() )
3602                         {
3603                             pEntry->SetBackupGraphic( backup );
3604                         }
3605                     }
3606 
3607                     aGraphicSeq[ 0 ] = newgraphic;
3608                     try
3609                     {
3610                         GetSaveInData()->GetImageManager()->replaceImages(
3611                             GetImageType(), aURLSeq, aGraphicSeq );
3612 
3613                         Image aImage( newgraphic );
3614 
3615                         aContentsListBox->GetModel()->Remove( pActEntry );
3616                         SvLBoxEntry* pNewLBEntry =
3617                             InsertEntryIntoUI( pEntry, nSelectionPos );
3618 
3619                         aContentsListBox->SetCheckButtonState( pNewLBEntry,
3620                             pEntry->IsVisible() ?
3621                                 SV_BUTTON_CHECKED : SV_BUTTON_UNCHECKED );
3622 
3623                         aContentsListBox->Select( pNewLBEntry );
3624                         aContentsListBox->MakeVisible( pNewLBEntry );
3625 
3626                         GetSaveInData()->PersistChanges(
3627                             GetSaveInData()->GetImageManager() );
3628                     }
3629                     catch ( uno::Exception& )
3630                     {
3631                         OSL_TRACE("Error replacing image");
3632                     }
3633                 }
3634             }
3635 
3636             delete pIconDialog;
3637 
3638             break;
3639         }
3640         case ID_RESET_SYMBOL:
3641         {
3642             SvLBoxEntry* pActEntry = aContentsListBox->GetCurEntry();
3643             SvxConfigEntry* pEntry =
3644                 (SvxConfigEntry*) pActEntry->GetUserData();
3645 
3646             sal_uInt16 nSelectionPos = 0;
3647 
3648             // find position of entry within the list
3649             for ( sal_uInt16 i = 0; i < aContentsListBox->GetEntryCount(); i++ )
3650             {
3651                 if ( aContentsListBox->GetEntry( 0, i ) == pActEntry )
3652                 {
3653                     nSelectionPos = i;
3654                     break;
3655                 }
3656             }
3657 
3658             uno::Reference< graphic::XGraphic > backup =
3659                 pEntry->GetBackupGraphic();
3660 
3661             uno::Sequence< uno::Reference< graphic::XGraphic > >
3662                 aGraphicSeq( 1 );
3663             aGraphicSeq[ 0 ] = backup;
3664 
3665             uno::Sequence< OUString > aURLSeq( 1 );
3666             aURLSeq[ 0 ] = pEntry->GetCommand();
3667 
3668             try
3669             {
3670                 GetSaveInData()->GetImageManager()->replaceImages(
3671                     GetImageType(), aURLSeq, aGraphicSeq );
3672 
3673                 Image aImage( backup );
3674                 aContentsListBox->GetModel()->Remove( pActEntry );
3675 
3676                 SvLBoxEntry* pNewLBEntry =
3677                     InsertEntryIntoUI( pEntry, nSelectionPos );
3678 
3679                 aContentsListBox->SetCheckButtonState( pNewLBEntry,
3680                     pEntry->IsVisible() ?
3681                         SV_BUTTON_CHECKED : SV_BUTTON_UNCHECKED );
3682 
3683                 aContentsListBox->Select( pNewLBEntry );
3684                 aContentsListBox->MakeVisible( pNewLBEntry );
3685 
3686                 // reset backup in entry
3687                 pEntry->SetBackupGraphic(
3688                     uno::Reference< graphic::XGraphic >() );
3689 
3690                 GetSaveInData()->PersistChanges(
3691                     GetSaveInData()->GetImageManager() );
3692             }
3693             catch ( uno::Exception& )
3694             {
3695                 OSL_TRACE("Error resetting image");
3696             }
3697             break;
3698         }
3699     }
3700 
3701     if ( bNeedsApply == sal_True )
3702     {
3703         (( ToolbarSaveInData* ) GetSaveInData())->ApplyToolbar( pToolbar );
3704         UpdateButtonStates();
3705     }
3706 
3707     return 1;
3708 }
3709 
3710 void SvxToolbarConfigPage::Init()
3711 {
3712     // ensure that the UI is cleared before populating it
3713     aTopLevelListBox.Clear();
3714     aContentsListBox->Clear();
3715 
3716     ReloadTopLevelListBox();
3717 
3718     sal_uInt16 nPos = 0;
3719     if ( m_aURLToSelect.getLength() != 0 )
3720     {
3721         for ( sal_uInt16 i = 0 ; i < aTopLevelListBox.GetEntryCount(); i++ )
3722         {
3723             SvxConfigEntry* pData =
3724                 (SvxConfigEntry*) aTopLevelListBox.GetEntryData( i );
3725 
3726             if ( pData->GetCommand().equals( m_aURLToSelect ) )
3727             {
3728                 nPos = i;
3729                 break;
3730             }
3731         }
3732 
3733         // in future select the default toolbar: Standard
3734         m_aURLToSelect = OUString::createFromAscii( ITEM_TOOLBAR_URL );
3735         m_aURLToSelect += OUString::createFromAscii( "standardbar" );
3736     }
3737 
3738     aTopLevelListBox.SelectEntryPos(nPos, sal_True);
3739     aTopLevelListBox.GetSelectHdl().Call(this);
3740 }
3741 
3742 SaveInData* SvxToolbarConfigPage::CreateSaveInData(
3743     const uno::Reference< css::ui::XUIConfigurationManager >& xCfgMgr,
3744     const uno::Reference< css::ui::XUIConfigurationManager >& xParentCfgMgr,
3745     const OUString& aModuleId,
3746     bool bDocConfig )
3747 {
3748     return static_cast< SaveInData* >(
3749         new ToolbarSaveInData( xCfgMgr, xParentCfgMgr, aModuleId, bDocConfig ));
3750 }
3751 
3752 ToolbarSaveInData::ToolbarSaveInData(
3753     const uno::Reference < css::ui::XUIConfigurationManager >& xCfgMgr,
3754     const uno::Reference < css::ui::XUIConfigurationManager >& xParentCfgMgr,
3755     const OUString& aModuleId,
3756     bool docConfig ) :
3757 
3758     SaveInData              ( xCfgMgr, xParentCfgMgr, aModuleId, docConfig ),
3759     pRootEntry              ( NULL ),
3760     m_aDescriptorContainer  ( RTL_CONSTASCII_USTRINGPARAM( ITEM_DESCRIPTOR_CONTAINER ) )
3761 
3762 {
3763     // Initialize the m_xPersistentWindowState variable which is used
3764     // to get the default properties of system toolbars such as name
3765     uno::Reference< container::XNameAccess > xPWSS(
3766         m_xServiceManager->createInstance(
3767             OUString( RTL_CONSTASCII_USTRINGPARAM(
3768                 "com.sun.star.ui.WindowStateConfiguration" ) ) ),
3769         uno::UNO_QUERY );
3770 
3771     if ( xPWSS.is() )
3772         xPWSS->getByName( aModuleId ) >>= m_xPersistentWindowState;
3773 }
3774 
3775 ToolbarSaveInData::~ToolbarSaveInData()
3776 {
3777     delete pRootEntry;
3778 }
3779 
3780 void ToolbarSaveInData::SetSystemStyle(
3781     uno::Reference< frame::XFrame > xFrame,
3782     const OUString& rResourceURL,
3783     sal_Int32 nStyle )
3784 {
3785     // change the style using the API
3786     SetSystemStyle( rResourceURL, nStyle );
3787 
3788     // this code is a temporary hack as the UI is not updating after
3789     // changing the toolbar style via the API
3790     uno::Reference< css::frame::XLayoutManager > xLayoutManager;
3791     Window *window = NULL;
3792 
3793     uno::Reference< beans::XPropertySet > xPropSet( xFrame, uno::UNO_QUERY );
3794     if ( xPropSet.is() )
3795     {
3796         uno::Any a = xPropSet->getPropertyValue(
3797             OUString( RTL_CONSTASCII_USTRINGPARAM( "LayoutManager" ) ) );
3798         a >>= xLayoutManager;
3799     }
3800 
3801     if ( xLayoutManager.is() )
3802     {
3803         uno::Reference< css::ui::XUIElement > xUIElement =
3804             xLayoutManager->getElement( rResourceURL );
3805 
3806         // check reference before we call getRealInterface. The layout manager
3807         // can only provide references for elements that have been created
3808         // before. It's possible that the current element is not available.
3809         uno::Reference< com::sun::star::awt::XWindow > xWindow;
3810         if ( xUIElement.is() )
3811             xWindow = uno::Reference< com::sun::star::awt::XWindow >(
3812                         xUIElement->getRealInterface(), uno::UNO_QUERY );
3813 
3814         window = VCLUnoHelper::GetWindow( xWindow );
3815     }
3816 
3817     if ( window != NULL && window->GetType() == WINDOW_TOOLBOX )
3818     {
3819         ToolBox* toolbox = (ToolBox*)window;
3820 
3821         if ( nStyle == 0 )
3822         {
3823             toolbox->SetButtonType( BUTTON_SYMBOL );
3824         }
3825         else if ( nStyle == 1 )
3826         {
3827             toolbox->SetButtonType( BUTTON_TEXT );
3828         }
3829         if ( nStyle == 2 )
3830         {
3831             toolbox->SetButtonType( BUTTON_SYMBOLTEXT );
3832         }
3833     }
3834 }
3835 
3836 void ToolbarSaveInData::SetSystemStyle(
3837     const OUString& rResourceURL,
3838     sal_Int32 nStyle )
3839 {
3840     if ( rResourceURL.indexOf( OUString::createFromAscii( "private" ) ) == 0 &&
3841          m_xPersistentWindowState.is() &&
3842          m_xPersistentWindowState->hasByName( rResourceURL ) )
3843     {
3844         try
3845         {
3846             uno::Sequence< beans::PropertyValue > aProps;
3847 
3848             uno::Any a( m_xPersistentWindowState->getByName( rResourceURL ) );
3849 
3850             if ( a >>= aProps )
3851             {
3852                 for ( sal_Int32 i = 0; i < aProps.getLength(); i++ )
3853                 {
3854                     if ( aProps[ i ].Name.equalsAscii( ITEM_DESCRIPTOR_STYLE) )
3855                     {
3856                         aProps[ i ].Value = uno::makeAny( nStyle );
3857                         break;
3858                     }
3859                 }
3860             }
3861 
3862             uno::Reference< container::XNameReplace >
3863                 xNameReplace( m_xPersistentWindowState, uno::UNO_QUERY );
3864 
3865             xNameReplace->replaceByName( rResourceURL, uno::makeAny( aProps ) );
3866         }
3867         catch ( uno::Exception& )
3868         {
3869             // do nothing, a default value is returned
3870             OSL_TRACE("Exception setting toolbar style");
3871         }
3872     }
3873 }
3874 
3875 sal_Int32 ToolbarSaveInData::GetSystemStyle( const OUString& rResourceURL )
3876 {
3877     sal_Int32 result = 0;
3878 
3879     if ( rResourceURL.indexOf( OUString::createFromAscii( "private" ) ) == 0 &&
3880          m_xPersistentWindowState.is() &&
3881          m_xPersistentWindowState->hasByName( rResourceURL ) )
3882     {
3883         try
3884         {
3885             uno::Sequence< beans::PropertyValue > aProps;
3886             uno::Any a( m_xPersistentWindowState->getByName( rResourceURL ) );
3887 
3888             if ( a >>= aProps )
3889             {
3890                 for ( sal_Int32 i = 0; i < aProps.getLength(); i++ )
3891                 {
3892                     if ( aProps[ i ].Name.equalsAscii( ITEM_DESCRIPTOR_STYLE) )
3893                     {
3894                         aProps[i].Value >>= result;
3895                         break;
3896                     }
3897                 }
3898             }
3899         }
3900         catch ( uno::Exception& )
3901         {
3902             // do nothing, a default value is returned
3903         }
3904     }
3905 
3906     return result;
3907 }
3908 
3909 OUString ToolbarSaveInData::GetSystemUIName( const OUString& rResourceURL )
3910 {
3911     OUString result;
3912 
3913     if ( rResourceURL.indexOf( OUString::createFromAscii( "private" ) ) == 0 &&
3914          m_xPersistentWindowState.is() &&
3915          m_xPersistentWindowState->hasByName( rResourceURL ) )
3916     {
3917         try
3918         {
3919             uno::Sequence< beans::PropertyValue > aProps;
3920             uno::Any a( m_xPersistentWindowState->getByName( rResourceURL ) );
3921 
3922             if ( a >>= aProps )
3923             {
3924                 for ( sal_Int32 i = 0; i < aProps.getLength(); i++ )
3925                 {
3926                     if ( aProps[ i ].Name.equalsAscii( ITEM_DESCRIPTOR_UINAME) )
3927                     {
3928                         aProps[ i ].Value >>= result;
3929                     }
3930                 }
3931             }
3932         }
3933         catch ( uno::Exception& )
3934         {
3935             // do nothing, an empty UIName will be returned
3936         }
3937     }
3938 
3939     if ( rResourceURL.indexOf( OUString::createFromAscii( ".uno" ) ) == 0 &&
3940          m_xCommandToLabelMap.is() &&
3941          m_xCommandToLabelMap->hasByName( rResourceURL ) )
3942     {
3943         uno::Any a;
3944         try
3945         {
3946             a = m_xCommandToLabelMap->getByName( rResourceURL );
3947 
3948             uno::Sequence< beans::PropertyValue > aPropSeq;
3949             if ( a >>= aPropSeq )
3950             {
3951                 for ( sal_Int32 i = 0; i < aPropSeq.getLength(); i++ )
3952                 {
3953                     if ( aPropSeq[i].Name.equalsAscii( ITEM_DESCRIPTOR_LABEL ) )
3954                     {
3955                         aPropSeq[i].Value >>= result;
3956                     }
3957                 }
3958             }
3959         }
3960         catch ( uno::Exception& )
3961         {
3962             // not a system command name
3963         }
3964     }
3965 
3966     return result;
3967 }
3968 
3969 bool EntrySort( SvxConfigEntry* a, SvxConfigEntry* b )
3970 {
3971     return a->GetName().compareTo( b->GetName() ) < 0;
3972 }
3973 
3974 SvxEntries* ToolbarSaveInData::GetEntries()
3975 {
3976     typedef ::std::hash_map< ::rtl::OUString,
3977                              bool,
3978                              ::rtl::OUStringHash,
3979                              ::std::equal_to< ::rtl::OUString > > ToolbarInfo;
3980 
3981     ToolbarInfo aToolbarInfo;
3982 
3983     if ( pRootEntry == NULL )
3984     {
3985 
3986         pRootEntry = new SvxConfigEntry(
3987             String::CreateFromAscii("MainToolbars"), String(), sal_True );
3988 
3989         uno::Sequence< uno::Sequence < beans::PropertyValue > > info =
3990             GetConfigManager()->getUIElementsInfo(
3991                 css::ui::UIElementType::TOOLBAR );
3992 
3993         for ( sal_Int32 i = 0; i < info.getLength(); i++ )
3994         {
3995             uno::Sequence< beans::PropertyValue > props = info[ i ];
3996 
3997             OUString url;
3998             OUString systemname;
3999             OUString uiname;
4000 
4001             for ( sal_Int32 j = 0; j < props.getLength(); j++ )
4002             {
4003                 if ( props[ j ].Name.equalsAscii( ITEM_DESCRIPTOR_RESOURCEURL) )
4004                 {
4005                     props[ j ].Value >>= url;
4006                     systemname = url.copy( url.lastIndexOf( '/' ) + 1 );
4007                 }
4008                 else if ( props[ j ].Name.equalsAscii( ITEM_DESCRIPTOR_UINAME) )
4009                 {
4010                     props[ j ].Value >>= uiname;
4011                 }
4012             }
4013 
4014             try
4015             {
4016                 uno::Reference< container::XIndexAccess > xToolbarSettings =
4017                     GetConfigManager()->getSettings( url, sal_False );
4018 
4019                 if ( uiname.getLength() == 0 )
4020                 {
4021                     // try to get the name from m_xPersistentWindowState
4022                     uiname = GetSystemUIName( url );
4023 
4024                     if ( uiname.getLength() == 0 )
4025                     {
4026                         uiname = systemname;
4027                     }
4028                 }
4029 
4030                 SvxConfigEntry* pEntry = new SvxConfigEntry(
4031                     uiname, url, sal_True );
4032 
4033                 pEntry->SetMain( sal_True );
4034                 pEntry->SetStyle( GetSystemStyle( url ) );
4035 
4036 
4037                 // insert into hash_map to filter duplicates from the parent
4038                 aToolbarInfo.insert( ToolbarInfo::value_type( systemname, true ));
4039 
4040                 OUString custom = OUString::createFromAscii(CUSTOM_TOOLBAR_STR);
4041                 if ( systemname.indexOf( custom ) == 0 )
4042                 {
4043                     pEntry->SetUserDefined( sal_True );
4044                 }
4045                 else
4046                 {
4047                     pEntry->SetUserDefined( sal_False );
4048                 }
4049 
4050                 pRootEntry->GetEntries()->push_back( pEntry );
4051 
4052                 LoadToolbar( xToolbarSettings, pEntry );
4053             }
4054             catch ( container::NoSuchElementException& )
4055             {
4056                 // TODO, handle resourceURL with no settings
4057             }
4058         }
4059 
4060         uno::Reference< css::ui::XUIConfigurationManager > xParentCfgMgr = GetParentConfigManager();
4061         if ( xParentCfgMgr.is() )
4062         {
4063             // Retrieve also the parent toolbars to make it possible
4064             // to configure module toolbars and save them into the document
4065             // config manager.
4066             uno::Sequence< uno::Sequence < beans::PropertyValue > > info_ =
4067                 xParentCfgMgr->getUIElementsInfo(
4068                     css::ui::UIElementType::TOOLBAR );
4069 
4070             for ( sal_Int32 i = 0; i < info_.getLength(); i++ )
4071             {
4072                 uno::Sequence< beans::PropertyValue > props = info_[ i ];
4073 
4074                 OUString url;
4075                 OUString systemname;
4076                 OUString uiname;
4077 
4078                 for ( sal_Int32 j = 0; j < props.getLength(); j++ )
4079                 {
4080                     if ( props[ j ].Name.equalsAscii( ITEM_DESCRIPTOR_RESOURCEURL) )
4081                     {
4082                         props[ j ].Value >>= url;
4083                         systemname = url.copy( url.lastIndexOf( '/' ) + 1 );
4084                     }
4085                     else if ( props[ j ].Name.equalsAscii( ITEM_DESCRIPTOR_UINAME) )
4086                     {
4087                         props[ j ].Value >>= uiname;
4088                     }
4089                 }
4090 
4091                 // custom toolbars of the parent are not visible in the document layer
4092                 OUString custom = OUString::createFromAscii(CUSTOM_TOOLBAR_STR);
4093                 if ( systemname.indexOf( custom ) == 0 )
4094                     continue;
4095 
4096                 // check if toolbar is already in the document layer
4097                 ToolbarInfo::const_iterator pIter = aToolbarInfo.find( systemname );
4098                 if ( pIter == aToolbarInfo.end() )
4099                 {
4100                     aToolbarInfo.insert( ToolbarInfo::value_type( systemname, true ));
4101 
4102                     try
4103                     {
4104                         uno::Reference< container::XIndexAccess > xToolbarSettings =
4105                             xParentCfgMgr->getSettings( url, sal_False );
4106 
4107                         if ( uiname.getLength() == 0 )
4108                         {
4109                             // try to get the name from m_xPersistentWindowState
4110                             uiname = GetSystemUIName( url );
4111 
4112                             if ( uiname.getLength() == 0 )
4113                             {
4114                                 uiname = systemname;
4115                             }
4116                         }
4117 
4118                         SvxConfigEntry* pEntry = new SvxConfigEntry(
4119                             uiname, url, sal_True, sal_True );
4120 
4121                         pEntry->SetMain( sal_True );
4122                         pEntry->SetStyle( GetSystemStyle( url ) );
4123 
4124                         if ( systemname.indexOf( custom ) == 0 )
4125                         {
4126                             pEntry->SetUserDefined( sal_True );
4127                         }
4128                         else
4129                         {
4130                             pEntry->SetUserDefined( sal_False );
4131                         }
4132 
4133                         pRootEntry->GetEntries()->push_back( pEntry );
4134 
4135                         LoadToolbar( xToolbarSettings, pEntry );
4136                     }
4137                     catch ( container::NoSuchElementException& )
4138                     {
4139                         // TODO, handle resourceURL with no settings
4140                     }
4141                 }
4142             }
4143         }
4144 
4145         std::sort( GetEntries()->begin(), GetEntries()->end(), EntrySort );
4146     }
4147 
4148     return pRootEntry->GetEntries();
4149 }
4150 
4151 void
4152 ToolbarSaveInData::SetEntries( SvxEntries* pNewEntries )
4153 {
4154     // delete old menu hierarchy first
4155     if ( pRootEntry != NULL && pRootEntry->GetEntries() != NULL )
4156     {
4157         delete pRootEntry->GetEntries();
4158     }
4159 
4160     // now set new menu hierarchy
4161     pRootEntry->SetEntries( pNewEntries );
4162 }
4163 
4164 bool
4165 ToolbarSaveInData::HasURL( const OUString& rURL )
4166 {
4167     SvxEntries::const_iterator iter = GetEntries()->begin();
4168     SvxEntries::const_iterator end = GetEntries()->end();
4169 
4170     while ( iter != end )
4171     {
4172         SvxConfigEntry* pEntry = *iter;
4173 
4174         if ( pEntry->GetCommand().equals( rURL ) )
4175         {
4176             if ( pEntry->IsParentData() )
4177                 return sal_False;
4178             else
4179                 return sal_True;
4180         }
4181 
4182         iter++;
4183     }
4184     return sal_False;
4185 }
4186 
4187 bool ToolbarSaveInData::HasSettings()
4188 {
4189     // return true if there is at least one toolbar entry
4190     if ( GetEntries()->size() > 0 )
4191     {
4192         return sal_True;
4193     }
4194     return sal_False;
4195 }
4196 
4197 void ToolbarSaveInData::Reset()
4198 {
4199     SvxEntries::const_iterator toolbars = GetEntries()->begin();
4200     SvxEntries::const_iterator end = GetEntries()->end();
4201 
4202     // reset each toolbar by calling removeSettings for it's toolbar URL
4203     for ( ; toolbars != end; toolbars++ )
4204     {
4205         SvxConfigEntry* pToolbar = *toolbars;
4206 
4207         try
4208         {
4209             OUString url = pToolbar->GetCommand();
4210             GetConfigManager()->removeSettings( url );
4211         }
4212         catch ( uno::Exception& )
4213         {
4214             // error occured removing the settings
4215             // TODO - add error dialog in future?
4216         }
4217     }
4218 
4219     // persist changes to toolbar storage
4220     PersistChanges( GetConfigManager() );
4221 
4222     // now delete the root SvxConfigEntry the next call to GetEntries()
4223     // causes it to be reinitialised
4224     delete pRootEntry;
4225     pRootEntry = NULL;
4226 
4227     // reset all icons to default
4228     try
4229     {
4230         GetImageManager()->reset();
4231         PersistChanges( GetImageManager() );
4232     }
4233     catch ( uno::Exception& )
4234     {
4235         OSL_TRACE("Error resetting all icons when resetting toolbars");
4236     }
4237 }
4238 
4239 bool ToolbarSaveInData::Apply()
4240 {
4241     // toolbar changes are instantly applied
4242     return sal_False;
4243 }
4244 
4245 void ToolbarSaveInData::ApplyToolbar(
4246     uno::Reference< container::XIndexContainer >& rToolbarBar,
4247     uno::Reference< lang::XSingleComponentFactory >& rFactory,
4248     SvxConfigEntry* pToolbarData )
4249 {
4250     SvxEntries::const_iterator iter = pToolbarData->GetEntries()->begin();
4251     SvxEntries::const_iterator end = pToolbarData->GetEntries()->end();
4252 
4253     for ( ; iter != end; iter++ )
4254     {
4255         SvxConfigEntry* pEntry = *iter;
4256 
4257         if ( pEntry->IsPopup() )
4258         {
4259             uno::Sequence< beans::PropertyValue > aPropValueSeq =
4260                 ConvertToolbarEntry( m_xCommandToLabelMap, pEntry );
4261 
4262             uno::Reference< container::XIndexContainer > xSubMenuBar(
4263                 rFactory->createInstanceWithContext( m_xComponentContext ),
4264                     uno::UNO_QUERY );
4265 
4266             sal_Int32 nIndex = aPropValueSeq.getLength();
4267             aPropValueSeq.realloc( nIndex + 1 );
4268             aPropValueSeq[nIndex].Name = m_aDescriptorContainer;
4269             aPropValueSeq[nIndex].Value <<= xSubMenuBar;
4270             rToolbarBar->insertByIndex(
4271                 rToolbarBar->getCount(), uno::makeAny( aPropValueSeq ));
4272 
4273             ApplyToolbar( xSubMenuBar, rFactory, pEntry );
4274         }
4275         else if ( pEntry->IsSeparator() )
4276         {
4277             rToolbarBar->insertByIndex(
4278                 rToolbarBar->getCount(), uno::makeAny( m_aSeparatorSeq ));
4279         }
4280         else
4281         {
4282             uno::Sequence< beans::PropertyValue > aPropValueSeq =
4283                 ConvertToolbarEntry( m_xCommandToLabelMap, pEntry );
4284 
4285             rToolbarBar->insertByIndex(
4286                 rToolbarBar->getCount(), uno::makeAny( aPropValueSeq ));
4287         }
4288     }
4289 }
4290 
4291 void ToolbarSaveInData::ApplyToolbar( SvxConfigEntry* pToolbar )
4292 {
4293     // Apply new toolbar structure to our settings container
4294     uno::Reference< container::XIndexAccess > xSettings(
4295         GetConfigManager()->createSettings(), uno::UNO_QUERY );
4296 
4297     uno::Reference< container::XIndexContainer > xIndexContainer (
4298         xSettings, uno::UNO_QUERY );
4299 
4300     uno::Reference< lang::XSingleComponentFactory > xFactory (
4301         xSettings, uno::UNO_QUERY );
4302 
4303     ApplyToolbar( xIndexContainer, xFactory, pToolbar );
4304 
4305     uno::Reference< beans::XPropertySet > xProps(
4306         xSettings, uno::UNO_QUERY );
4307 
4308     if ( pToolbar->IsUserDefined() )
4309     {
4310         xProps->setPropertyValue(
4311             OUString::createFromAscii( ITEM_DESCRIPTOR_UINAME ),
4312             uno::makeAny( OUString( pToolbar->GetName() ) ) );
4313     }
4314 
4315     try
4316     {
4317         if ( GetConfigManager()->hasSettings( pToolbar->GetCommand() ) )
4318         {
4319             GetConfigManager()->replaceSettings(
4320                 pToolbar->GetCommand(), xSettings );
4321         }
4322         else
4323         {
4324             GetConfigManager()->insertSettings(
4325                 pToolbar->GetCommand(), xSettings );
4326             if ( pToolbar->IsParentData() )
4327                 pToolbar->SetParentData( false );
4328         }
4329     }
4330     catch ( container::NoSuchElementException& )
4331     {
4332         OSL_TRACE("caught container::NoSuchElementException saving settings");
4333     }
4334     catch ( com::sun::star::io::IOException& )
4335     {
4336         OSL_TRACE("caught IOException saving settings");
4337     }
4338     catch ( com::sun::star::uno::Exception& )
4339     {
4340         OSL_TRACE("caught some other exception saving settings");
4341     }
4342 
4343     PersistChanges( GetConfigManager() );
4344 }
4345 
4346 void ToolbarSaveInData::CreateToolbar( SvxConfigEntry* pToolbar )
4347 {
4348     // show the new toolbar in the UI also
4349     uno::Reference< container::XIndexAccess >
4350         xSettings( GetConfigManager()->createSettings(), uno::UNO_QUERY );
4351 
4352     uno::Reference< container::XIndexContainer >
4353         xIndexContainer ( xSettings, uno::UNO_QUERY );
4354 
4355     uno::Reference< beans::XPropertySet >
4356         xPropertySet( xSettings, uno::UNO_QUERY );
4357 
4358     xPropertySet->setPropertyValue(
4359         OUString::createFromAscii( ITEM_DESCRIPTOR_UINAME ),
4360             uno::makeAny( pToolbar->GetName() ) );
4361 
4362     try
4363     {
4364         GetConfigManager()->insertSettings( pToolbar->GetCommand(), xSettings );
4365     }
4366     catch ( container::ElementExistException& )
4367     {
4368         OSL_TRACE("caught ElementExistsException saving settings");
4369     }
4370     catch ( com::sun::star::lang::IllegalArgumentException& )
4371     {
4372         OSL_TRACE("caught IOException saving settings");
4373     }
4374     catch ( com::sun::star::lang::IllegalAccessException& )
4375     {
4376         OSL_TRACE("caught IOException saving settings");
4377     }
4378     catch ( com::sun::star::uno::Exception& )
4379     {
4380         OSL_TRACE("caught some other exception saving settings");
4381     }
4382 
4383     GetEntries()->push_back( pToolbar );
4384 
4385     PersistChanges( GetConfigManager() );
4386 }
4387 
4388 void ToolbarSaveInData::RemoveToolbar( SvxConfigEntry* pToolbar )
4389 {
4390     try
4391     {
4392         OUString url = pToolbar->GetCommand();
4393         GetConfigManager()->removeSettings( url );
4394         RemoveEntry( GetEntries(), pToolbar );
4395         delete pToolbar;
4396 
4397         PersistChanges( GetConfigManager() );
4398 
4399         // remove the persistent window state data
4400         css::uno::Reference< css::container::XNameContainer > xNameContainer(
4401             m_xPersistentWindowState, css::uno::UNO_QUERY_THROW );
4402 
4403         xNameContainer->removeByName( url );
4404     }
4405     catch ( uno::Exception& )
4406     {
4407         // error occured removing the settings
4408     }
4409 }
4410 
4411 void ToolbarSaveInData::RestoreToolbar( SvxConfigEntry* pToolbar )
4412 {
4413     OUString url = pToolbar->GetCommand();
4414 
4415     // Restore of toolbar is done by removing it from
4416     // it's configuration manager and then getting it again
4417     bool bParentToolbar = pToolbar->IsParentData();
4418 
4419     // Cannot restore parent toolbar
4420     if ( bParentToolbar )
4421         return;
4422 
4423     try
4424     {
4425         GetConfigManager()->removeSettings( url );
4426         pToolbar->GetEntries()->clear();
4427         PersistChanges( GetConfigManager() );
4428     }
4429     catch ( uno::Exception& )
4430     {
4431         // if an error occurs removing the settings then just return
4432         return;
4433     }
4434 
4435     // Now reload the toolbar settings
4436     try
4437     {
4438         uno::Reference< container::XIndexAccess > xToolbarSettings;
4439         if ( IsDocConfig() )
4440         {
4441             xToolbarSettings = GetParentConfigManager()->getSettings( url, sal_False );
4442             pToolbar->SetParentData( true );
4443         }
4444         else
4445             xToolbarSettings = GetConfigManager()->getSettings( url, sal_False );
4446 
4447         LoadToolbar( xToolbarSettings, pToolbar );
4448 
4449         // After reloading, ensure that the icon is reset of each entry
4450         // in the toolbar
4451         SvxEntries::const_iterator iter = pToolbar->GetEntries()->begin();
4452         uno::Sequence< OUString > aURLSeq( 1 );
4453         for ( ; iter != pToolbar->GetEntries()->end(); iter++ )
4454         {
4455             SvxConfigEntry* pEntry = *iter;
4456             aURLSeq[ 0 ] = pEntry->GetCommand();
4457 
4458             try
4459             {
4460                 GetImageManager()->removeImages( GetImageType(), aURLSeq );
4461             }
4462             catch ( uno::Exception& )
4463             {
4464                 OSL_TRACE("Error restoring icon when resetting toolbar");
4465             }
4466         }
4467         PersistChanges( GetImageManager() );
4468     }
4469     catch ( container::NoSuchElementException& )
4470     {
4471         // cannot find the resource URL after removing it
4472         // so no entry will appear in the toolbar list
4473     }
4474 }
4475 
4476 bool ToolbarSaveInData::LoadToolbar(
4477     const uno::Reference< container::XIndexAccess >& xToolbarSettings,
4478     SvxConfigEntry* pParentData )
4479 {
4480     SvxEntries*         pEntries            = pParentData->GetEntries();
4481 
4482     for ( sal_Int32 nIndex = 0; nIndex < xToolbarSettings->getCount(); nIndex++ )
4483     {
4484         uno::Reference< container::XIndexAccess >   xSubMenu;
4485         OUString                aCommandURL;
4486         OUString                aLabel;
4487         bool                    bIsUserDefined = sal_True;
4488         sal_Bool                bIsVisible;
4489         sal_Int32               nStyle;
4490 
4491         sal_uInt16 nType( css::ui::ItemType::DEFAULT );
4492 
4493         bool bItem = GetToolbarItemData( xToolbarSettings, nIndex, aCommandURL,
4494             aLabel, nType, bIsVisible, nStyle, xSubMenu );
4495 
4496         if ( bItem )
4497         {
4498             if ( nType == css::ui::ItemType::DEFAULT )
4499             {
4500                 uno::Any a;
4501                 try
4502                 {
4503                     a = m_xCommandToLabelMap->getByName( aCommandURL );
4504                     bIsUserDefined = sal_False;
4505                 }
4506                 catch ( container::NoSuchElementException& )
4507                 {
4508                     bIsUserDefined = sal_True;
4509                 }
4510 
4511                 // If custom label not set retrieve it from the command
4512                 // to info service
4513                 if ( aLabel.equals( OUString() ) )
4514                 {
4515                     uno::Sequence< beans::PropertyValue > aPropSeq;
4516                     if ( a >>= aPropSeq )
4517                     {
4518                         for ( sal_Int32 i = 0; i < aPropSeq.getLength(); i++ )
4519                         {
4520                             if ( aPropSeq[i].Name.equalsAscii( ITEM_DESCRIPTOR_LABEL ) )
4521                             {
4522                                 aPropSeq[i].Value >>= aLabel;
4523                                 break;
4524                             }
4525                         }
4526                     }
4527                 }
4528 
4529                 if ( xSubMenu.is() )
4530                 {
4531                     SvxConfigEntry* pEntry = new SvxConfigEntry(
4532                         aLabel, aCommandURL, sal_True );
4533 
4534                     pEntry->SetUserDefined( bIsUserDefined );
4535                     pEntry->SetVisible( bIsVisible );
4536 
4537                     pEntries->push_back( pEntry );
4538 
4539                     LoadToolbar( xSubMenu, pEntry );
4540                 }
4541                 else
4542                 {
4543                     SvxConfigEntry* pEntry = new SvxConfigEntry(
4544                         aLabel, aCommandURL, sal_False );
4545                     pEntry->SetUserDefined( bIsUserDefined );
4546                     pEntry->SetVisible( bIsVisible );
4547                     pEntry->SetStyle( nStyle );
4548                     pEntries->push_back( pEntry );
4549                 }
4550             }
4551             else
4552             {
4553                 SvxConfigEntry* pEntry = new SvxConfigEntry;
4554                 pEntry->SetUserDefined( bIsUserDefined );
4555                 pEntries->push_back( pEntry );
4556             }
4557         }
4558     }
4559 
4560     return true;
4561 }
4562 
4563 IMPL_LINK( SvxToolbarConfigPage, SelectToolbarEntry, Control *, pBox )
4564 {
4565     (void)pBox;
4566     UpdateButtonStates();
4567     return 1;
4568 }
4569 
4570 void SvxToolbarConfigPage::UpdateButtonStates()
4571 {
4572     PopupMenu* pPopup = aModifyCommandButton.GetPopupMenu();
4573     pPopup->EnableItem( ID_RENAME, sal_False );
4574     pPopup->EnableItem( ID_DELETE, sal_False );
4575     pPopup->EnableItem( ID_BEGIN_GROUP, sal_False );
4576     pPopup->EnableItem( ID_DEFAULT_COMMAND, sal_False );
4577     pPopup->EnableItem( ID_ICON_ONLY, sal_False );
4578     pPopup->EnableItem( ID_ICON_AND_TEXT, sal_False );
4579     pPopup->EnableItem( ID_TEXT_ONLY, sal_False );
4580     pPopup->EnableItem( ID_CHANGE_SYMBOL, sal_False );
4581     pPopup->EnableItem( ID_RESET_SYMBOL, sal_False );
4582 
4583     aDescriptionField.Clear();
4584 
4585     SvLBoxEntry* selection = aContentsListBox->GetCurEntry();
4586     if ( aContentsListBox->GetEntryCount() == 0 || selection == NULL )
4587     {
4588         return;
4589     }
4590 
4591     SvxConfigEntry* pEntryData = (SvxConfigEntry*) selection->GetUserData();
4592     if ( pEntryData->IsSeparator() )
4593         pPopup->EnableItem( ID_DELETE, sal_True );
4594     else
4595     {
4596         pPopup->EnableItem( ID_BEGIN_GROUP, sal_True );
4597         pPopup->EnableItem( ID_DELETE, sal_True );
4598         pPopup->EnableItem( ID_RENAME, sal_True );
4599         pPopup->EnableItem( ID_ICON_ONLY, sal_True );
4600         pPopup->EnableItem( ID_ICON_AND_TEXT, sal_True );
4601         pPopup->EnableItem( ID_TEXT_ONLY, sal_True );
4602         pPopup->EnableItem( ID_CHANGE_SYMBOL, sal_True );
4603 
4604         if ( !pEntryData->IsUserDefined() )
4605             pPopup->EnableItem( ID_DEFAULT_COMMAND, sal_True );
4606 
4607         if ( pEntryData->IsIconModified() )
4608             pPopup->EnableItem( ID_RESET_SYMBOL, sal_True );
4609 
4610         aDescriptionField.SetNewText( pEntryData->GetHelpText() );
4611     }
4612 }
4613 
4614 short SvxToolbarConfigPage::QueryReset()
4615 {
4616     String msg =
4617         String( CUI_RES( RID_SVXSTR_CONFIRM_TOOLBAR_RESET ) );
4618 
4619     String saveInName = aSaveInListBox.GetEntry(
4620         aSaveInListBox.GetSelectEntryPos() );
4621 
4622     OUString label = replaceSaveInName( msg, saveInName );
4623 
4624     QueryBox qbox( this, WB_YES_NO, label );
4625 
4626     return qbox.Execute();
4627 }
4628 
4629 IMPL_LINK( SvxToolbarConfigPage, SelectToolbar, ListBox *, pBox )
4630 {
4631     (void)pBox;
4632 
4633     aContentsListBox->Clear();
4634 
4635     SvxConfigEntry* pToolbar = GetTopLevelSelection();
4636     if ( pToolbar == NULL )
4637     {
4638         aModifyTopLevelButton.Enable( sal_False );
4639         aModifyCommandButton.Enable( sal_False );
4640         aAddCommandsButton.Enable( sal_False );
4641 
4642         return 0;
4643     }
4644 
4645     aModifyTopLevelButton.Enable( sal_True );
4646     aModifyCommandButton.Enable( sal_True );
4647     aAddCommandsButton.Enable( sal_True );
4648 
4649     PopupMenu* pPopup = aModifyTopLevelButton.GetPopupMenu();
4650 
4651     pPopup->EnableItem( ID_DELETE, pToolbar->IsDeletable() );
4652     pPopup->EnableItem( ID_RENAME, pToolbar->IsRenamable() );
4653     pPopup->EnableItem( ID_DEFAULT_STYLE, !pToolbar->IsRenamable() );
4654 
4655     switch( pToolbar->GetStyle() )
4656     {
4657         case 0:
4658         {
4659             pPopup->CheckItem( ID_ICONS_ONLY );
4660             break;
4661         }
4662         case 1:
4663         {
4664             pPopup->CheckItem( ID_TEXT_ONLY );
4665             break;
4666         }
4667         case 2:
4668         {
4669             pPopup->CheckItem( ID_ICONS_AND_TEXT );
4670             break;
4671         }
4672     }
4673 
4674     SvxEntries* pEntries = pToolbar->GetEntries();
4675     SvxEntries::const_iterator iter = pEntries->begin();
4676 
4677     for ( ; iter != pEntries->end(); iter++ )
4678     {
4679         SvxConfigEntry* pEntry = *iter;
4680 
4681         SvLBoxEntry* pNewLBEntry = InsertEntryIntoUI( pEntry );
4682 
4683         if (pEntry->IsBinding())
4684         {
4685             aContentsListBox->SetCheckButtonState( pNewLBEntry,
4686                 pEntry->IsVisible() ? SV_BUTTON_CHECKED : SV_BUTTON_UNCHECKED );
4687         }
4688         else
4689         {
4690             aContentsListBox->SetCheckButtonState(
4691                 pNewLBEntry, SV_BUTTON_TRISTATE );
4692         }
4693     }
4694 
4695     UpdateButtonStates();
4696 
4697     return 0;
4698 }
4699 
4700 IMPL_LINK( SvxToolbarConfigPage, NewToolbarHdl, Button *, pButton )
4701 {
4702     (void)pButton;
4703 
4704     String prefix =
4705         String( CUI_RES( RID_SVXSTR_NEW_TOOLBAR ) );
4706 
4707     OUString aNewName =
4708         generateCustomName( prefix, GetSaveInData()->GetEntries() );
4709 
4710     OUString aNewURL =
4711         generateCustomURL( GetSaveInData()->GetEntries() );
4712 
4713     SvxNewToolbarDialog* pNameDialog = new SvxNewToolbarDialog( 0, aNewName );
4714 
4715     sal_uInt16 nInsertPos;
4716     for ( sal_uInt16 i = 0 ; i < aSaveInListBox.GetEntryCount(); i++ )
4717     {
4718         SaveInData* pData =
4719             (SaveInData*) aSaveInListBox.GetEntryData( i );
4720 
4721         nInsertPos = pNameDialog->aSaveInListBox.InsertEntry(
4722             aSaveInListBox.GetEntry( i ) );
4723 
4724         pNameDialog->aSaveInListBox.SetEntryData( nInsertPos, pData );
4725     }
4726 
4727     pNameDialog->aSaveInListBox.SelectEntryPos(
4728         aSaveInListBox.GetSelectEntryPos(), sal_True );
4729 
4730     bool ret = pNameDialog->Execute();
4731     if ( ret == RET_OK )
4732     {
4733         pNameDialog->GetName( aNewName );
4734 
4735         nInsertPos = pNameDialog->aSaveInListBox.GetSelectEntryPos();
4736 
4737         ToolbarSaveInData* pData = (ToolbarSaveInData*)
4738             pNameDialog->aSaveInListBox.GetEntryData( nInsertPos );
4739 
4740         if ( GetSaveInData() != pData )
4741         {
4742             aSaveInListBox.SelectEntryPos( nInsertPos, sal_True );
4743             aSaveInListBox.GetSelectHdl().Call(this);
4744         }
4745 
4746         SvxConfigEntry* pToolbar =
4747             new SvxConfigEntry( aNewName, aNewURL, sal_True );
4748 
4749         pToolbar->SetUserDefined( sal_True );
4750         pToolbar->SetMain( sal_True );
4751 
4752         pData->CreateToolbar( pToolbar );
4753 
4754         nInsertPos = aTopLevelListBox.InsertEntry( pToolbar->GetName() );
4755         aTopLevelListBox.SetEntryData( nInsertPos, pToolbar );
4756         aTopLevelListBox.SelectEntryPos( nInsertPos, sal_True );
4757         aTopLevelListBox.GetSelectHdl().Call(this);
4758 
4759         pData->SetModified( sal_True );
4760     }
4761 
4762     delete pNameDialog;
4763 
4764     return 0;
4765 }
4766 
4767 IMPL_LINK( SvxToolbarConfigPage, AddCommandsHdl, Button *, pButton )
4768 {
4769     (void)pButton;
4770 
4771     if ( pSelectorDlg == NULL )
4772     {
4773         // Create Script Selector which shows slot commands
4774         pSelectorDlg = new SvxScriptSelectorDialog( this, sal_True, m_xFrame );
4775 
4776         // Position the Script Selector over the Add button so it is
4777         // beside the menu contents list and does not obscure it
4778         pSelectorDlg->SetPosPixel( aAddCommandsButton.GetPosPixel() );
4779 
4780         pSelectorDlg->SetAddHdl(
4781             LINK( this, SvxToolbarConfigPage, AddFunctionHdl ) );
4782     }
4783 
4784     pSelectorDlg->SetImageProvider(
4785         static_cast< ImageProvider* >( GetSaveInData() ) );
4786 
4787     pSelectorDlg->Show();
4788     return 1;
4789 }
4790 
4791 IMPL_LINK( SvxToolbarConfigPage, AddFunctionHdl,
4792     SvxScriptSelectorDialog *, pDialog )
4793 {
4794     (void)pDialog;
4795 
4796     AddFunction();
4797 
4798     return 0;
4799 }
4800 
4801 SvLBoxEntry* SvxToolbarConfigPage::AddFunction(
4802     SvLBoxEntry* pTarget, bool bFront, bool bAllowDuplicates )
4803 {
4804     SvLBoxEntry* pNewLBEntry =
4805         SvxConfigPage::AddFunction( pTarget, bFront, bAllowDuplicates );
4806 
4807     SvxConfigEntry* pEntry = (SvxConfigEntry*) pNewLBEntry->GetUserData();
4808 
4809     if ( pEntry->IsBinding() )
4810     {
4811         pEntry->SetVisible( sal_True );
4812         aContentsListBox->SetCheckButtonState(
4813             pNewLBEntry, SV_BUTTON_CHECKED );
4814     }
4815     else
4816     {
4817         aContentsListBox->SetCheckButtonState(
4818             pNewLBEntry, SV_BUTTON_TRISTATE );
4819     }
4820 
4821     // get currently selected toolbar and apply change
4822     SvxConfigEntry* pToolbar = GetTopLevelSelection();
4823 
4824     if ( pToolbar != NULL )
4825     {
4826         ( ( ToolbarSaveInData* ) GetSaveInData() )->ApplyToolbar( pToolbar );
4827     }
4828 
4829     return pNewLBEntry;
4830 }
4831 
4832 // -----------------------------------------------------------------------
4833 
4834 SvxToolbarEntriesListBox::SvxToolbarEntriesListBox(
4835     Window* pParent, const ResId& aResId )
4836     :
4837         SvxMenuEntriesListBox( pParent, aResId ),
4838         pPage( ( SvxToolbarConfigPage* ) pParent )
4839 {
4840     m_pButtonData = new SvLBoxButtonData( this );
4841     BuildCheckBoxButtonImages( m_pButtonData );
4842     EnableCheckButton( m_pButtonData );
4843 
4844     m_bHiContrastMode = GetSettings().GetStyleSettings().GetHighContrastMode();
4845 }
4846 
4847 // --------------------------------------------------------
4848 
4849 SvxToolbarEntriesListBox::~SvxToolbarEntriesListBox()
4850 {
4851     delete m_pButtonData;
4852 }
4853 
4854 // --------------------------------------------------------
4855 
4856 void SvxToolbarEntriesListBox::BuildCheckBoxButtonImages( SvLBoxButtonData* pData )
4857 {
4858     // Build checkbox images according to the current application
4859     // settings. This is necessary to be able to have correct colors
4860     // in all color modes, like high contrast.
4861     const AllSettings& rSettings = Application::GetSettings();
4862 
4863     VirtualDevice   aDev;
4864     Size            aSize( 26, 20 );
4865 
4866     aDev.SetOutputSizePixel( aSize );
4867 
4868     Image aImage = GetSizedImage( aDev, aSize,
4869         CheckBox::GetCheckImage( rSettings, BUTTON_DRAW_DEFAULT ));
4870 
4871     // Fill button data struct with new images
4872     pData->aBmps[SV_BMP_UNCHECKED]      = aImage;
4873     pData->aBmps[SV_BMP_CHECKED]        = GetSizedImage( aDev, aSize, CheckBox::GetCheckImage( rSettings, BUTTON_DRAW_CHECKED ));
4874     pData->aBmps[SV_BMP_HICHECKED]      = GetSizedImage( aDev, aSize, CheckBox::GetCheckImage( rSettings, BUTTON_DRAW_CHECKED | BUTTON_DRAW_PRESSED ));
4875     pData->aBmps[SV_BMP_HIUNCHECKED]    = GetSizedImage( aDev, aSize, CheckBox::GetCheckImage( rSettings, BUTTON_DRAW_DEFAULT | BUTTON_DRAW_PRESSED));
4876     pData->aBmps[SV_BMP_TRISTATE]       = GetSizedImage( aDev, aSize, Image() ); // Use tristate bitmaps to have no checkbox for separator entries
4877     pData->aBmps[SV_BMP_HITRISTATE]     = GetSizedImage( aDev, aSize, Image() );
4878 
4879     // Get image size
4880     m_aCheckBoxImageSizePixel = aImage.GetSizePixel();
4881 }
4882 
4883 Image SvxToolbarEntriesListBox::GetSizedImage(
4884     VirtualDevice& aDev, const Size& aNewSize, const Image& aImage )
4885 {
4886     // Create new checkbox images for treelistbox. They must have a
4887     // decent width to have a clear column for the visibility checkbox.
4888 
4889     // Standard transparent color is light magenta as is won't be
4890     // used for other things
4891     Color   aFillColor( COL_LIGHTMAGENTA );
4892 
4893     // Position image at the center of (width-2),(height) rectangle.
4894     // We need 2 pixels to have a bigger border to the next button image
4895     sal_uInt16  nPosX = std::max( (sal_uInt16) (((( aNewSize.Width() - 2 ) - aImage.GetSizePixel().Width() ) / 2 ) - 1), (sal_uInt16) 0 );
4896     sal_uInt16  nPosY = std::max( (sal_uInt16) (((( aNewSize.Height() - 2 ) - aImage.GetSizePixel().Height() ) / 2 ) + 1), (sal_uInt16) 0 );
4897     Point   aPos( nPosX > 0 ? nPosX : 0, nPosY > 0 ? nPosY : 0 );
4898     aDev.SetFillColor( aFillColor );
4899     aDev.SetLineColor( aFillColor );
4900     aDev.DrawRect( Rectangle( Point(), aNewSize ));
4901     aDev.DrawImage( aPos, aImage );
4902 
4903     // Draw separator line 2 pixels left from the right border
4904     Color aLineColor = GetDisplayBackground().GetColor().IsDark() ? Color( COL_WHITE ) : Color( COL_BLACK );
4905     aDev.SetLineColor( aLineColor );
4906     aDev.DrawLine( Point( aNewSize.Width()-3, 0 ), Point( aNewSize.Width()-3, aNewSize.Height()-1 ));
4907 
4908     // Create new image that uses the fillcolor as transparent
4909     return Image( aDev.GetBitmap( Point(), aNewSize ), aFillColor );
4910 }
4911 
4912 void SvxToolbarEntriesListBox::DataChanged( const DataChangedEvent& rDCEvt )
4913 {
4914     SvTreeListBox::DataChanged( rDCEvt );
4915 
4916     if (( rDCEvt.GetType() == DATACHANGED_SETTINGS ) &&
4917         ( rDCEvt.GetFlags() & SETTINGS_STYLE ))
4918     {
4919         // We have to reset all images because we change to/from high contrast mode
4920         m_bHiContrastMode = GetSettings().GetStyleSettings().GetHighContrastMode();
4921 
4922         BuildCheckBoxButtonImages( m_pButtonData );
4923         Invalidate();
4924     }
4925 }
4926 
4927 // --------------------------------------------------------
4928 
4929 void SvxToolbarEntriesListBox::ChangeVisibility( SvLBoxEntry* pEntry )
4930 {
4931     if ( pEntry != NULL )
4932     {
4933         SvxConfigEntry* pEntryData =
4934             (SvxConfigEntry*) pEntry->GetUserData();
4935 
4936         if ( pEntryData->IsBinding() )
4937         {
4938             pEntryData->SetVisible( !pEntryData->IsVisible() );
4939 
4940             SvxConfigEntry* pToolbar = pPage->GetTopLevelSelection();
4941 
4942             ToolbarSaveInData* pToolbarSaveInData = ( ToolbarSaveInData* )
4943                 pPage->GetSaveInData();
4944 
4945             pToolbarSaveInData->ApplyToolbar( pToolbar );
4946 
4947             SetCheckButtonState( pEntry, pEntryData->IsVisible() ?
4948                 SV_BUTTON_CHECKED : SV_BUTTON_UNCHECKED );
4949         }
4950     }
4951 }
4952 
4953 void SvxToolbarEntriesListBox::CheckButtonHdl()
4954 {
4955     ChangeVisibility( GetHdlEntry() );
4956 }
4957 
4958 void SvxToolbarEntriesListBox::KeyInput( const KeyEvent& rKeyEvent )
4959 {
4960     // space key will change visibility of toolbar items
4961     if ( rKeyEvent.GetKeyCode() == KEY_SPACE )
4962     {
4963         ChangeVisibility( GetCurEntry() );
4964     }
4965     else
4966     {
4967         // pass on to superclass
4968         SvxMenuEntriesListBox::KeyInput( rKeyEvent );
4969     }
4970 }
4971 
4972 sal_Bool SvxToolbarEntriesListBox::NotifyMoving(
4973     SvLBoxEntry* pTarget, SvLBoxEntry* pSource,
4974     SvLBoxEntry*& rpNewParent, sal_uLong& rNewChildPos)
4975 {
4976     bool result = SvxMenuEntriesListBox::NotifyMoving(
4977         pTarget, pSource, rpNewParent, rNewChildPos );
4978 
4979     if ( result == sal_True )
4980     {
4981         // Instant Apply changes to UI
4982         SvxConfigEntry* pToolbar = pPage->GetTopLevelSelection();
4983         if ( pToolbar != NULL )
4984         {
4985             ToolbarSaveInData* pSaveInData =
4986                 ( ToolbarSaveInData*) pPage->GetSaveInData();
4987             pSaveInData->ApplyToolbar( pToolbar );
4988         }
4989     }
4990 
4991     return result;
4992 }
4993 
4994 sal_Bool SvxToolbarEntriesListBox::NotifyCopying(
4995     SvLBoxEntry*  pTarget,
4996     SvLBoxEntry*  pSource,
4997     SvLBoxEntry*& rpNewParent,
4998     sal_uLong&      rNewChildPos)
4999 {
5000     (void)pSource;
5001     (void)rpNewParent;
5002     (void)rNewChildPos;
5003 
5004     if ( !m_bIsInternalDrag )
5005     {
5006         // if the target is NULL then add function to the start of the list
5007         ((SvxToolbarConfigPage*)pPage)->AddFunction( pTarget, pTarget == NULL );
5008 
5009         // Instant Apply changes to UI
5010         SvxConfigEntry* pToolbar = pPage->GetTopLevelSelection();
5011         if ( pToolbar != NULL )
5012         {
5013             ToolbarSaveInData* pSaveInData =
5014                 ( ToolbarSaveInData*) pPage->GetSaveInData();
5015             pSaveInData->ApplyToolbar( pToolbar );
5016         }
5017 
5018         // AddFunction already adds the listbox entry so return FALSE
5019         // to stop another listbox entry being added
5020         return sal_False;
5021     }
5022 
5023     // Copying is only allowed from external controls, not within the listbox
5024     return sal_False;
5025 }
5026 
5027 SvxNewToolbarDialog::SvxNewToolbarDialog(
5028     Window* pWindow, const String& rName )
5029     :
5030     ModalDialog     ( pWindow, CUI_RES( MD_NEW_TOOLBAR ) ),
5031     aFtDescription  ( this, CUI_RES( FT_NAME ) ),
5032     aEdtName        ( this, CUI_RES( EDT_STRING ) ),
5033     aSaveInText     ( this, CUI_RES( TXT_SAVEIN ) ),
5034     aBtnOK          ( this, CUI_RES( BTN_OK ) ),
5035     aBtnCancel      ( this, CUI_RES( BTN_CANCEL ) ),
5036     aBtnHelp        ( this, CUI_RES( BTN_HELP ) ),
5037     aSaveInListBox  ( this, CUI_RES( LB_SAVEIN ) )
5038 {
5039     FreeResource();
5040 
5041     aEdtName.SetText( rName );
5042     aEdtName.SetSelection(Selection(SELECTION_MIN, SELECTION_MAX));
5043     ModifyHdl(&aEdtName);
5044     aEdtName.SetModifyHdl(LINK(this, SvxNewToolbarDialog, ModifyHdl));
5045 }
5046 
5047 IMPL_LINK(SvxNewToolbarDialog, ModifyHdl, Edit*, pEdit)
5048 {
5049     (void)pEdit;
5050 
5051     if(aCheckNameHdl.IsSet())
5052         aBtnOK.Enable(aCheckNameHdl.Call(this) > 0);
5053 
5054     return 0;
5055 }
5056 
5057 /*******************************************************************************
5058 *
5059 * The SvxIconSelectorDialog class
5060 *
5061 *******************************************************************************/
5062 SvxIconSelectorDialog::SvxIconSelectorDialog( Window *pWindow,
5063     const uno::Reference< css::ui::XImageManager >& rXImageManager,
5064     const uno::Reference< css::ui::XImageManager >& rXParentImageManager )
5065     :
5066     ModalDialog          ( pWindow, CUI_RES( MD_ICONSELECTOR ) ),
5067     aFtDescription       ( this, CUI_RES( FT_SYMBOLS ) ),
5068     aTbSymbol            ( this, CUI_RES( TB_SYMBOLS ) ),
5069     aFtNote              ( this, CUI_RES( FT_NOTE ) ),
5070     aBtnOK               ( this, CUI_RES( BTN_OK ) ),
5071     aBtnCancel           ( this, CUI_RES( BTN_CANCEL ) ),
5072     aBtnHelp             ( this, CUI_RES( BTN_HELP ) ),
5073     aBtnImport           ( this, CUI_RES( BTN_IMPORT ) ),
5074     aBtnDelete           ( this, CUI_RES( BTN_DELETE ) ),
5075     aFlSeparator         ( this, CUI_RES( FL_SEPARATOR ) ),
5076     m_nNextId            ( 0 ),
5077     m_xImageManager      ( rXImageManager ),
5078     m_xParentImageManager( rXParentImageManager )
5079 {
5080     FreeResource();
5081 
5082     typedef ::std::hash_map< ::rtl::OUString,
5083                              bool,
5084                              ::rtl::OUStringHash,
5085                              ::std::equal_to< ::rtl::OUString > > ImageInfo;
5086 
5087     aTbSymbol.SetPageScroll( sal_True );
5088 
5089     bool bLargeIcons = GetImageType() & css::ui::ImageType::SIZE_LARGE;
5090     m_nExpectedSize = bLargeIcons ? 26 : 16;
5091 
5092     if ( m_nExpectedSize != 16 )
5093     {
5094         aFtNote.SetText( replaceSixteen( aFtNote.GetText(), m_nExpectedSize ) );
5095     }
5096 
5097     uno::Reference< lang::XMultiServiceFactory > xServiceManager =
5098         ::comphelper::getProcessServiceFactory();
5099 
5100     if ( xServiceManager.is() )
5101     {
5102         m_xGraphProvider = uno::Reference< graphic::XGraphicProvider >(
5103             xServiceManager->createInstance(
5104                 ::rtl::OUString::createFromAscii(
5105                     "com.sun.star.graphic.GraphicProvider" ) ),
5106             uno::UNO_QUERY );
5107     }
5108 
5109     if ( !m_xGraphProvider.is() )
5110     {
5111         aBtnImport.Enable( sal_False );
5112     }
5113 
5114     uno::Reference< beans::XPropertySet > xPropSet(
5115         xServiceManager->createInstance( ::rtl::OUString::createFromAscii( "com.sun.star.util.PathSettings" ) ),
5116         uno::UNO_QUERY );
5117 
5118     uno::Any aAny = xPropSet->getPropertyValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "UserConfig" ) ) );
5119 
5120     ::rtl::OUString aDirectory;
5121 
5122     aAny >>= aDirectory;
5123 
5124     sal_Int32 aCount = aDirectory.getLength();
5125 
5126     if ( aCount > 0 )
5127     {
5128         sal_Unicode aChar = aDirectory[ aCount-1 ];
5129         if ( aChar != '/')
5130         {
5131             aDirectory += ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "/" ) );
5132         }
5133     }
5134     else
5135     {
5136         aBtnImport.Enable( sal_False );
5137     }
5138 
5139     aDirectory += ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "soffice.cfg/import" ) );
5140 
5141     uno::Reference< lang::XSingleServiceFactory > xStorageFactory(
5142         xServiceManager->createInstance(
5143         ::rtl::OUString::createFromAscii( "com.sun.star.embed.FileSystemStorageFactory" )),
5144         uno::UNO_QUERY );
5145 
5146     uno::Sequence< uno::Any > aArgs( 2 );
5147     aArgs[ 0 ] <<= aDirectory;
5148     aArgs[ 1 ] <<= com::sun::star::embed::ElementModes::READWRITE;
5149 
5150     uno::Reference< com::sun::star::embed::XStorage > xStorage(
5151         xStorageFactory->createInstanceWithArguments( aArgs ), uno::UNO_QUERY );
5152 
5153     uno::Sequence< uno::Any > aProp( 2 );
5154     beans::PropertyValue aPropValue;
5155 
5156     aPropValue.Name = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "UserConfigStorage" ) );
5157     aPropValue.Value <<= xStorage;
5158     aProp[ 0 ] <<= aPropValue;
5159 
5160     aPropValue.Name = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "OpenMode" ) );
5161     aPropValue.Value <<= com::sun::star::embed::ElementModes::READWRITE;
5162     aProp[ 1 ] <<= aPropValue;
5163 
5164     m_xImportedImageManager = uno::Reference< com::sun::star::ui::XImageManager >(
5165         xServiceManager->createInstanceWithArguments(
5166         ::rtl::OUString::createFromAscii( "com.sun.star.ui.ImageManager" ), aProp ),
5167         uno::UNO_QUERY );
5168 
5169     ImageInfo mImageInfo;
5170     uno::Sequence< OUString > names;
5171     if ( m_xImportedImageManager.is() )
5172     {
5173         names = m_xImportedImageManager->getAllImageNames( GetImageType() );
5174         for ( sal_Int32 n = 0; n < names.getLength(); n++ )
5175             mImageInfo.insert( ImageInfo::value_type( names[n], false ));
5176     }
5177     sal_uInt16 nId = 1;
5178     ImageInfo::const_iterator pConstIter = mImageInfo.begin();
5179     uno::Sequence< OUString > name( 1 );
5180     while ( pConstIter != mImageInfo.end() )
5181     {
5182         name[ 0 ] = pConstIter->first;
5183         uno::Sequence< uno::Reference< graphic::XGraphic> > graphics = m_xImportedImageManager->getImages( GetImageType(), name );
5184         if ( graphics.getLength() > 0 )
5185         {
5186             Image img = Image( graphics[ 0 ] );
5187             aTbSymbol.InsertItem( nId, img, pConstIter->first );
5188 
5189             graphics[ 0 ]->acquire();
5190 
5191             aTbSymbol.SetItemData(
5192                 nId, static_cast< void * > ( graphics[ 0 ].get() ) );
5193 
5194             ++nId;
5195         }
5196         ++pConstIter;
5197     }
5198 
5199     ImageInfo                 aImageInfo;
5200 
5201     if ( m_xParentImageManager.is() )
5202     {
5203         names = m_xParentImageManager->getAllImageNames( GetImageType() );
5204         for ( sal_Int32 n = 0; n < names.getLength(); n++ )
5205             aImageInfo.insert( ImageInfo::value_type( names[n], false ));
5206     }
5207 
5208     names = m_xImageManager->getAllImageNames( GetImageType() );
5209     for ( sal_Int32 n = 0; n < names.getLength(); n++ )
5210     {
5211         ImageInfo::iterator pIter = aImageInfo.find( names[n] );
5212         if ( pIter != aImageInfo.end() )
5213             pIter->second = true;
5214         else
5215             aImageInfo.insert( ImageInfo::value_type( names[n], true ));
5216     }
5217 
5218     // large growth factor, expecting many entries
5219     pConstIter = aImageInfo.begin();
5220     while ( pConstIter != aImageInfo.end() )
5221     {
5222         name[ 0 ] = pConstIter->first;
5223 
5224         uno::Sequence< uno::Reference< graphic::XGraphic> > graphics;
5225         try
5226         {
5227             if ( pConstIter->second )
5228                 graphics = m_xImageManager->getImages( GetImageType(), name );
5229             else
5230                 graphics = m_xParentImageManager->getImages( GetImageType(), name );
5231         }
5232         catch ( uno::Exception& )
5233         {
5234             // can't get sequence for this name so it will not be
5235             // added to the list
5236         }
5237 
5238         if ( graphics.getLength() > 0 )
5239         {
5240             Image img = Image( graphics[ 0 ] );
5241             aTbSymbol.InsertItem( nId, img, pConstIter->first );
5242 
5243             uno::Reference< graphic::XGraphic > xGraphic = graphics[ 0 ];
5244 
5245             if ( xGraphic.is() )
5246                 xGraphic->acquire();
5247 
5248             aTbSymbol.SetItemData(
5249                 nId, static_cast< void * > ( xGraphic.get() ) );
5250 
5251             ++nId;
5252         }
5253 
5254         ++pConstIter;
5255     }
5256 
5257     aBtnDelete.Enable( sal_False );
5258     aTbSymbol.SetSelectHdl( LINK(this, SvxIconSelectorDialog, SelectHdl) );
5259     aBtnImport.SetClickHdl( LINK(this, SvxIconSelectorDialog, ImportHdl) );
5260     aBtnDelete.SetClickHdl( LINK(this, SvxIconSelectorDialog, DeleteHdl) );
5261 
5262     m_nNextId = aTbSymbol.GetItemCount()+1;
5263 }
5264 
5265 SvxIconSelectorDialog::~SvxIconSelectorDialog()
5266 {
5267     sal_uInt16 nCount = aTbSymbol.GetItemCount();
5268 
5269     for (sal_uInt16 n = 0; n < nCount; n++ )
5270     {
5271         sal_uInt16 nId = aTbSymbol.GetItemId(n);
5272 
5273         uno::XInterface* xi = static_cast< uno::XInterface* >(
5274             aTbSymbol.GetItemData( nId ) );
5275 
5276         if ( xi != NULL )
5277         {
5278             xi->release();
5279         }
5280     }
5281 }
5282 
5283 uno::Reference< graphic::XGraphic> SvxIconSelectorDialog::GetSelectedIcon()
5284 {
5285     uno::Reference< graphic::XGraphic > result;
5286 
5287     sal_uInt16 nId;
5288     for ( sal_uInt16 n = 0; n < aTbSymbol.GetItemCount(); n++ )
5289     {
5290         nId = aTbSymbol.GetItemId( n );
5291         if ( aTbSymbol.IsItemChecked( nId ) )
5292         {
5293             result = uno::Reference< graphic::XGraphic >(
5294                 reinterpret_cast< graphic::XGraphic* >(
5295                     aTbSymbol.GetItemData( nId ) ) );
5296         }
5297     }
5298 
5299     return result;
5300 }
5301 
5302 IMPL_LINK( SvxIconSelectorDialog, SelectHdl, ToolBox *, pToolBox )
5303 {
5304     (void)pToolBox;
5305 
5306     sal_uInt16 nCount = aTbSymbol.GetItemCount();
5307 
5308     for (sal_uInt16 n = 0; n < nCount; n++ )
5309     {
5310         sal_uInt16 nId = aTbSymbol.GetItemId( n );
5311 
5312         if ( aTbSymbol.IsItemChecked( nId ) )
5313         {
5314             aTbSymbol.CheckItem( nId, sal_False );
5315         }
5316     }
5317 
5318     sal_uInt16 nId = aTbSymbol.GetCurItemId();
5319     aTbSymbol.CheckItem( nId );
5320 
5321     ::rtl::OUString aSelImageText = aTbSymbol.GetItemText( nId );
5322     if ( m_xImportedImageManager->hasImage( GetImageType(), aSelImageText ) )
5323     {
5324         aBtnDelete.Enable( sal_True );
5325     }
5326     else
5327     {
5328         aBtnDelete.Enable( sal_False );
5329     }
5330 
5331     return 0;
5332 }
5333 
5334 IMPL_LINK( SvxIconSelectorDialog, ImportHdl, PushButton *, pButton )
5335 {
5336     (void)pButton;
5337 
5338     sfx2::FileDialogHelper aImportDialog(
5339         css::ui::dialogs::TemplateDescription::FILEOPEN_LINK_PREVIEW,
5340         SFXWB_GRAPHIC | SFXWB_MULTISELECTION );
5341 
5342     // disable the link checkbox in the dialog
5343     uno::Reference< css::ui::dialogs::XFilePickerControlAccess >
5344         xController( aImportDialog.GetFilePicker(), uno::UNO_QUERY);
5345     if ( xController.is() )
5346     {
5347         xController->enableControl(
5348             css::ui::dialogs::ExtendedFilePickerElementIds::CHECKBOX_LINK,
5349             sal_False);
5350     }
5351 
5352     aImportDialog.SetCurrentFilter(
5353         String::CreateFromAscii( "PNG - Portable Network Graphic" ) );
5354 
5355     if ( ERRCODE_NONE == aImportDialog.Execute() )
5356     {
5357         uno::Sequence< OUString > paths = aImportDialog.GetMPath();
5358         ImportGraphics ( paths );
5359     }
5360 
5361     return 0;
5362 }
5363 
5364 IMPL_LINK( SvxIconSelectorDialog, DeleteHdl, PushButton *, pButton )
5365 {
5366     (void)pButton;
5367 
5368     OUString message = String( CUI_RES( RID_SVXSTR_DELETE_ICON_CONFIRM ) );
5369     bool ret = WarningBox( this, WinBits(WB_OK_CANCEL), message ).Execute();
5370 
5371     if ( ret == RET_OK )
5372     {
5373         sal_uInt16 nCount = aTbSymbol.GetItemCount();
5374 
5375         for (sal_uInt16 n = 0; n < nCount; n++ )
5376         {
5377             sal_uInt16 nId = aTbSymbol.GetItemId( n );
5378 
5379             if ( aTbSymbol.IsItemChecked( nId ) )
5380             {
5381                 ::rtl::OUString aSelImageText = aTbSymbol.GetItemText( nId );
5382                 uno::Sequence< OUString > URLs(1);
5383                 URLs[0] = aSelImageText;
5384                 aTbSymbol.RemoveItem( aTbSymbol.GetItemPos( nId ) );
5385                 m_xImportedImageManager->removeImages( GetImageType(), URLs );
5386                 uno::Reference< css::ui::XUIConfigurationPersistence >
5387                     xConfigPersistence( m_xImportedImageManager, uno::UNO_QUERY );
5388                 if ( xConfigPersistence.is() && xConfigPersistence->isModified() )
5389                 {
5390                     xConfigPersistence->store();
5391                 }
5392                 break;
5393             }
5394         }
5395     }
5396     return 0;
5397 }
5398 
5399 bool SvxIconSelectorDialog::ReplaceGraphicItem(
5400     const ::rtl::OUString& aURL )
5401 {
5402     uno::Sequence< OUString > URLs(1);
5403     uno::Sequence< uno::Reference<graphic::XGraphic > > aImportGraph( 1 );
5404     uno::Reference< css::ui::XUIConfigurationPersistence >
5405         xConfigPer( m_xImportedImageManager, uno::UNO_QUERY );
5406 
5407     uno::Reference< graphic::XGraphic > xGraphic;
5408     uno::Sequence< beans::PropertyValue > aMediaProps( 1 );
5409     aMediaProps[0].Name = ::rtl::OUString::createFromAscii("URL");
5410     aMediaProps[0].Value <<= aURL;
5411 
5412     com::sun::star::awt::Size aSize;
5413     bool bOK = sal_False;
5414     try
5415     {
5416         xGraphic = m_xGraphProvider->queryGraphic( aMediaProps );
5417 
5418         uno::Reference< beans::XPropertySet > props =
5419             m_xGraphProvider->queryGraphicDescriptor( aMediaProps );
5420         uno::Any a = props->getPropertyValue(
5421             OUString::createFromAscii("SizePixel") );
5422         a >>= aSize;
5423         if (0 == aSize.Width || 0 == aSize.Height)
5424             return sal_False;
5425         else
5426             bOK = sal_True;
5427     }
5428     catch ( uno::Exception& )
5429     {
5430         return false;
5431     }
5432 
5433     bool   bResult( false );
5434     sal_uInt16 nCount = aTbSymbol.GetItemCount();
5435     for (sal_uInt16 n = 0; n < nCount; n++ )
5436     {
5437         sal_uInt16 nId = aTbSymbol.GetItemId( n );
5438 
5439         if ( OUString( aTbSymbol.GetItemText( nId ) ) == aURL )
5440         {
5441             try
5442             {
5443                 // replace/insert image with provided URL
5444                 aTbSymbol.RemoveItem( aTbSymbol.GetItemPos( nId ) );
5445                 aMediaProps[0].Value <<= aURL;
5446 
5447                 Image aImage( xGraphic );
5448                 if ( bOK && ((aSize.Width != m_nExpectedSize) || (aSize.Height != m_nExpectedSize)) )
5449                 {
5450                     BitmapEx aBitmap = aImage.GetBitmapEx();
5451                     BitmapEx aBitmapex = AutoScaleBitmap(aBitmap, m_nExpectedSize);
5452                     aImage = Image( aBitmapex);
5453                 }
5454                 aTbSymbol.InsertItem( nId,aImage, aURL, 0, 0 ); //modify
5455 
5456                 xGraphic = aImage.GetXGraphic();
5457 
5458                 URLs[0] = aURL;
5459                 aImportGraph[ 0 ] = xGraphic;
5460                 m_xImportedImageManager->replaceImages( GetImageType(), URLs, aImportGraph );
5461                 xConfigPer->store();
5462 
5463                 bResult = true;
5464                 break;
5465             }
5466             catch ( ::com::sun::star::uno::Exception& )
5467             {
5468                 break;
5469             }
5470         }
5471     }
5472 
5473     return bResult;
5474 }
5475 
5476 void SvxIconSelectorDialog::ImportGraphics(
5477     const uno::Sequence< OUString >& rPaths )
5478 {
5479     uno::Sequence< OUString > rejected( rPaths.getLength() );
5480     sal_Int32 rejectedCount = 0;
5481 
5482     sal_uInt16 ret = 0;
5483     sal_Int32 aIndex;
5484     OUString aIconName;
5485     uno::Sequence< OUString > URLs(1);
5486     uno::Sequence< uno::Reference<graphic::XGraphic > > aImportGraph( 1 );
5487     uno::Sequence< beans::PropertyValue > aMediaProps( 1 );
5488     aMediaProps[0].Name = ::rtl::OUString::createFromAscii("URL");
5489     uno::Reference< css::ui::XUIConfigurationPersistence >
5490         xConfigPer( m_xImportedImageManager, uno::UNO_QUERY );
5491 
5492     if ( rPaths.getLength() == 1 )
5493     {
5494         if ( m_xImportedImageManager->hasImage( GetImageType(), rPaths[0] ) )
5495         {
5496             aIndex = rPaths[0].lastIndexOf( '/' );
5497             aIconName = rPaths[0].copy( aIndex+1 );
5498             ret = SvxIconReplacementDialog( this, aIconName ).ShowDialog();
5499             if ( ret == 2 )
5500             {
5501                 ReplaceGraphicItem( rPaths[0] );
5502             }
5503         }
5504         else
5505         {
5506             if ( ImportGraphic( rPaths[0] ) == sal_False )
5507             {
5508                 rejected[0] = rPaths[0];
5509                 rejectedCount = 1;
5510             }
5511         }
5512     }
5513     else
5514     {
5515         ::rtl::OUString aSourcePath( rPaths[0] );
5516         if ( rPaths[0].lastIndexOf( '/' ) != rPaths[0].getLength() -1 )
5517             aSourcePath = rPaths[0] + ::rtl::OUString::createFromAscii( "/" );
5518 
5519         for ( sal_Int32 i = 1; i < rPaths.getLength(); i++ )
5520         {
5521             ::rtl::OUString aPath = aSourcePath + rPaths[i];
5522             if ( m_xImportedImageManager->hasImage( GetImageType(), aPath ) )
5523             {
5524                 aIndex = rPaths[i].lastIndexOf( '/' );
5525                 aIconName = rPaths[i].copy( aIndex+1 );
5526                 ret = SvxIconReplacementDialog( this, aIconName, sal_True ).ShowDialog();
5527                 if ( ret == 2 )
5528                 {
5529                     ReplaceGraphicItem( aPath );
5530                 }
5531                 else if ( ret == 5 )
5532                 {
5533                     for ( sal_Int32 k = i; k < rPaths.getLength(); k++ )
5534                     {
5535                         aPath = aSourcePath + rPaths[k];
5536                         bool bHasReplaced = ReplaceGraphicItem( aPath );
5537 
5538                         if ( !bHasReplaced )
5539                         {
5540                             bool result = ImportGraphic( aPath );
5541                             if ( result == sal_False )
5542                             {
5543                                 rejected[ rejectedCount ] = rPaths[i];
5544                                 rejectedCount++;
5545                             }
5546                         }
5547                     }
5548                     break;
5549                 }
5550             }
5551             else
5552             {
5553                 bool result = ImportGraphic( aSourcePath + rPaths[i] );
5554                 if ( result == sal_False )
5555                 {
5556                     rejected[ rejectedCount ] = rPaths[i];
5557                     rejectedCount++;
5558                 }
5559             }
5560         }
5561     }
5562 
5563     if ( rejectedCount != 0 )
5564     {
5565         OUString message =OUString::createFromAscii("");
5566         OUString newLine = OUString::createFromAscii("\n");
5567         rtl::OUString fPath = OUString::createFromAscii("");
5568         if (rejectedCount > 1)
5569             fPath = rPaths[0].copy(8) + ::rtl::OUString::createFromAscii( "/" );
5570         for ( sal_Int32 i = 0; i < rejectedCount; i++ )
5571         {
5572             message += fPath + rejected[i];
5573             message += newLine;
5574         }
5575 
5576         SvxIconChangeDialog aDialog(this, message);
5577         aDialog.Execute();
5578     }
5579 }
5580 
5581 bool SvxIconSelectorDialog::ImportGraphic( const OUString& aURL )
5582 {
5583     bool result = sal_False;
5584 
5585     sal_uInt16 nId = m_nNextId;
5586     ++m_nNextId;
5587 
5588     uno::Sequence< beans::PropertyValue > aMediaProps( 1 );
5589     aMediaProps[0].Name = ::rtl::OUString::createFromAscii("URL");
5590 
5591     uno::Reference< graphic::XGraphic > xGraphic;
5592     com::sun::star::awt::Size aSize;
5593     bool bOK = sal_True;
5594     aMediaProps[0].Value <<= aURL;
5595     try
5596     {
5597         uno::Reference< beans::XPropertySet > props =
5598             m_xGraphProvider->queryGraphicDescriptor( aMediaProps );
5599 
5600         uno::Any a = props->getPropertyValue(
5601             OUString::createFromAscii("SizePixel") );
5602 
5603             xGraphic = m_xGraphProvider->queryGraphic( aMediaProps );
5604             if ( xGraphic.is() )
5605             {
5606                 a >>= aSize;
5607                 if ( 0 == aSize.Width || 0 == aSize.Height )
5608                     bOK = sal_False;
5609 
5610                 Image aImage( xGraphic );
5611 
5612                 if ( bOK && ((aSize.Width != m_nExpectedSize) || (aSize.Height != m_nExpectedSize)) )
5613                 {
5614                     BitmapEx aBitmap = aImage.GetBitmapEx();
5615                     BitmapEx aBitmapex = AutoScaleBitmap(aBitmap, m_nExpectedSize);
5616                     aImage = Image( aBitmapex);
5617                 }
5618                 if ( bOK && !!aImage )
5619                 {
5620                     aTbSymbol.InsertItem( nId, aImage, aURL, 0, 0 );
5621 
5622                     xGraphic = aImage.GetXGraphic();
5623                     xGraphic->acquire();
5624 
5625                     aTbSymbol.SetItemData(
5626                         nId, static_cast< void * > ( xGraphic.get() ) );
5627                     uno::Sequence< OUString > aImportURL( 1 );
5628                     aImportURL[ 0 ] = aURL;
5629                     uno::Sequence< uno::Reference<graphic::XGraphic > > aImportGraph( 1 );
5630                     aImportGraph[ 0 ] = xGraphic;
5631                     m_xImportedImageManager->insertImages( GetImageType(), aImportURL, aImportGraph );
5632                     uno::Reference< css::ui::XUIConfigurationPersistence >
5633                     xConfigPersistence( m_xImportedImageManager, uno::UNO_QUERY );
5634 
5635                     if ( xConfigPersistence.is() && xConfigPersistence->isModified() )
5636                     {
5637                         xConfigPersistence->store();
5638                     }
5639 
5640                     result = sal_True;
5641                 }
5642                 else
5643                 {
5644                     OSL_TRACE("could not create Image from XGraphic");
5645                 }
5646             }
5647             else
5648             {
5649                 OSL_TRACE("could not get query XGraphic");
5650             }
5651     }
5652     catch( uno::Exception& e )
5653     {
5654         OSL_TRACE("Caught exception importing XGraphic: %s", PRTSTR(e.Message));
5655     }
5656     return result;
5657 }
5658 
5659 /*******************************************************************************
5660 *
5661 * The SvxIconReplacementDialog class
5662 *
5663 *******************************************************************************/
5664 SvxIconReplacementDialog :: SvxIconReplacementDialog(
5665     Window *pWindow, const rtl::OUString& aMessage, bool /*bYestoAll*/ )
5666     :
5667 MessBox( pWindow, WB_DEF_YES, String( CUI_RES( RID_SVXSTR_REPLACE_ICON_CONFIRM ) ),  String( CUI_RES( RID_SVXSTR_REPLACE_ICON_WARNING ) ) )
5668 
5669 {
5670     SetImage( WarningBox::GetStandardImage() );
5671     SetMessText( ReplaceIconName( aMessage ) );
5672     RemoveButton( 1 );
5673     AddButton( BUTTON_YES, 2, 0 );
5674     AddButton( String( CUI_RES( RID_SVXSTR_YESTOALL ) ), 5, 0 );
5675     AddButton( BUTTON_NO, 3, 0 );
5676     AddButton( BUTTON_CANCEL, 4, 0 );
5677 }
5678 
5679 SvxIconReplacementDialog :: SvxIconReplacementDialog(
5680     Window *pWindow, const rtl::OUString& aMessage )
5681     :
5682 MessBox( pWindow, WB_YES_NO_CANCEL, String( CUI_RES( RID_SVXSTR_REPLACE_ICON_CONFIRM ) ),  String( CUI_RES( RID_SVXSTR_REPLACE_ICON_WARNING ) ) )
5683 {
5684     SetImage( WarningBox::GetStandardImage() );
5685     SetMessText( ReplaceIconName( aMessage ));
5686 }
5687 
5688 rtl::OUString SvxIconReplacementDialog :: ReplaceIconName( const OUString& rMessage )
5689 {
5690     rtl::OUString name;
5691     rtl::OUString message = String( CUI_RES( RID_SVXSTR_REPLACE_ICON_WARNING ) );
5692     rtl::OUString placeholder = OUString::createFromAscii( "%ICONNAME" );
5693     sal_Int32 pos = message.indexOf( placeholder );
5694     if ( pos != -1 )
5695     {
5696         name = message.replaceAt(
5697             pos, placeholder.getLength(), rMessage );
5698     }
5699     return name;
5700 }
5701 
5702 sal_uInt16 SvxIconReplacementDialog :: ShowDialog()
5703 {
5704     this->Execute();
5705     return ( this->GetCurButtonId() );
5706 }
5707 /*******************************************************************************
5708 *
5709 * The SvxIconChangeDialog class added for issue83555
5710 *
5711 *******************************************************************************/
5712 SvxIconChangeDialog::SvxIconChangeDialog(
5713     Window *pWindow, const rtl::OUString& aMessage)
5714     :
5715     ModalDialog            ( pWindow, CUI_RES( MD_ICONCHANGE ) ),
5716     aFImageInfo            (this, CUI_RES( FI_INFO ) ),
5717     aBtnOK                 (this, CUI_RES(MD_BTN_OK)),
5718     aDescriptionLabel      (this, CUI_RES(FTCHGE_DESCRIPTION)),
5719     aLineEditDescription   (this, CUI_RES(EDT_ADDR))
5720 {
5721     FreeResource();
5722     aFImageInfo.SetImage(InfoBox::GetStandardImage());
5723     aLineEditDescription.SetControlBackground( GetSettings().GetStyleSettings().GetDialogColor() );
5724     aLineEditDescription.SetAutoScroll( sal_True );
5725     aLineEditDescription.EnableCursor( sal_False );
5726     aLineEditDescription.SetText(aMessage);
5727 }
5728 
5729 BitmapEx SvxIconSelectorDialog::AutoScaleBitmap(BitmapEx & aBitmap, const long aStandardSize)
5730 {
5731     Point aEmptyPoint(0,0);
5732     sal_Int32 imgNewWidth = 0;
5733     sal_Int32 imgNewHeight = 0;
5734     double imgposX = 0;
5735     double imgposY = 0;
5736     BitmapEx  aRet = aBitmap;
5737     double imgOldWidth = aRet.GetSizePixel().Width();
5738     double imgOldHeight =aRet.GetSizePixel().Height();
5739 
5740     Size aScaledSize;
5741     if (imgOldWidth >= aStandardSize || imgOldHeight >= aStandardSize)
5742     {
5743         if (imgOldWidth >= imgOldHeight)
5744         {
5745             imgNewWidth = aStandardSize;
5746             imgNewHeight = sal_Int32(imgOldHeight / (imgOldWidth / aStandardSize) + 0.5);
5747             imgposX = 0;
5748             imgposY = (aStandardSize - (imgOldHeight / (imgOldWidth / aStandardSize) + 0.5)) / 2 + 0.5;
5749         }
5750         else
5751         {
5752             imgNewHeight = aStandardSize;
5753             imgNewWidth = sal_Int32(imgOldWidth / (imgOldHeight / aStandardSize) + 0.5);
5754             imgposY = 0;
5755             imgposX = (aStandardSize - (imgOldWidth / (imgOldHeight / aStandardSize) + 0.5)) / 2 + 0.5;
5756         }
5757 
5758         aScaledSize = Size( imgNewWidth, imgNewHeight );
5759         aRet.Scale( aScaledSize, BMP_SCALE_INTERPOLATE );
5760     }
5761     else
5762     {
5763         imgposX = (aStandardSize - imgOldWidth) / 2 + 0.5;
5764         imgposY = (aStandardSize - imgOldHeight) / 2 + 0.5;
5765     }
5766 
5767     Size aBmpSize = aRet.GetSizePixel();
5768     Size aStdSize( aStandardSize, aStandardSize );
5769     Rectangle aRect(aEmptyPoint, aStdSize );
5770 
5771     VirtualDevice aVirDevice( *Application::GetDefaultDevice(), 0, 1 );
5772     aVirDevice.SetOutputSizePixel( aStdSize );
5773     aVirDevice.SetFillColor( COL_TRANSPARENT );
5774     aVirDevice.SetLineColor( COL_TRANSPARENT );
5775 
5776     //draw a rect into virDevice
5777     aVirDevice.DrawRect( aRect );
5778     Point aPointPixel( (long)imgposX, (long)imgposY );
5779     aVirDevice.DrawBitmapEx( aPointPixel, aRet );
5780     aRet = aVirDevice.GetBitmapEx( aEmptyPoint, aStdSize );
5781 
5782     return aRet;
5783 }
5784