Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
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/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
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 .
18 : */
19 :
20 : #include "ChartModel.hxx"
21 : #include "servicenames.hxx"
22 : #include "MediaDescriptorHelper.hxx"
23 : #include "macros.hxx"
24 : #include "DataSourceHelper.hxx"
25 : #include "ChartModelHelper.hxx"
26 : #include "DiagramHelper.hxx"
27 : #include "DisposeHelper.hxx"
28 : #include "ControllerLockGuard.hxx"
29 : #include "ObjectIdentifier.hxx"
30 : #include "PageBackground.hxx"
31 : #include "CloneHelper.hxx"
32 : #include "NameContainer.hxx"
33 : #include "UndoManager.hxx"
34 : #include "ChartView.hxx"
35 : #include <svx/charthelper.hxx>
36 :
37 : #include <vcl/openglwin.hxx>
38 :
39 : #include <com/sun/star/chart/ChartDataRowSource.hpp>
40 :
41 : #include <comphelper/InlineContainer.hxx>
42 : #include <comphelper/processfactory.hxx>
43 :
44 : #include <svl/numuno.hxx>
45 : #include <com/sun/star/lang/DisposedException.hpp>
46 : #include <com/sun/star/lang/XInitialization.hpp>
47 : #include <com/sun/star/view/XSelectionSupplier.hpp>
48 : #include <com/sun/star/embed/XEmbedObjectCreator.hpp>
49 : #include <com/sun/star/embed/XEmbedPersist.hpp>
50 : #include <com/sun/star/embed/EmbedStates.hpp>
51 : #include <com/sun/star/embed/XComponentSupplier.hpp>
52 : #include <com/sun/star/embed/XStorage.hpp>
53 : #include <com/sun/star/embed/EmbedMapUnits.hpp>
54 : #include <com/sun/star/embed/Aspects.hpp>
55 : #include <com/sun/star/awt/Gradient.hpp>
56 : #include <com/sun/star/awt/XWindow.hpp>
57 : #include <com/sun/star/awt/PosSize.hpp>
58 : #include <com/sun/star/datatransfer/XTransferable.hpp>
59 : #include <com/sun/star/drawing/Hatch.hpp>
60 : #include <com/sun/star/drawing/LineDash.hpp>
61 : #include <com/sun/star/drawing/XShapes.hpp>
62 : #include <com/sun/star/document/DocumentProperties.hpp>
63 : #include <com/sun/star/chart2/XTimeBased.hpp>
64 :
65 : #include <svl/zforlist.hxx>
66 :
67 : using ::com::sun::star::uno::Sequence;
68 : using ::com::sun::star::uno::Reference;
69 : using ::com::sun::star::uno::RuntimeException;
70 : using ::com::sun::star::uno::Any;
71 : using ::osl::MutexGuard;
72 :
73 : using namespace ::com::sun::star;
74 : using namespace ::apphelper;
75 : using namespace ::chart::CloneHelper;
76 :
77 : namespace
78 : {
79 72 : const OUString lcl_aGDIMetaFileMIMEType(
80 36 : "application/x-openoffice-gdimetafile;windows_formatname=\"GDIMetaFile\"");
81 72 : const OUString lcl_aGDIMetaFileMIMETypeHighContrast(
82 36 : "application/x-openoffice-highcontrast-gdimetafile;windows_formatname=\"GDIMetaFile\"");
83 :
84 : } // anonymous namespace
85 :
86 : // ChartModel Constructor and Destructor
87 :
88 : namespace chart
89 : {
90 :
91 606 : ChartModel::ChartModel(uno::Reference<uno::XComponentContext > const & xContext)
92 : : m_aLifeTimeManager( this, this )
93 : , m_bReadOnly( false )
94 : , m_bModified( false )
95 : , m_nInLoad(0)
96 : , m_bUpdateNotificationsPending(false)
97 : , mbTimeBased(false)
98 : , mpChartView(NULL)
99 : , m_pUndoManager( NULL )
100 : , m_aControllers( m_aModelMutex )
101 : , m_nControllerLockCount(0)
102 : , m_xContext( xContext )
103 : , m_aVisualAreaSize( ChartModelHelper::getDefaultPageSize() )
104 : , m_xDataProvider( 0 )
105 : , m_xInternalDataProvider( 0 )
106 606 : , m_xPageBackground( new PageBackground( m_xContext ) )
107 606 : , m_xXMLNamespaceMap( createNameContainer( ::cppu::UnoType<OUString>::get(),
108 : "com.sun.star.xml.NamespaceMap", "com.sun.star.comp.chart.XMLNameSpaceMap" ), uno::UNO_QUERY)
109 : , mnStart(0)
110 : , mnEnd(0)
111 : ,bSet(false)
112 1818 : , mpOpenGLWindow(NULL)
113 : {
114 : OSL_TRACE( "ChartModel: CTOR called" );
115 :
116 606 : osl_atomic_increment(&m_refCount);
117 : {
118 : m_xOldModelAgg.set(
119 1212 : m_xContext->getServiceManager()->createInstanceWithContext(
120 : CHART_CHARTAPIWRAPPER_SERVICE_NAME,
121 606 : m_xContext ), uno::UNO_QUERY_THROW );
122 606 : m_xOldModelAgg->setDelegator( *this );
123 : }
124 :
125 : {
126 606 : ModifyListenerHelper::addListener( m_xPageBackground, this );
127 1212 : m_xChartTypeManager.set( xContext->getServiceManager()->createInstanceWithContext(
128 606 : "com.sun.star.chart2.ChartTypeManager", m_xContext ), uno::UNO_QUERY );
129 : }
130 606 : osl_atomic_decrement(&m_refCount);
131 606 : }
132 :
133 0 : ChartModel::ChartModel( const ChartModel & rOther )
134 : : impl::ChartModel_Base()
135 : , m_aLifeTimeManager( this, this )
136 : , m_bReadOnly( rOther.m_bReadOnly )
137 : , m_bModified( rOther.m_bModified )
138 : , m_nInLoad(0)
139 : , m_bUpdateNotificationsPending(false)
140 : , mbTimeBased(rOther.mbTimeBased)
141 : , mpChartView(NULL)
142 : , m_aResource( rOther.m_aResource )
143 : , m_aMediaDescriptor( rOther.m_aMediaDescriptor )
144 : , m_aControllers( m_aModelMutex )
145 : , m_nControllerLockCount(0)
146 : , m_xContext( rOther.m_xContext )
147 : // @note: the old model aggregate must not be shared with other models if it
148 : // is, you get mutex deadlocks
149 : , m_xOldModelAgg( 0 ) //rOther.m_xOldModelAgg )
150 : , m_xStorage( 0 ) //rOther.m_xStorage )
151 : , m_aVisualAreaSize( rOther.m_aVisualAreaSize )
152 : , m_aGraphicObjectVector( rOther.m_aGraphicObjectVector )
153 : , m_xDataProvider( rOther.m_xDataProvider )
154 : , m_xInternalDataProvider( rOther.m_xInternalDataProvider )
155 : , mnStart(rOther.mnStart)
156 : , mnEnd(rOther.mnEnd)
157 : , bSet(false)
158 0 : , mpOpenGLWindow(NULL)
159 : {
160 : OSL_TRACE( "ChartModel: Copy-CTOR called" );
161 :
162 0 : osl_atomic_increment(&m_refCount);
163 : {
164 : m_xOldModelAgg.set(
165 0 : m_xContext->getServiceManager()->createInstanceWithContext(
166 : CHART_CHARTAPIWRAPPER_SERVICE_NAME,
167 0 : m_xContext ), uno::UNO_QUERY_THROW );
168 0 : m_xOldModelAgg->setDelegator( *this );
169 :
170 0 : Reference< util::XModifyListener > xListener;
171 0 : Reference< chart2::XTitle > xNewTitle = CreateRefClone< Reference< chart2::XTitle > >()( rOther.m_xTitle );
172 0 : Reference< chart2::XDiagram > xNewDiagram = CreateRefClone< Reference< chart2::XDiagram > >()( rOther.m_xDiagram );
173 0 : Reference< beans::XPropertySet > xNewPageBackground = CreateRefClone< Reference< beans::XPropertySet > >()( rOther.m_xPageBackground );
174 0 : Reference< chart2::XChartTypeManager > xChartTypeManager = CreateRefClone< Reference< chart2::XChartTypeManager > >()( rOther.m_xChartTypeManager );
175 0 : Reference< container::XNameAccess > xXMLNamespaceMap = CreateRefClone< Reference< container::XNameAccess > >()( rOther.m_xXMLNamespaceMap );
176 :
177 : {
178 0 : MutexGuard aGuard( m_aModelMutex );
179 0 : xListener = this;
180 0 : m_xTitle = xNewTitle;
181 0 : m_xDiagram = xNewDiagram;
182 0 : m_xPageBackground = xNewPageBackground;
183 0 : m_xChartTypeManager = xChartTypeManager;
184 0 : m_xXMLNamespaceMap = xXMLNamespaceMap;
185 : }
186 :
187 0 : ModifyListenerHelper::addListener( xNewTitle, xListener );
188 0 : ModifyListenerHelper::addListener( xNewDiagram, xListener );
189 0 : ModifyListenerHelper::addListener( xNewPageBackground, xListener );
190 0 : xListener.clear();
191 : }
192 0 : osl_atomic_decrement(&m_refCount);
193 0 : }
194 :
195 1722 : ChartModel::~ChartModel()
196 : {
197 : OSL_TRACE( "ChartModel: DTOR called" );
198 574 : if( m_xOldModelAgg.is())
199 574 : m_xOldModelAgg->setDelegator( NULL );
200 1148 : }
201 :
202 574 : void SAL_CALL ChartModel::initialize( const Sequence< Any >& /*rArguments*/ )
203 : throw (uno::Exception, uno::RuntimeException, std::exception)
204 : {
205 : //#i113722# avoid duplicate creation
206 :
207 : //maybe additional todo?:
208 : //support argument "EmbeddedObject"?
209 : //support argument "EmbeddedScriptSupport"?
210 : //support argument "DocumentRecoverySupport"?
211 574 : }
212 :
213 : // private methods
214 :
215 370 : OUString ChartModel::impl_g_getLocation()
216 : {
217 :
218 370 : LifeTimeGuard aGuard(m_aLifeTimeManager);
219 370 : if(!aGuard.startApiCall())
220 0 : return OUString(); //behave passive if already disposed or closed or throw exception @todo?
221 : //mutex is acquired
222 370 : return m_aResource;
223 : }
224 :
225 34 : bool ChartModel::impl_isControllerConnected( const uno::Reference< frame::XController >& xController )
226 : {
227 : try
228 : {
229 34 : uno::Sequence< uno::Reference<uno::XInterface> > aSeq = m_aControllers.getElements();
230 68 : for( sal_Int32 nN = aSeq.getLength(); nN--; )
231 : {
232 34 : if( aSeq[nN] == xController )
233 34 : return true;
234 0 : }
235 : }
236 0 : catch (const uno::Exception&)
237 : {
238 : }
239 0 : return false;
240 : }
241 :
242 387 : uno::Reference< frame::XController > ChartModel::impl_getCurrentController() throw(uno::RuntimeException)
243 : {
244 : //@todo? hold only weak references to controllers
245 :
246 : // get the last active controller of this model
247 387 : if( m_xCurrentController.is() )
248 387 : return m_xCurrentController;
249 :
250 : // get the first controller of this model
251 0 : if( m_aControllers.getLength() )
252 : {
253 0 : uno::Reference<uno::XInterface> xI = m_aControllers.getElements()[0];
254 0 : return uno::Reference<frame::XController>( xI, uno::UNO_QUERY );
255 : }
256 :
257 : //return nothing if no controllers are connected at all
258 0 : return uno::Reference< frame::XController > ();
259 : }
260 :
261 604 : void SAL_CALL ChartModel::impl_notifyCloseListeners()
262 : throw( uno::RuntimeException)
263 : {
264 : ::cppu::OInterfaceContainerHelper* pIC = m_aLifeTimeManager.m_aListenerContainer
265 604 : .getContainer( cppu::UnoType<util::XCloseListener>::get());
266 604 : if( pIC )
267 : {
268 604 : lang::EventObject aEvent( static_cast< lang::XComponent*>(this) );
269 1208 : ::cppu::OInterfaceIteratorHelper aIt( *pIC );
270 1208 : while( aIt.hasMoreElements() )
271 : {
272 0 : uno::Reference< util::XCloseListener > xListener( aIt.next(), uno::UNO_QUERY );
273 0 : if( xListener.is() )
274 0 : xListener->notifyClosing( aEvent );
275 604 : }
276 : }
277 604 : }
278 :
279 874 : void ChartModel::impl_adjustAdditionalShapesPositionAndSize( const awt::Size& aVisualAreaSize )
280 : {
281 874 : uno::Reference< beans::XPropertySet > xProperties( static_cast< ::cppu::OWeakObject* >( this ), uno::UNO_QUERY );
282 874 : if ( xProperties.is() )
283 : {
284 874 : uno::Reference< drawing::XShapes > xShapes;
285 874 : xProperties->getPropertyValue( "AdditionalShapes" ) >>= xShapes;
286 874 : if ( xShapes.is() )
287 : {
288 0 : sal_Int32 nCount = xShapes->getCount();
289 0 : for ( sal_Int32 i = 0; i < nCount; ++i )
290 : {
291 0 : Reference< drawing::XShape > xShape;
292 0 : if ( xShapes->getByIndex( i ) >>= xShape )
293 : {
294 0 : if ( xShape.is() )
295 : {
296 0 : awt::Point aPos( xShape->getPosition() );
297 0 : awt::Size aSize( xShape->getSize() );
298 :
299 0 : double fWidth = static_cast< double >( aVisualAreaSize.Width ) / m_aVisualAreaSize.Width;
300 0 : double fHeight = static_cast< double >( aVisualAreaSize.Height ) / m_aVisualAreaSize.Height;
301 :
302 0 : aPos.X = static_cast< long >( aPos.X * fWidth );
303 0 : aPos.Y = static_cast< long >( aPos.Y * fHeight );
304 0 : aSize.Width = static_cast< long >( aSize.Width * fWidth );
305 0 : aSize.Height = static_cast< long >( aSize.Height * fHeight );
306 :
307 0 : xShape->setPosition( aPos );
308 0 : xShape->setSize( aSize );
309 : }
310 : }
311 0 : }
312 874 : }
313 874 : }
314 874 : }
315 :
316 : // lang::XServiceInfo
317 :
318 52768 : APPHELPER_XSERVICEINFO_IMPL(ChartModel,CHART_MODEL_SERVICE_IMPLEMENTATION_NAME)
319 :
320 27006 : uno::Sequence< OUString > ChartModel::getSupportedServiceNames_Static()
321 : {
322 27006 : uno::Sequence< OUString > aSNS( 3 );
323 27006 : aSNS[0] = CHART_MODEL_SERVICE_NAME;
324 27006 : aSNS[1] = "com.sun.star.document.OfficeDocument";
325 27006 : aSNS[2] = "com.sun.star.chart.ChartDocument";
326 : //// @todo : add additional services if you support any further
327 27006 : return aSNS;
328 : }
329 :
330 : // frame::XModel (required interface)
331 :
332 1154 : sal_Bool SAL_CALL ChartModel::attachResource( const OUString& rURL
333 : , const uno::Sequence< beans::PropertyValue >& rMediaDescriptor )
334 : throw(uno::RuntimeException, std::exception)
335 : {
336 : /*
337 : The method attachResource() is used by the frame loader implementations
338 : to inform the model about its URL and MediaDescriptor.
339 : */
340 :
341 1154 : LifeTimeGuard aGuard(m_aLifeTimeManager);
342 1154 : if(!aGuard.startApiCall())
343 0 : return sal_False; //behave passive if already disposed or closed or throw exception @todo?
344 : //mutex is acquired
345 :
346 1154 : if(!m_aResource.isEmpty())//we have a resource already //@todo? or is setting a new resource allowed?
347 0 : return sal_False;
348 1154 : m_aResource = rURL;
349 1154 : m_aMediaDescriptor = rMediaDescriptor;
350 :
351 : //@todo ? check rURL ??
352 : //@todo ? evaluate m_aMediaDescriptor;
353 : //@todo ? ... ??? --> nothing, this method is only for setting information
354 :
355 1154 : return sal_True;
356 : }
357 :
358 370 : OUString SAL_CALL ChartModel::getURL() throw(uno::RuntimeException, std::exception)
359 : {
360 370 : return impl_g_getLocation();
361 : }
362 :
363 6 : uno::Sequence< beans::PropertyValue > SAL_CALL ChartModel::getArgs() throw(uno::RuntimeException, std::exception)
364 : {
365 : /*
366 : The method getArgs() returns a sequence of property values
367 : that report the resource description according to com.sun.star.document.MediaDescriptor,
368 : specified on loading or saving with storeAsURL.
369 : */
370 :
371 6 : LifeTimeGuard aGuard(m_aLifeTimeManager);
372 6 : if(!aGuard.startApiCall())
373 0 : return uno::Sequence< beans::PropertyValue >(); //behave passive if already disposed or closed or throw exception @todo?
374 : //mutex is acquired
375 :
376 6 : return m_aMediaDescriptor;
377 : }
378 :
379 34 : void SAL_CALL ChartModel::connectController( const uno::Reference< frame::XController >& xController )
380 : throw(uno::RuntimeException, std::exception)
381 : {
382 : //@todo? this method is declared as oneway -> ...?
383 :
384 34 : LifeTimeGuard aGuard(m_aLifeTimeManager);
385 34 : if(!aGuard.startApiCall())
386 34 : return ; //behave passive if already disposed or closed
387 : //mutex is acquired
388 :
389 : //--add controller
390 34 : m_aControllers.addInterface(xController);
391 : }
392 :
393 2 : void SAL_CALL ChartModel::disconnectController( const uno::Reference< frame::XController >& xController )
394 : throw(uno::RuntimeException, std::exception)
395 : {
396 : //@todo? this method is declared as oneway -> ...?
397 :
398 2 : LifeTimeGuard aGuard(m_aLifeTimeManager);
399 2 : if(!aGuard.startApiCall())
400 2 : return; //behave passive if already disposed or closed
401 :
402 : //--remove controller
403 2 : m_aControllers.removeInterface(xController);
404 :
405 : //case: current controller is disconnected:
406 2 : if( m_xCurrentController == xController )
407 2 : m_xCurrentController.clear();
408 :
409 2 : DisposeHelper::DisposeAndClear( m_xRangeHighlighter );
410 : }
411 :
412 3848 : void SAL_CALL ChartModel::lockControllers() throw(uno::RuntimeException, std::exception)
413 : {
414 : /*
415 : suspends some notifications to the controllers which are used for display updates.
416 :
417 : The calls to lockControllers() and unlockControllers() may be nested
418 : and even overlapping, but they must be in pairs. While there is at least one lock
419 : remaining, some notifications for display updates are not broadcasted.
420 : */
421 :
422 : //@todo? this method is declared as oneway -> ...?
423 :
424 3848 : LifeTimeGuard aGuard(m_aLifeTimeManager);
425 3848 : if(!aGuard.startApiCall())
426 3848 : return; //behave passive if already disposed or closed or throw exception @todo?
427 3848 : ++m_nControllerLockCount;
428 : }
429 :
430 3848 : void SAL_CALL ChartModel::unlockControllers() throw(uno::RuntimeException, std::exception)
431 : {
432 : /*
433 : resumes the notifications which were suspended by lockControllers() .
434 :
435 : The calls to lockControllers() and unlockControllers() may be nested
436 : and even overlapping, but they must be in pairs. While there is at least one lock
437 : remaining, some notifications for display updates are not broadcasted.
438 : */
439 :
440 : //@todo? this method is declared as oneway -> ...?
441 :
442 3848 : LifeTimeGuard aGuard(m_aLifeTimeManager);
443 3848 : if(!aGuard.startApiCall())
444 0 : return; //behave passive if already disposed or closed or throw exception @todo?
445 3848 : if( m_nControllerLockCount == 0 )
446 : {
447 : OSL_TRACE( "ChartModel: unlockControllers called with m_nControllerLockCount == 0" );
448 0 : return;
449 : }
450 3848 : --m_nControllerLockCount;
451 3848 : if( m_nControllerLockCount == 0 && m_bUpdateNotificationsPending )
452 : {
453 1416 : aGuard.clear();
454 1416 : impl_notifyModifiedListeners();
455 3848 : }
456 : }
457 :
458 30930 : sal_Bool SAL_CALL ChartModel::hasControllersLocked() throw(uno::RuntimeException, std::exception)
459 : {
460 30930 : LifeTimeGuard aGuard(m_aLifeTimeManager);
461 30930 : if(!aGuard.startApiCall())
462 0 : return sal_False; //behave passive if already disposed or closed or throw exception @todo?
463 30930 : return ( m_nControllerLockCount != 0 ) ;
464 : }
465 :
466 387 : uno::Reference< frame::XController > SAL_CALL ChartModel::getCurrentController() throw(uno::RuntimeException, std::exception)
467 : {
468 387 : LifeTimeGuard aGuard(m_aLifeTimeManager);
469 387 : if(!aGuard.startApiCall())
470 : throw lang::DisposedException(
471 : "getCurrentController was called on an already disposed or closed model",
472 0 : static_cast< ::cppu::OWeakObject* >(this) );
473 :
474 387 : return impl_getCurrentController();
475 : }
476 :
477 34 : void SAL_CALL ChartModel::setCurrentController( const uno::Reference< frame::XController >& xController )
478 : throw(container::NoSuchElementException, uno::RuntimeException, std::exception)
479 : {
480 34 : LifeTimeGuard aGuard(m_aLifeTimeManager);
481 34 : if(!aGuard.startApiCall())
482 : throw lang::DisposedException(
483 : "setCurrentController was called on an already disposed or closed model",
484 0 : static_cast< ::cppu::OWeakObject* >(this) );
485 :
486 : //OSL_ENSURE( impl_isControllerConnected(xController), "setCurrentController is called with a Controller which is not connected" );
487 34 : if(!impl_isControllerConnected(xController))
488 : throw container::NoSuchElementException(
489 : "setCurrentController is called with a Controller which is not connected",
490 0 : static_cast< ::cppu::OWeakObject* >(this) );
491 :
492 34 : m_xCurrentController = xController;
493 :
494 34 : DisposeHelper::DisposeAndClear( m_xRangeHighlighter );
495 34 : }
496 :
497 0 : uno::Reference< uno::XInterface > SAL_CALL ChartModel::getCurrentSelection() throw(uno::RuntimeException, std::exception)
498 : {
499 0 : LifeTimeGuard aGuard(m_aLifeTimeManager);
500 0 : if(!aGuard.startApiCall())
501 : throw lang::DisposedException(
502 : "getCurrentSelection was called on an already disposed or closed model",
503 0 : static_cast< ::cppu::OWeakObject* >(this) );
504 :
505 0 : uno::Reference< uno::XInterface > xReturn;
506 0 : uno::Reference< frame::XController > xController = impl_getCurrentController();
507 :
508 0 : aGuard.clear();
509 0 : if( xController.is() )
510 : {
511 0 : uno::Reference< view::XSelectionSupplier > xSelectionSupl( xController, uno::UNO_QUERY );
512 0 : if ( xSelectionSupl.is() )
513 : {
514 0 : uno::Any aSel = xSelectionSupl->getSelection();
515 0 : OUString aObjectCID;
516 0 : if( aSel >>= aObjectCID )
517 0 : xReturn.set( ObjectIdentifier::getObjectPropertySet( aObjectCID, Reference< XChartDocument >(this)));
518 0 : }
519 : }
520 0 : return xReturn;
521 : }
522 :
523 : // lang::XComponent (base of XModel)
524 1212 : void SAL_CALL ChartModel::dispose() throw(uno::RuntimeException, std::exception)
525 : {
526 1212 : Reference< XInterface > xKeepAlive( *this );
527 :
528 : //This object should release all resources and references in the
529 : //easiest possible manner
530 : //This object must notify all registered listeners using the method
531 : //<member>XEventListener::disposing</member>
532 :
533 : //hold no mutex
534 1212 : if( !m_aLifeTimeManager.dispose() )
535 1818 : return;
536 :
537 : //--release all resources and references
538 : //// @todo
539 :
540 606 : if ( m_xDiagram.is() )
541 598 : ModifyListenerHelper::removeListener( m_xDiagram, this );
542 :
543 606 : m_xDataProvider.clear();
544 606 : m_xInternalDataProvider.clear();
545 606 : m_xNumberFormatsSupplier.clear();
546 606 : DisposeHelper::DisposeAndClear( m_xOwnNumberFormatsSupplier );
547 606 : DisposeHelper::DisposeAndClear( m_xChartTypeManager );
548 606 : DisposeHelper::DisposeAndClear( m_xDiagram );
549 606 : DisposeHelper::DisposeAndClear( m_xTitle );
550 606 : DisposeHelper::DisposeAndClear( m_xPageBackground );
551 606 : DisposeHelper::DisposeAndClear( m_xXMLNamespaceMap );
552 :
553 606 : m_xStorage.clear();
554 : // just clear, don't dispose - we're not the owner
555 :
556 606 : if ( m_pUndoManager.is() )
557 34 : m_pUndoManager->disposing();
558 606 : m_pUndoManager.clear();
559 : // that's important, since the UndoManager implementation delegates its ref counting to ourself.
560 :
561 606 : if( m_xOldModelAgg.is()) // #i120828#, to release cyclic reference to ChartModel object
562 606 : m_xOldModelAgg->setDelegator( 0 );
563 :
564 606 : m_aControllers.disposeAndClear( lang::EventObject( static_cast< cppu::OWeakObject * >( this )));
565 606 : m_xCurrentController.clear();
566 :
567 606 : DisposeHelper::DisposeAndClear( m_xRangeHighlighter );
568 :
569 606 : if( m_xOldModelAgg.is())
570 606 : m_xOldModelAgg->setDelegator( NULL );
571 :
572 606 : OSL_TRACE( "ChartModel: dispose() called" );
573 : }
574 :
575 2358 : void SAL_CALL ChartModel::addEventListener( const uno::Reference< lang::XEventListener > & xListener )
576 : throw(uno::RuntimeException, std::exception)
577 : {
578 2358 : if( m_aLifeTimeManager.impl_isDisposedOrClosed() )
579 2358 : return; //behave passive if already disposed or closed
580 :
581 2358 : m_aLifeTimeManager.m_aListenerContainer.addInterface( cppu::UnoType<lang::XEventListener>::get(), xListener );
582 : }
583 :
584 2356 : void SAL_CALL ChartModel::removeEventListener( const uno::Reference< lang::XEventListener > & xListener )
585 : throw(uno::RuntimeException, std::exception)
586 : {
587 2356 : if( m_aLifeTimeManager.impl_isDisposedOrClosed(false) )
588 0 : return; //behave passive if already disposed or closed
589 :
590 2356 : m_aLifeTimeManager.m_aListenerContainer.removeInterface( cppu::UnoType<lang::XEventListener>::get(), xListener );
591 2356 : return;
592 : }
593 :
594 : // util::XCloseBroadcaster (base of XCloseable)
595 608 : void SAL_CALL ChartModel::addCloseListener( const uno::Reference< util::XCloseListener > & xListener )
596 : throw(uno::RuntimeException, std::exception)
597 : {
598 608 : m_aLifeTimeManager.g_addCloseListener( xListener );
599 608 : }
600 :
601 32 : void SAL_CALL ChartModel::removeCloseListener( const uno::Reference< util::XCloseListener > & xListener )
602 : throw(uno::RuntimeException, std::exception)
603 : {
604 32 : if( m_aLifeTimeManager.impl_isDisposedOrClosed(false) )
605 30 : return; //behave passive if already disposed or closed
606 :
607 2 : m_aLifeTimeManager.m_aListenerContainer.removeInterface( cppu::UnoType<util::XCloseListener>::get(), xListener );
608 2 : return;
609 : }
610 :
611 : // util::XCloseable
612 606 : void SAL_CALL ChartModel::close( sal_Bool bDeliverOwnership )
613 : throw( util::CloseVetoException,
614 : uno::RuntimeException, std::exception )
615 : {
616 : //hold no mutex
617 :
618 606 : if( !m_aLifeTimeManager.g_close_startTryClose( bDeliverOwnership ) )
619 604 : return;
620 : //no mutex is acquired
621 :
622 : // At the end of this method may we must dispose ourself ...
623 : // and may nobody from outside hold a reference to us ...
624 : // then it's a good idea to do that by ourself.
625 604 : uno::Reference< uno::XInterface > xSelfHold( static_cast< ::cppu::OWeakObject* >(this) );
626 :
627 : //the listeners have had no veto
628 : //check whether we self can close
629 : {
630 : util::CloseVetoException aVetoException = util::CloseVetoException(
631 : "the model itself could not be closed",
632 604 : static_cast< ::cppu::OWeakObject* >(this) );
633 :
634 604 : if( m_aLifeTimeManager.g_close_isNeedToCancelLongLastingCalls( bDeliverOwnership, aVetoException ) )
635 : {
636 : ////you can empty this block, if you never start longlasting calls or
637 : ////if your longlasting calls are per default not cancelable (check how you have constructed your LifeTimeManager)
638 :
639 0 : bool bLongLastingCallsAreCanceled = false;
640 : try
641 : {
642 : //try to cancel running longlasting calls
643 : //// @todo
644 : }
645 : catch (const uno::Exception&)
646 : {
647 : //// @todo
648 : //do not throw anything here!! (without endTryClose)
649 : }
650 : //if not successful canceled
651 0 : if(!bLongLastingCallsAreCanceled)
652 : {
653 0 : m_aLifeTimeManager.g_close_endTryClose( bDeliverOwnership, true );
654 0 : throw aVetoException;
655 : }
656 604 : }
657 :
658 : }
659 604 : m_aLifeTimeManager.g_close_endTryClose_doClose();
660 :
661 : // BM @todo: is it ok to call the listeners here?
662 604 : impl_notifyCloseListeners();
663 : }
664 :
665 : // lang::XTypeProvider
666 0 : uno::Sequence< uno::Type > SAL_CALL ChartModel::getTypes()
667 : throw (uno::RuntimeException, std::exception)
668 : {
669 0 : uno::Reference< lang::XTypeProvider > xAggTypeProvider;
670 0 : if( (m_xOldModelAgg->queryAggregation( ::getCppuType( & xAggTypeProvider )) >>= xAggTypeProvider)
671 0 : && xAggTypeProvider.is())
672 : {
673 0 : uno::Sequence< uno::Type > aOwnTypes( impl::ChartModel_Base::getTypes());
674 0 : uno::Sequence< uno::Type > aAggTypes( xAggTypeProvider->getTypes());
675 0 : uno::Sequence< uno::Type > aResult( aOwnTypes.getLength() + aAggTypes.getLength());
676 0 : sal_Int32 i=0;
677 0 : for( ;i<aOwnTypes.getLength(); ++i )
678 0 : aResult[i] = aOwnTypes[i];
679 0 : for( sal_Int32 j=0; i<aResult.getLength(); ++j, ++i)
680 0 : aResult[i] = aAggTypes[j];
681 0 : return aResult;
682 : }
683 :
684 0 : return impl::ChartModel_Base::getTypes();
685 : }
686 :
687 : // document::XDocumentPropertiesSupplier
688 : uno::Reference< document::XDocumentProperties > SAL_CALL
689 4324 : ChartModel::getDocumentProperties() throw (uno::RuntimeException, std::exception)
690 : {
691 4324 : ::osl::MutexGuard aGuard( m_aModelMutex );
692 4324 : if ( !m_xDocumentProperties.is() )
693 : {
694 424 : m_xDocumentProperties.set( document::DocumentProperties::create( ::comphelper::getProcessComponentContext() ) );
695 : }
696 4324 : return m_xDocumentProperties;
697 : }
698 :
699 : // document::XDocumentPropertiesSupplier
700 69 : Reference< document::XUndoManager > SAL_CALL ChartModel::getUndoManager( ) throw (RuntimeException, std::exception)
701 : {
702 69 : ::osl::MutexGuard aGuard( m_aModelMutex );
703 69 : if ( !m_pUndoManager.is() )
704 34 : m_pUndoManager.set( new UndoManager( *this, m_aModelMutex ) );
705 69 : return m_pUndoManager.get();
706 : }
707 :
708 : // chart2::XChartDocument
709 :
710 878101 : uno::Reference< chart2::XDiagram > SAL_CALL ChartModel::getFirstDiagram()
711 : throw (uno::RuntimeException, std::exception)
712 : {
713 878101 : MutexGuard aGuard( m_aModelMutex );
714 878101 : return m_xDiagram;
715 : }
716 :
717 1108 : void SAL_CALL ChartModel::setFirstDiagram( const uno::Reference< chart2::XDiagram >& xDiagram )
718 : throw (uno::RuntimeException, std::exception)
719 : {
720 1108 : Reference< chart2::XDiagram > xOldDiagram;
721 1706 : Reference< util::XModifyListener > xListener;
722 : {
723 1108 : MutexGuard aGuard( m_aModelMutex );
724 1108 : if( xDiagram == m_xDiagram )
725 1618 : return;
726 598 : xOldDiagram = m_xDiagram;
727 598 : m_xDiagram = xDiagram;
728 598 : xListener = this;
729 : }
730 : //don't keep the mutex locked while calling out
731 598 : ModifyListenerHelper::removeListener( xOldDiagram, xListener );
732 598 : ModifyListenerHelper::addListener( xDiagram, xListener );
733 1196 : setModified( sal_True );
734 : }
735 :
736 28 : Reference< chart2::data::XDataSource > ChartModel::impl_createDefaultData()
737 : {
738 28 : Reference< chart2::data::XDataSource > xDataSource;
739 28 : if( hasInternalDataProvider() )
740 : {
741 28 : uno::Reference< lang::XInitialization > xIni(m_xInternalDataProvider,uno::UNO_QUERY);
742 28 : if( xIni.is() )
743 : {
744 : //init internal dataprovider
745 : {
746 28 : uno::Sequence< uno::Any > aArgs(1);
747 56 : beans::NamedValue aParam( "CreateDefaultData" ,uno::makeAny(sal_True) );
748 28 : aArgs[0] <<= aParam;
749 56 : xIni->initialize(aArgs);
750 : }
751 : //create data
752 28 : uno::Sequence< beans::PropertyValue > aArgs( 4 );
753 56 : aArgs[0] = beans::PropertyValue(
754 : OUString( "CellRangeRepresentation" ), -1,
755 28 : uno::makeAny( OUString("all") ), beans::PropertyState_DIRECT_VALUE );
756 56 : aArgs[1] = beans::PropertyValue(
757 : "HasCategories",
758 : -1,
759 : uno::makeAny( true ),
760 28 : beans::PropertyState_DIRECT_VALUE );
761 56 : aArgs[2] = beans::PropertyValue(
762 : "FirstCellAsLabel",
763 : -1,
764 : uno::makeAny( true ),
765 28 : beans::PropertyState_DIRECT_VALUE );
766 56 : aArgs[3] = beans::PropertyValue(
767 : "DataRowSource",
768 : -1,
769 : uno::makeAny( ::com::sun::star::chart::ChartDataRowSource_COLUMNS ),
770 28 : beans::PropertyState_DIRECT_VALUE );
771 28 : xDataSource = m_xInternalDataProvider->createDataSource( aArgs );
772 28 : }
773 : }
774 28 : return xDataSource;
775 : }
776 :
777 582 : void SAL_CALL ChartModel::createInternalDataProvider( sal_Bool bCloneExistingData )
778 : throw (util::CloseVetoException, uno::RuntimeException, std::exception)
779 : {
780 : // don't lock the mutex, because this call calls out to code that tries to
781 : // lock the solar mutex. On the other hand, a paint locks the solar mutex
782 : // and calls to the model lock the model's mutex => deadlock
783 : // @todo: lock a separate mutex in the InternalData class
784 582 : if( !hasInternalDataProvider() )
785 : {
786 396 : if( bCloneExistingData )
787 0 : m_xInternalDataProvider = ChartModelHelper::createInternalDataProvider( this, true );
788 : else
789 396 : m_xInternalDataProvider = ChartModelHelper::createInternalDataProvider( Reference<XChartDocument>(), true );
790 396 : m_xDataProvider.set( m_xInternalDataProvider );
791 : }
792 582 : setModified( sal_True );
793 582 : }
794 :
795 13530 : sal_Bool SAL_CALL ChartModel::hasInternalDataProvider()
796 : throw (uno::RuntimeException, std::exception)
797 : {
798 13530 : return m_xDataProvider.is() && m_xInternalDataProvider.is();
799 : }
800 :
801 15665 : uno::Reference< chart2::data::XDataProvider > SAL_CALL ChartModel::getDataProvider()
802 : throw (uno::RuntimeException, std::exception)
803 : {
804 15665 : MutexGuard aGuard( m_aModelMutex );
805 15665 : return m_xDataProvider;
806 : }
807 :
808 : // ____ XDataReceiver ____
809 :
810 208 : void SAL_CALL ChartModel::attachDataProvider( const uno::Reference< chart2::data::XDataProvider >& xDataProvider )
811 : throw (uno::RuntimeException, std::exception)
812 : {
813 : {
814 208 : MutexGuard aGuard( m_aModelMutex );
815 416 : uno::Reference< beans::XPropertySet > xProp( xDataProvider, uno::UNO_QUERY );
816 208 : if( xProp.is() )
817 : {
818 : try
819 : {
820 202 : bool bIncludeHiddenCells = ChartModelHelper::isIncludeHiddenCells( Reference< frame::XModel >(this) );
821 202 : xProp->setPropertyValue("IncludeHiddenCells", uno::makeAny(bIncludeHiddenCells));
822 : }
823 0 : catch (const beans::UnknownPropertyException&)
824 : {
825 : }
826 : }
827 :
828 208 : m_xDataProvider.set( xDataProvider );
829 416 : m_xInternalDataProvider.clear();
830 :
831 : //the numberformatter is kept independent of the data provider!
832 : }
833 208 : setModified( sal_True );
834 208 : }
835 :
836 532 : void SAL_CALL ChartModel::attachNumberFormatsSupplier( const uno::Reference< util::XNumberFormatsSupplier >& xNewSupplier )
837 : throw (uno::RuntimeException, std::exception)
838 : {
839 : {
840 532 : MutexGuard aGuard( m_aModelMutex );
841 532 : if( xNewSupplier==m_xNumberFormatsSupplier )
842 152 : return;
843 380 : if( xNewSupplier==m_xOwnNumberFormatsSupplier )
844 0 : return;
845 380 : if( m_xOwnNumberFormatsSupplier.is() && xNewSupplier.is() )
846 : {
847 : //@todo
848 : //merge missing numberformats from own to new formatter
849 : }
850 380 : else if( !xNewSupplier.is() )
851 : {
852 0 : if( m_xNumberFormatsSupplier.is() )
853 : {
854 : //@todo
855 : //merge missing numberformats from old numberformatter to own numberformatter
856 : //create own numberformatter if necessary
857 : }
858 : }
859 :
860 380 : m_xNumberFormatsSupplier.set( xNewSupplier );
861 380 : m_xOwnNumberFormatsSupplier.clear();
862 : }
863 380 : setModified( sal_True );
864 : }
865 :
866 26 : void SAL_CALL ChartModel::setArguments( const Sequence< beans::PropertyValue >& aArguments )
867 : throw (lang::IllegalArgumentException,
868 : uno::RuntimeException, std::exception)
869 : {
870 : {
871 26 : MutexGuard aGuard( m_aModelMutex );
872 26 : if( !m_xDataProvider.is() )
873 26 : return;
874 26 : lockControllers();
875 :
876 : try
877 : {
878 26 : Reference< chart2::data::XDataSource > xDataSource( m_xDataProvider->createDataSource( aArguments ) );
879 26 : if( xDataSource.is() )
880 : {
881 26 : Reference< chart2::XDiagram > xDia( getFirstDiagram() );
882 26 : if( !xDia.is() )
883 : {
884 14 : Reference< chart2::XChartTypeTemplate > xTemplate( impl_createDefaultChartTypeTemplate() );
885 14 : if( xTemplate.is())
886 14 : setFirstDiagram( xTemplate->createDiagramByDataSource( xDataSource, aArguments ) );
887 : }
888 : else
889 12 : xDia->setDiagramData( xDataSource, aArguments );
890 26 : }
891 : }
892 0 : catch (const lang::IllegalArgumentException&)
893 : {
894 0 : throw;
895 : }
896 0 : catch (const uno::Exception& ex)
897 : {
898 : ASSERT_EXCEPTION( ex );
899 : }
900 26 : unlockControllers();
901 : }
902 26 : setModified( sal_True );
903 : }
904 :
905 12 : Sequence< OUString > SAL_CALL ChartModel::getUsedRangeRepresentations()
906 : throw (uno::RuntimeException, std::exception)
907 : {
908 12 : return DataSourceHelper::getUsedDataRanges( Reference< frame::XModel >(this));
909 : }
910 :
911 84 : Reference< chart2::data::XDataSource > SAL_CALL ChartModel::getUsedData()
912 : throw (uno::RuntimeException, std::exception)
913 : {
914 84 : return DataSourceHelper::getUsedData( Reference< chart2::XChartDocument >(this));
915 : }
916 :
917 226 : Reference< chart2::data::XRangeHighlighter > SAL_CALL ChartModel::getRangeHighlighter()
918 : throw (uno::RuntimeException, std::exception)
919 : {
920 226 : if( ! m_xRangeHighlighter.is())
921 : {
922 27 : uno::Reference< view::XSelectionSupplier > xSelSupp( this->getCurrentController(), uno::UNO_QUERY );
923 27 : if( xSelSupp.is() )
924 27 : m_xRangeHighlighter.set( ChartModelHelper::createRangeHighlighter( xSelSupp ));
925 : }
926 226 : return m_xRangeHighlighter;
927 : }
928 :
929 42 : Reference< chart2::XChartTypeTemplate > ChartModel::impl_createDefaultChartTypeTemplate()
930 : {
931 42 : Reference< chart2::XChartTypeTemplate > xTemplate;
932 84 : Reference< lang::XMultiServiceFactory > xFact( m_xChartTypeManager, uno::UNO_QUERY );
933 42 : if( xFact.is() )
934 42 : xTemplate.set( xFact->createInstance( "com.sun.star.chart2.template.Column" ), uno::UNO_QUERY );
935 84 : return xTemplate;
936 : }
937 :
938 0 : void SAL_CALL ChartModel::setChartTypeManager( const uno::Reference< chart2::XChartTypeManager >& xNewManager )
939 : throw (uno::RuntimeException, std::exception)
940 : {
941 : {
942 0 : MutexGuard aGuard( m_aModelMutex );
943 0 : m_xChartTypeManager = xNewManager;
944 : }
945 0 : setModified( sal_True );
946 0 : }
947 :
948 5826 : uno::Reference< chart2::XChartTypeManager > SAL_CALL ChartModel::getChartTypeManager()
949 : throw (uno::RuntimeException, std::exception)
950 : {
951 5826 : MutexGuard aGuard( m_aModelMutex );
952 5826 : return m_xChartTypeManager;
953 : }
954 :
955 32112 : uno::Reference< beans::XPropertySet > SAL_CALL ChartModel::getPageBackground()
956 : throw (uno::RuntimeException, std::exception)
957 : {
958 32112 : MutexGuard aGuard( m_aModelMutex );
959 32112 : return m_xPageBackground;
960 : }
961 :
962 28 : void SAL_CALL ChartModel::createDefaultChart()
963 : throw (css::uno::RuntimeException, std::exception)
964 : {
965 28 : insertDefaultChart();
966 28 : }
967 :
968 203 : sal_Bool SAL_CALL ChartModel::isOpenGLChart()
969 : throw (css::uno::RuntimeException, std::exception)
970 : {
971 203 : return ChartHelper::isGL3DDiagram(m_xDiagram);
972 : }
973 :
974 : // ____ XTitled ____
975 29056 : uno::Reference< chart2::XTitle > SAL_CALL ChartModel::getTitleObject()
976 : throw (uno::RuntimeException, std::exception)
977 : {
978 29056 : MutexGuard aGuard( m_aModelMutex );
979 29056 : return m_xTitle;
980 : }
981 :
982 404 : void SAL_CALL ChartModel::setTitleObject( const uno::Reference< chart2::XTitle >& xTitle )
983 : throw (uno::RuntimeException, std::exception)
984 : {
985 : {
986 404 : MutexGuard aGuard( m_aModelMutex );
987 404 : if( m_xTitle.is() )
988 4 : ModifyListenerHelper::removeListener( m_xTitle, this );
989 404 : m_xTitle = xTitle;
990 404 : ModifyListenerHelper::addListener( m_xTitle, this );
991 : }
992 404 : setModified( sal_True );
993 404 : }
994 :
995 : // ____ XInterface (for old API wrapper) ____
996 1882489 : uno::Any SAL_CALL ChartModel::queryInterface( const uno::Type& aType )
997 : throw (uno::RuntimeException, std::exception)
998 : {
999 1882489 : uno::Any aResult( impl::ChartModel_Base::queryInterface( aType ));
1000 :
1001 1882489 : if( ! aResult.hasValue())
1002 : {
1003 : // try old API wrapper
1004 : try
1005 : {
1006 22511 : if( m_xOldModelAgg.is())
1007 22511 : aResult = m_xOldModelAgg->queryAggregation( aType );
1008 : }
1009 0 : catch (const uno::Exception& ex)
1010 : {
1011 : ASSERT_EXCEPTION( ex );
1012 : }
1013 : }
1014 :
1015 1882489 : return aResult;
1016 : }
1017 :
1018 : // ____ XCloneable ____
1019 0 : Reference< util::XCloneable > SAL_CALL ChartModel::createClone()
1020 : throw (uno::RuntimeException, std::exception)
1021 : {
1022 0 : return Reference< util::XCloneable >( new ChartModel( *this ));
1023 : }
1024 :
1025 : // ____ XVisualObject ____
1026 1130 : void SAL_CALL ChartModel::setVisualAreaSize( ::sal_Int64 nAspect, const awt::Size& aSize )
1027 : throw (lang::IllegalArgumentException,
1028 : embed::WrongStateException,
1029 : uno::Exception,
1030 : uno::RuntimeException, std::exception)
1031 : {
1032 1130 : if( nAspect == embed::Aspects::MSOLE_CONTENT )
1033 : {
1034 1130 : ControllerLockGuard aLockGuard( *this );
1035 : bool bChanged =
1036 1386 : (m_aVisualAreaSize.Width != aSize.Width ||
1037 1386 : m_aVisualAreaSize.Height != aSize.Height);
1038 :
1039 : // #i12587# support for shapes in chart
1040 1130 : if ( bChanged )
1041 : {
1042 874 : impl_adjustAdditionalShapesPositionAndSize( aSize );
1043 : }
1044 :
1045 1130 : m_aVisualAreaSize = aSize;
1046 1130 : if( bChanged )
1047 874 : setModified( sal_True );
1048 : }
1049 : else
1050 : {
1051 : OSL_FAIL( "setVisualAreaSize: Aspect not implemented yet.");
1052 : }
1053 1130 : }
1054 :
1055 4274 : awt::Size SAL_CALL ChartModel::getVisualAreaSize( ::sal_Int64 nAspect )
1056 : throw (lang::IllegalArgumentException,
1057 : embed::WrongStateException,
1058 : uno::Exception,
1059 : uno::RuntimeException, std::exception)
1060 : {
1061 : OSL_ENSURE( nAspect == embed::Aspects::MSOLE_CONTENT,
1062 : "No aspects other than content are supported" );
1063 : (void)(nAspect); // avoid warning in non-debug builds
1064 : // other possible aspects are MSOLE_THUMBNAIL, MSOLE_ICON and MSOLE_DOCPRINT
1065 :
1066 4274 : return m_aVisualAreaSize;
1067 : }
1068 :
1069 0 : embed::VisualRepresentation SAL_CALL ChartModel::getPreferredVisualRepresentation( ::sal_Int64 nAspect )
1070 : throw (lang::IllegalArgumentException,
1071 : embed::WrongStateException,
1072 : uno::Exception,
1073 : uno::RuntimeException, std::exception)
1074 : {
1075 : OSL_ENSURE( nAspect == embed::Aspects::MSOLE_CONTENT,
1076 : "No aspects other than content are supported" );
1077 : (void)(nAspect); // avoid warning in non-debug builds
1078 :
1079 0 : embed::VisualRepresentation aResult;
1080 :
1081 : try
1082 : {
1083 0 : Sequence< sal_Int8 > aMetafile;
1084 :
1085 : //get view from old api wrapper
1086 : Reference< datatransfer::XTransferable > xTransferable(
1087 0 : this->createInstance( CHART_VIEW_SERVICE_NAME ), uno::UNO_QUERY );
1088 0 : if( xTransferable.is() )
1089 : {
1090 : datatransfer::DataFlavor aDataFlavor( lcl_aGDIMetaFileMIMEType,
1091 : "GDIMetaFile",
1092 0 : ::getCppuType( (const uno::Sequence< sal_Int8 >*) 0 ) );
1093 :
1094 0 : uno::Any aData( xTransferable->getTransferData( aDataFlavor ) );
1095 0 : aData >>= aMetafile;
1096 : }
1097 :
1098 0 : aResult.Flavor.MimeType = lcl_aGDIMetaFileMIMEType;
1099 0 : aResult.Flavor.DataType = getCppuType( &aMetafile );
1100 :
1101 0 : aResult.Data <<= aMetafile;
1102 : }
1103 0 : catch (const uno::Exception& ex)
1104 : {
1105 : ASSERT_EXCEPTION( ex );
1106 : }
1107 :
1108 0 : return aResult;
1109 : }
1110 :
1111 1828 : ::sal_Int32 SAL_CALL ChartModel::getMapUnit( ::sal_Int64 nAspect )
1112 : throw (uno::Exception,
1113 : uno::RuntimeException, std::exception)
1114 : {
1115 : OSL_ENSURE( nAspect == embed::Aspects::MSOLE_CONTENT,
1116 : "No aspects other than content are supported" );
1117 : (void)(nAspect); // avoid warning in non-debug builds
1118 1828 : return embed::EmbedMapUnits::ONE_100TH_MM;
1119 : }
1120 :
1121 : // ____ datatransfer::XTransferable ____
1122 0 : uno::Any SAL_CALL ChartModel::getTransferData( const datatransfer::DataFlavor& aFlavor )
1123 : throw (datatransfer::UnsupportedFlavorException,
1124 : io::IOException,
1125 : uno::RuntimeException, std::exception)
1126 : {
1127 0 : uno::Any aResult;
1128 0 : if( this->isDataFlavorSupported( aFlavor ))
1129 : {
1130 : try
1131 : {
1132 : //get view from old api wrapper
1133 : Reference< datatransfer::XTransferable > xTransferable(
1134 0 : this->createInstance( CHART_VIEW_SERVICE_NAME ), uno::UNO_QUERY );
1135 0 : if( xTransferable.is() &&
1136 0 : xTransferable->isDataFlavorSupported( aFlavor ))
1137 : {
1138 0 : aResult = xTransferable->getTransferData( aFlavor );
1139 0 : }
1140 : }
1141 0 : catch (const uno::Exception& ex)
1142 : {
1143 : ASSERT_EXCEPTION( ex );
1144 : }
1145 : }
1146 : else
1147 : {
1148 : throw datatransfer::UnsupportedFlavorException(
1149 0 : aFlavor.MimeType, static_cast< ::cppu::OWeakObject* >( this ));
1150 : }
1151 :
1152 0 : return aResult;
1153 : }
1154 :
1155 0 : Sequence< datatransfer::DataFlavor > SAL_CALL ChartModel::getTransferDataFlavors()
1156 : throw (uno::RuntimeException, std::exception)
1157 : {
1158 0 : uno::Sequence< datatransfer::DataFlavor > aRet(1);
1159 :
1160 0 : aRet[0] = datatransfer::DataFlavor( lcl_aGDIMetaFileMIMETypeHighContrast,
1161 : "GDIMetaFile",
1162 0 : ::getCppuType( (const uno::Sequence< sal_Int8 >*) NULL ) );
1163 :
1164 0 : return aRet;
1165 : }
1166 :
1167 0 : sal_Bool SAL_CALL ChartModel::isDataFlavorSupported( const datatransfer::DataFlavor& aFlavor )
1168 : throw (uno::RuntimeException, std::exception)
1169 : {
1170 0 : return aFlavor.MimeType.equals(lcl_aGDIMetaFileMIMETypeHighContrast);
1171 : }
1172 :
1173 : namespace
1174 : {
1175 : enum eServiceType
1176 : {
1177 : SERVICE_DASH_TABLE,
1178 : SERVICE_GARDIENT_TABLE,
1179 : SERVICE_HATCH_TABLE,
1180 : SERVICE_BITMAP_TABLE,
1181 : SERVICE_TRANSP_GRADIENT_TABLE,
1182 : SERVICE_MARKER_TABLE,
1183 : SERVICE_NAMESPACE_MAP
1184 : };
1185 :
1186 : typedef ::std::map< OUString, enum eServiceType > tServiceNameMap;
1187 : typedef ::comphelper::MakeMap< OUString, enum eServiceType > tMakeServiceNameMap;
1188 :
1189 21932 : tServiceNameMap & lcl_getStaticServiceNameMap()
1190 : {
1191 : static tServiceNameMap aServiceNameMap(
1192 : tMakeServiceNameMap
1193 : ( "com.sun.star.drawing.DashTable", SERVICE_DASH_TABLE )
1194 64 : ( "com.sun.star.drawing.GradientTable", SERVICE_GARDIENT_TABLE )
1195 96 : ( "com.sun.star.drawing.HatchTable", SERVICE_HATCH_TABLE )
1196 96 : ( "com.sun.star.drawing.BitmapTable", SERVICE_BITMAP_TABLE )
1197 96 : ( "com.sun.star.drawing.TransparencyGradientTable", SERVICE_TRANSP_GRADIENT_TABLE )
1198 96 : ( "com.sun.star.drawing.MarkerTable", SERVICE_MARKER_TABLE )
1199 96 : ( "com.sun.star.xml.NamespaceMap", SERVICE_NAMESPACE_MAP )
1200 21964 : );
1201 21932 : return aServiceNameMap;
1202 : }
1203 : }
1204 : // ____ XMultiServiceFactory ____
1205 21932 : Reference< uno::XInterface > SAL_CALL ChartModel::createInstance( const OUString& rServiceSpecifier )
1206 : throw( uno::Exception, uno::RuntimeException, std::exception )
1207 : {
1208 21932 : uno::Reference< uno::XInterface > xResult;
1209 21932 : tServiceNameMap & rMap = lcl_getStaticServiceNameMap();
1210 :
1211 21932 : tServiceNameMap::const_iterator aIt( rMap.find( rServiceSpecifier ));
1212 21932 : if( aIt != rMap.end())
1213 : {
1214 7992 : switch( (*aIt).second )
1215 : {
1216 : case SERVICE_DASH_TABLE:
1217 : case SERVICE_GARDIENT_TABLE:
1218 : case SERVICE_HATCH_TABLE:
1219 : case SERVICE_BITMAP_TABLE:
1220 : case SERVICE_TRANSP_GRADIENT_TABLE:
1221 : case SERVICE_MARKER_TABLE:
1222 : {
1223 6360 : if(!mpChartView)
1224 : {
1225 606 : mpChartView = new ChartView( m_xContext, *this);
1226 606 : xChartView = static_cast< ::cppu::OWeakObject* >( mpChartView );
1227 : }
1228 6360 : return mpChartView->createInstance( rServiceSpecifier );
1229 : }
1230 : break;
1231 : case SERVICE_NAMESPACE_MAP:
1232 1632 : return Reference< uno::XInterface >( m_xXMLNamespaceMap );
1233 : }
1234 : }
1235 13940 : else if(rServiceSpecifier == CHART_VIEW_SERVICE_NAME)
1236 : {
1237 6040 : if(!mpChartView)
1238 : {
1239 0 : mpChartView = new ChartView( m_xContext, *this);
1240 0 : xChartView = static_cast< ::cppu::OWeakObject* >( mpChartView );
1241 : }
1242 :
1243 6040 : return static_cast< ::cppu::OWeakObject* >( mpChartView );
1244 : }
1245 : else
1246 : {
1247 7900 : if( m_xOldModelAgg.is() )
1248 : {
1249 7900 : Any aAny = m_xOldModelAgg->queryAggregation( cppu::UnoType<lang::XMultiServiceFactory>::get());
1250 7900 : uno::Reference< lang::XMultiServiceFactory > xOldModelFactory;
1251 7900 : if( (aAny >>= xOldModelFactory) && xOldModelFactory.is() )
1252 : {
1253 7900 : return xOldModelFactory->createInstance( rServiceSpecifier );
1254 0 : }
1255 : }
1256 : }
1257 0 : return 0;
1258 : }
1259 :
1260 0 : Reference< uno::XInterface > SAL_CALL ChartModel::createInstanceWithArguments(
1261 : const OUString& rServiceSpecifier , const Sequence< Any >& Arguments )
1262 : throw( uno::Exception, uno::RuntimeException, std::exception )
1263 : {
1264 : OSL_ENSURE( Arguments.getLength(), "createInstanceWithArguments: Warning: Arguments are ignored" );
1265 : (void)(Arguments); // avoid warning in non-debug builds
1266 0 : return createInstance( rServiceSpecifier );
1267 : }
1268 :
1269 544 : Sequence< OUString > SAL_CALL ChartModel::getAvailableServiceNames()
1270 : throw( uno::RuntimeException, std::exception )
1271 : {
1272 544 : uno::Sequence< OUString > aResult;
1273 :
1274 544 : if( m_xOldModelAgg.is())
1275 : {
1276 544 : Any aAny = m_xOldModelAgg->queryAggregation( cppu::UnoType<lang::XMultiServiceFactory>::get());
1277 544 : uno::Reference< lang::XMultiServiceFactory > xOldModelFactory;
1278 544 : if( (aAny >>= xOldModelFactory) && xOldModelFactory.is() )
1279 : {
1280 544 : return xOldModelFactory->getAvailableServiceNames();
1281 0 : }
1282 : }
1283 0 : return aResult;
1284 : }
1285 :
1286 8444 : Reference< util::XNumberFormatsSupplier > ChartModel::getNumberFormatsSupplier()
1287 : {
1288 8444 : if( !m_xNumberFormatsSupplier.is() )
1289 : {
1290 217 : if( !m_xOwnNumberFormatsSupplier.is() )
1291 : {
1292 217 : m_apSvNumberFormatter.reset( new SvNumberFormatter( m_xContext, LANGUAGE_SYSTEM ) );
1293 217 : m_xOwnNumberFormatsSupplier = new SvNumberFormatsSupplierObj( m_apSvNumberFormatter.get() );
1294 : //pOwnNumberFormatter->ChangeStandardPrec( 15 ); todo?
1295 : }
1296 217 : m_xNumberFormatsSupplier = m_xOwnNumberFormatsSupplier;
1297 : }
1298 8444 : return m_xNumberFormatsSupplier;
1299 : }
1300 :
1301 : // ____ XUnoTunnel ___
1302 4778 : ::sal_Int64 SAL_CALL ChartModel::getSomething( const Sequence< ::sal_Int8 >& aIdentifier )
1303 : throw( uno::RuntimeException, std::exception)
1304 : {
1305 14334 : if( aIdentifier.getLength() == 16 && 0 == memcmp( SvNumberFormatsSupplierObj::getUnoTunnelId().getConstArray(),
1306 9556 : aIdentifier.getConstArray(), 16 ) )
1307 : {
1308 3654 : Reference< lang::XUnoTunnel > xTunnel( getNumberFormatsSupplier(), uno::UNO_QUERY );
1309 3654 : if( xTunnel.is() )
1310 3654 : return xTunnel->getSomething( aIdentifier );
1311 : }
1312 1124 : return 0;
1313 : }
1314 :
1315 : // ____ XNumberFormatsSupplier ____
1316 0 : uno::Reference< beans::XPropertySet > SAL_CALL ChartModel::getNumberFormatSettings()
1317 : throw (uno::RuntimeException, std::exception)
1318 : {
1319 0 : Reference< util::XNumberFormatsSupplier > xSupplier( getNumberFormatsSupplier() );
1320 0 : if( xSupplier.is() )
1321 0 : return xSupplier->getNumberFormatSettings();
1322 0 : return uno::Reference< beans::XPropertySet >();
1323 : }
1324 :
1325 3255 : uno::Reference< util::XNumberFormats > SAL_CALL ChartModel::getNumberFormats()
1326 : throw (uno::RuntimeException, std::exception)
1327 : {
1328 3255 : Reference< util::XNumberFormatsSupplier > xSupplier( getNumberFormatsSupplier() );
1329 3255 : if( xSupplier.is() )
1330 3255 : return xSupplier->getNumberFormats();
1331 0 : return uno::Reference< util::XNumberFormats >();
1332 : }
1333 :
1334 : // ____ XChild ____
1335 2324 : Reference< uno::XInterface > SAL_CALL ChartModel::getParent()
1336 : throw (uno::RuntimeException, std::exception)
1337 : {
1338 2324 : return Reference< uno::XInterface >(m_xParent,uno::UNO_QUERY);
1339 : }
1340 :
1341 1446 : void SAL_CALL ChartModel::setParent( const Reference< uno::XInterface >& Parent )
1342 : throw (lang::NoSupportException,
1343 : uno::RuntimeException, std::exception)
1344 : {
1345 1446 : if( Parent != m_xParent )
1346 592 : m_xParent.set( Parent, uno::UNO_QUERY );
1347 1446 : }
1348 :
1349 : // ____ XDataSource ____
1350 4 : uno::Sequence< Reference< chart2::data::XLabeledDataSequence > > SAL_CALL ChartModel::getDataSequences()
1351 : throw (uno::RuntimeException, std::exception)
1352 : {
1353 : Reference< chart2::data::XDataSource > xSource(
1354 4 : DataSourceHelper::getUsedData( uno::Reference< frame::XModel >(this) ) );
1355 4 : if( xSource.is())
1356 4 : return xSource->getDataSequences();
1357 :
1358 0 : return uno::Sequence< Reference< chart2::data::XLabeledDataSequence > >();
1359 : }
1360 :
1361 : //XDumper
1362 0 : OUString SAL_CALL ChartModel::dump()
1363 : throw (uno::RuntimeException, std::exception)
1364 : {
1365 : uno::Reference< qa::XDumper > xDumper(
1366 0 : this->createInstance( CHART_VIEW_SERVICE_NAME ), uno::UNO_QUERY );
1367 0 : if (xDumper.is())
1368 0 : return xDumper->dump();
1369 :
1370 0 : return OUString();
1371 : }
1372 :
1373 0 : void ChartModel::setTimeBased(bool bTimeBased)
1374 : {
1375 0 : mbTimeBased = bTimeBased;
1376 : uno::Sequence<Reference< chart2::data::XLabeledDataSequence > >
1377 0 : xDataSequences = getDataSequences();
1378 0 : sal_Int32 n = xDataSequences.getLength();
1379 0 : for(sal_Int32 i = 0; i < n; ++i)
1380 : {
1381 0 : uno::Reference< chart2::XTimeBased > xTimeBased(xDataSequences[i]->getValues(), uno::UNO_QUERY);
1382 : SAL_WARN_IF(!xTimeBased.is(), "chart2", "does not support time based charting");
1383 0 : if(xTimeBased.is())
1384 : {
1385 0 : uno::Reference< beans::XPropertySet > xPropSet(xTimeBased, uno::UNO_QUERY_THROW);
1386 0 : xPropSet->setPropertyValue("TimeBased", uno::makeAny(bTimeBased));
1387 : }
1388 0 : }
1389 0 : }
1390 :
1391 0 : void ChartModel::getNextTimePoint()
1392 : {
1393 0 : uno::Sequence< Reference< chart2::data::XLabeledDataSequence > > xDataSequences = getDataSequences();
1394 0 : sal_Int32 n = xDataSequences.getLength();
1395 0 : for(sal_Int32 i = 0; i < n; ++i)
1396 : {
1397 0 : uno::Reference< chart2::XTimeBased > xTimeBased(xDataSequences[i]->getValues(), uno::UNO_QUERY);
1398 : SAL_WARN_IF(!xTimeBased.is(), "chart2", "does not support time based charting");
1399 0 : if(xTimeBased.is())
1400 : {
1401 0 : if(!bSet)
1402 0 : xTimeBased->setRange(mnStart, mnEnd);
1403 0 : xTimeBased->switchToNext(sal_True);
1404 : }
1405 0 : }
1406 0 : bSet = true;
1407 0 : }
1408 :
1409 0 : void ChartModel::setTimeBasedRange(sal_Int32 nStart, sal_Int32 nEnd)
1410 : {
1411 0 : bSet = false;
1412 0 : mnStart = nStart;
1413 0 : mnEnd = nEnd;
1414 0 : mbTimeBased = true;
1415 0 : }
1416 :
1417 36 : void ChartModel::setWindow( const sal_uInt64 nWindowPtr )
1418 : throw (uno::RuntimeException, std::exception)
1419 : {
1420 36 : OpenGLWindow* pWindow = reinterpret_cast<OpenGLWindow*>(nWindowPtr);
1421 36 : mpOpenGLWindow = pWindow;
1422 36 : }
1423 :
1424 34 : void ChartModel::update()
1425 : throw (uno::RuntimeException, std::exception)
1426 : {
1427 34 : if(!mpChartView)
1428 : {
1429 0 : mpChartView = new ChartView( m_xContext, *this);
1430 0 : xChartView = static_cast< ::cppu::OWeakObject* >( mpChartView );
1431 : }
1432 34 : if(mpChartView)
1433 : {
1434 34 : mpChartView->setViewDirty();
1435 34 : mpChartView->update();
1436 34 : mpChartView->updateOpenGLWindow();
1437 : }
1438 34 : }
1439 :
1440 108 : } // namespace chart
1441 :
1442 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|