tdf#121991 Chart OOXML import: fix deleted legend entries

The legend showed deleted legend entries too.

Change-Id: I1e205cdfc4262c73d2bb189237d6bc316781931d
Reviewed-on: https://gerrit.libreoffice.org/84516
Reviewed-by: László Németh <nemeth@numbertext.org>
Tested-by: László Németh <nemeth@numbertext.org>
This commit is contained in:
Tünde Tóth
2019-12-04 16:17:09 +01:00
committed by László Németh
parent 4a8d3b8028
commit cea1ae2a4f
9 changed files with 127 additions and 3 deletions

View File

@@ -148,6 +148,7 @@ public:
void testXaxisValues();
void testTdf123504();
void testTdf122765();
void testTdf121991();
CPPUNIT_TEST_SUITE(Chart2ImportTest);
CPPUNIT_TEST(Fdo60083);
@@ -245,6 +246,7 @@ public:
CPPUNIT_TEST(testXaxisValues);
CPPUNIT_TEST(testTdf123504);
CPPUNIT_TEST(testTdf122765);
CPPUNIT_TEST(testTdf121991);
CPPUNIT_TEST_SUITE_END();
@@ -2281,6 +2283,19 @@ void Chart2ImportTest::testTdf122765()
CPPUNIT_ASSERT_GREATER(sal_Int32(7000), aSlicePosition.X);
}
void Chart2ImportTest::testTdf121991()
{
load("/chart2/qa/extras/data/xlsx/", "deleted_legend_entry.xlsx");
Reference< chart2::XChartDocument > xChartDoc = getChartDocFromSheet(0, mxComponent);
CPPUNIT_ASSERT(xChartDoc.is());
Reference<chart2::XDataSeries> xDataSeries(getDataSeriesFromDoc(xChartDoc, 1));
CPPUNIT_ASSERT(xDataSeries.is());
Reference<beans::XPropertySet> xPropertySet(xDataSeries, uno::UNO_QUERY_THROW);
bool bShowLegendEntry = true;
CPPUNIT_ASSERT(xPropertySet->getPropertyValue("ShowLegendEntry") >>= bShowLegendEntry);
CPPUNIT_ASSERT(!bShowLegendEntry);
}
CPPUNIT_TEST_SUITE_REGISTRATION(Chart2ImportTest);
CPPUNIT_PLUGIN_IMPLEMENT();

Binary file not shown.

View File

@@ -55,6 +55,18 @@ public:
virtual ::oox::core::ContextHandlerRef onCreateContext( sal_Int32 nElement, const AttributeList& rAttribs ) override;
};
struct LegendEntryModel;
/** Handler for a chart legend entry context (c:legendEntry element).
*/
class LegendEntryContext : public ContextBase< LegendEntryModel >
{
public:
explicit LegendEntryContext( ::oox::core::ContextHandler2Helper& rParent, LegendEntryModel& rModel );
virtual ~LegendEntryContext() override;
virtual ::oox::core::ContextHandlerRef onCreateContext( sal_Int32 nElement, const AttributeList& rAttribs ) override;
};
struct LegendModel;

View File

@@ -90,6 +90,9 @@ public:
/** Creates a legend object and attaches it at the passed diagram. */
void convertFromModel(
const css::uno::Reference< css::chart2::XDiagram >& rxDiagram );
private:
void legendEntriesFormatting(const css::uno::Reference<css::chart2::XDiagram>& rxDiagram);
};

View File

