]> git.sesse.net Git - vlc/commitdiff
* modules/video_output/directx/*:
authorGildas Bazin <gbazin@videolan.org>
Thu, 22 Apr 2004 12:57:56 +0000 (12:57 +0000)
committerGildas Bazin <gbazin@videolan.org>
Thu, 22 Apr 2004 12:57:56 +0000 (12:57 +0000)
  - Major changes to way the embedded vout is handled.
    + the vout windows are created in our event thread so we do receive the events now.
    + we do not use the external window directly (as for normal vout we create our vout window + video sub-window).
    + Create a WS_EX_NOPARENTNOTIFY vout window to make mozilla happy.
  - Improved the mouse auto-hide feature.
  - Do the DirectXUpdateOverlay() in the events thread. This should make S3 graphics cards happy again.

modules/video_output/directx/directx.c
modules/video_output/directx/events.c
modules/video_output/directx/vout.h

index 6a55f95c299f75a163d08b6f8f0961313a4af6dd..5c249b8490fef0c3ef309059c841c0cb63e00ded 100644 (file)
@@ -160,7 +160,7 @@ vlc_module_end();
 static int OpenVideo( vlc_object_t *p_this )
 {
     vout_thread_t * p_vout = (vout_thread_t *)p_this;
-    vlc_value_t val, text;
+    vlc_value_t val;
     HMODULE huser32;
 
     /* Allocate structure */
@@ -186,7 +186,9 @@ static int OpenVideo( vlc_object_t *p_this )
     p_vout->p_sys->hwnd = p_vout->p_sys->hvideownd = NULL;
     p_vout->p_sys->hparent = NULL;
     p_vout->p_sys->i_changes = 0;
-    SetRectEmpty( &p_vout->p_sys->rect_display  );
+    vlc_mutex_init( p_vout, &p_vout->p_sys->lock );
+    SetRectEmpty( &p_vout->p_sys->rect_display );
+    SetRectEmpty( &p_vout->p_sys->rect_parent );
 
     /* Multimonitor stuff */
     p_vout->p_sys->hmonitor = NULL;
@@ -371,8 +373,7 @@ static int Init( vout_thread_t *p_vout )
     }
 
     /* Change the window title bar text */
-    if( p_vout->p_sys->hparent ) ; /* Do nothing */
-    else PostMessage( p_vout->p_sys->hwnd, WM_VLC_CHANGE_TEXT, 0, 0 );
+    PostMessage( p_vout->p_sys->hwnd, WM_VLC_CHANGE_TEXT, 0, 0 );
 
     return VLC_SUCCESS;
 }
@@ -422,6 +423,8 @@ static void CloseVideo( vlc_object_t *p_this )
         vlc_object_destroy( p_vout->p_sys->p_event );
     }
 
