tdf#138556 Don’t add Open Values to stock chart types 1 and 3

A new function was defined, XdataInterpreter::getChartTypeSpecificData.
Being 100% chart-type-agnostic when retrieving chart data is impossible;
candlestick charts can have different numbers of sequences per series,
and this information is not present in any other chart type.

Change-Id: I0f54b09202c42667331b083d54d90e4ceee81083
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/113075
Tested-by: Jenkins
Reviewed-by: Noel Grandin <noel.grandin@collabora.co.uk>
This commit is contained in:
Aritz Erkiaga 2021-03-25 09:25:27 +01:00 committed by Noel Grandin
parent 9431984f8d
commit c8598f28db
9 changed files with 157 additions and 2 deletions

View File

@ -261,6 +261,26 @@ void lcl_SetSequenceRole(
xProp->setPropertyValue( "Role" , uno::Any( rRole ));
}
Sequence< OUString > lcl_CopyExcludingValuesFirst(
Sequence< OUString > const & i_aInput )
{
Sequence< OUString > aOutput( i_aInput.getLength());
int nSourceIndex, nDestIndex;
for( nSourceIndex = nDestIndex = 0; nSourceIndex < i_aInput.getLength(); nSourceIndex++ )
{
if( i_aInput[nSourceIndex] == "values-first" )
{
aOutput.realloc( aOutput.getLength() - 1 );
}
else
{
aOutput[nDestIndex] = i_aInput[nSourceIndex];
nDestIndex++;
}
}
return aOutput;
}
Reference< XDataSeries > lcl_CreateNewSeries(
const Reference< uno::XComponentContext > & xContext,
const Reference< XChartType > & xChartType,
@ -309,8 +329,29 @@ Reference< XDataSeries > lcl_CreateNewSeries(
std::vector< Reference< data::XLabeledDataSequence > > aNewSequences;
const OUString aRoleOfSeqForSeriesLabel = xChartType->getRoleOfSequenceForSeriesLabel();
const OUString aLabel(::chart::SchResId(STR_DATA_UNNAMED_SERIES));
const Sequence< OUString > aRoles( xChartType->getSupportedMandatoryRoles());
const Sequence< OUString > aOptRoles( xChartType->getSupportedOptionalRoles());
Sequence< OUString > aPossibleRoles( xChartType->getSupportedMandatoryRoles());
Sequence< OUString > aPossibleOptRoles( xChartType->getSupportedOptionalRoles());
//special handling for candlestick type
if( xTemplate.is())
{
Reference< XDataInterpreter > xInterpreter( xTemplate->getDataInterpreter());
if( xInterpreter.is())
{
sal_Int32 nStockVariant;
if( xInterpreter->getChartTypeSpecificData("stock variant") >>= nStockVariant )
{
if( nStockVariant == 0 || nStockVariant == 2) {
//delete "values-first" role
aPossibleRoles = lcl_CopyExcludingValuesFirst(aPossibleRoles);
aPossibleOptRoles = lcl_CopyExcludingValuesFirst(aPossibleOptRoles);
}
}
}
}
const Sequence< OUString > aRoles( aPossibleRoles );
const Sequence< OUString > aOptRoles( aPossibleOptRoles );
for(OUString const & role : aRoles)
{

View File

@ -298,6 +298,12 @@ Reference< data::XDataSource > SAL_CALL DataInterpreter::mergeInterpretedData(
return DataSourceHelper::createDataSource( comphelper::containerToSequence( aResultVec ) );
}
uno::Any SAL_CALL DataInterpreter::getChartTypeSpecificData(
const OUString & )
{
return uno::Any();
}
// convenience methods
OUString DataInterpreter::GetRole( const Reference< data::XDataSequence > & xSeq )

View File

@ -68,6 +68,8 @@ protected:
const css::chart2::InterpretedData& aInterpretedData ) override;
virtual css::uno::Reference< css::chart2::data::XDataSource > SAL_CALL mergeInterpretedData(
const css::chart2::InterpretedData& aInterpretedData ) override;
virtual css::uno::Any SAL_CALL getChartTypeSpecificData(
const OUString& sKey ) override;
};
} // namespace chart

View File

@ -18,6 +18,7 @@
*/
#include "StockDataInterpreter.hxx"
#include "StockChartTypeTemplate.hxx"
#include <DataSeries.hxx>
#include <com/sun/star/chart2/data/XDataSink.hpp>
#include <tools/diagnose_ex.h>
@ -314,6 +315,23 @@ InterpretedData SAL_CALL StockDataInterpreter::reinterpretDataSeries(
return aInterpretedData;
}
uno::Any SAL_CALL StockDataInterpreter::getChartTypeSpecificData(
const OUString& sKey )
{
if( sKey == "stock variant" )
{
StockChartTypeTemplate::StockVariant eStockVariant( GetStockVariant());
std::map< StockChartTypeTemplate::StockVariant, sal_Int32 > aTranslation {
{ StockChartTypeTemplate::StockVariant::NONE, 0 },
{ StockChartTypeTemplate::StockVariant::Open, 1 },
{ StockChartTypeTemplate::StockVariant::Volume, 2 },
{ StockChartTypeTemplate::StockVariant::VolumeOpen, 3 }
};
return uno::Any( aTranslation[eStockVariant] );
}
return uno::Any();
}
} // namespace chart
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */

