Skip to content
Projects
Groups
Snippets
Help
Loading...
Sign in / Register
Toggle navigation
O
opencv
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
opencv
Commits
a6f5e1f0
Commit
a6f5e1f0
authored
Aug 24, 2017
by
tribta
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Tutorial Filter2D
parent
08515281
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
297 additions
and
87 deletions
+297
-87
filter_2d.markdown
doc/tutorials/imgproc/imgtrans/filter_2d/filter_2d.markdown
+112
-43
table_of_content_imgproc.markdown
doc/tutorials/imgproc/table_of_content_imgproc.markdown
+2
-0
filter2D_demo.cpp
samples/cpp/tutorial_code/ImgTrans/filter2D_demo.cpp
+48
-44
Filter2D_Demo.java
...s/java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java
+81
-0
filter2D.py
samples/python/tutorial_code/ImgTrans/Filter2D/filter2D.py
+54
-0
No files found.
doc/tutorials/imgproc/imgtrans/filter_2d/filter_2d.markdown
View file @
a6f5e1f0
Making your own linear filters! {#tutorial_filter_2d}
===============================
@prev_tutorial{tutorial_threshold_inRange}
@next_tutorial{tutorial_copyMakeBorder}
Goal
----
In this tutorial you will learn how to:
-
Use the OpenCV function
@ref cv::filter2D
to create your own linear filters.
-
Use the OpenCV function
**filter2D()**
to create your own linear filters.
Theory
------
...
...
@@ -40,61 +43,127 @@ Expressing the procedure above in the form of an equation we would have:
\f
[
H(x,y) = \sum_{i=0}^{M_{i} - 1} \sum_{j=0}^{M_{j}-1} I(x+i - a_{i}, y + j - a_{j})K(i,j)\f
]
Fortunately, OpenCV provides you with the function
@ref cv::filter2D
so you do not have to code all
Fortunately, OpenCV provides you with the function
**filter2D()**
so you do not have to code all
these operations.
Code
----
-#
**What does this program do?**
-
Loads an image
-
Performs a
*normalized box filter*
. For instance, for a kernel of size
\f
$size = 3
\f
$, the
kernel would be:
### What does this program do?
-
Loads an image
-
Performs a
*normalized box filter*
. For instance, for a kernel of size
\f
$size = 3
\f
$, the
kernel would be:
\f[K = \dfrac{1}{3 \cdot 3} \begin{bmatrix}
1 & 1 & 1 \\
\f
[
K =
\d
frac{1}{3
\c
dot 3}
\b
egin{bmatrix}
1 & 1 & 1
\\
1 & 1 & 1
\\
1 & 1 & 1
\end{bmatrix}\f]
\e
nd{bmatrix}
\f
]
The program will perform the filter operation with kernels of sizes 3, 5, 7, 9 and 11.
The program will perform the filter operation with kernels of sizes 3, 5, 7, 9 and 11.
-
The filter output (with each kernel) will be shown during 500 milliseconds
- The filter output (with each kernel) will be shown during 500 milliseconds
Code
----
-# The tutorial code's is shown lines below. You can also download it from
[
here
](
https://github.com/opencv/opencv/tree/master/samples/cpp/tutorial_code/ImgTrans/filter2D_demo.cpp
)
@include cpp/tutorial_code/ImgTrans/filter2D_demo.cpp
The tutorial code's is shown in the lines below.
@add_toggle_cpp
You can also download it from
[
here
](
https://raw.githubusercontent.com/opencv/opencv/master/samples/cpp/tutorial_code/ImgTrans/filter2D_demo.cpp
)
@include cpp/tutorial_code/ImgTrans/filter2D_demo.cpp
@end_toggle
@add_toggle_java
You can also download it from
[
here
](
https://raw.githubusercontent.com/opencv/opencv/master/samples/java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java
)
@include java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java
@end_toggle
@add_toggle_python
You can also download it from
[
here
](
https://raw.githubusercontent.com/opencv/opencv/master/samples/python/tutorial_code/ImgTrans/Filter2D/filter2D.py
)
@include python/tutorial_code/ImgTrans/Filter2D/filter2D.py
@end_toggle
Explanation
-----------
-# Load an image
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp load
-# Initialize the arguments for the linear filter
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp init_arguments
-# Perform an infinite loop updating the kernel size and applying our linear filter to the input
image. Let's analyze that more in detail:
-# First we define the kernel our filter is going to use. Here it is:
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp update_kernel
The first line is to update the
*kernel_size*
to odd values in the range:
\f
$
[
3,11
]
\f
$. The second
line actually builds the kernel by setting its value to a matrix filled with
\f
$1's
\f
$ and
normalizing it by dividing it between the number of elements.
-# After setting the kernel, we can generate the filter by using the function @ref cv::filter2D :
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp apply_filter
The arguments denote:
-# *src*: Source image
-# *dst*: Destination image
-# *ddepth*: The depth of *dst*. A negative value (such as \f$-1\f$) indicates that the depth is
#### Load an image
@add_toggle_cpp
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp load
@end_toggle
@add_toggle_java
@snippet java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java load
@end_toggle
@add_toggle_python
@snippet python/tutorial_code/ImgTrans/Filter2D/filter2D.py load
@end_toggle
#### Initialize the arguments
@add_toggle_cpp
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp init_arguments
@end_toggle
@add_toggle_java
@snippet java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java init_arguments
@end_toggle
@add_toggle_python
@snippet python/tutorial_code/ImgTrans/Filter2D/filter2D.py init_arguments
@end_toggle
##### Loop
Perform an infinite loop updating the kernel size and applying our linear filter to the input
image. Let's analyze that more in detail:
-
First we define the kernel our filter is going to use. Here it is:
@add_toggle_cpp
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp update_kernel
@end_toggle
@add_toggle_java
@snippet java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java update_kernel
@end_toggle
@add_toggle_python
@snippet python/tutorial_code/ImgTrans/Filter2D/filter2D.py update_kernel
@end_toggle
The first line is to update the
*kernel_size*
to odd values in the range:
\f
$
[
3,11
]
\f
$.
The second line actually builds the kernel by setting its value to a matrix filled with
\f
$1's
\f
$ and normalizing it by dividing it between the number of elements.
-
After setting the kernel, we can generate the filter by using the function
**filter2D()**
:
@add_toggle_cpp
@snippet cpp/tutorial_code/ImgTrans/filter2D_demo.cpp apply_filter
@end_toggle
@add_toggle_java
@snippet java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java apply_filter
@end_toggle
@add_toggle_python
@snippet python/tutorial_code/ImgTrans/Filter2D/filter2D.py apply_filter
@end_toggle
-
The arguments denote:
-
*src*
: Source image
-
*dst*
: Destination image
-
*ddepth*
: The depth of
*dst*
. A negative value (such as
\f
$-1
\f
$) indicates that the depth is
the same as the source.
-#
*kernel*: The kernel to be scanned through the image
-#
*anchor*: The position of the anchor relative to its kernel. The location *Point(-1, -1)*
indicates the center by default.
-#
*delta*: A value to be added to each pixel during the correlation. By default it is \f$0\f$
-#
*BORDER_DEFAULT*: We let this value by default (more details in the following tutorial)
-
*kernel*
: The kernel to be scanned through the image
-
*anchor*
: The position of the anchor relative to its kernel. The location
*Point(-1, -1)*
indicates the center by default.
-
*delta*
: A value to be added to each pixel during the correlation. By default it is
\f
$0
\f
$
-
*BORDER_DEFAULT*
: We let this value by default (more details in the following tutorial)
-
#
Our program will effectuate a
*while*
loop, each 500 ms the kernel size of our filter will be
-
Our program will effectuate a
*while*
loop, each 500 ms the kernel size of our filter will be
updated in the range indicated.
Results
...
...
@@ -104,4 +173,4 @@ Results
result should be a window that shows an image blurred by a normalized filter. Each 0.5 seconds
the kernel size should change, as can be seen in the series of snapshots below:
![](images/filter_2d_tutorial_result.jpg)
![](
images/filter_2d_tutorial_result.jpg
)
doc/tutorials/imgproc/table_of_content_imgproc.markdown
View file @
a6f5e1f0
...
...
@@ -77,6 +77,8 @@ In this section you will learn about the image processing (manipulation) functio
-
@subpage tutorial_filter_2d
*Languages:* C++, Java, Python
*Compatibility:* \> OpenCV 2.0
*Author:* Ana Huamán
...
...
samples/cpp/tutorial_code/ImgTrans/filter2D_demo.cpp
View file @
a6f5e1f0
...
...
@@ -15,56 +15,60 @@ using namespace cv;
*/
int
main
(
int
argc
,
char
**
argv
)
{
/
// Declare variables
Mat
src
,
dst
;
// Declare variables
Mat
src
,
dst
;
Mat
kernel
;
Point
anchor
;
double
delta
;
int
ddepth
;
int
kernel_size
;
const
char
*
window_name
=
"filter2D Demo"
;
Mat
kernel
;
Point
anchor
;
double
delta
;
int
ddepth
;
int
kernel_size
;
const
char
*
window_name
=
"filter2D Demo"
;
//![load]
String
imageName
(
"../data/lena.jpg"
);
// by default
if
(
argc
>
1
)
{
imageName
=
argv
[
1
];
}
src
=
imread
(
imageName
,
IMREAD_COLOR
);
// Load an image
//![load]
const
char
*
imageName
=
argc
>=
2
?
argv
[
1
]
:
"../data/lena.jpg"
;
if
(
src
.
empty
()
)
{
return
-
1
;
}
//![load]
// Loads an image
src
=
imread
(
imageName
,
IMREAD_COLOR
);
// Load an image
//![init_arguments]
/// Initialize arguments for the filter
anchor
=
Point
(
-
1
,
-
1
);
delta
=
0
;
ddepth
=
-
1
;
//![init_arguments]
if
(
src
.
empty
()
)
{
printf
(
" Error opening image
\n
"
);
printf
(
" Program Arguments: [image_name -- default ../data/lena.jpg]
\n
"
);
return
-
1
;
}
//![load]
/// Loop - Will filter the image with different kernel sizes each 0.5 seconds
int
ind
=
0
;
for
(;;)
{
char
c
=
(
char
)
waitKey
(
500
);
/// Press 'ESC' to exit the program
if
(
c
==
27
)
{
break
;
}
//![init_arguments]
// Initialize arguments for the filter
anchor
=
Point
(
-
1
,
-
1
);
delta
=
0
;
ddepth
=
-
1
;
//![init_arguments]
//![update_kernel]
/// Update kernel size for a normalized box filter
kernel_size
=
3
+
2
*
(
ind
%
5
);
kernel
=
Mat
::
ones
(
kernel_size
,
kernel_size
,
CV_32F
)
/
(
float
)(
kernel_size
*
kernel_size
);
//![update_kernel]
// Loop - Will filter the image with different kernel sizes each 0.5 seconds
int
ind
=
0
;
for
(;;)
{
//![update_kernel]
// Update kernel size for a normalized box filter
kernel_size
=
3
+
2
*
(
ind
%
5
);
kernel
=
Mat
::
ones
(
kernel_size
,
kernel_size
,
CV_32F
)
/
(
float
)(
kernel_size
*
kernel_size
);
//![update_kernel]
//![apply_filter]
filter2D
(
src
,
dst
,
ddepth
,
kernel
,
anchor
,
delta
,
BORDER_DEFAULT
);
//![apply_filter]
imshow
(
window_name
,
dst
);
ind
++
;
}
//![apply_filter]
// Apply filter
filter2D
(
src
,
dst
,
ddepth
,
kernel
,
anchor
,
delta
,
BORDER_DEFAULT
);
//![apply_filter]
imshow
(
window_name
,
dst
);
return
0
;
char
c
=
(
char
)
waitKey
(
500
);
// Press 'ESC' to exit the program
if
(
c
==
27
)
{
break
;
}
ind
++
;
}
return
0
;
}
samples/java/tutorial_code/ImgTrans/Filter2D/Filter2D_Demo.java
0 → 100644
View file @
a6f5e1f0
/**
* @file Filter2D_demo.java
* @brief Sample code that shows how to implement your own linear filters by using filter2D function
*/
import
org.opencv.core.*
;
import
org.opencv.core.Point
;
import
org.opencv.highgui.HighGui
;
import
org.opencv.imgcodecs.Imgcodecs
;
import
org.opencv.imgproc.Imgproc
;
class
Filter2D_DemoRun
{
public
void
run
(
String
[]
args
)
{
// Declare variables
Mat
src
,
dst
=
new
Mat
();
Mat
kernel
=
new
Mat
();
Point
anchor
;
double
delta
;
int
ddepth
;
int
kernel_size
;
String
window_name
=
"filter2D Demo"
;
//! [load]
String
imageName
=
((
args
.
length
>
0
)
?
args
[
0
]
:
"../data/lena.jpg"
);
// Load an image
src
=
Imgcodecs
.
imread
(
imageName
,
Imgcodecs
.
IMREAD_COLOR
);
// Check if image is loaded fine
if
(
src
.
empty
()
)
{
System
.
out
.
println
(
"Error opening image!"
);
System
.
out
.
println
(
"Program Arguments: [image_name -- default ../data/lena.jpg] \n"
);
System
.
exit
(-
1
);
}
//! [load]
//! [init_arguments]
// Initialize arguments for the filter
anchor
=
new
Point
(
-
1
,
-
1
);
delta
=
0.0
;
ddepth
=
-
1
;
//! [init_arguments]
// Loop - Will filter the image with different kernel sizes each 0.5 seconds
int
ind
=
0
;
while
(
true
)
{
//! [update_kernel]
// Update kernel size for a normalized box filter
kernel_size
=
3
+
2
*(
ind
%
5
);
Mat
ones
=
Mat
.
ones
(
kernel_size
,
kernel_size
,
CvType
.
CV_32F
);
Core
.
multiply
(
ones
,
new
Scalar
(
1
/(
double
)(
kernel_size
*
kernel_size
)),
kernel
);
//! [update_kernel]
//! [apply_filter]
// Apply filter
Imgproc
.
filter2D
(
src
,
dst
,
ddepth
,
kernel
,
anchor
,
delta
,
Core
.
BORDER_DEFAULT
);
//! [apply_filter]
HighGui
.
imshow
(
window_name
,
dst
);
int
c
=
HighGui
.
waitKey
(
500
);
// Press 'ESC' to exit the program
if
(
c
==
27
)
{
break
;
}
ind
++;
}
System
.
exit
(
0
);
}
}
public
class
Filter2D_Demo
{
public
static
void
main
(
String
[]
args
)
{
// Load the native library.
System
.
loadLibrary
(
Core
.
NATIVE_LIBRARY_NAME
);
new
Filter2D_DemoRun
().
run
(
args
);
}
}
samples/python/tutorial_code/ImgTrans/Filter2D/filter2D.py
0 → 100644
View file @
a6f5e1f0
"""
@file filter2D.py
@brief Sample code that shows how to implement your own linear filters by using filter2D function
"""
import
sys
import
cv2
import
numpy
as
np
def
main
(
argv
):
window_name
=
'filter2D Demo'
## [load]
imageName
=
argv
[
0
]
if
len
(
argv
)
>
0
else
"../data/lena.jpg"
# Loads an image
src
=
cv2
.
imread
(
imageName
,
cv2
.
IMREAD_COLOR
)
# Check if image is loaded fine
if
src
is
None
:
print
(
'Error opening image!'
)
print
(
'Usage: filter2D.py [image_name -- default ../data/lena.jpg]
\n
'
)
return
-
1
## [load]
## [init_arguments]
# Initialize ddepth argument for the filter
ddepth
=
-
1
## [init_arguments]
# Loop - Will filter the image with different kernel sizes each 0.5 seconds
ind
=
0
while
True
:
## [update_kernel]
# Update kernel size for a normalized box filter
kernel_size
=
3
+
2
*
(
ind
%
5
)
kernel
=
np
.
ones
((
kernel_size
,
kernel_size
),
dtype
=
np
.
float32
)
kernel
/=
(
kernel_size
*
kernel_size
)
## [update_kernel]
## [apply_filter]
# Apply filter
dst
=
cv2
.
filter2D
(
src
,
ddepth
,
kernel
)
## [apply_filter]
cv2
.
imshow
(
window_name
,
dst
)
c
=
cv2
.
waitKey
(
500
)
if
c
==
27
:
break
ind
+=
1
return
0
if
__name__
==
"__main__"
:
main
(
sys
.
argv
[
1
:])
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