/**************************************************************
 * 
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 * 
 *   http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 * 
 *************************************************************/



// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_framework.hxx"

//_________________________________________________________________________________________________________________
//	my own includes
//_________________________________________________________________________________________________________________
#include <services/frame.hxx>
#include <dispatch/dispatchprovider.hxx>

#ifndef __FRAMEWORK_DISPATCH_INTERCEPTIONHELPER_HXX_
#include <dispatch/interceptionhelper.hxx>
#endif
#include <dispatch/closedispatcher.hxx>
#include <dispatch/windowcommanddispatch.hxx>
#include <loadenv/loadenv.hxx>
#include <helper/oframes.hxx>
#include <helper/statusindicatorfactory.hxx>
#include <framework/titlehelper.hxx>
#include <classes/droptargetlistener.hxx>
#include <classes/taskcreator.hxx>
#include <loadenv/targethelper.hxx>
#include <framework/framelistanalyzer.hxx>
#include <helper/dockingareadefaultacceptor.hxx>
#include <dispatch/dispatchinformationprovider.hxx>
#include <threadhelp/transactionguard.hxx>
#include <pattern/window.hxx>
#include <services.h>
#include <properties.h>

//_________________________________________________________________________________________________________________
//	interface includes
//_________________________________________________________________________________________________________________
#include <com/sun/star/lang/XInitialization.hpp>
#include <com/sun/star/lang/DisposedException.hpp>
#include <com/sun/star/task/XJobExecutor.hpp>
#include <com/sun/star/util/XURLTransformer.hpp>
#include <com/sun/star/util/XCloseable.hpp>
#include <com/sun/star/awt/XDevice.hpp>
#include <com/sun/star/awt/XTopWindow.hpp>
#include <com/sun/star/frame/XDesktop.hpp>
#include <com/sun/star/awt/PosSize.hpp>
#include <com/sun/star/frame/FrameSearchFlag.hpp>
#include <com/sun/star/awt/XWindowPeer.hpp>
#include <com/sun/star/awt/XVclWindowPeer.hpp>
#include <com/sun/star/task/XStatusIndicatorSupplier.hpp>
#include <com/sun/star/beans/PropertyAttribute.hpp>
#include <com/sun/star/beans/PropertyValue.hpp>
#include <com/sun/star/beans/XPropertySet.hpp>
#include <com/sun/star/frame/XModel.hpp>
#include <com/sun/star/awt/XDataTransferProviderAccess.hpp>
#include <com/sun/star/datatransfer/dnd/XDropTarget.hpp>
#include <com/sun/star/awt/WindowAttribute.hpp>
#include <com/sun/star/container/XIndexAccess.hpp>
#include <com/sun/star/beans/XMaterialHolder.hpp>

#ifndef _COM_SUN_STAR_FRAME_XTITLECHANGEBROADCASTER_HPP_
#include <com/sun/star/frame/XTitleChangeBroadcaster.hpp>
#endif

//_________________________________________________________________________________________________________________
//	includes of other projects
//_________________________________________________________________________________________________________________
#include <comphelper/sequenceashashmap.hxx>
#include <cppuhelper/queryinterface.hxx>
#include <cppuhelper/typeprovider.hxx>
#include <cppuhelper/factory.hxx>
#include <cppuhelper/proptypehlp.hxx>
#include <rtl/ustrbuf.hxx>
#include <vcl/window.hxx>
#include <vcl/wrkwin.hxx>
#include <vcl/svapp.hxx>

#ifndef _TOOLKIT_HELPER_VCLUNOHELPER_HXX_
#include <toolkit/helper/vclunohelper.hxx>
#endif
#include <toolkit/awt/vclxwindow.hxx>
#include <comphelper/processfactory.hxx>
#include <unotools/moduleoptions.hxx>
#include <tools/diagnose_ex.h>

#ifdef ENABLE_ASSERTIONS
	#ifndef _RTL_STRBUF_HXX_
	#include <rtl/strbuf.hxx>
	#endif
#endif

#include <vcl/menu.hxx>

//_________________________________________________________________________________________________________________
//	namespace
//_________________________________________________________________________________________________________________

namespace framework{

//_________________________________________________________________________________________________________________
//	non exported const
//_________________________________________________________________________________________________________________

//_________________________________________________________________________________________________________________
//	non exported definitions
//_________________________________________________________________________________________________________________

css::uno::WeakReference< css::frame::XFrame > Frame::m_xCloserFrame = css::uno::WeakReference< css::frame::XFrame >();

//_________________________________________________________________________________________________________________
//	declarations
//_________________________________________________________________________________________________________________

//*****************************************************************************************************************
//	XInterface, XTypeProvider, XServiceInfo
//*****************************************************************************************************************
DEFINE_XINTERFACE_21                (   Frame                                                                   ,
										OWeakObject																,
										DIRECT_INTERFACE(css::lang::XTypeProvider								),
										DIRECT_INTERFACE(css::lang::XServiceInfo								),
										DIRECT_INTERFACE(css::frame::XFramesSupplier							),
										DIRECT_INTERFACE(css::frame::XFrame										),
										DIRECT_INTERFACE(css::lang::XComponent									),
										DIRECT_INTERFACE(css::task::XStatusIndicatorFactory						),
										DIRECT_INTERFACE(css::frame::XDispatchProvider							),
										DIRECT_INTERFACE(css::frame::XDispatchInformationProvider				),
										DIRECT_INTERFACE(css::frame::XDispatchProviderInterception				),
										DIRECT_INTERFACE(css::beans::XPropertySet								),
										DIRECT_INTERFACE(css::beans::XPropertySetInfo   						),
										DIRECT_INTERFACE(css::awt::XWindowListener								),
										DIRECT_INTERFACE(css::awt::XTopWindowListener							),
										DIRECT_INTERFACE(css::awt::XFocusListener								),
										DERIVED_INTERFACE(css::lang::XEventListener, css::awt::XWindowListener	),
                                        DIRECT_INTERFACE(css::document::XActionLockable                         ),
                                        DIRECT_INTERFACE(css::util::XCloseable                                  ),
                                        DIRECT_INTERFACE(css::util::XCloseBroadcaster                           ),
                                        DIRECT_INTERFACE(css::frame::XComponentLoader                           ),
                                        DIRECT_INTERFACE(css::frame::XTitle                                     ),
                                        DIRECT_INTERFACE(css::frame::XTitleChangeBroadcaster                    )
									)

DEFINE_XTYPEPROVIDER_20             (   Frame                                                                   ,
										css::lang::XTypeProvider												,
										css::lang::XServiceInfo													,
										css::frame::XFramesSupplier												,
										css::frame::XFrame														,
										css::lang::XComponent													,
										css::task::XStatusIndicatorFactory										,
										css::beans::XPropertySet												,
										css::beans::XPropertySetInfo											,
										css::frame::XDispatchProvider											,
										css::frame::XDispatchInformationProvider								,
										css::frame::XDispatchProviderInterception								,
										css::awt::XWindowListener								 				,
										css::awt::XTopWindowListener											,
										css::awt::XFocusListener												,
                                        css::lang::XEventListener                                               ,
                                        css::util::XCloseable                                                   ,
                                        css::util::XCloseBroadcaster                                            ,
                                        css::frame::XComponentLoader                                            ,
                                        css::frame::XTitle                                                      ,
                                        css::frame::XTitleChangeBroadcaster
									)

DEFINE_XSERVICEINFO_MULTISERVICE	(	Frame																	,
                                        ::cppu::OWeakObject                                                     ,
										SERVICENAME_FRAME														,
										IMPLEMENTATIONNAME_FRAME
									)

DEFINE_INIT_SERVICE                 (   Frame,
                                        {
                                            /*Attention
                                                I think we don't need any mutex or lock here ... because we are called by our own static method impl_createInstance()
                                                to create a new instance of this class by our own supported service factory.
                                                see macro DEFINE_XSERVICEINFO_MULTISERVICE and "impl_initService()" for further informations!
                                            */
                                            css::uno::Reference< css::uno::XInterface > xThis(static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY_THROW);

                                            //-------------------------------------------------------------------------------------------------------------
                                            // Initialize a new dispatchhelper-object to handle dispatches.
                                            // We use these helper as slave for our interceptor helper ... not directly!
                                            // But he is event listener on THIS instance!
                                            DispatchProvider* pDispatchHelper = new DispatchProvider( m_xFactory, this );
                                            css::uno::Reference< css::frame::XDispatchProvider > xDispatchProvider( static_cast< ::cppu::OWeakObject* >(pDispatchHelper), css::uno::UNO_QUERY );

                                            //-------------------------------------------------------------------------------------------------------------
                                            DispatchInformationProvider* pInfoHelper = new DispatchInformationProvider(m_xFactory, this);
                                            m_xDispatchInfoHelper = css::uno::Reference< css::frame::XDispatchInformationProvider >( static_cast< ::cppu::OWeakObject* >(pInfoHelper), css::uno::UNO_QUERY );

                                            //-------------------------------------------------------------------------------------------------------------
                                            // Initialize a new interception helper object to handle dispatches and implement an interceptor mechanism.
                                            // Set created dispatch provider as slowest slave of it.
                                            // Hold interception helper by reference only - not by pointer!
                                            // So it's easiear to destroy it.
                                            InterceptionHelper* pInterceptionHelper = new InterceptionHelper( this, xDispatchProvider );
                                            m_xDispatchHelper = css::uno::Reference< css::frame::XDispatchProvider >( static_cast< ::cppu::OWeakObject* >(pInterceptionHelper), css::uno::UNO_QUERY );

                                            //-------------------------------------------------------------------------------------------------------------
                                            // Initialize a new XFrames-helper-object to handle XIndexAccess and XElementAccess.
                                            // We hold member as reference ... not as pointer too!
                                            // Attention: We share our frame container with this helper. Container is threadsafe himself ... So I think we can do that.
                                            // But look on dispose() for right order of deinitialization.
                                            OFrames* pFramesHelper = new OFrames( m_xFactory, this, &m_aChildFrameContainer );
                                            m_xFramesHelper = css::uno::Reference< css::frame::XFrames >( static_cast< ::cppu::OWeakObject* >(pFramesHelper), css::uno::UNO_QUERY );

                                            //-------------------------------------------------------------------------------------------------------------
                                            // Initialize a the drop target listener.
                                            // We hold member as reference ... not as pointer too!
                                            DropTargetListener* pDropListener = new DropTargetListener( m_xFactory, this );
                                            m_xDropTargetListener = css::uno::Reference< css::datatransfer::dnd::XDropTargetListener >( static_cast< ::cppu::OWeakObject* >(pDropListener), css::uno::UNO_QUERY );

                                            // Safe impossible cases
                                            // We can't work without these helpers!
                                            LOG_ASSERT2( xDispatchProvider.is    ()==sal_False, "Frame::impl_initService()", "Slowest slave for dispatch- and interception helper isn't valid. XDispatchProvider, XDispatch, XDispatchProviderInterception are not full supported!" )
                                            LOG_ASSERT2( m_xDispatchHelper.is    ()==sal_False, "Frame::impl_initService()", "Interception helper isn't valid. XDispatchProvider, XDispatch, XDispatchProviderInterception are not full supported!"                                 )
                                            LOG_ASSERT2( m_xFramesHelper.is      ()==sal_False, "Frame::impl_initService()", "Frames helper isn't valid. XFrames, XIndexAccess and XElementAcces are not supported!"                                                                )
                                            LOG_ASSERT2( m_xDropTargetListener.is()==sal_False, "Frame::impl_initService()", "DropTarget helper isn't valid. Drag and drop without functionality!"                                                                                  )

                                            //-------------------------------------------------------------------------------------------------------------
                                            // establish notifies for changing of "disabled commands" configuration during runtime
                                            m_aCommandOptions.EstablisFrameCallback(this);

                                            //-------------------------------------------------------------------------------------------------------------
                                            // Create an initial layout manager
                                            // Create layout manager and connect it to the newly created frame
                                            m_xLayoutManager = css::uno::Reference< css::frame::XLayoutManager >(m_xFactory->createInstance(SERVICENAME_LAYOUTMANAGER), css::uno::UNO_QUERY);

                                            //-------------------------------------------------------------------------------------------------------------
                                            // set information about all supported properties at the base class helper PropertySetHelper
                                            impl_initializePropInfo();
                                        }
                                    )

/*-****************************************************************************************************//**
	@short		standard constructor to create instance by factory
	@descr		This constructor initialize a new instance of this class by valid factory,
				and will be set valid values on his member and baseclasses.

    @attention  a)  Don't use your own reference during an UNO-Service-ctor! There is no guarantee, that you
                    will get over this. (e.g. using of your reference as parameter to initialize some member)
                    Do such things in DEFINE_INIT_SERVICE() method, which is called automaticly after your ctor!!!
                b)  Baseclass OBroadcastHelper is a typedef in namespace cppu!
                    The microsoft compiler has some problems to handle it right BY using namespace explicitly ::cppu::OBroadcastHelper.
                    If we write it without a namespace or expand the typedef to OBrodcastHelperVar<...> -> it will be OK!?
                    I don't know why! (other compiler not tested .. but it works!)

    @seealso    method DEFINE_INIT_SERVICE()

	@param		"xFactory" is the multi service manager, which create this instance.
				The value must be different from NULL!
	@return		-

	@onerror	ASSERT in debug version or nothing in relaese version.
*//*-*****************************************************************************************************/
Frame::Frame( const css::uno::Reference< css::lang::XMultiServiceFactory >& xFactory )
        :   ThreadHelpBase              ( &Application::GetSolarMutex()                     )
        ,   TransactionBase             (                                                   )
        ,   PropertySetHelper           ( xFactory,
                                          &m_aLock,
                                          &m_aTransactionManager,
                                          sal_False) // sal_False => dont release shared mutex on calling us!
        ,   ::cppu::OWeakObject         (                                                   )
		//	init member
        ,   m_xFactory                  ( xFactory                                          )
        ,   m_aListenerContainer        ( m_aLock.getShareableOslMutex()                    )
        ,   m_xParent                   (                                                   )
        ,   m_xContainerWindow          (                                                   )
        ,   m_xComponentWindow          (                                                   )
        ,   m_xController               (                                                   )
        ,   m_eActiveState              ( E_INACTIVE                                        )
        ,   m_sName                     (                                                   )
        ,   m_bIsFrameTop               ( sal_True                                          ) // I think we are top without a parent ... and there is no parent yet!
        ,   m_bConnected                ( sal_False                                         ) // There exist no component inside of use => sal_False, we are not connected!
        ,   m_nExternalLockCount        ( 0                                                 )
        ,   m_bSelfClose                ( sal_False                                         ) // Important!
        ,   m_bIsHidden                 ( sal_True                                          )
        ,   m_xTitleHelper              (                                                   )
	     ,   mp_WindowCommandDispatch    ( NULL                                              )
        ,   m_aChildFrameContainer      (                                                   )
{
    // Check incoming parameter to avoid against wrong initialization.
    LOG_ASSERT2( implcp_ctor( xFactory ), "Frame::Frame()", "Invalid parameter detected!" )

    /* Please have a look on "@attentions" of description before! */
}

/*-****************************************************************************************************//**
	@short		standard destructor
	@descr		This one do NOTHING! Use dispose() instaed of this.

	@seealso	method dispose()

	@param		-
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
Frame::~Frame()
{
    LOG_ASSERT2( m_aTransactionManager.getWorkingMode()!=E_CLOSE, "Frame::~Frame()", "Who forgot to dispose this service?" )
	 if (mp_WindowCommandDispatch != NULL)
	 {
		  delete ((WindowCommandDispatch *)mp_WindowCommandDispatch);  // memory leak #i120079#
	 }
}

/*-************************************************************************************************************//**
    @interface  XComponentLoader
    @short      try to load given URL into a task
    @descr      You can give us some informations about the content, which you will load into a frame.
                We search or create this target for you, make a type detection of given URL and try to load it.
                As result of this operation we return the new created component or nothing, if loading failed.

    @seealso    -

    @param      "sURL"              , URL, which represant the content
    @param      "sTargetFrameName"  , name of target frame or special value like "_self", "_blank" ...
    @param      "nSearchFlags"      , optional arguments for frame search, if target isn't a special one
    @param      "lArguments"        , optional arguments for loading
    @return     A valid component reference, if loading was successfully.
                A null reference otherwise.

    @onerror    We return a null reference.
    @threadsafe yes
*//*-*************************************************************************************************************/
css::uno::Reference< css::lang::XComponent > SAL_CALL Frame::loadComponentFromURL( const ::rtl::OUString&                                 sURL            ,
                                                                                   const ::rtl::OUString&                                 sTargetFrameName,
                                                                                         sal_Int32                                        nSearchFlags    ,
                                                                                   const css::uno::Sequence< css::beans::PropertyValue >& lArguments      ) throw( css::io::IOException                ,
                                                                                                                                                                   css::lang::IllegalArgumentException ,
                                                                                                                                                                   css::uno::RuntimeException          )
{
    {
        // If the frame is closed the call might lead to crash even with target "_blank",
        // so the DisposedException should be thrown in this case
        // It still looks to be too dangerous to set the transaction for the whole loading process
        // so the guard is used in scopes to let the standard check be used

        TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );
    }

