Main Page | Modules | Class Hierarchy | Class List | Directories | File List | Class Members | File Members | Related Pages

win32_loop.cpp

00001 /*****************************************************************************
00002  * win32_loop.cpp
00003  *****************************************************************************
00004  * Copyright (C) 2003 the VideoLAN team
00005  * $Id: win32_loop.cpp 11664 2005-07-09 06:17:09Z courmisch $
00006  *
00007  * Authors: Cyril Deguet     <[email protected]>
00008  *          Olivier Teulière <[email protected]>
00009  *
00010  * This program is free software; you can redistribute it and/or modify
00011  * it under the terms of the GNU General Public License as published by
00012  * the Free Software Foundation; either version 2 of the License, or
00013  * (at your option) any later version.
00014  *
00015  * This program is distributed in the hope that it will be useful,
00016  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00017  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00018  * GNU General Public License for more details.
00019  *
00020  * You should have received a copy of the GNU General Public License
00021  * along with this program; if not, write to the Free Software
00022  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111, USA.
00023  *****************************************************************************/
00024 
00025 #ifdef WIN32_SKINS
00026 
00027 #include "win32_factory.hpp"
00028 #include "win32_loop.hpp"
00029 #include "../src/generic_window.hpp"
00030 #include "../events/evt_key.hpp"
00031 #include "../events/evt_leave.hpp"
00032 #include "../events/evt_motion.hpp"
00033 #include "../events/evt_mouse.hpp"
00034 #include "../events/evt_refresh.hpp"
00035 #include "../events/evt_scroll.hpp"
00036 #include "vlc_keys.h"
00037 
00038 
00039 // XXX: Cygwin (at least) doesn't define these macros. Too bad...
00040 #ifndef GET_X_LPARAM
00041     #define GET_X_LPARAM(a) ((int16_t)(a))
00042     #define GET_Y_LPARAM(a) ((int16_t)((a)>>16))
00043 #endif
00044 
00045 
00046 Win32Loop::Win32Loop( intf_thread_t *pIntf ): OSLoop( pIntf )
00047 {
00048     // Initialize the map
00049     virtKeyToVlcKey[VK_F1] = KEY_F1;
00050     virtKeyToVlcKey[VK_F2] = KEY_F2;
00051     virtKeyToVlcKey[VK_F3] = KEY_F3;
00052     virtKeyToVlcKey[VK_F4] = KEY_F4;
00053     virtKeyToVlcKey[VK_F5] = KEY_F5;
00054     virtKeyToVlcKey[VK_F6] = KEY_F6;
00055     virtKeyToVlcKey[VK_F7] = KEY_F7;
00056     virtKeyToVlcKey[VK_F8] = KEY_F8;
00057     virtKeyToVlcKey[VK_F9] = KEY_F9;
00058     virtKeyToVlcKey[VK_F10] = KEY_F10;
00059     virtKeyToVlcKey[VK_F11] = KEY_F11;
00060     virtKeyToVlcKey[VK_F12] = KEY_F12;
00061     virtKeyToVlcKey[VK_RETURN] = KEY_ENTER;
00062     virtKeyToVlcKey[VK_SPACE] = KEY_SPACE;
00063     virtKeyToVlcKey[VK_ESCAPE] = KEY_ESC;
00064     virtKeyToVlcKey[VK_LEFT] = KEY_LEFT;
00065     virtKeyToVlcKey[VK_RIGHT] = KEY_RIGHT;
00066     virtKeyToVlcKey[VK_UP] = KEY_UP;
00067     virtKeyToVlcKey[VK_DOWN] = KEY_DOWN;
00068     virtKeyToVlcKey[VK_HOME] = KEY_HOME;
00069     virtKeyToVlcKey[VK_END] = KEY_END;
00070     virtKeyToVlcKey[VK_PRIOR] = KEY_PAGEUP;
00071     virtKeyToVlcKey[VK_NEXT] = KEY_PAGEDOWN;
00072 }
00073 
00074 
00075 Win32Loop::~Win32Loop()
00076 {
00077 }
00078 
00079 
00080 OSLoop *Win32Loop::instance( intf_thread_t *pIntf )
00081 {
00082     if( pIntf->p_sys->p_osLoop == NULL )
00083     {
00084         OSLoop *pOsLoop = new Win32Loop( pIntf );
00085         pIntf->p_sys->p_osLoop = pOsLoop;
00086     }
00087     return pIntf->p_sys->p_osLoop;
00088 }
00089 
00090 
00091 void Win32Loop::destroy( intf_thread_t *pIntf )
00092 {
00093     if( pIntf->p_sys->p_osLoop )
00094     {
00095         delete pIntf->p_sys->p_osLoop;
00096         pIntf->p_sys->p_osLoop = NULL;
00097     }
00098 }
00099 
00100 
00101 void Win32Loop::run()
00102 {
00103     MSG msg;
00104 
00105     // Compute windows message list
00106     while( GetMessage( &msg, NULL, 0, 0 ) )
00107     {
00108         Win32Factory *pFactory =
00109             (Win32Factory*)Win32Factory::instance( getIntf() );
00110         GenericWindow *pWin = pFactory->m_windowMap[msg.hwnd];
00111         if( pWin == NULL )
00112         {
00113             // We are probably getting a message for a tooltip (which has no
00114             // associated GenericWindow), for a timer, or for the parent window
00115             DispatchMessage( &msg );
00116             continue;
00117         }
00118 
00119         GenericWindow &win = *pWin;
00120         switch( msg.message )
00121         {
00122             case WM_PAINT:
00123             {
00124                 PAINTSTRUCT Infos;
00125                 BeginPaint( msg.hwnd, &Infos );
00126                 EvtRefresh evt( getIntf(),
00127                                 Infos.rcPaint.left,
00128                                 Infos.rcPaint.top,
00129                                 Infos.rcPaint.right - Infos.rcPaint.left + 1,
00130                                 Infos.rcPaint.bottom - Infos.rcPaint.top + 1 );
00131                 EndPaint( msg.hwnd, &Infos );
00132                 win.processEvent( evt );
00133                 break;
00134             }
00135             case WM_MOUSEMOVE:
00136             {
00137                 // Needed to generate WM_MOUSELEAVE events
00138                 TRACKMOUSEEVENT TrackEvent;
00139                 TrackEvent.cbSize      = sizeof( TRACKMOUSEEVENT );
00140                 TrackEvent.dwFlags     = TME_LEAVE;
00141                 TrackEvent.hwndTrack   = msg.hwnd;
00142                 TrackEvent.dwHoverTime = 1;
00143                 TrackMouseEvent( &TrackEvent );
00144 
00145                 // Compute the absolute position of the mouse
00146                 int x = GET_X_LPARAM( msg.lParam ) + win.getLeft();
00147                 int y = GET_Y_LPARAM( msg.lParam ) + win.getTop();
00148                 EvtMotion evt( getIntf(), x, y );
00149                 win.processEvent( evt );
00150                 break;
00151             }
00152             case WM_MOUSELEAVE:
00153             {
00154                 EvtLeave evt( getIntf() );
00155                 win.processEvent( evt );
00156                 break;
00157             }
00158             case WM_MOUSEWHEEL:
00159             {
00160                 int x = GET_X_LPARAM( msg.lParam ) - win.getLeft();
00161                 int y = GET_Y_LPARAM( msg.lParam ) - win.getTop();
00162                 int mod = getMod( msg.wParam );
00163                 if( GET_WHEEL_DELTA_WPARAM( msg.wParam ) > 0 )
00164                 {
00165                     EvtScroll evt( getIntf(), x, y, EvtScroll::kUp, mod );
00166                     win.processEvent( evt );
00167                 }
00168                 else
00169                 {
00170                     EvtScroll evt( getIntf(), x, y, EvtScroll::kDown, mod );
00171                     win.processEvent( evt );
00172                 }
00173                 break;
00174             }
00175             case WM_LBUTTONDOWN:
00176             {
00177                 SetCapture( msg.hwnd );
00178                 EvtMouse evt( getIntf(), GET_X_LPARAM( msg.lParam ),
00179                               GET_Y_LPARAM( msg.lParam ), EvtMouse::kLeft,
00180                               EvtMouse::kDown, getMod( msg.wParam ) );
00181                 win.processEvent( evt );
00182                 break;
00183             }
00184             case WM_RBUTTONDOWN:
00185             {
00186                 SetCapture( msg.hwnd );
00187                 EvtMouse evt( getIntf(), GET_X_LPARAM( msg.lParam ),
00188                               GET_Y_LPARAM( msg.lParam ), EvtMouse::kRight,
00189                               EvtMouse::kDown, getMod( msg.wParam ) );
00190                 win.processEvent( evt );
00191                 break;
00192             }
00193             case WM_LBUTTONUP:
00194             {
00195                 ReleaseCapture();
00196                 EvtMouse evt( getIntf(), GET_X_LPARAM( msg.lParam ),
00197                               GET_Y_LPARAM( msg.lParam ), EvtMouse::kLeft,
00198                               EvtMouse::kUp, getMod( msg.wParam ) );
00199                 win.processEvent( evt );
00200                 break;
00201             }
00202             case WM_RBUTTONUP:
00203             {
00204                 ReleaseCapture();
00205                 EvtMouse evt( getIntf(), GET_X_LPARAM( msg.lParam ),
00206                               GET_Y_LPARAM( msg.lParam ), EvtMouse::kRight,
00207                               EvtMouse::kUp, getMod( msg.wParam ) );
00208                 win.processEvent( evt );
00209                 break;
00210             }
00211             case WM_LBUTTONDBLCLK:
00212             {
00213                 ReleaseCapture();
00214                 EvtMouse evt( getIntf(), GET_X_LPARAM( msg.lParam ),
00215                               GET_Y_LPARAM( msg.lParam ), EvtMouse::kLeft,
00216                               EvtMouse::kDblClick, getMod( msg.wParam ) );
00217                 win.processEvent( evt );
00218                 break;
00219             }
00220             case WM_RBUTTONDBLCLK:
00221             {
00222                 ReleaseCapture();
00223                 EvtMouse evt( getIntf(), GET_X_LPARAM( msg.lParam ),
00224                               GET_Y_LPARAM( msg.lParam ), EvtMouse::kRight,
00225                               EvtMouse::kDblClick, getMod( msg.wParam ) );
00226                 win.processEvent( evt );
00227                 break;
00228             }
00229             case WM_KEYDOWN:
00230             case WM_SYSKEYDOWN:
00231             case WM_KEYUP:
00232             case WM_SYSKEYUP:
00233             {
00234                 // The key events are first processed here and not translated
00235                 // into WM_CHAR events because we need to know the status of
00236                 // the modifier keys.
00237 
00238                 // Get VLC key code from the virtual key code
00239                 int key = virtKeyToVlcKey[msg.wParam];
00240                 if( !key )
00241                 {
00242                     // This appears to be a "normal" (ascii) key
00243                     key = tolower( MapVirtualKey( msg.wParam, 2 ) );
00244                 }
00245 
00246                 if( key )
00247                 {
00248                     // Get the modifier
00249                     int mod = 0;
00250                     if( GetKeyState( VK_CONTROL ) & 0x8000 )
00251                     {
00252                         mod |= EvtInput::kModCtrl;
00253                     }
00254                     if( GetKeyState( VK_SHIFT ) & 0x8000 )
00255                     {
00256                         mod |= EvtInput::kModShift;
00257                     }
00258                     if( GetKeyState( VK_MENU ) & 0x8000 )
00259                     {
00260                         mod |= EvtInput::kModAlt;
00261                     }
00262 
00263                     // Get the state
00264                     EvtKey::ActionType_t state;
00265                     if( msg.message == WM_KEYDOWN ||
00266                         msg.message == WM_SYSKEYDOWN )
00267                     {
00268                         state = EvtKey::kDown;
00269                     }
00270                     else
00271                     {
00272                         state = EvtKey::kUp;
00273                     }
00274 
00275                     EvtKey evt( getIntf(), key, state, mod );
00276                     win.processEvent( evt );
00277                 }
00278                 break;
00279             }
00280             default:
00281                 TranslateMessage( &msg );
00282                 DispatchMessage( &msg );
00283         }
00284     }
00285 }
00286 
00287 
00288 int Win32Loop::getMod( WPARAM wParam ) const
00289 {
00290     int mod = EvtInput::kModNone;
00291     if( wParam & MK_CONTROL )
00292         mod |= EvtInput::kModCtrl;
00293     if( wParam & MK_SHIFT )
00294         mod |= EvtInput::kModShift;
00295 
00296     return mod;
00297 }
00298 
00299 
00300 void Win32Loop::exit()
00301 {
00302     PostQuitMessage(0);
00303 }
00304 
00305 #endif

Generated on Tue Dec 20 10:14:44 2005 for vlc-0.8.4a by  doxygen 1.4.2