使用gstvideooverlay在用户创建的wayland表面上渲染视频

时间:2016-08-14 21:52:35

标签: arm gstreamer wayland

我正在尝试在自己创建的Wayland曲面上播放视频文件但渲染没有发生。我参考了 https://gstreamer.freedesktop.org/data/doc/gstreamer/head/gst-plugins-base-libs/html/gst-plugins-base-libs-gstvideooverlay.htmlhttps://git.collabora.com/cgit/user/gkiagia/gst-wayland-gtk-demo.git/tree/main.c

创建管道后(filesrc-> parser-> decoder-> waylandsink);我将bus_set_sync_handler设置为

    gst_bus_set_sync_handler (bus, (GstBusSyncHandler) create_window_own,
        gstreamerData.pipeline, NULL);

create_window_own的实现在

之下
static GstBusSyncReply create_window_own (GstBus * bus, GstMessage * message, GstPipeline * pipeline)

{

if (counter == 0)
{
    display = wl_display_connect(NULL);

    if (display == NULL)
    {
        fprintf(stderr, "Can't connect to display\n");
        exit(1);
    }
    printf("connected to display\n");

    struct wl_registry *registry = wl_display_get_registry(display);
    wl_registry_add_listener(registry, &registry_listener, NULL);

    wl_display_dispatch(display);
    wl_display_roundtrip(display);

    if (compositor == NULL) {
        fprintf(stderr, "Can't find compositor\n");
        exit(1);
    } else {
        fprintf(stderr, "Found compositor\n");
    }

    surface = wl_compositor_create_surface(compositor);
    if (surface == NULL) {
        fprintf(stderr, "Can't create surface\n");
        exit(1);
    } else {
        fprintf(stderr, "Created surface\n");
    }


    shell_surface = wl_shell_get_shell_surface(shell, surface);
    if (shell_surface == NULL) {
        fprintf(stderr, "Can't create shell surface\n");
        exit(1);
    } else {
        fprintf(stderr, "Created shell surface\n");
    }
    wl_shell_surface_set_toplevel(shell_surface);

    wl_shell_surface_add_listener(shell_surface,
            &shell_surface_listener, NULL);

    create_window();
    //paint_pixels();

    wl_surface_attach(surface, buffer, 0, 0);
    //wl_surface_attach(surface, NULL, 0, 0);
    //wl_surface_damage(surface, 0, 0, WIDTH, HEIGHT);
    //wl_surface_commit(surface);
    printf("Before Thread\n");
    pthread_create(&tid, NULL, myThreadFun, (void*)display);
    printf("After Thread\n");

    counter = 1;
}
if (gst_is_wayland_display_handle_need_context_message (message)) {
    if (display != 0) {
        GstContext *context;
        printf("getting context\n");
        context = gst_wayland_display_handle_context_new (display);
        gst_element_set_context(GST_ELEMENT (GST_MESSAGE_SRC (message)), context);

        /* HACK save the pointer to the sink (which implements GstWaylandVideo)
         * from this point. Unfortunately, d->overlay can also be the playbin
         * instead of waylandsink */
        wlvideo = GST_WAYLAND_VIDEO (GST_MESSAGE_SRC (message));
    } else {
        g_warning ("Should have obtained display_handle by now!\n");
    }

    gst_message_unref (message);
    return GST_BUS_DROP;
} else if (gst_is_video_overlay_prepare_window_handle_message (message)) {
    if (surface != 0) {
        /* GST_MESSAGE_SRC (message) will be the overlay object that we have to
         * use. This may be waylandsink, but it may also be playbin. In the latter
         * case, we must make sure to use playbin instead of waylandsink, because
         * playbin resets the window handle and render_rectangle after restarting
         * playback and the actual window size is lost */
        overlay = GST_VIDEO_OVERLAY (GST_MESSAGE_SRC (message));
        /*
           g_print ("setting window handle and size (%d x %d)\n",
           d->video_widget_allocation.width, d->video_widget_allocation.height);
         */
        gst_video_overlay_set_window_handle (overlay, (guintptr) surface);
        if (wlvideo && overlay ) {
            gst_wayland_video_begin_geometry_change (wlvideo);
            printf("setting rendrer rectangle\n");
            gst_video_overlay_set_render_rectangle (overlay,
                    0, 0,
                    800, 480);
        } else {
            g_warning ("Should have obtained surface by now!\n");
        }

        gst_message_unref (message);
        return GST_BUS_DROP;
    }
}


printf("+++ret\n");
return GST_BUS_PASS;

}

1 个答案:

答案 0 :(得分:0)

在创建窗口后设置

wl_shell_surface_set_fullscreen(shell_surface,
                                WL_SHELL_SURFACE_FULLSCREEN_METHOD_DEFAULT,
                                0, NULL);