예제 #1
0
파일: events.c 프로젝트: chouquette/vlc
/*****************************************************************************
 * Win32VoutCloseWindow: close the window created by Win32VoutCreateWindow
 *****************************************************************************
 * This function returns all resources allocated by Win32VoutCreateWindow.
 *****************************************************************************/
static void Win32VoutCloseWindow( event_thread_t *p_event )
{
    vout_display_t *vd = p_event->vd;
    msg_Dbg( vd, "Win32VoutCloseWindow" );

    #if defined(MODULE_NAME_IS_direct3d9) || defined(MODULE_NAME_IS_direct3d11)
    DestroyWindow( p_event->hvideownd );
    #endif
    DestroyWindow( p_event->hwnd );
    if( p_event->hfswnd )
        DestroyWindow( p_event->hfswnd );

    #if defined(MODULE_NAME_IS_direct3d9) || defined(MODULE_NAME_IS_direct3d11)
    if( !p_event->use_desktop )
    #endif
        vout_display_DeleteWindow( vd, p_event->parent_window );
    p_event->hwnd = NULL;

    HINSTANCE hInstance = GetModuleHandle(NULL);
    UnregisterClass( p_event->class_video, hInstance );
    UnregisterClass( p_event->class_main, hInstance );

    if( p_event->vlc_icon )
        DestroyIcon( p_event->vlc_icon );

    DestroyCursor( p_event->cursor_empty );

    CloseGestures( p_event->p_gesture);
}
예제 #2
0
파일: aa.c 프로젝트: chouquette/vlc
/**
 * This function allocates and initializes a aa vout method.
 */
static int Open(vlc_object_t *object)
{
    vout_display_t *vd = (vout_display_t *)object;
    vout_display_sys_t *sys;

#ifndef _WIN32
    if (!vlc_xlib_init (object))
        return VLC_EGENERIC;
#endif

    /* Allocate structure */
    vd->sys = sys = calloc(1, sizeof(*sys));
    if (!sys)
        return VLC_ENOMEM;

    /* Don't parse any options, but take $AAOPTS into account */
    aa_parseoptions(NULL, NULL, NULL, NULL);

    /* */
    sys->aa_context = aa_autoinit(&aa_defparams);
    if (!sys->aa_context) {
        msg_Err(vd, "cannot initialize aalib");
        goto error;
    }
    vout_display_DeleteWindow(vd, NULL);

    aa_autoinitkbd(sys->aa_context, 0);
    aa_autoinitmouse(sys->aa_context, AA_MOUSEALLMASK);

    /* */
    video_format_t fmt = vd->fmt;
    fmt.i_chroma = VLC_CODEC_RGB8;
    fmt.i_width  = aa_imgwidth(sys->aa_context);
    fmt.i_height = aa_imgheight(sys->aa_context);
    fmt.i_visible_width = fmt.i_width;
    fmt.i_visible_height = fmt.i_height;

    /* Setup vout_display now that everything is fine */
    vd->fmt = fmt;
    vd->info.has_pictures_invalid = true;
    vd->info.needs_event_thread = true;

    vd->pool    = Pool;
    vd->prepare = Prepare;
    vd->display = PictureDisplay;
    vd->control = Control;
    vd->manage  = Manage;

    /* Inspect initial configuration and send correction events
     * FIXME how to handle aspect ratio with aa ? */
    vout_display_SendEventDisplaySize(vd, fmt.i_width, fmt.i_height);

    return VLC_SUCCESS;

error:
    if (sys && sys->aa_context)
        aa_close(sys->aa_context);
    free(sys);
    return VLC_EGENERIC;
}
예제 #3
0
파일: vdummy.c 프로젝트: qdk0901/vlc
/*****************************************************************************
 * OpenVideo: activates dummy vout display method
 *****************************************************************************/
static int Open(vlc_object_t *object,
                void (*display)(vout_display_t *, picture_t *, subpicture_t *))
{
    vout_display_t *vd = (vout_display_t *)object;
    vout_display_sys_t *sys;

    vd->sys = sys = calloc(1, sizeof(*sys));
    if (!sys)
        return VLC_EGENERIC;
    sys->pool = NULL;

    /* p_vd->info is not modified */

    char *chroma = var_InheritString(vd, "dummy-chroma");
    if (chroma) {
        vlc_fourcc_t fcc = vlc_fourcc_GetCodecFromString(VIDEO_ES, chroma);
        if (fcc != 0) {
            msg_Dbg(vd, "forcing chroma 0x%.8x (%4.4s)", fcc, (char*)&fcc);
            vd->fmt.i_chroma = fcc;
        }
        free(chroma);
    }
    vd->pool    = Pool;
    vd->prepare = NULL;
    vd->display = display;
    vd->control = Control;
    vd->manage  = NULL;

    vout_display_DeleteWindow(vd, NULL);

    return VLC_SUCCESS;
}
예제 #4
0
파일: gl.c 프로젝트: banketree/faplayer
/**
 * Destroys the OpenGL context.
 */
static void Close (vlc_object_t *obj)
{
    vout_display_t *vd = (vout_display_t *)obj;
    vout_display_sys_t *sys = vd->sys;

    vout_display_opengl_Clean (&sys->vgl);
    vlc_gl_Destroy (sys->gl);
    vout_display_DeleteWindow (vd, sys->window);
    free (sys);
}
예제 #5
0
파일: x11.c 프로젝트: Annovae/vlc
/**
 * Disconnect from the X server.
 */
static void Close (vlc_object_t *obj)
{
    vout_display_t *vd = (vout_display_t *)obj;
    vout_display_sys_t *sys = vd->sys;

    ResetPictures (vd);

    /* show the default cursor */
    xcb_change_window_attributes (sys->conn, sys->embed->handle.xid, XCB_CW_CURSOR,
                                  &(uint32_t) { XCB_CURSOR_NONE });
    xcb_flush (sys->conn);

    /* colormap, window and context are garbage-collected by X */
    xcb_disconnect (sys->conn);
    vout_display_DeleteWindow (vd, sys->embed);
    free (sys);
}
예제 #6
0
/**
 * Allocates a surface and an OpenGL context for video output.
 */
static int Open (vlc_object_t *obj)
{
    vout_display_t *vd = (vout_display_t *)obj;
    vout_display_sys_t *sys = malloc (sizeof (*sys));
    if (unlikely(sys == NULL))
        return VLC_ENOMEM;

    sys->gl = NULL;
    sys->pool = NULL;

    sys->window = MakeWindow (vd);
    if (sys->window == NULL)
        goto error;

    sys->gl = vlc_gl_Create (sys->window, API, "$" MODULE_VARNAME);
    if (sys->gl == NULL)
        goto error;

    if (vlc_gl_MakeCurrent (sys->gl))
        goto error;

    /* Initialize video display */
    sys->vgl = vout_display_opengl_New (&vd->fmt, NULL, sys->gl);
    if (!sys->vgl)
        goto error;

    vd->sys = sys;
    vd->info.has_pictures_invalid = false;
    vd->info.has_event_thread = false;
    vd->pool = Pool;
    vd->prepare = PictureRender;
    vd->display = PictureDisplay;
    vd->control = Control;
    vd->manage = NULL;
    return VLC_SUCCESS;

error:
    if (sys->gl != NULL)
        vlc_gl_Destroy (sys->gl);
    if (sys->window != NULL)
        vout_display_DeleteWindow (vd, sys->window);
    free (sys);
    return VLC_EGENERIC;
}
예제 #7
0
/*****************************************************************************
 * DirectXCloseWindow: close the window created by DirectXCreateWindow
 *****************************************************************************
 * This function returns all resources allocated by DirectXCreateWindow.
 *****************************************************************************/