    ReadGuard aReadLock(m_aLock);
    css::uno::Reference< css::frame::XComponentLoader > xThis(static_cast< css::frame::XComponentLoader* >(this), css::uno::UNO_QUERY);
    css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR = m_xFactory;
    aReadLock.unlock();

    return LoadEnv::loadComponentFromURL(xThis, xSMGR, sURL, sTargetFrameName, nSearchFlags, lArguments);
}

/*-****************************************************************************************************//**
	@short		return access to append or remove childs on desktop
	@descr		We don't implement these interface directly. We use a helper class to do this.
				If you wish to add or delete childs to/from the container, call these method to get
				a reference to the helper.

	@seealso	class OFrames

	@param		-
	@return		A reference to the helper which answer your queries.

	@onerror	A null reference is returned.
*//*-*****************************************************************************************************/
css::uno::Reference< css::frame::XFrames > SAL_CALL Frame::getFrames() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.

/*TODO
    This is a temp. HACK!
    Our parent (a Task!) stand in close/dispose and set working mode to E_BEFOERECLOSE
    and call dispose on us! We tra to get this xFramesHelper and are reject by an "already closed" pranet instance ....
    => We use SOFTEXCEPTIONS here ... but we should make it right in further times ....
 */

    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    // Return access to all child frames to caller.
    // Ouer childframe container is implemented in helper class OFrames and used as a reference m_xFramesHelper!
    return m_xFramesHelper;
}

/*-****************************************************************************************************//**
	@short		get the current active child frame
	@descr		It must be a frameto. Direct childs of a frame are frames only! No task or desktop is accepted.
				We don't save this information directly in this class. We use ouer container-helper
				to do that.

	@seealso	class OFrameContainer
	@seealso	method setActiveFrame()

	@param		-
	@return		A reference to ouer current active childframe, if anyone exist.
	@return		A null reference, if nobody is active.

	@onerror	A null reference is returned.
*//*-*****************************************************************************************************/
css::uno::Reference< css::frame::XFrame > SAL_CALL Frame::getActiveFrame() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

    /* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

	// Return current active frame.
	// This information is avaliable on the container.
	return m_aChildFrameContainer.getActive();
}

/*-****************************************************************************************************//**
	@short		set the new active direct child frame
	@descr		It must be a frame to. Direct childs of frame are frames only! No task or desktop is accepted.
				We don't save this information directly in this class. We use ouer container-helper
				to do that.

	@seealso	class OFrameContainer
	@seealso	method getActiveFrame()

	@param		"xFrame", reference to new active child. It must be an already existing child!
	@return		-

	@onerror    An assertion is thrown and element is ignored, if given frame is'nt already a child of us.
*//*-*****************************************************************************************************/
void SAL_CALL Frame::setActiveFrame( const css::uno::Reference< css::frame::XFrame >& xFrame ) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Check incoming parameters.
    LOG_ASSERT2( implcp_setActiveFrame( xFrame ), "Frame::setActiveFrame()", "Invalid parameter detected!" )
    // Look for rejected calls!
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    WriteGuard aWriteLock( m_aLock );

    // Copy neccessary member for threadsafe access!
    // m_aChildFrameContainer is threadsafe himself and he live if we live!!!
    // ...and our transaction is non breakable too ...
    css::uno::Reference< css::frame::XFrame > xActiveChild = m_aChildFrameContainer.getActive();
    EActiveState                              eActiveState = m_eActiveState             ;

    aWriteLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    // Don't work, if "new" active frame is'nt different from current one!
    // (xFrame==NULL is allowed to UNSET it!)
    if( xActiveChild != xFrame )
    {
        // ... otherwise set new and deactivate old one.
        m_aChildFrameContainer.setActive( xFrame );
        if  (
                ( eActiveState      !=  E_INACTIVE  )   &&
                ( xActiveChild.is() ==  sal_True    )
            )
        {
            xActiveChild->deactivate();
        }
    }

    if( xFrame.is() == sal_True )
    {
        // If last active frame had focus ...
        // ... reset state to ACTIVE and send right FrameActionEvent for focus lost.
        if( eActiveState == E_FOCUS )
        {
            aWriteLock.lock();
            eActiveState   = E_ACTIVE    ;
            m_eActiveState = eActiveState;
            aWriteLock.unlock();
            implts_sendFrameActionEvent( css::frame::FrameAction_FRAME_UI_DEACTIVATING );
        }

        // If last active frame was active ...
        // but new one isn't it ...
        // ... set it as active one.
        if  (
                ( eActiveState          ==  E_ACTIVE    )   &&
                ( xFrame->isActive()    ==  sal_False   )
            )
        {
            xFrame->activate();
        }
    }
    else
    // If this frame is active and has no active subframe anymore it is UI active too
    if( eActiveState == E_ACTIVE )
    {
        aWriteLock.lock();
        eActiveState   = E_FOCUS     ;
        m_eActiveState = eActiveState;
        aWriteLock.unlock();
        implts_sendFrameActionEvent( css::frame::FrameAction_FRAME_UI_ACTIVATED );
    }
}

/*-****************************************************************************************************//**
   initialize new created layout manager
**/
void lcl_enableLayoutManager(const css::uno::Reference< css::frame::XLayoutManager >& xLayoutManager,
                             const css::uno::Reference< css::frame::XFrame >&         xFrame        )
{
    // Provide container window to our layout manager implementation
    xLayoutManager->attachFrame(xFrame);

    css::uno::Reference< css::frame::XFrameActionListener > xListen(xLayoutManager, css::uno::UNO_QUERY_THROW);
    xFrame->addFrameActionListener(xListen);

    DockingAreaDefaultAcceptor* pAcceptor = new DockingAreaDefaultAcceptor(xFrame);
    css::uno::Reference< css::ui::XDockingAreaAcceptor > xDockingAreaAcceptor( static_cast< ::cppu::OWeakObject* >(pAcceptor), css::uno::UNO_QUERY_THROW);
    xLayoutManager->setDockingAreaAcceptor(xDockingAreaAcceptor);
}

/*-****************************************************************************************************//**
   deinitialize layout manager
**/
void lcl_disableLayoutManager(const css::uno::Reference< css::frame::XLayoutManager >& xLayoutManager,
                              const css::uno::Reference< css::frame::XFrame >&         xFrame        )
{
    css::uno::Reference< css::frame::XFrameActionListener > xListen(xLayoutManager, css::uno::UNO_QUERY_THROW);
    xFrame->removeFrameActionListener(xListen);
    xLayoutManager->setDockingAreaAcceptor(css::uno::Reference< css::ui::XDockingAreaAcceptor >());
    xLayoutManager->attachFrame(css::uno::Reference< css::frame::XFrame >());
}

/*-****************************************************************************************************//**
	@short		initialize frame instance
	@descr		A frame needs a window. This method set a new one ... but should called one times only!
				We use this window to listen for window events and forward it to our set component.
				Its used as parent of component window too.

	@seealso	method getContainerWindow()
	@seealso	method setComponent()
	@seealso	member m_xContainerWindow

	@param		"xWindow", reference to new container window - must be valid!
	@return		-

	@onerror	We do nothing.
*//*-*****************************************************************************************************/
void SAL_CALL Frame::initialize( const css::uno::Reference< css::awt::XWindow >& xWindow ) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    if (!xWindow.is())
        throw css::uno::RuntimeException(
                    ::rtl::OUString::createFromAscii("Frame::initialize() called without a valid container window reference."),
                    static_cast< css::frame::XFrame* >(this));

    /* SAFE AREA ----------------------------------------------------------------------------------------------- */
    WriteGuard aWriteLock( m_aLock );

    if ( m_xContainerWindow.is() )
        throw css::uno::RuntimeException(
                ::rtl::OUString::createFromAscii("Frame::initialized() is called more then once, which isnt usefull nor allowed."),
                static_cast< css::frame::XFrame* >(this));

    // Look for rejected calls first!
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

    // Enable object for real working ... so follow impl methods don't must handle it special! (e.g. E_SOFTEXCEPTIONS for rejected calls)
    m_aTransactionManager.setWorkingMode( E_WORK );

    // This must be the first call of this method!
    // We should initialize our object and open it for working.
    // Set the new window.
    LOG_ASSERT2( m_xContainerWindow.is()==sal_True, "Frame::initialize()", "Leak detected! This state should never occure ..." )
    m_xContainerWindow = xWindow;

    // if window is initially visible, we will never get a windowShowing event
    Window* pWindow = VCLUnoHelper::GetWindow(xWindow);
    if (pWindow && pWindow->IsVisible())
        m_bIsHidden = sal_False;

    css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR          = m_xFactory;
    css::uno::Reference< css::frame::XLayoutManager >     xLayoutManager = m_xLayoutManager;

    // Release lock ... because we call some impl methods, which are threadsafe by himself.
    // If we hold this lock - we will produce our own deadlock!
    aWriteLock.unlock();
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    if (xLayoutManager.is())
        lcl_enableLayoutManager(xLayoutManager, this);

    // create progress helper
    css::uno::Reference< css::frame::XFrame >                 xThis            (static_cast< css::frame::XFrame* >(this)                        , css::uno::UNO_QUERY_THROW);
    css::uno::Reference< css::task::XStatusIndicatorFactory > xIndicatorFactory(xSMGR->createInstance(IMPLEMENTATIONNAME_STATUSINDICATORFACTORY), css::uno::UNO_QUERY_THROW);
    css::uno::Reference< css::lang::XInitialization >         xIndicatorInit   (xIndicatorFactory                                               , css::uno::UNO_QUERY_THROW);
    css::uno::Sequence< css::uno::Any > lArgs(2);
    css::beans::NamedValue aArg;
    aArg.Name    = STATUSINDICATORFACTORY_PROPNAME_FRAME;
    aArg.Value <<= xThis;
    lArgs[0]   <<= aArg;
    aArg.Name    = STATUSINDICATORFACTORY_PROPNAME_ALLOWPARENTSHOW;
    aArg.Value <<= sal_True;
    lArgs[1]   <<= aArg;
    xIndicatorInit->initialize(lArgs);

    // SAFE -> ----------------------------------
    aWriteLock.lock();
    m_xIndicatorFactoryHelper = xIndicatorFactory;
    aWriteLock.unlock();
    // <- SAFE ----------------------------------

    // Start listening for events after setting it on helper class ...
    // So superflous messages are filtered to NULL :-)
    implts_startWindowListening();

    impl_enablePropertySet();

    // create WindowCommandDispatch; it is supposed to release itself at frame destruction
    mp_WindowCommandDispatch = new WindowCommandDispatch(xSMGR, this);  // memory leak #i120079#

    // Initialize title functionality
    TitleHelper* pTitleHelper = new TitleHelper(xSMGR);
    m_xTitleHelper = css::uno::Reference< css::frame::XTitle >(static_cast< ::cppu::OWeakObject* >(pTitleHelper), css::uno::UNO_QUERY_THROW);
    pTitleHelper->setOwner(xThis);
}

/*-****************************************************************************************************//**
	@short		returns current set container window
	@descr		The ContainerWindow property is used as a container for the component
				in this frame. So this object implements a container interface too.
				The instantiation of the container window is done by the user of this class.
				The frame is the owner of its container window.

	@seealso	method initialize()

	@param		-
	@return		A reference to current set containerwindow.

	@onerror	A null reference is returned.
*//*-*****************************************************************************************************/
css::uno::Reference< css::awt::XWindow > SAL_CALL Frame::getContainerWindow() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    return m_xContainerWindow;
}

/*-****************************************************************************************************//**
	@short		set parent frame
	@descr		We need a parent to support some functionality! e.g. findFrame()
                By the way we use the chance to set an internal information about our top state.
                So we must not check this information during every isTop() call.
                We are top, if our parent is the desktop instance or we havent any parent.

    @seealso    getCreator()
    @seealso    findFrame()
    @seealso    isTop()
    @seealos    m_bIsFrameTop

    @param      xCreator
                    valid reference to our new owner frame, which should implement a supplier interface

    @threadsafe yes
    @modified   08.05.2002 09:35, as96863
*//*-*****************************************************************************************************/
void SAL_CALL Frame::setCreator( const css::uno::Reference< css::frame::XFramesSupplier >& xCreator ) throw( css::uno::RuntimeException )
{
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

    /* SAFE { */
        WriteGuard aWriteLock( m_aLock );
            m_xParent = xCreator;
        aWriteLock.unlock();
    /* } SAFE */

    css::uno::Reference< css::frame::XDesktop > xIsDesktop( xCreator, css::uno::UNO_QUERY );
    m_bIsFrameTop = ( xIsDesktop.is() || ! xCreator.is() );
}

/*-****************************************************************************************************//**
	@short		returns current parent frame
	@descr		The Creator is the parent frame container. If it is NULL, the frame is the uppermost one.

	@seealso	method setCreator()

	@param		-
	@return		A reference to current set parent frame container.

	@onerror	A null reference is returned.
*//*-*****************************************************************************************************/
css::uno::Reference< css::frame::XFramesSupplier > SAL_CALL Frame::getCreator() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    return m_xParent;
}

/*-****************************************************************************************************//**
	@short		returns current set name of frame
	@descr		This name is used to find target of findFrame() or queryDispatch() calls.

	@seealso	method setName()

	@param		-
	@return		Current set name of frame.

	@onerror	An empty string is returned.
*//*-*****************************************************************************************************/
::rtl::OUString SAL_CALL Frame::getName() throw( css::uno::RuntimeException )
{
	/* SAFE { */
    ReadGuard aReadLock( m_aLock );
    return m_sName;
	/* } SAFE */
}

