update dev300-m58
[ooovba.git] / framework / source / loadenv / loadenv.cxx
blob902a5a970fb660ed7d16303414995b34b4863450
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: loadenv.cxx,v $
10 * $Revision: 1.31 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_framework.hxx"
33 //_______________________________________________
34 // includes of own project
35 #include <loadenv/loadenv.hxx>
37 #ifndef __FRAMEWORK_LOADENV_TARGETHELPER_HXX_
38 #include <loadenv/targethelper.hxx>
39 #endif
40 #include <classes/framelistanalyzer.hxx>
42 #ifndef __FRAMEWORK_CONSTANT_FILTER_HXX_
43 #include <constant/filter.hxx>
44 #endif
45 #include <dispatch/interaction.hxx>
47 #ifndef __FRAMEWORK_CONSTANT_FRAMELOADER_HXX_
48 #include <constant/frameloader.hxx>
49 #endif
51 #ifndef __FRAMEWORK_CONSTANT_CONTENTHANDLER_HXX_
52 #include <constant/contenthandler.hxx>
53 #endif
55 #ifndef __FRAMEWORK_CONSTANT_CONTAINERQUERY_HXX_
56 #include <constant/containerquery.hxx>
57 #endif
58 #include <interaction/stillinteraction.hxx>
59 #include <threadhelp/writeguard.hxx>
60 #include <threadhelp/readguard.hxx>
61 #include <threadhelp/resetableguard.hxx>
62 #include <properties.h>
63 #include <protocols.h>
64 #include <services.h>
65 #include <dispatch/interaction.hxx>
67 //_______________________________________________
68 // includes of uno interface
69 #include <com/sun/star/task/ErrorCodeRequest.hpp>
70 #include <com/sun/star/uno/RuntimeException.hpp>
71 #include <com/sun/star/frame/DispatchResultState.hpp>
72 #include <com/sun/star/frame/FrameSearchFlag.hpp>
73 #include <com/sun/star/util/XURLTransformer.hpp>
74 #include <com/sun/star/ucb/XContentProviderManager.hpp>
75 #include <com/sun/star/util/XCloseable.hpp>
76 #include <com/sun/star/lang/XComponent.hpp>
77 #include <com/sun/star/lang/XServiceInfo.hpp>
78 #include <com/sun/star/lang/DisposedException.hpp>
79 #include <com/sun/star/awt/XWindow.hpp>
80 #include <com/sun/star/awt/XWindow2.hpp>
81 #include <com/sun/star/awt/XTopWindow.hpp>
82 #include <com/sun/star/frame/XModel.hpp>
83 #include <com/sun/star/frame/XFrameLoader.hpp>
84 #include <com/sun/star/frame/XSynchronousFrameLoader.hpp>
85 #include <com/sun/star/frame/XNotifyingDispatch.hpp>
86 #include <com/sun/star/task/XStatusIndicatorFactory.hpp>
87 #include <com/sun/star/task/XStatusIndicator.hpp>
88 #include <com/sun/star/util/XModifiable.hpp>
89 #include <com/sun/star/frame/XDispatchProvider.hpp>
90 #include <com/sun/star/document/XTypeDetection.hpp>
91 #include <com/sun/star/document/XActionLockable.hpp>
92 #include <com/sun/star/io/XInputStream.hpp>
93 #include <com/sun/star/task/XInteractionHandler.hpp>
94 #include <com/sun/star/container/XNameAccess.hpp>
95 #include <com/sun/star/container/XContainerQuery.hpp>
96 #include <com/sun/star/container/XEnumeration.hpp>
97 #include <com/sun/star/document/MacroExecMode.hpp>
98 #include <com/sun/star/document/UpdateDocMode.hpp>
100 //_______________________________________________
101 // includes of an other project
102 #include <vcl/window.hxx>
103 #include <vcl/wrkwin.hxx>
104 #include <vcl/syswin.hxx>
106 #ifndef _TOOLKIT_HELPER_VCLUNOHELPER_HXX_
107 #include <toolkit/unohlp.hxx>
108 #endif
109 #include <svtools/moduleoptions.hxx>
110 #include <svtools/sfxecode.hxx>
111 #include <unotools/processfactory.hxx>
112 #include <comphelper/configurationhelper.hxx>
113 #include <rtl/ustrbuf.hxx>
114 #include <vcl/svapp.hxx>
116 //_______________________________________________
117 // namespace
119 namespace framework{
121 // may there exist already a define .-(
122 #ifndef css
123 namespace css = ::com::sun::star;
124 #endif
126 //_______________________________________________
127 // declarations
129 class LoadEnvListener : private ThreadHelpBase
130 , public ::cppu::WeakImplHelper2< css::frame::XLoadEventListener ,
131 css::frame::XDispatchResultListener >
133 private:
135 void** m_ppCheck ;
136 LoadEnv* m_pLoadEnv;
138 public:
140 //_______________________________________
141 LoadEnvListener(void* pCheck ,
142 LoadEnv* pLoadEnv)
144 m_ppCheck = &pCheck ;
145 m_pLoadEnv = pLoadEnv;
148 //_______________________________________
149 // frame.XLoadEventListener
150 virtual void SAL_CALL loadFinished(const css::uno::Reference< css::frame::XFrameLoader >& xLoader)
151 throw(css::uno::RuntimeException);
153 virtual void SAL_CALL loadCancelled(const css::uno::Reference< css::frame::XFrameLoader >& xLoader)
154 throw(css::uno::RuntimeException);
156 //_______________________________________
157 // frame.XDispatchResultListener
158 virtual void SAL_CALL dispatchFinished(const css::frame::DispatchResultEvent& aEvent)
159 throw(css::uno::RuntimeException);
161 //_______________________________________
162 // lang.XEventListener
163 virtual void SAL_CALL disposing(const css::lang::EventObject& aEvent)
164 throw(css::uno::RuntimeException);
167 /*-----------------------------------------------
168 14.10.2003 13:43
169 -----------------------------------------------*/
170 LoadEnv::LoadEnv(const css::uno::Reference< css::lang::XMultiServiceFactory >& xSMGR)
171 throw(LoadEnvException, css::uno::RuntimeException)
172 : ThreadHelpBase( )
173 , m_xSMGR (xSMGR)
174 , m_pCheck (this )
178 /*-----------------------------------------------
179 14.10.2003 13:43
180 -----------------------------------------------*/
181 LoadEnv::~LoadEnv()
183 m_pCheck = 0;
186 /*-----------------------------------------------
187 10.09.2003 14:05
188 -----------------------------------------------*/
189 css::uno::Reference< css::lang::XComponent > LoadEnv::loadComponentFromURL(const css::uno::Reference< css::frame::XComponentLoader >& xLoader,
190 const css::uno::Reference< css::lang::XMultiServiceFactory >& xSMGR ,
191 const ::rtl::OUString& sURL ,
192 const ::rtl::OUString& sTarget,
193 sal_Int32 nFlags ,
194 const css::uno::Sequence< css::beans::PropertyValue >& lArgs )
195 throw(css::lang::IllegalArgumentException,
196 css::io::IOException ,
197 css::uno::RuntimeException )
199 css::uno::Reference< css::lang::XComponent > xComponent;
203 LoadEnv aEnv(xSMGR);
205 aEnv.initializeLoading(sURL,
206 lArgs,
207 css::uno::Reference< css::frame::XFrame >(xLoader, css::uno::UNO_QUERY),
208 sTarget,
209 nFlags,
210 LoadEnv::E_NO_FEATURE);
211 aEnv.startLoading();
212 aEnv.waitWhileLoading(); // wait for ever!
214 xComponent = aEnv.getTargetComponent();
216 catch(const LoadEnvException& ex)
218 switch(ex.m_nID)
220 case LoadEnvException::ID_INVALID_MEDIADESCRIPTOR:
221 throw css::lang::IllegalArgumentException(
222 ::rtl::OUString::createFromAscii("Optional list of arguments seem to be corrupted."),
223 xLoader,
226 case LoadEnvException::ID_UNSUPPORTED_CONTENT:
227 throw css::lang::IllegalArgumentException(
228 ::rtl::OUString::createFromAscii("URL seems to be an unsupported one."),
229 xLoader,
232 default: xComponent.clear();
233 break;
237 return xComponent;
240 //-----------------------------------------------
241 ::comphelper::MediaDescriptor impl_mergeMediaDescriptorWithMightExistingModelArgs(const css::uno::Sequence< css::beans::PropertyValue >& lOutsideDescriptor)
243 ::comphelper::MediaDescriptor lDescriptor(lOutsideDescriptor);
244 css::uno::Reference< css::frame::XModel > xModel = lDescriptor.getUnpackedValueOrDefault(
245 ::comphelper::MediaDescriptor::PROP_MODEL (),
246 css::uno::Reference< css::frame::XModel > ());
247 if (xModel.is ())
249 ::comphelper::MediaDescriptor lModelDescriptor(xModel->getArgs());
250 ::comphelper::MediaDescriptor::iterator pIt = lModelDescriptor.find( ::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE() );
251 if ( pIt != lModelDescriptor.end() )
252 lDescriptor[::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE()] = pIt->second;
255 return lDescriptor;
258 /*-----------------------------------------------
259 20.08.2003 09:49
260 -----------------------------------------------*/
261 void LoadEnv::initializeLoading(const ::rtl::OUString& sURL ,
262 const css::uno::Sequence< css::beans::PropertyValue >& lMediaDescriptor,
263 const css::uno::Reference< css::frame::XFrame >& xBaseFrame ,
264 const ::rtl::OUString& sTarget ,
265 sal_Int32 nSearchFlags ,
266 EFeature eFeature , // => use default ...
267 EContentType eContentType ) // => use default ...
268 throw(LoadEnvException, css::uno::RuntimeException)
270 // SAFE -> ----------------------------------
271 WriteGuard aWriteLock(m_aLock);
273 // Handle still running processes!
274 if (m_xAsynchronousJob.is())
275 throw LoadEnvException(LoadEnvException::ID_STILL_RUNNING);
277 // take over all new parameters.
278 m_xTargetFrame.clear();
279 m_xBaseFrame = xBaseFrame ;
280 m_lMediaDescriptor = impl_mergeMediaDescriptorWithMightExistingModelArgs(lMediaDescriptor);
281 m_sTarget = sTarget ;
282 m_nSearchFlags = nSearchFlags ;
283 m_eFeature = eFeature ;
284 m_eContentType = eContentType ;
285 m_bCloseFrameOnError = sal_False ;
286 m_bReactivateControllerOnError = sal_False ;
287 m_bLoaded = sal_False ;
289 // try to find out, if its realy a content, which can be loaded or must be "handled"
290 // We use a default value for this in-parameter. Then we have to start a complex check method
291 // internaly. But if this check was already done outside it can be supressed to perform
292 // the load request. We take over the result then!
293 if (m_eContentType == E_UNSUPPORTED_CONTENT)
295 m_eContentType = LoadEnv::classifyContent(sURL, lMediaDescriptor);
296 if (m_eContentType == E_UNSUPPORTED_CONTENT)
297 throw LoadEnvException(LoadEnvException::ID_UNSUPPORTED_CONTENT);
300 // make URL part of the MediaDescriptor
301 // It doesnt mater, if its already an item of it.
302 // It must be the same value ... so we can overwrite it :-)
303 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_URL()] <<= sURL;
305 // parse it - because some following code require that
306 m_aURL.Complete = sURL;
307 css::uno::Reference< css::util::XURLTransformer > xParser(m_xSMGR->createInstance(SERVICENAME_URLTRANSFORMER), css::uno::UNO_QUERY);
308 xParser->parseStrict(m_aURL);
310 // BTW: Split URL and JumpMark ...
311 // Because such mark is an explicit value of the media descriptor!
312 if (m_aURL.Mark.getLength())
313 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_JUMPMARK()] <<= m_aURL.Mark;
315 // By the way: remove the old and deprecated value "FileName" from the descriptor!
316 ::comphelper::MediaDescriptor::iterator pIt = m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_FILENAME());
317 if (pIt != m_lMediaDescriptor.end())
318 m_lMediaDescriptor.erase(pIt);
320 // patch the MediaDescriptor, so it fullfill the outside requirements
321 // Means especialy items like e.g. UI InteractionHandler, Status Indicator,
322 // MacroExecutionMode etcpp.
324 /*TODO progress is bound to a frame ... How can we set it here? */
326 css::uno::Reference< css::task::XInteractionHandler > xInteractionHandler;
327 sal_Int16 nMacroMode ;
328 sal_Int16 nUpdateMode ;
330 // UI mode
331 if (
332 ((m_eFeature & E_WORK_WITH_UI) == E_WORK_WITH_UI) &&
333 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN() , sal_False) == sal_False ) &&
334 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_PREVIEW(), sal_False) == sal_False )
337 nMacroMode = css::document::MacroExecMode::USE_CONFIG;
338 nUpdateMode = css::document::UpdateDocMode::ACCORDING_TO_CONFIG;
341 xInteractionHandler = css::uno::Reference< css::task::XInteractionHandler >(m_xSMGR->createInstance(IMPLEMENTATIONNAME_UIINTERACTIONHANDLER), css::uno::UNO_QUERY);
343 catch(const css::uno::RuntimeException&) {throw;}
344 catch(const css::uno::Exception& ) { }
346 // hidden mode
347 else
349 nMacroMode = css::document::MacroExecMode::NEVER_EXECUTE;
350 nUpdateMode = css::document::UpdateDocMode::NO_UPDATE;
351 StillInteraction* pInteraction = new StillInteraction();
352 xInteractionHandler = css::uno::Reference< css::task::XInteractionHandler >(static_cast< css::task::XInteractionHandler* >(pInteraction), css::uno::UNO_QUERY);
355 if (
356 (xInteractionHandler.is() ) &&
357 (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_INTERACTIONHANDLER()) == m_lMediaDescriptor.end())
360 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_INTERACTIONHANDLER()] <<= xInteractionHandler;
363 if (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE()) == m_lMediaDescriptor.end())
364 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE()] <<= nMacroMode;
366 if (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_UPDATEDOCMODE()) == m_lMediaDescriptor.end())
367 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_UPDATEDOCMODE()] <<= nUpdateMode;
369 aWriteLock.unlock();
370 // <- SAFE ----------------------------------
373 /*-----------------------------------------------
374 15.08.2003 08:16
375 -----------------------------------------------*/
376 void LoadEnv::startLoading()
377 throw(LoadEnvException, css::uno::RuntimeException)
379 // SAFE ->
380 ReadGuard aReadLock(m_aLock);
382 // Handle still running processes!
383 if (m_xAsynchronousJob.is())
384 throw LoadEnvException(LoadEnvException::ID_STILL_RUNNING);
386 // content can not be loaded or handled
387 // check "classifyContent()" failed before ...
388 if (m_eContentType == E_UNSUPPORTED_CONTENT)
389 throw LoadEnvException(LoadEnvException::ID_UNSUPPORTED_CONTENT);
391 // <- SAFE
392 aReadLock.unlock();
394 // detect its type/filter etcpp.
395 // These information will be available by the
396 // used descriptor member afterwards and is needed
397 // for all following operations!
398 // Note: An exception will be thrown, in case operation was not successfully ...
399 if (m_eContentType != E_CAN_BE_SET)/* Attention: special feature to set existing component on a frame must ignore type detection! */
400 impl_detectTypeAndFilter();
402 // start loading the content ...
403 // Attention: Dont check m_eContentType deeper then UNSUPPORTED/SUPPORTED!
404 // Because it was made in th easiest way ... may a flat detection was made only.
405 // And such simple detection can fail some times .-)
406 // Use another strategy here. Try it and let it run into the case "loading not possible".
407 sal_Bool bStarted = sal_False;
408 if (
409 ((m_eFeature & E_ALLOW_CONTENTHANDLER) == E_ALLOW_CONTENTHANDLER) &&
410 (m_eContentType != E_CAN_BE_SET ) /* Attention: special feature to set existing component on a frame must ignore type detection! */
413 bStarted = impl_handleContent();
416 if (!bStarted)
417 bStarted = impl_loadContent();
419 // not started => general error
420 // We cant say - what was the reason for.
421 if (!bStarted)
422 throw LoadEnvException(LoadEnvException::ID_GENERAL_ERROR);
425 /*-----------------------------------------------
426 15.08.2003 09:50
427 TODO
428 First draft does not implement timeout using [ms].
429 Current implementation counts yield calls only ...
430 -----------------------------------------------*/
431 sal_Bool LoadEnv::waitWhileLoading(sal_uInt32 nTimeout)
432 throw(LoadEnvException, css::uno::RuntimeException)
434 // Because its not a good idea to block the main thread
435 // (and we cant be shure that we are currently not used inside the
436 // main thread!), we cant use conditions here realy. We must yield
437 // in an intellegent manner :-)
439 sal_Int32 nTime = nTimeout;
440 while(true)
442 // SAFE -> ------------------------------
443 ReadGuard aReadLock1(m_aLock);
444 if (!m_xAsynchronousJob.is())
445 break;
446 aReadLock1.unlock();
447 // <- SAFE ------------------------------
449 Application::Yield();
451 // forever!
452 if (nTimeout==0)
453 continue;
455 // timed out?
456 --nTime;
457 if (nTime<1)
458 break;
461 // SAFE -> ----------------------------------
462 ReadGuard aReadLock2(m_aLock);
463 return !m_xAsynchronousJob.is();
464 // <- SAFE ----------------------------------
467 /*-----------------------------------------------
468 20.08.2003 10:00
469 -----------------------------------------------*/
470 void LoadEnv::cancelLoading()
471 throw(LoadEnvException, css::uno::RuntimeException)
473 // PARTIAL(!) SAFE -> ------------------------------
474 ReadGuard aReadLock(m_aLock);
476 // Still running? Might waitWhileLoading()
477 // runned into the timeout!
478 if (m_xAsynchronousJob.is())
480 // try to cancel it ... if its an asynchronous frame loader
481 css::uno::Reference< css::frame::XFrameLoader > xAsyncLoader(m_xAsynchronousJob, css::uno::UNO_QUERY);
482 if (xAsyncLoader.is())
484 aReadLock.unlock();
485 // <- BREAK SAFE ------------------------------
486 xAsyncLoader->cancel();
487 // <- RESTART SAFE ----------------------------
488 aReadLock.lock();
489 /* Attention:
490 After returning from any cancel/dispose call, neither the frame nor weself
491 may be called back. Because only we can cancel this job, we already know
492 the result! => Thats why its not usefull nor neccessary to wait for any
493 asynchronous listener notification.
495 m_bLoaded = sal_False;
496 m_xAsynchronousJob.clear();
498 // or may be its a content handler? Such handler cant be cancelled in its running
499 // operation :-( And we cant deregister us there again :-(
500 // => The only chance is an exception :-)
501 else
502 throw LoadEnvException(LoadEnvException::ID_STILL_RUNNING);
505 impl_reactForLoadingState();
507 aReadLock.unlock();
508 // <- PARTIAL(!) SAFE ------------------------------
511 /*-----------------------------------------------
512 14.08.2003 13:33
513 -----------------------------------------------*/
514 css::uno::Reference< css::frame::XFrame > LoadEnv::getTarget() const
516 // SAFE ->
517 ReadGuard aReadLock(m_aLock);
518 return m_xTargetFrame;
519 // <- SAFE
522 /*-----------------------------------------------
523 14.08.2003 13:35
524 -----------------------------------------------*/
525 css::uno::Reference< css::lang::XComponent > LoadEnv::getTargetComponent() const
527 // SAFE ->
528 ReadGuard aReadLock(m_aLock);
530 if (!m_xTargetFrame.is())
531 return css::uno::Reference< css::lang::XComponent >();
533 css::uno::Reference< css::frame::XController > xController = m_xTargetFrame->getController();
534 if (!xController.is())
535 return css::uno::Reference< css::lang::XComponent >(m_xTargetFrame->getComponentWindow(), css::uno::UNO_QUERY);
537 css::uno::Reference< css::frame::XModel > xModel = xController->getModel();
538 if (!xModel.is())
539 return css::uno::Reference< css::lang::XComponent >(xController, css::uno::UNO_QUERY);
541 return css::uno::Reference< css::lang::XComponent >(xModel, css::uno::UNO_QUERY);
542 // <- SAFE
545 /*-----------------------------------------------
546 15.08.2003 11:15
547 -----------------------------------------------*/
548 void SAL_CALL LoadEnvListener::loadFinished(const css::uno::Reference< css::frame::XFrameLoader >&)
549 throw(css::uno::RuntimeException)
551 // SAFE -> ----------------------------------
552 WriteGuard aWriteLock(m_aLock);
554 if (m_ppCheck && *m_ppCheck)
555 m_pLoadEnv->impl_setResult(sal_True);
556 m_ppCheck = NULL;
558 aWriteLock.unlock();
559 // <- SAFE ----------------------------------
562 /*-----------------------------------------------
563 14.10.2003 12:23
564 -----------------------------------------------*/
565 void SAL_CALL LoadEnvListener::loadCancelled(const css::uno::Reference< css::frame::XFrameLoader >&)
566 throw(css::uno::RuntimeException)
568 // SAFE -> ----------------------------------
569 WriteGuard aWriteLock(m_aLock);
571 if (m_ppCheck && *m_ppCheck)
572 m_pLoadEnv->impl_setResult(sal_False);
573 m_ppCheck = NULL;
575 aWriteLock.unlock();
576 // <- SAFE ----------------------------------
579 /*-----------------------------------------------
580 14.10.2003 12:23
581 -----------------------------------------------*/
582 void SAL_CALL LoadEnvListener::dispatchFinished(const css::frame::DispatchResultEvent& aEvent)
583 throw(css::uno::RuntimeException)
585 // SAFE -> ----------------------------------
586 WriteGuard aWriteLock(m_aLock);
588 if (!m_ppCheck || !*m_ppCheck)
589 return;
591 switch(aEvent.State)
593 case css::frame::DispatchResultState::FAILURE :
594 m_pLoadEnv->impl_setResult(sal_False);
595 break;
597 case css::frame::DispatchResultState::SUCCESS :
598 m_pLoadEnv->impl_setResult(sal_False);
599 break;
601 case css::frame::DispatchResultState::DONTKNOW :
602 m_pLoadEnv->impl_setResult(sal_False);
603 break;
605 m_ppCheck = NULL;
607 aWriteLock.unlock();
608 // <- SAFE ----------------------------------
611 /*-----------------------------------------------
612 14.10.2003 12:24
613 -----------------------------------------------*/
614 void SAL_CALL LoadEnvListener::disposing(const css::lang::EventObject&)
615 throw(css::uno::RuntimeException)
617 // SAFE -> ----------------------------------
618 WriteGuard aWriteLock(m_aLock);
620 if (m_ppCheck && *m_ppCheck)
621 m_pLoadEnv->impl_setResult(sal_False);
622 m_ppCheck = NULL;
624 aWriteLock.unlock();
625 // <- SAFE ----------------------------------
628 /*-----------------------------------------------
629 14.10.2003 12:20
630 -----------------------------------------------*/
631 void LoadEnv::impl_setResult(sal_Bool bResult)
633 // SAFE -> ----------------------------------
634 WriteGuard aWriteLock(m_aLock);
636 m_bLoaded = bResult;
638 impl_reactForLoadingState();
640 // clearing of this reference will unblock waitWhileLoading()!
641 // So we must be shure, that loading process was realy finished.
642 // => do it as last operation of this method ...
643 m_xAsynchronousJob.clear();
645 aWriteLock.unlock();
646 // <- SAFE ----------------------------------
649 /*-----------------------------------------------
650 06.02.2004 14:03
651 TODO: Is it a good idea to change Sequence<>
652 parameter to stl-adapter?
653 -----------------------------------------------*/
654 LoadEnv::EContentType LoadEnv::classifyContent(const ::rtl::OUString& sURL ,
655 const css::uno::Sequence< css::beans::PropertyValue >& lMediaDescriptor)
657 //-------------------------------------------
658 // (i) Filter some special well known URL protocols,
659 // which can not be handled or loaded in general.
660 // Of course an empty URL must be ignored here too.
661 // Note: These URL schemata are fix and well known ...
662 // But there can be some additional ones, which was not
663 // defined at implementation time of this class :-(
664 // So we have to make shure, that the following code
665 // can detect such protocol schemata too :-)
668 (!sURL.getLength() ) ||
669 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_UNO )) ||
670 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_SLOT )) ||
671 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_MACRO )) ||
672 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_SERVICE)) ||
673 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_MAILTO )) ||
674 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_NEWS ))
677 return E_UNSUPPORTED_CONTENT;
680 //-------------------------------------------
681 // (ii) Some special URLs indicates a given input stream,
682 // a full featured document model directly or
683 // specify a request for opening an empty document.
684 // Such contents are loadable in general.
685 // But we have to check, if the media descriptor contains
686 // all needed resources. If they are missing - the following
687 // load request will fail.
689 /* Attention: The following code cant work on such special URLs!
690 It should not break the office .. but it make no sense
691 to start expensive object creations and complex search
692 algorithm if its clear, that such URLs must be handled
693 in a special way .-)
696 // creation of new documents
697 if (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_PRIVATE_FACTORY))
698 return E_CAN_BE_LOADED;
700 // using of an existing input stream
701 ::comphelper::MediaDescriptor stlMediaDescriptor(lMediaDescriptor);
702 ::comphelper::MediaDescriptor::const_iterator pIt;
703 if (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_PRIVATE_STREAM))
705 pIt = stlMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_INPUTSTREAM());
706 css::uno::Reference< css::io::XInputStream > xStream;
707 if (pIt != stlMediaDescriptor.end())
708 pIt->second >>= xStream;
709 if (xStream.is())
710 return E_CAN_BE_LOADED;
711 LOG_WARNING("LoadEnv::classifyContent()", "loading from stream with right URL but invalid stream detected")
712 return E_UNSUPPORTED_CONTENT;
715 // using of a full featured document
716 if (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_PRIVATE_OBJECT))
718 pIt = stlMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_MODEL());
719 css::uno::Reference< css::frame::XModel > xModel;
720 if (pIt != stlMediaDescriptor.end())
721 pIt->second >>= xModel;
722 if (xModel.is())
723 return E_CAN_BE_SET;
724 LOG_WARNING("LoadEnv::classifyContent()", "loading with object with right URL but invalid object detected")
725 return E_UNSUPPORTED_CONTENT;
728 // following operatons can work on an internal type name only :-(
729 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = ::utl::getProcessServiceFactory();
730 css::uno::Reference< css::document::XTypeDetection > xDetect(xSMGR->createInstance(SERVICENAME_TYPEDETECTION), css::uno::UNO_QUERY);
732 ::rtl::OUString sType = xDetect->queryTypeByURL(sURL);
734 css::uno::Sequence< css::beans::NamedValue > lQuery(1) ;
735 css::uno::Reference< css::container::XContainerQuery > xContainer ;
736 css::uno::Reference< css::container::XEnumeration > xSet ;
737 css::uno::Sequence< ::rtl::OUString > lTypesReg(1);
740 //-------------------------------------------
741 lQuery[0].Name = ::framework::constant::Filter::PROP_TYPE;
742 lQuery[0].Value <<= sType;
744 xContainer = css::uno::Reference< css::container::XContainerQuery >(xSMGR->createInstance(SERVICENAME_FILTERFACTORY), css::uno::UNO_QUERY);
745 xSet = xContainer->createSubSetEnumerationByProperties(lQuery);
746 // at least one registered frame loader is enough!
747 if (xSet->hasMoreElements())
748 return E_CAN_BE_LOADED;
751 //-------------------------------------------
752 // (iii) If a FrameLoader service (or at least
753 // a Filter) can be found, which supports
754 // this URL - it must be a loadable content.
755 // Because both items are registered for types
756 // its enough to check for frame loaders only.
757 // Mos of our filters are handled by our global
758 // default loader. But there exist some specialized
759 // loader, which does not work on top of filters!
760 // So its not enough to search on the filter configuration.
761 // Further its not enough to search for types!
762 // Because there exist some types, which are referenced by
763 // other objects ... but not by filters nor frame loaders!
765 lTypesReg[0] = sType;
766 lQuery[0].Name = ::framework::constant::FrameLoader::PROP_TYPES;
767 lQuery[0].Value <<= lTypesReg;
769 xContainer = css::uno::Reference< css::container::XContainerQuery >(xSMGR->createInstance(SERVICENAME_FRAMELOADERFACTORY), css::uno::UNO_QUERY);
770 xSet = xContainer->createSubSetEnumerationByProperties(lQuery);
771 // at least one registered frame loader is enough!
772 if (xSet->hasMoreElements())
773 return E_CAN_BE_LOADED;
775 //-------------------------------------------
776 // (iv) Some URL protocols are supported by special services.
777 // E.g. ContentHandler.
778 // Such contents can be handled ... but not loaded.
780 lTypesReg[0] = sType;
781 lQuery[0].Name = ::framework::constant::ContentHandler::PROP_TYPES;
782 lQuery[0].Value <<= lTypesReg;
784 xContainer = css::uno::Reference< css::container::XContainerQuery >(xSMGR->createInstance(SERVICENAME_CONTENTHANDLERFACTORY), css::uno::UNO_QUERY);
785 xSet = xContainer->createSubSetEnumerationByProperties(lQuery);
786 // at least one registered content handler is enough!
787 if (xSet->hasMoreElements())
788 return E_CAN_BE_HANDLED;
790 //-------------------------------------------
791 // (v) Last but not least the UCB is used inside office to
792 // load contents. He has a special configuration to know
793 // which URL schemata can be used inside office.
794 css::uno::Reference< css::ucb::XContentProviderManager > xUCB(xSMGR->createInstance(SERVICENAME_UCBCONTENTBROKER), css::uno::UNO_QUERY);
795 if (xUCB->queryContentProvider(sURL).is())
796 return E_CAN_BE_LOADED;
798 //-------------------------------------------
799 // (TODO) At this point, we have no idea .-)
800 // But it seems to be better, to break all
801 // further requests for this URL. Otherwhise
802 // we can run into some trouble.
803 LOG_WARNING("LoadEnv::classifyContent()", "realy an unsupported content?")
804 return E_UNSUPPORTED_CONTENT;
807 /*-----------------------------------------------
808 03.11.2003 09:31
809 -----------------------------------------------*/
810 void LoadEnv::impl_detectTypeAndFilter()
811 throw(LoadEnvException, css::uno::RuntimeException)
813 static ::rtl::OUString TYPEPROP_PREFERREDFILTER = ::rtl::OUString::createFromAscii("PreferredFilter");
814 static ::rtl::OUString FILTERPROP_FLAGS = ::rtl::OUString::createFromAscii("Flags" );
815 static sal_Int32 FILTERFLAG_TEMPLATEPATH = 16;
817 // SAFE ->
818 ReadGuard aReadLock(m_aLock);
820 // Attention: Because our stl media descriptor is a copy of an uno sequence
821 // we cant use as an in/out parameter here. Copy it before and dont forget to
822 // actualize structure afterwards again!
823 css::uno::Sequence< css::beans::PropertyValue > lDescriptor = m_lMediaDescriptor.getAsConstPropertyValueList();
824 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
826 aReadLock.unlock();
827 // <- SAFE
829 ::rtl::OUString sType;
830 css::uno::Reference< css::document::XTypeDetection > xDetect(xSMGR->createInstance(SERVICENAME_TYPEDETECTION), css::uno::UNO_QUERY);
831 if (xDetect.is())
832 sType = xDetect->queryTypeByDescriptor(lDescriptor, sal_True); /*TODO should deep detection be able for enable/disable it from outside? */
834 // no valid content -> loading not possible
835 if (!sType.getLength())
836 throw LoadEnvException(LoadEnvException::ID_UNSUPPORTED_CONTENT);
838 // SAFE ->
839 WriteGuard aWriteLock(m_aLock);
841 // detection was successfully => update the descriptor member of this class
842 m_lMediaDescriptor << lDescriptor;
843 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_TYPENAME()] <<= sType;
844 // Is there an already detected (may be preselected) filter?
845 // see below ...
846 ::rtl::OUString sFilter = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_FILTERNAME(), ::rtl::OUString());
848 aWriteLock.unlock();
849 // <- SAFE
851 // But the type isnt enough. For loading sometimes we need more informations.
852 // E.g. for our "_default" feature, where we recylce any frame which contains
853 // and "Untitled" document, we must know if the new document is based on a template!
854 // But this information is available as a filter property only.
855 // => We must try(!) to detect the right filter for this load request.
856 // On the other side ... if no filter is available .. ignore it.
857 // Then the type information must be enough.
858 if (!sFilter.getLength())
860 // no -> try to find a preferred filter for the detected type.
861 // Dont forget to updatet he media descriptor.
862 css::uno::Reference< css::container::XNameAccess > xTypeCont(xDetect, css::uno::UNO_QUERY_THROW);
865 ::comphelper::SequenceAsHashMap lTypeProps(xTypeCont->getByName(sType));
866 sFilter = lTypeProps.getUnpackedValueOrDefault(TYPEPROP_PREFERREDFILTER, ::rtl::OUString());
867 if (sFilter.getLength())
869 // SAFE ->
870 aWriteLock.lock();
871 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_FILTERNAME()] <<= sFilter;
872 aWriteLock.unlock();
873 // <- SAFE
876 catch(const css::container::NoSuchElementException&)
880 // check if the filter (if one exists) points to a template format filter.
881 // Then we have to add the property "AsTemplate".
882 // We need this information to decide afterwards if we can use a "recycle frame"
883 // for target "_default" or has to create a new one everytimes.
884 // On the other side we have to supress that, if this property already exists
885 // and should trigger a special handling. Then the outside calli of this method here,
886 // has to know, what he is doing .-)
888 sal_Bool bIsOwnTemplate = sal_False;
889 if (sFilter.getLength())
891 css::uno::Reference< css::container::XNameAccess > xFilterCont(xSMGR->createInstance(SERVICENAME_FILTERFACTORY), css::uno::UNO_QUERY_THROW);
894 ::comphelper::SequenceAsHashMap lFilterProps(xFilterCont->getByName(sFilter));
895 sal_Int32 nFlags = lFilterProps.getUnpackedValueOrDefault(FILTERPROP_FLAGS, (sal_Int32)0);
896 bIsOwnTemplate = ((nFlags & FILTERFLAG_TEMPLATEPATH) == FILTERFLAG_TEMPLATEPATH);
898 catch(const css::container::NoSuchElementException&)
901 if (bIsOwnTemplate)
903 // SAFE ->
904 aWriteLock.lock();
905 // Dont overwrite external decisions! See comments before ...
906 ::comphelper::MediaDescriptor::const_iterator pAsTemplateItem = m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_ASTEMPLATE());
907 if (pAsTemplateItem == m_lMediaDescriptor.end())
908 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_ASTEMPLATE()] <<= sal_True;
909 aWriteLock.unlock();
910 // <- SAFE
914 /*-----------------------------------------------
915 15.08.2003 09:38
916 -----------------------------------------------*/
917 sal_Bool LoadEnv::impl_handleContent()
918 throw(LoadEnvException, css::uno::RuntimeException)
920 // SAFE -> -----------------------------------
921 ReadGuard aReadLock(m_aLock);
923 // the type must exist inside the descriptor ... otherwhise this class is implemented wrong :-)
924 ::rtl::OUString sType = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_TYPENAME(), ::rtl::OUString());
925 if (!sType.getLength())
926 throw LoadEnvException(LoadEnvException::ID_INVALID_MEDIADESCRIPTOR);
928 // convert media descriptor and URL to right format for later interface call!
929 css::uno::Sequence< css::beans::PropertyValue > lDescriptor;
930 m_lMediaDescriptor >> lDescriptor;
931 css::util::URL aURL = m_aURL;
933 // get neccessary container to query for a handler object
934 css::uno::Reference< css::lang::XMultiServiceFactory > xFactory(m_xSMGR->createInstance(SERVICENAME_CONTENTHANDLERFACTORY), css::uno::UNO_QUERY);
935 css::uno::Reference< css::container::XContainerQuery > xQuery (xFactory , css::uno::UNO_QUERY);
937 aReadLock.unlock();
938 // <- SAFE -----------------------------------
940 // query
941 css::uno::Sequence< ::rtl::OUString > lTypeReg(1);
942 lTypeReg[0] = sType;
944 css::uno::Sequence< css::beans::NamedValue > lQuery(1);
945 lQuery[0].Name = ::framework::constant::ContentHandler::PROP_TYPES;
946 lQuery[0].Value <<= lTypeReg;
948 css::uno::Reference< css::container::XEnumeration > xSet = xQuery->createSubSetEnumerationByProperties(lQuery);
949 while(xSet->hasMoreElements())
951 ::comphelper::SequenceAsHashMap lProps (xSet->nextElement());
952 ::rtl::OUString sHandler = lProps.getUnpackedValueOrDefault(::framework::constant::ContentHandler::PROP_NAME, ::rtl::OUString());
954 css::uno::Reference< css::frame::XNotifyingDispatch > xHandler;
957 xHandler = css::uno::Reference< css::frame::XNotifyingDispatch >(xFactory->createInstance(sHandler), css::uno::UNO_QUERY);
958 if (!xHandler.is())
959 continue;
961 catch(const css::uno::RuntimeException&)
962 { throw; }
963 catch(const css::uno::Exception&)
964 { continue; }
966 // SAFE -> -----------------------------------
967 WriteGuard aWriteLock(m_aLock);
968 m_xAsynchronousJob = xHandler;
969 m_pCheck = this;
970 LoadEnvListener* pListener = new LoadEnvListener(m_pCheck, this);
971 aWriteLock.unlock();
972 // <- SAFE -----------------------------------
974 css::uno::Reference< css::frame::XDispatchResultListener > xListener(static_cast< css::frame::XDispatchResultListener* >(pListener), css::uno::UNO_QUERY);
975 xHandler->dispatchWithNotification(aURL, lDescriptor, xListener);
977 return sal_True;
980 return sal_False;
983 //-----------------------------------------------
984 sal_Bool LoadEnv::impl_furtherDocsAllowed()
986 // SAFE ->
987 ReadGuard aReadLock(m_aLock);
988 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
989 aReadLock.unlock();
990 // <- SAFE
992 sal_Bool bAllowed = sal_True;
996 css::uno::Any aVal = ::comphelper::ConfigurationHelper::readDirectKey(
997 xSMGR,
998 ::rtl::OUString::createFromAscii("org.openoffice.Office.Common/"),
999 ::rtl::OUString::createFromAscii("Misc"),
1000 ::rtl::OUString::createFromAscii("MaxOpenDocuments"),
1001 ::comphelper::ConfigurationHelper::E_READONLY);
1003 // NIL means: count of allowed documents = infinite !
1004 // => return TRUE
1005 if ( ! aVal.hasValue())
1006 bAllowed = sal_True;
1007 else
1009 sal_Int32 nMaxOpenDocuments = 0;
1010 aVal >>= nMaxOpenDocuments;
1012 css::uno::Reference< css::frame::XFramesSupplier > xDesktop(
1013 xSMGR->createInstance(SERVICENAME_DESKTOP),
1014 css::uno::UNO_QUERY_THROW);
1016 FrameListAnalyzer aAnalyzer(xDesktop,
1017 css::uno::Reference< css::frame::XFrame >(),
1018 FrameListAnalyzer::E_HELP |
1019 FrameListAnalyzer::E_BACKINGCOMPONENT |
1020 FrameListAnalyzer::E_HIDDEN);
1022 sal_Int32 nOpenDocuments = aAnalyzer.m_lOtherVisibleFrames.getLength();
1023 bAllowed = (nOpenDocuments < nMaxOpenDocuments);
1026 catch(const css::uno::Exception&)
1027 { bAllowed = sal_True; } // !! internal errors are no reason to disturb the office from opening documents .-)
1029 if ( ! bAllowed )
1031 // SAFE ->
1032 aReadLock.lock();
1033 css::uno::Reference< css::task::XInteractionHandler > xInteraction = m_lMediaDescriptor.getUnpackedValueOrDefault(
1034 ::comphelper::MediaDescriptor::PROP_INTERACTIONHANDLER(),
1035 css::uno::Reference< css::task::XInteractionHandler >());
1036 aReadLock.unlock();
1037 // <- SAFE
1039 if (xInteraction.is())
1041 css::uno::Any aInteraction;
1042 css::uno::Sequence< css::uno::Reference< css::task::XInteractionContinuation > > lContinuations(2);
1044 ContinuationAbort* pAbort = new ContinuationAbort();
1045 ContinuationApprove* pApprove = new ContinuationApprove();
1047 lContinuations[0] = css::uno::Reference< css::task::XInteractionContinuation >(
1048 static_cast< css::task::XInteractionContinuation* >(pAbort),
1049 css::uno::UNO_QUERY_THROW);
1050 lContinuations[1] = css::uno::Reference< css::task::XInteractionContinuation >(
1051 static_cast< css::task::XInteractionContinuation* >(pApprove),
1052 css::uno::UNO_QUERY_THROW);
1054 css::task::ErrorCodeRequest aErrorCode;
1055 aErrorCode.ErrCode = ERRCODE_SFX_NOMOREDOCUMENTSALLOWED;
1056 aInteraction <<= aErrorCode;
1058 InteractionRequest* pRequest = new InteractionRequest(aInteraction, lContinuations);
1059 css::uno::Reference< css::task::XInteractionRequest > xRequest(
1060 static_cast< css::task::XInteractionRequest* >(pRequest),
1061 css::uno::UNO_QUERY_THROW);
1063 xInteraction->handle(xRequest);
1067 return bAllowed;
1070 //-----------------------------------------------
1071 sal_Bool LoadEnv::impl_loadContent()
1072 throw(LoadEnvException, css::uno::RuntimeException)
1074 // SAFE -> -----------------------------------
1075 WriteGuard aWriteLock(m_aLock);
1077 // search or create right target frame
1078 ::rtl::OUString sTarget = m_sTarget;
1079 if (TargetHelper::matchSpecialTarget(sTarget, TargetHelper::E_DEFAULT))
1081 m_xTargetFrame = impl_searchAlreadyLoaded();
1082 if (m_xTargetFrame.is())
1084 impl_setResult(sal_True);
1085 return sal_True;
1087 m_xTargetFrame = impl_searchRecycleTarget();
1090 if (! m_xTargetFrame.is())
1092 if (
1093 (TargetHelper::matchSpecialTarget(sTarget, TargetHelper::E_BLANK )) ||
1094 (TargetHelper::matchSpecialTarget(sTarget, TargetHelper::E_DEFAULT))
1097 if (! impl_furtherDocsAllowed())
1098 return sal_False;
1099 m_xTargetFrame = m_xBaseFrame->findFrame(SPECIALTARGET_BLANK, 0);
1100 m_bCloseFrameOnError = m_xTargetFrame.is();
1102 else
1104 sal_Int32 nFlags = m_nSearchFlags & ~css::frame::FrameSearchFlag::CREATE;
1105 m_xTargetFrame = m_xBaseFrame->findFrame(sTarget, nFlags);
1106 if (! m_xTargetFrame.is())
1108 if (! impl_furtherDocsAllowed())
1109 return sal_False;
1110 m_xTargetFrame = m_xBaseFrame->findFrame(SPECIALTARGET_BLANK, 0);
1111 m_bCloseFrameOnError = m_xTargetFrame.is();
1116 // If we couldn't find a valid frame or the frame has no container window
1117 // we have to throw an exception.
1118 if (
1119 ( ! m_xTargetFrame.is() ) ||
1120 ( ! m_xTargetFrame->getContainerWindow().is() )
1122 throw LoadEnvException(LoadEnvException::ID_NO_TARGET_FOUND);
1124 css::uno::Reference< css::frame::XFrame > xTargetFrame = m_xTargetFrame;
1126 // Now we have a valid frame ... and type detection was already done.
1127 // We should apply the module dependend window position and size to the
1128 // frame window.
1129 impl_applyPersistentWindowState(xTargetFrame->getContainerWindow());
1131 // Don't forget to lock task for following load process. Otherwise it could die
1132 // during this operation runs by terminating the office or closing this task via api.
1133 // If we set this lock "close()" will return false and closing will be broken.
1134 // Attention: Don't forget to reset this lock again after finishing operation.
1135 // Otherwise task AND office couldn't die!!!
1136 // This includes gracefully handling of Exceptions (Runtime!) too ...
1137 // Thats why we use a specialized guard, which will reset the lock
1138 // if it will be run out of scope.
1140 // Note further: ignore if this internal guard already contains a resource.
1141 // Might impl_searchRecylcTarget() set it before. But incase this impl-method wasnt used
1142 // and the target frame was new created ... this lock here must be set!
1143 css::uno::Reference< css::document::XActionLockable > xTargetLock(xTargetFrame, css::uno::UNO_QUERY);
1144 m_aTargetLock.setResource(xTargetLock);
1146 // Add status indicator to descriptor. Loader can show an progresses then.
1147 // But don't do it, if loading should be hidden or preview is used ...!
1148 // So we prevent our code against wrong using. Why?
1149 // It could be, that using of this progress could make trouble. e.g. He make window visible ...
1150 // but shouldn't do that. But if no indicator is available ... nobody has a chance to do that!
1151 sal_Bool bHidden = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN() , sal_False );
1152 sal_Bool bMinimized = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_MINIMIZED() , sal_False );
1153 sal_Bool bPreview = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_PREVIEW() , sal_False );
1154 css::uno::Reference< css::task::XStatusIndicator > xProgress = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_STATUSINDICATOR(), css::uno::Reference< css::task::XStatusIndicator >());
1156 if (!bHidden && !bMinimized && !bPreview && !xProgress.is())
1158 // Note: its an optional interface!
1159 css::uno::Reference< css::task::XStatusIndicatorFactory > xProgressFactory(xTargetFrame, css::uno::UNO_QUERY);
1160 if (xProgressFactory.is())
1162 xProgress = xProgressFactory->createStatusIndicator();
1163 if (xProgress.is())
1164 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_STATUSINDICATOR()] <<= xProgress;
1168 // convert media descriptor and URL to right format for later interface call!
1169 css::uno::Sequence< css::beans::PropertyValue > lDescriptor;
1170 m_lMediaDescriptor >> lDescriptor;
1171 ::rtl::OUString sURL = m_aURL.Complete;
1173 // try to locate any interested frame loader
1174 css::uno::Reference< css::uno::XInterface > xLoader = impl_searchLoader();
1175 css::uno::Reference< css::frame::XFrameLoader > xAsyncLoader(xLoader, css::uno::UNO_QUERY);
1176 css::uno::Reference< css::frame::XSynchronousFrameLoader > xSyncLoader (xLoader, css::uno::UNO_QUERY);
1178 if (xAsyncLoader.is())
1180 // SAFE -> -----------------------------------
1181 aWriteLock.lock();
1182 m_xAsynchronousJob = xAsyncLoader;
1183 m_pCheck = this;
1184 LoadEnvListener* pListener = new LoadEnvListener(m_pCheck, this);
1185 aWriteLock.unlock();
1186 // <- SAFE -----------------------------------
1188 css::uno::Reference< css::frame::XLoadEventListener > xListener(static_cast< css::frame::XLoadEventListener* >(pListener), css::uno::UNO_QUERY);
1189 xAsyncLoader->load(xTargetFrame, sURL, lDescriptor, xListener);
1191 return sal_True;
1193 else
1194 if (xSyncLoader.is())
1196 sal_Bool bResult = xSyncLoader->load(lDescriptor, xTargetFrame);
1197 // react for the result here, so the outside waiting
1198 // code can ask for it later.
1199 impl_setResult(bResult);
1200 // But the return value indicates a valid started(!) operation.
1201 // And thats true everxtimes, we reach this line :-)
1202 return sal_True;
1205 aWriteLock.unlock();
1206 // <- SAFE
1208 return sal_False;
1211 /*-----------------------------------------------
1212 06.02.2004 14:40
1213 -----------------------------------------------*/
1214 css::uno::Reference< css::uno::XInterface > LoadEnv::impl_searchLoader()
1216 // SAFE -> -----------------------------------
1217 ReadGuard aReadLock(m_aLock);
1219 // special mode to set an existing component on this frame
1220 // In such case the laoder is fix. It must be the SFX based implementation,
1221 // which can create a view on top of such xModel components :-)
1222 if (m_eContentType == E_CAN_BE_SET)
1226 return m_xSMGR->createInstance(IMPLEMENTATIONNAME_GENERICFRAMELOADER);
1228 catch(const css::uno::RuntimeException&)
1229 { throw; }
1230 catch(const css::uno::Exception&)
1232 throw LoadEnvException(LoadEnvException::ID_INVALID_ENVIRONMENT);
1235 // Otherwhise ...
1236 // We need this type information to locate an registered frame loader
1237 // Without such information we cant work!
1238 ::rtl::OUString sType = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_TYPENAME(), ::rtl::OUString());
1239 if (!sType.getLength())
1240 throw LoadEnvException(LoadEnvException::ID_INVALID_MEDIADESCRIPTOR);
1242 // try to locate any interested frame loader
1243 css::uno::Reference< css::lang::XMultiServiceFactory > xLoaderFactory(m_xSMGR->createInstance(SERVICENAME_FRAMELOADERFACTORY), css::uno::UNO_QUERY);
1244 css::uno::Reference< css::container::XContainerQuery > xQuery (xLoaderFactory , css::uno::UNO_QUERY);
1246 aReadLock.unlock();
1247 // <- SAFE -----------------------------------
1249 css::uno::Sequence< ::rtl::OUString > lTypesReg(1);
1250 lTypesReg[0] = sType;
1252 css::uno::Sequence< css::beans::NamedValue > lQuery(1);
1253 lQuery[0].Name = ::framework::constant::FrameLoader::PROP_TYPES;
1254 lQuery[0].Value <<= lTypesReg;
1256 css::uno::Reference< css::container::XEnumeration > xSet = xQuery->createSubSetEnumerationByProperties(lQuery);
1257 while(xSet->hasMoreElements())
1259 // try everyone ...
1260 // Ignore any loader, which makes trouble :-)
1261 ::comphelper::SequenceAsHashMap lLoaderProps(xSet->nextElement());
1262 ::rtl::OUString sLoader = lLoaderProps.getUnpackedValueOrDefault(::framework::constant::FrameLoader::PROP_NAME, ::rtl::OUString());
1263 css::uno::Reference< css::uno::XInterface > xLoader ;
1266 xLoader = xLoaderFactory->createInstance(sLoader);
1267 if (xLoader.is())
1268 return xLoader;
1270 catch(const css::uno::RuntimeException&)
1271 { throw; }
1272 catch(const css::uno::Exception&)
1273 { continue; }
1276 return css::uno::Reference< css::uno::XInterface >();
1279 /*-----------------------------------------------
1280 24.01.2006 15:11
1281 -----------------------------------------------*/
1282 void LoadEnv::impl_jumpToMark(const css::uno::Reference< css::frame::XFrame >& xFrame,
1283 const css::util::URL& aURL )
1285 if (! aURL.Mark.getLength())
1286 return;
1288 css::uno::Reference< css::frame::XDispatchProvider > xProvider(xFrame, css::uno::UNO_QUERY);
1289 if (! xProvider.is())
1290 return;
1292 // SAFE ->
1293 ReadGuard aReadLock(m_aLock);
1294 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
1295 aReadLock.unlock();
1296 // <- SAFE
1298 css::util::URL aCmd;
1299 aCmd.Complete = ::rtl::OUString::createFromAscii(".uno:JumpToMark");
1301 css::uno::Reference< css::util::XURLTransformer > xParser(xSMGR->createInstance(SERVICENAME_URLTRANSFORMER), css::uno::UNO_QUERY_THROW);
1302 xParser->parseStrict(aCmd);
1304 css::uno::Reference< css::frame::XDispatch > xDispatcher = xProvider->queryDispatch(aCmd, SPECIALTARGET_SELF, 0);
1305 if (! xDispatcher.is())
1306 return;
1308 ::comphelper::SequenceAsHashMap lArgs;
1309 lArgs[::rtl::OUString::createFromAscii("Bookmark")] <<= aURL.Mark;
1310 xDispatcher->dispatch(aCmd, lArgs.getAsConstPropertyValueList());
1313 /*-----------------------------------------------
1314 31.07.2003 09:02
1315 -----------------------------------------------*/
1316 css::uno::Reference< css::frame::XFrame > LoadEnv::impl_searchAlreadyLoaded()
1317 throw(LoadEnvException, css::uno::RuntimeException)
1319 // SAFE ->
1320 ReadGuard aReadLock(m_aLock);
1322 // such search is allowed for special requests only ...
1323 // or better its not allowed for some requests in general :-)
1324 if (
1325 ( ! TargetHelper::matchSpecialTarget(m_sTarget, TargetHelper::E_DEFAULT) ) ||
1326 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_ASTEMPLATE() , sal_False) == sal_True) ||
1327 // (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN() , sal_False) == sal_True) ||
1328 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_OPENNEWVIEW(), sal_False) == sal_True)
1331 return css::uno::Reference< css::frame::XFrame >();
1334 // check URL
1335 // May its not usefull to start expensive document search, if it
1336 // can fail only .. because we load from a stream or model directly!
1337 if (
1338 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_STREAM )) ||
1339 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_OBJECT ))
1340 /*TODO should be private:factory here tested too? */
1343 return css::uno::Reference< css::frame::XFrame >();
1346 // otherwhise - iterate through the tasks of the desktop container
1347 // to find out, which of them might contains the requested document
1348 css::uno::Reference< css::frame::XFramesSupplier > xSupplier(m_xSMGR->createInstance(SERVICENAME_DESKTOP), css::uno::UNO_QUERY);
1349 css::uno::Reference< css::container::XIndexAccess > xTaskList(xSupplier->getFrames() , css::uno::UNO_QUERY);
1351 if (!xTaskList.is())
1352 return css::uno::Reference< css::frame::XFrame >(); // task list can be empty!
1354 // Note: To detect if a document was alrady loaded before
1355 // we check URLs here only. But might the existing and the requred
1356 // document has different versions! Then its URLs are the same ...
1357 sal_Int16 nNewVersion = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_VERSION(), (sal_Int16)(-1));
1359 // will be used to save the first hidden frame referring the searched model
1360 // Normaly we are interested on visible frames ... but if there is no such visible
1361 // frame we referr to any hidden frame also (but as fallback only).
1362 css::uno::Reference< css::frame::XFrame > xHiddenTask;
1363 css::uno::Reference< css::frame::XFrame > xTask;
1365 sal_Int32 count = xTaskList->getCount();
1366 for (sal_Int32 i=0; i<count; ++i)
1370 // locate model of task
1371 // Note: Without a model there is no chance to decide if
1372 // this task contains the searched document or not!
1373 xTaskList->getByIndex(i) >>= xTask;
1374 if (!xTask.is())
1375 continue;
1377 css::uno::Reference< css::frame::XController > xController = xTask->getController();
1378 if (!xController.is())
1380 xTask.clear ();
1381 continue;
1384 css::uno::Reference< css::frame::XModel > xModel = xController->getModel();
1385 if (!xModel.is())
1387 xTask.clear ();
1388 continue;
1391 // don't check the complete URL here.
1392 // use its main part - ignore optional jumpmarks!
1393 const ::rtl::OUString sURL = xModel->getURL();
1394 if (!m_aURL.Main.equals(sURL))
1396 xTask.clear ();
1397 continue;
1400 // get the original load arguments from the current document
1401 // and decide if its realy the same then the one will be.
1402 // It must be visible and must use the same file revision ...
1403 // or must not have any file revision set (-1 == -1!)
1404 ::comphelper::MediaDescriptor lOldDocDescriptor(xModel->getArgs());
1406 if (lOldDocDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_VERSION(), (sal_Int32)(-1)) != nNewVersion)
1408 xTask.clear ();
1409 continue;
1412 // Hidden frames are special.
1413 // They will be used as "last chance" if there is no visible frame pointing to the same model.
1414 // Safe the result but continue with current loop might be looking for other visible frames.
1415 ::sal_Bool bIsHidden = lOldDocDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN(), sal_False);
1416 if (
1417 ( bIsHidden ) &&
1418 ( ! xHiddenTask.is())
1421 xHiddenTask = xTask;
1422 xTask.clear ();
1423 continue;
1426 // We found a visible task pointing to the right model ...
1427 // Break search.
1428 break;
1430 catch(const css::uno::RuntimeException& exRun)
1431 { throw exRun; }
1432 catch(const css::uno::Exception&)
1433 { continue; }
1436 css::uno::Reference< css::frame::XFrame > xResult;
1437 if (xTask.is())
1438 xResult = xTask;
1439 else
1440 if (xHiddenTask.is())
1441 xResult = xHiddenTask;
1443 if (xResult.is())
1445 // Now we are shure, that this task includes the searched document.
1446 // It's time to activate it. As special feature we try to jump internaly
1447 // if an optional jumpmark is given too.
1448 if (m_aURL.Mark.getLength())
1449 impl_jumpToMark(xResult, m_aURL);
1451 // bring it to front and make sure it's visible...
1452 impl_makeFrameWindowVisible(xResult->getContainerWindow(), sal_True);
1455 aReadLock.unlock();
1456 // <- SAFE
1458 return xResult;
1461 /*-----------------------------------------------
1462 30.03.2004 09:12
1463 -----------------------------------------------*/
1464 sal_Bool LoadEnv::impl_isFrameAlreadyUsedForLoading(const css::uno::Reference< css::frame::XFrame >& xFrame) const
1466 css::uno::Reference< css::document::XActionLockable > xLock(xFrame, css::uno::UNO_QUERY);
1468 // ? no lock interface ?
1469 // Might its an external written frame implementation :-(
1470 // Allowing using of it ... but it can fail if its not synchronized with our processes !
1471 if (!xLock.is())
1472 return sal_False;
1474 // Otherwhise we have to look for any other existing lock.
1475 return xLock->isActionLocked();
1478 /*-----------------------------------------------
1479 30.03.2004 09:12
1480 -----------------------------------------------*/
1481 css::uno::Reference< css::frame::XFrame > LoadEnv::impl_searchRecycleTarget()
1482 throw(LoadEnvException, css::uno::RuntimeException)
1484 // SAFE -> ..................................
1485 ReadGuard aReadLock(m_aLock);
1487 // The special backing mode frame will be recycled by definition!
1488 // It does'nt matter if somehwere whish to create a new view
1489 // or open a new untitled document ...
1490 // The only exception form that - hidden frames!
1491 if (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN(), sal_False) == sal_True)
1492 return css::uno::Reference< css::frame::XFrame >();
1494 css::uno::Reference< css::frame::XFramesSupplier > xSupplier(m_xSMGR->createInstance(SERVICENAME_DESKTOP), css::uno::UNO_QUERY);
1495 FrameListAnalyzer aTasksAnalyzer(xSupplier, css::uno::Reference< css::frame::XFrame >(), FrameListAnalyzer::E_BACKINGCOMPONENT);
1496 if (aTasksAnalyzer.m_xBackingComponent.is())
1498 if (!impl_isFrameAlreadyUsedForLoading(aTasksAnalyzer.m_xBackingComponent))
1500 // bring it to front ...
1501 impl_makeFrameWindowVisible(aTasksAnalyzer.m_xBackingComponent->getContainerWindow(), sal_True);
1502 return aTasksAnalyzer.m_xBackingComponent;
1506 // These states indicates the wishing for creation of a new view in general.
1507 if (
1508 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_ASTEMPLATE() , sal_False) == sal_True) ||
1509 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_OPENNEWVIEW(), sal_False) == sal_True)
1512 return css::uno::Reference< css::frame::XFrame >();
1515 // On the other side some special URLs will open a new frame everytimes (expecting
1516 // they can use the backing-mode frame!)
1517 if (
1518 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_FACTORY )) ||
1519 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_STREAM )) ||
1520 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_OBJECT ))
1523 return css::uno::Reference< css::frame::XFrame >();
1526 // No backing frame! No special URL => recycle active task - if possible.
1527 // Means - if it does not already contains a modified document, or
1528 // use another office module.
1529 css::uno::Reference< css::frame::XFrame > xTask = xSupplier->getActiveFrame();
1531 // not a real error - but might a focus problem!
1532 if (!xTask.is())
1533 return css::uno::Reference< css::frame::XFrame >();
1535 // not a real error - may its a view only
1536 css::uno::Reference< css::frame::XController > xController = xTask->getController();
1537 if (!xController.is())
1538 return css::uno::Reference< css::frame::XFrame >();
1540 // not a real error - may its a db component instead of a full feartured office document
1541 css::uno::Reference< css::frame::XModel > xModel = xController->getModel();
1542 if (!xModel.is())
1543 return css::uno::Reference< css::frame::XFrame >();
1545 // get some more informations ...
1547 // A valid set URL means: there is already a location for this document.
1548 // => it was saved there or opened from there. Such Documents can not be used here.
1549 // We search for empty document ... created by a private:factory/ URL!
1550 if (xModel->getURL().getLength()>0)
1551 return css::uno::Reference< css::frame::XFrame >();
1553 // The old document must be unmodified ...
1554 css::uno::Reference< css::util::XModifiable > xModified(xModel, css::uno::UNO_QUERY);
1555 if (xModified->isModified())
1556 return css::uno::Reference< css::frame::XFrame >();
1558 Window* pWindow = VCLUnoHelper::GetWindow(xTask->getContainerWindow());
1559 if (pWindow && pWindow->IsInModalMode())
1560 return css::uno::Reference< css::frame::XFrame >();
1562 // find out the application type of this document
1563 // We can recycle only documents, which uses the same application
1564 // then the new one.
1565 SvtModuleOptions::EFactory eOldApp = SvtModuleOptions::ClassifyFactoryByModel(xModel);
1566 SvtModuleOptions::EFactory eNewApp = SvtModuleOptions::ClassifyFactoryByURL (m_aURL.Complete, m_lMediaDescriptor.getAsConstPropertyValueList());
1568 aReadLock.unlock();
1569 // <- SAFE ..................................
1571 if (eOldApp != eNewApp)
1572 return css::uno::Reference< css::frame::XFrame >();
1574 // OK this task seams to be useable for recycling
1575 // But we should mark it as such - means set an action lock.
1576 // Otherwhise it would be used more then ones or will be destroyed
1577 // by a close() or terminate() request.
1578 // But if such lock already exist ... it means this task is used for
1579 // any other operation already. Don't use it then.
1580 if (impl_isFrameAlreadyUsedForLoading(xTask))
1581 return css::uno::Reference< css::frame::XFrame >();
1583 // OK - there is a valid target frame.
1584 // But may be it contains already a document.
1585 // Then we have to ask it, if it allows recylcing of this frame .-)
1586 sal_Bool bReactivateOldControllerOnError = sal_False;
1587 css::uno::Reference< css::frame::XController > xOldDoc = xTask->getController();
1588 if (xOldDoc.is())
1590 bReactivateOldControllerOnError = xOldDoc->suspend(sal_True);
1591 if (! bReactivateOldControllerOnError)
1592 return css::uno::Reference< css::frame::XFrame >();
1595 // SAFE -> ..................................
1596 WriteGuard aWriteLock(m_aLock);
1598 css::uno::Reference< css::document::XActionLockable > xLock(xTask, css::uno::UNO_QUERY);
1599 if (!m_aTargetLock.setResource(xLock))
1600 return css::uno::Reference< css::frame::XFrame >();
1602 m_bReactivateControllerOnError = bReactivateOldControllerOnError;
1603 aWriteLock.unlock();
1604 // <- SAFE ..................................
1606 // bring it to front ...
1607 impl_makeFrameWindowVisible(xTask->getContainerWindow(), sal_True);
1609 return xTask;
1612 /*-----------------------------------------------
1613 15.08.2003 12:39
1614 -----------------------------------------------*/
1615 void LoadEnv::impl_reactForLoadingState()
1616 throw(LoadEnvException, css::uno::RuntimeException)
1618 /*TODO reset action locks */
1620 // SAFE -> ----------------------------------
1621 ReadGuard aReadLock(m_aLock);
1623 if (m_bLoaded)
1625 // Bring the new loaded document to front (if allowed!).
1626 // Note: We show new created frames here only.
1627 // We dont hide already visible frames here ...
1628 css::uno::Reference< css::awt::XWindow > xWindow = m_xTargetFrame->getContainerWindow();
1629 sal_Bool bHidden = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN(), sal_False);
1630 sal_Bool bRecovered = (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_SALVAGEDFILE()) != m_lMediaDescriptor.end());
1631 sal_Bool bMinimized = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_MINIMIZED(), sal_False);
1633 if (bMinimized)
1635 ::vos::OClearableGuard aSolarGuard(Application::GetSolarMutex());
1636 Window* pWindow = VCLUnoHelper::GetWindow(xWindow);
1637 // check for system window is neccessary to guarantee correct pointer cast!
1638 if (pWindow && pWindow->IsSystemWindow())
1639 ((WorkWindow*)pWindow)->Minimize();
1641 else
1642 if (!bHidden && !bRecovered)
1644 // show frame ... if it's not still visible ...
1645 // But do nothing if it's already visible!
1646 impl_makeFrameWindowVisible(xWindow, sal_False);
1649 // Note: Only if an existing property "FrameName" is given by this media descriptor,
1650 // it should be used. Otherwhise we should do nothing. May be the outside code has already
1651 // set a frame name on the target!
1652 ::comphelper::MediaDescriptor::const_iterator pFrameName = m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_FRAMENAME());
1653 if (pFrameName != m_lMediaDescriptor.end())
1655 ::rtl::OUString sFrameName;
1656 pFrameName->second >>= sFrameName;
1657 // Check the name again. e.g. "_default" isnt allowed.
1658 // On the other side "_beamer" is a valid name :-)
1659 if (TargetHelper::isValidNameForFrame(sFrameName))
1660 m_xTargetFrame->setName(sFrameName);
1663 else
1664 if (m_bReactivateControllerOnError)
1666 // Try to reactivate the old document (if any exists!)
1667 css::uno::Reference< css::frame::XController > xOldDoc = m_xTargetFrame->getController();
1668 // clear does not depend from reactivation state of a might existing old document!
1669 // We must make shure, that a might following getTargetComponent() call does not return
1670 // the old document!
1671 m_xTargetFrame.clear();
1672 if (xOldDoc.is())
1674 sal_Bool bReactivated = xOldDoc->suspend(sal_False);
1675 if (!bReactivated)
1676 throw LoadEnvException(LoadEnvException::ID_COULD_NOT_REACTIVATE_CONTROLLER);
1677 m_bReactivateControllerOnError = sal_False;
1680 else
1681 if (m_bCloseFrameOnError)
1683 // close empty frames
1684 css::uno::Reference< css::util::XCloseable > xCloseable (m_xTargetFrame, css::uno::UNO_QUERY);
1685 css::uno::Reference< css::lang::XComponent > xDisposable(m_xTargetFrame, css::uno::UNO_QUERY);
1689 if (xCloseable.is())
1690 xCloseable->close(sal_True);
1691 else
1692 if (xDisposable.is())
1693 xDisposable->dispose();
1695 catch(const css::util::CloseVetoException&)
1697 catch(const css::lang::DisposedException&)
1699 m_xTargetFrame.clear();
1702 // This max force an implicit closing of our target frame ...
1703 // e.g. in case close(TRUE) was called before and the frame
1704 // kill itself if our external use-lock is released here!
1705 // Thats why we releas this lock AFTER ALL OPERATIONS on this frame
1706 // are finished. The frame itslef must handle then
1707 // this situation gracefully.
1708 m_aTargetLock.freeResource();
1710 // Last but not least :-)
1711 // We have to clear the current media descriptor.
1712 // Otherwhise it hold a might existing stream open!
1713 m_lMediaDescriptor.clear();
1715 aReadLock.unlock();
1716 // <- SAFE ----------------------------------
1719 /*-----------------------------------------------
1720 16.01.2005 13:04
1721 -----------------------------------------------*/
1722 void LoadEnv::impl_makeFrameWindowVisible(const css::uno::Reference< css::awt::XWindow >& xWindow ,
1723 sal_Bool bForceToFront)
1725 css::uno::Reference< css::awt::XTopWindow > xTopWindow(xWindow, css::uno::UNO_QUERY);
1727 if (xWindow.is())
1728 xWindow->setVisible(sal_True);
1730 if (xTopWindow.is() && bForceToFront)
1731 xTopWindow->toFront();
1733 /* #i19976#
1734 We tried to prevent a toFront() call in case the user putted the
1735 loading document into the background ..
1736 But we had several errors trying that. So we decided to
1737 rollback these changes and bring the new loaded document to front hardly !
1739 css::uno::Reference< css::awt::XWindow2 > xWindow2(xWindow, css::uno::UNO_QUERY);
1741 sal_Bool bIsVisible = sal_False;
1742 if (xWindow2.is())
1743 bIsVisible = xWindow2->isVisible(); // TODO is parent visible too ? .-)
1745 if (!bIsVisible)
1747 xWindow->setVisible(sal_True);
1748 bForceToFront = sal_True;
1751 if (
1752 (bForceToFront ) &&
1753 (xTopWindow.is())
1756 xTopWindow->toFront();
1761 /*-----------------------------------------------
1762 15.03.2005 11:12
1763 -----------------------------------------------*/
1764 void LoadEnv::impl_applyPersistentWindowState(const css::uno::Reference< css::awt::XWindow >& xWindow)
1766 static ::rtl::OUString PACKAGE_SETUP_MODULES = ::rtl::OUString::createFromAscii("/org.openoffice.Setup/Office/Factories");
1768 // no window -> action not possible
1769 if (!xWindow.is())
1770 return;
1772 // window already visible -> do nothing! If we use a "recycle frame" for loading ...
1773 // the current position and size must be used.
1774 css::uno::Reference< css::awt::XWindow2 > xVisibleCheck(xWindow, css::uno::UNO_QUERY);
1775 if (
1776 (xVisibleCheck.is() ) &&
1777 (xVisibleCheck->isVisible())
1779 return;
1781 // SOLAR SAFE ->
1782 ::vos::OClearableGuard aSolarLock1(Application::GetSolarMutex());
1784 Window* pWindow = VCLUnoHelper::GetWindow(xWindow);
1785 sal_Bool bSystemWindow = pWindow->IsSystemWindow();
1786 sal_Bool bWorkWindow = (pWindow->GetType() == WINDOW_WORKWINDOW);
1788 if (!bSystemWindow && !bWorkWindow)
1789 return;
1791 // dont overwrite this special state!
1792 WorkWindow* pWorkWindow = (WorkWindow*)pWindow;
1793 if (pWorkWindow->IsMinimized())
1794 return;
1796 aSolarLock1.clear();
1797 // <- SOLAR SAFE
1799 // SAFE ->
1800 ReadGuard aReadLock(m_aLock);
1802 // no filter -> no module -> no persistent window state
1803 ::rtl::OUString sFilter = m_lMediaDescriptor.getUnpackedValueOrDefault(
1804 ::comphelper::MediaDescriptor::PROP_FILTERNAME(),
1805 ::rtl::OUString());
1806 if (!sFilter.getLength())
1807 return;
1809 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
1811 aReadLock.unlock();
1812 // <- SAFE
1816 // retrieve the module name from the filter configuration
1817 css::uno::Reference< css::container::XNameAccess > xFilterCfg(
1818 xSMGR->createInstance(SERVICENAME_FILTERFACTORY),
1819 css::uno::UNO_QUERY_THROW);
1820 ::comphelper::SequenceAsHashMap lProps (xFilterCfg->getByName(sFilter));
1821 ::rtl::OUString sModule = lProps.getUnpackedValueOrDefault(FILTER_PROPNAME_DOCUMENTSERVICE, ::rtl::OUString());
1823 // get access to the configuration of this office module
1824 css::uno::Reference< css::container::XNameAccess > xModuleCfg(::comphelper::ConfigurationHelper::openConfig(
1825 xSMGR,
1826 PACKAGE_SETUP_MODULES,
1827 ::comphelper::ConfigurationHelper::E_READONLY),
1828 css::uno::UNO_QUERY_THROW);
1830 // read window state from the configuration
1831 // and apply it on the window.
1832 // Do nothing, if no configuration entry exists!
1833 ::rtl::OUString sWindowState ;
1834 ::comphelper::ConfigurationHelper::readRelativeKey(xModuleCfg, sModule, OFFICEFACTORY_PROPNAME_WINDOWATTRIBUTES) >>= sWindowState;
1835 if (sWindowState.getLength())
1837 // SOLAR SAFE ->
1838 ::vos::OClearableGuard aSolarLock2(Application::GetSolarMutex());
1840 // We have to retrieve the window pointer again. Because nobody can guarantee
1841 // that the XWindow was not disposed inbetween .-)
1842 // But if we get a valid pointer we can be sure, that it's the system window pointer
1843 // we already checked and used before. Because nobody recylce the same uno reference for
1844 // a new internal c++ implementation ... hopefully .-))
1845 Window* pWindowCheck = VCLUnoHelper::GetWindow(xWindow);
1846 if (! pWindowCheck)
1847 return;
1849 SystemWindow* pSystemWindow = (SystemWindow*)pWindowCheck;
1850 pSystemWindow->SetWindowState(U2B_ENC(sWindowState,RTL_TEXTENCODING_UTF8));
1852 aSolarLock2.clear();
1853 // <- SOLAR SAFE
1856 catch(const css::uno::RuntimeException& exRun)
1857 { throw exRun; }
1858 catch(const css::uno::Exception&)
1862 } // namespace framework