+    vlc_mutex_destroy( &p_vout->p_sys->lock );
+
     if( p_vout->p_sys )
     {
         free( p_vout->p_sys );
@@ -441,9 +444,37 @@ static int Manage( vout_thread_t *p_vout )
 
     /* If we do not control our window, we check for geometry changes
      * ourselves because the parent might not send us its events. */
+    vlc_mutex_lock( &p_vout->p_sys->lock );
     if( p_vout->p_sys->hparent )
     {
-        DirectXUpdateRects( p_vout, VLC_FALSE );
+        RECT rect_parent;
+        POINT point;
+
+        vlc_mutex_unlock( &p_vout->p_sys->lock );
+
+        GetClientRect( p_vout->p_sys->hparent, &rect_parent );
+        point.x = point.y = 0;
+        ClientToScreen( p_vout->p_sys->hparent, &point );
+        OffsetRect( &rect_parent, point.x, point.y );
+
+        if( !EqualRect( &rect_parent, &p_vout->p_sys->rect_parent ) )
+        {
+            p_vout->p_sys->rect_parent = rect_parent;
+
+            /* This one is to force the update even if only
+            * the position has changed */
+            SetWindowPos( p_vout->p_sys->hwnd, 0, 1, 1,
+                          rect_parent.right - rect_parent.left,
+                          rect_parent.bottom - rect_parent.top, 0 );
+
+            SetWindowPos( p_vout->p_sys->hwnd, 0, 0, 0,
+                          rect_parent.right - rect_parent.left,
+                          rect_parent.bottom - rect_parent.top, 0 );
+        }
+    }
+    else
+    {
+        vlc_mutex_unlock( &p_vout->p_sys->lock );
     }
 
     /*
@@ -453,9 +484,6 @@ static int Manage( vout_thread_t *p_vout )
     {
         p_vout->p_sys->i_changes &= ~DX_POSITION_CHANGE;
 
-        if( p_vout->p_sys->b_using_overlay )
-            DirectXUpdateOverlay( p_vout );
-
         /* Check if we are still on the same monitor */
         if( p_vout->p_sys->MonitorFromWindow &&
             p_vout->p_sys->hmonitor !=
@@ -478,6 +506,7 @@ static int Manage( vout_thread_t *p_vout )
     if( p_vout->i_changes & VOUT_FULLSCREEN_CHANGE
         || p_vout->p_sys->i_changes & VOUT_FULLSCREEN_CHANGE )
     {
+        int i_style = 0;
         vlc_value_t val;
 
         p_vout->b_fullscreen = ! p_vout->b_fullscreen;
@@ -487,21 +516,33 @@ static int Manage( vout_thread_t *p_vout )
         GetWindowPlacement( p_vout->p_sys->hwnd, &window_placement );
         if( p_vout->b_fullscreen )
         {
+           if( p_vout->p_sys->hparent )
+               SetParent( p_vout->p_sys->hwnd, GetDesktopWindow() );
+
             /* Maximized window */
             window_placement.showCmd = SW_SHOWMAXIMIZED;
             /* Change window style, no borders and no title bar */
-            SetWindowLong( p_vout->p_sys->hwnd, GWL_STYLE, WS_CLIPCHILDREN );
-
+            i_style = WS_CLIPCHILDREN;
         }
         else
         {
+            if( p_vout->p_sys->hparent )
+            {
+                SetParent( p_vout->p_sys->hwnd, p_vout->p_sys->hparent );
+                i_style = WS_CLIPCHILDREN | WS_VISIBLE | WS_CHILD;
+            }
+            else
+            {
+                i_style = WS_CLIPCHILDREN | WS_OVERLAPPEDWINDOW |
+                          WS_SIZEBOX | WS_VISIBLE;
+            }
+
             /* Normal window */
             window_placement.showCmd = SW_SHOWNORMAL;
-            /* Change window style, borders and title bar */
-            SetWindowLong( p_vout->p_sys->hwnd, GWL_STYLE, WS_CLIPCHILDREN |
-                           WS_OVERLAPPEDWINDOW | WS_SIZEBOX | WS_VISIBLE );
         }
 
+        /* Change window style, borders and title bar */
+        SetWindowLong( p_vout->p_sys->hwnd, GWL_STYLE, i_style );
         SetWindowPlacement( p_vout->p_sys->hwnd, &window_placement );
 
         /* Update the object variable and trigger callback */
@@ -518,12 +559,24 @@ static int Manage( vout_thread_t *p_vout )
     if( (!p_vout->p_sys->b_cursor_hidden) &&
         ( (mdate() - p_vout->p_sys->i_lastmoved) > 5000000 ) )
     {
-        /* Hide the mouse automatically */
-        if( p_vout->p_sys->hwnd != p_vout->p_sys->hparent )
+        POINT point;
+        RECT rect;
+
+        /* Hide the cursor only if it is inside our window */
+        GetClientRect( p_vout->p_sys->hwnd, &rect );
+        point.x = point.y = 0;
+        ClientToScreen( p_vout->p_sys->hwnd, &point );
+        OffsetRect( &rect, point.x, point.y );
+        GetCursorPos( &point );
+        if( PtInRect( &rect, point ) )
         {
             p_vout->p_sys->b_cursor_hidden = VLC_TRUE;
             PostMessage( p_vout->p_sys->hwnd, WM_VLC_HIDE_MOUSE, 0, 0 );
         }
+        else
+        {
+            p_vout->p_sys->i_lastmoved = mdate();
+        }
     }
 
     /*
@@ -1084,9 +1137,14 @@ int DirectXUpdateOverlay( vout_thread_t *p_vout )
     RECT            rect_src = p_vout->p_sys->rect_src_clipped;
     RECT            rect_dest = p_vout->p_sys->rect_dest_clipped;
 
-    if( p_vout->p_sys->p_current_surface == NULL ||
-        !p_vout->p_sys->b_using_overlay )
+    if( !p_vout->p_sys->b_using_overlay ) return VLC_EGENERIC;
+
+    vlc_mutex_lock( &p_vout->p_sys->lock );
+    if( p_vout->p_sys->p_current_surface == NULL )
+    {
+        vlc_mutex_unlock( &p_vout->p_sys->lock );
         return VLC_EGENERIC;
+    }
 
     /* The new window dimensions should already have been computed by the
      * caller of this function */
@@ -1103,6 +1161,9 @@ int DirectXUpdateOverlay( vout_thread_t *p_vout )
                    p_vout->p_sys->p_current_surface,
                    &rect_src, p_vout->p_sys->p_display, &rect_dest,
                    dwFlags, &ddofx );
+
+    vlc_mutex_unlock( &p_vout->p_sys->lock );
+
     if(dxresult != DD_OK)
     {
         msg_Warn( p_vout, "DirectXUpdateOverlay cannot move/resize overlay" );
@@ -1435,6 +1496,10 @@ static void FreePictureVec( vout_thread_t *p_vout, picture_t *p_pic,
 {
     int i;
 
+    vlc_mutex_lock( &p_vout->p_sys->lock );
+    p_vout->p_sys->p_current_surface = 0;
+    vlc_mutex_unlock( &p_vout->p_sys->lock );
+
     for( i = 0; i < i_num_pics; i++ )
     {
         DirectXCloseSurface( p_vout, p_pic[i].p_sys->p_front_surface );
@@ -1444,8 +1509,6 @@ static void FreePictureVec( vout_thread_t *p_vout, picture_t *p_pic,
             free( p_pic[i].p_sys );
         }
     }
-
-    p_vout->p_sys->p_current_surface = 0;
 }
 
 /*****************************************************************************
index 0cfb5861b1213d463b1ab5e89b1fd04d91b3d5d4..81904a585fb4a9b91f1eff8cb93cdb9d05547da0 100644 (file)
@@ -81,7 +81,7 @@ static int DirectXConvertKey( int i_key );
 void DirectXEventThread( event_thread_t *p_event )
 {
     MSG msg;
-    POINT old_mouse_pos = {0,0};
+    POINT old_mouse_pos = {0,0}, mouse_pos;
     vlc_value_t val;
     int i_width, i_height, i_x, i_y;
     HMODULE hkernel32;
@@ -118,21 +118,13 @@ void DirectXEventThread( event_thread_t *p_event )
 
     /* Main loop */
     /* GetMessage will sleep if there's no message in the queue */
-    while( !p_event->b_die && ( p_event->p_vout->p_sys->hparent ||
-           GetMessage( &msg, p_event->p_vout->p_sys->hwnd, 0, 0 ) ) )
+    while( !p_event->b_die &&
+           GetMessage( &msg, p_event->p_vout->p_sys->hwnd, 0, 0 ) )
     {
         /* Check if we are asked to exit */
         if( p_event->b_die )
             break;
 
-        if( p_event->p_vout->p_sys->hparent )
-        {
-            /* Parent window was created in another thread so we can't
-             * access the window messages. */
-            msleep( INTF_IDLE_SLEEP );
-            continue;
-        }
-
         switch( msg.message )
         {
 
@@ -162,8 +154,9 @@ void DirectXEventThread( event_thread_t *p_event )
             }
 
         case WM_NCMOUSEMOVE:
-            if( (abs(GET_X_LPARAM(msg.lParam) - old_mouse_pos.x) > 2 ||
-                (abs(GET_Y_LPARAM(msg.lParam) - old_mouse_pos.y)) > 2 ) )
+            GetCursorPos( &mouse_pos );
+            if( (abs(mouse_pos.x - old_mouse_pos.x) > 2 ||
+                (abs(mouse_pos.y - old_mouse_pos.y)) > 2 ) )
             {
                 GetCursorPos( &old_mouse_pos );
                 p_event->p_vout->p_sys->i_lastmoved = mdate();
@@ -348,6 +341,10 @@ static int DirectXCreateWindow( vout_thread_t *p_vout )
     HINSTANCE  hInstance;
     HMENU      hMenu;
     RECT       rect_window;
+    WNDCLASSEX wc;                            /* window class components */
+    HICON      vlc_icon = NULL;
+    char       vlc_path[MAX_PATH+1];
+    int        i_style;
 
     msg_Dbg( p_vout, "DirectXCreateWindow" );
 
@@ -355,116 +352,99 @@ static int DirectXCreateWindow( vout_thread_t *p_vout )
     hInstance = GetModuleHandle(NULL);
 
     /* If an external window was specified, we'll draw in it. */
-    p_vout->p_sys->hparent = p_vout->p_sys->hwnd =
+    p_vout->p_sys->hparent =
         vout_RequestWindow( p_vout, &p_vout->p_sys->i_window_x,
                             &p_vout->p_sys->i_window_y,
                             &p_vout->p_sys->i_window_width,
                             &p_vout->p_sys->i_window_height );
 
-    if( p_vout->p_sys->hparent )
+    /* We create the window ourself, there is no previous window proc. */
+    p_vout->p_sys->pf_wndproc = NULL;
+
+    /* Get the Icon from the main app */
+    vlc_icon = NULL;
+    if( GetModuleFileName( NULL, vlc_path, MAX_PATH ) )
     {
-        msg_Dbg( p_vout, "using external window %p\n", p_vout->p_sys->hwnd );
-
-        /* Set stuff in the window that we can not put directly in
-         * a class (see below). */
-        SetClassLong( p_vout->p_sys->hwnd,
-                      GCL_STYLE, CS_DBLCLKS );
-        SetClassLong( p_vout->p_sys->hwnd,
-                      GCL_HBRBACKGROUND, (LONG)GetStockObject(BLACK_BRUSH) );
-        SetClassLong( p_vout->p_sys->hwnd,
-                      GCL_HCURSOR, (LONG)LoadCursor(NULL, IDC_ARROW) );
-        /* Store a p_vout pointer into the window local storage (for later
-         * use in DirectXEventProc). */
-        SetWindowLongPtr( p_vout->p_sys->hwnd, GWLP_USERDATA, (LONG_PTR)p_vout );
-
-        p_vout->p_sys->pf_wndproc =
-            (WNDPROC)SetWindowLong( p_vout->p_sys->hwnd, GWLP_WNDPROC,
-                                    (LONG_PTR)DirectXEventProc );
-
-        /* Blam! Erase everything that might have been there. */
-        InvalidateRect( p_vout->p_sys->hwnd, NULL, TRUE );
+        vlc_icon = ExtractIcon( hInstance, vlc_path, 0 );
     }
-    else
+
+    /* Fill in the window class structure */
+    wc.cbSize        = sizeof(WNDCLASSEX);
+    wc.style         = CS_DBLCLKS;                   /* style: dbl click */
+    wc.lpfnWndProc   = (WNDPROC)DirectXEventProc;       /* event handler */
+    wc.cbClsExtra    = 0;                         /* no extra class data */
+    wc.cbWndExtra    = 0;                        /* no extra window data */
+    wc.hInstance     = hInstance;                            /* instance */
+    wc.hIcon         = vlc_icon;                /* load the vlc big icon */
+    wc.hCursor       = LoadCursor(NULL, IDC_ARROW);    /* default cursor */
+    wc.hbrBackground = GetStockObject(BLACK_BRUSH);  /* background color */
+    wc.lpszMenuName  = NULL;                                  /* no menu */
+    wc.lpszClassName = "VLC DirectX";             /* use a special class */
+    wc.hIconSm       = vlc_icon;              /* load the vlc small icon */
+
+    /* Register the window class */
+    if( !RegisterClassEx(&wc) )
     {
-        WNDCLASSEX wc;                            /* window class components */
-        HICON      vlc_icon = NULL;
-        char       vlc_path[MAX_PATH+1];
+        WNDCLASS wndclass;
 
-        /* We create the window ourself, there is no previous window proc. */
-        p_vout->p_sys->pf_wndproc = NULL;
+        if( vlc_icon ) DestroyIcon( vlc_icon );
 
-        /* Get the Icon from the main app */
-        vlc_icon = NULL;
-        if( GetModuleFileName( NULL, vlc_path, MAX_PATH ) )
+        /* Check why it failed. If it's because one already exists
+         * then fine, otherwise return with an error. */
+        if( !GetClassInfo( hInstance, "VLC DirectX", &wndclass ) )
         {
-            vlc_icon = ExtractIcon( hInstance, vlc_path, 0 );
+            msg_Err( p_vout, "DirectXCreateWindow RegisterClass FAILED" );
+            return VLC_EGENERIC;
         }
+    }
 
-        /* Fill in the window class structure */
-        wc.cbSize        = sizeof(WNDCLASSEX);
-        wc.style         = CS_DBLCLKS;                   /* style: dbl click */
-        wc.lpfnWndProc   = (WNDPROC)DirectXEventProc;       /* event handler */
-        wc.cbClsExtra    = 0;                         /* no extra class data */
-        wc.cbWndExtra    = 0;                        /* no extra window data */
-        wc.hInstance     = hInstance;                            /* instance */
-        wc.hIcon         = vlc_icon;                /* load the vlc big icon */
-        wc.hCursor       = LoadCursor(NULL, IDC_ARROW);    /* default cursor */
-        wc.hbrBackground = GetStockObject(BLACK_BRUSH);  /* background color */
-        wc.lpszMenuName  = NULL;                                  /* no menu */
-        wc.lpszClassName = "VLC DirectX";             /* use a special class */
-        wc.hIconSm       = vlc_icon;              /* load the vlc small icon */
-
-        /* Register the window class */
-        if( !RegisterClassEx(&wc) )
-        {
-            WNDCLASS wndclass;
+    /* When you create a window you give the dimensions you wish it to
+     * have. Unfortunatly these dimensions will include the borders and
+     * titlebar. We use the following function to find out the size of
+     * the window corresponding to the useable surface we want */
+    rect_window.top    = 10;
+    rect_window.left   = 10;
+    rect_window.right  = rect_window.left + p_vout->p_sys->i_window_width;
+    rect_window.bottom = rect_window.top + p_vout->p_sys->i_window_height;
+    AdjustWindowRect( &rect_window, WS_OVERLAPPEDWINDOW|WS_SIZEBOX, 0 );
 
-            if( vlc_icon )
-            {
-                DestroyIcon( vlc_icon );
-            }
-
-            /* Check why it failed. If it's because one already exists
-             * then fine, otherwise return with an error. */
-            if( !GetClassInfo( hInstance, "VLC DirectX", &wndclass ) )
-            {
-                msg_Err( p_vout, "DirectXCreateWindow RegisterClass FAILED" );
-                return VLC_EGENERIC;
-            }
-        }
-
-        /* When you create a window you give the dimensions you wish it to
-         * have. Unfortunatly these dimensions will include the borders and
-         * titlebar. We use the following function to find out the size of
-         * the window corresponding to the useable surface we want */
-        rect_window.top    = 10;
-        rect_window.left   = 10;
-        rect_window.right  = rect_window.left + p_vout->p_sys->i_window_width;
-        rect_window.bottom = rect_window.top + p_vout->p_sys->i_window_height;
-        AdjustWindowRect( &rect_window, WS_OVERLAPPEDWINDOW|WS_SIZEBOX, 0 );
+    if( p_vout->p_sys->hparent )
+        i_style = WS_VISIBLE|WS_CLIPCHILDREN|WS_CHILD;
+    else
+        i_style = WS_OVERLAPPEDWINDOW|WS_SIZEBOX|WS_VISIBLE|WS_CLIPCHILDREN;
 
-        /* Create the window */
-        p_vout->p_sys->hwnd =
-            CreateWindow( "VLC DirectX",             /* name of window class */
+    /* Create the window */
+    p_vout->p_sys->hwnd =
+        CreateWindowEx( WS_EX_NOPARENTNOTIFY,
+                    "VLC DirectX",                   /* name of window class */
                     VOUT_TITLE " (DirectX Output)", /* window title bar text */
-                    WS_OVERLAPPEDWINDOW | WS_SIZEBOX | WS_VISIBLE |
-                    WS_CLIPCHILDREN,                         /* window style */
+                    i_style,                                 /* window style */
                     (p_vout->p_sys->i_window_x < 0) ? CW_USEDEFAULT :
                         p_vout->p_sys->i_window_x,   /* default X coordinate */
                     (p_vout->p_sys->i_window_y < 0) ? CW_USEDEFAULT :
                         p_vout->p_sys->i_window_y,   /* default Y coordinate */
                     rect_window.right - rect_window.left,    /* window width */
                     rect_window.bottom - rect_window.top,   /* window height */
-                    NULL,                                /* no parent window */
+                    p_vout->p_sys->hparent,                 /* parent window */
                     NULL,                          /* no menu in this window */
                     hInstance,            /* handle of this program instance */
                     (LPVOID)p_vout );            /* send p_vout to WM_CREATE */
 
-        if( !p_vout->p_sys->hwnd )
-        {
-            msg_Warn( p_vout, "DirectXCreateWindow create window FAILED" );
-            return VLC_EGENERIC;
-        }
+    if( !p_vout->p_sys->hwnd )
+    {
+        msg_Warn( p_vout, "DirectXCreateWindow create window FAILED" );
+        return VLC_EGENERIC;
+    }
+
+    if( p_vout->p_sys->hparent )
+    {
+        LONG i_style;
+
+        /* We don't want the window owner to overwrite our client area */
+        i_style = GetWindowLong( p_vout->p_sys->hparent, GWL_STYLE );
+        SetWindowLong( p_vout->p_sys->hparent, GWL_STYLE,
+                       i_style | WS_CLIPCHILDREN );
+
     }
 
     /* Now display the window */
@@ -493,25 +473,10 @@ static void DirectXCloseWindow( vout_thread_t *p_vout )
 {
     msg_Dbg( p_vout, "DirectXCloseWindow" );
 
-    if( p_vout->p_sys->hwnd && !p_vout->p_sys->hparent )
-    {
-        DestroyWindow( p_vout->p_sys->hwnd );
-    }
-    else if( p_vout->p_sys->hparent )
-    {
-        /* Get rid of the video sub-window */
-        PostMessage( p_vout->p_sys->hvideownd, WM_VLC_DESTROY_VIDEO_WIN, 0, 0);
-
-        /* We don't want our windowproc to be called anymore */
-        SetWindowLongPtr( p_vout->p_sys->hwnd,
-                          GWLP_WNDPROC, (LONG_PTR)p_vout->p_sys->pf_wndproc );
-        SetWindowLongPtr( p_vout->p_sys->hwnd, GWLP_USERDATA, 0 );
-
-        /* Blam! Erase everything that might have been there. */
-        InvalidateRect( p_vout->p_sys->hwnd, NULL, TRUE );
+    DestroyWindow( p_vout->p_sys->hwnd );
 
+    if( p_vout->p_sys->hparent )
         vout_ReleaseWindow( p_vout, (void *)p_vout->p_sys->hparent );
-    }
 
     p_vout->p_sys->hwnd = NULL;
 
@@ -662,6 +627,9 @@ void DirectXUpdateRects( vout_thread_t *p_vout, vlc_bool_t b_force )
     rect_dest_clipped.top -= p_vout->p_sys->rect_display.top;
     rect_dest_clipped.bottom -= p_vout->p_sys->rect_display.top;
 
+    if( p_vout->p_sys->b_using_overlay )
+        DirectXUpdateOverlay( p_vout );
+
     /* Signal the change in size/position */
     p_vout->p_sys->i_changes |= DX_POSITION_CHANGE;
 
@@ -799,31 +767,8 @@ static long FAR PASCAL DirectXEventProc( HWND hwnd, UINT message,
         break;
     }
 
-    if( p_vout->p_sys->pf_wndproc )
-    {
-        LRESULT i_ret;
-
-        /* Hmmm mozilla does manage somehow to save the pointer to our
-         * windowproc and will call us again whereby creating an
-         * infinite loop.
-         * We can detect this by resetting GWL_USERDATA before calling
-         * the parent's windowproc. */
-        SetWindowLongPtr( p_vout->p_sys->hwnd, GWLP_USERDATA, 0 );
-
-        /* Call next window proc in chain */
-        i_ret = CallWindowProc( p_vout->p_sys->pf_wndproc, hwnd, message,
-                                wParam, lParam );
-
-        SetWindowLongPtr( p_vout->p_sys->hwnd, GWLP_USERDATA,
-                          (LONG_PTR)p_vout );
-        return i_ret;
-    }
-    else
-    {
-        /* Let windows handle the message */
-        return DefWindowProc(hwnd, message, wParam, lParam);
-    }
-
+    /* Let windows handle the message */
+    return DefWindowProc(hwnd, message, wParam, lParam);
 }
 
 static long FAR PASCAL DirectXVideoEventProc( HWND hwnd, UINT message,
@@ -834,10 +779,6 @@ static long FAR PASCAL DirectXVideoEventProc( HWND hwnd, UINT message,
 
     switch( message )
     {
-    case WM_VLC_DESTROY_VIDEO_WIN:
-        /* Destroy video sub-window */
-        DestroyWindow( hwnd );
-        break;
     case WM_MOUSEMOVE:
     case WM_LBUTTONDOWN:
     case WM_LBUTTONUP:
@@ -961,6 +902,21 @@ static int Control( vout_thread_t *p_vout, int i_query, va_list args )
 
         return VLC_SUCCESS;
 
+    case VOUT_REPARENT:
+        /* Change window style, borders and title bar */
+        vlc_mutex_lock( &p_vout->p_sys->lock );
+        p_vout->p_sys->hparent = 0;
+        vlc_mutex_unlock( &p_vout->p_sys->lock );
+
+        SetParent( p_vout->p_sys->hwnd, GetDesktopWindow() );
+        SetWindowLong( p_vout->p_sys->hwnd, GWL_STYLE,
+                       WS_CLIPCHILDREN | WS_OVERLAPPEDWINDOW |
+                       WS_SIZEBOX | WS_VISIBLE );
+        SetWindowPos( p_vout->p_sys->hwnd, 0, 0, 0, 0, 0,
+                      SWP_NOMOVE|SWP_NOSIZE|SWP_NOZORDER|SWP_FRAMECHANGED );
+
+      return VLC_SUCCESS;
+
     case VOUT_CLOSE:
         return VLC_SUCCESS;
 
index 8a38a837b5e45f5a58737ccd58945b62b30e1c8a..3fbfec36104e6a4062a985ea37adab1bd422e3b6 100644 (file)
@@ -77,6 +77,7 @@ struct vout_sys_t
     RECT         rect_src_clipped;
     RECT         rect_dest;
     RECT         rect_dest_clipped;
+    RECT         rect_parent;
 
     /* Overlay alignment restrictions */
     int          i_align_src_boundary;
@@ -97,9 +98,10 @@ struct vout_sys_t
     volatile mtime_t    i_lastmoved;
 
     /* Misc */
-    vlc_bool_t          b_on_top_change;
+    vlc_bool_t      b_on_top_change;
 
-    event_thread_t *    p_event;
+    event_thread_t *p_event;
+    vlc_mutex_t    lock;
 };
 
 /*****************************************************************************