/*-****************************************************************************************************//**
	@short		set new name for frame
	@descr		This name is used to find target of findFrame() or queryDispatch() calls.

	@attention	Special names like "_blank", "_self" aren't allowed ...
				"_beamer" or "_menubar" excepts this rule!

	@seealso	method getName()

	@param		"sName", new frame name.
	@return		-

	@onerror	We do nothing.
*//*-*****************************************************************************************************/
void SAL_CALL Frame::setName( const ::rtl::OUString& sName ) throw( css::uno::RuntimeException )
{
	/* SAFE { */
    WriteGuard aWriteLock( m_aLock );
    // Set new name ... but look for invalid special target names!
    // They are not allowed to set.
    if (TargetHelper::isValidNameForFrame(sName))
        m_sName = sName;
	aWriteLock.unlock();
	/* } SAFE */
}

/*-****************************************************************************************************//**
	@short		search for frames
	@descr		This method searches for a frame with the specified name.
				Frames may contain other frames (e.g. a frameset) and may
				be contained in other frames. This hierarchie ist searched by
				this method.
				First some special names are taken into account, i.e. "",
                "_self", "_top", "_blank" etc. The nSearchFlags are ignored
				when comparing these names with sTargetFrameName, further steps are
				controlled by the search flags. If allowed, the name of the frame
				itself is compared with the desired one, then ( again if allowed )
                the method findFrame() is called for all children, for siblings
                and as last for the parent frame.
				If no frame with the given name is found until the top frames container,
				a new top one is created, if this is allowed by a special
				flag. The new frame also gets the desired name.

    @param      sTargetFrameName
                    special names (_blank, _self) or real name of target frame
    @param      nSearchFlags
                    optional flags which regulate search for non special target frames

    @return     A reference to found or may be new created frame.
    @threadsafe yes
    @modified   16.05.2002 11:08, as96863
*//*-*****************************************************************************************************/
css::uno::Reference< css::frame::XFrame > SAL_CALL Frame::findFrame( const ::rtl::OUString&  sTargetFrameName,
                                                                           sal_Int32         nSearchFlags    ) throw( css::uno::RuntimeException )
{
    css::uno::Reference< css::frame::XFrame > xTarget;

    //-----------------------------------------------------------------------------------------------------
    // 0) Ignore wrong parameter!
    //    We doesn't support search for following special targets.
    //    If we reject this requests - we mustnt check for such names
    //    in following code again and again. If we do not so -wrong
    //    search results can occure!
    //-----------------------------------------------------------------------------------------------------
    if (
        (sTargetFrameName==SPECIALTARGET_DEFAULT  )   ||    // valid for dispatches - not for findFrame()!
        (sTargetFrameName==SPECIALTARGET_MENUBAR  )   ||    // valid for dispatches - not for findFrame()!
        (sTargetFrameName==SPECIALTARGET_HELPAGENT)         // valid for dispatches - not for findFrame()!
       )
    {
        return NULL;
    }

    //-----------------------------------------------------------------------------------------------------
    // I) check for special defined targets first which must be handled exclusive.
    //    force using of "if() else if() ..."
    //-----------------------------------------------------------------------------------------------------

    // get threadsafe some neccessary member which are neccessary for following functionality
    /* SAFE { */
    ReadGuard aReadLock( m_aLock );
    css::uno::Reference< css::frame::XFrame >              xParent      ( m_xParent, css::uno::UNO_QUERY );
    css::uno::Reference< css::lang::XMultiServiceFactory > xFactory     = m_xFactory;
    sal_Bool                                               bIsTopFrame  = m_bIsFrameTop;
    sal_Bool                                               bIsTopWindow = WindowHelper::isTopWindow(m_xContainerWindow);
    aReadLock.unlock();
    /* } SAFE */

    //-----------------------------------------------------------------------------------------------------
    // I.I) "_blank"
    //  Not allowed for a normal frame - but for the desktop.
    //  Use helper class to do so. It use the desktop automaticly.
    //-----------------------------------------------------------------------------------------------------
    if ( sTargetFrameName==SPECIALTARGET_BLANK )
    {
        TaskCreator aCreator(xFactory);
        xTarget = aCreator.createTask(sTargetFrameName,sal_False);
    }

    //-----------------------------------------------------------------------------------------------------
    // I.II) "_parent"
    //  It doesn't matter if we have a valid parent or not. User ask for him and get it.
    //  An empty result is a valid result too.
    //-----------------------------------------------------------------------------------------------------
    else
    if ( sTargetFrameName==SPECIALTARGET_PARENT )
    {
        xTarget = xParent;
    }

    //-----------------------------------------------------------------------------------------------------
    // I.III) "_top"
    //  If we are not the top frame in this hierarchy, we must forward request to our parent.
    //  Otherwhise we must return ourself.
    //-----------------------------------------------------------------------------------------------------
    else
    if ( sTargetFrameName==SPECIALTARGET_TOP )
    {
        if (bIsTopFrame)
            xTarget = this;
        else
        if (xParent.is()) // If we are not top - the parent MUST exist. But may it's better to check it again .-)
            xTarget = xParent->findFrame(SPECIALTARGET_TOP,0);
    }

    //-----------------------------------------------------------------------------------------------------
    // I.IV) "_self", ""
    //  This mean this frame in every case.
    //-----------------------------------------------------------------------------------------------------
    else
    if (
        ( sTargetFrameName==SPECIALTARGET_SELF ) ||
        ( sTargetFrameName.getLength()<1       )
       )
    {
        xTarget = this;
    }

    //-----------------------------------------------------------------------------------------------------
    // I.V) "_beamer"
    //  This is a special sub frame of any task. We must return it if we found it on our direct childrens
    //  or create it there if it not already exists.
    //  Note: Such beamer exists for task(top) frames only!
    //-----------------------------------------------------------------------------------------------------
    else
    if ( sTargetFrameName==SPECIALTARGET_BEAMER )
    {
        // We are a task => search or create the beamer
        if (bIsTopWindow)
        {
            xTarget = m_aChildFrameContainer.searchOnDirectChildrens(SPECIALTARGET_BEAMER);
            if ( ! xTarget.is() )
            {
                /* TODO
                    Creation not supported yet!
                    Wait for new layout manager service because we can't plug it
                    inside already opened document of this frame ...
                */
            }
        }
        // We arent a task => forward request to our parent or ignore it.
        else
        if (xParent.is())
            xTarget = xParent->findFrame(SPECIALTARGET_BEAMER,0);
    }

    else
    {
        //-------------------------------------------------------------------------------------------------
        // II) otherwhise use optional given search flags
        //  force using of combinations of such flags. means no "else" part of use if() statements.
        //  But we ust break further searches if target was already found.
        //  Order of using flags is fix: SELF - CHILDREN - SIBLINGS - PARENT
        //  TASK and CREATE are handled special.
        //-------------------------------------------------------------------------------------------------

        // get threadsafe some neccessary member which are neccessary for following functionality
        /* SAFE { */
        aReadLock.lock();
        ::rtl::OUString sOwnName = m_sName;
        aReadLock.unlock();
        /* } SAFE */

        //-------------------------------------------------------------------------------------------------
        // II.I) SELF
        //  Check for right name. If it's the searched one return ourself - otherwhise
        //  ignore this flag.
        //-------------------------------------------------------------------------------------------------
        if (
            (nSearchFlags &  css::frame::FrameSearchFlag::SELF)  &&
            (sOwnName     == sTargetFrameName                 )
           )
        {
            xTarget = this;
        }

        //-------------------------------------------------------------------------------------------------
        // II.II) CHILDREN
        //  Search on all children for the given target name.
        //  An empty name value can't occure here - because it must be already handled as "_self"
        //  before. Used helper function of container doesn't create any frame.
        //  It makes a deep search only.
        //-------------------------------------------------------------------------------------------------
        if (
            ( ! xTarget.is()                                     ) &&
            (nSearchFlags & css::frame::FrameSearchFlag::CHILDREN)
           )
        {
            xTarget = m_aChildFrameContainer.searchOnAllChildrens(sTargetFrameName);
        }

        //-------------------------------------------------------------------------------------------------
        // II.III) TASKS
        //  This is a special flag. It regulate search on this task tree only or allow search on
        //  all other ones (which are sibling trees of us) too.
        //  Upper search must stop at this frame if we are the topest one and the TASK flag isn't set
        //  or we can ignore it if we have no valid parent.
        //-------------------------------------------------------------------------------------------------
        if (
            (   bIsTopFrame && (nSearchFlags & css::frame::FrameSearchFlag::TASKS) )   ||
            ( ! bIsTopFrame                                                        )
           )
        {
            //-------------------------------------------------------------------------------------------------
            // II.III.I) SIBLINGS
            //  Search on all our direct siblings - means all childrens of our parent.
            //  Use this flag in combination with TASK. We must supress such upper search if
            //  user has not set it and if we are a top frame.
            //
            //  Attention: Don't forward this request to our parent as a findFrame() call.
            //  In such case we must protect us against recursive calls.
            //  Use snapshot of our parent. But don't use queryFrames() of XFrames interface.
            //  Because it's return all siblings and all her childrens including our children too
            //  if we call it with the CHILDREN flag. We doesn't need that - we need the direct container
            //  items of our parent only to start searches there. So we must use the container interface
            //  XIndexAccess instead of XFrames.
            //-------------------------------------------------------------------------------------------------
            if (
                ( ! xTarget.is()                                      ) &&
                (nSearchFlags &  css::frame::FrameSearchFlag::SIBLINGS) &&
                (   xParent.is()                                      ) // search on siblings is impossible without a parent
               )
            {
                css::uno::Reference< css::frame::XFramesSupplier > xSupplier( xParent, css::uno::UNO_QUERY );
                if (xSupplier.is())
                {
                    css::uno::Reference< css::container::XIndexAccess > xContainer( xSupplier->getFrames(), css::uno::UNO_QUERY );
                    if (xContainer.is())
                    {
                        sal_Int32 nCount = xContainer->getCount();
                        for( sal_Int32 i=0; i<nCount; ++i )
                        {
                            css::uno::Reference< css::frame::XFrame > xSibling;
                            if (
                                ( !(xContainer->getByIndex(i)>>=xSibling)                                 ) ||  // control unpacking
                                ( ! xSibling.is()                                     ) ||  // check for valid items
                                ( xSibling==static_cast< ::cppu::OWeakObject* >(this) )     // ignore ourself! (We are a part of this container too - but search on our children was already done.)
                            )
                            {
                                continue;
                            }

                            // Don't allow upper search here! Use rigth flags to regulate it.
							// And allow deep search on children only - if it was allowed for us too.
							sal_Int32 nRightFlags = css::frame::FrameSearchFlag::SELF;
							if (nSearchFlags & css::frame::FrameSearchFlag::CHILDREN)
								nRightFlags |= css::frame::FrameSearchFlag::CHILDREN;
                            xTarget = xSibling->findFrame(sTargetFrameName, nRightFlags );
                            // perform search be breaking further search if a result exist.
                            if (xTarget.is())
                                break;
                        }
                    }
                }
            }

            //-------------------------------------------------------------------------------------------------
            // II.III.II) PARENT
            //  Forward search to our parent (if he exists.)
            //  To prevent us against recursive and superflous calls (which can occure if we allow him
            //  to search on his childrens too) we must change used search flags.
            //-------------------------------------------------------------------------------------------------
            if (
                ( ! xTarget.is()                                    ) &&
                (nSearchFlags &  css::frame::FrameSearchFlag::PARENT) &&
                (   xParent.is()                                    )
               )
            {
				if (xParent->getName() == sTargetFrameName)
					xTarget = xParent;
				else
				{
					sal_Int32 nRightFlags  = nSearchFlags;
							  nRightFlags &= ~css::frame::FrameSearchFlag::CHILDREN;
					xTarget = xParent->findFrame(sTargetFrameName, nRightFlags);
				}
            }
        }

        //-------------------------------------------------------------------------------------------------
        // II.IV) CREATE
        //  If we haven't found any valid target frame by using normal flags - but user allowed us to create
        //  a new one ... we should do that. Used TaskCreator use Desktop instance automaticly as parent!
        //-------------------------------------------------------------------------------------------------
        if (
            ( ! xTarget.is()                                   )    &&
            (nSearchFlags & css::frame::FrameSearchFlag::CREATE)
           )
        {
            TaskCreator aCreator(xFactory);
            xTarget = aCreator.createTask(sTargetFrameName,sal_False);
        }
    }

    return xTarget;
}

/*-****************************************************************************************************//**
	@short		-
	@descr		Returns sal_True, if this frame is a "top frame", otherwise sal_False.
				The "m_bIsFrameTop" member must be set in the ctor or setCreator() method.
    			A top frame is a member of the top frame container or a member of the
    			task frame container. Both containers can create new frames if the findFrame()
                method of their css::frame::XFrame interface is called with a frame name not yet known.

	@seealso	ctor
	@seealso	method setCreator()
	@seealso	method findFrame()

	@param		-
	@return		true, if is it a top frame ... false otherwise.

	@onerror	No error should occure!
*//*-*****************************************************************************************************/
sal_Bool SAL_CALL Frame::isTop() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    // This information is set in setCreator().
    // We are top, if ouer parent is a task or the desktop or if no parent exist!
    return m_bIsFrameTop;
}

