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_svx.hxx" 26 27 #define ENABLE_BYTESTRING_STREAM_OPERATORS 28 29 #include <com/sun/star/lang/XUnoTunnel.hpp> 30 #include <sfx2/objsh.hxx> 31 #include <sfx2/docfac.hxx> 32 #include <comphelper/classids.hxx> 33 #include <unotools/pathoptions.hxx> 34 #include <tools/rcid.h> 35 #include <tools/vcompat.hxx> 36 #include <vcl/virdev.hxx> 37 #include <svl/itempool.hxx> 38 #include <svx/fmmodel.hxx> 39 #include <svx/fmview.hxx> 40 #include <svx/fmpage.hxx> 41 #include "gallery.hrc" 42 #include "svx/galmisc.hxx" 43 #include "galobj.hxx" 44 #include <vcl/salbtype.hxx> // FRound 45 #include <vcl/svapp.hxx> 46 #include <vcl/dibtools.hxx> 47 #include "gallerydrawmodel.hxx" 48 49 using namespace ::com::sun::star; 50 51 // ------------- 52 // - SgaObject - 53 // ------------- 54 55 SgaObject::SgaObject() 56 : bIsValid ( sal_False ), 57 bIsThumbBmp ( sal_True ) 58 { 59 } 60 61 BitmapEx SgaObject::createPreviewBitmapEx(const Size& rSizePixel) const 62 { 63 BitmapEx aRetval; 64 65 if(rSizePixel.Width() && rSizePixel.Height()) 66 { 67 if(SGA_OBJ_SOUND == GetObjKind()) 68 { 69 aRetval = GAL_RESID(RID_SVXBMP_GALLERY_MEDIA); 70 } 71 else if(IsThumbBitmap()) 72 { 73 aRetval = GetThumbBmp(); 74 } 75 else 76 { 77 const Graphic aGraphic(GetThumbMtf()); 78 79 aRetval = aGraphic.GetBitmapEx(); 80 } 81 82 if(!aRetval.IsEmpty()) 83 { 84 const Size aCurrentSizePixel(aRetval.GetSizePixel()); 85 const double fScaleX((double)rSizePixel.Width() / (double)aCurrentSizePixel.Width()); 86 const double fScaleY((double)rSizePixel.Height() / (double)aCurrentSizePixel.Height()); 87 const double fScale(std::min(fScaleX, fScaleY)); 88 89 // only scale when need to decrease, no need to make bigger as original. Also 90 // prevent scaling close to 1.0 which is not needed for pixel graphics 91 if(fScale < 1.0 && fabs(1.0 - fScale) > 0.005) 92 { 93 static sal_uInt32 nScaleFlag = BMP_SCALE_FASTESTINTERPOLATE; 94 95 aRetval.Scale(fScale, fScale, nScaleFlag); 96 } 97 } 98 } 99 100 return aRetval; 101 } 102 103 // ------------------------------------------------------------------------ 104 105 sal_Bool SgaObject::CreateThumb( const Graphic& rGraphic ) 106 { 107 sal_Bool bRet = sal_False; 108 109 if( rGraphic.GetType() == GRAPHIC_BITMAP ) 110 { 111 BitmapEx aBmpEx( rGraphic.GetBitmapEx() ); 112 Size aBmpSize( aBmpEx.GetSizePixel() ); 113 114 if( aBmpSize.Width() && aBmpSize.Height() ) 115 { 116 const Color aWhite( COL_WHITE ); 117 118 if( aBmpEx.GetPrefMapMode().GetMapUnit() != MAP_PIXEL && 119 aBmpEx.GetPrefSize().Width() > 0 && 120 aBmpEx.GetPrefSize().Height() > 0 ) 121 { 122 Size aLogSize( OutputDevice::LogicToLogic( aBmpEx.GetPrefSize(), aBmpEx.GetPrefMapMode(), MAP_100TH_MM ) ); 123 124 if( aLogSize.Width() > 0 && aLogSize.Height() > 0 ) 125 { 126 double fFactorLog = static_cast< double >( aLogSize.Width() ) / aLogSize.Height(); 127 double fFactorPix = static_cast< double >( aBmpSize.Width() ) / aBmpSize.Height(); 128 129 if( fFactorPix > fFactorLog ) 130 aBmpSize.Width() = FRound( aBmpSize.Height() * fFactorLog ); 131 else 132 aBmpSize.Height() = FRound( aBmpSize.Width() / fFactorLog ); 133 134 aBmpEx.SetSizePixel( aBmpSize, BMP_SCALE_BESTQUALITY ); 135 } 136 } 137 138 // take over BitmapEx 139 aThumbBmp = aBmpEx; 140 141 if( ( aBmpSize.Width() <= S_THUMB ) && ( aBmpSize.Height() <= S_THUMB ) ) 142 { 143 aThumbBmp.Convert( BMP_CONVERSION_8BIT_COLORS ); 144 bRet = sal_True; 145 } 146 else 147 { 148 const float fFactor = (float) aBmpSize.Width() / aBmpSize.Height(); 149 const Size aNewSize( Max( (long) (fFactor < 1. ? S_THUMB * fFactor : S_THUMB), 8L ), 150 Max( (long) (fFactor < 1. ? S_THUMB : S_THUMB / fFactor), 8L ) ); 151 152 if(aThumbBmp.Scale( 153 (double) aNewSize.Width() / aBmpSize.Width(), 154 (double) aNewSize.Height() / aBmpSize.Height(), 155 BMP_SCALE_BESTQUALITY ) ) 156 { 157 aThumbBmp.Convert( BMP_CONVERSION_8BIT_COLORS ); 158 bRet = sal_True; 159 } 160 } 161 } 162 } 163 else if( rGraphic.GetType() == GRAPHIC_GDIMETAFILE ) 164 { 165 const Size aPrefSize( rGraphic.GetPrefSize() ); 166 const double fFactor = (double)aPrefSize.Width() / (double)aPrefSize.Height(); 167 Size aSize( S_THUMB, S_THUMB ); 168 if ( fFactor < 1.0 ) 169 aSize.Width() = (sal_Int32)( S_THUMB * fFactor ); 170 else 171 aSize.Height() = (sal_Int32)( S_THUMB / fFactor ); 172 173 const GraphicConversionParameters aParameters(aSize, false, true, true, true); 174 aThumbBmp = rGraphic.GetBitmapEx(aParameters); 175 176 if( !aThumbBmp.IsEmpty() ) 177 { 178 aThumbBmp.Convert( BMP_CONVERSION_8BIT_COLORS ); 179 bRet = sal_True; 180 } 181 } 182 183 return bRet; 184 } 185 186 // ------------------------------------------------------------------------ 187 188 void SgaObject::WriteData( SvStream& rOut, const String& rDestDir ) const 189 { 190 static const sal_uInt32 nInventor = COMPAT_FORMAT( 'S', 'G', 'A', '3' ); 191 192 rOut << nInventor << (sal_uInt16) 0x0004 << GetVersion() << (sal_uInt16) GetObjKind(); 193 rOut << bIsThumbBmp; 194 195 if( bIsThumbBmp ) 196 { 197 const sal_uInt16 nOldCompressMode = rOut.GetCompressMode(); 198 const sal_uIntPtr nOldVersion = rOut.GetVersion(); 199 200 rOut.SetCompressMode( COMPRESSMODE_ZBITMAP ); 201 rOut.SetVersion( SOFFICE_FILEFORMAT_50 ); 202 203 WriteDIBBitmapEx(aThumbBmp, rOut); 204 205 rOut.SetVersion( nOldVersion ); 206 rOut.SetCompressMode( nOldCompressMode ); 207 } 208 else 209 rOut << aThumbMtf; 210 211 String aURLWithoutDestDir = String(aURL.GetMainURL( INetURLObject::NO_DECODE )); 212 aURLWithoutDestDir.SearchAndReplace(rDestDir, String()); 213 rOut << ByteString( aURLWithoutDestDir, RTL_TEXTENCODING_UTF8 ); 214 } 215 216 // ------------------------------------------------------------------------ 217 218 void SgaObject::ReadData(SvStream& rIn, sal_uInt16& rReadVersion ) 219 { 220 ByteString aTmpStr; 221 sal_uInt32 nTmp32; 222 sal_uInt16 nTmp16; 223 224 rIn >> nTmp32 >> nTmp16 >> rReadVersion >> nTmp16 >> bIsThumbBmp; 225 226 if( bIsThumbBmp ) 227 { 228 ReadDIBBitmapEx(aThumbBmp, rIn); 229 } 230 else 231 { 232 rIn >> aThumbMtf; 233 } 234 235 rIn >> aTmpStr; aURL = INetURLObject( String( aTmpStr.GetBuffer(), RTL_TEXTENCODING_UTF8 ) ); 236 } 237 238 // ------------------------------------------------------------------------ 239 240 const String SgaObject::GetTitle() const 241 { 242 String aReturnValue( aTitle ); 243 if ( !getenv( "GALLERY_SHOW_PRIVATE_TITLE" ) ) 244 { 245 if ( aReturnValue.GetTokenCount( ':' ) == 3 ) 246 { 247 String aPrivateInd ( aReturnValue.GetToken( 0, ':' ) ); 248 String aResourceName( aReturnValue.GetToken( 1, ':' ) ); 249 sal_Int32 nResId ( aReturnValue.GetToken( 2, ':' ).ToInt32() ); 250 if ( aReturnValue.GetToken( 0, ':' ).EqualsAscii( "private" ) && 251 aResourceName.Len() && ( nResId > 0 ) && ( nResId < 0x10000 ) ) 252 { 253 ByteString aMgrName( aResourceName, RTL_TEXTENCODING_UTF8 ); 254 ResMgr* pResMgr = ResMgr::CreateResMgr( aMgrName.GetBuffer(), 255 Application::GetSettings().GetUILocale() ); 256 if ( pResMgr ) 257 { 258 ResId aResId( (sal_uInt16)nResId, *pResMgr ); 259 aResId.SetRT( RSC_STRING ); 260 if ( pResMgr->IsAvailable( aResId ) ) 261 { 262 aReturnValue = String( aResId ); 263 } 264 delete pResMgr; 265 } 266 } 267 } 268 } 269 return aReturnValue; 270 } 271 272 // ------------------------------------------------------------------------ 273 274 void SgaObject::SetTitle( const String& rTitle ) 275 { 276 aTitle = rTitle; 277 } 278 279 // ------------------------------------------------------------------------ 280 281 SvStream& operator<<( SvStream& rOut, const SgaObject& rObj ) 282 { 283 rObj.WriteData( rOut, String() ); 284 return rOut; 285 } 286 287 // ------------------------------------------------------------------------ 288 289 SvStream& operator>>( SvStream& rIn, SgaObject& rObj ) 290 { 291 sal_uInt16 nReadVersion; 292 293 rObj.ReadData( rIn, nReadVersion ); 294 rObj.bIsValid = ( rIn.GetError() == ERRCODE_NONE ); 295 296 return rIn; 297 } 298 299 // ---------------- 300 // - SgaObjectBmp - 301 // ---------------- 302 303 SgaObjectBmp::SgaObjectBmp() 304 { 305 } 306 307 // ------------------------------------------------------------------------ 308 309 SgaObjectBmp::SgaObjectBmp( const INetURLObject& rURL ) 310 { 311 Graphic aGraphic; 312 String aFilter; 313 314 if ( SGA_IMPORT_NONE != GalleryGraphicImport( rURL, aGraphic, aFilter ) ) 315 Init( aGraphic, rURL ); 316 } 317 318 // ------------------------------------------------------------------------ 319 320 SgaObjectBmp::SgaObjectBmp( const Graphic& rGraphic, const INetURLObject& rURL, const String& ) 321 { 322 if( FileExists( rURL ) ) 323 Init( rGraphic, rURL ); 324 } 325 326 // ------------------------------------------------------------------------ 327 328 void SgaObjectBmp::Init( const Graphic& rGraphic, const INetURLObject& rURL ) 329 { 330 aURL = rURL; 331 bIsValid = CreateThumb( rGraphic ); 332 } 333 334 // ------------------------------------------------------------------------ 335 336 void SgaObjectBmp::WriteData( SvStream& rOut, const String& rDestDir ) const 337 { 338 String aDummyStr; 339 char aDummy[ 10 ]; 340 341 // Version setzen 342 SgaObject::WriteData( rOut, rDestDir ); 343 rOut.Write( aDummy, 10 ); 344 rOut << ByteString( aDummyStr, RTL_TEXTENCODING_UTF8 ) << ByteString( aTitle, RTL_TEXTENCODING_UTF8 ); 345 } 346 347 // ------------------------------------------------------------------------ 348 349 void SgaObjectBmp::ReadData( SvStream& rIn, sal_uInt16& rReadVersion ) 350 { 351 ByteString aTmpStr; 352 353 SgaObject::ReadData( rIn, rReadVersion ); 354 rIn.SeekRel( 10 ); // 16, 16, 32, 16 355 rIn >> aTmpStr; // dummy 356 357 if( rReadVersion >= 5 ) 358 { 359 rIn >> aTmpStr; aTitle = String( aTmpStr.GetBuffer(), RTL_TEXTENCODING_UTF8 ); 360 } 361 } 362 363 // ------------------ 364 // - SgaObjectSound - 365 // ------------------ 366 DBG_NAME(SgaObjectSound) 367 368 SgaObjectSound::SgaObjectSound() : 369 eSoundType( SOUND_STANDARD ) 370 { 371 DBG_CTOR(SgaObjectSound,NULL); 372 373 } 374 375 // ------------------------------------------------------------------------ 376 377 SgaObjectSound::SgaObjectSound( const INetURLObject& rURL ) : 378 eSoundType( SOUND_STANDARD ) 379 { 380 DBG_CTOR(SgaObjectSound,NULL); 381 382 if( FileExists( rURL ) ) 383 { 384 aURL = rURL; 385 aThumbBmp = Bitmap( Size( 1, 1 ), 1 ); 386 bIsValid = sal_True; 387 } 388 else 389 bIsValid = sal_False; 390 } 391 392 // ------------------------------------------------------------------------ 393 394 SgaObjectSound::~SgaObjectSound() 395 { 396 397 DBG_DTOR(SgaObjectSound,NULL); 398 } 399 400 // ------------------------------------------------------------------------ 401 402 BitmapEx SgaObjectSound::GetThumbBmp() const 403 { 404 sal_uInt16 nId; 405 406 switch( eSoundType ) 407 { 408 case( SOUND_COMPUTER ): nId = RID_SVXBMP_GALLERY_SOUND_1; break; 409 case( SOUND_MISC ): nId = RID_SVXBMP_GALLERY_SOUND_2; break; 410 case( SOUND_MUSIC ): nId = RID_SVXBMP_GALLERY_SOUND_3; break; 411 case( SOUND_NATURE ): nId = RID_SVXBMP_GALLERY_SOUND_4; break; 412 case( SOUND_SPEECH ): nId = RID_SVXBMP_GALLERY_SOUND_5; break; 413 case( SOUND_TECHNIC ): nId = RID_SVXBMP_GALLERY_SOUND_6; break; 414 case( SOUND_ANIMAL ): nId = RID_SVXBMP_GALLERY_SOUND_7; break; 415 416 // standard 417 default: 418 nId = RID_SVXBMP_GALLERY_MEDIA; 419 break; 420 } 421 422 const BitmapEx aBmpEx( GAL_RESID( nId ) ); 423 424 return aBmpEx; 425 } 426 427 // ------------------------------------------------------------------------ 428 429 void SgaObjectSound::WriteData( SvStream& rOut, const String& rDestDir ) const 430 { 431 SgaObject::WriteData( rOut, rDestDir ); 432 rOut << (sal_uInt16) eSoundType << ByteString( aTitle, RTL_TEXTENCODING_UTF8 ); 433 } 434 435 // ------------------------------------------------------------------------ 436 437 void SgaObjectSound::ReadData( SvStream& rIn, sal_uInt16& rReadVersion ) 438 { 439 SgaObject::ReadData( rIn, rReadVersion ); 440 441 if( rReadVersion >= 5 ) 442 { 443 ByteString aTmpStr; 444 sal_uInt16 nTmp16; 445 446 rIn >> nTmp16; eSoundType = (GalSoundType) nTmp16; 447 448 if( rReadVersion >= 6 ) 449 { 450 rIn >> aTmpStr; aTitle = String( aTmpStr.GetBuffer(), RTL_TEXTENCODING_UTF8 ); 451 } 452 } 453 } 454 455 // ----------------- 456 // - SgaObjectAnim - 457 // ----------------- 458 459 SgaObjectAnim::SgaObjectAnim() 460 { 461 } 462 463 // ------------------------------------------------------------------------ 464 465 SgaObjectAnim::SgaObjectAnim( const Graphic& rGraphic, 466 const INetURLObject& rURL, 467 const String& ) 468 { 469 aURL = rURL; 470 bIsValid = CreateThumb( rGraphic ); 471 } 472 473 // ----------------- 474 // - SgaObjectINet - 475 // ----------------- 476 477 SgaObjectINet::SgaObjectINet() 478 { 479 } 480 481 // ------------------------------------------------------------------------ 482 483 SgaObjectINet::SgaObjectINet( const Graphic& rGraphic, const INetURLObject& rURL, const String& rFormatName ) : 484 SgaObjectAnim ( rGraphic, rURL, rFormatName ) 485 { 486 } 487 488 // ------------------- 489 // - SgaObjectSvDraw - 490 // ------------------- 491 492 SgaObjectSvDraw::SgaObjectSvDraw() 493 { 494 } 495 496 // ------------------------------------------------------------------------ 497 498 SgaObjectSvDraw::SgaObjectSvDraw( const FmFormModel& rModel, const INetURLObject& rURL ) 499 { 500 aURL = rURL; 501 bIsValid = CreateThumb( rModel ); 502 } 503 504 // ------------------------------------------------------------------------ 505 DBG_NAME(SvxGalleryDrawModel) 506 507 SvxGalleryDrawModel::SvxGalleryDrawModel() 508 : mpFormModel( 0 ) 509 { 510 DBG_CTOR(SvxGalleryDrawModel,NULL); 511 512 const String sFactoryURL(RTL_CONSTASCII_USTRINGPARAM("sdraw")); 513 514 mxDoc = SfxObjectShell::CreateObjectByFactoryName( sFactoryURL ); 515 516 if( mxDoc.Is() ) 517 { 518 mxDoc->DoInitNew(0); 519 520 uno::Reference< lang::XUnoTunnel > xTunnel( mxDoc->GetModel(), uno::UNO_QUERY ); 521 if( xTunnel.is() ) 522 { 523 mpFormModel = dynamic_cast< FmFormModel* >( 524 reinterpret_cast<SdrModel*>(xTunnel->getSomething(SdrModel::getUnoTunnelImplementationId()))); 525 if( mpFormModel ) 526 { 527 mpFormModel->InsertPage( mpFormModel->AllocPage( false ) ); 528 } 529 } 530 } 531 } 532 533 // ------------------------------------------------------------------------ 534 535 SvxGalleryDrawModel::~SvxGalleryDrawModel() 536 { 537 if( mxDoc.Is() ) 538 mxDoc->DoClose(); 539 540 DBG_DTOR(SvxGalleryDrawModel,NULL); 541 } 542 543 // ------------------------------------------------------------------------ 544 545 SgaObjectSvDraw::SgaObjectSvDraw( SvStream& rIStm, const INetURLObject& rURL ) 546 { 547 SvxGalleryDrawModel aModel; 548 549 if( aModel.GetModel() ) 550 { 551 if( GallerySvDrawImport( rIStm, *aModel.GetModel() ) ) 552 { 553 aURL = rURL; 554 bIsValid = CreateThumb( *aModel.GetModel() ); 555 } 556 } 557 } 558 559 // ------------------------------------------------------------------------ 560 561 sal_Bool SgaObjectSvDraw::CreateThumb( const FmFormModel& rModel ) 562 { 563 Graphic aGraphic; 564 ImageMap aImageMap; 565 sal_Bool bRet = sal_False; 566 567 if ( CreateIMapGraphic( rModel, aGraphic, aImageMap ) ) 568 { 569 bRet = SgaObject::CreateThumb( aGraphic ); 570 } 571 else 572 { 573 const FmFormPage* pPage = static_cast< const FmFormPage* >(rModel.GetPage(0)); 574 575 if(pPage) 576 { 577 const Rectangle aObjRect(pPage->GetAllObjBoundRect()); 578 579 if(aObjRect.GetWidth() && aObjRect.GetHeight()) 580 { 581 VirtualDevice aVDev; 582 FmFormView aView(const_cast< FmFormModel* >(&rModel), &aVDev); 583 584 aView.ShowSdrPage(const_cast< FmFormPage* >(pPage)); 585 aView.MarkAllObj(); 586 aThumbBmp = aView.GetMarkedObjBitmapEx(); 587 588 const Size aDiscreteSize(aThumbBmp.GetSizePixel()); 589 590 if(aDiscreteSize.Width() && aDiscreteSize.Height()) 591 { 592 sal_uInt32 nTargetSizeX(S_THUMB); 593 sal_uInt32 nTargetSizeY(S_THUMB); 594 595 if(aDiscreteSize.Width() > aDiscreteSize.Height()) 596 { 597 nTargetSizeY = (aDiscreteSize.Height() * nTargetSizeX) / aDiscreteSize.Width(); 598 } 599 else 600 { 601 nTargetSizeX = (aDiscreteSize.Width() * nTargetSizeY) / aDiscreteSize.Height(); 602 } 603 604 if(!!aThumbBmp) 605 { 606 aThumbBmp.Scale(Size(nTargetSizeX, nTargetSizeY), BMP_SCALE_BESTQUALITY); 607 aThumbBmp.Convert(BMP_CONVERSION_8BIT_COLORS); 608 bRet = true; 609 } 610 } 611 } 612 } 613 } 614 615 return bRet; 616 } 617 618 // ------------------------------------------------------------------------ 619 620 void SgaObjectSvDraw::WriteData( SvStream& rOut, const String& rDestDir ) const 621 { 622 SgaObject::WriteData( rOut, rDestDir ); 623 rOut << ByteString( aTitle, RTL_TEXTENCODING_UTF8 ); 624 } 625 626 // ------------------------------------------------------------------------ 627 628 void SgaObjectSvDraw::ReadData( SvStream& rIn, sal_uInt16& rReadVersion ) 629 { 630 SgaObject::ReadData( rIn, rReadVersion ); 631 632 if( rReadVersion >= 5 ) 633 { 634 ByteString aTmpStr; 635 rIn >> aTmpStr; aTitle = String( aTmpStr.GetBuffer(), RTL_TEXTENCODING_UTF8 ); 636 } 637 } 638 639 // eof 640