1 /**************************************************************
2 *
3 * Licensed to the Apache Software Foundation (ASF) under one
4 * or more contributor license agreements. See the NOTICE file
5 * distributed with this work for additional information
6 * regarding copyright ownership. The ASF licenses this file
7 * to you under the Apache License, Version 2.0 (the
8 * "License"); you may not use this file except in compliance
9 * with the License. You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing,
14 * software distributed under the License is distributed on an
15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16 * KIND, either express or implied. See the License for the
17 * specific language governing permissions and limitations
18 * under the License.
19 *
20 *************************************************************/
21
22
23
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_chart2.hxx"
26 #include "ChartType.hxx"
27 #include "PropertyHelper.hxx"
28 #include "CommonFunctors.hxx"
29 #include "macros.hxx"
30 #include "CartesianCoordinateSystem.hxx"
31 #include "AxisHelper.hxx"
32 #include "CloneHelper.hxx"
33 #include "AxisIndexDefines.hxx"
34 #include "ContainerHelper.hxx"
35 #include <com/sun/star/chart2/AxisType.hpp>
36 #include <com/sun/star/beans/PropertyAttribute.hpp>
37
38 using namespace ::com::sun::star;
39
40 using ::rtl::OUString;
41 using ::com::sun::star::beans::Property;
42 using ::com::sun::star::uno::Sequence;
43 using ::com::sun::star::uno::Reference;
44 using ::com::sun::star::uno::Any;
45 using ::osl::MutexGuard;
46
47 namespace chart
48 {
49
ChartType(const Reference<uno::XComponentContext> & xContext)50 ChartType::ChartType(
51 const Reference< uno::XComponentContext > & xContext ) :
52 ::property::OPropertySet( m_aMutex ),
53 m_xModifyEventForwarder( ModifyListenerHelper::createModifyEventForwarder()),
54 m_xContext( xContext ),
55 m_bNotifyChanges( true )
56 {}
57
ChartType(const ChartType & rOther)58 ChartType::ChartType( const ChartType & rOther ) :
59 MutexContainer(),
60 impl::ChartType_Base(),
61 ::property::OPropertySet( rOther, m_aMutex ),
62 m_xModifyEventForwarder( ModifyListenerHelper::createModifyEventForwarder()),
63 m_xContext( rOther.m_xContext ),
64 m_bNotifyChanges( true )
65 {
66 CloneHelper::CloneRefVector< Reference< chart2::XDataSeries > >( rOther.m_aDataSeries, m_aDataSeries );
67 ModifyListenerHelper::addListenerToAllElements( m_aDataSeries, m_xModifyEventForwarder );
68 }
69
~ChartType()70 ChartType::~ChartType()
71 {
72 ModifyListenerHelper::removeListenerFromAllElements( m_aDataSeries, m_xModifyEventForwarder );
73 m_aDataSeries.clear();
74 }
75
GetComponentContext() const76 Reference< uno::XComponentContext > ChartType::GetComponentContext() const
77 {
78 return m_xContext;
79 }
80
81 // ____ XChartType ____
82 Reference< chart2::XCoordinateSystem > SAL_CALL
createCoordinateSystem(::sal_Int32 DimensionCount)83 ChartType::createCoordinateSystem( ::sal_Int32 DimensionCount )
84 throw (lang::IllegalArgumentException,
85 uno::RuntimeException)
86 {
87 Reference< chart2::XCoordinateSystem > xResult(
88 new CartesianCoordinateSystem(
89 GetComponentContext(), DimensionCount, /* bSwapXAndYAxis */ sal_False ));
90
91 for( sal_Int32 i=0; i<DimensionCount; ++i )
92 {
93 Reference< chart2::XAxis > xAxis( xResult->getAxisByDimension( i, MAIN_AXIS_INDEX ) );
94 if( !xAxis.is() )
95 {
96 OSL_ENSURE(false,"a created coordinate system should have an axis for each dimension");
97 continue;
98 }
99
100 chart2::ScaleData aScaleData = xAxis->getScaleData();
101 aScaleData.Orientation = chart2::AxisOrientation_MATHEMATICAL;
102 aScaleData.Scaling = AxisHelper::createLinearScaling();
103
104 switch( i )
105 {
106 case 0: aScaleData.AxisType = chart2::AxisType::CATEGORY; break;
107 case 2: aScaleData.AxisType = chart2::AxisType::SERIES; break;
108 default: aScaleData.AxisType = chart2::AxisType::REALNUMBER; break;
109 }
110
111 xAxis->setScaleData( aScaleData );
112 }
113
114 return xResult;
115 }
116
getSupportedMandatoryRoles()117 Sequence< OUString > SAL_CALL ChartType::getSupportedMandatoryRoles()
118 throw (uno::RuntimeException)
119 {
120 static Sequence< OUString > aDefaultSeq;
121
122 if( aDefaultSeq.getLength() == 0 )
123 {
124 aDefaultSeq.realloc( 2 );
125 aDefaultSeq[0] = C2U( "label" );
126 aDefaultSeq[1] = C2U( "values-y" );
127 }
128
129 return aDefaultSeq;
130 }
131
getSupportedOptionalRoles()132 Sequence< OUString > SAL_CALL ChartType::getSupportedOptionalRoles()
133 throw (uno::RuntimeException)
134 {
135 static Sequence< OUString > aDefaultOptRolesSeq;
136
137 // if( aDefaultOptRolesSeq.getLength() == 0 )
138 // {
139 // aDefaultOptRolesSeq.realloc( 1 );
140 // aDefaultOptRolesSeq[0] = C2U( "error-bars-y" );
141 // }
142
143 return aDefaultOptRolesSeq;
144 }
145
getRoleOfSequenceForSeriesLabel()146 OUString SAL_CALL ChartType::getRoleOfSequenceForSeriesLabel()
147 throw (uno::RuntimeException)
148 {
149 return C2U( "values-y" );
150 }
151
impl_addDataSeriesWithoutNotification(const Reference<chart2::XDataSeries> & xDataSeries)152 void ChartType::impl_addDataSeriesWithoutNotification(
153 const Reference< chart2::XDataSeries >& xDataSeries )
154 {
155 if( ::std::find( m_aDataSeries.begin(), m_aDataSeries.end(), xDataSeries )
156 != m_aDataSeries.end())
157 throw lang::IllegalArgumentException();
158
159 m_aDataSeries.push_back( xDataSeries );
160 ModifyListenerHelper::addListener( xDataSeries, m_xModifyEventForwarder );
161 }
162
163 // ____ XDataSeriesContainer ____
addDataSeries(const Reference<chart2::XDataSeries> & xDataSeries)164 void SAL_CALL ChartType::addDataSeries( const Reference< chart2::XDataSeries >& xDataSeries )
165 throw (lang::IllegalArgumentException,
166 uno::RuntimeException)
167 {
168 impl_addDataSeriesWithoutNotification( xDataSeries );
169 fireModifyEvent();
170 }
171
removeDataSeries(const Reference<chart2::XDataSeries> & xDataSeries)172 void SAL_CALL ChartType::removeDataSeries( const Reference< chart2::XDataSeries >& xDataSeries )
173 throw (container::NoSuchElementException,
174 uno::RuntimeException)
175 {
176 if( !xDataSeries.is())
177 throw container::NoSuchElementException();
178
179 tDataSeriesContainerType::iterator aIt(
180 ::std::find( m_aDataSeries.begin(), m_aDataSeries.end(), xDataSeries ) );
181
182 if( aIt == m_aDataSeries.end())
183 throw container::NoSuchElementException(
184 C2U( "The given series is no element of this charttype" ),
185 static_cast< uno::XWeak * >( this ));
186
187 ModifyListenerHelper::removeListener( xDataSeries, m_xModifyEventForwarder );
188 m_aDataSeries.erase( aIt );
189 fireModifyEvent();
190 }
191
getDataSeries()192 Sequence< Reference< chart2::XDataSeries > > SAL_CALL ChartType::getDataSeries()
193 throw (uno::RuntimeException)
194 {
195 return ContainerHelper::ContainerToSequence( m_aDataSeries );
196 }
197
setDataSeries(const Sequence<Reference<chart2::XDataSeries>> & aDataSeries)198 void SAL_CALL ChartType::setDataSeries( const Sequence< Reference< chart2::XDataSeries > >& aDataSeries )
199 throw (lang::IllegalArgumentException,
200 uno::RuntimeException)
201 {
202 m_bNotifyChanges = false;
203 try
204 {
205 Sequence< Reference< chart2::XDataSeries > > aOldSeries( this->getDataSeries() );
206 for( sal_Int32 nN=0; nN<aOldSeries.getLength(); ++nN )
207 ModifyListenerHelper::removeListener( aOldSeries[nN], m_xModifyEventForwarder );
208 m_aDataSeries.clear();
209
210 for( sal_Int32 i=0; i<aDataSeries.getLength(); ++i )
211 impl_addDataSeriesWithoutNotification( aDataSeries[i] );
212 }
213 catch( ... )
214 {
215 m_bNotifyChanges = true;
216 throw;
217 }
218 m_bNotifyChanges = true;
219 fireModifyEvent();
220 }
221
222 // ____ OPropertySet ____
GetDefaultValue(sal_Int32) const223 uno::Any ChartType::GetDefaultValue( sal_Int32 /* nHandle */ ) const
224 throw(beans::UnknownPropertyException)
225 {
226 return uno::Any();
227 }
228
229 namespace
230 {
231
232 struct StaticChartTypeInfoHelper_Initializer
233 {
operator ()chart::__anon1268f7890111::StaticChartTypeInfoHelper_Initializer234 ::cppu::OPropertyArrayHelper* operator()()
235 {
236 // using assignment for broken gcc 3.3
237 static ::cppu::OPropertyArrayHelper aPropHelper = ::cppu::OPropertyArrayHelper(
238 Sequence< beans::Property >() );
239 return &aPropHelper;
240 }
241 };
242
243 struct StaticChartTypeInfoHelper : public rtl::StaticAggregate< ::cppu::OPropertyArrayHelper, StaticChartTypeInfoHelper_Initializer >
244 {
245 };
246
247 struct StaticChartTypeInfo_Initializer
248 {
operator ()chart::__anon1268f7890111::StaticChartTypeInfo_Initializer249 uno::Reference< beans::XPropertySetInfo >* operator()()
250 {
251 static uno::Reference< beans::XPropertySetInfo > xPropertySetInfo(
252 ::cppu::OPropertySetHelper::createPropertySetInfo(*StaticChartTypeInfoHelper::get() ) );
253 return &xPropertySetInfo;
254 }
255 };
256
257 struct StaticChartTypeInfo : public rtl::StaticAggregate< uno::Reference< beans::XPropertySetInfo >, StaticChartTypeInfo_Initializer >
258 {
259 };
260
261 }
262
263 // ____ OPropertySet ____
getInfoHelper()264 ::cppu::IPropertyArrayHelper & SAL_CALL ChartType::getInfoHelper()
265 {
266 return *StaticChartTypeInfoHelper::get();
267 }
268
269 // ____ XPropertySet ____
getPropertySetInfo()270 uno::Reference< beans::XPropertySetInfo > SAL_CALL ChartType::getPropertySetInfo()
271 throw (uno::RuntimeException)
272 {
273 return *StaticChartTypeInfo::get();
274 }
275
276 // ____ XModifyBroadcaster ____
addModifyListener(const uno::Reference<util::XModifyListener> & aListener)277 void SAL_CALL ChartType::addModifyListener( const uno::Reference< util::XModifyListener >& aListener )
278 throw (uno::RuntimeException)
279 {
280 try
281 {
282 uno::Reference< util::XModifyBroadcaster > xBroadcaster( m_xModifyEventForwarder, uno::UNO_QUERY_THROW );
283 xBroadcaster->addModifyListener( aListener );
284 }
285 catch( const uno::Exception & ex )
286 {
287 ASSERT_EXCEPTION( ex );
288 }
289 }
290
removeModifyListener(const uno::Reference<util::XModifyListener> & aListener)291 void SAL_CALL ChartType::removeModifyListener( const uno::Reference< util::XModifyListener >& aListener )
292 throw (uno::RuntimeException)
293 {
294 try
295 {
296 uno::Reference< util::XModifyBroadcaster > xBroadcaster( m_xModifyEventForwarder, uno::UNO_QUERY_THROW );
297 xBroadcaster->removeModifyListener( aListener );
298 }
299 catch( const uno::Exception & ex )
300 {
301 ASSERT_EXCEPTION( ex );
302 }
303 }
304
305 // ____ XModifyListener ____
modified(const lang::EventObject & aEvent)306 void SAL_CALL ChartType::modified( const lang::EventObject& aEvent )
307 throw (uno::RuntimeException)
308 {
309 m_xModifyEventForwarder->modified( aEvent );
310 }
311
312 // ____ XEventListener (base of XModifyListener) ____
disposing(const lang::EventObject &)313 void SAL_CALL ChartType::disposing( const lang::EventObject& /* Source */ )
314 throw (uno::RuntimeException)
315 {
316 // nothing
317 }
318
319 // ____ OPropertySet ____
firePropertyChangeEvent()320 void ChartType::firePropertyChangeEvent()
321 {
322 fireModifyEvent();
323 }
324
fireModifyEvent()325 void ChartType::fireModifyEvent()
326 {
327 if( m_bNotifyChanges )
328 m_xModifyEventForwarder->modified( lang::EventObject( static_cast< uno::XWeak* >( this )));
329 }
330
331 // ================================================================================
332
333 using impl::ChartType_Base;
334
335 IMPLEMENT_FORWARD_XINTERFACE2( ChartType, ChartType_Base, ::property::OPropertySet )
336 IMPLEMENT_FORWARD_XTYPEPROVIDER2( ChartType, ChartType_Base, ::property::OPropertySet )
337
338 } // namespace chart
339