1 // Copyright (C) 2016  Lukas Lalinsky
2 // Distributed under the MIT license, see the LICENSE file for details.
3 
4 #ifndef CHROMAPRINT_AUDIO_FFMPEG_AUDIO_PROCESSOR_SWRESAMPLE_H_
5 #define CHROMAPRINT_AUDIO_FFMPEG_AUDIO_PROCESSOR_SWRESAMPLE_H_
6 
7 extern "C" {
8 #include <libswresample/swresample.h>
9 }
10 
11 namespace chromaprint {
12 
13 class FFmpegAudioProcessor {
14 public:
FFmpegAudioProcessor()15 	FFmpegAudioProcessor() {
16 		m_swr_ctx = swr_alloc();
17 	}
18 
~FFmpegAudioProcessor()19 	~FFmpegAudioProcessor() {
20 		swr_free(&m_swr_ctx);
21 	}
22 
SetCompatibleMode()23 	void SetCompatibleMode() {
24 		av_opt_set_int(m_swr_ctx, "resampler", SWR_ENGINE_SWR, 0);
25 		av_opt_set_int(m_swr_ctx, "filter_size", 16, 0);
26 		av_opt_set_int(m_swr_ctx, "phase_shift", 8, 0);
27 		av_opt_set_int(m_swr_ctx, "linear_interp", 1, 0);
28 		av_opt_set_double(m_swr_ctx, "cutoff", 0.8, 0);
29 	}
30 
SetInputChannelLayout(int64_t channel_layout)31 	void SetInputChannelLayout(int64_t channel_layout) {
32 		av_opt_set_int(m_swr_ctx, "icl", channel_layout, 0);
33 		av_opt_set_int(m_swr_ctx, "ich", av_get_channel_layout_nb_channels(channel_layout), 0);
34 	}
35 
SetInputSampleFormat(AVSampleFormat sample_format)36 	void SetInputSampleFormat(AVSampleFormat sample_format) {
37 		av_opt_set_int(m_swr_ctx, "isf", sample_format, 0);
38 	}
39 
SetInputSampleRate(int sample_rate)40 	void SetInputSampleRate(int sample_rate) {
41 		av_opt_set_int(m_swr_ctx, "isr", sample_rate, 0);
42 	}
43 
SetOutputChannelLayout(int64_t channel_layout)44 	void SetOutputChannelLayout(int64_t channel_layout) {
45 		av_opt_set_int(m_swr_ctx, "ocl", channel_layout, 0);
46 		av_opt_set_int(m_swr_ctx, "och", av_get_channel_layout_nb_channels(channel_layout), 0);
47 	}
48 
SetOutputSampleFormat(AVSampleFormat sample_format)49 	void SetOutputSampleFormat(AVSampleFormat sample_format) {
50 		av_opt_set_int(m_swr_ctx, "osf", sample_format, 0);
51 	}
52 
SetOutputSampleRate(int sample_rate)53 	void SetOutputSampleRate(int sample_rate) {
54 		av_opt_set_int(m_swr_ctx, "osr", sample_rate, 0);
55 	}
56 
Init()57 	int Init() {
58 		return swr_init(m_swr_ctx);
59 	}
60 
Convert(uint8_t ** out,int out_count,const uint8_t ** in,int in_count)61 	int Convert(uint8_t **out, int out_count, const uint8_t **in, int in_count) {
62 		return swr_convert(m_swr_ctx, out, out_count, in, in_count);
63 	}
64 
Flush(uint8_t ** out,int out_count)65 	int Flush(uint8_t **out, int out_count) {
66 		return swr_convert(m_swr_ctx, out, out_count, nullptr, 0);
67 	}
68 
69 private:
70 	SwrContext *m_swr_ctx = nullptr;
71 };
72 
73 }; // namespace chromaprint
74 
75 #endif
76