⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 directx.c

📁 VLC媒体播放程序
💻 C
📖 第 1 页 / 共 5 页
字号:
        case VLC_FOURCC('U','Y','V','Y'):        case VLC_FOURCC('U','Y','N','V'):        case VLC_FOURCC('Y','4','2','2'):            p_vout->output.i_chroma = VLC_FOURCC('U','Y','V','Y');            break;        case VLC_FOURCC('Y','V','Y','U'):            p_vout->output.i_chroma = VLC_FOURCC('Y','V','Y','U');            break;        default:            p_vout->output.i_chroma = VLC_FOURCC('Y','V','1','2');            break;    }    NewPictureVec( p_vout, p_vout->p_picture, MAX_DIRECTBUFFERS );    i_chroma_backup = p_vout->output.i_chroma;    if( !I_OUTPUTPICTURES )    {        /* hmmm, it didn't work! Let's try commonly supported chromas */        if( p_vout->output.i_chroma != VLC_FOURCC('Y','V','1','2') )        {            p_vout->output.i_chroma = VLC_FOURCC('Y','V','1','2');            NewPictureVec( p_vout, p_vout->p_picture, MAX_DIRECTBUFFERS );        }        if( !I_OUTPUTPICTURES )        {            /* hmmm, it still didn't work! Let's try another one */            p_vout->output.i_chroma = VLC_FOURCC('Y','U','Y','2');            NewPictureVec( p_vout, p_vout->p_picture, MAX_DIRECTBUFFERS );        }    }    if( !I_OUTPUTPICTURES )    {        /* If it still didn't work then don't try to use an overlay */        p_vout->output.i_chroma = i_chroma_backup;        p_vout->p_sys->b_using_overlay = 0;        NewPictureVec( p_vout, p_vout->p_picture, MAX_DIRECTBUFFERS );    }    /* 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 );    return VLC_SUCCESS;}/***************************************************************************** * End: terminate Sys video thread output method ***************************************************************************** * Terminate an output method created by Create. * It is called at the end of the thread. *****************************************************************************/static void End( vout_thread_t *p_vout ){    FreePictureVec( p_vout, p_vout->p_picture, I_OUTPUTPICTURES );    DirectXCloseDisplay( p_vout );    DirectXCloseDDraw( p_vout );    return;}/***************************************************************************** * CloseVideo: destroy Sys video thread output method ***************************************************************************** * Terminate an output method created by Create *****************************************************************************/static void CloseVideo( vlc_object_t *p_this ){    vout_thread_t * p_vout = (vout_thread_t *)p_this;    msg_Dbg( p_vout, "CloseVideo" );    var_Destroy( p_vout, "video-on-top" );    if( p_vout->p_sys->p_event )    {        vlc_object_detach( p_vout->p_sys->p_event );        /* Kill DirectXEventThread */        p_vout->p_sys->p_event->b_die = VLC_TRUE;        /* we need to be sure DirectXEventThread won't stay stuck in         * GetMessage, so we send a fake message */        if( p_vout->p_sys->hwnd )        {            PostMessage( p_vout->p_sys->hwnd, WM_NULL, 0, 0);        }        vlc_thread_join( p_vout->p_sys->p_event );        vlc_object_destroy( p_vout->p_sys->p_event );    }    if( p_vout->p_sys )    {        free( p_vout->p_sys );        p_vout->p_sys = NULL;    }}/***************************************************************************** * Manage: handle Sys events ***************************************************************************** * This function should be called regularly by the video output thread. * It returns a non null value if an error occured. *****************************************************************************/static int Manage( vout_thread_t *p_vout ){    WINDOWPLACEMENT window_placement;    /* If we do not control our window, we check for geometry changes     * ourselves because the parent might not send us its events. */    if( p_vout->p_sys->hparent )    {        DirectXUpdateRects( p_vout, VLC_FALSE );    }    /*     * Position Change     */    if( 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 !=                p_vout->p_sys->MonitorFromWindow( p_vout->p_sys->hwnd,                                                  MONITOR_DEFAULTTONEAREST ) )        {            /* This will force the vout core to recreate the picture buffers */            p_vout->i_changes |= VOUT_PICTURE_BUFFERS_CHANGE;        }        p_vout->p_sys->i_changes &= ~DX_POSITION_CHANGE;    }    /* We used to call the Win32 PeekMessage function here to read the window     * messages. But since window can stay blocked into this function for a     * long time (for example when you move your window on the screen), I     * decided to isolate PeekMessage in another thread. */    /*     * Fullscreen change     */    if( p_vout->i_changes & VOUT_FULLSCREEN_CHANGE        || p_vout->p_sys->i_changes & VOUT_FULLSCREEN_CHANGE )    {        vlc_value_t val;        p_vout->b_fullscreen = ! p_vout->b_fullscreen;        /* We need to switch between Maximized and Normal sized window */        window_placement.length = sizeof(WINDOWPLACEMENT);        GetWindowPlacement( p_vout->p_sys->hwnd, &window_placement );        if( p_vout->b_fullscreen )        {            /* 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 );        }        else        {            /* 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 );        }        SetWindowPlacement( p_vout->p_sys->hwnd, &window_placement );        /* Update the object variable and trigger callback */        val.b_bool = p_vout->b_fullscreen;        var_Set( p_vout, "fullscreen", val );        p_vout->i_changes &= ~VOUT_FULLSCREEN_CHANGE;        p_vout->p_sys->i_changes &= ~VOUT_FULLSCREEN_CHANGE;    }    /*     * Pointer change     */    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 )        {            p_vout->p_sys->b_cursor_hidden = VLC_TRUE;            PostMessage( p_vout->p_sys->hwnd, WM_VLC_HIDE_MOUSE, 0, 0 );        }    }    /*     * "Always on top" status change     */    if( p_vout->p_sys->b_on_top_change )    {        vlc_value_t val;        HMENU hMenu = GetSystemMenu( p_vout->p_sys->hwnd, FALSE );        var_Get( p_vout, "video-on-top", &val );        /* Set the window on top if necessary */        if( val.b_bool && !( GetWindowLong( p_vout->p_sys->hwnd, GWL_EXSTYLE )                           & WS_EX_TOPMOST ) )        {            CheckMenuItem( hMenu, IDM_TOGGLE_ON_TOP,                           MF_BYCOMMAND | MFS_CHECKED );            SetWindowPos( p_vout->p_sys->hwnd, HWND_TOPMOST, 0, 0, 0, 0,                          SWP_NOSIZE | SWP_NOMOVE );        }        else        /* The window shouldn't be on top */        if( !val.b_bool && ( GetWindowLong( p_vout->p_sys->hwnd, GWL_EXSTYLE )                           & WS_EX_TOPMOST ) )        {            CheckMenuItem( hMenu, IDM_TOGGLE_ON_TOP,                           MF_BYCOMMAND | MFS_UNCHECKED );            SetWindowPos( p_vout->p_sys->hwnd, HWND_NOTOPMOST, 0, 0, 0, 0,                          SWP_NOSIZE | SWP_NOMOVE );        }        p_vout->p_sys->b_on_top_change = VLC_FALSE;    }    /* Check if the event thread is still running */    if( p_vout->p_sys->p_event->b_die )    {        return VLC_EGENERIC; /* exit */    }    return VLC_SUCCESS;}/***************************************************************************** * Display: displays previously rendered output ***************************************************************************** * This function sends the currently rendered image to the display, wait until * it is displayed and switch the two rendering buffers, preparing next frame. *****************************************************************************/static void Display( vout_thread_t *p_vout, picture_t *p_pic ){    HRESULT dxresult;    if( (p_vout->p_sys->p_display == NULL) )    {        msg_Warn( p_vout, "no display!" );        return;    }    /* Our surface can be lost so be sure to check this     * and restore it if need be */    if( IDirectDrawSurface2_IsLost( p_vout->p_sys->p_display )        == DDERR_SURFACELOST )    {        if( IDirectDrawSurface2_Restore( p_vout->p_sys->p_display ) == DD_OK &&            p_vout->p_sys->b_using_overlay )            DirectXUpdateOverlay( p_vout );    }    if( !p_vout->p_sys->b_using_overlay )    {        DDBLTFX  ddbltfx;        /* We ask for the "NOTEARING" option */        memset( &ddbltfx, 0, sizeof(DDBLTFX) );        ddbltfx.dwSize = sizeof(DDBLTFX);        ddbltfx.dwDDFX = DDBLTFX_NOTEARING;        /* Blit video surface to display */        dxresult = IDirectDrawSurface2_Blt( p_vout->p_sys->p_display,                                            &p_vout->p_sys->rect_dest_clipped,                                            p_pic->p_sys->p_surface,                                            &p_vout->p_sys->rect_src_clipped,                                            DDBLT_ASYNC, &ddbltfx );        if( dxresult != DD_OK )        {            msg_Warn( p_vout, "could not blit surface (error %li)", dxresult );            return;        }    }    else /* using overlay */    {        /* Flip the overlay buffers if we are using back buffers */        if( p_pic->p_sys->p_front_surface == p_pic->p_sys->p_surface )        {            return;        }        dxresult = IDirectDrawSurface2_Flip( p_pic->p_sys->p_front_surface,                                             NULL, DDFLIP_WAIT );        if( dxresult != DD_OK )        {            msg_Warn( p_vout, "could not flip overlay (error %li)", dxresult );        }        /* set currently displayed pic */        p_vout->p_sys->p_current_surface = p_pic->p_sys->p_front_surface;        /* Lock surface to get all the required info */        if( DirectXLockSurface( p_vout, p_pic ) )        {            /* AAARRGG */            msg_Warn( p_vout, "cannot lock surface" );            return;        }        DirectXUnlockSurface( p_vout, p_pic );    }}/* following functions are local *//***************************************************************************** * DirectXEnumCallback: Device enumeration ***************************************************************************** * This callback function is called by DirectDraw once for each * available DirectDraw device. *****************************************************************************/BOOL WINAPI DirectXEnumCallback( GUID* p_guid, LPTSTR psz_desc,                                 LPTSTR psz_drivername, VOID* p_context,                                 HMONITOR hmon ){    vout_thread_t *p_vout = (vout_thread_t *)p_context;    vlc_value_t device;    msg_Dbg( p_vout, "DirectXEnumCallback: %s, %s", psz_desc, psz_drivername );

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -