Add rotation of spatial audio (first order ambisonics) 28/153028/3
authorMykola Alieksieiev <m.alieksieie@samsung.com>
Wed, 27 Sep 2017 15:55:48 +0000 (18:55 +0300)
committerMykola Alieksieiev <m.alieksieie@samsung.com>
Fri, 29 Sep 2017 08:39:19 +0000 (11:39 +0300)
Change-Id: I11d28fa80d652411233a0a631af482620196b0fd
Signed-off-by: Mykola Alieksieiev <m.alieksieie@samsung.com>
ext/openal/Makefile.am
ext/openal/gstopenalsink.c
ext/openal/gstopenalsink.h
packaging/gst-plugins-bad.spec

index c42c31e..9022336 100644 (file)
@@ -7,7 +7,7 @@ libgstopenal_la_SOURCES = gstopenal.c gstopenalsink.c gstopenalsrc.c
 
 # compiler and linker flags used to compile this plugin, set in configure.ac
 libgstopenal_la_CFLAGS = $(GST_PLUGINS_BASE_CFLAGS) $(GST_BASE_CFLAGS) $(GST_CFLAGS) $(OPENAL_CFLAGS) $(GST_PLUGINS_BAD_CFLAGS)
-libgstopenal_la_LIBADD = $(GST_PLUGINS_BASE_LIBS) -lgstaudio-@GST_API_VERSION@ $(GST_BASE_LIBS) $(GST_LIBS) $(OPENAL_LIBS)
+libgstopenal_la_LIBADD = $(GST_PLUGINS_BASE_LIBS) -lgstaudio-@GST_API_VERSION@ -lgstvideo-@GST_API_VERSION@ $(GST_BASE_LIBS) $(GST_LIBS) $(OPENAL_LIBS)
 libgstopenal_la_LDFLAGS = $(GST_PLUGIN_LDFLAGS)
 libgstopenal_la_LIBTOOLFLAGS = $(GST_PLUGIN_LIBTOOLFLAGS)
 
index 1fa1c65..a9b2b13 100644 (file)
 #include "config.h"
 #endif
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+#include <math.h>
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
 #include <gst/gst.h>
 #include <gst/gsterror.h>
 
@@ -82,6 +86,17 @@ static gint gst_openal_sink_write (GstAudioSink * audiosink, gpointer data,
 static guint gst_openal_sink_delay (GstAudioSink * audiosink);
 static void gst_openal_sink_reset (GstAudioSink * audiosink);
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+void set_angles (GstElement * element, float absolute_angle_x,
+    float absolute_angle_y, float absolute_angle_z);
+void apply_rotation (GstElement * element, float rotation_x, float rotation_y,
+    float rotation_z);
+static gboolean gst_openal_sink_src_event (GstElement * element,
+    GstEvent * event);
+
+gfloat source_rotation_y_old = 0;
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
 #define OPENAL_DEFAULT_DEVICE NULL
 
 #define OPENAL_MIN_RATE 8000
@@ -96,9 +111,56 @@ enum
 
   PROP_USER_DEVICE,
   PROP_USER_CONTEXT,
+#ifndef TIZEN_FEATURE_OALSINK_MODIFICATION
   PROP_USER_SOURCE
+#else
+  PROP_USER_SOURCE,
+
+  PROP_USE_STREAM_INFO,
+  PROP_STREAM_INFO,
+
+  PROP_SOURCE_ORIENTATION_X_AXIS,
+  PROP_SOURCE_ORIENTATION_Y_AXIS,
+  PROP_SOURCE_ORIENTATION_Z_AXIS,
+
+  PROP_SOURCE_AMBISONIC_TYPE
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
 };
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+/* Register GTtypes for custom enums */
+#define GST_TYPE_AMBISONICS_TYPE (gst_openalsink_ambisonicstype_get_type ())
+
+static GType
+gst_openalsink_ambisonicstype_get_type (void)
+{
+  static GType ambisonics_type = 0;
+
+  if (!ambisonics_type) {
+    static GEnumValue ambisonics_types[] = {
+      { AMBISONICS_TYPE_UNKNOWN, "Ambisonics type is not determined", "unknown" },
+      { AMBISONICS_TYPE_PERIPHONIC, "Periphonic ambisonics", "periphonic" },
+      { AMBISONICS_TYPE_NON_PERIPHONIC, "Non-periphonic ambisonics", "non-periphonic" },
+      { 0, NULL, NULL },
+    };
+
+    ambisonics_type =
+      g_enum_register_static ("GstOpenalsinkAmbisonicsType", ambisonics_types);
+  }
+
+  return ambisonics_type;
+}
+
+enum
+{
+  /* action signals */
+  ROTATE,
+  /* emit signals */
+  LAST_SIGNAL
+};
+static guint openalsink_signals[LAST_SIGNAL];
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
 static GstStaticPadTemplate openalsink_factory =
     GST_STATIC_PAD_TEMPLATE ("sink",
     GST_PAD_SINK,
@@ -110,15 +172,7 @@ static GstStaticPadTemplate openalsink_factory =
         "audio/x-raw, " "format = (string) " GST_AUDIO_NE (S16) ", "
         "rate = (int) [ 1, MAX ], " "channels = (int) [ 1, MAX ]; "
         "audio/x-raw, " "format = (string) " G_STRINGIFY (U8) ", "
-        "rate = (int) [ 1, MAX ], " "channels = (int) [ 1, MAX ]; "
-        /* These caps do not work on my card */
-        // "audio/x-adpcm, " "layout = (string) ima, "
-        // "rate = (int) [ 1, MAX ], " "channels = (int) [ 1, 2 ]; "
-        // "audio/x-alaw, " "rate = (int) [ 1, MAX ], "
-        // "channels = (int) [ 1, 2 ]; "
-        // "audio/x-mulaw, " "rate = (int) [ 1, MAX ], "
-        // "channels = (int) [ 1, MAX ]"
-    )
+        "rate = (int) [ 1, MAX ], " "channels = (int) [ 1, MAX ]; ")
     );
 
 static PFNALCSETTHREADCONTEXTPROC palcSetThreadContext;
@@ -185,6 +239,12 @@ gst_openal_sink_class_init (GstOpenALSinkClass * klass)
     palcGetThreadContext = alcGetProcAddress (NULL, "alcGetThreadContext");
   }
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  klass->rotate = set_angles;
+
+  gstelement_class->send_event = GST_DEBUG_FUNCPTR (gst_openal_sink_src_event);
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
   gobject_class->dispose = GST_DEBUG_FUNCPTR (gst_openal_sink_dispose);
   gobject_class->finalize = GST_DEBUG_FUNCPTR (gst_openal_sink_finalize);
   gobject_class->set_property =
@@ -225,6 +285,44 @@ gst_openal_sink_class_init (GstOpenALSinkClass * klass)
       g_param_spec_uint ("user-source", "ALsource", "User source", 0, UINT_MAX,
           0, G_PARAM_READWRITE));
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  g_object_class_install_property (gobject_class, PROP_USE_STREAM_INFO,
+      g_param_spec_uint ("use-stream-info", "UseTizenAudioStreamInfo",
+          "Option to use stream info (0 | 1)", 0, 1, 0, G_PARAM_READWRITE));
+
+  g_object_class_install_property (gobject_class, PROP_STREAM_INFO,
+      g_param_spec_pointer ("stream-info", "TizenAudioStreamInfo", "Stream info",
+          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
+
+  g_object_class_install_property (gobject_class, PROP_SOURCE_AMBISONIC_TYPE,
+      g_param_spec_enum ("source-ambisonics-type", "ALsourceAmbisonicType",
+          "Type of Ambisonics (Unknown | Periphonic | Non-periphonic)",
+          GST_TYPE_AMBISONICS_TYPE, AMBISONICS_TYPE_UNKNOWN,
+          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
+
+  g_object_class_install_property (gobject_class, PROP_SOURCE_ORIENTATION_X_AXIS,
+      g_param_spec_int ("source-orientation-x", "ALSourceOrientationX",
+          "Source orientation (rotation angle) against X axis, deg.", -90, 90,
+          0, G_PARAM_READWRITE));
+
+  g_object_class_install_property (gobject_class, PROP_SOURCE_ORIENTATION_Y_AXIS,
+      g_param_spec_int ("source-orientation-y", "ALSourceOrientationY",
+          "Source orientation (rotation angle) against Y axis, deg.", -180, 180,
+          0, G_PARAM_READWRITE));
+
+  g_object_class_install_property (gobject_class, PROP_SOURCE_ORIENTATION_Z_AXIS,
+      g_param_spec_int ("source-orientation-z", "ALSourceOrientationZ",
+          "Source orientation (rotation angle) against Z axis, deg.", -180, 180,
+          0, G_PARAM_READWRITE));
+
+  openalsink_signals[ROTATE] =
+      g_signal_new ("rotate",
+      G_TYPE_FROM_CLASS (klass),
+      G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
+      G_STRUCT_OFFSET (GstOpenALSinkClass, rotate), NULL, NULL, NULL,
+          G_TYPE_NONE, 3, G_TYPE_FLOAT, G_TYPE_FLOAT, G_TYPE_FLOAT);
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
   gst_element_class_set_static_metadata (gstelement_class, "OpenAL Audio Sink",
       "Sink/Audio", "Output audio through OpenAL",
       "Juan Manuel Borges CaƱo <juanmabcmail@gmail.com>");
@@ -257,6 +355,16 @@ gst_openal_sink_init (GstOpenALSink * sink)
   sink->write_reset = AL_FALSE;
   sink->probed_caps = NULL;
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  sink->use_stream_info = 0;
+  sink->stream_info = NULL;
+
+  sink->ambisonic_type = AMBISONICS_TYPE_UNKNOWN;
+  sink->source_rotation_x = 0.f;
+  sink->source_rotation_y = 0.f;
+  sink->source_rotation_z = 0.f;
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
   g_mutex_init (&sink->openal_lock);
 }
 
@@ -299,6 +407,29 @@ gst_openal_sink_set_property (GObject * object, guint prop_id,
         sink->user_source = g_value_get_uint (value);
       break;
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+    case PROP_USE_STREAM_INFO:
+      sink->use_stream_info = g_value_get_uint (value);
+      break;
+    case PROP_STREAM_INFO:
+      if (!sink->stream_info)
+        sink->stream_info = g_value_get_pointer (value);
+      break;
+    case PROP_SOURCE_AMBISONIC_TYPE:
+      sink->ambisonic_type = g_value_get_enum (value);
+      GST_DEBUG_OBJECT (sink, "sink->user_source %d", sink->user_source);
+      break;
+    case PROP_SOURCE_ORIENTATION_X_AXIS:
+      sink->source_rotation_x = (ALfloat)g_value_get_int (value) / 180 * M_PI;
+      break;
+    case PROP_SOURCE_ORIENTATION_Y_AXIS:
+      sink->source_rotation_y = (ALfloat)g_value_get_int (value) / 180 * M_PI;
+      break;
+    case PROP_SOURCE_ORIENTATION_Z_AXIS:
+      sink->source_rotation_z = (ALfloat)g_value_get_int (value) / 180 * M_PI;
+      break;
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -315,6 +446,10 @@ gst_openal_sink_get_property (GObject * object, guint prop_id, GValue * value,
   ALCcontext *context = sink->default_context;
   ALuint source = sink->default_source;
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  sound_stream_info_h stream_info = sink->stream_info;
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
   switch (prop_id) {
     case PROP_DEVICE_NAME:
       device_name = "";
@@ -340,6 +475,29 @@ gst_openal_sink_get_property (GObject * object, guint prop_id, GValue * value,
       g_value_set_uint (value, source);
       break;
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+    case PROP_USE_STREAM_INFO:
+      g_value_set_uint (value, sink->use_stream_info);
+      break;
+    case PROP_STREAM_INFO:
+      if (!stream_info)
+        stream_info = sink->stream_info;
+      g_value_set_pointer (value, stream_info);
+      break;
+    case PROP_SOURCE_AMBISONIC_TYPE:
+      g_value_set_enum (value, sink->ambisonic_type);
+      break;
+    case PROP_SOURCE_ORIENTATION_X_AXIS:
+      g_value_set_int (value, (int)(sink->source_rotation_x / M_PI * 180));
+      break;
+    case PROP_SOURCE_ORIENTATION_Y_AXIS:
+      g_value_set_int (value, (int)(sink->source_rotation_y / M_PI * 180));
+      break;
+    case PROP_SOURCE_ORIENTATION_Z_AXIS:
+      g_value_set_int (value, (int)(sink->source_rotation_z / M_PI * 180));
+      break;
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -517,6 +675,24 @@ gst_openal_helper_probe_caps (ALCcontext * context)
     gst_caps_append_structure (caps, structure);
   }
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  if (alIsExtensionPresent ("AL_EXT_BFORMAT")) {
+    guint64 channel_mask = GST_AUDIO_CHANNEL_POSITION_MASK (FRONT_LEFT) |
+        GST_AUDIO_CHANNEL_POSITION_MASK (FRONT_RIGHT) |
+        GST_AUDIO_CHANNEL_POSITION_MASK (FRONT_CENTER) |
+        GST_AUDIO_CHANNEL_POSITION_MASK (REAR_CENTER);
+
+    structure =
+        gst_structure_new ("audio/x-raw",
+        "format", G_TYPE_STRING, GST_AUDIO_NE (S16),
+        "rate", GST_TYPE_INT_RANGE, OPENAL_MIN_RATE, OPENAL_MAX_RATE,
+        "channels", G_TYPE_INT, 4, NULL);
+    gst_structure_set (structure, "channel-mask", GST_TYPE_BITMASK,
+        channel_mask, NULL);
+    gst_caps_append_structure (caps, structure);
+  }
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
   if (alIsExtensionPresent ("AL_EXT_ALAW")) {
     structure =
         gst_structure_new ("audio/x-alaw", "rate", GST_TYPE_INT_RANGE,
@@ -628,8 +804,27 @@ gst_openal_sink_open (GstAudioSink * audiosink)
     }
   } else if (sink->user_context)
     sink->default_device = alcGetContextsDevice (sink->user_context);
+
+#ifndef TIZEN_FEATURE_OALSINK_MODIFICATION
   else
     sink->default_device = alcOpenDevice (sink->device_name);
+#else /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+  else {
+    if (sink->use_stream_info) {
+      GST_DEBUG_OBJECT (sink, "The Tizen Stream Policy API is used.");
+      if (!sink->stream_info) {
+        GST_ELEMENT_ERROR (sink, RESOURCE, FAILED,
+          ("Unable to process stream info."), GST_ALC_ERROR (sink->default_device));
+        return FALSE;
+      }
+      sink->default_device = alcOpenDeviceNew (sink->device_name, sink->stream_info);
+    } else {
+      GST_DEBUG_OBJECT (sink, "The Tizen Stream Policy API is not used.");
+        sink->default_device = alcOpenDevice (sink->device_name);
+    }
+  }
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
   if (!sink->default_device) {
     GST_ELEMENT_ERROR (sink, RESOURCE, OPEN_WRITE,
         ("Could not open device."), GST_ALC_ERROR (sink->default_device));
@@ -711,6 +906,10 @@ gst_openal_sink_parse_spec (GstOpenALSink * sink,
               break;
             case 4:
               format = AL_FORMAT_QUAD16;
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+              if (sink->ambisonic_type == 1)
+                format = AL_FORMAT_BFORMAT3D_16;        /*FIXME (m.alieskieie): Implement B-format support in more extended way */
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
               break;
             case 6:
               format = AL_FORMAT_51CHN16;
@@ -967,11 +1166,34 @@ gst_openal_sink_write (GstAudioSink * audiosink, gpointer data, guint length)
   ALint processed, queued, state;
   ALCcontext *old;
   gulong rest_us;
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  ALfloat sourceOri[] = { 0.0, 0.0, -1.0, 0.0, 1.0, 0.0 };
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
 
   g_assert (length == sink->buffer_length);
 
   old = pushContext (sink->default_context);
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  if (sink->ambisonic_type == 1) {
+    sink->format = AL_FORMAT_BFORMAT3D_16;
+    if (sink->source_rotation_y != source_rotation_y_old) {
+      /* FIXME (m.alieskieie): Implement more appropriate
+         Euler angles -> AL Source orientation transform algorithm */
+      sourceOri[0] = (-1) * sin (sink->source_rotation_y);
+      sourceOri[2] = (-1) * cos (sink->source_rotation_y);
+      GST_DEBUG_OBJECT (sink,
+          "Source_rotation_y = %g    atx = %g    atz = %g\n",
+          sink->source_rotation_y, sourceOri[0], sourceOri[2]);
+      alSourcefv (sink->default_source, AL_ORIENTATION, sourceOri);
+      if (alGetError () != AL_NO_ERROR)
+        GST_ELEMENT_ERROR (sink, RESOURCE, WRITE, (NULL),
+            ("Failed to set Source's orientation"));
+      source_rotation_y_old = sink->source_rotation_y;
+    }
+  }
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
   rest_us =
       (guint64) (sink->buffer_length / sink->bytes_per_sample) *
       G_USEC_PER_SEC / sink->rate / sink->channels;
@@ -1094,3 +1316,72 @@ gst_openal_sink_reset (GstAudioSink * audiosink)
   popContext (old, sink->default_context);
   GST_OPENAL_SINK_UNLOCK (sink);
 }
+
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+void
+set_angles (GstElement * element, float abs_angle_x, float abs_angle_y,
+    float abs_angle_z)
+{
+  GstOpenALSink *sink = GST_OPENAL_SINK (element);
+  sink->source_rotation_x = abs_angle_x;
+  sink->source_rotation_y = abs_angle_y;
+  sink->source_rotation_z = abs_angle_z;
+  GST_DEBUG_OBJECT (sink, "\nAbsolute angles have been set directly:\n"
+      "x = %g (%g deg.)\n"
+      "y = %g (%g deg.)\n"
+      "z = %g (%g deg.)",
+      sink->source_rotation_x, sink->source_rotation_x / M_PI * 180,
+      sink->source_rotation_y, sink->source_rotation_y / M_PI * 180,
+      sink->source_rotation_z, sink->source_rotation_z / M_PI * 180);
+}
+
+void
+apply_rotation (GstElement * element, float rotation_x, float rotation_y,
+    float rotation_z)
+{
+  GstOpenALSink *sink = GST_OPENAL_SINK (element);
+  sink->source_rotation_x += rotation_x;
+  sink->source_rotation_y += rotation_y;
+  sink->source_rotation_z += rotation_z;
+
+  GST_DEBUG_OBJECT (sink, "\nAbsolute angles have been changed to:\n"
+      "x = %g (%g deg.)    delta = %g (%g deg.)\n"
+      "y = %g (%g deg.)    delta = %g (%g deg.)\n"
+      "z = %g (%g deg.)    delta = %g (%g deg.)",
+      sink->source_rotation_x, sink->source_rotation_x / M_PI * 180,
+      rotation_x, rotation_x / M_PI * 180,
+      sink->source_rotation_y, sink->source_rotation_y / M_PI * 180,
+      rotation_y, rotation_y / M_PI * 180,
+      sink->source_rotation_z, sink->source_rotation_z / M_PI * 180,
+      rotation_z, rotation_z / M_PI * 180);
+}
+
+static gboolean
+gst_openal_sink_src_event (GstElement * element, GstEvent * event)
+{
+  GstOpenALSink *sink = GST_OPENAL_SINK (element);
+  gdouble x = 0, y = 0;
+  gdouble dx = 0, dy = 0;
+  gdouble yaw, pitch, roll;
+
+
+  if (GST_EVENT_TYPE (event) == GST_EVENT_NAVIGATION) {
+    if (gst_navigation_event_get_type (event) == GST_NAVIGATION_EVENT_MOUSE_MOVE) {
+      GstStructure *structure = (GstStructure *) gst_event_get_structure (event);
+      if (gst_structure_get_double (structure, "yaw", &yaw) &&
+          gst_structure_get_double (structure, "pitch", &pitch) &&
+          gst_structure_get_double (structure, "roll", &roll)) {
+
+          GST_DEBUG_OBJECT (sink, "yaw   = %g (%g deg.)\n", yaw, yaw / M_PI * 180);
+          GST_DEBUG_OBJECT (sink, "pitch = %g (%g deg.)\n", pitch, pitch / M_PI * 180);
+          GST_DEBUG_OBJECT (sink, "roll  = %g (%g deg.)\n", roll, roll / M_PI * 180);
+
+          set_angles(element, pitch, yaw, -roll);
+      }
+    }
+  }
+
+  return GST_ELEMENT_CLASS (gst_openal_sink_parent_class)->send_event (element,
+      event);
+}
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
index 6088251..4fddf39 100644 (file)
 #include <gst/gst.h>
 #include <gst/audio/audio.h>
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+#include <gst/video/navigation.h>
+#include <sound_manager.h>
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
 #ifdef _WIN32
 #include <al.h>
 #include <alc.h>
@@ -70,6 +75,14 @@ typedef struct _GstOpenALSinkClass GstOpenALSinkClass;
 #define GST_OPENAL_SINK_LOCK(obj)     (g_mutex_lock(GST_OPENAL_SINK_GET_LOCK(obj)))
 #define GST_OPENAL_SINK_UNLOCK(obj)   (g_mutex_unlock(GST_OPENAL_SINK_GET_LOCK(obj)))
 
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+typedef enum {
+  AMBISONICS_TYPE_UNKNOWN = 0,
+  AMBISONICS_TYPE_PERIPHONIC = 1,        /**< To comply with Google's Spatial Audio RFC*/
+  AMBISONICS_TYPE_NON_PERIPHONIC = 2,
+} AmbisonicsType;
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
 struct _GstOpenALSink
 {
   GstAudioSink sink;
@@ -103,11 +116,29 @@ struct _GstOpenALSink
   GstCaps *probed_caps;
 
   GMutex openal_lock;
+
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  ALuint use_stream_info;
+  sound_stream_info_h stream_info;
+
+  AmbisonicsType ambisonic_type;
+  ALfloat source_rotation_x;
+  ALfloat source_rotation_y;
+  ALfloat source_rotation_z;
+
+  gulong signal_id;
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
+
 };
 
 struct _GstOpenALSinkClass
 {
   GstAudioSinkClass parent_class;
+
+#ifdef TIZEN_FEATURE_OALSINK_MODIFICATION
+  void (*rotate) (GstElement * element, float rotation_x, float rotation_y, float rotation_z);
+  void (*event) (GstElement * element, GstEvent * event);
+#endif /* TIZEN_FEATURE_OALSINK_MODIFICATION */
 };
 
 GType gst_openal_sink_get_type (void);
index 0682ff0..d1ab245 100644 (file)
@@ -41,6 +41,7 @@ BuildRequires:  pkgconfig(wayland-egl) >= 9.0
 BuildRequires:  pkgconfig(wayland-client) >= 1.0.0
 BuildRequires:  pkgconfig(wayland-cursor) >= 1.0.0
 BuildRequires:  pkgconfig(wayland-tbm-client)
+BuildRequires:  pkgconfig(openal)
 BuildRequires:  pkgconfig(tizen-extension-client)
 BuildRequires:  pkgconfig(libxml-2.0)
 %endif
@@ -83,6 +84,7 @@ export CFLAGS+=" -Wall -g -fPIC\
   -DTIZEN_FEATURE_AVOID_PAD_SWITCHING\
   -DTIZEN_FEATURE_ADAPTIVE_MODIFICATION\
   -DTIZEN_FEATURE_TSDEMUX_MODIFICATION\
+  -DTIZEN_FEATURE_OALSINK_MODIFICATION\
   -DTIZEN_FEATURE_UPSTREAM"
 
 %configure\
@@ -168,6 +170,7 @@ export CFLAGS+=" -Wall -g -fPIC\
        --enable-wayland=yes\
        --enable-gles2=yes\
        --disable-glx\
+       --enable-openal=yes\
        --disable-sndfile\
        --disable-gtk-doc\
        --disable-warnings-as-errors\
@@ -275,6 +278,7 @@ rm -rf $RPM_BUILD_ROOT
 %{_libdir}/libgstwayland-%{gst_branch}.so.0*
 %{_libdir}/gstreamer-%{gst_branch}/libgstwaylandsink.so
 %endif
+%{_libdir}/gstreamer-%{gst_branch}/libgstopenal.so
 
 %{_libdir}/libgstcodecparsers-%{gst_branch}.so.0*
 %{_libdir}/libgstmpegts-%{gst_branch}.so.0*