Update ooo320-m1
[ooovba.git] / framework / source / loadenv / loadenv.cxx
blobed861956185fb8ea5b2c20497b1f87cce40fc61a
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/quietinteraction.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 )
175 , m_pQuietInteraction( 0 )
179 /*-----------------------------------------------
180 14.10.2003 13:43
181 -----------------------------------------------*/
182 LoadEnv::~LoadEnv()
184 m_pCheck = 0;
187 /*-----------------------------------------------
188 10.09.2003 14:05
189 -----------------------------------------------*/
190 css::uno::Reference< css::lang::XComponent > LoadEnv::loadComponentFromURL(const css::uno::Reference< css::frame::XComponentLoader >& xLoader,
191 const css::uno::Reference< css::lang::XMultiServiceFactory >& xSMGR ,
192 const ::rtl::OUString& sURL ,
193 const ::rtl::OUString& sTarget,
194 sal_Int32 nFlags ,
195 const css::uno::Sequence< css::beans::PropertyValue >& lArgs )
196 throw(css::lang::IllegalArgumentException,
197 css::io::IOException ,
198 css::uno::RuntimeException )
200 css::uno::Reference< css::lang::XComponent > xComponent;
204 LoadEnv aEnv(xSMGR);
206 aEnv.initializeLoading(sURL,
207 lArgs,
208 css::uno::Reference< css::frame::XFrame >(xLoader, css::uno::UNO_QUERY),
209 sTarget,
210 nFlags,
211 LoadEnv::E_NO_FEATURE);
212 aEnv.startLoading();
213 aEnv.waitWhileLoading(); // wait for ever!
215 xComponent = aEnv.getTargetComponent();
217 catch(const LoadEnvException& ex)
219 switch(ex.m_nID)
221 case LoadEnvException::ID_INVALID_MEDIADESCRIPTOR:
222 throw css::lang::IllegalArgumentException(
223 ::rtl::OUString::createFromAscii("Optional list of arguments seem to be corrupted."),
224 xLoader,
227 case LoadEnvException::ID_UNSUPPORTED_CONTENT:
228 throw css::lang::IllegalArgumentException(
229 ::rtl::OUString::createFromAscii("URL seems to be an unsupported one."),
230 xLoader,
233 default: xComponent.clear();
234 break;
238 return xComponent;
241 //-----------------------------------------------
242 ::comphelper::MediaDescriptor impl_mergeMediaDescriptorWithMightExistingModelArgs(const css::uno::Sequence< css::beans::PropertyValue >& lOutsideDescriptor)
244 ::comphelper::MediaDescriptor lDescriptor(lOutsideDescriptor);
245 css::uno::Reference< css::frame::XModel > xModel = lDescriptor.getUnpackedValueOrDefault(
246 ::comphelper::MediaDescriptor::PROP_MODEL (),
247 css::uno::Reference< css::frame::XModel > ());
248 if (xModel.is ())
250 ::comphelper::MediaDescriptor lModelDescriptor(xModel->getArgs());
251 ::comphelper::MediaDescriptor::iterator pIt = lModelDescriptor.find( ::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE() );
252 if ( pIt != lModelDescriptor.end() )
253 lDescriptor[::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE()] = pIt->second;
256 return lDescriptor;
259 /*-----------------------------------------------
260 20.08.2003 09:49
261 -----------------------------------------------*/
262 void LoadEnv::initializeLoading(const ::rtl::OUString& sURL ,
263 const css::uno::Sequence< css::beans::PropertyValue >& lMediaDescriptor,
264 const css::uno::Reference< css::frame::XFrame >& xBaseFrame ,
265 const ::rtl::OUString& sTarget ,
266 sal_Int32 nSearchFlags ,
267 EFeature eFeature , // => use default ...
268 EContentType eContentType ) // => use default ...
269 throw(LoadEnvException, css::uno::RuntimeException)
271 // SAFE -> ----------------------------------
272 WriteGuard aWriteLock(m_aLock);
274 // Handle still running processes!
275 if (m_xAsynchronousJob.is())
276 throw LoadEnvException(LoadEnvException::ID_STILL_RUNNING);
278 // take over all new parameters.
279 m_xTargetFrame.clear();
280 m_xBaseFrame = xBaseFrame ;
281 m_lMediaDescriptor = impl_mergeMediaDescriptorWithMightExistingModelArgs(lMediaDescriptor);
282 m_sTarget = sTarget ;
283 m_nSearchFlags = nSearchFlags ;
284 m_eFeature = eFeature ;
285 m_eContentType = eContentType ;
286 m_bCloseFrameOnError = sal_False ;
287 m_bReactivateControllerOnError = sal_False ;
288 m_bLoaded = sal_False ;
290 // try to find out, if its realy a content, which can be loaded or must be "handled"
291 // We use a default value for this in-parameter. Then we have to start a complex check method
292 // internaly. But if this check was already done outside it can be supressed to perform
293 // the load request. We take over the result then!
294 if (m_eContentType == E_UNSUPPORTED_CONTENT)
296 m_eContentType = LoadEnv::classifyContent(sURL, lMediaDescriptor);
297 if (m_eContentType == E_UNSUPPORTED_CONTENT)
298 throw LoadEnvException(LoadEnvException::ID_UNSUPPORTED_CONTENT);
301 // make URL part of the MediaDescriptor
302 // It doesnt mater, if its already an item of it.
303 // It must be the same value ... so we can overwrite it :-)
304 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_URL()] <<= sURL;
306 // parse it - because some following code require that
307 m_aURL.Complete = sURL;
308 css::uno::Reference< css::util::XURLTransformer > xParser(m_xSMGR->createInstance(SERVICENAME_URLTRANSFORMER), css::uno::UNO_QUERY);
309 xParser->parseStrict(m_aURL);
311 // BTW: Split URL and JumpMark ...
312 // Because such mark is an explicit value of the media descriptor!
313 if (m_aURL.Mark.getLength())
314 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_JUMPMARK()] <<= m_aURL.Mark;
316 // By the way: remove the old and deprecated value "FileName" from the descriptor!
317 ::comphelper::MediaDescriptor::iterator pIt = m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_FILENAME());
318 if (pIt != m_lMediaDescriptor.end())
319 m_lMediaDescriptor.erase(pIt);
321 // patch the MediaDescriptor, so it fullfill the outside requirements
322 // Means especialy items like e.g. UI InteractionHandler, Status Indicator,
323 // MacroExecutionMode etcpp.
325 /*TODO progress is bound to a frame ... How can we set it here? */
327 css::uno::Reference< css::task::XInteractionHandler > xInteractionHandler;
328 sal_Int16 nMacroMode ;
329 sal_Int16 nUpdateMode ;
331 // UI mode
332 if (
333 ((m_eFeature & E_WORK_WITH_UI) == E_WORK_WITH_UI) &&
334 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN() , sal_False) == sal_False ) &&
335 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_PREVIEW(), sal_False) == sal_False )
338 nMacroMode = css::document::MacroExecMode::USE_CONFIG;
339 nUpdateMode = css::document::UpdateDocMode::ACCORDING_TO_CONFIG;
342 xInteractionHandler = css::uno::Reference< css::task::XInteractionHandler >(m_xSMGR->createInstance(IMPLEMENTATIONNAME_UIINTERACTIONHANDLER), css::uno::UNO_QUERY);
344 catch(const css::uno::RuntimeException&) {throw;}
345 catch(const css::uno::Exception& ) { }
347 // hidden mode
348 else
350 nMacroMode = css::document::MacroExecMode::NEVER_EXECUTE;
351 nUpdateMode = css::document::UpdateDocMode::NO_UPDATE;
352 m_pQuietInteraction = new QuietInteraction();
353 m_pQuietInteraction->acquire();
354 xInteractionHandler = css::uno::Reference< css::task::XInteractionHandler >(static_cast< css::task::XInteractionHandler* >(m_pQuietInteraction), css::uno::UNO_QUERY);
357 if (
358 (xInteractionHandler.is() ) &&
359 (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_INTERACTIONHANDLER()) == m_lMediaDescriptor.end())
362 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_INTERACTIONHANDLER()] <<= xInteractionHandler;
365 if (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE()) == m_lMediaDescriptor.end())
366 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_MACROEXECUTIONMODE()] <<= nMacroMode;
368 if (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_UPDATEDOCMODE()) == m_lMediaDescriptor.end())
369 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_UPDATEDOCMODE()] <<= nUpdateMode;
371 aWriteLock.unlock();
372 // <- SAFE ----------------------------------
375 /*-----------------------------------------------
376 15.08.2003 08:16
377 -----------------------------------------------*/
378 void LoadEnv::startLoading()
379 throw(LoadEnvException, css::uno::RuntimeException)
381 // SAFE ->
382 ReadGuard aReadLock(m_aLock);
384 // Handle still running processes!
385 if (m_xAsynchronousJob.is())
386 throw LoadEnvException(LoadEnvException::ID_STILL_RUNNING);
388 // content can not be loaded or handled
389 // check "classifyContent()" failed before ...
390 if (m_eContentType == E_UNSUPPORTED_CONTENT)
391 throw LoadEnvException(LoadEnvException::ID_UNSUPPORTED_CONTENT);
393 // <- SAFE
394 aReadLock.unlock();
396 // detect its type/filter etcpp.
397 // These information will be available by the
398 // used descriptor member afterwards and is needed
399 // for all following operations!
400 // Note: An exception will be thrown, in case operation was not successfully ...
401 if (m_eContentType != E_CAN_BE_SET)/* Attention: special feature to set existing component on a frame must ignore type detection! */
402 impl_detectTypeAndFilter();
404 // start loading the content ...
405 // Attention: Dont check m_eContentType deeper then UNSUPPORTED/SUPPORTED!
406 // Because it was made in th easiest way ... may a flat detection was made only.
407 // And such simple detection can fail some times .-)
408 // Use another strategy here. Try it and let it run into the case "loading not possible".
409 sal_Bool bStarted = sal_False;
410 if (
411 ((m_eFeature & E_ALLOW_CONTENTHANDLER) == E_ALLOW_CONTENTHANDLER) &&
412 (m_eContentType != E_CAN_BE_SET ) /* Attention: special feature to set existing component on a frame must ignore type detection! */
415 bStarted = impl_handleContent();
418 if (!bStarted)
419 bStarted = impl_loadContent();
421 // not started => general error
422 // We cant say - what was the reason for.
423 if (!bStarted)
424 throw LoadEnvException(LoadEnvException::ID_GENERAL_ERROR);
427 /*-----------------------------------------------
428 15.08.2003 09:50
429 TODO
430 First draft does not implement timeout using [ms].
431 Current implementation counts yield calls only ...
432 -----------------------------------------------*/
433 sal_Bool LoadEnv::waitWhileLoading(sal_uInt32 nTimeout)
434 throw(LoadEnvException, css::uno::RuntimeException)
436 // Because its not a good idea to block the main thread
437 // (and we cant be shure that we are currently not used inside the
438 // main thread!), we cant use conditions here realy. We must yield
439 // in an intellegent manner :-)
441 sal_Int32 nTime = nTimeout;
442 while(true)
444 // SAFE -> ------------------------------
445 ReadGuard aReadLock1(m_aLock);
446 if (!m_xAsynchronousJob.is())
447 break;
448 aReadLock1.unlock();
449 // <- SAFE ------------------------------
451 Application::Yield();
453 // forever!
454 if (nTimeout==0)
455 continue;
457 // timed out?
458 --nTime;
459 if (nTime<1)
460 break;
463 // SAFE -> ----------------------------------
464 ReadGuard aReadLock2(m_aLock);
465 return !m_xAsynchronousJob.is();
466 // <- SAFE ----------------------------------
469 /*-----------------------------------------------
470 20.08.2003 10:00
471 -----------------------------------------------*/
472 void LoadEnv::cancelLoading()
473 throw(LoadEnvException, css::uno::RuntimeException)
475 // PARTIAL(!) SAFE -> ------------------------------
476 ReadGuard aReadLock(m_aLock);
478 // Still running? Might waitWhileLoading()
479 // runned into the timeout!
480 if (m_xAsynchronousJob.is())
482 // try to cancel it ... if its an asynchronous frame loader
483 css::uno::Reference< css::frame::XFrameLoader > xAsyncLoader(m_xAsynchronousJob, css::uno::UNO_QUERY);
484 if (xAsyncLoader.is())
486 aReadLock.unlock();
487 // <- BREAK SAFE ------------------------------
488 xAsyncLoader->cancel();
489 // <- RESTART SAFE ----------------------------
490 aReadLock.lock();
491 /* Attention:
492 After returning from any cancel/dispose call, neither the frame nor weself
493 may be called back. Because only we can cancel this job, we already know
494 the result! => Thats why its not usefull nor neccessary to wait for any
495 asynchronous listener notification.
497 m_bLoaded = sal_False;
498 m_xAsynchronousJob.clear();
500 // or may be its a content handler? Such handler cant be cancelled in its running
501 // operation :-( And we cant deregister us there again :-(
502 // => The only chance is an exception :-)
503 else
504 throw LoadEnvException(LoadEnvException::ID_STILL_RUNNING);
507 impl_reactForLoadingState();
509 aReadLock.unlock();
510 // <- PARTIAL(!) SAFE ------------------------------
513 /*-----------------------------------------------
514 14.08.2003 13:33
515 -----------------------------------------------*/
516 css::uno::Reference< css::frame::XFrame > LoadEnv::getTarget() const
518 // SAFE ->
519 ReadGuard aReadLock(m_aLock);
520 return m_xTargetFrame;
521 // <- SAFE
524 /*-----------------------------------------------
525 14.08.2003 13:35
526 -----------------------------------------------*/
527 css::uno::Reference< css::lang::XComponent > LoadEnv::getTargetComponent() const
529 // SAFE ->
530 ReadGuard aReadLock(m_aLock);
532 if (!m_xTargetFrame.is())
533 return css::uno::Reference< css::lang::XComponent >();
535 css::uno::Reference< css::frame::XController > xController = m_xTargetFrame->getController();
536 if (!xController.is())
537 return css::uno::Reference< css::lang::XComponent >(m_xTargetFrame->getComponentWindow(), css::uno::UNO_QUERY);
539 css::uno::Reference< css::frame::XModel > xModel = xController->getModel();
540 if (!xModel.is())
541 return css::uno::Reference< css::lang::XComponent >(xController, css::uno::UNO_QUERY);
543 return css::uno::Reference< css::lang::XComponent >(xModel, css::uno::UNO_QUERY);
544 // <- SAFE
547 /*-----------------------------------------------
548 15.08.2003 11:15
549 -----------------------------------------------*/
550 void SAL_CALL LoadEnvListener::loadFinished(const css::uno::Reference< css::frame::XFrameLoader >&)
551 throw(css::uno::RuntimeException)
553 // SAFE -> ----------------------------------
554 WriteGuard aWriteLock(m_aLock);
556 if (m_ppCheck && *m_ppCheck)
557 m_pLoadEnv->impl_setResult(sal_True);
558 m_ppCheck = NULL;
560 aWriteLock.unlock();
561 // <- SAFE ----------------------------------
564 /*-----------------------------------------------
565 14.10.2003 12:23
566 -----------------------------------------------*/
567 void SAL_CALL LoadEnvListener::loadCancelled(const css::uno::Reference< css::frame::XFrameLoader >&)
568 throw(css::uno::RuntimeException)
570 // SAFE -> ----------------------------------
571 WriteGuard aWriteLock(m_aLock);
573 if (m_ppCheck && *m_ppCheck)
574 m_pLoadEnv->impl_setResult(sal_False);
575 m_ppCheck = NULL;
577 aWriteLock.unlock();
578 // <- SAFE ----------------------------------
581 /*-----------------------------------------------
582 14.10.2003 12:23
583 -----------------------------------------------*/
584 void SAL_CALL LoadEnvListener::dispatchFinished(const css::frame::DispatchResultEvent& aEvent)
585 throw(css::uno::RuntimeException)
587 // SAFE -> ----------------------------------
588 WriteGuard aWriteLock(m_aLock);
590 if (!m_ppCheck || !*m_ppCheck)
591 return;
593 switch(aEvent.State)
595 case css::frame::DispatchResultState::FAILURE :
596 m_pLoadEnv->impl_setResult(sal_False);
597 break;
599 case css::frame::DispatchResultState::SUCCESS :
600 m_pLoadEnv->impl_setResult(sal_False);
601 break;
603 case css::frame::DispatchResultState::DONTKNOW :
604 m_pLoadEnv->impl_setResult(sal_False);
605 break;
607 m_ppCheck = NULL;
609 aWriteLock.unlock();
610 // <- SAFE ----------------------------------
613 /*-----------------------------------------------
614 14.10.2003 12:24
615 -----------------------------------------------*/
616 void SAL_CALL LoadEnvListener::disposing(const css::lang::EventObject&)
617 throw(css::uno::RuntimeException)
619 // SAFE -> ----------------------------------
620 WriteGuard aWriteLock(m_aLock);
622 if (m_ppCheck && *m_ppCheck)
623 m_pLoadEnv->impl_setResult(sal_False);
624 m_ppCheck = NULL;
626 aWriteLock.unlock();
627 // <- SAFE ----------------------------------
630 /*-----------------------------------------------
631 14.10.2003 12:20
632 -----------------------------------------------*/
633 void LoadEnv::impl_setResult(sal_Bool bResult)
635 // SAFE -> ----------------------------------
636 WriteGuard aWriteLock(m_aLock);
638 m_bLoaded = bResult;
640 impl_reactForLoadingState();
642 // clearing of this reference will unblock waitWhileLoading()!
643 // So we must be shure, that loading process was realy finished.
644 // => do it as last operation of this method ...
645 m_xAsynchronousJob.clear();
647 aWriteLock.unlock();
648 // <- SAFE ----------------------------------
651 /*-----------------------------------------------
652 06.02.2004 14:03
653 TODO: Is it a good idea to change Sequence<>
654 parameter to stl-adapter?
655 -----------------------------------------------*/
656 LoadEnv::EContentType LoadEnv::classifyContent(const ::rtl::OUString& sURL ,
657 const css::uno::Sequence< css::beans::PropertyValue >& lMediaDescriptor)
659 //-------------------------------------------
660 // (i) Filter some special well known URL protocols,
661 // which can not be handled or loaded in general.
662 // Of course an empty URL must be ignored here too.
663 // Note: These URL schemata are fix and well known ...
664 // But there can be some additional ones, which was not
665 // defined at implementation time of this class :-(
666 // So we have to make shure, that the following code
667 // can detect such protocol schemata too :-)
670 (!sURL.getLength() ) ||
671 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_UNO )) ||
672 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_SLOT )) ||
673 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_MACRO )) ||
674 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_SERVICE)) ||
675 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_MAILTO )) ||
676 (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_NEWS ))
679 return E_UNSUPPORTED_CONTENT;
682 //-------------------------------------------
683 // (ii) Some special URLs indicates a given input stream,
684 // a full featured document model directly or
685 // specify a request for opening an empty document.
686 // Such contents are loadable in general.
687 // But we have to check, if the media descriptor contains
688 // all needed resources. If they are missing - the following
689 // load request will fail.
691 /* Attention: The following code cant work on such special URLs!
692 It should not break the office .. but it make no sense
693 to start expensive object creations and complex search
694 algorithm if its clear, that such URLs must be handled
695 in a special way .-)
698 // creation of new documents
699 if (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_PRIVATE_FACTORY))
700 return E_CAN_BE_LOADED;
702 // using of an existing input stream
703 ::comphelper::MediaDescriptor stlMediaDescriptor(lMediaDescriptor);
704 ::comphelper::MediaDescriptor::const_iterator pIt;
705 if (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_PRIVATE_STREAM))
707 pIt = stlMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_INPUTSTREAM());
708 css::uno::Reference< css::io::XInputStream > xStream;
709 if (pIt != stlMediaDescriptor.end())
710 pIt->second >>= xStream;
711 if (xStream.is())
712 return E_CAN_BE_LOADED;
713 LOG_WARNING("LoadEnv::classifyContent()", "loading from stream with right URL but invalid stream detected")
714 return E_UNSUPPORTED_CONTENT;
717 // using of a full featured document
718 if (ProtocolCheck::isProtocol(sURL,ProtocolCheck::E_PRIVATE_OBJECT))
720 pIt = stlMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_MODEL());
721 css::uno::Reference< css::frame::XModel > xModel;
722 if (pIt != stlMediaDescriptor.end())
723 pIt->second >>= xModel;
724 if (xModel.is())
725 return E_CAN_BE_SET;
726 LOG_WARNING("LoadEnv::classifyContent()", "loading with object with right URL but invalid object detected")
727 return E_UNSUPPORTED_CONTENT;
730 // following operatons can work on an internal type name only :-(
731 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = ::utl::getProcessServiceFactory();
732 css::uno::Reference< css::document::XTypeDetection > xDetect(xSMGR->createInstance(SERVICENAME_TYPEDETECTION), css::uno::UNO_QUERY);
734 ::rtl::OUString sType = xDetect->queryTypeByURL(sURL);
736 css::uno::Sequence< css::beans::NamedValue > lQuery(1) ;
737 css::uno::Reference< css::container::XContainerQuery > xContainer ;
738 css::uno::Reference< css::container::XEnumeration > xSet ;
739 css::uno::Sequence< ::rtl::OUString > lTypesReg(1);
742 //-------------------------------------------
743 lQuery[0].Name = ::framework::constant::Filter::PROP_TYPE;
744 lQuery[0].Value <<= sType;
746 xContainer = css::uno::Reference< css::container::XContainerQuery >(xSMGR->createInstance(SERVICENAME_FILTERFACTORY), css::uno::UNO_QUERY);
747 xSet = xContainer->createSubSetEnumerationByProperties(lQuery);
748 // at least one registered frame loader is enough!
749 if (xSet->hasMoreElements())
750 return E_CAN_BE_LOADED;
753 //-------------------------------------------
754 // (iii) If a FrameLoader service (or at least
755 // a Filter) can be found, which supports
756 // this URL - it must be a loadable content.
757 // Because both items are registered for types
758 // its enough to check for frame loaders only.
759 // Mos of our filters are handled by our global
760 // default loader. But there exist some specialized
761 // loader, which does not work on top of filters!
762 // So its not enough to search on the filter configuration.
763 // Further its not enough to search for types!
764 // Because there exist some types, which are referenced by
765 // other objects ... but not by filters nor frame loaders!
767 lTypesReg[0] = sType;
768 lQuery[0].Name = ::framework::constant::FrameLoader::PROP_TYPES;
769 lQuery[0].Value <<= lTypesReg;
771 xContainer = css::uno::Reference< css::container::XContainerQuery >(xSMGR->createInstance(SERVICENAME_FRAMELOADERFACTORY), css::uno::UNO_QUERY);
772 xSet = xContainer->createSubSetEnumerationByProperties(lQuery);
773 // at least one registered frame loader is enough!
774 if (xSet->hasMoreElements())
775 return E_CAN_BE_LOADED;
777 //-------------------------------------------
778 // (iv) Some URL protocols are supported by special services.
779 // E.g. ContentHandler.
780 // Such contents can be handled ... but not loaded.
782 lTypesReg[0] = sType;
783 lQuery[0].Name = ::framework::constant::ContentHandler::PROP_TYPES;
784 lQuery[0].Value <<= lTypesReg;
786 xContainer = css::uno::Reference< css::container::XContainerQuery >(xSMGR->createInstance(SERVICENAME_CONTENTHANDLERFACTORY), css::uno::UNO_QUERY);
787 xSet = xContainer->createSubSetEnumerationByProperties(lQuery);
788 // at least one registered content handler is enough!
789 if (xSet->hasMoreElements())
790 return E_CAN_BE_HANDLED;
792 //-------------------------------------------
793 // (v) Last but not least the UCB is used inside office to
794 // load contents. He has a special configuration to know
795 // which URL schemata can be used inside office.
796 css::uno::Reference< css::ucb::XContentProviderManager > xUCB(xSMGR->createInstance(SERVICENAME_UCBCONTENTBROKER), css::uno::UNO_QUERY);
797 if (xUCB->queryContentProvider(sURL).is())
798 return E_CAN_BE_LOADED;
800 //-------------------------------------------
801 // (TODO) At this point, we have no idea .-)
802 // But it seems to be better, to break all
803 // further requests for this URL. Otherwhise
804 // we can run into some trouble.
805 LOG_WARNING("LoadEnv::classifyContent()", "realy an unsupported content?")
806 return E_UNSUPPORTED_CONTENT;
809 /*-----------------------------------------------
810 03.11.2003 09:31
811 -----------------------------------------------*/
812 void LoadEnv::impl_detectTypeAndFilter()
813 throw(LoadEnvException, css::uno::RuntimeException)
815 static ::rtl::OUString TYPEPROP_PREFERREDFILTER = ::rtl::OUString::createFromAscii("PreferredFilter");
816 static ::rtl::OUString FILTERPROP_FLAGS = ::rtl::OUString::createFromAscii("Flags" );
817 static sal_Int32 FILTERFLAG_TEMPLATEPATH = 16;
819 // SAFE ->
820 ReadGuard aReadLock(m_aLock);
822 // Attention: Because our stl media descriptor is a copy of an uno sequence
823 // we cant use as an in/out parameter here. Copy it before and dont forget to
824 // actualize structure afterwards again!
825 css::uno::Sequence< css::beans::PropertyValue > lDescriptor = m_lMediaDescriptor.getAsConstPropertyValueList();
826 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
828 aReadLock.unlock();
829 // <- SAFE
831 ::rtl::OUString sType;
832 css::uno::Reference< css::document::XTypeDetection > xDetect(xSMGR->createInstance(SERVICENAME_TYPEDETECTION), css::uno::UNO_QUERY);
833 if (xDetect.is())
834 sType = xDetect->queryTypeByDescriptor(lDescriptor, sal_True); /*TODO should deep detection be able for enable/disable it from outside? */
836 // no valid content -> loading not possible
837 if (!sType.getLength())
838 throw LoadEnvException(LoadEnvException::ID_UNSUPPORTED_CONTENT);
840 // SAFE ->
841 WriteGuard aWriteLock(m_aLock);
843 // detection was successfully => update the descriptor member of this class
844 m_lMediaDescriptor << lDescriptor;
845 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_TYPENAME()] <<= sType;
846 // Is there an already detected (may be preselected) filter?
847 // see below ...
848 ::rtl::OUString sFilter = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_FILTERNAME(), ::rtl::OUString());
850 aWriteLock.unlock();
851 // <- SAFE
853 // But the type isnt enough. For loading sometimes we need more informations.
854 // E.g. for our "_default" feature, where we recylce any frame which contains
855 // and "Untitled" document, we must know if the new document is based on a template!
856 // But this information is available as a filter property only.
857 // => We must try(!) to detect the right filter for this load request.
858 // On the other side ... if no filter is available .. ignore it.
859 // Then the type information must be enough.
860 if (!sFilter.getLength())
862 // no -> try to find a preferred filter for the detected type.
863 // Dont forget to updatet he media descriptor.
864 css::uno::Reference< css::container::XNameAccess > xTypeCont(xDetect, css::uno::UNO_QUERY_THROW);
867 ::comphelper::SequenceAsHashMap lTypeProps(xTypeCont->getByName(sType));
868 sFilter = lTypeProps.getUnpackedValueOrDefault(TYPEPROP_PREFERREDFILTER, ::rtl::OUString());
869 if (sFilter.getLength())
871 // SAFE ->
872 aWriteLock.lock();
873 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_FILTERNAME()] <<= sFilter;
874 aWriteLock.unlock();
875 // <- SAFE
878 catch(const css::container::NoSuchElementException&)
882 // check if the filter (if one exists) points to a template format filter.
883 // Then we have to add the property "AsTemplate".
884 // We need this information to decide afterwards if we can use a "recycle frame"
885 // for target "_default" or has to create a new one everytimes.
886 // On the other side we have to supress that, if this property already exists
887 // and should trigger a special handling. Then the outside calli of this method here,
888 // has to know, what he is doing .-)
890 sal_Bool bIsOwnTemplate = sal_False;
891 if (sFilter.getLength())
893 css::uno::Reference< css::container::XNameAccess > xFilterCont(xSMGR->createInstance(SERVICENAME_FILTERFACTORY), css::uno::UNO_QUERY_THROW);
896 ::comphelper::SequenceAsHashMap lFilterProps(xFilterCont->getByName(sFilter));
897 sal_Int32 nFlags = lFilterProps.getUnpackedValueOrDefault(FILTERPROP_FLAGS, (sal_Int32)0);
898 bIsOwnTemplate = ((nFlags & FILTERFLAG_TEMPLATEPATH) == FILTERFLAG_TEMPLATEPATH);
900 catch(const css::container::NoSuchElementException&)
903 if (bIsOwnTemplate)
905 // SAFE ->
906 aWriteLock.lock();
907 // Dont overwrite external decisions! See comments before ...
908 ::comphelper::MediaDescriptor::const_iterator pAsTemplateItem = m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_ASTEMPLATE());
909 if (pAsTemplateItem == m_lMediaDescriptor.end())
910 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_ASTEMPLATE()] <<= sal_True;
911 aWriteLock.unlock();
912 // <- SAFE
916 /*-----------------------------------------------
917 15.08.2003 09:38
918 -----------------------------------------------*/
919 sal_Bool LoadEnv::impl_handleContent()
920 throw(LoadEnvException, css::uno::RuntimeException)
922 // SAFE -> -----------------------------------
923 ReadGuard aReadLock(m_aLock);
925 // the type must exist inside the descriptor ... otherwhise this class is implemented wrong :-)
926 ::rtl::OUString sType = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_TYPENAME(), ::rtl::OUString());
927 if (!sType.getLength())
928 throw LoadEnvException(LoadEnvException::ID_INVALID_MEDIADESCRIPTOR);
930 // convert media descriptor and URL to right format for later interface call!
931 css::uno::Sequence< css::beans::PropertyValue > lDescriptor;
932 m_lMediaDescriptor >> lDescriptor;
933 css::util::URL aURL = m_aURL;
935 // get neccessary container to query for a handler object
936 css::uno::Reference< css::lang::XMultiServiceFactory > xFactory(m_xSMGR->createInstance(SERVICENAME_CONTENTHANDLERFACTORY), css::uno::UNO_QUERY);
937 css::uno::Reference< css::container::XContainerQuery > xQuery (xFactory , css::uno::UNO_QUERY);
939 aReadLock.unlock();
940 // <- SAFE -----------------------------------
942 // query
943 css::uno::Sequence< ::rtl::OUString > lTypeReg(1);
944 lTypeReg[0] = sType;
946 css::uno::Sequence< css::beans::NamedValue > lQuery(1);
947 lQuery[0].Name = ::framework::constant::ContentHandler::PROP_TYPES;
948 lQuery[0].Value <<= lTypeReg;
950 css::uno::Reference< css::container::XEnumeration > xSet = xQuery->createSubSetEnumerationByProperties(lQuery);
951 while(xSet->hasMoreElements())
953 ::comphelper::SequenceAsHashMap lProps (xSet->nextElement());
954 ::rtl::OUString sHandler = lProps.getUnpackedValueOrDefault(::framework::constant::ContentHandler::PROP_NAME, ::rtl::OUString());
956 css::uno::Reference< css::frame::XNotifyingDispatch > xHandler;
959 xHandler = css::uno::Reference< css::frame::XNotifyingDispatch >(xFactory->createInstance(sHandler), css::uno::UNO_QUERY);
960 if (!xHandler.is())
961 continue;
963 catch(const css::uno::RuntimeException&)
964 { throw; }
965 catch(const css::uno::Exception&)
966 { continue; }
968 // SAFE -> -----------------------------------
969 WriteGuard aWriteLock(m_aLock);
970 m_xAsynchronousJob = xHandler;
971 m_pCheck = this;
972 LoadEnvListener* pListener = new LoadEnvListener(m_pCheck, this);
973 aWriteLock.unlock();
974 // <- SAFE -----------------------------------
976 css::uno::Reference< css::frame::XDispatchResultListener > xListener(static_cast< css::frame::XDispatchResultListener* >(pListener), css::uno::UNO_QUERY);
977 xHandler->dispatchWithNotification(aURL, lDescriptor, xListener);
979 return sal_True;
982 return sal_False;
985 //-----------------------------------------------
986 sal_Bool LoadEnv::impl_furtherDocsAllowed()
988 // SAFE ->
989 ReadGuard aReadLock(m_aLock);
990 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
991 aReadLock.unlock();
992 // <- SAFE
994 sal_Bool bAllowed = sal_True;
998 css::uno::Any aVal = ::comphelper::ConfigurationHelper::readDirectKey(
999 xSMGR,
1000 ::rtl::OUString::createFromAscii("org.openoffice.Office.Common/"),
1001 ::rtl::OUString::createFromAscii("Misc"),
1002 ::rtl::OUString::createFromAscii("MaxOpenDocuments"),
1003 ::comphelper::ConfigurationHelper::E_READONLY);
1005 // NIL means: count of allowed documents = infinite !
1006 // => return TRUE
1007 if ( ! aVal.hasValue())
1008 bAllowed = sal_True;
1009 else
1011 sal_Int32 nMaxOpenDocuments = 0;
1012 aVal >>= nMaxOpenDocuments;
1014 css::uno::Reference< css::frame::XFramesSupplier > xDesktop(
1015 xSMGR->createInstance(SERVICENAME_DESKTOP),
1016 css::uno::UNO_QUERY_THROW);
1018 FrameListAnalyzer aAnalyzer(xDesktop,
1019 css::uno::Reference< css::frame::XFrame >(),
1020 FrameListAnalyzer::E_HELP |
1021 FrameListAnalyzer::E_BACKINGCOMPONENT |
1022 FrameListAnalyzer::E_HIDDEN);
1024 sal_Int32 nOpenDocuments = aAnalyzer.m_lOtherVisibleFrames.getLength();
1025 bAllowed = (nOpenDocuments < nMaxOpenDocuments);
1028 catch(const css::uno::Exception&)
1029 { bAllowed = sal_True; } // !! internal errors are no reason to disturb the office from opening documents .-)
1031 if ( ! bAllowed )
1033 // SAFE ->
1034 aReadLock.lock();
1035 css::uno::Reference< css::task::XInteractionHandler > xInteraction = m_lMediaDescriptor.getUnpackedValueOrDefault(
1036 ::comphelper::MediaDescriptor::PROP_INTERACTIONHANDLER(),
1037 css::uno::Reference< css::task::XInteractionHandler >());
1038 aReadLock.unlock();
1039 // <- SAFE
1041 if (xInteraction.is())
1043 css::uno::Any aInteraction;
1044 css::uno::Sequence< css::uno::Reference< css::task::XInteractionContinuation > > lContinuations(2);
1046 ContinuationAbort* pAbort = new ContinuationAbort();
1047 ContinuationApprove* pApprove = new ContinuationApprove();
1049 lContinuations[0] = css::uno::Reference< css::task::XInteractionContinuation >(
1050 static_cast< css::task::XInteractionContinuation* >(pAbort),
1051 css::uno::UNO_QUERY_THROW);
1052 lContinuations[1] = css::uno::Reference< css::task::XInteractionContinuation >(
1053 static_cast< css::task::XInteractionContinuation* >(pApprove),
1054 css::uno::UNO_QUERY_THROW);
1056 css::task::ErrorCodeRequest aErrorCode;
1057 aErrorCode.ErrCode = ERRCODE_SFX_NOMOREDOCUMENTSALLOWED;
1058 aInteraction <<= aErrorCode;
1060 InteractionRequest* pRequest = new InteractionRequest(aInteraction, lContinuations);
1061 css::uno::Reference< css::task::XInteractionRequest > xRequest(
1062 static_cast< css::task::XInteractionRequest* >(pRequest),
1063 css::uno::UNO_QUERY_THROW);
1065 xInteraction->handle(xRequest);
1069 return bAllowed;
1072 //-----------------------------------------------
1073 sal_Bool LoadEnv::impl_loadContent()
1074 throw(LoadEnvException, css::uno::RuntimeException)
1076 // SAFE -> -----------------------------------
1077 WriteGuard aWriteLock(m_aLock);
1079 // search or create right target frame
1080 ::rtl::OUString sTarget = m_sTarget;
1081 if (TargetHelper::matchSpecialTarget(sTarget, TargetHelper::E_DEFAULT))
1083 m_xTargetFrame = impl_searchAlreadyLoaded();
1084 if (m_xTargetFrame.is())
1086 impl_setResult(sal_True);
1087 return sal_True;
1089 m_xTargetFrame = impl_searchRecycleTarget();
1092 if (! m_xTargetFrame.is())
1094 if (
1095 (TargetHelper::matchSpecialTarget(sTarget, TargetHelper::E_BLANK )) ||
1096 (TargetHelper::matchSpecialTarget(sTarget, TargetHelper::E_DEFAULT))
1099 if (! impl_furtherDocsAllowed())
1100 return sal_False;
1101 m_xTargetFrame = m_xBaseFrame->findFrame(SPECIALTARGET_BLANK, 0);
1102 m_bCloseFrameOnError = m_xTargetFrame.is();
1104 else
1106 sal_Int32 nFlags = m_nSearchFlags & ~css::frame::FrameSearchFlag::CREATE;
1107 m_xTargetFrame = m_xBaseFrame->findFrame(sTarget, nFlags);
1108 if (! m_xTargetFrame.is())
1110 if (! impl_furtherDocsAllowed())
1111 return sal_False;
1112 m_xTargetFrame = m_xBaseFrame->findFrame(SPECIALTARGET_BLANK, 0);
1113 m_bCloseFrameOnError = m_xTargetFrame.is();
1118 // If we couldn't find a valid frame or the frame has no container window
1119 // we have to throw an exception.
1120 if (
1121 ( ! m_xTargetFrame.is() ) ||
1122 ( ! m_xTargetFrame->getContainerWindow().is() )
1124 throw LoadEnvException(LoadEnvException::ID_NO_TARGET_FOUND);
1126 css::uno::Reference< css::frame::XFrame > xTargetFrame = m_xTargetFrame;
1128 // Now we have a valid frame ... and type detection was already done.
1129 // We should apply the module dependend window position and size to the
1130 // frame window.
1131 impl_applyPersistentWindowState(xTargetFrame->getContainerWindow());
1133 // Don't forget to lock task for following load process. Otherwise it could die
1134 // during this operation runs by terminating the office or closing this task via api.
1135 // If we set this lock "close()" will return false and closing will be broken.
1136 // Attention: Don't forget to reset this lock again after finishing operation.
1137 // Otherwise task AND office couldn't die!!!
1138 // This includes gracefully handling of Exceptions (Runtime!) too ...
1139 // Thats why we use a specialized guard, which will reset the lock
1140 // if it will be run out of scope.
1142 // Note further: ignore if this internal guard already contains a resource.
1143 // Might impl_searchRecylcTarget() set it before. But incase this impl-method wasnt used
1144 // and the target frame was new created ... this lock here must be set!
1145 css::uno::Reference< css::document::XActionLockable > xTargetLock(xTargetFrame, css::uno::UNO_QUERY);
1146 m_aTargetLock.setResource(xTargetLock);
1148 // Add status indicator to descriptor. Loader can show an progresses then.
1149 // But don't do it, if loading should be hidden or preview is used ...!
1150 // So we prevent our code against wrong using. Why?
1151 // It could be, that using of this progress could make trouble. e.g. He make window visible ...
1152 // but shouldn't do that. But if no indicator is available ... nobody has a chance to do that!
1153 sal_Bool bHidden = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN() , sal_False );
1154 sal_Bool bMinimized = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_MINIMIZED() , sal_False );
1155 sal_Bool bPreview = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_PREVIEW() , sal_False );
1156 css::uno::Reference< css::task::XStatusIndicator > xProgress = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_STATUSINDICATOR(), css::uno::Reference< css::task::XStatusIndicator >());
1158 if (!bHidden && !bMinimized && !bPreview && !xProgress.is())
1160 // Note: its an optional interface!
1161 css::uno::Reference< css::task::XStatusIndicatorFactory > xProgressFactory(xTargetFrame, css::uno::UNO_QUERY);
1162 if (xProgressFactory.is())
1164 xProgress = xProgressFactory->createStatusIndicator();
1165 if (xProgress.is())
1166 m_lMediaDescriptor[::comphelper::MediaDescriptor::PROP_STATUSINDICATOR()] <<= xProgress;
1170 // convert media descriptor and URL to right format for later interface call!
1171 css::uno::Sequence< css::beans::PropertyValue > lDescriptor;
1172 m_lMediaDescriptor >> lDescriptor;
1173 ::rtl::OUString sURL = m_aURL.Complete;
1175 // try to locate any interested frame loader
1176 css::uno::Reference< css::uno::XInterface > xLoader = impl_searchLoader();
1177 css::uno::Reference< css::frame::XFrameLoader > xAsyncLoader(xLoader, css::uno::UNO_QUERY);
1178 css::uno::Reference< css::frame::XSynchronousFrameLoader > xSyncLoader (xLoader, css::uno::UNO_QUERY);
1180 if (xAsyncLoader.is())
1182 // SAFE -> -----------------------------------
1183 aWriteLock.lock();
1184 m_xAsynchronousJob = xAsyncLoader;
1185 m_pCheck = this;
1186 LoadEnvListener* pListener = new LoadEnvListener(m_pCheck, this);
1187 aWriteLock.unlock();
1188 // <- SAFE -----------------------------------
1190 css::uno::Reference< css::frame::XLoadEventListener > xListener(static_cast< css::frame::XLoadEventListener* >(pListener), css::uno::UNO_QUERY);
1191 xAsyncLoader->load(xTargetFrame, sURL, lDescriptor, xListener);
1193 return sal_True;
1195 else
1196 if (xSyncLoader.is())
1198 sal_Bool bResult = xSyncLoader->load(lDescriptor, xTargetFrame);
1199 // react for the result here, so the outside waiting
1200 // code can ask for it later.
1201 impl_setResult(bResult);
1202 // But the return value indicates a valid started(!) operation.
1203 // And thats true everxtimes, we reach this line :-)
1204 return sal_True;
1207 aWriteLock.unlock();
1208 // <- SAFE
1210 return sal_False;
1213 /*-----------------------------------------------
1214 06.02.2004 14:40
1215 -----------------------------------------------*/
1216 css::uno::Reference< css::uno::XInterface > LoadEnv::impl_searchLoader()
1218 // SAFE -> -----------------------------------
1219 ReadGuard aReadLock(m_aLock);
1221 // special mode to set an existing component on this frame
1222 // In such case the laoder is fix. It must be the SFX based implementation,
1223 // which can create a view on top of such xModel components :-)
1224 if (m_eContentType == E_CAN_BE_SET)
1228 return m_xSMGR->createInstance(IMPLEMENTATIONNAME_GENERICFRAMELOADER);
1230 catch(const css::uno::RuntimeException&)
1231 { throw; }
1232 catch(const css::uno::Exception&)
1234 throw LoadEnvException(LoadEnvException::ID_INVALID_ENVIRONMENT);
1237 // Otherwhise ...
1238 // We need this type information to locate an registered frame loader
1239 // Without such information we cant work!
1240 ::rtl::OUString sType = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_TYPENAME(), ::rtl::OUString());
1241 if (!sType.getLength())
1242 throw LoadEnvException(LoadEnvException::ID_INVALID_MEDIADESCRIPTOR);
1244 // try to locate any interested frame loader
1245 css::uno::Reference< css::lang::XMultiServiceFactory > xLoaderFactory(m_xSMGR->createInstance(SERVICENAME_FRAMELOADERFACTORY), css::uno::UNO_QUERY);
1246 css::uno::Reference< css::container::XContainerQuery > xQuery (xLoaderFactory , css::uno::UNO_QUERY);
1248 aReadLock.unlock();
1249 // <- SAFE -----------------------------------
1251 css::uno::Sequence< ::rtl::OUString > lTypesReg(1);
1252 lTypesReg[0] = sType;
1254 css::uno::Sequence< css::beans::NamedValue > lQuery(1);
1255 lQuery[0].Name = ::framework::constant::FrameLoader::PROP_TYPES;
1256 lQuery[0].Value <<= lTypesReg;
1258 css::uno::Reference< css::container::XEnumeration > xSet = xQuery->createSubSetEnumerationByProperties(lQuery);
1259 while(xSet->hasMoreElements())
1261 // try everyone ...
1262 // Ignore any loader, which makes trouble :-)
1263 ::comphelper::SequenceAsHashMap lLoaderProps(xSet->nextElement());
1264 ::rtl::OUString sLoader = lLoaderProps.getUnpackedValueOrDefault(::framework::constant::FrameLoader::PROP_NAME, ::rtl::OUString());
1265 css::uno::Reference< css::uno::XInterface > xLoader ;
1268 xLoader = xLoaderFactory->createInstance(sLoader);
1269 if (xLoader.is())
1270 return xLoader;
1272 catch(const css::uno::RuntimeException&)
1273 { throw; }
1274 catch(const css::uno::Exception&)
1275 { continue; }
1278 return css::uno::Reference< css::uno::XInterface >();
1281 /*-----------------------------------------------
1282 24.01.2006 15:11
1283 -----------------------------------------------*/
1284 void LoadEnv::impl_jumpToMark(const css::uno::Reference< css::frame::XFrame >& xFrame,
1285 const css::util::URL& aURL )
1287 if (! aURL.Mark.getLength())
1288 return;
1290 css::uno::Reference< css::frame::XDispatchProvider > xProvider(xFrame, css::uno::UNO_QUERY);
1291 if (! xProvider.is())
1292 return;
1294 // SAFE ->
1295 ReadGuard aReadLock(m_aLock);
1296 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
1297 aReadLock.unlock();
1298 // <- SAFE
1300 css::util::URL aCmd;
1301 aCmd.Complete = ::rtl::OUString::createFromAscii(".uno:JumpToMark");
1303 css::uno::Reference< css::util::XURLTransformer > xParser(xSMGR->createInstance(SERVICENAME_URLTRANSFORMER), css::uno::UNO_QUERY_THROW);
1304 xParser->parseStrict(aCmd);
1306 css::uno::Reference< css::frame::XDispatch > xDispatcher = xProvider->queryDispatch(aCmd, SPECIALTARGET_SELF, 0);
1307 if (! xDispatcher.is())
1308 return;
1310 ::comphelper::SequenceAsHashMap lArgs;
1311 lArgs[::rtl::OUString::createFromAscii("Bookmark")] <<= aURL.Mark;
1312 xDispatcher->dispatch(aCmd, lArgs.getAsConstPropertyValueList());
1315 /*-----------------------------------------------
1316 31.07.2003 09:02
1317 -----------------------------------------------*/
1318 css::uno::Reference< css::frame::XFrame > LoadEnv::impl_searchAlreadyLoaded()
1319 throw(LoadEnvException, css::uno::RuntimeException)
1321 // SAFE ->
1322 ReadGuard aReadLock(m_aLock);
1324 // such search is allowed for special requests only ...
1325 // or better its not allowed for some requests in general :-)
1326 if (
1327 ( ! TargetHelper::matchSpecialTarget(m_sTarget, TargetHelper::E_DEFAULT) ) ||
1328 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_ASTEMPLATE() , sal_False) == sal_True) ||
1329 // (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN() , sal_False) == sal_True) ||
1330 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_OPENNEWVIEW(), sal_False) == sal_True)
1333 return css::uno::Reference< css::frame::XFrame >();
1336 // check URL
1337 // May its not usefull to start expensive document search, if it
1338 // can fail only .. because we load from a stream or model directly!
1339 if (
1340 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_STREAM )) ||
1341 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_OBJECT ))
1342 /*TODO should be private:factory here tested too? */
1345 return css::uno::Reference< css::frame::XFrame >();
1348 // otherwhise - iterate through the tasks of the desktop container
1349 // to find out, which of them might contains the requested document
1350 css::uno::Reference< css::frame::XFramesSupplier > xSupplier(m_xSMGR->createInstance(SERVICENAME_DESKTOP), css::uno::UNO_QUERY);
1351 css::uno::Reference< css::container::XIndexAccess > xTaskList(xSupplier->getFrames() , css::uno::UNO_QUERY);
1353 if (!xTaskList.is())
1354 return css::uno::Reference< css::frame::XFrame >(); // task list can be empty!
1356 // Note: To detect if a document was alrady loaded before
1357 // we check URLs here only. But might the existing and the requred
1358 // document has different versions! Then its URLs are the same ...
1359 sal_Int16 nNewVersion = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_VERSION(), (sal_Int16)(-1));
1361 // will be used to save the first hidden frame referring the searched model
1362 // Normaly we are interested on visible frames ... but if there is no such visible
1363 // frame we referr to any hidden frame also (but as fallback only).
1364 css::uno::Reference< css::frame::XFrame > xHiddenTask;
1365 css::uno::Reference< css::frame::XFrame > xTask;
1367 sal_Int32 count = xTaskList->getCount();
1368 for (sal_Int32 i=0; i<count; ++i)
1372 // locate model of task
1373 // Note: Without a model there is no chance to decide if
1374 // this task contains the searched document or not!
1375 xTaskList->getByIndex(i) >>= xTask;
1376 if (!xTask.is())
1377 continue;
1379 css::uno::Reference< css::frame::XController > xController = xTask->getController();
1380 if (!xController.is())
1382 xTask.clear ();
1383 continue;
1386 css::uno::Reference< css::frame::XModel > xModel = xController->getModel();
1387 if (!xModel.is())
1389 xTask.clear ();
1390 continue;
1393 // don't check the complete URL here.
1394 // use its main part - ignore optional jumpmarks!
1395 const ::rtl::OUString sURL = xModel->getURL();
1396 if (!m_aURL.Main.equals(sURL))
1398 xTask.clear ();
1399 continue;
1402 // get the original load arguments from the current document
1403 // and decide if its realy the same then the one will be.
1404 // It must be visible and must use the same file revision ...
1405 // or must not have any file revision set (-1 == -1!)
1406 ::comphelper::MediaDescriptor lOldDocDescriptor(xModel->getArgs());
1408 if (lOldDocDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_VERSION(), (sal_Int32)(-1)) != nNewVersion)
1410 xTask.clear ();
1411 continue;
1414 // Hidden frames are special.
1415 // They will be used as "last chance" if there is no visible frame pointing to the same model.
1416 // Safe the result but continue with current loop might be looking for other visible frames.
1417 ::sal_Bool bIsHidden = lOldDocDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN(), sal_False);
1418 if (
1419 ( bIsHidden ) &&
1420 ( ! xHiddenTask.is())
1423 xHiddenTask = xTask;
1424 xTask.clear ();
1425 continue;
1428 // We found a visible task pointing to the right model ...
1429 // Break search.
1430 break;
1432 catch(const css::uno::RuntimeException& exRun)
1433 { throw exRun; }
1434 catch(const css::uno::Exception&)
1435 { continue; }
1438 css::uno::Reference< css::frame::XFrame > xResult;
1439 if (xTask.is())
1440 xResult = xTask;
1441 else
1442 if (xHiddenTask.is())
1443 xResult = xHiddenTask;
1445 if (xResult.is())
1447 // Now we are shure, that this task includes the searched document.
1448 // It's time to activate it. As special feature we try to jump internaly
1449 // if an optional jumpmark is given too.
1450 if (m_aURL.Mark.getLength())
1451 impl_jumpToMark(xResult, m_aURL);
1453 // bring it to front and make sure it's visible...
1454 impl_makeFrameWindowVisible(xResult->getContainerWindow(), sal_True);
1457 aReadLock.unlock();
1458 // <- SAFE
1460 return xResult;
1463 /*-----------------------------------------------
1464 30.03.2004 09:12
1465 -----------------------------------------------*/
1466 sal_Bool LoadEnv::impl_isFrameAlreadyUsedForLoading(const css::uno::Reference< css::frame::XFrame >& xFrame) const
1468 css::uno::Reference< css::document::XActionLockable > xLock(xFrame, css::uno::UNO_QUERY);
1470 // ? no lock interface ?
1471 // Might its an external written frame implementation :-(
1472 // Allowing using of it ... but it can fail if its not synchronized with our processes !
1473 if (!xLock.is())
1474 return sal_False;
1476 // Otherwhise we have to look for any other existing lock.
1477 return xLock->isActionLocked();
1480 /*-----------------------------------------------
1481 30.03.2004 09:12
1482 -----------------------------------------------*/
1483 css::uno::Reference< css::frame::XFrame > LoadEnv::impl_searchRecycleTarget()
1484 throw(LoadEnvException, css::uno::RuntimeException)
1486 // SAFE -> ..................................
1487 ReadGuard aReadLock(m_aLock);
1489 // The special backing mode frame will be recycled by definition!
1490 // It does'nt matter if somehwere whish to create a new view
1491 // or open a new untitled document ...
1492 // The only exception form that - hidden frames!
1493 if (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN(), sal_False) == sal_True)
1494 return css::uno::Reference< css::frame::XFrame >();
1496 css::uno::Reference< css::frame::XFramesSupplier > xSupplier(m_xSMGR->createInstance(SERVICENAME_DESKTOP), css::uno::UNO_QUERY);
1497 FrameListAnalyzer aTasksAnalyzer(xSupplier, css::uno::Reference< css::frame::XFrame >(), FrameListAnalyzer::E_BACKINGCOMPONENT);
1498 if (aTasksAnalyzer.m_xBackingComponent.is())
1500 if (!impl_isFrameAlreadyUsedForLoading(aTasksAnalyzer.m_xBackingComponent))
1502 // bring it to front ...
1503 impl_makeFrameWindowVisible(aTasksAnalyzer.m_xBackingComponent->getContainerWindow(), sal_True);
1504 return aTasksAnalyzer.m_xBackingComponent;
1508 // These states indicates the wishing for creation of a new view in general.
1509 if (
1510 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_ASTEMPLATE() , sal_False) == sal_True) ||
1511 (m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_OPENNEWVIEW(), sal_False) == sal_True)
1514 return css::uno::Reference< css::frame::XFrame >();
1517 // On the other side some special URLs will open a new frame everytimes (expecting
1518 // they can use the backing-mode frame!)
1519 if (
1520 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_FACTORY )) ||
1521 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_STREAM )) ||
1522 (ProtocolCheck::isProtocol(m_aURL.Complete, ProtocolCheck::E_PRIVATE_OBJECT ))
1525 return css::uno::Reference< css::frame::XFrame >();
1528 // No backing frame! No special URL => recycle active task - if possible.
1529 // Means - if it does not already contains a modified document, or
1530 // use another office module.
1531 css::uno::Reference< css::frame::XFrame > xTask = xSupplier->getActiveFrame();
1533 // not a real error - but might a focus problem!
1534 if (!xTask.is())
1535 return css::uno::Reference< css::frame::XFrame >();
1537 // not a real error - may its a view only
1538 css::uno::Reference< css::frame::XController > xController = xTask->getController();
1539 if (!xController.is())
1540 return css::uno::Reference< css::frame::XFrame >();
1542 // not a real error - may its a db component instead of a full feartured office document
1543 css::uno::Reference< css::frame::XModel > xModel = xController->getModel();
1544 if (!xModel.is())
1545 return css::uno::Reference< css::frame::XFrame >();
1547 // get some more informations ...
1549 // A valid set URL means: there is already a location for this document.
1550 // => it was saved there or opened from there. Such Documents can not be used here.
1551 // We search for empty document ... created by a private:factory/ URL!
1552 if (xModel->getURL().getLength()>0)
1553 return css::uno::Reference< css::frame::XFrame >();
1555 // The old document must be unmodified ...
1556 css::uno::Reference< css::util::XModifiable > xModified(xModel, css::uno::UNO_QUERY);
1557 if (xModified->isModified())
1558 return css::uno::Reference< css::frame::XFrame >();
1560 Window* pWindow = VCLUnoHelper::GetWindow(xTask->getContainerWindow());
1561 if (pWindow && pWindow->IsInModalMode())
1562 return css::uno::Reference< css::frame::XFrame >();
1564 // find out the application type of this document
1565 // We can recycle only documents, which uses the same application
1566 // then the new one.
1567 SvtModuleOptions::EFactory eOldApp = SvtModuleOptions::ClassifyFactoryByModel(xModel);
1568 SvtModuleOptions::EFactory eNewApp = SvtModuleOptions::ClassifyFactoryByURL (m_aURL.Complete, m_lMediaDescriptor.getAsConstPropertyValueList());
1570 aReadLock.unlock();
1571 // <- SAFE ..................................
1573 if (eOldApp != eNewApp)
1574 return css::uno::Reference< css::frame::XFrame >();
1576 // OK this task seams to be useable for recycling
1577 // But we should mark it as such - means set an action lock.
1578 // Otherwhise it would be used more then ones or will be destroyed
1579 // by a close() or terminate() request.
1580 // But if such lock already exist ... it means this task is used for
1581 // any other operation already. Don't use it then.
1582 if (impl_isFrameAlreadyUsedForLoading(xTask))
1583 return css::uno::Reference< css::frame::XFrame >();
1585 // OK - there is a valid target frame.
1586 // But may be it contains already a document.
1587 // Then we have to ask it, if it allows recylcing of this frame .-)
1588 sal_Bool bReactivateOldControllerOnError = sal_False;
1589 css::uno::Reference< css::frame::XController > xOldDoc = xTask->getController();
1590 if (xOldDoc.is())
1592 bReactivateOldControllerOnError = xOldDoc->suspend(sal_True);
1593 if (! bReactivateOldControllerOnError)
1594 return css::uno::Reference< css::frame::XFrame >();
1597 // SAFE -> ..................................
1598 WriteGuard aWriteLock(m_aLock);
1600 css::uno::Reference< css::document::XActionLockable > xLock(xTask, css::uno::UNO_QUERY);
1601 if (!m_aTargetLock.setResource(xLock))
1602 return css::uno::Reference< css::frame::XFrame >();
1604 m_bReactivateControllerOnError = bReactivateOldControllerOnError;
1605 aWriteLock.unlock();
1606 // <- SAFE ..................................
1608 // bring it to front ...
1609 impl_makeFrameWindowVisible(xTask->getContainerWindow(), sal_True);
1611 return xTask;
1614 /*-----------------------------------------------
1615 15.08.2003 12:39
1616 -----------------------------------------------*/
1617 void LoadEnv::impl_reactForLoadingState()
1618 throw(LoadEnvException, css::uno::RuntimeException)
1620 /*TODO reset action locks */
1622 // SAFE -> ----------------------------------
1623 ReadGuard aReadLock(m_aLock);
1625 if (m_bLoaded)
1627 // Bring the new loaded document to front (if allowed!).
1628 // Note: We show new created frames here only.
1629 // We dont hide already visible frames here ...
1630 css::uno::Reference< css::awt::XWindow > xWindow = m_xTargetFrame->getContainerWindow();
1631 sal_Bool bHidden = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_HIDDEN(), sal_False);
1632 sal_Bool bRecovered = (m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_SALVAGEDFILE()) != m_lMediaDescriptor.end());
1633 sal_Bool bMinimized = m_lMediaDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_MINIMIZED(), sal_False);
1635 if (bMinimized)
1637 ::vos::OClearableGuard aSolarGuard(Application::GetSolarMutex());
1638 Window* pWindow = VCLUnoHelper::GetWindow(xWindow);
1639 // check for system window is neccessary to guarantee correct pointer cast!
1640 if (pWindow && pWindow->IsSystemWindow())
1641 ((WorkWindow*)pWindow)->Minimize();
1643 else
1644 if (!bHidden && !bRecovered)
1646 // show frame ... if it's not still visible ...
1647 // But do nothing if it's already visible!
1648 impl_makeFrameWindowVisible(xWindow, sal_False);
1651 // Note: Only if an existing property "FrameName" is given by this media descriptor,
1652 // it should be used. Otherwhise we should do nothing. May be the outside code has already
1653 // set a frame name on the target!
1654 ::comphelper::MediaDescriptor::const_iterator pFrameName = m_lMediaDescriptor.find(::comphelper::MediaDescriptor::PROP_FRAMENAME());
1655 if (pFrameName != m_lMediaDescriptor.end())
1657 ::rtl::OUString sFrameName;
1658 pFrameName->second >>= sFrameName;
1659 // Check the name again. e.g. "_default" isnt allowed.
1660 // On the other side "_beamer" is a valid name :-)
1661 if (TargetHelper::isValidNameForFrame(sFrameName))
1662 m_xTargetFrame->setName(sFrameName);
1665 else if (m_bReactivateControllerOnError)
1667 // Try to reactivate the old document (if any exists!)
1668 css::uno::Reference< css::frame::XController > xOldDoc = m_xTargetFrame->getController();
1669 // clear does not depend from reactivation state of a might existing old document!
1670 // We must make shure, that a might following getTargetComponent() call does not return
1671 // the old document!
1672 m_xTargetFrame.clear();
1673 if (xOldDoc.is())
1675 sal_Bool bReactivated = xOldDoc->suspend(sal_False);
1676 if (!bReactivated)
1677 throw LoadEnvException(LoadEnvException::ID_COULD_NOT_REACTIVATE_CONTROLLER);
1678 m_bReactivateControllerOnError = sal_False;
1681 else 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 css::uno::Any aRequest;
1716 bool bThrow = false;
1717 if ( !m_bLoaded && m_pQuietInteraction && m_pQuietInteraction->wasUsed() )
1719 aRequest = m_pQuietInteraction->getRequest();
1720 m_pQuietInteraction->release();
1721 m_pQuietInteraction = 0;
1722 bThrow = true;
1725 aReadLock.unlock();
1727 if (bThrow)
1729 css::uno::Exception aEx;
1730 if ( aRequest >>= aEx )
1731 throw LoadEnvException( LoadEnvException::ID_GENERAL_ERROR, aEx );
1734 // <- SAFE ----------------------------------
1737 /*-----------------------------------------------
1738 16.01.2005 13:04
1739 -----------------------------------------------*/
1740 void LoadEnv::impl_makeFrameWindowVisible(const css::uno::Reference< css::awt::XWindow >& xWindow ,
1741 sal_Bool bForceToFront)
1743 css::uno::Reference< css::awt::XTopWindow > xTopWindow(xWindow, css::uno::UNO_QUERY);
1745 if (xWindow.is())
1746 xWindow->setVisible(sal_True);
1748 if (xTopWindow.is() && bForceToFront)
1749 xTopWindow->toFront();
1751 /* #i19976#
1752 We tried to prevent a toFront() call in case the user putted the
1753 loading document into the background ..
1754 But we had several errors trying that. So we decided to
1755 rollback these changes and bring the new loaded document to front hardly !
1757 css::uno::Reference< css::awt::XWindow2 > xWindow2(xWindow, css::uno::UNO_QUERY);
1759 sal_Bool bIsVisible = sal_False;
1760 if (xWindow2.is())
1761 bIsVisible = xWindow2->isVisible(); // TODO is parent visible too ? .-)
1763 if (!bIsVisible)
1765 xWindow->setVisible(sal_True);
1766 bForceToFront = sal_True;
1769 if (
1770 (bForceToFront ) &&
1771 (xTopWindow.is())
1774 xTopWindow->toFront();
1779 /*-----------------------------------------------
1780 15.03.2005 11:12
1781 -----------------------------------------------*/
1782 void LoadEnv::impl_applyPersistentWindowState(const css::uno::Reference< css::awt::XWindow >& xWindow)
1784 static ::rtl::OUString PACKAGE_SETUP_MODULES = ::rtl::OUString::createFromAscii("/org.openoffice.Setup/Office/Factories");
1786 // no window -> action not possible
1787 if (!xWindow.is())
1788 return;
1790 // window already visible -> do nothing! If we use a "recycle frame" for loading ...
1791 // the current position and size must be used.
1792 css::uno::Reference< css::awt::XWindow2 > xVisibleCheck(xWindow, css::uno::UNO_QUERY);
1793 if (
1794 (xVisibleCheck.is() ) &&
1795 (xVisibleCheck->isVisible())
1797 return;
1799 // SOLAR SAFE ->
1800 ::vos::OClearableGuard aSolarLock1(Application::GetSolarMutex());
1802 Window* pWindow = VCLUnoHelper::GetWindow(xWindow);
1803 sal_Bool bSystemWindow = pWindow->IsSystemWindow();
1804 sal_Bool bWorkWindow = (pWindow->GetType() == WINDOW_WORKWINDOW);
1806 if (!bSystemWindow && !bWorkWindow)
1807 return;
1809 // dont overwrite this special state!
1810 WorkWindow* pWorkWindow = (WorkWindow*)pWindow;
1811 if (pWorkWindow->IsMinimized())
1812 return;
1814 aSolarLock1.clear();
1815 // <- SOLAR SAFE
1817 // SAFE ->
1818 ReadGuard aReadLock(m_aLock);
1820 // no filter -> no module -> no persistent window state
1821 ::rtl::OUString sFilter = m_lMediaDescriptor.getUnpackedValueOrDefault(
1822 ::comphelper::MediaDescriptor::PROP_FILTERNAME(),
1823 ::rtl::OUString());
1824 if (!sFilter.getLength())
1825 return;
1827 css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xSMGR;
1829 aReadLock.unlock();
1830 // <- SAFE
1834 // retrieve the module name from the filter configuration
1835 css::uno::Reference< css::container::XNameAccess > xFilterCfg(
1836 xSMGR->createInstance(SERVICENAME_FILTERFACTORY),
1837 css::uno::UNO_QUERY_THROW);
1838 ::comphelper::SequenceAsHashMap lProps (xFilterCfg->getByName(sFilter));
1839 ::rtl::OUString sModule = lProps.getUnpackedValueOrDefault(FILTER_PROPNAME_DOCUMENTSERVICE, ::rtl::OUString());
1841 // get access to the configuration of this office module
1842 css::uno::Reference< css::container::XNameAccess > xModuleCfg(::comphelper::ConfigurationHelper::openConfig(
1843 xSMGR,
1844 PACKAGE_SETUP_MODULES,
1845 ::comphelper::ConfigurationHelper::E_READONLY),
1846 css::uno::UNO_QUERY_THROW);
1848 // read window state from the configuration
1849 // and apply it on the window.
1850 // Do nothing, if no configuration entry exists!
1851 ::rtl::OUString sWindowState ;
1852 ::comphelper::ConfigurationHelper::readRelativeKey(xModuleCfg, sModule, OFFICEFACTORY_PROPNAME_WINDOWATTRIBUTES) >>= sWindowState;
1853 if (sWindowState.getLength())
1855 // SOLAR SAFE ->
1856 ::vos::OClearableGuard aSolarLock2(Application::GetSolarMutex());
1858 // We have to retrieve the window pointer again. Because nobody can guarantee
1859 // that the XWindow was not disposed inbetween .-)
1860 // But if we get a valid pointer we can be sure, that it's the system window pointer
1861 // we already checked and used before. Because nobody recylce the same uno reference for
1862 // a new internal c++ implementation ... hopefully .-))
1863 Window* pWindowCheck = VCLUnoHelper::GetWindow(xWindow);
1864 if (! pWindowCheck)
1865 return;
1867 SystemWindow* pSystemWindow = (SystemWindow*)pWindowCheck;
1868 pSystemWindow->SetWindowState(U2B_ENC(sWindowState,RTL_TEXTENCODING_UTF8));
1870 aSolarLock2.clear();
1871 // <- SOLAR SAFE
1874 catch(const css::uno::RuntimeException& exRun)
1875 { throw exRun; }
1876 catch(const css::uno::Exception&)
1880 } // namespace framework