static void DirectXCloseWindow( event_thread_t *p_event )
{
    vout_display_t *vd = p_event->vd;
    msg_Dbg( vd, "DirectXCloseWindow" );

    DestroyWindow( p_event->hwnd );
    if( p_event->hfswnd )
        DestroyWindow( p_event->hfswnd );

    #ifdef MODULE_NAME_IS_direct3d
    if( !p_event->use_desktop )
    #endif
        vout_display_DeleteWindow( vd, p_event->parent_window );
    p_event->hwnd = NULL;

    HINSTANCE hInstance = GetModuleHandle(NULL);
    UnregisterClass( p_event->class_video, hInstance );
    UnregisterClass( p_event->class_main, hInstance );

#ifndef UNDER_CE
    DestroyCursor( p_event->cursor_empty );
#endif
}
예제 #8
0
/**
 * This function allocates and initializes a FB vout method.
 */
static int Open(vlc_object_t *object)
{
    vout_display_t     *vd = (vout_display_t *)object;
    vout_display_sys_t *sys;

    /* Allocate instance and initialize some members */
    vd->sys = sys = calloc(1, sizeof(*sys));
    if (!sys)
        return VLC_ENOMEM;

    /* Does the framebuffer uses hw acceleration? */
    sys->is_hw_accel = var_InheritBool(vd, "fb-hw-accel");

    /* Set tty and fb devices */
    sys->tty = 0; /* 0 == /dev/tty0 == current console */
    sys->is_tty = var_InheritBool(vd, "fb-tty");
#if !defined(_WIN32) &&  defined(HAVE_ISATTY)
    /* Check that stdin is a TTY */
    if (sys->is_tty && !isatty(0)) {
        msg_Warn(vd, "standard input is not a TTY");
        free(sys);
        return VLC_EGENERIC;
    }
    msg_Warn(vd, "disabling TTY handling, use with caution because "
             "there is no way to return to the TTY");
#endif

    const int mode = var_InheritInteger(vd, "fb-mode");
    bool force_resolution = true;
    switch (mode) {
    case 0: /* QCIF */
        sys->width  = 176;
        sys->height = 144;
        break;
    case 1: /* CIF */
        sys->width  = 352;
        sys->height = 288;
        break;
    case 2: /* NTSC */
        sys->width  = 640;
        sys->height = 480;
        break;
    case 3: /* PAL */
        sys->width  = 704;
        sys->height = 576;
        break;
    case 4:
    default:
        force_resolution = false;
        break;
    }

    char *chroma = var_InheritString(vd, "fb-chroma");
    if (chroma) {
        sys->chroma = vlc_fourcc_GetCodecFromString(VIDEO_ES, chroma);

        if (sys->chroma)
            msg_Dbg(vd, "forcing chroma '%s'", chroma);
        else
            msg_Warn(vd, "chroma %s invalid, using default", chroma);

        free(chroma);
    } else
        sys->chroma = 0;

    /* tty handling */
    if (sys->is_tty && TtyInit(vd)) {
        free(sys);
        return VLC_EGENERIC;
    }

    /* */
    sys->video_ptr = MAP_FAILED;
    sys->picture = NULL;
    sys->pool = NULL;

    if (OpenDisplay(vd, force_resolution)) {
        Close(VLC_OBJECT(vd));
        return VLC_EGENERIC;
    }
    vout_display_DeleteWindow(vd, NULL);

    /* */
    video_format_t fmt = vd->fmt;

    if (sys->chroma) {
        fmt.i_chroma = sys->chroma;
    } else {
        /* Assume RGB */

        msg_Dbg(vd, "%d bppd", sys->var_info.bits_per_pixel);
        switch (sys->var_info.bits_per_pixel) {
        case 8: /* FIXME: set the palette */
            fmt.i_chroma = VLC_CODEC_RGB8;
            break;
        case 15:
            fmt.i_chroma = VLC_CODEC_RGB15;
            break;
        case 16:
            fmt.i_chroma = VLC_CODEC_RGB16;
            break;
        case 24:
            fmt.i_chroma = VLC_CODEC_RGB24;
            break;
        case 32:
            fmt.i_chroma = VLC_CODEC_RGB32;
            break;
        default:
            msg_Err(vd, "unknown screendepth %i", sys->var_info.bits_per_pixel);
            Close(VLC_OBJECT(vd));
            return VLC_EGENERIC;
        }
        if (sys->var_info.bits_per_pixel != 8) {
            fmt.i_rmask = ((1 << sys->var_info.red.length) - 1)
                          << sys->var_info.red.offset;
            fmt.i_gmask = ((1 << sys->var_info.green.length) - 1)
                          << sys->var_info.green.offset;
            fmt.i_bmask = ((1 << sys->var_info.blue.length) - 1)
                          << sys->var_info.blue.offset;
        }
    }

    fmt.i_visible_width  = sys->width;
    fmt.i_visible_height = sys->height;

    /* */
    vout_display_info_t info = vd->info;
    info.has_hide_mouse = true;

    /* */
    vd->fmt     = fmt;
    vd->info    = info;
    vd->pool    = Pool;
    vd->prepare = NULL;
    vd->display = Display;
    vd->control = Control;
    vd->manage  = NULL;

    /* */
    vout_display_SendEventFullscreen(vd, true);
    vout_display_SendEventDisplaySize(vd, fmt.i_visible_width, fmt.i_visible_height, true);
    return VLC_SUCCESS;
}
예제 #9
0
파일: sdl.c 프로젝트: BloodExecutioner/vlc
/**
 * This function initializes SDL vout method.
 */
