summaryrefslogtreecommitdiff
path: root/chart2
diff options
context:
space:
mode:
authorTomaž Vajngerl <tomaz.vajngerl@collabora.co.uk>2017-05-11 21:04:31 +0200
committerTomaž Vajngerl <quikee@gmail.com>2017-05-11 22:56:04 +0200
commit9e92527f500a20de838a93201718a761278d8f8d (patch)
treed5a3c312dee318ad41f02d051eac739d8f3c0743 /chart2
parent8bb6dab0b4007501bd7a970658360520667e5093 (diff)
tdf#107103 fixes for the legend in a pivot chart
- Solves issue described in the bug where the legend calculation was not correct if using custom legend placing and the buttons were added to the legend (like in a pivot chart). - Place the legend buttons horizontally if the legend is placed at the top or bottom (wide legend expansion), so the space is used more efficiently. - Fix automatic placing of the legend when we have buttons at the bottom of the chart so that we don't cover them with the legend. - It can happen that the button click is triggered when we resize the legend, so make sure we trigger only when mouse-down and mouse-up are on button. Change-Id: I6a60e7885f7a2ddd6424b1cdfc22e8b046c89dd4 Reviewed-on: https://gerrit.libreoffice.org/37518 Tested-by: Jenkins <ci@libreoffice.org> Reviewed-by: Tomaž Vajngerl <quikee@gmail.com>
Diffstat (limited to 'chart2')
-rw-r--r--chart2/source/controller/inc/ChartController.hxx1
-rw-r--r--chart2/source/controller/main/ChartController.cxx1
-rw-r--r--chart2/source/controller/main/ChartController_Window.cxx20
-rw-r--r--chart2/source/view/main/VLegend.cxx77
4 files changed, 71 insertions, 28 deletions
diff --git a/chart2/source/controller/inc/ChartController.hxx b/chart2/source/controller/inc/ChartController.hxx
index b32b4b7e725d..19ac675b14ae 100644
--- a/chart2/source/controller/inc/ChartController.hxx
+++ b/chart2/source/controller/inc/ChartController.hxx
@@ -390,6 +390,7 @@ private:
Timer m_aDoubleClickTimer;
bool m_bWaitingForDoubleClick;
bool m_bWaitingForMouseUp;
+ bool m_bFieldButtonDown;
bool m_bConnectingToView;
bool m_bDisposed;
diff --git a/chart2/source/controller/main/ChartController.cxx b/chart2/source/controller/main/ChartController.cxx
index 2c5b84f8a48a..119146a67de0 100644
--- a/chart2/source/controller/main/ChartController.cxx
+++ b/chart2/source/controller/main/ChartController.cxx
@@ -114,6 +114,7 @@ ChartController::ChartController(uno::Reference<uno::XComponentContext> const &
m_eDragMode(SdrDragMode::Move),
m_bWaitingForDoubleClick(false),
m_bWaitingForMouseUp(false),
+ m_bFieldButtonDown(false),
m_bConnectingToView(false),
m_bDisposed(false),
m_xUndoManager( nullptr ),
diff --git a/chart2/source/controller/main/ChartController_Window.cxx b/chart2/source/controller/main/ChartController_Window.cxx
index 7d42bcff5490..9b3d0e3ba69d 100644
--- a/chart2/source/controller/main/ChartController_Window.cxx
+++ b/chart2/source/controller/main/ChartController_Window.cxx
@@ -547,6 +547,7 @@ void ChartController::execute_MouseButtonDown( const MouseEvent& rMEvt )
SolarMutexGuard aGuard;
m_bWaitingForMouseUp = true;
+ m_bFieldButtonDown = false;
if( isDoubleClick(rMEvt) )
stopDoubleClickWaiting();
@@ -568,7 +569,10 @@ void ChartController::execute_MouseButtonDown( const MouseEvent& rMEvt )
{
OUString aCID = pObject->GetName();
if (aCID.startsWith("FieldButton"))
+ {
+ m_bFieldButtonDown = true;
return; // Don't take any action if button was clicked
+ }
}
if ( MOUSE_LEFT == rMEvt.GetButtons() )
@@ -738,14 +742,18 @@ void ChartController::execute_MouseButtonUp( const MouseEvent& rMEvt )
Point aMPos = pChartWindow->PixelToLogic(rMEvt.GetPosPixel());
// Check if button was clicked
- SdrObject* pObject = pDrawViewWrapper->getHitObject(aMPos);
- if (pObject)
+ if (m_bFieldButtonDown)
{
- OUString aCID = pObject->GetName();
- if (aCID.startsWith("FieldButton"))
+ m_bFieldButtonDown = false;
+ SdrObject* pObject = pDrawViewWrapper->getHitObject(aMPos);
+ if (pObject)
{
- sendPopupRequest(aCID, pObject->GetCurrentBoundRect());
- return;
+ OUString aCID = pObject->GetName();
+ if (aCID.startsWith("FieldButton"))
+ {
+ sendPopupRequest(aCID, pObject->GetCurrentBoundRect());
+ return;
+ }
}
}
diff --git a/chart2/source/view/main/VLegend.cxx b/chart2/source/view/main/VLegend.cxx
index bf51d0bd64d8..4790dec34763 100644
--- a/chart2/source/view/main/VLegend.cxx
+++ b/chart2/source/view/main/VLegend.cxx
@@ -267,12 +267,13 @@ awt::Size lcl_placeLegendEntries(
tPropertyValues & rTextProperties,
const Reference< drawing::XShapes > & xTarget,
const Reference< lang::XMultiServiceFactory > & xShapeFactory,
- const awt::Rectangle& rRemainingSpace)
+ const awt::Size& rRemainingSpace,
+ sal_Int32 nYStartPosition)
{
bool bIsCustomSize = (eExpansion == css::chart::ChartLegendExpansion_CUSTOM);
awt::Size aResultingLegendSize(0,0);
if( bIsCustomSize )
- aResultingLegendSize = awt::Size(rRemainingSpace.Width, rRemainingSpace.Height);
+ aResultingLegendSize = awt::Size(rRemainingSpace.Width, rRemainingSpace.Height + nYStartPosition);
// #i109336# Improve auto positioning in chart
sal_Int32 nXPadding = static_cast< sal_Int32 >( std::max( 100.0, fViewFontSize * 0.33 ) );
@@ -517,7 +518,7 @@ awt::Size lcl_placeLegendEntries(
for (sal_Int32 nColumn = 0; nColumn < nNumberOfColumns; ++nColumn)
{
- sal_Int32 nCurrentYPos = nYPadding + rRemainingSpace.Y;
+ sal_Int32 nCurrentYPos = nYPadding + nYStartPosition;
for (sal_Int32 nRow = 0; nRow < nNumberOfRows; ++nRow)
{
sal_Int32 nEntry = (nColumn + nRow * nNumberOfColumns);
@@ -649,8 +650,13 @@ chart2::RelativePosition lcl_getDefaultPosition( LegendPosition ePos, const awt:
// #i109336# Improve auto positioning in chart
const double fDefaultDistance = ( static_cast< double >( lcl_getLegendTopBottomMargin() ) /
static_cast< double >( rPageSize.Height ) );
+
+ double fDistance = double(rPageSize.Height - (rOutAvailableSpace.Y + rOutAvailableSpace.Height));
+ fDistance += fDefaultDistance;
+ fDistance /= double(rPageSize.Height);
+
aResult = chart2::RelativePosition(
- 0.5, 1.0 - fDefaultDistance, drawing::Alignment_BOTTOM );
+ 0.5, 1.0 - fDistance, drawing::Alignment_BOTTOM );
}
break;
@@ -765,9 +771,9 @@ bool lcl_shouldSymbolsBePlacedOnTheLeftSide( const Reference< beans::XPropertySe
}
std::vector<std::shared_ptr<VButton>> lcl_createButtons(
- const uno::Reference< drawing::XShapes>& xLegendContainer,
- const uno::Reference< lang::XMultiServiceFactory>& xShapeFactory,
- ChartModel& rModel, long& nUsedHeight)
+ uno::Reference<drawing::XShapes> const & xLegendContainer,
+ uno::Reference<lang::XMultiServiceFactory> const & xShapeFactory,
+ ChartModel& rModel, bool bPlaceButtonsVertically, long & nUsedHeight)
{
std::vector<std::shared_ptr<VButton>> aButtons;
@@ -779,13 +785,15 @@ std::vector<std::shared_ptr<VButton>> lcl_createButtons(
return aButtons;
awt::Size aSize(2000, 700);
+ int x = 100;
int y = 100;
+
for (chart2::data::PivotTableFieldEntry const & sColumnFieldEntry : xPivotTableDataProvider->getColumnFields())
{
std::shared_ptr<VButton> pButton(new VButton);
aButtons.push_back(pButton);
pButton->init(xLegendContainer, xShapeFactory);
- awt::Point aNewPosition = awt::Point(100, y);
+ awt::Point aNewPosition = awt::Point(x, y);
pButton->setLabel(sColumnFieldEntry.Name);
pButton->setCID("FieldButton.Column." + OUString::number(sColumnFieldEntry.DimensionIndex));
pButton->setPosition(aNewPosition);
@@ -794,9 +802,16 @@ std::vector<std::shared_ptr<VButton>> lcl_createButtons(
pButton->showArrow(false);
if (sColumnFieldEntry.HasHiddenMembers)
pButton->setArrowColor(0x0000FF);
- y += aSize.Height + 100;
+
+ if (bPlaceButtonsVertically)
+ y += aSize.Height + 100;
+ else
+ x += aSize.Width + 100;
}
- nUsedHeight += y + 100;
+ if (bPlaceButtonsVertically)
+ nUsedHeight += y + 100;
+ else
+ nUsedHeight += aSize.Height + 100;
return aButtons;
}
@@ -866,10 +881,6 @@ void VLegend::createShapes(
Reference< drawing::XShapes > xLegendContainer( m_xShape, uno::UNO_QUERY );
if( xLegendContainer.is())
{
- long nUsedHeight = 0;
- std::vector<std::shared_ptr<VButton>> aButtons;
- aButtons = lcl_createButtons(xLegendContainer, m_xShapeFactory, mrModel, nUsedHeight);
-
// for quickly setting properties
tPropertyValues aLineFillProperties;
tPropertyValues aTextProperties;
@@ -878,21 +889,27 @@ void VLegend::createShapes(
css::chart::ChartLegendExpansion eExpansion = css::chart::ChartLegendExpansion_HIGH;
awt::Size aLegendSize( rAvailableSpace );
- if( xLegendProp.is())
+ bool bCustom = false;
+ LegendPosition eLegendPosition = LegendPosition_CUSTOM;
+ if (xLegendProp.is())
{
// get Expansion property
- xLegendProp->getPropertyValue( "Expansion") >>= eExpansion;
+ xLegendProp->getPropertyValue("Expansion") >>= eExpansion;
if( eExpansion == css::chart::ChartLegendExpansion_CUSTOM )
{
RelativeSize aRelativeSize;
- if ((xLegendProp->getPropertyValue( "RelativeSize") >>= aRelativeSize))
+ if (xLegendProp->getPropertyValue("RelativeSize") >>= aRelativeSize)
{
aLegendSize.Width = static_cast<sal_Int32>(::rtl::math::approxCeil( aRelativeSize.Primary * rPageSize.Width ));
aLegendSize.Height = static_cast<sal_Int32>(::rtl::math::approxCeil( aRelativeSize.Secondary * rPageSize.Height ));
+ bCustom = true;
}
else
+ {
eExpansion = css::chart::ChartLegendExpansion_HIGH;
+ }
}
+ xLegendProp->getPropertyValue("AnchorPosition") >>= eLegendPosition;
lcl_getProperties( xLegendProp, aLineFillProperties, aTextProperties, rPageSize );
}
@@ -933,18 +950,34 @@ void VLegend::createShapes(
if (!aViewEntries.empty())
{
- awt::Rectangle aRectangle(0, nUsedHeight, aLegendSize.Width, aLegendSize.Height - nUsedHeight);
+ // create buttons
+ long nUsedButtonHeight = 0;
+ bool bPlaceButtonsVertically = (eLegendPosition != LegendPosition_PAGE_START &&
+ eLegendPosition != LegendPosition_PAGE_END &&
+ eExpansion != css::chart::ChartLegendExpansion_WIDE);
- // place entries
- aLegendSize = lcl_placeLegendEntries(aViewEntries, eExpansion, bSymbolsLeftSide, fViewFontSize, aMaxSymbolExtent,
- aTextProperties, xLegendContainer, m_xShapeFactory, aRectangle);
+ std::vector<std::shared_ptr<VButton>> aButtons;
+ aButtons = lcl_createButtons(xLegendContainer, m_xShapeFactory, mrModel, bPlaceButtonsVertically, nUsedButtonHeight);
+ // A custom size includes the size we used for buttons already, so we need to
+ // subtract that from the size that is available for the legend
+ if (bCustom)
+ aLegendSize.Height -= nUsedButtonHeight;
+
+ // place the legend entries
+ aLegendSize = lcl_placeLegendEntries(aViewEntries, eExpansion, bSymbolsLeftSide, fViewFontSize,
+ aMaxSymbolExtent, aTextProperties, xLegendContainer,
+ m_xShapeFactory, aLegendSize, nUsedButtonHeight);
uno::Reference<beans::XPropertySet> xModelPage(mrModel.getPageBackground());
for (std::shared_ptr<VButton> const & pButton : aButtons)
{
- pButton->setSize({aLegendSize.Width - 200, pButton->getSize().Height});
+ // adjust the width of the buttons if we place them vertically
+ if (bPlaceButtonsVertically)
+ pButton->setSize({aLegendSize.Width - 200, pButton->getSize().Height});
+
+ // create the buttons
pButton->createShapes(xModelPage);
}
}