1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_vcl.hxx" 26 27 #include <tools/ref.hxx> 28 #include <tools/debug.hxx> 29 #include <tools/poly.hxx> 30 31 #include <vcl/svapp.hxx> 32 #include <vcl/region.hxx> 33 #include <vcl/virdev.hxx> 34 #include <vcl/window.hxx> 35 #include <vcl/metaact.hxx> 36 #include <vcl/gdimtf.hxx> 37 #include <vcl/print.hxx> 38 #include <vcl/outdev.hxx> 39 #include <vcl/unowrap.hxx> 40 41 #include <window.h> 42 #include <outdev.h> 43 #include <sallayout.hxx> 44 #include <salgdi.hxx> 45 #include <salframe.hxx> 46 #include <salvd.hxx> 47 #include <salprn.hxx> 48 #include <svdata.hxx> 49 #include <outdata.hxx> 50 51 52 #include "basegfx/polygon/b2dpolygon.hxx" 53 54 // ---------------------------------------------------------------------------- 55 // The only common SalFrame method 56 // ---------------------------------------------------------------------------- 57 58 SalFrameGeometry SalFrame::GetGeometry() 59 { 60 // mirror frame coordinates at parent 61 SalFrame *pParent = GetParent(); 62 if( pParent && Application::GetSettings().GetLayoutRTL() ) 63 { 64 SalFrameGeometry aGeom = maGeometry; 65 int parent_x = aGeom.nX - pParent->maGeometry.nX; 66 aGeom.nX = pParent->maGeometry.nX + pParent->maGeometry.nWidth - maGeometry.nWidth - parent_x; 67 return aGeom; 68 } 69 else 70 return maGeometry; 71 } 72 73 // ---------------------------------------------------------------------------- 74 75 SalGraphics::SalGraphics() 76 : m_nLayout( 0 ), 77 m_bAntiAliasB2DDraw(false) 78 { 79 // read global RTL settings 80 if( Application::GetSettings().GetLayoutRTL() ) 81 m_nLayout = SAL_LAYOUT_BIDI_RTL; 82 } 83 84 SalGraphics::~SalGraphics() 85 { 86 } 87 88 // ---------------------------------------------------------------------------- 89 90 bool SalGraphics::drawAlphaBitmap( const SalTwoRect&, 91 const SalBitmap&, const SalBitmap& ) 92 { 93 return false; 94 } 95 96 // ---------------------------------------------------------------------------- 97 98 bool SalGraphics::drawTransformedBitmap( 99 const basegfx::B2DPoint& /* rNull */, 100 const basegfx::B2DPoint& /* rX */, 101 const basegfx::B2DPoint& /* rY */, 102 const SalBitmap& /* rSourceBitmap */, 103 const SalBitmap* /* pAlphaBitmap */) 104 { 105 // here direct support for transformed bitmaps can be impemented 106 return false; 107 } 108 109 // ---------------------------------------------------------------------------- 110 111 void SalGraphics::mirror( long& x, const OutputDevice *pOutDev, bool bBack ) const 112 { 113 long w; 114 if( pOutDev && pOutDev->GetOutDevType() == OUTDEV_VIRDEV ) 115 w = pOutDev->GetOutputWidthPixel(); 116 else 117 w = GetGraphicsWidth(); 118 119 if( w ) 120 { 121 if( pOutDev && pOutDev->ImplIsAntiparallel() ) 122 { 123 OutputDevice *pOutDevRef = (OutputDevice*) pOutDev; 124 // mirror this window back 125 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) ) 126 { 127 long devX = w-pOutDevRef->GetOutputWidthPixel()-pOutDevRef->GetOutOffXPixel(); // re-mirrored mnOutOffX 128 if( bBack ) 129 x = x - devX + pOutDevRef->GetOutOffXPixel(); 130 else 131 x = devX + (x - pOutDevRef->GetOutOffXPixel()); 132 } 133 else 134 { 135 long devX = pOutDevRef->GetOutOffXPixel(); // re-mirrored mnOutOffX 136 if( bBack ) 137 x = x - pOutDevRef->GetOutputWidthPixel() + devX - pOutDevRef->GetOutOffXPixel() + 1; 138 else 139 x = pOutDevRef->GetOutputWidthPixel() - (x - devX) + pOutDevRef->GetOutOffXPixel() - 1; 140 } 141 } 142 else if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) ) 143 x = w-1-x; 144 } 145 } 146 147 void SalGraphics::mirror( long& x, long& nWidth, const OutputDevice *pOutDev, bool bBack ) const 148 { 149 long w; 150 if( pOutDev && pOutDev->GetOutDevType() == OUTDEV_VIRDEV ) 151 w = pOutDev->GetOutputWidthPixel(); 152 else 153 w = GetGraphicsWidth(); 154 155 if( w ) 156 { 157 if( pOutDev && pOutDev->ImplIsAntiparallel() ) 158 { 159 OutputDevice *pOutDevRef = (OutputDevice*) pOutDev; 160 // mirror this window back 161 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) ) 162 { 163 long devX = w-pOutDevRef->GetOutputWidthPixel()-pOutDevRef->GetOutOffXPixel(); // re-mirrored mnOutOffX 164 if( bBack ) 165 x = x - devX + pOutDevRef->GetOutOffXPixel(); 166 else 167 x = devX + (x - pOutDevRef->GetOutOffXPixel()); 168 } 169 else 170 { 171 long devX = pOutDevRef->GetOutOffXPixel(); // re-mirrored mnOutOffX 172 if( bBack ) 173 x = x - pOutDevRef->GetOutputWidthPixel() + devX - pOutDevRef->GetOutOffXPixel() + nWidth; 174 else 175 x = pOutDevRef->GetOutputWidthPixel() - (x - devX) + pOutDevRef->GetOutOffXPixel() - nWidth; 176 } 177 } 178 else if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) ) 179 x = w-nWidth-x; 180 181 } 182 } 183 184 sal_Bool SalGraphics::mirror( sal_uInt32 nPoints, const SalPoint *pPtAry, SalPoint *pPtAry2, const OutputDevice *pOutDev, bool bBack ) const 185 { 186 long w; 187 if( pOutDev && pOutDev->GetOutDevType() == OUTDEV_VIRDEV ) 188 w = pOutDev->GetOutputWidthPixel(); 189 else 190 w = GetGraphicsWidth(); 191 192 if( w ) 193 { 194 sal_uInt32 i, j; 195 196 if( pOutDev && pOutDev->ImplIsAntiparallel() ) 197 { 198 OutputDevice *pOutDevRef = (OutputDevice*) pOutDev; 199 // mirror this window back 200 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) ) 201 { 202 long devX = w-pOutDevRef->GetOutputWidthPixel()-pOutDevRef->GetOutOffXPixel(); // re-mirrored mnOutOffX 203 if( bBack ) 204 { 205 for( i=0, j=nPoints-1; i<nPoints; i++,j-- ) 206 { 207 //long x = w-1-pPtAry[i].mnX; 208 //pPtAry2[j].mnX = devX + ( pOutDevRef->mnOutWidth - 1 - (x - devX) ); 209 pPtAry2[j].mnX = pOutDevRef->GetOutOffXPixel() + (pPtAry[i].mnX - devX); 210 pPtAry2[j].mnY = pPtAry[i].mnY; 211 } 212 } 213 else 214 { 215 for( i=0, j=nPoints-1; i<nPoints; i++,j-- ) 216 { 217 //long x = w-1-pPtAry[i].mnX; 218 //pPtAry2[j].mnX = devX + ( pOutDevRef->mnOutWidth - 1 - (x - devX) ); 219 pPtAry2[j].mnX = devX + (pPtAry[i].mnX - pOutDevRef->GetOutOffXPixel()); 220 pPtAry2[j].mnY = pPtAry[i].mnY; 221 } 222 } 223 } 224 else 225 { 226 long devX = pOutDevRef->GetOutOffXPixel(); // re-mirrored mnOutOffX 227 if( bBack ) 228 { 229 for( i=0, j=nPoints-1; i<nPoints; i++,j-- ) 230 { 231 //long x = w-1-pPtAry[i].mnX; 232 //pPtAry2[j].mnX = devX + ( pOutDevRef->mnOutWidth - 1 - (x - devX) ); 233 pPtAry2[j].mnX = pPtAry[i].mnX - pOutDevRef->GetOutputWidthPixel() + devX - pOutDevRef->GetOutOffXPixel() + 1; 234 pPtAry2[j].mnY = pPtAry[i].mnY; 235 } 236 } 237 else 238 { 239 for( i=0, j=nPoints-1; i<nPoints; i++,j-- ) 240 { 241 //long x = w-1-pPtAry[i].mnX; 242 //pPtAry2[j].mnX = devX + ( pOutDevRef->mnOutWidth - 1 - (x - devX) ); 243 pPtAry2[j].mnX = pOutDevRef->GetOutputWidthPixel() - (pPtAry[i].mnX - devX) + pOutDevRef->GetOutOffXPixel() - 1; 244 pPtAry2[j].mnY = pPtAry[i].mnY; 245 } 246 } 247 } 248 } 249 else if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) ) 250 { 251 for( i=0, j=nPoints-1; i<nPoints; i++,j-- ) 252 { 253 pPtAry2[j].mnX = w-1-pPtAry[i].mnX; 254 pPtAry2[j].mnY = pPtAry[i].mnY; 255 } 256 } 257 return sal_True; 258 } 259 else 260 return sal_False; 261 } 262 263 void SalGraphics::mirror( Region& rRgn, const OutputDevice *pOutDev, bool bBack ) const 264 { 265 if( rRgn.HasPolyPolygonOrB2DPolyPolygon() ) 266 { 267 const basegfx::B2DPolyPolygon aPolyPoly(mirror(rRgn.GetAsB2DPolyPolygon(), pOutDev, bBack)); 268 269 rRgn = Region(aPolyPoly); 270 } 271 else 272 { 273 RectangleVector aRectangles; 274 rRgn.GetRegionRectangles(aRectangles); 275 rRgn.SetEmpty(); 276 277 for(RectangleVector::iterator aRectIter(aRectangles.begin()); aRectIter != aRectangles.end(); aRectIter++) 278 { 279 mirror(*aRectIter, pOutDev, bBack); 280 rRgn.Union(*aRectIter); 281 } 282 283 //ImplRegionInfo aInfo; 284 //bool bRegionRect; 285 //Region aMirroredRegion; 286 //long nX, nY, nWidth, nHeight; 287 // 288 //bRegionRect = rRgn.ImplGetFirstRect( aInfo, nX, nY, nWidth, nHeight ); 289 //while ( bRegionRect ) 290 //{ 291 // Rectangle aRect( Point(nX, nY), Size(nWidth, nHeight) ); 292 // mirror( aRect, pOutDev, bBack ); 293 // aMirroredRegion.Union( aRect ); 294 // bRegionRect = rRgn.ImplGetNextRect( aInfo, nX, nY, nWidth, nHeight ); 295 //} 296 //rRgn = aMirroredRegion; 297 } 298 } 299 300 void SalGraphics::mirror( Rectangle& rRect, const OutputDevice *pOutDev, bool bBack ) const 301 { 302 long nWidth = rRect.GetWidth(); 303 long x = rRect.Left(); 304 long x_org = x; 305 306 mirror( x, nWidth, pOutDev, bBack ); 307 rRect.Move( x - x_org, 0 ); 308 } 309 310 basegfx::B2DPoint SalGraphics::mirror( const basegfx::B2DPoint& i_rPoint, const OutputDevice *i_pOutDev, bool i_bBack ) const 311 { 312 long w; 313 if( i_pOutDev && i_pOutDev->GetOutDevType() == OUTDEV_VIRDEV ) 314 w = i_pOutDev->GetOutputWidthPixel(); 315 else 316 w = GetGraphicsWidth(); 317 318 DBG_ASSERT( w, "missing graphics width" ); 319 320 basegfx::B2DPoint aRet( i_rPoint ); 321 if( w ) 322 { 323 if( i_pOutDev && !i_pOutDev->IsRTLEnabled() ) 324 { 325 OutputDevice *pOutDevRef = (OutputDevice*)i_pOutDev; 326 // mirror this window back 327 double devX = w-pOutDevRef->GetOutputWidthPixel()-pOutDevRef->GetOutOffXPixel(); // re-mirrored mnOutOffX 328 if( i_bBack ) 329 aRet.setX( i_rPoint.getX() - devX + pOutDevRef->GetOutOffXPixel() ); 330 else 331 aRet.setX( devX + (i_rPoint.getX() - pOutDevRef->GetOutOffXPixel()) ); 332 } 333 else 334 aRet.setX( w-1-i_rPoint.getX() ); 335 } 336 return aRet; 337 } 338 339 basegfx::B2DPolygon SalGraphics::mirror( const basegfx::B2DPolygon& i_rPoly, const OutputDevice *i_pOutDev, bool i_bBack ) const 340 { 341 long w; 342 if( i_pOutDev && i_pOutDev->GetOutDevType() == OUTDEV_VIRDEV ) 343 w = i_pOutDev->GetOutputWidthPixel(); 344 else 345 w = GetGraphicsWidth(); 346 347 DBG_ASSERT( w, "missing graphics width" ); 348 349 basegfx::B2DPolygon aRet; 350 if( w ) 351 { 352 sal_Int32 nPoints = i_rPoly.count(); 353 for( sal_Int32 i = 0; i < nPoints; i++ ) 354 { 355 aRet.append( mirror( i_rPoly.getB2DPoint( i ), i_pOutDev, i_bBack ) ); 356 if( i_rPoly.isPrevControlPointUsed( i ) ) 357 aRet.setPrevControlPoint( i, mirror( i_rPoly.getPrevControlPoint( i ), i_pOutDev, i_bBack ) ); 358 if( i_rPoly.isNextControlPointUsed( i ) ) 359 aRet.setNextControlPoint( i, mirror( i_rPoly.getNextControlPoint( i ), i_pOutDev, i_bBack ) ); 360 } 361 aRet.setClosed( i_rPoly.isClosed() ); 362 aRet.flip(); 363 } 364 else 365 aRet = i_rPoly; 366 return aRet; 367 } 368 369 basegfx::B2DPolyPolygon SalGraphics::mirror( const basegfx::B2DPolyPolygon& i_rPoly, const OutputDevice *i_pOutDev, bool i_bBack ) const 370 { 371 long w; 372 if( i_pOutDev && i_pOutDev->GetOutDevType() == OUTDEV_VIRDEV ) 373 w = i_pOutDev->GetOutputWidthPixel(); 374 else 375 w = GetGraphicsWidth(); 376 377 DBG_ASSERT( w, "missing graphics width" ); 378 379 basegfx::B2DPolyPolygon aRet; 380 if( w ) 381 { 382 sal_Int32 nPoly = i_rPoly.count(); 383 for( sal_Int32 i = 0; i < nPoly; i++ ) 384 aRet.append( mirror( i_rPoly.getB2DPolygon( i ), i_pOutDev, i_bBack ) ); 385 aRet.setClosed( i_rPoly.isClosed() ); 386 aRet.flip(); 387 } 388 else 389 aRet = i_rPoly; 390 return aRet; 391 } 392 393 // ---------------------------------------------------------------------------- 394 395 bool SalGraphics::SetClipRegion( const Region& i_rClip, const OutputDevice *pOutDev ) 396 { 397 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 398 { 399 Region aMirror( i_rClip ); 400 mirror( aMirror, pOutDev ); 401 return setClipRegion( aMirror ); 402 } 403 return setClipRegion( i_rClip ); 404 } 405 406 void SalGraphics::DrawPixel( long nX, long nY, const OutputDevice *pOutDev ) 407 { 408 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 409 mirror( nX, pOutDev ); 410 drawPixel( nX, nY ); 411 } 412 void SalGraphics::DrawPixel( long nX, long nY, SalColor nSalColor, const OutputDevice *pOutDev ) 413 { 414 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 415 mirror( nX, pOutDev ); 416 drawPixel( nX, nY, nSalColor ); 417 } 418 void SalGraphics::DrawLine( long nX1, long nY1, long nX2, long nY2, const OutputDevice *pOutDev ) 419 { 420 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 421 { 422 mirror( nX1, pOutDev ); 423 mirror( nX2, pOutDev ); 424 } 425 drawLine( nX1, nY1, nX2, nY2 ); 426 } 427 void SalGraphics::DrawRect( long nX, long nY, long nWidth, long nHeight, const OutputDevice *pOutDev ) 428 { 429 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 430 mirror( nX, nWidth, pOutDev ); 431 drawRect( nX, nY, nWidth, nHeight ); 432 } 433 bool SalGraphics::drawPolyLine( 434 const basegfx::B2DPolygon& /*rPolyPolygon*/, 435 double /*fTransparency*/, 436 const basegfx::B2DVector& /*rLineWidths*/, 437 basegfx::B2DLineJoin /*eLineJoin*/, 438 com::sun::star::drawing::LineCap /*eLineCap*/) 439 { 440 return false; 441 } 442 443 void SalGraphics::DrawPolyLine( sal_uLong nPoints, const SalPoint* pPtAry, const OutputDevice *pOutDev ) 444 { 445 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 446 { 447 SalPoint* pPtAry2 = new SalPoint[nPoints]; 448 sal_Bool bCopied = mirror( nPoints, pPtAry, pPtAry2, pOutDev ); 449 drawPolyLine( nPoints, bCopied ? pPtAry2 : pPtAry ); 450 delete [] pPtAry2; 451 } 452 else 453 drawPolyLine( nPoints, pPtAry ); 454 } 455 456 void SalGraphics::DrawPolygon( sal_uLong nPoints, const SalPoint* pPtAry, const OutputDevice *pOutDev ) 457 { 458 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 459 { 460 SalPoint* pPtAry2 = new SalPoint[nPoints]; 461 sal_Bool bCopied = mirror( nPoints, pPtAry, pPtAry2, pOutDev ); 462 drawPolygon( nPoints, bCopied ? pPtAry2 : pPtAry ); 463 delete [] pPtAry2; 464 } 465 else 466 drawPolygon( nPoints, pPtAry ); 467 } 468 469 void SalGraphics::DrawPolyPolygon( sal_uInt32 nPoly, const sal_uInt32* pPoints, PCONSTSALPOINT* pPtAry, const OutputDevice *pOutDev ) 470 { 471 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 472 { 473 // TODO: optimize, reduce new/delete calls 474 SalPoint **pPtAry2 = new SalPoint*[nPoly]; 475 sal_uLong i; 476 for(i=0; i<nPoly; i++) 477 { 478 sal_uLong nPoints = pPoints[i]; 479 pPtAry2[i] = new SalPoint[ nPoints ]; 480 mirror( nPoints, pPtAry[i], pPtAry2[i], pOutDev ); 481 } 482 483 drawPolyPolygon( nPoly, pPoints, (PCONSTSALPOINT*)pPtAry2 ); 484 485 for(i=0; i<nPoly; i++) 486 delete [] pPtAry2[i]; 487 delete [] pPtAry2; 488 } 489 else 490 drawPolyPolygon( nPoly, pPoints, pPtAry ); 491 } 492 493 bool SalGraphics::DrawPolyPolygon( const ::basegfx::B2DPolyPolygon& i_rPolyPolygon, double i_fTransparency, const OutputDevice* i_pOutDev ) 494 { 495 bool bRet = false; 496 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (i_pOutDev && i_pOutDev->IsRTLEnabled()) ) 497 { 498 basegfx::B2DPolyPolygon aMirror( mirror( i_rPolyPolygon, i_pOutDev ) ); 499 bRet = drawPolyPolygon( aMirror, i_fTransparency ); 500 } 501 else 502 bRet = drawPolyPolygon( i_rPolyPolygon, i_fTransparency ); 503 return bRet; 504 } 505 506 bool SalGraphics::drawPolyPolygon( const ::basegfx::B2DPolyPolygon&, double /*fTransparency*/) 507 { 508 return false; 509 } 510 511 sal_Bool SalGraphics::DrawPolyLineBezier( sal_uLong nPoints, const SalPoint* pPtAry, const sal_uInt8* pFlgAry, const OutputDevice* pOutDev ) 512 { 513 sal_Bool bResult = sal_False; 514 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 515 { 516 SalPoint* pPtAry2 = new SalPoint[nPoints]; 517 sal_Bool bCopied = mirror( nPoints, pPtAry, pPtAry2, pOutDev ); 518 bResult = drawPolyLineBezier( nPoints, bCopied ? pPtAry2 : pPtAry, pFlgAry ); 519 delete [] pPtAry2; 520 } 521 else 522 bResult = drawPolyLineBezier( nPoints, pPtAry, pFlgAry ); 523 return bResult; 524 } 525 526 sal_Bool SalGraphics::DrawPolygonBezier( sal_uLong nPoints, const SalPoint* pPtAry, const sal_uInt8* pFlgAry, const OutputDevice* pOutDev ) 527 { 528 sal_Bool bResult = sal_False; 529 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 530 { 531 SalPoint* pPtAry2 = new SalPoint[nPoints]; 532 sal_Bool bCopied = mirror( nPoints, pPtAry, pPtAry2, pOutDev ); 533 bResult = drawPolygonBezier( nPoints, bCopied ? pPtAry2 : pPtAry, pFlgAry ); 534 delete [] pPtAry2; 535 } 536 else 537 bResult = drawPolygonBezier( nPoints, pPtAry, pFlgAry ); 538 return bResult; 539 } 540 541 sal_Bool SalGraphics::DrawPolyPolygonBezier( sal_uInt32 i_nPoly, const sal_uInt32* i_pPoints, 542 const SalPoint* const* i_pPtAry, const sal_uInt8* const* i_pFlgAry, const OutputDevice* i_pOutDev ) 543 { 544 sal_Bool bRet = sal_False; 545 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (i_pOutDev && i_pOutDev->IsRTLEnabled()) ) 546 { 547 // TODO: optimize, reduce new/delete calls 548 SalPoint **pPtAry2 = new SalPoint*[i_nPoly]; 549 sal_uLong i; 550 for(i=0; i<i_nPoly; i++) 551 { 552 sal_uLong nPoints = i_pPoints[i]; 553 pPtAry2[i] = new SalPoint[ nPoints ]; 554 mirror( nPoints, i_pPtAry[i], pPtAry2[i], i_pOutDev ); 555 } 556 557 bRet = drawPolyPolygonBezier( i_nPoly, i_pPoints, (PCONSTSALPOINT*)pPtAry2, i_pFlgAry ); 558 559 for(i=0; i<i_nPoly; i++) 560 delete [] pPtAry2[i]; 561 delete [] pPtAry2; 562 } 563 else 564 bRet = drawPolyPolygonBezier( i_nPoly, i_pPoints, i_pPtAry, i_pFlgAry ); 565 return bRet; 566 } 567 568 bool SalGraphics::DrawPolyLine( 569 const ::basegfx::B2DPolygon& i_rPolygon, 570 double i_fTransparency, 571 const ::basegfx::B2DVector& i_rLineWidth, 572 basegfx::B2DLineJoin i_eLineJoin, 573 com::sun::star::drawing::LineCap i_eLineCap, 574 const OutputDevice* i_pOutDev ) 575 { 576 bool bRet = false; 577 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (i_pOutDev && i_pOutDev->IsRTLEnabled()) ) 578 { 579 basegfx::B2DPolygon aMirror( mirror( i_rPolygon, i_pOutDev ) ); 580 bRet = drawPolyLine( aMirror, i_fTransparency, i_rLineWidth, i_eLineJoin, i_eLineCap ); 581 } 582 else 583 bRet = drawPolyLine( i_rPolygon, i_fTransparency, i_rLineWidth, i_eLineJoin, i_eLineCap ); 584 return bRet; 585 } 586 587 void SalGraphics::CopyArea( long nDestX, long nDestY, 588 long nSrcX, long nSrcY, 589 long nSrcWidth, long nSrcHeight, 590 sal_uInt16 nFlags, const OutputDevice *pOutDev ) 591 { 592 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 593 { 594 mirror( nDestX, nSrcWidth, pOutDev ); 595 mirror( nSrcX, nSrcWidth, pOutDev ); 596 } 597 copyArea( nDestX, nDestY, nSrcX, nSrcY, nSrcWidth, nSrcHeight, nFlags ); 598 } 599 void SalGraphics::CopyBits( const SalTwoRect& rPosAry, 600 SalGraphics* pSrcGraphics, const OutputDevice *pOutDev, const OutputDevice *pSrcOutDev ) 601 { 602 if( ( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) || 603 (pSrcGraphics && ( (pSrcGraphics->GetLayout() & SAL_LAYOUT_BIDI_RTL) || (pSrcOutDev && pSrcOutDev->IsRTLEnabled()) ) ) ) 604 { 605 SalTwoRect aPosAry2 = rPosAry; 606 if( (pSrcGraphics && (pSrcGraphics->GetLayout() & SAL_LAYOUT_BIDI_RTL)) || (pSrcOutDev && pSrcOutDev->IsRTLEnabled()) ) 607 mirror( aPosAry2.mnSrcX, aPosAry2.mnSrcWidth, pSrcOutDev ); 608 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 609 mirror( aPosAry2.mnDestX, aPosAry2.mnDestWidth, pOutDev ); 610 copyBits( aPosAry2, pSrcGraphics ); 611 } 612 else 613 copyBits( rPosAry, pSrcGraphics ); 614 } 615 void SalGraphics::DrawBitmap( const SalTwoRect& rPosAry, 616 const SalBitmap& rSalBitmap, const OutputDevice *pOutDev ) 617 { 618 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 619 { 620 SalTwoRect aPosAry2 = rPosAry; 621 mirror( aPosAry2.mnDestX, aPosAry2.mnDestWidth, pOutDev ); 622 drawBitmap( aPosAry2, rSalBitmap ); 623 } 624 else 625 drawBitmap( rPosAry, rSalBitmap ); 626 } 627 void SalGraphics::DrawBitmap( const SalTwoRect& rPosAry, 628 const SalBitmap& rSalBitmap, 629 SalColor nTransparentColor, const OutputDevice *pOutDev ) 630 { 631 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 632 { 633 SalTwoRect aPosAry2 = rPosAry; 634 mirror( aPosAry2.mnDestX, aPosAry2.mnDestWidth, pOutDev ); 635 drawBitmap( aPosAry2, rSalBitmap, nTransparentColor ); 636 } 637 else 638 drawBitmap( rPosAry, rSalBitmap, nTransparentColor ); 639 } 640 void SalGraphics::DrawBitmap( const SalTwoRect& rPosAry, 641 const SalBitmap& rSalBitmap, 642 const SalBitmap& rTransparentBitmap, const OutputDevice *pOutDev ) 643 { 644 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 645 { 646 SalTwoRect aPosAry2 = rPosAry; 647 mirror( aPosAry2.mnDestX, aPosAry2.mnDestWidth, pOutDev ); 648 drawBitmap( aPosAry2, rSalBitmap, rTransparentBitmap ); 649 } 650 else 651 drawBitmap( rPosAry, rSalBitmap, rTransparentBitmap ); 652 } 653 void SalGraphics::DrawMask( const SalTwoRect& rPosAry, 654 const SalBitmap& rSalBitmap, 655 SalColor nMaskColor, const OutputDevice *pOutDev ) 656 { 657 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 658 { 659 SalTwoRect aPosAry2 = rPosAry; 660 mirror( aPosAry2.mnDestX, aPosAry2.mnDestWidth, pOutDev ); 661 drawMask( aPosAry2, rSalBitmap, nMaskColor ); 662 } 663 else 664 drawMask( rPosAry, rSalBitmap, nMaskColor ); 665 } 666 SalBitmap* SalGraphics::GetBitmap( long nX, long nY, long nWidth, long nHeight, const OutputDevice *pOutDev ) 667 { 668 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 669 mirror( nX, nWidth, pOutDev ); 670 return getBitmap( nX, nY, nWidth, nHeight ); 671 } 672 SalColor SalGraphics::GetPixel( long nX, long nY, const OutputDevice *pOutDev ) 673 { 674 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 675 mirror( nX, pOutDev ); 676 return getPixel( nX, nY ); 677 } 678 void SalGraphics::Invert( long nX, long nY, long nWidth, long nHeight, SalInvert nFlags, const OutputDevice *pOutDev ) 679 { 680 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 681 mirror( nX, nWidth, pOutDev ); 682 invert( nX, nY, nWidth, nHeight, nFlags ); 683 } 684 void SalGraphics::Invert( sal_uLong nPoints, const SalPoint* pPtAry, SalInvert nFlags, const OutputDevice *pOutDev ) 685 { 686 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 687 { 688 SalPoint* pPtAry2 = new SalPoint[nPoints]; 689 sal_Bool bCopied = mirror( nPoints, pPtAry, pPtAry2, pOutDev ); 690 invert( nPoints, bCopied ? pPtAry2 : pPtAry, nFlags ); 691 delete [] pPtAry2; 692 } 693 else 694 invert( nPoints, pPtAry, nFlags ); 695 } 696 697 sal_Bool SalGraphics::DrawEPS( long nX, long nY, long nWidth, long nHeight, void* pPtr, sal_uLong nSize, const OutputDevice *pOutDev ) 698 { 699 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 700 mirror( nX, nWidth, pOutDev ); 701 return drawEPS( nX, nY, nWidth, nHeight, pPtr, nSize ); 702 } 703 704 sal_Bool SalGraphics::HitTestNativeControl( ControlType nType, ControlPart nPart, const Rectangle& rControlRegion, 705 const Point& aPos, sal_Bool& rIsInside, const OutputDevice *pOutDev ) 706 { 707 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 708 { 709 Point pt( aPos ); 710 Rectangle rgn( rControlRegion ); 711 mirror( pt.X(), pOutDev ); 712 mirror( rgn, pOutDev ); 713 return hitTestNativeControl( nType, nPart, rgn, pt, rIsInside ); 714 } 715 else 716 return hitTestNativeControl( nType, nPart, rControlRegion, aPos, rIsInside ); 717 } 718 719 void SalGraphics::mirror( ControlType , const ImplControlValue& rVal, const OutputDevice* pOutDev, bool bBack ) const 720 { 721 switch( rVal.getType() ) 722 { 723 case CTRL_SLIDER: 724 { 725 SliderValue* pSlVal = static_cast<SliderValue*>(const_cast<ImplControlValue*>(&rVal)); 726 mirror(pSlVal->maThumbRect,pOutDev,bBack); 727 } 728 break; 729 case CTRL_SCROLLBAR: 730 { 731 ScrollbarValue* pScVal = static_cast<ScrollbarValue*>(const_cast<ImplControlValue*>(&rVal)); 732 mirror(pScVal->maThumbRect,pOutDev,bBack); 733 mirror(pScVal->maButton1Rect,pOutDev,bBack); 734 mirror(pScVal->maButton2Rect,pOutDev,bBack); 735 } 736 break; 737 case CTRL_SPINBOX: 738 case CTRL_SPINBUTTONS: 739 { 740 SpinbuttonValue* pSpVal = static_cast<SpinbuttonValue*>(const_cast<ImplControlValue*>(&rVal)); 741 mirror(pSpVal->maUpperRect,pOutDev,bBack); 742 mirror(pSpVal->maLowerRect,pOutDev,bBack); 743 } 744 break; 745 case CTRL_TOOLBAR: 746 { 747 ToolbarValue* pTVal = static_cast<ToolbarValue*>(const_cast<ImplControlValue*>(&rVal)); 748 mirror(pTVal->maGripRect,pOutDev,bBack); 749 } 750 break; 751 } 752 } 753 754 sal_Bool SalGraphics::DrawNativeControl( ControlType nType, ControlPart nPart, const Rectangle& rControlRegion, 755 ControlState nState, const ImplControlValue& aValue, 756 const OUString& aCaption, const OutputDevice *pOutDev ) 757 { 758 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 759 { 760 Rectangle rgn( rControlRegion ); 761 mirror( rgn, pOutDev ); 762 mirror( nType, aValue, pOutDev ); 763 sal_Bool bRet = drawNativeControl( nType, nPart, rgn, nState, aValue, aCaption ); 764 mirror( nType, aValue, pOutDev, true ); 765 return bRet; 766 } 767 else 768 return drawNativeControl( nType, nPart, rControlRegion, nState, aValue, aCaption ); 769 } 770 771 sal_Bool SalGraphics::DrawNativeControlText( ControlType nType, ControlPart nPart, const Rectangle& rControlRegion, 772 ControlState nState, const ImplControlValue& aValue, 773 const OUString& aCaption, const OutputDevice *pOutDev ) 774 { 775 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 776 { 777 Rectangle rgn( rControlRegion ); 778 mirror( rgn, pOutDev ); 779 mirror( nType, aValue, pOutDev ); 780 sal_Bool bRet = drawNativeControlText( nType, nPart, rgn, nState, aValue, aCaption ); 781 mirror( nType, aValue, pOutDev, true ); 782 return bRet; 783 } 784 else 785 return drawNativeControlText( nType, nPart, rControlRegion, nState, aValue, aCaption ); 786 } 787 788 sal_Bool SalGraphics::GetNativeControlRegion( ControlType nType, ControlPart nPart, const Rectangle& rControlRegion, ControlState nState, 789 const ImplControlValue& aValue, const OUString& aCaption, 790 Rectangle &rNativeBoundingRegion, Rectangle &rNativeContentRegion, const OutputDevice *pOutDev ) 791 { 792 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 793 { 794 Rectangle rgn( rControlRegion ); 795 mirror( rgn, pOutDev ); 796 mirror( nType, aValue, pOutDev ); 797 if( getNativeControlRegion( nType, nPart, rgn, nState, aValue, aCaption, 798 rNativeBoundingRegion, rNativeContentRegion ) ) 799 { 800 mirror( rNativeBoundingRegion, pOutDev, true ); 801 mirror( rNativeContentRegion, pOutDev, true ); 802 mirror( nType, aValue, pOutDev, true ); 803 return sal_True; 804 } 805 else 806 { 807 mirror( nType, aValue, pOutDev, true ); 808 return sal_False; 809 } 810 } 811 else 812 return getNativeControlRegion( nType, nPart, rControlRegion, nState, aValue, aCaption, 813 rNativeBoundingRegion, rNativeContentRegion ); 814 } 815 816 bool SalGraphics::DrawAlphaBitmap( const SalTwoRect& rPosAry, 817 const SalBitmap& rSourceBitmap, 818 const SalBitmap& rAlphaBitmap, 819 const OutputDevice *pOutDev ) 820 { 821 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 822 { 823 SalTwoRect aPosAry2 = rPosAry; 824 mirror( aPosAry2.mnDestX, aPosAry2.mnDestWidth, pOutDev ); 825 return drawAlphaBitmap( aPosAry2, rSourceBitmap, rAlphaBitmap ); 826 } 827 else 828 return drawAlphaBitmap( rPosAry, rSourceBitmap, rAlphaBitmap ); 829 } 830 831 bool SalGraphics::DrawTransformedBitmap( 832 const basegfx::B2DPoint& rNull, 833 const basegfx::B2DPoint& rX, 834 const basegfx::B2DPoint& rY, 835 const SalBitmap& rSourceBitmap, 836 const SalBitmap* pAlphaBitmap, 837 const OutputDevice* pOutDev) 838 { 839 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 840 { 841 basegfx::B2DPoint aNull(rNull); 842 basegfx::B2DPoint aX(rX); 843 basegfx::B2DPoint aY(rY); 844 845 mirror(aNull, pOutDev); 846 mirror(aX, pOutDev); 847 mirror(aY, pOutDev); 848 849 return drawTransformedBitmap(aNull, aX, aY, rSourceBitmap, pAlphaBitmap); 850 } 851 else 852 { 853 return drawTransformedBitmap(rNull, rX, rY, rSourceBitmap, pAlphaBitmap); 854 } 855 } 856 857 bool SalGraphics::DrawAlphaRect( long nX, long nY, long nWidth, long nHeight, 858 sal_uInt8 nTransparency, const OutputDevice *pOutDev ) 859 { 860 if( (m_nLayout & SAL_LAYOUT_BIDI_RTL) || (pOutDev && pOutDev->IsRTLEnabled()) ) 861 mirror( nX, nWidth, pOutDev ); 862 863 return drawAlphaRect( nX, nY, nWidth, nHeight, nTransparency ); 864 } 865 866 bool SalGraphics::filterText( const String&, String&, xub_StrLen, xub_StrLen&, xub_StrLen&, xub_StrLen& ) 867 { 868 return false; 869 } 870 871 void SalGraphics::AddDevFontSubstitute( OutputDevice* pOutDev, 872 const String& rFontName, 873 const String& rReplaceFontName, 874 sal_uInt16 nFlags ) 875 { 876 pOutDev->ImplAddDevFontSubstitute( rFontName, rReplaceFontName, nFlags ); 877 } 878 879