/*-****************************************************************************************************//**
	@short		activate frame in hierarchy
	@descr		This feature is used to mark active pathes in our frame hierarchy.
				You can be a listener for this event to react for it ... change some internal states or something else.

	@seealso	method deactivate()
	@seealso	method isActivate()
	@seealso	enum EActiveState
	@seealso	listener mechanism

	@param		-
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void SAL_CALL Frame::activate() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    WriteGuard aWriteLock( m_aLock );

    // Copy neccessary member and free the lock.
    // It's not neccessary for m_aChildFrameContainer ... because
    // he is threadsafe himself and live if we live.
    // We use a registered transaction to prevent us against
    // breaks during this operation!
    css::uno::Reference< css::frame::XFrame >           xActiveChild    = m_aChildFrameContainer.getActive()                                ;
    css::uno::Reference< css::frame::XFramesSupplier >  xParent         ( m_xParent, css::uno::UNO_QUERY )                                ;
    css::uno::Reference< css::frame::XFrame >           xThis           ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    css::uno::Reference< css::awt::XWindow >            xComponentWindow( m_xComponentWindow, css::uno::UNO_QUERY )                       ;
    EActiveState                                        eState          = m_eActiveState                                                  ;

    aWriteLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    //_________________________________________________________________________________________________________
    //  1)  If I'am not active before ...
    if( eState == E_INACTIVE )
    {
        // ... do it then.
        aWriteLock.lock();
        eState         = E_ACTIVE;
        m_eActiveState = eState;
        aWriteLock.unlock();
        // Deactivate sibling path and forward activation to parent ... if any parent exist!
        if( xParent.is() == sal_True )
        {
            // Everytime set THIS frame as active child of parent and activate it.
            // We MUST have a valid path from bottom to top as active path!
            // But we must deactivate the old active sibling path first.

            // Attention: Deactivation of an active path, deactivate the whole path ... from bottom to top!
            // But we wish to deactivate founded sibling-tree only.
            // [ see deactivate() / step 4) for further informations! ]

            xParent->setActiveFrame( xThis );

            // Then we can activate from here to top.
            // Attention: We are ACTIVE now. And the parent will call activate() at us!
            // But we do nothing then! We are already activated.
            xParent->activate();
        }
        // Its neccessary to send event NOW - not before.
        // Activation goes from bottom to top!
        // Thats the reason to activate parent first and send event now.
        implts_sendFrameActionEvent( css::frame::FrameAction_FRAME_ACTIVATED );
    }

    //_________________________________________________________________________________________________________
    //  2)  I was active before or current activated and there is a path from here to bottom, who CAN be active.
    //      But ouer direct child of path is not active yet.
    //      (It can be, if activation occur in the middle of a current path!)
    //      In these case we activate path to bottom to set focus on right frame!
    if  (
            ( eState                    ==  E_ACTIVE    )   &&
            ( xActiveChild.is()         ==  sal_True    )   &&
            ( xActiveChild->isActive()  ==  sal_False   )
        )
    {
        xActiveChild->activate();
    }

    //_________________________________________________________________________________________________________
    //  3)  I was active before or current activated. But if I have no active child => I will get the focus!
    if  (
            ( eState            ==  E_ACTIVE    )   &&
            ( xActiveChild.is() ==  sal_False   )
        )
    {
        aWriteLock.lock();
        eState         = E_FOCUS;
        m_eActiveState = eState;
        aWriteLock.unlock();
        implts_sendFrameActionEvent( css::frame::FrameAction_FRAME_UI_ACTIVATED );
    }
}

/*-****************************************************************************************************//**
	@short		deactivate frame in hierarchy
	@descr		This feature is used to deactive pathes in our frame hierarchy.
				You can be a listener for this event to react for it ... change some internal states or something else.

	@seealso	method activate()
	@seealso	method isActivate()
	@seealso	enum EActiveState
	@seealso	listener mechanism

	@param		-
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void SAL_CALL Frame::deactivate() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    WriteGuard aWriteLock( m_aLock );

    // Copy neccessary member and free the lock.
    css::uno::Reference< css::frame::XFrame >           xActiveChild    = m_aChildFrameContainer.getActive()                                     ;
    css::uno::Reference< css::frame::XFramesSupplier >  xParent         ( m_xParent, css::uno::UNO_QUERY )                                ;
    css::uno::Reference< css::frame::XFrame >           xThis           ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    EActiveState                                        eState          = m_eActiveState                                                  ;

    aWriteLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    // Work only, if there something to do!
    if( eState != E_INACTIVE )
    {
        //_____________________________________________________________________________________________________
        //  1)  Deactivate all active childs.
        if  (
                ( xActiveChild.is()         ==  sal_True    )   &&
                ( xActiveChild->isActive()  ==  sal_True    )
            )
        {
            xActiveChild->deactivate();
        }

        //_____________________________________________________________________________________________________
        //  2)  If I have the focus - I will lost it now.
        if( eState == E_FOCUS )
        {
            // Set new state INACTIVE(!) and send message to all listener.
            // Don't set ACTIVE as new state. This frame is deactivated for next time - due to activate().
            aWriteLock.lock();
            eState          = E_ACTIVE;
            m_eActiveState  = eState  ;
            aWriteLock.unlock();
            implts_sendFrameActionEvent( css::frame::FrameAction_FRAME_UI_DEACTIVATING );
        }

        //_____________________________________________________________________________________________________
        //  3)  If I'am active - I will be deactivated now.
        if( eState == E_ACTIVE )
        {
            // Set new state and send message to all listener.
            aWriteLock.lock();
            eState          = E_INACTIVE;
            m_eActiveState  = eState    ;
            aWriteLock.unlock();
            implts_sendFrameActionEvent( css::frame::FrameAction_FRAME_DEACTIVATING );
        }

        //_____________________________________________________________________________________________________
        //  4)  If there is a path from here to my parent ...
        //      ... I'am on the top or in the middle of deactivated subtree and action was started here.
        //      I must deactivate all frames from here to top, which are members of current path.
        //      Stop, if THESE frame not the active frame of ouer parent!
        if  (
                ( xParent.is()              ==  sal_True    )   &&
                ( xParent->getActiveFrame() ==  xThis       )
            )
        {
            // We MUST break the path - otherwise we will get the focus - not ouer parent! ...
            // Attention: Ouer parent don't call us again - WE ARE NOT ACTIVE YET!
            // [ see step 3 and condition "if ( m_eActiveState!=INACTIVE ) ..." in this method! ]
            xParent->deactivate();
        }
    }
}

/*-****************************************************************************************************//**
	@short		returns active state
	@descr		Call it to get informations about current active state of this frame.

	@seealso	method activate()
	@seealso	method deactivate()
	@seealso	enum EActiveState

	@param		-
	@return		true if active, false otherwise.

	@onerror	No error should occure.
*//*-*****************************************************************************************************/
sal_Bool SAL_CALL Frame::isActive() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    return  (
                ( m_eActiveState    ==  E_ACTIVE    )   ||
                ( m_eActiveState    ==  E_FOCUS     )
            );
}

/*-****************************************************************************************************//**
	@short		???
	@descr		-

	@seealso	-

	@param		-
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void SAL_CALL Frame::contextChanged() throw( css::uno::RuntimeException )
{
    // Look for rejected calls!
    // Sometimes called during closing object... => soft exceptions
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );
    // Impl-method is threadsafe himself!
	// Send event to all listener for frame actions.
    implts_sendFrameActionEvent( css::frame::FrameAction_CONTEXT_CHANGED );
}

/*-****************************************************************************************************//**
	@short		set new component inside the frame
	@descr		A frame is a container for a component. Use this method to set, change or realease it!
				We accept null references! The xComponentWindow will be a child of our container window
				and get all window events from us.

    @attention  (a) A current set component can disagree with the suspend() request!
                    We don't set the new one and return with false then.
                (b) It's possible to set:
                        (b1) a simple component here which supports the window only - no controller;
                        (b2) a full featured component which supports window and controller;
                        (b3) or both to NULL if outside code which to forget this component.

	@seealso	method getComponentWindow()
	@seealso	method getController()

    @param      xComponentWindow
                    valid reference to new component window which will be a child of internal container window
                    May <NULL/> for releasing.
    @param      xController
                    reference to new component controller
                    (may <NULL/> for relasing or setting of a simple component)

    @return     <TRUE/> if operation was successful, <FALSE/> otherwise.

    @onerror    We return <FALSE/>.
    @threadsafe yes
    @modified   06.05.2002 11:39, as96863
*//*-*****************************************************************************************************/
sal_Bool SAL_CALL Frame::setComponent(  const   css::uno::Reference< css::awt::XWindow >&       xComponentWindow ,
                                        const   css::uno::Reference< css::frame::XController >& xController      ) throw( css::uno::RuntimeException )
{
    //_____________________________________________________________________________________________________
    // Ignore this HACK of sfx2!
    // He call us with an valid controller without a valid window ... Thats not allowed!
    if  ( xController.is() && ! xComponentWindow.is() )
		return sal_True;

	TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

    //_____________________________________________________________________________________________________
    // Get threadsafe some copies of used members.
    /* SAFE { */
    ReadGuard aReadLock( m_aLock );
    css::uno::Reference< css::awt::XWindow >       xContainerWindow    = m_xContainerWindow;
    css::uno::Reference< css::awt::XWindow >       xOldComponentWindow = m_xComponentWindow;
    css::uno::Reference< css::frame::XController > xOldController      = m_xController;
    Window*                                        pOwnWindow = VCLUnoHelper::GetWindow( xContainerWindow );
    sal_Bool                                       bHadFocus           = pOwnWindow->HasChildPathFocus();
    sal_Bool                                       bWasConnected       = m_bConnected;
    aReadLock.unlock();
    /* } SAFE */

    //_____________________________________________________________________________________________________
	// stop listening on old window
	// May it produce some trouble.
    // But don't forget to listen on new window again ... or reactivate listening
    // if we reject this setComponent() request and leave this method without changing the old window.
    implts_stopWindowListening();

	// Notify all listener, that this component (if current one exist) will be unloaded.
	if (bWasConnected)
		implts_sendFrameActionEvent( css::frame::FrameAction_COMPONENT_DETACHING );

    //_____________________________________________________________________________________________________
    // otherwhise release old component first
    // Always release controller before releasing window,
    // because controller may want to access its window!
    // But check for real changes - may the new controller is the old one.
    if (
        (xOldController.is()          )   &&
        (xOldController != xController)
       )
    {
        /* ATTENTION
            Don't suspend the old controller here. Because the outside caller must do that
            by definition. We have to dispose it here only.
         */

        // Before we dispose this controller we should hide it inside this frame instance.
        // We hold it alive for next calls by using xOldController!
        /* SAFE {*/
        WriteGuard aWriteLock( m_aLock );
        m_xController = NULL;
        aWriteLock.unlock();
        /* } SAFE */

        css::uno::Reference< css::lang::XComponent > xDisposable( xOldController, css::uno::UNO_QUERY );
        if (xDisposable.is())
        {
            try
            {
                xDisposable->dispose();
            }
            catch(const css::lang::DisposedException&)
                {}
        }
	    xOldController = NULL;
    }

    //_____________________________________________________________________________________________________
    // Now it's time to release the component window.
    // If controller wasn't released successfully - this code line shouldn't be reached.
    // Because in case of "suspend()==false" we return immediately with false ...
    // see before
    // Check for real changes too.
    if (
        (xOldComponentWindow.is()               )   &&
        (xOldComponentWindow != xComponentWindow)
       )
    {
        /* SAFE { */
        WriteGuard aWriteLock( m_aLock );
        m_xComponentWindow = NULL;
        aWriteLock.unlock();
        /* } SAFE */

        css::uno::Reference< css::lang::XComponent > xDisposable( xOldComponentWindow, css::uno::UNO_QUERY );
        if (xDisposable.is())
        {
            try
            {
                xDisposable->dispose();
            }
            catch(const css::lang::DisposedException&)
                {}
        }
	    xOldComponentWindow = NULL;
    }

    //_____________________________________________________________________________________________________
    // Now it's time to set the new component ...
    // By the way - find out our new "load state" - means if we have a valid component inside.
    /* SAFE { */
    WriteGuard aWriteLock( m_aLock );
	m_xComponentWindow = xComponentWindow;
    m_xController      = xController     ;
    m_bConnected       = (m_xComponentWindow.is() || m_xController.is());
    sal_Bool bIsConnected       = m_bConnected;
    aWriteLock.unlock();
    /* } SAFE */

    //_____________________________________________________________________________________________________
	// notifies all interest listener, that current component was changed or a new one was loaded
    if (bIsConnected && bWasConnected)
        implts_sendFrameActionEvent( css::frame::FrameAction_COMPONENT_REATTACHED );
    else
    if (bIsConnected && !bWasConnected)
        implts_sendFrameActionEvent( css::frame::FrameAction_COMPONENT_ATTACHED   );

    //_____________________________________________________________________________________________________
    // A new component window doesn't know anything about current active/focus states.
    // Set this information on it!
    if (
        (bHadFocus            ) &&
        (xComponentWindow.is())
       )
    {
        xComponentWindow->setFocus();
    }

    // If it was a new component window - we must resize it to fill out
    // our container window.
    implts_resizeComponentWindow();
    // New component should change our current icon ...
    implts_setIconOnWindow();
	// OK - start listening on new window again - or do nothing if it is an empty one.
    implts_startWindowListening();

    /* SAFE { */
    aWriteLock.lock();
    impl_checkMenuCloser();
    aWriteLock.unlock();
    /* } SAFE */

	return sal_True;
}

/*-****************************************************************************************************//**
	@short		returns current set component window
	@descr		Frames are used to display components. The actual displayed component is
				held by the m_xComponentWindow property. If the component implements only a
				XComponent interface, the communication between the frame and the
				component is very restricted. Better integration is achievable through a
				XController interface.
				If the component wants other objects to be able to get information about its
				ResourceDescriptor it has to implement a XModel interface.
				This frame is the owner of the component window.

	@seealso	method setComponent()

	@param		-
    @return     css::uno::Reference to current set component window.

	@onerror	A null reference is returned.
*//*-*****************************************************************************************************/
css::uno::Reference< css::awt::XWindow > SAL_CALL Frame::getComponentWindow() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Register transaction and reject wrong calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    return m_xComponentWindow;
}

/*-****************************************************************************************************//**
	@short		returns current set controller
	@descr		Frames are used to display components. The actual displayed component is
				held by the m_xComponentWindow property. If the component implements only a
				XComponent interface, the communication between the frame and the
				component is very restricted. Better integration is achievable through a
				XController interface.
				If the component wants other objects to be able to get information about its
				ResourceDescriptor it has to implement a XModel interface.
				This frame is the owner of the component window.

	@seealso	method setComponent()

	@param		-
    @return     css::uno::Reference to current set controller.

	@onerror	A null reference is returned.
*//*-*****************************************************************************************************/
css::uno::Reference< css::frame::XController > SAL_CALL Frame::getController() throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // It seems to be unavoidable that disposed frames allow to ask for a Controller (#111452)
    // Register transaction and reject wrong calls.
    // TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    return m_xController;
}

/*-****************************************************************************************************//**
	@short		add/remove listener for activate/deactivate/contextChanged events
	@descr		-

	@seealso	method activate()
	@seealso	method deactivate()
	@seealso	method contextChanged()

	@param		"xListener" reference to your listener object
	@return		-

	@onerror	Listener is ignored.
*//*-*****************************************************************************************************/
void SAL_CALL Frame::addFrameActionListener( const css::uno::Reference< css::frame::XFrameActionListener >& xListener ) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_addFrameActionListener( xListener ), "Frame::addFrameActionListener()", "Invalid parameter detected." )
    // Listener container is threadsafe by himself ... but we must look for rejected calls!
    // Our OMenuDispatch-helper (is a member of ODispatchProvider!) is create at startup of this frame BEFORE initialize!
    // => soft exceptions!
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    m_aListenerContainer.addInterface( ::getCppuType( (const css::uno::Reference< css::frame::XFrameActionListener >*)NULL ), xListener );
}

//*****************************************************************************************************************
void SAL_CALL Frame::removeFrameActionListener( const css::uno::Reference< css::frame::XFrameActionListener >& xListener ) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_removeFrameActionListener( xListener ), "Frame::removeFrameActionListener()", "Invalid parameter detected." )
	// Listener container is threadsafe by himself ... but we must look for rejected calls after disposing!
    // But we must work with E_SOFTEXCEPTIONS ... because sometimes we are called from our listeners
    // during dispose! Our work mode is E_BEFORECLOSE then ... and E_HARDEXCEPTIONS whould throw a DisposedException.
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    m_aListenerContainer.removeInterface( ::getCppuType( (const css::uno::Reference< css::frame::XFrameActionListener >*)NULL ), xListener );
}

