1 /*
2 * Copyright (c) 2024, Alliance for Open Media. All rights reserved
3 *
4 * This source code is subject to the terms of the BSD 3-Clause Clear License
5 * and the Alliance for Open Media Patent License 1.0. If the BSD 3-Clause Clear
6 * License was not distributed with this source code in the LICENSE file, you
7 * can obtain it at www.aomedia.org/license/software-license/bsd-3-c-c. If the
8 * Alliance for Open Media Patent License 1.0 was not distributed with this
9 * source code in the PATENTS file, you can obtain it at
10 * www.aomedia.org/license/patent.
11 */
12 #include "iamf/cli/renderer_factory.h"
13
14 #include <cstddef>
15
16 #include "gtest/gtest.h"
17 #include "iamf/cli/channel_label.h"
18 #include "iamf/cli/proto/obu_header.pb.h"
19 #include "iamf/cli/proto/parameter_data.pb.h"
20 #include "iamf/cli/proto/temporal_delimiter.pb.h"
21 #include "iamf/cli/proto/user_metadata.pb.h"
22 #include "iamf/obu/audio_element.h"
23 #include "iamf/obu/mix_presentation.h"
24
25 namespace iamf_tools {
26 namespace {
27
28 using enum LoudspeakersSsConventionLayout::SoundSystem;
29 using enum ChannelAudioLayerConfig::LoudspeakerLayout;
30 using enum ChannelLabel::Label;
31
32 const Layout kMonoLayout = {
33 .layout_type = Layout::kLayoutTypeLoudspeakersSsConvention,
34 .specific_layout =
35 LoudspeakersSsConventionLayout{.sound_system = kSoundSystem12_0_1_0}};
36 const Layout kBinauralLayout = {.layout_type = Layout::kLayoutTypeBinaural};
37
38 constexpr size_t kNumSamplesPerFrame = 8;
39
40 const ScalableChannelLayoutConfig kBinauralChannelLayoutConfig = {
41 .num_layers = 1,
42 .channel_audio_layer_configs = {{.loudspeaker_layout = kLayoutBinaural}}};
43
44 const ScalableChannelLayoutConfig kMonoScalableChannelLayoutConfig = {
45 .num_layers = 1,
46 .channel_audio_layer_configs = {{.loudspeaker_layout = kLayoutMono}}};
47
48 const ScalableChannelLayoutConfig kStereoScalableChannelLayoutConfig = {
49 .num_layers = 1,
50 .channel_audio_layer_configs = {{.loudspeaker_layout = kLayoutStereo}}};
51
52 const AmbisonicsConfig kFullZerothOrderAmbisonicsConfig = {
53 .ambisonics_mode = AmbisonicsConfig::kAmbisonicsModeMono,
54 .ambisonics_config = AmbisonicsMonoConfig{.output_channel_count = 1,
55 .substream_count = 1,
56 .channel_mapping = {0}}};
57
58 const ExtensionConfig kExtensionConfig = {.audio_element_config_size = 0,
59 .audio_element_config_bytes = {}};
60
61 const RenderingConfig kHeadphonesAsStereoRenderingConfig = {
62 .headphones_rendering_mode =
63 RenderingConfig::kHeadphonesRenderingModeStereo};
64
65 const RenderingConfig kHeadphonesAsBinauralRenderingConfig = {
66 .headphones_rendering_mode =
67 RenderingConfig::kHeadphonesRenderingModeBinaural};
68
TEST(CreateRendererForLayout,SupportsPassThroughRenderer)69 TEST(CreateRendererForLayout, SupportsPassThroughRenderer) {
70 const RendererFactory factory;
71
72 EXPECT_NE(
73 factory.CreateRendererForLayout(
74 {0}, {{0, {kMono}}}, AudioElementObu::kAudioElementChannelBased,
75 kMonoScalableChannelLayoutConfig, kHeadphonesAsStereoRenderingConfig,
76 kMonoLayout, kNumSamplesPerFrame),
77 nullptr);
78 }
79
TEST(CreateRendererForLayout,SupportsPassThroughBinauralRenderer)80 TEST(CreateRendererForLayout, SupportsPassThroughBinauralRenderer) {
81 const RendererFactory factory;
82
83 EXPECT_NE(
84 factory.CreateRendererForLayout(
85 {0}, {{0, {kL2, kR2}}}, AudioElementObu::kAudioElementChannelBased,
86 kBinauralChannelLayoutConfig, kHeadphonesAsBinauralRenderingConfig,
87 kBinauralLayout, kNumSamplesPerFrame),
88 nullptr);
89 }
90
TEST(CreateRendererForLayout,ReturnsNullPtrWhenTypeIsSceneBasedButConfigIsChannelBased)91 TEST(CreateRendererForLayout,
92 ReturnsNullPtrWhenTypeIsSceneBasedButConfigIsChannelBased) {
93 const RendererFactory factory;
94
95 EXPECT_EQ(
96 factory.CreateRendererForLayout(
97 {0}, {{0, {kA0}}}, AudioElementObu::kAudioElementSceneBased,
98 kMonoScalableChannelLayoutConfig, kHeadphonesAsStereoRenderingConfig,
99 kMonoLayout, kNumSamplesPerFrame),
100 nullptr);
101 }
102
TEST(CreateRendererForLayout,ReturnsNullPtrWhenTypeIsChannelBasedButConfigIsAmbisonics)103 TEST(CreateRendererForLayout,
104 ReturnsNullPtrWhenTypeIsChannelBasedButConfigIsAmbisonics) {
105 const RendererFactory factory;
106
107 EXPECT_EQ(
108 factory.CreateRendererForLayout(
109 {0}, {{0, {kMono}}}, AudioElementObu::kAudioElementChannelBased,
110 kFullZerothOrderAmbisonicsConfig, kHeadphonesAsStereoRenderingConfig,
111 kMonoLayout, kNumSamplesPerFrame),
112 nullptr);
113 }
114
115 // TODO(b/282877209): Support channel-based to binaural renderer.
TEST(CreateRendererForLayout,ReturnsNullPtrForChannelToBinauralRenderer)116 TEST(CreateRendererForLayout, ReturnsNullPtrForChannelToBinauralRenderer) {
117 const RendererFactory factory;
118
119 EXPECT_EQ(factory.CreateRendererForLayout(
120 {0}, {{0, {kMono}}}, AudioElementObu::kAudioElementChannelBased,
121 kMonoScalableChannelLayoutConfig,
122 kHeadphonesAsBinauralRenderingConfig, kBinauralLayout,
123 kNumSamplesPerFrame),
124 nullptr);
125 }
126
TEST(CreateRendererForLayout,ReturnsNullPtrForUnknownExtension)127 TEST(CreateRendererForLayout, ReturnsNullPtrForUnknownExtension) {
128 const RendererFactory factory;
129
130 EXPECT_EQ(factory.CreateRendererForLayout(
131 {0}, {{0, {kMono}}}, AudioElementObu::kAudioElementEndReserved,
132 kExtensionConfig, kHeadphonesAsStereoRenderingConfig,
133 kBinauralLayout, kNumSamplesPerFrame),
134 nullptr);
135 }
136
TEST(CreateRendererForLayout,SupportsChannelToChannelRenderer)137 TEST(CreateRendererForLayout, SupportsChannelToChannelRenderer) {
138 const RendererFactory factory;
139
140 EXPECT_NE(
141 factory.CreateRendererForLayout(
142 {0}, {{0, {kL2, kR2}}}, AudioElementObu::kAudioElementChannelBased,
143 kStereoScalableChannelLayoutConfig,
144 kHeadphonesAsStereoRenderingConfig, kMonoLayout, kNumSamplesPerFrame),
145 nullptr);
146 }
147
TEST(CreateRendererForLayout,SupportsAmbisonicsToChannelRenderer)148 TEST(CreateRendererForLayout, SupportsAmbisonicsToChannelRenderer) {
149 const RendererFactory factory;
150
151 EXPECT_NE(
152 factory.CreateRendererForLayout(
153 {0}, {{0, {kA0}}}, AudioElementObu::kAudioElementSceneBased,
154 kFullZerothOrderAmbisonicsConfig, kHeadphonesAsStereoRenderingConfig,
155 kMonoLayout, kNumSamplesPerFrame),
156 nullptr);
157 }
158
159 // TODO(b/282877209): Support ambisonics to binaural renderer.
TEST(CreateRendererForLayout,ReturnsNullPtrForAmbisonicsToBinauralRenderer)160 TEST(CreateRendererForLayout, ReturnsNullPtrForAmbisonicsToBinauralRenderer) {
161 const RendererFactory factory;
162
163 EXPECT_EQ(factory.CreateRendererForLayout(
164 {0}, {{0, {kA0}}}, AudioElementObu::kAudioElementSceneBased,
165 kFullZerothOrderAmbisonicsConfig,
166 kHeadphonesAsBinauralRenderingConfig, kBinauralLayout,
167 kNumSamplesPerFrame),
168 nullptr);
169 }
170
171 } // namespace
172 } // namespace iamf_tools
173