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_xmloff.hxx"
26
27 #include "SchXMLPlotAreaContext.hxx"
28 #include "SchXMLImport.hxx"
29 #include "SchXMLAxisContext.hxx"
30 #include "SchXMLSeries2Context.hxx"
31 #include "SchXMLTools.hxx"
32 #include <tools/debug.hxx>
33 #ifdef DBG_UTIL
34 #include <tools/string.hxx>
35 #endif
36
37 #include <comphelper/processfactory.hxx>
38 #include "xmloff/xmlnmspe.hxx"
39 #include <xmloff/xmlement.hxx>
40 #include <xmloff/nmspmap.hxx>
41 #include <xmloff/xmluconv.hxx>
42 #include <xmloff/prstylei.hxx>
43 #include <xmloff/xmlstyle.hxx>
44 #include "xexptran.hxx"
45 #include <cppuhelper/implbase1.hxx>
46
47 #include <com/sun/star/awt/Point.hpp>
48 #include <com/sun/star/awt/Size.hpp>
49
50 #include <com/sun/star/chart/ChartDataRowSource.hpp>
51 #include <com/sun/star/chart/X3DDisplay.hpp>
52 #include <com/sun/star/chart/XStatisticDisplay.hpp>
53 #include <com/sun/star/chart/XDiagramPositioning.hpp>
54
55 #include <com/sun/star/chart2/data/XRangeXMLConversion.hpp>
56 #include <com/sun/star/chart2/XChartTypeContainer.hpp>
57 #include <com/sun/star/chart2/XDataSeriesContainer.hpp>
58 #include <com/sun/star/chart2/RelativePosition.hpp>
59
60 #include <com/sun/star/drawing/CameraGeometry.hpp>
61 #include <com/sun/star/drawing/FillStyle.hpp>
62 #include <com/sun/star/lang/XServiceInfo.hpp>
63 #include <com/sun/star/util/XStringMapping.hpp>
64 #include <com/sun/star/xml/sax/XAttributeList.hpp>
65
66 using namespace com::sun::star;
67 using namespace ::xmloff::token;
68
69 using ::rtl::OUString;
70 using com::sun::star::uno::Reference;
71
72 namespace
73 {
74
75 struct lcl_AxisHasCategories : public ::std::unary_function< SchXMLAxis, bool >
76 {
operator ()__anona483cd000111::lcl_AxisHasCategories77 bool operator() ( const SchXMLAxis & rAxis )
78 {
79 return rAxis.bHasCategories;
80 }
81 };
82
lcl_ConvertRange(const::rtl::OUString & rRange,const uno::Reference<chart2::XChartDocument> & xDoc)83 OUString lcl_ConvertRange( const ::rtl::OUString & rRange, const uno::Reference< chart2::XChartDocument > & xDoc )
84 {
85 OUString aResult = rRange;
86 if(!xDoc.is())
87 return aResult;
88 uno::Reference< chart2::data::XRangeXMLConversion > xConversion(
89 xDoc->getDataProvider(), uno::UNO_QUERY );
90 if( xConversion.is())
91 aResult = xConversion->convertRangeFromXML( rRange );
92 return aResult;
93 }
94
95 } // anonymous namespace
96
SchXML3DSceneAttributesHelper(SvXMLImport & rImporter)97 SchXML3DSceneAttributesHelper::SchXML3DSceneAttributesHelper( SvXMLImport& rImporter )
98 : SdXML3DSceneAttributesHelper( rImporter )
99 {
100 }
101
getCameraDefaultFromDiagram(const uno::Reference<chart::XDiagram> & xDiagram)102 void SchXML3DSceneAttributesHelper::getCameraDefaultFromDiagram( const uno::Reference< chart::XDiagram >& xDiagram )
103 {
104 //different defaults for camera geometry necessary to workaround wrong behaviour in old chart
105 //in future make this version dependent if we have versioning (metastream) for ole objects
106
107 try
108 {
109 uno::Reference< beans::XPropertySet > xProp( xDiagram, uno::UNO_QUERY );
110 if( xProp.is() )
111 {
112 drawing::CameraGeometry aCamGeo;
113 xProp->getPropertyValue( ::rtl::OUString::createFromAscii("D3DCameraGeometry")) >>= aCamGeo;
114 maVRP.setX( aCamGeo.vrp.PositionX );
115 maVRP.setY( aCamGeo.vrp.PositionY );
116 maVRP.setZ( aCamGeo.vrp.PositionZ );
117 maVPN.setX( aCamGeo.vpn.DirectionX );
118 maVPN.setY( aCamGeo.vpn.DirectionY );
119 maVPN.setZ( aCamGeo.vpn.DirectionZ );
120 maVUP.setX( aCamGeo.vup.DirectionX );
121 maVUP.setY( aCamGeo.vup.DirectionY );
122 maVUP.setZ( aCamGeo.vup.DirectionZ );
123 }
124 }
125 catch( uno::Exception & rEx )
126 {
127 #ifdef DBG_UTIL
128 String aStr( rEx.Message );
129 ByteString aBStr( aStr, RTL_TEXTENCODING_ASCII_US );
130 DBG_ERROR1( "Exception caught for property NumberOfLines: %s", aBStr.GetBuffer());
131 #else
132 (void)rEx; // avoid warning for pro build
133 #endif
134 }
135 }
136
~SchXML3DSceneAttributesHelper()137 SchXML3DSceneAttributesHelper::~SchXML3DSceneAttributesHelper()
138 {
139 }
140
SchXMLPlotAreaContext(SchXMLImportHelper & rImpHelper,SvXMLImport & rImport,const rtl::OUString & rLocalName,const rtl::OUString & rXLinkHRefAttributeToIndicateDataProvider,uno::Sequence<chart::ChartSeriesAddress> & rSeriesAddresses,::rtl::OUString & rCategoriesAddress,::rtl::OUString & rChartAddress,bool & rbHasRangeAtPlotArea,sal_Bool & rAllRangeAddressesAvailable,sal_Bool & rColHasLabels,sal_Bool & rRowHasLabels,chart::ChartDataRowSource & rDataRowSource,SeriesDefaultsAndStyles & rSeriesDefaultsAndStyles,const::rtl::OUString & aChartTypeServiceName,tSchXMLLSequencesPerIndex & rLSequencesPerIndex,const awt::Size & rChartSize)141 SchXMLPlotAreaContext::SchXMLPlotAreaContext(
142 SchXMLImportHelper& rImpHelper,
143 SvXMLImport& rImport, const rtl::OUString& rLocalName,
144 const rtl::OUString& rXLinkHRefAttributeToIndicateDataProvider,
145 uno::Sequence< chart::ChartSeriesAddress >& rSeriesAddresses,
146 ::rtl::OUString& rCategoriesAddress,
147 ::rtl::OUString& rChartAddress,
148 bool& rbHasRangeAtPlotArea,
149 sal_Bool & rAllRangeAddressesAvailable,
150 sal_Bool & rColHasLabels,
151 sal_Bool & rRowHasLabels,
152 chart::ChartDataRowSource & rDataRowSource,
153 SeriesDefaultsAndStyles& rSeriesDefaultsAndStyles,
154 const ::rtl::OUString& aChartTypeServiceName,
155 tSchXMLLSequencesPerIndex & rLSequencesPerIndex,
156 const awt::Size & rChartSize ) :
157 SvXMLImportContext( rImport, XML_NAMESPACE_CHART, rLocalName ),
158 mrImportHelper( rImpHelper ),
159 mrSeriesAddresses( rSeriesAddresses ),
160 mrCategoriesAddress( rCategoriesAddress ),
161 mrSeriesDefaultsAndStyles( rSeriesDefaultsAndStyles ),
162 mnNumOfLinesProp( 0 ),
163 mbStockHasVolume( sal_False ),
164 mnSeries( 0 ),
165 m_aGlobalSeriesImportInfo( rAllRangeAddressesAvailable ),
166 maSceneImportHelper( rImport ),
167 m_aOuterPositioning( rImport ),
168 m_aInnerPositioning( rImport ),
169 mbPercentStacked(false),
170 m_bAxisPositionAttributeImported(false),
171 m_rXLinkHRefAttributeToIndicateDataProvider(rXLinkHRefAttributeToIndicateDataProvider),
172 mrChartAddress( rChartAddress ),
173 m_rbHasRangeAtPlotArea( rbHasRangeAtPlotArea ),
174 mrColHasLabels( rColHasLabels ),
175 mrRowHasLabels( rRowHasLabels ),
176 mrDataRowSource( rDataRowSource ),
177 maChartTypeServiceName( aChartTypeServiceName ),
178 mrLSequencesPerIndex( rLSequencesPerIndex ),
179 mbGlobalChartTypeUsedBySeries( false ),
180 maChartSize( rChartSize )
181 {
182 m_rbHasRangeAtPlotArea = false;
183
184 // get Diagram
185 uno::Reference< chart::XChartDocument > xDoc( rImpHelper.GetChartDocument(), uno::UNO_QUERY );
186 if( xDoc.is())
187 {
188 mxDiagram = xDoc->getDiagram();
189 mxNewDoc.set( xDoc, uno::UNO_QUERY );
190
191 maSceneImportHelper.getCameraDefaultFromDiagram( mxDiagram );
192 }
193 DBG_ASSERT( mxDiagram.is(), "Couldn't get XDiagram" );
194
195 // turn off all axes initially
196 uno::Any aFalseBool;
197 aFalseBool <<= (sal_Bool)(sal_False);
198
199 uno::Reference< lang::XServiceInfo > xInfo( mxDiagram, uno::UNO_QUERY );
200 uno::Reference< beans::XPropertySet > xProp( mxDiagram, uno::UNO_QUERY );
201 if( xInfo.is() &&
202 xProp.is())
203 {
204 try
205 {
206 xProp->setPropertyValue(
207 rtl::OUString::createFromAscii( "HasXAxis" ), aFalseBool );
208 xProp->setPropertyValue(
209 rtl::OUString::createFromAscii( "HasXAxisGrid" ), aFalseBool );
210 xProp->setPropertyValue(
211 rtl::OUString::createFromAscii( "HasXAxisDescription" ), aFalseBool );
212 xProp->setPropertyValue(
213 rtl::OUString::createFromAscii( "HasSecondaryXAxis" ), aFalseBool );
214 xProp->setPropertyValue(
215 rtl::OUString::createFromAscii( "HasSecondaryXAxisDescription" ), aFalseBool );
216
217 xProp->setPropertyValue(
218 rtl::OUString::createFromAscii( "HasYAxis" ), aFalseBool );
219 xProp->setPropertyValue(
220 rtl::OUString::createFromAscii( "HasYAxisGrid" ), aFalseBool );
221 xProp->setPropertyValue(
222 rtl::OUString::createFromAscii( "HasYAxisDescription" ), aFalseBool );
223 xProp->setPropertyValue(
224 rtl::OUString::createFromAscii( "HasSecondaryYAxis" ), aFalseBool );
225 xProp->setPropertyValue(
226 rtl::OUString::createFromAscii( "HasSecondaryYAxisDescription" ), aFalseBool );
227
228 xProp->setPropertyValue(
229 rtl::OUString::createFromAscii( "HasZAxis" ), aFalseBool );
230 xProp->setPropertyValue(
231 rtl::OUString::createFromAscii( "HasZAxisDescription" ), aFalseBool );
232
233 uno::Any aAny;
234 chart::ChartDataRowSource eSource = chart::ChartDataRowSource_COLUMNS;
235 aAny <<= eSource;
236 xProp->setPropertyValue( rtl::OUString::createFromAscii( "DataRowSource" ), aAny );
237 }
238 catch( beans::UnknownPropertyException & )
239 {
240 DBG_ERROR( "Property required by service not supported" );
241 }
242 }
243 }
244
~SchXMLPlotAreaContext()245 SchXMLPlotAreaContext::~SchXMLPlotAreaContext()
246 {}
247
StartElement(const uno::Reference<xml::sax::XAttributeList> & xAttrList)248 void SchXMLPlotAreaContext::StartElement( const uno::Reference< xml::sax::XAttributeList >& xAttrList )
249 {
250 // parse attributes
251 sal_Int16 nAttrCount = xAttrList.is()? xAttrList->getLength(): 0;
252 const SvXMLTokenMap& rAttrTokenMap = mrImportHelper.GetPlotAreaAttrTokenMap();
253 uno::Reference< chart2::XChartDocument > xNewDoc( GetImport().GetModel(), uno::UNO_QUERY );
254
255 for( sal_Int16 i = 0; i < nAttrCount; i++ )
256 {
257 rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
258 rtl::OUString aLocalName;
259 rtl::OUString aValue = xAttrList->getValueByIndex( i );
260 sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName( sAttrName, &aLocalName );
261
262 switch( rAttrTokenMap.Get( nPrefix, aLocalName ))
263 {
264 case XML_TOK_PA_X:
265 case XML_TOK_PA_Y:
266 case XML_TOK_PA_WIDTH:
267 case XML_TOK_PA_HEIGHT:
268 m_aOuterPositioning.readPositioningAttribute( nPrefix, aLocalName, aValue );
269 break;
270 case XML_TOK_PA_STYLE_NAME:
271 msAutoStyleName = aValue;
272 break;
273 case XML_TOK_PA_CHART_ADDRESS:
274 mrChartAddress = lcl_ConvertRange( aValue, xNewDoc );
275 // indicator for getting data from the outside
276 m_rbHasRangeAtPlotArea = true;
277 break;
278 case XML_TOK_PA_DS_HAS_LABELS:
279 {
280 if( aValue.equals( ::xmloff::token::GetXMLToken( ::xmloff::token::XML_BOTH )))
281 mrColHasLabels = mrRowHasLabels = sal_True;
282 else if( aValue.equals( ::xmloff::token::GetXMLToken( ::xmloff::token::XML_ROW )))
283 mrRowHasLabels = sal_True;
284 else if( aValue.equals( ::xmloff::token::GetXMLToken( ::xmloff::token::XML_COLUMN )))
285 mrColHasLabels = sal_True;
286 }
287 break;
288 case XML_TOK_PA_TRANSFORM:
289 case XML_TOK_PA_VRP:
290 case XML_TOK_PA_VPN:
291 case XML_TOK_PA_VUP:
292 case XML_TOK_PA_PROJECTION:
293 case XML_TOK_PA_DISTANCE:
294 case XML_TOK_PA_FOCAL_LENGTH:
295 case XML_TOK_PA_SHADOW_SLANT:
296 case XML_TOK_PA_SHADE_MODE:
297 case XML_TOK_PA_AMBIENT_COLOR:
298 case XML_TOK_PA_LIGHTING_MODE:
299 maSceneImportHelper.processSceneAttribute( nPrefix, aLocalName, aValue );
300 break;
301 }
302 }
303
304 if( ! mxNewDoc.is())
305 {
306 uno::Reference< beans::XPropertySet > xDocProp( mrImportHelper.GetChartDocument(), uno::UNO_QUERY );
307 if( xDocProp.is())
308 {
309 try
310 {
311 uno::Any aAny;
312 aAny <<= (sal_Bool)(mrColHasLabels);
313 xDocProp->setPropertyValue(
314 ::rtl::OUString::createFromAscii( "DataSourceLabelsInFirstColumn" ),
315 aAny );
316
317 aAny <<= (sal_Bool)(mrRowHasLabels);
318 xDocProp->setPropertyValue(
319 ::rtl::OUString::createFromAscii( "DataSourceLabelsInFirstRow" ),
320 aAny );
321 }
322 catch( beans::UnknownPropertyException & )
323 {
324 DBG_ERRORFILE( "Properties missing" );
325 }
326 }
327 }
328
329 // set properties
330 uno::Reference< beans::XPropertySet > xProp( mxDiagram, uno::UNO_QUERY );
331 if( msAutoStyleName.getLength())
332 {
333 if( xProp.is())
334 {
335 const SvXMLStylesContext* pStylesCtxt = mrImportHelper.GetAutoStylesContext();
336 if( pStylesCtxt )
337 {
338 const SvXMLStyleContext* pStyle = pStylesCtxt->FindStyleChildContext(
339 mrImportHelper.GetChartFamilyID(), msAutoStyleName );
340
341 XMLPropStyleContext* pPropStyleContext =
342 const_cast< XMLPropStyleContext * >(
343 dynamic_cast< const XMLPropStyleContext * >( pStyle ) );
344 if( pPropStyleContext )
345 {
346 pPropStyleContext->FillPropertySet( xProp );
347
348 // get the data row source that was set without having data
349 xProp->getPropertyValue( ::rtl::OUString::createFromAscii("DataRowSource"))
350 >>= mrDataRowSource;
351
352 //lines on/off
353 //this old property is not supported fully anymore with the new chart, so we need to get the information a little bit different from similar properties
354 mrSeriesDefaultsAndStyles.maLinesOnProperty = SchXMLTools::getPropertyFromContext(
355 ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Lines")), pPropStyleContext, pStylesCtxt );
356
357 //handle automatic position and size
358 m_aOuterPositioning.readAutomaticPositioningProperties( pPropStyleContext, pStylesCtxt );
359
360 //correct default starting angle for old 3D pies
361 if( SchXMLTools::isDocumentGeneratedWithOpenOfficeOlderThan3_0( GetImport().GetModel() ) )
362 {
363 bool bIs3d = false;
364 if( xProp.is() && ( xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Dim3D"))) >>= bIs3d ) &&
365 bIs3d )
366 {
367 if( maChartTypeServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart2.PieChartType" ))
368 || maChartTypeServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart2.DonutChartType" )) )
369 {
370 ::rtl::OUString aPropName( ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("StartingAngle")) );
371 uno::Any aAStartingAngle( SchXMLTools::getPropertyFromContext( aPropName, pPropStyleContext, pStylesCtxt ) );
372 if( !aAStartingAngle.hasValue() )
373 xProp->setPropertyValue( aPropName, uno::makeAny(sal_Int32(0)) ) ;
374 }
375 }
376 }
377 }
378 }
379 }
380 }
381
382 //remember default values for dataseries
383 if(xProp.is())
384 try
385 {
386 mrSeriesDefaultsAndStyles.maSymbolTypeDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("SymbolType")));
387 mrSeriesDefaultsAndStyles.maDataCaptionDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("DataCaption")));
388
389 mrSeriesDefaultsAndStyles.maErrorIndicatorDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("ErrorIndicator")));
390 mrSeriesDefaultsAndStyles.maErrorCategoryDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("ErrorCategory")));
391 mrSeriesDefaultsAndStyles.maConstantErrorLowDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("ConstantErrorLow")));
392 mrSeriesDefaultsAndStyles.maConstantErrorHighDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("ConstantErrorHigh")));
393 mrSeriesDefaultsAndStyles.maPercentageErrorDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("PercentageError")));
394 mrSeriesDefaultsAndStyles.maErrorMarginDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("ErrorMargin")));
395
396 mrSeriesDefaultsAndStyles.maMeanValueDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("MeanValue")));
397 mrSeriesDefaultsAndStyles.maRegressionCurvesDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("RegressionCurves")));
398
399 bool bStacked = false;
400 mrSeriesDefaultsAndStyles.maStackedDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Stacked")));
401 mrSeriesDefaultsAndStyles.maStackedDefault >>= bStacked;
402 mrSeriesDefaultsAndStyles.maPercentDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Percent")));
403 mrSeriesDefaultsAndStyles.maPercentDefault >>= mbPercentStacked;
404 mrSeriesDefaultsAndStyles.maStackedBarsConnectedDefault = xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("StackedBarsConnected")));
405
406 // deep
407 uno::Any aDeepProperty( xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Deep"))));
408 // #124488# old versions store a 3d area and 3D line deep chart with Deep==false => workaround for this
409 if( ! (bStacked || mbPercentStacked ))
410 {
411 if( SchXMLTools::isDocumentGeneratedWithOpenOfficeOlderThan2_3( GetImport().GetModel() ) )
412 {
413 bool bIs3d = false;
414 if( ( xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Dim3D"))) >>= bIs3d ) &&
415 bIs3d )
416 {
417 if( maChartTypeServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart2.AreaChartType" )) ||
418 maChartTypeServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart2.LineChartType" )) )
419 {
420 aDeepProperty <<= uno::makeAny( true );
421 }
422 }
423 }
424 }
425 mrSeriesDefaultsAndStyles.maDeepDefault = aDeepProperty;
426
427 xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("NumberOfLines"))) >>= mnNumOfLinesProp;
428 xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Volume"))) >>= mbStockHasVolume;
429 }
430 catch( uno::Exception & rEx )
431 {
432 #ifdef DBG_UTIL
433 String aStr( rEx.Message );
434 ByteString aBStr( aStr, RTL_TEXTENCODING_ASCII_US );
435 DBG_ERROR1( "PlotAreaContext:EndElement(): Exception caught: %s", aBStr.GetBuffer());
436 #else
437 (void)rEx; // avoid warning for pro build
438 #endif
439 }
440 //
441
442 bool bCreateInternalDataProvider = false;
443 if( m_rXLinkHRefAttributeToIndicateDataProvider.equalsAscii( "." ) ) //data comes from the chart itself
444 bCreateInternalDataProvider = true;
445 else if( m_rXLinkHRefAttributeToIndicateDataProvider.equalsAscii( ".." ) ) //data comes from the parent application
446 bCreateInternalDataProvider = false;
447 else if( m_rXLinkHRefAttributeToIndicateDataProvider.getLength() ) //not supported so far to get the data by sibling objects -> fall back to chart itself
448 bCreateInternalDataProvider = true;
449 else if( !m_rbHasRangeAtPlotArea )
450 bCreateInternalDataProvider = true;
451
452 if( bCreateInternalDataProvider && mxNewDoc.is() )
453 {
454 // we have no complete range => we have own data, so switch the data
455 // provider to internal. Clone is not necessary, as we don't have any
456 // data yet.
457 mxNewDoc->createInternalDataProvider( false /* bCloneExistingData */ );
458 if( xProp.is() && mrDataRowSource!=chart::ChartDataRowSource_COLUMNS )
459 xProp->setPropertyValue( rtl::OUString::createFromAscii( "DataRowSource" ), uno::makeAny(mrDataRowSource) );
460 }
461 }
462
CreateChildContext(sal_uInt16 nPrefix,const rtl::OUString & rLocalName,const uno::Reference<xml::sax::XAttributeList> & xAttrList)463 SvXMLImportContext* SchXMLPlotAreaContext::CreateChildContext(
464 sal_uInt16 nPrefix,
465 const rtl::OUString& rLocalName,
466 const uno::Reference< xml::sax::XAttributeList >& xAttrList )
467 {
468 SvXMLImportContext* pContext = 0;
469 const SvXMLTokenMap& rTokenMap = mrImportHelper.GetPlotAreaElemTokenMap();
470
471 switch( rTokenMap.Get( nPrefix, rLocalName ))
472 {
473 case XML_TOK_PA_COORDINATE_REGION_EXT:
474 case XML_TOK_PA_COORDINATE_REGION:
475 {
476 pContext = new SchXMLCoordinateRegionContext( GetImport(), nPrefix, rLocalName, m_aInnerPositioning );
477 }
478 break;
479
480 case XML_TOK_PA_AXIS:
481 {
482 bool bAddMissingXAxisForNetCharts = false;
483 bool bAdaptWrongPercentScaleValues = false;
484 if( SchXMLTools::isDocumentGeneratedWithOpenOfficeOlderThan2_3( GetImport().GetModel() ) )
485 {
486 //correct errors from older versions
487
488 // for NetCharts there were no xAxis exported to older files
489 // so we need to add the x axis here for those old NetChart files
490 if( maChartTypeServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart2.NetChartType" )) )
491 bAddMissingXAxisForNetCharts = true;
492
493 //Issue 59288
494 if( mbPercentStacked )
495 bAdaptWrongPercentScaleValues = true;
496 }
497
498 bool bAdaptXAxisOrientationForOld2DBarCharts = false;
499 if( SchXMLTools::isDocumentGeneratedWithOpenOfficeOlderThan2_4( GetImport().GetModel() ) )
500 {
501 //issue74660
502 if( maChartTypeServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart2.ColumnChartType" )) )
503 bAdaptXAxisOrientationForOld2DBarCharts = true;
504 }
505
506 pContext = new SchXMLAxisContext( mrImportHelper, GetImport(), rLocalName, mxDiagram, maAxes, mrCategoriesAddress,
507 bAddMissingXAxisForNetCharts, bAdaptWrongPercentScaleValues, bAdaptXAxisOrientationForOld2DBarCharts, m_bAxisPositionAttributeImported );
508 }
509 break;
510
511 case XML_TOK_PA_SERIES:
512 {
513 if( mxNewDoc.is())
514 {
515 pContext = new SchXMLSeries2Context(
516 mrImportHelper, GetImport(), rLocalName,
517 mxNewDoc, maAxes,
518 mrSeriesDefaultsAndStyles.maSeriesStyleList,
519 mnSeries,
520 mbStockHasVolume,
521 m_aGlobalSeriesImportInfo,
522 maChartTypeServiceName,
523 mrLSequencesPerIndex,
524 mbGlobalChartTypeUsedBySeries, maChartSize );
525 }
526 mnSeries++;
527 }
528 break;
529
530 case XML_TOK_PA_WALL:
531 pContext = new SchXMLWallFloorContext( mrImportHelper, GetImport(), nPrefix, rLocalName, mxDiagram,
532 SchXMLWallFloorContext::CONTEXT_TYPE_WALL );
533 break;
534 case XML_TOK_PA_FLOOR:
535 pContext = new SchXMLWallFloorContext( mrImportHelper, GetImport(), nPrefix, rLocalName, mxDiagram,
536 SchXMLWallFloorContext::CONTEXT_TYPE_FLOOR );
537 break;
538
539 case XML_TOK_PA_LIGHT_SOURCE:
540 pContext = maSceneImportHelper.create3DLightContext( nPrefix, rLocalName, xAttrList );
541 break;
542
543 // elements for stock charts
544 case XML_TOK_PA_STOCK_GAIN:
545 pContext = new SchXMLStockContext( mrImportHelper, GetImport(), nPrefix, rLocalName, mxDiagram,
546 SchXMLStockContext::CONTEXT_TYPE_GAIN );
547 break;
548 case XML_TOK_PA_STOCK_LOSS:
549 pContext = new SchXMLStockContext( mrImportHelper, GetImport(), nPrefix, rLocalName, mxDiagram,
550 SchXMLStockContext::CONTEXT_TYPE_LOSS );
551 break;
552 case XML_TOK_PA_STOCK_RANGE:
553 pContext = new SchXMLStockContext( mrImportHelper, GetImport(), nPrefix, rLocalName, mxDiagram,
554 SchXMLStockContext::CONTEXT_TYPE_RANGE );
555 break;
556
557 default:
558 pContext = new SvXMLImportContext( GetImport(), nPrefix, rLocalName );
559 }
560
561 return pContext;
562 }
563
EndElement()564 void SchXMLPlotAreaContext::EndElement()
565 {
566 // set categories
567 if( mrCategoriesAddress.getLength() && mxNewDoc.is())
568 {
569 uno::Reference< chart2::data::XDataProvider > xDataProvider(
570 mxNewDoc->getDataProvider() );
571 // @todo: correct coordinate system index
572 sal_Int32 nDimension( 0 );
573 ::std::vector< SchXMLAxis >::const_iterator aIt(
574 ::std::find_if( maAxes.begin(), maAxes.end(), lcl_AxisHasCategories()));
575 if( aIt != maAxes.end())
576 nDimension = static_cast< sal_Int32 >( (*aIt).eDimension );
577 SchXMLTools::CreateCategories(
578 xDataProvider, mxNewDoc, mrCategoriesAddress,
579 0 /* nCooSysIndex */,
580 nDimension, &mrLSequencesPerIndex );
581 }
582
583 uno::Reference< beans::XPropertySet > xDiaProp( mxDiagram, uno::UNO_QUERY );
584 if( xDiaProp.is())
585 {
586 sal_Bool bIsThreeDim = sal_False;
587 uno::Any aAny = xDiaProp->getPropertyValue( ::rtl::OUString::createFromAscii( "Dim3D" ));
588 aAny >>= bIsThreeDim;
589
590 // set 3d scene attributes
591 if( bIsThreeDim )
592 {
593 // set scene attributes at diagram
594 maSceneImportHelper.setSceneAttributes( xDiaProp );
595 }
596
597 // set correct number of lines at series
598 if( ! m_aGlobalSeriesImportInfo.rbAllRangeAddressesAvailable &&
599 mnNumOfLinesProp > 0 &&
600 maChartTypeServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart2.ColumnChartType" )))
601 {
602 try
603 {
604 xDiaProp->setPropertyValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "NumberOfLines" )),
605 uno::makeAny( mnNumOfLinesProp ));
606 }
607 catch( uno::Exception & rEx )
608 {
609 #ifdef DBG_UTIL
610 String aStr( rEx.Message );
611 ByteString aBStr( aStr, RTL_TEXTENCODING_ASCII_US );
612 DBG_ERROR1( "Exception caught for property NumberOfLines: %s", aBStr.GetBuffer());
613 #else
614 (void)rEx; // avoid warning for pro build
615 #endif
616 }
617 }
618
619 // #i32366# stock has volume
620 if( ( 0 == mxDiagram->getDiagramType().reverseCompareToAsciiL(
621 RTL_CONSTASCII_STRINGPARAM( "com.sun.star.chart.StockDiagram" ))) &&
622 mbStockHasVolume )
623 {
624 try
625 {
626 xDiaProp->setPropertyValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Volume" )),
627 uno::makeAny( true ));
628 }
629 catch( uno::Exception & rEx )
630 {
631 #ifdef DBG_UTIL
632 String aStr( rEx.Message );
633 ByteString aBStr( aStr, RTL_TEXTENCODING_ASCII_US );
634 DBG_ERROR1( "Exception caught for property Volume: %s", aBStr.GetBuffer());
635 #else
636 (void)rEx; // avoid warning for pro build
637 #endif
638 }
639 }
640 }
641
642 // set changed size and position after properties (esp. 3d)
643
644 uno::Reference< chart::XDiagramPositioning > xDiaPos( mxDiagram, uno::UNO_QUERY );
645 if( xDiaPos.is())
646 {
647 if( !m_aOuterPositioning.isAutomatic() )
648 {
649 if( m_aInnerPositioning.hasPosSize() )
650 xDiaPos->setDiagramPositionExcludingAxes( m_aInnerPositioning.getRectangle() );
651 else if( m_aOuterPositioning.hasPosSize() )
652 {
653 if( SchXMLTools::isDocumentGeneratedWithOpenOfficeOlderThan3_3( GetImport().GetModel() ) ) //old version of OOo did write a wrong rectangle for the diagram size
654 xDiaPos->setDiagramPositionIncludingAxesAndAxisTitles( m_aOuterPositioning.getRectangle() );
655 else
656 xDiaPos->setDiagramPositionIncludingAxes( m_aOuterPositioning.getRectangle() );
657 }
658 }
659 }
660
661 SchXMLAxisContext::CorrectAxisPositions( uno::Reference< chart2::XChartDocument >( mrImportHelper.GetChartDocument(), uno::UNO_QUERY ), maChartTypeServiceName, GetImport().GetODFVersion(), m_bAxisPositionAttributeImported );
662 }
663
664 // ========================================
665
SchXMLDataPointContext(SchXMLImportHelper & rImpHelper,SvXMLImport & rImport,const rtl::OUString & rLocalName,::std::list<DataRowPointStyle> & rStyleList,const::com::sun::star::uno::Reference<::com::sun::star::chart2::XDataSeries> & xSeries,sal_Int32 & rIndex,bool bSymbolSizeForSeriesIsMissingInFile)666 SchXMLDataPointContext::SchXMLDataPointContext( SchXMLImportHelper& rImpHelper,
667 SvXMLImport& rImport, const rtl::OUString& rLocalName,
668 ::std::list< DataRowPointStyle >& rStyleList,
669 const ::com::sun::star::uno::Reference<
670 ::com::sun::star::chart2::XDataSeries >& xSeries,
671 sal_Int32& rIndex,
672 bool bSymbolSizeForSeriesIsMissingInFile ) :
673 SvXMLImportContext( rImport, XML_NAMESPACE_CHART, rLocalName ),
674 mrImportHelper( rImpHelper ),
675 mrStyleList( rStyleList ),
676 m_xSeries( xSeries ),
677 mrIndex( rIndex ),
678 mbSymbolSizeForSeriesIsMissingInFile( bSymbolSizeForSeriesIsMissingInFile )
679 {
680 }
681
~SchXMLDataPointContext()682 SchXMLDataPointContext::~SchXMLDataPointContext()
683 {
684 }
685
StartElement(const uno::Reference<xml::sax::XAttributeList> & xAttrList)686 void SchXMLDataPointContext::StartElement( const uno::Reference< xml::sax::XAttributeList >& xAttrList )
687 {
688 sal_Int16 nAttrCount = xAttrList.is()? xAttrList->getLength(): 0;
689 ::rtl::OUString aValue;
690 ::rtl::OUString sAutoStyleName;
691 sal_Int32 nRepeat = 1;
692
693 for( sal_Int16 i = 0; i < nAttrCount; i++ )
694 {
695 rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
696 rtl::OUString aLocalName;
697 sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName( sAttrName, &aLocalName );
698
699 if( nPrefix == XML_NAMESPACE_CHART )
700 {
701 if( IsXMLToken( aLocalName, XML_STYLE_NAME ) )
702 sAutoStyleName = xAttrList->getValueByIndex( i );
703 else if( IsXMLToken( aLocalName, XML_REPEATED ) )
704 nRepeat = xAttrList->getValueByIndex( i ).toInt32();
705 }
706 }
707
708 if( sAutoStyleName.getLength())
709 {
710 DataRowPointStyle aStyle(
711 DataRowPointStyle::DATA_POINT,
712 m_xSeries, mrIndex, nRepeat, sAutoStyleName );
713 aStyle.mbSymbolSizeForSeriesIsMissingInFile = mbSymbolSizeForSeriesIsMissingInFile;
714 mrStyleList.push_back( aStyle );
715 }
716 mrIndex += nRepeat;
717 }
718
719 // ========================================
720
SchXMLPositonAttributesHelper(SvXMLImport & rImporter)721 SchXMLPositonAttributesHelper::SchXMLPositonAttributesHelper( SvXMLImport& rImporter )
722 : m_rImport( rImporter )
723 , m_aPosition(0,0)
724 , m_aSize(0,0)
725 , m_bHasSizeWidth( false )
726 , m_bHasSizeHeight( false )
727 , m_bHasPositionX( false )
728 , m_bHasPositionY( false )
729 , m_bAutoSize( false )
730 , m_bAutoPosition( false )
731 {
732 }
733
~SchXMLPositonAttributesHelper()734 SchXMLPositonAttributesHelper::~SchXMLPositonAttributesHelper()
735 {
736 }
737
hasSize() const738 bool SchXMLPositonAttributesHelper::hasSize() const
739 {
740 return m_bHasSizeWidth && m_bHasSizeHeight;
741 }
hasPosition() const742 bool SchXMLPositonAttributesHelper::hasPosition() const
743 {
744 return m_bHasPositionX && m_bHasPositionY;
745 }
hasPosSize() const746 bool SchXMLPositonAttributesHelper::hasPosSize() const
747 {
748 return hasPosition() && hasSize();
749 }
isAutomatic() const750 bool SchXMLPositonAttributesHelper::isAutomatic() const
751 {
752 return m_bAutoSize || m_bAutoPosition;
753 }
getPosition() const754 awt::Point SchXMLPositonAttributesHelper::getPosition() const
755 {
756 return m_aPosition;
757 }
getSize() const758 awt::Size SchXMLPositonAttributesHelper::getSize() const
759 {
760 return m_aSize;
761 }
getRectangle() const762 awt::Rectangle SchXMLPositonAttributesHelper::getRectangle() const
763 {
764 return awt::Rectangle( m_aPosition.X, m_aPosition.Y, m_aSize.Width, m_aSize.Height );
765 }
766
readPositioningAttribute(sal_uInt16 nPrefix,const::rtl::OUString & rLocalName,const::rtl::OUString & rValue)767 bool SchXMLPositonAttributesHelper::readPositioningAttribute( sal_uInt16 nPrefix, const ::rtl::OUString& rLocalName, const ::rtl::OUString& rValue )
768 {
769 //returns true if the attribute was proccessed
770 bool bReturn = true;
771
772 if( XML_NAMESPACE_SVG == nPrefix )
773 {
774 if( IsXMLToken( rLocalName, XML_X ) )
775 {
776 m_rImport.GetMM100UnitConverter().convertMeasure( m_aPosition.X, rValue );
777 m_bHasPositionX = true;
778 }
779 else if( IsXMLToken( rLocalName, XML_Y ) )
780 {
781 m_rImport.GetMM100UnitConverter().convertMeasure( m_aPosition.Y, rValue );
782 m_bHasPositionY = true;
783 }
784 else if( IsXMLToken( rLocalName, XML_WIDTH ) )
785 {
786 m_rImport.GetMM100UnitConverter().convertMeasure( m_aSize.Width, rValue );
787 m_bHasSizeWidth = true;
788 }
789 else if( IsXMLToken( rLocalName, XML_HEIGHT ) )
790 {
791 m_rImport.GetMM100UnitConverter().convertMeasure( m_aSize.Height, rValue );
792 m_bHasSizeHeight = true;
793 }
794 else
795 bReturn = false;
796 }
797 else
798 bReturn = false;
799
800 return bReturn;
801 }
802
803
readAutomaticPositioningProperties(XMLPropStyleContext * pPropStyleContext,const SvXMLStylesContext * pStylesCtxt)804 void SchXMLPositonAttributesHelper::readAutomaticPositioningProperties( XMLPropStyleContext* pPropStyleContext, const SvXMLStylesContext* pStylesCtxt )
805 {
806 if( pPropStyleContext && pStylesCtxt )
807 {
808 //handle automatic position and size
809 SchXMLTools::getPropertyFromContext(
810 ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("AutomaticSize")), pPropStyleContext, pStylesCtxt ) >>= m_bAutoSize;
811 SchXMLTools::getPropertyFromContext(
812 ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("AutomaticPosition")), pPropStyleContext, pStylesCtxt ) >>= m_bAutoPosition;
813 }
814 }
815
816 // ========================================
817
SchXMLCoordinateRegionContext(SvXMLImport & rImport,sal_uInt16 nPrefix,const rtl::OUString & rLocalName,SchXMLPositonAttributesHelper & rPositioning)818 SchXMLCoordinateRegionContext::SchXMLCoordinateRegionContext(
819 SvXMLImport& rImport
820 , sal_uInt16 nPrefix
821 , const rtl::OUString& rLocalName
822 , SchXMLPositonAttributesHelper& rPositioning )
823 : SvXMLImportContext( rImport, nPrefix, rLocalName )
824 , m_rPositioning( rPositioning )
825 {
826 }
827
~SchXMLCoordinateRegionContext()828 SchXMLCoordinateRegionContext::~SchXMLCoordinateRegionContext()
829 {
830 }
831
StartElement(const uno::Reference<xml::sax::XAttributeList> & xAttrList)832 void SchXMLCoordinateRegionContext::StartElement( const uno::Reference< xml::sax::XAttributeList >& xAttrList )
833 {
834 // parse attributes
835 sal_Int16 nAttrCount = xAttrList.is()? xAttrList->getLength(): 0;
836
837 for( sal_Int16 i = 0; i < nAttrCount; i++ )
838 {
839 rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
840 rtl::OUString aLocalName;
841 rtl::OUString aValue = xAttrList->getValueByIndex( i );
842 sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName( sAttrName, &aLocalName );
843 m_rPositioning.readPositioningAttribute( nPrefix, aLocalName, aValue );
844 }
845 }
846
847 // ========================================
848
SchXMLWallFloorContext(SchXMLImportHelper & rImpHelper,SvXMLImport & rImport,sal_uInt16 nPrefix,const rtl::OUString & rLocalName,uno::Reference<chart::XDiagram> & xDiagram,ContextType eContextType)849 SchXMLWallFloorContext::SchXMLWallFloorContext(
850 SchXMLImportHelper& rImpHelper,
851 SvXMLImport& rImport,
852 sal_uInt16 nPrefix,
853 const rtl::OUString& rLocalName,
854 uno::Reference< chart::XDiagram >& xDiagram,
855 ContextType eContextType ) :
856 SvXMLImportContext( rImport, nPrefix, rLocalName ),
857 mrImportHelper( rImpHelper ),
858 mxWallFloorSupplier( xDiagram, uno::UNO_QUERY ),
859 meContextType( eContextType )
860 {
861 }
862
~SchXMLWallFloorContext()863 SchXMLWallFloorContext::~SchXMLWallFloorContext()
864 {
865 }
866
StartElement(const uno::Reference<xml::sax::XAttributeList> & xAttrList)867 void SchXMLWallFloorContext::StartElement( const uno::Reference< xml::sax::XAttributeList >& xAttrList )
868 {
869 if( mxWallFloorSupplier.is())
870 {
871 sal_Int16 nAttrCount = xAttrList.is()? xAttrList->getLength(): 0;
872 rtl::OUString sAutoStyleName;
873
874 for( sal_Int16 i = 0; i < nAttrCount; i++ )
875 {
876 rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
877 rtl::OUString aLocalName;
878 sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName( sAttrName, &aLocalName );
879
880 if( nPrefix == XML_NAMESPACE_CHART &&
881 IsXMLToken( aLocalName, XML_STYLE_NAME ) )
882 {
883 sAutoStyleName = xAttrList->getValueByIndex( i );
884 }
885 }
886
887 // set properties
888 uno::Reference< beans::XPropertySet > xProp( ( meContextType == CONTEXT_TYPE_WALL )
889 ? mxWallFloorSupplier->getWall()
890 : mxWallFloorSupplier->getFloor(),
891 uno::UNO_QUERY );
892 if( xProp.is())
893 {
894 if( sAutoStyleName.getLength())
895 {
896 const SvXMLStylesContext* pStylesCtxt = mrImportHelper.GetAutoStylesContext();
897 if( pStylesCtxt )
898 {
899 const SvXMLStyleContext* pStyle = pStylesCtxt->FindStyleChildContext(
900 mrImportHelper.GetChartFamilyID(), sAutoStyleName );
901
902 if( pStyle && pStyle->ISA( XMLPropStyleContext ))
903 (( XMLPropStyleContext* )pStyle )->FillPropertySet( xProp );
904 }
905 }
906 }
907 }
908 }
909
910 // ========================================
911
SchXMLStockContext(SchXMLImportHelper & rImpHelper,SvXMLImport & rImport,sal_uInt16 nPrefix,const rtl::OUString & rLocalName,uno::Reference<chart::XDiagram> & xDiagram,ContextType eContextType)912 SchXMLStockContext::SchXMLStockContext(
913 SchXMLImportHelper& rImpHelper,
914 SvXMLImport& rImport,
915 sal_uInt16 nPrefix,
916 const rtl::OUString& rLocalName,
917 uno::Reference< chart::XDiagram >& xDiagram,
918 ContextType eContextType ) :
919 SvXMLImportContext( rImport, nPrefix, rLocalName ),
920 mrImportHelper( rImpHelper ),
921 mxStockPropProvider( xDiagram, uno::UNO_QUERY ),
922 meContextType( eContextType )
923 {
924 }
925
~SchXMLStockContext()926 SchXMLStockContext::~SchXMLStockContext()
927 {
928 }
929
StartElement(const uno::Reference<xml::sax::XAttributeList> & xAttrList)930 void SchXMLStockContext::StartElement( const uno::Reference< xml::sax::XAttributeList >& xAttrList )
931 {
932 if( mxStockPropProvider.is())
933 {
934 sal_Int16 nAttrCount = xAttrList.is()? xAttrList->getLength(): 0;
935 rtl::OUString sAutoStyleName;
936
937 for( sal_Int16 i = 0; i < nAttrCount; i++ )
938 {
939 rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
940 rtl::OUString aLocalName;
941 sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName( sAttrName, &aLocalName );
942
943 if( nPrefix == XML_NAMESPACE_CHART &&
944 IsXMLToken( aLocalName, XML_STYLE_NAME ) )
945 {
946 sAutoStyleName = xAttrList->getValueByIndex( i );
947 }
948 }
949
950 if( sAutoStyleName.getLength())
951 {
952 // set properties
953 uno::Reference< beans::XPropertySet > xProp;
954 switch( meContextType )
955 {
956 case CONTEXT_TYPE_GAIN:
957 xProp = mxStockPropProvider->getUpBar();
958 break;
959 case CONTEXT_TYPE_LOSS:
960 xProp = mxStockPropProvider->getDownBar();
961 break;
962 case CONTEXT_TYPE_RANGE:
963 xProp = mxStockPropProvider->getMinMaxLine();
964 break;
965 }
966 if( xProp.is())
967 {
968 const SvXMLStylesContext* pStylesCtxt = mrImportHelper.GetAutoStylesContext();
969 if( pStylesCtxt )
970 {
971 const SvXMLStyleContext* pStyle = pStylesCtxt->FindStyleChildContext(
972 mrImportHelper.GetChartFamilyID(), sAutoStyleName );
973
974 if( pStyle && pStyle->ISA( XMLPropStyleContext ))
975 (( XMLPropStyleContext* )pStyle )->FillPropertySet( xProp );
976 }
977 }
978 }
979 }
980 }
981
982 // ========================================
983
SchXMLStatisticsObjectContext(SchXMLImportHelper & rImpHelper,SvXMLImport & rImport,sal_uInt16 nPrefix,const rtl::OUString & rLocalName,::std::list<DataRowPointStyle> & rStyleList,const::com::sun::star::uno::Reference<::com::sun::star::chart2::XDataSeries> & xSeries,ContextType eContextType,const awt::Size & rChartSize)984 SchXMLStatisticsObjectContext::SchXMLStatisticsObjectContext(
985
986 SchXMLImportHelper& rImpHelper,
987 SvXMLImport& rImport,
988 sal_uInt16 nPrefix,
989 const rtl::OUString& rLocalName,
990 ::std::list< DataRowPointStyle >& rStyleList,
991 const ::com::sun::star::uno::Reference<
992 ::com::sun::star::chart2::XDataSeries >& xSeries,
993 ContextType eContextType,
994 const awt::Size & rChartSize ) :
995
996 SvXMLImportContext( rImport, nPrefix, rLocalName ),
997 mrImportHelper( rImpHelper ),
998 mrStyleList( rStyleList ),
999 m_xSeries( xSeries ),
1000 meContextType( eContextType ),
1001 maChartSize( rChartSize )
1002 {}
1003
~SchXMLStatisticsObjectContext()1004 SchXMLStatisticsObjectContext::~SchXMLStatisticsObjectContext()
1005 {
1006 }
1007
StartElement(const uno::Reference<xml::sax::XAttributeList> & xAttrList)1008 void SchXMLStatisticsObjectContext::StartElement( const uno::Reference< xml::sax::XAttributeList >& xAttrList )
1009 {
1010 sal_Int16 nAttrCount = xAttrList.is()? xAttrList->getLength(): 0;
1011 ::rtl::OUString aValue;
1012 ::rtl::OUString sAutoStyleName;
1013
1014 for( sal_Int16 i = 0; i < nAttrCount; i++ )
1015 {
1016 rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
1017 rtl::OUString aLocalName;
1018 sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName( sAttrName, &aLocalName );
1019
1020 if( nPrefix == XML_NAMESPACE_CHART )
1021 {
1022 if( IsXMLToken( aLocalName, XML_STYLE_NAME ) )
1023 sAutoStyleName = xAttrList->getValueByIndex( i );
1024 }
1025 }
1026
1027 // note: regression-curves must get a style-object even if there is no
1028 // auto-style set, because they can contain an equation
1029 if( sAutoStyleName.getLength() || meContextType == CONTEXT_TYPE_REGRESSION_CURVE )
1030 {
1031 DataRowPointStyle::StyleType eType = DataRowPointStyle::MEAN_VALUE;
1032 switch( meContextType )
1033 {
1034 case CONTEXT_TYPE_MEAN_VALUE_LINE:
1035 eType = DataRowPointStyle::MEAN_VALUE;
1036 break;
1037 case CONTEXT_TYPE_REGRESSION_CURVE:
1038 eType = DataRowPointStyle::REGRESSION;
1039 break;
1040 case CONTEXT_TYPE_ERROR_INDICATOR:
1041 eType = DataRowPointStyle::ERROR_INDICATOR;
1042 break;
1043 }
1044 DataRowPointStyle aStyle(
1045 eType, m_xSeries, -1, 1, sAutoStyleName );
1046 mrStyleList.push_back( aStyle );
1047 }
1048 }
1049
CreateChildContext(sal_uInt16 nPrefix,const rtl::OUString & rLocalName,const uno::Reference<xml::sax::XAttributeList> & xAttrList)1050 SvXMLImportContext* SchXMLStatisticsObjectContext::CreateChildContext(
1051 sal_uInt16 nPrefix,
1052 const rtl::OUString& rLocalName,
1053 const uno::Reference< xml::sax::XAttributeList >& xAttrList )
1054 {
1055 SvXMLImportContext* pContext = 0;
1056
1057 if( nPrefix == XML_NAMESPACE_CHART &&
1058 IsXMLToken( rLocalName, XML_EQUATION ) )
1059 {
1060 pContext = new SchXMLEquationContext(
1061 mrImportHelper, GetImport(), nPrefix, rLocalName, m_xSeries, maChartSize, mrStyleList.back());
1062 }
1063 else
1064 {
1065 pContext = SvXMLImportContext::CreateChildContext( nPrefix, rLocalName, xAttrList );
1066 }
1067
1068 return pContext;
1069 }
1070
1071 // ========================================
1072
SchXMLEquationContext(SchXMLImportHelper & rImpHelper,SvXMLImport & rImport,sal_uInt16 nPrefix,const rtl::OUString & rLocalName,const::com::sun::star::uno::Reference<::com::sun::star::chart2::XDataSeries> & xSeries,const awt::Size & rChartSize,DataRowPointStyle & rRegressionStyle)1073 SchXMLEquationContext::SchXMLEquationContext(
1074 SchXMLImportHelper& rImpHelper,
1075 SvXMLImport& rImport,
1076 sal_uInt16 nPrefix,
1077 const rtl::OUString& rLocalName,
1078 const ::com::sun::star::uno::Reference<
1079 ::com::sun::star::chart2::XDataSeries >& xSeries,
1080 const awt::Size & rChartSize,
1081 DataRowPointStyle & rRegressionStyle ) :
1082 SvXMLImportContext( rImport, nPrefix, rLocalName ),
1083 mrImportHelper( rImpHelper ),
1084 mrRegressionStyle( rRegressionStyle ),
1085 m_xSeries( xSeries ),
1086 maChartSize( rChartSize )
1087 {}
1088
~SchXMLEquationContext()1089 SchXMLEquationContext::~SchXMLEquationContext()
1090 {}
1091
StartElement(const uno::Reference<xml::sax::XAttributeList> & xAttrList)1092 void SchXMLEquationContext::StartElement( const uno::Reference< xml::sax::XAttributeList >& xAttrList )
1093 {
1094 // parse attributes
1095 sal_Int16 nAttrCount = xAttrList.is()? xAttrList->getLength(): 0;
1096 SchXMLImport& rImport = ( SchXMLImport& )GetImport();
1097 const SvXMLTokenMap& rAttrTokenMap = mrImportHelper.GetRegEquationAttrTokenMap();
1098 OUString sAutoStyleName;
1099
1100 sal_Bool bShowEquation = sal_True;
1101 sal_Bool bShowRSquare = sal_False;
1102 awt::Point aPosition;
1103 bool bHasXPos = false;
1104 bool bHasYPos = false;
1105
1106 for( sal_Int16 i = 0; i < nAttrCount; i++ )
1107 {
1108 rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
1109 rtl::OUString aLocalName;
1110 rtl::OUString aValue = xAttrList->getValueByIndex( i );
1111 sal_uInt16 nPrefix = rImport.GetNamespaceMap().GetKeyByAttrName( sAttrName, &aLocalName );
1112
1113 switch( rAttrTokenMap.Get( nPrefix, aLocalName ))
1114 {
1115 case XML_TOK_REGEQ_POS_X:
1116 rImport.GetMM100UnitConverter().convertMeasure( aPosition.X, aValue );
1117 bHasXPos = true;
1118 break;
1119 case XML_TOK_REGEQ_POS_Y:
1120 rImport.GetMM100UnitConverter().convertMeasure( aPosition.Y, aValue );
1121 bHasYPos = true;
1122 break;
1123 case XML_TOK_REGEQ_DISPLAY_EQUATION:
1124 rImport.GetMM100UnitConverter().convertBool( bShowEquation, aValue );
1125 break;
1126 case XML_TOK_REGEQ_DISPLAY_R_SQUARE:
1127 rImport.GetMM100UnitConverter().convertBool( bShowRSquare, aValue );
1128 break;
1129 case XML_TOK_REGEQ_STYLE_NAME:
1130 sAutoStyleName = aValue;
1131 break;
1132 }
1133 }
1134
1135 if( sAutoStyleName.getLength() || bShowEquation || bShowRSquare )
1136 {
1137 uno::Reference< beans::XPropertySet > xEqProp;
1138 uno::Reference< lang::XMultiServiceFactory > xFact( comphelper::getProcessServiceFactory(), uno::UNO_QUERY );
1139 if( xFact.is())
1140 xEqProp.set( xFact->createInstance(
1141 ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.chart2.RegressionEquation" ))), uno::UNO_QUERY );
1142 if( xEqProp.is())
1143 {
1144 if( sAutoStyleName.getLength() )
1145 {
1146 const SvXMLStylesContext* pStylesCtxt = mrImportHelper.GetAutoStylesContext();
1147 if( pStylesCtxt )
1148 {
1149 const SvXMLStyleContext* pStyle = pStylesCtxt->FindStyleChildContext(
1150 mrImportHelper.GetChartFamilyID(), sAutoStyleName );
1151 // note: SvXMLStyleContext::FillPropertySet is not const
1152 XMLPropStyleContext * pPropStyleContext =
1153 const_cast< XMLPropStyleContext * >( dynamic_cast< const XMLPropStyleContext * >( pStyle ));
1154
1155 if( pPropStyleContext )
1156 pPropStyleContext->FillPropertySet( xEqProp );
1157 }
1158 }
1159 xEqProp->setPropertyValue( OUString( RTL_CONSTASCII_USTRINGPARAM("ShowEquation")), uno::makeAny( bShowEquation ));
1160 xEqProp->setPropertyValue( OUString( RTL_CONSTASCII_USTRINGPARAM("ShowCorrelationCoefficient")), uno::makeAny( bShowRSquare ));
1161
1162 if( bHasXPos && bHasYPos )
1163 {
1164 chart2::RelativePosition aRelPos;
1165 aRelPos.Primary = static_cast< double >( aPosition.X ) / static_cast< double >( maChartSize.Width );
1166 aRelPos.Secondary = static_cast< double >( aPosition.Y ) / static_cast< double >( maChartSize.Height );
1167 xEqProp->setPropertyValue( OUString( RTL_CONSTASCII_USTRINGPARAM( "RelativePosition" )),
1168 uno::makeAny( aRelPos ));
1169 }
1170 OSL_ASSERT( mrRegressionStyle.meType == DataRowPointStyle::REGRESSION );
1171 mrRegressionStyle.m_xEquationProperties.set( xEqProp );
1172 }
1173 }
1174 }
1175