Skip to content
Projects
Groups
Snippets
Help
Loading...
Sign in / Register
Toggle navigation
F
ffmpeg
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Packages
Packages
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
submodule
ffmpeg
Commits
89920387
Commit
89920387
authored
Nov 30, 2012
by
Stefano Sabatini
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
examples: add resampling_audio.c file
parent
3ab5f7dc
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
224 additions
and
0 deletions
+224
-0
Makefile
doc/examples/Makefile
+1
-0
resampling_audio.c
doc/examples/resampling_audio.c
+223
-0
No files found.
doc/examples/Makefile
View file @
89920387
...
...
@@ -17,6 +17,7 @@ EXAMPLES= decoding_encoding \
filtering_audio
\
metadata
\
muxing
\
resampling_audio
\
scaling_video
\
OBJS
=
$
(
addsuffix .o,
$(EXAMPLES)
)
...
...
doc/examples/resampling_audio.c
0 → 100644
View file @
89920387
/*
* Copyright (c) 2012 Stefano Sabatini
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
/**
* @example
* libswresample API use example.
*/
#include <libavutil/opt.h>
#include <libavutil/channel_layout.h>
#include <libavutil/samplefmt.h>
#include <libswresample/swresample.h>
static
int
get_format_from_sample_fmt
(
const
char
**
fmt
,
enum
AVSampleFormat
sample_fmt
)
{
int
i
;
struct
sample_fmt_entry
{
enum
AVSampleFormat
sample_fmt
;
const
char
*
fmt_be
,
*
fmt_le
;
}
sample_fmt_entries
[]
=
{
{
AV_SAMPLE_FMT_U8
,
"u8"
,
"u8"
},
{
AV_SAMPLE_FMT_S16
,
"s16be"
,
"s16le"
},
{
AV_SAMPLE_FMT_S32
,
"s32be"
,
"s32le"
},
{
AV_SAMPLE_FMT_FLT
,
"f32be"
,
"f32le"
},
{
AV_SAMPLE_FMT_DBL
,
"f64be"
,
"f64le"
},
};
*
fmt
=
NULL
;
for
(
i
=
0
;
i
<
FF_ARRAY_ELEMS
(
sample_fmt_entries
);
i
++
)
{
struct
sample_fmt_entry
*
entry
=
&
sample_fmt_entries
[
i
];
if
(
sample_fmt
==
entry
->
sample_fmt
)
{
*
fmt
=
AV_NE
(
entry
->
fmt_be
,
entry
->
fmt_le
);
return
0
;
}
}
fprintf
(
stderr
,
"Sample format %s not supported as output format
\n
"
,
av_get_sample_fmt_name
(
sample_fmt
));
return
AVERROR
(
EINVAL
);
}
/**
* Fill dst buffer with nb_samples, generated starting from t.
*/
void
fill_samples
(
double
*
dst
,
int
nb_samples
,
int
nb_channels
,
int
sample_rate
,
double
*
t
)
{
int
i
,
j
;
double
tincr
=
1
.
0
/
sample_rate
,
*
dstp
=
dst
;
const
double
c
=
2
*
M_PI
*
440
.
0
;
/* generate sin tone with 440Hz frequency and duplicated channels */
for
(
i
=
0
;
i
<
nb_samples
;
i
++
)
{
*
dstp
=
sin
(
c
*
*
t
);
for
(
j
=
1
;
j
<
nb_channels
;
j
++
)
dstp
[
j
]
=
dstp
[
0
];
dstp
+=
nb_channels
;
*
t
+=
tincr
;
}
}
int
alloc_samples_array_and_data
(
uint8_t
***
data
,
int
*
linesize
,
int
nb_channels
,
int
nb_samples
,
enum
AVSampleFormat
sample_fmt
,
int
align
)
{
int
nb_planes
=
av_sample_fmt_is_planar
(
sample_fmt
)
?
nb_channels
:
1
;
*
data
=
av_malloc
(
sizeof
(
*
data
)
*
nb_planes
);
if
(
!*
data
)
return
AVERROR
(
ENOMEM
);
return
av_samples_alloc
(
*
data
,
linesize
,
nb_channels
,
nb_samples
,
sample_fmt
,
align
);
}
int
main
(
int
argc
,
char
**
argv
)
{
int64_t
src_ch_layout
=
AV_CH_LAYOUT_STEREO
,
dst_ch_layout
=
AV_CH_LAYOUT_SURROUND
;
int
src_rate
=
48000
,
dst_rate
=
44100
;
uint8_t
**
src_data
=
NULL
,
**
dst_data
=
NULL
;
int
src_nb_channels
=
0
,
dst_nb_channels
=
0
;
int
src_linesize
,
dst_linesize
;
int
src_nb_samples
=
1024
,
dst_nb_samples
,
max_dst_nb_samples
;
enum
AVSampleFormat
src_sample_fmt
=
AV_SAMPLE_FMT_DBL
,
dst_sample_fmt
=
AV_SAMPLE_FMT_S16
;
const
char
*
dst_filename
=
NULL
;
FILE
*
dst_file
;
int
dst_bufsize
;
const
char
*
fmt
;
struct
SwrContext
*
swr_ctx
;
double
t
;
int
ret
;
if
(
argc
!=
2
)
{
fprintf
(
stderr
,
"Usage: %s output_file
\n
"
"API example program to show how to resample an audio stream with libswresample.
\n
"
"This program generates a series of audio frames, resamples them to a specified "
"output format and rate and saves them to an output file named output_file.
\n
"
,
argv
[
0
]);
exit
(
1
);
}
dst_filename
=
argv
[
1
];
dst_file
=
fopen
(
dst_filename
,
"wb"
);
if
(
!
dst_file
)
{
fprintf
(
stderr
,
"Could not open destination file %s
\n
"
,
dst_filename
);
exit
(
1
);
}
/* create resampler context */
swr_ctx
=
swr_alloc
();
if
(
!
swr_ctx
)
{
fprintf
(
stderr
,
"Could not allocate resampler context
\n
"
);
ret
=
AVERROR
(
ENOMEM
);
goto
end
;
}
/* set options */
av_opt_set_int
(
swr_ctx
,
"in_channel_layout"
,
src_ch_layout
,
0
);
av_opt_set_int
(
swr_ctx
,
"in_sample_rate"
,
src_rate
,
0
);
av_opt_set_sample_fmt
(
swr_ctx
,
"in_sample_fmt"
,
src_sample_fmt
,
0
);
av_opt_set_int
(
swr_ctx
,
"out_channel_layout"
,
dst_ch_layout
,
0
);
av_opt_set_int
(
swr_ctx
,
"out_sample_rate"
,
dst_rate
,
0
);
av_opt_set_sample_fmt
(
swr_ctx
,
"out_sample_fmt"
,
dst_sample_fmt
,
0
);
/* initialize the resampling context */
if
((
ret
=
swr_init
(
swr_ctx
))
<
0
)
{
fprintf
(
stderr
,
"Failed to initialize the resampling context
\n
"
);
goto
end
;
}
/* allocate source and destination samples buffers */
src_nb_channels
=
av_get_channel_layout_nb_channels
(
src_ch_layout
);
ret
=
alloc_samples_array_and_data
(
&
src_data
,
&
src_linesize
,
src_nb_channels
,
src_nb_samples
,
src_sample_fmt
,
0
);
if
(
ret
<
0
)
{
fprintf
(
stderr
,
"Could not allocate source samples
\n
"
);
goto
end
;
}
/* compute the number of converted samples: buffering is avoided
* ensuring that the output buffer will contain at least all the
* converted input samples */
max_dst_nb_samples
=
dst_nb_samples
=
av_rescale_rnd
(
src_nb_samples
,
dst_rate
,
src_rate
,
AV_ROUND_UP
);
/* buffer is going to be directly written to a rawaudio file, no alignment */
dst_nb_channels
=
av_get_channel_layout_nb_channels
(
dst_ch_layout
);
ret
=
alloc_samples_array_and_data
(
&
dst_data
,
&
dst_linesize
,
dst_nb_channels
,
dst_nb_samples
,
dst_sample_fmt
,
0
);
if
(
ret
<
0
)
{
fprintf
(
stderr
,
"Could not allocate destination samples
\n
"
);
goto
end
;
}
t
=
0
;
do
{
/* generate synthetic audio */
fill_samples
((
double
*
)
src_data
[
0
],
src_nb_samples
,
src_nb_channels
,
src_rate
,
&
t
);
/* compute destination number of samples */
dst_nb_samples
=
av_rescale_rnd
(
swr_get_delay
(
swr_ctx
,
src_rate
)
+
src_nb_samples
,
dst_rate
,
src_rate
,
AV_ROUND_UP
);
if
(
dst_nb_samples
>
max_dst_nb_samples
)
{
av_free
(
dst_data
[
0
]);
ret
=
av_samples_alloc
(
dst_data
,
&
dst_linesize
,
dst_nb_channels
,
dst_nb_samples
,
dst_sample_fmt
,
1
);
if
(
ret
<
0
)
break
;
max_dst_nb_samples
=
dst_nb_samples
;
}
/* convert to destination format */
ret
=
swr_convert
(
swr_ctx
,
dst_data
,
dst_nb_samples
,
(
const
uint8_t
**
)
src_data
,
src_nb_samples
);
if
(
ret
<
0
)
{
fprintf
(
stderr
,
"Error while converting
\n
"
);
goto
end
;
}
dst_bufsize
=
av_samples_get_buffer_size
(
&
dst_linesize
,
dst_nb_channels
,
ret
,
dst_sample_fmt
,
1
);
printf
(
"t:%f in:%d out:%d
\n
"
,
t
,
src_nb_samples
,
ret
);
fwrite
(
dst_data
[
0
],
1
,
dst_bufsize
,
dst_file
);
}
while
(
t
<
10
);
if
((
ret
=
get_format_from_sample_fmt
(
&
fmt
,
dst_sample_fmt
)
<
0
))
goto
end
;
fprintf
(
stderr
,
"Resampling succeeded. Play the output file with the command:
\n
"
"ffplay -f %s -channel_layout %"
PRId64
" -channels %d -ar %d %s
\n
"
,
fmt
,
dst_ch_layout
,
dst_nb_channels
,
dst_rate
,
dst_filename
);
end:
if
(
dst_file
)
fclose
(
dst_file
);
if
(
src_data
)
av_freep
(
&
src_data
[
0
]);
av_freep
(
&
src_data
);
if
(
dst_data
)
av_freep
(
&
dst_data
[
0
]);
av_freep
(
&
dst_data
);
swr_free
(
&
swr_ctx
);
return
ret
<
0
;
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment