* scribo/binarization/internal/wolf_formula.hh,
* scribo/binarization/internal/wolf_functor.hh,
* scribo/binarization/wolf.hh,
* scribo/util/integral_sum_sum2_global_min_functor.hh,
* src/binarization/wolf.cc,
* tests/binarization/wolf.cc,
* tests/binarization/wolf.ref.pbm,
* tests/binarization/wolf_weven_hodd.ref.pbm,
* tests/binarization/wolf_wodd_heven.ref.pbm,
* tests/binarization/wolf_wodd_hodd.ref.pbm: New.
* src/binarization/Makefile.am,
* tests/binarization/Makefile.am: Add new target.
---
scribo/ChangeLog | 18 ++
.../scribo/binarization/internal/wolf_formula.hh | 95 ++++++++++
.../scribo/binarization/internal/wolf_functor.hh | 176 +++++++++++++++++
scribo/scribo/binarization/wolf.hh | 197 ++++++++++++++++++++
.../util/integral_sum_sum2_global_min_functor.hh | 156 ++++++++++++++++
scribo/src/binarization/Makefile.am | 9 +-
scribo/src/binarization/wolf.cc | 107 +++++++++++
scribo/tests/binarization/Makefile.am | 19 ++-
scribo/tests/binarization/wolf.cc | 93 +++++++++
scribo/tests/binarization/wolf.ref.pbm | Bin 0 -> 32884 bytes
scribo/tests/binarization/wolf_weven_hodd.ref.pbm | Bin 0 -> 32820 bytes
scribo/tests/binarization/wolf_wodd_heven.ref.pbm | Bin 0 -> 32884 bytes
scribo/tests/binarization/wolf_wodd_hodd.ref.pbm | Bin 0 -> 32820 bytes
13 files changed, 867 insertions(+), 3 deletions(-)
create mode 100644 scribo/scribo/binarization/internal/wolf_formula.hh
create mode 100644 scribo/scribo/binarization/internal/wolf_functor.hh
create mode 100644 scribo/scribo/binarization/wolf.hh
create mode 100644 scribo/scribo/util/integral_sum_sum2_global_min_functor.hh
create mode 100644 scribo/src/binarization/wolf.cc
create mode 100644 scribo/tests/binarization/wolf.cc
create mode 100644 scribo/tests/binarization/wolf.ref.pbm
create mode 100644 scribo/tests/binarization/wolf_weven_hodd.ref.pbm
create mode 100644 scribo/tests/binarization/wolf_wodd_heven.ref.pbm
create mode 100644 scribo/tests/binarization/wolf_wodd_hodd.ref.pbm
diff --git a/scribo/ChangeLog b/scribo/ChangeLog
index 9604def..ff7d1fa 100644
--- a/scribo/ChangeLog
+++ b/scribo/ChangeLog
@@ -1,5 +1,23 @@
2012-08-23 Guillaume Lazzara <z(a)lrde.epita.fr>
+ Add Wolf's binarization algorithm.
+
+ * scribo/binarization/internal/wolf_formula.hh,
+ * scribo/binarization/internal/wolf_functor.hh,
+ * scribo/binarization/wolf.hh,
+ * scribo/util/integral_sum_sum2_global_min_functor.hh,
+ * src/binarization/wolf.cc,
+ * tests/binarization/wolf.cc,
+ * tests/binarization/wolf.ref.pbm,
+ * tests/binarization/wolf_weven_hodd.ref.pbm,
+ * tests/binarization/wolf_wodd_heven.ref.pbm,
+ * tests/binarization/wolf_wodd_hodd.ref.pbm: New.
+
+ * src/binarization/Makefile.am,
+ * tests/binarization/Makefile.am: Add new target.
+
+2012-08-23 Guillaume Lazzara <z(a)lrde.epita.fr>
+
Add more debug.
* scribo/binarization/internal/local_threshold_debug.hh,
diff --git a/scribo/scribo/binarization/internal/wolf_formula.hh
b/scribo/scribo/binarization/internal/wolf_formula.hh
new file mode 100644
index 0000000..a3084a7
--- /dev/null
+++ b/scribo/scribo/binarization/internal/wolf_formula.hh
@@ -0,0 +1,95 @@
+// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to produce
+// an executable, this file does not by itself cause the resulting
+// executable to be covered by the GNU General Public License. This
+// exception does not however invalidate any other reasons why the
+// executable file might be covered by the GNU General Public License.
+
+#ifndef SCRIBO_BINARIZATION_INTERNAL_WOLF_FORMULA_HH
+# define SCRIBO_BINARIZATION_INTERNAL_WOLF_FORMULA_HH
+
+
+/// \file
+///
+/// \brief Routines computing a threshold using Wolf's binarization
+/// formula.
+
+
+// Setup default Wolf's formula parameters values.
+// These macros may be used in other variant of Wolf's algorithms.
+//
+// Values are set according to the following reference: <FIXME>
+
+# define SCRIBO_DEFAULT_WOLF_K 0.34
+
+
+#include <mln/core/alias/point2d.hh>
+
+namespace scribo
+{
+
+ namespace binarization
+ {
+
+ namespace internal
+ {
+
+ using namespace mln;
+
+ template <typename V>
+ struct wolf_formula
+ {
+
+ /*! \brief Compute a threshold using Wolf's formula.
+
+ \todo doc!
+
+ \return A threshold.
+ */
+ double operator()(const double m_x_y, const double s_x_y,
+ const double K, const double global_max_stddev,
+ const V& global_min) const;
+
+ };
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename V>
+ inline
+ double
+ wolf_formula<V>::operator()(const double m_x_y, const double s_x_y,
+ const double K, const double global_max_stddev,
+ const V& global_min) const
+ {
+ return m_x_y - K * (1 - s_x_y / global_max_stddev) * (m_x_y - global_min);
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::binarization::internal
+
+ } // end of namespace scribo::binarization
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_BINARIZATION_INTERNAL_WOLF_FORMULA_HH
diff --git a/scribo/scribo/binarization/internal/wolf_functor.hh
b/scribo/scribo/binarization/internal/wolf_functor.hh
new file mode 100644
index 0000000..d394c21
--- /dev/null
+++ b/scribo/scribo/binarization/internal/wolf_functor.hh
@@ -0,0 +1,176 @@
+// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to produce
+// an executable, this file does not by itself cause the resulting
+// executable to be covered by the GNU General Public License. This
+// exception does not however invalidate any other reasons why the
+// executable file might be covered by the GNU General Public License.
+
+#ifndef SCRIBO_BINARIZATION_INTERNAL_WOLF_FUNCTOR_HH
+# define SCRIBO_BINARIZATION_INTERNAL_WOLF_FUNCTOR_HH
+
+/// \file
+///
+///
+
+# include <mln/core/image/image2d.hh>
+# include <mln/core/alias/neighb2d.hh>
+# include <mln/extension/fill.hh>
+
+# include <scribo/binarization/internal/wolf_formula.hh>
+
+# ifdef SCRIBO_LOCAL_THRESHOLD_DEBUG
+# include <scribo/binarization/internal/local_threshold_debug.hh>
+# endif // ! SCRIBO_LOCAL_THRESHOLD_DEBUG
+
+
+namespace scribo
+{
+
+ namespace binarization
+ {
+
+ namespace internal
+ {
+
+ using namespace mln;
+
+
+ template <typename I>
+ struct wolf_functor
+ {
+ typedef mln_value(I) V;
+
+ wolf_functor(const Image<I>& input, double K,
+ const mln_value(I)& global_min,
+ double global_max_stddev);
+
+ // Run every 4 pixels.
+ void exec(double mean, double stddev);
+
+ void end_of_row(int);
+
+ void finalize();
+
+
+ const I input;
+ mln_ch_value(I,bool) output;
+
+ const mln_value(I)* pi;
+ bool* po;
+
+ double K_;
+
+ V global_min_;
+ double global_max_stddev_;
+
+ scribo::binarization::internal::wolf_formula<V> formula_;
+
+ int step_;
+ unsigned next_line3;
+ unsigned offset1;
+ unsigned offset2;
+ };
+
+#ifndef MLN_INCLUDE_ONLY
+
+ template <typename I>
+ wolf_functor<I>::wolf_functor(const Image<I>& input_,
+ double K,
+ const mln_value(I)& global_min,
+ double global_max_stddev)
+ : input(exact(input_)),
+ pi(&input(input.domain().pmin())),
+ K_(K),
+ global_min_(global_min),
+ global_max_stddev_(global_max_stddev)
+ {
+ step_ = 3;
+
+ // Since we iterate from a smaller image in the largest ones
+ // and image at scale 1 does not always have a size which can
+ // be divided by 3, some sites in the border may not be
+ // processed and we must skip them.
+ int more_offset = - (3 - input.ncols() % 3);
+ if (more_offset == - 3)
+ more_offset = 0; // No offset needed.
+
+ next_line3 = input.delta_index(dpoint2d(+2,0))
+ + 2 * input.border() + more_offset;
+
+ offset1 = input.delta_index(dpoint2d(+1,0));
+ offset2 = input.delta_index(dpoint2d(+2,0));
+
+ initialize(output, input);
+ po = &output(output.domain().pmin());
+ }
+
+ template <typename I>
+ void
+ wolf_functor<I>::exec(double mean, double stddev)
+ {
+ double th = formula_(mean, stddev, K_,
+ global_max_stddev_, global_min_);
+
+ for (int i = 0; i < step_; ++i, ++po, ++pi)
+ {
+ *po = (*pi <= th);
+ *(po + offset1) = (*(pi + offset1) <= th);
+ *(po + offset2) = (*(pi + offset2) <= th);
+ }
+
+# ifdef SCRIBO_LOCAL_THRESHOLD_DEBUG
+ // Store local mean
+ unsigned index = pi - input.buffer();
+
+ debug_mean.element(index) = mean * mean_debug_factor;
+ debug_stddev.element(index) = stddev * stddev_debug_factor;
+ debug_threshold.element(index) = th;
+
+ double alpha = K_ * (1 - stddev / R_);
+ debug_alpham.element(index) = alpha * mean * alpham_debug_factor;
+ debug_alphacond.element(index) = (stddev < (alpha * mean / 2.));
+# endif // ! SCRIBO_LOCAL_THRESHOLD_DEBUG
+
+ }
+
+ template <typename I>
+ void
+ wolf_functor<I>::end_of_row(int)
+ {
+ po += next_line3;
+ pi += next_line3;
+ }
+
+ template <typename I>
+ void
+ wolf_functor<I>::finalize()
+ {
+ }
+
+#endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::binarization::internal
+
+ } // end of namespace scribo::binarization
+
+} // end of namespace scribo
+
+#endif // SCRIBO_BINARIZATION_INTERNAL_WOLF_FUNCTOR_HH
diff --git a/scribo/scribo/binarization/wolf.hh b/scribo/scribo/binarization/wolf.hh
new file mode 100644
index 0000000..25b4531
--- /dev/null
+++ b/scribo/scribo/binarization/wolf.hh
@@ -0,0 +1,197 @@
+// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to produce
+// an executable, this file does not by itself cause the resulting
+// executable to be covered by the GNU General Public License. This
+// exception does not however invalidate any other reasons why the
+// executable file might be covered by the GNU General Public License.
+
+#ifndef SCRIBO_BINARIZATION_WOLF_HH
+# define SCRIBO_BINARIZATION_WOLF_HH
+
+/// \file
+///
+///
+
+# include <mln/core/concept/image.hh>
+# include <scribo/binarization/internal/wolf_functor.hh>
+# include <scribo/binarization/internal/local_threshold_core.hh>
+# include <scribo/util/integral_sum_sum2_global_min_functor.hh>
+
+namespace scribo
+{
+
+ namespace binarization
+ {
+
+ using namespace mln;
+
+
+ /*! \brief Convert an image into a binary image.
+
+ \input[in] input An image.
+ \input[in] window_size The window size.
+ \input[in] K Wolf's formulae constant.
+
+ \return A binary image.
+
+ This implementation is based on article "Text Localization,
+ Enhancement and Binarization in Multimedia Documents", Christian
+ Wolf, Jean-Michel Jolion, Françoise Chassaing, ICPR 2002.
+
+ */
+ template <typename I>
+ mln_ch_value(I, bool)
+ wolf(const Image<I>& input, unsigned window_size, double K);
+
+
+
+ /*! \brief Convert an image into a binary image.
+
+ Wolf's formulae constant K is set to 0.34.
+
+ \input[in] input An image.
+ \input[in] window_size The window size.
+
+ \return A binary image.
+
+ */
+ template <typename I>
+ mln_ch_value(I, bool)
+ wolf(const Image<I>& input, unsigned window_size);
+
+
+ /// \overload
+ /// The window size is set to 11.
+ //
+ template <typename I>
+ mln_ch_value(I, bool)
+ wolf(const Image<I>& input);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ namespace internal
+ {
+
+ template <typename I>
+ struct global_max_stddev
+ {
+ global_max_stddev()
+ : max_stddev(0)
+ {
+ }
+
+ // Run every 4 pixels.
+ void exec(double mean, double stddev)
+ {
+ (void) mean;
+ if (max_stddev < stddev)
+ max_stddev = stddev;
+ }
+
+ void end_of_row(int)
+ {
+ }
+
+ void finalize()
+ {
+ }
+
+ double max_stddev;
+ };
+
+ } // end of namespace scribo::binarization::internal
+
+
+ // Facades
+
+ template <typename I>
+ mln_ch_value(I, bool)
+ wolf(const Image<I>& input, unsigned window_size, double K)
+ {
+ trace::entering("scribo::binarization::wolf");
+
+ mln_precondition(exact(input).is_valid());
+
+
+ // Make sure the image sizes are a multiple of 3 in each
+ // dimension. (browsing while binarizing relies on that
+ // property).
+ mln::util::array<mln::util::couple<box2d, unsigned> >
+ sub_domains = scribo::util::compute_sub_domains(input, 1, 3);
+
+ border::adjust(input, sub_domains(1).second());
+ border::mirror(input);
+
+ scribo::util::integral_sum_sum2_global_min_functor<value::int_u8, double>
fi;
+ image2d<mln::util::couple<double,double> >
+ integral = scribo::util::init_integral_image(input, 3, fi,
+ sub_domains[2].first(),
+ sub_domains[2].second());
+
+ window_size /= 3;
+ if (window_size % 2)
+ window_size += 2;
+ else
+ window_size += 1;
+
+
+ // Compute max(stddev) of all windows.
+ internal::global_max_stddev<I> f_max_stddev;
+ scribo::canvas::integral_browsing(integral, 1, window_size,
+ window_size, 3, f_max_stddev);
+
+ // Binarize !
+ internal::wolf_functor<I>
+ f(input, K, fi.global_min(), f_max_stddev.max_stddev);
+ scribo::canvas::integral_browsing(integral, 1, window_size,
+ window_size, 3, f);
+
+ trace::exiting("scribo::binarization::wolf");
+ return f.output;
+ }
+
+
+ template <typename I>
+ mln_ch_value(I, bool)
+ wolf(const Image<I>& input, unsigned window_size)
+ {
+ return wolf(input, window_size, SCRIBO_DEFAULT_WOLF_K);
+ }
+
+
+ template <typename I>
+ mln_ch_value(I, bool)
+ wolf(const Image<I>& input)
+ {
+ return wolf(input, 11);
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::binarization
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_BINARIZATION_WOLF_HH
diff --git a/scribo/scribo/util/integral_sum_sum2_global_min_functor.hh
b/scribo/scribo/util/integral_sum_sum2_global_min_functor.hh
new file mode 100644
index 0000000..20a61c0
--- /dev/null
+++ b/scribo/scribo/util/integral_sum_sum2_global_min_functor.hh
@@ -0,0 +1,156 @@
+// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to produce
+// an executable, this file does not by itself cause the resulting
+// executable to be covered by the GNU General Public License. This
+// exception does not however invalidate any other reasons why the
+// executable file might be covered by the GNU General Public License.
+
+#ifndef SCRIBO_UTIL_INTEGRAL_SUM_SUM2_GLOBAL_MIN_FUNCTOR_HH
+# define SCRIBO_UTIL_INTEGRAL_SUM_SUM2_GLOBAL_MIN_FUNCTOR_HH
+
+/// \file
+///
+///
+
+# include <mln/util/couple.hh>
+
+namespace scribo
+{
+
+ namespace util
+ {
+
+ template <typename V, typename S = mln_sum(V)>
+ class integral_sum_sum2_global_min_functor
+ {
+ public:
+ typedef mln::util::couple<S, S> result;
+
+ void begin_of_first_row();
+ void begin_of_row();
+ void end_of_row();
+
+ void begin_of_col();
+ void end_of_col();
+
+
+ void take(const V& v);
+
+ result to_result_first_row() const;
+ result to_result(const result& up_result) const;
+
+ const V& global_min() const;
+
+ private:
+ S h_sum_;
+ S h_sum_2_;
+
+ V global_min_;
+ };
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename V, typename S>
+ inline
+ void
+ integral_sum_sum2_global_min_functor<V,S>::begin_of_first_row()
+ {
+ h_sum_ = 0;
+ h_sum_2_ = 0;
+ global_min_ = 0;
+ }
+
+ template <typename V, typename S>
+ inline
+ void
+ integral_sum_sum2_global_min_functor<V,S>::begin_of_row()
+ {
+ h_sum_ = 0;
+ h_sum_2_ = 0;
+ }
+
+ template <typename V, typename S>
+ inline
+ void
+ integral_sum_sum2_global_min_functor<V,S>::take(const V& v)
+ {
+ if (global_min_ > v)
+ global_min_ = v;
+
+ h_sum_ += v;
+ h_sum_2_ += v * v;
+ }
+
+ template <typename V, typename S>
+ inline
+ typename integral_sum_sum2_global_min_functor<V,S>::result
+ integral_sum_sum2_global_min_functor<V,S>::to_result_first_row() const
+ {
+ return result(h_sum_, h_sum_2_);
+ }
+
+ template <typename V, typename S>
+ inline
+ typename integral_sum_sum2_global_min_functor<V,S>::result
+ integral_sum_sum2_global_min_functor<V,S>::to_result(const result&
up_result) const
+ {
+ return result(h_sum_ + up_result.first(),
+ h_sum_2_ + up_result.second());
+ }
+
+ template <typename V, typename S>
+ inline
+ const V&
+ integral_sum_sum2_global_min_functor<V,S>::global_min() const
+ {
+ return global_min_;
+ }
+
+ template <typename V, typename S>
+ inline
+ void
+ integral_sum_sum2_global_min_functor<V,S>::begin_of_col()
+ {
+ }
+
+ template <typename V, typename S>
+ inline
+ void
+ integral_sum_sum2_global_min_functor<V,S>::end_of_col()
+ {
+ }
+
+
+ template <typename V, typename S>
+ inline
+ void
+ integral_sum_sum2_global_min_functor<V,S>::end_of_row()
+ {
+ }
+
+#endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::util
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_UTIL_INTEGRAL_SUM_SUM2_GLOBAL_MIN_FUNCTOR_HH
diff --git a/scribo/src/binarization/Makefile.am b/scribo/src/binarization/Makefile.am
index a0a4378..68b83dc 100644
--- a/scribo/src/binarization/Makefile.am
+++ b/scribo/src/binarization/Makefile.am
@@ -35,7 +35,8 @@ if HAVE_MAGICKXX
sauvola \
sauvola_ms \
sauvola_ms_fg \
- sauvola_ms_split
+ sauvola_ms_split \
+ wolf
global_threshold_SOURCES = global_threshold.cc
@@ -70,6 +71,12 @@ if HAVE_MAGICKXX
sauvola_LDFLAGS = $(AM_LDFLAGS) \
$(MAGICKXX_LDFLAGS)
+ wolf_SOURCES = wolf.cc
+ wolf_CPPFLAGS = $(AM_CPPFLAGS) \
+ $(MAGICKXX_CPPFLAGS)
+ wolf_LDFLAGS = $(AM_LDFLAGS) \
+ $(MAGICKXX_LDFLAGS)
+
sauvola_debug_SOURCES = sauvola_debug.cc
sauvola_debug_CPPFLAGS = $(AM_CPPFLAGS) \
-DSCRIBO_LOCAL_THRESHOLD_DEBUG \
diff --git a/scribo/src/binarization/wolf.cc b/scribo/src/binarization/wolf.cc
new file mode 100644
index 0000000..c481e09
--- /dev/null
+++ b/scribo/src/binarization/wolf.cc
@@ -0,0 +1,107 @@
+// Copyright (C) 2009, 2010, 2011 EPITA Research and Development
+// Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to produce
+// an executable, this file does not by itself cause the resulting
+// executable to be covered by the GNU General Public License. This
+// exception does not however invalidate any other reasons why the
+// executable file might be covered by the GNU General Public License.
+
+#include <mln/core/image/image2d.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/io/magick/load.hh>
+#include <mln/io/pbm/save.hh>
+#include <mln/data/transform.hh>
+#include <mln/fun/v2v/rgb_to_luma.hh>
+
+#include <scribo/binarization/wolf.hh>
+#include <scribo/debug/option_parser.hh>
+#include <scribo/debug/logger.hh>
+
+static const scribo::debug::arg_data arg_desc[] =
+{
+ { "input.*", "An image." },
+ { "output.pbm", "A binary image." },
+ {0, 0}
+};
+
+
+// --enable/disable-<name>
+static const scribo::debug::toggle_data toggle_desc[] =
+{
+ // name, description, default value
+ {0, 0, false}
+};
+
+
+// --<name> <args>
+static const scribo::debug::opt_data opt_desc[] =
+{
+ // name, description, arguments, check args function, number of args, default arg
+ { "debug-prefix", "Enable debug image outputs. Prefix image name with
that "
+ "given prefix.", "<prefix>", 0, 1, 0 },
+ { "k", "Wolf's formulae parameter", "<value>",
0, 1, "0.34" },
+ { "verbose", "Enable verbose mode", 0, 0, 0, 0 },
+ { "win-size", "Window size", "<size>", 0, 1,
"101" },
+ {0, 0, 0, 0, 0, 0}
+};
+
+
+
+int main(int argc, char *argv[])
+{
+ using namespace mln;
+
+ scribo::debug::option_parser options(arg_desc, toggle_desc, opt_desc);
+
+ if (!options.parse(argc, argv))
+ return 1;
+
+ // Enable debug output.
+ if (options.is_set("debug-prefix"))
+ {
+
scribo::debug::logger().set_filename_prefix(options.opt_value("debug-prefix").c_str());
+ scribo::debug::logger().set_level(scribo::debug::All);
+ }
+
+ Magick::InitializeMagick(*argv);
+
+ trace::entering("main");
+
+ bool verbose = options.is_set("verbose");
+ unsigned w = atoi(options.opt_value("win-size").c_str());
+ double k = atof(options.opt_value("k").c_str());
+
+ if (verbose)
+ std::cout << "Using w=" << w << " and k="
<< k << std::endl;
+
+ image2d<value::rgb8> input;
+ io::magick::load(input, options.arg("input.*"));
+
+ // Convert to Gray level image.
+ image2d<value::int_u8>
+ input_1_gl = data::transform(input,
mln::fun::v2v::rgb_to_luma<value::int_u8>());
+
+ image2d<bool> out = scribo::binarization::wolf(input_1_gl, w, k);
+
+ io::pbm::save(out, options.arg("output.pbm"));
+
+ trace::exiting("main");
+}
diff --git a/scribo/tests/binarization/Makefile.am
b/scribo/tests/binarization/Makefile.am
index a2962bb..bac5a24 100644
--- a/scribo/tests/binarization/Makefile.am
+++ b/scribo/tests/binarization/Makefile.am
@@ -22,9 +22,22 @@ include $(top_srcdir)/scribo/tests/tests.mk
EXTRA_DIST = \
niblack.res.pbm \
+ niblack_wodd_heven.ref.pbm \
+ niblack_weven_hodd.ref.pbm \
+ niblack_wodd_hodd.ref.pbm \
sauvola_ms.ref.pbm \
+ sauvola_ms_wodd_heven.ref.pbm \
+ sauvola_ms_weven_hodd.ref.pbm \
+ sauvola_ms_wodd_hodd.ref.pbm \
sauvola.ref.pbm \
- otsu.ref.pbm
+ sauvola_wodd_heven.ref.pbm \
+ sauvola_weven_hodd.ref.pbm \
+ sauvola_wodd_hodd.ref.pbm \
+ otsu.ref.pbm \
+ wolf.ref.pbm \
+ wolf_wodd_heven.ref.pbm \
+ wolf_weven_hodd.ref.pbm \
+ wolf_wodd_hodd.ref.pbm
check_PROGRAMS = \
global_threshold \
@@ -32,7 +45,8 @@ check_PROGRAMS = \
niblack \
otsu \
sauvola \
- sauvola_ms
+ sauvola_ms \
+ wolf
global_threshold_SOURCES = global_threshold.cc
@@ -41,6 +55,7 @@ niblack_SOURCES = niblack.cc
otsu_SOURCES = otsu.cc
sauvola_SOURCES = sauvola.cc
sauvola_ms_SOURCES = sauvola_ms.cc
+wolf_SOURCES = wolf.cc
TESTS = $(check_PROGRAMS)
diff --git a/scribo/tests/binarization/wolf.cc b/scribo/tests/binarization/wolf.cc
new file mode 100644
index 0000000..27d7cd2
--- /dev/null
+++ b/scribo/tests/binarization/wolf.cc
@@ -0,0 +1,93 @@
+// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to produce
+// an executable, this file does not by itself cause the resulting
+// executable to be covered by the GNU General Public License. This
+// exception does not however invalidate any other reasons why the
+// executable file might be covered by the GNU General Public License.
+
+/// \file
+
+#include <mln/core/image/image2d.hh>
+#include <mln/data/compare.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/io/pgm/load.hh>
+#include <mln/io/pbm/load.hh>
+
+#include <scribo/binarization/wolf.hh>
+
+#include "tests/data.hh"
+
+int main()
+{
+ using namespace mln;
+
+ // even height and width
+ {
+ image2d<value::int_u8> input;
+ io::pgm::load(input, MILENA_IMG_DIR "/lena.pgm");
+
+ image2d<bool> bin = scribo::binarization::wolf(input, 101);
+
+ image2d<bool> ref;
+ io::pbm::load(ref, SCRIBO_TESTS_DIR "binarization/wolf.ref.pbm");
+
+ mln_assertion(bin == ref);
+ }
+
+ // even height and odd width
+ {
+ image2d<value::int_u8> input;
+ io::pgm::load(input, SCRIBO_IMG_DIR "/lena_wodd_heven.pgm");
+
+ image2d<bool> bin = scribo::binarization::wolf(input, 101);
+
+ image2d<bool> ref;
+ io::pbm::load(ref, SCRIBO_TESTS_DIR
"binarization/wolf_wodd_heven.ref.pbm");
+
+ mln_assertion(bin == ref);
+ }
+
+ // odd height and even width
+ {
+ image2d<value::int_u8> input;
+ io::pgm::load(input, SCRIBO_IMG_DIR "/lena_weven_hodd.pgm");
+
+ image2d<bool> bin = scribo::binarization::wolf(input, 101);
+
+ image2d<bool> ref;
+ io::pbm::load(ref, SCRIBO_TESTS_DIR
"binarization/wolf_weven_hodd.ref.pbm");
+
+ mln_assertion(bin == ref);
+ }
+
+ // odd height and width
+ {
+ image2d<value::int_u8> input;
+ io::pgm::load(input, SCRIBO_IMG_DIR "/lena_wodd_hodd.pgm");
+
+ image2d<bool> bin = scribo::binarization::wolf(input, 101);
+
+ image2d<bool> ref;
+ io::pbm::load(ref, SCRIBO_TESTS_DIR
"binarization/wolf_wodd_hodd.ref.pbm");
+
+ mln_assertion(bin == ref);
+ }
+}
diff --git a/scribo/tests/binarization/wolf.ref.pbm
b/scribo/tests/binarization/wolf.ref.pbm
new file mode 100644
index 0000000..9b8a367
Binary files /dev/null and b/scribo/tests/binarization/wolf.ref.pbm differ
diff --git a/scribo/tests/binarization/wolf_weven_hodd.ref.pbm
b/scribo/tests/binarization/wolf_weven_hodd.ref.pbm
new file mode 100644
index 0000000..d2281ed
Binary files /dev/null and b/scribo/tests/binarization/wolf_weven_hodd.ref.pbm differ
diff --git a/scribo/tests/binarization/wolf_wodd_heven.ref.pbm
b/scribo/tests/binarization/wolf_wodd_heven.ref.pbm
new file mode 100644
index 0000000..c29fffa
Binary files /dev/null and b/scribo/tests/binarization/wolf_wodd_heven.ref.pbm differ
diff --git a/scribo/tests/binarization/wolf_wodd_hodd.ref.pbm
b/scribo/tests/binarization/wolf_wodd_hodd.ref.pbm
new file mode 100644
index 0000000..9dce37a
Binary files /dev/null and b/scribo/tests/binarization/wolf_wodd_hodd.ref.pbm differ
--
1.7.2.5