[vlc-devel] [PATCH 15/16] pulse: handle AUDIO_CHANNELS_TYPE_AMBISONICS

Rémi Denis-Courmont remi at remlab.net
Fri Jul 7 17:16:24 CEST 2017


Le 7 juillet 2017 17:03:01 GMT+03:00, Thomas Guillem <thomas at gllm.fr> a écrit :
>---
>modules/audio_output/pulse.c | 90
>+++++++++++++++++++++++++++++++++++++++++++-
> 1 file changed, 89 insertions(+), 1 deletion(-)
>
>diff --git a/modules/audio_output/pulse.c
>b/modules/audio_output/pulse.c
>index ac1254c8b9..ccec8df8f4 100644
>--- a/modules/audio_output/pulse.c
>+++ b/modules/audio_output/pulse.c
>@@ -74,6 +74,10 @@ struct aout_sys_t
>pa_stream_flags_t flags_force; /**< Forced flags (stream must be NULL)
>*/
>     char *sink_force; /**< Forced sink name (stream must be NULL) */
> 
>+    vlc_fourcc_t fourcc;
>+    uint8_t chans_table[AOUT_CHAN_MAX];
>+    uint8_t chans_to_reorder;
>+
>     struct sink *sinks; /**< Locally-cached list of sinks */
> };
> 
>@@ -490,6 +494,11 @@ static void Play(audio_output_t *aout, block_t
>*block)
>     aout_sys_t *sys = aout->sys;
>     pa_stream *s = sys->stream;
> 
>+    if (sys->chans_to_reorder)
>+        aout_ChannelReorder(block->p_buffer, block->i_buffer,
>+                            sys->chans_to_reorder, sys->chans_table,
>+                            sys->fourcc);
>+
>     const void *ptr = data_convert(&block);
>     if (unlikely(ptr == NULL))
>         return;
>@@ -687,6 +696,36 @@ static const char *str_map(const char *key, const
>char *const table[][2],
>      return (r != NULL) ? r[1] : NULL;
> }
> 
>+static int channel_map_pulse_to_vlc(pa_channel_position_t map)
>+{
>+    static_assert(AOUT_CHAN_MAX == 9, "Missing channels");
>+
>+    switch (map)
>+    {
>+        case PA_CHANNEL_POSITION_FRONT_LEFT:
>+            return AOUT_CHAN_LEFT;
>+        case PA_CHANNEL_POSITION_FRONT_RIGHT:
>+            return AOUT_CHAN_RIGHT;
>+        case PA_CHANNEL_POSITION_SIDE_LEFT:
>+            return AOUT_CHAN_MIDDLELEFT;
>+        case PA_CHANNEL_POSITION_SIDE_RIGHT:
>+            return AOUT_CHAN_MIDDLERIGHT;
>+        case PA_CHANNEL_POSITION_REAR_LEFT:
>+            return AOUT_CHAN_REARLEFT;
>+        case PA_CHANNEL_POSITION_REAR_RIGHT:
>+            return AOUT_CHAN_REARRIGHT;
>+        case PA_CHANNEL_POSITION_REAR_CENTER:
>+            return AOUT_CHAN_REARCENTER;
>+        case PA_CHANNEL_POSITION_LFE:
>+            return AOUT_CHAN_LFE;
>+        case PA_CHANNEL_POSITION_MONO:
>+        case PA_CHANNEL_POSITION_FRONT_CENTER:
>+            return AOUT_CHAN_CENTER;
>+        default:
>+            return 0;
>+    }
>+}
>+
> /**
>  * Create a PulseAudio playback stream, a.k.a. a sink input.
>  */
>@@ -804,6 +843,7 @@ static int Start(audio_output_t *aout,
>audio_sample_format_t *restrict fmt)
> 
>     if (encoding != PA_ENCODING_PCM)
>     {
>+        assert(fmt->channels_type == AUDIO_CHANNELS_TYPE_PHYSICAL);
>         pa_format_info_set_channels(formatv, ss.channels);
> 
>   /* FIX flags are only permitted for PCM, and there is no way to pass
>@@ -812,7 +852,7 @@ static int Start(audio_output_t *aout,
>audio_sample_format_t *restrict fmt)
>                  | PA_STREAM_FIX_RATE
>                  | PA_STREAM_FIX_CHANNELS);
>     }
>-    else
>+    else if (fmt->channels_type == AUDIO_CHANNELS_TYPE_PHYSICAL)
>     {
>         /* Channel mapping (order defined in vlc_aout.h) */
>         struct pa_channel_map map;
>@@ -861,6 +901,19 @@ static int Start(audio_output_t *aout,
>audio_sample_format_t *restrict fmt)
>         pa_format_info_set_channels(formatv, ss.channels);
>         pa_format_info_set_channel_map(formatv, &map);
>     }
>+    else
>+    {   /* AUDIO_CHANNELS_TYPE_AMBISONICS */
>+        fmt->channels_type = AUDIO_CHANNELS_TYPE_PHYSICAL;
>+
>+        /* Use the channel layout of the sink and override the current
>one.
>+         * This new layout be will used to configure the ambisonics
>filter. */
>+        flags |= PA_STREAM_FIX_CHANNELS;
>+
>+        /* Setup low latency in order to quickly react to ambisonics
>filters
>+         * viewpoint changes. */
>+        flags |= PA_STREAM_ADJUST_LATENCY;
>+        attr.tlength = pa_usec_to_bytes(2 * AOUT_MIN_PREPARE_TIME,
>&ss);
>+    }
> 
>     /* Create a playback stream */
>     pa_proplist *props = pa_proplist_new();
>@@ -934,9 +987,44 @@ static int Start(audio_output_t *aout,
>audio_sample_format_t *restrict fmt)
>         fmt->i_rate = spec->rate;
>     }
> 
>+    if (flags & PA_STREAM_FIX_CHANNELS)
>+    {
>+        const pa_channel_map *map = pa_stream_get_channel_map(s);
>+        assert(map != NULL);
>+
>+        const char *name = pa_channel_map_to_name(map);
>+        msg_Info(aout, "using %s channel map", (name != NULL) ? name :
>"?");
>+
>+        uint8_t chans_out_count = 0;
>+        uint32_t chans_out[AOUT_CHAN_MAX];
>+        fmt->i_physical_channels = 0;
>+        for (uint8_t i = 0; i < map->channels; ++i)
>+        {
>+            int vlcchan = channel_map_pulse_to_vlc(map->map[i]);
>+            if (vlcchan != 0)
>+            {
>+                chans_out[chans_out_count++] = vlcchan;
>+                assert(chans_out_count <= AOUT_CHAN_MAX);
>+                fmt->i_physical_channels |= vlcchan;
>+            }
>+        }
>+        if (chans_out_count != map->channels)
>+            msg_Warn(aout, "%u channels won't be mapped",
>+                     map->channels - chans_out_count);
>+        fmt->i_original_channels = fmt->i_physical_channels;
>+        aout_FormatPrepare(fmt);
>+
>+        sys->chans_to_reorder =
>+            aout_CheckChannelReorder(NULL, chans_out,
>fmt->i_physical_channels,
>+                                     sys->chans_table);
>+    }
>+    else
>+        sys->chans_to_reorder = 0;
>+
>     stream_buffer_attr_cb(s, aout);
>     stream_moved_cb(s, aout);
>     pa_threaded_mainloop_unlock(sys->mainloop);
>+    sys->fourcc = fmt->i_format;
> 
>     return VLC_SUCCESS;
> 
>-- 
>2.11.0
>
>_______________________________________________
>vlc-devel mailing list
>To unsubscribe or modify your subscription options:
>https://mailman.videolan.org/listinfo/vlc-devel

Why do you impose the channel order here?!
-- 
Rémi Denis-Courmont
Typed on an inconvenient virtual keyboard
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mailman.videolan.org/pipermail/vlc-devel/attachments/20170707/0021d3ab/attachment.html>


More information about the vlc-devel mailing list