Exemplo n.º 1
0
static int  AndroidLockSurface(picture_t *picture) {
    picture_sys_t *picsys = picture->p_sys;
    vout_display_sys_t *sys = picsys->sys;
    SurfaceInfo *info;
    uint32_t sw, sh;
    void *surf;

    sw = picture->p[0].i_visible_pitch / picture->p[0].i_pixel_pitch;
    sh = picture->p[0].i_visible_lines;

    picsys->surf = surf = jni_LockAndGetAndroidSurface();
    info = &(picsys->info);

    if (unlikely(!surf)) {
        jni_UnlockAndroidSurface();
        return VLC_EGENERIC;
    }

    if (sys->s_lock)
        sys->s_lock(surf, info, 1);
    else
        sys->s_lock2(surf, info, NULL);

    // For RGB (32 or 16) we need to align on 8 or 4 pixels, 16 pixels for YUV
    int align_pixels = (16 / picture->p[0].i_pixel_pitch) - 1;
    uint32_t aligned_width = (sw + align_pixels) & ~align_pixels;

    if (info->w != aligned_width || info->h != sh) {
        // input size doesn't match the surface size -> request a resize
        jni_SetAndroidSurfaceSize(sw, sh, sys->i_sar_num, sys->i_sar_den);
        sys->s_unlockAndPost(surf);
        jni_UnlockAndroidSurface();
        return VLC_EGENERIC;
    }

    picture->p[0].p_pixels = (uint8_t*)info->bits;
    picture->p[0].i_lines = info->h;
    picture->p[0].i_pitch = picture->p[0].i_pixel_pitch * info->s;

    if (info->format == 0x32315659 /*ANDROID_IMAGE_FORMAT_YV12*/)
        SetupPictureYV12(info, picture);

    return VLC_SUCCESS;
}
Exemplo n.º 2
0
/**
 * Create an Android native window.
 */
static int Open(vout_window_t *wnd, const vout_window_cfg_t *cfg)
{
    vout_window_sys_t *p_sys = malloc(sizeof (*p_sys));
    if (p_sys == NULL)
        return VLC_ENOMEM;

    p_sys->p_library = LoadNativeWindowAPI(&p_sys->native_window);
    if (p_sys->p_library == NULL)
    {
        free(p_sys);
        return VLC_EGENERIC;
    }

    // Create the native window by first getting the Java surface.
    jobject javaSurface = jni_LockAndGetAndroidJavaSurface();
    if (javaSurface == NULL)
        goto error;

    JNIEnv *p_env;
    (*myVm)->AttachCurrentThread(myVm, &p_env, NULL);
    p_sys->window = p_sys->native_window.winFromSurface(p_env, javaSurface); // ANativeWindow_fromSurface call.
    (*myVm)->DetachCurrentThread(myVm);

    jni_UnlockAndroidSurface();

    if (p_sys->window == NULL)
        goto error;

    wnd->handle.anativewindow = p_sys->window;
    wnd->control = Control;
    wnd->sys = p_sys;

    // Set the Java surface size.
    jni_SetAndroidSurfaceSize(cfg->width, cfg->height, cfg->width, cfg->height, 1, 1);

    return VLC_SUCCESS;

error:
    dlclose(p_sys->p_library);
    free(p_sys);
    return VLC_EGENERIC;
}
Exemplo n.º 3
0
/**
 * Window control.
 */
