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
91cbb6ba
Commit
91cbb6ba
authored
Dec 26, 2010
by
Stefano Sabatini
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Add dilate libopencv filter.
Originally committed as revision 26096 to
svn://svn.ffmpeg.org/ffmpeg/trunk
parent
a187c686
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
212 additions
and
1 deletion
+212
-1
filters.texi
doc/filters.texi
+46
-0
avfilter.h
libavfilter/avfilter.h
+1
-1
vf_libopencv.c
libavfilter/vf_libopencv.c
+165
-0
No files found.
doc/filters.texi
View file @
91cbb6ba
...
...
@@ -532,6 +532,52 @@ informations:
Follows the list of supported libopencv filters.
@subsection dilate
Dilate an image by using a specific structuring element.
This filter corresponds to the libopencv function @code{cvDilate}.
It accepts the parameters: @var{struct_el}:@var{nb_iterations}.
@var{struct_el} represents a structuring element, and has the syntax:
@var{cols}x@var{rows}+@var{anchor_x}x@var{anchor_y}/@var{shape}
@var{cols} and @var{rows} represent the number of colums and rows of
the structuring element, @var{anchor_x} and @var{anchor_y} the anchor
point, and @var{shape} the shape for the structuring element, and
can be one of the values "rect", "cross", "ellipse", "custom".
If the value for @var{shape} is "custom", it must be followed by a
string of the form "=@var{filename}". The file with name
@var{filename} is assumed to represent a binary image, with each
printable character corresponding to a bright pixel. When a custom
@var{shape} is used, @var{cols} and @var{rows} are ignored, the number
or columns and rows of the read file are assumed instead.
The default value for @var{struct_el} is "3x3+0x0/rect".
@var{nb_iterations} specifies the number of times the transform is
applied to the image, and defaults to 1.
Follow some example:
@example
# use the default values
ocv=dilate
# dilate using a structuring element with a 5x5 cross, iterate two times
ocv=dilate=5x5+2x2/cross:2
# read the shape from the file diamond.shape, iterate two times
# the file diamond.shape may contain a pattern of characters like this:
# *
# ***
# *****
# ***
# *
# the specified cols and rows are ignored (but not the anchor point coordinates)
ocv=0x0+2x2/custom=diamond.shape:2
@end example
@subsection smooth
Smooth the input video.
...
...
libavfilter/avfilter.h
View file @
91cbb6ba
...
...
@@ -28,7 +28,7 @@
#define LIBAVFILTER_VERSION_MAJOR 1
#define LIBAVFILTER_VERSION_MINOR 70
#define LIBAVFILTER_VERSION_MICRO
0
#define LIBAVFILTER_VERSION_MICRO
1
#define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \
LIBAVFILTER_VERSION_MINOR, \
...
...
libavfilter/vf_libopencv.c
View file @
91cbb6ba
...
...
@@ -23,8 +23,12 @@
* libopencv wrapper functions
*/
/* #define DEBUG */
#include <opencv/cv.h>
#include <opencv/cxtypes.h>
#include "libavutil/avstring.h"
#include "libavutil/file.h"
#include "avfilter.h"
static
void
fill_iplimage_from_picref
(
IplImage
*
img
,
const
AVFilterBufferRef
*
picref
,
enum
PixelFormat
pixfmt
)
...
...
@@ -127,6 +131,166 @@ static void smooth_end_frame_filter(AVFilterContext *ctx, IplImage *inimg, IplIm
cvSmooth
(
inimg
,
outimg
,
smooth
->
type
,
smooth
->
param1
,
smooth
->
param2
,
smooth
->
param3
,
smooth
->
param4
);
}
static
int
read_shape_from_file
(
int
*
cols
,
int
*
rows
,
int
**
values
,
const
char
*
filename
,
void
*
log_ctx
)
{
uint8_t
*
buf
,
*
p
,
*
pend
;
size_t
size
;
int
ret
,
i
,
j
,
w
;
if
((
ret
=
av_file_map
(
filename
,
&
buf
,
&
size
,
0
,
log_ctx
))
<
0
)
return
ret
;
/* prescan file to get the number of lines and the maximum width */
w
=
0
;
for
(
i
=
0
;
i
<
size
;
i
++
)
{
if
(
buf
[
i
]
==
'\n'
)
{
if
(
*
rows
==
INT_MAX
)
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Overflow on the number of rows in the file
\n
"
);
return
AVERROR_INVALIDDATA
;
}
++
(
*
rows
);
*
cols
=
FFMAX
(
*
cols
,
w
);
w
=
0
;
}
else
if
(
w
==
INT_MAX
)
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Overflow on the number of columns in the file
\n
"
);
return
AVERROR_INVALIDDATA
;
}
w
++
;
}
if
(
*
rows
>
(
FF_INTERNAL_MEM_TYPE_MAX_VALUE
/
(
sizeof
(
int
))
/
*
cols
))
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"File with size %dx%d is too big
\n
"
,
*
rows
,
*
cols
);
return
AVERROR_INVALIDDATA
;
}
if
(
!
(
*
values
=
av_mallocz
(
sizeof
(
int
)
*
*
rows
*
*
cols
)))
return
AVERROR
(
ENOMEM
);
/* fill *values */
p
=
buf
;
pend
=
buf
+
size
-
1
;
for
(
i
=
0
;
i
<
*
rows
;
i
++
)
{
for
(
j
=
0
;;
j
++
)
{
if
(
p
>
pend
||
*
p
==
'\n'
)
{
p
++
;
break
;
}
else
(
*
values
)[
*
cols
*
i
+
j
]
=
!!
isgraph
(
*
(
p
++
));
}
}
av_file_unmap
(
buf
,
size
);
#ifdef DEBUG
{
char
*
line
;
if
(
!
(
line
=
av_malloc
(
*
cols
+
1
)))
return
AVERROR
(
ENOMEM
);
for
(
i
=
0
;
i
<
*
rows
;
i
++
)
{
for
(
j
=
0
;
j
<
*
cols
;
j
++
)
line
[
j
]
=
(
*
values
)[
i
*
*
cols
+
j
]
?
'@'
:
' '
;
line
[
j
]
=
0
;
av_log
(
log_ctx
,
AV_LOG_DEBUG
,
"%3d: %s
\n
"
,
i
,
line
);
}
av_free
(
line
);
}
#endif
return
0
;
}
static
int
parse_iplconvkernel
(
IplConvKernel
**
kernel
,
char
*
buf
,
void
*
log_ctx
)
{
char
shape_filename
[
128
]
=
""
,
shape_str
[
32
]
=
"rect"
;
int
cols
=
0
,
rows
=
0
,
anchor_x
=
0
,
anchor_y
=
0
,
shape
=
CV_SHAPE_RECT
;
int
*
values
=
NULL
,
ret
;
sscanf
(
buf
,
"%dx%d+%dx%d/%32[^=]=%127s"
,
&
cols
,
&
rows
,
&
anchor_x
,
&
anchor_y
,
shape_str
,
shape_filename
);
if
(
!
strcmp
(
shape_str
,
"rect"
))
shape
=
CV_SHAPE_RECT
;
else
if
(
!
strcmp
(
shape_str
,
"cross"
))
shape
=
CV_SHAPE_CROSS
;
else
if
(
!
strcmp
(
shape_str
,
"ellipse"
))
shape
=
CV_SHAPE_ELLIPSE
;
else
if
(
!
strcmp
(
shape_str
,
"custom"
))
{
shape
=
CV_SHAPE_CUSTOM
;
if
((
ret
=
read_shape_from_file
(
&
cols
,
&
rows
,
&
values
,
shape_filename
,
log_ctx
))
<
0
)
return
ret
;
}
else
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Shape unspecified or type '%s' unknown
\n
."
,
shape_str
);
return
AVERROR
(
EINVAL
);
}
if
(
rows
<=
0
||
cols
<=
0
)
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Invalid non-positive values for shape size %dx%d
\n
"
,
cols
,
rows
);
return
AVERROR
(
EINVAL
);
}
if
(
anchor_x
<
0
||
anchor_y
<
0
||
anchor_x
>=
cols
||
anchor_y
>=
rows
)
{
av_log
(
log_ctx
,
AV_LOG_ERROR
,
"Shape anchor %dx%d is not inside the rectangle with size %dx%d.
\n
"
,
anchor_x
,
anchor_y
,
cols
,
rows
);
return
AVERROR
(
EINVAL
);
}
*
kernel
=
cvCreateStructuringElementEx
(
cols
,
rows
,
anchor_x
,
anchor_y
,
shape
,
values
);
av_freep
(
&
values
);
if
(
!*
kernel
)
return
AVERROR
(
ENOMEM
);
av_log
(
log_ctx
,
AV_LOG_INFO
,
"Structuring element: w:%d h:%d x:%d y:%d shape:%s
\n
"
,
rows
,
cols
,
anchor_x
,
anchor_y
,
shape_str
);
return
0
;
}
typedef
struct
{
int
nb_iterations
;
IplConvKernel
*
kernel
;
}
DilateContext
;
static
av_cold
int
dilate_init
(
AVFilterContext
*
ctx
,
const
char
*
args
,
void
*
opaque
)
{
OCVContext
*
ocv
=
ctx
->
priv
;
DilateContext
*
dilate
=
ocv
->
priv
;
char
default_kernel_str
[]
=
"3x3+0x0/rect"
;
char
*
kernel_str
;
const
char
*
buf
=
args
;
int
ret
;
dilate
->
nb_iterations
=
1
;
if
(
args
)
kernel_str
=
av_get_token
(
&
buf
,
":"
);
if
((
ret
=
parse_iplconvkernel
(
&
dilate
->
kernel
,
*
kernel_str
?
kernel_str
:
default_kernel_str
,
ctx
))
<
0
)
return
ret
;
av_free
(
kernel_str
);
sscanf
(
buf
,
":%d"
,
&
dilate
->
nb_iterations
);
av_log
(
ctx
,
AV_LOG_INFO
,
"iterations_nb:%d
\n
"
,
dilate
->
nb_iterations
);
if
(
dilate
->
nb_iterations
<=
0
)
{
av_log
(
ctx
,
AV_LOG_ERROR
,
"Invalid non-positive value '%d' for nb_iterations
\n
"
,
dilate
->
nb_iterations
);
return
AVERROR
(
EINVAL
);
}
return
0
;
}
static
av_cold
void
dilate_uninit
(
AVFilterContext
*
ctx
)
{
OCVContext
*
ocv
=
ctx
->
priv
;
DilateContext
*
dilate
=
ocv
->
priv
;
cvReleaseStructuringElement
(
&
dilate
->
kernel
);
}
static
void
dilate_end_frame_filter
(
AVFilterContext
*
ctx
,
IplImage
*
inimg
,
IplImage
*
outimg
)
{
OCVContext
*
ocv
=
ctx
->
priv
;
DilateContext
*
dilate
=
ocv
->
priv
;
cvDilate
(
inimg
,
outimg
,
dilate
->
kernel
,
dilate
->
nb_iterations
);
}
typedef
struct
{
const
char
*
name
;
size_t
priv_size
;
...
...
@@ -136,6 +300,7 @@ typedef struct {
}
OCVFilterEntry
;
static
OCVFilterEntry
ocv_filter_entries
[]
=
{
{
"dilate"
,
sizeof
(
DilateContext
),
dilate_init
,
dilate_uninit
,
dilate_end_frame_filter
},
{
"smooth"
,
sizeof
(
SmoothContext
),
smooth_init
,
NULL
,
smooth_end_frame_filter
},
};
...
...
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