Add Java and Python code for the following imgproc tutorials: Affine Transformations...
authorcatree <catree.catreus@outlook.com>
Wed, 23 May 2018 17:44:27 +0000 (19:44 +0200)
committercatree <catree.catreus@outlook.com>
Wed, 23 May 2018 23:11:28 +0000 (01:11 +0200)
24 files changed:
doc/tutorials/imgproc/histograms/back_projection/back_projection.markdown
doc/tutorials/imgproc/histograms/histogram_calculation/histogram_calculation.markdown
doc/tutorials/imgproc/histograms/histogram_comparison/histogram_comparison.markdown
doc/tutorials/imgproc/histograms/histogram_equalization/histogram_equalization.markdown
doc/tutorials/imgproc/imgtrans/warp_affine/warp_affine.markdown
doc/tutorials/imgproc/table_of_content_imgproc.markdown
samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp
samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp
samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo2.cpp
samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp
samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp
samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp
samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java [new file with mode: 0644]
samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo2.java [new file with mode: 0644]
samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java [new file with mode: 0644]
samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java [new file with mode: 0644]
samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java [new file with mode: 0644]
samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java [new file with mode: 0644]
samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py [new file with mode: 0644]
samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo2.py [new file with mode: 0644]
samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py [new file with mode: 0644]
samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py [new file with mode: 0644]
samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py [new file with mode: 0644]
samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py [new file with mode: 0644]

index 8657541..4b67f0b 100644 (file)
@@ -67,46 +67,104 @@ Code
     -   Calculate the histogram (and update it if the bins change) and the backprojection of the
         same image.
     -   Display the backprojection and the histogram in windows.
--   **Downloadable code**:
 
