LRE
Sign In
Sign Up
Sign In
Sign Up
Manage this list
×
Keyboard Shortcuts
Thread View
j
: Next unread message
k
: Previous unread message
j a
: Jump to all threads
j l
: Jump to MailingList overview
2024
December
November
October
September
August
July
June
May
April
March
February
January
2023
December
November
October
September
August
July
June
May
April
March
February
January
2022
December
November
October
September
August
July
June
May
April
March
February
January
2021
December
November
October
September
August
July
June
May
April
March
February
January
2020
December
November
October
September
August
July
June
May
April
March
February
January
2019
December
November
October
September
August
July
June
May
April
March
February
January
2018
December
November
October
September
August
July
June
May
April
March
February
January
2017
December
November
October
September
August
July
June
May
April
March
February
January
2016
December
November
October
September
August
July
June
May
April
March
February
January
2015
December
November
October
September
August
July
June
May
April
March
February
January
2014
December
November
October
September
August
July
June
May
April
March
February
January
2013
December
November
October
September
August
July
June
May
April
March
February
January
2012
December
November
October
September
August
July
June
May
April
March
February
January
2011
December
November
October
September
August
July
June
May
April
March
February
January
2010
December
November
October
September
August
July
June
May
April
March
February
January
2009
December
November
October
September
August
July
June
May
April
March
February
January
2008
December
November
October
September
August
July
June
May
April
March
February
January
2007
December
November
October
September
August
July
June
May
April
March
February
January
2006
December
November
October
September
August
July
June
May
April
March
February
January
2005
December
November
October
September
August
July
June
May
April
March
February
January
2004
December
November
October
September
August
July
June
May
April
March
List overview
Download
Olena-patches
March 2010
----- 2024 -----
December 2024
November 2024
October 2024
September 2024
August 2024
July 2024
June 2024
May 2024
April 2024
March 2024
February 2024
January 2024
----- 2023 -----
December 2023
November 2023
October 2023
September 2023
August 2023
July 2023
June 2023
May 2023
April 2023
March 2023
February 2023
January 2023
----- 2022 -----
December 2022
November 2022
October 2022
September 2022
August 2022
July 2022
June 2022
May 2022
April 2022
March 2022
February 2022
January 2022
----- 2021 -----
December 2021
November 2021
October 2021
September 2021
August 2021
July 2021
June 2021
May 2021
April 2021
March 2021
February 2021
January 2021
----- 2020 -----
December 2020
November 2020
October 2020
September 2020
August 2020
July 2020
June 2020
May 2020
April 2020
March 2020
February 2020
January 2020
----- 2019 -----
December 2019
November 2019
October 2019
September 2019
August 2019
July 2019
June 2019
May 2019
April 2019
March 2019
February 2019
January 2019
----- 2018 -----
December 2018
November 2018
October 2018
September 2018
August 2018
July 2018
June 2018
May 2018
April 2018
March 2018
February 2018
January 2018
----- 2017 -----
December 2017
November 2017
October 2017
September 2017
August 2017
July 2017
June 2017
May 2017
April 2017
March 2017
February 2017
January 2017
----- 2016 -----
December 2016
November 2016
October 2016
September 2016
August 2016
July 2016
June 2016
May 2016
April 2016
March 2016
February 2016
January 2016
----- 2015 -----
December 2015
November 2015
October 2015
September 2015
August 2015
July 2015
June 2015
May 2015
April 2015
March 2015
February 2015
January 2015
----- 2014 -----
December 2014
November 2014
October 2014
September 2014
August 2014
July 2014
June 2014
May 2014
April 2014
March 2014
February 2014
January 2014
----- 2013 -----
December 2013
November 2013
October 2013
September 2013
August 2013
July 2013
June 2013
May 2013
April 2013
March 2013
February 2013
January 2013
----- 2012 -----
December 2012
November 2012
October 2012
September 2012
August 2012
July 2012
June 2012
May 2012
April 2012
March 2012
February 2012
January 2012
----- 2011 -----
December 2011
November 2011
October 2011
September 2011
August 2011
July 2011
June 2011
May 2011
April 2011
March 2011
February 2011
January 2011
----- 2010 -----
December 2010
November 2010
October 2010
September 2010
August 2010
July 2010
June 2010
May 2010
April 2010
March 2010
February 2010
January 2010
----- 2009 -----
December 2009
November 2009
October 2009
September 2009
August 2009
July 2009
June 2009
May 2009
April 2009
March 2009
February 2009
January 2009
----- 2008 -----
December 2008
November 2008
October 2008
September 2008
August 2008
July 2008
June 2008
May 2008
April 2008
March 2008
February 2008
January 2008
----- 2007 -----
December 2007
November 2007
October 2007
September 2007
August 2007
July 2007
June 2007
May 2007
April 2007
March 2007
February 2007
January 2007
----- 2006 -----
December 2006
November 2006
October 2006
September 2006
August 2006
July 2006
June 2006
May 2006
April 2006
March 2006
February 2006
January 2006
----- 2005 -----
December 2005
November 2005
October 2005
September 2005
August 2005
July 2005
June 2005
May 2005
April 2005
March 2005
February 2005
January 2005
----- 2004 -----
December 2004
November 2004
October 2004
September 2004
August 2004
July 2004
June 2004
May 2004
April 2004
March 2004
olena-patches@lrde.epita.fr
4 participants
277 discussions
Start a n
N
ew thread
last-svn-commit-44-g27b5f71 configure.ac: Configure scribo/demo/review.
by Guillaume Lazzara
--- ChangeLog | 4 ++++ configure.ac | 2 +- 2 files changed, 5 insertions(+), 1 deletions(-) diff --git a/ChangeLog b/ChangeLog index 961ff85..4f21dd6 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,7 @@ +2010-02-16 Guillaume Lazzara <z(a)lrde.epita.fr> + + * configure.ac: Configure scribo/demo/review. + 2009-12-15 Guillaume Lazzara <z(a)lrde.epita.fr> * configure.ac: Configure scribo/tests/core. diff --git a/configure.ac b/configure.ac index 0f66fa3..0edfcb6 100644 --- a/configure.ac +++ b/configure.ac @@ -210,7 +210,7 @@ AM_CONDITIONAL([ENABLE_SCRIBO], [test x$enable_scribo = xyes]) AC_CONFIG_FILES([ scribo/Makefile - scribo/demo/Makefile + scribo/demo/review/Makefile scribo/src/Makefile scribo/src/binarization/Makefile scribo/src/debug/Makefile -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-43-g800a27b Move Scribo demo.
by Guillaume Lazzara
* demo/Makefile.am, * demo/demo.pro, * demo/demo.qrc, * demo/icons/document-open.png, * demo/icons/edit-find.png, * demo/icons/format-indent-more.png, * demo/icons/go-next.png, * demo/icons/image-x-generic.png, * demo/icons/list-add.png, * demo/icons/ocr.png, * demo/icons/text-x-generic.png, * demo/icons/view-refresh.png, * demo/icons/x-office-spreadsheet.png, * demo/src/main.cc, * demo/src/mainwindow.cc, * demo/src/mainwindow.hh, * demo/ui/mainwindow.ui: Move... * demo/review/Makefile.am, * demo/review/icons/document-open.png, * demo/review/icons/edit-find.png, * demo/review/icons/format-indent-more.png, * demo/review/icons/go-next.png, * demo/review/icons/image-x-generic.png, * demo/review/icons/list-add.png, * demo/review/icons/ocr.png, * demo/review/icons/text-x-generic.png, * demo/review/icons/view-refresh.png, * demo/review/icons/x-office-spreadsheet.png, * demo/review/review.pro, * demo/review/review.qrc, * demo/review/src/main.cc, * demo/review/src/mainwindow.cc, * demo/review/src/mainwindow.hh, * demo/review/ui/mainwindow.ui: ... here. --- scribo/ChangeLog | 40 ++++++++++++++++++++ scribo/demo/{ => review}/Makefile.am | 0 scribo/demo/{ => review}/icons/document-open.png | Bin 1550 -> 1550 bytes scribo/demo/{ => review}/icons/edit-find.png | Bin 1636 -> 1636 bytes .../demo/{ => review}/icons/format-indent-more.png | Bin 766 -> 766 bytes scribo/demo/{ => review}/icons/go-next.png | Bin 1219 -> 1219 bytes scribo/demo/{ => review}/icons/image-x-generic.png | Bin 1163 -> 1163 bytes scribo/demo/{ => review}/icons/list-add.png | Bin 601 -> 601 bytes scribo/demo/{ => review}/icons/ocr.png | Bin 14929 -> 14929 bytes scribo/demo/{ => review}/icons/text-x-generic.png | Bin 744 -> 744 bytes scribo/demo/{ => review}/icons/view-refresh.png | Bin 2024 -> 2024 bytes .../{ => review}/icons/x-office-spreadsheet.png | Bin 1518 -> 1518 bytes scribo/demo/{demo.pro => review/review.pro} | 4 +- scribo/demo/{demo.qrc => review/review.qrc} | 0 scribo/demo/{ => review}/src/main.cc | 0 scribo/demo/{ => review}/src/mainwindow.cc | 0 scribo/demo/{ => review}/src/mainwindow.hh | 0 scribo/demo/{ => review}/ui/mainwindow.ui | 0 18 files changed, 42 insertions(+), 2 deletions(-) rename scribo/demo/{ => review}/Makefile.am (100%) rename scribo/demo/{ => review}/icons/document-open.png (100%) rename scribo/demo/{ => review}/icons/edit-find.png (100%) rename scribo/demo/{ => review}/icons/format-indent-more.png (100%) rename scribo/demo/{ => review}/icons/go-next.png (100%) rename scribo/demo/{ => review}/icons/image-x-generic.png (100%) rename scribo/demo/{ => review}/icons/list-add.png (100%) rename scribo/demo/{ => review}/icons/ocr.png (100%) rename scribo/demo/{ => review}/icons/text-x-generic.png (100%) rename scribo/demo/{ => review}/icons/view-refresh.png (100%) rename scribo/demo/{ => review}/icons/x-office-spreadsheet.png (100%) rename scribo/demo/{demo.pro => review/review.pro} (84%) rename scribo/demo/{demo.qrc => review/review.qrc} (100%) rename scribo/demo/{ => review}/src/main.cc (100%) rename scribo/demo/{ => review}/src/mainwindow.cc (100%) rename scribo/demo/{ => review}/src/mainwindow.hh (100%) rename scribo/demo/{ => review}/ui/mainwindow.ui (100%) diff --git a/scribo/ChangeLog b/scribo/ChangeLog index f3c022a..26f6201 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,3 +1,43 @@ +2010-02-09 Guillaume Lazzara <z(a)lrde.epita.fr> + + Move Scribo demo. + + * demo/Makefile.am, + * demo/demo.pro, + * demo/demo.qrc, + * demo/icons/document-open.png, + * demo/icons/edit-find.png, + * demo/icons/format-indent-more.png, + * demo/icons/go-next.png, + * demo/icons/image-x-generic.png, + * demo/icons/list-add.png, + * demo/icons/ocr.png, + * demo/icons/text-x-generic.png, + * demo/icons/view-refresh.png, + * demo/icons/x-office-spreadsheet.png, + * demo/src/main.cc, + * demo/src/mainwindow.cc, + * demo/src/mainwindow.hh, + * demo/ui/mainwindow.ui: Move... + + * demo/review/Makefile.am, + * demo/review/icons/document-open.png, + * demo/review/icons/edit-find.png, + * demo/review/icons/format-indent-more.png, + * demo/review/icons/go-next.png, + * demo/review/icons/image-x-generic.png, + * demo/review/icons/list-add.png, + * demo/review/icons/ocr.png, + * demo/review/icons/text-x-generic.png, + * demo/review/icons/view-refresh.png, + * demo/review/icons/x-office-spreadsheet.png, + * demo/review/review.pro, + * demo/review/review.qrc, + * demo/review/src/main.cc, + * demo/review/src/mainwindow.cc, + * demo/review/src/mainwindow.hh, + * demo/review/ui/mainwindow.ui: ... here. + 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> * io/xml/save_text_lines.hh: New. Add partial support for diff --git a/scribo/demo/Makefile.am b/scribo/demo/review/Makefile.am similarity index 100% rename from scribo/demo/Makefile.am rename to scribo/demo/review/Makefile.am diff --git a/scribo/demo/icons/document-open.png b/scribo/demo/review/icons/document-open.png similarity index 100% rename from scribo/demo/icons/document-open.png rename to scribo/demo/review/icons/document-open.png diff --git a/scribo/demo/icons/edit-find.png b/scribo/demo/review/icons/edit-find.png similarity index 100% rename from scribo/demo/icons/edit-find.png rename to scribo/demo/review/icons/edit-find.png diff --git a/scribo/demo/icons/format-indent-more.png b/scribo/demo/review/icons/format-indent-more.png similarity index 100% rename from scribo/demo/icons/format-indent-more.png rename to scribo/demo/review/icons/format-indent-more.png diff --git a/scribo/demo/icons/go-next.png b/scribo/demo/review/icons/go-next.png similarity index 100% rename from scribo/demo/icons/go-next.png rename to scribo/demo/review/icons/go-next.png diff --git a/scribo/demo/icons/image-x-generic.png b/scribo/demo/review/icons/image-x-generic.png similarity index 100% rename from scribo/demo/icons/image-x-generic.png rename to scribo/demo/review/icons/image-x-generic.png diff --git a/scribo/demo/icons/list-add.png b/scribo/demo/review/icons/list-add.png similarity index 100% rename from scribo/demo/icons/list-add.png rename to scribo/demo/review/icons/list-add.png diff --git a/scribo/demo/icons/ocr.png b/scribo/demo/review/icons/ocr.png similarity index 100% rename from scribo/demo/icons/ocr.png rename to scribo/demo/review/icons/ocr.png diff --git a/scribo/demo/icons/text-x-generic.png b/scribo/demo/review/icons/text-x-generic.png similarity index 100% rename from scribo/demo/icons/text-x-generic.png rename to scribo/demo/review/icons/text-x-generic.png diff --git a/scribo/demo/icons/view-refresh.png b/scribo/demo/review/icons/view-refresh.png similarity index 100% rename from scribo/demo/icons/view-refresh.png rename to scribo/demo/review/icons/view-refresh.png diff --git a/scribo/demo/icons/x-office-spreadsheet.png b/scribo/demo/review/icons/x-office-spreadsheet.png similarity index 100% rename from scribo/demo/icons/x-office-spreadsheet.png rename to scribo/demo/review/icons/x-office-spreadsheet.png diff --git a/scribo/demo/demo.pro b/scribo/demo/review/review.pro similarity index 84% rename from scribo/demo/demo.pro rename to scribo/demo/review/review.pro index 01e36ee..3ee66e9 100644 --- a/scribo/demo/demo.pro +++ b/scribo/demo/review/review.pro @@ -5,7 +5,7 @@ TEMPLATE = app TARGET = DEPENDPATH += . src ui -INCLUDEPATH += . src ../../ ../../milena +INCLUDEPATH += . src ../../../ ../../../milena DEFINES += NDEBUG # Input @@ -13,4 +13,4 @@ HEADERS += src/mainwindow.hh FORMS += ui/mainwindow.ui SOURCES += src/main.cc src/mainwindow.cc -RESOURCES = demo.qrc +RESOURCES = review.qrc diff --git a/scribo/demo/demo.qrc b/scribo/demo/review/review.qrc similarity index 100% rename from scribo/demo/demo.qrc rename to scribo/demo/review/review.qrc diff --git a/scribo/demo/src/main.cc b/scribo/demo/review/src/main.cc similarity index 100% rename from scribo/demo/src/main.cc rename to scribo/demo/review/src/main.cc diff --git a/scribo/demo/src/mainwindow.cc b/scribo/demo/review/src/mainwindow.cc similarity index 100% rename from scribo/demo/src/mainwindow.cc rename to scribo/demo/review/src/mainwindow.cc diff --git a/scribo/demo/src/mainwindow.hh b/scribo/demo/review/src/mainwindow.hh similarity index 100% rename from scribo/demo/src/mainwindow.hh rename to scribo/demo/review/src/mainwindow.hh diff --git a/scribo/demo/ui/mainwindow.ui b/scribo/demo/review/ui/mainwindow.ui similarity index 100% rename from scribo/demo/ui/mainwindow.ui rename to scribo/demo/review/ui/mainwindow.ui -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-42-gb41ec08 Small fixes in Milena.
by Guillaume Lazzara
* milena/mln/accu/center.hh: Add nsites() member. * milena/mln/accu/pair.hh: Provide access to the underlying accus. * milena/mln/accu/stat/variance.hh: Use literal::zero. * milena/mln/core/internal/labeled_image_base.hh: Indent. * milena/mln/core/site_set/box.hh: Rename center() as pcenter(). * milena/mln/labeling/blobs_and_compute.hh: Return the array of accumulators. * milena/mln/labeling/colorize.hh: Make sure a color is not used twice in the same image. * milena/mln/labeling/compute.hh: Add a new overload. * milena/mln/transform/influence_zone_geodesic.hh: Fix a segmentation fault when an image had a border. --- milena/ChangeLog | 25 +++++ milena/mln/accu/center.hh | 14 +++- milena/mln/accu/pair.hh | 26 ++++++ milena/mln/accu/stat/variance.hh | 4 +- milena/mln/core/internal/labeled_image_base.hh | 2 +- milena/mln/core/site_set/box.hh | 4 +- milena/mln/labeling/blobs_and_compute.hh | 14 ++- milena/mln/labeling/colorize.hh | 51 ++++++++--- milena/mln/labeling/compute.hh | 111 +++++++++++++++++++---- milena/mln/transform/influence_zone_geodesic.hh | 13 +-- 10 files changed, 214 insertions(+), 50 deletions(-) diff --git a/milena/ChangeLog b/milena/ChangeLog index 73b9647..ec2ef35 100644 --- a/milena/ChangeLog +++ b/milena/ChangeLog @@ -1,3 +1,28 @@ +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + + Small fixes in Milena. + + * milena/mln/accu/center.hh: Add nsites() member. + + * milena/mln/accu/pair.hh: Provide access to the underlying accus. + + * milena/mln/accu/stat/variance.hh: Use literal::zero. + + * milena/mln/core/internal/labeled_image_base.hh: Indent. + + * milena/mln/core/site_set/box.hh: Rename center() as pcenter(). + + * milena/mln/labeling/blobs_and_compute.hh: Return the array of + accumulators. + + * milena/mln/labeling/colorize.hh: Make sure a color is not used + twice in the same image. + + * milena/mln/labeling/compute.hh: Add a new overload. + + * milena/mln/transform/influence_zone_geodesic.hh: Fix a + segmentation fault when an image had a border. + 2009-12-14 Guillaume Lazzara <z(a)lrde.epita.fr> Add rbg_to_int_u function. diff --git a/milena/mln/accu/center.hh b/milena/mln/accu/center.hh index 7cfbe78..a3622b3 100644 --- a/milena/mln/accu/center.hh +++ b/milena/mln/accu/center.hh @@ -1,4 +1,5 @@ -// Copyright (C) 2008, 2009 EPITA Research and Development Laboratory (LRDE) +// Copyright (C) 2008, 2009, 2010 EPITA Research and Development +// Laboratory (LRDE) // // This file is part of Olena. // @@ -73,6 +74,9 @@ namespace mln /// Check whether this accu is able to return a result. bool is_valid() const; + /// Return the number of sites taken in consideration. + unsigned nsites() const; + protected: algebra::vec<P::dim, mln_sum(mln_coord(P))> center_; unsigned nsites_; @@ -158,6 +162,14 @@ namespace mln return nsites_ > 0; } + template <typename P, typename V> + inline + unsigned + center<P,V>::nsites() const + { + return nsites_; + } + # endif // ! MLN_INCLUDE_ONLY diff --git a/milena/mln/accu/pair.hh b/milena/mln/accu/pair.hh index bb0b691..11f4dc6 100644 --- a/milena/mln/accu/pair.hh +++ b/milena/mln/accu/pair.hh @@ -81,9 +81,16 @@ namespace mln void get_result(result_1& r1, result_2& r2) const; /// \} + /// Return the result of the first accumulator. mln_result(A1) first() const; + /// Return the result of the second accumulator. mln_result(A2) second() const; + /// Return the first accumulator. + A1 first_accu() const; + /// Return the second accumulator. + A2 second_accu() const; + /// Check whether this accu is able to return a result. /// Always true here. bool is_valid() const; @@ -194,6 +201,25 @@ namespace mln return a2_.to_result(); } + + + template <typename A1, typename A2, typename T> + inline + A1 + pair<A1,A2,T>::first_accu() const + { + return a1_; + } + + template <typename A1, typename A2, typename T> + inline + A2 + pair<A1,A2,T>::second_accu() const + { + return a2_; + } + + template <typename A1, typename A2, typename T> inline bool diff --git a/milena/mln/accu/stat/variance.hh b/milena/mln/accu/stat/variance.hh index 23e7731..c19761e 100644 --- a/milena/mln/accu/stat/variance.hh +++ b/milena/mln/accu/stat/variance.hh @@ -125,7 +125,7 @@ namespace mln variance<T,S,R>::init() { n_ = 0; - sum_ = sum2_ = 0; + sum_ = sum2_ = literal::zero; } template <typename T, typename S, typename R> @@ -187,7 +187,7 @@ namespace mln variance<T,S,R>::mean() const { if (n_ == 0u) - return 0; // Safety. + return literal::zero; // Safety. return sum_ / n_; } diff --git a/milena/mln/core/internal/labeled_image_base.hh b/milena/mln/core/internal/labeled_image_base.hh index 9e2d314..86bb077 100644 --- a/milena/mln/core/internal/labeled_image_base.hh +++ b/milena/mln/core/internal/labeled_image_base.hh @@ -310,7 +310,7 @@ namespace mln const util::array<typename labeled_image_base<I,E>::bbox_t>& labeled_image_base<I,E>::bboxes() const { - return this->data_->bboxes_; + return this->data_->bboxes_; } diff --git a/milena/mln/core/site_set/box.hh b/milena/mln/core/site_set/box.hh index 75fb91c..077ac3d 100644 --- a/milena/mln/core/site_set/box.hh +++ b/milena/mln/core/site_set/box.hh @@ -143,7 +143,7 @@ namespace mln box<P> to_larger(unsigned b) const; /// Return the approximated central site of this box. - P center() const; + P pcenter() const; /// Test that the box owns valid data, i.e., is initialized and /// with pmin being 'less-than' pmax. @@ -390,7 +390,7 @@ namespace mln template <typename P> inline P - box<P>::center() const + box<P>::pcenter() const { mln_precondition(is_valid()); P center; diff --git a/milena/mln/labeling/blobs_and_compute.hh b/milena/mln/labeling/blobs_and_compute.hh index 4d5d5d8..b76b62a 100644 --- a/milena/mln/labeling/blobs_and_compute.hh +++ b/milena/mln/labeling/blobs_and_compute.hh @@ -53,7 +53,9 @@ namespace mln */ template <typename I, typename N, typename L, typename A> - util::couple<mln_ch_value(I, L), util::array<mln_result(A)> > + util::couple<mln_ch_value(I,L), + util::couple<util::array<mln_result(A)>, + util::array<A> > > blobs_and_compute(const Image<I>& input, const Neighborhood<N>& nbh, L& nlabels, const Accumulator<A>& accu); @@ -72,7 +74,8 @@ namespace mln { typedef mln_result(A) accu_result; typedef mln_argument(A) accu_argument; - typedef util::array<accu_result> result; + typedef util::couple<util::array<accu_result>, + util::array<A> > result; void init() { @@ -133,7 +136,9 @@ namespace mln template <typename I, typename N, typename L, typename A> - util::couple<mln_ch_value(I,L), util::array<mln_result(A)> > + util::couple<mln_ch_value(I,L), + util::couple<util::array<mln_result(A)>, + util::array<A> > > blobs_and_compute(const Image<I>& input, const Neighborhood<N>& nbh, L& nlabels, const Accumulator<A>& accu) { @@ -151,7 +156,8 @@ namespace mln output = canvas::labeling::blobs(input, nbh, nlabels, functor); util::couple<out_t, typename func_t::result> - result = make::couple(output, functor.result_); + result = make::couple(output, + make::couple(functor.result_, functor.accus_)); trace::exiting("labeling::blobs_and_compute"); return result; diff --git a/milena/mln/labeling/colorize.hh b/milena/mln/labeling/colorize.hh index 26a78df..69493d5 100644 --- a/milena/mln/labeling/colorize.hh +++ b/milena/mln/labeling/colorize.hh @@ -103,11 +103,9 @@ namespace mln unsigned random_number() { - static unsigned last = 1; + unsigned last = colorize_::min_value + (colorize_::max_value - colorize_::min_value + 1) * rand(); - last = (323 * last + 6603) % 1025; - - return colorize_::min_value + last % colorize_::max_value; + return math::min(colorize_::min_value + last % colorize_::max_value, colorize_::max_value); } @@ -120,17 +118,42 @@ namespace mln mln::value::rgb<n> random_color(const mln::value::rgb<n>&) { - // Make sure the numbers are generated in the same order - // whatever the compiler used. - // For instance, ICC does not compute function arguments in - // the same order as GCC does. - unsigned - red = random_number(), - green = random_number(), + static unsigned + nelements = colorize_::max_value - colorize_::min_value + 1; + static util::array<util::set<unsigned> > + red_(nelements), + green_(nelements); + + unsigned red, green, blue; + + unsigned ntries = 0; + do + { + red = random_number(); + ++ntries; + } + while (red_[red - colorize_::min_value].nelements() == nelements + && ntries < nelements); + + if (ntries == nelements) + { + trace::warning("labeling::colorize - Can't find a new unique color. Returning black."); + return literal::black; + } + + + do + green = random_number(); + while (red_[red - colorize_::min_value].has(green) + || green_[green - colorize_::min_value].nelements() == nelements); + red_[red - colorize_::min_value].insert(green); + + do blue = random_number(); - return mln::value::rgb<n>(red, - green, - blue); + while (green_[green - colorize_::min_value].has(blue)); + green_[green - colorize_::min_value].insert(blue); + + return mln::value::rgb<n>(red, green, blue); } } diff --git a/milena/mln/labeling/compute.hh b/milena/mln/labeling/compute.hh index d29242f..4f0d97d 100644 --- a/milena/mln/labeling/compute.hh +++ b/milena/mln/labeling/compute.hh @@ -1,4 +1,5 @@ -// Copyright (C) 2008, 2009 EPITA Research and Development Laboratory (LRDE) +// Copyright (C) 2008, 2009 EPITA Research and Development Laboratory +// (LRDE) // // This file is part of Olena. // @@ -60,23 +61,6 @@ namespace mln /// Compute an accumulator onto the pixel values of the image \p input. /// for each component of the image \p label. /// - /// \param[in] a An array of accumulator. - /// \param[in] input The input image. - /// \param[in] label The labeled image. - /// \param[in] nlabels The number of labels in \p label. - /// \return A mln::p_array of accumulator result (one result per label). - // - template <typename A, typename I, typename L> - util::array<mln_result(A)> - compute(util::array<A>& a, - const Image<I>& input, - const Image<L>& label, - const mln_value(L)& nlabels); - - - /// Compute an accumulator onto the pixel values of the image \p input. - /// for each component of the image \p label. - /// /// \param[in] a An accumulator. /// \param[in] input The input image. /// \param[in] label The labeled image. @@ -138,6 +122,23 @@ namespace mln const mln_value(L)& nlabels); + /// Compute an accumulator onto the pixel values of the image \p input. + /// for each component of the image \p label. + /// + /// \param[in] a An array of accumulator. + /// \param[in] input The input image. + /// \param[in] label The labeled image. + /// \param[in] nlabels The number of labels in \p label. + /// \return A mln::p_array of accumulator result (one result per label). + // + template <typename A, typename I, typename L> + util::array<mln_result(A)> + compute(util::array<A>& a, + const Image<I>& input, + const Image<L>& label, + const mln_value(L)& nlabels); + + # ifndef MLN_INCLUDE_ONLY @@ -221,6 +222,49 @@ namespace mln return res; } + /// Generic implementation of labeling::compute. + /// + /// \param[in] accus_ An array of accumulators. If the size is + /// set to nlabels + 1, the accumulators are + /// considered as initialized. Otherwise, + /// the size is adjusted. + /// \param[in] label_ The labeled image. + /// \param[in] nlabels The number of labels in \p label. + /// + /// \return A mln::p_array of accumulator result (one result per label). + // + template <typename A, typename L> + inline + util::array<mln_result(A)> + compute(util::array<A>& accus, + const Image<L>& label_, + const mln_value(L)& nlabels) + { + trace::entering("labeling::impl::generic::compute"); + internal::compute_tests(A(), label_, nlabels); + + if (static_cast<unsigned>(nlabels) + 1 != accus.size()) + { + accus.resize(0); // Make sure all the accumulators are + // re-initialized when resizing on next + // line. + accus.resize(static_cast<unsigned>(nlabels) + 1); + } + + const L& label = exact(label_); + + mln_piter(L) p(label.domain()); + for_all(p) + accus[label(p)].take(p); + + util::array<mln_result(A)> res; + convert::from_to(accus, res); + + trace::exiting("labeling::impl::generic::compute"); + return res; + } + + /// Generic implementation of labeling::compute. /// @@ -343,6 +387,15 @@ namespace mln return impl::generic::compute(a, input, label, nlabels); } + template <typename A, typename L> + inline + util::array<mln_result(A)> + compute_dispatch(util::array<A>& accus, + const Image<L>& label, + const mln_value(L)& nlabels) + { + return impl::generic::compute(accus, label, nlabels); + } } // end of namespace mln::labeling::internal @@ -406,6 +459,28 @@ namespace mln template <typename A, typename L> inline util::array<mln_result(A)> + compute(util::array<A>& accus, + const Image<L>& label, + const mln_value(L)& nlabels) + { + trace::entering("labeling::compute"); + + internal::compute_tests(A(), label, nlabels); + + typedef util::array<mln_result(A)> R; + R res = internal::compute_dispatch(accus, label, nlabels); + + mln_postcondition(res.nelements() == static_cast<unsigned>(nlabels) + 1); + + trace::exiting("labeling::compute"); + return res; + } + + + + template <typename A, typename L> + inline + util::array<mln_result(A)> compute(const Accumulator<A>& a, const Image<L>& label, const mln_value(L)& nlabels) diff --git a/milena/mln/transform/influence_zone_geodesic.hh b/milena/mln/transform/influence_zone_geodesic.hh index 4d7255a..b9a763f 100644 --- a/milena/mln/transform/influence_zone_geodesic.hh +++ b/milena/mln/transform/influence_zone_geodesic.hh @@ -1,4 +1,5 @@ -// Copyright (C) 2008, 2009 EPITA Research and Development Laboratory (LRDE) +// Copyright (C) 2008, 2009 EPITA Research and Development Laboratory +// (LRDE) // // This file is part of Olena. // @@ -104,16 +105,12 @@ namespace mln const N& nbh = exact(nbh_); internal::influence_zone_geodesic_tests(input, nbh); - mln_precondition(input.domain().pmin() == literal::origin); std::queue<mln_value(I)*> q; mln_concrete(I) output; util::array<int> dp = offsets_wrt(input, nbh); const unsigned n_nbhs = dp.nelements(); - const unsigned - ncols = input.ncols(), - first_offset = input.border() * (ncols + 2 * input.border() + 1); // Initialization. { @@ -124,9 +121,9 @@ namespace mln extension::fill(output, 1); // in propagation const unsigned nelts = input.nelements(); - const mln_value(I)* p_i = & input.at_(0, 0); - mln_value(I)* p_o = & output.at_(0, 0); - for (unsigned i = first_offset; i < nelts; ++i, ++p_i, ++p_o) + const mln_value(I)* p_i = input.buffer(); + mln_value(I)* p_o = output.buffer(); + for (unsigned i = 0; i < nelts; ++i, ++p_i, ++p_o) { if (*p_i == 0) continue; -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-41-g41b6112 io/xml/save_text_lines.hh: New. Add partial support for PageContent XML format.
by Guillaume Lazzara
--- scribo/ChangeLog | 59 +++++++++------- scribo/io/xml/save_text_lines.hh | 144 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 176 insertions(+), 27 deletions(-) create mode 100644 scribo/io/xml/save_text_lines.hh diff --git a/scribo/ChangeLog b/scribo/ChangeLog index dfac25a..f3c022a 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,3 +1,8 @@ +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + + * io/xml/save_text_lines.hh: New. Add partial support for + PageContent XML format. + 2010-03-11 Guillaume Lazzara <z(a)lrde.epita.fr> Introduce new Scribo core classes and start using them. @@ -48,58 +53,58 @@ Add anchor support in debug routines. - * scribo/debug/alignment_decision_image.hh, - * scribo/debug/links_decision_image.hh, - * scribo/debug/save_linked_bboxes_image.hh, - * scribo/draw/bounding_box_links.hh: Make use of anchor points to + * debug/alignment_decision_image.hh, + * debug/links_decision_image.hh, + * debug/save_linked_bboxes_image.hh, + * draw/bounding_box_links.hh: Make use of anchor points to draw debug outputs. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> Add new link filters. - * scribo/filter/object_links_non_aligned_simple.hh: Handle new + * filter/object_links_non_aligned_simple.hh: Handle new cases. - * scribo/filter/object_links_left_aligned.hh, - * scribo/filter/object_links_right_aligned.hh: New filters. + * filter/object_links_left_aligned.hh, + * filter/object_links_right_aligned.hh: New filters. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> Improve object linking backend. - * scribo/primitive/internal/find_left_link.hh, - * scribo/primitive/internal/find_right_link.hh, - * scribo/primitive/internal/is_invalid_link.hh: Remove. + * primitive/internal/find_left_link.hh, + * primitive/internal/find_right_link.hh, + * primitive/internal/is_invalid_link.hh: Remove. - * scribo/primitive/link/internal/compute_anchor.hh, - * scribo/primitive/link/internal/link_ms_dmax_base.hh, - * scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh, - * scribo/primitive/link/internal/link_single_dmax_base.hh, - * scribo/primitive/link/internal/link_single_dmax_ratio_base.hh, - * scribo/primitive/link/with_single_down_link.hh, - * scribo/primitive/link/with_single_left_link.hh, - * scribo/primitive/link/with_single_left_link_dmax_ratio.hh, - * scribo/primitive/link/with_single_right_link.hh, - * scribo/primitive/link/with_single_right_link_dmax_ratio.hh, - * scribo/primitive/link/with_single_up_link.hh: Introduce the + * primitive/link/internal/compute_anchor.hh, + * primitive/link/internal/link_ms_dmax_base.hh, + * primitive/link/internal/link_ms_dmax_ratio_base.hh, + * primitive/link/internal/link_single_dmax_base.hh, + * primitive/link/internal/link_single_dmax_ratio_base.hh, + * primitive/link/with_single_down_link.hh, + * primitive/link/with_single_left_link.hh, + * primitive/link/with_single_left_link_dmax_ratio.hh, + * primitive/link/with_single_right_link.hh, + * primitive/link/with_single_right_link_dmax_ratio.hh, + * primitive/link/with_single_up_link.hh: Introduce the anchor concept and make use of it. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> - * scribo/filter/objects_with_holes.hh: New component filter. + * filter/objects_with_holes.hh: New component filter. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> - * scribo/draw/bounding_boxes.hh: Do not draw box centers anymore. + * draw/bounding_boxes.hh: Do not draw box centers anymore. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> Add dedicated routines for AFP's use case. - * scribo/src/afp/components.hh, - * scribo/src/afp/link.hh, - * scribo/src/afp/regroup.hh: New. + * src/afp/components.hh, + * src/afp/link.hh, + * src/afp/regroup.hh: New. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> diff --git a/scribo/io/xml/save_text_lines.hh b/scribo/io/xml/save_text_lines.hh new file mode 100644 index 0000000..c86f121 --- /dev/null +++ b/scribo/io/xml/save_text_lines.hh @@ -0,0 +1,144 @@ +// Copyright (C) 2010 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_IO_XML_SAVE_TEXT_LINES_HH +# define SCRIBO_IO_XML_SAVE_TEXT_LINES_HH + +/// \file +/// +/// \brief Save text line information as XML. + +#include <fstream> +#include <sstream> + + +namespace scribo +{ + + namespace io + { + + namespace xml + { + + /*! \brief Save text line information as XML. + + We use a XML Schema part of the PAGE (Page Analysis and Ground + truth Elements) image representation framework. + + This schema was used in the Page Segmentation COMPetition + (PSCOMP) for ICDAR 2009. + + Its XSD file is located here: +
http://schema.primaresearch.org/PAGE/gts/pagecontent/2009-03-16/pagecontent…
+ + */ + template <typename L> + void + save_text_lines(const std::string& input_name, + const line_set<L>& lines, + const std::string& output_name); + + +# ifndef MLN_INCLUDE_ONLY + + + template <typename L> + void + save_text_lines(const std::string& input_name, + const line_set<L>& lines, + const std::string& output_name) + { + trace::entering("scribo::io::xml:save_text_lines"); + + std::ofstream file(output_name.c_str()); + if (! file) + { + std::cerr << "error: cannot open file '" << input_name << "'!"; + abort(); + } + + file << "<?xml version=\"1.0\"?>" << std::endl; + file << "<pcGts xmlns=\"
http://schema.primaresearch.org/PAGE/gts/pagecontent/2009-03-16\
" xmlns:xsi=\"
http://www.w3.org/2001/XMLSchema-instance\
" xsi:schemaLocation=\"
http://schema.primaresearch.org/PAGE/gts/pagecontent/2009-03-16
http://schema.primaresearch.org/PAGE/gts/pagecontent/2009-03-16/pagecontent…
" pcGtsId=\"" << input_name << "\">" << std::endl; + + + file << " <pcMetadata>" << std::endl; + file << " <pcCreator>LRDE</pcCreator>" << std::endl; + file << " <pcCreated/>" << std::endl; + file << " <pcLastChange/>" << std::endl; + file << " <pcComments/>" << std::endl; + file << " </pcMetadata>" << std::endl; + + file << " <page image_filename=\"" << input_name + << "\" image_width=\"" << lines.component_set_().labeled_image().ncols() + << "\" image_height=\"" << lines.component_set_().labeled_image().nrows() + << "\">" << std::endl; + + for_all_lines(l, lines) + { + file << " <text_region id=\"" << lines(l).id() + << "\" txt_orientation=\"0.000\" " + << "txt_reading_orientation=\"0.000\" " + << "txt_reading_direction=\"Left_To_Right\" " + << "txt_reverse_video=\"No\" " + << "txt_indented=\"No\">" + << std::endl; + + file << " <coords>" << std::endl + << " <point x=\"" << lines(l).bbox().pmin().row() + << "\" y=\"" << lines(l).bbox().pmin().col() << "\"/>" + << std::endl + << " <point x=\"" << lines(l).bbox().pmin().row() + << "\" y=\"" << lines(l).bbox().pmax().col() << "\"/>" + << std::endl + << " <point x=\"" << lines(l).bbox().pmax().row() + << "\" y=\"" << lines(l).bbox().pmin().col() << "\"/>" + << std::endl + << " <point x=\"" << lines(l).bbox().pmax().row() + << "\" y=\"" << lines(l).bbox().pmax().col() << "\"/>" + << std::endl + << " </coords>" << std::endl; + } + + file << " </text_region>" << std::endl; + file << " </page>" << std::endl; + file << "</pcGts>" << std::endl; + + + + trace::exiting("scribo::io::xml::save_text_lines"); + } + + +# endif // ! MLN_INCLUDE_ONLY + + } // end of namespace scribo::io::xml + + } // end of namespace scribo::io + +} // end of namespace scribo + + +#endif // ! SCRIBO_IO_XML_SAVE_TEXT_LINES_HH -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-39-gc24feb9 Add anchor support in debug routines.
by Guillaume Lazzara
* scribo/debug/alignment_decision_image.hh, * scribo/debug/links_decision_image.hh, * scribo/debug/save_linked_bboxes_image.hh, * scribo/draw/bounding_box_links.hh: Make use of anchor points to draw debug outputs. --- scribo/ChangeLog | 10 +++++ scribo/debug/alignment_decision_image.hh | 26 ++++++++++-- scribo/debug/links_decision_image.hh | 34 ++++++++++++++--- scribo/debug/save_linked_bboxes_image.hh | 48 +++++++++++++++++------ scribo/draw/bounding_box_links.hh | 61 ++++++++++++------------------ 5 files changed, 118 insertions(+), 61 deletions(-) diff --git a/scribo/ChangeLog b/scribo/ChangeLog index 01ab3a1..52a13dd 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,5 +1,15 @@ 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Add anchor support in debug routines. + + * scribo/debug/alignment_decision_image.hh, + * scribo/debug/links_decision_image.hh, + * scribo/debug/save_linked_bboxes_image.hh, + * scribo/draw/bounding_box_links.hh: Make use of anchor points to + draw debug outputs. + +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Add new link filters. * scribo/filter/object_links_non_aligned_simple.hh: Handle new diff --git a/scribo/debug/alignment_decision_image.hh b/scribo/debug/alignment_decision_image.hh index 9a4fa50..e3b6163 100644 --- a/scribo/debug/alignment_decision_image.hh +++ b/scribo/debug/alignment_decision_image.hh @@ -114,7 +114,8 @@ namespace scribo alignment_decision_image(const Image<I>& input_, const object_links<L>& links, const object_links<L>& filtered_links, - const Alignment& alignment) + const Alignment& alignment, + unsigned max_link_length) { trace::entering("scribo::debug::alignment_decision_image"); const I& input = exact(input_); @@ -147,10 +148,11 @@ namespace scribo mln::util::couple<P,P> anchors = internal::find_anchors(objects, i, links[i], alignment); - mln::draw::line(decision_image, - anchors.first(), - anchors.second(), - value); + if (norm::l1_distance(anchors.first(), anchors.second()) < max_link_length) + mln::draw::line(decision_image, + anchors.first(), + anchors.second(), + value); } } @@ -159,6 +161,20 @@ namespace scribo } + template <typename I, typename L> + mln_ch_value(I,value::rgb8) + alignment_decision_image(const Image<I>& input_, + const object_links<L>& links, + const object_links<L>& filtered_links, + const Alignment& alignment) + { + return alignment_decision_image(input_, + links, + filtered_links, + alignment, + mln_max(unsigned)); + } + # endif // ! MLN_INCLUDE_ONLY diff --git a/scribo/debug/links_decision_image.hh b/scribo/debug/links_decision_image.hh index 368d9b7..e1cf766 100644 --- a/scribo/debug/links_decision_image.hh +++ b/scribo/debug/links_decision_image.hh @@ -36,6 +36,7 @@ # include <mln/value/rgb8.hh> # include <mln/literal/colors.hh> # include <mln/util/array.hh> +# include <mln/norm/l1.hh> # include <scribo/core/object_groups.hh> # include <scribo/draw/bounding_boxes.hh> @@ -54,8 +55,15 @@ namespace scribo mln_ch_value(I,value::rgb8) links_decision_image(const Image<I>& input_, const object_links<L>& links, - const object_links<L>& filtered_links); + const object_links<L>& filtered_links, + unsigned max_link_length); + /// \overload + template <typename I, typename L> + mln_ch_value(I,value::rgb8) + links_decision_image(const Image<I>& input_, + const object_links<L>& links, + const object_links<L>& filtered_links); # ifndef MLN_INCLUDE_ONLY @@ -63,7 +71,8 @@ namespace scribo mln_ch_value(I,value::rgb8) links_decision_image(const Image<I>& input_, const object_links<L>& links, - const object_links<L>& filtered_links) + const object_links<L>& filtered_links, + unsigned max_link_length) { trace::entering("scribo::debug::links_decision_image"); const I& input = exact(input_); @@ -105,10 +114,11 @@ namespace scribo while (objects(p2) != links[i] && objects.domain().has(p2)) ++p2.col(); - mln::draw::line(links_decision_image, - p1, - p2, - value); + if (norm::l1_distance(p2.to_vec(), p1.to_vec()) < max_link_length) + mln::draw::line(links_decision_image, + p1, + p2, + value); } } @@ -117,6 +127,18 @@ namespace scribo } + template <typename I, typename L> + mln_ch_value(I,value::rgb8) + links_decision_image(const Image<I>& input_, + const object_links<L>& links, + const object_links<L>& filtered_links) + { + return links_decision_image(input_, + links, + filtered_links, + mln_max(unsigned)); + } + # endif // ! MLN_INCLUDE_ONLY } // end of namespace scribo::debug diff --git a/scribo/debug/save_linked_bboxes_image.hh b/scribo/debug/save_linked_bboxes_image.hh index 364f06e..c4e3cd1 100644 --- a/scribo/debug/save_linked_bboxes_image.hh +++ b/scribo/debug/save_linked_bboxes_image.hh @@ -62,6 +62,21 @@ namespace scribo /// \param[in] box_value Value used to draw line bounding boxes. /// \param[in] link_value Value used to draw line links. /// \param[in] filename The target file name. + /// \param[in] anchor Anchor from where the links are drawn. + // + template <typename I, typename L> + void + save_linked_bboxes_image(const Image<I>& input, + const object_image(L)& objects, + const object_links<L>& array, + const value::rgb8& box_value, + const value::rgb8& link_value, + const std::string& filename, + anchor::Type anchor); + + /// \overload + /// The default anchor type is set to anchor::Center. + // template <typename I, typename L> void save_linked_bboxes_image(const Image<I>& input, @@ -145,20 +160,16 @@ namespace scribo const object_links<L>& array, const value::rgb8& box_value, const value::rgb8& link_value, - const std::string& filename) + const std::string& filename, + anchor::Type anchor) { trace::entering("scribo::debug::save_linked_bboxes_image"); mln_precondition(exact(input).is_valid()); mln_ch_value(I,value::rgb8) tmp = data::convert(value::rgb8(), input); - mln::util::array<mln_result(accu::center<mln_psite(L)>)> - mass_center = labeling::compute(accu::meta::center(), - objects, - objects.nlabels()); - draw::bounding_boxes(tmp, objects.bboxes(), box_value); - draw::bounding_box_links(tmp, mass_center, array, link_value); + draw::bounding_box_links(tmp, array, link_value, anchor); io::ppm::save(tmp, filename); @@ -171,6 +182,22 @@ namespace scribo void save_linked_bboxes_image(const Image<I>& input, const object_image(L)& objects, + const object_links<L>& array, + const value::rgb8& box_value, + const value::rgb8& link_value, + const std::string& filename) + { + save_linked_bboxes_image(input, objects, array, box_value, + link_value, filename, anchor::Center); + } + + + + template <typename I, typename L> + inline + void + save_linked_bboxes_image(const Image<I>& input, + const object_image(L)& objects, const object_links<L>& left_link, const object_links<L>& right_link, const value::rgb8& box_value, @@ -182,13 +209,8 @@ namespace scribo mln_ch_value(I,value::rgb8) tmp = data::convert(value::rgb8(), input); - mln::util::array<mln_result(accu::center<mln_psite(L)>)> - mass_center = labeling::compute(accu::meta::center(), - objects, - objects.nlabels()); - draw::bounding_boxes(tmp, objects.bboxes(), box_value); - draw::bounding_box_links(tmp, mass_center, + draw::bounding_box_links(tmp, objects.mass_centers(), left_link, right_link, value); diff --git a/scribo/draw/bounding_box_links.hh b/scribo/draw/bounding_box_links.hh index 47a4f0a..ed6337d 100644 --- a/scribo/draw/bounding_box_links.hh +++ b/scribo/draw/bounding_box_links.hh @@ -35,9 +35,11 @@ # include <mln/util/array.hh> # include <mln/canvas/browsing/depth_first_search.hh> +# include <scribo/core/tag/anchor.hh> # include <scribo/core/macros.hh> # include <scribo/core/object_links.hh> # include <scribo/primitive/internal/is_link_valid.hh> +# include <scribo/primitive/link/internal/compute_anchor.hh> namespace scribo { @@ -54,25 +56,22 @@ namespace scribo /// \param[in] bboxes Bounding boxes. /// \param[in] links Bounding box links. /// \param[in] value Value used to draw links. + /// \param[in] anchor Anchor from where the links are drawn. + // template <typename I, typename L> void bounding_box_links(Image<I>& input_, - const mln::util::array< box<mln_site(I)> >& bboxes, const object_links<L>& link, - const mln_value(I)& value); + const mln_value(I)& value, + anchor::Type anchor); - /// Draw a list of bounding box links from their mass centers. - /// - /// \param[in,out] input_ An image where to draw. - /// \param[in] mass_centers Bounding boxes mass centers. - /// \param[in] links Bounding box links. - /// \param[in] value Value used to draw links. + /// \overload + /// The default anchor type is set to anchor::Center. + // template <typename I, typename L> - inline void bounding_box_links(Image<I>& input_, - const mln::util::array<mln_site(I)::vec>& mass_centers, const object_links<L>& link, const mln_value(I)& value); @@ -236,9 +235,9 @@ namespace scribo inline void bounding_box_links(Image<I>& input_, - const mln::util::array< box<mln_site(I)> >& bboxes, const object_links<L>& links, - const mln_value(I)& value) + const mln_value(I)& value, + anchor::Type anchor) { trace::entering("scribo::draw::bounding_box_links"); @@ -246,41 +245,29 @@ namespace scribo mln_precondition(input.is_valid()); + const object_image(L)& objects = links.object_image_(); for_all_components(i, links) - if (links[i] != i) - mln::draw::line(input, - bboxes[i].center(), - bboxes[links[i]].center(), - value); + if (links[i] != i && links[i] != 0) + { + mln_site(L) + p1 = primitive::link::internal::compute_anchor(objects, i, anchor), + p2 = primitive::link::internal::compute_anchor(objects, links[i], anchor); + + mln::draw::line(input, p1, p2, value); + } trace::exiting("scribo::draw::bounding_box_links"); } + template <typename I, typename L> inline void - bounding_box_links(Image<I>& input_, - const mln::util::array<mln_site(I)::vec>& mass_centers, + bounding_box_links(Image<I>& input, const object_links<L>& links, const mln_value(I)& value) { - trace::entering("scribo::draw::bounding_box_links"); - - I& input = exact(input_); - - mln_precondition(input.is_valid()); - - for_all_components(i, links) - { - if (links[i] != i) - mln::draw::line(input, - mass_centers[i], - mass_centers[links[i]], - value); - input(mass_centers[i]) = value; - } - - trace::exiting("scribo::draw::bounding_box_links"); + return bounding_box_links(input, links, value, anchor::Center); } @@ -401,7 +388,7 @@ namespace scribo mln_precondition(exact(g).v_nmax() == bboxes.nelements()); internal::draw_graph_edges_functor<I> f(exact(input), bboxes, link_value); - canvas::browsing::depth_first_search(g, f); + mln::canvas::browsing::depth_first_search(g, f); trace::exiting("scribo::draw::bounding_box_links"); } -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-38-g33d6df3 Add new link filters.
by Guillaume Lazzara
* scribo/filter/object_links_non_aligned_simple.hh: Handle new cases. * scribo/filter/object_links_left_aligned.hh, * scribo/filter/object_links_right_aligned.hh: New filters. --- scribo/ChangeLog | 10 +++++ ...top_aligned.hh => object_links_left_aligned.hh} | 33 +++++++++--------- scribo/filter/object_links_non_aligned_simple.hh | 36 ++++++++++++++++++++ ...op_aligned.hh => object_links_right_aligned.hh} | 30 ++++++++-------- 4 files changed, 78 insertions(+), 31 deletions(-) copy scribo/filter/{object_links_top_aligned.hh => object_links_left_aligned.hh} (76%) copy scribo/filter/{object_links_top_aligned.hh => object_links_right_aligned.hh} (77%) diff --git a/scribo/ChangeLog b/scribo/ChangeLog index 45faa9f..01ab3a1 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,5 +1,15 @@ 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Add new link filters. + + * scribo/filter/object_links_non_aligned_simple.hh: Handle new + cases. + + * scribo/filter/object_links_left_aligned.hh, + * scribo/filter/object_links_right_aligned.hh: New filters. + +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Improve object linking backend. * scribo/primitive/internal/find_left_link.hh, diff --git a/scribo/filter/object_links_top_aligned.hh b/scribo/filter/object_links_left_aligned.hh similarity index 76% copy from scribo/filter/object_links_top_aligned.hh copy to scribo/filter/object_links_left_aligned.hh index 4a92c96..e69b110 100644 --- a/scribo/filter/object_links_top_aligned.hh +++ b/scribo/filter/object_links_left_aligned.hh @@ -23,14 +23,15 @@ // exception does not however invalidate any other reasons why the // executable file might be covered by the GNU General Public License. -#ifndef SCRIBO_FILTER_OBJECT_LINKS_TOP_ALIGNED_HH -# define SCRIBO_FILTER_OBJECT_LINKS_TOP_ALIGNED_HH +#ifndef SCRIBO_FILTER_OBJECT_LINKS_LEFT_ALIGNED_HH +# define SCRIBO_FILTER_OBJECT_LINKS_LEFT_ALIGNED_HH /// \file /// -/// Invalidate links between two objects if their top are not +/// Invalidate links between two objects if their left are not /// aligned. - +/// +/// \fixme UPDATE DOC! # include <mln/util/array.hh> @@ -48,7 +49,7 @@ namespace scribo using namespace mln; - /*! \brief Invalidate links between two objects if their top are not + /*! \brief Invalidate links between two objects if their left are not aligned. \param[in] objects An object image. @@ -77,13 +78,13 @@ namespace scribo \endverbatim - The angle between the two tops must be lower than \p max_alpha. + The angle between the two lefts must be lower than \p max_alpha. */ template <typename L> object_links<L> - object_links_top_aligned(const object_image(L)& objects, - const object_links<L>& links, - float max_alpha); + object_links_left_aligned(const object_image(L)& objects, + const object_links<L>& links, + float max_alpha); # ifndef MLN_INCLUDE_ONLY @@ -91,21 +92,21 @@ namespace scribo template <typename L> object_links<L> - object_links_top_aligned(const object_image(L)& objects, - const object_links<L>& links, - float max_alpha) + object_links_left_aligned(const object_image(L)& objects, + const object_links<L>& links, + float max_alpha) { - trace::entering("scribo::filter::object_links_top_aligned"); + trace::entering("scribo::filter::object_links_left_aligned"); mln_precondition(objects.is_valid()); mln_precondition(links.is_valid()); object_links<L> output = object_links_non_aligned_simple(objects, links, - 1, + 3, max_alpha); - trace::exiting("scribo::filter::object_links_top_aligned"); + trace::exiting("scribo::filter::object_links_left_aligned"); return output; } @@ -118,4 +119,4 @@ namespace scribo } // end of namespace scribo -#endif // ! SCRIBO_FILTER_OBJECT_LINKS_TOP_ALIGNED_HH +#endif // ! SCRIBO_FILTER_OBJECT_LINKS_LEFT_ALIGNED_HH diff --git a/scribo/filter/object_links_non_aligned_simple.hh b/scribo/filter/object_links_non_aligned_simple.hh index 706497d..15be8e9 100644 --- a/scribo/filter/object_links_non_aligned_simple.hh +++ b/scribo/filter/object_links_non_aligned_simple.hh @@ -84,6 +84,8 @@ namespace scribo 0 = center 1 = top 2 = bottom + 3 = left + 4 = right */ template <typename L> @@ -166,6 +168,40 @@ namespace scribo } } } + // Left + else if (edge == 3) + { + for_all_components(i, objects.bboxes()) + { + if (links[i] != i) + { + dr = math::abs(bboxes[i].center().row() + - bboxes[links[i]].center().row()); + dc = math::abs(bboxes[i].pmin().col() + - bboxes[links[i]].pmin().col()); + + if (std::atan(dc / dr) > max_alpha_rad) + output[i] = i; + } + } + } + // Right + else if (edge == 4) + { + for_all_components(i, objects.bboxes()) + { + if (links[i] != i) + { + dr = math::abs(bboxes[i].center().row() + - bboxes[links[i]].center().row()); + dc = math::abs(bboxes[i].pmax().col() + - bboxes[links[i]].pmax().col()); + + if (std::atan(dc / dr) > max_alpha_rad) + output[i] = i; + } + } + } else { trace::warning("Invalid edge value... Aborting computation."); diff --git a/scribo/filter/object_links_top_aligned.hh b/scribo/filter/object_links_right_aligned.hh similarity index 77% copy from scribo/filter/object_links_top_aligned.hh copy to scribo/filter/object_links_right_aligned.hh index 4a92c96..2ee0280 100644 --- a/scribo/filter/object_links_top_aligned.hh +++ b/scribo/filter/object_links_right_aligned.hh @@ -23,12 +23,12 @@ // exception does not however invalidate any other reasons why the // executable file might be covered by the GNU General Public License. -#ifndef SCRIBO_FILTER_OBJECT_LINKS_TOP_ALIGNED_HH -# define SCRIBO_FILTER_OBJECT_LINKS_TOP_ALIGNED_HH +#ifndef SCRIBO_FILTER_OBJECT_LINKS_RIGHT_ALIGNED_HH +# define SCRIBO_FILTER_OBJECT_LINKS_RIGHT_ALIGNED_HH /// \file /// -/// Invalidate links between two objects if their top are not +/// Invalidate links between two objects if their right are not /// aligned. @@ -48,7 +48,7 @@ namespace scribo using namespace mln; - /*! \brief Invalidate links between two objects if their top are not + /*! \brief Invalidate links between two objects if their right are not aligned. \param[in] objects An object image. @@ -77,13 +77,13 @@ namespace scribo \endverbatim - The angle between the two tops must be lower than \p max_alpha. + The angle between the two rights must be lower than \p max_alpha. */ template <typename L> object_links<L> - object_links_top_aligned(const object_image(L)& objects, - const object_links<L>& links, - float max_alpha); + object_links_right_aligned(const object_image(L)& objects, + const object_links<L>& links, + float max_alpha); # ifndef MLN_INCLUDE_ONLY @@ -91,21 +91,21 @@ namespace scribo template <typename L> object_links<L> - object_links_top_aligned(const object_image(L)& objects, - const object_links<L>& links, - float max_alpha) + object_links_right_aligned(const object_image(L)& objects, + const object_links<L>& links, + float max_alpha) { - trace::entering("scribo::filter::object_links_top_aligned"); + trace::entering("scribo::filter::object_links_right_aligned"); mln_precondition(objects.is_valid()); mln_precondition(links.is_valid()); object_links<L> output = object_links_non_aligned_simple(objects, links, - 1, + 4, max_alpha); - trace::exiting("scribo::filter::object_links_top_aligned"); + trace::exiting("scribo::filter::object_links_right_aligned"); return output; } @@ -118,4 +118,4 @@ namespace scribo } // end of namespace scribo -#endif // ! SCRIBO_FILTER_OBJECT_LINKS_TOP_ALIGNED_HH +#endif // ! SCRIBO_FILTER_OBJECT_LINKS_RIGHT_ALIGNED_HH -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-37-g17faab3 Improve object linking backend.
by Guillaume Lazzara
* scribo/primitive/internal/find_left_link.hh, * scribo/primitive/internal/find_right_link.hh, * scribo/primitive/internal/is_invalid_link.hh: Remove. * scribo/primitive/link/internal/compute_anchor.hh, * scribo/primitive/link/internal/link_ms_dmax_base.hh, * scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh, * scribo/primitive/link/internal/link_single_dmax_base.hh, * scribo/primitive/link/internal/link_single_dmax_ratio_base.hh, * scribo/primitive/link/with_single_down_link.hh, * scribo/primitive/link/with_single_left_link.hh, * scribo/primitive/link/with_single_left_link_dmax_ratio.hh, * scribo/primitive/link/with_single_right_link.hh, * scribo/primitive/link/with_single_right_link_dmax_ratio.hh, * scribo/primitive/link/with_single_up_link.hh: Introduce the anchor concept and make use of it. --- scribo/ChangeLog | 21 +++ scribo/primitive/internal/find_left_link.hh | 108 --------------- scribo/primitive/internal/find_right_link.hh | 108 --------------- scribo/primitive/internal/is_invalid_link.hh | 100 -------------- scribo/primitive/link/internal/compute_anchor.hh | 143 +++++++++++++++++--- .../primitive/link/internal/link_ms_dmax_base.hh | 27 ++-- .../link/internal/link_ms_dmax_ratio_base.hh | 18 ++- .../link/internal/link_single_dmax_base.hh | 21 ++-- .../link/internal/link_single_dmax_ratio_base.hh | 20 ++-- ...ingle_left_link.hh => with_single_down_link.hh} | 68 +++++++--- scribo/primitive/link/with_single_left_link.hh | 2 +- .../link/with_single_left_link_dmax_ratio.hh | 10 +- scribo/primitive/link/with_single_right_link.hh | 4 +- .../link/with_single_right_link_dmax_ratio.hh | 8 +- ...le_right_link_top.hh => with_single_up_link.hh} | 81 +++++++---- 15 files changed, 296 insertions(+), 443 deletions(-) delete mode 100644 scribo/primitive/internal/find_left_link.hh delete mode 100644 scribo/primitive/internal/find_right_link.hh delete mode 100644 scribo/primitive/internal/is_invalid_link.hh copy scribo/primitive/link/{with_single_left_link.hh => with_single_down_link.hh} (60%) copy scribo/primitive/link/{with_single_right_link_top.hh => with_single_up_link.hh} (60%) diff --git a/scribo/ChangeLog b/scribo/ChangeLog index 891cd30..45faa9f 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,5 +1,26 @@ 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Improve object linking backend. + + * scribo/primitive/internal/find_left_link.hh, + * scribo/primitive/internal/find_right_link.hh, + * scribo/primitive/internal/is_invalid_link.hh: Remove. + + * scribo/primitive/link/internal/compute_anchor.hh, + * scribo/primitive/link/internal/link_ms_dmax_base.hh, + * scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh, + * scribo/primitive/link/internal/link_single_dmax_base.hh, + * scribo/primitive/link/internal/link_single_dmax_ratio_base.hh, + * scribo/primitive/link/with_single_down_link.hh, + * scribo/primitive/link/with_single_left_link.hh, + * scribo/primitive/link/with_single_left_link_dmax_ratio.hh, + * scribo/primitive/link/with_single_right_link.hh, + * scribo/primitive/link/with_single_right_link_dmax_ratio.hh, + * scribo/primitive/link/with_single_up_link.hh: Introduce the + anchor concept and make use of it. + +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + * scribo/filter/objects_with_holes.hh: New component filter. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> diff --git a/scribo/primitive/internal/find_left_link.hh b/scribo/primitive/internal/find_left_link.hh deleted file mode 100644 index 4f30e36..0000000 --- a/scribo/primitive/internal/find_left_link.hh +++ /dev/null @@ -1,108 +0,0 @@ -// Copyright (C) 2009 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_PRIMITIVE_INTERNAL_FIND_LEFT_LINK_HH -# define SCRIBO_PRIMITIVE_INTERNAL_FIND_LEFT_LINK_HH - -/// \file -/// -/// Find the left neighbor of a line of text if exists. -/// -/// \todo To be deleted. - -# include <mln/core/concept/image.hh> - -# include <mln/math/abs.hh> - -# include <mln/util/array.hh> -# include <mln/util/couple.hh> - -# include <scribo/core/object_image.hh> -# include <scribo/primitive/internal/update_link_array.hh> -# include <scribo/primitive/internal/is_invalid_link.hh> - -//FIXME: not generic. -# include <mln/core/alias/dpoint2d.hh> - -namespace scribo -{ - - namespace primitive - { - - namespace internal - { - - /// Find the left neighbor of a line of text if exists. - /// - /// \param objects An image of objects. - /// \param left_link The left neighbors. - /// \param current_comp A text line id. - /// \param dmax The maximum lookup distance. - /// \param c The lookup start point. - // - template <typename L> - mln::util::couple<bool, mln_site(L)> - find_left_link(const object_image(L)& objects, - mln::util::array<unsigned>& left_link, - unsigned current_comp, - float dmax, - const mln_site(L)& c); - - -# ifndef MLN_INCLUDE_ONLY - - template <typename L> - mln::util::couple<bool, mln_site(L)> - find_left_link(const object_image(L)& objects, - mln::util::array<unsigned>& left_link, - unsigned current_comp, - float dmax, - const mln_site(L)& c) - { - ///FIXME: the following code is not generic... - /// First site on the right of the central site - mln_site(L) p = c + mln::left; - - while (is_invalid_link(objects, left_link, p, - current_comp, c, dmax)) - --p.col(); - - bool - b = update_link_array(objects, left_link, p, c, current_comp, dmax); - - return mln::make::couple(b, p); - } - -# endif // MLN_INCLUDE_ONLY - - } // end of namespace scribo::primitive::internal - - } // end of namespace scribo::primitive - -} // end of namespace scribo - - -#endif // ! SCRIBO_PRIMITIVE_INTERNAL_FIND_LEFT_LINK_HH diff --git a/scribo/primitive/internal/find_right_link.hh b/scribo/primitive/internal/find_right_link.hh deleted file mode 100644 index 09e60f9..0000000 --- a/scribo/primitive/internal/find_right_link.hh +++ /dev/null @@ -1,108 +0,0 @@ -// Copyright (C) 2009 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_PRIMITIVE_INTERNAL_FIND_RIGHT_LINK_HH -# define SCRIBO_PRIMITIVE_INTERNAL_FIND_RIGHT_LINK_HH - -/// \file -/// -/// Find the right neighbor of a line of text if exists. -/// -/// \todo To be deleted. - -# include <mln/core/concept/image.hh> - -# include <mln/math/abs.hh> - -# include <mln/util/array.hh> -# include <mln/util/couple.hh> - -# include <scribo/core/object_image.hh> -# include <scribo/primitive/internal/update_link_array.hh> -# include <scribo/primitive/internal/is_invalid_link.hh> - -//FIXME: not generic. -# include <mln/core/alias/dpoint2d.hh> - -namespace scribo -{ - - namespace primitive - { - - namespace internal - { - - /// Find the right neighbor of a line of text if exists. - /// - /// \param objects An image of objects. - /// \param right_link The right neighbors. - /// \param current_comp A text line id. - /// \param dmax The maximum lookup distance. - /// \param c The lookup start point. - // - template <typename L> - mln::util::couple<bool, mln_site(L)> - find_right_link(const object_image(L)& objects, - mln::util::array<unsigned>& right_link, - unsigned current_comp, - float dmax, - const mln_site(L)& c); - - -# ifndef MLN_INCLUDE_ONLY - - template <typename L> - mln::util::couple<bool, mln_site(L)> - find_right_link(const object_image(L)& objects, - mln::util::array<unsigned>& right_link, - unsigned current_comp, - float dmax, - const mln_site(L)& c) - { - /// FIXME: the following code is not generic... - /// First site on the right of the central site - mln_site(L) p = c + mln::right; - - while (is_invalid_link(objects, right_link, p, - current_comp, c, dmax)) - ++p.col(); - - bool - b = update_link_array(objects, right_link, p, c, current_comp, dmax); - - return mln::make::couple(b, p); - } - -# endif // MLN_INCLUDE_ONLY - - } // end of namespace scribo::primitive::internal - - } // end of namespace scribo::primitive - -} // end of namespace scribo - - -#endif // ! SCRIBO_PRIMITIVE_INTERNAL_FIND_RIGHT_LINK_HH diff --git a/scribo/primitive/internal/is_invalid_link.hh b/scribo/primitive/internal/is_invalid_link.hh deleted file mode 100644 index e6343fd..0000000 --- a/scribo/primitive/internal/is_invalid_link.hh +++ /dev/null @@ -1,100 +0,0 @@ -// Copyright (C) 2009 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_PRIMITIVE_INTERNAL_IS_INVALID_LINK_HH -# define SCRIBO_PRIMITIVE_INTERNAL_IS_INVALID_LINK_HH - -/// \file -/// -/// Check whether an objects link is invalid or not. -/// -/// \todo To be deleted. - -# include <mln/math/abs.hh> -# include <mln/literal/zero.hh> - -# include <scribo/core/object_image.hh> - -namespace scribo -{ - - namespace primitive - { - - namespace internal - { - - using namespace mln; - - - /// Check whether an objects link is invalid or not. - /// - /// \param objects An image of objects. - /// \param left_link The left neighbors. - /// \param p The current site. - /// \param current_comp The current object id. - /// \param c The left link start point. - /// \param dmax The maximum lookup distance. - // - template <typename L> - bool - is_invalid_link(const object_image(L)& objects_, - mln::util::array<unsigned>& link_array, - const mln_site(L)& p, - unsigned current_comp, - const mln_site(L)& c, - float dmax); - -# ifndef MLN_INCLUDE_ONLY - - template <typename L> - inline - bool - is_invalid_link(const object_image(L)& objects, - mln::util::array<unsigned>& link_array, - const mln_site(L)& p, - unsigned current_comp, - const mln_site(L)& c, - float dmax) - { - return (objects.domain().has(p) // Not outside image domain - && (objects(p) == literal::zero // Is the background - || objects(p) == current_comp // Is the current component - || link_array[objects(p)] == current_comp) // Creates a loop - && static_cast<float>(math::abs(p.col() - c.col())) < dmax); // Not too far - } - -# endif // ! MLN_INCLUDE_ONLY - - } // end of namespace scribo::primitive::internal - - } // end of namespace scribo::primitive - -} // end of namespace scribo - - -#endif // ! SCRIBO_PRIMITIVE_INTERNAL_IS_INVALID_LINK_HH - - diff --git a/scribo/primitive/link/internal/compute_anchor.hh b/scribo/primitive/link/internal/compute_anchor.hh index c7bae11..0d3b6f2 100644 --- a/scribo/primitive/link/internal/compute_anchor.hh +++ b/scribo/primitive/link/internal/compute_anchor.hh @@ -52,15 +52,11 @@ namespace scribo /*! \brief Return the proper anchor used to find a neighbor. \param[in] objects An object image. - \param[in] mass_centers Object mass centers. \param[in] current_object An object id. \param[in] anchor The expected anchor. - Anchor can take one of the following values: - - anchor::MassCenter, mass center anchor. - - anchor::Top, top anchor. - - anchor::Bottom, bottom anchor. - - anchor::Center, center anchor. + Anchor can take one of the values defined in the + scribo::anchor::Type enum. Top and bottom anchors are respectively computed from the @@ -76,64 +72,169 @@ namespace scribo out.row = P.row - min(10, h /10) */ - template <typename L, typename P> + template <typename L> mln_site(L) compute_anchor(const object_image(L)& objects, - const mln::util::array<P>& mass_centers, unsigned current_object, anchor::Type anchor); # ifndef MLN_INCLUDE_ONLY - template <typename L, typename P> + template <typename L> mln_site(L) compute_anchor(const object_image(L)& objects, - const mln::util::array<P>& mass_centers, unsigned current_object, anchor::Type anchor) { + typedef mln_site(L) P; + unsigned h = objects.bbox(current_object).pmax().row() - objects.bbox(current_object).pmin().row(); + unsigned w = objects.bbox(current_object).pmax().col() + - objects.bbox(current_object).pmin().col(); mln_site(L) sp = objects.bbox(current_object).center(); - def::coord r = 0; switch (anchor) { - // Masss Center + // Component masss center case anchor::MassCenter: - return mass_centers(current_object); + return objects.mass_center(current_object); - // Top + // Bounding box top center case anchor::Top: if (h < 30) - r = objects.bbox(current_object).pmin().row() + sp.row() = objects.bbox(current_object).pmin().row() + math::min(2u, (h + 1) / 2 - 1); else - r = objects.bbox(current_object).pmin().row() + sp.row() = objects.bbox(current_object).pmin().row() + math::min(10u, h /10); break; - // Bottom + // Bounding box bottom center case anchor::Bottom: if (h < 30) - r = objects.bbox(current_object).pmax().row() + sp.row() = objects.bbox(current_object).pmax().row() - math::min(2u, (h + 1) / 2 - 1); else - r = objects.bbox(current_object).pmax().row() + sp.row() = objects.bbox(current_object).pmax().row() - math::min(10u, h /10); break; + + // Bounding box center case anchor::Center: return objects.bbox(current_object).center(); + + // Bounding box actual left center + case anchor::ActualLeft: + return P(objects.bbox(current_object).center().row(), + objects.bbox(current_object).pmin().col()); + + + // Bounding box left center + case anchor::Left: + if (w < 30) + sp.col() = objects.bbox(current_object).pmin().col() + + math::min(2u, (w + 1) / 2 - 1); + else + sp.col() = objects.bbox(current_object).pmin().col() + + math::min(10u, w /10); + break; + + + // Bounding box actual right center + case anchor::ActualRight: + return P(objects.bbox(current_object).center().row(), + objects.bbox(current_object).pmax().col()); + + + // Bounding box right center + case anchor::Right: + if (w < 30) + sp.col() = objects.bbox(current_object).pmax().col() + - math::min(2u, (w + 1) / 2 - 1); + else + sp.col() = objects.bbox(current_object).pmax().col() + - math::min(10u, w /10); + break; + + + // Bounding box top left + case anchor::TopLeft: + if (h < 30) + sp.row() = objects.bbox(current_object).pmin().row() + + math::min(2u, (h + 1) / 2 - 1); + else + sp.row() = objects.bbox(current_object).pmin().row() + + math::min(10u, h /10); + if (w < 30) + sp.col() = objects.bbox(current_object).pmin().col() + + math::min(2u, (w + 1) / 2 - 1); + else + sp.col() = objects.bbox(current_object).pmin().col() + + math::min(10u, w /10); + break; + + + // Bounding box top right + case anchor::TopRight: + if (h < 30) + sp.row() = objects.bbox(current_object).pmin().row() + + math::min(2u, (h + 1) / 2 - 1); + else + sp.row() = objects.bbox(current_object).pmin().row() + + math::min(10u, h /10); + if (w < 30) + sp.col() = objects.bbox(current_object).pmax().col() + - math::min(2u, (w + 1) / 2 - 1); + else + sp.col() = objects.bbox(current_object).pmax().col() + - math::min(10u, w /10); + break; + + + // Bounding box bottom left + case anchor::BottomLeft: + if (h < 30) + sp.row() = objects.bbox(current_object).pmax().row() + - math::min(2u, (h + 1) / 2 - 1); + else + sp.row() = objects.bbox(current_object).pmax().row() + - math::min(10u, h /10); + if (w < 30) + sp.col() = objects.bbox(current_object).pmin().col() + + math::min(2u, (w + 1) / 2 - 1); + else + sp.col() = objects.bbox(current_object).pmin().col() + + math::min(10u, w /10); + break; + + // Bounding box bottom right + case anchor::BottomRight: + if (h < 30) + sp.row() = objects.bbox(current_object).pmax().row() + - math::min(2u, (h + 1) / 2 - 1); + else + sp.row() = objects.bbox(current_object).pmax().row() + - math::min(10u, h /10); + if (w < 30) + sp.col() = objects.bbox(current_object).pmax().col() + - math::min(2u, (w + 1) / 2 - 1); + else + sp.col() = objects.bbox(current_object).pmax().col() + - math::min(10u, w /10); + break; + + + default: trace::warning("Non handled anchor"); - mln_assertion(anchor > 2); + mln_assertion(anchor < anchor::Invalid); } - sp.row() = r; return sp; } diff --git a/scribo/primitive/link/internal/link_ms_dmax_base.hh b/scribo/primitive/link/internal/link_ms_dmax_base.hh index 80a9a13..edb0941 100644 --- a/scribo/primitive/link/internal/link_ms_dmax_base.hh +++ b/scribo/primitive/link/internal/link_ms_dmax_base.hh @@ -75,12 +75,11 @@ namespace scribo link_ms_dmax_base(const object_image(L)& objects, - unsigned neighb_max_distance); - - + unsigned neighb_max_distance, + anchor::Direction direction); bool verify_link_criterion_(unsigned current_object, - const P& start_point, const P& p) const; + const P& start_point, const P& p) const; mln_site(L) start_point_(unsigned current_object, unsigned anchor); @@ -88,9 +87,9 @@ namespace scribo void start_processing_object_(unsigned current_object); private: - mln::util::array<ms_t> mass_centers_; float dmax_; float neighb_max_distance_; + anchor::Direction direction_; }; @@ -101,17 +100,17 @@ namespace scribo inline link_ms_dmax_base<L, E>::link_ms_dmax_base( const object_image(L)& objects, - unsigned neighb_max_distance) + unsigned neighb_max_distance, + anchor::Direction direction) : super_(objects), dmax_(0), - neighb_max_distance_(neighb_max_distance) + neighb_max_distance_(neighb_max_distance), + direction_(direction) { - - mass_centers_ = labeling::compute(accu::meta::center(), - objects, objects.nlabels()); } + template <typename L, typename E> inline bool @@ -121,7 +120,7 @@ namespace scribo { (void) current_object; - float dist = math::abs(p.col() - start_point.col()); + float dist = math::abs(p[direction_] - start_point[direction_]); return dist <= dmax_; // Not too far } @@ -133,7 +132,7 @@ namespace scribo unsigned anchor) { (void) anchor; - return mass_centers_(current_object); + return this->objects_.mass_center(current_object); } @@ -144,8 +143,8 @@ namespace scribo unsigned current_object) { float - midcol = (this->objects_.bbox(current_object).pmax().col() - - this->objects_.bbox(current_object).pmin().col()) / 2; + midcol = (this->objects_.bbox(current_object).pmax()[direction_] + - this->objects_.bbox(current_object).pmin()[direction_]) / 2; dmax_ = midcol + neighb_max_distance_; } diff --git a/scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh b/scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh index 414e0b2..8eca53d 100644 --- a/scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh +++ b/scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh @@ -76,7 +76,8 @@ namespace scribo link_ms_dmax_ratio_base(const object_image(L)& objects, - float dmax_ratio); + float dmax_ratio, + anchor::Direction direction); @@ -89,9 +90,9 @@ namespace scribo void start_processing_object_(unsigned current_object); private: - mln::util::array<ms_t> mass_centers_; float dmax_ratio_; float dmax_; + anchor::Direction direction_; }; @@ -102,14 +103,14 @@ namespace scribo inline link_ms_dmax_ratio_base<L, E>::link_ms_dmax_ratio_base( const object_image(L)& objects, - float dmax_ratio) + float dmax_ratio, + anchor::Direction direction) : super_(objects), dmax_ratio_(dmax_ratio), - dmax_(0) + dmax_(0), + direction_(direction) { - mass_centers_ = labeling::compute(accu::meta::center(), - objects, objects.nlabels()); } template <typename L, typename E> @@ -120,9 +121,10 @@ namespace scribo const P& start_point, const P& p) const { + mln_assertion(dmax_ != 0); (void) current_object; - float dist = math::abs(p.col() - start_point.col()); + float dist = math::abs(p[direction_] - start_point[direction_]); return dist <= dmax_; // Not too far } @@ -134,7 +136,7 @@ namespace scribo unsigned anchor) { (void) anchor; - return mass_centers_(current_object); + return this->objects_.mass_center(current_object); } diff --git a/scribo/primitive/link/internal/link_single_dmax_base.hh b/scribo/primitive/link/internal/link_single_dmax_base.hh index 4f571af..8d594f5 100644 --- a/scribo/primitive/link/internal/link_single_dmax_base.hh +++ b/scribo/primitive/link/internal/link_single_dmax_base.hh @@ -76,7 +76,8 @@ namespace scribo typedef mln_site(L) P; link_single_dmax_base(const object_image(L)& objects, - unsigned neighb_max_distance); + unsigned neighb_max_distance, + anchor::Direction direction); bool verify_link_criterion_(unsigned current_object, @@ -90,7 +91,7 @@ namespace scribo private: float dmax_; float neighb_max_distance_; -// mln::util::array<ms_t> mass_centers_; + anchor::Direction direction_; }; @@ -101,14 +102,14 @@ namespace scribo inline link_single_dmax_base<L, E>::link_single_dmax_base( const object_image(L)& objects, - unsigned neighb_max_distance) + unsigned neighb_max_distance, + anchor::Direction direction) : super_(objects), dmax_(0), - neighb_max_distance_(neighb_max_distance) + neighb_max_distance_(neighb_max_distance), + direction_(direction) { -// mass_centers_ = labeling::compute(accu::meta::center(), -// objects, objects.nlabels()); } @@ -122,7 +123,7 @@ namespace scribo { (void) current_object; - float dist = math::abs(p.col() - start_point.col()); + float dist = math::abs(p[direction_] - start_point[direction_]); return dist <= dmax_; // Not too far } @@ -133,7 +134,7 @@ namespace scribo link_single_dmax_base<L, E>::start_point_(unsigned current_object, anchor::Type anchor) { - return internal::compute_anchor(this->objects_, this->objects_.mass_centers(),//mass_centers_, + return internal::compute_anchor(this->objects_, current_object, anchor); } @@ -145,8 +146,8 @@ namespace scribo unsigned current_object) { float - midcol = (this->objects_.bbox(current_object).pmax().col() - - this->objects_.bbox(current_object).pmin().col()) / 2; + midcol = (this->objects_.bbox(current_object).pmax()[direction_] + - this->objects_.bbox(current_object).pmin()[direction_]) / 2; dmax_ = midcol + neighb_max_distance_; } diff --git a/scribo/primitive/link/internal/link_single_dmax_ratio_base.hh b/scribo/primitive/link/internal/link_single_dmax_ratio_base.hh index 9eadba7..ebe0b6a 100644 --- a/scribo/primitive/link/internal/link_single_dmax_ratio_base.hh +++ b/scribo/primitive/link/internal/link_single_dmax_ratio_base.hh @@ -78,8 +78,8 @@ namespace scribo link_single_dmax_ratio_base(const object_image(L)& objects, - float dmax_ratio, - unsigned center_type_); + float dmax_ratio, + anchor::Direction direction); @@ -94,7 +94,7 @@ namespace scribo private: float dmax_ratio_; float dmax_; - mln::util::array<ms_t> mass_centers_; + anchor::Direction direction_; }; @@ -105,14 +105,14 @@ namespace scribo inline link_single_dmax_ratio_base<L, E>::link_single_dmax_ratio_base( const object_image(L)& objects, - float dmax_ratio) + float dmax_ratio, + anchor::Direction direction) : super_(objects), dmax_ratio_(dmax_ratio), - dmax_(0) + dmax_(0), + direction_(direction) { - mass_centers_ = labeling::compute(accu::meta::center(), - objects, objects.nlabels()); } template <typename L, typename E> @@ -125,7 +125,7 @@ namespace scribo { (void) current_object; - float dist = math::abs(p.col() - start_point.col()); + float dist = math::abs(p[direction_] - start_point[direction_]); return dist <= dmax_; // Not too far } @@ -137,8 +137,8 @@ namespace scribo anchor::Type anchor) { (void) anchor; - return internal::compute_anchors(this->objects_, mass_centers_, - current_object, anchor); + return internal::compute_anchor(this->objects_, + current_object, anchor); } diff --git a/scribo/primitive/link/with_single_left_link.hh b/scribo/primitive/link/with_single_down_link.hh similarity index 60% copy from scribo/primitive/link/with_single_left_link.hh copy to scribo/primitive/link/with_single_down_link.hh index 2cf0c5a..7e4e82c 100644 --- a/scribo/primitive/link/with_single_left_link.hh +++ b/scribo/primitive/link/with_single_down_link.hh @@ -23,12 +23,12 @@ // exception does not however invalidate any other reasons why the // executable file might be covered by the GNU General Public License. -#ifndef SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_LEFT_LINK_HH -# define SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_LEFT_LINK_HH +#ifndef SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_DOWN_LINK_HH +# define SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_DOWN_LINK_HH /// \file /// -/// Link text objects with their left neighbor. +/// Link text objects with their down neighbor. # include <mln/core/concept/image.hh> # include <mln/core/concept/neighborhood.hh> @@ -61,17 +61,29 @@ namespace scribo namespace link { - /// \brief Link objects with their left neighbor if exists. + /// \brief Link objects with their down neighbor if exists. /// /// \param[in] objects An object image. - /// \param[in] The maximum distance allowed to seach a neighbor object. + /// \param[in] neighb_max_distance The maximum distance allowed + /// to seach a neighbor object. + /// \param[in] anchor The neighborhod lookup start point. /// /// \return Object links data. // template <typename L> inline object_links<L> - with_single_left_link(const object_image(L)& objects, + with_single_down_link(const object_image(L)& objects, + unsigned neighb_max_distance, + anchor::Type anchor); + + /// \overload + /// Anchor type is set to anchor::MassCenter + // + template <typename L> + inline + object_links<L> + with_single_down_link(const object_image(L)& objects, unsigned neighb_max_distance); @@ -80,7 +92,7 @@ namespace scribo template <typename L> inline object_links<L> - with_single_left_link(const object_image(L)& objects); + with_single_down_link(const object_image(L)& objects); # ifndef MLN_INCLUDE_ONLY @@ -92,23 +104,23 @@ namespace scribo // Functor template <typename L> - class single_left_functor - : public internal::link_single_dmax_base<L, single_left_functor<L> > + class single_down_functor + : public internal::link_single_dmax_base<L, single_down_functor<L> > { typedef - internal::link_single_dmax_base<L, single_left_functor<L> > super_; + internal::link_single_dmax_base<L, single_down_functor<L> > sdowner_; public: typedef mln_site(L) P; - single_left_functor(const object_image(L)& objects, unsigned dmax) - : super_(objects, dmax) + single_down_functor(const object_image(L)& objects, unsigned dmax) + : sdowner_(objects, dmax, anchor::Vertical) { } void compute_next_site_(P& p) { - --p.col(); + ++p.row(); } }; @@ -122,19 +134,20 @@ namespace scribo template <typename L> inline object_links<L> - with_single_left_link(const object_image(L)& objects, - unsigned neighb_max_distance) + with_single_down_link(const object_image(L)& objects, + unsigned neighb_max_distance, + anchor::Type anchor) { - trace::entering("scribo::primitive::link::with_single_left_link"); + trace::entering("scribo::primitive::link::with_single_down_link"); mln_precondition(objects.is_valid()); - internal::single_left_functor<L> + internal::single_down_functor<L> functor(objects, neighb_max_distance); - object_links<L> output = compute(functor); + object_links<L> output = compute(functor, anchor); - trace::exiting("scribo::primitive::link::with_single_left_link"); + trace::exiting("scribo::primitive::link::with_single_down_link"); return output; } @@ -142,9 +155,20 @@ namespace scribo template <typename L> inline object_links<L> - with_single_left_link(const object_image(L)& objects) + with_single_down_link(const object_image(L)& objects, + unsigned neighb_max_distance) + { + return with_single_down_link(objects, neighb_max_distance, + anchor::MassCenter); + } + + + template <typename L> + inline + object_links<L> + with_single_down_link(const object_image(L)& objects) { - return with_single_left_link(objects, mln_max(unsigned)); + return with_single_down_link(objects, mln_max(unsigned)); } @@ -156,4 +180,4 @@ namespace scribo } // end of namespace scribo -#endif // ! SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_LEFT_LINK_HH +#endif // ! SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_DOWN_LINK_HH diff --git a/scribo/primitive/link/with_single_left_link.hh b/scribo/primitive/link/with_single_left_link.hh index 2cf0c5a..651f1f6 100644 --- a/scribo/primitive/link/with_single_left_link.hh +++ b/scribo/primitive/link/with_single_left_link.hh @@ -102,7 +102,7 @@ namespace scribo typedef mln_site(L) P; single_left_functor(const object_image(L)& objects, unsigned dmax) - : super_(objects, dmax) + : super_(objects, dmax, anchor::Horizontal) { } diff --git a/scribo/primitive/link/with_single_left_link_dmax_ratio.hh b/scribo/primitive/link/with_single_left_link_dmax_ratio.hh index 587fb6c..d59bbc1 100644 --- a/scribo/primitive/link/with_single_left_link_dmax_ratio.hh +++ b/scribo/primitive/link/with_single_left_link_dmax_ratio.hh @@ -44,7 +44,7 @@ # include <scribo/core/object_links.hh> # include <scribo/primitive/link/internal/find_link.hh> -# include <scribo/primitive/link/internal/link_ms_dmax_ratio_base.hh> +# include <scribo/primitive/link/internal/link_single_dmax_ratio_base.hh> # include <scribo/primitive/link/compute.hh> @@ -99,18 +99,18 @@ namespace scribo template <typename L> class single_left_dmax_ratio_functor - : public internal::link_ms_dmax_ratio_base<L, - single_left_dmax_ratio_functor<L> > + : public internal::link_single_dmax_ratio_base<L, + single_left_dmax_ratio_functor<L> > { typedef single_left_dmax_ratio_functor<L> self_t; - typedef internal::link_ms_dmax_ratio_base<L, self_t> super_; + typedef internal::link_single_dmax_ratio_base<L, self_t> super_; public: typedef mln_site(L) P; single_left_dmax_ratio_functor(const object_image(L)& objects, unsigned dmax) - : super_(objects, dmax) + : super_(objects, dmax, anchor::Horizontal) { } diff --git a/scribo/primitive/link/with_single_right_link.hh b/scribo/primitive/link/with_single_right_link.hh index f7272ee..22380ab 100644 --- a/scribo/primitive/link/with_single_right_link.hh +++ b/scribo/primitive/link/with_single_right_link.hh @@ -40,7 +40,7 @@ # include <mln/util/array.hh> # include <scribo/core/macros.hh> -# include <scribo/core/anchors.hh> +# include <scribo/core/tag/anchor.hh> # include <scribo/core/object_image.hh> # include <scribo/core/object_links.hh> @@ -102,7 +102,7 @@ namespace scribo typedef mln_site(L) P; single_right_functor(const object_image(L)& objects, unsigned dmax) - : super_(objects, dmax) + : super_(objects, dmax, anchor::Horizontal) { } diff --git a/scribo/primitive/link/with_single_right_link_dmax_ratio.hh b/scribo/primitive/link/with_single_right_link_dmax_ratio.hh index ac6ef31..cd8360f 100644 --- a/scribo/primitive/link/with_single_right_link_dmax_ratio.hh +++ b/scribo/primitive/link/with_single_right_link_dmax_ratio.hh @@ -99,18 +99,18 @@ namespace scribo template <typename L> class single_right_dmax_ratio_functor - : public link_ms_dmax_ratio_base<L, - single_right_dmax_ratio_functor<L> > + : public link_single_dmax_ratio_base<L, + single_right_dmax_ratio_functor<L> > { typedef single_right_dmax_ratio_functor<L> self_t; - typedef link_ms_dmax_ratio_base<L, self_t> super_; + typedef link_single_dmax_ratio_base<L, self_t> super_; public: typedef mln_site(L) P; single_right_dmax_ratio_functor(const object_image(L)& objects, unsigned dmax) - : super_(objects, dmax) + : super_(objects, dmax, anchor::Horizontal) { } diff --git a/scribo/primitive/link/with_single_right_link_top.hh b/scribo/primitive/link/with_single_up_link.hh similarity index 60% copy from scribo/primitive/link/with_single_right_link_top.hh copy to scribo/primitive/link/with_single_up_link.hh index 1e3e0df..8781128 100644 --- a/scribo/primitive/link/with_single_right_link_top.hh +++ b/scribo/primitive/link/with_single_up_link.hh @@ -23,24 +23,26 @@ // exception does not however invalidate any other reasons why the // executable file might be covered by the GNU General Public License. -#ifndef SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_RIGHT_LINK_TOP_HH -# define SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_RIGHT_LINK_TOP_HH +#ifndef SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_UP_LINK_HH +# define SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_UP_LINK_HH /// \file /// -/// Link text objects with their right neighbor. - +/// Link text objects with their up neighbor. # include <mln/core/concept/image.hh> # include <mln/core/concept/neighborhood.hh> # include <mln/accu/center.hh> + # include <mln/labeling/compute.hh> + # include <mln/math/abs.hh> + # include <mln/util/array.hh> + # include <scribo/core/macros.hh> -# include <scribo/core/anchors.hh> # include <scribo/core/object_image.hh> # include <scribo/core/object_links.hh> @@ -59,28 +61,39 @@ namespace scribo namespace link { - /// \brief Link objects with their right neighbor if exists. - /// Lookup startup point is the object top center. + /// \brief Link objects with their up neighbor if exists. /// /// \param[in] objects An object image. - /// \param[in] The maximum distance allowed to seach a neighbor object. + /// \param[in] neighb_max_distance The maximum distance allowed + /// to seach a neighbor object. + /// \param[in] anchor The neighborhod lookup start point. /// /// \return Object links data. // template <typename L> inline object_links<L> - with_single_right_link_top(const object_image(L)& objects, - unsigned neighb_max_distance); + with_single_up_link(const object_image(L)& objects, + unsigned neighb_max_distance, + anchor::Type anchor); + + /// \overload + /// Anchor type is set to anchor::Center + // + template <typename L> + inline + object_links<L> + with_single_up_link(const object_image(L)& objects, + unsigned neighb_max_distance); /// \overload /// Max distance is set to mln_max(unsigned). + // template <typename L> inline object_links<L> - with_single_right_link_top(const object_image(L)& objects); - + with_single_up_link(const object_image(L)& objects); # ifndef MLN_INCLUDE_ONLY @@ -92,26 +105,23 @@ namespace scribo // Functor template <typename L> - class single_right_top_functor - : public link_single_dmax_base<L, - single_right_top_functor<L> > + class single_up_functor + : public internal::link_single_dmax_base<L, single_up_functor<L> > { typedef - link_single_dmax_base<L, single_right_top_functor<L> > - super_; + internal::link_single_dmax_base<L, single_up_functor<L> > super_; public: typedef mln_site(L) P; - single_right_top_functor(const object_image(L)& objects, - unsigned dmax) - : super_(objects, dmax) + single_up_functor(const object_image(L)& objects, unsigned dmax) + : super_(objects, dmax, anchor::Vertical) { } void compute_next_site_(P& p) { - ++p.col(); + --p.row(); } }; @@ -125,29 +135,40 @@ namespace scribo template <typename L> inline object_links<L> - with_single_right_link_top(const object_image(L)& objects, - unsigned neighb_max_distance) + with_single_up_link(const object_image(L)& objects, + unsigned neighb_max_distance, + anchor::Type anchor) { - trace::entering("scribo::primitive::link::with_single_right_link_top"); + trace::entering("scribo::primitive::link::with_single_up_link"); mln_precondition(objects.is_valid()); - internal::single_right_top_functor<L> + internal::single_up_functor<L> functor(objects, neighb_max_distance); - object_links<L> output = compute(functor, anchor::Top); + object_links<L> output = compute(functor, anchor); - trace::exiting("scribo::primitive::link::with_single_right_link_top"); + trace::exiting("scribo::primitive::link::with_single_up_link"); return output; } + template <typename L> + inline + object_links<L> + with_single_up_link(const object_image(L)& objects, + unsigned neighb_max_distance) + { + return with_single_up_link(objects, neighb_max_distance, + anchor::MassCenter); + } + template <typename L> inline object_links<L> - with_single_right_link_top(const object_image(L)& objects) + with_single_up_link(const object_image(L)& objects) { - return with_single_right_link_top(objects, mln_max(unsigned)); + return with_single_up_link(objects, mln_max(unsigned)); } @@ -159,4 +180,4 @@ namespace scribo } // end of namespace scribo -#endif // ! SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_RIGHT_LINK_TOP_HH +#endif // ! SCRIBO_PRIMITIVE_LINK_WITH_SINGLE_UP_LINK_HH -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-36-g55f2abf scribo/filter/objects_with_holes.hh: New component filter.
by Guillaume Lazzara
--- scribo/ChangeLog | 4 + scribo/filter/objects_with_holes.hh | 575 +++++++++++++++++++++++++++++++++++ 2 files changed, 579 insertions(+), 0 deletions(-) create mode 100644 scribo/filter/objects_with_holes.hh diff --git a/scribo/ChangeLog b/scribo/ChangeLog index bfde10a..891cd30 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,5 +1,9 @@ 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + * scribo/filter/objects_with_holes.hh: New component filter. + +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + * scribo/draw/bounding_boxes.hh: Do not draw box centers anymore. 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> diff --git a/scribo/filter/objects_with_holes.hh b/scribo/filter/objects_with_holes.hh new file mode 100644 index 0000000..c448e58 --- /dev/null +++ b/scribo/filter/objects_with_holes.hh @@ -0,0 +1,575 @@ +// Copyright (C) 2009 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_FILTER_OBJECTS_WITH_HOLES_HH +# define SCRIBO_FILTER_OBJECTS_WITH_HOLES_HH + +/// \file +/// +/// \brief Remove objects having a minimum number of holes. + +# include <sstream> + +# include <mln/core/concept/image.hh> +# include <mln/core/alias/neighb2d.hh> +# include <mln/core/routine/extend.hh> +# include <mln/core/image/dmorph/extended.hh> + +# include <mln/extension/duplicate.hh> + +# include <mln/draw/box_plain.hh> +# include <mln/util/array.hh> + +# include <mln/labeling/blobs_and_compute.hh> + +# include <mln/accu/math/count.hh> + +# include <mln/fun/i2v/array.hh> + +# include <mln/io/pbm/save.hh> +# include <mln/io/pgm/save.hh> + +# include <mln/data/convert.hh> + +# include <mln/labeling/background.hh> + +# include <scribo/core/macros.hh> +# include <scribo/core/object_image.hh> +# include <scribo/filter/internal/compute.hh> + +# include <mln/data/fill.hh> +# include <mln/data/paste.hh> + +# include <mln/util/timer.hh> + +# include <mln/value/label_16.hh> +# include <mln/core/var.hh> + + +#include <mln/debug/filename.hh> + +namespace scribo +{ + + namespace filter + { + + using namespace mln; + + /*! \brief Remove objects having a minimum number of holes. + + + + */ + template <typename L> + object_image(L) + objects_with_holes(const object_image(L)& objects, + unsigned min_holes_count, + unsigned min_size); + + + template <typename L> + inline + object_image(L) + objects_with_two_holes(const object_image(L)& objects, + unsigned min_size); + + +# ifndef MLN_INCLUDE_ONLY + + namespace internal + { + + unsigned my_find_root(image2d<unsigned>& parent, unsigned x) + { + if (parent.element(x) == x) + return x; + return parent.element(x) = my_find_root(parent, + parent.element(x)); + } + + + template <typename L> + mln_concrete(L) + compute_bboxes_image(const object_image(L)& objects) + { + typedef mln_psite(L) P; + typedef mln_dpsite(P) D; + + extension::adjust_fill(objects, 1, 0); + + mln_concrete(L) output; + initialize(output, objects); + data::fill(output, 0); + + for_all_components(i, objects.bboxes()) + { + mln_box(L) b = objects.bbox(i); + b.enlarge(1); + + unsigned + nrows = b.pmax().row() - b.pmin().row() + 1, + ncols = b.pmax().col() - b.pmin().col() + 1, + row_offset = objects.labeled_image_().delta_index(D(+1, -ncols)); + + mln_value(L) *ptr = &output(b.pmin()); + for (unsigned row = 0; row < nrows; ++row, ptr += row_offset) + for (unsigned col = 0; col < ncols; ++col) + *ptr++ = i; + } + + extension::duplicate(output); + + return output; + } + + + } // end of namespace scribo::filter::internal + + + + /*! + Label the background and count the number of background + components in an object bounding box. + */ + template <typename L> + inline + object_image(L) + objects_with_holes(const object_image(L)& objects, + unsigned min_holes_count, + unsigned min_size) + { + trace::entering("scribo::filter::objects_with_holes"); + + typedef object_image(L) O; + neighb2d nbh = c4(); + + image2d<unsigned> parent, card; + L bboxes_ima; + + util::array<util::set<unsigned> > bg_comps( + static_cast<unsigned>(objects.nlabels()) + 1); + + fun::i2v::array<bool> + to_keep(static_cast<unsigned>(objects.nlabels()) + 1, + false); + + const L& lbl = objects.labeled_image_(); + + std::cout << "objects.nlabels = " << objects.nlabels() << std::endl; + + util::timer timer_; + timer_.start(); + + // init + { + extension::adjust_fill(objects, nbh, mln_max(mln_value(L))); + initialize(parent, objects); + data::fill(parent, 0u); + + initialize(card, objects); + data::fill(card, 1); + + + // FIXME: Improve. + util::timer t2; + t2.start(); + bboxes_ima = internal::compute_bboxes_image(objects); + float t2_ = t2; + std::cout << "compute bboxes image " << t2_ << std::endl; + + to_keep(0) = true; + } + float t_ = timer_; + std::cout << "init = " << t_ << std::endl; + + // 1st pass + timer_.restart(); + { + util::array<int> dp = positive_offsets_wrt(lbl, nbh); + const unsigned n_nbhs = dp.nelements(); + + mln_bkd_pixter(const L) pxl(lbl); // Backward. + for_all(pxl) + { + unsigned p = pxl.offset(); + if (bboxes_ima.element(p) == 0 || lbl.element(p) != literal::zero) + continue; + + parent.element(p) = p; + for (unsigned i = 0; i < n_nbhs; ++i) + { + unsigned n = p + dp[i]; + if (bboxes_ima.element(n) == 0 || lbl.element(n) != literal::zero) + continue; + + unsigned r = internal::my_find_root(parent, n); + if (r != p) + { + parent.element(r) = p; + card.element(p) += card.element(r); + } + } // for_all(n) + + } // for_all(pxl) + + } + t_ = timer_; + std::cout << "1st pass = " << t_ << std::endl; + + // FIXME: Iterate over another label when a label is marked as + // "to be kept". + + // 2nd pass + timer_.restart(); + { + unsigned kept = 0; + mln_fwd_pixter(const L) pxl(bboxes_ima); // Forward. + for_all(pxl) + { + unsigned p = pxl.offset(); + + // Foreground, ignored. + if (parent.element(p) == 0 || bboxes_ima.element(p) == literal::zero) + continue; + + unsigned& parent_p = parent.element(p); + + if (parent_p != p) // Not root => propagation + parent_p = parent.element(parent_p); + else // Root + if (card.element(p) < min_size) + { + parent_p = 0; + continue; + } + +// if (bboxes_ima.element(p) != literal::zero) +// { + mln_value(L) object_id = bboxes_ima.element(p); + if (parent_p != 0 // Check parent again since + // parent's may have been set to + // 0. + && bg_comps(object_id).nelements() < min_holes_count) + { + if (! bg_comps(object_id).has(parent_p)) + { + bg_comps(object_id).insert(parent_p); + + if (bg_comps(object_id).nelements() == min_holes_count) + { + to_keep(object_id) = true; + ++kept; + } + } + } +// } + } + + float t_ = timer_; + std::cout << "2nd pass = " << t_ << std::endl; + + std::cout << "kept = " << kept << std::endl; +// debug::println(parent); +// std::cout << bg_comps << std::endl; +// std::cout << to_keep << std::endl; + + timer_.restart(); + object_image(L) output; + + if (kept == objects.nlabels()) + { + trace::exiting("scribo::filter::objects_with_holes"); + return objects; + } + + output.init_from_(objects); + output.relabel(to_keep); + t_ = timer_; + std::cout << "init output = " << t_ << std::endl; + + trace::exiting("scribo::filter::objects_with_holes"); + return output; + } + + + } + + + template <typename L> + inline + object_image(L) + objects_with_two_holes(const object_image(L)& objects, + unsigned min_size) + { + trace::entering("scribo::filter::objects_with_holes"); + + std::cout << objects.nlabels() << std::endl; + + typedef object_image(L) O; + neighb2d nbh = c8(); + + image2d<unsigned> parent, card; + L bboxes_ima; + + util::array<unsigned> bg_comps( + static_cast<unsigned>(objects.nlabels()) + 1, 0); + util::array<bool> bg_comps_done( + static_cast<unsigned>(objects.nlabels()) + 1, false); + + fun::i2v::array<bool> + to_keep(static_cast<unsigned>(objects.nlabels()) + 1, + false); + + const L& lbl = objects.labeled_image_(); + + // init + { + extension::fill(objects, mln_max(mln_value(L))); +// extension::adjust_fill(objects, nbh, mln_max(mln_value(L))); + initialize(parent, objects); + data::fill(parent, 0u); + + initialize(card, objects); + data::fill(card, 1); + border::fill(card, 1); + + bboxes_ima = internal::compute_bboxes_image(objects); + + to_keep(0) = true; + } + + // 1st pass + std::cout << "1st pass" << std::endl; + { + util::array<int> dp = positive_offsets_wrt(lbl, nbh); + const unsigned n_nbhs = dp.nelements(); + + mln_bkd_pixter(const L) pxl(lbl); // Backward. + for_all(pxl) + { + unsigned p = pxl.offset(); + if (bboxes_ima.element(p) == 0 || lbl.element(p) != literal::zero) + continue; + + parent.element(p) = p; + for (unsigned i = 0; i < n_nbhs; ++i) + { + unsigned n = p + dp[i]; + if (bboxes_ima.element(n) == 0 || lbl.element(n) != literal::zero) + continue; + + unsigned r = internal::my_find_root(parent, n); + if (r != p) + { + parent.element(r) = p; + card.element(p) += card.element(r); + } + } // for_all(n) + + } // for_all(pxl) + + } + + // 2nd pass + std::cout << "2nd pass" << std::endl; + { + unsigned kept = 0; + mln_fwd_pixter(const L) pxl(bboxes_ima); // Forward. + for_all(pxl) + { + unsigned p = pxl.offset(); + if (parent.element(p) == 0) // Foreground, ignored. + continue; + + unsigned& parent_p = parent.element(p); + + if (parent_p != p) // Not root => propagation + parent_p = parent.element(parent_p); + else // Root + if (card.element(p) < min_size) + { + parent_p = 0; + continue; + } + + if (parent_p != 0 // Check parent again since + // parent's may have been set to + // 0. + && bboxes_ima.element(p) != literal::zero) + { + mln_value(L) object_id = bboxes_ima.element(p); + if (!bg_comps_done(object_id)) + { + if (bg_comps(object_id) == 0) + { + bg_comps(object_id) = parent_p; + } + else if (bg_comps(object_id) != parent_p) + { + bg_comps_done(object_id) = true; + to_keep(object_id) = true; + ++kept; + } + } + } + } + + object_image(L) output; + if (kept == objects.nlabels()) + { + trace::exiting("scribo::filter::objects_with_holes"); + return objects; + } + + output.init_from_(objects); + output.relabel(to_keep); + + trace::exiting("scribo::filter::objects_with_holes"); + return output; + } + + } + + + +// template <typename L> +// inline +// object_image(L) +// objects_with_holes(const object_image(L)& objects, +// unsigned min_holes_count) +// { +// trace::entering("scribo::filter::objects_with_holes"); + +// mln_precondition(objects.is_valid()); + + +// L bboxes_ima; +// initialize(bboxes_ima, objects); +// data::fill(bboxes_ima, literal::zero); + +// for_all_components(i, objects.bboxes()) +// mln::draw::box(bboxes_ima, objects.bbox(i), i); + +// util::array<util::set<mln_value(L)> > first_bg_comp( +// static_cast<unsigned>(objects.nlabels()) + 1); + +// fun::i2v::array<bool> +// to_keep(static_cast<unsigned>(objects.nlabels()) + 1, +// false); +// to_keep(0) = true; + +// mln_value(L) nbglabels; +// L bg_lbl = labeling::background(objects, c8(), nbglabels); + +// unsigned kept; +// mln_piter(L) p(bboxes_ima.domain()); +// for_all(p) +// { +// if (bboxes_ima(p) == literal::zero) +// continue; + +// if (bg_lbl(p) != 0) +// if (! first_bg_comp(bboxes_ima(p)).has(bg_lbl(p))) +// if (first_bg_comp(bboxes_ima(p)).nelements() < min_holes_count - 1) +// first_bg_comp(bboxes_ima(p)).insert(bg_lbl(p)); +// else +// { +// to_keep(bboxes_ima(p)) == true; +// ++kept; +// } +// } + +// object_image(L) output; +// if (kept == objects.nlabels()) +// output = objects; +// else +// output = internal::compute(objects, to_keep); + +// trace::exiting("scribo::filter::objects_with_holes"); +// return output; +// } + + + template <typename L> + inline + object_image(L) + objects_with_holes_slow(const object_image(L)& objects, + unsigned min_holes_count) + { + trace::entering("scribo::filter::objects_with_holes"); + + mln_precondition(objects.is_valid()); + + fun::i2v::array<bool> + to_keep(static_cast<unsigned>(objects.nlabels()) + 1, + true); + + bool to_remove = false; + for_all_components(i, objects.bboxes()) + { + mln_domain(L) b = objects.bbox(i); + b.enlarge(1); + + mln_ch_value(L, bool) tmp(b); + data::fill(tmp, true); + data::fill((tmp | ((objects | objects.bbox(i)) | (pw::value(objects) == pw::cst(i))).domain()).rw(), false); + + typedef accu::math::count<mln_value(L)> accu_t; + mln_value(L) nlabels; + util::array<unsigned> counts + = labeling::blobs_and_compute(tmp, + c8(), nlabels, + accu_t()).second(); + unsigned nholes = 0; + for_all_components(j, counts) + if (counts(j) > 4u) + ++nholes; + + if (nholes < min_holes_count) + { + to_keep(i) = false; + to_remove = true; + } + } + + object_image(L) output; + if (! to_remove) + output = objects; + else + output = internal::compute(objects, to_keep); + + trace::exiting("scribo::filter::objects_with_holes"); + return output; + } + +# endif // ! MLN_INCLUDE_ONLY + + } // end of namespace scribo::filter + +} // end of namespace scribo + + +#endif // ! SCRIBO_FILTER_OBJECTS_WITH_HOLES_HH -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-35-gdb3dc85 scribo/draw/bounding_boxes.hh: Do not draw box centers anymore.
by Guillaume Lazzara
--- scribo/ChangeLog | 4 ++++ scribo/draw/bounding_boxes.hh | 9 +++------ 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/scribo/ChangeLog b/scribo/ChangeLog index d35119e..bfde10a 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,5 +1,9 @@ 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + * scribo/draw/bounding_boxes.hh: Do not draw box centers anymore. + +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Add dedicated routines for AFP's use case. * scribo/src/afp/components.hh, diff --git a/scribo/draw/bounding_boxes.hh b/scribo/draw/bounding_boxes.hh index 2fe2cd3..0d4ab9b 100644 --- a/scribo/draw/bounding_boxes.hh +++ b/scribo/draw/bounding_boxes.hh @@ -28,7 +28,7 @@ /// \file /// -/// Draw a list of bounding boxes and their associated mass center. +/// Draw a list of bounding boxes # include <mln/core/concept/image.hh> # include <mln/draw/box.hh> @@ -45,7 +45,7 @@ namespace scribo using namespace mln; - /// Draw a list of bounding boxes and their associated mass center. + /// Draw a list of bounding boxes. template <typename I> void bounding_boxes(Image<I>& input_, @@ -53,7 +53,7 @@ namespace scribo const mln_value(I)& value); - /// Draw object bounding boxes and their associated mass center. + /// Draw object bounding boxes. template <typename I, typename L> void bounding_boxes(Image<I>& input_, @@ -79,10 +79,7 @@ namespace scribo for_all_components(i, boxes) if (boxes[i].is_valid()) - { - input(boxes[i].center()) = value; mln::draw::box(input, boxes[i], value); - } trace::exiting("scribo::draw::bounding_boxes"); } -- 1.5.6.5
14 years, 9 months
1
0
0
0
last-svn-commit-34-g7681799 Add dedicated routines for AFP's use case.
by Guillaume Lazzara
* scribo/src/afp/components.hh, * scribo/src/afp/link.hh, * scribo/src/afp/regroup.hh: New. --- scribo/ChangeLog | 8 ++ scribo/src/afp/components.hh | 255 ++++++++++++++++++++++++++++++++++++++++++ scribo/src/afp/link.hh | 138 +++++++++++++++++++++++ scribo/src/afp/regroup.hh | 84 ++++++++++++++ 4 files changed, 485 insertions(+), 0 deletions(-) create mode 100644 scribo/src/afp/components.hh create mode 100644 scribo/src/afp/link.hh create mode 100644 scribo/src/afp/regroup.hh diff --git a/scribo/ChangeLog b/scribo/ChangeLog index f7a0e58..d35119e 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,5 +1,13 @@ 2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Add dedicated routines for AFP's use case. + + * scribo/src/afp/components.hh, + * scribo/src/afp/link.hh, + * scribo/src/afp/regroup.hh: New. + +2010-02-19 Guillaume Lazzara <z(a)lrde.epita.fr> + Add new tools in Scribo. * src/preprocessing/Makefile.am, diff --git a/scribo/src/afp/components.hh b/scribo/src/afp/components.hh new file mode 100644 index 0000000..7db8572 --- /dev/null +++ b/scribo/src/afp/components.hh @@ -0,0 +1,255 @@ +#include <mln/io/pbm/load.hh> +#include <mln/io/pgm/save.hh> + +#include <mln/extension/adjust.hh> +#include <mln/extension/fill.hh> +#include <mln/data/fill.hh> +#include <mln/accu/shape/bbox.hh> + +#include <mln/core/alias/neighb2d.hh> +#include <mln/core/image/dmorph/image_if.hh> +#include <mln/pw/value.hh> +#include <mln/debug/println.hh> + +#include <mln/util/timer.hh> +#include <mln/labeling/foreground.hh> +#include <mln/labeling/wrap.hh> +#include <mln/extension/fill.hh> +#include <mln/data/compare.hh> + + +namespace mln +{ + + template <typename I> + unsigned my_find_root(image2d<I>& data, unsigned x) + { + if (data.element(x).parent == x) + return x; + else + return data.element(x).parent = my_find_root(data, + data.element(x).parent); + } + + + + struct info + { + unsigned parent; + unsigned card; + float row_sum, col_sum; + point2d p_min, p_max; + + int width() const + { + return p_max.col() - p_min.col(); + } + + int height() const + { + return p_max.row() - p_min.row(); + } + + void init(unsigned p, int row, int col) + { + parent = p; + card = 1; + row_sum = row; + col_sum = col; + p_min.row() = row; + p_max.row() = row; + p_min.col() = col; + p_max.col() = col; + } + + void update(info& r) + { + r.parent = this->parent; + card += r.card; + row_sum += r.row_sum; + col_sum += r.col_sum; + + // bkd browsing => p is always higher (lower row) than r + mln_invariant(p_min.row() <= r.p_min.row()); + + if (r.p_min.col() < p_min.col()) + p_min.col() = r.p_min.col(); + if (r.p_max.row() > p_max.row()) + p_max.row() = r.p_max.row(); + if (r.p_max.col() > p_max.col()) + p_max.col() = r.p_max.col(); + } + }; + + + + template <typename V> + image2d<V> + extract_components(const image2d<bool>& input, + V& nlabels, + util::array<box2d>& bboxes, + util::array<point2d>& mass_centers) + { + typedef image2d<bool> I; + + neighb2d nbh = c8(); + const int + nrows = input.nrows(), + ncols = input.ncols(); + + bboxes.resize(1); + mass_centers.resize(1); + + image2d<info> data; + image2d<V> label; + V current_label = 0; + int N, dp_border; + +// util::timer time; +// time.start(); + + // init + { + extension::adjust(input, nbh); + N = input.nelements(); + dp_border = 2 * input.border(); + extension::fill(input, false); + initialize(data, input); + } + +// float t = time; +// std::cout << "init = " << t << std::endl; +// time.restart(); + + // 1st pass + { + util::array<int> dp = positive_offsets_wrt(input, nbh); + const unsigned n_nbhs = dp.nelements(); + + // Backward. + unsigned p = input.index_of_point(point2d(nrows - 1, ncols - 1)); + for (int row = nrows - 1; row >= 0; --row, p -= dp_border) + for (int col = ncols - 1; col >= 0; --col, --p) + { + if (! input.element(p)) + continue; + + data.element(p).init(p, row, col); // init + + for (unsigned i = 0; i < n_nbhs; ++i) + { + unsigned n = p + dp[i]; + if (! input.element(n)) + continue; + unsigned r = my_find_root(data, n); + if (r != p) + { + data.element(p).update( data.element(r) ); // update + } + } + } + } + +// t = time; +// std::cout << "1st pass = " << t << std::endl; +// time.restart(); + + // 2nd pass + { + initialize(label, input); + data::fill(label, 0); + + // Forward. + unsigned p = input.index_of_point(point2d(0, 0)); + for (int row = 0; row < nrows; ++row, p += dp_border) + for (int col = 0; col < ncols; ++col, ++p) + { + if (! input.element(p)) + continue; + const info& dta = data.element(p); + if (dta.parent == p) + { + if (dta.card > 5 + && (dta.width() >= 1 + && dta.height() >= 1)) + { + label.element(p) = ++current_label; + + bboxes.append(box2d(dta.p_min, dta.p_max)); + mass_centers.append(point2d(dta.row_sum / dta.card, + dta.col_sum / dta.card)); + } + } + else + label.element(p) = label.element(dta.parent); + } + } +// t = time; +// std::cout << "2nd pass = " << t << std::endl; + + nlabels = current_label; + return label; + } + + +} // mln + + + +// void usage(char* argv[]) +// { +// std::cerr << argv[0] << " input.pbm output.pgm" << std::endl; +// std::abort(); +// } + + +// int main(int argc, char* argv[]) +// { +// if (argc != 3) +// usage(argv); + +// using namespace mln; + +// image2d<bool> input; +// io::pbm::load(input, argv[1]); + + +// image2d<unsigned> ref; + +// // { +// // util::timer t; +// // t.start(); + +// // unsigned nlabels; +// // ref = labeling::foreground(input, c4(), nlabels); + +// // float ts = t.stop(); +// // std::cout << "tufa: " << ts << " " << nlabels << std::endl; +// // } + +// { +// util::timer t; +// t.start(); + + +// util::array<box2d> bboxes(1, box2d(1,1)); +// util::array<point2d> mass_centers(1, point2d(0,0)); + +// // util::array<std::pair<box2d, point2d> > data_out(1); +// unsigned nlabels; +// image2d<unsigned> comps = extract_components(input, nlabels, bboxes, mass_centers); + +// float ts = t.stop(); +// std::cout << ts << " " << nlabels << std::endl; + +// // std::cout << bboxes << std::endl; +// // std::cout << mass_centers << std::endl; + +// // if (comps != ref) +// // std::cout << "diff" << std::endl; + +// io::pgm::save(labeling::wrap(value::int_u8(), comps), +// argv[2]); +// } + +// } diff --git a/scribo/src/afp/link.hh b/scribo/src/afp/link.hh new file mode 100644 index 0000000..b899957 --- /dev/null +++ b/scribo/src/afp/link.hh @@ -0,0 +1,138 @@ +#include <mln/geom/ncols.hh> +#include <mln/geom/nrows.hh> +#include <mln/util/couple.hh> +#include <scribo/core/object_image.hh> +#include <scribo/core/macros.hh> +#include <scribo/primitive/internal/init_link_array.hh> + +namespace scribo +{ + + namespace primitive + { + + namespace link + { + + + template <typename L> + util::couple<object_links<L>, object_links<L> > + left_right(const object_image(L)& objects) + { + object_links<L> + right(objects, static_cast<unsigned>(objects.nlabels()) + 1); + primitive::internal::init_link_array(right); + + object_links<L> + left(objects, static_cast<unsigned>(objects.nlabels()) + 1); + primitive::internal::init_link_array(left); + + for_all_components(i, objects.bboxes()) + { + float + w = (objects.bbox(i).pmax().col() + - objects.bbox(i).pmin().col()), + h = (objects.bbox(i).pmax().row() + - objects.bbox(i).pmin().row()); + unsigned dmax = (w / 2.0f) + (3 * math::max(w, h)); + + + const mln_site(L) c = objects.mass_center(i); + + int + midcol = (objects.bbox(i).pmax().col() + - objects.bbox(i).pmin().col()) / 2; + int + nrightima = geom::ncols(objects) - c.col(), + nleftima = c.col(), + nright = std::min(static_cast<unsigned>(nrightima), midcol + dmax), + nleft = std::min(static_cast<unsigned>(nleftima), midcol + dmax); + + // Right + { + const mln_value(L) + *p = &objects(c), + *pstop = p + nright + 1; + + for (; p != pstop; ++p) + { + if (*p != literal::zero // Not the background + && *p != i // Not the current component + && right[*p] != i) // No loops + { + right[i] = *p; + break; + } + } + } + + + // Left + { + const mln_value(L) + *p = &objects(c), + *pstop = p - nleft - 1; + + for (; p != pstop; --p) + { + if (*p != literal::zero // Not the background + && *p != i // Not the current component + && left[*p] != i) // No loops + { + left[i] = *p; + break; + } + } + } + } + + return mln::make::couple(left, right); + } + + + template <typename L> + object_links<L> + left(const object_image(L)& objects, unsigned dmax) + { + object_links<L> + left(objects, static_cast<unsigned>(objects.nlabels()) + 1); + primitive::internal::init_link_array(left); + + for_all_components(i, objects.bboxes()) + { + const mln_site(L) c = objects.mass_center(i); + + int + midcol = (objects.bbox(i).pmax().col() + - objects.bbox(i).pmin().col()) / 2; + int + nleftima = c.col(), + nleft = std::min(static_cast<unsigned>(nleftima), midcol + dmax); + + // Left + { + const mln_value(L) + *p = &objects(c), + *pstop = p - nleft - 1; + + for (; p != pstop; --p) + { + if (*p != literal::zero // Not the background + && *p != i // Not the current component + && left[*p] != i) // No loops + { + left[i] = *p; + break; + } + } + } + } + + return left; + } + + } // end of namespace scribo::primitive::link + + } // end of namespace scribo::primitive + +} // end of namespace scribo diff --git a/scribo/src/afp/regroup.hh b/scribo/src/afp/regroup.hh new file mode 100644 index 0000000..c24880b --- /dev/null +++ b/scribo/src/afp/regroup.hh @@ -0,0 +1,84 @@ +#include <mln/geom/ncols.hh> +#include <mln/geom/nrows.hh> +#include <mln/util/couple.hh> +#include <scribo/core/object_image.hh> +#include <scribo/core/macros.hh> +#include <scribo/primitive/internal/init_link_array.hh> + +namespace scribo +{ + + namespace primitive + { + + namespace group + { + + template <typename L> + object_groups<L> + regroup_left(const object_image(L)& objects, + const object_groups<L>& groups, + unsigned dmax) + { + trace::entering("scribo::primitive::group::regroup_left"); + + mln_precondition(groups.is_valid()); + + object_groups<L> + new_groups(objects, static_cast<unsigned>(objects.nlabels()) + 1, 0); + + unsigned ngroups = 0; + for_all_components(i, objects.bboxes()) + { + if (groups[i] == 0) + continue; + + // We MUST set a group id here since the most left group + // component won't have any id otherwise. + if (new_groups[i] == 0) + new_groups[i] = ++ngroups; + + const mln_site(L) c = objects.mass_center(i); + + int + midcol = (objects.bbox(i).pmax().col() + - objects.bbox(i).pmin().col()) / 2; + int + nleftima = geom::ncols(objects), + nleft = std::min(static_cast<unsigned>(nleftima), midcol + dmax); + + // Left + { + const mln_value(L) + *p = &objects(c), + *pstop = p - nleft - 1; + + for (; p != pstop; --p) + { + if (*p != literal::zero // Not the background + && *p != i // Not the current component +// && new_groups[*p] != ngroups + && groups[*p] != 0) + { + if (new_groups[*p] == 0) + new_groups[*p] = ngroups; + else + { + new_groups[i] = new_groups[*p]; + --ngroups; + } + + break; + } + } + } + } + + return new_groups; + } + + } // end of namespace scribo::primitive::group + + } // end of namespace scribo::primitive + +} // end of namespace scribo -- 1.5.6.5
14 years, 9 months
1
0
0
0
← Newer
1
...
18
19
20
21
22
23
24
...
28
Older →
Jump to page:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
Results per page:
10
25
50
100
200