Esempio n. 1
0
/**
 * \brief Toogle window ontop attribute.
 *
 * Should be called on VOCTRL_ONTOP event.
 */
void vo_w32_ontop(struct vo *vo)
{
    vo->opts->ontop = !vo->opts->ontop;
    reinit_window_state(vo);
}
Esempio n. 2
0
/**
 * \brief Toogle window border attribute.
 *
 * Should be called on VOCTRL_BORDER event.
 */
void vo_w32_border(struct vo *vo)
{
    vo->opts->border = !vo->opts->border;
    reinit_window_state(vo);
}
Esempio n. 3
0
/**
 * \brief Initialize w32_common framework.
 *
 * The first function that should be called from the w32_common framework.
 * It handles window creation on the screen with proper title and attributes.
 * It also initializes the framework's internal variables. The function should
 * be called after your own preinit initialization and you shouldn't do any
 * window management on your own.
 *
 * Global libvo variables changed:
 * vo_w32_window
 * vo_screenwidth
 * vo_screenheight
 *
 * \return 1 = Success, 0 = Failure
 */
int vo_w32_init(struct vo *vo)
{
    struct vo_w32_state *w32 = vo->w32;
    if (w32 && w32->window)
        return 1;

    if (!w32)
        w32 = vo->w32 = talloc_zero(vo, struct vo_w32_state);

    HINSTANCE hInstance = GetModuleHandleW(NULL);

    HICON mplayerIcon = LoadIconW(hInstance, L"IDI_ICON1");

    WNDCLASSEXW wcex = {
        .cbSize = sizeof wcex,
        .style = CS_OWNDC | CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW,
        .lpfnWndProc = WndProc,
        .hInstance = hInstance,
        .hIcon = mplayerIcon,
        .hCursor = LoadCursor(0, IDC_ARROW),
        .lpszClassName = classname,
        .hIconSm = mplayerIcon,
    };

    if (!RegisterClassExW(&wcex)) {
        mp_msg(MSGT_VO, MSGL_ERR,
               "vo: win32: unable to register window class!\n");
        return 0;
    }

    if (vo->opts->WinID >= 0) {
        RECT r;
        GetClientRect(WIN_ID_TO_HWND(vo->opts->WinID), &r);
        vo->dwidth = r.right; vo->dheight = r.bottom;
        w32->window = CreateWindowExW(WS_EX_NOPARENTNOTIFY, classname,
                                      classname,
                                      WS_CHILD | WS_VISIBLE,
                                      0, 0, vo->dwidth, vo->dheight,
                                      WIN_ID_TO_HWND(vo->opts->WinID),
                                      0, hInstance, vo);
    } else {
        w32->window = CreateWindowExW(0, classname,
                                      classname,
                                      update_style(vo, 0),
                                      CW_USEDEFAULT, 0, 100, 100,
                                      0, 0, hInstance, vo);
    }

    if (!w32->window) {
        mp_msg(MSGT_VO, MSGL_ERR, "vo: win32: unable to create window!\n");
        return 0;
    }

    if (vo->opts->WinID >= 0)
        EnableWindow(w32->window, 0);

    // we don't have proper event handling
    vo->wakeup_period = 0.02;

    updateScreenProperties(vo);

    mp_msg(MSGT_VO, MSGL_V, "vo: win32: running at %dx%d\n",
           vo->opts->screenwidth, vo->opts->screenheight);

    return 1;
}

/**
 * \brief Toogle fullscreen / windowed mode.
 *
 * Should be called on VOCTRL_FULLSCREEN event. The window is
 * always resized during this call, so the rendering context
 * should be reinitialized with the new dimensions.
 * It is unspecified if vo_check_events will create a resize
 * event in addition or not.
 */

void vo_w32_fullscreen(struct vo *vo)
{
    vo->opts->fs = !vo->opts->fs;
    reinit_window_state(vo);
}
Esempio n. 4
0
/**
 * \brief Configure and show window on the screen.
 *
 * This function should be called in libvo's "config" callback.
 * It configures a window and shows it on the screen.
 *
 * \return 1 - Success, 0 - Failure
 */
