diff options
Diffstat (limited to 'chart2/source/view/main/LabelPositionHelper.cxx')
-rw-r--r-- | chart2/source/view/main/LabelPositionHelper.cxx | 355 |
1 files changed, 355 insertions, 0 deletions
diff --git a/chart2/source/view/main/LabelPositionHelper.cxx b/chart2/source/view/main/LabelPositionHelper.cxx index b5bf518770fa..e2784f488ab0 100644 --- a/chart2/source/view/main/LabelPositionHelper.cxx +++ b/chart2/source/view/main/LabelPositionHelper.cxx @@ -131,6 +131,361 @@ void LabelPositionHelper::doDynamicFontResize( tAnySequence& rPropValues } } +namespace +{ + +void lcl_correctRotation_Left( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize, bool bRotateAroundCenter ) +{ + //correct label positions for labels on a left side of something with a right centered alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree==0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfXCorrection = -aSize.Height*rtl::math::sin( fAnglePi )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = -aSize.Width*rtl::math::sin( fAnglePi )/2.0; + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = fAnglePi-F_PI/2.0; + rfXCorrection = -aSize.Width *rtl::math::sin( beta ) + -aSize.Height *rtl::math::cos( beta )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = -aSize.Width *rtl::math::cos( beta )/2.0; + else + rfYCorrection = -aSize.Width *rtl::math::cos( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = fAnglePi - F_PI; + rfXCorrection = -aSize.Width *rtl::math::cos( beta ) + -aSize.Height*rtl::math::sin( beta )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = aSize.Width *rtl::math::sin( beta )/2.0; + else + rfYCorrection = aSize.Width *rtl::math::sin( beta ); + } + else + { + double beta = 2*F_PI - fAnglePi; + rfXCorrection = -aSize.Height*rtl::math::sin( beta )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = aSize.Width*rtl::math::sin( beta )/2.0; + } +} + +void lcl_correctRotation_Right( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize, bool bRotateAroundCenter ) +{ + //correct label positions for labels on a right side of something with a left centered alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree== 0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfXCorrection = aSize.Height*rtl::math::sin( fAnglePi )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = aSize.Width*rtl::math::sin( fAnglePi )/2.0; + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = F_PI - fAnglePi; + rfXCorrection = aSize.Width *rtl::math::cos( beta ) + + aSize.Height*rtl::math::sin( beta )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = aSize.Width *rtl::math::sin( beta )/2.0; + else + rfYCorrection = aSize.Width *rtl::math::sin( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = 3*F_PI/2.0 - fAnglePi; + rfXCorrection = aSize.Width *rtl::math::sin( beta ) + +aSize.Height*rtl::math::cos( beta )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = -aSize.Width *rtl::math::cos( beta )/2.0; + else + rfYCorrection = -aSize.Width *rtl::math::cos( beta ); + } + else + { + rfXCorrection = aSize.Height*rtl::math::sin( 2*F_PI - fAnglePi )/2.0; + if( bRotateAroundCenter ) + rfYCorrection = -aSize.Width*rtl::math::sin( 2*F_PI - fAnglePi )/2.0; + } +} + +void lcl_correctRotation_Top( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize, bool bRotateAroundCenter ) +{ + //correct label positions for labels on top of something with a bottom centered alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree== 0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfXCorrection = aSize.Height*rtl::math::sin( fAnglePi )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection += aSize.Width*rtl::math::cos( fAnglePi )/2.0; + rfYCorrection = -aSize.Width*rtl::math::sin( fAnglePi )/2.0; + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = fAnglePi - F_PI/2.0; + rfXCorrection = aSize.Height*rtl::math::cos( beta )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection -= aSize.Width*rtl::math::sin( beta )/2.0; + rfYCorrection = -aSize.Width*rtl::math::cos( beta )/2.0 + - aSize.Height*rtl::math::sin( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = fAnglePi - F_PI; + rfXCorrection = -aSize.Height *rtl::math::sin( beta )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection += aSize.Width *rtl::math::cos( beta )/2.0; + rfYCorrection = -aSize.Width *rtl::math::sin( beta )/2.0 + -aSize.Height *rtl::math::cos( beta ); + } + else + { + rfXCorrection = aSize.Height*rtl::math::sin( fAnglePi )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection -= aSize.Width*rtl::math::cos( fAnglePi )/2.0; + rfYCorrection = aSize.Width*rtl::math::sin( fAnglePi )/2.0; + } +} + +void lcl_correctRotation_Bottom( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize, bool bRotateAroundCenter ) +{ + //correct label positions for labels below something with a top centered alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree==0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfXCorrection = -aSize.Height*rtl::math::sin( fAnglePi )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection -= aSize.Width *rtl::math::cos( fAnglePi )/2.0; + rfYCorrection = aSize.Width*rtl::math::sin( fAnglePi )/2.0; + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = fAnglePi-F_PI/2.0; + rfXCorrection = -aSize.Height*rtl::math::cos( beta )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection += aSize.Width *rtl::math::sin( beta )/2.0; + rfYCorrection = aSize.Width *rtl::math::cos( beta )/2.0 + +aSize.Height*rtl::math::sin( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = 3*F_PI/2.0 - fAnglePi; + rfXCorrection = aSize.Height*rtl::math::cos( beta )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection -= aSize.Width *rtl::math::sin( beta )/2.0; + rfYCorrection = aSize.Height*rtl::math::sin( beta ) + +aSize.Width*rtl::math::cos( beta )/2.0; + } + else + { + double beta = 2*F_PI - fAnglePi; + rfXCorrection = aSize.Height*rtl::math::sin( beta )/2.0; + if( !bRotateAroundCenter ) + rfXCorrection += aSize.Width*rtl::math::cos( beta )/2.0; + rfYCorrection = aSize.Width*rtl::math::sin( beta )/2.0; + } +} + +void lcl_correctRotation_Left_Top( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize ) +{ + //correct position for labels at the left top corner of something with a bottom right alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree==0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfYCorrection = -aSize.Width*rtl::math::sin( fAnglePi ); + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = fAnglePi-F_PI/2.0; + rfXCorrection = -aSize.Width*rtl::math::sin( beta ); + rfYCorrection = -aSize.Height*rtl::math::sin( beta ) + -aSize.Width*rtl::math::cos( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = 3*F_PI/2.0 - fAnglePi; + rfXCorrection = -aSize.Height*rtl::math::cos( beta ) + -aSize.Width*rtl::math::sin( beta ); + rfYCorrection = -aSize.Height*rtl::math::sin( beta ); + } + else + { + rfXCorrection = aSize.Height*rtl::math::sin( fAnglePi ); + } +} + +void lcl_correctRotation_Left_Bottom( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize ) +{ + //correct position for labels at the left bottom corner of something with a top right alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree==0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfXCorrection = -aSize.Height*rtl::math::sin( fAnglePi ); + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = fAnglePi-F_PI/2.0; + rfXCorrection = -aSize.Width*rtl::math::sin( beta ) + -aSize.Height*rtl::math::cos( beta );; + rfYCorrection = aSize.Height*rtl::math::sin( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = 3*F_PI/2.0 - fAnglePi; + rfXCorrection = -aSize.Width*rtl::math::sin( beta ); + rfYCorrection = aSize.Width*rtl::math::cos( beta ) + +aSize.Height*rtl::math::sin( beta ); + } + else + { + rfYCorrection = -aSize.Width*rtl::math::sin( fAnglePi ); + } +} + +void lcl_correctRotation_Right_Top( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize ) +{ + //correct position for labels at the right top corner of something with a bottom left alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree==0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfXCorrection = aSize.Height*rtl::math::sin( fAnglePi ); + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = fAnglePi-F_PI/2.0; + rfXCorrection = aSize.Width*rtl::math::sin( beta ) + +aSize.Height*rtl::math::cos( beta ); + rfYCorrection = -aSize.Height*rtl::math::sin( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = 3*F_PI/2.0 - fAnglePi; + rfXCorrection = aSize.Width*rtl::math::sin( beta ); + rfYCorrection = -aSize.Width*rtl::math::cos( beta ) + -aSize.Height*rtl::math::sin( beta ); + } + else + { + rfYCorrection = aSize.Width*rtl::math::sin( fAnglePi ); + } +} + +void lcl_correctRotation_Right_Bottom( double& rfXCorrection, double& rfYCorrection + , double fAnglePositiveDegree, const awt::Size& aSize ) +{ + //correct position for labels at the right bottom corner of something with a top left alignment + double fAnglePi = fAnglePositiveDegree*F_PI/180.0; + if( fAnglePositiveDegree==0.0 ) + { + } + else if( fAnglePositiveDegree<= 90.0 ) + { + rfYCorrection = aSize.Width*rtl::math::sin( fAnglePi ); + } + else if( fAnglePositiveDegree<= 180.0 ) + { + double beta = fAnglePi-F_PI/2.0; + rfXCorrection = aSize.Width*rtl::math::sin( beta ); + rfYCorrection = aSize.Height*rtl::math::sin( beta ) + +aSize.Width*rtl::math::cos( beta ); + } + else if( fAnglePositiveDegree<= 270.0 ) + { + double beta = 3*F_PI/2.0 - fAnglePi; + rfXCorrection = aSize.Height*rtl::math::cos( beta ) + +aSize.Width*rtl::math::sin( beta ); + rfYCorrection = aSize.Height*rtl::math::sin( beta ); + } + else + { + rfXCorrection = -aSize.Height*rtl::math::sin( fAnglePi ); + } +} + +}//end anonymous namespace + +//static +void LabelPositionHelper::correctPositionForRotation( const uno::Reference< drawing::XShape >& xShape2DText + , LabelAlignment eLabelAlignment, const double fRotationAngle, bool bRotateAroundCenter ) +{ + if( !xShape2DText.is() ) + return; + + awt::Point aOldPos = xShape2DText->getPosition(); + awt::Size aSize = xShape2DText->getSize(); + + double fYCorrection = 0.0; + double fXCorrection = 0.0; + + double fAnglePositiveDegree = fRotationAngle; + while(fAnglePositiveDegree<0.0) + fAnglePositiveDegree+=360.0; + + switch(eLabelAlignment) + { + case LABEL_ALIGN_LEFT: + lcl_correctRotation_Left( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize, bRotateAroundCenter ); + break; + case LABEL_ALIGN_RIGHT: + lcl_correctRotation_Right( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize, bRotateAroundCenter ); + break; + case LABEL_ALIGN_TOP: + lcl_correctRotation_Top( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize, bRotateAroundCenter ); + break; + case LABEL_ALIGN_BOTTOM: + lcl_correctRotation_Bottom( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize, bRotateAroundCenter ); + break; + case LABEL_ALIGN_LEFT_TOP: + lcl_correctRotation_Left_Top( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize ); + break; + case LABEL_ALIGN_LEFT_BOTTOM: + lcl_correctRotation_Left_Bottom( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize ); + break; + case LABEL_ALIGN_RIGHT_TOP: + lcl_correctRotation_Right_Top( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize ); + break; + case LABEL_ALIGN_RIGHT_BOTTOM: + lcl_correctRotation_Right_Bottom( fXCorrection, fYCorrection, fAnglePositiveDegree, aSize ); + break; + default: //LABEL_ALIGN_CENTER + break; + } + + xShape2DText->setPosition( awt::Point( + static_cast<sal_Int32>(aOldPos.X + fXCorrection ) + , static_cast<sal_Int32>(aOldPos.Y + fYCorrection ) ) ); +} + //............................................................................. } //namespace chart //............................................................................. |