1*cdf0e10cSrcweir /************************************************************************* 2*cdf0e10cSrcweir * 3*cdf0e10cSrcweir * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4*cdf0e10cSrcweir * 5*cdf0e10cSrcweir * Copyright 2000, 2010 Oracle and/or its affiliates. 6*cdf0e10cSrcweir * 7*cdf0e10cSrcweir * OpenOffice.org - a multi-platform office productivity suite 8*cdf0e10cSrcweir * 9*cdf0e10cSrcweir * This file is part of OpenOffice.org. 10*cdf0e10cSrcweir * 11*cdf0e10cSrcweir * OpenOffice.org is free software: you can redistribute it and/or modify 12*cdf0e10cSrcweir * it under the terms of the GNU Lesser General Public License version 3 13*cdf0e10cSrcweir * only, as published by the Free Software Foundation. 14*cdf0e10cSrcweir * 15*cdf0e10cSrcweir * OpenOffice.org is distributed in the hope that it will be useful, 16*cdf0e10cSrcweir * but WITHOUT ANY WARRANTY; without even the implied warranty of 17*cdf0e10cSrcweir * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18*cdf0e10cSrcweir * GNU Lesser General Public License version 3 for more details 19*cdf0e10cSrcweir * (a copy is included in the LICENSE file that accompanied this code). 20*cdf0e10cSrcweir * 21*cdf0e10cSrcweir * You should have received a copy of the GNU Lesser General Public License 22*cdf0e10cSrcweir * version 3 along with OpenOffice.org. If not, see 23*cdf0e10cSrcweir * <http://www.openoffice.org/license.html> 24*cdf0e10cSrcweir * for a copy of the LGPLv3 License. 25*cdf0e10cSrcweir * 26*cdf0e10cSrcweir ************************************************************************/ 27*cdf0e10cSrcweir 28*cdf0e10cSrcweir #include "precompiled_svx.hxx" 29*cdf0e10cSrcweir #include <svx/sdr/primitive2d/sdrmeasureprimitive2d.hxx> 30*cdf0e10cSrcweir #include <svx/sdr/primitive2d/sdrdecompositiontools.hxx> 31*cdf0e10cSrcweir #include <basegfx/matrix/b2dhommatrix.hxx> 32*cdf0e10cSrcweir #include <svx/sdr/primitive2d/sdrtextprimitive2d.hxx> 33*cdf0e10cSrcweir #include <svx/sdr/attribute/sdrtextattribute.hxx> 34*cdf0e10cSrcweir #include <basegfx/polygon/b2dpolypolygontools.hxx> 35*cdf0e10cSrcweir #include <basegfx/tools/canvastools.hxx> 36*cdf0e10cSrcweir #include <drawinglayer/primitive2d/groupprimitive2d.hxx> 37*cdf0e10cSrcweir #include <svx/sdr/primitive2d/svx_primitivetypes2d.hxx> 38*cdf0e10cSrcweir #include <basegfx/matrix/b2dhommatrixtools.hxx> 39*cdf0e10cSrcweir #include <drawinglayer/primitive2d/hiddengeometryprimitive2d.hxx> 40*cdf0e10cSrcweir 41*cdf0e10cSrcweir ////////////////////////////////////////////////////////////////////////////// 42*cdf0e10cSrcweir 43*cdf0e10cSrcweir using namespace com::sun::star; 44*cdf0e10cSrcweir 45*cdf0e10cSrcweir ////////////////////////////////////////////////////////////////////////////// 46*cdf0e10cSrcweir 47*cdf0e10cSrcweir namespace drawinglayer 48*cdf0e10cSrcweir { 49*cdf0e10cSrcweir namespace primitive2d 50*cdf0e10cSrcweir { 51*cdf0e10cSrcweir Primitive2DReference SdrMeasurePrimitive2D::impCreatePart( 52*cdf0e10cSrcweir const attribute::SdrLineAttribute& rLineAttribute, 53*cdf0e10cSrcweir const basegfx::B2DHomMatrix& rObjectMatrix, 54*cdf0e10cSrcweir const basegfx::B2DPoint& rStart, 55*cdf0e10cSrcweir const basegfx::B2DPoint& rEnd, 56*cdf0e10cSrcweir bool bLeftActive, 57*cdf0e10cSrcweir bool bRightActive) const 58*cdf0e10cSrcweir { 59*cdf0e10cSrcweir const attribute::SdrLineStartEndAttribute& rLineStartEnd = getSdrLSTAttribute().getLineStartEnd(); 60*cdf0e10cSrcweir basegfx::B2DPolygon aPolygon; 61*cdf0e10cSrcweir 62*cdf0e10cSrcweir aPolygon.append(rStart); 63*cdf0e10cSrcweir aPolygon.append(rEnd); 64*cdf0e10cSrcweir 65*cdf0e10cSrcweir if(rLineStartEnd.isDefault() || (!bLeftActive && !bRightActive)) 66*cdf0e10cSrcweir { 67*cdf0e10cSrcweir return createPolygonLinePrimitive( 68*cdf0e10cSrcweir aPolygon, 69*cdf0e10cSrcweir rObjectMatrix, 70*cdf0e10cSrcweir rLineAttribute, 71*cdf0e10cSrcweir attribute::SdrLineStartEndAttribute()); 72*cdf0e10cSrcweir } 73*cdf0e10cSrcweir 74*cdf0e10cSrcweir if(bLeftActive && bRightActive) 75*cdf0e10cSrcweir { 76*cdf0e10cSrcweir return createPolygonLinePrimitive( 77*cdf0e10cSrcweir aPolygon, 78*cdf0e10cSrcweir rObjectMatrix, 79*cdf0e10cSrcweir rLineAttribute, 80*cdf0e10cSrcweir rLineStartEnd); 81*cdf0e10cSrcweir } 82*cdf0e10cSrcweir 83*cdf0e10cSrcweir const basegfx::B2DPolyPolygon aEmpty; 84*cdf0e10cSrcweir const attribute::SdrLineStartEndAttribute aLineStartEnd( 85*cdf0e10cSrcweir bLeftActive ? rLineStartEnd.getStartPolyPolygon() : aEmpty, bRightActive ? rLineStartEnd.getEndPolyPolygon() : aEmpty, 86*cdf0e10cSrcweir bLeftActive ? rLineStartEnd.getStartWidth() : 0.0, bRightActive ? rLineStartEnd.getEndWidth() : 0.0, 87*cdf0e10cSrcweir bLeftActive ? rLineStartEnd.isStartActive() : false, bRightActive ? rLineStartEnd.isEndActive() : false, 88*cdf0e10cSrcweir bLeftActive ? rLineStartEnd.isStartCentered() : false, bRightActive? rLineStartEnd.isEndCentered() : false); 89*cdf0e10cSrcweir 90*cdf0e10cSrcweir return createPolygonLinePrimitive(aPolygon, rObjectMatrix, rLineAttribute, aLineStartEnd); 91*cdf0e10cSrcweir } 92*cdf0e10cSrcweir 93*cdf0e10cSrcweir Primitive2DSequence SdrMeasurePrimitive2D::create2DDecomposition(const geometry::ViewInformation2D& aViewInformation) const 94*cdf0e10cSrcweir { 95*cdf0e10cSrcweir Primitive2DSequence aRetval; 96*cdf0e10cSrcweir SdrBlockTextPrimitive2D* pBlockText = 0; 97*cdf0e10cSrcweir basegfx::B2DRange aTextRange; 98*cdf0e10cSrcweir double fTextX((getStart().getX() + getEnd().getX()) * 0.5); 99*cdf0e10cSrcweir double fTextY((getStart().getX() + getEnd().getX()) * 0.5); 100*cdf0e10cSrcweir const basegfx::B2DVector aLine(getEnd() - getStart()); 101*cdf0e10cSrcweir const double fDistance(aLine.getLength()); 102*cdf0e10cSrcweir const double fAngle(atan2(aLine.getY(), aLine.getX())); 103*cdf0e10cSrcweir bool bAutoUpsideDown(false); 104*cdf0e10cSrcweir const attribute::SdrTextAttribute rTextAttribute = getSdrLSTAttribute().getText(); 105*cdf0e10cSrcweir const basegfx::B2DHomMatrix aObjectMatrix( 106*cdf0e10cSrcweir basegfx::tools::createShearXRotateTranslateB2DHomMatrix(0.0, fAngle, getStart())); 107*cdf0e10cSrcweir 108*cdf0e10cSrcweir // preapare text, but do not add yet; it needs to be aligned to 109*cdf0e10cSrcweir // the line geometry 110*cdf0e10cSrcweir if(!rTextAttribute.isDefault()) 111*cdf0e10cSrcweir { 112*cdf0e10cSrcweir basegfx::B2DHomMatrix aTextMatrix; 113*cdf0e10cSrcweir double fTestAngle(fAngle); 114*cdf0e10cSrcweir 115*cdf0e10cSrcweir if(getTextRotation()) 116*cdf0e10cSrcweir { 117*cdf0e10cSrcweir aTextMatrix.rotate(-90.0 * F_PI180); 118*cdf0e10cSrcweir fTestAngle -= (90.0 * F_PI180); 119*cdf0e10cSrcweir 120*cdf0e10cSrcweir if(getTextAutoAngle() && fTestAngle < -F_PI) 121*cdf0e10cSrcweir { 122*cdf0e10cSrcweir fTestAngle += F_2PI; 123*cdf0e10cSrcweir } 124*cdf0e10cSrcweir } 125*cdf0e10cSrcweir 126*cdf0e10cSrcweir if(getTextAutoAngle()) 127*cdf0e10cSrcweir { 128*cdf0e10cSrcweir if(fTestAngle > (F_PI / 4.0) || fTestAngle < (-F_PI * (3.0 / 4.0))) 129*cdf0e10cSrcweir { 130*cdf0e10cSrcweir bAutoUpsideDown = true; 131*cdf0e10cSrcweir } 132*cdf0e10cSrcweir } 133*cdf0e10cSrcweir 134*cdf0e10cSrcweir // create primitive and get text range 135*cdf0e10cSrcweir pBlockText = new SdrBlockTextPrimitive2D( 136*cdf0e10cSrcweir &rTextAttribute.getSdrText(), 137*cdf0e10cSrcweir rTextAttribute.getOutlinerParaObject(), 138*cdf0e10cSrcweir aTextMatrix, 139*cdf0e10cSrcweir SDRTEXTHORZADJUST_CENTER, 140*cdf0e10cSrcweir SDRTEXTVERTADJUST_CENTER, 141*cdf0e10cSrcweir rTextAttribute.isScroll(), 142*cdf0e10cSrcweir false, 143*cdf0e10cSrcweir false, 144*cdf0e10cSrcweir false, 145*cdf0e10cSrcweir false); 146*cdf0e10cSrcweir 147*cdf0e10cSrcweir aTextRange = pBlockText->getB2DRange(aViewInformation); 148*cdf0e10cSrcweir } 149*cdf0e10cSrcweir 150*cdf0e10cSrcweir // prepare line attribute and result 151*cdf0e10cSrcweir { 152*cdf0e10cSrcweir const attribute::SdrLineAttribute rLineAttribute(getSdrLSTAttribute().getLine()); 153*cdf0e10cSrcweir bool bArrowsOutside(false); 154*cdf0e10cSrcweir bool bMainLineSplitted(false); 155*cdf0e10cSrcweir const attribute::SdrLineStartEndAttribute& rLineStartEnd = getSdrLSTAttribute().getLineStartEnd(); 156*cdf0e10cSrcweir double fStartArrowW(0.0); 157*cdf0e10cSrcweir double fStartArrowH(0.0); 158*cdf0e10cSrcweir double fEndArrowW(0.0); 159*cdf0e10cSrcweir double fEndArrowH(0.0); 160*cdf0e10cSrcweir 161*cdf0e10cSrcweir if(!rLineStartEnd.isDefault()) 162*cdf0e10cSrcweir { 163*cdf0e10cSrcweir if(rLineStartEnd.isStartActive()) 164*cdf0e10cSrcweir { 165*cdf0e10cSrcweir const basegfx::B2DRange aArrowRange(basegfx::tools::getRange(rLineStartEnd.getStartPolyPolygon())); 166*cdf0e10cSrcweir fStartArrowW = rLineStartEnd.getStartWidth(); 167*cdf0e10cSrcweir fStartArrowH = aArrowRange.getHeight() * fStartArrowW / aArrowRange.getWidth(); 168*cdf0e10cSrcweir 169*cdf0e10cSrcweir if(rLineStartEnd.isStartCentered()) 170*cdf0e10cSrcweir { 171*cdf0e10cSrcweir fStartArrowH *= 0.5; 172*cdf0e10cSrcweir } 173*cdf0e10cSrcweir } 174*cdf0e10cSrcweir 175*cdf0e10cSrcweir if(rLineStartEnd.isEndActive()) 176*cdf0e10cSrcweir { 177*cdf0e10cSrcweir const basegfx::B2DRange aArrowRange(basegfx::tools::getRange(rLineStartEnd.getEndPolyPolygon())); 178*cdf0e10cSrcweir fEndArrowW = rLineStartEnd.getEndWidth(); 179*cdf0e10cSrcweir fEndArrowH = aArrowRange.getHeight() * fEndArrowW / aArrowRange.getWidth(); 180*cdf0e10cSrcweir 181*cdf0e10cSrcweir if(rLineStartEnd.isEndCentered()) 182*cdf0e10cSrcweir { 183*cdf0e10cSrcweir fEndArrowH *= 0.5; 184*cdf0e10cSrcweir } 185*cdf0e10cSrcweir } 186*cdf0e10cSrcweir } 187*cdf0e10cSrcweir 188*cdf0e10cSrcweir const double fSpaceNeededByArrows(fStartArrowH + fEndArrowH + ((fStartArrowW + fEndArrowW) * 0.5)); 189*cdf0e10cSrcweir const double fArrowsOutsideLen((fStartArrowH + fEndArrowH + fStartArrowW + fEndArrowW) * 0.5); 190*cdf0e10cSrcweir const double fHalfLineWidth(rLineAttribute.getWidth() * 0.5); 191*cdf0e10cSrcweir 192*cdf0e10cSrcweir if(fSpaceNeededByArrows > fDistance) 193*cdf0e10cSrcweir { 194*cdf0e10cSrcweir bArrowsOutside = true; 195*cdf0e10cSrcweir } 196*cdf0e10cSrcweir 197*cdf0e10cSrcweir MeasureTextPosition eHorizontal(getHorizontal()); 198*cdf0e10cSrcweir MeasureTextPosition eVertical(getVertical()); 199*cdf0e10cSrcweir 200*cdf0e10cSrcweir if(MEASURETEXTPOSITION_AUTOMATIC == eVertical) 201*cdf0e10cSrcweir { 202*cdf0e10cSrcweir eVertical = MEASURETEXTPOSITION_NEGATIVE; 203*cdf0e10cSrcweir } 204*cdf0e10cSrcweir 205*cdf0e10cSrcweir if(MEASURETEXTPOSITION_CENTERED == eVertical) 206*cdf0e10cSrcweir { 207*cdf0e10cSrcweir bMainLineSplitted = true; 208*cdf0e10cSrcweir } 209*cdf0e10cSrcweir 210*cdf0e10cSrcweir if(MEASURETEXTPOSITION_AUTOMATIC == eHorizontal) 211*cdf0e10cSrcweir { 212*cdf0e10cSrcweir if(aTextRange.getWidth() > fDistance) 213*cdf0e10cSrcweir { 214*cdf0e10cSrcweir eHorizontal = MEASURETEXTPOSITION_NEGATIVE; 215*cdf0e10cSrcweir } 216*cdf0e10cSrcweir else 217*cdf0e10cSrcweir { 218*cdf0e10cSrcweir eHorizontal = MEASURETEXTPOSITION_CENTERED; 219*cdf0e10cSrcweir } 220*cdf0e10cSrcweir 221*cdf0e10cSrcweir if(bMainLineSplitted) 222*cdf0e10cSrcweir { 223*cdf0e10cSrcweir if(aTextRange.getWidth() + fSpaceNeededByArrows > fDistance) 224*cdf0e10cSrcweir { 225*cdf0e10cSrcweir bArrowsOutside = true; 226*cdf0e10cSrcweir } 227*cdf0e10cSrcweir } 228*cdf0e10cSrcweir else 229*cdf0e10cSrcweir { 230*cdf0e10cSrcweir const double fSmallArrowNeed(fStartArrowH + fEndArrowH + ((fStartArrowW + fEndArrowW) * 0.125)); 231*cdf0e10cSrcweir 232*cdf0e10cSrcweir if(aTextRange.getWidth() + fSmallArrowNeed > fDistance) 233*cdf0e10cSrcweir { 234*cdf0e10cSrcweir bArrowsOutside = true; 235*cdf0e10cSrcweir } 236*cdf0e10cSrcweir } 237*cdf0e10cSrcweir } 238*cdf0e10cSrcweir 239*cdf0e10cSrcweir if(MEASURETEXTPOSITION_CENTERED != eHorizontal) 240*cdf0e10cSrcweir { 241*cdf0e10cSrcweir bArrowsOutside = true; 242*cdf0e10cSrcweir } 243*cdf0e10cSrcweir 244*cdf0e10cSrcweir // switch text above/below? 245*cdf0e10cSrcweir if(getBelow() || (bAutoUpsideDown && !getTextRotation())) 246*cdf0e10cSrcweir { 247*cdf0e10cSrcweir if(MEASURETEXTPOSITION_NEGATIVE == eVertical) 248*cdf0e10cSrcweir { 249*cdf0e10cSrcweir eVertical = MEASURETEXTPOSITION_POSITIVE; 250*cdf0e10cSrcweir } 251*cdf0e10cSrcweir else if(MEASURETEXTPOSITION_POSITIVE == eVertical) 252*cdf0e10cSrcweir { 253*cdf0e10cSrcweir eVertical = MEASURETEXTPOSITION_NEGATIVE; 254*cdf0e10cSrcweir } 255*cdf0e10cSrcweir } 256*cdf0e10cSrcweir 257*cdf0e10cSrcweir const double fMainLineOffset(getBelow() ? getDistance() : -getDistance()); 258*cdf0e10cSrcweir const basegfx::B2DPoint aMainLeft(0.0, fMainLineOffset); 259*cdf0e10cSrcweir const basegfx::B2DPoint aMainRight(fDistance, fMainLineOffset); 260*cdf0e10cSrcweir 261*cdf0e10cSrcweir // main line 262*cdf0e10cSrcweir if(bArrowsOutside) 263*cdf0e10cSrcweir { 264*cdf0e10cSrcweir double fLenLeft(fArrowsOutsideLen); 265*cdf0e10cSrcweir double fLenRight(fArrowsOutsideLen); 266*cdf0e10cSrcweir 267*cdf0e10cSrcweir if(!bMainLineSplitted) 268*cdf0e10cSrcweir { 269*cdf0e10cSrcweir if(MEASURETEXTPOSITION_NEGATIVE == eHorizontal) 270*cdf0e10cSrcweir { 271*cdf0e10cSrcweir fLenLeft = fStartArrowH + aTextRange.getWidth(); 272*cdf0e10cSrcweir } 273*cdf0e10cSrcweir else if(MEASURETEXTPOSITION_POSITIVE == eHorizontal) 274*cdf0e10cSrcweir { 275*cdf0e10cSrcweir fLenRight = fEndArrowH + aTextRange.getWidth(); 276*cdf0e10cSrcweir } 277*cdf0e10cSrcweir } 278*cdf0e10cSrcweir 279*cdf0e10cSrcweir const basegfx::B2DPoint aMainLeftLeft(aMainLeft.getX() - fLenLeft, aMainLeft.getY()); 280*cdf0e10cSrcweir const basegfx::B2DPoint aMainRightRight(aMainRight.getX() + fLenRight, aMainRight.getY()); 281*cdf0e10cSrcweir 282*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aMainLeftLeft, aMainLeft, false, true)); 283*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aMainRight, aMainRightRight, true, false)); 284*cdf0e10cSrcweir 285*cdf0e10cSrcweir if(!bMainLineSplitted || MEASURETEXTPOSITION_CENTERED != eHorizontal) 286*cdf0e10cSrcweir { 287*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aMainLeft, aMainRight, false, false)); 288*cdf0e10cSrcweir } 289*cdf0e10cSrcweir } 290*cdf0e10cSrcweir else 291*cdf0e10cSrcweir { 292*cdf0e10cSrcweir if(bMainLineSplitted) 293*cdf0e10cSrcweir { 294*cdf0e10cSrcweir const double fHalfLength((fDistance - (aTextRange.getWidth() + (fStartArrowH + fEndArrowH) * 0.25)) * 0.5); 295*cdf0e10cSrcweir const basegfx::B2DPoint aMainInnerLeft(aMainLeft.getX() + fHalfLength, aMainLeft.getY()); 296*cdf0e10cSrcweir const basegfx::B2DPoint aMainInnerRight(aMainRight.getX() - fHalfLength, aMainRight.getY()); 297*cdf0e10cSrcweir 298*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aMainLeft, aMainInnerLeft, true, false)); 299*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aMainInnerRight, aMainRight, false, true)); 300*cdf0e10cSrcweir } 301*cdf0e10cSrcweir else 302*cdf0e10cSrcweir { 303*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aMainLeft, aMainRight, true, true)); 304*cdf0e10cSrcweir } 305*cdf0e10cSrcweir } 306*cdf0e10cSrcweir 307*cdf0e10cSrcweir // left/right help line value preparation 308*cdf0e10cSrcweir const double fTopEdge(getBelow() ? getUpper() + getDistance() : -getUpper() - getDistance()); 309*cdf0e10cSrcweir const double fBottomLeft(getBelow() ? getLower() - getLeftDelta() : getLeftDelta() - getLower()); 310*cdf0e10cSrcweir const double fBottomRight(getBelow() ? getLower() - getRightDelta() : getRightDelta() - getLower()); 311*cdf0e10cSrcweir 312*cdf0e10cSrcweir // left help line 313*cdf0e10cSrcweir const basegfx::B2DPoint aLeftUp(0.0, fTopEdge); 314*cdf0e10cSrcweir const basegfx::B2DPoint aLeftDown(0.0, fBottomLeft); 315*cdf0e10cSrcweir 316*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aLeftDown, aLeftUp, false, false)); 317*cdf0e10cSrcweir 318*cdf0e10cSrcweir // right help line 319*cdf0e10cSrcweir const basegfx::B2DPoint aRightUp(fDistance, fTopEdge); 320*cdf0e10cSrcweir const basegfx::B2DPoint aRightDown(fDistance, fBottomRight); 321*cdf0e10cSrcweir 322*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, impCreatePart(rLineAttribute, aObjectMatrix, aRightDown, aRightUp, false, false)); 323*cdf0e10cSrcweir 324*cdf0e10cSrcweir // text horizontal position 325*cdf0e10cSrcweir if(MEASURETEXTPOSITION_NEGATIVE == eHorizontal) 326*cdf0e10cSrcweir { 327*cdf0e10cSrcweir // left 328*cdf0e10cSrcweir const double fSmall(fArrowsOutsideLen * 0.18); 329*cdf0e10cSrcweir fTextX = aMainLeft.getX() - (fStartArrowH + aTextRange.getWidth() + fSmall + fHalfLineWidth); 330*cdf0e10cSrcweir 331*cdf0e10cSrcweir if(bMainLineSplitted) 332*cdf0e10cSrcweir { 333*cdf0e10cSrcweir fTextX -= (fArrowsOutsideLen - fStartArrowH); 334*cdf0e10cSrcweir } 335*cdf0e10cSrcweir 336*cdf0e10cSrcweir if(!rTextAttribute.isDefault()) 337*cdf0e10cSrcweir { 338*cdf0e10cSrcweir fTextX -= rTextAttribute.getTextRightDistance(); 339*cdf0e10cSrcweir } 340*cdf0e10cSrcweir } 341*cdf0e10cSrcweir else if(MEASURETEXTPOSITION_POSITIVE == eHorizontal) 342*cdf0e10cSrcweir { 343*cdf0e10cSrcweir // right 344*cdf0e10cSrcweir const double fSmall(fArrowsOutsideLen * 0.18); 345*cdf0e10cSrcweir fTextX = aMainRight.getX() + (fEndArrowH + fSmall + fHalfLineWidth); 346*cdf0e10cSrcweir 347*cdf0e10cSrcweir if(bMainLineSplitted) 348*cdf0e10cSrcweir { 349*cdf0e10cSrcweir fTextX += (fArrowsOutsideLen - fEndArrowH); 350*cdf0e10cSrcweir } 351*cdf0e10cSrcweir 352*cdf0e10cSrcweir if(!rTextAttribute.isDefault()) 353*cdf0e10cSrcweir { 354*cdf0e10cSrcweir fTextX += rTextAttribute.getTextLeftDistance(); 355*cdf0e10cSrcweir } 356*cdf0e10cSrcweir } 357*cdf0e10cSrcweir else // MEASURETEXTPOSITION_CENTERED 358*cdf0e10cSrcweir { 359*cdf0e10cSrcweir // centered 360*cdf0e10cSrcweir fTextX = aMainLeft.getX() + ((fDistance - aTextRange.getWidth()) * 0.5); 361*cdf0e10cSrcweir 362*cdf0e10cSrcweir if(!rTextAttribute.isDefault()) 363*cdf0e10cSrcweir { 364*cdf0e10cSrcweir fTextX += (rTextAttribute.getTextLeftDistance() - rTextAttribute.getTextRightDistance()) / 2L; 365*cdf0e10cSrcweir } 366*cdf0e10cSrcweir } 367*cdf0e10cSrcweir 368*cdf0e10cSrcweir // text vertical position 369*cdf0e10cSrcweir if(MEASURETEXTPOSITION_NEGATIVE == eVertical) 370*cdf0e10cSrcweir { 371*cdf0e10cSrcweir // top 372*cdf0e10cSrcweir const double fSmall(fArrowsOutsideLen * 0.10); 373*cdf0e10cSrcweir fTextY = aMainLeft.getY() - (aTextRange.getHeight() + fSmall + fHalfLineWidth); 374*cdf0e10cSrcweir 375*cdf0e10cSrcweir if(!rTextAttribute.isDefault()) 376*cdf0e10cSrcweir { 377*cdf0e10cSrcweir fTextY -= rTextAttribute.getTextLowerDistance(); 378*cdf0e10cSrcweir } 379*cdf0e10cSrcweir } 380*cdf0e10cSrcweir else if(MEASURETEXTPOSITION_POSITIVE == eVertical) 381*cdf0e10cSrcweir { 382*cdf0e10cSrcweir // bottom 383*cdf0e10cSrcweir const double fSmall(fArrowsOutsideLen * 0.10); 384*cdf0e10cSrcweir fTextY = aMainLeft.getY() + (fSmall + fHalfLineWidth); 385*cdf0e10cSrcweir 386*cdf0e10cSrcweir if(!rTextAttribute.isDefault()) 387*cdf0e10cSrcweir { 388*cdf0e10cSrcweir fTextY += rTextAttribute.getTextUpperDistance(); 389*cdf0e10cSrcweir } 390*cdf0e10cSrcweir } 391*cdf0e10cSrcweir else // MEASURETEXTPOSITION_CENTERED 392*cdf0e10cSrcweir { 393*cdf0e10cSrcweir // centered 394*cdf0e10cSrcweir fTextY = aMainLeft.getY() - (aTextRange.getHeight() * 0.5); 395*cdf0e10cSrcweir 396*cdf0e10cSrcweir if(!rTextAttribute.isDefault()) 397*cdf0e10cSrcweir { 398*cdf0e10cSrcweir fTextY += (rTextAttribute.getTextUpperDistance() - rTextAttribute.getTextLowerDistance()) / 2L; 399*cdf0e10cSrcweir } 400*cdf0e10cSrcweir } 401*cdf0e10cSrcweir } 402*cdf0e10cSrcweir 403*cdf0e10cSrcweir if(getSdrLSTAttribute().getLine().isDefault()) 404*cdf0e10cSrcweir { 405*cdf0e10cSrcweir // embed line geometry to invisible (100% transparent) line group for HitTest 406*cdf0e10cSrcweir const Primitive2DReference xHiddenLines(new HiddenGeometryPrimitive2D(aRetval)); 407*cdf0e10cSrcweir 408*cdf0e10cSrcweir aRetval = Primitive2DSequence(&xHiddenLines, 1); 409*cdf0e10cSrcweir } 410*cdf0e10cSrcweir 411*cdf0e10cSrcweir if(pBlockText) 412*cdf0e10cSrcweir { 413*cdf0e10cSrcweir // create transformation to text primitive end position 414*cdf0e10cSrcweir basegfx::B2DHomMatrix aChange; 415*cdf0e10cSrcweir 416*cdf0e10cSrcweir // handle auto text rotation 417*cdf0e10cSrcweir if(bAutoUpsideDown) 418*cdf0e10cSrcweir { 419*cdf0e10cSrcweir aChange.rotate(F_PI); 420*cdf0e10cSrcweir } 421*cdf0e10cSrcweir 422*cdf0e10cSrcweir // move from aTextRange.TopLeft to fTextX, fTextY 423*cdf0e10cSrcweir aChange.translate(fTextX - aTextRange.getMinX(), fTextY - aTextRange.getMinY()); 424*cdf0e10cSrcweir 425*cdf0e10cSrcweir // apply object matrix 426*cdf0e10cSrcweir aChange *= aObjectMatrix; 427*cdf0e10cSrcweir 428*cdf0e10cSrcweir // apply to existing text primitive 429*cdf0e10cSrcweir SdrTextPrimitive2D* pNewBlockText = pBlockText->createTransformedClone(aChange); 430*cdf0e10cSrcweir OSL_ENSURE(pNewBlockText, "SdrMeasurePrimitive2D::create2DDecomposition: Could not create transformed clone of text primitive (!)"); 431*cdf0e10cSrcweir delete pBlockText; 432*cdf0e10cSrcweir 433*cdf0e10cSrcweir // add to local primitives 434*cdf0e10cSrcweir appendPrimitive2DReferenceToPrimitive2DSequence(aRetval, Primitive2DReference(pNewBlockText)); 435*cdf0e10cSrcweir } 436*cdf0e10cSrcweir 437*cdf0e10cSrcweir // add shadow 438*cdf0e10cSrcweir if(!getSdrLSTAttribute().getShadow().isDefault()) 439*cdf0e10cSrcweir { 440*cdf0e10cSrcweir aRetval = createEmbeddedShadowPrimitive( 441*cdf0e10cSrcweir aRetval, 442*cdf0e10cSrcweir getSdrLSTAttribute().getShadow()); 443*cdf0e10cSrcweir } 444*cdf0e10cSrcweir 445*cdf0e10cSrcweir return aRetval; 446*cdf0e10cSrcweir } 447*cdf0e10cSrcweir 448*cdf0e10cSrcweir SdrMeasurePrimitive2D::SdrMeasurePrimitive2D( 449*cdf0e10cSrcweir const attribute::SdrLineShadowTextAttribute& rSdrLSTAttribute, 450*cdf0e10cSrcweir const basegfx::B2DPoint& rStart, 451*cdf0e10cSrcweir const basegfx::B2DPoint& rEnd, 452*cdf0e10cSrcweir MeasureTextPosition eHorizontal, 453*cdf0e10cSrcweir MeasureTextPosition eVertical, 454*cdf0e10cSrcweir double fDistance, 455*cdf0e10cSrcweir double fUpper, 456*cdf0e10cSrcweir double fLower, 457*cdf0e10cSrcweir double fLeftDelta, 458*cdf0e10cSrcweir double fRightDelta, 459*cdf0e10cSrcweir bool bBelow, 460*cdf0e10cSrcweir bool bTextRotation, 461*cdf0e10cSrcweir bool bTextAutoAngle) 462*cdf0e10cSrcweir : BufferedDecompositionPrimitive2D(), 463*cdf0e10cSrcweir maSdrLSTAttribute(rSdrLSTAttribute), 464*cdf0e10cSrcweir maStart(rStart), 465*cdf0e10cSrcweir maEnd(rEnd), 466*cdf0e10cSrcweir meHorizontal(eHorizontal), 467*cdf0e10cSrcweir meVertical(eVertical), 468*cdf0e10cSrcweir mfDistance(fDistance), 469*cdf0e10cSrcweir mfUpper(fUpper), 470*cdf0e10cSrcweir mfLower(fLower), 471*cdf0e10cSrcweir mfLeftDelta(fLeftDelta), 472*cdf0e10cSrcweir mfRightDelta(fRightDelta), 473*cdf0e10cSrcweir mbBelow(bBelow), 474*cdf0e10cSrcweir mbTextRotation(bTextRotation), 475*cdf0e10cSrcweir mbTextAutoAngle(bTextAutoAngle) 476*cdf0e10cSrcweir { 477*cdf0e10cSrcweir } 478*cdf0e10cSrcweir 479*cdf0e10cSrcweir bool SdrMeasurePrimitive2D::operator==(const BasePrimitive2D& rPrimitive) const 480*cdf0e10cSrcweir { 481*cdf0e10cSrcweir if(BufferedDecompositionPrimitive2D::operator==(rPrimitive)) 482*cdf0e10cSrcweir { 483*cdf0e10cSrcweir const SdrMeasurePrimitive2D& rCompare = (SdrMeasurePrimitive2D&)rPrimitive; 484*cdf0e10cSrcweir 485*cdf0e10cSrcweir return (getStart() == rCompare.getStart() 486*cdf0e10cSrcweir && getEnd() == rCompare.getEnd() 487*cdf0e10cSrcweir && getHorizontal() == rCompare.getHorizontal() 488*cdf0e10cSrcweir && getVertical() == rCompare.getVertical() 489*cdf0e10cSrcweir && getDistance() == rCompare.getDistance() 490*cdf0e10cSrcweir && getUpper() == rCompare.getUpper() 491*cdf0e10cSrcweir && getLower() == rCompare.getLower() 492*cdf0e10cSrcweir && getLeftDelta() == rCompare.getLeftDelta() 493*cdf0e10cSrcweir && getRightDelta() == rCompare.getRightDelta() 494*cdf0e10cSrcweir && getBelow() == rCompare.getBelow() 495*cdf0e10cSrcweir && getTextRotation() == rCompare.getTextRotation() 496*cdf0e10cSrcweir && getTextAutoAngle() == rCompare.getTextAutoAngle() 497*cdf0e10cSrcweir && getSdrLSTAttribute() == rCompare.getSdrLSTAttribute()); 498*cdf0e10cSrcweir } 499*cdf0e10cSrcweir 500*cdf0e10cSrcweir return false; 501*cdf0e10cSrcweir } 502*cdf0e10cSrcweir 503*cdf0e10cSrcweir // provide unique ID 504*cdf0e10cSrcweir ImplPrimitrive2DIDBlock(SdrMeasurePrimitive2D, PRIMITIVE2D_ID_SDRMEASUREPRIMITIVE2D) 505*cdf0e10cSrcweir 506*cdf0e10cSrcweir } // end of namespace primitive2d 507*cdf0e10cSrcweir } // end of namespace drawinglayer 508*cdf0e10cSrcweir 509*cdf0e10cSrcweir ////////////////////////////////////////////////////////////////////////////// 510*cdf0e10cSrcweir // eof 511