/*-****************************************************************************************************//**
    @short      support two way mechanism to release a frame
    @descr      This method ask internal component (controller) if he accept this close request.
                In case of <TRUE/> nothing will be happen (from point of caller of this close method).
                In case of <FALSE/> a CloseVetoException is thrown. After such exception given parameter
                <var>bDeliverOwnerShip</var> regulate which will be the new owner of this instance.

    @attention  It's the replacement for XTask::close() which is marked as obsolete method.

    @param      bDeliverOwnerShip
                    If parameter is set to <FALSE/> the original caller will be the owner after thrown
                    veto exception and must try to close this frame at later time again. Otherwhise the
                    source of throwed exception is the right one. May it will be the frame himself.

    @thrown     CloseVetoException
                    if any internal things willn't be closed

    @threadsafe yes
    @modified   06.05.2002 08:33, as96863
*//*-*****************************************************************************************************/
void SAL_CALL Frame::close( sal_Bool bDeliverOwnerShip ) throw( css::util::CloseVetoException,
                                                                css::uno::RuntimeException   )
{
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

    // At the end of this method may we must dispose ourself ...
    // and may nobody from outside hold a reference to us ...
    // then it's a good idea to do that by ourself.
    css::uno::Reference< css::uno::XInterface > xSelfHold( static_cast< ::cppu::OWeakObject* >(this) );

    // Check any close listener before we look for currently running internal processes.
    // Because if a listener disagree with this close() request - we hace time to finish this
    // internal operations too ...
    // Note: container is threadsafe himself.
    css::lang::EventObject             aSource    (static_cast< ::cppu::OWeakObject*>(this));
    ::cppu::OInterfaceContainerHelper* pContainer = m_aListenerContainer.getContainer( ::getCppuType( ( const css::uno::Reference< css::util::XCloseListener >*) NULL ) );
    if (pContainer!=NULL)
	{
        ::cppu::OInterfaceIteratorHelper pIterator(*pContainer);
        while (pIterator.hasMoreElements())
        {
            try
            {
                ((css::util::XCloseListener*)pIterator.next())->queryClosing( aSource, bDeliverOwnerShip );
            }
            catch( css::uno::RuntimeException& )
            {
                pIterator.remove();
            }
        }
	}

    // Ok - no listener disagreed with this close() request
    // check if this frame is used for any load process currently
    if (isActionLocked())
    {
        if (bDeliverOwnerShip)
		{
			/* SAFE */
			WriteGuard aWriteLock( m_aLock );
			m_bSelfClose = sal_True;
			aWriteLock.unlock();
			/* SAFE */
		}

		throw css::util::CloseVetoException(DECLARE_ASCII("Frame in use for loading document ..."),static_cast< ::cppu::OWeakObject*>(this));
    }

    if ( ! setComponent(NULL,NULL) )
        throw css::util::CloseVetoException(DECLARE_ASCII("Component couldn't be deattached ..."),static_cast< ::cppu::OWeakObject*>(this));

    // If closing is allowed ... inform all istener and dispose this frame!
    pContainer = m_aListenerContainer.getContainer( ::getCppuType( ( const css::uno::Reference< css::util::XCloseListener >*) NULL ) );
    if (pContainer!=NULL)
	{
        ::cppu::OInterfaceIteratorHelper pIterator(*pContainer);
        while (pIterator.hasMoreElements())
        {
            try
            {
                ((css::util::XCloseListener*)pIterator.next())->notifyClosing( aSource );
            }
            catch( css::uno::RuntimeException& )
            {
                pIterator.remove();
            }
        }
	}

    /* SAFE { */
	WriteGuard aWriteLock( m_aLock );
    m_bIsHidden = sal_True;
    aWriteLock.unlock();
    /* } SAFE */
    impl_checkMenuCloser();

    // Attention: We must release our own registered transaction here. Otherwhise following dispose() call
    // wait for us too ....
    aTransaction.stop();
    dispose();
}

/*-****************************************************************************************************//**
    @short      be a listener for close events!
    @descr      Adds/remove a CloseListener at this frame instance. If the close() method is called on
                this object, the such listener are informed and can disagree with that by throwing
                a CloseVetoException.

    @seealso    Frame::close()

    @param      xListener
                    reference to your listener object

	@onerror	Listener is ignored.

    @threadsafe yes
    @modified   06.05.2002 10:03, as96863
*//*-*****************************************************************************************************/
void SAL_CALL Frame::addCloseListener( const css::uno::Reference< css::util::XCloseListener >& xListener ) throw (css::uno::RuntimeException)
{
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );
    // We doesn't need any lock here ...
    // Container lives if we live and is threadsafe by himself.
    m_aListenerContainer.addInterface( ::getCppuType( ( const css::uno::Reference< css::util::XCloseListener >* ) NULL ), xListener );
}

//*****************************************************************************************************************
void SAL_CALL Frame::removeCloseListener( const css::uno::Reference< css::util::XCloseListener >& xListener ) throw (css::uno::RuntimeException)
{
    // Use soft exception mode - moslty this method is called during disposing of this frame ...
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );
    // We doesn't need any lock here ...
    // Container lives if we live and is threadsafe by himself.
    m_aListenerContainer.removeInterface( ::getCppuType( ( const css::uno::Reference< css::util::XCloseListener >* ) NULL ), xListener );
}

//*****************************************************************************************************************
::rtl::OUString SAL_CALL Frame::getTitle()
    throw (css::uno::RuntimeException)
{
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	// SAFE ->
	ReadGuard aReadLock(m_aLock);
	css::uno::Reference< css::frame::XTitle > xTitle(m_xTitleHelper, css::uno::UNO_QUERY_THROW);
	aReadLock.unlock();
	// <- SAFE

    return xTitle->getTitle();
}

//*****************************************************************************************************************
void SAL_CALL Frame::setTitle( const ::rtl::OUString& sTitle )
    throw (css::uno::RuntimeException)
{
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	// SAFE ->
	ReadGuard aReadLock(m_aLock);
	css::uno::Reference< css::frame::XTitle > xTitle(m_xTitleHelper, css::uno::UNO_QUERY_THROW);
	aReadLock.unlock();
	// <- SAFE

    xTitle->setTitle(sTitle);
}

//*****************************************************************************************************************
void SAL_CALL Frame::addTitleChangeListener( const css::uno::Reference< css::frame::XTitleChangeListener >& xListener)
    throw (css::uno::RuntimeException)
{
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	// SAFE ->
	ReadGuard aReadLock(m_aLock);
	css::uno::Reference< css::frame::XTitleChangeBroadcaster > xTitle(m_xTitleHelper, css::uno::UNO_QUERY_THROW);
	aReadLock.unlock();
	// <- SAFE

    xTitle->addTitleChangeListener(xListener);
}

//*****************************************************************************************************************
void SAL_CALL Frame::removeTitleChangeListener( const css::uno::Reference< css::frame::XTitleChangeListener >& xListener )
    throw (css::uno::RuntimeException)
{
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	// SAFE ->
	ReadGuard aReadLock(m_aLock);
	css::uno::Reference< css::frame::XTitleChangeBroadcaster > xTitle(m_xTitleHelper, css::uno::UNO_QUERY_THROW);
	aReadLock.unlock();
	// <- SAFE

    xTitle->removeTitleChangeListener(xListener);
}

/*-****************************************************************************************************/
void Frame::implts_forgetSubFrames()
{
	// SAFE ->
	ReadGuard aReadLock(m_aLock);
	css::uno::Reference< css::container::XIndexAccess > xContainer(m_xFramesHelper, css::uno::UNO_QUERY_THROW);
	aReadLock.unlock();
	// <- SAFE

	sal_Int32 c = xContainer->getCount();
	sal_Int32 i = 0;

	for (i=0; i<c; ++i)
	{
		try
		{
			css::uno::Reference< css::frame::XFrame > xFrame;
			xContainer->getByIndex(i) >>= xFrame;
			if (xFrame.is())
				xFrame->setCreator(css::uno::Reference< css::frame::XFramesSupplier >());
		}
		catch(const css::uno::Exception&)
		{
			// Ignore errors here.
			// Nobody can guarantee a stable index in multi threaded environments .-)
		}
	}

	// SAFE ->
	WriteGuard aWriteLock(m_aLock);
    m_xFramesHelper.clear(); // clear uno reference
    m_aChildFrameContainer.clear(); // clear container content
	aWriteLock.unlock();
	// <- SAFE
}

/*-****************************************************************************************************//**
	@short		destroy instance
	@descr		The owner of this object calles the dispose method if the object
				should be destroyed. All other objects and components, that are registered
				as an EventListener are forced to release their references to this object.
				Furthermore this frame is removed from its parent frame container to release
				this reference. The reference attributes are disposed and released also.

	@attention	Look for globale description at beginning of file too!
				(DisposedException, FairRWLock ..., initialize, dispose)

	@seealso	method initialize()
	@seealso	baseclass FairRWLockBase!

	@param		-
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void SAL_CALL Frame::dispose() throw( css::uno::RuntimeException )
{
    // We should hold a reference to ourself ...
    // because our owner dispose us and release our reference ...
    // May be we will die before we could finish this method ...
    css::uno::Reference< css::frame::XFrame > xThis( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );

    LOG_DISPOSEEVENT( "Frame", sName )

    // First operation should be ... "stopp all listening for window events on our container window".
    // These events are superflous but can make trouble!
    // We will die, die and die ...
    implts_stopWindowListening();

    // Send message to all listener and forget her references.
    css::lang::EventObject aEvent( xThis );
    m_aListenerContainer.disposeAndClear( aEvent );

    // set "end of live" for our property set helper
    impl_disablePropertySet();

    // interception/dispatch chain must be destructed explicitly
    // Otherwhise some dispatches and/or interception objects wont die.
    css::uno::Reference< css::lang::XEventListener > xDispatchHelper(m_xDispatchHelper, css::uno::UNO_QUERY_THROW);
    xDispatchHelper->disposing(aEvent);
    xDispatchHelper.clear();

    // Disable this instance for further work.
    // This will wait for all current running ones ...
    // and reject all further requests!
    m_aTransactionManager.setWorkingMode( E_BEFORECLOSE );

    // Don't show any dialogs, errors or something else any more!
    // If somewhere called dispose() whitout close() before - normaly no dialogs
    // should exist. Otherwhise it's the problem of the outside caller.
    // Note:
    //      (a) Do it after stopWindowListening(). May that force some active/deactive
    //          notifications which we doesn't need here realy.
    //      (b) Don't forget to save the old value of IsDialogCancelEnabled() to
    //          restore it afterwards. We cannot call EnableDialogCancel( sal_False )
    //          as we would kill the headless mode!
    sal_Bool bCancelDialogs( Application::IsDialogCancelEnabled() );
    Application::EnableDialogCancel( sal_True );

    // We should be alone for ever and further dispose calls are rejected by lines before ...
    // I hope it :-)

    // Free references of our frame tree.
    // Force parent container to forget this frame too ...
    // ( It's contained in m_xParent and so no css::lang::XEventListener for m_xParent! )
    // It's important to do that before we free some other internal structures.
    // Because if our parent gets an activate and found us as last possible active frame
    // he try to deactivate us ... and we run into some trouble (DisposedExceptions!).
    if( m_xParent.is() == sal_True )
    {
        m_xParent->getFrames()->remove( xThis );
        m_xParent = css::uno::Reference< css::frame::XFramesSupplier >();
    }

    /* } SAFE */
    // Forget our internal component and her window first.
    // So we can release our container window later without problems.
    // Because this container window is the parent of the component window ...
    // Note: Dispose it hard - because suspending must be done inside close() call!
	// But try to dispose the controller first befor you destroy the window.
	// Because the window is used by the controller too ...
    if (m_xController.is())
    {
        css::uno::Reference< css::lang::XComponent > xDisposable( m_xController, css::uno::UNO_QUERY );
        if (xDisposable.is())
            xDisposable->dispose();
    }

    if (m_xComponentWindow.is())
    {
        css::uno::Reference< css::lang::XComponent > xDisposable( m_xComponentWindow, css::uno::UNO_QUERY );
        if (xDisposable.is())
            xDisposable->dispose();
    }

    impl_checkMenuCloser();

    impl_disposeContainerWindow( m_xContainerWindow );

    /*ATTENTION
        Clear container after successful removing from parent container ...
        because our parent could be the desktop which stand in dispose too!
        If we have already cleared our own container we lost our child before this could be
        remove himself at this instance ...
        Release m_xFramesHelper after that ... it's the same problem between parent and child!
        "m_xParent->getFrames()->remove( xThis );" needs this helper ...
        Otherwise we get a null reference and could finish removing successfuly.
        => You see: Order of calling operations is important!!!
     */
	implts_forgetSubFrames();

    // Release some other references.
    // This calls should be easy ... I hope it :-)
    m_xDispatchHelper.clear();
    m_xFactory.clear();
    m_xDropTargetListener.clear();
    m_xDispatchRecorderSupplier.clear();
    m_xLayoutManager.clear();
    m_xIndicatorFactoryHelper.clear();

    // It's important to set default values here!
    // If may be later somewhere change the disposed-behaviour of this implementation
    // and doesn't throw any DisposedExceptions we must guarantee best matching default values ...
    m_eActiveState       = E_INACTIVE;
    m_sName              = ::rtl::OUString();
    m_bIsFrameTop        = sal_False;
    m_bConnected         = sal_False;
    m_nExternalLockCount = 0;
    m_bSelfClose         = sal_False;
    m_bIsHidden          = sal_True;

    // Disable this instance for further working realy!
    m_aTransactionManager.setWorkingMode( E_CLOSE );

    // Don't forget it restore old value -
    // otherwhise no dialogs can be shown anymore in other frames.
    Application::EnableDialogCancel( bCancelDialogs );
}

/*-****************************************************************************************************//**
	@short		Be a listener for dispose events!
	@descr		Adds/remove an EventListener to this object. If the dispose method is called on
				this object, the disposing method of the listener is called.

	@seealso	-

	@param		"xListener" reference to your listener object.
	@return		-

	@onerror	Listener is ignored.
*//*-*****************************************************************************************************/
void SAL_CALL Frame::addEventListener( const css::uno::Reference< css::lang::XEventListener >& xListener ) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_addEventListener( xListener ), "Frame::addEventListener()", "Invalid parameter detected." )
    // Look for rejected calls only!
    // Container is threadsafe.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    m_aListenerContainer.addInterface( ::getCppuType( ( const css::uno::Reference< css::lang::XEventListener >* ) NULL ), xListener );
}

//*****************************************************************************************************************
void SAL_CALL Frame::removeEventListener( const css::uno::Reference< css::lang::XEventListener >& xListener ) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_removeEventListener( xListener ), "Frame::removeEventListener()", "Invalid parameter detected." )
    // Look for rejected calls only!
    // Container is threadsafe.
    // Use E_SOFTEXCEPTIONS to allow removing listeners during dispose call!
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    m_aListenerContainer.removeInterface( ::getCppuType( ( const css::uno::Reference< css::lang::XEventListener >* ) NULL ), xListener );
}

/*-****************************************************************************************************//**
	@short		create new status indicator
	@descr		Use returned status indicator to show progresses and some text informations.
				All created objects share the same dialog! Only the last one can show his information.

    @seealso    class StatusIndicatorFactory
    @seealso    class StatusIndicator

	@param		-
	@return		A reference to created object.

	@onerror	We return a null reference.
*//*-*****************************************************************************************************/
css::uno::Reference< css::task::XStatusIndicator > SAL_CALL Frame::createStatusIndicator() throw( css::uno::RuntimeException )
{
    /* UNSAFE AREA ----------------------------------------------------------------------------------------- */
    // Look for rejected calls!
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    // Make snapshot of neccessary member and define default return value.
    css::uno::Reference< css::task::XStatusIndicator >        xExternal(m_xIndicatorInterception.get(), css::uno::UNO_QUERY);
    css::uno::Reference< css::task::XStatusIndicatorFactory > xFactory = m_xIndicatorFactoryHelper;

    aReadLock.unlock();
    /* UNSAFE AREA ----------------------------------------------------------------------------------------- */

    // Was set from outside to intercept any progress activities!
    if (xExternal.is())
        return xExternal;

    // Or use our own factory as fallback, to create such progress.
    if (xFactory.is())
        return xFactory->createStatusIndicator();

	return css::uno::Reference< css::task::XStatusIndicator >();
}

/*-****************************************************************************************************//**
	@short		search for target to load URL
	@descr		This method searches for a dispatch for the specified DispatchDescriptor.
				The FrameSearchFlags and the FrameName of the DispatchDescriptor are
				treated as described for findFrame.

	@seealso	method findFrame()
	@seealso	method queryDispatches()
	@seealso	method set/getName()
	@seealso	class TargetFinder

	@param		"aURL"				, URL for loading
	@param		"sTargetFrameName"	, name of target frame
	@param		"nSearchFlags"		, additional flags to regulate search if sTargetFrameName isn't clear
    @return     css::uno::Reference to dispatch handler.

	@onerror	A null reference is returned.
*//*-*****************************************************************************************************/
css::uno::Reference< css::frame::XDispatch > SAL_CALL Frame::queryDispatch( const css::util::URL&   aURL            ,
                                                                            const ::rtl::OUString&  sTargetFrameName,
                                                                                  sal_Int32         nSearchFlags    ) throw( css::uno::RuntimeException )
{
	const char UNO_PROTOCOL[] = ".uno:";

	// Don't check incoming parameter here! Our helper do it for us and it isn't a good idea to do it more then ones!
    // But look for rejected calls!
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	// Remove uno and cmd protocol part as we want to support both of them. We store only the command part
	// in our hash map. All other protocols are stored with the protocol part.
	String aCommand( aURL.Main );
	if ( aURL.Protocol.equalsIgnoreAsciiCaseAsciiL( UNO_PROTOCOL, sizeof( UNO_PROTOCOL )-1 ))
		aCommand = aURL.Path;

	// Make hash_map lookup if the current URL is in the disabled list
	if ( m_aCommandOptions.Lookup( SvtCommandOptions::CMDOPTION_DISABLED, aCommand ) )
		return css::uno::Reference< css::frame::XDispatch >();
	else
	{
		// We use a helper to support these interface and an interceptor mechanism.
		// Our helper is threadsafe by himself!
		return m_xDispatchHelper->queryDispatch( aURL, sTargetFrameName, nSearchFlags );
	}
}

/*-****************************************************************************************************//**
	@short		handle more then ones dispatches at same call
    @descr      Returns a sequence of dispatches. For details see the queryDispatch method.
				For failed dispatches we return empty items in list!

	@seealso	method queryDispatch()

	@param		"lDescriptor" list of dispatch arguments for queryDispatch()!
	@return		List of dispatch references. Some elements can be NULL!

	@onerror	An empty list is returned.
*//*-*****************************************************************************************************/
css::uno::Sequence< css::uno::Reference< css::frame::XDispatch > > SAL_CALL Frame::queryDispatches( const css::uno::Sequence< css::frame::DispatchDescriptor >& lDescriptor ) throw( css::uno::RuntimeException )
{
	// Don't check incoming parameter here! Our helper do it for us and it isn't a good idea to do it more then ones!
    // But look for rejected calls!
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	// We use a helper to support these interface and an interceptor mechanism.
    // Our helper is threadsafe by himself!
    return m_xDispatchHelper->queryDispatches( lDescriptor );
}

/*-****************************************************************************************************//**
	@short		register/unregister interceptor for dispatch calls
	@descr		If you whish to handle some dispatches by himself ... you should be
				an interceptor for it. Please see class OInterceptionHelper for further informations.

	@seealso	class OInterceptionHelper

	@param		"xInterceptor", reference to your interceptor implementation.
	@return		-

	@onerror	Interceptor is ignored.
*//*-*****************************************************************************************************/
void SAL_CALL Frame::registerDispatchProviderInterceptor( const css::uno::Reference< css::frame::XDispatchProviderInterceptor >& xInterceptor ) throw( css::uno::RuntimeException )
{
	// We use a helper to support these interface and an interceptor mechanism.
    // This helper is threadsafe himself and check incoming parameter too.
    // I think we don't need any lock here!
    // But we must look for rejected calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

    css::uno::Reference< css::frame::XDispatchProviderInterception > xInterceptionHelper( m_xDispatchHelper, css::uno::UNO_QUERY );
    xInterceptionHelper->registerDispatchProviderInterceptor( xInterceptor );
}

//*****************************************************************************************************************
void SAL_CALL Frame::releaseDispatchProviderInterceptor( const css::uno::Reference< css::frame::XDispatchProviderInterceptor >& xInterceptor ) throw( css::uno::RuntimeException )
{
	// We use a helper to support these interface and an interceptor mechanism.
    // This helper is threadsafe himself and check incoming parameter too.
    // I think we don't need any lock here!
    // But we must look for rejected calls ...
    // Sometimes we are called during our dispose() method ... => soft exceptions!
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

    css::uno::Reference< css::frame::XDispatchProviderInterception > xInterceptionHelper( m_xDispatchHelper, css::uno::UNO_QUERY );
    xInterceptionHelper->releaseDispatchProviderInterceptor( xInterceptor );
}

/*-****************************************************************************************************//**
	@short		provides information about all possible dispatch functions
                inside the currnt frame environment
*//*-*****************************************************************************************************/
css::uno::Sequence< sal_Int16 > SAL_CALL Frame::getSupportedCommandGroups()
    throw(css::uno::RuntimeException)
{
    return m_xDispatchInfoHelper->getSupportedCommandGroups();
}

//*****************************************************************************************************************
css::uno::Sequence< css::frame::DispatchInformation > SAL_CALL Frame::getConfigurableDispatchInformation(sal_Int16 nCommandGroup)
    throw(css::uno::RuntimeException)
{
    return m_xDispatchInfoHelper->getConfigurableDispatchInformation(nCommandGroup);
}

/*-****************************************************************************************************//**
	@short		notifications for window events
	@descr		We are a listener on our container window to forward it to our component window.

	@seealso	method setComponent()
	@seealso	member m_xContainerWindow
	@seealso	member m_xComponentWindow

	@param		"aEvent" describe source of detected event
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void SAL_CALL Frame::windowResized( const css::awt::WindowEvent&
#if OSL_DEBUG_LEVEL > 0
aEvent
#endif
) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_windowResized( aEvent ), "Frame::windowResized()", "Invalid parameter detected." )
    // Look for rejected calls.
    // Part of dispose-mechanism => soft exceptions
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
	// Impl-method is threadsafe!
	// If we have a current component window - we must resize it!
    implts_resizeComponentWindow();
}

//*****************************************************************************************************************
void SAL_CALL Frame::focusGained( const css::awt::FocusEvent&
#if OSL_DEBUG_LEVEL > 0
aEvent
#endif
) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_focusGained( aEvent ), "Frame::focusGained()", "Invalid parameter detected." )
    // Look for rejected calls.
    // Part of dispose() mechanism ... => soft exceptions!
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );
    // Make snapshot of member!
    css::uno::Reference< css::awt::XWindow > xComponentWindow = m_xComponentWindow;
    aReadLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    if( xComponentWindow.is() == sal_True )
    {
        xComponentWindow->setFocus();
    }
}

/*-****************************************************************************************************//**
	@short		notifications for window events
	@descr		We are a listener on our container window to forward it to our component window ...
				but a XTopWindowListener we are only if we are a top frame!

	@seealso	method setComponent()
	@seealso	member m_xContainerWindow
	@seealso	member m_xComponentWindow

	@param		"aEvent" describe source of detected event
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void SAL_CALL Frame::windowActivated( const css::lang::EventObject&
#if OSL_DEBUG_LEVEL > 0
aEvent
#endif
) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_windowActivated( aEvent ), "Frame::windowActivated()", "Invalid parameter detected." )
    // Look for rejected calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );
    // Make snapshot of member!
    EActiveState eState = m_eActiveState;
    aReadLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Activate the new active path from here to top.
    if( eState == E_INACTIVE )
    {
//       CheckMenuCloser_Impl();
        setActiveFrame( css::uno::Reference< css::frame::XFrame >() );
        activate();
    }
}

//*****************************************************************************************************************
void SAL_CALL Frame::windowDeactivated( const css::lang::EventObject&
#if OSL_DEBUG_LEVEL > 0
aEvent
#endif
) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_windowDeactivated( aEvent ), "Frame::windowDeactivated()", "Invalid parameter detected." )
    // Look for rejected calls.
    // Sometimes called during dispose() => soft exceptions
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );

    css::uno::Reference< css::frame::XFrame > xParent          ( m_xParent, css::uno::UNO_QUERY );
    css::uno::Reference< css::awt::XWindow >  xContainerWindow = m_xContainerWindow;
    EActiveState                              eActiveState     = m_eActiveState    ;

    aReadLock.unlock();

    if( eActiveState != E_INACTIVE )
    {
        // Deactivation is always done implicitely by activation of another frame.
        // Only if no activation is done, deactivations have to be processed if the activated window
        // is a parent window of the last active Window!
        ::vos::OClearableGuard aSolarGuard( Application::GetSolarMutex() );
//       CheckMenuCloser_Impl();
        Window* pFocusWindow = Application::GetFocusWindow();
        if  (
                ( xContainerWindow.is()                                                              ==  sal_True    )   &&
                ( xParent.is()                                                                       ==  sal_True    )   &&
                ( (css::uno::Reference< css::frame::XDesktop >( xParent, css::uno::UNO_QUERY )).is() ==  sal_False   )
            )
        {
            css::uno::Reference< css::awt::XWindow >  xParentWindow   = xParent->getContainerWindow()             ;
            Window*                                   pParentWindow   = VCLUnoHelper::GetWindow( xParentWindow    );
            //#i70261#: dialogs opend from an OLE object will cause a deactivate on the frame of the OLE object
            // on Solaris/Linux at that time pFocusWindow is still NULL because the focus handling is different; right after
            // the deactivation the focus will be set into the dialog!
            // currently I see no case where a sub frame could get a deactivate with pFocusWindow being NULL permanently
            // so for now this case is omitted from handled deactivations
            if( pFocusWindow && pParentWindow->IsChild( pFocusWindow ) )
            {
                css::uno::Reference< css::frame::XFramesSupplier > xSupplier( xParent, css::uno::UNO_QUERY );
                if( xSupplier.is() == sal_True )
                {
                    aSolarGuard.clear();
                    xSupplier->setActiveFrame( css::uno::Reference< css::frame::XFrame >() );
                }
            }
        }
    }
}

//*****************************************************************************************************************
void SAL_CALL Frame::windowClosing( const css::lang::EventObject& ) throw( css::uno::RuntimeException )
{
    /* #i62088#
        Some interceptor objects intercept our "internaly asynchronoues implemented" dispatch call.
        And they close this frame directly (means synchronous then).
        Means: Frame::windowClosing()->Frame::close()
        In such situation its not a good idea to hold this transaction count alive .-)
    */
    {
        // Look for rejected calls.
        TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );
        // deactivate this frame ...
    	deactivate();
    }

    // ... and try to close it
    // But do it asynchron inside the main thread.
    // VCL has no fun to do such things outside his main thread :-(
    // Note: The used dispatch make it asynchronous for us .-)

    /*ATTENTION!
        Don't try to suspend the controller here! Because it's done inside used dispatch().
        Otherwhise the dialog "would you save your changes?" will be shown more then once ...
     */

    /* SAFE */
    ReadGuard aReadLock( m_aLock );
    css::uno::Reference< css::lang::XMultiServiceFactory > xFactory = m_xFactory;
    aReadLock.unlock();
    /* SAFE */

    css::util::URL aURL;
    aURL.Complete = DECLARE_ASCII(".uno:CloseFrame");
    css::uno::Reference< css::util::XURLTransformer > xParser(xFactory->createInstance(SERVICENAME_URLTRANSFORMER), css::uno::UNO_QUERY_THROW);
    xParser->parseStrict(aURL);

    css::uno::Reference< css::frame::XDispatch > xCloser = queryDispatch(aURL, SPECIALTARGET_SELF, 0);
    if (xCloser.is())
        xCloser->dispatch(aURL, css::uno::Sequence< css::beans::PropertyValue >());

    // Attention: If this dispatch works synchronous ... and full fill its job ...
    // this line of code will never be reached ...
    // Or if it will be reached it will be for sure that all your member are gone .-)
}

/*-****************************************************************************************************//**
    @short      react for a show event for the internal container window
    @descr      Normaly we doesn't need this information realy. But we can use it to
                implement the special feature "trigger first visible task".

                Algorithm: - first we have to check if we are a top (task) frame
                             It's not enough to be a top frame! Because we MUST have the desktop as parent.
                             But frames without a parent are top too. So it's not possible to check isTop() here!
                             We have to look for the type of our parent.
                           - if we are a task frame, then we have to check if we are the first one.
                             We use a static variable to do so. They will be reset to afterwards be shure
                             that further calls of this method doesn't do anything then.
                           - Then we have to trigger the right event string on the global job executor.

    @seealso    css::task::JobExecutor

    @param      aEvent
                    describes the source of this event
                    We are not interested on this information. We are interested on the visible state only.

    @threadsafe yes
    @modified   31.07.2002 07:56, as96863
*//*-*****************************************************************************************************/
void SAL_CALL Frame::windowShown( const css::lang::EventObject& ) throw(css::uno::RuntimeException)
{
    static sal_Bool bFirstVisibleTask = sal_True;

    /* SAFE { */
    ReadGuard aReadLock(m_aLock);
    css::uno::Reference< css::frame::XDesktop >             xDesktopCheck( m_xParent, css::uno::UNO_QUERY );
    css::uno::Reference< css::lang::XMultiServiceFactory >  xFactory     = m_xFactory;
    m_bIsHidden = sal_False;
    aReadLock.unlock();
    /* } SAFE */

    impl_checkMenuCloser();

    if (xDesktopCheck.is())
    {
        /* STATIC SAFE { */
        WriteGuard aStaticWriteLock( LockHelper::getGlobalLock() );
        sal_Bool bMustBeTriggered  = bFirstVisibleTask;
                 bFirstVisibleTask = sal_False;
        aStaticWriteLock.unlock();
        /* } STATIC SAFE */

        if (bMustBeTriggered)
        {
            css::uno::Reference< css::task::XJobExecutor > xExecutor( xFactory->createInstance( SERVICENAME_JOBEXECUTOR ), css::uno::UNO_QUERY );
            if (xExecutor.is())
            {
                xExecutor->trigger( DECLARE_ASCII("onFirstVisibleTask") );
            }
        }
    }
}

void SAL_CALL Frame::windowHidden( const css::lang::EventObject& ) throw(css::uno::RuntimeException)
{
    /* SAFE { */
    ReadGuard aReadLock(m_aLock);
    m_bIsHidden = sal_True;
    aReadLock.unlock();
    /* } SAFE */

    impl_checkMenuCloser();
}