int vo_w32_config(struct vo *vo, uint32_t width, uint32_t height,
                  uint32_t flags)
{
    struct vo_w32_state *w32 = vo->w32;
    PIXELFORMATDESCRIPTOR pfd;
    int pf;
    HDC vo_hdc = GetDC(w32->window);

    memset(&pfd, 0, sizeof pfd);
    pfd.nSize = sizeof pfd;
    pfd.nVersion = 1;
    pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
    if (flags & VOFLAG_STEREO)
        pfd.dwFlags |= PFD_STEREO;
    pfd.iPixelType = PFD_TYPE_RGBA;
    pfd.cColorBits = 24;
    pfd.iLayerType = PFD_MAIN_PLANE;
    pf = ChoosePixelFormat(vo_hdc, &pfd);
    if (!pf) {
        mp_msg(MSGT_VO, MSGL_ERR, "vo: win32: unable to select a valid pixel format!\n");
        ReleaseDC(w32->window, vo_hdc);
        return 0;
    }

    SetPixelFormat(vo_hdc, pf, &pfd);
    ReleaseDC(w32->window, vo_hdc);

    // we already have a fully initialized window, so nothing needs to be done
    if (flags & VOFLAG_HIDDEN)
        return 1;

    bool reset_size = !(w32->o_dwidth == width && w32->o_dheight == height);

    w32->o_dwidth = width;
    w32->o_dheight = height;

    // the desired size is ignored in wid mode, it always matches the window size.
    if (vo->opts->WinID < 0) {
        if (w32->window_bounds_initialized) {
            // restore vo_dwidth/vo_dheight, which are reset against our will
            // in vo_config()
            RECT r;
            GetClientRect(w32->window, &r);
            vo->dwidth = r.right;
            vo->dheight = r.bottom;
        } else {
            // first vo_config call; vo_config() will always set vo_dx/dy so
            // that the window is centered on the screen, and this is the only
            // time we actually want to use vo_dy/dy (this is not sane, and
            // vo.h should provide a function to query the initial
            // window position instead)
            w32->window_bounds_initialized = true;
            reset_size = true;
            w32->window_x = w32->prev_x = vo->dx;
            w32->window_y = w32->prev_y = vo->dy;
        }
        if (reset_size) {
            w32->prev_width = vo->dwidth = width;
            w32->prev_height = vo->dheight = height;
        }
    } else {
        RECT r;
        GetClientRect(w32->window, &r);
        vo->dwidth = r.right;
        vo->dheight = r.bottom;
    }

    vo->opts->fs = flags & VOFLAG_FULLSCREEN;
    return reinit_window_state(vo);
}
Esempio n. 5
0
int vo_w32_control(struct vo *vo, int *events, int request, void *arg)
{
    struct vo_w32_state *w32 = vo->w32;
    switch (request) {
    case VOCTRL_CHECK_EVENTS:
        *events |= vo_w32_check_events(vo);
        return VO_TRUE;
    case VOCTRL_FULLSCREEN:
        vo_w32_fullscreen(vo);
        *events |= VO_EVENT_RESIZE;
        return VO_TRUE;
    case VOCTRL_ONTOP:
        vo_w32_ontop(vo);
        return VO_TRUE;
    case VOCTRL_BORDER:
        vo_w32_border(vo);
        *events |= VO_EVENT_RESIZE;
        return VO_TRUE;
    case VOCTRL_UPDATE_SCREENINFO:
        w32_update_xinerama_info(vo);
        return VO_TRUE;
    case VOCTRL_GET_WINDOW_SIZE: {
        int *s = arg;
        if (!w32->window_bounds_initialized)
            return VO_FALSE;
        s[0] = w32->current_fs ? w32->prev_width : vo->dwidth;
        s[1] = w32->current_fs ? w32->prev_height : vo->dheight;
        return VO_TRUE;
    }
    case VOCTRL_SET_WINDOW_SIZE: {
        int *s = arg;
        if (!w32->window_bounds_initialized)
            return VO_FALSE;
        if (w32->current_fs) {
            w32->prev_width = s[0];
            w32->prev_height = s[1];
        } else {
            vo->dwidth = s[0];
            vo->dheight = s[1];
        }
        reinit_window_state(vo);
        *events |= VO_EVENT_RESIZE;
        return VO_TRUE;
    }
    case VOCTRL_SET_CURSOR_VISIBILITY:
        w32->cursor_visible = *(bool *)arg;

        if (vo_w32_is_cursor_in_client(vo)) {
            if (w32->cursor_visible)
                SetCursor(LoadCursor(NULL, IDC_ARROW));
            else
                SetCursor(NULL);
        }
        return VO_TRUE;
    case VOCTRL_KILL_SCREENSAVER:
        w32->disable_screensaver = true;
        SetThreadExecutionState(ES_CONTINUOUS | ES_DISPLAY_REQUIRED);
        return VO_TRUE;
    case VOCTRL_RESTORE_SCREENSAVER:
        w32->disable_screensaver = false;
        SetThreadExecutionState(ES_CONTINUOUS);
        return VO_TRUE;
    case VOCTRL_UPDATE_WINDOW_TITLE: {
        wchar_t *title = mp_from_utf8(NULL, (char *)arg);
        SetWindowTextW(w32->window, title);
        talloc_free(title);
        return VO_TRUE;
    }
    }
    return VO_NOTIMPL;
}
Esempio n. 6
0
/**
 * \brief Initialize w32_common framework.
 *
 * The first function that should be called from the w32_common framework.
 * It handles window creation on the screen with proper title and attributes.
 * It also initializes the framework's internal variables. The function should
 * be called after your own preinit initialization and you shouldn't do any
 * window management on your own.
 *
 * Global libvo variables changed:
 * vo_w32_window
 * vo_screenwidth
 * vo_screenheight
 *
 * \return 1 = Success, 0 = Failure
 */