static int Open(vlc_object_t *object)
{
    vout_display_t *vd = (vout_display_t *)object;
    vout_display_sys_t *sys;

#if !defined(WIN32) && !defined(__OS2__)
    if (!vlc_xlib_init (object))
        return VLC_EGENERIC;
#endif

    /* XXX: check for conflicts with the SDL audio output */
    vlc_mutex_lock(&sdl_lock);

    /* Check if SDL video module has been initialized */
    if (SDL_WasInit(SDL_INIT_VIDEO) != 0) {
        vlc_mutex_unlock(&sdl_lock);
        return VLC_EGENERIC;
    }

    vd->sys = sys = calloc(1, sizeof(*sys));
    if (!sys) {
        vlc_mutex_unlock(&sdl_lock);
        return VLC_ENOMEM;
    }

    /* */
    int sdl_flags = SDL_INIT_VIDEO;
#ifndef WIN32
    /* Win32 SDL implementation doesn't support SDL_INIT_EVENTTHREAD yet*/
    sdl_flags |= SDL_INIT_EVENTTHREAD;
#endif
    /* In debug mode you may want vlc to dump a core instead of staying stuck */
    sdl_flags |= SDL_INIT_NOPARACHUTE;

    /* Initialize library */
    if (SDL_Init(sdl_flags) < 0) {
        vlc_mutex_unlock(&sdl_lock);

        msg_Err(vd, "cannot initialize SDL (%s)", SDL_GetError());
        free(sys);
        return VLC_EGENERIC;
    }
    vlc_mutex_unlock(&sdl_lock);

    /* Translate keys into unicode */
    SDL_EnableUNICODE(1);

    /* Get the desktop resolution */
    /* FIXME: SDL has a problem with virtual desktop */
    sys->desktop_width  = SDL_GetVideoInfo()->current_w;
    sys->desktop_height = SDL_GetVideoInfo()->current_h;

    /* */
    video_format_t fmt = vd->fmt;

    /* */
    vout_display_info_t info = vd->info;

    /* Set main window's size */
    int display_width;
    int display_height;
    if (vd->cfg->is_fullscreen) {
        display_width  = sys->desktop_width;
        display_height = sys->desktop_height;
    } else {
        display_width  = vd->cfg->display.width;
        display_height = vd->cfg->display.height;
    }

    /* Initialize flags and cursor */
    sys->display_flags = SDL_ANYFORMAT | SDL_HWPALETTE | SDL_HWSURFACE | SDL_DOUBLEBUF;
    sys->display_flags |= vd->cfg->is_fullscreen ? SDL_FULLSCREEN : SDL_RESIZABLE;

    sys->display_bpp = SDL_VideoModeOK(display_width, display_height,
                                       16, sys->display_flags);
    if (sys->display_bpp == 0) {
        msg_Err(vd, "no video mode available");
        goto error;
    }
    vout_display_DeleteWindow(vd, NULL);

    sys->display = SDL_SetVideoMode(display_width, display_height,
                                    sys->display_bpp, sys->display_flags);
    if (!sys->display) {
        msg_Err(vd, "cannot set video mode");
        goto error;
    }

    /* We keep the surface locked forever */
    SDL_LockSurface(sys->display);

    /* */
    vlc_fourcc_t forced_chroma = 0;
    char *psz_chroma = var_InheritString(vd, "sdl-chroma");
    if (psz_chroma) {
        forced_chroma = vlc_fourcc_GetCodecFromString(VIDEO_ES, psz_chroma);
        if (forced_chroma)
            msg_Dbg(vd, "Forcing chroma to 0x%.8x (%4.4s)",
                    forced_chroma, (const char*)&forced_chroma);
        free(psz_chroma);
    }

    /* Try to open an overlay if requested */
    sys->overlay = NULL;
    const bool is_overlay = var_InheritBool(vd, "overlay");
    if (is_overlay) {
        static const struct
        {
            vlc_fourcc_t vlc;
            uint32_t     sdl;
        } vlc_to_sdl[] = {
            { VLC_CODEC_YV12, SDL_YV12_OVERLAY },
            { VLC_CODEC_I420, SDL_IYUV_OVERLAY },
            { VLC_CODEC_YUYV, SDL_YUY2_OVERLAY },
            { VLC_CODEC_UYVY, SDL_UYVY_OVERLAY },
            { VLC_CODEC_YVYU, SDL_YVYU_OVERLAY },

            { 0, 0 }
        };
        const vlc_fourcc_t forced_chromas[] = {
            forced_chroma, 0
        };
        const vlc_fourcc_t *fallback_chromas =
            vlc_fourcc_GetYUVFallback(fmt.i_chroma);
        const vlc_fourcc_t *chromas = forced_chroma ? forced_chromas : fallback_chromas;

        for (int pass = forced_chroma ? 1 : 0; pass < 2 && !sys->overlay; pass++) {
            for (int i = 0; chromas[i] != 0; i++) {
                const vlc_fourcc_t vlc = chromas[i];

                uint32_t sdl = 0;
                for (int j = 0; vlc_to_sdl[j].vlc != 0 && !sdl; j++) {
                    if (vlc_to_sdl[j].vlc == vlc)
                        sdl = vlc_to_sdl[j].sdl;
                }
                if (!sdl)
                    continue;

                sys->overlay = SDL_CreateYUVOverlay(fmt.i_width, fmt.i_height,
                                                    sdl, sys->display);
                if (sys->overlay && !sys->overlay->hw_overlay && pass == 0) {
                    /* Ignore non hardware overlay surface in first pass */
                    SDL_FreeYUVOverlay(sys->overlay);
                    sys->overlay = NULL;
                }
                if (sys->overlay) {
                    /* We keep the surface locked forever */
                    SDL_LockYUVOverlay(sys->overlay);

                    fmt.i_chroma = vlc;
                    sys->is_uv_swapped = vlc_fourcc_AreUVPlanesSwapped(fmt.i_chroma,
                                                                       vd->fmt.i_chroma);
                    if (sys->is_uv_swapped)
                        fmt.i_chroma = vd->fmt.i_chroma;
                    break;
                }
            }
        }
    } else {
        msg_Warn(vd, "SDL overlay disabled by the user");
    }

    /* */
    vout_display_cfg_t place_cfg = *vd->cfg;
    place_cfg.display.width  = display_width;
    place_cfg.display.height = display_height;
    vout_display_PlacePicture(&sys->place, &vd->source, &place_cfg, !sys->overlay);

    /* If no overlay, fallback to software output */
    if (!sys->overlay) {
        /* */
        switch (sys->display->format->BitsPerPixel) {
        case 8:
            fmt.i_chroma = VLC_CODEC_RGB8;
            break;
        case 15:
            fmt.i_chroma = VLC_CODEC_RGB15;
            break;
        case 16:
            fmt.i_chroma = VLC_CODEC_RGB16;
            break;
        case 24:
            fmt.i_chroma = VLC_CODEC_RGB24;
            break;
        case 32:
            fmt.i_chroma = VLC_CODEC_RGB32;
            break;
        default:
            msg_Err(vd, "unknown screen depth %i",
                    sys->display->format->BitsPerPixel);
            goto error;
        }

        /* All we have is an RGB image with square pixels */
        fmt.i_width  = display_width;
        fmt.i_height = display_height;
        fmt.i_rmask = sys->display->format->Rmask;
        fmt.i_gmask = sys->display->format->Gmask;
        fmt.i_bmask = sys->display->format->Bmask;

        info.has_pictures_invalid = true;
    }

    if (vd->cfg->display.title)
        SDL_WM_SetCaption(vd->cfg->display.title,
                          vd->cfg->display.title);
    else if (!sys->overlay)
        SDL_WM_SetCaption(VOUT_TITLE " (software RGB SDL output)",
                          VOUT_TITLE " (software RGB SDL output)");
    else if (sys->overlay->hw_overlay)
        SDL_WM_SetCaption(VOUT_TITLE " (hardware YUV SDL output)",
                          VOUT_TITLE " (hardware YUV SDL output)");
    else
        SDL_WM_SetCaption(VOUT_TITLE " (software YUV SDL output)",
                          VOUT_TITLE " (software YUV SDL output)");

    /* Setup events */
    SDL_EventState(SDL_KEYUP, SDL_IGNORE);               /* ignore keys up */

    /* Setup vout_display now that everything is fine */
    vd->fmt = fmt;
    vd->info = info;

    vd->pool    = Pool;
    vd->prepare = NULL;
    vd->display = PictureDisplay;
    vd->control = Control;
    vd->manage  = Manage;

    /* */
    vout_display_SendEventDisplaySize(vd, display_width, display_height, vd->cfg->is_fullscreen);
    return VLC_SUCCESS;

error:
    msg_Err(vd, "cannot set up SDL (%s)", SDL_GetError());

    if (sys->display) {
        SDL_UnlockSurface(sys->display);
        SDL_FreeSurface(sys->display);
    }

    vlc_mutex_lock(&sdl_lock);
    SDL_QuitSubSystem(SDL_INIT_VIDEO);
    vlc_mutex_unlock(&sdl_lock);

    free(sys);
    return VLC_EGENERIC;
}
예제 #10
0
파일: kva.c 프로젝트: fabsther/vlc-mort
static void PMThread( void *arg )
{
    vout_display_t *vd = ( vout_display_t * )arg;
    vout_display_sys_t * sys = vd->sys;
    ULONG i_frame_flags;
    QMSG qm;
    char *psz_mode;
    ULONG i_kva_mode;

    /* */
    video_format_t fmt = vd->fmt;

    /* */
    vout_display_info_t info = vd->info;
    info.is_slow = false;
    info.has_double_click = true;
    info.has_hide_mouse = false;
    info.has_pictures_invalid = false;

    MorphToPM();

    sys->hab = WinInitialize( 0 );
    sys->hmq = WinCreateMsgQueue( sys->hab, 0);

    WinRegisterClass( sys->hab,
                      WC_VLC_KVA,
                      WndProc,
                      CS_SIZEREDRAW | CS_MOVENOTIFY,
                      sizeof( PVOID ));

    sys->b_fixt23 = var_CreateGetBool( vd, "kva-fixt23");

    if( !sys->b_fixt23 )
    {
        vout_window_cfg_t wnd_cfg;

        wnd_cfg.is_standalone = false;
        wnd_cfg.type          = VOUT_WINDOW_TYPE_HWND;
        wnd_cfg.x             = var_InheritInteger(vd, "video-x");
        wnd_cfg.y             = var_InheritInteger(vd, "video-y");
        wnd_cfg.width         = vd->cfg->display.width;
        wnd_cfg.height        = vd->cfg->display.height;

        /* If an external window was specified, we'll draw in it. */
        sys->parent_window =
            vout_display_NewWindow( vd, &wnd_cfg );
    }

    if( sys->parent_window )
    {
        sys->parent = ( HWND )sys->parent_window->handle.hwnd;

        /* Workaround :
         * When an embedded window opened first, it is not positioned
         * correctly. So reposition it here, again.
         */
        WinSetWindowPos( WinQueryWindow( sys->parent, QW_PARENT ),
                         HWND_TOP, 0, 0, 0, 0, SWP_MOVE );

        ULONG i_style = WinQueryWindowULong( sys->parent, QWL_STYLE );
        WinSetWindowULong( sys->parent, QWL_STYLE,
                           i_style | WS_CLIPCHILDREN );

        i_frame_flags = FCF_TITLEBAR;
    }
    else
    {
        sys->parent = HWND_DESKTOP;

        i_frame_flags = FCF_SYSMENU    | FCF_TITLEBAR | FCF_MINMAX |
                        FCF_SIZEBORDER | FCF_TASKLIST;
    }

    sys->frame =
        WinCreateStdWindow( sys->parent,      /* parent window handle */
                            WS_VISIBLE,       /* frame window style */
                            &i_frame_flags,   /* window style */
                            WC_VLC_KVA,       /* class name */
                            "",               /* window title */
                            0L,               /* default client style */
                            NULLHANDLE,       /* resource in exe file */
                            1,                /* frame window id */
                            &sys->client );   /* client window handle */

    if( sys->frame == NULLHANDLE )
    {
        msg_Err( vd, "cannot create a frame window");

        goto exit_frame;
    }

    WinSetWindowPtr( sys->client, 0, vd );

    if( sys->b_fixt23 )
    {
        WinSetWindowPtr( sys->frame, 0, vd );
        sys->p_old_frame = WinSubclassWindow( sys->frame, MyFrameWndProc );
    }

    psz_mode = var_CreateGetString( vd, "kva-video-mode" );

    i_kva_mode = KVAM_AUTO;
    if( strcmp( psz_mode, "snap" ) == 0 )
        i_kva_mode = KVAM_SNAP;
    else if( strcmp( psz_mode, "wo" ) == 0 )
        i_kva_mode = KVAM_WO;
    else if( strcmp( psz_mode, "vman" ) == 0 )
        i_kva_mode = KVAM_VMAN;
    else if( strcmp( psz_mode, "dive" ) == 0 )
        i_kva_mode = KVAM_DIVE;

    free( psz_mode );

    if( kvaInit( i_kva_mode, sys->client, COLOR_KEY ))
    {
        msg_Err( vd, "cannot initialize KVA");

        goto exit_kva_init;
    }

    kvaCaps( &sys->kvac );

    msg_Dbg( vd, "selected video mode = %s",
             psz_video_mode[ sys->kvac.ulMode - 1 ]);

    if( OpenDisplay( vd, &fmt ) )
    {
        msg_Err( vd, "cannot open display");

        goto exit_open_display;
    }

    if( vd->cfg->is_fullscreen )
    {
        if( sys->parent_window )
            vout_window_SetFullScreen(sys->parent_window, true);
        else
            WinPostMsg( sys->client, WM_VLC_FULLSCREEN_CHANGE,
                        MPFROMLONG( true ), 0 );
    }

    kvaDisableScreenSaver();

    /* Setup vout_display now that everything is fine */
    vd->fmt     = fmt;
    vd->info    = info;

    vd->pool    = Pool;
    vd->prepare = NULL;
    vd->display = Display;
    vd->control = Control;
    vd->manage  = Manage;

    /* Prevent SIG_FPE */
    _control87(MCW_EM, MCW_EM);

    sys->i_result = VLC_SUCCESS;
    DosPostEventSem( sys->ack_event );

    while( WinGetMsg( sys->hab, &qm, NULLHANDLE, 0, 0 ))
        WinDispatchMsg( sys->hab, &qm );

    kvaEnableScreenSaver();

    CloseDisplay( vd );

    /* fall through */

exit_open_display :
    kvaDone();

exit_kva_init :
    if( sys->b_fixt23 )
        WinSubclassWindow( sys->frame, sys->p_old_frame );

    WinDestroyWindow( sys->frame );

exit_frame :
    vout_display_DeleteWindow( vd, sys->parent_window );

    if( sys->is_mouse_hidden )
        WinShowPointer( HWND_DESKTOP, TRUE );

    WinDestroyMsgQueue( sys->hmq );
    WinTerminate( sys->hab );

    sys->i_result = VLC_EGENERIC;
    DosPostEventSem( sys->ack_event );
}
예제 #11
0
파일: decklink.cpp 프로젝트: Adatan/vlc
static struct decklink_sys_t *OpenDecklink(vout_display_t *vd)
{
    vout_display_sys_t *sys = vd->sys;
#define CHECK(message) do { \
    if (result != S_OK) \
    { \
        msg_Err(vd, message ": 0x%X", result); \
        goto error; \
    } \
} while(0)

    HRESULT result;
    IDeckLinkIterator *decklink_iterator = NULL;
    IDeckLinkDisplayMode *p_display_mode = NULL;
    IDeckLinkDisplayModeIterator *p_display_iterator = NULL;
    IDeckLinkConfiguration *p_config = NULL;
    IDeckLink *p_card = NULL;

    struct decklink_sys_t *decklink_sys = GetDLSys(VLC_OBJECT(vd));
    vlc_mutex_lock(&decklink_sys->lock);
    decklink_sys->users++;

    /* wait until aout is ready */
    while (decklink_sys->i_rate == -1)
        vlc_cond_wait(&decklink_sys->cond, &decklink_sys->lock);

    int i_card_index = var_InheritInteger(vd, CFG_PREFIX "card-index");
    BMDVideoConnection vconn = getVConn(vd);
    char *mode = var_InheritString(vd, VIDEO_CFG_PREFIX "mode");
    size_t len = mode ? strlen(mode) : 0;
    if (!mode || len > 4)
    {
        free(mode);
        msg_Err(vd, "Missing or invalid mode");
        goto error;
    }

    BMDDisplayMode wanted_mode_id;
    memset(&wanted_mode_id, ' ', 4);
    strncpy((char*)&wanted_mode_id, mode, 4);
    free(mode);

    if (i_card_index < 0)
    {
        msg_Err(vd, "Invalid card index %d", i_card_index);
        goto error;
    }

    decklink_iterator = CreateDeckLinkIteratorInstance();
    if (!decklink_iterator)
    {
        msg_Err(vd, "DeckLink drivers not found.");
        goto error;
    }

    for(int i = 0; i <= i_card_index; ++i)
    {
        if (p_card)
            p_card->Release();
        result = decklink_iterator->Next(&p_card);
        CHECK("Card not found");
    }

    const char *psz_model_name;
    result = p_card->GetModelName(&psz_model_name);
    CHECK("Unknown model name");

    msg_Dbg(vd, "Opened DeckLink PCI card %s", psz_model_name);

    result = p_card->QueryInterface(IID_IDeckLinkOutput,
        (void**)&decklink_sys->p_output);
    CHECK("No outputs");

    result = p_card->QueryInterface(IID_IDeckLinkConfiguration,
        (void**)&p_config);
    CHECK("Could not get config interface");

    if (vconn)
    {
        result = p_config->SetInt(
            bmdDeckLinkConfigVideoOutputConnection, vconn);
        CHECK("Could not set video output connection");
    }

    result = decklink_sys->p_output->GetDisplayModeIterator(&p_display_iterator);
    CHECK("Could not enumerate display modes");

    for (; ; p_display_mode->Release())
    {
        int w, h;
        result = p_display_iterator->Next(&p_display_mode);
        if (result != S_OK)
            break;

        BMDDisplayMode mode_id = ntohl(p_display_mode->GetDisplayMode());

        const char *psz_mode_name;
        result = p_display_mode->GetName(&psz_mode_name);
        CHECK("Could not get display mode name");

        result = p_display_mode->GetFrameRate(&decklink_sys->frameduration,
            &decklink_sys->timescale);
        CHECK("Could not get frame rate");

        w = p_display_mode->GetWidth();
        h = p_display_mode->GetHeight();
        msg_Dbg(vd, "Found mode '%4.4s': %s (%dx%d, %.3f fps)",
                (char*)&mode_id, psz_mode_name, w, h,
                double(decklink_sys->timescale) / decklink_sys->frameduration);
        msg_Dbg(vd, "scale %d dur %d", (int)decklink_sys->timescale,
            (int)decklink_sys->frameduration);

        if (wanted_mode_id != mode_id)
            continue;

        decklink_sys->i_width = w;
        decklink_sys->i_height = h;

        mode_id = htonl(mode_id);

        BMDVideoOutputFlags flags = bmdVideoOutputVANC;
        if (mode_id == bmdModeNTSC ||
            mode_id == bmdModeNTSC2398 ||
            mode_id == bmdModePAL)
        {
            flags = bmdVideoOutputVITC;
        }

        BMDDisplayModeSupport support;
        IDeckLinkDisplayMode *resultMode;

        result = decklink_sys->p_output->DoesSupportVideoMode(mode_id,
            sys->tenbits ? bmdFormat10BitYUV : bmdFormat8BitYUV,
            flags, &support, &resultMode);
        CHECK("Does not support video mode");
        if (support == bmdDisplayModeNotSupported)
        {
            msg_Err(vd, "Video mode not supported");
                goto error;
        }

        result = decklink_sys->p_output->EnableVideoOutput(mode_id, flags);
        CHECK("Could not enable video output");

        break;
    }

    if (decklink_sys->i_width < 0 || decklink_sys->i_width & 1)
    {
        msg_Err(vd, "Unknown video mode specified.");
        goto error;
    }

    if (/*decklink_sys->i_channels > 0 &&*/ decklink_sys->i_rate > 0)
    {
        result = decklink_sys->p_output->EnableAudioOutput(
            decklink_sys->i_rate,
            bmdAudioSampleType16bitInteger,
            /*decklink_sys->i_channels*/ 2,
            bmdAudioOutputStreamTimestamped);
    }
    CHECK("Could not start audio output");

    /* start */
    result = decklink_sys->p_output->StartScheduledPlayback(
        (mdate() * decklink_sys->timescale) / CLOCK_FREQ, decklink_sys->timescale, 1.0);
    CHECK("Could not start playback");

    p_config->Release();
    p_display_mode->Release();
    p_display_iterator->Release();
    p_card->Release();
    decklink_iterator->Release();

    vlc_mutex_unlock(&decklink_sys->lock);

    vout_display_DeleteWindow(vd, NULL);

    return decklink_sys;