/*-****************************************************************************************************//**
	@short		called by dispose of our windows!
	@descr		This object is forced to release all references to the interfaces given
				by the parameter source. We are a listener at our container window and
				should listen for his diposing.

	@seealso	XWindowListener
	@seealso	XTopWindowListener
	@seealso	XFocusListener

	@param		-
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void SAL_CALL Frame::disposing( const css::lang::EventObject& aEvent ) throw( css::uno::RuntimeException )
{
	/* UNSAFE AREA --------------------------------------------------------------------------------------------- */
	// Check incoming parameter.
    LOG_ASSERT2( implcp_disposing( aEvent ), "Frame::disposing()", "Invalid parameter detected." )
    // Look for rejected calls.
    // May be we are called during releasing our windows in our in dispose call!? => soft exceptions
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    WriteGuard aWriteLock( m_aLock );

    if( aEvent.Source == m_xContainerWindow )
    {
        // NECCESSARY: Impl-method is threadsafe by himself!
        aWriteLock.unlock();
        implts_stopWindowListening();
        aWriteLock.lock();
        m_xContainerWindow = css::uno::Reference< css::awt::XWindow >();
    }
}

/*-************************************************************************************************************//**
    @interface  com.sun.star.document.XActionLockable
    @short      implement locking of frame/task from outside
    @descr      Sometimes we have problems to decide if closing of task is allowed. Because; frame/task
                could be used for pending loading jobs. So you can lock this object from outside and
                prevent instance against closing during using! But - don't do it in a wrong or expensive manner.
                Otherwise task couldn't die anymore!!!

    @seealso    interface XActionLockable
    @seeelso    method BaseDispatcher::implts_loadIt()
    @seeelso    method Desktop::loadComponentFromURL()

    @param      -
    @return     true if frame/task is locked
                false otherwise

    @onerror    -
    @threadsafe yes
*//*-*************************************************************************************************************/
sal_Bool SAL_CALL Frame::isActionLocked() throw( css::uno::RuntimeException )
{
	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    ReadGuard aReadLock( m_aLock );
    return( m_nExternalLockCount!=0);
}

//*****************************************************************************************************************
void SAL_CALL Frame::addActionLock() throw( css::uno::RuntimeException )
{
	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    WriteGuard aWriteLock( m_aLock );
    ++m_nExternalLockCount;
}

//*****************************************************************************************************************
void SAL_CALL Frame::removeActionLock() throw( css::uno::RuntimeException )
{
	// Register no transaction here! Otherwhise we wait for ever inside possible
	// implts_checkSuicide()/dispose() request ...

    /* SAFE AREA */{
        WriteGuard aWriteLock( m_aLock );
        LOG_ASSERT2( m_nExternalLockCount<=0, "Frame::removeActionLock()", "Frame isn't locked! Possible multithreading problem detected." )
        --m_nExternalLockCount;
    }/* SAFE */

    implts_checkSuicide();
}

//*****************************************************************************************************************
void SAL_CALL Frame::setActionLocks( sal_Int16 nLock ) throw( css::uno::RuntimeException )
{
	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    WriteGuard aWriteLock( m_aLock );
    // Attention: If somewhere called resetActionLocks() before and get e.g. 5 locks ...
    //            and tried to set these 5 ones here after his operations ...
    //            we can't ignore setted requests during these two calls!
    //            So we must add(!) these 5 locks here.
    m_nExternalLockCount = m_nExternalLockCount + nLock;
}

//*****************************************************************************************************************
sal_Int16 SAL_CALL Frame::resetActionLocks() throw( css::uno::RuntimeException )
{
	// Register no transaction here! Otherwhise we wait for ever inside possible
	// implts_checkSuicide()/dispose() request ...

    sal_Int16 nCurrentLocks = 0;
    /* SAFE */{
        WriteGuard aWriteLock( m_aLock );
        nCurrentLocks = m_nExternalLockCount;
        m_nExternalLockCount = 0;
    }/* SAFE */

    // Attention:
	// external lock count is 0 here every time ... but if
    // member m_bSelfClose is set to true too .... we call our own close()/dispose().
    // See close() for further informations
    implts_checkSuicide();

    return nCurrentLocks;
}

//*****************************************************************************************************************
void Frame::impl_initializePropInfo()
{
    impl_setPropertyChangeBroadcaster(static_cast< css::frame::XFrame* >(this));

    impl_addPropertyInfo(
        css::beans::Property(
            FRAME_PROPNAME_DISPATCHRECORDERSUPPLIER,
            FRAME_PROPHANDLE_DISPATCHRECORDERSUPPLIER,
            ::getCppuType((const css::uno::Reference< css::frame::XDispatchRecorderSupplier >*)NULL),
            css::beans::PropertyAttribute::TRANSIENT));

    impl_addPropertyInfo(
        css::beans::Property(
            FRAME_PROPNAME_INDICATORINTERCEPTION,
            FRAME_PROPHANDLE_INDICATORINTERCEPTION,
            ::getCppuType((const css::uno::Reference< css::task::XStatusIndicator >*)NULL),
            css::beans::PropertyAttribute::TRANSIENT));

    impl_addPropertyInfo(
        css::beans::Property(
            FRAME_PROPNAME_ISHIDDEN,
            FRAME_PROPHANDLE_ISHIDDEN,
            ::getBooleanCppuType(),
            css::beans::PropertyAttribute::TRANSIENT | css::beans::PropertyAttribute::READONLY));

    impl_addPropertyInfo(
        css::beans::Property(
            FRAME_PROPNAME_LAYOUTMANAGER,
            FRAME_PROPHANDLE_LAYOUTMANAGER,
            ::getCppuType((const css::uno::Reference< ::com::sun::star::frame::XLayoutManager >*)NULL),
            css::beans::PropertyAttribute::TRANSIENT));

    impl_addPropertyInfo(
        css::beans::Property(
            FRAME_PROPNAME_TITLE,
            FRAME_PROPHANDLE_TITLE,
            ::getCppuType((const ::rtl::OUString*)NULL),
            css::beans::PropertyAttribute::TRANSIENT));
}

//*****************************************************************************************************************
void SAL_CALL Frame::impl_setPropertyValue(const ::rtl::OUString& /*sProperty*/,
                                                 sal_Int32        nHandle  ,
                                           const css::uno::Any&   aValue   )

{
    static ::rtl::OUString MATERIALPROP_TITLE = ::rtl::OUString::createFromAscii("title");

    /* There is no need to lock any mutex here. Because we share the
       solar mutex with our base class. And we said to our base class: "dont release it on calling us" .-)
       see ctor of PropertySetHelper for further informations.
    */

    /* Attention: You can use nHandle only, if you are sure that all supported
                  properties has an unique handle. That must be guaranteed
                  inside method impl_initializePropInfo()!
    */
	switch (nHandle)
	{
        case FRAME_PROPHANDLE_TITLE :
                {
                    ::rtl::OUString sExternalTitle;
                    aValue >>= sExternalTitle;
					setTitle (sExternalTitle);
                }
                break;

        case FRAME_PROPHANDLE_DISPATCHRECORDERSUPPLIER :
                aValue >>= m_xDispatchRecorderSupplier;
                break;

        case FRAME_PROPHANDLE_LAYOUTMANAGER :
                {
                    css::uno::Reference< css::frame::XLayoutManager > xOldLayoutManager = m_xLayoutManager;
                    css::uno::Reference< css::frame::XLayoutManager > xNewLayoutManager;
                    aValue >>= xNewLayoutManager;

                    if (xOldLayoutManager != xNewLayoutManager)
                    {
                        m_xLayoutManager = xNewLayoutManager;
                        if (xOldLayoutManager.is())
                            lcl_disableLayoutManager(xOldLayoutManager, this);
                        if (xNewLayoutManager.is())
                            lcl_enableLayoutManager(xNewLayoutManager, this);
                    }
                }
                break;

        case FRAME_PROPHANDLE_INDICATORINTERCEPTION :
                {
                    css::uno::Reference< css::task::XStatusIndicator > xProgress;
                    aValue >>= xProgress;
                    m_xIndicatorInterception = xProgress;
                }
                break;

        #ifdef ENABLE_WARNINGS
        default :
                LOG_WARNING( "Frame::setFastPropertyValue_NoBroadcast()", "Invalid handle detected!" )
                break;
		#endif
	}
}

//*****************************************************************************************************************
css::uno::Any SAL_CALL Frame::impl_getPropertyValue(const ::rtl::OUString& /*sProperty*/,
                                                          sal_Int32        nHandle  )
{
    /* There is no need to lock any mutex here. Because we share the
       solar mutex with our base class. And we said to our base class: "dont release it on calling us" .-)
       see ctor of PropertySetHelper for further informations.
    */

    /* Attention: You can use nHandle only, if you are sure that all supported
                  properties has an unique handle. That must be guaranteed
                  inside method impl_initializePropInfo()!
    */
    css::uno::Any aValue;
	switch (nHandle)
	{
        case FRAME_PROPHANDLE_TITLE :
				aValue <<= getTitle ();
                break;

        case FRAME_PROPHANDLE_DISPATCHRECORDERSUPPLIER :
                aValue <<= m_xDispatchRecorderSupplier;
                break;

        case FRAME_PROPHANDLE_ISHIDDEN :
                aValue <<= m_bIsHidden;
                break;

        case FRAME_PROPHANDLE_LAYOUTMANAGER :
                aValue <<= m_xLayoutManager;
                break;

        case FRAME_PROPHANDLE_INDICATORINTERCEPTION :
                {
                    css::uno::Reference< css::task::XStatusIndicator > xProgress(m_xIndicatorInterception.get(), css::uno::UNO_QUERY);
                    aValue = css::uno::makeAny(xProgress);
                }
                break;

        #ifdef ENABLE_WARNINGS
        default :
                LOG_WARNING( "Frame::getFastPropertyValue()", "Invalid handle detected!" )
                break;
		#endif
	}

    return aValue;
}

/*-****************************************************************************************************//**
    @short      dispose old container window and forget his reference
    @descr      Sometimes we must repair our "modal dialog parent mechanism" too!

	@seealso	-

    @param      "xWindow", reference to old container window to dispose it
    @return     An empty reference.

    @onerror    -
    @threadsafe NO!
*//*-*****************************************************************************************************/
void Frame::impl_disposeContainerWindow( css::uno::Reference< css::awt::XWindow >& xWindow )
{
    if( xWindow.is() == sal_True )
    {
        xWindow->setVisible( sal_False );
        // All VclComponents are XComponents; so call dispose before discarding
        // a css::uno::Reference< XVclComponent >, because this frame is the owner of the window
        xWindow->dispose();
        xWindow = css::uno::Reference< css::awt::XWindow >();
    }
}

/*-****************************************************************************************************//**
	@short		send frame action event to our listener
	@descr		This method is threadsafe AND can be called by our dispose method too!

	@seealso	-

	@param		"aAction", describe the event for sending
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void Frame::implts_sendFrameActionEvent( const css::frame::FrameAction& aAction )
{
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Sometimes used by dispose() => soft exceptions!
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

	// Log informations about order of events to file!
	// (only activated in debug version!)
	LOG_FRAMEACTIONEVENT( "Frame", m_sName, aAction )

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    // Send css::frame::FrameAction event to all listener.
	// Get container for right listener.
    // FOLLOW LINES ARE THREADSAFE!!!
    // ( OInterfaceContainerHelper is synchronized with m_aListenerContainer! )
    ::cppu::OInterfaceContainerHelper* pContainer = m_aListenerContainer.getContainer( ::getCppuType( ( const css::uno::Reference< css::frame::XFrameActionListener >*) NULL ) );

	if( pContainer != NULL )
	{
		// Build action event.
        css::frame::FrameActionEvent aFrameActionEvent( static_cast< ::cppu::OWeakObject* >(this), this, aAction );

		// Get iterator for access to listener.
        ::cppu::OInterfaceIteratorHelper aIterator( *pContainer );
		// Send message to all listener.
        while( aIterator.hasMoreElements() == sal_True )
		{
            try
            {
                ((css::frame::XFrameActionListener*)aIterator.next())->frameAction( aFrameActionEvent );
            }
            catch( css::uno::RuntimeException& )
            {
                aIterator.remove();
            }
		}
	}
}

/*-****************************************************************************************************//**
	@short		helper to resize our component window
	@descr		A frame contains 2 windows - a container ~ and a component window.
				This method resize inner component window to full size of outer container window.
				This method is threadsafe AND can be called by our dispose method too!

	@seealso	-

	@param		-
	@return		-

	@onerror	-
*//*-*****************************************************************************************************/
void Frame::implts_resizeComponentWindow()
{
	// usually the LayoutManager does the resizing
    // in case there is no LayoutManager resizing has to be done here
    if ( !m_xLayoutManager.is() )
    {
        css::uno::Reference< css::awt::XWindow > xComponentWindow( getComponentWindow() );
        if( xComponentWindow.is() == sal_True )
        {
            css::uno::Reference< css::awt::XDevice > xDevice( getContainerWindow(), css::uno::UNO_QUERY );

            // Convert relativ size to output size.
            css::awt::Rectangle  aRectangle  = getContainerWindow()->getPosSize();
            css::awt::DeviceInfo aInfo       = xDevice->getInfo();
            css::awt::Size       aSize       (  aRectangle.Width  - aInfo.LeftInset - aInfo.RightInset  ,
                                                aRectangle.Height - aInfo.TopInset  - aInfo.BottomInset );

            // Resize our component window.
            xComponentWindow->setPosSize( 0, 0, aSize.Width, aSize.Height, css::awt::PosSize::POSSIZE );
        }
    }
}

/*-****************************************************************************************************//**
    @short      helper to set icon on our container window (if it is a system window!)
    @descr      We use our internal set controller (if it exist) to specify which factory he represanted.
                These information can be used to find right icon. But our controller can say it us directly
                too ... we should ask his optional property set first ...

    @seealso    method Window::SetIcon()

    @param      -
    @return     -

    @onerror    We do nothing.
*//*-*****************************************************************************************************/
void Frame::implts_setIconOnWindow()
{
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Look for rejected calls.
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

	/* SAFE AREA ----------------------------------------------------------------------------------------------- */
    // Make snapshot of neccessary members and release lock.
    ReadGuard aReadLock( m_aLock );
    css::uno::Reference< css::awt::XWindow >       xContainerWindow( m_xContainerWindow, css::uno::UNO_QUERY );
    css::uno::Reference< css::frame::XController > xController     ( m_xController     , css::uno::UNO_QUERY );
    aReadLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    if(
        ( xContainerWindow.is() == sal_True )   &&
        ( xController.is()      == sal_True )
      )
    {
        //-------------------------------------------------------------------------------------------------------------
        // a) set default value to an invalid one. So we can start further searches for right icon id, if
        //    first steps failed!
        //    We must reset it to any fallback value - if no search step returns a valid result.
        sal_Int32 nIcon = -1;

        //-------------------------------------------------------------------------------------------------------------
        // b) try to find information on controller propertyset directly
        //    Don't forget to catch possible exceptions - because these property is an optional one!
        css::uno::Reference< css::beans::XPropertySet > xSet( xController, css::uno::UNO_QUERY );
        if( xSet.is() == sal_True )
        {
            try
            {
                css::uno::Reference< css::beans::XPropertySetInfo > const xPSI( xSet->getPropertySetInfo(), css::uno::UNO_SET_THROW );
                if ( xPSI->hasPropertyByName( CONTROLLER_PROPNAME_ICONID ) )
                    xSet->getPropertyValue( CONTROLLER_PROPNAME_ICONID ) >>= nIcon;
            }
            catch( css::uno::Exception& )
            {
                DBG_UNHANDLED_EXCEPTION();
            }
        }

        //-------------------------------------------------------------------------------------------------------------
        // c) if b) failed ... analyze argument list of currently loaded document insde the frame to find the filter.
        //    He can be used to detect right factory - and these can be used to match factory to icon ...
        if( nIcon == -1 )
        {
            css::uno::Reference< css::frame::XModel > xModel = xController->getModel();
            if( xModel.is() == sal_True )
            {
                SvtModuleOptions::EFactory eFactory = SvtModuleOptions::ClassifyFactoryByModel(xModel);
                if (eFactory != SvtModuleOptions::E_UNKNOWN_FACTORY)
                    nIcon = SvtModuleOptions().GetFactoryIcon( eFactory );
            }
        }

        //-------------------------------------------------------------------------------------------------------------
        // d) if all steps failed - use fallback!
        if( nIcon == -1 )
        {
            nIcon = 0;
        }

        //-------------------------------------------------------------------------------------------------------------
        // e) set icon on container window now
        //    Don't forget SolarMutex! We use vcl directly :-(
        //    Check window pointer for right WorkWindow class too!!!
        /* SAFE AREA ----------------------------------------------------------------------------------------------- */
        ::vos::OClearableGuard aSolarGuard( Application::GetSolarMutex() );
        Window* pWindow = (VCLUnoHelper::GetWindow( xContainerWindow ));
        if(
            ( pWindow            != NULL              ) &&
            ( pWindow->GetType() == WINDOW_WORKWINDOW )
        )
        {
            WorkWindow* pWorkWindow = (WorkWindow*)pWindow;
            pWorkWindow->SetIcon( (sal_uInt16)nIcon );
        }
        aSolarGuard.clear();
        /* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    }
}

/*-************************************************************************************************************//**
    @short      helper to start/stop listeneing for window events on container window
    @descr      If we get a new container window, we must set it on internal memeber ...
                and stop listening at old one ... and start listening on new one!
                But sometimes (in dispose() call!) it's neccessary to stop listeneing without starting
                on new connections. So we split this functionality to make it easier at use.

    @seealso    method initialize()
    @seealso    method dispose()

    @param      -
    @return     -

    @onerror    We do nothing!
    @threadsafe yes
*//*-*************************************************************************************************************/
void Frame::implts_startWindowListening()
{
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    TransactionGuard aTransaction( m_aTransactionManager, E_HARDEXCEPTIONS );

    /* SAFE AREA ----------------------------------------------------------------------------------------------- */
    // Make snapshot of neccessary member!
    ReadGuard aReadLock( m_aLock );
    css::uno::Reference< css::awt::XWindow >                            xContainerWindow    = m_xContainerWindow   ;
    css::uno::Reference< css::lang::XMultiServiceFactory >              xFactory            = m_xFactory           ;
    css::uno::Reference< css::datatransfer::dnd::XDropTargetListener >  xDragDropListener   = m_xDropTargetListener;
    css::uno::Reference< css::awt::XWindowListener >                    xWindowListener     ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    css::uno::Reference< css::awt::XFocusListener >                     xFocusListener      ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    css::uno::Reference< css::awt::XTopWindowListener >                 xTopWindowListener  ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    aReadLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    if( xContainerWindow.is() == sal_True )
    {
        xContainerWindow->addWindowListener( xWindowListener);
        xContainerWindow->addFocusListener ( xFocusListener );

        css::uno::Reference< css::awt::XTopWindow > xTopWindow( xContainerWindow, css::uno::UNO_QUERY );
        if( xTopWindow.is() == sal_True )
        {
            xTopWindow->addTopWindowListener( xTopWindowListener );

            css::uno::Reference< css::awt::XDataTransferProviderAccess > xTransfer( xFactory->createInstance( SERVICENAME_VCLTOOLKIT ), css::uno::UNO_QUERY );
            if( xTransfer.is() == sal_True )
			{
                css::uno::Reference< css::datatransfer::dnd::XDropTarget > xDropTarget = xTransfer->getDropTarget( xContainerWindow );
                if( xDropTarget.is() == sal_True )
				{
                    xDropTarget->addDropTargetListener( xDragDropListener );
					xDropTarget->setActive( sal_True );
				}
			}
		}
    }
}

//*****************************************************************************************************************
void Frame::implts_stopWindowListening()
{
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */
    // Sometimes used by dispose() => soft exceptions!
    TransactionGuard aTransaction( m_aTransactionManager, E_SOFTEXCEPTIONS );

    /* SAFE AREA ----------------------------------------------------------------------------------------------- */
    // Make snapshot of neccessary member!
    ReadGuard aReadLock( m_aLock );
    css::uno::Reference< css::awt::XWindow >                            xContainerWindow    = m_xContainerWindow   ;
    css::uno::Reference< css::lang::XMultiServiceFactory >              xFactory            = m_xFactory           ;
    css::uno::Reference< css::datatransfer::dnd::XDropTargetListener >  xDragDropListener   = m_xDropTargetListener;
    css::uno::Reference< css::awt::XWindowListener >                    xWindowListener     ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    css::uno::Reference< css::awt::XFocusListener >                     xFocusListener      ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    css::uno::Reference< css::awt::XTopWindowListener >                 xTopWindowListener  ( static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY );
    aReadLock.unlock();
    /* UNSAFE AREA --------------------------------------------------------------------------------------------- */

    if( xContainerWindow.is() == sal_True )
    {
        xContainerWindow->removeWindowListener( xWindowListener);
        xContainerWindow->removeFocusListener ( xFocusListener );

        css::uno::Reference< css::awt::XTopWindow > xTopWindow( xContainerWindow, css::uno::UNO_QUERY );
        if( xTopWindow.is() == sal_True )
        {
            xTopWindow->removeTopWindowListener( xTopWindowListener );

            css::uno::Reference< css::awt::XDataTransferProviderAccess > xTransfer( xFactory->createInstance( SERVICENAME_VCLTOOLKIT ), css::uno::UNO_QUERY );
            if( xTransfer.is() == sal_True )
			{
                css::uno::Reference< css::datatransfer::dnd::XDropTarget > xDropTarget = xTransfer->getDropTarget( xContainerWindow );
                if( xDropTarget.is() == sal_True )
				{
                    xDropTarget->removeDropTargetListener( xDragDropListener );
					xDropTarget->setActive( sal_False );
				}
			}
        }
    }
}

/*-****************************************************************************************************//**
    @short      helper to force breaked close() request again
    @descr      If we self disagree with a close() request, and detect that all external locks are gone ...
                then we must try to close this frame again.

    @seealso    XCloseable::close()
    @seealso    Frame::close()
    @seealso    Frame::removeActionLock()
    @seealso    Frame::resetActionLock()
    @seealso    m_bSelfClose
    @seealso    m_nExternalLockCount

    @threadsafe yes
    @modified   06.05.2002 09:31, as96863
*//*-*****************************************************************************************************/
void Frame::implts_checkSuicide()
{
    /* SAFE */
    ReadGuard aReadLock(m_aLock);
    // in case of lock==0 and safed state of previous close() request m_bSelfClose
    // we must force close() again. Because we had disagreed with that before.
    sal_Bool bSuicide = (m_nExternalLockCount==0 && m_bSelfClose);
    m_bSelfClose = sal_False;
    aReadLock.unlock();
    /* } SAFE */
    // force close and deliver owner ship to source of possible throwed veto exception
    // Attention: Because this method isn't designed to throw such exception we must supress
    // it for outside code!
    try
    {
        if (bSuicide)
            close(sal_True);
    }
    catch(const css::util::CloseVetoException&)
        {}
    catch(const css::lang::DisposedException&)
        {}
}

//_______________________________________________________________

/** little helper to enable/disable the menu closer at the menubar of the given frame.

    @param  xFrame
            we use its layout manager to set/reset a special callback.
            Its existence regulate visibility of this closer item.

    @param  bState
                <TRUE/> enable; <FALSE/> disable this state
 */

void Frame::impl_setCloser( /*IN*/ const css::uno::Reference< css::frame::XFrame >& xFrame ,
                            /*IN*/       sal_Bool                                   bState  )
{
    // Note: If start module isnt installed - no closer has to be shown!
    if (!SvtModuleOptions().IsModuleInstalled(SvtModuleOptions::E_SSTARTMODULE))
        return;

    try
    {
        css::uno::Reference< css::beans::XPropertySet > xFrameProps(xFrame, css::uno::UNO_QUERY_THROW);
        css::uno::Reference< css::frame::XLayoutManager > xLayoutManager;
        xFrameProps->getPropertyValue(FRAME_PROPNAME_LAYOUTMANAGER) >>= xLayoutManager;
        css::uno::Reference< css::beans::XPropertySet > xLayoutProps(xLayoutManager, css::uno::UNO_QUERY_THROW);
        xLayoutProps->setPropertyValue(LAYOUTMANAGER_PROPNAME_MENUBARCLOSER, css::uno::makeAny(bState));
    }
    catch(const css::uno::RuntimeException&)
        { throw; }
    catch(const css::uno::Exception&)
        {}
}

//_______________________________________________________________

/** it checks, which of the top level task frames must have the special menu closer for
    switching to the backing window mode.

    It analyze the current list of visible top level frames. Only the last real document
    frame can have this symbol. Not the help frame nor the backing task itself.
    Here we do anything related to this closer. We remove it from the old frame and set it
    for the new one.
 */

void Frame::impl_checkMenuCloser()
{
    /* SAFE { */
    ReadGuard aReadLock(m_aLock);

    // only top frames, which are part of our desktop hierarchy, can
    // do so! By the way - we need the desktop instance to have acess
    // to all other top level frames too.
    css::uno::Reference< css::frame::XDesktop >        xDesktop     (m_xParent, css::uno::UNO_QUERY);
    css::uno::Reference< css::frame::XFramesSupplier > xTaskSupplier(xDesktop , css::uno::UNO_QUERY);
    if ( !xDesktop.is() || !xTaskSupplier.is() )
        return;

    aReadLock.unlock();
    /* } SAFE */

    // analyze the list of current open tasks
    // Suppress search for other views to the same model ...
    // It's not needed here and can be very expensive.
    FrameListAnalyzer aAnalyzer(
        xTaskSupplier,
        this,
        FrameListAnalyzer::E_HIDDEN | FrameListAnalyzer::E_HELP | FrameListAnalyzer::E_BACKINGCOMPONENT);

    // specify the new frame, which must have this special state ...
    css::uno::Reference< css::frame::XFrame > xNewCloserFrame;

    // -----------------------------
    // a)
    // If there exist ate least one other frame - there are two frames currently open.
    // But we can enable this closer only, if one of these two tasks includes the help module.
    // The "other frame" couldn't be the help. Because then it wouldn't be part of this "other list".
    // In such case it will be seperated to the reference aAnalyzer.m_xHelp!
    // But we must check, if weself includes the help ...
    // Check aAnalyzer.m_bReferenceIsHelp!
    if (
        (aAnalyzer.m_lOtherVisibleFrames.getLength()==1)   &&
        (
            (aAnalyzer.m_bReferenceIsHelp  ) ||
            (aAnalyzer.m_bReferenceIsHidden)
        )
       )
    {
        // others[0] can't be the backing component!
        // Because it's set at the special member aAnalyzer.m_xBackingComponent ... :-)
        xNewCloserFrame = aAnalyzer.m_lOtherVisibleFrames[0];
    }
    else
    // -----------------------------
    // b)
    // There is no other frame ... means no other document frame. The help module
    // will be handled seperatly and must(!) be ignored here ... excepting weself includes the help.
    if (
        (aAnalyzer.m_lOtherVisibleFrames.getLength()==0) &&
        (!aAnalyzer.m_bReferenceIsHelp                 ) &&
        (!aAnalyzer.m_bReferenceIsHidden               ) &&
        (!aAnalyzer.m_bReferenceIsBacking              )
       )
    {
        xNewCloserFrame = this;
    }

    // Look for neccessary actions ...
    // Only if the closer state must be moved from one frame to another one
    // or must be enabled/disabled at all.
    /* STATIC SAFE { */
    WriteGuard aStaticWriteLock(LockHelper::getGlobalLock());
    css::uno::Reference< css::frame::XFrame > xCloserFrame (m_xCloserFrame.get(), css::uno::UNO_QUERY);
    if (xCloserFrame!=xNewCloserFrame)
    {
        if (xCloserFrame.is())
            impl_setCloser(xCloserFrame, sal_False);
        if (xNewCloserFrame.is())
            impl_setCloser(xNewCloserFrame, sal_True);
        m_xCloserFrame = xNewCloserFrame;
    }
    aStaticWriteLock.unlock();
    /* } STATIC SAFE */
}

//_________________________________________________________________________________________________________________
//	debug methods
//_________________________________________________________________________________________________________________

/*-----------------------------------------------------------------------------------------------------------------
	The follow methods checks the parameter for other functions. If a parameter or his value is non valid,
    we return "sal_True". (otherwise sal_False) This mechanism is used to throw an ASSERT!
-----------------------------------------------------------------------------------------------------------------*/

#ifdef ENABLE_ASSERTIONS

//*****************************************************************************************************************
// We don't accept null pointer or references!
sal_Bool Frame::implcp_ctor( const css::uno::Reference< css::lang::XMultiServiceFactory >& xFactory )
{
	return	(
				( &xFactory		==	NULL		)	||
				( xFactory.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
// Its allowed to reset the active frame membervariable with a NULL-css::uno::Reference but not with a NULL-pointer!
// And we accept frames only! No tasks and desktops!
sal_Bool Frame::implcp_setActiveFrame( const css::uno::Reference< css::frame::XFrame >& xFrame )
{
	return	(
                ( &xFrame                                                                                   ==  NULL        )   ||
                ( css::uno::Reference< css::frame::XDesktop >( xFrame, css::uno::UNO_QUERY ).is()           ==  sal_True    )
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_addFrameActionListener( const css::uno::Reference< css::frame::XFrameActionListener >& xListener )
{
	return	(
				( &xListener		==	NULL		)	||
				( xListener.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_removeFrameActionListener( const css::uno::Reference< css::frame::XFrameActionListener >& xListener )
{
	return	(
				( &xListener		==	NULL		)	||
				( xListener.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_addEventListener( const css::uno::Reference< css::lang::XEventListener >& xListener )
{
	return	(
				( &xListener		==	NULL		)	||
				( xListener.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_removeEventListener( const css::uno::Reference< css::lang::XEventListener >& xListener )
{
	return	(
				( &xListener		==	NULL		)	||
				( xListener.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_windowResized( const css::awt::WindowEvent& aEvent )
{
	return	(
				( &aEvent				==	NULL		)	||
				( aEvent.Source.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_focusGained( const css::awt::FocusEvent& aEvent )
{
	return	(
				( &aEvent				==	NULL		)	||
				( aEvent.Source.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_windowActivated( const css::lang::EventObject& aEvent )
{
	return	(
				( &aEvent				==	NULL		)	||
				( aEvent.Source.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_windowDeactivated( const css::lang::EventObject& aEvent )
{
	return	(
				( &aEvent				==	NULL		)	||
				( aEvent.Source.is()	==	sal_False	)
			);
}

//*****************************************************************************************************************
sal_Bool Frame::implcp_disposing( const css::lang::EventObject& aEvent )
{
	return	(
				( &aEvent				==	NULL		)	||
				( aEvent.Source.is()	==	sal_False	)
			);
}

#endif	// #ifdef ENABLE_ASSERTIONS

}	// namespace framework
