Bump version to 4.1-6
[LibreOffice.git] / sfx2 / source / view / frame2.cxx
blob71f578390ff65ad2d7c7adb41d490a5dc0c02d6f
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
21 #include "impframe.hxx"
22 #include "objshimp.hxx"
23 #include "sfx2/sfxhelp.hxx"
24 #include "workwin.hxx"
26 #include "sfx2/app.hxx"
27 #include "sfx2/bindings.hxx"
28 #include "sfx2/dispatch.hxx"
29 #include "sfx2/docfac.hxx"
30 #include "sfx2/docfile.hxx"
31 #include "sfx2/event.hxx"
32 #include "sfx2/objface.hxx"
33 #include "sfx2/request.hxx"
35 #include <com/sun/star/awt/XWindow2.hpp>
36 #include <com/sun/star/beans/XPropertySet.hpp>
37 #include <com/sun/star/frame/Desktop.hpp>
38 #include <com/sun/star/frame/XComponentLoader.hpp>
39 #include <com/sun/star/frame/Frame.hpp>
40 #include <com/sun/star/frame/XFramesSupplier.hpp>
41 #include <com/sun/star/frame/XLayoutManager.hpp>
43 #include <comphelper/componentcontext.hxx>
44 #include <comphelper/namedvaluecollection.hxx>
45 #include <comphelper/processfactory.hxx>
46 #include <svl/eitem.hxx>
47 #include <svl/intitem.hxx>
48 #include <svl/itemset.hxx>
49 #include <svl/rectitem.hxx>
50 #include <svl/stritem.hxx>
51 #include <toolkit/helper/vclunohelper.hxx>
52 #include <tools/diagnose_ex.h>
54 using namespace ::com::sun::star;
55 using namespace ::com::sun::star::uno;
56 using namespace ::com::sun::star::frame;
57 using namespace ::com::sun::star::util;
58 using namespace ::com::sun::star::container;
59 using namespace ::com::sun::star::beans;
60 using ::com::sun::star::lang::XMultiServiceFactory;
61 using ::com::sun::star::lang::XComponent;
62 using ::com::sun::star::frame::XComponentLoader;
64 //------------------------------------------------------------------------
66 class SfxFrameWindow_Impl : public Window
68 public:
69 SfxFrame* pFrame;
71 SfxFrameWindow_Impl( SfxFrame* pF, Window& i_rContainerWindow );
72 ~SfxFrameWindow_Impl( );
74 virtual void DataChanged( const DataChangedEvent& rDCEvt );
75 virtual void StateChanged( StateChangedType nStateChange );
76 virtual long PreNotify( NotifyEvent& rNEvt );
77 virtual long Notify( NotifyEvent& rEvt );
78 virtual void Resize();
79 virtual void GetFocus();
80 void DoResize();
83 SfxFrameWindow_Impl::SfxFrameWindow_Impl( SfxFrame* pF, Window& i_rContainerWindow )
84 : Window( &i_rContainerWindow, WB_BORDER | WB_CLIPCHILDREN | WB_NODIALOGCONTROL | WB_3DLOOK )
85 , pFrame( pF )
89 SfxFrameWindow_Impl::~SfxFrameWindow_Impl( )
93 void SfxFrameWindow_Impl::DataChanged( const DataChangedEvent& rDCEvt )
95 Window::DataChanged( rDCEvt );
96 SfxWorkWindow *pWorkWin = pFrame->GetWorkWindow_Impl();
97 if ( pWorkWin )
98 pWorkWin->DataChanged_Impl( rDCEvt );
101 long SfxFrameWindow_Impl::Notify( NotifyEvent& rNEvt )
103 if ( pFrame->IsClosing_Impl() || !pFrame->GetFrameInterface().is() )
104 return sal_False;
106 SfxViewFrame* pView = pFrame->GetCurrentViewFrame();
107 if ( !pView || !pView->GetObjectShell() )
108 return Window::Notify( rNEvt );
110 if ( rNEvt.GetType() == EVENT_GETFOCUS )
112 if ( pView->GetViewShell() && !pView->GetViewShell()->GetUIActiveIPClient_Impl() && !pFrame->IsInPlace() )
114 OSL_TRACE("SfxFrame: GotFocus");
115 pView->MakeActive_Impl( sal_False );
118 // if focus was on an external window, the clipboard content might have been changed
119 pView->GetBindings().Invalidate( SID_PASTE );
120 pView->GetBindings().Invalidate( SID_PASTE_SPECIAL );
121 return sal_True;
123 else if( rNEvt.GetType() == EVENT_KEYINPUT )
125 if ( pView->GetViewShell()->KeyInput( *rNEvt.GetKeyEvent() ) )
126 return sal_True;
128 else if ( rNEvt.GetType() == EVENT_EXECUTEDIALOG /*|| rNEvt.GetType() == EVENT_INPUTDISABLE*/ )
130 pView->SetModalMode( sal_True );
131 return sal_True;
133 else if ( rNEvt.GetType() == EVENT_ENDEXECUTEDIALOG /*|| rNEvt.GetType() == EVENT_INPUTENABLE*/ )
135 pView->SetModalMode( sal_False );
136 return sal_True;
139 return Window::Notify( rNEvt );
142 long SfxFrameWindow_Impl::PreNotify( NotifyEvent& rNEvt )
144 sal_uInt16 nType = rNEvt.GetType();
145 if ( nType == EVENT_KEYINPUT || nType == EVENT_KEYUP )
147 SfxViewFrame* pView = pFrame->GetCurrentViewFrame();
148 SfxViewShell* pShell = pView ? pView->GetViewShell() : NULL;
149 if ( pShell && pShell->HasKeyListeners_Impl() && pShell->HandleNotifyEvent_Impl( rNEvt ) )
150 return sal_True;
152 else if ( nType == EVENT_MOUSEBUTTONUP || nType == EVENT_MOUSEBUTTONDOWN )
154 Window* pWindow = rNEvt.GetWindow();
155 SfxViewFrame* pView = pFrame->GetCurrentViewFrame();
156 SfxViewShell* pShell = pView ? pView->GetViewShell() : NULL;
157 if ( pShell )
158 if ( pWindow == pShell->GetWindow() || pShell->GetWindow()->IsChild( pWindow ) )
159 if ( pShell->HasMouseClickListeners_Impl() && pShell->HandleNotifyEvent_Impl( rNEvt ) )
160 return sal_True;
163 if ( nType == EVENT_MOUSEBUTTONDOWN )
165 Window* pWindow = rNEvt.GetWindow();
166 const MouseEvent* pMEvent = rNEvt.GetMouseEvent();
167 Point aPos = pWindow->OutputToScreenPixel( pMEvent->GetPosPixel() );
168 SfxWorkWindow *pWorkWin = pFrame->GetWorkWindow_Impl();
169 if ( pWorkWin )
170 pWorkWin->EndAutoShow_Impl( aPos );
173 return Window::PreNotify( rNEvt );
176 void SfxFrameWindow_Impl::GetFocus()
178 if ( pFrame && !pFrame->IsClosing_Impl() && pFrame->GetCurrentViewFrame() && pFrame->GetFrameInterface().is() )
179 pFrame->GetCurrentViewFrame()->MakeActive_Impl( sal_True );
182 void SfxFrameWindow_Impl::Resize()
184 if ( IsReallyVisible() || IsReallyShown() || GetOutputSizePixel().Width() )
185 DoResize();
188 void SfxFrameWindow_Impl::StateChanged( StateChangedType nStateChange )
190 if ( nStateChange == STATE_CHANGE_INITSHOW )
192 pFrame->pImp->bHidden = sal_False;
193 if ( pFrame->IsInPlace() )
194 // TODO/MBA: workaround for bug in LayoutManager: the final resize does not get through because the
195 // LayoutManager works asynchronously and between resize and time execution the DockingAcceptor was exchanged so that
196 // the resize event never is sent to the component
197 SetSizePixel( GetParent()->GetOutputSizePixel() );
199 DoResize();
200 SfxViewFrame* pView = pFrame->GetCurrentViewFrame();
201 if ( pView )
202 pView->GetBindings().GetWorkWindow_Impl()->ShowChildren_Impl();
205 Window::StateChanged( nStateChange );
208 void SfxFrameWindow_Impl::DoResize()
210 if ( !pFrame->pImp->bLockResize )
211 pFrame->Resize();
214 Reference < XFrame > SfxFrame::CreateBlankFrame()
216 Reference < XFrame > xFrame;
219 Reference < XDesktop2 > xDesktop = Desktop::create( ::comphelper::getProcessComponentContext() );
220 xFrame.set( xDesktop->findFrame( "_blank", 0 ), UNO_SET_THROW );
222 catch( const Exception& )
224 DBG_UNHANDLED_EXCEPTION();
226 return xFrame;
229 SfxFrame* SfxFrame::Create( SfxObjectShell& rDoc, Window& rWindow, sal_uInt16 nViewId, bool bHidden )
231 SfxFrame* pFrame = NULL;
234 // create and initialize new top level frame for this window
235 Reference < XComponentContext > xContext( ::comphelper::getProcessComponentContext() );
236 Reference < XDesktop2 > xDesktop = Desktop::create( xContext );
237 Reference < XFrame2 > xFrame = Frame::create( xContext );
239 Reference< awt::XWindow2 > xWin( VCLUnoHelper::GetInterface ( &rWindow ), uno::UNO_QUERY_THROW );
240 xFrame->initialize( xWin.get() );
241 xDesktop->getFrames()->append( Reference<XFrame>(xFrame, uno::UNO_QUERY_THROW) );
243 if ( xWin->isActive() )
244 xFrame->activate();
246 // create load arguments
247 Sequence< PropertyValue > aLoadArgs;
248 TransformItems( SID_OPENDOC, *rDoc.GetMedium()->GetItemSet(), aLoadArgs );
250 ::comphelper::NamedValueCollection aArgs( aLoadArgs );
251 aArgs.put( "Model", rDoc.GetModel() );
252 aArgs.put( "Hidden", bHidden );
253 if ( nViewId )
254 aArgs.put( "ViewId", nViewId );
256 aLoadArgs = aArgs.getPropertyValues();
258 // load the doc into that frame
259 OUString sLoaderURL( "private:object" );
260 Reference< XComponentLoader > xLoader( xFrame, UNO_QUERY_THROW );
261 xLoader->loadComponentFromURL(
262 sLoaderURL,
263 OUString( "_self" ),
265 aLoadArgs
268 for ( pFrame = SfxFrame::GetFirst();
269 pFrame;
270 pFrame = SfxFrame::GetNext( *pFrame )
273 if ( pFrame->GetFrameInterface() == xFrame )
274 break;
277 OSL_ENSURE( pFrame, "SfxFrame::Create: load succeeded, but no SfxFrame was created during this!" );
279 catch( const Exception& )
281 DBG_UNHANDLED_EXCEPTION();
284 return pFrame;
287 SfxFrame* SfxFrame::Create( const Reference < XFrame >& i_rFrame )
289 // create a new TopFrame to an external XFrame object ( wrap controller )
290 ENSURE_OR_THROW( i_rFrame.is(), "NULL frame not allowed" );
291 Window* pWindow = VCLUnoHelper::GetWindow( i_rFrame->getContainerWindow() );
292 ENSURE_OR_THROW( pWindow, "frame without container window not allowed" );
294 SfxFrame* pFrame = new SfxFrame( *pWindow, false );
295 pFrame->SetFrameInterface_Impl( i_rFrame );
296 return pFrame;
299 SfxFrame::SfxFrame( Window& i_rContainerWindow, bool i_bHidden )
300 :pParentFrame( NULL )
301 ,pChildArr( NULL )
302 ,pImp( NULL )
303 ,pWindow( NULL )
305 Construct_Impl();
307 pImp->bHidden = i_bHidden;
308 InsertTopFrame_Impl( this );
309 pImp->pExternalContainerWindow = &i_rContainerWindow;
311 pWindow = new SfxFrameWindow_Impl( this, i_rContainerWindow );
313 // always show pWindow, which is the ComponentWindow of the XFrame we live in
314 // nowadays, since SfxFrames can be created with an XFrame only, hiding or showing the complete XFrame
315 // is not done at level of the container window, not at SFX level. Thus, the component window can
316 // always be visible.
317 pWindow->Show();
320 void SfxFrame::SetPresentationMode( sal_Bool bSet )
322 if ( GetCurrentViewFrame() )
323 GetCurrentViewFrame()->GetWindow().SetBorderStyle( bSet ? WINDOW_BORDER_NOBORDER : WINDOW_BORDER_NORMAL );
325 Reference< com::sun::star::beans::XPropertySet > xPropSet( GetFrameInterface(), UNO_QUERY );
326 Reference< ::com::sun::star::frame::XLayoutManager > xLayoutManager;
328 if ( xPropSet.is() )
330 Any aValue = xPropSet->getPropertyValue( OUString( "LayoutManager" ));
331 aValue >>= xLayoutManager;
334 if ( xLayoutManager.is() )
335 xLayoutManager->setVisible( !bSet ); // we don't want to have ui in presentation mode
337 SetMenuBarOn_Impl( !bSet );
338 if ( GetWorkWindow_Impl() )
339 GetWorkWindow_Impl()->SetDockingAllowed( !bSet );
340 if ( GetCurrentViewFrame() )
341 GetCurrentViewFrame()->GetDispatcher()->Update_Impl( sal_True );
344 SystemWindow* SfxFrame::GetSystemWindow() const
346 return GetTopWindow_Impl();
349 SystemWindow* SfxFrame::GetTopWindow_Impl() const
351 if ( pImp->pExternalContainerWindow->IsSystemWindow() )
352 return (SystemWindow*) pImp->pExternalContainerWindow;
353 else
354 return NULL;
357 Window& SfxFrame::GetWindow() const
359 return *pWindow;
362 sal_Bool SfxFrame::Close()
364 delete this;
365 return sal_True;
368 void SfxFrame::LockResize_Impl( sal_Bool bLock )
370 pImp->bLockResize = bLock;
373 void SfxFrame::SetMenuBarOn_Impl( sal_Bool bOn )
375 pImp->bMenuBarOn = bOn;
377 Reference< com::sun::star::beans::XPropertySet > xPropSet( GetFrameInterface(), UNO_QUERY );
378 Reference< ::com::sun::star::frame::XLayoutManager > xLayoutManager;
380 if ( xPropSet.is() )
382 Any aValue = xPropSet->getPropertyValue( OUString( "LayoutManager" ));
383 aValue >>= xLayoutManager;
386 if ( xLayoutManager.is() )
388 OUString aMenuBarURL( "private:resource/menubar/menubar" );
390 if ( bOn )
391 xLayoutManager->showElement( aMenuBarURL );
392 else
393 xLayoutManager->hideElement( aMenuBarURL );
397 sal_Bool SfxFrame::IsMenuBarOn_Impl() const
399 return pImp->bMenuBarOn;
402 void SfxFrame::PrepareForDoc_Impl( SfxObjectShell& i_rDoc )
404 const ::comphelper::NamedValueCollection aDocumentArgs( i_rDoc.GetModel()->getArgs() );
406 // hidden?
407 OSL_ENSURE( !pImp->bHidden, "when does this happen?" );
408 pImp->bHidden = aDocumentArgs.getOrDefault( "Hidden", pImp->bHidden );
410 // update our descriptor
411 UpdateDescriptor( &i_rDoc );
413 // plugin mode
414 sal_Int16 nPluginMode = aDocumentArgs.getOrDefault( "PluginMode", sal_Int16( 0 ) );
415 if ( nPluginMode && ( nPluginMode != 2 ) )
416 SetInPlace_Impl( sal_True );
419 bool SfxFrame::IsMarkedHidden_Impl() const
421 return pImp->bHidden;
424 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */