merge the formfield patch from ooo-build
[ooovba.git] / sc / source / ui / view / tabvwshb.cxx
blobb9a5a589227a2b7cbeaad930daa24f0e62d27668
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: tabvwshb.cxx,v $
10 * $Revision: 1.39.128.1 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_sc.hxx"
33 #include <com/sun/star/embed/NoVisualAreaSizeException.hpp>
34 #include <com/sun/star/chart2/data/XDataReceiver.hpp>
38 //------------------------------------------------------------------
40 #ifdef _MSC_VER
41 #pragma optimize ("", off)
42 #endif
44 // INCLUDE ---------------------------------------------------------------
46 #include <com/sun/star/embed/EmbedMisc.hpp>
47 #include <com/sun/star/embed/EmbedStates.hpp>
48 #include <sfx2/app.hxx>
49 #include <toolkit/helper/vclunohelper.hxx>
50 #include <svx/svxdlg.hxx>
51 #include <svx/dataaccessdescriptor.hxx>
52 #include <svx/pfiledlg.hxx>
53 #include <svx/svditer.hxx>
54 #include <svx/svdmark.hxx>
55 #include <svx/svdograf.hxx>
56 #include <svx/svdogrp.hxx>
57 #include <svx/svdoole2.hxx>
58 #include <svx/svdouno.hxx>
59 #include <svx/svdview.hxx>
60 #include <svx/linkmgr.hxx>
61 #include <svx/fontworkbar.hxx>
62 #include <sfx2/bindings.hxx>
63 #include <sfx2/dispatch.hxx>
64 #include <sfx2/viewfrm.hxx>
65 #include <svtools/soerr.hxx>
66 #include <svtools/rectitem.hxx>
67 #include <svtools/whiter.hxx>
68 #include <svtools/moduleoptions.hxx>
69 #include <sot/exchange.hxx>
71 #include "tabvwsh.hxx"
72 #include "globstr.hrc"
73 #include "scmod.hxx"
74 #include "document.hxx"
75 #include "sc.hrc"
76 #include "client.hxx"
77 #include "fuinsert.hxx"
78 #include "docsh.hxx"
79 #include "chartarr.hxx"
80 #include "drawview.hxx"
81 #include "ChartRangeSelectionListener.hxx"
83 using namespace com::sun::star;
85 // STATIC DATA -----------------------------------------------------------
87 void ScTabViewShell::ConnectObject( SdrOle2Obj* pObj )
89 // wird aus dem Paint gerufen
91 uno::Reference < embed::XEmbeddedObject > xObj = pObj->GetObjRef();
92 Window* pWin = GetActiveWin();
94 // #41412# wenn schon connected ist, nicht nochmal SetObjArea/SetSizeScale
96 SfxInPlaceClient* pClient = FindIPClient( xObj, pWin );
97 if ( !pClient )
99 pClient = new ScClient( this, pWin, GetSdrView()->GetModel(), pObj );
100 Rectangle aRect = pObj->GetLogicRect();
101 Size aDrawSize = aRect.GetSize();
103 Size aOleSize = pObj->GetOrigObjSize();
105 Fraction aScaleWidth (aDrawSize.Width(), aOleSize.Width() );
106 Fraction aScaleHeight(aDrawSize.Height(), aOleSize.Height() );
107 aScaleWidth.ReduceInaccurate(10); // kompatibel zum SdrOle2Obj
108 aScaleHeight.ReduceInaccurate(10);
109 pClient->SetSizeScale(aScaleWidth,aScaleHeight);
111 // sichtbarer Ausschnitt wird nur inplace veraendert!
112 // the object area must be set after the scaling since it triggers the resizing
113 aRect.SetSize( aOleSize );
114 pClient->SetObjArea( aRect );
116 ((ScClient*)pClient)->SetGrafEdit( NULL );
120 BOOL ScTabViewShell::ActivateObject( SdrOle2Obj* pObj, long nVerb )
122 // #41081# Gueltigkeits-Hinweisfenster nicht ueber dem Objekt stehenlassen
123 RemoveHintWindow();
125 uno::Reference < embed::XEmbeddedObject > xObj = pObj->GetObjRef();
126 Window* pWin = GetActiveWin();
127 ErrCode nErr = ERRCODE_NONE;
128 BOOL bErrorShown = FALSE;
130 // linked objects aren't supported
131 // if ( xIPObj->IsLink() )
132 // nErr = xIPObj->DoVerb(nVerb); // gelinkt -> ohne Client etc.
133 // else
135 SfxInPlaceClient* pClient = FindIPClient( xObj, pWin );
136 if ( !pClient )
137 pClient = new ScClient( this, pWin, GetSdrView()->GetModel(), pObj );
139 if ( !(nErr & ERRCODE_ERROR_MASK) && xObj.is() )
141 Rectangle aRect = pObj->GetLogicRect();
142 Size aDrawSize = aRect.GetSize();
144 MapMode aMapMode( MAP_100TH_MM );
145 Size aOleSize = pObj->GetOrigObjSize( &aMapMode );
147 if ( pClient->GetAspect() != embed::Aspects::MSOLE_ICON
148 && ( xObj->getStatus( pClient->GetAspect() ) & embed::EmbedMisc::MS_EMBED_RECOMPOSEONRESIZE ) )
150 // scale must always be 1 - change VisArea if different from client size
152 if ( aDrawSize != aOleSize )
154 MapUnit aUnit = VCLUnoHelper::UnoEmbed2VCLMapUnit( xObj->getMapUnit( pClient->GetAspect() ) );
155 aOleSize = OutputDevice::LogicToLogic( aDrawSize,
156 MAP_100TH_MM, aUnit );
157 awt::Size aSz( aOleSize.Width(), aOleSize.Height() );
158 xObj->setVisualAreaSize( pClient->GetAspect(), aSz );
160 Fraction aOne( 1, 1 );
161 pClient->SetSizeScale( aOne, aOne );
163 else
165 // calculate scale from client and VisArea size
167 Fraction aScaleWidth (aDrawSize.Width(), aOleSize.Width() );
168 Fraction aScaleHeight(aDrawSize.Height(), aOleSize.Height() );
169 aScaleWidth.ReduceInaccurate(10); // kompatibel zum SdrOle2Obj
170 aScaleHeight.ReduceInaccurate(10);
171 pClient->SetSizeScale(aScaleWidth,aScaleHeight);
174 // sichtbarer Ausschnitt wird nur inplace veraendert!
175 // the object area must be set after the scaling since it triggers the resizing
176 aRect.SetSize( aOleSize );
177 pClient->SetObjArea( aRect );
179 ((ScClient*)pClient)->SetGrafEdit( NULL );
181 nErr = pClient->DoVerb( nVerb );
182 bErrorShown = TRUE;
183 // SfxViewShell::DoVerb zeigt seine Fehlermeldungen selber an
185 // attach listener to selection changes in chart that affect cell
186 // ranges, so those can be highlighted
187 // note: do that after DoVerb, so that the chart controller exists
188 if ( SvtModuleOptions().IsChart() )
190 SvGlobalName aObjClsId ( xObj->getClassID() );
191 if (SotExchange::IsChart( aObjClsId ))
195 uno::Reference < embed::XComponentSupplier > xSup( xObj, uno::UNO_QUERY_THROW );
196 uno::Reference< chart2::data::XDataReceiver > xDataReceiver(
197 xSup->getComponent(), uno::UNO_QUERY_THROW );
198 uno::Reference< chart2::data::XRangeHighlighter > xRangeHightlighter(
199 xDataReceiver->getRangeHighlighter());
200 if( xRangeHightlighter.is())
202 uno::Reference< view::XSelectionChangeListener > xListener(
203 new ScChartRangeSelectionListener( this ));
204 xRangeHightlighter->addSelectionChangeListener( xListener );
207 catch( const uno::Exception & )
209 DBG_ERROR( "Exception caught while querying chart" );
215 if (nErr != ERRCODE_NONE && !bErrorShown)
216 ErrorHandler::HandleError(nErr);
218 //! SetDocumentName sollte schon im Sfx passieren ???
219 //TODO/LATER: how "SetDocumentName"?
220 //xIPObj->SetDocumentName( GetViewData()->GetDocShell()->GetTitle() );
222 return ( !(nErr & ERRCODE_ERROR_MASK) );
225 ErrCode __EXPORT ScTabViewShell::DoVerb(long nVerb)
227 SdrView* pView = GetSdrView();
228 if (!pView)
229 return ERRCODE_SO_NOTIMPL; // soll nicht sein
231 SdrOle2Obj* pOle2Obj = NULL;
232 SdrGrafObj* pGrafObj = NULL;
233 SdrObject* pObj = NULL;
234 ErrCode nErr = ERRCODE_NONE;
236 const SdrMarkList& rMarkList = pView->GetMarkedObjectList();
237 if (rMarkList.GetMarkCount() == 1)
239 pObj = rMarkList.GetMark(0)->GetMarkedSdrObj();
240 if (pObj->GetObjIdentifier() == OBJ_OLE2)
241 pOle2Obj = (SdrOle2Obj*) pObj;
242 else if (pObj->GetObjIdentifier() == OBJ_GRAF)
244 pGrafObj = (SdrGrafObj*) pObj;
248 if (pOle2Obj)
250 ActivateObject( pOle2Obj, nVerb );
252 else
254 DBG_ERROR("kein Objekt fuer Verb gefunden");
257 return nErr;
260 void ScTabViewShell::DeactivateOle()
262 // deactivate inplace editing if currently active
264 ScModule* pScMod = SC_MOD();
265 bool bUnoRefDialog = pScMod->IsRefDialogOpen() && pScMod->GetCurRefDlgId() == WID_SIMPLE_REF;
267 ScClient* pClient = (ScClient*) GetIPClient();
268 if ( pClient && pClient->IsObjectInPlaceActive() && !bUnoRefDialog )
269 pClient->DeactivateObject();
272 void ScTabViewShell::ExecDrawIns(SfxRequest& rReq)
274 USHORT nSlot = rReq.GetSlot();
275 if (nSlot != SID_OBJECTRESIZE )
277 SC_MOD()->InputEnterHandler();
278 UpdateInputHandler();
281 // Rahmen fuer Chart einfuegen wird abgebrochen:
282 FuPoor* pPoor = GetDrawFuncPtr();
283 if ( pPoor && pPoor->GetSlotID() == SID_DRAW_CHART )
284 GetViewData()->GetDispatcher().Execute(SID_DRAW_CHART, SFX_CALLMODE_SLOT | SFX_CALLMODE_RECORD);
286 MakeDrawLayer();
288 SfxBindings& rBindings = GetViewFrame()->GetBindings();
289 ScTabView* pTabView = GetViewData()->GetView();
290 Window* pWin = pTabView->GetActiveWin();
291 ScDrawView* pView = pTabView->GetScDrawView();
292 ScDocShell* pDocSh = GetViewData()->GetDocShell();
293 ScDocument* pDoc = pDocSh->GetDocument();
294 // SdrModel* pDrModel = pDocSh->MakeDrawLayer();
295 SdrModel* pDrModel = pView->GetModel();
297 switch ( nSlot )
299 case SID_INSERT_GRAPHIC:
300 FuInsertGraphic(this, pWin, pView, pDrModel, rReq);
301 // shell is set in MarkListHasChanged
302 break;
304 case SID_INSERT_AVMEDIA:
305 FuInsertMedia(this, pWin, pView, pDrModel, rReq);
306 // shell is set in MarkListHasChanged
307 break;
309 case SID_INSERT_DIAGRAM:
310 FuInsertChart(this, pWin, pView, pDrModel, rReq);
311 //? SC_MOD()->SetFunctionDlg( NULL );//XXX
312 break;
314 case SID_INSERT_OBJECT:
315 case SID_INSERT_PLUGIN:
316 case SID_INSERT_SOUND:
317 case SID_INSERT_VIDEO:
318 case SID_INSERT_APPLET:
319 case SID_INSERT_SMATH:
320 case SID_INSERT_FLOATINGFRAME:
321 FuInsertOLE(this, pWin, pView, pDrModel, rReq);
322 break;
324 case SID_OBJECTRESIZE:
326 // Der Server moechte die Clientgrosse verandern
328 SfxInPlaceClient* pClient = GetIPClient();
330 if ( pClient && pClient->IsObjectInPlaceActive() )
332 const SfxRectangleItem& rRect =
333 (SfxRectangleItem&)rReq.GetArgs()->Get(SID_OBJECTRESIZE);
334 Rectangle aRect( pWin->PixelToLogic( rRect.GetValue() ) );
336 if ( pView->AreObjectsMarked() )
338 const SdrMarkList& rMarkList = pView->GetMarkedObjectList();
340 if (rMarkList.GetMarkCount() == 1)
342 SdrMark* pMark = rMarkList.GetMark(0);
343 SdrObject* pObj = pMark->GetMarkedSdrObj();
345 UINT16 nSdrObjKind = pObj->GetObjIdentifier();
347 if (nSdrObjKind == OBJ_OLE2)
349 if ( ( (SdrOle2Obj*) pObj)->GetObjRef().is() )
351 pObj->SetLogicRect(aRect);
358 break;
360 case SID_LINKS:
362 SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
363 SfxAbstractLinksDialog* pDlg = pFact->CreateLinksDialog( pWin, pDoc->GetLinkManager() );
364 if ( pDlg )
366 pDlg->Execute();
367 rBindings.Invalidate( nSlot );
368 SFX_APP()->Broadcast( SfxSimpleHint( SC_HINT_AREALINKS_CHANGED ) ); // Navigator
369 rReq.Done();
372 break;
374 // #98721#
375 case SID_FM_CREATE_FIELDCONTROL:
377 SFX_REQUEST_ARG( rReq, pDescriptorItem, SfxUnoAnyItem, SID_FM_DATACCESS_DESCRIPTOR, sal_False );
378 DBG_ASSERT( pDescriptorItem, "SID_FM_CREATE_FIELDCONTROL: invalid request args!" );
380 if(pDescriptorItem)
382 //! merge with ScViewFunc::PasteDataFormat (SOT_FORMATSTR_ID_SBA_FIELDDATAEXCHANGE)?
384 ScDrawView* pDrView = GetScDrawView();
385 SdrPageView* pPageView = pDrView ? pDrView->GetSdrPageView() : NULL;
386 if(pPageView)
388 ::svx::ODataAccessDescriptor aDescriptor(pDescriptorItem->GetValue());
389 SdrObject* pNewDBField = pDrView->CreateFieldControl(aDescriptor);
391 if(pNewDBField)
393 Rectangle aVisArea = pWin->PixelToLogic(Rectangle(Point(0,0), pWin->GetOutputSizePixel()));
394 Point aObjPos(aVisArea.Center());
395 Size aObjSize(pNewDBField->GetLogicRect().GetSize());
396 aObjPos.X() -= aObjSize.Width() / 2;
397 aObjPos.Y() -= aObjSize.Height() / 2;
398 Rectangle aNewObjectRectangle(aObjPos, aObjSize);
400 pNewDBField->SetLogicRect(aNewObjectRectangle);
402 // controls must be on control layer, groups on front layer
403 if ( pNewDBField->ISA(SdrUnoObj) )
404 pNewDBField->NbcSetLayer(SC_LAYER_CONTROLS);
405 else
406 pNewDBField->NbcSetLayer(SC_LAYER_FRONT);
407 if (pNewDBField->ISA(SdrObjGroup))
409 SdrObjListIter aIter( *pNewDBField, IM_DEEPWITHGROUPS );
410 SdrObject* pSubObj = aIter.Next();
411 while (pSubObj)
413 if ( pSubObj->ISA(SdrUnoObj) )
414 pSubObj->NbcSetLayer(SC_LAYER_CONTROLS);
415 else
416 pSubObj->NbcSetLayer(SC_LAYER_FRONT);
417 pSubObj = aIter.Next();
421 pView->InsertObjectAtView(pNewDBField, *pPageView);
425 rReq.Done();
427 break;
429 case SID_FONTWORK_GALLERY_FLOATER:
430 svx::FontworkBar::execute( pView, rReq, GetViewFrame()->GetBindings() );
431 rReq.Ignore();
432 break;
436 void ScTabViewShell::GetDrawInsState(SfxItemSet &rSet)
438 BOOL bOle = GetViewFrame()->GetFrame()->IsInPlace();
439 BOOL bTabProt = GetViewData()->GetDocument()->IsTabProtected(GetViewData()->GetTabNo());
440 ScDocShell* pDocShell = ( GetViewData() ? GetViewData()->GetDocShell() : NULL );
441 bool bShared = ( pDocShell ? pDocShell->IsDocShared() : false );
443 SfxWhichIter aIter(rSet);
444 USHORT nWhich = aIter.FirstWhich();
445 while ( nWhich )
447 switch ( nWhich )
449 case SID_INSERT_DIAGRAM:
450 if ( bOle || bTabProt || !SvtModuleOptions().IsChart() || bShared )
451 rSet.DisableItem( nWhich );
452 break;
454 case SID_INSERT_SMATH:
455 if ( bOle || bTabProt || !SvtModuleOptions().IsMath() || bShared )
456 rSet.DisableItem( nWhich );
457 break;
459 case SID_INSERT_OBJECT:
460 case SID_INSERT_PLUGIN:
461 case SID_INSERT_FLOATINGFRAME:
462 if ( bOle || bTabProt || bShared )
463 rSet.DisableItem( nWhich );
464 break;
466 case SID_INSERT_SOUND:
467 case SID_INSERT_VIDEO:
468 /* #i102735# discussed with NN: removed for performance reasons
469 || !SvxPluginFileDlg::IsAvailable(nWhich)
471 if ( bOle || bTabProt || bShared )
472 rSet.DisableItem( nWhich );
473 break;
475 case SID_INSERT_APPLET:
476 // wenn SOLAR_JAVA nicht definiert ist, immer disablen
477 #ifdef SOLAR_JAVA
478 if (bOle || bTabProt)
479 #endif
480 rSet.DisableItem( nWhich );
481 break;
483 case SID_INSERT_GRAPHIC:
484 case SID_INSERT_AVMEDIA:
485 case SID_FONTWORK_GALLERY_FLOATER:
486 if ( bTabProt || bShared )
487 rSet.DisableItem( nWhich );
488 break;
490 case SID_LINKS:
492 if (GetViewData()->GetDocument()->GetLinkManager()->GetLinks().Count() == 0 )
493 rSet.DisableItem( SID_LINKS );
495 break;
497 nWhich = aIter.NextWhich();