static int Control(vout_window_t *wnd, int cmd, va_list ap)
{
    switch (cmd)
    {
    case VOUT_WINDOW_SET_SIZE:
    {
        unsigned width = va_arg(ap, unsigned);
        unsigned height = va_arg(ap, unsigned);
        jni_SetAndroidSurfaceSize(width, height, width, height, 1, 1);
        break;
    }
    case VOUT_WINDOW_SET_STATE:
    case VOUT_WINDOW_SET_FULLSCREEN:
        return VLC_EGENERIC;
    default:
        msg_Err (wnd, "request %d not implemented", cmd);
        return VLC_EGENERIC;
    }
    return VLC_SUCCESS;
}
Exemplo n.º 4
0
static int  AndroidLockSurface(picture_t *picture) {
    picture_sys_t *picsys = picture->p_sys;
    vout_display_sys_t *sys = picsys->sys;
    SurfaceInfo *info;
    uint32_t sw, sh;
    void *surf;

    sw = picture->p[0].i_visible_pitch / picture->p[0].i_pixel_pitch;
    sh = picture->p[0].i_visible_lines;

    picsys->surf = surf = jni_LockAndGetAndroidSurface();
    info = &(picsys->info);

    if (unlikely(!surf)) {
        jni_UnlockAndroidSurface();
        return VLC_EGENERIC;
    }

    if (sys->s_lock)
        sys->s_lock(surf, info, 1);
    else
        sys->s_lock2(surf, info, NULL);

    // input size doesn't match the surface size,
    // request a resize
    if (info->w != sw || info->h != sh) {
        jni_SetAndroidSurfaceSize(sw, sh, sys->i_sar_num, sys->i_sar_den);
        sys->s_unlockAndPost(surf);
        jni_UnlockAndroidSurface();
        return VLC_EGENERIC;
    }

    picture->p->p_pixels = (uint8_t*)info->bits;
    picture->p->i_pitch = 4 * info->s;
    picture->p->i_lines = info->h;

    return VLC_SUCCESS;
}
Exemplo n.º 5
0
static int  AndroidLockSurface(picture_t *picture)
{
    picture_sys_t *picsys = picture->p_sys;
    vout_display_sys_t *sys = picsys->sys;
    SurfaceInfo *info;
    uint32_t sw, sh;
    void *surf;

    sw = sys->fmt.i_width;
    sh = sys->fmt.i_height;

    if (sys->native_window.winFromSurface) {
        jobject jsurf = jni_LockAndGetAndroidJavaSurface();
        if (unlikely(!jsurf)) {
            jni_UnlockAndroidSurface();
            return VLC_EGENERIC;
        }
        if (sys->window && jsurf != sys->jsurf) {
            sys->native_window.winRelease(sys->window);
            sys->window = NULL;
        }
        sys->jsurf = jsurf;
        if (!sys->window) {
            JNIEnv *p_env;
            (*myVm)->AttachCurrentThread(myVm, &p_env, NULL);
            sys->window = sys->native_window.winFromSurface(p_env, jsurf);
            (*myVm)->DetachCurrentThread(myVm);
        }
        // Using sys->window instead of the native surface object
        // as parameter to the unlock function
        picsys->surf = surf = sys->window;
    } else {
        picsys->surf = surf = jni_LockAndGetAndroidSurface();
        if (unlikely(!surf)) {
            jni_UnlockAndroidSurface();
            return VLC_EGENERIC;
        }
    }
    info = &picsys->info;

    if (sys->native_window.winLock) {
        ANativeWindow_Buffer buf = { 0 };
        sys->native_window.winLock(sys->window, &buf, NULL);
        info->w      = buf.width;
        info->h      = buf.height;
        info->bits   = buf.bits;
        info->s      = buf.stride;
        info->format = buf.format;
    } else if (sys->s_lock)
        sys->s_lock(surf, info, 1);
    else
        sys->s_lock2(surf, info, NULL);

    // For RGB (32 or 16) we need to align on 8 or 4 pixels, 16 pixels for YUV
    int align_pixels = (16 / picture->p[0].i_pixel_pitch) - 1;
    uint32_t aligned_width = (sw + align_pixels) & ~align_pixels;

    if (info->w != aligned_width || info->h != sh || sys->b_changed_crop) {
        // input size doesn't match the surface size -> request a resize
        jni_SetAndroidSurfaceSize(aligned_width, sh, sys->fmt.i_visible_width, sys->fmt.i_visible_height, sys->i_sar_num, sys->i_sar_den);
        // When using ANativeWindow, one should use ANativeWindow_setBuffersGeometry
        // to set the size and format. In our case, these are set via the SurfaceHolder
        // in Java, so we seem to manage without calling this ANativeWindow function.
        sys->s_unlockAndPost(surf);
        jni_UnlockAndroidSurface();
        sys->b_changed_crop = false;
        return VLC_EGENERIC;
    }

    picture->p[0].p_pixels = (uint8_t*)info->bits;
    picture->p[0].i_lines = info->h;
    picture->p[0].i_pitch = picture->p[0].i_pixel_pitch * info->s;

    if (info->format == 0x32315659 /*ANDROID_IMAGE_FORMAT_YV12*/)
        SetupPictureYV12(info, picture);

    return VLC_SUCCESS;
}