1/* 2 * GStreamer 3 * Copyright (C) 2015 Matthew Waters <matthew@centricular.com> 4 * 5 * This library is free software; you can redistribute it and/or 6 * modify it under the terms of the GNU Library General Public 7 * License as published by the Free Software Foundation; either 8 * version 2 of the License, or (at your option) any later version. 9 * 10 * This library is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 * Library General Public License for more details. 14 * 15 * You should have received a copy of the GNU Library General Public 16 * License along with this library; if not, write to the 17 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, 18 * Boston, MA 02110-1301, USA. 19 */ 20 21#include <gst/gst.h> 22 23#include <Cocoa/Cocoa.h> 24#include <QuartzCore/QuartzCore.h> 25#include <CoreFoundation/CoreFoundation.h> 26#include <CoreMedia/CoreMedia.h> 27 28#if MAC_OS_X_VERSION_MAX_ALLOWED < 101200 29#define NSWindowStyleMaskBorderless NSBorderlessWindowMask 30#endif 31 32static NSRunLoop *loop; 33static int quit = 0; 34 35static void 36end_stream_cb(GstBus* bus, GstMessage* message, GstElement* pipeline) 37{ 38 switch (GST_MESSAGE_TYPE (message)) 39 { 40 case GST_MESSAGE_EOS: 41 g_print ("End of stream\n"); 42 43 g_atomic_int_set (&quit, 1);; 44 CFRunLoopStop ([loop getCFRunLoop]); 45 break; 46 case GST_MESSAGE_ERROR: 47 { 48 gchar *debug = NULL; 49 GError *err = NULL; 50 51 gst_message_parse_error (message, &err, &debug); 52 53 g_print ("Error: %s\n", err->message); 54 g_error_free (err); 55 56 if (debug) 57 { 58 g_print ("Debug details: %s\n", debug); 59 g_free (debug); 60 } 61 62 g_atomic_int_set (&quit, 1);; 63 CFRunLoopStop ([loop getCFRunLoop]); 64 break; 65 } 66 default: 67 break; 68 } 69} 70 71gint main (gint argc, gchar *argv[]) 72{ 73 CALayer *layer; 74 loop = [NSRunLoop currentRunLoop]; 75 76 gst_init (&argc, &argv); 77 78 [NSApplication sharedApplication]; 79 80 GstElement* pipeline = gst_pipeline_new ("pipeline"); 81 GstElement* videosrc = gst_element_factory_make ("videotestsrc", NULL); 82 GstElement* videosink = gst_element_factory_make ("avsamplebufferlayersink", NULL); 83 GstCaps *caps = gst_caps_from_string ("video/x-raw,format=UYVY"); 84 85 gst_bin_add_many (GST_BIN (pipeline), videosrc, videosink, NULL); 86 87 gboolean link_ok = gst_element_link_filtered (videosrc, videosink, caps); 88 gst_caps_unref (caps); 89 if (!link_ok) { 90 g_critical ("Failed to link an element!\n") ; 91 return -1; 92 } 93 94 g_object_set (videosrc, "num-buffers", 500, NULL); 95 96 GstBus* bus = gst_pipeline_get_bus (GST_PIPELINE (pipeline)); 97 98 gst_element_set_state (pipeline, GST_STATE_READY); 99 gst_element_get_state (pipeline, NULL, NULL, GST_CLOCK_TIME_NONE); 100 101 g_object_get (videosink, "layer", &layer, NULL); 102 103 NSWindow *window = [[NSWindow alloc] initWithContentRect:NSMakeRect (0, 0, 320, 240) 104 styleMask:NSWindowStyleMaskBorderless backing:NSBackingStoreBuffered defer:NO]; 105 [window setOpaque:NO]; 106 [window.contentView setWantsLayer:YES]; 107 108 NSView *view = [window.contentView superview]; 109 [view setLayer:layer]; 110 111 gst_element_set_state(pipeline, GST_STATE_PLAYING); 112 113 [window orderFront:window]; 114 115 while (!g_atomic_int_get (&quit) && [loop runMode:NSDefaultRunLoopMode 116 beforeDate:[NSDate distantPast]]) { 117 GstMessage *msg; 118 while ((msg = gst_bus_timed_pop (bus, 1 * GST_MSECOND))) 119 end_stream_cb (bus, msg, pipeline); 120 } 121 122 gst_element_set_state (pipeline, GST_STATE_NULL); 123 gst_object_unref (bus); 124 gst_object_unref (pipeline); 125 126 return 0; 127} 128 129