olena-2.0-74-g9be09ea Compute Sauvola on documents with light text and dark background.

* scribo/binarization/internal/compute_local_threshold.hh, * scribo/binarization/internal/first_pass_functor.hh, * scribo/binarization/internal/sauvola_formula.hh, * scribo/binarization/local_threshold.hh: Update formula. --- scribo/ChangeLog | 9 ++++++ .../internal/compute_local_threshold.hh | 15 +++++++++- .../binarization/internal/first_pass_functor.hh | 2 +- .../binarization/internal/sauvola_formula.hh | 22 +++++++++++----- scribo/scribo/binarization/local_threshold.hh | 27 +++++++++++++------ 5 files changed, 56 insertions(+), 19 deletions(-) diff --git a/scribo/ChangeLog b/scribo/ChangeLog index f8d7491..6c79022 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,3 +1,12 @@ +2012-08-23 Guillaume Lazzara <z@lrde.epita.fr> + + Compute Sauvola on documents with light text and dark background. + + * scribo/binarization/internal/compute_local_threshold.hh, + * scribo/binarization/internal/first_pass_functor.hh, + * scribo/binarization/internal/sauvola_formula.hh, + * scribo/binarization/local_threshold.hh: Update formula. + 2012-05-10 Guillaume Lazzara <z@lrde.epita.fr> Improve option parser. diff --git a/scribo/scribo/binarization/internal/compute_local_threshold.hh b/scribo/scribo/binarization/internal/compute_local_threshold.hh index 147ef0f..4c25e17 100644 --- a/scribo/scribo/binarization/internal/compute_local_threshold.hh +++ b/scribo/scribo/binarization/internal/compute_local_threshold.hh @@ -42,7 +42,8 @@ -// extern mln::image2d<double> skewness; +extern mln::image2d<double> skewness; +extern mln::image2d<bool> skewness_pbm; namespace scribo { @@ -117,6 +118,11 @@ namespace scribo - simple.at_(row_max, col_min) - simple.at_(row_min, col_max)); + // if (!skewness_pbm(p)) + // { + // m_x_y_tmp = 255 * wh - m_x_y_tmp; + // } + double m_x_y = m_x_y_tmp / wh; # ifdef SCRIBO_LOCAL_THRESHOLD_DEBUG @@ -130,6 +136,11 @@ namespace scribo - squared.at_(row_max, col_min) - squared.at_(row_min, col_max)); + // if (!skewness_pbm(p)) + // { + // s_x_y_tmp = std::pow(255, 2) * wh - s_x_y_tmp; + // } + double s_x_y = std::sqrt((s_x_y_tmp - (m_x_y_tmp * m_x_y_tmp) / wh) / (wh - 1.f)); # ifdef SCRIBO_LOCAL_THRESHOLD_DEBUG @@ -140,7 +151,7 @@ namespace scribo // Thresholding. // skewness_ = skewness(p); // b = (p == point2d(5,5)); - double t_x_y = formula(m_x_y, s_x_y, K, R); + double t_x_y = formula(p, m_x_y, s_x_y, K, R); # ifdef SCRIBO_LOCAL_THRESHOLD_DEBUG double alpha = K * (1 - s_x_y / R); diff --git a/scribo/scribo/binarization/internal/first_pass_functor.hh b/scribo/scribo/binarization/internal/first_pass_functor.hh index 8da401b..f0ae5a9 100644 --- a/scribo/scribo/binarization/internal/first_pass_functor.hh +++ b/scribo/scribo/binarization/internal/first_pass_functor.hh @@ -132,7 +132,7 @@ namespace scribo unsigned p = pxl.offset(); value::int_u8 t_p; - mln::convert::from_to(formula_(mean, stddev, K_, R_), + mln::convert::from_to(formula_(input.point_at_index(p), mean, stddev, K_, R_), t_p); msk.element(p) = input.element(p) < t_p; diff --git a/scribo/scribo/binarization/internal/sauvola_formula.hh b/scribo/scribo/binarization/internal/sauvola_formula.hh index adbef13..e010e85 100644 --- a/scribo/scribo/binarization/internal/sauvola_formula.hh +++ b/scribo/scribo/binarization/internal/sauvola_formula.hh @@ -46,6 +46,10 @@ # define SCRIBO_DEFAULT_SAUVOLA_R 128 +#include <mln/core/alias/point2d.hh> + +extern mln::image2d<bool> skewness_pbm; + namespace scribo { @@ -55,6 +59,8 @@ namespace scribo namespace internal { + using namespace mln; + struct sauvola_formula { @@ -70,13 +76,13 @@ namespace scribo \return A threshold. */ - double operator()(const double m_x_y, const double s_x_y, + double operator()(const point2d& p, const double m_x_y, const double s_x_y, const double K, const double R) const; /*! \overload K = 0.34 and R = 128. */ - double operator()(const double m_x_y, const double s_x_y) const; + double operator()(const point2d& p, const double m_x_y, const double s_x_y) const; }; @@ -88,7 +94,7 @@ namespace scribo inline double - sauvola_formula::operator()(const double m_x_y, const double s_x_y, + sauvola_formula::operator()(const point2d& p, const double m_x_y, const double s_x_y, const double K, const double R) const { // if (b) @@ -98,15 +104,17 @@ namespace scribo // if (skewness_ > 0) // if (new_t != old_t) // std::cout << skewness_ << " - " << new_t << " vs " << old_t << std::endl; - - return m_x_y * (1.0 + K * ((s_x_y / R) - 1.0)); + if (skewness_pbm(p)) + return m_x_y * (1.0 + K * ((s_x_y / R) - 1.0)); + else + return (255 - m_x_y) * (1.0 + K * ((s_x_y / R) - 1.0)); } inline double - sauvola_formula::operator()(const double m_x_y, const double s_x_y) const + sauvola_formula::operator()(const point2d& p, const double m_x_y, const double s_x_y) const { - return (*this)(m_x_y, s_x_y, + return (*this)(p, m_x_y, s_x_y, SCRIBO_DEFAULT_SAUVOLA_K, SCRIBO_DEFAULT_SAUVOLA_R); } diff --git a/scribo/scribo/binarization/local_threshold.hh b/scribo/scribo/binarization/local_threshold.hh index 9d116ed..ab589e2 100644 --- a/scribo/scribo/binarization/local_threshold.hh +++ b/scribo/scribo/binarization/local_threshold.hh @@ -34,12 +34,13 @@ /// /// \brief Binarize an image using a threshold image. +extern mln::image2d<bool> skewness_pbm; + namespace scribo { using namespace mln; - namespace binarization { @@ -110,8 +111,10 @@ namespace scribo mln_piter(I) p(input.domain()); for_all(p) - output(p) = (input(p) <= threshold(p)); - + if (skewness_pbm(p)) + output(p) = (input(p) <= threshold(p)); + else + output(p) = ((255 - input(p)) <= threshold(p)); trace::exiting("scribo::binarization::impl::generic::local_threshold"); return output; @@ -132,6 +135,8 @@ namespace scribo const I& input = exact(input_); const T& threshold = exact(threshold_); + border::resize(::skewness_pbm, input.border()); + typedef mln_ch_value(I, bool) O; O output; initialize(output, input); @@ -139,8 +144,12 @@ namespace scribo mln_pixter(const I) pi(input); mln_pixter(const T) pt(threshold); mln_pixter(O) po(output); + for_all_3(pi, pt, po) - po.val() = pi.val() <= pt.val(); + if (skewness_pbm.element(pi.offset())) + po.val() = (pi.val() <= pt.val()); + else + po.val() = ((255 - pi.val()) <= pt.val()); trace::exiting("scribo::binarization::impl::generic::local_threshold_fastest"); return output; @@ -159,7 +168,7 @@ namespace scribo template <typename I, typename T> mln_ch_value(I, bool) - local_threshold_dispatch(trait::image::value_alignment::any, + local_threshold_dispatch(trait::image::speed::any, trait::image::speed::any, const Image<I>& input, const Image<T>& threshold) { @@ -169,7 +178,7 @@ namespace scribo template <typename I, typename T> mln_ch_value(I, bool) - local_threshold_dispatch(trait::image::value_alignment::with_grid, + local_threshold_dispatch(trait::image::speed::fastest, trait::image::speed::fastest, const Image<I>& input, const Image<T>& threshold) { @@ -181,9 +190,9 @@ namespace scribo local_threshold_dispatch(const Image<I>& input, const Image<T>& threshold) { - return local_threshold_dispatch(mln_trait_image_value_alignment(I)(), - mln_trait_image_speed(I)(), - exact(input), exact(threshold)); + return local_threshold_dispatch(mln_trait_image_speed(I)(), + mln_trait_image_speed(T)(), + input, threshold); } } // end of namespace scribo::binarization::internal -- 1.7.2.5
participants (1)
-
Guillaume Lazzara