1 /************************************************************************ 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 #include "mediawindow_impl.hxx" 29 #include "mediaevent_impl.hxx" 30 #include "mediamisc.hxx" 31 #include "mediawindow.hrc" 32 #include "helpids.hrc" 33 34 #include <algorithm> 35 #include <cmath> 36 #include <osl/mutex.hxx> 37 #include <tools/time.hxx> 38 #include <vcl/svapp.hxx> 39 40 #ifndef _COM_SUN_STAR_AWT_SYSTEMPOINTER_HDL_ 41 #include <com/sun/star/awt/SystemPointer.hdl> 42 #endif 43 #ifndef _COM_SUN_STAR_LANG_XCOMPONENT_HDL_ 44 #include <com/sun/star/lang/XComponent.hdl> 45 #endif 46 47 #define AVMEDIA_TOOLBOXITEM_PREV 0x0001 48 #define AVMEDIA_TOOLBOXITEM_PLAY 0x0002 49 #define AVMEDIA_TOOLBOXITEM_PAUSE 0x0004 50 #define AVMEDIA_TOOLBOXITEM_STOP 0x0008 51 #define AVMEDIA_TOOLBOXITEM_NEXT 0x0010 52 #define AVMEDIA_TOOLBOXITEM_MUTE 0x0100 53 54 #define AVMEDIA_FFW_PLAYRATE 4 55 56 using namespace ::com::sun::star; 57 58 namespace avmedia { namespace priv { 59 60 // ---------------------- 61 // - MediaWindowControl - 62 // ---------------------- 63 64 MediaWindowControl::MediaWindowControl( Window* pParent ) : 65 MediaControl( pParent, MEDIACONTROLSTYLE_MULTILINE ) 66 { 67 } 68 69 // --------------------------------------------------------------------- 70 71 MediaWindowControl::~MediaWindowControl() 72 { 73 } 74 75 // --------------------------------------------------------------------- 76 77 void MediaWindowControl::update() 78 { 79 MediaItem aItem; 80 81 static_cast< MediaWindowImpl* >( GetParent() )->updateMediaItem( aItem ); 82 setState( aItem ); 83 } 84 85 // --------------------------------------------------------------------- 86 87 void MediaWindowControl::execute( const MediaItem& rItem ) 88 { 89 static_cast< MediaWindowImpl* >( GetParent() )->executeMediaItem( rItem ); 90 } 91 92 // -------------------- 93 // - MediaChildWindow - 94 // -------------------- 95 96 MediaChildWindow::MediaChildWindow( Window* pParent ) : 97 SystemChildWindow( pParent, WB_CLIPCHILDREN ) 98 { 99 } 100 101 // --------------------------------------------------------------------- 102 103 MediaChildWindow::~MediaChildWindow() 104 { 105 } 106 107 // --------------------------------------------------------------------- 108 109 void MediaChildWindow::MouseMove( const MouseEvent& rMEvt ) 110 { 111 const MouseEvent aTransformedEvent( GetParent()->ScreenToOutputPixel( OutputToScreenPixel( rMEvt.GetPosPixel() ) ), 112 rMEvt.GetClicks(), rMEvt.GetMode(), rMEvt.GetButtons(), rMEvt.GetModifier() ); 113 114 SystemChildWindow::MouseMove( rMEvt ); 115 GetParent()->MouseMove( aTransformedEvent ); 116 } 117 118 // --------------------------------------------------------------------- 119 120 void MediaChildWindow::MouseButtonDown( const MouseEvent& rMEvt ) 121 { 122 const MouseEvent aTransformedEvent( GetParent()->ScreenToOutputPixel( OutputToScreenPixel( rMEvt.GetPosPixel() ) ), 123 rMEvt.GetClicks(), rMEvt.GetMode(), rMEvt.GetButtons(), rMEvt.GetModifier() ); 124 125 SystemChildWindow::MouseButtonDown( rMEvt ); 126 GetParent()->MouseButtonDown( aTransformedEvent ); 127 } 128 129 // --------------------------------------------------------------------- 130 131 void MediaChildWindow::MouseButtonUp( const MouseEvent& rMEvt ) 132 { 133 const MouseEvent aTransformedEvent( GetParent()->ScreenToOutputPixel( OutputToScreenPixel( rMEvt.GetPosPixel() ) ), 134 rMEvt.GetClicks(), rMEvt.GetMode(), rMEvt.GetButtons(), rMEvt.GetModifier() ); 135 136 SystemChildWindow::MouseButtonUp( rMEvt ); 137 GetParent()->MouseButtonUp( aTransformedEvent ); 138 } 139 140 // --------------------------------------------------------------------- 141 142 void MediaChildWindow::KeyInput( const KeyEvent& rKEvt ) 143 { 144 SystemChildWindow::KeyInput( rKEvt ); 145 GetParent()->KeyInput( rKEvt ); 146 } 147 148 // --------------------------------------------------------------------- 149 150 void MediaChildWindow::KeyUp( const KeyEvent& rKEvt ) 151 { 152 SystemChildWindow::KeyUp( rKEvt ); 153 GetParent()->KeyUp( rKEvt ); 154 } 155 156 // --------------------------------------------------------------------- 157 158 void MediaChildWindow::Command( const CommandEvent& rCEvt ) 159 { 160 const CommandEvent aTransformedEvent( GetParent()->ScreenToOutputPixel( OutputToScreenPixel( rCEvt.GetMousePosPixel() ) ), 161 rCEvt.GetCommand(), rCEvt.IsMouseEvent(), rCEvt.GetData() ); 162 163 SystemChildWindow::Command( rCEvt ); 164 GetParent()->Command( aTransformedEvent ); 165 } 166 167 // ---------------------- 168 // - MediaWindowImpl - 169 // ---------------------- 170 171 MediaWindowImpl::MediaWindowImpl( Window* pParent, MediaWindow* pMediaWindow, bool bInternalMediaControl ) : 172 Control( pParent ), 173 MediaWindowBaseImpl( pMediaWindow ), 174 DropTargetHelper( this ), 175 DragSourceHelper( this ), 176 mxEventsIf( static_cast< ::cppu::OWeakObject* >( mpEvents = new MediaEventListenersImpl( maChildWindow ) ) ), 177 maChildWindow( this ), 178 mpMediaWindowControl( bInternalMediaControl ? new MediaWindowControl( this ) : NULL ), 179 mpEmptyBmpEx( NULL ), 180 mpAudioBmpEx( NULL ) 181 { 182 maChildWindow.SetBackground( Color( COL_BLACK ) ); 183 maChildWindow.SetHelpId( HID_AVMEDIA_PLAYERWINDOW ); 184 maChildWindow.Hide(); 185 186 if( mpMediaWindowControl ) 187 { 188 mpMediaWindowControl->SetSizePixel( mpMediaWindowControl->getMinSizePixel() ); 189 mpMediaWindowControl->Show(); 190 } 191 } 192 193 // --------------------------------------------------------------------- 194 195 MediaWindowImpl::~MediaWindowImpl() 196 { 197 delete mpEmptyBmpEx; 198 delete mpAudioBmpEx; 199 delete mpMediaWindowControl; 200 } 201 202 // --------------------------------------------------------------------- 203 204 void MediaWindowImpl::cleanUp() 205 { 206 uno::Reference< media::XPlayerWindow > xPlayerWindow( getPlayerWindow() ); 207 208 mpEvents->cleanUp(); 209 210 if( xPlayerWindow.is() ) 211 { 212 xPlayerWindow->removeKeyListener( uno::Reference< awt::XKeyListener >( mxEventsIf, uno::UNO_QUERY ) ); 213 xPlayerWindow->removeMouseListener( uno::Reference< awt::XMouseListener >( mxEventsIf, uno::UNO_QUERY ) ); 214 xPlayerWindow->removeMouseMotionListener( uno::Reference< awt::XMouseMotionListener >( mxEventsIf, uno::UNO_QUERY ) ); 215 216 uno::Reference< lang::XComponent > xComponent( xPlayerWindow, uno::UNO_QUERY ); 217 218 if( xComponent.is() ) 219 xComponent->dispose(); 220 221 setPlayerWindow( NULL ); 222 } 223 224 MediaWindowBaseImpl::cleanUp(); 225 } 226 227 // --------------------------------------------------------------------- 228 229 void MediaWindowImpl::onURLChanged() 230 { 231 if( getPlayer().is() ) 232 { 233 uno::Reference< media::XPlayerWindow > xPlayerWindow; 234 235 const Point aPoint; 236 const Size aSize( maChildWindow.GetSizePixel() ); 237 const sal_IntPtr nWndHandle = (sal_IntPtr) maChildWindow.GetParentWindowHandle( isMediaWindowJavaBased() ); 238 239 try 240 { 241 if( nWndHandle != 0 ) 242 { 243 uno::Sequence< uno::Any > aArgs( 3 ); 244 245 aArgs[ 0 ] = uno::makeAny( nWndHandle ); 246 aArgs[ 1 ] = uno::makeAny( awt::Rectangle( aPoint.X(), aPoint.Y(), aSize.Width(), aSize.Height() ) ); 247 aArgs[ 2 ] = uno::makeAny( reinterpret_cast< sal_IntPtr >( &maChildWindow ) ); 248 249 xPlayerWindow = getPlayer()->createPlayerWindow( aArgs ); 250 } 251 } 252 catch( uno::RuntimeException ) 253 { 254 // happens eg, on MacOSX where Java frames cannot be created from X11 window handles 255 } 256 257 setPlayerWindow( xPlayerWindow ); 258 259 if( xPlayerWindow.is() ) 260 { 261 xPlayerWindow->addKeyListener( uno::Reference< awt::XKeyListener >( mxEventsIf, uno::UNO_QUERY ) ); 262 xPlayerWindow->addMouseListener( uno::Reference< awt::XMouseListener >( mxEventsIf, uno::UNO_QUERY ) ); 263 xPlayerWindow->addMouseMotionListener( uno::Reference< awt::XMouseMotionListener >( mxEventsIf, uno::UNO_QUERY ) ); 264 xPlayerWindow->addFocusListener( uno::Reference< awt::XFocusListener >( mxEventsIf, uno::UNO_QUERY ) ); 265 } 266 } 267 else 268 setPlayerWindow( NULL ); 269 270 if( getPlayerWindow().is() ) 271 maChildWindow.Show(); 272 else 273 maChildWindow.Hide(); 274 275 if( mpMediaWindowControl ) 276 { 277 MediaItem aItem; 278 279 updateMediaItem( aItem ); 280 mpMediaWindowControl->setState( aItem ); 281 } 282 } 283 284 // --------------------------------------------------------------------- 285 286 void MediaWindowImpl::update() 287 { 288 uno::Reference< media::XPlayerWindow > xPlayerWindow( getPlayerWindow() ); 289 290 if( xPlayerWindow.is() ) 291 xPlayerWindow->update(); 292 } 293 294 // --------------------------------------------------------------------- 295 296 void MediaWindowImpl::setPosSize( const Rectangle& rRect ) 297 { 298 SetPosSizePixel( rRect.TopLeft(), rRect.GetSize() ); 299 } 300 301 // --------------------------------------------------------------------- 302 303 void MediaWindowImpl::setPointer( const Pointer& rPointer ) 304 { 305 uno::Reference< media::XPlayerWindow > xPlayerWindow( getPlayerWindow() ); 306 307 SetPointer( rPointer ); 308 maChildWindow.SetPointer( rPointer ); 309 310 if( xPlayerWindow.is() ) 311 { 312 long nPointer; 313 314 switch( rPointer.GetStyle() ) 315 { 316 case( POINTER_CROSS ): nPointer = awt::SystemPointer::CROSS; break; 317 case( POINTER_HAND ): nPointer = awt::SystemPointer::HAND; break; 318 case( POINTER_MOVE ): nPointer = awt::SystemPointer::MOVE; break; 319 case( POINTER_WAIT ): nPointer = awt::SystemPointer::WAIT; break; 320 321 default: nPointer = awt::SystemPointer::ARROW; break; 322 } 323 324 xPlayerWindow->setPointerType( nPointer ); 325 } 326 } 327 328 // --------------------------------------------------------------------- 329 330 const Pointer& MediaWindowImpl::getPointer() const 331 { 332 return GetPointer(); 333 } 334 335 // --------------------------------------------------------------------- 336 337 bool MediaWindowImpl::hasInternalMediaControl() const 338 { 339 return( mpMediaWindowControl != NULL ); 340 } 341 342 // --------------------------------------------------------------------- 343 344 void MediaWindowImpl::Resize() 345 { 346 uno::Reference< media::XPlayerWindow > xPlayerWindow( getPlayerWindow() ); 347 const Size aCurSize( GetOutputSizePixel() ); 348 const sal_Int32 nOffset( mpMediaWindowControl ? AVMEDIA_CONTROLOFFSET : 0 ); 349 Size aPlayerWindowSize( aCurSize.Width() - ( nOffset << 1 ), 350 aCurSize.Height() - ( nOffset << 1 ) ); 351 352 if( mpMediaWindowControl ) 353 { 354 const sal_Int32 nControlHeight = mpMediaWindowControl->GetSizePixel().Height(); 355 const sal_Int32 nControlY = ::std::max( aCurSize.Height() - nControlHeight - nOffset, 0L ); 356 357 aPlayerWindowSize.Height() = ( nControlY - ( nOffset << 1 ) ); 358 mpMediaWindowControl->SetPosSizePixel( Point( nOffset, nControlY ), Size( aCurSize.Width() - ( nOffset << 1 ), nControlHeight ) ); 359 } 360 361 if( xPlayerWindow.is() ) 362 xPlayerWindow->setPosSize( 0, 0, aPlayerWindowSize.Width(), aPlayerWindowSize.Height(), 0 ); 363 364 maChildWindow.SetPosSizePixel( Point( nOffset, nOffset ), aPlayerWindowSize ); 365 } 366 367 // --------------------------------------------------------------------- 368 369 void MediaWindowImpl::StateChanged( StateChangedType eType ) 370 { 371 uno::Reference< media::XPlayerWindow > xPlayerWindow( getPlayerWindow() ); 372 373 if( xPlayerWindow.is() ) 374 { 375 // stop playing when going disabled or hidden 376 switch( eType ) 377 { 378 case STATE_CHANGE_VISIBLE: 379 { 380 stopPlayingInternal( !IsVisible() ); 381 xPlayerWindow->setVisible( IsVisible() ); 382 } 383 break; 384 385 case STATE_CHANGE_ENABLE: 386 { 387 stopPlayingInternal( !IsEnabled() ); 388 xPlayerWindow->setEnable( IsEnabled() ); 389 } 390 break; 391 392 default: 393 break; 394 } 395 } 396 } 397 398 // --------------------------------------------------------------------- 399 400 void MediaWindowImpl::Paint( const Rectangle& ) 401 { 402 BitmapEx* pLogo = NULL; 403 404 if( !getPlayer().is() ) 405 { 406 if( !mpEmptyBmpEx ) 407 mpEmptyBmpEx = new BitmapEx( AVMEDIA_RESID( AVMEDIA_BMP_EMPTYLOGO ) ); 408 409 pLogo = mpEmptyBmpEx; 410 } 411 else if( !getPlayerWindow().is() ) 412 { 413 if( !mpAudioBmpEx ) 414 mpAudioBmpEx = new BitmapEx( AVMEDIA_RESID( AVMEDIA_BMP_AUDIOLOGO ) ); 415 416 pLogo = mpAudioBmpEx; 417 } 418 419 const Point aBasePos( maChildWindow.GetPosPixel() ); 420 const Rectangle aVideoRect( aBasePos, maChildWindow.GetSizePixel() ); 421 422 if( pLogo && !pLogo->IsEmpty() && ( aVideoRect.GetWidth() > 0 ) && ( aVideoRect.GetHeight() > 0 ) ) 423 { 424 Size aLogoSize( pLogo->GetSizePixel() ); 425 const Color aBackgroundColor( 67, 67, 67 ); 426 427 SetLineColor( aBackgroundColor ); 428 SetFillColor( aBackgroundColor ); 429 DrawRect( aVideoRect ); 430 431 if( ( aLogoSize.Width() > aVideoRect.GetWidth() || aLogoSize.Height() > aVideoRect.GetHeight() ) && 432 ( aLogoSize.Height() > 0 ) ) 433 { 434 const double fLogoWH = (double) aLogoSize.Width() / aLogoSize.Height(); 435 436 if( fLogoWH < ( (double) aVideoRect.GetWidth() / aVideoRect.GetHeight() ) ) 437 { 438 aLogoSize.Width() = (long) ( aVideoRect.GetHeight() * fLogoWH ); 439 aLogoSize.Height()= aVideoRect.GetHeight(); 440 } 441 else 442 { 443 aLogoSize.Width() = aVideoRect.GetWidth(); 444 aLogoSize.Height()= (long) ( aVideoRect.GetWidth() / fLogoWH ); 445 } 446 } 447 448 DrawBitmapEx( Point( aBasePos.X() + ( ( aVideoRect.GetWidth() - aLogoSize.Width() ) >> 1 ), 449 aBasePos.Y() + ( ( aVideoRect.GetHeight() - aLogoSize.Height() ) >> 1 ) ), 450 aLogoSize, *pLogo ); 451 } 452 } 453 454 // --------------------------------------------------------------------- 455 456 void MediaWindowImpl::GetFocus() 457 { 458 } 459 460 // --------------------------------------------------------------------- 461 462 void MediaWindowImpl::MouseMove( const MouseEvent& rMEvt ) 463 { 464 MediaWindow* pMediaWindow = getMediaWindow(); 465 466 if( pMediaWindow ) 467 pMediaWindow->MouseMove( rMEvt ); 468 } 469 470 // --------------------------------------------------------------------- 471 472 void MediaWindowImpl::MouseButtonDown( const MouseEvent& rMEvt ) 473 { 474 MediaWindow* pMediaWindow = getMediaWindow(); 475 476 if( pMediaWindow ) 477 pMediaWindow->MouseButtonDown( rMEvt ); 478 } 479 480 // --------------------------------------------------------------------- 481 482 void MediaWindowImpl::MouseButtonUp( const MouseEvent& rMEvt ) 483 { 484 MediaWindow* pMediaWindow = getMediaWindow(); 485 486 if( pMediaWindow ) 487 pMediaWindow->MouseButtonUp( rMEvt ); 488 } 489 490 // --------------------------------------------------------------------- 491 492 void MediaWindowImpl::KeyInput( const KeyEvent& rKEvt ) 493 { 494 MediaWindow* pMediaWindow = getMediaWindow(); 495 496 if( pMediaWindow ) 497 pMediaWindow->KeyInput( rKEvt ); 498 } 499 500 // --------------------------------------------------------------------- 501 502 void MediaWindowImpl::KeyUp( const KeyEvent& rKEvt ) 503 { 504 MediaWindow* pMediaWindow = getMediaWindow(); 505 506 if( pMediaWindow ) 507 pMediaWindow->KeyUp( rKEvt ); 508 } 509 510 // --------------------------------------------------------------------- 511 512 void MediaWindowImpl::Command( const CommandEvent& rCEvt ) 513 { 514 MediaWindow* pMediaWindow = getMediaWindow(); 515 516 if( pMediaWindow ) 517 pMediaWindow->Command( rCEvt ); 518 } 519 520 // --------------------------------------------------------------------- 521 522 sal_Int8 MediaWindowImpl::AcceptDrop( const AcceptDropEvent& rEvt ) 523 { 524 MediaWindow* pMediaWindow = getMediaWindow(); 525 return( pMediaWindow ? pMediaWindow->AcceptDrop( rEvt ) : 0 ); 526 } 527 528 // --------------------------------------------------------------------- 529 530 sal_Int8 MediaWindowImpl::ExecuteDrop( const ExecuteDropEvent& rEvt ) 531 { 532 MediaWindow* pMediaWindow = getMediaWindow(); 533 return( pMediaWindow ? pMediaWindow->ExecuteDrop( rEvt ) : 0 ); 534 } 535 536 // --------------------------------------------------------------------- 537 538 void MediaWindowImpl::StartDrag( sal_Int8 nAction, const Point& rPosPixel ) 539 { 540 MediaWindow* pMediaWindow = getMediaWindow(); 541 542 if( pMediaWindow ) 543 pMediaWindow->StartDrag( nAction, rPosPixel ); 544 } 545 546 } // namespace priv 547 } // namespace avmedia 548