@@ -57,12 +57,23 @@ struct TitleModel
~TitleModel();
};
struct LegendEntryModel
{
sal_Int32 mnLegendEntryIdx; /// Legend entry index.
bool mbLabelDeleted; /// True = legend label deleted.
LegendEntryModel();
~LegendEntryModel();
};
struct LegendModel
{
typedef ModelRef< Shape > ShapeRef;
typedef ModelRef< TextBody > TextBodyRef;
typedef ModelRef< LayoutModel > LayoutRef;
typedef ModelVector< LegendEntryModel > LegendEntryVector;
typedef ModelRef< Shape > ShapeRef;
typedef ModelRef< TextBody > TextBodyRef;
typedef ModelRef< LayoutModel > LayoutRef;
LegendEntryVector maLegendEntries; /// Legend entries formatting.
ShapeRef mxShapeProp; /// Legend shape formatting.
TextBodyRef mxTextProp; /// Legend text formatting.
LayoutRef mxLayout; /// Layout/position of the legend.

View File

@@ -114,6 +114,31 @@ ContextHandlerRef TitleContext::onCreateContext( sal_Int32 nElement, const Attri
return nullptr;
}
LegendEntryContext::LegendEntryContext( ContextHandler2Helper& rParent, LegendEntryModel& rModel ) :
ContextBase< LegendEntryModel >( rParent, rModel )
{
}
LegendEntryContext::~LegendEntryContext()
{
}
ContextHandlerRef LegendEntryContext::onCreateContext( sal_Int32 nElement, const AttributeList& rAttribs )
{
// this context handler is used for <c:legendEntry> only
switch( nElement )
{
case C_TOKEN( idx ):
mrModel.mnLegendEntryIdx = rAttribs.getInteger( XML_val, -1 );
return nullptr;
case C_TOKEN( delete ):
mrModel.mbLabelDeleted = rAttribs.getBool( XML_val, true );
return nullptr;
}
return nullptr;
}
LegendContext::LegendContext( ContextHandler2Helper& rParent, LegendModel& rModel ) :
ContextBase< LegendModel >( rParent, rModel )
{
@@ -136,6 +161,9 @@ ContextHandlerRef LegendContext::onCreateContext( sal_Int32 nElement, const Attr
mrModel.mnPosition = rAttribs.getToken( XML_val, XML_r );
return nullptr;
case C_TOKEN( legendEntry ):
return new LegendEntryContext( *this, mrModel.maLegendEntries.create() );
case C_TOKEN( overlay ):
mrModel.mbOverlay = rAttribs.getBool( XML_val, !bMSO2007Doc );
return nullptr;

View File

@@ -26,6 +26,9 @@
#include <com/sun/star/chart2/XLegend.hpp>
#include <com/sun/star/chart2/XTitle.hpp>
#include <com/sun/star/chart2/XTitled.hpp>
#include <com/sun/star/chart2/XChartTypeContainer.hpp>
#include <com/sun/star/chart2/XCoordinateSystemContainer.hpp>
#include <com/sun/star/chart2/XDataSeriesContainer.hpp>
#include <osl/diagnose.h>
#include <drawingml/textbody.hxx>
#include <drawingml/textparagraph.hxx>
@@ -249,12 +252,53 @@ void LegendConverter::convertFromModel( const Reference< XDiagram >& rxDiagram )
if(eLegendPos == LegendPosition_CUSTOM && bTopRight && !bManualLayout)
aPropSet.setProperty( PROP_RelativePosition , makeAny(eRelPos));
if (mrModel.maLegendEntries.size() > 0)
legendEntriesFormatting(rxDiagram);
}
catch( Exception& )
{
}
}
void LegendConverter::legendEntriesFormatting(const Reference<XDiagram>& rxDiagram)
{
Reference<XCoordinateSystemContainer> xCooSysContainer(rxDiagram, UNO_QUERY_THROW);
const Sequence<Reference<XCoordinateSystem>> xCooSysSequence(xCooSysContainer->getCoordinateSystems());
if (!xCooSysSequence.hasElements())
return;
sal_Int32 nIndex = 0;
for (const auto& rCooSysSequence : xCooSysSequence)
{
Reference<XChartTypeContainer> xChartTypeContainer(rCooSysSequence, UNO_QUERY_THROW);
const Sequence<Reference<XChartType>> xChartTypeSequence(xChartTypeContainer->getChartTypes());
if (!xChartTypeSequence.hasElements())
continue;
for (const auto& rCT : xChartTypeSequence)
{
Reference<XDataSeriesContainer> xDSCont(rCT, UNO_QUERY);
if (!xDSCont.is())
continue;
const Sequence<Reference<XDataSeries>> aDataSeriesSeq = xDSCont->getDataSeries();
for (const auto& rDataSeries : aDataSeriesSeq)
{
PropertySet aSeriesProp(rDataSeries);
for (const auto& rLegendEntry : mrModel.maLegendEntries)
{
if (nIndex == rLegendEntry->mnLegendEntryIdx)
{
aSeriesProp.setProperty(PROP_ShowLegendEntry, !rLegendEntry->mbLabelDeleted);
break;
}
}
nIndex++;
}
}
}
}
} // namespace chart
} // namespace drawingml
} // namespace oox

View File

@@ -42,6 +42,16 @@ TitleModel::~TitleModel()
{
}
LegendEntryModel::LegendEntryModel() :
mnLegendEntryIdx( -1 ),
mbLabelDeleted( false )
{
}
LegendEntryModel::~LegendEntryModel()
{
}
LegendModel::LegendModel(bool bMSO2007Doc) :
mnPosition( XML_r ),
mbOverlay( !bMSO2007Doc )

View File

@@ -462,6 +462,7 @@ ShowFormulas
ShowGrid
ShowHighLow
ShowInputMessage
ShowLegendEntry
ShowList
ShowNegativeError
ShowObjects