Commit fa2499d8 authored by Davis King's avatar Davis King
Browse files

Added a file that defines a new generic image interface for images in dlib.

This is the dlib/image_processing/generic_image.h file.  Then I changed all the
image processing functions so that they use this interface.  All the changes
are very minor, but there are just a lot of them.

Any user code that was using array2d objects to represent images will still
work.  However, this change makes it so that users can use their own custom
image objects with dlib by simply implementing a few global functions for their
image object.
parent dc0fd24d
......@@ -21,13 +21,16 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- pixel_traits<typename in_image_type::type>::is_unsigned == true
- pixel_traits<typename out_image_type::type>::is_unsigned == true
- pixel_traits<typename in_image_type::type>::max() <= 65535
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- Let pixel_type be the type of pixel in either input or output images, then we
must have:
- pixel_traits<pixel_type>::has_alpha == false
- pixel_traits<pixel_type>::is_unsigned == true
- For the input image pixel type, we have the additional requirement that:
- pixel_traits<pixel_type>::max() <= 65535
ensures
- #out_img == the histogram equalized version of in_img
- #out_img.nc() == in_img.nc()
......@@ -61,9 +64,11 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::is_unsigned == true
- pixel_traits<typename in_image_type::type>::max() <= 65535
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- Let pixel_type denote the type of pixel in in_img, then we must have:
- pixel_traits<pixel_type>::is_unsigned == true
- pixel_traits<pixel_type>::max() <= 65535
- hist must be capable of representing a column vector of length
pixel_traits<typename in_image_type>::max(). I.e. if R and C are nonzero
then they must be values that don't conflict with the previous sentence.
......
......@@ -22,7 +22,7 @@ namespace dlib
namespace impl_fhog
{
template <typename image_type>
inline typename dlib::enable_if_c<pixel_traits<typename image_type::type>::rgb>::type get_gradient (
inline typename dlib::enable_if_c<pixel_traits<typename image_type::pixel_type>::rgb>::type get_gradient (
const int r,
const int c,
const image_type& img,
......@@ -60,7 +60,7 @@ namespace dlib
}
template <typename image_type>
inline typename dlib::enable_if_c<pixel_traits<typename image_type::type>::rgb>::type get_gradient (
inline typename dlib::enable_if_c<pixel_traits<typename image_type::pixel_type>::rgb>::type get_gradient (
const int r,
const int c,
const image_type& img,
......@@ -145,7 +145,7 @@ namespace dlib
// ------------------------------------------------------------------------------------
template <typename image_type>
inline typename dlib::disable_if_c<pixel_traits<typename image_type::type>::rgb>::type get_gradient (
inline typename dlib::disable_if_c<pixel_traits<typename image_type::pixel_type>::rgb>::type get_gradient (
const int r,
const int c,
const image_type& img,
......@@ -159,7 +159,7 @@ namespace dlib
}
template <typename image_type>
inline typename dlib::disable_if_c<pixel_traits<typename image_type::type>::rgb>::type get_gradient (
inline typename dlib::disable_if_c<pixel_traits<typename image_type::pixel_type>::rgb>::type get_gradient (
int r,
int c,
const image_type& img,
......@@ -275,13 +275,14 @@ namespace dlib
typename out_type
>
void impl_extract_fhog_features(
const image_type& img,
const image_type& img_,
out_type& hog,
int cell_size,
int filter_rows_padding,
int filter_cols_padding
)
{
const_image_view<image_type> img(img_);
// make sure requires clause is not broken
DLIB_ASSERT( cell_size > 0 &&
filter_rows_padding > 0 &&
......
......@@ -29,9 +29,8 @@ namespace dlib
- cell_size > 0
- filter_rows_padding > 0
- filter_cols_padding > 0
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- img contains some kind of pixel type.
(i.e. pixel_traits<typename image_type::type> is defined)
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- T should be float or double
ensures
- This function implements the HOG feature extraction method described in
......@@ -89,9 +88,8 @@ namespace dlib
- cell_size > 0
- filter_rows_padding > 0
- filter_cols_padding > 0
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- img contains some kind of pixel type.
(i.e. pixel_traits<typename image_type::type> is defined)
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- T should be float or double
ensures
- This function is identical to the above extract_fhog_features() routine
......@@ -124,9 +122,8 @@ namespace dlib
- cell_size > 0
- filter_rows_padding > 0
- filter_cols_padding > 0
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- img contains some kind of pixel type.
(i.e. pixel_traits<typename image_type::type> is defined)
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
ensures
- This function calls the above extract_fhog_features() routine and simply
packages the entire output into a dlib::matrix. The matrix is constructed
......@@ -158,9 +155,8 @@ namespace dlib
- cell_size > 0
- filter_rows_padding > 0
- filter_cols_padding > 0
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- img contains some kind of pixel type.
(i.e. pixel_traits<typename image_type::type> is defined)
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- T is float, double, or long double
ensures
- This function is identical to the above version of extract_fhog_features()
......
......@@ -119,8 +119,10 @@ namespace dlib
<< "\n\t this: " << this
);
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
down.clear();
}
......@@ -220,8 +222,9 @@ namespace dlib
template <typename T, typename U>
struct both_images_rgb
{
const static bool value = pixel_traits<typename T::type>::rgb &&
pixel_traits<typename U::type>::rgb;
typedef typename image_traits<T>::pixel_type T_pix;
typedef typename image_traits<U>::pixel_type U_pix;
const static bool value = pixel_traits<T_pix>::rgb && pixel_traits<U_pix>::rgb;
};
public:
......@@ -230,19 +233,24 @@ namespace dlib
typename out_image_type
>
typename disable_if<both_images_rgb<in_image_type,out_image_type> >::type operator() (
const in_image_type& original,
out_image_type& down
const in_image_type& original_,
out_image_type& down_
) const
{
// make sure requires clause is not broken
DLIB_ASSERT( is_same_object(original, down) == false,
DLIB_ASSERT( is_same_object(original_, down_) == false,
"\t void pyramid_down_2_1::operator()"
<< "\n\t is_same_object(original, down): " << is_same_object(original, down)
<< "\n\t is_same_object(original_, down_): " << is_same_object(original_, down_)
<< "\n\t this: " << this
);
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
const_image_view<in_image_type> original(original_);
image_view<out_image_type> down(down_);
if (original.nr() <= 8 || original.nc() <= 8)
{
......@@ -250,7 +258,7 @@ namespace dlib
return;
}
typedef typename pixel_traits<typename in_image_type::type>::basic_pixel_type bp_type;
typedef typename pixel_traits<in_pixel_type>::basic_pixel_type bp_type;
typedef typename promote<bp_type>::type ptype;
array2d<ptype> temp_img;
temp_img.set_size(original.nr(), (original.nc()-3)/2);
......@@ -326,19 +334,24 @@ namespace dlib
typename out_image_type
>
typename enable_if<both_images_rgb<in_image_type,out_image_type> >::type operator() (
const in_image_type& original,
out_image_type& down
const in_image_type& original_,
out_image_type& down_
) const
{
// make sure requires clause is not broken
DLIB_ASSERT( is_same_object(original, down) == false,
DLIB_ASSERT( is_same_object(original_, down_) == false,
"\t void pyramid_down_2_1::operator()"
<< "\n\t is_same_object(original, down): " << is_same_object(original, down)
<< "\n\t is_same_object(original_, down_): " << is_same_object(original_, down_)
<< "\n\t this: " << this
);
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
const_image_view<in_image_type> original(original_);
image_view<out_image_type> down(down_);
if (original.nr() <= 8 || original.nc() <= 8)
{
......@@ -539,8 +552,9 @@ namespace dlib
template <typename T, typename U>
struct both_images_rgb
{
const static bool value = pixel_traits<typename T::type>::rgb &&
pixel_traits<typename U::type>::rgb;
typedef typename image_traits<T>::pixel_type T_pix;
typedef typename image_traits<U>::pixel_type U_pix;
const static bool value = pixel_traits<T_pix>::rgb && pixel_traits<U_pix>::rgb;
};
public:
......@@ -549,19 +563,24 @@ namespace dlib
typename out_image_type
>
typename disable_if<both_images_rgb<in_image_type,out_image_type> >::type operator() (
const in_image_type& original,
out_image_type& down
const in_image_type& original_,
out_image_type& down_
) const
{
// make sure requires clause is not broken
DLIB_ASSERT(is_same_object(original, down) == false,
DLIB_ASSERT(is_same_object(original_, down_) == false,
"\t void pyramid_down_3_2::operator()"
<< "\n\t is_same_object(original, down): " << is_same_object(original, down)
<< "\n\t is_same_object(original_, down_): " << is_same_object(original_, down_)
<< "\n\t this: " << this
);
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
const_image_view<in_image_type> original(original_);
image_view<out_image_type> down(down_);
if (original.nr() <= 8 || original.nc() <= 8)
{
......@@ -572,7 +591,7 @@ namespace dlib
const long size_in = 3;
const long size_out = 2;
typedef typename pixel_traits<typename in_image_type::type>::basic_pixel_type bp_type;
typedef typename pixel_traits<in_pixel_type>::basic_pixel_type bp_type;
typedef typename promote<bp_type>::type ptype;
const long full_nr = size_out*((original.nr()-2)/size_in);
const long part_nr = (size_out*(original.nr()-2))/size_in;
......@@ -590,7 +609,7 @@ namespace dlib
for (c = 0; c < full_nc; c+=size_out)
{
ptype block[size_in][size_in];
separable_3x3_filter_block_grayscale(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_grayscale(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate block
assign_pixel(down[r][c] , (block[0][0]*9 + block[1][0]*3 + block[0][1]*3 + block[1][1])/(16*256));
......@@ -603,7 +622,7 @@ namespace dlib
if (part_nc - full_nc == 1)
{
ptype block[size_in][2];
separable_3x3_filter_block_grayscale(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_grayscale(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate partial block
assign_pixel(down[r][c] , (block[0][0]*9 + block[1][0]*3 + block[0][1]*3 + block[1][1])/(16*256));
......@@ -618,7 +637,7 @@ namespace dlib
for (c = 0; c < full_nc; c+=size_out)
{
ptype block[2][size_in];
separable_3x3_filter_block_grayscale(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_grayscale(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate partial block
assign_pixel(down[r][c] , (block[0][0]*9 + block[1][0]*3 + block[0][1]*3 + block[1][1])/(16*256));
......@@ -629,7 +648,7 @@ namespace dlib
if (part_nc - full_nc == 1)
{
ptype block[2][2];
separable_3x3_filter_block_grayscale(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_grayscale(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate partial block
assign_pixel(down[r][c] , (block[0][0]*9 + block[1][0]*3 + block[0][1]*3 + block[1][1])/(16*256));
......@@ -655,19 +674,24 @@ namespace dlib
typename out_image_type
>
typename enable_if<both_images_rgb<in_image_type,out_image_type> >::type operator() (
const in_image_type& original,
out_image_type& down
const in_image_type& original_,
out_image_type& down_
) const
{
// make sure requires clause is not broken
DLIB_ASSERT( is_same_object(original, down) == false,
DLIB_ASSERT( is_same_object(original_, down_) == false,
"\t void pyramid_down_3_2::operator()"
<< "\n\t is_same_object(original, down): " << is_same_object(original, down)
<< "\n\t is_same_object(original_, down_): " << is_same_object(original_, down_)
<< "\n\t this: " << this
);
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
const_image_view<in_image_type> original(original_);
image_view<out_image_type> down(down_);
if (original.nr() <= 8 || original.nc() <= 8)
{
......@@ -694,7 +718,7 @@ namespace dlib
for (c = 0; c < full_nc; c+=size_out)
{
rgbptype block[size_in][size_in];
separable_3x3_filter_block_rgb(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_rgb(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate block
down[r][c].red = (block[0][0].red*9 + block[1][0].red*3 + block[0][1].red*3 + block[1][1].red)/(16*256);
......@@ -718,7 +742,7 @@ namespace dlib
if (part_nc - full_nc == 1)
{
rgbptype block[size_in][2];
separable_3x3_filter_block_rgb(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_rgb(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate partial block
down[r][c].red = (block[0][0].red*9 + block[1][0].red*3 + block[0][1].red*3 + block[1][1].red)/(16*256);
......@@ -738,7 +762,7 @@ namespace dlib
for (c = 0; c < full_nc; c+=size_out)
{
rgbptype block[2][size_in];
separable_3x3_filter_block_rgb(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_rgb(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate partial block
down[r][c].red = (block[0][0].red*9 + block[1][0].red*3 + block[0][1].red*3 + block[1][1].red)/(16*256);
......@@ -754,7 +778,7 @@ namespace dlib
if (part_nc - full_nc == 1)
{
rgbptype block[2][2];
separable_3x3_filter_block_rgb(block, original, rr, cc, 2, 12, 2);
separable_3x3_filter_block_rgb(block, original_, rr, cc, 2, 12, 2);
// bi-linearly interpolate partial block
down[r][c].red = (block[0][0].red*9 + block[1][0].red*3 + block[0][1].red*3 + block[1][1].red)/(16*256);
......@@ -878,12 +902,13 @@ namespace dlib
<< "\n\t this: " << this
);
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
down.set_size(((N-1)*original.nr())/N,
((N-1)*original.nc())/N);
set_image_size(down, ((N-1)*num_rows(original))/N, ((N-1)*num_columns(original))/N);
resize_image(original, down);
}
};
......
......@@ -47,10 +47,12 @@ namespace dlib
/*!
requires
- is_same_object(original, down) == false
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- for both pixel types P in the input and output images, we require:
- pixel_traits<P>::has_alpha == false
ensures
- #down will contain an image that is roughly (N-1)/N times the size of the
original image.
......
......@@ -31,9 +31,10 @@ namespace dlib
template <typename image_type>
void load (
const image_type& img
const image_type& img_
)
{
const_image_view<image_type> img(img_);
T pixel;
int_img.set_size(img.nr(), img.nc());
......
......@@ -59,8 +59,10 @@ namespace dlib
);
/*!
requires
- image_type == a type that implements the array2d/array2d_kernel_abstract.h interface
- pixel_traits<typename image_type::type>::has_alpha == false
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- Let P denote the type of pixel in img, then we require:
- pixel_traits<P>::has_alpha == false
ensures
- #nr() == img.nr()
- #nc() == img.nc()
......
......@@ -20,14 +20,14 @@ namespace dlib
{
public:
template <typename image_type, typename pixel_type>
template <typename image_view_type, typename pixel_type>
bool operator() (
const image_type& img,
const image_view_type& img,
const dlib::point& p,
pixel_type& result
) const
{
COMPILE_TIME_ASSERT(pixel_traits<typename image_type::type>::has_alpha == false);
COMPILE_TIME_ASSERT(pixel_traits<typename image_view_type::pixel_type>::has_alpha == false);
if (get_rect(img).contains(p))
{
......@@ -49,19 +49,19 @@ namespace dlib
template <typename T>
struct is_rgb_image
{
const static bool value = pixel_traits<typename T::type>::rgb;
const static bool value = pixel_traits<typename T::pixel_type>::rgb;
};
public:
template <typename T, typename image_type, typename pixel_type>
typename disable_if<is_rgb_image<image_type>,bool>::type operator() (
const image_type& img,
template <typename T, typename image_view_type, typename pixel_type>
typename disable_if<is_rgb_image<image_view_type>,bool>::type operator() (
const image_view_type& img,
const dlib::vector<T,2>& p,
pixel_type& result
) const
{
COMPILE_TIME_ASSERT(pixel_traits<typename image_type::type>::has_alpha == false);
COMPILE_TIME_ASSERT(pixel_traits<typename image_view_type::pixel_type>::has_alpha == false);
const long left = static_cast<long>(std::floor(p.x()));
const long top = static_cast<long>(std::floor(p.y()));
......@@ -90,14 +90,14 @@ namespace dlib
return true;
}
template <typename T, typename image_type, typename pixel_type>
typename enable_if<is_rgb_image<image_type>,bool>::type operator() (
const image_type& img,
template <typename T, typename image_view_type, typename pixel_type>
typename enable_if<is_rgb_image<image_view_type>,bool>::type operator() (
const image_view_type& img,
const dlib::vector<T,2>& p,
pixel_type& result
) const
{
COMPILE_TIME_ASSERT(pixel_traits<typename image_type::type>::has_alpha == false);
COMPILE_TIME_ASSERT(pixel_traits<typename image_view_type::pixel_type>::has_alpha == false);
const long left = static_cast<long>(std::floor(p.x()));
const long top = static_cast<long>(std::floor(p.y()));
......@@ -151,19 +151,19 @@ namespace dlib
template <typename T>
struct is_rgb_image
{
const static bool value = pixel_traits<typename T::type>::rgb;
const static bool value = pixel_traits<typename T::pixel_type>::rgb;
};
public:
template <typename T, typename image_type, typename pixel_type>
typename disable_if<is_rgb_image<image_type>,bool>::type operator() (
const image_type& img,
template <typename T, typename image_view_type, typename pixel_type>
typename disable_if<is_rgb_image<image_view_type>,bool>::type operator() (
const image_view_type& img,
const dlib::vector<T,2>& p,
pixel_type& result
) const
{
COMPILE_TIME_ASSERT(pixel_traits<typename image_type::type>::has_alpha == false);
COMPILE_TIME_ASSERT(pixel_traits<typename image_view_type::pixel_type>::has_alpha == false);
const point pp(p);
......@@ -189,14 +189,14 @@ namespace dlib
return true;
}
template <typename T, typename image_type, typename pixel_type>
typename enable_if<is_rgb_image<image_type>,bool>::type operator() (
const image_type& img,
template <typename T, typename image_view_type, typename pixel_type>
typename enable_if<is_rgb_image<image_view_type>,bool>::type operator() (
const image_view_type& img,
const dlib::vector<T,2>& p,
pixel_type& result
) const
{
COMPILE_TIME_ASSERT(pixel_traits<typename image_type::type>::has_alpha == false);
COMPILE_TIME_ASSERT(pixel_traits<typename image_view_type::pixel_type>::has_alpha == false);
const point pp(p);
......@@ -342,13 +342,15 @@ namespace dlib
<< "\n\t is_same_object(in_img, out_img): " << is_same_object(in_img, out_img)
);
const_image_view<image_type1> imgv(in_img);
image_view<image_type2> out_imgv(out_img);
for (long r = area.top(); r <= area.bottom(); ++r)
{
for (long c = area.left(); c <= area.right(); ++c)
{
if (!interp(in_img, map_point(dlib::vector<double,2>(c,r)), out_img[r][c]))
set_background(out_img[r][c]);
if (!interp(imgv, map_point(dlib::vector<double,2>(c,r)), out_imgv[r][c]))
set_background(out_imgv[r][c]);
}
}
}
......@@ -522,9 +524,9 @@ namespace dlib
// ----------------------------------------------------------------------------------------
template <typename image_type>
struct is_rgb_image { const static bool value = pixel_traits<typename image_type::type>::rgb; };
struct is_rgb_image { const static bool value = pixel_traits<typename image_traits<image_type>::pixel_type>::rgb; };
template <typename image_type>
struct is_grayscale_image { const static bool value = pixel_traits<typename image_type::type>::grayscale; };
struct is_grayscale_image { const static bool value = pixel_traits<typename image_traits<image_type>::pixel_type>::grayscale; };
// This is an optimized version of resize_image for the case where bilinear
// interpolation is used.
......@@ -535,17 +537,21 @@ namespace dlib
typename disable_if_c<(is_rgb_image<image_type1>::value&&is_rgb_image<image_type2>::value) ||
(is_grayscale_image<image_type1>::value&&is_grayscale_image<image_type2>::value)>::type
resize_image (
const image_type1& in_img,
image_type2& out_img,
const image_type1& in_img_,
image_type2& out_img_,
interpolate_bilinear
)
{
// make sure requires clause is not broken
DLIB_ASSERT( is_same_object(in_img, out_img) == false ,
DLIB_ASSERT( is_same_object(in_img_, out_img_) == false ,
"\t void resize_image()"
<< "\n\t Invalid inputs were given to this function."
<< "\n\t is_same_object(in_img, out_img): " << is_same_object(in_img, out_img)
<< "\n\t is_same_object(in_img_, out_img_): " << is_same_object(in_img_, out_img_)
);
const_image_view<image_type1> in_img(in_img_);
image_view<image_type2> out_img(out_img_);
if (out_img.nr() <= 1 || out_img.nc() <= 1)
{
assign_all_pixels(out_img, 0);
......@@ -553,8 +559,8 @@ namespace dlib
}
typedef typename image_type1::type T;
typedef typename image_type2::type U;
typedef typename image_traits<image_type1>::pixel_type T;
typedef typename image_traits<image_type2>::pixel_type U;
const double x_scale = (in_img.nc()-1)/(double)std::max<long>((out_img.nc()-1),1);
const double y_scale = (in_img.nr()-1)/(double)std::max<long>((out_img.nr()-1),1);
double y = -y_scale;
......@@ -618,24 +624,28 @@ namespace dlib
typename image_type
>
typename enable_if<is_grayscale_image<image_type> >::type resize_image (
const image_type& in_img,
image_type& out_img,
const image_type& in_img_,
image_type& out_img_,
interpolate_bilinear
)
{
// make sure requires clause is not broken
DLIB_ASSERT( is_same_object(in_img, out_img) == false ,
DLIB_ASSERT( is_same_object(in_img_, out_img_) == false ,
"\t void resize_image()"
<< "\n\t Invalid inputs were given to this function."
<< "\n\t is_same_object(in_img, out_img): " << is_same_object(in_img, out_img)
<< "\n\t is_same_object(in_img_, out_img_): " << is_same_object(in_img_, out_img_)
);
const_image_view<image_type> in_img(in_img_);
image_view<image_type> out_img(out_img_);
if (out_img.nr() <= 1 || out_img.nc() <= 1)
{
assign_all_pixels(out_img, 0);
return;
}
typedef typename image_type::type T;
typedef typename image_traits<image_type>::pixel_type T;
const double x_scale = (in_img.nc()-1)/(double)std::max<long>((out_img.nc()-1),1);
const double y_scale = (in_img.nr()-1)/(double)std::max<long>((out_img.nr()-1),1);
double y = -y_scale;
......@@ -716,17 +726,21 @@ namespace dlib
typename image_type
>
typename enable_if<is_rgb_image<image_type> >::type resize_image (
const image_type& in_img,
image_type& out_img,
const image_type& in_img_,
image_type& out_img_,
interpolate_bilinear
)
{
// make sure requires clause is not broken
DLIB_ASSERT( is_same_object(in_img, out_img) == false ,
DLIB_ASSERT( is_same_object(in_img_, out_img_) == false ,
"\t void resize_image()"
<< "\n\t Invalid inputs were given to this function."
<< "\n\t is_same_object(in_img, out_img): " << is_same_object(in_img, out_img)
<< "\n\t is_same_object(in_img_, out_img_): " << is_same_object(in_img_, out_img_)
);
const_image_view<image_type> in_img(in_img_);
image_view<image_type> out_img(out_img_);
if (out_img.nr() <= 1 || out_img.nc() <= 1)
{
assign_all_pixels(out_img, 0);
......@@ -734,7 +748,7 @@ namespace dlib
}
typedef typename image_type::type T;
typedef typename image_traits<image_type>::pixel_type T;
const double x_scale = (in_img.nc()-1)/(double)std::max<long>((out_img.nc()-1),1);
const double y_scale = (in_img.nr()-1)/(double)std::max<long>((out_img.nr()-1),1);
double y = -y_scale;
......@@ -1046,7 +1060,7 @@ namespace dlib
for (unsigned long i = 0; i < images.size(); ++i)
{
flip_image_left_right(images[i], temp);
temp.swap(images[i]);
swap(temp,images[i]);
for (unsigned long j = 0; j < objects[i].size(); ++j)
{
objects[i][j] = impl::flip_rect_left_right(objects[i][j], get_rect(images[i]));
......@@ -1077,7 +1091,7 @@ namespace dlib
for (unsigned long i = 0; i < images.size(); ++i)
{
flip_image_left_right(images[i], temp);
temp.swap(images[i]);
swap(temp, images[i]);
for (unsigned long j = 0; j < objects[i].size(); ++j)
{
objects[i][j] = impl::flip_rect_left_right(objects[i][j], get_rect(images[i]));
......@@ -1113,7 +1127,7 @@ namespace dlib
for (unsigned long i = 0; i < images.size(); ++i)
{
pyramid_up(images[i], temp, pyr);
temp.swap(images[i]);
swap(temp, images[i]);
for (unsigned long j = 0; j < objects[i].size(); ++j)
{
objects[i][j] = pyr.rect_up(objects[i][j]);
......@@ -1146,7 +1160,7 @@ namespace dlib
for (unsigned long i = 0; i < images.size(); ++i)
{
pyramid_up(images[i], temp, pyr);
temp.swap(images[i]);
swap(temp, images[i]);
for (unsigned long j = 0; j < objects[i].size(); ++j)
{
objects[i][j] = pyr.rect_up(objects[i][j]);
......@@ -1179,7 +1193,7 @@ namespace dlib
for (unsigned long i = 0; i < images.size(); ++i)
{
const point_transform_affine tran = rotate_image(images[i], temp, angle);
temp.swap(images[i]);
swap(temp, images[i]);
for (unsigned long j = 0; j < objects[i].size(); ++j)
{
const rectangle rect = objects[i][j];
......@@ -1210,7 +1224,7 @@ namespace dlib
for (unsigned long i = 0; i < images.size(); ++i)
{
const point_transform_affine tran = rotate_image(images[i], temp, angle);
temp.swap(images[i]);
swap(temp, images[i]);
for (unsigned long j = 0; j < objects[i].size(); ++j)
{
const rectangle rect = objects[i][j];
......@@ -1325,9 +1339,9 @@ namespace dlib
<< "\n\t is_same_object(in_img, out_img): " << is_same_object(in_img, out_img)
);
if (in_img.size() == 0)
if (image_size(in_img) == 0)
{
out_img.clear();
set_image_size(out_img, 0, 0);
return;
}
......@@ -1335,10 +1349,10 @@ namespace dlib
rectangle uprect = pyr.rect_up(rect);
if (uprect.is_empty())
{
out_img.clear();
set_image_size(out_img, 0, 0);
return;
}
out_img.set_size(uprect.bottom()+1, uprect.right()+1);
set_image_size(out_img, uprect.bottom()+1, uprect.right()+1);
resize_image(in_img, out_img, interp);
}
......@@ -1379,7 +1393,7 @@ namespace dlib
{
image_type temp;
pyramid_up(img, temp, pyr);
temp.swap(img);
swap(temp, img);
}
// ----------------------------------------------------------------------------------------
......@@ -1502,7 +1516,7 @@ namespace dlib
chips.resize(chip_locations.size());
for (unsigned long i = 0; i < chips.size(); ++i)
{
chips[i].set_size(chip_locations[i].rows, chip_locations[i].cols);
set_image_size(chips[i], chip_locations[i].rows, chip_locations[i].cols);
// figure out which level in the pyramid to use to extract the chip
int level = -1;
......@@ -1545,7 +1559,7 @@ namespace dlib
std::vector<chip_details> chip_locations(1,location);
dlib::array<image_type2> chips;
extract_image_chips(img, chip_locations, chips);
chips[0].swap(chip);
swap(chips[0], chip);
}
// ----------------------------------------------------------------------------------------
......
......@@ -22,18 +22,18 @@ namespace dlib
public:
template <
typename image_type,
typename image_view_type,
typename pixel_type
>
bool operator() (
const image_type& img,
const image_view_type& img,
const dlib::point& p,
pixel_type& result
) const;
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type>::has_alpha == false
- image_view_type == an image_view or const_image_view object.
- pixel_traits<typename image_view_type::pixel_type>::has_alpha == false
- pixel_traits<pixel_type> is defined
ensures
- if (p is located inside img) then
......@@ -63,18 +63,18 @@ namespace dlib
template <
typename T,
typename image_type,
typename image_view_type,
typename pixel_type
>
bool operator() (
const image_type& img,
const image_view_type& img,
const dlib::vector<T,2>& p,
pixel_type& result
) const;
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type>::has_alpha == false
- image_view_type == an image_view or const_image_view object
- pixel_traits<typename image_view_type::pixel_type>::has_alpha == false
- pixel_traits<pixel_type> is defined
ensures
- if (there is an interpolatable image location at point p in img) then
......@@ -104,18 +104,18 @@ namespace dlib
template <
typename T,
typename image_type,
typename image_view_type,
typename pixel_type
>
bool operator() (
const image_type& img,
const image_view_type& img,
const dlib::vector<T,2>& p,
pixel_type& result
) const;
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type>::has_alpha == false
- image_view_type == an image_view or const_image_view object.
- pixel_traits<typename image_view_type::pixel_type>::has_alpha == false
- pixel_traits<pixel_type> is defined
ensures
- if (there is an interpolatable image location at point p in img) then
......@@ -197,15 +197,17 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- interpolation_type == interpolate_nearest_neighbor, interpolate_bilinear,
interpolate_quadratic, or a type with a compatible interface.
- map_point should be a function which takes dlib::vector<T,2> objects and
returns dlib::vector<T,2> objects. An example is point_transform_affine.
- set_background should be a function which can take a single argument of
type image_type2::type. Examples are black_background, white_background,
and no_background.
type image_traits<image_type2>::pixel_type. Examples are black_background,
white_background, and no_background.
- get_rect(out_img).contains(area) == true
- is_same_object(in_img, out_img) == false
ensures
......@@ -241,14 +243,16 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- interpolation_type == interpolate_nearest_neighbor, interpolate_bilinear,
interpolate_quadratic, or a type with a compatible interface.
- map_point should be a function which takes dlib::vector<T,2> objects and
returns dlib::vector<T,2> objects. An example is point_transform_affine.
- set_background should be a function which can take a single argument of
type image_type2::type. Examples are black_background, white_background,
type image_traits<image_type2>::pixel_type. Examples are black_background, white_background,
and no_background.
- is_same_object(in_img, out_img) == false
ensures
......@@ -273,8 +277,10 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- interpolation_type == interpolate_nearest_neighbor, interpolate_bilinear,
interpolate_quadratic, or a type with a compatible interface.
- map_point should be a function which takes dlib::vector<T,2> objects and
......@@ -302,8 +308,10 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- interpolation_type == interpolate_nearest_neighbor, interpolate_bilinear,
interpolate_quadratic, or a type with a compatible interface.
- is_same_object(in_img, out_img) == false
......@@ -331,10 +339,11 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type1::type>::has_alpha == false
- pixel_traits<typename image_type2::type> is defined
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- pixel_traits<typename image_traits<image_type1>::pixel_type>::has_alpha == false
- is_same_object(in_img, out_img) == false
ensures
- #out_img == a copy of in_img which has been rotated angle radians counter clockwise.
......@@ -359,8 +368,10 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- interpolation_type == interpolate_nearest_neighbor, interpolate_bilinear,
interpolate_quadratic, or a type with a compatible interface.
- is_same_object(in_img, out_img) == false
......@@ -387,10 +398,11 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type1::type>::has_alpha == false
- pixel_traits<typename image_type2::type> is defined
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- pixel_traits<typename image_traits<image_type1>::pixel_type>::has_alpha == false
- is_same_object(in_img, out_img) == false
ensures
- #out_img == A copy of in_img which has been stretched so that it
......@@ -413,10 +425,10 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type1::type> is defined
- pixel_traits<typename image_type2::type> is defined
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- is_same_object(in_img, out_img) == false
ensures
- #out_img.nr() == in_img.nr()
......@@ -439,8 +451,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- T == rectangle or full_object_detection
- images.size() == objects.size()
ensures
......@@ -470,8 +482,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- images.size() == objects.size()
- images.size() == objects2.size()
- T == rectangle or full_object_detection
......@@ -507,10 +519,10 @@ namespace dlib
);
/*!
requires
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- is_vector(angles) == true
- angles.size() > 0
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- images.size() == objects.size()
- images.size() == objects2.size()
- T == rectangle or full_object_detection
......@@ -545,10 +557,10 @@ namespace dlib
);
/*!
requires
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- is_vector(angles) == true
- angles.size() > 0
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- images.size() == objects.size()
- T == rectangle or full_object_detection
ensures
......@@ -567,8 +579,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- images.size() == objects.size()
ensures
- This function replaces each image in images with the left/right flipped
......@@ -593,8 +605,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- images.size() == objects.size()
- images.size() == objects2.size()
ensures
......@@ -623,8 +635,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- images.size() == objects.size()
ensures
- This function replaces each image in images with an upsampled version of that
......@@ -651,8 +663,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- images.size() == objects.size()
- images.size() == objects2.size()
ensures
......@@ -680,8 +692,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- images.size() == objects.size()
ensures
- This function replaces each image in images with a rotated version of that
......@@ -711,8 +723,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type::type> is defined
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- images.size() == objects.size()
- images.size() == objects2.size()
ensures
......@@ -747,10 +759,10 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type1::type> is defined
- pixel_traits<typename image_type2::type> is defined
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- is_same_object(in_img, out_img) == false
ensures
- #out_img.nr() == in_img.nr()
......@@ -774,8 +786,10 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- pyramid_type == a type compatible with the image pyramid objects defined
in dlib/image_transforms/image_pyramid_abstract.h
- interpolation_type == interpolate_nearest_neighbor, interpolate_bilinear,
......@@ -810,8 +824,10 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- pyramid_type == a type compatible with the image pyramid objects defined
in dlib/image_transforms/image_pyramid_abstract.h
- is_same_object(in_img, out_img) == false
......@@ -831,7 +847,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- pyramid_type == a type compatible with the image pyramid objects defined
in dlib/image_transforms/image_pyramid_abstract.h
ensures
......@@ -851,7 +868,8 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
ensures
- performs: pyramid_up(img, pyramid_down<2>());
(i.e. it upsamples the given image and doubles it in size.)
......@@ -998,10 +1016,11 @@ namespace dlib
);
/*!
requires
- image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename image_type1::type>::has_alpha == false
- pixel_traits<typename image_type2::type> is defined
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- pixel_traits<typename image_traits<image_type1>::pixel_type>::has_alpha == false
- for all valid i:
- chip_locations[i].rect.is_empty() == false
- chip_locations[i].size != 0
......
......@@ -113,19 +113,21 @@ namespace dlib
typename connected_functor_type
>
unsigned long label_connected_blobs (
const image_type& img,
const image_type& img_,
const background_functor_type& is_background,
const neighbors_functor_type& get_neighbors,
const connected_functor_type& is_connected,
label_image_type& label_img
label_image_type& label_img_
)
{
// make sure requires clause is not broken
DLIB_ASSERT(is_same_object(img, label_img) == false,
DLIB_ASSERT(is_same_object(img_, label_img_) == false,
"\t unsigned long label_connected_blobs()"
<< "\n\t The input image and output label image can't be the same object."
);
const_image_view<image_type> img(img_);
image_view<label_image_type> label_img(label_img_);
std::stack<point> neighbors;
label_img.set_size(img.nr(), img.nc());
......
......@@ -58,9 +58,9 @@ namespace dlib
with the label_connected_blobs() routine defined below.
!*/
template <typename image_type>
template <typename image_view_type>
bool operator() (
const image_type& img,
const image_view_type& img,
const point& a,
const point& b
) const
......@@ -77,9 +77,9 @@ namespace dlib
with the label_connected_blobs() routine defined below.
!*/
template <typename image_type>
template <typename image_view_type>
bool operator() (
const image_type& img,
const image_view_type& img,
const point& a,
const point& b
) const
......@@ -98,9 +98,9 @@ namespace dlib
with the label_connected_blobs() routine defined below.
!*/
template <typename image_type>
template <typename image_view_type>
bool operator() (
const image_type& img,
const image_view_type& img,
const point& p
) const
{
......@@ -117,9 +117,9 @@ namespace dlib
with the label_connected_blobs() routine defined below.
!*/
template <typename image_type>
template <typename image_view_type>
bool operator() (
const image_type&,
const image_view_type&,
const point&
) const
{
......@@ -146,9 +146,10 @@ namespace dlib
);
/*!
requires
- image_type == is an implementation of array2d/array2d_kernel_abstract.h
- label_image_type == is an implementation of array2d/array2d_kernel_abstract.h
and it must contain integers.
- image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- label_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h and it must contain integer pixels.
- is_background(img, point(c,r)) is a legal expression that evaluates to a bool.
- is_connected(img, point(c,r), point(c2,r2)) is a legal expression that
evaluates to a bool.
......
......@@ -16,14 +16,15 @@ namespace dlib
{
template <typename image_type>
bool is_binary_image (
const image_type& img
const image_type& img_
)
/*!
ensures
- returns true if img contains only on_pixel and off_pixel values.
- returns true if img_ contains only on_pixel and off_pixel values.
- returns false otherwise
!*/
{
const_image_view<image_type> img(img_);
for (long r = 0; r < img.nr(); ++r)
{
for (long c = 0; c < img.nc(); ++c)
......@@ -75,23 +76,25 @@ namespace dlib
long N
>
void binary_dilation (
const in_image_type& in_img,
out_image_type& out_img,
const in_image_type& in_img_,
out_image_type& out_img_,
const unsigned char (&structuring_element)[M][N]
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(M%2 == 1);
COMPILE_TIME_ASSERT(N%2 == 1);
DLIB_ASSERT(is_same_object(in_img,out_img) == false,
DLIB_ASSERT(is_same_object(in_img_,out_img_) == false,
"\tvoid binary_dilation()"
<< "\n\tYou must give two different image objects"
);
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type::type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img) ,
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img_) ,
"\tvoid binary_dilation()"
<< "\n\tin_img must be a binary image"
);
......@@ -101,6 +104,8 @@ namespace dlib
);
const_image_view<in_image_type> in_img(in_img_);
image_view<out_image_type> out_img(out_img_);
// if there isn't any input image then don't do anything
if (in_img.size() == 0)
......@@ -147,23 +152,25 @@ namespace dlib
long N
>
void binary_erosion (
const in_image_type& in_img,
out_image_type& out_img,
const in_image_type& in_img_,
out_image_type& out_img_,
const unsigned char (&structuring_element)[M][N]
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(M%2 == 1);
COMPILE_TIME_ASSERT(N%2 == 1);
DLIB_ASSERT(is_same_object(in_img,out_img) == false,
DLIB_ASSERT(is_same_object(in_img_,out_img_) == false,
"\tvoid binary_erosion()"
<< "\n\tYou must give two different image objects"
);
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type::type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img) ,
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img_) ,
"\tvoid binary_erosion()"
<< "\n\tin_img must be a binary image"
);
......@@ -172,6 +179,8 @@ namespace dlib
<< "\n\tthe structuring_element must be a binary image"
);
const_image_view<in_image_type> in_img(in_img_);
image_view<out_image_type> out_img(out_img_);
// if there isn't any input image then don't do anything
......@@ -229,8 +238,10 @@ namespace dlib
const unsigned long iter = 1
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(M%2 == 1);
......@@ -239,7 +250,7 @@ namespace dlib
"\tvoid binary_open()"
<< "\n\tYou must give two different image objects"
);
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type::type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img) ,
"\tvoid binary_open()"
<< "\n\tin_img must be a binary image"
......@@ -251,13 +262,13 @@ namespace dlib
// if there isn't any input image then don't do anything
if (in_img.size() == 0)
if (num_rows(in_img)*num_columns(in_img) == 0)
{
out_img.clear();
set_image_size(out_img, 0,0);
return;
}
out_img.set_size(in_img.nr(),in_img.nc());
set_image_size(out_img, num_rows(in_img), num_columns(in_img));
if (iter == 0)
{
......@@ -278,14 +289,14 @@ namespace dlib
// do the extra erosions
for (unsigned long i = 1; i < iter; ++i)
{
temp1.swap(temp2);
swap(temp1, temp2);
binary_erosion(temp2,temp1,structuring_element);
}
// do the extra dilations
for (unsigned long i = 1; i < iter; ++i)
{
temp1.swap(temp2);
swap(temp1, temp2);
binary_dilation(temp2,temp1,structuring_element);
}
......@@ -308,8 +319,11 @@ namespace dlib
const unsigned long iter = 1
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(M%2 == 1);
......@@ -318,7 +332,7 @@ namespace dlib
"\tvoid binary_close()"
<< "\n\tYou must give two different image objects"
);
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type::type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img) ,
"\tvoid binary_close()"
<< "\n\tin_img must be a binary image"
......@@ -330,13 +344,13 @@ namespace dlib
// if there isn't any input image then don't do anything
if (in_img.size() == 0)
if (num_rows(in_img)*num_columns(in_img) == 0)
{
out_img.clear();
set_image_size(out_img, 0,0);
return;
}
out_img.set_size(in_img.nr(),in_img.nc());
set_image_size(out_img, num_rows(in_img), num_columns(in_img));
if (iter == 0)
{
......@@ -357,14 +371,14 @@ namespace dlib
// do the extra dilations
for (unsigned long i = 1; i < iter; ++i)
{
temp1.swap(temp2);
swap(temp1, temp2);
binary_dilation(temp2,temp1,structuring_element);
}
// do the extra erosions
for (unsigned long i = 1; i < iter; ++i)
{
temp1.swap(temp2);
swap(temp1, temp2);
binary_erosion(temp2,temp1,structuring_element);
}
......@@ -380,26 +394,34 @@ namespace dlib
typename out_image_type
>
void binary_intersection (
const in_image_type1& in_img1,
const in_image_type2& in_img2,
out_image_type& out_img
const in_image_type1& in_img1_,
const in_image_type2& in_img2_,
out_image_type& out_img_
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type1::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type2::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type1>::pixel_type in_pixel_type1;
typedef typename image_traits<in_image_type2>::pixel_type in_pixel_type2;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type1>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type2>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type1::type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type2::type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img1) ,
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type1>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type2>::grayscale);
DLIB_ASSERT(is_binary_image(in_img1_) ,
"\tvoid binary_intersection()"
<< "\n\tin_img1 must be a binary image"
);
DLIB_ASSERT(is_binary_image(in_img2) ,
DLIB_ASSERT(is_binary_image(in_img2_) ,
"\tvoid binary_intersection()"
<< "\n\tin_img2 must be a binary image"
);
const_image_view<in_image_type1> in_img1(in_img1_);
const_image_view<in_image_type2> in_img2(in_img2_);
image_view<out_image_type> out_img(out_img_);
DLIB_ASSERT(in_img1.nc() == in_img2.nc(),
"\tvoid binary_intersection()"
<< "\n\tin_img1 and in_img2 must have the same ncs."
......@@ -444,26 +466,35 @@ namespace dlib
typename out_image_type
>
void binary_union (
const in_image_type1& in_img1,
const in_image_type2& in_img2,
out_image_type& out_img
const in_image_type1& in_img1_,
const in_image_type2& in_img2_,
out_image_type& out_img_
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type1::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type2::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type1>::pixel_type in_pixel_type1;
typedef typename image_traits<in_image_type2>::pixel_type in_pixel_type2;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type1>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type2>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type1::type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type2::type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img1) ,
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type1>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type2>::grayscale);
DLIB_ASSERT(is_binary_image(in_img1_) ,
"\tvoid binary_intersection()"
<< "\n\tin_img1 must be a binary image"
);
DLIB_ASSERT(is_binary_image(in_img2) ,
DLIB_ASSERT(is_binary_image(in_img2_) ,
"\tvoid binary_intersection()"
<< "\n\tin_img2 must be a binary image"
);
const_image_view<in_image_type1> in_img1(in_img1_);
const_image_view<in_image_type2> in_img2(in_img2_);
image_view<out_image_type> out_img(out_img_);
DLIB_ASSERT(in_img1.nc() == in_img2.nc(),
"\tvoid binary_intersection()"
<< "\n\tin_img1 and in_img2 must have the same ncs."
......@@ -508,26 +539,34 @@ namespace dlib
typename out_image_type
>
void binary_difference (
const in_image_type1& in_img1,
const in_image_type2& in_img2,
out_image_type& out_img
const in_image_type1& in_img1_,
const in_image_type2& in_img2_,
out_image_type& out_img_
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type1::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type2::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type1>::pixel_type in_pixel_type1;
typedef typename image_traits<in_image_type2>::pixel_type in_pixel_type2;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type1>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type2>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type1::type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type2::type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img1) ,
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type1>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type2>::grayscale);
DLIB_ASSERT(is_binary_image(in_img1_) ,
"\tvoid binary_difference()"
<< "\n\tin_img1 must be a binary image"
);
DLIB_ASSERT(is_binary_image(in_img2) ,
DLIB_ASSERT(is_binary_image(in_img2_) ,
"\tvoid binary_difference()"
<< "\n\tin_img2 must be a binary image"
);
const_image_view<in_image_type1> in_img1(in_img1_);
const_image_view<in_image_type2> in_img2(in_img2_);
image_view<out_image_type> out_img(out_img_);
DLIB_ASSERT(in_img1.nc() == in_img2.nc(),
"\tvoid binary_difference()"
<< "\n\tin_img1 and in_img2 must have the same ncs."
......@@ -571,20 +610,25 @@ namespace dlib
typename out_image_type
>
void binary_complement (
const in_image_type& in_img,
out_image_type& out_img
const in_image_type& in_img_,
out_image_type& out_img_
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
typedef typename image_traits<in_image_type>::pixel_type in_pixel_type;
typedef typename image_traits<out_image_type>::pixel_type out_pixel_type;
COMPILE_TIME_ASSERT( pixel_traits<in_pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<out_pixel_type>::has_alpha == false );
using namespace morphological_operations_helpers;
COMPILE_TIME_ASSERT(pixel_traits<typename in_image_type::type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img) ,
COMPILE_TIME_ASSERT(pixel_traits<in_pixel_type>::grayscale);
DLIB_ASSERT(is_binary_image(in_img_) ,
"\tvoid binary_complement()"
<< "\n\tin_img must be a binary image"
);
const_image_view<in_image_type> in_img(in_img_);
image_view<out_image_type> out_img(out_img_);
// if there isn't any input image then don't do anything
if (in_img.size() == 0)
......
......@@ -24,11 +24,11 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::grayscale == true
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type and out_image_type are image objects that implement the
interface defined in dlib/image_processing/generic_image.h
- in_img must contain a grayscale pixel type.
- both in_img and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- is_same_object(in_img,out_img) == false
- M % 2 == 1 (i.e. M must be odd)
- N % 2 == 1 (i.e. N must be odd)
......@@ -58,11 +58,11 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::grayscale == true
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type and out_image_type are image objects that implement the
interface defined in dlib/image_processing/generic_image.h
- in_img must contain a grayscale pixel type.
- both in_img and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- is_same_object(in_img,out_img) == false
- M % 2 == 1 (i.e. M must be odd)
- N % 2 == 1 (i.e. N must be odd)
......@@ -93,11 +93,11 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::grayscale == true
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type and out_image_type are image objects that implement the
interface defined in dlib/image_processing/generic_image.h
- in_img must contain a grayscale pixel type.
- both in_img and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- is_same_object(in_img,out_img) == false
- M % 2 == 1 (i.e. M must be odd)
- N % 2 == 1 (i.e. N must be odd)
......@@ -129,11 +129,11 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::grayscale == true
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type and out_image_type are image objects that implement the
interface defined in dlib/image_processing/generic_image.h
- in_img must contain a grayscale pixel type.
- both in_img and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- is_same_object(in_img,out_img) == false
- M % 2 == 1 (i.e. M must be odd)
- N % 2 == 1 (i.e. N must be odd)
......@@ -163,14 +163,11 @@ namespace dlib
);
/*!
requires
- in_image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- in_image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type1::type>::grayscale == true
- pixel_traits<typename in_image_type2::type>::grayscale == true
- pixel_traits<typename in_image_type1::type>::has_alpha == false
- pixel_traits<typename in_image_type2::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type1, in_image_type2, and out_image_type are image objects that
implement the interface defined in dlib/image_processing/generic_image.h
- in_img1 and in_img2 must contain grayscale pixel types.
- in_img1, in_img2, and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- all pixels in in_img1 and in_img2 are set to either on_pixel or off_pixel
(i.e. they must be binary images)
- in_img1.nc() == in_img2.nc()
......@@ -197,14 +194,11 @@ namespace dlib
);
/*!
requires
- in_image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- in_image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type1::type>::grayscale == true
- pixel_traits<typename in_image_type2::type>::grayscale == true
- pixel_traits<typename in_image_type1::type>::has_alpha == false
- pixel_traits<typename in_image_type2::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type1, in_image_type2, and out_image_type are image objects that
implement the interface defined in dlib/image_processing/generic_image.h
- in_img1 and in_img2 must contain grayscale pixel types.
- in_img1, in_img2, and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- all pixels in in_img1 and in_img2 are set to either on_pixel or off_pixel
(i.e. they must be binary images)
- in_img1.nc() == in_img2.nc()
......@@ -231,14 +225,11 @@ namespace dlib
);
/*!
requires
- in_image_type1 == is an implementation of array2d/array2d_kernel_abstract.h
- in_image_type2 == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type1::type>::grayscale == true
- pixel_traits<typename in_image_type2::type>::grayscale == true
- pixel_traits<typename in_image_type1::type>::has_alpha == false
- pixel_traits<typename in_image_type2::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type1, in_image_type2, and out_image_type are image objects that
implement the interface defined in dlib/image_processing/generic_image.h
- in_img1 and in_img2 must contain grayscale pixel types.
- in_img1, in_img2, and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- all pixels in in_img1 and in_img2 are set to either on_pixel or off_pixel
(i.e. they must be binary images)
- in_img1.nc() == in_img2.nc()
......@@ -263,11 +254,11 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::grayscale == true
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type and out_image_type are image objects that implement the
interface defined in dlib/image_processing/generic_image.h
- in_img must contain a grayscale pixel type.
- both in_img and out_img must contain pixels with no alpha channel.
(i.e. pixel_traits::has_alpha==false for their pixels)
- all pixels in in_img are set to either on_pixel or off_pixel
(i.e. it must be a binary image)
ensures
......
......@@ -125,18 +125,28 @@ namespace dlib
// ------------------------------------------------------------------------------------
namespace impl
{
template <typename image_view_type>
struct uint8_or_uint16_pixels
{
typedef typename image_view_type::pixel_type pixel_type;
const static bool value = is_same_type<pixel_type,uint8>::value ||
is_same_type<pixel_type,uint16>::value;
};
}
// This is an overload of get_pixel_edges() that is optimized to segment images
// with 8bit or 16bit pixels very quickly. We do this by using a radix sort
// instead of quicksort.
template <typename in_image_type, typename T>
typename enable_if_c<is_same_type<typename in_image_type::type,uint8>::value ||
is_same_type<typename in_image_type::type,uint16>::value>::type
typename enable_if<impl::uint8_or_uint16_pixels<in_image_type> >::type
get_pixel_edges (
const in_image_type& in_img,
std::vector<segment_image_edge_data_T<T> >& sorted_edges
)
{
typedef typename in_image_type::type ptype;
typedef typename in_image_type::pixel_type ptype;
typedef T diff_type;
std::vector<unsigned long> counts(std::numeric_limits<ptype>::max()+1, 0);
......@@ -243,8 +253,7 @@ namespace dlib
// This is the general purpose version of get_pixel_edges(). It handles all pixel types.
template <typename in_image_type, typename T>
typename disable_if_c<is_same_type<typename in_image_type::type,uint8>::value ||
is_same_type<typename in_image_type::type,uint16>::value>::type
typename disable_if<impl::uint8_or_uint16_pixels<in_image_type> >::type
get_pixel_edges (
const in_image_type& in_img,
std::vector<segment_image_edge_data_T<T> >& sorted_edges
......@@ -253,7 +262,7 @@ namespace dlib
const rectangle area = get_rect(in_img);
sorted_edges.reserve(area.area()*4);
typedef typename in_image_type::type ptype;
typedef typename in_image_type::pixel_type ptype;
edge_diff_funct<ptype> edge_diff;
typedef T diff_type;
typedef segment_image_edge_data_T<T> segment_image_edge_data;
......@@ -327,23 +336,26 @@ namespace dlib
typename out_image_type
>
void segment_image (
const in_image_type& in_img,
out_image_type& out_img,
const in_image_type& in_img_,
out_image_type& out_img_,
const double k = 200,
const unsigned long min_size = 10
)
{
using namespace dlib::impl;
typedef typename in_image_type::type ptype;
typedef typename image_traits<in_image_type>::pixel_type ptype;
typedef typename edge_diff_funct<ptype>::diff_type diff_type;
// make sure requires clause is not broken
DLIB_ASSERT(is_same_object(in_img, out_img) == false,
DLIB_ASSERT(is_same_object(in_img_, out_img_) == false,
"\t void segment_image()"
<< "\n\t The input images can't be the same object."
);
COMPILE_TIME_ASSERT(is_unsigned_type<typename out_image_type::type>::value);
COMPILE_TIME_ASSERT(is_unsigned_type<typename image_traits<out_image_type>::pixel_type>::value);
const_image_view<in_image_type> in_img(in_img_);
image_view<out_image_type> out_img(out_img_);
out_img.set_size(in_img.nr(), in_img.nc());
// don't bother doing anything if the image is too small
......@@ -610,7 +622,7 @@ namespace dlib
typename EXP
>
void find_candidate_object_locations (
const in_image_type& in_img,
const in_image_type& in_img_,
std::vector<rectangle>& rects,
const matrix_exp<EXP>& kvals,
const unsigned long min_size = 20,
......@@ -629,9 +641,10 @@ namespace dlib
typedef dlib::set<rectangle, mm_type>::kernel_1a set_of_rects;
using namespace dlib::impl;
typedef typename in_image_type::type ptype;
typedef typename image_traits<in_image_type>::pixel_type ptype;
typedef typename edge_diff_funct<ptype>::diff_type diff_type;
const_image_view<in_image_type> in_img(in_img_);
// don't bother doing anything if the image is too small
if (in_img.nr() < 2 || in_img.nc() < 2)
......
......@@ -23,11 +23,13 @@ namespace dlib
);
/*!
requires
- in_image_type == an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == an implementation of array2d/array2d_kernel_abstract.h
- in_image_type::type == Any pixel type with a pixel_traits specialization or a
dlib matrix object representing a row or column vector.
- out_image_type::type == unsigned integer type
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- in_image_type can contain any pixel type with a pixel_traits specialization
or a dlib matrix object representing a row or column vector.
- out_image_type must contain an unsigned integer pixel type.
- is_same_object(in_img, out_img) == false
ensures
- Attempts to segment in_img into regions which have some visual consistency to
......@@ -65,6 +67,8 @@ namespace dlib
);
/*!
requires
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- is_vector(kvals) == true
- kvals.size() > 0
ensures
......
This diff is collapsed.
......@@ -27,15 +27,17 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- in_img and out_img do not contain pixels with an alpha channel. That is,
pixel_traits::has_alpha is false for the pixels in these objects.
- is_same_object(in_img, out_img) == false
- T must be some scalar type
- filter.size() != 0
- scale != 0
- if (pixel_traits<typename in_image_type::type>::grayscale == false) then
- if (in_img doesn't contain grayscale pixels) then
- use_abs == false && add_to == false
(i.e. You can only use the use_abs and add_to options with grayscale images)
ensures
......@@ -47,7 +49,7 @@ namespace dlib
any applicable color space conversion or value saturation is performed. Note that if
add_to is true then the filtered output value will be added to out_img rather than
overwriting the original value.
- if (pixel_traits<typename in_image_type::type>::grayscale == false) then
- if (in_img doesn't contain grayscale pixels) then
- The filter is applied to each color channel independently.
- if (use_abs == true) then
- pixel values after filtering that are < 0 are converted to their absolute values.
......@@ -88,10 +90,12 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- in_img and out_img do not contain pixels with an alpha channel. That is,
pixel_traits::has_alpha is false for the pixels in these objects.
- is_same_object(in_img, out_img) == false
- T must be some scalar type
- scale != 0
......@@ -99,7 +103,7 @@ namespace dlib
- col_filter.size() != 0
- is_vector(row_filter) == true
- is_vector(col_filter) == true
- if (pixel_traits<typename in_image_type::type>::grayscale == false) then
- if (in_img doesn't contain grayscale pixels) then
- use_abs == false && add_to == false
(i.e. You can only use the use_abs and add_to options with grayscale images)
ensures
......@@ -114,7 +118,7 @@ namespace dlib
any applicable color space conversion or value saturation is performed. Note that if
add_to is true then the filtered output value will be added to out_img rather than
overwriting the original value.
- if (pixel_traits<typename in_image_type::type>::grayscale == false) then
- if (in_img doesn't contain grayscale pixels) then
- The filter is applied to each color channel independently.
- if (use_abs == true) then
- pixel values after filtering that are < 0 are converted to their absolute values
......@@ -153,8 +157,10 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- in_img, out_img, row_filter, and col_filter must all contain float type elements.
- is_same_object(in_img, out_img) == false
- row_filter.size() != 0
......@@ -196,11 +202,13 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::grayscale == true
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- in_img and out_img do not contain pixels with an alpha channel. That is,
pixel_traits::has_alpha is false for the pixels in these objects.
- out_img contains grayscale pixels.
- is_same_object(in_img, out_img) == false
- T must be some scalar type
- scale != 0
......@@ -244,8 +252,8 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type> must be defined
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- T and U should be scalar types
- shrink_rect(get_rect(img),1).contains(c,r)
- shrink_rect(get_rect(img),1).contains(c+NC-1,r+NR-1)
......@@ -281,8 +289,10 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::rgb == true
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- img must contain RGB pixels, that is pixel_traits::rgb == true for the pixels
in img.
- T should be a struct with .red .green and .blue members.
- U should be a scalar type
- shrink_rect(get_rect(img),1).contains(c,r)
......@@ -350,10 +360,12 @@ namespace dlib
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- in_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- out_image_type == an image object that implements the interface defined in
dlib/image_processing/generic_image.h
- in_img and out_img do not contain pixels with an alpha channel. That is,
pixel_traits::has_alpha is false for the pixels in these objects.
- is_same_object(in_img, out_img) == false
- sigma > 0
- max_size > 0
......@@ -365,7 +377,7 @@ namespace dlib
results are stored into #out_img.
- Pixel values are stored into out_img using the assign_pixel() function and therefore
any applicable color space conversion or value saturation is performed.
- if (pixel_traits<typename in_image_type::type>::grayscale == false) then
- if (in_img doesn't contain grayscale pixels) then
- The filter is applied to each color channel independently.
- Pixels close enough to the edge of in_img to not have the filter still fit
inside the image are set to zero.
......@@ -388,10 +400,10 @@ namespace dlib
requires
- out.nr() == img.nr()
- out.nc() == img.nc()
- image_type1 == an implementation of array2d/array2d_kernel_abstract.h
and it must contain a scalar type
- image_type2 == an implementation of array2d/array2d_kernel_abstract.h
and it must contain a scalar type
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h and it must contain grayscale pixels.
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h and it must contain grayscale pixels.
- is_same_object(img,out) == false
ensures
- for all valid r and c:
......@@ -413,10 +425,10 @@ namespace dlib
);
/*!
requires
- image_type1 == an implementation of array2d/array2d_kernel_abstract.h
and it must contain a scalar type
- image_type2 == an implementation of array2d/array2d_kernel_abstract.h
and it must contain a scalar type
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h and it must contain grayscale pixels.
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h and it must contain grayscale pixels.
- is_same_object(img,out) == false
ensures
- #out.nr() == img.nr()
......@@ -438,16 +450,16 @@ namespace dlib
image_type2& out,
const long width,
const long height,
const typename image_type1::type& thresh
const typename image_traits<image_type1>::pixel_type& thresh
);
/*!
requires
- out.nr() == img.nr()
- out.nc() == img.nc()
- image_type1 == an implementation of array2d/array2d_kernel_abstract.h
and it must contain a scalar type
- image_type2 == an implementation of array2d/array2d_kernel_abstract.h
and it must contain a scalar type
- image_type1 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h and it must contain grayscale pixels.
- image_type2 == an image object that implements the interface defined in
dlib/image_processing/generic_image.h and it must contain grayscale pixels.
- is_same_object(img,out) == false
- width > 0 && height > 0
ensures
......
......@@ -22,15 +22,18 @@ namespace dlib
typename out_image_type
>
void threshold_image (
const in_image_type& in_img,
out_image_type& out_img,
typename pixel_traits<typename in_image_type::type>::basic_pixel_type thresh
const in_image_type& in_img_,
out_image_type& out_img_,
typename pixel_traits<typename image_traits<in_image_type>::pixel_type>::basic_pixel_type thresh
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<in_image_type>::pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<out_image_type>::pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT(pixel_traits<typename out_image_type::type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<typename image_traits<out_image_type>::pixel_type>::grayscale);
const_image_view<in_image_type> in_img(in_img_);
image_view<out_image_type> out_img(out_img_);
// if there isn't any input image then don't do anything
if (in_img.size() == 0)
......@@ -60,7 +63,7 @@ namespace dlib
>
void threshold_image (
image_type& img,
typename pixel_traits<typename image_type::type>::basic_pixel_type thresh
typename pixel_traits<typename image_traits<image_type>::pixel_type>::basic_pixel_type thresh
)
{
threshold_image(img,img,thresh);
......@@ -73,16 +76,19 @@ namespace dlib
typename out_image_type
>
void auto_threshold_image (
const in_image_type& in_img,
out_image_type& out_img
const in_image_type& in_img_,
out_image_type& out_img_
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::is_unsigned == true );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::is_unsigned == true );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<in_image_type>::pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<out_image_type>::pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<in_image_type>::pixel_type>::is_unsigned == true );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<out_image_type>::pixel_type>::is_unsigned == true );
COMPILE_TIME_ASSERT(pixel_traits<typename image_traits<out_image_type>::pixel_type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<typename out_image_type::type>::grayscale);
const_image_view<in_image_type> in_img(in_img_);
image_view<out_image_type> out_img(out_img_);
// if there isn't any input image then don't do anything
if (in_img.size() == 0)
......@@ -171,7 +177,7 @@ namespace dlib
thresh = (a + b)/2;
// now actually apply the threshold
threshold_image(in_img,out_img,thresh);
threshold_image(in_img_,out_img_,thresh);
}
template <
......@@ -191,25 +197,28 @@ namespace dlib
typename out_image_type
>
void hysteresis_threshold (
const in_image_type& in_img,
out_image_type& out_img,
typename pixel_traits<typename in_image_type::type>::basic_pixel_type lower_thresh,
typename pixel_traits<typename in_image_type::type>::basic_pixel_type upper_thresh
const in_image_type& in_img_,
out_image_type& out_img_,
typename pixel_traits<typename image_traits<in_image_type>::pixel_type>::basic_pixel_type lower_thresh,
typename pixel_traits<typename image_traits<in_image_type>::pixel_type>::basic_pixel_type upper_thresh
)
{
COMPILE_TIME_ASSERT( pixel_traits<typename in_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename out_image_type::type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<in_image_type>::pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT( pixel_traits<typename image_traits<out_image_type>::pixel_type>::has_alpha == false );
COMPILE_TIME_ASSERT(pixel_traits<typename out_image_type::type>::grayscale);
COMPILE_TIME_ASSERT(pixel_traits<typename image_traits<out_image_type>::pixel_type>::grayscale);
DLIB_ASSERT( lower_thresh <= upper_thresh && is_same_object(in_img, out_img) == false,
"\tvoid hysteresis_threshold(in_img, out_img, lower_thresh, upper_thresh)"
DLIB_ASSERT( lower_thresh <= upper_thresh && is_same_object(in_img_, out_img_) == false,
"\tvoid hysteresis_threshold(in_img_, out_img_, lower_thresh, upper_thresh)"
<< "\n\tYou can't use an upper_thresh that is less than your lower_thresh"
<< "\n\tlower_thresh: " << lower_thresh
<< "\n\tupper_thresh: " << upper_thresh
<< "\n\tis_same_object(in_img,out_img): " << is_same_object(in_img,out_img)
<< "\n\tis_same_object(in_img_,out_img_): " << is_same_object(in_img_,out_img_)
);
const_image_view<in_image_type> in_img(in_img_);
image_view<out_image_type> out_img(out_img_);
// if there isn't any input image then don't do anything
if (in_img.size() == 0)
{
......@@ -229,7 +238,7 @@ namespace dlib
{
for (long c = 0; c < in_img.nc(); ++c)
{
typename pixel_traits<typename in_image_type::type>::basic_pixel_type p;
typename pixel_traits<typename image_traits<in_image_type>::pixel_type>::basic_pixel_type p;
assign_pixel(p,in_img[r][c]);
if (p >= upper_thresh)
{
......
......@@ -22,15 +22,15 @@ namespace dlib
void threshold_image (
const in_image_type& in_img,
out_image_type& out_img,
typename pixel_traits<typename in_image_type::type>::basic_pixel_type thresh
typename pixel_traits<typename image_traits<in_image_type>::pixel_type>::basic_pixel_type thresh
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename out_image_type::type>::grayscale == true
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- pixel_traits<typename image_traits<out_image_type>::pixel_type>::grayscale == true
- pixel_traits<typename image_traits<in_image_type>::pixel_type>::has_alpha == false
- pixel_traits<typename image_traits<out_image_type>::pixel_type>::has_alpha == false
ensures
- #out_img == the thresholded version of in_img (in_img is converted to a grayscale
intensity image if it is color). Pixels in in_img with grayscale values >= thresh
......@@ -44,7 +44,7 @@ namespace dlib
>
void threshold_image (
image_type& img,
typename pixel_traits<typename image_type::type>::basic_pixel_type thresh
typename pixel_traits<typename image_traits<image_type>::pixel_type>::basic_pixel_type thresh
);
/*!
requires
......@@ -67,12 +67,12 @@ namespace dlib
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename in_image_type::type>::max() <= 65535
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename in_image_type::type>::is_unsigned == true
- pixel_traits<typename out_image_type::type>::grayscale == true
- pixel_traits<typename out_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::is_unsigned == true
- pixel_traits<typename image_traits<in_image_type>::pixel_type>::max() <= 65535
- pixel_traits<typename image_traits<in_image_type>::pixel_type>::has_alpha == false
- pixel_traits<typename image_traits<in_image_type>::pixel_type>::is_unsigned == true
- pixel_traits<typename image_traits<out_image_type>::pixel_type>::grayscale == true
- pixel_traits<typename image_traits<out_image_type>::pixel_type>::has_alpha == false
- pixel_traits<typename image_traits<out_image_type>::pixel_type>::is_unsigned == true
ensures
- #out_img == the thresholded version of in_img (in_img is converted to a grayscale
intensity image if it is color). Pixels in in_img with grayscale values >= thresh
......@@ -106,16 +106,16 @@ namespace dlib
void hysteresis_threshold (
const in_image_type& in_img,
out_image_type& out_img,
typename pixel_traits<typename in_image_type::type>::basic_pixel_type lower_thresh,
typename pixel_traits<typename in_image_type::type>::basic_pixel_type upper_thresh
typename pixel_traits<typename image_traits<in_image_type>::pixel_type>::basic_pixel_type lower_thresh,
typename pixel_traits<typename image_traits<in_image_type>::pixel_type>::basic_pixel_type upper_thresh
);
/*!
requires
- in_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- out_image_type == is an implementation of array2d/array2d_kernel_abstract.h
- pixel_traits<typename out_image_type::type>::grayscale == true
- pixel_traits<typename in_image_type::type>::has_alpha == false
- pixel_traits<typename out_image_type::type>::has_alpha == false
- pixel_traits<typename image_traits<out_image_type>::pixel_type>::grayscale == true
- pixel_traits<typename image_traits<in_image_type>::pixel_type>::has_alpha == false
- pixel_traits<typename image_traits<out_image_type>::pixel_type>::has_alpha == false
- lower_thresh <= upper_thresh
- is_same_object(in_img, out_img) == false
ensures
......
......@@ -13,6 +13,7 @@
#include "matrix/matrix_conv.h"
#include "matrix/matrix_read_from_istream.h"
#include "matrix/matrix_fft.h"
#include "matrix/matrix_generic_image.h"
#ifdef DLIB_USE_BLAS
#include "matrix/matrix_blas_bindings.h"
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment