Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(699)

Side by Side Diff: media/base/audio_sample_types.h

Issue 2024993004: AudioBus: Add a ToInterleavedFloat() method to AudioBus (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Switched to templated method approach Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « media/base/audio_bus_unittest.cc ('k') | media/cast/sender/audio_encoder.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright (c) 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifndef MEDIA_BASE_AUDIO_SAMPLE_TYPES_H_
6 #define MEDIA_BASE_AUDIO_SAMPLE_TYPES_H_
7
8 #include <cstdint>
9 #include <limits>
10
11 // Provides one class per sample type. Each class satisfies a concept we call
12 // "SampleTypeTraits", which requires that the following publics are provided:
13 // * A typedef |ValueType| specifying the C++ type for storing sample values
14 // * A static method min_value() that returns the minimum sample value
15 // * A static method max_value() that returns the maximum sample value
16 // * A static method zero_point_value() that returns the sample value
17 // representing an amplitude of zero
18 // * A static method convert_from_float32() that takes a float32 sample value
19 // and converts it to |ValueType|.
20 // * A static method convert_to_float32() that takes a value of |ValueType|
21 // to a float32 sample value.
22
23 namespace media {
24
25 class Linear8BitUnsignedIntSampleTypeTraits {
26 public:
27 typedef uint8_t ValueType;
miu 2016/06/07 22:16:36 Chromium's preferring the new syntax for new code:
chfremer 2016/06/08 18:46:39 Done.
28 static uint8_t min_value() { return 0; }
miu 2016/06/07 22:16:36 All the zero-arg static methods in these classes s
chfremer 2016/06/08 18:46:39 Done.
29 static uint8_t max_value() { return 255; }
30 static uint8_t zero_point_value() { return 128; }
31 static uint8_t convert_from_float32(float source_value) {
32 // Apply clipping to avoid having out-of-range values wrap around in the
33 // uint8_t domain.
34 if (source_value <= -1.0f) {
35 return min_value();
36 }
37 if (source_value >= 1.0f) {
38 return max_value();
39 }
40 // Apply scaling and shift
41 return static_cast<uint8_t>(
42 (source_value * get_scale_factor(source_value)) + zero_point_value());
43 }
44 static float convert_to_float32(uint8_t source_value) {
45 // Apply shift
46 float shifted_value = static_cast<float>(source_value) - zero_point_value();
47 // Apply scaling
48 return shifted_value / get_scale_factor(shifted_value);
49 }
50
51 private:
52 // Since zero_point_value() is not the exact center between
53 // min_value() and max_value(), we apply a different scaling for positive
54 // and negative values.
55 static float get_scale_factor(float input_value) {
56 return (input_value < 0.0f) ? scale_factor_for_negative()
57 : scale_factor_for_positive();
58 }
59 static float scale_factor_for_positive() {
60 return max_value() - zero_point_value();
61 }
62 static float scale_factor_for_negative() {
63 return zero_point_value() - min_value();
64 }
65 };
66
67 class Linear16BitSignedIntSampleTypeTraits {
miu 2016/06/07 22:16:36 Seems all these classes for the integer types are
chfremer 2016/06/08 18:46:39 Thanks for this beautiful suggestion. I will creat
68 public:
69 typedef int16_t ValueType;
70 static int16_t min_value() { return std::numeric_limits<int16_t>::min(); }
71 static int16_t max_value() { return std::numeric_limits<int16_t>::max(); }
72 static int16_t zero_point_value() { return 0; }
73
74 static int16_t convert_from_float32(float source_value) {
75 // Apply clipping to avoid having out-of-range values wrap around in the
76 // int16_t domain.
77 if (source_value <= -1.0f) {
78 return min_value();
79 }
80 if (source_value >= 1.0f) {
81 return max_value();
82 }
83 // Apply scaling and convert type.
84 return static_cast<int16_t>(source_value * get_scale_factor(source_value));
85 }
86
87 static float convert_to_float32(int16_t source_value) {
88 return source_value / get_scale_factor(source_value);
89 }
90
91 private:
92 // Since zero_point_value() is not the exact center between
93 // min_value() and max_value(), we apply a different scaling for positive
94 // and negative values.
95 static float get_scale_factor(float input_value) {
96 return (input_value < 0.0f) ? (-static_cast<float>(min_value()))
97 : static_cast<float>(max_value());
98 }
99 };
100
101 class Linear32BitSignedIntSampleTypeTraits {
102 public:
103 typedef int32_t ValueType;
104 static int32_t min_value() { return std::numeric_limits<int32_t>::min(); }
105 static int32_t max_value() { return std::numeric_limits<int32_t>::max(); }
106 static int32_t zero_point_value() { return 0; }
107
108 static int32_t convert_from_float32(float source_value) {
109 // Note: Due to the limited precision, float cannot represent the integer
110 // std::numeric_limits<int32_t>::max(), which we want to use as the scaling
111 // factor for positive values. When converting to float, this scaling factor
112 // gets quantized to a neighboring value that float can represent.
113 // Not sure if this depends on the compiler or platform, but when tested on
114 // an example workstation, the quantized value came out as
115 // std::numeric_limits<int32_t>::max() + 1. When multiplied with a
116 // |source_value| of 1.0f and converted to int32_t, this would cause an
117 // overflow leading to a large negative value instead.
118 // To ensure this does not happen, we handle the case of |source_value| ==
119 // 1.0 in the handling for clipping.
120 // For the case of |source_value| being the largest possible float value
121 // smaller than 1.0, multiplying by (numeric_limits<int32_t>::max() + 1)
122 // already results in a value smaller than numeric_limits<int32_t>::max(),
123 // so this does not cause any issue.
124 // For the negative case of std::numeric_limits<int32_t>::min() it turns out
125 // that the quantized value matches the desired value exactly, so there is
126 // no issue at all.
127
128 // Apply clipping and handling of the 1.0f case
129 if (source_value <= -1.0f) {
130 return min_value();
131 }
132 if (source_value >= 1.0f) {
133 return max_value();
134 }
135 // Apply scaling and convert type.
136 return static_cast<int32_t>(source_value * get_scale_factor(source_value));
137 }
138
139 static float convert_to_float32(int32_t source_value) {
140 // Note: For the case of |source_value| == numeric_limits<int32_t>::max()
141 // what happens is that, before the division, |source_value| gets converted
142 // to float, which causes the same quantization error that we get for the
143 // scale factor. As a result, we obtain exactly 1.0f, which is what we want.
144 return source_value / get_scale_factor(source_value);
145 }
146
147 private:
148 // Since zero_point_value() is not the exact center between
149 // min_value() and max_value(), we apply a different scaling for positive
150 // and negative values.
151 static float get_scale_factor(float input_value) {
152 return (input_value < 0.0f) ? (-static_cast<float>(min_value()))
153 : static_cast<float>(max_value());
154 }
155 };
156
157 class Float32SampleTypeTraits {
158 public:
159 typedef float ValueType;
160 static float min_value() { return -1.0f; }
161 static float max_value() { return 1.0f; }
162 static float zero_point_value() { return 0.0f; }
163 static float convert_from_float32(float source_value) { return source_value; }
164 static float convert_to_float32(float source_value) { return source_value; }
165 };
166
167 } // namespace media
168
169 #endif // MEDIA_BASE_AUDIO_SAMPLE_TYPES_H_
OLDNEW
« no previous file with comments | « media/base/audio_bus_unittest.cc ('k') | media/cast/sender/audio_encoder.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698