-    -#  Click
+@add_toggle_cpp
+-   **Downloadable code**:
+    -   Click
         [here](https://github.com/opencv/opencv/tree/master/samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp)
         for the basic version (explained in this tutorial).
-    -#  For stuff slightly fancier (using H-S histograms and floodFill to define a mask for the
+    -   For stuff slightly fancier (using H-S histograms and floodFill to define a mask for the
         skin area) you can check the [improved
         demo](https://github.com/opencv/opencv/tree/master/samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo2.cpp)
-    -#  ...or you can always check out the classical
+    -   ...or you can always check out the classical
         [camshiftdemo](https://github.com/opencv/opencv/tree/master/samples/cpp/camshiftdemo.cpp)
         in samples.
 
 -   **Code at glance:**
 @include samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp
+@end_toggle
+
+@add_toggle_java
+-   **Downloadable code**:
+    -   Click
+        [here](https://github.com/opencv/opencv/tree/master/samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java)
+        for the basic version (explained in this tutorial).
+    -   For stuff slightly fancier (using H-S histograms and floodFill to define a mask for the
+        skin area) you can check the [improved
+        demo](https://github.com/opencv/opencv/tree/master/samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo2.java)
+    -   ...or you can always check out the classical
+        [camshiftdemo](https://github.com/opencv/opencv/tree/master/samples/cpp/camshiftdemo.cpp)
+        in samples.
+
+-   **Code at glance:**
+@include samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java
+@end_toggle
+
+@add_toggle_python
+-   **Downloadable code**:
+    -   Click
+        [here](https://github.com/opencv/opencv/tree/master/samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py)
+        for the basic version (explained in this tutorial).
+    -   For stuff slightly fancier (using H-S histograms and floodFill to define a mask for the
+        skin area) you can check the [improved
+        demo](https://github.com/opencv/opencv/tree/master/samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo2.py)
+    -   ...or you can always check out the classical
+        [camshiftdemo](https://github.com/opencv/opencv/tree/master/samples/cpp/camshiftdemo.cpp)
+        in samples.
+
+-   **Code at glance:**
+@include samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py
+@end_toggle
 
 Explanation
 -----------
 
--#  Declare the matrices to store our images and initialize the number of bins to be used by our
-    histogram:
-    @code{.cpp}
-    Mat src; Mat hsv; Mat hue;
-    int bins = 25;
-    @endcode
--#  Read the input image and transform it to HSV format:
-    @code{.cpp}
-    src = imread( argv[1], 1 );
-    cvtColor( src, hsv, COLOR_BGR2HSV );
-    @endcode
--#  For this tutorial, we will use only the Hue value for our 1-D histogram (check out the fancier
+-   Read the input image:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Read the image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Read the image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Read the image
+    @end_toggle
+
+-   Transform it to HSV format:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Transform it to HSV
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Transform it to HSV
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Transform it to HSV
+    @end_toggle
+
+-   For this tutorial, we will use only the Hue value for our 1-D histogram (check out the fancier
     code in the links above if you want to use the more standard H-S histogram, which yields better
     results):
-    @code{.cpp}
-    hue.create( hsv.size(), hsv.depth() );
-    int ch[] = { 0, 0 };
-    mixChannels( &hsv, 1, &hue, 1, ch, 1 );
-    @endcode
-    as you see, we use the function @ref cv::mixChannels to get only the channel 0 (Hue) from
-    the hsv image. It gets the following parameters:
 
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Use only the Hue value
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Use only the Hue value
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Use only the Hue value
+    @end_toggle
+
+-   as you see, we use the function @ref cv::mixChannels to get only the channel 0 (Hue) from
+    the hsv image. It gets the following parameters:
     -   **&hsv:** The source array from which the channels will be copied
     -   **1:** The number of source arrays
     -   **&hue:** The destination array of the copied channels
@@ -115,59 +173,108 @@ Explanation
         case, the Hue(0) channel of &hsv is being copied to the 0 channel of &hue (1-channel)
     -   **1:** Number of index pairs
 
--#  Create a Trackbar for the user to enter the bin values. Any change on the Trackbar means a call
+-   Create a Trackbar for the user to enter the bin values. Any change on the Trackbar means a call
     to the **Hist_and_Backproj** callback function.
-    @code{.cpp}
-    char* window_image = "Source image";
-    namedWindow( window_image, WINDOW_AUTOSIZE );
-    createTrackbar("* Hue  bins: ", window_image, &bins, 180, Hist_and_Backproj );
-    Hist_and_Backproj(0, 0);
-    @endcode
--#  Show the image and wait for the user to exit the program:
-    @code{.cpp}
-    imshow( window_image, src );
-
-    waitKey(0);
-    return 0;
-    @endcode
--#  **Hist_and_Backproj function:** Initialize the arguments needed for @ref cv::calcHist . The
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Create Trackbar to enter the number of bins
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Create Trackbar to enter the number of bins
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Create Trackbar to enter the number of bins
+    @end_toggle
+
+-   Show the image and wait for the user to exit the program:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Show the image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Show the image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Show the image
+    @end_toggle
+
+-   **Hist_and_Backproj function:** Initialize the arguments needed for @ref cv::calcHist . The
     number of bins comes from the Trackbar:
-    @code{.cpp}
-    void Hist_and_Backproj(int, void* )
-    {
-      MatND hist;
-      int histSize = MAX( bins, 2 );
-      float hue_range[] = { 0, 180 };
-      const float* ranges = { hue_range };
-    @endcode
--#  Calculate the Histogram and normalize it to the range \f$[0,255]\f$
-    @code{.cpp}
-    calcHist( &hue, 1, 0, Mat(), hist, 1, &histSize, &ranges, true, false );
-    normalize( hist, hist, 0, 255, NORM_MINMAX, -1, Mat() );
-    @endcode
--#  Get the Backprojection of the same image by calling the function @ref cv::calcBackProject
-    @code{.cpp}
-    MatND backproj;
-    calcBackProject( &hue, 1, 0, hist, backproj, &ranges, 1, true );
-    @endcode
-    all the arguments are known (the same as used to calculate the histogram), only we add the
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp initialize
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java initialize
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py initialize
+    @end_toggle
+
+-   Calculate the Histogram and normalize it to the range \f$[0,255]\f$
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Get the Histogram and normalize it
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Get the Histogram and normalize it
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Get the Histogram and normalize it
+    @end_toggle
+
+-   Get the Backprojection of the same image by calling the function @ref cv::calcBackProject
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Get Backprojection
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Get Backprojection
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Get Backprojection
+    @end_toggle
+
+-   all the arguments are known (the same as used to calculate the histogram), only we add the
     backproj matrix, which will store the backprojection of the source image (&hue)
 
--#  Display backproj:
-    @code{.cpp}
-    imshow( "BackProj", backproj );
-    @endcode
--#  Draw the 1-D Hue histogram of the image:
-    @code{.cpp}
-    int w = 400; int h = 400;
-    int bin_w = cvRound( (double) w / histSize );
-    Mat histImg = Mat::zeros( w, h, CV_8UC3 );
-
-    for( int i = 0; i < bins; i ++ )
-       { rectangle( histImg, Point( i*bin_w, h ), Point( (i+1)*bin_w, h - cvRound( hist.at<float>(i)*h/255.0 ) ), Scalar( 0, 0, 255 ), -1 ); }
-
-    imshow( "Histogram", histImg );
-    @endcode
+-   Display backproj:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Draw the backproj
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Draw the backproj
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Draw the backproj
+    @end_toggle
+
+-   Draw the 1-D Hue histogram of the image:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcBackProject_Demo1.cpp Draw the histogram
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java Draw the histogram
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py Draw the histogram
+    @end_toggle
 
 Results
 -------
index 2907bf3..30930cd 100644 (file)
@@ -17,7 +17,8 @@ histogram called *Image histogram*. Now we will considerate it in its more gener
 
 -   Histograms are collected *counts* of data organized into a set of predefined *bins*
 -   When we say *data* we are not restricting it to be intensity values (as we saw in the previous
-    Tutorial). The data collected can be whatever feature you find useful to describe your image.
+    Tutorial @ref tutorial_histogram_equalization). The data collected can be whatever feature you find
+    useful to describe your image.
 -   Let's see an example. Imagine that a Matrix contains information of an image (i.e. intensity in
     the range \f$0-255\f$):
 
@@ -65,122 +66,193 @@ Code
     -   Splits the image into its R, G and B planes using the function @ref cv::split
     -   Calculate the Histogram of each 1-channel plane by calling the function @ref cv::calcHist
     -   Plot the three histograms in a window
+
+@add_toggle_cpp
 -   **Downloadable code**: Click
     [here](https://github.com/opencv/opencv/tree/master/samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp)
+
 -   **Code at glance:**
     @include samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp
+@end_toggle
+
+@add_toggle_java
+-   **Downloadable code**: Click
+    [here](https://github.com/opencv/opencv/tree/master/samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java)
+
+-   **Code at glance:**
+    @include samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java
+@end_toggle
+
+@add_toggle_python
+-   **Downloadable code**: Click
+    [here](https://github.com/opencv/opencv/tree/master/samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py)
+
+-   **Code at glance:**
+    @include samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py
+@end_toggle
 
 Explanation
 -----------
 
--#  Create the necessary matrices:
-    @code{.cpp}
-    Mat src, dst;
-    @endcode
--#  Load the source image
-    @code{.cpp}
-    src = imread( argv[1], 1 );
+-   Load the source image
 
-    if( !src.data )
-      { return -1; }
-    @endcode
--#  Separate the source image in its three R,G and B planes. For this we use the OpenCV function
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Load image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Load image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Load image
+    @end_toggle
+
+-   Separate the source image in its three R,G and B planes. For this we use the OpenCV function
     @ref cv::split :
-    @code{.cpp}
-    vector<Mat> bgr_planes;
-    split( src, bgr_planes );
-    @endcode
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Separate the image in 3 places ( B, G and R )
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Separate the image in 3 places ( B, G and R )
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Separate the image in 3 places ( B, G and R )
+    @end_toggle
     our input is the image to be divided (this case with three channels) and the output is a vector
     of Mat )
 
--#  Now we are ready to start configuring the **histograms** for each plane. Since we are working
+-   Now we are ready to start configuring the **histograms** for each plane. Since we are working
     with the B, G and R planes, we know that our values will range in the interval \f$[0,255]\f$
-    -#  Establish number of bins (5, 10...):
-        @code{.cpp}
-        int histSize = 256; //from 0 to 255
-        @endcode
-    -#  Set the range of values (as we said, between 0 and 255 )
-        @code{.cpp}
-        /// Set the ranges ( for B,G,R) )
-        float range[] = { 0, 256 } ; //the upper boundary is exclusive
-        const float* histRange = { range };
-        @endcode
-    -#  We want our bins to have the same size (uniform) and to clear the histograms in the
-        beginning, so:
-        @code{.cpp}
-        bool uniform = true; bool accumulate = false;
-        @endcode
-    -#  Finally, we create the Mat objects to save our histograms. Creating 3 (one for each plane):
-        @code{.cpp}
-        Mat b_hist, g_hist, r_hist;
-        @endcode
-    -#  We proceed to calculate the histograms by using the OpenCV function @ref cv::calcHist :
-        @code{.cpp}
-        /// Compute the histograms:
-        calcHist( &bgr_planes[0], 1, 0, Mat(), b_hist, 1, &histSize, &histRange, uniform, accumulate );
-        calcHist( &bgr_planes[1], 1, 0, Mat(), g_hist, 1, &histSize, &histRange, uniform, accumulate );
-        calcHist( &bgr_planes[2], 1, 0, Mat(), r_hist, 1, &histSize, &histRange, uniform, accumulate );
-        @endcode
-        where the arguments are:
-
-        -   **&bgr_planes[0]:** The source array(s)
-        -   **1**: The number of source arrays (in this case we are using 1. We can enter here also
-            a list of arrays )
-        -   **0**: The channel (*dim*) to be measured. In this case it is just the intensity (each
-            array is single-channel) so we just write 0.
-        -   **Mat()**: A mask to be used on the source array ( zeros indicating pixels to be ignored
-            ). If not defined it is not used
-        -   **b_hist**: The Mat object where the histogram will be stored
-        -   **1**: The histogram dimensionality.
-        -   **histSize:** The number of bins per each used dimension
-        -   **histRange:** The range of values to be measured per each dimension
-        -   **uniform** and **accumulate**: The bin sizes are the same and the histogram is cleared
-            at the beginning.
-
--#  Create an image to display the histograms:
-    @code{.cpp}
-    // Draw the histograms for R, G and B
-    int hist_w = 512; int hist_h = 400;
-    int bin_w = cvRound( (double) hist_w/histSize );
 
-    Mat histImage( hist_h, hist_w, CV_8UC3, Scalar( 0,0,0) );
-    @endcode
--#  Notice that before drawing, we first @ref cv::normalize the histogram so its values fall in the
+-   Establish the number of bins (5, 10...):
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Establish the number of bins
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Establish the number of bins
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Establish the number of bins
+    @end_toggle
+
+-   Set the range of values (as we said, between 0 and 255 )
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Set the ranges ( for B,G,R) )
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Set the ranges ( for B,G,R) )
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Set the ranges ( for B,G,R) )
+    @end_toggle
+
+-   We want our bins to have the same size (uniform) and to clear the histograms in the
+    beginning, so:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Set histogram param
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Set histogram param
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Set histogram param
+    @end_toggle
+
+-   We proceed to calculate the histograms by using the OpenCV function @ref cv::calcHist :
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Compute the histograms
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Compute the histograms
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Compute the histograms
+    @end_toggle
+
+-   where the arguments are (**C++ code**):
+    -   **&bgr_planes[0]:** The source array(s)
+    -   **1**: The number of source arrays (in this case we are using 1. We can enter here also
+        a list of arrays )
+    -   **0**: The channel (*dim*) to be measured. In this case it is just the intensity (each
+        array is single-channel) so we just write 0.
+    -   **Mat()**: A mask to be used on the source array ( zeros indicating pixels to be ignored
+        ). If not defined it is not used
+    -   **b_hist**: The Mat object where the histogram will be stored
+    -   **1**: The histogram dimensionality.
+    -   **histSize:** The number of bins per each used dimension
+    -   **histRange:** The range of values to be measured per each dimension
+    -   **uniform** and **accumulate**: The bin sizes are the same and the histogram is cleared
+        at the beginning.
+
+-   Create an image to display the histograms:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Draw the histograms for B, G and R
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Draw the histograms for B, G and R
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Draw the histograms for B, G and R
+    @end_toggle
+
+-   Notice that before drawing, we first @ref cv::normalize the histogram so its values fall in the
     range indicated by the parameters entered:
-    @code{.cpp}
-    /// Normalize the result to [ 0, histImage.rows ]
-    normalize(b_hist, b_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
-    normalize(g_hist, g_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
-    normalize(r_hist, r_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
-    @endcode
-    this function receives these arguments:
 
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Normalize the result to ( 0, histImage.rows )
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Normalize the result to ( 0, histImage.rows )
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Normalize the result to ( 0, histImage.rows )
+    @end_toggle
+
+-   this function receives these arguments (**C++ code**):
     -   **b_hist:** Input array
     -   **b_hist:** Output normalized array (can be the same)
-    -   **0** and\**histImage.rows: For this example, they are the lower and upper limits to
-        normalize the values ofr_hist*\*
+    -   **0** and **histImage.rows**: For this example, they are the lower and upper limits to
+        normalize the values of **r_hist**
     -   **NORM_MINMAX:** Argument that indicates the type of normalization (as described above, it
         adjusts the values between the two limits set before)
     -   **-1:** Implies that the output normalized array will be the same type as the input
     -   **Mat():** Optional mask
 
--#  Finally, observe that to access the bin (in this case in this 1D-Histogram):
-    @code{.cpp}
-    /// Draw for each channel
-    for( int i = 1; i < histSize; i++ )
-    {
-        line( histImage, Point( bin_w*(i-1), hist_h - cvRound(b_hist.at<float>(i-1)) ) ,
-                         Point( bin_w*(i), hist_h - cvRound(b_hist.at<float>(i)) ),
-                         Scalar( 255, 0, 0), 2, 8, 0  );
-        line( histImage, Point( bin_w*(i-1), hist_h - cvRound(g_hist.at<float>(i-1)) ) ,
-                         Point( bin_w*(i), hist_h - cvRound(g_hist.at<float>(i)) ),
-                         Scalar( 0, 255, 0), 2, 8, 0  );
-        line( histImage, Point( bin_w*(i-1), hist_h - cvRound(r_hist.at<float>(i-1)) ) ,
-                         Point( bin_w*(i), hist_h - cvRound(r_hist.at<float>(i)) ),
-                         Scalar( 0, 0, 255), 2, 8, 0  );
-    }
-    @endcode
-    we use the expression:
+-   Observe that to access the bin (in this case in this 1D-Histogram):
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Draw for each channel
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Draw for each channel
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Draw for each channel
+    @end_toggle
+    we use the expression (**C++ code**):
     @code{.cpp}
     b_hist.at<float>(i)
     @endcode
@@ -189,20 +261,24 @@ Explanation
     b_hist.at<float>( i, j )
     @endcode
 
--#  Finally we display our histograms and wait for the user to exit:
-    @code{.cpp}
-    namedWindow("calcHist Demo", WINDOW_AUTOSIZE );
-    imshow("calcHist Demo", histImage );
+-   Finally we display our histograms and wait for the user to exit:
 
-    waitKey(0);
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/calcHist_Demo.cpp Display
+    @end_toggle
 
-    return 0;
-    @endcode
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java Display
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py Display
+    @end_toggle
 
 Result
 ------
 
--#  Using as input argument an image like the shown below:
+-#  Using as input argument an image like the one shown below:
 
     ![](images/Histogram_Calculation_Original_Image.jpg)
 
index 37ae5ea..23c478a 100644 (file)
@@ -43,90 +43,118 @@ Code
     -   Compare the histogram of the *base image* with respect to the 2 test histograms, the
         histogram of the lower half base image and with the same base image histogram.
     -   Display the numerical matching parameters obtained.
+
+@add_toggle_cpp
 -   **Downloadable code**: Click
     [here](https://github.com/opencv/opencv/tree/master/samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp)
+
+-   **Code at glance:**
+    @include samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp
+@end_toggle
+
+@add_toggle_java
+-   **Downloadable code**: Click
+    [here](https://github.com/opencv/opencv/tree/master/samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java)
+
 -   **Code at glance:**
+    @include samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java
+@end_toggle
+
+@add_toggle_python
+-   **Downloadable code**: Click
+    [here](https://github.com/opencv/opencv/tree/master/samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py)
 
-@include cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp
+-   **Code at glance:**
+    @include samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py
+@end_toggle
 
 Explanation
 -----------
 
--#  Declare variables such as the matrices to store the base image and the two other images to
-    compare ( BGR and HSV )
-    @code{.cpp}
-    Mat src_base, hsv_base;
-    Mat src_test1, hsv_test1;
-    Mat src_test2, hsv_test2;
-    Mat hsv_half_down;
-    @endcode
--#  Load the base image (src_base) and the other two test images:
-    @code{.cpp}
-    if( argc < 4 )
-      { printf("** Error. Usage: ./compareHist_Demo <image_settings0> <image_setting1> <image_settings2>\n");
-        return -1;
-      }
-
-    src_base = imread( argv[1], 1 );
-    src_test1 = imread( argv[2], 1 );
-    src_test2 = imread( argv[3], 1 );
-    @endcode
--#  Convert them to HSV format:
-    @code{.cpp}
-    cvtColor( src_base, hsv_base, COLOR_BGR2HSV );
-    cvtColor( src_test1, hsv_test1, COLOR_BGR2HSV );
-    cvtColor( src_test2, hsv_test2, COLOR_BGR2HSV );
-    @endcode
--#  Also, create an image of half the base image (in HSV format):
-    @code{.cpp}
-    hsv_half_down = hsv_base( Range( hsv_base.rows/2, hsv_base.rows - 1 ), Range( 0, hsv_base.cols - 1 ) );
-    @endcode
--#  Initialize the arguments to calculate the histograms (bins, ranges and channels H and S ).
-    @code{.cpp}
-    int h_bins = 50; int s_bins = 60;
-    int histSize[] = { h_bins, s_bins };
-
-    float h_ranges[] = { 0, 180 };
-    float s_ranges[] = { 0, 256 };
-
-    const float* ranges[] = { h_ranges, s_ranges };
-
-    int channels[] = { 0, 1 };
-    @endcode
--#  Create the MatND objects to store the histograms:
-    @code{.cpp}
-    MatND hist_base;
-    MatND hist_half_down;
-    MatND hist_test1;
-    MatND hist_test2;
-    @endcode
--#  Calculate the Histograms for the base image, the 2 test images and the half-down base image:
-    @code{.cpp}
-    calcHist( &hsv_base, 1, channels, Mat(), hist_base, 2, histSize, ranges, true, false );
-    normalize( hist_base, hist_base, 0, 1, NORM_MINMAX, -1, Mat() );
-
-    calcHist( &hsv_half_down, 1, channels, Mat(), hist_half_down, 2, histSize, ranges, true, false );
-    normalize( hist_half_down, hist_half_down, 0, 1, NORM_MINMAX, -1, Mat() );
-
-    calcHist( &hsv_test1, 1, channels, Mat(), hist_test1, 2, histSize, ranges, true, false );
-    normalize( hist_test1, hist_test1, 0, 1, NORM_MINMAX, -1, Mat() );
-
-    calcHist( &hsv_test2, 1, channels, Mat(), hist_test2, 2, histSize, ranges, true, false );
-    normalize( hist_test2, hist_test2, 0, 1, NORM_MINMAX, -1, Mat() );
-    @endcode
--#  Apply sequentially the 4 comparison methods between the histogram of the base image (hist_base)
+-   Load the base image (src_base) and the other two test images:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp Load three images with different environment settings
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java Load three images with different environment settings
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Load three images with different environment settings
+    @end_toggle
+
+-   Convert them to HSV format:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp Convert to HSV
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java Convert to HSV
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Convert to HSV
+    @end_toggle
+
+-   Also, create an image of half the base image (in HSV format):
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp Convert to HSV half
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java Convert to HSV half
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Convert to HSV half
+    @end_toggle
+
+-   Initialize the arguments to calculate the histograms (bins, ranges and channels H and S ).
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp Using 50 bins for hue and 60 for saturation
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java Using 50 bins for hue and 60 for saturation
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Using 50 bins for hue and 60 for saturation
+    @end_toggle
+
+-   Calculate the Histograms for the base image, the 2 test images and the half-down base image:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp Calculate the histograms for the HSV images
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java Calculate the histograms for the HSV images
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Calculate the histograms for the HSV images
+    @end_toggle
+
+-   Apply sequentially the 4 comparison methods between the histogram of the base image (hist_base)
     and the other histograms:
-    @code{.cpp}
-    for( int i = 0; i < 4; i++ )
-       { int compare_method = i;
-         double base_base = compareHist( hist_base, hist_base, compare_method );
-         double base_half = compareHist( hist_base, hist_half_down, compare_method );
-         double base_test1 = compareHist( hist_base, hist_test1, compare_method );
-         double base_test2 = compareHist( hist_base, hist_test2, compare_method );
-
-        printf( " Method [%d] Perfect, Base-Half, Base-Test(1), Base-Test(2) : %f, %f, %f, %f \n", i, base_base, base_half , base_test1, base_test2 );
-      }
-    @endcode
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/compareHist_Demo.cpp Apply the histogram comparison methods
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java Apply the histogram comparison methods
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py Apply the histogram comparison methods
+    @end_toggle
 
 Results
 -------
@@ -144,13 +172,13 @@ Results
     are from the same source. For the other two test images, we can observe that they have very
     different lighting conditions, so the matching should not be very good:
 
--#  Here the numeric results:
+-#  Here the numeric results we got with OpenCV 3.4.1:
       *Method*        |  Base - Base |  Base - Half |  Base - Test 1 |  Base - Test 2
     ----------------- | ------------ | ------------ | -------------- | ---------------
-      *Correlation*   |  1.000000    |  0.930766    |  0.182073      |  0.120447
-      *Chi-square*    |  0.000000    |  4.940466    |  21.184536     |  49.273437
-      *Intersection*  |  24.391548   |  14.959809   |  3.889029      |  5.775088
-      *Bhattacharyya* |  0.000000    |  0.222609    |  0.646576      |  0.801869
+      *Correlation*   |  1.000000    |  0.880438    |  0.20457       |  0.0664547
+      *Chi-square*    |  0.000000    |  4.6834      |  2697.98       |  4763.8
+      *Intersection*  |  18.8947     |  13.022      |  5.44085       |  2.58173
+      *Bhattacharyya* |  0.000000    |  0.237887    |  0.679826      |  0.874173
     For the *Correlation* and *Intersection* methods, the higher the metric, the more accurate the
     match. As we can see, the match *base-base* is the highest of all as expected. Also we can observe
     that the match *base-half* is the second best match (as we predicted). For the other two metrics,
index 4fecb15..5a452a7 100644 (file)
@@ -22,7 +22,7 @@ Theory
 ### What is Histogram Equalization?
 
 -   It is a method that improves the contrast in an image, in order to stretch out the intensity
-    range.
+    range (see also the corresponding <a href="https://en.wikipedia.org/wiki/Histogram_equalization">Wikipedia entry</a>).
 -   To make it clearer, from the image above, you can see that the pixels seem clustered around the
     middle of the available range of intensities. What Histogram Equalization does is to *stretch
     out* this range. Take a look at the figure below: The green circles indicate the
@@ -61,53 +61,105 @@ Code
     -   Convert the original image to grayscale
     -   Equalize the Histogram by using the OpenCV function @ref cv::equalizeHist
     -   Display the source and equalized images in a window.
+
+@add_toggle_cpp
 -   **Downloadable code**: Click
     [here](https://github.com/opencv/opencv/tree/master/samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp)
+
 -   **Code at glance:**
     @include samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp
+@end_toggle
+
+@add_toggle_java
+-   **Downloadable code**: Click
+    [here](https://github.com/opencv/opencv/tree/master/samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java)
+
+-   **Code at glance:**
+    @include samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java
+@end_toggle
+
+@add_toggle_python
+-   **Downloadable code**: Click
+    [here](https://github.com/opencv/opencv/tree/master/samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py)
+
+-   **Code at glance:**
+    @include samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py
+@end_toggle
 
 Explanation
 -----------
 
--#  Declare the source and destination images as well as the windows names:
-    @code{.cpp}
-    Mat src, dst;
-
-    char* source_window = "Source image";
-    char* equalized_window = "Equalized Image";
-    @endcode
--#  Load the source image:
-    @code{.cpp}
-    src = imread( argv[1], 1 );
-
-    if( !src.data )
-      { cout<<"Usage: ./Histogram_Demo <path_to_image>"<<endl;
-        return -1;}
-    @endcode
--#  Convert it to grayscale:
-    @code{.cpp}
-    cvtColor( src, src, COLOR_BGR2GRAY );
-    @endcode
--#  Apply histogram equalization with the function @ref cv::equalizeHist :
-    @code{.cpp}
-    equalizeHist( src, dst );
-    @endcode
+-   Load the source image:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp Load image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java Load image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py Load image
+    @end_toggle
+
+-   Convert it to grayscale:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp Convert to grayscale
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java Convert to grayscale
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py Convert to grayscale
+    @end_toggle
+
+-   Apply histogram equalization with the function @ref cv::equalizeHist :
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp Apply Histogram Equalization
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java Apply Histogram Equalization
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py Apply Histogram Equalization
+    @end_toggle
     As it can be easily seen, the only arguments are the original image and the output (equalized)
     image.
 
--#  Display both images (original and equalized) :
-    @code{.cpp}
-    namedWindow( source_window, WINDOW_AUTOSIZE );
-    namedWindow( equalized_window, WINDOW_AUTOSIZE );
-
-    imshow( source_window, src );
-    imshow( equalized_window, dst );
-    @endcode
--#  Wait until user exists the program
-    @code{.cpp}
-    waitKey(0);
-    return 0;
-    @endcode
+-   Display both images (original and equalized):
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp Display results
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java Display results
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py Display results
+    @end_toggle
+
+-   Wait until user exists the program
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/Histograms_Matching/EqualizeHist_Demo.cpp Wait until user exits the program
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java Wait until user exits the program
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py Wait until user exits the program
+    @end_toggle
 
 Results
 -------
index 6ad4cfc..c72fc29 100644 (file)
@@ -80,7 +80,7 @@ Theory
 Code
 ----
 
--#  **What does this program do?**
+-   **What does this program do?**
     -   Loads an image
     -   Applies an Affine Transform to the image. This transform is obtained from the relation
         between three points. We use the function @ref cv::warpAffine for that purpose.
@@ -88,57 +88,88 @@ Code
         the image center
     -   Waits until the user exits the program
 
--#  The tutorial's code is shown below. You can also download it here
-    [here](https://github.com/opencv/opencv/tree/master/samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp)
+@add_toggle_cpp
+-   The tutorial's code is shown below. You can also download it
+    [here](https://raw.githubusercontent.com/opencv/opencv/master/samples/cpp/tutorial_code/ImgProc/Smoothing/Smoothing.cpp)
     @include samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp
+@end_toggle
+
+@add_toggle_java
+-   The tutorial's code is shown below. You can also download it
+    [here](https://raw.githubusercontent.com/opencv/opencv/master/samples/cpp/tutorial_code/ImgProc/Smoothing/Smoothing.cpp)
+    @include samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java
+@end_toggle
+
+@add_toggle_python
+-   The tutorial's code is shown below. You can also download it
+    [here](https://raw.githubusercontent.com/opencv/opencv/master/samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py)
+    @include samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py
+@end_toggle
 
 Explanation
 -----------
 
--#  Declare some variables we will use, such as the matrices to store our results and 2 arrays of
-    points to store the 2D points that define our Affine Transform.
-    @code{.cpp}
-    Point2f srcTri[3];
-    Point2f dstTri[3];
-
-    Mat rot_mat( 2, 3, CV_32FC1 );
-    Mat warp_mat( 2, 3, CV_32FC1 );
-    Mat src, warp_dst, warp_rotate_dst;
-    @endcode
--#  Load an image:
-    @code{.cpp}
-    src = imread( argv[1], 1 );
-    @endcode
--#  Initialize the destination image as having the same size and type as the source:
-    @code{.cpp}
-    warp_dst = Mat::zeros( src.rows, src.cols, src.type() );
-    @endcode
--#  **Affine Transform:** As we explained in lines above, we need two sets of 3 points to derive the
+-   Load an image:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Load the image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Load the image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Load the image
+    @end_toggle
+
+-   **Affine Transform:** As we explained in lines above, we need two sets of 3 points to derive the
     affine transform relation. Have a look:
-    @code{.cpp}
-    srcTri[0] = Point2f( 0, 0 );
-    srcTri[1] = Point2f( src.cols - 1, 0 );
-    srcTri[2] = Point2f( 0, src.rows - 1 );
-
-    dstTri[0] = Point2f( src.cols*0.0, src.rows*0.33 );
-    dstTri[1] = Point2f( src.cols*0.85, src.rows*0.25 );
-    dstTri[2] = Point2f( src.cols*0.15, src.rows*0.7 );
-    @endcode
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Set your 3 points to calculate the  Affine Transform
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Set your 3 points to calculate the  Affine Transform
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Set your 3 points to calculate the  Affine Transform
+    @end_toggle
     You may want to draw these points to get a better idea on how they change. Their locations are
     approximately the same as the ones depicted in the example figure (in the Theory section). You
     may note that the size and orientation of the triangle defined by the 3 points change.
 
--#  Armed with both sets of points, we calculate the Affine Transform by using OpenCV function @ref
+-   Armed with both sets of points, we calculate the Affine Transform by using OpenCV function @ref
     cv::getAffineTransform :
-    @code{.cpp}
-    warp_mat = getAffineTransform( srcTri, dstTri );
-    @endcode
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Get the Affine Transform
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Get the Affine Transform
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Get the Affine Transform
+    @end_toggle
     We get a \f$2 \times 3\f$ matrix as an output (in this case **warp_mat**)
 
--#  We then apply the Affine Transform just found to the src image
-    @code{.cpp}
-    warpAffine( src, warp_dst, warp_mat, warp_dst.size() );
-    @endcode
+-   We then apply the Affine Transform just found to the src image
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Apply the Affine Transform just found to the src image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Apply the Affine Transform just found to the src image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Apply the Affine Transform just found to the src image
+    @end_toggle
     with the following arguments:
 
     -   **src**: Input image
@@ -149,47 +180,87 @@ Explanation
     We just got our first transformed image! We will display it in one bit. Before that, we also
     want to rotate it...
 
--#  **Rotate:** To rotate an image, we need to know two things:
+-   **Rotate:** To rotate an image, we need to know two things:
 
     -#  The center with respect to which the image will rotate
     -#  The angle to be rotated. In OpenCV a positive angle is counter-clockwise
     -#  *Optional:* A scale factor
 
     We define these parameters with the following snippet:
-    @code{.cpp}
-    Point center = Point( warp_dst.cols/2, warp_dst.rows/2 );
-    double angle = -50.0;
-    double scale = 0.6;
-    @endcode
--#  We generate the rotation matrix with the OpenCV function @ref cv::getRotationMatrix2D , which
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Compute a rotation matrix with respect to the center of the image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Compute a rotation matrix with respect to the center of the image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Compute a rotation matrix with respect to the center of the image
+    @end_toggle
+
+-   We generate the rotation matrix with the OpenCV function @ref cv::getRotationMatrix2D , which
     returns a \f$2 \times 3\f$ matrix (in this case *rot_mat*)
-    @code{.cpp}
-    rot_mat = getRotationMatrix2D( center, angle, scale );
-    @endcode
--#  We now apply the found rotation to the output of our previous Transformation.
-    @code{.cpp}
-    warpAffine( warp_dst, warp_rotate_dst, rot_mat, warp_dst.size() );
-    @endcode
--#  Finally, we display our results in two windows plus the original image for good measure:
-    @code{.cpp}
-    namedWindow( source_window, WINDOW_AUTOSIZE );
-    imshow( source_window, src );
-
-    namedWindow( warp_window, WINDOW_AUTOSIZE );
-    imshow( warp_window, warp_dst );
-
-    namedWindow( warp_rotate_window, WINDOW_AUTOSIZE );
-    imshow( warp_rotate_window, warp_rotate_dst );
-    @endcode
--#  We just have to wait until the user exits the program
-    @code{.cpp}
-    waitKey(0);
-    @endcode
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Get the rotation matrix with the specifications above
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Get the rotation matrix with the specifications above
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Get the rotation matrix with the specifications above
+    @end_toggle
+
+-   We now apply the found rotation to the output of our previous Transformation:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Rotate the warped image
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Rotate the warped image
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Rotate the warped image
+    @end_toggle
+
+-   Finally, we display our results in two windows plus the original image for good measure:
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Show what you got
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Show what you got
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Show what you got
+    @end_toggle
+
+-   We just have to wait until the user exits the program
+
+    @add_toggle_cpp
+    @snippet samples/cpp/tutorial_code/ImgTrans/Geometric_Transforms_Demo.cpp Wait until user exits the program
+    @end_toggle
+
+    @add_toggle_java
+    @snippet samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java Wait until user exits the program
+    @end_toggle
+
+    @add_toggle_python
+    @snippet samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py Wait until user exits the program
+    @end_toggle
 
 Result
 ------
 
--#  After compiling the code above, we can give it the path of an image as argument. For instance,
+-   After compiling the code above, we can give it the path of an image as argument. For instance,
     for a picture like:
 
     ![](images/Warp_Affine_Tutorial_Original_Image.jpg)
index 17b0e84..fc93ae0 100644 (file)
@@ -165,6 +165,8 @@ In this section you will learn about the image processing (manipulation) functio
 
 -   @subpage tutorial_warp_affine
 
+    *Languages:* C++, Java, Python
+
     *Compatibility:* \> OpenCV 2.0
 
     *Author:* Ana Huamán
@@ -173,6 +175,8 @@ In this section you will learn about the image processing (manipulation) functio
 
 -   @subpage tutorial_histogram_equalization
 
+    *Languages:* C++, Java, Python
+
     *Compatibility:* \> OpenCV 2.0
 
     *Author:* Ana Huamán
@@ -181,6 +185,8 @@ In this section you will learn about the image processing (manipulation) functio
 
 -   @subpage tutorial_histogram_calculation
 
+    *Languages:* C++, Java, Python
+
     *Compatibility:* \> OpenCV 2.0
 
     *Author:* Ana Huamán
@@ -189,6 +195,8 @@ In this section you will learn about the image processing (manipulation) functio
 
 -   @subpage tutorial_histogram_comparison
 
+    *Languages:* C++, Java, Python
+
     *Compatibility:* \> OpenCV 2.0
 
     *Author:* Ana Huamán
@@ -197,6 +205,8 @@ In this section you will learn about the image processing (manipulation) functio
 
 -   @subpage tutorial_back_projection
 
+    *Languages:* C++, Java, Python
+
     *Compatibility:* \> OpenCV 2.0
 
     *Author:* Ana Huamán
index 7c7f4d4..8f5492b 100644 (file)
@@ -17,37 +17,35 @@ using namespace std;
  */
 int main( int argc, char** argv )
 {
-  Mat src, dst;
-
-  const char* source_window = "Source image";
-  const char* equalized_window = "Equalized Image";
-
-  /// Load image
-  CommandLineParser parser( argc, argv, "{@input | ../data/lena.jpg | input image}" );
-  src = imread( parser.get<String>( "@input" ), IMREAD_COLOR );
-  if( src.empty() )
-  {
-    cout << "Could not open or find the image!\n" << endl;
-    cout << "Usage: " << argv[0] << " <Input image>" << endl;
-    return -1;
-  }
-
-  /// Convert to grayscale
-  cvtColor( src, src, COLOR_BGR2GRAY );
-
-  /// Apply Histogram Equalization
-  equalizeHist( src, dst );
-
-  /// Display results
-  namedWindow( source_window, WINDOW_AUTOSIZE );
-  namedWindow( equalized_window, WINDOW_AUTOSIZE );
-
-  imshow( source_window, src );
-  imshow( equalized_window, dst );
-
-  /// Wait until user exits the program
-  waitKey(0);
-
-  return 0;
+    //! [Load image]
+    CommandLineParser parser( argc, argv, "{@input | ../data/lena.jpg | input image}" );
+    Mat src = imread( parser.get<String>( "@input" ), IMREAD_COLOR );
+    if( src.empty() )
+    {
+        cout << "Could not open or find the image!\n" << endl;
+        cout << "Usage: " << argv[0] << " <Input image>" << endl;
+        return -1;
+    }
+    //! [Load image]
+
+    //! [Convert to grayscale]
+    cvtColor( src, src, COLOR_BGR2GRAY );
+    //! [Convert to grayscale]
+
+    //! [Apply Histogram Equalization]
+    Mat dst;
+    equalizeHist( src, dst );
+    //! [Apply Histogram Equalization]
+
+    //! [Display results]
+    imshow( "Source image", src );
+    imshow( "Equalized Image", dst );
+    //! [Display results]
+
+    //! [Wait until user exits the program]
+    waitKey();
+    //! [Wait until user exits the program]
+
+    return 0;
 
 }
index 1e2fe92..61b6d60 100644 (file)
@@ -14,79 +14,93 @@ using namespace cv;
 using namespace std;
 
 /// Global Variables
-Mat src; Mat hsv; Mat hue;
+Mat hue;
 int bins = 25;
 
 /// Function Headers
 void Hist_and_Backproj(int, void* );
 
-
 /**
  * @function main
  */
-int main( int, char** argv )
+int main( int argc, char* argv[] )
 {
-  /// Read the image
-  src = imread( argv[1], IMREAD_COLOR );
-
-  if( src.empty() )
-    { cout<<"Usage: ./calcBackProject_Demo1 <path_to_image>"<<endl;
-      return -1;
+    //! [Read the image]
+    CommandLineParser parser( argc, argv, "{@input |  | input image}" );
+    Mat src = imread( parser.get<String>( "@input" ) );
+    if( src.empty() )
+    {
+        cout << "Could not open or find the image!\n" << endl;
+        cout << "Usage: " << argv[0] << " <Input image>" << endl;
+        return -1;
     }
-
-  /// Transform it to HSV
-  cvtColor( src, hsv, COLOR_BGR2HSV );
-
-  /// Use only the Hue value
-  hue.create( hsv.size(), hsv.depth() );
-  int ch[] = { 0, 0 };
-  mixChannels( &hsv, 1, &hue, 1, ch, 1 );
-
-  /// Create Trackbar to enter the number of bins
-  const char* window_image = "Source image";
-  namedWindow( window_image, WINDOW_AUTOSIZE );
-  createTrackbar("* Hue  bins: ", window_image, &bins, 180, Hist_and_Backproj );
-  Hist_and_Backproj(0, 0);
-
-  /// Show the image
-  imshow( window_image, src );
-
-  /// Wait until user exits the program
-  waitKey(0);
-  return 0;
+    //! [Read the image]
+
+    //! [Transform it to HSV]
+    Mat hsv;
+    cvtColor( src, hsv, COLOR_BGR2HSV );
+    //! [Transform it to HSV]
+
+    //! [Use only the Hue value]
+    hue.create(hsv.size(), hsv.depth());
+    int ch[] = { 0, 0 };
+    mixChannels( &hsv, 1, &hue, 1, ch, 1 );
+    //! [Use only the Hue value]
+
+    //! [Create Trackbar to enter the number of bins]
+    const char* window_image = "Source image";
+    namedWindow( window_image );
+    createTrackbar("* Hue  bins: ", window_image, &bins, 180, Hist_and_Backproj );
+    Hist_and_Backproj(0, 0);
+    //! [Create Trackbar to enter the number of bins]
+
+    //! [Show the image]
+    imshow( window_image, src );
+    // Wait until user exits the program
+    waitKey();
+    //! [Show the image]
+
+    return 0;
 }
 
-
 /**
  * @function Hist_and_Backproj
  * @brief Callback to Trackbar
  */
 void Hist_and_Backproj(int, void* )
 {
-  MatND hist;
-  int histSize = MAX( bins, 2 );
-  float hue_range[] = { 0, 180 };
-  const float* ranges = { hue_range };
-
-  /// Get the Histogram and normalize it
-  calcHist( &hue, 1, 0, Mat(), hist, 1, &histSize, &ranges, true, false );
-  normalize( hist, hist, 0, 255, NORM_MINMAX, -1, Mat() );
-
-  /// Get Backprojection
-  MatND backproj;
-  calcBackProject( &hue, 1, 0, hist, backproj, &ranges, 1, true );
-
-  /// Draw the backproj
-  imshow( "BackProj", backproj );
-
-  /// Draw the histogram
-  int w = 400; int h = 400;
-  int bin_w = cvRound( (double) w / histSize );
-  Mat histImg = Mat::zeros( w, h, CV_8UC3 );
-
-  for( int i = 0; i < bins; i ++ )
-     { rectangle( histImg, Point( i*bin_w, h ), Point( (i+1)*bin_w, h - cvRound( hist.at<float>(i)*h/255.0 ) ), Scalar( 0, 0, 255 ), -1 ); }
-
-  imshow( "Histogram", histImg );
+    //! [initialize]
+    int histSize = MAX( bins, 2 );
+    float hue_range[] = { 0, 180 };
+    const float* ranges = { hue_range };
+    //! [initialize]
+
+    //! [Get the Histogram and normalize it]
+    Mat hist;
+    calcHist( &hue, 1, 0, Mat(), hist, 1, &histSize, &ranges, true, false );
+    normalize( hist, hist, 0, 255, NORM_MINMAX, -1, Mat() );
+    //! [Get the Histogram and normalize it]
+
+    //! [Get Backprojection]
+    Mat backproj;
+    calcBackProject( &hue, 1, 0, hist, backproj, &ranges, 1, true );
+    //! [Get Backprojection]
+
+    //! [Draw the backproj]
+    imshow( "BackProj", backproj );
+    //! [Draw the backproj]
+
+    //! [Draw the histogram]
+    int w = 400, h = 400;
+    int bin_w = cvRound( (double) w / histSize );
+    Mat histImg = Mat::zeros( h, w, CV_8UC3 );
+
+    for (int i = 0; i < bins; i++)
+    {
+        rectangle( histImg, Point( i*bin_w, h ), Point( (i+1)*bin_w, h - cvRound( hist.at<float>(i)*h/255.0 ) ),
+                   Scalar( 0, 0, 255 ), FILLED );
+    }
 
+    imshow( "Histogram", histImg );
+    //! [Draw the histogram]
 }
index ecb7737..9c42c0f 100644 (file)
@@ -14,10 +14,9 @@ using namespace cv;
 using namespace std;
 
 /// Global Variables
-Mat src; Mat hsv;
-Mat mask;
+Mat src, hsv, mask;
 
-int lo = 20; int up = 20;
+int low = 20, up = 20;
 const char* window_image = "Source image";
 
 /// Function Headers
@@ -29,23 +28,24 @@ void pickPoint (int event, int x, int y, int, void* );
  */
 int main( int, char** argv )
 {
-  /// Read the image
-  src = imread( argv[1], IMREAD_COLOR );
-  /// Transform it to HSV
-  cvtColor( src, hsv, COLOR_BGR2HSV );
-
-  /// Show the image
-  namedWindow( window_image, WINDOW_AUTOSIZE );
-  imshow( window_image, src );
-
-  /// Set Trackbars for floodfill thresholds
-  createTrackbar( "Low thresh", window_image, &lo, 255, 0 );
-  createTrackbar( "High thresh", window_image, &up, 255, 0 );
-  /// Set a Mouse Callback
-  setMouseCallback( window_image, pickPoint, 0 );
-
-  waitKey(0);
-  return 0;
+    /// Read the image
+    src = imread( argv[1] );
+
+    /// Transform it to HSV
+    cvtColor( src, hsv, COLOR_BGR2HSV );
+
+    /// Show the image
+    namedWindow( window_image );
+    imshow( window_image, src );
+
+    /// Set Trackbars for floodfill thresholds
+    createTrackbar( "Low thresh", window_image, &low, 255, 0 );
+    createTrackbar( "High thresh", window_image, &up, 255, 0 );
+    /// Set a Mouse Callback
+    setMouseCallback( window_image, pickPoint, 0 );
+
+    waitKey();
+    return 0;
 }
 
 /**
@@ -53,25 +53,27 @@ int main( int, char** argv )
  */
 void pickPoint (int event, int x, int y, int, void* )
 {
-  if( event != EVENT_LBUTTONDOWN )
-    { return; }
+    if( event != EVENT_LBUTTONDOWN )
+    {
+        return;
+    }
 
-  // Fill and get the mask
-  Point seed = Point( x, y );
+    // Fill and get the mask
+    Point seed = Point( x, y );
 
-  int newMaskVal = 255;
-  Scalar newVal = Scalar( 120, 120, 120 );
+    int newMaskVal = 255;
+    Scalar newVal = Scalar( 120, 120, 120 );
 
-  int connectivity = 8;
-  int flags = connectivity + (newMaskVal << 8 ) + FLOODFILL_FIXED_RANGE + FLOODFILL_MASK_ONLY;
+    int connectivity = 8;
+    int flags = connectivity + (newMaskVal << 8 ) + FLOODFILL_FIXED_RANGE + FLOODFILL_MASK_ONLY;
 
-  Mat mask2 = Mat::zeros( src.rows + 2, src.cols + 2, CV_8UC1 );
-  floodFill( src, mask2, seed, newVal, 0, Scalar( lo, lo, lo ), Scalar( up, up, up), flags );
-  mask = mask2( Range( 1, mask2.rows - 1 ), Range( 1, mask2.cols - 1 ) );
+    Mat mask2 = Mat::zeros( src.rows + 2, src.cols + 2, CV_8U );
+    floodFill( src, mask2, seed, newVal, 0, Scalar( low, low, low ), Scalar( up, up, up), flags );
+    mask = mask2( Range( 1, mask2.rows - 1 ), Range( 1, mask2.cols - 1 ) );
 
-  imshow( "Mask", mask );
+    imshow( "Mask", mask );
 
-  Hist_and_Backproj( );
+    Hist_and_Backproj( );
 }
 
 /**
@@ -79,26 +81,25 @@ void pickPoint (int event, int x, int y, int, void* )
  */
 void Hist_and_Backproj( )
 {
-  MatND hist;
-  int h_bins = 30; int s_bins = 32;
-  int histSize[] = { h_bins, s_bins };
-
-  float h_range[] = { 0, 179 };
-  float s_range[] = { 0, 255 };
-  const float* ranges[] = { h_range, s_range };
+    Mat hist;
+    int h_bins = 30; int s_bins = 32;
+    int histSize[] = { h_bins, s_bins };
 
-  int channels[] = { 0, 1 };
+    float h_range[] = { 0, 180 };
+    float s_range[] = { 0, 256 };
+    const float* ranges[] = { h_range, s_range };
 
-  /// Get the Histogram and normalize it
-  calcHist( &hsv, 1, channels, mask, hist, 2, histSize, ranges, true, false );
+    int channels[] = { 0, 1 };
 
-  normalize( hist, hist, 0, 255, NORM_MINMAX, -1, Mat() );
+    /// Get the Histogram and normalize it
+    calcHist( &hsv, 1, channels, mask, hist, 2, histSize, ranges, true, false );
 
-  /// Get Backprojection
-  MatND backproj;
-  calcBackProject( &hsv, 1, channels, hist, backproj, ranges, 1, true );
+    normalize( hist, hist, 0, 255, NORM_MINMAX, -1, Mat() );
 
-  /// Draw the backproj
-  imshow( "BackProj", backproj );
+    /// Get Backprojection
+    Mat backproj;
+    calcBackProject( &hsv, 1, channels, hist, backproj, ranges, 1, true );
 
+    /// Draw the backproj
+    imshow( "BackProj", backproj );
 }
index 27e21e7..fc45fc2 100644 (file)
@@ -17,72 +17,73 @@ using namespace cv;
  */
 int main(int argc, char** argv)
 {
-  Mat src, dst;
-
-  /// Load image
-  String imageName( "../data/lena.jpg" ); // by default
-
-  if (argc > 1)
-  {
-      imageName = argv[1];
-  }
-
-  src = imread( imageName, IMREAD_COLOR );
-
-  if( src.empty() )
-    { return -1; }
-
-  /// Separate the image in 3 places ( B, G and R )
-  vector<Mat> bgr_planes;
-  split( src, bgr_planes );
-
-  /// Establish the number of bins
-  int histSize = 256;
-
-  /// Set the ranges ( for B,G,R) )
-  float range[] = { 0, 256 } ;
-  const float* histRange = { range };
-
-  bool uniform = true; bool accumulate = false;
-
-  Mat b_hist, g_hist, r_hist;
-
-  /// Compute the histograms:
-  calcHist( &bgr_planes[0], 1, 0, Mat(), b_hist, 1, &histSize, &histRange, uniform, accumulate );
-  calcHist( &bgr_planes[1], 1, 0, Mat(), g_hist, 1, &histSize, &histRange, uniform, accumulate );
-  calcHist( &bgr_planes[2], 1, 0, Mat(), r_hist, 1, &histSize, &histRange, uniform, accumulate );
-
-  // Draw the histograms for B, G and R
-  int hist_w = 512; int hist_h = 400;
-  int bin_w = cvRound( (double) hist_w/histSize );
-
-  Mat histImage( hist_h, hist_w, CV_8UC3, Scalar( 0,0,0) );
-
-  /// Normalize the result to [ 0, histImage.rows ]
-  normalize(b_hist, b_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
-  normalize(g_hist, g_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
-  normalize(r_hist, r_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
-
-  /// Draw for each channel
-  for( int i = 1; i < histSize; i++ )
-  {
-      line( histImage, Point( bin_w*(i-1), hist_h - cvRound(b_hist.at<float>(i-1)) ) ,
-                       Point( bin_w*(i), hist_h - cvRound(b_hist.at<float>(i)) ),
-                       Scalar( 255, 0, 0), 2, 8, 0  );
-      line( histImage, Point( bin_w*(i-1), hist_h - cvRound(g_hist.at<float>(i-1)) ) ,
-                       Point( bin_w*(i), hist_h - cvRound(g_hist.at<float>(i)) ),
-                       Scalar( 0, 255, 0), 2, 8, 0  );
-      line( histImage, Point( bin_w*(i-1), hist_h - cvRound(r_hist.at<float>(i-1)) ) ,
-                       Point( bin_w*(i), hist_h - cvRound(r_hist.at<float>(i)) ),
-                       Scalar( 0, 0, 255), 2, 8, 0  );
-  }
-
-  /// Display
-  namedWindow("calcHist Demo", WINDOW_AUTOSIZE );
-  imshow("calcHist Demo", histImage );
-
-  waitKey(0);
-
-  return 0;
-
+    //! [Load image]
+    CommandLineParser parser( argc, argv, "{@input | ../data/lena.jpg | input image}" );
+    Mat src = imread( parser.get<String>( "@input" ), IMREAD_COLOR );
+    if( src.empty() )
+    {
+        return -1;
+    }
+    //! [Load image]
+
+    //! [Separate the image in 3 places ( B, G and R )]
+    vector<Mat> bgr_planes;
+    split( src, bgr_planes );
+    //! [Separate the image in 3 places ( B, G and R )]
+
+    //! [Establish the number of bins]
+    int histSize = 256;
+    //! [Establish the number of bins]
+
+    //! [Set the ranges ( for B,G,R) )]
+    float range[] = { 0, 256 }; //the upper boundary is exclusive
+    const float* histRange = { range };
+    //! [Set the ranges ( for B,G,R) )]
+
+    //! [Set histogram param]
+    bool uniform = true, accumulate = false;
+    //! [Set histogram param]
+
+    //! [Compute the histograms]
+    Mat b_hist, g_hist, r_hist;
+    calcHist( &bgr_planes[0], 1, 0, Mat(), b_hist, 1, &histSize, &histRange, uniform, accumulate );
+    calcHist( &bgr_planes[1], 1, 0, Mat(), g_hist, 1, &histSize, &histRange, uniform, accumulate );
+    calcHist( &bgr_planes[2], 1, 0, Mat(), r_hist, 1, &histSize, &histRange, uniform, accumulate );
+    //! [Compute the histograms]
+
+    //! [Draw the histograms for B, G and R]
+    int hist_w = 512, hist_h = 400;
+    int bin_w = cvRound( (double) hist_w/histSize );
+
+    Mat histImage( hist_h, hist_w, CV_8UC3, Scalar( 0,0,0) );
+    //! [Draw the histograms for B, G and R]
+
+    //! [Normalize the result to ( 0, histImage.rows )]
+    normalize(b_hist, b_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
+    normalize(g_hist, g_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
+    normalize(r_hist, r_hist, 0, histImage.rows, NORM_MINMAX, -1, Mat() );
+    //! [Normalize the result to ( 0, histImage.rows )]
+
+    //! [Draw for each channel]
+    for( int i = 1; i < histSize; i++ )
+    {
+        line( histImage, Point( bin_w*(i-1), hist_h - cvRound(b_hist.at<float>(i-1)) ),
+              Point( bin_w*(i), hist_h - cvRound(b_hist.at<float>(i)) ),
+              Scalar( 255, 0, 0), 2, 8, 0  );
+        line( histImage, Point( bin_w*(i-1), hist_h - cvRound(g_hist.at<float>(i-1)) ),
+              Point( bin_w*(i), hist_h - cvRound(g_hist.at<float>(i)) ),
+              Scalar( 0, 255, 0), 2, 8, 0  );
+        line( histImage, Point( bin_w*(i-1), hist_h - cvRound(r_hist.at<float>(i-1)) ),
+              Point( bin_w*(i), hist_h - cvRound(r_hist.at<float>(i)) ),
+              Scalar( 0, 0, 255), 2, 8, 0  );
+    }
+    //! [Draw for each channel]
+
+    //! [Display]
+    imshow("Source image", src );
+    imshow("calcHist Demo", histImage );
+    waitKey();
+    //! [Display]
+
+    return 0;
 }
index 4d0123b..73aa3c9 100644 (file)
 using namespace std;
 using namespace cv;
 
+const char* keys =
+    "{ help  h| | Print help message. }"
+    "{ input1 | | Path to input image 1. }"
+    "{ input2 | | Path to input image 2. }"
+    "{ input3 | | Path to input image 3. }";
+
 /**
  * @function main
  */
 int main( int argc, char** argv )
 {
-    Mat src_base, hsv_base;
-    Mat src_test1, hsv_test1;
-    Mat src_test2, hsv_test2;
-    Mat hsv_half_down;
-
-    /// Load three images with different environment settings
-    if( argc < 4 )
+    //! [Load three images with different environment settings]
+    CommandLineParser parser( argc, argv, keys );
+    Mat src_base = imread( parser.get<String>("input1") );
+    Mat src_test1 = imread( parser.get<String>("input2") );
+    Mat src_test2 = imread( parser.get<String>("input3") );
+    if( src_base.empty() || src_test1.empty() || src_test2.empty() )
     {
-        printf("** Error. Usage: ./compareHist_Demo <image_settings0> <image_settings1> <image_settings2>\n");
+        cout << "Could not open or find the images!\n" << endl;
+        parser.printMessage();
         return -1;
     }
+    //! [Load three images with different environment settings]
 
-    src_base = imread( argv[1], IMREAD_COLOR );
-    src_test1 = imread( argv[2], IMREAD_COLOR );
-    src_test2 = imread( argv[3], IMREAD_COLOR );
-
-    if(src_base.empty() || src_test1.empty() || src_test2.empty())
-    {
-      cout << "Can't read one of the images" << endl;
-      return -1;
-    }
-
-    /// Convert to HSV
+    //! [Convert to HSV]
+    Mat hsv_base, hsv_test1, hsv_test2;
     cvtColor( src_base, hsv_base, COLOR_BGR2HSV );
     cvtColor( src_test1, hsv_test1, COLOR_BGR2HSV );
     cvtColor( src_test2, hsv_test2, COLOR_BGR2HSV );
+    //! [Convert to HSV]
 
-    hsv_half_down = hsv_base( Range( hsv_base.rows/2, hsv_base.rows - 1 ), Range( 0, hsv_base.cols - 1 ) );
+    //! [Convert to HSV half]
+    Mat hsv_half_down = hsv_base( Range( hsv_base.rows/2, hsv_base.rows ), Range( 0, hsv_base.cols ) );
+    //! [Convert to HSV half]
 
-    /// Using 50 bins for hue and 60 for saturation
-    int h_bins = 50; int s_bins = 60;
+    //! [Using 50 bins for hue and 60 for saturation]
+    int h_bins = 50, s_bins = 60;
     int histSize[] = { h_bins, s_bins };
 
     // hue varies from 0 to 179, saturation from 0 to 255
@@ -56,17 +57,13 @@ int main( int argc, char** argv )
 
     const float* ranges[] = { h_ranges, s_ranges };
 
-    // Use the o-th and 1-st channels
+    // Use the 0-th and 1-st channels
     int channels[] = { 0, 1 };
+    //! [Using 50 bins for hue and 60 for saturation]
 
+    //! [Calculate the histograms for the HSV images]
+    Mat hist_base, hist_half_down, hist_test1, hist_test2;
 
-    /// Histograms
-    MatND hist_base;
-    MatND hist_half_down;
-    MatND hist_test1;
-    MatND hist_test2;
-
-    /// Calculate the histograms for the HSV images
     calcHist( &hsv_base, 1, channels, Mat(), hist_base, 2, histSize, ranges, true, false );
     normalize( hist_base, hist_base, 0, 1, NORM_MINMAX, -1, Mat() );
 
@@ -78,20 +75,21 @@ int main( int argc, char** argv )
 
     calcHist( &hsv_test2, 1, channels, Mat(), hist_test2, 2, histSize, ranges, true, false );
     normalize( hist_test2, hist_test2, 0, 1, NORM_MINMAX, -1, Mat() );
+    //! [Calculate the histograms for the HSV images]
 
-    /// Apply the histogram comparison methods
-    for( int i = 0; i < 4; i++ )
+    //! [Apply the histogram comparison methods]
+    for( int compare_method = 0; compare_method < 4; compare_method++ )
     {
-        int compare_method = i;
         double base_base = compareHist( hist_base, hist_base, compare_method );
         double base_half = compareHist( hist_base, hist_half_down, compare_method );
         double base_test1 = compareHist( hist_base, hist_test1, compare_method );
         double base_test2 = compareHist( hist_base, hist_test2, compare_method );
 
-        printf( " Method [%d] Perfect, Base-Half, Base-Test(1), Base-Test(2) : %f, %f, %f, %f \n", i, base_base, base_half , base_test1, base_test2 );
+        cout << "Method " << compare_method << " Perfect, Base-Half, Base-Test(1), Base-Test(2) : "
+             <<  base_base << " / " << base_half << " / " << base_test1 << " / " << base_test2 << endl;
     }
+    //! [Apply the histogram comparison methods]
 
-    printf( "Done \n" );
-
+    cout << "Done \n";
     return 0;
 }
index 93250a5..2e91467 100644 (file)
 using namespace cv;
 using namespace std;
 
-/// Global variables
-const char* source_window = "Source image";
-const char* warp_window = "Warp";
-const char* warp_rotate_window = "Warp + Rotate";
-
 /**
  * @function main
  */
 int main( int argc, char** argv )
 {
-  Point2f srcTri[3];
-  Point2f dstTri[3];
-
-  Mat rot_mat( 2, 3, CV_32FC1 );
-  Mat warp_mat( 2, 3, CV_32FC1 );
-  Mat src, warp_dst, warp_rotate_dst;
-
-  /// Load the image
-  CommandLineParser parser( argc, argv, "{@input | ../data/lena.jpg | input image}" );
-  src = imread( parser.get<String>( "@input" ), IMREAD_COLOR );
-  if( src.empty() )
-  {
-      cout << "Could not open or find the image!\n" << endl;
-      cout << "Usage: " << argv[0] << " <Input image>" << endl;
-      return -1;
-  }
-
-  /// Set the dst image the same type and size as src
-  warp_dst = Mat::zeros( src.rows, src.cols, src.type() );
-
-  /// Set your 3 points to calculate the  Affine Transform
-  srcTri[0] = Point2f( 0,0 );
-  srcTri[1] = Point2f( src.cols - 1.f, 0 );
-  srcTri[2] = Point2f( 0, src.rows - 1.f );
-
-  dstTri[0] = Point2f( src.cols*0.0f, src.rows*0.33f );
-  dstTri[1] = Point2f( src.cols*0.85f, src.rows*0.25f );
-  dstTri[2] = Point2f( src.cols*0.15f, src.rows*0.7f );
-
-  /// Get the Affine Transform
-  warp_mat = getAffineTransform( srcTri, dstTri );
-
-  /// Apply the Affine Transform just found to the src image
-  warpAffine( src, warp_dst, warp_mat, warp_dst.size() );
-
-  /** Rotating the image after Warp */
-
-  /// Compute a rotation matrix with respect to the center of the image
-  Point center = Point( warp_dst.cols/2, warp_dst.rows/2 );
-  double angle = -50.0;
-  double scale = 0.6;
-
-  /// Get the rotation matrix with the specifications above
-  rot_mat = getRotationMatrix2D( center, angle, scale );
-
-  /// Rotate the warped image
-  warpAffine( warp_dst, warp_rotate_dst, rot_mat, warp_dst.size() );
-
-
-  /// Show what you got
-  namedWindow( source_window, WINDOW_AUTOSIZE );
-  imshow( source_window, src );
-
-  namedWindow( warp_window, WINDOW_AUTOSIZE );
-  imshow( warp_window, warp_dst );
-
-  namedWindow( warp_rotate_window, WINDOW_AUTOSIZE );
-  imshow( warp_rotate_window, warp_rotate_dst );
-
-  /// Wait until user exits the program
-  waitKey(0);
-
-  return 0;
+    //! [Load the image]
+    CommandLineParser parser( argc, argv, "{@input | ../data/lena.jpg | input image}" );
+    Mat src = imread( parser.get<String>( "@input" ) );
+    if( src.empty() )
+    {
+        cout << "Could not open or find the image!\n" << endl;
+        cout << "Usage: " << argv[0] << " <Input image>" << endl;
+        return -1;
+    }
+    //! [Load the image]
+
+    //! [Set your 3 points to calculate the  Affine Transform]
+    Point2f srcTri[3];
+    srcTri[0] = Point2f( 0.f, 0.f );
+    srcTri[1] = Point2f( src.cols - 1.f, 0.f );
+    srcTri[2] = Point2f( 0.f, src.rows - 1.f );
+
+    Point2f dstTri[3];
+    dstTri[0] = Point2f( 0.f, src.rows*0.33f );
+    dstTri[1] = Point2f( src.cols*0.85f, src.rows*0.25f );
+    dstTri[2] = Point2f( src.cols*0.15f, src.rows*0.7f );
+    //! [Set your 3 points to calculate the  Affine Transform]
+
+    //! [Get the Affine Transform]
+    Mat warp_mat = getAffineTransform( srcTri, dstTri );
+    //! [Get the Affine Transform]
+
+    //! [Apply the Affine Transform just found to the src image]
+    /// Set the dst image the same type and size as src
+    Mat warp_dst = Mat::zeros( src.rows, src.cols, src.type() );
+
+    warpAffine( src, warp_dst, warp_mat, warp_dst.size() );
+    //! [Apply the Affine Transform just found to the src image]
+
+    /** Rotating the image after Warp */
+
+    //! [Compute a rotation matrix with respect to the center of the image]
+    Point center = Point( warp_dst.cols/2, warp_dst.rows/2 );
+    double angle = -50.0;
+    double scale = 0.6;
+    //! [Compute a rotation matrix with respect to the center of the image]
+
+    //! [Get the rotation matrix with the specifications above]
+    Mat rot_mat = getRotationMatrix2D( center, angle, scale );
+    //! [Get the rotation matrix with the specifications above]
+
+    //! [Rotate the warped image]
+    Mat warp_rotate_dst;
+    warpAffine( warp_dst, warp_rotate_dst, rot_mat, warp_dst.size() );
+    //! [Rotate the warped image]
+
+    //! [Show what you got]
+    imshow( "Source image", src );
+    imshow( "Warp", warp_dst );
+    imshow( "Warp + Rotate", warp_rotate_dst );
+    //! [Show what you got]
+
+    //! [Wait until user exits the program]
+    waitKey();
+    //! [Wait until user exits the program]
+
+    return 0;
 }
diff --git a/samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java b/samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo1.java
new file mode 100644 (file)
index 0000000..c5b5f8d
--- /dev/null
@@ -0,0 +1,173 @@
+import java.awt.BorderLayout;
+import java.awt.Container;
+import java.awt.Image;
+import java.util.Arrays;
+import java.util.List;
+
+import javax.swing.BoxLayout;
+import javax.swing.ImageIcon;
+import javax.swing.JFrame;
+import javax.swing.JLabel;
+import javax.swing.JPanel;
+import javax.swing.JSlider;
+import javax.swing.event.ChangeEvent;
+import javax.swing.event.ChangeListener;
+
+import org.opencv.core.Core;
+import org.opencv.core.CvType;
+import org.opencv.core.Mat;
+import org.opencv.core.MatOfFloat;
+import org.opencv.core.MatOfInt;
+import org.opencv.core.Point;
+import org.opencv.core.Scalar;
+import org.opencv.highgui.HighGui;
+import org.opencv.imgcodecs.Imgcodecs;
+import org.opencv.imgproc.Imgproc;
+
+class CalcBackProject1 {
+    private Mat hue;
+    private Mat histImg = new Mat();
+    private JFrame frame;
+    private JLabel imgLabel;
+    private JLabel backprojLabel;
+    private JLabel histImgLabel;
+    private static final int MAX_SLIDER = 180;
+    private int bins = 25;
+
+    public CalcBackProject1(String[] args) {
+        //! [Read the image]
+        if (args.length != 1) {
+            System.err.println("You must supply one argument that corresponds to the path to the image.");
+            System.exit(0);
+        }
+
+        Mat src = Imgcodecs.imread(args[0]);
+        if (src.empty()) {
+            System.err.println("Empty image: " + args[0]);
+            System.exit(0);
+        }
+        //! [Read the image]
+
+        //! [Transform it to HSV]
+        Mat hsv = new Mat();
+        Imgproc.cvtColor(src, hsv, Imgproc.COLOR_BGR2HSV);
+        //! [Transform it to HSV]
+
+        //! [Use only the Hue value]
+        hue = new Mat(hsv.size(), hsv.depth());
+        Core.mixChannels(Arrays.asList(hsv), Arrays.asList(hue), new MatOfInt(0, 0));
+        //! [Use only the Hue value]
+
+        // Create and set up the window.
+        frame = new JFrame("Back Projection 1 demo");
+        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+        // Set up the content pane.
+        Image img = HighGui.toBufferedImage(src);
+        addComponentsToPane(frame.getContentPane(), img);
+        //! [Show the image]
+        // Use the content pane's default BorderLayout. No need for
+        // setLayout(new BorderLayout());
+        // Display the window.
+        frame.pack();
+        frame.setVisible(true);
+        //! [Show the image]
+    }
+
+    private void addComponentsToPane(Container pane, Image img) {
+        if (!(pane.getLayout() instanceof BorderLayout)) {
+            pane.add(new JLabel("Container doesn't use BorderLayout!"));
+            return;
+        }
+
+        //! [Create Trackbar to enter the number of bins]
+        JPanel sliderPanel = new JPanel();
+        sliderPanel.setLayout(new BoxLayout(sliderPanel, BoxLayout.PAGE_AXIS));
+
+        sliderPanel.add(new JLabel("* Hue  bins: "));
+        JSlider slider = new JSlider(0, MAX_SLIDER, bins);
+        slider.setMajorTickSpacing(25);
+        slider.setMinorTickSpacing(5);
+        slider.setPaintTicks(true);
+        slider.setPaintLabels(true);
+        slider.addChangeListener(new ChangeListener() {
+            @Override
+            public void stateChanged(ChangeEvent e) {
+                JSlider source = (JSlider) e.getSource();
+                bins = source.getValue();
+                update();
+            }
+        });
+        sliderPanel.add(slider);
+        pane.add(sliderPanel, BorderLayout.PAGE_START);
+        //! [Create Trackbar to enter the number of bins]
+
+        JPanel imgPanel = new JPanel();
+        imgLabel = new JLabel(new ImageIcon(img));
+        imgPanel.add(imgLabel);
+
+        backprojLabel = new JLabel();
+        imgPanel.add(backprojLabel);
+
+        histImgLabel = new JLabel();
+        imgPanel.add(histImgLabel);
+        pane.add(imgPanel, BorderLayout.CENTER);
+    }
+
+    private void update() {
+        //! [initialize]
+        int histSize = Math.max(bins, 2);
+        float[] hueRange = {0, 180};
+        //! [initialize]
+
+        //! [Get the Histogram and normalize it]
+        Mat hist = new Mat();
+        List<Mat> hueList = Arrays.asList(hue);
+        Imgproc.calcHist(hueList, new MatOfInt(0), new Mat(), hist, new MatOfInt(histSize), new MatOfFloat(hueRange), false);
+        Core.normalize(hist, hist, 0, 255, Core.NORM_MINMAX);
+        //! [Get the Histogram and normalize it]
+
+        //! [Get Backprojection]
+        Mat backproj = new Mat();
+        Imgproc.calcBackProject(hueList, new MatOfInt(0), hist, backproj, new MatOfFloat(hueRange), 1);
+        //! [Get Backprojection]
+
+        //! [Draw the backproj]
+        Image backprojImg = HighGui.toBufferedImage(backproj);
+        backprojLabel.setIcon(new ImageIcon(backprojImg));
+        //! [Draw the backproj]
+
+        //! [Draw the histogram]
+        int w = 400, h = 400;
+        int binW = (int) Math.round((double) w / histSize);
+        histImg = Mat.zeros(h, w, CvType.CV_8UC3);
+
+        float[] histData = new float[(int) (hist.total() * hist.channels())];
+        hist.get(0, 0, histData);
+        for (int i = 0; i < bins; i++) {
+            Imgproc.rectangle(histImg, new Point(i * binW, h),
+                    new Point((i + 1) * binW, h - Math.round(histData[i] * h / 255.0)), new Scalar(0, 0, 255), Core.FILLED);
+        }
+        Image histImage = HighGui.toBufferedImage(histImg);
+        histImgLabel.setIcon(new ImageIcon(histImage));
+        //! [Draw the histogram]
+
+        frame.repaint();
+        frame.pack();
+    }
+}
+
+public class CalcBackProjectDemo1 {
+    public static void main(String[] args) {
+        // Load the native OpenCV library
+        System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
+
+        // Schedule a job for the event dispatch thread:
+        // creating and showing this application's GUI.
+        javax.swing.SwingUtilities.invokeLater(new Runnable() {
+            @Override
+            public void run() {
+                new CalcBackProject1(args);
+            }
+        });
+    }
+}
diff --git a/samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo2.java b/samples/java/tutorial_code/Histograms_Matching/back_projection/CalcBackProjectDemo2.java
new file mode 100644 (file)
index 0000000..a0ab39e
--- /dev/null
@@ -0,0 +1,189 @@
+import java.awt.BorderLayout;
+import java.awt.Container;
+import java.awt.Image;
+import java.awt.event.MouseAdapter;
+import java.awt.event.MouseEvent;
+import java.util.Arrays;
+import java.util.List;
+
+import javax.swing.BoxLayout;
+import javax.swing.ImageIcon;
+import javax.swing.JFrame;
+import javax.swing.JLabel;
+import javax.swing.JPanel;
+import javax.swing.JSlider;
+import javax.swing.event.ChangeEvent;
+import javax.swing.event.ChangeListener;
+
+import org.opencv.core.Core;
+import org.opencv.core.CvType;
+import org.opencv.core.Mat;
+import org.opencv.core.MatOfFloat;
+import org.opencv.core.MatOfInt;
+import org.opencv.core.Point;
+import org.opencv.core.Range;
+import org.opencv.core.Rect;
+import org.opencv.core.Scalar;
+import org.opencv.highgui.HighGui;
+import org.opencv.imgcodecs.Imgcodecs;
+import org.opencv.imgproc.Imgproc;
+
+class CalcBackProject2 {
+    private Mat src;
+    private Mat hsv = new Mat();
+    private Mat mask = new Mat();
+    private JFrame frame;
+    private JLabel imgLabel;
+    private JLabel backprojLabel;
+    private JLabel maskImgLabel;
+    private static final int MAX_SLIDER = 255;
+    private int low = 20;
+    private int up = 20;
+
+    public CalcBackProject2(String[] args) {
+        /// Read the image
+        if (args.length != 1) {
+            System.err.println("You must supply one argument that corresponds to the path to the image.");
+            System.exit(0);
+        }
+
+        src = Imgcodecs.imread(args[0]);
+        if (src.empty()) {
+            System.err.println("Empty image: " + args[0]);
+            System.exit(0);
+        }
+
+        /// Transform it to HSV
+        Imgproc.cvtColor(src, hsv, Imgproc.COLOR_BGR2HSV);
+
+        // Create and set up the window.
+        frame = new JFrame("Back Projection 2 demo");
+        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+        // Set up the content pane.
+        Image img = HighGui.toBufferedImage(src);
+        addComponentsToPane(frame.getContentPane(), img);
+        // Use the content pane's default BorderLayout. No need for
+        // setLayout(new BorderLayout());
+        // Display the window.
+        frame.pack();
+        frame.setVisible(true);
+    }
+
+    private void addComponentsToPane(Container pane, Image img) {
+        if (!(pane.getLayout() instanceof BorderLayout)) {
+            pane.add(new JLabel("Container doesn't use BorderLayout!"));
+            return;
+        }
+
+        /// Set Trackbars for floodfill thresholds
+        JPanel sliderPanel = new JPanel();
+        sliderPanel.setLayout(new BoxLayout(sliderPanel, BoxLayout.PAGE_AXIS));
+
+        sliderPanel.add(new JLabel("Low thresh"));
+        JSlider slider = new JSlider(0, MAX_SLIDER, low);
+        slider.setMajorTickSpacing(20);
+        slider.setMinorTickSpacing(10);
+        slider.setPaintTicks(true);
+        slider.setPaintLabels(true);
+        slider.addChangeListener(new ChangeListener() {
+            @Override
+            public void stateChanged(ChangeEvent e) {
+                JSlider source = (JSlider) e.getSource();
+                low = source.getValue();
+            }
+        });
+        sliderPanel.add(slider);
+        pane.add(sliderPanel, BorderLayout.PAGE_START);
+
+        sliderPanel.add(new JLabel("High thresh"));
+        slider = new JSlider(0, MAX_SLIDER, up);
+        slider.setMajorTickSpacing(20);
+        slider.setMinorTickSpacing(10);
+        slider.setPaintTicks(true);
+        slider.setPaintLabels(true);
+        slider.addChangeListener(new ChangeListener() {
+            @Override
+            public void stateChanged(ChangeEvent e) {
+                JSlider source = (JSlider) e.getSource();
+                up = source.getValue();
+            }
+        });
+        sliderPanel.add(slider);
+        pane.add(sliderPanel, BorderLayout.PAGE_START);
+
+        JPanel imgPanel = new JPanel();
+        imgLabel = new JLabel(new ImageIcon(img));
+        /// Set a Mouse Callback
+        imgLabel.addMouseListener(new MouseAdapter() {
+            @Override
+            public void mousePressed(MouseEvent e) {
+                update(e.getX(), e.getY());
+            }
+        });
+        imgPanel.add(imgLabel);
+
+        maskImgLabel = new JLabel();
+        imgPanel.add(maskImgLabel);
+
+        backprojLabel = new JLabel();
+        imgPanel.add(backprojLabel);
+
+        pane.add(imgPanel, BorderLayout.CENTER);
+    }
+
+    private void update(int x, int y) {
+        // Fill and get the mask
+        Point seed = new Point(x, y);
+
+        int newMaskVal = 255;
+        Scalar newVal = new Scalar(120, 120, 120);
+
+        int connectivity = 8;
+        int flags = connectivity + (newMaskVal << 8) + Imgproc.FLOODFILL_FIXED_RANGE + Imgproc.FLOODFILL_MASK_ONLY;
+
+        Mat mask2 = Mat.zeros(src.rows() + 2, src.cols() + 2, CvType.CV_8U);
+        Imgproc.floodFill(src, mask2, seed, newVal, new Rect(), new Scalar(low, low, low), new Scalar(up, up, up), flags);
+        mask = mask2.submat(new Range(1, mask2.rows() - 1), new Range(1, mask2.cols() - 1));
+
+        Image maskImg = HighGui.toBufferedImage(mask);
+        maskImgLabel.setIcon(new ImageIcon(maskImg));
+
+        int hBins = 30, sBins = 32;
+        int[] histSize = { hBins, sBins };
+        float[] ranges = { 0, 180, 0, 256 };
+        int[] channels = { 0, 1 };
+
+        /// Get the Histogram and normalize it
+        Mat hist = new Mat();
+        List<Mat> hsvList = Arrays.asList(hsv);
+        Imgproc.calcHist(hsvList, new MatOfInt(channels), mask, hist, new MatOfInt(histSize), new MatOfFloat(ranges), false );
+
+        Core.normalize(hist, hist, 0, 255, Core.NORM_MINMAX);
+
+        /// Get Backprojection
+        Mat backproj = new Mat();
+        Imgproc.calcBackProject(hsvList, new MatOfInt(channels), hist, backproj, new MatOfFloat(ranges), 1);
+
+        Image backprojImg = HighGui.toBufferedImage(backproj);
+        backprojLabel.setIcon(new ImageIcon(backprojImg));
+
+        frame.repaint();
+        frame.pack();
+    }
+}
+
+public class CalcBackProjectDemo2 {
+    public static void main(String[] args) {
+        // Load the native OpenCV library
+        System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
+
+        // Schedule a job for the event dispatch thread:
+        // creating and showing this application's GUI.
+        javax.swing.SwingUtilities.invokeLater(new Runnable() {
+            @Override
+            public void run() {
+                new CalcBackProject2(args);
+            }
+        });
+    }
+}
diff --git a/samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java b/samples/java/tutorial_code/Histograms_Matching/histogram_calculation/CalcHistDemo.java
new file mode 100644 (file)
index 0000000..16874e7
--- /dev/null
@@ -0,0 +1,99 @@
+import java.util.ArrayList;
+import java.util.List;
+
+import org.opencv.core.Core;
+import org.opencv.core.CvType;
+import org.opencv.core.Mat;
+import org.opencv.core.MatOfFloat;
+import org.opencv.core.MatOfInt;
+import org.opencv.core.Point;
+import org.opencv.core.Scalar;
+import org.opencv.highgui.HighGui;
+import org.opencv.imgcodecs.Imgcodecs;
+import org.opencv.imgproc.Imgproc;
+
+class CalcHist {
+    public void run(String[] args) {
+        //! [Load image]
+        String filename = args.length > 0 ? args[0] : "../data/lena.jpg";
+        Mat src = Imgcodecs.imread(filename);
+        if (src.empty()) {
+            System.err.println("Cannot read image: " + filename);
+            System.exit(0);
+        }
+        //! [Load image]
+
+        //! [Separate the image in 3 places ( B, G and R )]
+        List<Mat> bgrPlanes = new ArrayList<>();
+        Core.split(src, bgrPlanes);
+        //! [Separate the image in 3 places ( B, G and R )]
+
+        //! [Establish the number of bins]
+        int histSize = 256;
+        //! [Establish the number of bins]
+
+        //! [Set the ranges ( for B,G,R) )]
+        float[] range = {0, 256}; //the upper boundary is exclusive
+        MatOfFloat histRange = new MatOfFloat(range);
+        //! [Set the ranges ( for B,G,R) )]
+
+        //! [Set histogram param]
+        boolean accumulate = false;
+        //! [Set histogram param]
+
+        //! [Compute the histograms]
+        Mat bHist = new Mat(), gHist = new Mat(), rHist = new Mat();
+        Imgproc.calcHist(bgrPlanes, new MatOfInt(0), new Mat(), bHist, new MatOfInt(histSize), histRange, accumulate);
+        Imgproc.calcHist(bgrPlanes, new MatOfInt(1), new Mat(), gHist, new MatOfInt(histSize), histRange, accumulate);
+        Imgproc.calcHist(bgrPlanes, new MatOfInt(2), new Mat(), rHist, new MatOfInt(histSize), histRange, accumulate);
+        //! [Compute the histograms]
+
+        //! [Draw the histograms for B, G and R]
+        int histW = 512, histH = 400;
+        int binW = (int) Math.round((double) histW / histSize);
+
+        Mat histImage = new Mat( histH, histW, CvType.CV_8UC3, new Scalar( 0,0,0) );
+        //! [Draw the histograms for B, G and R]
+
+        //! [Normalize the result to ( 0, histImage.rows )]
+        Core.normalize(bHist, bHist, 0, histImage.rows(), Core.NORM_MINMAX);
+        Core.normalize(gHist, gHist, 0, histImage.rows(), Core.NORM_MINMAX);
+        Core.normalize(rHist, rHist, 0, histImage.rows(), Core.NORM_MINMAX);
+        //! [Normalize the result to ( 0, histImage.rows )]
+
+        //! [Draw for each channel]
+        float[] bHistData = new float[(int) (bHist.total() * bHist.channels())];
+        bHist.get(0, 0, bHistData);
+        float[] gHistData = new float[(int) (gHist.total() * gHist.channels())];
+        gHist.get(0, 0, gHistData);
+        float[] rHistData = new float[(int) (rHist.total() * rHist.channels())];
+        rHist.get(0, 0, rHistData);
+
+        for( int i = 1; i < histSize; i++ ) {
+            Imgproc.line(histImage, new Point(binW * (i - 1), histH - Math.round(bHistData[i - 1])),
+                    new Point(binW * (i), histH - Math.round(bHistData[i])), new Scalar(255, 0, 0), 2);
+            Imgproc.line(histImage, new Point(binW * (i - 1), histH - Math.round(gHistData[i - 1])),
+                    new Point(binW * (i), histH - Math.round(gHistData[i])), new Scalar(0, 255, 0), 2);
+            Imgproc.line(histImage, new Point(binW * (i - 1), histH - Math.round(rHistData[i - 1])),
+                    new Point(binW * (i), histH - Math.round(rHistData[i])), new Scalar(0, 0, 255), 2);
+        }
+        //! [Draw for each channel]
+
+        //! [Display]
+        HighGui.imshow( "Source image", src );
+        HighGui.imshow( "calcHist Demo", histImage );
+        HighGui.waitKey(0);
+        //! [Display]
+
+        System.exit(0);
+    }
+}
+
+public class CalcHistDemo {
+    public static void main(String[] args) {
+        // Load the native OpenCV library
+        System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
+
+        new CalcHist().run(args);
+    }
+}
diff --git a/samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java b/samples/java/tutorial_code/Histograms_Matching/histogram_comparison/CompareHistDemo.java
new file mode 100644 (file)
index 0000000..fb65dc6
--- /dev/null
@@ -0,0 +1,91 @@
+import java.util.Arrays;
+import java.util.List;
+
+import org.opencv.core.Core;
+import org.opencv.core.Mat;
+import org.opencv.core.MatOfFloat;
+import org.opencv.core.MatOfInt;
+import org.opencv.core.Range;
+import org.opencv.imgcodecs.Imgcodecs;
+import org.opencv.imgproc.Imgproc;
+
+class CompareHist {
+    public void run(String[] args) {
+        //! [Load three images with different environment settings]
+        if (args.length != 3) {
+            System.err.println("You must supply 3 arguments that correspond to the paths to 3 images.");
+            System.exit(0);
+        }
+        Mat srcBase = Imgcodecs.imread(args[0]);
+        Mat srcTest1 = Imgcodecs.imread(args[1]);
+        Mat srcTest2 = Imgcodecs.imread(args[2]);
+        if (srcBase.empty() || srcTest1.empty() || srcTest2.empty()) {
+            System.err.println("Cannot read the images");
+            System.exit(0);
+        }
+        //! [Load three images with different environment settings]
+
+        //! [Convert to HSV]
+        Mat hsvBase = new Mat(), hsvTest1 = new Mat(), hsvTest2 = new Mat();
+        Imgproc.cvtColor( srcBase, hsvBase, Imgproc.COLOR_BGR2HSV );
+        Imgproc.cvtColor( srcTest1, hsvTest1, Imgproc.COLOR_BGR2HSV );
+        Imgproc.cvtColor( srcTest2, hsvTest2, Imgproc.COLOR_BGR2HSV );
+        //! [Convert to HSV]
+
+        //! [Convert to HSV half]
+        Mat hsvHalfDown = hsvBase.submat( new Range( hsvBase.rows()/2, hsvBase.rows() - 1 ), new Range( 0, hsvBase.cols() - 1 ) );
+        //! [Convert to HSV half]
+
+        //! [Using 50 bins for hue and 60 for saturation]
+        int hBins = 50, sBins = 60;
+        int[] histSize = { hBins, sBins };
+
+        // hue varies from 0 to 179, saturation from 0 to 255
+        float[] ranges = { 0, 180, 0, 256 };
+
+        // Use the 0-th and 1-st channels
+        int[] channels = { 0, 1 };
+        //! [Using 50 bins for hue and 60 for saturation]
+
+        //! [Calculate the histograms for the HSV images]
+        Mat histBase = new Mat(), histHalfDown = new Mat(), histTest1 = new Mat(), histTest2 = new Mat();
+
+        List<Mat> hsvBaseList = Arrays.asList(hsvBase);
+        Imgproc.calcHist(hsvBaseList, new MatOfInt(channels), new Mat(), histBase, new MatOfInt(histSize), new MatOfFloat(ranges), false);
+        Core.normalize(histBase, histBase, 0, 1, Core.NORM_MINMAX);
+
+        List<Mat> hsvHalfDownList = Arrays.asList(hsvHalfDown);
+        Imgproc.calcHist(hsvHalfDownList, new MatOfInt(channels), new Mat(), histHalfDown, new MatOfInt(histSize), new MatOfFloat(ranges), false);
+        Core.normalize(histHalfDown, histHalfDown, 0, 1, Core.NORM_MINMAX);
+
+        List<Mat> hsvTest1List = Arrays.asList(hsvTest1);
+        Imgproc.calcHist(hsvTest1List, new MatOfInt(channels), new Mat(), histTest1, new MatOfInt(histSize), new MatOfFloat(ranges), false);
+        Core.normalize(histTest1, histTest1, 0, 1, Core.NORM_MINMAX);
+
+        List<Mat> hsvTest2List = Arrays.asList(hsvTest2);
+        Imgproc.calcHist(hsvTest2List, new MatOfInt(channels), new Mat(), histTest2, new MatOfInt(histSize), new MatOfFloat(ranges), false);
+        Core.normalize(histTest2, histTest2, 0, 1, Core.NORM_MINMAX);
+        //! [Calculate the histograms for the HSV images]
+
+        //! [Apply the histogram comparison methods]
+        for( int compareMethod = 0; compareMethod < 4; compareMethod++ ) {
+            double baseBase = Imgproc.compareHist( histBase, histBase, compareMethod );
+            double baseHalf = Imgproc.compareHist( histBase, histHalfDown, compareMethod );
+            double baseTest1 = Imgproc.compareHist( histBase, histTest1, compareMethod );
+            double baseTest2 = Imgproc.compareHist( histBase, histTest2, compareMethod );
+
+            System.out.println("Method " + compareMethod + " Perfect, Base-Half, Base-Test(1), Base-Test(2) : " + baseBase + " / " + baseHalf
+                    + " / " + baseTest1 + " / " + baseTest2);
+        }
+        //! [Apply the histogram comparison methods]
+    }
+}
+
+public class CompareHistDemo {
+    public static void main(String[] args) {
+        // Load the native OpenCV library
+        System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
+
+        new CompareHist().run(args);
+    }
+}
diff --git a/samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java b/samples/java/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHistDemo.java
new file mode 100644 (file)
index 0000000..0919243
--- /dev/null
@@ -0,0 +1,49 @@
+import org.opencv.core.Core;
+import org.opencv.core.Mat;
+import org.opencv.highgui.HighGui;
+import org.opencv.imgcodecs.Imgcodecs;
+import org.opencv.imgproc.Imgproc;
+
+class EqualizeHist {
+    public void run(String[] args) {
+        //! [Load image]
+        String filename = args.length > 0 ? args[0] : "../data/lena.jpg";
+        Mat src = Imgcodecs.imread(filename);
+        if (src.empty()) {
+            System.err.println("Cannot read image: " + filename);
+            System.exit(0);
+        }
+        //! [Load image]
+
+        //! [Convert to grayscale]
+        Imgproc.cvtColor(src, src, Imgproc.COLOR_BGR2GRAY);
+        //! [Convert to grayscale]
+
+        //! [Apply Histogram Equalization]
+        Mat dst = new Mat();
+        Imgproc.equalizeHist( src, dst );
+        //! [Apply Histogram Equalization]
+
+        //! [Display results]
+        HighGui.imshow( "Source image", src );
+        HighGui.imshow( "Equalized Image", dst );
+        //! [Display results]
+
+        //! [Wait until user exits the program]
+        HighGui.waitKey(0);
+        //! [Wait until user exits the program]
+
+        System.exit(0);
+    }
+}
+
+public class EqualizeHistDemo {
+
+    public static void main(String[] args) {
+        // Load the native OpenCV library
+        System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
+
+        new EqualizeHist().run(args);
+    }
+
+}
diff --git a/samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java b/samples/java/tutorial_code/ImgTrans/warp_affine/GeometricTransformsDemo.java
new file mode 100644 (file)
index 0000000..a391930
--- /dev/null
@@ -0,0 +1,80 @@
+import org.opencv.core.Core;
+import org.opencv.core.Mat;
+import org.opencv.core.MatOfPoint2f;
+import org.opencv.core.Point;
+import org.opencv.highgui.HighGui;
+import org.opencv.imgcodecs.Imgcodecs;
+import org.opencv.imgproc.Imgproc;
+
+class GeometricTransforms {
+    public void run(String[] args) {
+        //! [Load the image]
+        String filename = args.length > 0 ? args[0] : "../data/lena.jpg";
+        Mat src = Imgcodecs.imread(filename);
+        if (src.empty()) {
+            System.err.println("Cannot read image: " + filename);
+            System.exit(0);
+        }
+        //! [Load the image]
+
+        //! [Set your 3 points to calculate the  Affine Transform]
+        Point[] srcTri = new Point[3];
+        srcTri[0] = new Point( 0, 0 );
+        srcTri[1] = new Point( src.cols() - 1, 0 );
+        srcTri[2] = new Point( 0, src.rows() - 1 );
+
+        Point[] dstTri = new Point[3];
+        dstTri[0] = new Point( 0, src.rows()*0.33 );
+        dstTri[1] = new Point( src.cols()*0.85, src.rows()*0.25 );
+        dstTri[2] = new Point( src.cols()*0.15, src.rows()*0.7 );
+        //! [Set your 3 points to calculate the  Affine Transform]
+
+        //! [Get the Affine Transform]
+        Mat warpMat = Imgproc.getAffineTransform( new MatOfPoint2f(srcTri), new MatOfPoint2f(dstTri) );
+        //! [Get the Affine Transform]
+
+        //! [Apply the Affine Transform just found to the src image]
+        Mat warpDst = Mat.zeros( src.rows(), src.cols(), src.type() );
+
+        Imgproc.warpAffine( src, warpDst, warpMat, warpDst.size() );
+        //! [Apply the Affine Transform just found to the src image]
+
+        /** Rotating the image after Warp */
+
+        //! [Compute a rotation matrix with respect to the center of the image]
+        Point center = new Point(warpDst.cols() / 2, warpDst.rows() / 2);
+        double angle = -50.0;
+        double scale = 0.6;
+        //! [Compute a rotation matrix with respect to the center of the image]
+
+        //! [Get the rotation matrix with the specifications above]
+        Mat rotMat = Imgproc.getRotationMatrix2D( center, angle, scale );
+        //! [Get the rotation matrix with the specifications above]
+
+        //! [Rotate the warped image]
+        Mat warpRotateDst = new Mat();
+        Imgproc.warpAffine( warpDst, warpRotateDst, rotMat, warpDst.size() );
+        //! [Rotate the warped image]
+
+        //! [Show what you got]
+        HighGui.imshow( "Source image", src );
+        HighGui.imshow( "Warp", warpDst );
+        HighGui.imshow( "Warp + Rotate", warpRotateDst );
+        //! [Show what you got]
+
+        //! [Wait until user exits the program]
+        HighGui.waitKey(0);
+        //! [Wait until user exits the program]
+
+        System.exit(0);
+    }
+}
+
+public class GeometricTransformsDemo {
+    public static void main(String[] args) {
+        // Load the native OpenCV library
+        System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
+
+        new GeometricTransforms().run(args);
+    }
+}
diff --git a/samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py b/samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo1.py
new file mode 100644 (file)
index 0000000..eb0bdab
--- /dev/null
@@ -0,0 +1,71 @@
+from __future__ import print_function
+from __future__ import division
+import cv2 as cv
+import numpy as np
+import argparse
+
+def Hist_and_Backproj(val):
+    ## [initialize]
+    bins = val
+    histSize = max(bins, 2)
+    ranges = [0, 180] # hue_range
+    ## [initialize]
+
+    ## [Get the Histogram and normalize it]
+    hist = cv.calcHist([hue], [0], None, [histSize], ranges, accumulate=False)
+    cv.normalize(hist, hist, alpha=0, beta=255, norm_type=cv.NORM_MINMAX)
+    ## [Get the Histogram and normalize it]
+
+    ## [Get Backprojection]
+    backproj = cv.calcBackProject([hue], [0], hist, ranges, scale=1)
+    ## [Get Backprojection]
+
+    ## [Draw the backproj]
+    cv.imshow('BackProj', backproj)
+    ## [Draw the backproj]
+
+    ## [Draw the histogram]
+    w = 400
+    h = 400
+    bin_w = int(round(w / histSize))
+    histImg = np.zeros((h, w, 3), dtype=np.uint8)
+
+    for i in range(bins):
+        cv.rectangle(histImg, (i*bin_w, h), ( (i+1)*bin_w, h - int(round( hist[i]*h/255.0 )) ), (0, 0, 255), cv.FILLED)
+
+    cv.imshow('Histogram', histImg)
+    ## [Draw the histogram]
+
+## [Read the image]
+parser = argparse.ArgumentParser(description='Code for Back Projection tutorial.')
+parser.add_argument('--input', help='Path to input image.')
+args = parser.parse_args()
+
+src = cv.imread(args.input)
+if src is None:
+    print('Could not open or find the image:', args.input)
+    exit(0)
+## [Read the image]
+
+## [Transform it to HSV]
+hsv = cv.cvtColor(src, cv.COLOR_BGR2HSV)
+## [Transform it to HSV]
+
+## [Use only the Hue value]
+ch = (0, 0)
+hue = np.empty(hsv.shape, hsv.dtype)
+cv.mixChannels([hsv], [hue], ch)
+## [Use only the Hue value]
+
+## [Create Trackbar to enter the number of bins]
+window_image = 'Source image'
+cv.namedWindow(window_image)
+bins = 25
+cv.createTrackbar('* Hue  bins: ', window_image, bins, 180, Hist_and_Backproj )
+Hist_and_Backproj(bins)
+## [Create Trackbar to enter the number of bins]
+
+## [Show the image]
+cv.imshow(window_image, src)
+cv.waitKey()
+## [Show the image]
diff --git a/samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo2.py b/samples/python/tutorial_code/Histograms_Matching/back_projection/calcBackProject_Demo2.py
new file mode 100644 (file)
index 0000000..24255a2
--- /dev/null
@@ -0,0 +1,79 @@
+from __future__ import print_function
+import cv2 as cv
+import numpy as np
+import argparse
+
+low = 20
+up = 20
+
+def callback_low(val):
+    global low
+    low = val
+
+def callback_up(val):
+    global up
+    up = val
+
+def pickPoint(event, x, y, flags, param):
+    if event != cv.EVENT_LBUTTONDOWN:
+        return
+
+    # Fill and get the mask
+    seed = (x, y)
+    newMaskVal = 255
+    newVal = (120, 120, 120)
+    connectivity = 8
+    flags = connectivity + (newMaskVal << 8 ) + cv.FLOODFILL_FIXED_RANGE + cv.FLOODFILL_MASK_ONLY
+
+    mask2 = np.zeros((src.shape[0] + 2, src.shape[1] + 2), dtype=np.uint8)
+    print('low:', low, 'up:', up)
+    cv.floodFill(src, mask2, seed, newVal, (low, low, low), (up, up, up), flags)
+    mask = mask2[1:-1,1:-1]
+
+    cv.imshow('Mask', mask)
+    Hist_and_Backproj(mask)
+
+def Hist_and_Backproj(mask):
+    h_bins = 30
+    s_bins = 32
+    histSize = [h_bins, s_bins]
+    h_range = [0, 180]
+    s_range = [0, 256]
+    ranges = h_range + s_range # Concat list
+    channels = [0, 1]
+
+    # Get the Histogram and normalize it
+    hist = cv.calcHist([hsv], channels, mask, histSize, ranges, accumulate=False)
+    cv.normalize(hist, hist, alpha=0, beta=255, norm_type=cv.NORM_MINMAX)
+
+    # Get Backprojection
+    backproj = cv.calcBackProject([hsv], channels, hist, ranges, scale=1)
+
+    # Draw the backproj
+    cv.imshow('BackProj', backproj)
+
+# Read the image
+parser = argparse.ArgumentParser(description='Code for Back Projection tutorial.')
+parser.add_argument('--input', help='Path to input image.')
+args = parser.parse_args()
+
+src = cv.imread(args.input)
+if src is None:
+    print('Could not open or find the image:', args.input)
+    exit(0)
+
+# Transform it to HSV
+hsv = cv.cvtColor(src, cv.COLOR_BGR2HSV)
+
+# Show the image
+window_image = 'Source image'
+cv.namedWindow(window_image)
+cv.imshow(window_image, src)
+
+# Set Trackbars for floodfill thresholds
+cv.createTrackbar('Low thresh', window_image, low, 255, callback_low)
+cv.createTrackbar('High thresh', window_image, up, 255, callback_up)
+# Set a Mouse Callback
+cv.setMouseCallback(window_image, pickPoint)
+
+cv.waitKey()
diff --git a/samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py b/samples/python/tutorial_code/Histograms_Matching/histogram_calculation/calcHist_Demo.py
new file mode 100644 (file)
index 0000000..63302ab
--- /dev/null
@@ -0,0 +1,71 @@
+from __future__ import print_function
+from __future__ import division
+import cv2 as cv
+import numpy as np
+import argparse
+
+## [Load image]
+parser = argparse.ArgumentParser(description='Code for Histogram Calculation tutorial.')
+parser.add_argument('--input', help='Path to input image.', default='../data/lena.jpg')
+args = parser.parse_args()
+
+src = cv.imread(args.input)
+if src is None:
+    print('Could not open or find the image:', args.input)
+    exit(0)
+## [Load image]
+
+## [Separate the image in 3 places ( B, G and R )]
+bgr_planes = cv.split(src)
+## [Separate the image in 3 places ( B, G and R )]
+
+## [Establish the number of bins]
+histSize = 256
+## [Establish the number of bins]
+
+## [Set the ranges ( for B,G,R) )]
+histRange = (0, 256) # the upper boundary is exclusive
+## [Set the ranges ( for B,G,R) )]
+
+## [Set histogram param]
+accumulate = False
+## [Set histogram param]
+
+## [Compute the histograms]
+b_hist = cv.calcHist(bgr_planes, [0], None, [histSize], histRange, accumulate=accumulate)
+g_hist = cv.calcHist(bgr_planes, [1], None, [histSize], histRange, accumulate=accumulate)
+r_hist = cv.calcHist(bgr_planes, [2], None, [histSize], histRange, accumulate=accumulate)
+## [Compute the histograms]
+
+## [Draw the histograms for B, G and R]
+hist_w = 512
+hist_h = 400
+bin_w = int(round( hist_w/histSize ))
+
+histImage = np.zeros((hist_h, hist_w, 3), dtype=np.uint8)
+## [Draw the histograms for B, G and R]
+
+## [Normalize the result to ( 0, histImage.rows )]
+cv.normalize(b_hist, b_hist, alpha=0, beta=hist_h, norm_type=cv.NORM_MINMAX)
+cv.normalize(g_hist, g_hist, alpha=0, beta=hist_h, norm_type=cv.NORM_MINMAX)
+cv.normalize(r_hist, r_hist, alpha=0, beta=hist_h, norm_type=cv.NORM_MINMAX)
+## [Normalize the result to ( 0, histImage.rows )]
+
+## [Draw for each channel]
+for i in range(1, histSize):
+    cv.line(histImage, ( bin_w*(i-1), hist_h - int(round(b_hist[i-1])) ),
+            ( bin_w*(i), hist_h - int(round(b_hist[i])) ),
+            ( 255, 0, 0), thickness=2)
+    cv.line(histImage, ( bin_w*(i-1), hist_h - int(round(g_hist[i-1])) ),
+            ( bin_w*(i), hist_h - int(round(g_hist[i])) ),
+            ( 0, 255, 0), thickness=2)
+    cv.line(histImage, ( bin_w*(i-1), hist_h - int(round(r_hist[i-1])) ),
+            ( bin_w*(i), hist_h - int(round(r_hist[i])) ),
+            ( 0, 0, 255), thickness=2)
+## [Draw for each channel]
+
+## [Display]
+cv.imshow('Source image', src)
+cv.imshow('calcHist Demo', histImage)
+cv.waitKey()
+## [Display]
diff --git a/samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py b/samples/python/tutorial_code/Histograms_Matching/histogram_comparison/compareHist_Demo.py
new file mode 100644 (file)
index 0000000..08d0dc3
--- /dev/null
@@ -0,0 +1,69 @@
+from __future__ import print_function
+from __future__ import division
+import cv2 as cv
+import numpy as np
+import argparse
+
+## [Load three images with different environment settings]
+parser = argparse.ArgumentParser(description='Code for Histogram Comparison tutorial.')
+parser.add_argument('--input1', help='Path to input image 1.')
+parser.add_argument('--input2', help='Path to input image 2.')
+parser.add_argument('--input3', help='Path to input image 3.')
+args = parser.parse_args()
+
+src_base = cv.imread(args.input1)
+src_test1 = cv.imread(args.input2)
+src_test2 = cv.imread(args.input3)
+if src_base is None or src_test1 is None or src_test2 is None:
+    print('Could not open or find the images!')
+    exit(0)
+## [Load three images with different environment settings]
+
+## [Convert to HSV]
+hsv_base = cv.cvtColor(src_base, cv.COLOR_BGR2HSV)
+hsv_test1 = cv.cvtColor(src_test1, cv.COLOR_BGR2HSV)
+hsv_test2 = cv.cvtColor(src_test2, cv.COLOR_BGR2HSV)
+## [Convert to HSV]
+
+## [Convert to HSV half]
+hsv_half_down = hsv_base[hsv_base.shape[0]//2:,:]
+## [Convert to HSV half]
+
+## [Using 50 bins for hue and 60 for saturation]
+h_bins = 50
+s_bins = 60
+histSize = [h_bins, s_bins]
+
+# hue varies from 0 to 179, saturation from 0 to 255
+h_ranges = [0, 180]
+s_ranges = [0, 256]
+ranges = h_ranges + s_ranges # concat lists
+
+# Use the 0-th and 1-st channels
+channels = [0, 1]
+## [Using 50 bins for hue and 60 for saturation]
+
+## [Calculate the histograms for the HSV images]
+hist_base = cv.calcHist([hsv_base], channels, None, histSize, ranges, accumulate=False)
+cv.normalize(hist_base, hist_base, alpha=0, beta=1, norm_type=cv.NORM_MINMAX)
+
+hist_half_down = cv.calcHist([hsv_half_down], channels, None, histSize, ranges, accumulate=False)
+cv.normalize(hist_half_down, hist_half_down, alpha=0, beta=1, norm_type=cv.NORM_MINMAX)
+
+hist_test1 = cv.calcHist([hsv_test1], channels, None, histSize, ranges, accumulate=False)
+cv.normalize(hist_test1, hist_test1, alpha=0, beta=1, norm_type=cv.NORM_MINMAX)
+
+hist_test2 = cv.calcHist([hsv_test2], channels, None, histSize, ranges, accumulate=False)
+cv.normalize(hist_test2, hist_test2, alpha=0, beta=1, norm_type=cv.NORM_MINMAX)
+## [Calculate the histograms for the HSV images]
+
+## [Apply the histogram comparison methods]
+for compare_method in range(4):
+    base_base = cv.compareHist(hist_base, hist_base, compare_method)
+    base_half = cv.compareHist(hist_base, hist_half_down, compare_method)
+    base_test1 = cv.compareHist(hist_base, hist_test1, compare_method)
+    base_test2 = cv.compareHist(hist_base, hist_test2, compare_method)
+
+    print('Method:', compare_method, 'Perfect, Base-Half, Base-Test(1), Base-Test(2) :',\
+          base_base, '/', base_half, '/', base_test1, '/', base_test2)
+## [Apply the histogram comparison methods]
diff --git a/samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py b/samples/python/tutorial_code/Histograms_Matching/histogram_equalization/EqualizeHist_Demo.py
new file mode 100644 (file)
index 0000000..47caec4
--- /dev/null
@@ -0,0 +1,31 @@
+from __future__ import print_function
+import cv2 as cv
+import argparse
+
+## [Load image]
+parser = argparse.ArgumentParser(description='Code for Histogram Equalization tutorial.')
+parser.add_argument('--input', help='Path to input image.', default='../data/lena.jpg')
+args = parser.parse_args()
+
+src = cv.imread(args.input)
+if src is None:
+    print('Could not open or find the image:', args.input)
+    exit(0)
+## [Load image]
+
+## [Convert to grayscale]
+src = cv.cvtColor(src, cv.COLOR_BGR2GRAY)
+## [Convert to grayscale]
+
+## [Apply Histogram Equalization]
+dst = cv.equalizeHist(src);
+## [Apply Histogram Equalization]
+
+## [Display results]
+cv.imshow('Source image', src)
+cv.imshow('Equalized Image', dst)
+## [Display results]
+
+## [Wait until user exits the program]
+cv.waitKey()
+## [Wait until user exits the program]
diff --git a/samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py b/samples/python/tutorial_code/ImgTrans/warp_affine/Geometric_Transforms_Demo.py
new file mode 100644 (file)
index 0000000..462a412
--- /dev/null
@@ -0,0 +1,54 @@
+from __future__ import print_function
+import cv2 as cv
+import numpy as np
+import argparse
+
+## [Load the image]
+parser = argparse.ArgumentParser(description='Code for Affine Transformations tutorial.')
+parser.add_argument('--input', help='Path to input image.', default='../data/lena.jpg')
+args = parser.parse_args()
+
+src = cv.imread(args.input)
+if src is None:
+    print('Could not open or find the image:', args.input)
+    exit(0)
+## [Load the image]
+
+## [Set your 3 points to calculate the  Affine Transform]
+srcTri = np.array( [[0, 0], [src.shape[1] - 1, 0], [0, src.shape[0] - 1]] ).astype(np.float32)
+dstTri = np.array( [[0, src.shape[1]*0.33], [src.shape[1]*0.85, src.shape[0]*0.25], [src.shape[1]*0.15, src.shape[0]*0.7]] ).astype(np.float32)
+## [Set your 3 points to calculate the  Affine Transform]
+
+## [Get the Affine Transform]
+warp_mat = cv.getAffineTransform(srcTri, dstTri)
+## [Get the Affine Transform]
+
+## [Apply the Affine Transform just found to the src image]
+warp_dst = cv.warpAffine(src, warp_mat, (src.shape[1], src.shape[0]))
+## [Apply the Affine Transform just found to the src image]
+
+# Rotating the image after Warp
+
+## [Compute a rotation matrix with respect to the center of the image]
+center = (warp_dst.shape[1]//2, warp_dst.shape[0]//2)
+angle = -50
+scale = 0.6
+## [Compute a rotation matrix with respect to the center of the image]
+
+## [Get the rotation matrix with the specifications above]
+rot_mat = cv.getRotationMatrix2D( center, angle, scale )
+## [Get the rotation matrix with the specifications above]
+
+## [Rotate the warped image]
+warp_rotate_dst = cv.warpAffine(warp_dst, rot_mat, (warp_dst.shape[1], warp_dst.shape[0]))
+## [Rotate the warped image]
+
+## [Show what you got]
+cv.imshow('Source image', src)
+cv.imshow('Warp', warp_dst)
+cv.imshow('Warp + Rotate', warp_rotate_dst)
+## [Show what you got]
+
+## [Wait until user exits the program]
+cv.waitKey()
+## [Wait until user exits the program]