View File

@ -42,6 +42,8 @@ protected:
const css::chart2::InterpretedData& aInterpretedData ) override;
virtual css::chart2::InterpretedData SAL_CALL reinterpretDataSeries(
const css::chart2::InterpretedData& aInterpretedData ) override;
virtual css::uno::Any SAL_CALL getChartTypeSpecificData(
const OUString& sKey ) override;
private:
StockChartTypeTemplate::StockVariant m_eStockVariant;

View File

@ -86,6 +86,24 @@ interface XDataInterpreter : ::com::sun::star::uno::XInterface
the result of this method should be <code>xSource</code>.</p>
*/
com::sun::star::chart2::data::XDataSource mergeInterpretedData( [in] InterpretedData aInterpretedData );
/** Get chart information that is specific to a particular chart
type, by key.
@param sKey
name of the piece of data to retrieve.
<p>Supported key strings:</p>
<ul>
<li><tt>"stock variant"</tt>: stock chart variant,
with 0 = neither Open Values nor volume, 1 = Open Values,
2 = volume, 3 = both. Valid for candlestick charts.</li>
</ul>
@return
The value requested, or nothing if not present.
*/
any getChartTypeSpecificData([in] string sKey );
};
} ; // chart2

View File

@ -180,6 +180,7 @@ $(eval $(call gb_Module_add_uicheck_targets,sw,\
UITest_writer_tests6 \
UITest_writer_tests7 \
UITest_sw_table \
UITest_sw_chart \
UITest_sw_findBar \
UITest_sw_findReplace \
UITest_sw_findSimilarity \

12
sw/UITest_sw_chart.mk Normal file
View File

@ -0,0 +1,12 @@
# This file is part of the LibreOffice project.
#
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
#
$(eval $(call gb_UITest_UITest,sw_chart))
$(eval $(call gb_UITest_add_modules,sw_chart,$(SRCDIR)/sw/qa/uitest,\
chart/ \
))

View File

@ -0,0 +1,55 @@
# -*- tab-width: 4; indent-tabs-mode: nil; py-indent-offset: 4 -*-
#
# This file is part of the LibreOffice project.
#
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
#
from libreoffice.uno.propertyvalue import mkPropertyValues
from uitest.framework import UITestCase
from uitest.uihelper.common import get_state_as_dict
from uitest.debug import sleep
class tdf138556( UITestCase ):
def test_stock_chart13_insert_series( self ):
#Start LibreOffice Writer
xDocument = self.ui_test.create_doc_in_start_center( "writer" )
xMainTop = self.xUITest.getTopFocusWindow()
#Insert Chart
self.xUITest.executeCommand( ".uno:InsertObjectChart" )
xChartMainTop = self.xUITest.getTopFocusWindow()
xChartMain = xChartMainTop.getChild( "chart_window" )
xChart = xChartMain.getChild( "CID/Page=" )
#Change Chart Type to Stock 1
#TODO: test other subtypes
self.ui_test.execute_dialog_through_action( xChart, "COMMAND",
mkPropertyValues({ "COMMAND" : "DiagramType" }))
xDialog = self.xUITest.getTopFocusWindow()
xChartType = xDialog.getChild( "charttype" )
xStockType = xChartType.getChild( "8" )
xStockType.executeAction( "SELECT", tuple())
xOKBtn = xDialog.getChild( "ok" )
self.ui_test.close_dialog_through_button( xOKBtn )
#Insert Data Series
self.ui_test.execute_dialog_through_action( xChart, "COMMAND",
mkPropertyValues({ "COMMAND" : "DiagramData" }))
xDialog = self.xUITest.getTopFocusWindow()
xToolbar = xDialog.getChild( "toolbar" )
xToolbar.executeAction( "CLICK", mkPropertyValues({ "POS" : "1" }))
xOKBtn = xDialog.getChild( "close" )
self.ui_test.close_dialog_through_button( xOKBtn )
#Check Number of Sequences
xDocument = self.ui_test.get_component()
nSequences = len( xDocument.FirstDiagram.
CoordinateSystems[0].ChartTypes[0].DataSeries[0].DataSequences )
self.assertEqual( nSequences, 3 )
self.ui_test.close_doc()