error:
    if (decklink_sys->p_output) {
        decklink_sys->p_output->Release();
        decklink_sys->p_output = NULL;
    }
    if (p_card)
        p_card->Release();
    if (p_config)
        p_config->Release();
    if (p_display_iterator)
        p_display_iterator->Release();
    if (decklink_iterator)
        decklink_iterator->Release();
    if (p_display_mode)
        p_display_mode->Release();

    vlc_mutex_unlock(&decklink_sys->lock);
    ReleaseDLSys(VLC_OBJECT(vd));

    return NULL;
#undef CHECK
}
예제 #12
0
파일: events.c 프로젝트: chouquette/vlc
/*****************************************************************************
 * Win32VoutCreateWindow: create a window for the video.
 *****************************************************************************
 * Before creating a direct draw surface, we need to create a window in which
 * the video will be displayed. This window will also allow us to capture the
 * events.
 *****************************************************************************/
static int Win32VoutCreateWindow( event_thread_t *p_event )
{
    vout_display_t *vd = p_event->vd;
    HINSTANCE  hInstance;
    HMENU      hMenu;
    RECT       rect_window;
    WNDCLASS   wc;                            /* window class components */
    TCHAR      vlc_path[MAX_PATH+1];
    int        i_style;

    msg_Dbg( vd, "Win32VoutCreateWindow" );

    /* Get this module's instance */
    hInstance = GetModuleHandle(NULL);

    #if defined(MODULE_NAME_IS_direct3d9) || defined(MODULE_NAME_IS_direct3d11)
    if( !p_event->use_desktop )
    #endif
    {
        /* If an external window was specified, we'll draw in it. */
        p_event->parent_window = vout_display_NewWindow(vd, VOUT_WINDOW_TYPE_HWND);
        if( p_event->parent_window )
            p_event->hparent = p_event->parent_window->handle.hwnd;
        else
            p_event->hparent = NULL;
    }
    #if defined(MODULE_NAME_IS_direct3d9) || defined(MODULE_NAME_IS_direct3d11)
    else
    {
        vout_display_DeleteWindow(vd, NULL);
        p_event->parent_window = NULL;
        p_event->hparent = GetDesktopHandle(vd);
    }
    #endif
    p_event->cursor_arrow = LoadCursor(NULL, IDC_ARROW);
    p_event->cursor_empty = EmptyCursor(hInstance);

    /* Get the Icon from the main app */
    p_event->vlc_icon = NULL;
    if( GetModuleFileName( NULL, vlc_path, MAX_PATH ) )
    {
        p_event->vlc_icon = ExtractIcon( hInstance, vlc_path, 0 );
    }

    /* Fill in the window class structure */
    wc.style         = CS_OWNDC|CS_DBLCLKS;          /* style: dbl click */
    wc.lpfnWndProc   = (WNDPROC)WinVoutEventProc;       /* event handler */
    wc.cbClsExtra    = 0;                         /* no extra class data */
    wc.cbWndExtra    = 0;                        /* no extra window data */
    wc.hInstance     = hInstance;                            /* instance */
    wc.hIcon         = p_event->vlc_icon;       /* load the vlc big icon */
    wc.hCursor       = p_event->is_cursor_hidden ? p_event->cursor_empty :
                                                   p_event->cursor_arrow;
#if !VLC_WINSTORE_APP
    wc.hbrBackground = GetStockObject(BLACK_BRUSH);  /* background color */
#else
    wc.hbrBackground = NULL;
#endif
    wc.lpszMenuName  = NULL;                                  /* no menu */
    wc.lpszClassName = p_event->class_main;       /* use a special class */

    /* Register the window class */
    if( !RegisterClass(&wc) )
    {
        if( p_event->vlc_icon )
            DestroyIcon( p_event->vlc_icon );

        msg_Err( vd, "Win32VoutCreateWindow RegisterClass FAILED (err=%lu)", GetLastError() );
        return VLC_EGENERIC;
    }

    /* Register the video sub-window class */
    wc.lpszClassName = p_event->class_video;
    wc.hIcon = 0;
    wc.hbrBackground = NULL; /* no background color */
    if( !RegisterClass(&wc) )
    {
        msg_Err( vd, "Win32VoutCreateWindow RegisterClass FAILED (err=%lu)", GetLastError() );
        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.left   = 10;
    rect_window.top    = 10;
    rect_window.right  = rect_window.left + p_event->width;
    rect_window.bottom = rect_window.top  + p_event->height;

    i_style = var_GetBool( vd, "video-deco" )
        /* Open with window decoration */
        ? WS_OVERLAPPEDWINDOW|WS_SIZEBOX
        /* No window decoration */
        : WS_POPUP;
    AdjustWindowRect( &rect_window, i_style, 0 );
    i_style |= WS_VISIBLE|WS_CLIPCHILDREN;

    if( p_event->hparent )
    {
        i_style = WS_VISIBLE|WS_CLIPCHILDREN|WS_CHILD;

        /* allow user to regain control over input events if requested */
        bool b_mouse_support = var_InheritBool( vd, "mouse-events" );
        bool b_key_support = var_InheritBool( vd, "keyboard-events" );
        if( !b_mouse_support && !b_key_support )
            i_style |= WS_DISABLED;
    }

    p_event->i_window_style = i_style;

    /* Create the window */
    p_event->hwnd =
        CreateWindowEx( WS_EX_NOPARENTNOTIFY,
                    p_event->class_main,             /* name of window class */
                    _T(VOUT_TITLE) _T(" (VLC Video Output)"),/* window title */
                    i_style,                                 /* window style */
                    (!p_event->x) ? (UINT)CW_USEDEFAULT :
                        (UINT)p_event->x,            /* default X coordinate */
                    (!p_event->y) ? (UINT)CW_USEDEFAULT :
                        (UINT)p_event->y,            /* default Y coordinate */
                    rect_window.right - rect_window.left,    /* window width */
                    rect_window.bottom - rect_window.top,   /* window height */
                    p_event->hparent,                       /* parent window */
                    NULL,                          /* no menu in this window */
                    hInstance,            /* handle of this program instance */
                    (LPVOID)p_event );           /* send vd to WM_CREATE */

    if( !p_event->hwnd )
    {
        msg_Warn( vd, "Win32VoutCreateWindow create window FAILED (err=%lu)", GetLastError() );
        return VLC_EGENERIC;
    }

    InitGestures( p_event->hwnd, &p_event->p_gesture );

    if( p_event->hparent )
    {
        LONG i_style;

        /* We don't want the window owner to overwrite our client area */
        i_style = GetWindowLong( p_event->hparent, GWL_STYLE );

        if( !(i_style & WS_CLIPCHILDREN) )
            /* Hmmm, apparently this is a blocking call... */
            SetWindowLong( p_event->hparent, GWL_STYLE,
                           i_style | WS_CLIPCHILDREN );

        /* Create our fullscreen window */
        p_event->hfswnd =
            CreateWindowEx( WS_EX_APPWINDOW, p_event->class_main,
                            _T(VOUT_TITLE) _T(" (VLC Fullscreen Video Output)"),
                            WS_OVERLAPPEDWINDOW|WS_CLIPCHILDREN|WS_SIZEBOX,
                            CW_USEDEFAULT, CW_USEDEFAULT,
                            CW_USEDEFAULT, CW_USEDEFAULT,
                            NULL, NULL, hInstance, NULL );
    }
    else
    {
        p_event->hfswnd = NULL;
    }

    /* Append a "Always On Top" entry in the system menu */
    hMenu = GetSystemMenu( p_event->hwnd, FALSE );
    AppendMenu( hMenu, MF_SEPARATOR, 0, _T("") );
    AppendMenu( hMenu, MF_STRING | MF_UNCHECKED,
                       IDM_TOGGLE_ON_TOP, _T("Always on &Top") );

    /* Create video sub-window. This sub window will always exactly match
     * the size of the video, which allows us to use crazy overlay colorkeys
     * without having them shown outside of the video area. */
    /* FIXME vd->source.i_width/i_height seems wrong */
    p_event->hvideownd =
    CreateWindow( p_event->class_video, _T(""),   /* window class */
        WS_CHILD,                   /* window style, not visible initially */
        0, 0,
        vd->source.i_width,          /* default width */
        vd->source.i_height,        /* default height */
        p_event->hwnd,               /* parent window */
        NULL, hInstance,
        (LPVOID)p_event );    /* send vd to WM_CREATE */

    if( !p_event->hvideownd )
        msg_Warn( vd, "can't create video sub-window" );
    else
        msg_Dbg( vd, "created video sub-window" );

    /* Now display the window */
    ShowWindow( p_event->hwnd, SW_SHOW );

    return VLC_SUCCESS;
}
예제 #13
0
static int Open(vlc_object_t *object)
{
    vout_display_t *vd = (vout_display_t *)object;
    vout_display_sys_t *sys;

    /* Allocate structure */
    vd->sys = sys = malloc(sizeof(*sys));
    if (!sys)
        return VLC_ENOMEM;

    sys->directfb = NULL;
    sys->primary  = NULL;
    sys->width    = 0;
    sys->height   = 0;
    sys->pool     = NULL;

    /* Init DirectFB */
    if (DirectFBInit(NULL,NULL) != DFB_OK) {
        msg_Err(vd, "Cannot init DirectFB");
        free(sys);
        return VLC_EGENERIC;
    }

    if (OpenDisplay(vd)) {
        msg_Err(vd, "Cannot create primary surface");
        Close(VLC_OBJECT(vd));
        return VLC_EGENERIC;
    }
    vout_display_DeleteWindow(vd, NULL);

    /* */
    video_format_t fmt = vd->fmt;

    switch (sys->pixel_format) {
    case DSPF_RGB332:
        /* 8 bit RGB (1 byte, red 3@5, green 3@2, blue 2@0) */
        fmt.i_chroma = VLC_CODEC_RGB8;
        fmt.i_rmask = 0x7 << 5;
        fmt.i_gmask = 0x7 << 2;
        fmt.i_bmask = 0x3 << 0;
        break;
    case DSPF_RGB16:
        /* 16 bit RGB (2 byte, red 5@11, green 6@5, blue 5@0) */
        fmt.i_chroma = VLC_CODEC_RGB16;
        fmt.i_rmask = 0x1f << 11;
        fmt.i_gmask = 0x3f <<  5;
        fmt.i_bmask = 0x1f <<  0;
        break;
    case DSPF_RGB24:
        /* 24 bit RGB (3 byte, red 8@16, green 8@8, blue 8@0) */
        fmt.i_chroma = VLC_CODEC_RGB24;
        fmt.i_rmask = 0xff << 16;
        fmt.i_gmask = 0xff <<  8;
        fmt.i_bmask = 0xff <<  0;
        break;
    case DSPF_RGB32:
        /* 24 bit RGB (4 byte, nothing@24, red 8@16, green 8@8, blue 8@0) */
        fmt.i_chroma = VLC_CODEC_RGB32;
        fmt.i_rmask = 0xff << 16;
        fmt.i_gmask = 0xff <<  8;
        fmt.i_bmask = 0xff <<  0;
        break;
    default:
        msg_Err(vd, "unknown screen depth %i", sys->pixel_format);
        Close(VLC_OBJECT(vd));
        return VLC_EGENERIC;
    }

    fmt.i_width  = sys->width;
    fmt.i_height = sys->height;

    /* */
    vout_display_info_t info = vd->info;
    info.has_hide_mouse = true;

    /* */
    vd->fmt     = fmt;
    vd->info    = info;
    vd->pool    = Pool;
    vd->prepare = NULL;
    vd->display = Display;
    vd->control = Control;
    vd->manage  = Manage;

    /* */
    vout_display_SendEventFullscreen(vd, true);
    vout_display_SendEventDisplaySize(vd, fmt.i_width, fmt.i_height, true);
    return VLC_SUCCESS;
}
예제 #14
0
파일: yuv.c 프로젝트: Aakash-729/vlc
static int Open(vlc_object_t *object)
{
    vout_display_t *vd = (vout_display_t *)object;
    vout_display_sys_t *sys;

    /* Allocate instance and initialize some members */
    vd->sys = sys = malloc(sizeof(*sys));
    if (!sys)
        return VLC_ENOMEM;

    sys->is_first = false;
    sys->is_yuv4mpeg2 = var_InheritBool(vd, CFG_PREFIX "yuv4mpeg2");
    sys->pool = NULL;

    /* */
    char *psz_fcc = var_InheritString(vd, CFG_PREFIX "chroma");
    const vlc_fourcc_t requested_chroma = vlc_fourcc_GetCodecFromString(VIDEO_ES,
                                                                        psz_fcc);
    free(psz_fcc);

    const vlc_fourcc_t chroma = requested_chroma ? requested_chroma :
                                                   VLC_CODEC_I420;
    if (sys->is_yuv4mpeg2) {
        switch (chroma) {
        case VLC_CODEC_YV12:
        case VLC_CODEC_I420:
        case VLC_CODEC_J420:
            break;
        default:
            msg_Err(vd, "YUV4MPEG2 mode needs chroma YV12 not %4.4s as requested",
                    (char *)&chroma);
            free(sys);
            return VLC_EGENERIC;
        }
    }
    msg_Dbg(vd, "Using chroma %4.4s", (char *)&chroma);

    /* */
    char *name = var_InheritString(vd, CFG_PREFIX "file");
    if (!name) {
        msg_Err(vd, "Empty file name");
        free(sys);
        return VLC_EGENERIC;
    }
    sys->f = vlc_fopen(name, "wb");

    if (!sys->f) {
        msg_Err(vd, "Failed to open %s", name);
        free(name);
        free(sys);
        return VLC_EGENERIC;
    }
    msg_Dbg(vd, "Writing data to %s", name);
    free(name);

    /* */
    video_format_t fmt;
    video_format_ApplyRotation(&fmt, &vd->fmt);
    fmt.i_chroma = chroma;
    video_format_FixRgb(&fmt);

    /* */
    vout_display_info_t info = vd->info;
    info.has_hide_mouse = true;

    /* */
    vd->fmt     = fmt;
    vd->info    = info;
    vd->pool    = Pool;
    vd->prepare = NULL;
    vd->display = Display;
    vd->control = Control;
    vd->manage  = NULL;

    vout_display_SendEventFullscreen(vd, false);
    vout_display_DeleteWindow(vd, NULL);
    return VLC_SUCCESS;
}
예제 #15
0
/*****************************************************************************
 * Open: allocates video thread
 *****************************************************************************
 * This function allocates and initializes a vout method.
 *****************************************************************************/
static int Open(vlc_object_t *object)
{
    vout_display_t *vd = (vout_display_t *)object;
    vout_display_sys_t *sys = malloc(sizeof(*sys));
    if (unlikely(!sys))
        return VLC_ENOMEM;

    /* Get the callbacks */
    vlc_format_cb setup = var_InheritAddress(vd, "vmem-setup");

    sys->lock = var_InheritAddress(vd, "vmem-lock");
    if (sys->lock == NULL) {
        msg_Err(vd, "missing lock callback");
        free(sys);
        return VLC_EGENERIC;
    }
    sys->unlock = var_InheritAddress(vd, "vmem-unlock");
    sys->display = var_InheritAddress(vd, "vmem-display");
    sys->cleanup = var_InheritAddress(vd, "vmem-cleanup");
    sys->opaque = var_InheritAddress(vd, "vmem-data");
    sys->pool = NULL;

    /* Define the video format */
    video_format_t fmt;
    video_format_ApplyRotation(&fmt, &vd->fmt);

    if (setup != NULL) {
        char chroma[5];

        memcpy(chroma, &fmt.i_chroma, 4);
        chroma[4] = '\0';
        memset(sys->pitches, 0, sizeof(sys->pitches));
        memset(sys->lines, 0, sizeof(sys->lines));

        sys->count = setup(&sys->opaque, chroma, &fmt.i_width, &fmt.i_height,
                           sys->pitches, sys->lines);
        if (sys->count == 0) {
            msg_Err(vd, "video format setup failure (no pictures)");
            free(sys);
            return VLC_EGENERIC;
        }
        fmt.i_chroma = vlc_fourcc_GetCodecFromString(VIDEO_ES, chroma);

    } else {
        char *chroma = var_InheritString(vd, "vmem-chroma");
        fmt.i_chroma = vlc_fourcc_GetCodecFromString(VIDEO_ES, chroma);
        free(chroma);

        fmt.i_width  = var_InheritInteger(vd, "vmem-width");
        fmt.i_height = var_InheritInteger(vd, "vmem-height");
        sys->pitches[0] = var_InheritInteger(vd, "vmem-pitch");
        sys->lines[0] = fmt.i_height;
        for (size_t i = 1; i < PICTURE_PLANE_MAX; i++)
        {
            sys->pitches[i] = sys->pitches[0];
            sys->lines[i] = sys->lines[0];
        }
        sys->count = 1;
        sys->cleanup = NULL;
    }
    fmt.i_x_offset = fmt.i_y_offset = 0;
    fmt.i_visible_width = fmt.i_width;
    fmt.i_visible_height = fmt.i_height;

    if (!fmt.i_chroma) {
        msg_Err(vd, "vmem-chroma should be 4 characters long");
        free(sys);
        return VLC_EGENERIC;
    }

    /* Define the bitmasks */
    switch (fmt.i_chroma)
    {
    case VLC_CODEC_RGB15:
        fmt.i_rmask = 0x001f;
        fmt.i_gmask = 0x03e0;
        fmt.i_bmask = 0x7c00;
        break;
    case VLC_CODEC_RGB16:
        fmt.i_rmask = 0x001f;
        fmt.i_gmask = 0x07e0;
        fmt.i_bmask = 0xf800;
        break;
    case VLC_CODEC_RGB24:
    case VLC_CODEC_RGB32:
        fmt.i_rmask = 0xff0000;
        fmt.i_gmask = 0x00ff00;
        fmt.i_bmask = 0x0000ff;
        break;
    default:
        fmt.i_rmask = 0;
        fmt.i_gmask = 0;
        fmt.i_bmask = 0;
        break;
    }

    /* */
    vout_display_info_t info = vd->info;
    info.has_hide_mouse = true;

    /* */
    vd->sys     = sys;
    vd->fmt     = fmt;
    vd->info    = info;
    vd->pool    = Pool;
    vd->prepare = Prepare;
    vd->display = Display;
    vd->control = Control;
    vd->manage  = NULL;

    /* */
    vout_display_SendEventFullscreen(vd, false);
    vout_display_SendEventDisplaySize(vd, fmt.i_width, fmt.i_height);
    vout_display_DeleteWindow(vd, NULL);
    return VLC_SUCCESS;
}
예제 #16
0
파일: caca.c 프로젝트: RodrigoNieves/vlc
/**
 * This function initializes libcaca vout method.
 */
static int Open(vlc_object_t *object)
{
    vout_display_t *vd = (vout_display_t *)object;
    vout_display_sys_t *sys;

#if !defined(__APPLE__) && !defined(WIN32)
# ifndef X_DISPLAY_MISSING
    if (!vlc_xlib_init(object))
        return VLC_EGENERIC;
# endif
#endif

#if defined(WIN32)
    CONSOLE_SCREEN_BUFFER_INFO csbiInfo;
    SMALL_RECT rect;
    COORD coord;
    HANDLE hstdout;

    if (!AllocConsole()) {
        msg_Err(vd, "cannot create console");
        return VLC_EGENERIC;
    }

    hstdout =
        CreateConsoleScreenBuffer(GENERIC_READ | GENERIC_WRITE,
                                  FILE_SHARE_READ | FILE_SHARE_WRITE,
                                  NULL, CONSOLE_TEXTMODE_BUFFER, NULL);
    if (!hstdout || hstdout == INVALID_HANDLE_VALUE) {
        msg_Err(vd, "cannot create screen buffer");
        FreeConsole();
        return VLC_EGENERIC;
    }

    if (!SetConsoleActiveScreenBuffer(hstdout)) {
        msg_Err(vd, "cannot set active screen buffer");
        FreeConsole();
        return VLC_EGENERIC;
    }

    coord = GetLargestConsoleWindowSize(hstdout);
    msg_Dbg(vd, "SetConsoleWindowInfo: %ix%i", coord.X, coord.Y);

    /* Force size for now */
    coord.X = 100;
    coord.Y = 40;

    if (!SetConsoleScreenBufferSize(hstdout, coord))
        msg_Warn(vd, "SetConsoleScreenBufferSize %i %i",
                  coord.X, coord.Y);

    /* Get the current screen buffer size and window position. */
    if (GetConsoleScreenBufferInfo(hstdout, &csbiInfo)) {
        rect.Top = 0; rect.Left = 0;
        rect.Right = csbiInfo.dwMaximumWindowSize.X - 1;
        rect.Bottom = csbiInfo.dwMaximumWindowSize.Y - 1;
        if (!SetConsoleWindowInfo(hstdout, TRUE, &rect))
            msg_Dbg(vd, "SetConsoleWindowInfo failed: %ix%i",
                     rect.Right, rect.Bottom);
    }
#endif

    /* Allocate structure */
    vd->sys = sys = calloc(1, sizeof(*sys));
    if (!sys)
        goto error;

    sys->cv = cucul_create_canvas(0, 0);
    if (!sys->cv) {
        msg_Err(vd, "cannot initialize libcucul");
        goto error;
    }

    const char *driver = NULL;
#ifdef __APPLE__
    // Make sure we don't try to open a window.
    driver = "ncurses";
#endif

    sys->dp = caca_create_display_with_driver(sys->cv, driver);
    if (!sys->dp) {
        msg_Err(vd, "cannot initialize libcaca");
        goto error;
    }
    vout_display_DeleteWindow(vd, NULL);

    if (vd->cfg->display.title)
        caca_set_display_title(sys->dp,
                               vd->cfg->display.title);
    else
        caca_set_display_title(sys->dp,
                               VOUT_TITLE "(Colour AsCii Art)");

    /* Fix format */
    video_format_t fmt = vd->fmt;
    if (fmt.i_chroma != VLC_CODEC_RGB32) {
        fmt.i_chroma = VLC_CODEC_RGB32;
        fmt.i_rmask = 0x00ff0000;
        fmt.i_gmask = 0x0000ff00;
        fmt.i_bmask = 0x000000ff;
    }

    /* TODO */
    vout_display_info_t info = vd->info;

    /* Setup vout_display now that everything is fine */
    vd->fmt = fmt;
    vd->info = info;

    vd->pool    = Pool;
    vd->prepare = Prepare;
    vd->display = PictureDisplay;
    vd->control = Control;
    vd->manage  = Manage;

    /* Fix initial state */
    vout_display_SendEventFullscreen(vd, false);
    Refresh(vd);

    return VLC_SUCCESS;

error:
    if (sys) {
        if (sys->pool)
            picture_pool_Delete(sys->pool);
        if (sys->dither)
            cucul_free_dither(sys->dither);
        if (sys->dp)
            caca_free_display(sys->dp);
        if (sys->cv)
            cucul_free_canvas(sys->cv);

        free(sys);
    }
#if defined(WIN32)
    FreeConsole();
#endif
    return VLC_EGENERIC;
}