Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Contribute to GitLab
Sign in / Register
Toggle navigation
F
ffmpeg.wasm-core
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
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Linshizhi
ffmpeg.wasm-core
Commits
0eaa123b
Commit
0eaa123b
authored
Jan 16, 2012
by
Clément Bœsch
Committed by
Clément Bœsch
Feb 02, 2012
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
lavu: add public timecode API.
parent
b18ebcbe
Show whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
338 additions
and
1 deletion
+338
-1
APIchanges
doc/APIchanges
+3
-0
Makefile
libavutil/Makefile
+2
-0
avutil.h
libavutil/avutil.h
+1
-1
timecode.c
libavutil/timecode.c
+194
-0
timecode.h
libavutil/timecode.h
+138
-0
No files found.
doc/APIchanges
View file @
0eaa123b
...
...
@@ -13,6 +13,9 @@ libavutil: 2011-04-18
API changes, most recent first:
2012-02-02 - xxxxxxx - lavu 51.37.100
Add public timecode helpers.
2012-01-24 - xxxxxxx - lavfi 2.60.100
Add avfilter_graph_dump.
...
...
libavutil/Makefile
View file @
0eaa123b
...
...
@@ -37,6 +37,7 @@ HEADERS = adler32.h \
rational.h
\
samplefmt.h
\
sha.h
\
timecode.h
\
BUILT_HEADERS
=
avconfig.h
...
...
@@ -71,6 +72,7 @@ OBJS = adler32.o \
rc4.o
\
samplefmt.o
\
sha.o
\
timecode.o
\
tree.o
\
utils.o
\
...
...
libavutil/avutil.h
View file @
0eaa123b
...
...
@@ -154,7 +154,7 @@
*/
#define LIBAVUTIL_VERSION_MAJOR 51
#define LIBAVUTIL_VERSION_MINOR 3
6
#define LIBAVUTIL_VERSION_MINOR 3
7
#define LIBAVUTIL_VERSION_MICRO 100
#define LIBAVUTIL_VERSION_INT AV_VERSION_INT(LIBAVUTIL_VERSION_MAJOR, \
...
...
libavutil/timecode.c
0 → 100644
View file @
0eaa123b
/*
* Copyright (c) 2006 Smartjog S.A.S, Baptiste Coudurier <baptiste.coudurier@gmail.com>
* Copyright (c) 2011-2012 Smartjog S.A.S, Clément Bœsch <clement.boesch@smartjog.com>
*
* This file is part of FFmpeg.
*
* FFmpeg is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* FFmpeg is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with FFmpeg; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/**
* @file
* Timecode helpers
* A few references:
* https://en.wikipedia.org/wiki/SMPTE_time_code
* http://www.dropframetimecode.org
*/
#include <stdio.h>
#include "timecode.h"
#include "log.h"
#include "error.h"
int
av_timecode_adjust_ntsc_framenum
(
int
framenum
)
{
/* only works for NTSC 29.97 */
int
d
=
framenum
/
17982
;
int
m
=
framenum
%
17982
;
//if (m < 2) m += 2; /* not needed since -2,-1 / 1798 in C returns 0 */
return
framenum
+
18
*
d
+
2
*
((
m
-
2
)
/
1798
);
}
uint32_t
av_timecode_get_smpte_from_framenum
(
const
AVTimecode
*
tc
,
int
framenum
)
{
unsigned
fps
=
tc
->
fps
;
int
drop
=
!!
(
tc
->
flags
&
AV_TIMECODE_FLAG_DROPFRAME
);
int
hh
,
mm
,
ss
,
ff
;
framenum
+=
tc
->
start
;
if
(
drop
)
framenum
=
av_timecode_adjust_ntsc_framenum
(
framenum
);
ff
=
framenum
%
fps
;
ss
=
framenum
/
fps
%
60
;
mm
=
framenum
/
(
fps
*
60
)
%
60
;
hh
=
framenum
/
(
fps
*
3600
)
%
24
;
return
0
<<
31
|
// color frame flag (0: unsync mode, 1: sync mode)
drop
<<
30
|
// drop frame flag (0: non drop, 1: drop)
(
ff
/
10
)
<<
28
|
// tens of frames
(
ff
%
10
)
<<
24
|
// units of frames
0
<<
23
|
// PC (NTSC) or BGF0 (PAL)
(
ss
/
10
)
<<
20
|
// tens of seconds
(
ss
%
10
)
<<
16
|
// units of seconds
0
<<
15
|
// BGF0 (NTSC) or BGF2 (PAL)
(
mm
/
10
)
<<
12
|
// tens of minutes
(
mm
%
10
)
<<
8
|
// units of minutes
0
<<
7
|
// BGF2 (NTSC) or PC (PAL)
0
<<
6
|
// BGF1
(
hh
/
10
)
<<
4
|
// tens of hours
(
hh
%
10
);
// units of hours
}
char
*
av_timecode_make_string
(
const
AVTimecode
*
tc
,
char
*
buf
,
int
framenum
)
{
int
fps
=
tc
->
fps
;
int
drop
=
tc
->
flags
&
AV_TIMECODE_FLAG_DROPFRAME
;
int
hh
,
mm
,
ss
,
ff
,
neg
=
0
;
framenum
+=
tc
->
start
;
if
(
drop
)
framenum
=
av_timecode_adjust_ntsc_framenum
(
framenum
);
if
(
framenum
<
0
)
{
framenum
=
-
framenum
;
neg
=
tc
->
flags
&
AV_TIMECODE_FLAG_ALLOWNEGATIVE
;
}
ff
=
framenum
%
fps
;
ss
=
framenum
/
fps
%
60
;
mm
=
framenum
/
(
fps
*
60
)
%
60
;
hh
=
framenum
/
(
fps
*
3600
);
if
(
tc
->
flags
&
AV_TIMECODE_FLAG_24HOURSMAX
)
hh
=
hh
%
24
;
snprintf
(
buf
,
AV_TIMECODE_STR_SIZE
,
"%s%02d:%02d:%02d%c%02d"
,
neg
?
"-"
:
""
,
hh
,
mm
,
ss
,
drop
?
';'
:
':'
,
ff
);
return
buf
;
}
static
unsigned
bcd2uint
(
uint8_t
bcd
)
{
unsigned
low
=
bcd
&
0xf
;
unsigned
high
=
bcd
>>
4
;
if
(
low
>
9
||
high
>
9
)
return
0
;
return
low
+
10
*
high
;
}
char
*
av_timecode_make_smpte_tc_string
(
char
*
buf
,
uint32_t
tcsmpte
,
int
prevent_df
)
{
unsigned
hh
=
bcd2uint
(
tcsmpte
&
0x3f
);
// 6-bit hours
unsigned
mm
=
bcd2uint
(
tcsmpte
>>
8
&
0x7f
);
// 7-bit minutes
unsigned
ss
=
bcd2uint
(
tcsmpte
>>
16
&
0x7f
);
// 7-bit seconds
unsigned
ff
=
bcd2uint
(
tcsmpte
>>
24
&
0x3f
);
// 6-bit frames
unsigned
drop
=
tcsmpte
&
1
<<
30
&&
!
prevent_df
;
// 1-bit drop if not arbitrary bit
snprintf
(
buf
,
AV_TIMECODE_STR_SIZE
,
"%02u:%02u:%02u%c%02u"
,
hh
,
mm
,
ss
,
drop
?
';'
:
':'
,
ff
);
return
buf
;
}
char
*
av_timecode_make_mpeg_tc_string
(
char
*
buf
,
uint32_t
tc25bit
)
{
snprintf
(
buf
,
AV_TIMECODE_STR_SIZE
,
"%02u:%02u:%02u%c%02u"
,
tc25bit
>>
19
&
0x1f
,
// 5-bit hours
tc25bit
>>
13
&
0x3f
,
// 6-bit minutes
tc25bit
>>
6
&
0x3f
,
// 6-bit seconds
tc25bit
&
1
<<
24
?
';'
:
':'
,
// 1-bit drop flag
tc25bit
&
0x3f
);
// 6-bit frames
return
buf
;
}
static
int
check_timecode
(
void
*
log_ctx
,
AVTimecode
*
tc
)
{
if
(
tc
->
fps
<=
0
)
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Timecode frame rate must be specified
\n
"
);
return
AVERROR
(
EINVAL
);
}
if
((
tc
->
flags
&
AV_TIMECODE_FLAG_DROPFRAME
)
&&
tc
->
fps
!=
30
)
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Drop frame is only allowed with 30000/1001 FPS
\n
"
);
return
AVERROR
(
EINVAL
);
}
switch
(
tc
->
fps
)
{
case
24
:
case
25
:
case
30
:
return
0
;
default:
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Timecode frame rate not supported
\n
"
);
return
AVERROR_PATCHWELCOME
;
}
}
static
int
fps_from_frame_rate
(
AVRational
rate
)
{
if
(
!
rate
.
den
||
!
rate
.
num
)
return
-
1
;
return
(
rate
.
num
+
rate
.
den
/
2
)
/
rate
.
den
;
}
int
av_timecode_init
(
AVTimecode
*
tc
,
AVRational
rate
,
int
flags
,
int
frame_start
,
void
*
log_ctx
)
{
memset
(
tc
,
0
,
sizeof
(
*
tc
));
tc
->
start
=
frame_start
;
tc
->
flags
=
flags
;
tc
->
rate
=
rate
;
tc
->
fps
=
fps_from_frame_rate
(
rate
);
return
check_timecode
(
log_ctx
,
tc
);
}
int
av_timecode_init_from_string
(
AVTimecode
*
tc
,
AVRational
rate
,
const
char
*
str
,
void
*
log_ctx
)
{
char
c
;
int
hh
,
mm
,
ss
,
ff
,
ret
;
if
(
sscanf
(
str
,
"%d:%d:%d%c%d"
,
&
hh
,
&
mm
,
&
ss
,
&
c
,
&
ff
)
!=
5
)
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Unable to parse timecode, "
"syntax: hh:mm:ss[:;.]ff
\n
"
);
return
AVERROR_INVALIDDATA
;
}
memset
(
tc
,
0
,
sizeof
(
*
tc
));
tc
->
flags
=
c
!=
':'
?
AV_TIMECODE_FLAG_DROPFRAME
:
0
;
// drop if ';', '.', ...
tc
->
rate
=
rate
;
tc
->
fps
=
fps_from_frame_rate
(
rate
);
ret
=
check_timecode
(
log_ctx
,
tc
);
if
(
ret
<
0
)
return
ret
;
tc
->
start
=
(
hh
*
3600
+
mm
*
60
+
ss
)
*
tc
->
fps
+
ff
;
if
(
tc
->
flags
&
AV_TIMECODE_FLAG_DROPFRAME
)
{
/* adjust frame number */
int
tmins
=
60
*
hh
+
mm
;
tc
->
start
-=
2
*
(
tmins
-
tmins
/
10
);
}
return
0
;
}
libavutil/timecode.h
0 → 100644
View file @
0eaa123b
/*
* Copyright (c) 2006 Smartjog S.A.S, Baptiste Coudurier <baptiste.coudurier@gmail.com>
* Copyright (c) 2011-2012 Smartjog S.A.S, Clément Bœsch <clement.boesch@smartjog.com>
*
* This file is part of FFmpeg.
*
* FFmpeg is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* FFmpeg is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with FFmpeg; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
/**
* @file
* Timecode helpers header
*/
#ifndef AVUTIL_TIMECODE_H
#define AVUTIL_TIMECODE_H
#include <stdint.h>
#include "rational.h"
#define AV_TIMECODE_STR_SIZE 16
#define AV_TIMECODE_OPTION(ctx, string_field, flags) \
"timecode", "set timecode value following hh:mm:ss[:;.]ff format, " \
"use ';' or '.' before frame number for drop frame", \
offsetof(ctx, string_field), \
AV_OPT_TYPE_STRING, {.str=NULL}, CHAR_MIN, CHAR_MAX, flags
enum
AVTimecodeFlag
{
AV_TIMECODE_FLAG_DROPFRAME
=
1
<<
0
,
///< timecode is drop frame
AV_TIMECODE_FLAG_24HOURSMAX
=
1
<<
1
,
///< timecode wraps after 24 hours
AV_TIMECODE_FLAG_ALLOWNEGATIVE
=
1
<<
2
,
///< negative time values are allowed
};
typedef
struct
{
int
start
;
///< timecode frame start (first base frame number)
uint32_t
flags
;
///< flags such as drop frame, +24 hours support, ...
AVRational
rate
;
///< frame rate in rational form
unsigned
fps
;
///< frame per second; must be consistent with the rate field
}
AVTimecode
;
/**
* Adjust frame number for NTSC drop frame time code.
*
* @param framenum frame number to adjust
* @return adjusted frame number
* @warning adjustment is only valid in NTSC 29.97
*/
int
av_timecode_adjust_ntsc_framenum
(
int
framenum
);
/**
* Convert frame number to SMPTE 12M binary representation.
*
* @param tc timecode data correctly initialized
* @param framenum frame number
* @return the SMPTE binary representation
*
* @note Frame number adjustment is automatically done in case of drop timecode,
* you do NOT have to call av_timecode_adjust_ntsc_framenum().
* @note The frame number is relative to tc->start.
* @note Color frame (CF), binary group flags (BGF) and biphase mark polarity
* correction (PC) bits are set to zero.
*/
uint32_t
av_timecode_get_smpte_from_framenum
(
const
AVTimecode
*
tc
,
int
framenum
);
/**
* Load timecode string in buf.
*
* @param buf destination buffer, must be at least AV_TIMECODE_STR_SIZE long
* @param tc timecode data correctly initialized
* @param framenum frame number
* @return the buf parameter
*
* @note Timecode representation can be a negative timecode and have more than
* 24 hours, but will only be honored if the flags are correctly set.
* @note The frame number is relative to tc->start.
*/
char
*
av_timecode_make_string
(
const
AVTimecode
*
tc
,
char
*
buf
,
int
framenum
);
/**
* Get the timecode string from the SMPTE timecode format.
*
* @param buf destination buffer, must be at least AV_TIMECODE_STR_SIZE long
* @param tcsmpte the 32-bit SMPTE timecode
* @param prevent_df prevent the use of a drop flag when it is known the DF bit
* is arbitrary
* @return the buf parameter
*/
char
*
av_timecode_make_smpte_tc_string
(
char
*
buf
,
uint32_t
tcsmpte
,
int
prevent_df
);
/**
* Get the timecode string from the 25-bit timecode format (MPEG GOP format).
*
* @param buf destination buffer, must be at least AV_TIMECODE_STR_SIZE long
* @param tc25bit the 25-bits timecode
* @return the buf parameter
*/
char
*
av_timecode_make_mpeg_tc_string
(
char
*
buf
,
uint32_t
tc25bit
);
/**
* Init a timecode struct with the passed parameters.
*
* @param log_ctx a pointer to an arbitrary struct of which the first field
* is a pointer to an AVClass struct (used for av_log)
* @param tc pointer to an allocated AVTimecode
* @param rate frame rate in rational form
* @param flags miscellaneous flags such as drop frame, +24 hours, ...
* (see AVTimecodeFlag)
* @param frame_start the first frame number
* @return 0 on success, AVERROR otherwise
*/
int
av_timecode_init
(
AVTimecode
*
tc
,
AVRational
rate
,
int
flags
,
int
frame_start
,
void
*
log_ctx
);
/**
* Parse timecode representation (hh:mm:ss[:;.]ff).
*
* @param log_ctx a pointer to an arbitrary struct of which the first field is a
* pointer to an AVClass struct (used for av_log).
* @param tc pointer to an allocated AVTimecode
* @param rate frame rate in rational form
* @param str timecode string which will determine the frame start
* @return 0 on success, AVERROR otherwise
*/
int
av_timecode_init_from_string
(
AVTimecode
*
tc
,
AVRational
rate
,
const
char
*
str
,
void
*
log_ctx
);
#endif
/* AVUTIL_TIMECODE_H */
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