int vo_w32_init(struct vo *vo)
{
    assert(!vo->w32);

    struct vo_w32_state *w32 = talloc_zero(vo, struct vo_w32_state);
    vo->w32 = w32;

    HINSTANCE hInstance = GetModuleHandleW(NULL);

    HICON mplayerIcon = LoadIconW(hInstance, L"IDI_ICON1");

    WNDCLASSEXW wcex = {
        .cbSize = sizeof wcex,
        .style = CS_OWNDC | CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW,
        .lpfnWndProc = WndProc,
        .hInstance = hInstance,
        .hIcon = mplayerIcon,
        .hCursor = LoadCursor(NULL, IDC_ARROW),
        .lpszClassName = classname,
        .hIconSm = mplayerIcon,
    };

    if (!RegisterClassExW(&wcex)) {
        MP_ERR(vo, "win32: unable to register window class!\n");
        return 0;
    }

    if (vo->opts->WinID >= 0) {
        RECT r;
        GetClientRect(WIN_ID_TO_HWND(vo->opts->WinID), &r);
        vo->dwidth = r.right; vo->dheight = r.bottom;
        w32->window = CreateWindowExW(WS_EX_NOPARENTNOTIFY, classname,
                                      classname,
                                      WS_CHILD | WS_VISIBLE,
                                      0, 0, vo->dwidth, vo->dheight,
                                      WIN_ID_TO_HWND(vo->opts->WinID),
                                      0, hInstance, vo);
    } else {
        w32->window = CreateWindowExW(0, classname,
                                      classname,
                                      update_style(vo, 0),
                                      CW_USEDEFAULT, 0, 100, 100,
                                      0, 0, hInstance, vo);
    }

    if (!w32->window) {
        MP_ERR(vo, "win32: unable to create window!\n");
        return 0;
    }

    w32->tracking   = FALSE;
    w32->trackEvent = (TRACKMOUSEEVENT){
        .cbSize    = sizeof(TRACKMOUSEEVENT),
        .dwFlags   = TME_LEAVE,
        .hwndTrack = w32->window,
    };

    if (vo->opts->WinID >= 0)
        EnableWindow(w32->window, 0);
    w32->cursor_visible = true;

    // we don't have proper event handling
    vo->wakeup_period = 0.02;

    updateScreenProperties(vo);

    MP_VERBOSE(vo, "win32: running at %dx%d\n",
           vo->opts->screenwidth, vo->opts->screenheight);

    return 1;
}

/**
 * \brief Toogle fullscreen / windowed mode.
 *
 * Should be called on VOCTRL_FULLSCREEN event. The window is
 * always resized during this call, so the rendering context
 * should be reinitialized with the new dimensions.
 * It is unspecified if vo_check_events will create a resize
 * event in addition or not.
 */

static void vo_w32_fullscreen(struct vo *vo)
{
    if (vo->opts->fullscreen != vo->w32->current_fs)
        reinit_window_state(vo);
}

/**
 * \brief Toogle window border attribute.
 *
 * Should be called on VOCTRL_BORDER event.
 */
static void vo_w32_border(struct vo *vo)
{
    vo->opts->border = !vo->opts->border;
    reinit_window_state(vo);
}

/**
 * \brief Toogle window ontop attribute.
 *
 * Should be called on VOCTRL_ONTOP event.
 */
static void vo_w32_ontop(struct vo *vo)
{
    vo->opts->ontop = !vo->opts->ontop;
    reinit_window_state(vo);
}