Olena-patches
Threads by month
- ----- 2025 -----
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 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
- 9625 discussions
URL: https://svn.lrde.epita.fr/svn/oln/trunk/milena/sandbox
ChangeLog:
2009-03-11 Fabien Freling <fabien.freling(a)lrde.epita.fr>
Create watershed images in 3D..
* fabien/bin/dump2pgm8b.cc: Fix.
* fabien/igr/Makefile: Update.
* fabien/igr/nbasins_check.sh: New test file.
* fabien/igr/nbasins_finder.cc: New file for finding optimal parameters.
* fabien/igr/watershed3d.cc: Update.
---
TODO | 4 +-
bin/dump2pgm8b.cc | 5 ---
igr/Makefile | 5 ++-
igr/nbasins_check.sh | 17 ++++++++++
igr/nbasins_finder.cc | 80 ++++++++++++++++++++++++++++++++++++++++++++++++++
igr/watershed3d.cc | 1
6 files changed, 105 insertions(+), 7 deletions(-)
Index: trunk/milena/sandbox/fabien/igr/watershed3d.cc
===================================================================
--- trunk/milena/sandbox/fabien/igr/watershed3d.cc (revision 3511)
+++ trunk/milena/sandbox/fabien/igr/watershed3d.cc (revision 3512)
@@ -277,6 +277,7 @@
// Watershed
label_32 nbasins;
image3d<label_32> wshed = morpho::meyer_wst(clo, c6(), nbasins);
+ std::cout << "nbasins = " << nbasins << std::endl;
// Debug
io::dump::save(level::stretch(int_u8(), clo), "wsd_02.dump");
Index: trunk/milena/sandbox/fabien/igr/nbasins_check.sh
===================================================================
--- trunk/milena/sandbox/fabien/igr/nbasins_check.sh (revision 0)
+++ trunk/milena/sandbox/fabien/igr/nbasins_check.sh (revision 3512)
@@ -0,0 +1,17 @@
+#!/bin/zsh
+
+process_file ()
+{
+ echo "Processing $2..."
+
+ for lambda_closure in 500 1000 5000 10000 50000; do
+ echo " for lambda_closure = ${lambda_closure}";
+ ./nbasins_finder $1 $lambda_closure
+ ../bin/dump2ppm result_nbasins.dump results/nbasins_${2}_${lambda_closure}.ppm
+ done
+}
+
+#make nbasins
+#process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0052.dcm" "52"
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0061.dcm" "61"
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0064.dcm" "64"
Property changes on: trunk/milena/sandbox/fabien/igr/nbasins_check.sh
___________________________________________________________________
Name: svn:executable
+ *
Index: trunk/milena/sandbox/fabien/igr/nbasins_finder.cc
===================================================================
--- trunk/milena/sandbox/fabien/igr/nbasins_finder.cc (revision 0)
+++ trunk/milena/sandbox/fabien/igr/nbasins_finder.cc (revision 3512)
@@ -0,0 +1,80 @@
+#include <iostream>
+#include <mln/core/image/image3d.hh>
+
+#include <mln/core/alias/neighb3d.hh>
+#include <mln/core/alias/window3d.hh>
+#include <mln/core/image/image_if.hh>
+
+#include <mln/io/pgm/load.hh>
+#include <mln/io/dicom/load.hh>
+#include <mln/io/pgm/save.hh>
+#include <mln/io/dump/save.hh>
+
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u12.hh>
+#include <mln/value/label_16.hh>
+#include <mln/value/label_32.hh>
+#include <mln/value/rgb8.hh>
+
+#include <mln/labeling/regional_minima.hh>
+
+#include <mln/level/transform.hh>
+#include <mln/level/stretch.hh>
+
+#include <mln/morpho/elementary/gradient.hh>
+#include <mln/morpho/closing/volume.hh>
+#include <mln/morpho/watershed/flooding.hh>
+
+#include <mln/fun/l2l/wrap.hh>
+
+#include <mln/debug/colorize.hh>
+
+
+
+///////////////////
+// //
+// Main Function //
+// //
+///////////////////
+
+
+int main(int argc, char *argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+ using value::int_u12;
+ using value::label_16;
+ using value::label_32;
+ using value::rgb8;
+
+ if (argc != 3)
+ {
+ std::cout << "Usage: " << argv[0] << " <ima.dcm> <closure_lambda>"
+ << std::endl;
+ return 1;
+ }
+
+ unsigned closure_lambda = atoi(argv[2]);
+
+ image3d<int_u12> dcm;
+ io::dicom::load(dcm, argv[1]);
+
+ // Gradient
+ image3d<int_u12> grad = morpho::elementary::gradient(dcm, c6());
+
+ // Closure
+ image3d<int_u12> clo = morpho::closing::volume(grad, c6(), closure_lambda);
+
+ // Watershed
+ label_32 nbasins;
+ image3d<label_32> wshed = morpho::watershed::flooding(clo, c6(), nbasins);
+ //image3d<label_32> wshed = morpho::watershed::flooding(clo, c6(), nbasins);
+
+ // Visualization
+ std::cout << " nbasins = " << nbasins << std::endl;
+ //io::dump::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "result_nbasins.dump");
+ //io::dump::save(level::stretch(int_u8(), wshed), "result_nbasins.dump");
+ io::dump::save(debug::colorize(rgb8(), wshed, nbasins), "result_nbasins.dump");
+
+ return 0;
+}
Index: trunk/milena/sandbox/fabien/igr/Makefile
===================================================================
--- trunk/milena/sandbox/fabien/igr/Makefile (revision 3511)
+++ trunk/milena/sandbox/fabien/igr/Makefile (revision 3512)
@@ -23,7 +23,10 @@
g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} $^ -o wsd3d
wsd3dg: watershed.hh watershed3d.cc
- g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} -DNDEBUG -g $^ -o wsd3dg
+ g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} -g $^ -o wsd3dg
+
+nbasins: nbasins_finder.cc
+ g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} $^ -o nbasins_finder
clean:
rm -rf *.dump *.p?m *.plot *.log *.csv
Index: trunk/milena/sandbox/fabien/TODO
===================================================================
--- trunk/milena/sandbox/fabien/TODO (revision 3511)
+++ trunk/milena/sandbox/fabien/TODO (revision 3512)
@@ -25,4 +25,6 @@
[X] US: projection of internal gradient
[X] Create 3D US morpho with 2D stack
[ ] Create macro for_all_slice
-[ ] Batch process watershed with 2D, 3D and any combination of parameters
+[X] Batch process watershed with 2D, 3D and any combination of parameters
+[ ] Cut into small tools
+[ ] Test 3D workflow on 2D images
Index: trunk/milena/sandbox/fabien/bin/dump2pgm8b.cc
===================================================================
--- trunk/milena/sandbox/fabien/bin/dump2pgm8b.cc (revision 3511)
+++ trunk/milena/sandbox/fabien/bin/dump2pgm8b.cc (revision 3512)
@@ -3,12 +3,9 @@
#include <mln/debug/slices_2d.hh>
#include <mln/value/int_u8.hh>
-#include <mln/value/int_u12.hh>
#include <mln/io/dump/load.hh>
#include <mln/io/pgm/save.hh>
-#include <mln/literal/colors.hh>
-
int usage(char* argv[])
{
@@ -21,7 +18,6 @@
int main(int argc, char* argv[])
{
using namespace mln;
- using value::rgb8;
using value::int_u8;
if (argc != 3)
@@ -30,7 +26,6 @@
image3d<int_u8> vol;
io::dump::load(vol, argv[1]);
- rgb8 bg = literal::black;
image2d<int_u8> ima = debug::slices_2d(vol, 1.f, 0);
io::pgm::save(ima, argv[2]);
1
0
https://svn.lrde.epita.fr/svn/oln/trunk/milena
Index: ChangeLog
from Thierry Geraud <thierry.geraud(a)lrde.epita.fr>
Fix missing update in labeling extrema.
* mln/labeling/regional_minima.hh,
* mln/labeling/regional_maxima.hh: Fix missing update.
regional_maxima.hh | 6 +++---
regional_minima.hh | 6 +++---
2 files changed, 6 insertions(+), 6 deletions(-)
Index: mln/labeling/regional_minima.hh
--- mln/labeling/regional_minima.hh (revision 3510)
+++ mln/labeling/regional_minima.hh (working copy)
@@ -1,5 +1,5 @@
-// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
-// (LRDE)
+// Copyright (C) 2007, 2008, 2009 EPITA Research and Development
+// Laboratory (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -154,7 +154,7 @@
typedef impl::regional_minima_functor<I> F;
F f(exact(input));
mln_ch_value(I, L) output = canvas::labeling_sorted(input, nbh, nlabels,
- f, true);
+ f, false);
trace::exiting("labeling::regional_minima");
return output;
Index: mln/labeling/regional_maxima.hh
--- mln/labeling/regional_maxima.hh (revision 3510)
+++ mln/labeling/regional_maxima.hh (working copy)
@@ -1,5 +1,5 @@
-// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
-// (LRDE)
+// Copyright (C) 2007, 2008, 2009 EPITA Research and Development
+// Laboratory (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -141,7 +141,7 @@
typedef impl::regional_maxima_functor<I> F;
F f(exact(input));
mln_ch_value(I, L) output = canvas::labeling_sorted(input, nbh, nlabels,
- f, false);
+ f, true);
trace::exiting("labeling::regional_maxima");
return output;
1
0
URL: https://svn.lrde.epita.fr/svn/oln/trunk/milena/sandbox
ChangeLog:
2009-03-11 Fabien Freling <fabien.freling(a)lrde.epita.fr>
Bug in 3D watershed.
* fabien/igr/Makefile: Update with debug build.
* fabien/igr/check3d_wsd.sh: Update.
* fabien/igr/watershed3d.cc: Update.
---
Makefile | 3 +++
check3d_wsd.sh | 1 +
watershed3d.cc | 43 ++++++++++++++++++++++++++-----------------
3 files changed, 30 insertions(+), 17 deletions(-)
Index: trunk/milena/sandbox/fabien/igr/watershed3d.cc
===================================================================
--- trunk/milena/sandbox/fabien/igr/watershed3d.cc (revision 3509)
+++ trunk/milena/sandbox/fabien/igr/watershed3d.cc (revision 3510)
@@ -19,6 +19,7 @@
#include <mln/value/int_u8.hh>
#include <mln/value/int_u12.hh>
#include <mln/value/label_16.hh>
+#include <mln/value/label_32.hh>
#include <mln/level/transform.hh>
#include <mln/level/stretch.hh>
@@ -29,14 +30,14 @@
#include <mln/make/graph.hh>
-#include <mln/morpho/gradient.hh>
-#include <mln/morpho/closing/area.hh>
+#include <mln/morpho/elementary/dilation.hh>
+#include <mln/morpho/elementary/gradient.hh>
+#include <mln/morpho/closing/volume.hh>
#include <mln/morpho/meyer_wst.hh>
#include <mln/fun/l2l/wrap.hh>
#include <mln/core/var.hh>
-#include <mln/morpho/elementary/dilation.hh>
#include <mln/core/routine/extend.hh>
@@ -247,6 +248,7 @@
using value::int_u12;
using value::rgb8;
using value::label_16;
+ using value::label_32;
if (argc < 4)
{
@@ -262,32 +264,39 @@
image3d<int_u12> dcm;
io::dicom::load(dcm, argv[1]);
+ // Debug
+ assert(mln_max(label_32) == 4294967295);
io::dump::save(level::stretch(int_u8(), dcm), "wsd_01_src.dump");
- image3d<int_u12> grad = morpho::gradient(dcm, win_c4p_3d());
- image3d<int_u12> clo = morpho::closing::area(grad, c6(), closure_lambda);
+ // Gradient
+ image3d<int_u12> grad = morpho::elementary::gradient(dcm, c6());
- label_16 nbasins;
- image3d<label_16> wshed = morpho::meyer_wst(clo, c6(), nbasins);
+ // Closure
+ image3d<int_u12> clo = morpho::closing::volume(grad, c6(), closure_lambda);
+ // Watershed
+ label_32 nbasins;
+ image3d<label_32> wshed = morpho::meyer_wst(clo, c6(), nbasins);
+
+ // Debug
io::dump::save(level::stretch(int_u8(), clo), "wsd_02.dump");
io::dump::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_03.dump");
- mln_VAR(vol2_, morpho::elementary::dilation(extend(wshed | (pw::value(wshed) == 0u), wshed), c26()));
-
- data::fill((wshed | (pw::value(wshed) == 0u)).rw(), vol2_);
+ //mln_VAR(vol2_, morpho::elementary::dilation(extend(wshed | (pw::value(wshed) == 0u), wshed), c26()));
+ //data::fill((wshed | (pw::value(wshed) == 0u)).rw(), vol2_);
io::dump::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_04.dump");
- /// Build graph
- util::graph g = make::graph(wshed, c6(), nbasins);
+ /// Graph
+ trace::quiet = false;
+ util::graph g = make::region_adjacency_graph(wshed, c6(), nbasins);
// Build graph images and compute distance values with a RGB image.
- mln_VAR(ima_v, make_vertex_graph_image(g, dcm, wshed, nbasins));
+ /*mln_VAR(ima_v, make_vertex_graph_image(g, dcm, wshed, nbasins));
mln_VAR(ima_e, make_edge_graph_image(ima_v, g));
/// Try to merge vertices.
mln_piter_(ima_e_t) e(ima_e.domain());
- util::array<label_16> parent(g.v_nmax());
+ util::array<label_32> parent(g.v_nmax());
for (unsigned i = 0; i < parent.nelements(); ++i)
parent[i] = i;
@@ -299,7 +308,7 @@
parent[find_root(parent, v1)] = find_root(parent, v2);
}
- fun::i2v::array<label_16> f(parent.nelements());
+ fun::i2v::array<label_32> f(parent.nelements());
std::vector<unsigned> new_label(parent.nelements(), 0);
unsigned nbasins2 = 0;
for (unsigned i = 0; i < parent.nelements(); ++i)
@@ -312,7 +321,7 @@
}
mln_invariant(f(0) == 0u);
--nbasins2; // nbasins2 does not count the basin with label 0.
- image3d<label_16> wsd2 = level::transform(wshed, f);
+ image3d<label_32> wsd2 = level::transform(wshed, f);
io::dump::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_05.dump");
@@ -330,5 +339,5 @@
io::dump::save(level::transform(labeling::mean_values(dcm, wsd2, nbasins2), fun::l2l::wrap<int_u8>()), "wsd_06_mean_colors.dump");
//io::dump::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 4095)), "wsd_07_graph_image2_white.dump");
//io::dump::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 0)), "wsd_08_graph_image2_black.dump");
- io::dump::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_99_result.dump");
+ io::dump::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_99_result.dump");*/
}
Index: trunk/milena/sandbox/fabien/igr/check3d_wsd.sh
===================================================================
--- trunk/milena/sandbox/fabien/igr/check3d_wsd.sh (revision 3509)
+++ trunk/milena/sandbox/fabien/igr/check3d_wsd.sh (revision 3510)
@@ -29,6 +29,7 @@
done
}
+make wsd3d
process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0052.dcm" "52"
process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0061.dcm" "61"
process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0064.dcm" "64"
Index: trunk/milena/sandbox/fabien/igr/Makefile
===================================================================
--- trunk/milena/sandbox/fabien/igr/Makefile (revision 3509)
+++ trunk/milena/sandbox/fabien/igr/Makefile (revision 3510)
@@ -22,5 +22,8 @@
wsd3d: watershed.hh watershed3d.cc
g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} $^ -o wsd3d
+wsd3dg: watershed.hh watershed3d.cc
+ g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} -DNDEBUG -g $^ -o wsd3dg
+
clean:
rm -rf *.dump *.p?m *.plot *.log *.csv
1
0
URL: https://svn.lrde.epita.fr/svn/oln/trunk/milena
ChangeLog:
2009-03-10 Edwin Carlinet <carlinet(a)lrde.epita.fr>
Fix bug in leaf propagation.
* mln/morpho/tree/data.hh: Fix leaves calculus.
* sandbox/edwin/tree/propagate.hh: Fix bugs in propagations.
* sandbox/edwin/tree/tree.cc: Test file.
---
mln/morpho/tree/data.hh | 27 +++++++++++-----
sandbox/edwin/tree/propagate.hh | 17 +++++-----
sandbox/edwin/tree/tree.cc | 66 +++++++++++++++++++++++++++++-----------
3 files changed, 77 insertions(+), 33 deletions(-)
Index: trunk/milena/mln/morpho/tree/data.hh
===================================================================
--- trunk/milena/mln/morpho/tree/data.hh (revision 3508)
+++ trunk/milena/mln/morpho/tree/data.hh (revision 3509)
@@ -41,6 +41,7 @@
# include <mln/core/image/sub_image.hh>
# include <mln/core/site_set/p_array.hh>
# include <mln/core/site_set/p_set.hh>
+# include <mln/data/fill.hh>
namespace mln
{
@@ -140,11 +141,12 @@
/// \}
- /// \{ Leaves-related materials.
- typedef p_array<mln_psite(I)> leaves_t;
+ /// \{ Nodes-related materials.
+
+ typedef p_set<mln_psite(I)> leaves_t;
- const p_set<mln_psite(I)>& leaves() const
+ const leaves_t& leaves() const
{
mln_precondition(is_valid());
return leaves_;
@@ -185,8 +187,8 @@
const I& f_;
const S& s_;
mln_ch_value(I, mln_psite(I)) parent_;
+ leaves_t leaves_;
p_array<mln_psite(I)> nodes_;
- p_set<mln_psite(I)> leaves_;
unsigned nroots_;
};
@@ -210,14 +212,11 @@
// Store tree nodes.
nroots_ = 0;
mln_bkd_piter(S) p(s_);
- mln_psite(I) old;
for_all(p)
{
if (f_(parent_(p)) != f_(p))
{
nodes_.insert(p);
- if (parent_(p) != old)
- leaves_.insert(old);
}
else
if (parent_(p) == p)
@@ -225,7 +224,19 @@
nodes_.insert(p);
++nroots_;
}
- old = p;
+ }
+
+ // Store leaves.
+ mln_ch_value(I, bool) deja_vu;
+ initialize(deja_vu, f);
+ mln::data::fill(deja_vu, false);
+
+ mln_fwd_piter(nodes_t) n(nodes_);
+ for_all(n)
+ {
+ deja_vu(parent_(n)) = true;
+ if (!deja_vu(n))
+ leaves_.insert(n);
}
}
Index: trunk/milena/sandbox/edwin/tree/propagate.hh
===================================================================
--- trunk/milena/sandbox/edwin/tree/propagate.hh (revision 3508)
+++ trunk/milena/sandbox/edwin/tree/propagate.hh (revision 3509)
@@ -43,8 +43,9 @@
/// non-representative points of the same node.
template <typename T, typename A>
void
- propagate_to_node(const T& t, A& a)
+ propagate_representant(const T& t, Image<A>& a_)
{
+ A a = exact(a_);
mln_fwd_piter(T) p(t.domain());
for_all(p)
if (! t.is_a_node(p))
@@ -54,6 +55,8 @@
}
}
+ namespace binary {
+
/// Propagate a tagged node's value to its subbranches.
template <typename T, typename A>
void
@@ -62,7 +65,6 @@
mln_bkd_piter(T::nodes_t) n(t.nodes());
for_all(n)
{
- mln_assertion(t.is_a_node(n));
if (a(t.parent(n)))
{
mln_assertion(t.is_a_node(t.parent(n)));
@@ -80,7 +82,6 @@
mln_fwd_piter(T::nodes_t) n(t.nodes());
for_all(n)
{
- mln_assertion(t.is_a_node(n));
if (a(t.parent(n)))
{
mln_assertion(t.is_a_node(t.parent(n)));
@@ -97,7 +98,6 @@
mln_fwd_piter(T::nodes_t) n(t.nodes());
for_all(n)
{
- mln_assertion(t.is_a_node(n));
if (a(n))
{
mln_assertion(t.is_a_node(t.parent(n)));
@@ -109,7 +109,7 @@
/// Propagate a tagged node's value to its direct parents.
template <typename T, typename A>
void
- propagate_to_parents(const T& t, A& a)
+ propagate_to_parent(const T& t, A& a)
{
mln_bkd_piter(T::nodes_t) n(t.nodes());
for_all(n)
@@ -131,16 +131,17 @@
/// n <== l and a(l) is true.
/// TODO: post-condition which checks this property.
+
template <typename T, typename A>
void
propagate_leaf_to_ancestors(const T& t, A& a)
{
- // 1st pass: leaves' parents are set to false.
+
mln_fwd_piter(T::leaves_t) l(t.leaves());
for_all(l)
- t.parent(l) = 0;
+ a(t.parent(l)) = 0;
+
- // 2nd pass
mln_fwd_piter(T::nodes_t) n(t.nodes());
for_all(n)
{
Index: trunk/milena/sandbox/edwin/tree/tree.cc
===================================================================
--- trunk/milena/sandbox/edwin/tree/tree.cc (revision 3508)
+++ trunk/milena/sandbox/edwin/tree/tree.cc (revision 3509)
@@ -77,14 +77,18 @@
{
mln_VAR(a, morpho::tree::compute_attribute_image(a_, tree_));
- display_tree_attributes(tree_, a);
- find_treshold(a, tree_);
+ //display_tree_attributes(tree_, a);
+ //find_treshold(a, tree_);
+
+ mln_fwd_piter(tree_t::nodes_t) n(tree_.nodes());
+ for_all(n)
+ assert(tree_.is_a_leaf(tree_.parent(n)) == false);
img_ = duplicate((pw::cst(lambda1) < pw::value(a) &&
pw::value(a) < pw::cst(lambda2))
| a.domain());
- debug::println("attribut", a);
+ //debug::println("attribut", a);
}
template <typename I, typename T>
@@ -151,12 +155,12 @@
// Debug.
- {
- std::cout << " - " << val << ":" << pset.nsites() << " {";
- for_all(p)
- std::cout << p << ",";
- std::cout << "}" << std::endl;
- }
+// {
+// std::cout << " - " << val << ":" << pset.nsites() << " {";
+// for_all(p)
+// std::cout << p << ",";
+// std::cout << "}" << std::endl;
+// }
}
for (unsigned i = 0; i < f_domain.size() - 1; i++)
@@ -213,8 +217,9 @@
void usage(char* argv[])
{
- std::cerr << "usage: " << argv[0] << " input.pgm accumulator lambda1 [lambda2]"
- << std::endl;
+ std::cerr << "usage: " << argv[0] << " input.pgm accumulator propagation lambda1 [lambda2]"
+ << "\taccu:\tcard | sharpness" << std::endl
+ << "\tpropa:\tto_children | to_childhood | to_parent | to_ancestors | leaf_to_ancestors" << std::endl;
abort();
}
@@ -228,17 +233,29 @@
float lambda1;
float lambda2;
- I input;
+
if (argc < 4)
usage(argv);
+ I input;
io::pgm::load(input, argv[1]);
+// int_u8 vals[] = { 0, 1, 0, 2, 0, 1, 0,
+// 1, 1, 1, 2, 1, 1, 1,
+// 0, 1, 0, 2, 0, 1, 0,
+// 2, 2, 2, 2, 2, 2, 2,
+// 1, 1, 1, 2, 0, 1, 0,
+// 1, 1, 1, 2, 1, 1, 1,
+// 1, 1, 1, 2, 0, 1, 0};
+// I input = make::image2d(vals);
- lambda1 = atof(argv[3]);
- lambda2 = (argc == 5) ? atof(argv[4]) : mln_max(float);
+
+
+ lambda1 = atof(argv[4]);
+ lambda2 = (argc == 6) ? atof(argv[5]) : mln_max(float);
std::string s(argv[2]);
+ std::string propa(argv[3]);
treefilter<I>* f = 0;
if (s == "card")
f = new treefilter<I>(input, morpho::attribute::card<I>(), lambda1, lambda2);
@@ -249,11 +266,26 @@
std::cout << "s1" << std::endl;
- propagate_to_childhood(f->tree(), f->img());
+ if (propa == "to_childhood")
+ morpho::tree::propagate_to_childhood(f->tree(), f->img());
+ else if (propa == "to_children")
+ morpho::tree::propagate_to_children(f->tree(), f->img());
+ else if (propa == "to_ancestors")
+ morpho::tree::propagate_to_ancestors(f->tree(), f->img());
+ else if (propa == "to_parent")
+ morpho::tree::propagate_to_parent(f->tree(), f->img());
+ else if (propa == "leaf_to_ancestors")
+ morpho::tree::propagate_leaf_to_ancestors(f->tree(), f->img());
+ else
+ usage(argv);
+
std::cout << "s2" << std::endl;
- propagate_to_node(f->tree(), f->img());
+ morpho::tree::propagate_to_node(f->tree(), f->img());
std::cout << "s3" << std::endl;
- filtercheck(*f, accu::meta::count());
+
+
+
+ //filtercheck(*f, accu::meta::count());
io::pbm::save(f->img(), "out.pbm");
1
0
10 Mar '09
* mln/io/dump/load.hh,
* mln/io/dump/save.hh:
- Add new information in the header.
- Add more assertion on value type, dimension and file type.
Important note: Old dump files are not compatible with this new
format.
* mln/trait/value_.hh: add a new macro mln_trait_value_name.
* mln/value/builtin/floatings.hh
* mln/value/builtin/integers.hh
* mln/value/builtin/symbolics.hh
* mln/value/int_s.hh
* mln/value/int_u.hh
* mln/value/label.hh
* mln/value/rgb.hh: add name() member to value_<> specialization.
It returns the type name as a const char*.
* tests/io/dump/dump.cc: add new tests with builtin types.
---
milena/ChangeLog | 25 ++++++++++++
milena/mln/io/dump/load.hh | 70 +++++++++++++++++++++++++++++---
milena/mln/io/dump/save.hh | 26 ++++++++++++-
milena/mln/trait/value_.hh | 3 +-
milena/mln/value/builtin/floatings.hh | 10 ++++-
milena/mln/value/builtin/integers.hh | 65 ++++++++++++++++++++++++++----
milena/mln/value/builtin/symbolics.hh | 15 ++++---
milena/mln/value/int_s.hh | 9 ++++-
milena/mln/value/int_u.hh | 9 ++++-
milena/mln/value/label.hh | 7 +++
milena/mln/value/rgb.hh | 7 +++
milena/tests/io/dump/dump.cc | 28 +++++++++++++-
12 files changed, 246 insertions(+), 28 deletions(-)
diff --git a/milena/ChangeLog b/milena/ChangeLog
index 199bdd1..bd6d99c 100644
--- a/milena/ChangeLog
+++ b/milena/ChangeLog
@@ -1,5 +1,30 @@
2009-03-10 Guillaume Lazzara <lazzara(a)lrde.epita.fr>
+ Make io::dump::* more robust and improve dump format.
+
+ * mln/io/dump/load.hh,
+ * mln/io/dump/save.hh:
+ - Add new information in the header.
+ - Add more assertion on value type, dimension and file type.
+
+ Important note: Old dump files are not compatible with this new
+ format.
+
+ * mln/trait/value_.hh: add a new macro mln_trait_value_name.
+
+ * mln/value/builtin/floatings.hh
+ * mln/value/builtin/integers.hh
+ * mln/value/builtin/symbolics.hh
+ * mln/value/int_s.hh
+ * mln/value/int_u.hh
+ * mln/value/label.hh
+ * mln/value/rgb.hh: add name() member to value_<> specialization.
+ It returns the type name as a const char*.
+
+ * tests/io/dump/dump.cc: add new tests with builtin types.
+
+2009-03-10 Guillaume Lazzara <lazzara(a)lrde.epita.fr>
+
Various small fixes.
* headers.mk: update dist header list.
diff --git a/milena/mln/io/dump/load.hh b/milena/mln/io/dump/load.hh
index bc6a051..88f60a2 100644
--- a/milena/mln/io/dump/load.hh
+++ b/milena/mln/io/dump/load.hh
@@ -73,20 +73,74 @@ namespace mln
}
- template <typename I>
+ template <typename I>
inline
- void load_header(Image<I>& ima, std::ifstream& file)
+ void load_header(Image<I>& ima, std::ifstream& file,
+ const std::string& filename)
{
+ // Milena's file type ?
+ std::string file_type;
+ file >> file_type;
+ if (file_type != "milena/dump")
+ {
+ std::cerr << "io::dump::load - Error: invalid file type. '"
+ << filename
+ << "' is NOT a valid milena/dump file!"
+ << std::endl;
+ abort();
+ }
+
+ // Dimension ?
unsigned dim;
file >> dim;
-
typedef mln_site(I) P;
- mln_assertion(P::dim == dim);
+ if (P::dim != dim)
+ {
+ std::cerr << "io::dump::load - Error: invalid image dimension. '"
+ << filename << "' is a " << dim << "-D image "
+ << "but you try to load it into a " << P::dim
+ << "-D image!"
+ << std::endl;
+ abort();
+ }
- P pmin, pmax;
+ // Size information - Skip it, useless.
+ std::string tmp;
+ for (unsigned i = 0; i < dim; ++i)
+ file >> tmp;
+ // Skipping endline.
+ char c;
+ file.get(c);
+
+ // Value type name ?
+ // WARNING: value type name limited to 255 characters...
+ char value_type[255];
+ file.getline(value_type, 255);
+ if (mln_trait_value_name(mln_value(I)) != std::string(value_type))
+ {
+ std::cerr << "io::dump::load - Error: invalid image value type. '"
+ << filename << "' is an image of '" << value_type
+ << "' but you try to load it into an image of '"
+ << mln_trait_value_name(mln_value(I)) << "'!"
+ << std::endl;
+ abort();
+ }
+
+ // Empty line - may be used for a new information.
+ file.get(c);
+
+ // Empty line - may be used for a new information.
+ file.get(c);
+
+ // Pmin
+ P pmin;
read_point<P>(file, pmin);
+
+ // Pmax
+ P pmax;
read_point<P>(file, pmax);
+ // Initialize the image buffer.
mln_concrete(I) result(box<P>(pmin, pmax));
initialize(ima, result);
mln_assertion(exact(ima).is_valid());
@@ -123,11 +177,13 @@ namespace mln
std::ifstream file(filename.c_str());
if (! file)
{
- std::cerr << "error: cannot open file '" << filename << "'!";
+ std::cerr << "io::dump::load - Error: cannot open file '"
+ << filename << "'!"
+ << std::endl;
abort();
}
- internal::load_header(ima, file);
+ internal::load_header(ima, file, filename);
internal::load_data(ima, file);
mln_postcondition(exact(ima).is_valid());
diff --git a/milena/mln/io/dump/save.hh b/milena/mln/io/dump/save.hh
index a489a20..41d4571 100644
--- a/milena/mln/io/dump/save.hh
+++ b/milena/mln/io/dump/save.hh
@@ -40,6 +40,7 @@
# include <mln/core/box_runstart_piter.hh>
# include <mln/core/pixel.hh>
# include <mln/data/memcpy_.hh>
+# include <mln/trait/value_.hh>
namespace mln
{
@@ -68,12 +69,35 @@ namespace mln
void save_header(const I& ima,
std::ofstream& file)
{
+ // Milena's file type
+ file << "milena/dump" << std::endl;
+
+ // Dimension
typedef mln_site(I) P;
- file << P::dim;
+ file << P::dim << std::endl;
+
+ // Image size.
+ typedef algebra::vec<P::dim, unsigned> vec_t;
+ vec_t size = ima.domain().pmax() - ima.domain().pmin();
+ for (unsigned i = 0; i < P::dim - 1; ++i)
+ file << size[i] + 1 << " ";
+ file << size[P::dim - 1] + 1 << std::endl;
+
+ // Value type name
+ // WARNING: value type name limited to 255 characters...
+ file << mln_trait_value_name(mln_value(I)) << std::endl;
+
+ // Empty line - may be used for a new information.
+ file << std::endl;
+
+ // Empty line - may be used for a new information.
+ file << std::endl;
+ // Pmin
mln_site(I) p = ima.domain().pmin();
file.write((char*) (&p), sizeof (P));
+ // Pmax
p = ima.domain().pmax();
file.write((char*) (&p), sizeof (P));
}
diff --git a/milena/mln/trait/value_.hh b/milena/mln/trait/value_.hh
index d03403d..f607604 100644
--- a/milena/mln/trait/value_.hh
+++ b/milena/mln/trait/value_.hh
@@ -66,7 +66,8 @@
# define mln_sum(V) mln_trait_value_sum(V)
# define mln_sum_(V) mln_trait_value_sum_(V)
-
+/// Give the value type name
+# define mln_trait_value_name(V) mln::trait::value_< V >::name()
/// FIXME: check that the -1 is correct
# define mln_value_quant_from_(C) \
diff --git a/milena/mln/value/builtin/floatings.hh b/milena/mln/value/builtin/floatings.hh
index 3fd0b50..c777555 100644
--- a/milena/mln/value/builtin/floatings.hh
+++ b/milena/mln/value/builtin/floatings.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2007, 2008, 2009 EPITA Research and Development Laboratory
// (LRDE)
//
// This file is part of the Olena Library. This library is free
@@ -89,6 +89,10 @@ namespace mln
}
typedef float sum;
+
+ static const char* name()
+ { return "float"; }
+
};
template <>
@@ -120,6 +124,10 @@ namespace mln
}
typedef double sum;
+
+ static const char* name()
+ { return "float"; }
+
};
} // end of namespace mln::trait
diff --git a/milena/mln/value/builtin/integers.hh b/milena/mln/value/builtin/integers.hh
index cb4cced..71cfd34 100644
--- a/milena/mln/value/builtin/integers.hh
+++ b/milena/mln/value/builtin/integers.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2007, 2008, 2009 EPITA Research and Development Laboratory
// (LRDE)
//
// This file is part of the Olena Library. This library is free
@@ -90,14 +90,61 @@ namespace mln
} // end of namespace mln::trait::internal
- template <> struct value_< unsigned char > : internal::value_integer_< unsigned char > {};
- template <> struct value_< signed char > : internal::value_integer_< signed char > {};
- template <> struct value_< unsigned short > : internal::value_integer_< unsigned short > {};
- template <> struct value_< signed short > : internal::value_integer_< signed short > {};
- template <> struct value_< unsigned int > : internal::value_integer_< unsigned int > {};
- template <> struct value_< signed int > : internal::value_integer_< signed int > {};
- template <> struct value_< unsigned long > : internal::value_integer_< unsigned long > {};
- template <> struct value_< signed long > : internal::value_integer_< signed long > {};
+ template <> struct value_< unsigned char >
+ : internal::value_integer_< unsigned char >
+ {
+ static const char* name()
+ { return "unsigned char"; }
+ };
+
+ template <> struct value_< signed char >
+ : internal::value_integer_< signed char >
+ {
+ static const char* name()
+ { return "signed char"; }
+ };
+
+ template <> struct value_< unsigned short >
+ : internal::value_integer_< unsigned short >
+ {
+ static const char* name()
+ { return "unsigned short"; }
+ };
+
+ template <> struct value_< signed short >
+ : internal::value_integer_< signed short >
+ {
+ static const char* name()
+ { return "signed short"; }
+ };
+
+ template <> struct value_< unsigned int >
+ : internal::value_integer_< unsigned int >
+ {
+ static const char* name()
+ { return "unsigned int"; }
+ };
+
+ template <> struct value_< signed int >
+ : internal::value_integer_< signed int >
+ {
+ static const char* name()
+ { return "signed int"; }
+ };
+
+ template <> struct value_< unsigned long >
+ : internal::value_integer_< unsigned long >
+ {
+ static const char* name()
+ { return "unsigned long"; }
+ };
+
+ template <> struct value_< signed long >
+ : internal::value_integer_< signed long >
+ {
+ static const char* name()
+ { return "signed long"; }
+ };
} // end of namespace mln::trait
diff --git a/milena/mln/value/builtin/symbolics.hh b/milena/mln/value/builtin/symbolics.hh
index 8724c3a..65cdb3c 100644
--- a/milena/mln/value/builtin/symbolics.hh
+++ b/milena/mln/value/builtin/symbolics.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2007, 2008, 2009 EPITA Research and Development Laboratory
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,10 +28,10 @@
#ifndef MLN_VALUE_BUILTIN_SYMBOLICS_HH
# define MLN_VALUE_BUILTIN_SYMBOLICS_HH
-/*! \file mln/value/builtin/symbolics.hh
- *
- * \brief Some definitions about built-in symbolic types.
- */
+/// \file mln/value/builtin/symbolics.hh
+///
+/// Some definitions about built-in symbolic types.
+
# include <mln/value/concept/built_in.hh>
# include <mln/value/concept/symbolic.hh>
@@ -53,7 +53,7 @@ namespace mln
{
template <>
- struct value_< bool>
+ struct value_<bool>
{
typedef value::nature::symbolic nature;
typedef value::kind::binary kind;
@@ -63,6 +63,9 @@ namespace mln
card = 2
};
typedef value::quant::low quant;
+
+ static const char* name() { return "bool"; }
+
};
} // end of namespace mln::trait
diff --git a/milena/mln/value/int_s.hh b/milena/mln/value/int_s.hh
index e30206c..a6d02ca 100644
--- a/milena/mln/value/int_s.hh
+++ b/milena/mln/value/int_s.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2007, 2008, 2009 EPITA Research and Development Laboratory
// (LRDE)
//
// This file is part of the Olena Library. This library is free
@@ -89,6 +89,13 @@ namespace mln
static const self_ epsilon() { return 0; }
typedef float sum;
+
+ static const char* name()
+ {
+ static std::string s = std::string("int_s").append(1, n + '0');
+ return s.c_str();
+ }
+
};
} // end of namespace mln::trait
diff --git a/milena/mln/value/int_u.hh b/milena/mln/value/int_u.hh
index ce1993b..db3353e 100644
--- a/milena/mln/value/int_u.hh
+++ b/milena/mln/value/int_u.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2007, 2008, 2009 EPITA Research and Development Laboratory
// (LRDE)
//
// This file is part of the Olena Library. This library is free
@@ -95,6 +95,13 @@ namespace mln
static const self_ epsilon() { return 0; }
typedef float sum;
+
+ static const char* name()
+ {
+ static std::string s = std::string("int_u").append(1, n + '0');
+ return s.c_str();
+ }
+
};
} // end of namespace mln::trait
diff --git a/milena/mln/value/label.hh b/milena/mln/value/label.hh
index 53c3d60..51dfa2d 100644
--- a/milena/mln/value/label.hh
+++ b/milena/mln/value/label.hh
@@ -78,6 +78,13 @@ namespace mln
static const self_ min() { return 0; }
static const self_ max() { return mlc_pow_int(2, n) - 1; }
+
+ static const char* name()
+ {
+ static std::string s = std::string("label_").append(1, n + '0');
+ return s.c_str();
+ }
+
};
} // end of namespace trait
diff --git a/milena/mln/value/rgb.hh b/milena/mln/value/rgb.hh
index 2d13f94..11733cc 100644
--- a/milena/mln/value/rgb.hh
+++ b/milena/mln/value/rgb.hh
@@ -217,6 +217,13 @@ namespace mln
typedef mln_value_quant_from_(card) quant;
typedef algebra::vec<3, float> sum;
+
+ static const char* name()
+ {
+ static std::string s = std::string("rgb").append(1, n + '0');
+ return s.c_str();
+ }
+
};
} // end of namespace trait
diff --git a/milena/tests/io/dump/dump.cc b/milena/tests/io/dump/dump.cc
index 6099bc9..7c7ba04 100644
--- a/milena/tests/io/dump/dump.cc
+++ b/milena/tests/io/dump/dump.cc
@@ -67,7 +67,6 @@ int main()
1, 9 };
image2d<value::int_u8> pic = make::image2d(data);
io::dump::save(pic, "pic.dump");
-
image2d<value::int_u8> pic2;
io::dump::load(pic2, "pic.dump");
@@ -75,6 +74,33 @@ int main()
mln_assertion(pic == pic2);
}
+ /// Value: unsigned
+ {
+ unsigned data[4] = { 5, 1,
+ 1, 9 };
+ image2d<unsigned> pic = make::image2d(data);
+ io::dump::save(pic, "pic.dump");
+ image2d<unsigned> pic2;
+ io::dump::load(pic2, "pic.dump");
+
+ mln_assertion(pic.domain() == pic2.domain());
+ mln_assertion(pic == pic2);
+ }
+
+ /// Value: float
+ {
+ float data[4] = { 5, 1,
+ 1, 9 };
+ image2d<float> pic = make::image2d(data);
+ io::dump::save(pic, "pic.dump");
+ image2d<float> pic2;
+ io::dump::load(pic2, "pic.dump");
+
+ mln_assertion(pic.domain() == pic2.domain());
+ mln_assertion(pic == pic2);
+ }
+
+
/// Value: rgb8
{
using value::rgb8;
--
1.5.6.5
1
0
* headers.mk: update dist header list.
* mln/algebra/vec.hh: add contructor and operator= with literal::zero.
* mln/canvas/distance_front.hh: avoid a warning.
* mln/fun/i2v/array.hh,
* mln/fun/l2l/relabel.hh,
* mln/convert/from_to.hxx: add new from_to over_loads.
* mln/convert/impl/all.hh,
* mln/convert/impl/from_unsigned_to_value.hh: add a new from_to
implementation to fix ambiguities with from_int_to_value and
from_float_to_value.
* mln/win/essential.hh,
* mln/core/internal/image_identity.hh: update doc.
* mln/core/routine/essential.hh: fix includes.
* mln/fun/essential.hh: include fun/meta/essential.hh.
* mln/util/soft_heap.hh: fix guards.
---
milena/ChangeLog | 28 +++++
milena/headers.mk | 12 +-
milena/mln/algebra/vec.hh | 26 ++++-
milena/mln/canvas/distance_front.hh | 1 +
milena/mln/convert/from_to.hxx | 42 +++++++
milena/mln/convert/impl/all.hh | 1 +
milena/mln/convert/impl/from_unsigned_to_value.hh | 132 +++++++++++++++++++++
milena/mln/core/internal/image_identity.hh | 15 +--
milena/mln/core/routine/essential.hh | 12 +-
milena/mln/fun/essential.hh | 10 +-
milena/mln/fun/i2v/array.hh | 34 ++++++
milena/mln/fun/l2l/relabel.hh | 34 ++++++
milena/mln/util/soft_heap.hh | 6 +-
milena/mln/win/essential.hh | 9 +-
14 files changed, 328 insertions(+), 34 deletions(-)
create mode 100644 milena/mln/convert/impl/from_unsigned_to_value.hh
diff --git a/milena/ChangeLog b/milena/ChangeLog
index 4f0c24c..199bdd1 100644
--- a/milena/ChangeLog
+++ b/milena/ChangeLog
@@ -1,5 +1,33 @@
2009-03-10 Guillaume Lazzara <lazzara(a)lrde.epita.fr>
+ Various small fixes.
+
+ * headers.mk: update dist header list.
+
+ * mln/algebra/vec.hh: add contructor and operator= with literal::zero.
+
+ * mln/canvas/distance_front.hh: avoid a warning.
+
+ * mln/fun/i2v/array.hh,
+ * mln/fun/l2l/relabel.hh,
+ * mln/convert/from_to.hxx: add new from_to over_loads.
+
+ * mln/convert/impl/all.hh,
+ * mln/convert/impl/from_unsigned_to_value.hh: add a new from_to
+ implementation to fix ambiguities with from_int_to_value and
+ from_float_to_value.
+
+ * mln/win/essential.hh,
+ * mln/core/internal/image_identity.hh: update doc.
+
+ * mln/core/routine/essential.hh: fix includes.
+
+ * mln/fun/essential.hh: include fun/meta/essential.hh.
+
+ * mln/util/soft_heap.hh: fix guards.
+
+2009-03-10 Guillaume Lazzara <lazzara(a)lrde.epita.fr>
+
Add meta::first and meta::second.
* mln/fun/meta/all.hh,
diff --git a/milena/headers.mk b/milena/headers.mk
index e37427e..9513a84 100644
--- a/milena/headers.mk
+++ b/milena/headers.mk
@@ -95,6 +95,7 @@ mln/util/line_graph.hh \
mln/util/ord.hh \
mln/util/tree_fast_to_image.hh \
mln/util/tree.hh \
+mln/util/couple.hh \
mln/util/index.hh \
mln/util/multi_site.hh \
mln/util/branch_iter.hh \
@@ -367,6 +368,7 @@ mln/value/label_8.hh \
mln/value/essential.hh \
mln/accu/tuple.hh \
mln/accu/min_h.hh \
+mln/accu/stat/deviation.hh \
mln/accu/max.hh \
mln/accu/lor.hh \
mln/accu/rank.hh \
@@ -602,7 +604,6 @@ mln/linear/log.hh \
mln/linear/essential.hh \
mln/morpho/thinning.hh \
mln/morpho/meyer_wst.hh \
-mln/morpho/opening.hh \
mln/morpho/includes.hh \
mln/morpho/elementary/opening.hh \
mln/morpho/elementary/gradient_internal.hh \
@@ -634,7 +635,9 @@ mln/morpho/closing/leveling.hh \
mln/morpho/closing/area_on_vertices.hh \
mln/morpho/closing/area.hh \
mln/morpho/closing/volume.hh \
+mln/morpho/closing/sum.hh \
mln/morpho/closing/height.hh \
+mln/morpho/closing/structural.hh \
mln/morpho/closing/essential.hh \
mln/morpho/laplacian.hh \
mln/morpho/all.hh \
@@ -647,6 +650,7 @@ mln/morpho/opening/area_on_vertices.hh \
mln/morpho/opening/area.hh \
mln/morpho/opening/volume.hh \
mln/morpho/opening/height.hh \
+mln/morpho/opening/structural.hh \
mln/morpho/opening/essential.hh \
mln/morpho/attribute/all.hh \
mln/morpho/attribute/volume.hh \
@@ -665,15 +669,12 @@ mln/morpho/tree/data.hh \
mln/morpho/tree/compute_attribute_image.hh \
mln/morpho/general.spe.hh \
mln/morpho/min.hh \
-mln/morpho/closing.hh \
mln/morpho/top_hat.hh \
mln/morpho/erosion.hh \
mln/morpho/leveling_filter.hh \
-mln/morpho/closing_sum.hh \
mln/morpho/Rd.hh \
mln/morpho/thick_miss.hh \
mln/morpho/algebraic_filter.hh \
-mln/morpho/closing_attribute.hh \
mln/morpho/rank_filter.hh \
mln/morpho/essential.hh \
mln/topo/n_face_iter.hh \
@@ -708,6 +709,7 @@ mln/essential/routine.hh \
mln/essential/3d.hh \
mln/essential/2d.hh \
mln/win/inter.hh \
+mln/win/sphere3d.hh \
mln/win/backdiag2d.hh \
mln/win/segment1d.hh \
mln/win/cuboid3d.hh \
@@ -718,10 +720,10 @@ mln/win/multiple_size.hh \
mln/win/cube3d.hh \
mln/win/shift.hh \
mln/win/sym.hh \
+mln/win/ball.hh \
mln/win/diff.hh \
mln/win/multiple.hh \
mln/win/diag2d.hh \
-mln/win/ball3d.hh \
mln/win/disk2d.hh \
mln/win/rectangle2d.hh \
mln/win/hline2d.hh \
diff --git a/milena/mln/algebra/vec.hh b/milena/mln/algebra/vec.hh
index da2541c..9563a27 100644
--- a/milena/mln/algebra/vec.hh
+++ b/milena/mln/algebra/vec.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2006, 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2006, 2008, 2009 EPITA Research and Development Laboratory
// (LRDE)
//
// This file is part of the Olena Library. This library is free
@@ -39,6 +39,7 @@
# include <mln/core/concept/object.hh>
# include <mln/literal/zero.hh>
+# include <mln/literal/origin.hh>
# include <mln/norm/l2.hh>
# include <mln/trait/all.hh>
# include <mln/trait/value_.hh>
@@ -188,11 +189,16 @@ namespace mln
vec();
- /// \{ Constructors/assignments with literal zero.
+ /// \{ Constructors/assignments with literal::zero.
vec(const literal::zero_t&);
vec& operator=(const literal::zero_t&);
/// \}
+ /// \{ Constructors/assignments with literal::origin.
+ vec(const literal::origin_t&);
+ vec& operator=(const literal::origin_t&);
+ /// \}
+
vec(const vec<n, T>& rhs);
template <typename U>
@@ -386,6 +392,22 @@ namespace mln
template <unsigned n, typename T>
inline
+ vec<n,T>::vec(const literal::origin_t&)
+ {
+ this->set_all(0);
+ }
+
+ template <unsigned n, typename T>
+ inline
+ vec<n,T>&
+ vec<n,T>::operator=(const literal::origin_t&)
+ {
+ this->set_all(0);
+ return *this;
+ }
+
+ template <unsigned n, typename T>
+ inline
vec<n,T>::vec(const vec<n,T>& rhs)
: super_()
{
diff --git a/milena/mln/canvas/distance_front.hh b/milena/mln/canvas/distance_front.hh
index f374a2b..3eb8eeb 100644
--- a/milena/mln/canvas/distance_front.hh
+++ b/milena/mln/canvas/distance_front.hh
@@ -88,6 +88,7 @@ namespace mln
(void) nbh;
(void) max;
(void) functor;
+ (void) w_win;
}
diff --git a/milena/mln/convert/from_to.hxx b/milena/mln/convert/from_to.hxx
index df12d5d..d4ccc22 100644
--- a/milena/mln/convert/from_to.hxx
+++ b/milena/mln/convert/from_to.hxx
@@ -76,6 +76,10 @@ namespace mln
namespace i2v {
template <typename T> class array;
}
+
+ namespace l2l {
+ template <typename T> class relabel;
+ }
}
namespace histo {
@@ -333,17 +337,55 @@ namespace mln
void
from_to_(const util::array<T>& from, fun::i2v::array<T>& to);
+ // util::array<T> -> fun::i2v::array<U>
+ template <typename T, typename U>
+ void
+ from_to_(const util::array<T>& from, fun::i2v::array<U>& to);
+
// std::vector<T> -> fun::i2v::array<T>
template <typename T>
void
from_to_(const std::vector<T>& from, fun::i2v::array<T>& to);
+ // std::vector<T> -> fun::i2v::array<U>
+ template <typename T, typename U>
+ void
+ from_to_(const std::vector<T>& from, fun::i2v::array<U>& to);
+
+ // util::array<T1> -> util::array<T2>
+ template <typename T1, typename T2>
+ void
+ from_to_(const util::array<T1>& from, util::array<T2>& to);
+
+
+
+ // util::array<T> -> fun::l2l::relabel<T>
+ template <typename T>
+ void
+ from_to_(const util::array<T>& from, fun::l2l::relabel<T>& to);
+
+ // util::array<T> -> fun::l2l::relabel<U>
+ template <typename T, typename U>
+ void
+ from_to_(const util::array<T>& from, fun::l2l::relabel<U>& to);
+
+ // std::vector<T> -> fun::l2l::relabel<T>
+ template <typename T>
+ void
+ from_to_(const std::vector<T>& from, fun::l2l::relabel<T>& to);
+
+ // std::vector<T> -> fun::l2l::relabel<U>
+ template <typename T, typename U>
+ void
+ from_to_(const std::vector<T>& from, fun::l2l::relabel<U>& to);
+
// util::array<T1> -> util::array<T2>
template <typename T1, typename T2>
void
from_to_(const util::array<T1>& from, util::array<T2>& to);
+
// Accumulator<A> -> mln_result(A)
template <typename A>
void
diff --git a/milena/mln/convert/impl/all.hh b/milena/mln/convert/impl/all.hh
index dcaaf24..28cdde1 100644
--- a/milena/mln/convert/impl/all.hh
+++ b/milena/mln/convert/impl/all.hh
@@ -38,6 +38,7 @@
# include <mln/convert/impl/from_image_to_site_set.hh>
# include <mln/convert/impl/from_int_to_value.hh>
# include <mln/convert/impl/from_site_set_to_image.hh>
+# include <mln/convert/impl/from_unsigned_to_value.hh>
# include <mln/convert/impl/from_value_to_value.hh>
diff --git a/milena/mln/convert/impl/from_unsigned_to_value.hh b/milena/mln/convert/impl/from_unsigned_to_value.hh
new file mode 100644
index 0000000..4c6bac7
--- /dev/null
+++ b/milena/mln/convert/impl/from_unsigned_to_value.hh
@@ -0,0 +1,132 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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 MLN_CONVERT_IMPL_FROM_UNSIGNED_TO_VALUE_HH
+# define MLN_CONVERT_IMPL_FROM_UNSIGNED_TO_VALUE_HH
+
+/// \file mln/convert/impl/from_unsigned_to_value.hh
+///
+/// General conversion procedure from an unsigned to a value.
+///
+/// \todo Augment code + add checks.
+
+# include <utility>
+# include <mln/value/concept/integer.hh>
+# include <mln/core/concept/value.hh>
+# include <mln/math/round.hh>
+
+
+
+
+namespace mln
+{
+
+ namespace convert
+ {
+
+ /// Conversion of an unsigned \p from towards a value \p to.
+ template <typename V>
+ void
+ from_to(const unsigned& from, Value<V>& to);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ namespace impl
+ {
+
+ // Case 1:
+
+ template <typename V>
+ inline
+ void
+ from_unsigned_to_value(const unsigned& from,
+ mln::value::Integer<V>& to)
+ {
+ exact(to) = from;
+ }
+
+ template <unsigned n>
+ inline
+ void
+ from_unsigned_to_value(const unsigned& from,
+ mln::value::label<n>& to)
+ {
+ exact(to) = from;
+ }
+
+ // Default: no conversion defined.
+
+ template <typename V>
+ inline
+ void
+ from_unsigned_to_value(const unsigned&,
+ Value<V>&)
+ {
+ mlc_abort(V)::check();
+ }
+
+ } // end of namespace mln::convert::impl
+
+
+ namespace internal
+ {
+
+ template <typename V>
+ inline
+ void
+ from_unsigned_to_value_dispatch(const unsigned& from, Value<V>& to)
+ {
+ impl::from_unsigned_to_value(from, exact(to));
+ }
+
+ } // end of namespace mln::convert::unsignedernal
+
+
+ namespace over_load
+ {
+
+ // Facades.
+ // unsigned-> Value
+ template <typename V>
+ void
+ from_to_(const unsigned& from, Value<V>& to)
+ {
+ internal::from_unsigned_to_value_dispatch(from, to);
+ }
+
+ } // end of namespace mln::convert::over_load
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::convert
+
+} // end of namespace mln
+
+
+#endif // ! MLN_CONVERT_IMPL_FROM_UNSIGNED_TO_VALUE_HH
diff --git a/milena/mln/core/internal/image_identity.hh b/milena/mln/core/internal/image_identity.hh
index 3a2b20b..bddcdf7 100644
--- a/milena/mln/core/internal/image_identity.hh
+++ b/milena/mln/core/internal/image_identity.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2007 EPITA Research and Development Laboratory
+// Copyright (C) 2007, 2009 EPITA Research and Development Laboratory
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,13 +28,12 @@
#ifndef MLN_CORE_INTERNAL_IMAGE_IDENTITY_HH
# define MLN_CORE_INTERNAL_IMAGE_IDENTITY_HH
-/*! \file mln/core/internal/image_identity.hh
- *
- * \brief Definition of a base class for image morphers w.r.t. identity.
- *
- * \todo Move "fastest impl" elsewhere; it can be used by some other
- * classes.
- */
+/// \file mln/core/internal/image_identity.hh
+///
+/// Definition of a base class for image morphers w.r.t. identity.
+///
+/// \todo Move "fastest impl" elsewhere; it can be used by some other
+/// classes.
# include <mln/core/internal/image_morpher.hh>
diff --git a/milena/mln/core/routine/essential.hh b/milena/mln/core/routine/essential.hh
index 26568e5..dfc3d44 100644
--- a/milena/mln/core/routine/essential.hh
+++ b/milena/mln/core/routine/essential.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2008, 2009 EPITA Research and Development Laboratory
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,11 +28,11 @@
#ifndef MLN_CORE_ROUTINE_ESSENTIAL_HH_
# define MLN_CORE_ROUTINE_ESSENTIAL_HH_
-# include <mln/core/routine/duplicate.hh>
-# include <mln/core/routine/exact.hh>
-# include <mln/core/routine/extend.hh>
-# include <mln/core/routine/initialize.hh>
-# include <mln/core/routine/ops.hh>
+/// \file mln/core/routine/essential.hh
+///
+/// File that includes essential core routines.
+
+# include <mln/core/routine/all.hh>
#endif // !MLN_CORE_ROUTINE_ESSENTIAL_HH_
diff --git a/milena/mln/fun/essential.hh b/milena/mln/fun/essential.hh
index 9626e45..393242e 100644
--- a/milena/mln/fun/essential.hh
+++ b/milena/mln/fun/essential.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2008, 2009 EPITA Research and Development Laboratory
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,14 +28,14 @@
#ifndef MLN_FUN_ESSENTIAL_HH
# define MLN_FUN_ESSENTIAL_HH
-/*! \file mln/fun/essential.hh
- *
- * \brief File that includes essential fun-related routines.
- */
+/// \file mln/fun/essential.hh
+///
+/// File that includes essential fun-related routines.
# include <mln/fun/c.hh>
# include <mln/fun/ops.hh>
# include <mln/fun/i2v/essential.hh>
+# include <mln/fun/meta/essential.hh>
# include <mln/fun/p2b/essential.hh>
# include <mln/fun/p2v/essential.hh>
# include <mln/fun/v2b/essential.hh>
diff --git a/milena/mln/fun/i2v/array.hh b/milena/mln/fun/i2v/array.hh
index 13b6d5e..cd00db5 100644
--- a/milena/mln/fun/i2v/array.hh
+++ b/milena/mln/fun/i2v/array.hh
@@ -75,11 +75,22 @@ namespace mln
void
from_to_(const util::array<T>& from, fun::i2v::array<T>& to);
+ template <typename T, typename U>
+ inline
+ void
+ from_to_(const util::array<T>& from, fun::i2v::array<U>& to);
+
template <typename T>
inline
void
from_to_(const std::vector<T>& from, fun::i2v::array<T>& to);
+ template <typename T, typename U>
+ inline
+ void
+ from_to_(const std::vector<T>& from, fun::i2v::array<U>& to);
+
+
} // end of namespace mln::convert::over_load
} // end of namespace mln::convert
@@ -157,6 +168,17 @@ namespace mln
to = fun::i2v::array<T>(from);
}
+ template <typename T, typename U>
+ inline
+ void
+ from_to_(const util::array<T>& from, fun::i2v::array<U>& to)
+ {
+ mlc_converts_to(T,U)::check();
+
+ for (unsigned i = 0; i < from.nelements(); ++i)
+ to.append(convert::to<U>(from[i]));
+ }
+
template <typename T>
inline
void
@@ -165,6 +187,18 @@ namespace mln
to = fun::i2v::array<T>(from);
}
+ template <typename T, typename U>
+ inline
+ void
+ from_to_(const std::vector<T>& from, fun::i2v::array<U>& to)
+ {
+ mlc_converts_to(T,U)::check();
+
+ for (unsigned i = 0; i < from.size(); ++i)
+ to.append(convert::to<U>(from[i]));
+ }
+
+
} // end of namespace mln::convert::over_load
} // end of namespace mln::convert
diff --git a/milena/mln/fun/l2l/relabel.hh b/milena/mln/fun/l2l/relabel.hh
index 16da5b4..a57f3d4 100644
--- a/milena/mln/fun/l2l/relabel.hh
+++ b/milena/mln/fun/l2l/relabel.hh
@@ -72,12 +72,24 @@ namespace mln
from_to_(const util::array<L>& from,
fun::l2l::relabel<L>& to);
+ template <typename T, typename L>
+ inline
+ void
+ from_to_(const util::array<T>& from,
+ fun::l2l::relabel<L>& to);
+
template <typename L>
inline
void
from_to_(const std::vector<L>& from,
fun::l2l::relabel<L>& to);
+ template <typename T, typename L>
+ inline
+ void
+ from_to_(const std::vector<T>& from,
+ fun::l2l::relabel<L>& to);
+
} // end of namespace mln::convert::over_load
} // end of namespace mln::convert
@@ -155,6 +167,17 @@ namespace mln
to = fun::l2l::relabel<L>(from);
}
+ template <typename T, typename L>
+ inline
+ void
+ from_to_(const util::array<T>& from, fun::l2l::relabel<L>& to)
+ {
+ mlc_converts_to(T,L)::check();
+
+ for (unsigned i = 0; i < from.nelements(); ++i)
+ to.append(convert::to<L>(from[i]));
+ }
+
template <typename L>
inline
void
@@ -163,6 +186,17 @@ namespace mln
to = fun::l2l::relabel<L>(from);
}
+ template <typename T, typename L>
+ inline
+ void
+ from_to_(const std::vector<T>& from, fun::l2l::relabel<L>& to)
+ {
+ mlc_converts_to(T,L)::check();
+
+ for (unsigned i = 0; i < from.size(); ++i)
+ to.append(convert::to<L>(from[i]));
+ }
+
} // end of namespace mln::convert::over_load
} // end of namespace mln::convert
diff --git a/milena/mln/util/soft_heap.hh b/milena/mln/util/soft_heap.hh
index bff9d11..e0f8768 100644
--- a/milena/mln/util/soft_heap.hh
+++ b/milena/mln/util/soft_heap.hh
@@ -25,8 +25,8 @@
// reasons why the executable file might be covered by the GNU General
// Public License.
-#ifndef MLN_UTIL_FAST_HEAP_HH
-# define MLN_UTIL_FAST_HEAP_HH
+#ifndef MLN_UTIL_SOFT_HEAP_HH
+# define MLN_UTIL_SOFT_HEAP_HH
/// \file mln/util/soft_heap.hh
///
@@ -1132,4 +1132,4 @@ namespace mln
} // end of namespace mln
-#endif // ! MLN_UTIL_FAST_HEAP_HH
+#endif // ! MLN_UTIL_SOFT_HEAP_HH
diff --git a/milena/mln/win/essential.hh b/milena/mln/win/essential.hh
index e6fe809..00a4995 100644
--- a/milena/mln/win/essential.hh
+++ b/milena/mln/win/essential.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2009 EPITA Research and Development Laboratory
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,10 +28,9 @@
#ifndef MLN_WIN_ESSENTIAL_HH
# define MLN_WIN_ESSENTIAL_HH
-/*! \file mln/win/essential.hh
- *
- * \brief File that includes essential win-related routines.
- */
+/// \file mln/win/essential.hh
+///
+/// File that includes essential win-related routines.
// Types.
--
1.5.6.5
1
0
* mln/fun/meta/all.hh,
* mln/fun/meta/essential.hh: include new headers.
* mln/fun/meta/first.hh,
* mln/fun/meta/second.hh: meta function to access util::couple data.
---
milena/ChangeLog | 10 ++++
milena/mln/fun/meta/all.hh | 19 ++++---
milena/mln/fun/meta/{all.hh => essential.hh} | 31 ++---------
milena/mln/fun/meta/{all.hh => first.hh} | 69 ++++++++++++++++++++------
milena/mln/fun/meta/{all.hh => second.hh} | 69 ++++++++++++++++++++------
5 files changed, 134 insertions(+), 64 deletions(-)
copy milena/mln/fun/meta/{all.hh => essential.hh} (69%)
copy milena/mln/fun/meta/{all.hh => first.hh} (52%)
copy milena/mln/fun/meta/{all.hh => second.hh} (52%)
diff --git a/milena/ChangeLog b/milena/ChangeLog
index 994c509..4f0c24c 100644
--- a/milena/ChangeLog
+++ b/milena/ChangeLog
@@ -1,3 +1,13 @@
+2009-03-10 Guillaume Lazzara <lazzara(a)lrde.epita.fr>
+
+ Add meta::first and meta::second.
+
+ * mln/fun/meta/all.hh,
+ * mln/fun/meta/essential.hh: include new headers.
+
+ * mln/fun/meta/first.hh,
+ * mln/fun/meta/second.hh: meta function to access util::couple data.
+
2009-03-09 Edwin Carlinet <carlinet(a)lrde.epita.fr>
Add leaves container in tree structure and test new propagations.
diff --git a/milena/mln/fun/meta/all.hh b/milena/mln/fun/meta/all.hh
index 23d7bc2..49bd5b5 100644
--- a/milena/mln/fun/meta/all.hh
+++ b/milena/mln/fun/meta/all.hh
@@ -40,15 +40,16 @@ namespace mln
} // end of namespace mln
-#include<mln/fun/meta/red.hh>
-#include<mln/fun/meta/hue.hh>
-#include<mln/fun/meta/lum.hh>
-#include<mln/fun/meta/all.hh>
-#include<mln/fun/meta/green.hh>
-#include<mln/fun/meta/inty.hh>
-#include<mln/fun/meta/blue.hh>
-#include<mln/fun/meta/sat.hh>
-#include<mln/fun/meta/to_enc.hh>
+# include <mln/fun/meta/blue.hh>
+# include <mln/fun/meta/first.hh>
+# include <mln/fun/meta/green.hh>
+# include <mln/fun/meta/hue.hh>
+# include <mln/fun/meta/inty.hh>
+# include <mln/fun/meta/lum.hh>
+# include <mln/fun/meta/red.hh>
+# include <mln/fun/meta/sat.hh>
+# include <mln/fun/meta/second.hh>
+# include <mln/fun/meta/to_enc.hh>
#endif // ! MLN_FUN_META_ALL_HH
diff --git a/milena/mln/fun/meta/all.hh b/milena/mln/fun/meta/essential.hh
similarity index 69%
copy from milena/mln/fun/meta/all.hh
copy to milena/mln/fun/meta/essential.hh
index 23d7bc2..821a0a9 100644
--- a/milena/mln/fun/meta/all.hh
+++ b/milena/mln/fun/meta/essential.hh
@@ -1,5 +1,5 @@
-// Copyright (C) 2007, 2008, 2009 EPITA Research and Development
-// Laboratory (LRDE)
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -26,29 +26,10 @@
// reasons why the executable file might be covered by the GNU General
// Public License.
-#ifndef MLN_FUN_META_ALL_HH
-# define MLN_FUN_META_ALL_HH
+#ifndef MLN_FUN_META_ESSENTIAL_HH
+# define MLN_FUN_META_ESSENTIAL_HH
-namespace mln
-{
+# include <mln/fun/meta/all.hh>
- namespace meta
- {
-
- } // end of namespace mln::meta
-
-} // end of namespace mln
-
-
-#include<mln/fun/meta/red.hh>
-#include<mln/fun/meta/hue.hh>
-#include<mln/fun/meta/lum.hh>
-#include<mln/fun/meta/all.hh>
-#include<mln/fun/meta/green.hh>
-#include<mln/fun/meta/inty.hh>
-#include<mln/fun/meta/blue.hh>
-#include<mln/fun/meta/sat.hh>
-#include<mln/fun/meta/to_enc.hh>
-
-#endif // ! MLN_FUN_META_ALL_HH
+#endif // ! MLN_FUN_META_ESSENTIAL_HH
diff --git a/milena/mln/fun/meta/all.hh b/milena/mln/fun/meta/first.hh
similarity index 52%
copy from milena/mln/fun/meta/all.hh
copy to milena/mln/fun/meta/first.hh
index 23d7bc2..89d3f12 100644
--- a/milena/mln/fun/meta/all.hh
+++ b/milena/mln/fun/meta/first.hh
@@ -1,5 +1,5 @@
-// Copyright (C) 2007, 2008, 2009 EPITA Research and Development
-// Laboratory (LRDE)
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -26,8 +26,15 @@
// reasons why the executable file might be covered by the GNU General
// Public License.
-#ifndef MLN_FUN_META_ALL_HH
-# define MLN_FUN_META_ALL_HH
+#ifndef MLN_FUN_META_FIRST_HH
+# define MLN_FUN_META_FIRST_HH
+
+/// \file mln/fun/meta/first.hh
+///
+/// Meta function to retrieve/modify the first component.
+
+# include <mln/core/concept/meta_fun.hh>
+# include <mln/util/couple.hh>
namespace mln
{
@@ -35,20 +42,52 @@ namespace mln
namespace meta
{
+ template <class T>
+ struct first : impl< first<T> >
+ {
+ typedef T value;
+ };
+
} // end of namespace mln::meta
-} // end of namespace mln
+ template <typename T, typename U>
+ struct function< meta::first< util::couple<T,U> > >
+ : public Function_v2w_w2v<function< meta::first < util::couple<T,U> > > >
+ {
+ typedef util::couple<T,U> value;
+
+ typedef T result;
+ result read(const value& c);
+
+ typedef result& lresult;
+ lresult write(value& c);
+ };
+
+
+# ifndef MLN_INCLUDE_ONLY
-#include<mln/fun/meta/red.hh>
-#include<mln/fun/meta/hue.hh>
-#include<mln/fun/meta/lum.hh>
-#include<mln/fun/meta/all.hh>
-#include<mln/fun/meta/green.hh>
-#include<mln/fun/meta/inty.hh>
-#include<mln/fun/meta/blue.hh>
-#include<mln/fun/meta/sat.hh>
-#include<mln/fun/meta/to_enc.hh>
-#endif // ! MLN_FUN_META_ALL_HH
+ template <typename T, typename U>
+ inline
+ typename function< meta::first< util::couple<T,U> > >::result
+ function< meta::first< util::couple<T,U> > >::read(const value& c)
+ {
+ return c.first();
+ }
+
+ template <typename T, typename U>
+ inline
+ typename function< meta::first< util::couple<T,U> > >::lresult
+ function< meta::first< util::couple<T,U> > >::write(value& c)
+ {
+ return c.first();
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+} // end of namespace mln
+#endif // MLN_FUN_META_FIRST_HH
diff --git a/milena/mln/fun/meta/all.hh b/milena/mln/fun/meta/second.hh
similarity index 52%
copy from milena/mln/fun/meta/all.hh
copy to milena/mln/fun/meta/second.hh
index 23d7bc2..5f94846 100644
--- a/milena/mln/fun/meta/all.hh
+++ b/milena/mln/fun/meta/second.hh
@@ -1,5 +1,5 @@
-// Copyright (C) 2007, 2008, 2009 EPITA Research and Development
-// Laboratory (LRDE)
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -26,8 +26,15 @@
// reasons why the executable file might be covered by the GNU General
// Public License.
-#ifndef MLN_FUN_META_ALL_HH
-# define MLN_FUN_META_ALL_HH
+#ifndef MLN_FUN_META_SECOND_HH
+# define MLN_FUN_META_SECOND_HH
+
+/// \file mln/fun/meta/second.hh
+///
+/// Meta function to retrieve/modify the second component.
+
+# include <mln/core/concept/meta_fun.hh>
+# include <mln/util/couple.hh>
namespace mln
{
@@ -35,20 +42,52 @@ namespace mln
namespace meta
{
+ template <class T>
+ struct second : impl< second<T> >
+ {
+ typedef T value;
+ };
+
} // end of namespace mln::meta
-} // end of namespace mln
+ template <typename T, typename U>
+ struct function< meta::second< util::couple<T,U> > >
+ : public Function_v2w_w2v<function< meta::second < util::couple<T,U> > > >
+ {
+ typedef util::couple<T,U> value;
+
+ typedef T result;
+ result read(const value& c);
+
+ typedef result& lresult;
+ lresult write(value& c);
+ };
+
+
+# ifndef MLN_INCLUDE_ONLY
-#include<mln/fun/meta/red.hh>
-#include<mln/fun/meta/hue.hh>
-#include<mln/fun/meta/lum.hh>
-#include<mln/fun/meta/all.hh>
-#include<mln/fun/meta/green.hh>
-#include<mln/fun/meta/inty.hh>
-#include<mln/fun/meta/blue.hh>
-#include<mln/fun/meta/sat.hh>
-#include<mln/fun/meta/to_enc.hh>
-#endif // ! MLN_FUN_META_ALL_HH
+ template <typename T, typename U>
+ inline
+ typename function< meta::second< util::couple<T,U> > >::result
+ function< meta::second< util::couple<T,U> > >::read(const value& c)
+ {
+ return c.second();
+ }
+
+ template <typename T, typename U>
+ inline
+ typename function< meta::second< util::couple<T,U> > >::lresult
+ function< meta::second< util::couple<T,U> > >::write(value& c)
+ {
+ return c.second();
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+} // end of namespace mln
+#endif // MLN_FUN_META_SECOND_HH
--
1.5.6.5
1
0
10 Mar '09
---
ChangeLog | 4 ++++
configure.ac | 1 +
2 files changed, 5 insertions(+), 0 deletions(-)
diff --git a/ChangeLog b/ChangeLog
index 721d35a..e27b4aa 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,7 @@
+2009-03-10 Guillaume Lazzara <z(a)lrde.epita.fr>
+
+ * configure.ac: configure tests/morpho/opening/approx.
+
2009-03-09 Frederic Bour <bour(a)lrde.epita.fr>
Add missing trait for thru_morpher.
diff --git a/configure.ac b/configure.ac
index 40969bb..d8a30b5 100644
--- a/configure.ac
+++ b/configure.ac
@@ -248,6 +248,7 @@ AC_CONFIG_FILES([
milena/tests/morpho/watershed/Makefile
milena/tests/morpho/closing/Makefile
milena/tests/morpho/opening/Makefile
+ milena/tests/morpho/opening/approx/Makefile
milena/tests/norm/Makefile
milena/tests/opt/Makefile
milena/tests/pw/Makefile
--
1.5.6.5
1
0
* scribo/Makefile: update include path.
* scribo/core/central_sites.hh,
* scribo/core/component_bboxes.hh,
* scribo/core/erase_bboxes.hh,
* scribo/core/macros.hh,
* scribo/debug/save_label_image.hh,
* scribo/debug/save_linked_textbboxes_image.hh,
* scribo/debug/save_table_image.hh,
* scribo/debug/save_textbboxes_image.hh,
* scribo/draw/bounding_box_links.hh,
* scribo/draw/bounding_boxes.hh,
* scribo/make/debug_filename.hh,
* scribo/make/influence_zone_graph.hh,
* scribo/table/align_lines_horizontaly.hh,
* scribo/table/align_lines_verticaly.hh,
* scribo/table/connect_horizontal_lines.hh,
* scribo/table/connect_vertical_lines.hh,
* scribo/table/erase.hh,
* scribo/table/extract_lines_with_rank.hh,
* scribo/table/internal/align_lines.hh,
* scribo/table/internal/connect_lines.hh,
* scribo/table/internal/repair_lines.hh,
* scribo/table/repair_horizontal_lines.hh,
* scribo/table/repair_vertical_lines.hh,
* scribo/text/extract_bboxes.hh,
* scribo/text/grouping/group_from_double_link.hh,
* scribo/text/grouping/group_from_multiple_links.hh,
* scribo/text/grouping/group_from_single_link.hh,
* scribo/text/grouping/group_with_multiple_links.hh,
* scribo/text/grouping/group_with_single_left_link.hh,
* scribo/text/grouping/group_with_single_right_link.hh,
* scribo/text/grouping/internal/find_root.hh,
* scribo/text/grouping/internal/init_link_array.hh,
* scribo/text/grouping/internal/update_link_array.hh,
* scribo/text/grouping/internal/update_link_graph.hh,
* scribo/text/recognition.hh: new routines.
* scribo/photo.cc,
* scribo/table.cc: move...
* scribo/src/photo.cc,
* scribo/src/table.cc: ... here.
* scribo/src/extract_text_double_link.cc,
* scribo/src/extract_text_multiple_links.cc,
* scribo/src/extract_text_single_link.cc: new small test related to
text extraction.
---
milena/sandbox/ChangeLog | 52 +++++
milena/sandbox/scribo/Makefile | 23 ++-
milena/sandbox/scribo/core/central_sites.hh | 97 ++++++++++
milena/sandbox/scribo/core/component_bboxes.hh | 85 +++++++++
.../scribo/{photo.cc => core/erase_bboxes.hh} | 77 +++++---
milena/sandbox/scribo/{photo.cc => core/macros.hh} | 45 +----
.../scribo/{photo.cc => debug/save_label_image.hh} | 77 +++++----
.../scribo/debug/save_linked_textbboxes_image.hh | 170 +++++++++++++++++
milena/sandbox/scribo/debug/save_table_image.hh | 97 ++++++++++
.../sandbox/scribo/debug/save_textbboxes_image.hh | 90 +++++++++
milena/sandbox/scribo/draw/bounding_box_links.hh | 197 ++++++++++++++++++++
milena/sandbox/scribo/draw/bounding_boxes.hh | 93 +++++++++
.../scribo/{photo.cc => make/debug_filename.hh} | 89 ++++++----
milena/sandbox/scribo/make/influence_zone_graph.hh | 121 ++++++++++++
.../sandbox/scribo/src/extract_text_double_link.cc | 109 +++++++++++
.../scribo/src/extract_text_multiple_links.cc | 78 ++++++++
.../sandbox/scribo/src/extract_text_single_link.cc | 108 +++++++++++
milena/sandbox/scribo/{ => src}/photo.cc | 0
milena/sandbox/scribo/{ => src}/table.cc | 0
.../scribo/table/align_lines_horizontaly.hh | 97 ++++++++++
.../sandbox/scribo/table/align_lines_verticaly.hh | 98 ++++++++++
.../scribo/table/connect_horizontal_lines.hh | 94 ++++++++++
.../sandbox/scribo/table/connect_vertical_lines.hh | 95 ++++++++++
milena/sandbox/scribo/table/erase.hh | 97 ++++++++++
.../scribo/table/extract_lines_with_rank.hh | 127 +++++++++++++
.../sandbox/scribo/table/internal/align_lines.hh | 183 ++++++++++++++++++
.../sandbox/scribo/table/internal/connect_lines.hh | 118 ++++++++++++
.../sandbox/scribo/table/internal/repair_lines.hh | 132 +++++++++++++
.../scribo/table/repair_horizontal_lines.hh | 92 +++++++++
.../sandbox/scribo/table/repair_vertical_lines.hh | 98 ++++++++++
milena/sandbox/scribo/text/extract_bboxes.hh | 95 ++++++++++
.../scribo/text/grouping/group_from_double_link.hh | 108 +++++++++++
.../text/grouping/group_from_multiple_links.hh | 154 +++++++++++++++
.../scribo/text/grouping/group_from_single_link.hh | 101 ++++++++++
.../text/grouping/group_with_multiple_links.hh | 115 ++++++++++++
.../text/grouping/group_with_single_left_link.hh | 135 +++++++++++++
.../text/grouping/group_with_single_right_link.hh | 135 +++++++++++++
.../grouping/internal/find_root.hh} | 82 +++++----
.../grouping/internal/init_link_array.hh} | 79 +++++----
.../text/grouping/internal/update_link_array.hh | 93 +++++++++
.../text/grouping/internal/update_link_graph.hh | 92 +++++++++
milena/sandbox/scribo/text/recognition.hh | 142 ++++++++++++++
42 files changed, 3970 insertions(+), 200 deletions(-)
create mode 100644 milena/sandbox/scribo/core/central_sites.hh
create mode 100644 milena/sandbox/scribo/core/component_bboxes.hh
copy milena/sandbox/scribo/{photo.cc => core/erase_bboxes.hh} (51%)
copy milena/sandbox/scribo/{photo.cc => core/macros.hh} (52%)
copy milena/sandbox/scribo/{photo.cc => debug/save_label_image.hh} (52%)
create mode 100644 milena/sandbox/scribo/debug/save_linked_textbboxes_image.hh
create mode 100644 milena/sandbox/scribo/debug/save_table_image.hh
create mode 100644 milena/sandbox/scribo/debug/save_textbboxes_image.hh
create mode 100644 milena/sandbox/scribo/draw/bounding_box_links.hh
create mode 100644 milena/sandbox/scribo/draw/bounding_boxes.hh
copy milena/sandbox/scribo/{photo.cc => make/debug_filename.hh} (52%)
create mode 100644 milena/sandbox/scribo/make/influence_zone_graph.hh
create mode 100644 milena/sandbox/scribo/src/extract_text_double_link.cc
create mode 100644 milena/sandbox/scribo/src/extract_text_multiple_links.cc
create mode 100644 milena/sandbox/scribo/src/extract_text_single_link.cc
copy milena/sandbox/scribo/{ => src}/photo.cc (100%)
rename milena/sandbox/scribo/{ => src}/table.cc (100%)
create mode 100644 milena/sandbox/scribo/table/align_lines_horizontaly.hh
create mode 100644 milena/sandbox/scribo/table/align_lines_verticaly.hh
create mode 100644 milena/sandbox/scribo/table/connect_horizontal_lines.hh
create mode 100644 milena/sandbox/scribo/table/connect_vertical_lines.hh
create mode 100644 milena/sandbox/scribo/table/erase.hh
create mode 100644 milena/sandbox/scribo/table/extract_lines_with_rank.hh
create mode 100644 milena/sandbox/scribo/table/internal/align_lines.hh
create mode 100644 milena/sandbox/scribo/table/internal/connect_lines.hh
create mode 100644 milena/sandbox/scribo/table/internal/repair_lines.hh
create mode 100644 milena/sandbox/scribo/table/repair_horizontal_lines.hh
create mode 100644 milena/sandbox/scribo/table/repair_vertical_lines.hh
create mode 100644 milena/sandbox/scribo/text/extract_bboxes.hh
create mode 100644 milena/sandbox/scribo/text/grouping/group_from_double_link.hh
create mode 100644 milena/sandbox/scribo/text/grouping/group_from_multiple_links.hh
create mode 100644 milena/sandbox/scribo/text/grouping/group_from_single_link.hh
create mode 100644 milena/sandbox/scribo/text/grouping/group_with_multiple_links.hh
create mode 100644 milena/sandbox/scribo/text/grouping/group_with_single_left_link.hh
create mode 100644 milena/sandbox/scribo/text/grouping/group_with_single_right_link.hh
copy milena/sandbox/scribo/{photo.cc => text/grouping/internal/find_root.hh} (52%)
rename milena/sandbox/scribo/{photo.cc => text/grouping/internal/init_link_array.hh} (52%)
create mode 100644 milena/sandbox/scribo/text/grouping/internal/update_link_array.hh
create mode 100644 milena/sandbox/scribo/text/grouping/internal/update_link_graph.hh
create mode 100644 milena/sandbox/scribo/text/recognition.hh
diff --git a/milena/sandbox/ChangeLog b/milena/sandbox/ChangeLog
index 4b4d75e..beea9cf 100644
--- a/milena/sandbox/ChangeLog
+++ b/milena/sandbox/ChangeLog
@@ -1,3 +1,55 @@
+2009-03-10 Guillaume Lazzara <z(a)lrde.epita.fr>
+
+ Split Scribo's code into several routines.
+
+ * scribo/Makefile: update include path.
+
+ * scribo/core/central_sites.hh,
+ * scribo/core/component_bboxes.hh,
+ * scribo/core/erase_bboxes.hh,
+ * scribo/core/macros.hh,
+ * scribo/debug/save_label_image.hh,
+ * scribo/debug/save_linked_textbboxes_image.hh,
+ * scribo/debug/save_table_image.hh,
+ * scribo/debug/save_textbboxes_image.hh,
+ * scribo/draw/bounding_box_links.hh,
+ * scribo/draw/bounding_boxes.hh,
+ * scribo/make/debug_filename.hh,
+ * scribo/make/influence_zone_graph.hh,
+ * scribo/table/align_lines_horizontaly.hh,
+ * scribo/table/align_lines_verticaly.hh,
+ * scribo/table/connect_horizontal_lines.hh,
+ * scribo/table/connect_vertical_lines.hh,
+ * scribo/table/erase.hh,
+ * scribo/table/extract_lines_with_rank.hh,
+ * scribo/table/internal/align_lines.hh,
+ * scribo/table/internal/connect_lines.hh,
+ * scribo/table/internal/repair_lines.hh,
+ * scribo/table/repair_horizontal_lines.hh,
+ * scribo/table/repair_vertical_lines.hh,
+ * scribo/text/extract_bboxes.hh,
+ * scribo/text/grouping/group_from_double_link.hh,
+ * scribo/text/grouping/group_from_multiple_links.hh,
+ * scribo/text/grouping/group_from_single_link.hh,
+ * scribo/text/grouping/group_with_multiple_links.hh,
+ * scribo/text/grouping/group_with_single_left_link.hh,
+ * scribo/text/grouping/group_with_single_right_link.hh,
+ * scribo/text/grouping/internal/find_root.hh,
+ * scribo/text/grouping/internal/init_link_array.hh,
+ * scribo/text/grouping/internal/update_link_array.hh,
+ * scribo/text/grouping/internal/update_link_graph.hh,
+ * scribo/text/recognition.hh: new routines.
+
+ * scribo/photo.cc,
+ * scribo/table.cc: move...
+ * scribo/src/photo.cc,
+ * scribo/src/table.cc: ... here.
+
+ * scribo/src/extract_text_double_link.cc,
+ * scribo/src/extract_text_multiple_links.cc,
+ * scribo/src/extract_text_single_link.cc: new small test related to
+ text extraction.
+
2009-03-10 Fabien Freling <fabien.freling(a)lrde.epita.fr>
Implement 3D watershed and various tools.
diff --git a/milena/sandbox/scribo/Makefile b/milena/sandbox/scribo/Makefile
index 5d09e02..cbb462b 100644
--- a/milena/sandbox/scribo/Makefile
+++ b/milena/sandbox/scribo/Makefile
@@ -1,16 +1,31 @@
all: table photo
tabledbg: demat.hh
- g++ -Wextra -Wall -I../.. -I$(HOME)/local/include -O1 -g table.cc $(HOME)/local/lib/libtesseract_full.a -lpthread -o table
+ g++ -Wextra -Wall -I../.. -I../ -I$(HOME)/local/include -O1 -g src/table.cc $(HOME)/local/lib/libtesseract_full.a -lpthread -o bin/table.out
table: demat.hh
- g++ -Wextra -Wall -I../.. -I$(HOME)/local/include -O1 -DNDEBUG table.cc $(HOME)/local/lib/libtesseract_full.a -lpthread -o table
+ g++ -Wextra -Wall -I../.. -I. -I.. -I$(HOME)/local/include -O1 -DNDEBUG src/table.cc $(HOME)/local/lib/libtesseract_full.a -lpthread -o bin/table.out
+
+oldtable: demat.old.hh
+ g++ -Wextra -Wall -I../.. -I../ -I$(HOME)/local/include -O1 -DNDEBUG src/table_old.cc $(HOME)/local/lib/libtesseract_full.a -lpthread -o bin/table_old.out
photo: demat.hh
- g++ -Wextra -Wall -I../.. -I$(HOME)/local/include -O1 -DNDEBUG photo.cc $(HOME)/local/lib/libtesseract_full.a -lpthread -o photo
+ g++ -Wextra -Wall -I../.. -I. -I.. -I$(HOME)/local/include -O1 -DNDEBUG src/photo.cc $(HOME)/local/lib/libtesseract_full.a -lpthread -o bin/photo.out
+
+
+
+extract_text_single_link:
+ g++ -Wextra -Wall -I../.. -I../ -I$(HOME)/local/include -O1 -DNDEBUG src/extract_text_single_link.cc -o bin/extract_text_single_link.out
+
+extract_text_double_link:
+ g++ -Wextra -Wall -I../.. -I../ -I$(HOME)/local/include -O1 -DNDEBUG src/extract_text_double_link.cc -o bin/extract_text_double_link.out
+
+extract_text_multiple_links:
+ g++ -Wextra -Wall -I../.. -I../ -I$(HOME)/local/include -O1 -DNDEBUG src/extract_text_multiple_links.cc -o bin/extract_text_multiple_links.out
+
clean:
rm *.ppm *.pgm *.pbm
dist-clean: clean
- rm -f table photo
+ rm -f bin/table.out bin/photo.out
diff --git a/milena/sandbox/scribo/core/central_sites.hh b/milena/sandbox/scribo/core/central_sites.hh
new file mode 100644
index 0000000..fe47625
--- /dev/null
+++ b/milena/sandbox/scribo/core/central_sites.hh
@@ -0,0 +1,97 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_CORE_CENTRAL_SITES_HH
+# define SCRIBO_CORE_CENTRAL_SITES_HH
+
+/// \file scribo/core/central_sites.hh
+///
+/// Returns the edge central sites of a box.
+
+# include <mln/util/couple.hh>
+# include <mln/core/site_set/box.hh>
+
+namespace scribo
+{
+ using namespace mln;
+
+ /// Returns the edge central sites of a box
+ ///
+ /// \param[in] b the bbbox
+ /// \param[in] dim the dimension used to compute the site.
+ /*!
+ **
+ ** If dim == 0, returns the left and right central sites.
+ **
+ ** |-------| \n
+ ** X X \n
+ ** |-------| \n
+ **
+ ** If dim == 1, returns the top and bottom central sites.
+ **
+ ** |---X---| \n
+ ** | | \n
+ ** |---X---| \n
+ **
+ **
+ ** ... And so on.
+ **
+ */
+ template <typename P>
+ util::couple<P,P>
+ central_sites(const box<P>& b, unsigned dim);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename P>
+ inline
+ util::couple<P,P>
+ central_sites(const box<P>& b, unsigned dim)
+ {
+ trace::entering("scribo::central_sites");
+ mln_precondition(b.is_valid());
+
+ unsigned n = b.pmax()[dim] - b.pmin()[dim];
+
+ P p1 = b.center();
+ p1[dim] -= n / 2;
+ P p2 = b.center();
+ p2[dim] += n / 2;
+
+ trace::exiting("scribo::central_sites");
+ return make::couple(p1, p2);
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_CORE_CENTRAL_SITES_HH
diff --git a/milena/sandbox/scribo/core/component_bboxes.hh b/milena/sandbox/scribo/core/component_bboxes.hh
new file mode 100644
index 0000000..5af99fc
--- /dev/null
+++ b/milena/sandbox/scribo/core/component_bboxes.hh
@@ -0,0 +1,85 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_CORE_COMPONENT_BBOXES_HH
+# define SCRIBO_CORE_COMPONENT_BBOXES_HH
+
+/// \file scribo/core/component_bboxes.hh
+///
+/// Extract the bounding boxes of image components.
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/neighborhood.hh>
+# include <mln/core/site_set/box.hh>
+
+# include <mln/labeling/blobs.hh>
+# include <mln/labeling/compute.hh>
+
+# include <mln/util/array.hh>
+
+
+namespace scribo
+{
+
+ /// Extract the components bboxes.
+ template <typename I, typename N, typename V>
+ util::array< box<mln_site(I)> >
+ component_bboxes(const Image<I>& input,
+ const Neighborhood<N>& nbh, const V& label_type);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename N, typename V>
+ inline
+ util::array< box<mln_site(I)> >
+ component_bboxes(const Image<I>& input,
+ const Neighborhood<N>& nbh, const V&)
+ {
+ trace::entering("scribo::component_bboxes");
+
+ mlc_equal(mln_value(I),bool)::check();
+ mlc_is_a(V, mln::value::Symbolic)::check();
+ mln_precondition(exact(input).is_valid());
+ mln_precondition(exact(nbh).is_valid());
+
+ V nbboxes;
+ mln_ch_value(I,V) lbl = labeling::blobs(input, nbh, nbboxes);
+ typedef util::array< box<mln_site(I)> > bboxes_t;
+ bboxes_t bboxes = labeling::compute(accu::meta::bbox(), lbl, nbboxes);
+
+ trace::exiting("scribo::component_bboxes");
+ return bboxes;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_CORE_COMPONENT_BBOXES_HH
diff --git a/milena/sandbox/scribo/photo.cc b/milena/sandbox/scribo/core/erase_bboxes.hh
similarity index 51%
copy from milena/sandbox/scribo/photo.cc
copy to milena/sandbox/scribo/core/erase_bboxes.hh
index a173750..cea998b 100644
--- a/milena/sandbox/scribo/photo.cc
+++ b/milena/sandbox/scribo/core/erase_bboxes.hh
@@ -1,4 +1,5 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -25,40 +26,56 @@
// reasons why the executable file might be covered by the GNU General
// Public License.
+#ifndef SCRIBO_CORE_ERASE_BBOXES_HH
+# define SCRIBO_CORE_ERASE_BBOXES_HH
-#include "demat.hh"
+/// \file scribo/core/erase_bboxes.hh
+///
+/// Remove the content of bounding boxes from an image.
-int main(int argc, char*argv[])
+# include <mln/core/concept/image.hh>
+# include <mln/core/site_set/box.hh>
+# include <mln/data/paste.hh>
+# include <mln/pw/all.hh>
+# include <mln/util/array.hh>
+
+# include <scribo/core/macros.hh>
+
+namespace scribo
{
- using namespace mln;
- using value::int_u8;
- if (argc < 2)
+ /// Remove the content of bounding boxes from an image.
+ template <typename I>
+ void
+ erase_bboxes(Image<I>& input_,
+ const util::array< box<mln_site(I)> >& bboxes);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ void
+ erase_bboxes(Image<I>& input_,
+ const util::array< box<mln_site(I)> >& bboxes)
{
- std::cout << argv[0] << " <in.pbm> <out.pgm> <l> <bbox_larger> <bbox_distance> <min_comp_nsites>" << std::endl
- << std::endl << std::endl
- << std::endl
- << "=========="
- << std::endl << std::endl
- << "<in.pbm> B/W inverted input image."
- << std::endl << std::endl
-/* << "<out.ppm> RGB8 output image."
- << std::endl << std::endl
- << "<bbox_distance> Maximum distance between character bounding boxes. Used for bbox grouping."
- << std::endl << std::endl
- << "<min_comp_nsites> Minimum site count of a character/text component."
- << std::endl
- << " If a component have a site count lesser than this value, it is erased."
- << std::endl << std::endl
- << std::endl*/
- << "=========="
- << std::endl << std::endl
- << "HINT: compile with -DNOUT to avoid debug images."
- << std::endl << std::endl;
- return 1;
+ trace::entering("scribo::erase_bboxes");
+
+ mlc_equal(mln_value(I),bool)::check();
+
+ I& input = exact(input_);
+ mln_precondition(input.is_valid());
+
+ for_all_components(i, bboxes)
+ data::paste((pw::cst(false) | bboxes[i] |
+ (pw::value(input) == true)), input);
+
+ trace::exiting("scribo::erase_bboxes");
}
- scribo::demat_photo(argv);
- return 0;
-}
+# endif // ! MLN_INCLUDE_ONLY
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_CORE_ERASE_BBOXES_HH
diff --git a/milena/sandbox/scribo/photo.cc b/milena/sandbox/scribo/core/macros.hh
similarity index 52%
copy from milena/sandbox/scribo/photo.cc
copy to milena/sandbox/scribo/core/macros.hh
index a173750..91a335c 100644
--- a/milena/sandbox/scribo/photo.cc
+++ b/milena/sandbox/scribo/core/macros.hh
@@ -1,4 +1,5 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -25,40 +26,16 @@
// reasons why the executable file might be covered by the GNU General
// Public License.
+#ifndef SCRIBO_CORE_MACROS_HH
+# define SCRIBO_CORE_MACROS_HH
-#include "demat.hh"
+# define for_all_ncomponents(C, NCOMP) \
+ for (unsigned C = 1; C <= NCOMP; ++C)
-int main(int argc, char*argv[])
-{
- using namespace mln;
- using value::int_u8;
+# define for_all_components(C, S) \
+ for (unsigned C = 1; C < S.nelements(); ++C)
- if (argc < 2)
- {
- std::cout << argv[0] << " <in.pbm> <out.pgm> <l> <bbox_larger> <bbox_distance> <min_comp_nsites>" << std::endl
- << std::endl << std::endl
- << std::endl
- << "=========="
- << std::endl << std::endl
- << "<in.pbm> B/W inverted input image."
- << std::endl << std::endl
-/* << "<out.ppm> RGB8 output image."
- << std::endl << std::endl
- << "<bbox_distance> Maximum distance between character bounding boxes. Used for bbox grouping."
- << std::endl << std::endl
- << "<min_comp_nsites> Minimum site count of a character/text component."
- << std::endl
- << " If a component have a site count lesser than this value, it is erased."
- << std::endl << std::endl
- << std::endl*/
- << "=========="
- << std::endl << std::endl
- << "HINT: compile with -DNOUT to avoid debug images."
- << std::endl << std::endl;
- return 1;
- }
+# define for_all_elements(E, S) \
+ for (unsigned E = 0; E < S.nelements(); ++E)
- scribo::demat_photo(argv);
-
- return 0;
-}
+#endif // ! SCRIBO_CORE_MACROS_HH
diff --git a/milena/sandbox/scribo/photo.cc b/milena/sandbox/scribo/debug/save_label_image.hh
similarity index 52%
copy from milena/sandbox/scribo/photo.cc
copy to milena/sandbox/scribo/debug/save_label_image.hh
index a173750..e9b01f1 100644
--- a/milena/sandbox/scribo/photo.cc
+++ b/milena/sandbox/scribo/debug/save_label_image.hh
@@ -1,4 +1,5 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -26,39 +27,49 @@
// Public License.
-#include "demat.hh"
+#ifndef SCRIBO_MAKE_DEBUG_SAVE_LABEL_IMAGE_HH
+# define SCRIBO_MAKE_DEBUG_SAVE_LABEL_IMAGE_HH
-int main(int argc, char*argv[])
+/// \file scribo/debug/save_label_image.hh
+///
+/// Save a labeled image in a color image.
+
+namespace scribo
{
- using namespace mln;
- using value::int_u8;
- if (argc < 2)
+ namespace debug
{
- std::cout << argv[0] << " <in.pbm> <out.pgm> <l> <bbox_larger> <bbox_distance> <min_comp_nsites>" << std::endl
- << std::endl << std::endl
- << std::endl
- << "=========="
- << std::endl << std::endl
- << "<in.pbm> B/W inverted input image."
- << std::endl << std::endl
-/* << "<out.ppm> RGB8 output image."
- << std::endl << std::endl
- << "<bbox_distance> Maximum distance between character bounding boxes. Used for bbox grouping."
- << std::endl << std::endl
- << "<min_comp_nsites> Minimum site count of a character/text component."
- << std::endl
- << " If a component have a site count lesser than this value, it is erased."
- << std::endl << std::endl
- << std::endl*/
- << "=========="
- << std::endl << std::endl
- << "HINT: compile with -DNOUT to avoid debug images."
- << std::endl << std::endl;
- return 1;
- }
-
- scribo::demat_photo(argv);
-
- return 0;
-}
+
+ /// Save a labeled image in a color image.
+ template <typename I>
+ void
+ save_label_image(const Image<I>& lbl, const mln_value(I)& nlabels,
+ const char *filename);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I>
+ inline
+ void
+ save_label_image(const Image<I>& lbl, const mln_value(I)& nlabels,
+ const char *filename)
+ {
+ trace::entering("scribo::debug::save_label_image");
+ mlc_is_a(mln_value(I), mln::value::Symbolic)::check();
+ mln_precondition(exact(lbl).is_valid());
+
+ io::ppm::save(debug::colorize(rgb8(), lbl, nlabels), filename);
+
+ trace::exiting("scribo::debug::save_label_image");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::debug
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_MAKE_DEBUG_SAVE_LABEL_IMAGE_HH
diff --git a/milena/sandbox/scribo/debug/save_linked_textbboxes_image.hh b/milena/sandbox/scribo/debug/save_linked_textbboxes_image.hh
new file mode 100644
index 0000000..a7f8927
--- /dev/null
+++ b/milena/sandbox/scribo/debug/save_linked_textbboxes_image.hh
@@ -0,0 +1,170 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_DEBUG_SAVE_LINKED_TEXTBBOXES_IMAGE_HH
+# define SCRIBO_DEBUG_SAVE_LINKED_TEXTBBOXES_IMAGE_HH
+
+/// \file scribo/draw/bounding_boxes.hh
+///
+/// Save the bounding box links image.
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/graph.hh>
+# include <mln/level/convert.hh>
+# include <mln/value/rgb8.hh>
+# include <mln/util/array.hh>
+# include <mln/io/ppm/save.hh>
+
+# include <scribo/draw/bounding_boxes.hh>
+# include <scribo/draw/bounding_box_links.hh>
+
+
+namespace scribo
+{
+
+ namespace debug
+ {
+
+ using namespace mln;
+
+
+ /// Save the bounding box links image.
+ template <typename I>
+ void
+ save_linked_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const util::array<unsigned>& link_array,
+ const value::rgb8& box_value,
+ const value::rgb8& link_value,
+ const std::string& filename);
+
+
+ template <typename I>
+ void
+ save_linked_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const util::array<unsigned>& left_link,
+ const util::array<unsigned>& right_array,
+ const value::rgb8& box_value,
+ const value::rgb8& left_link_value,
+ const value::rgb8& right_link_value,
+ const std::string& filename);
+
+
+ template <typename I, typename G>
+ void
+ save_linked_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const Graph<G>& g,
+ const value::rgb8& box_value,
+ const value::rgb8& link_value,
+ const std::string& filename);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ inline
+ void
+ save_linked_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const util::array<unsigned>& link_array,
+ const value::rgb8& box_value,
+ const value::rgb8& link_value,
+ const std::string& filename)
+ {
+ trace::entering("scribo::debug::save_linked_textbboxes_image");
+ mln_precondition(exact(input).is_valid());
+
+ mln_ch_value(I,value::rgb8) tmp = level::convert(value::rgb8(), input);
+ draw::bounding_boxes(tmp, textbboxes, box_value);
+ draw::bounding_box_links(tmp, textbboxes, link_array, link_value);
+ io::ppm::save(tmp, filename);
+
+ trace::exiting("scribo::debug::save_linked_textbboxes_image");
+ }
+
+
+ template <typename I>
+ inline
+ void
+ save_linked_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const util::array<unsigned>& left_link,
+ const util::array<unsigned>& right_link,
+ const value::rgb8& box_value,
+ const value::rgb8& left_value,
+ const value::rgb8& right_value,
+ const std::string& filename)
+ {
+ trace::entering("scribo::debug::save_linked_textbboxes_image");
+ mln_precondition(exact(input).is_valid());
+
+ mln_ch_value(I,value::rgb8) tmp = level::convert(value::rgb8(), input);
+ draw::bounding_boxes(tmp, textbboxes, box_value);
+ draw::bounding_box_links(tmp, textbboxes,
+ left_link, right_link,
+ left_value, right_value);
+ io::ppm::save(tmp, filename);
+
+ trace::exiting("scribo::debug::save_linked_textbboxes_image");
+ }
+
+
+ template <typename I, typename G>
+ inline
+ void
+ save_linked_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const Graph<G>& g,
+ const value::rgb8& box_value,
+ const value::rgb8& link_value,
+ const std::string& filename)
+ {
+ trace::entering("scribo::debug::save_linked_textbboxes_image");
+ mln_precondition(exact(g).is_valid());
+ mln_precondition(exact(input).is_valid());
+
+ mln_ch_value(I,value::rgb8) tmp = level::convert(value::rgb8(), input);
+ draw::bounding_boxes(tmp, textbboxes, box_value);
+ draw::bounding_box_links(tmp, textbboxes, g, link_value);
+ io::ppm::save(tmp, filename);
+
+ trace::exiting("scribo::debug::save_linked_textbboxes_image");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::debug
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_DEBUG_SAVE_LINKED_TEXTBBOXES_IMAGE_HH
diff --git a/milena/sandbox/scribo/debug/save_table_image.hh b/milena/sandbox/scribo/debug/save_table_image.hh
new file mode 100644
index 0000000..b170420
--- /dev/null
+++ b/milena/sandbox/scribo/debug/save_table_image.hh
@@ -0,0 +1,97 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_DEBUG_SAVE_TABLE_IMAGE_HH
+# define SCRIBO_DEBUG_SAVE_TABLE_IMAGE_HH
+
+/// \file scribo/debug/save_table_image.hh
+///
+/// Save table line bounding boxes in an image.
+
+# include <string>
+
+# include <mln/core/concept/image.hh>
+# include <mln/data/fill.hh>
+# include <mln/util/array.hh>
+# include <mln/util/couple.hh>
+# include <mln/value/rgb8.hh>
+# include <mln/io/ppm/save.hh>
+
+# include <scribo/draw/bounding_boxes.hh>
+
+namespace scribo
+{
+
+ namespace debug
+ {
+
+ /// Save lines bounding boxes in an image filled with \p bg_color.
+ /// Bounding boxes are displayed with \p bbox_color.
+ template <typename I>
+ void
+ save_table(const Image<I>& input_,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > > tableboxes,
+ const value::rgb8& bg_color,
+ const value::rgb8& bbox_color,
+ const std::string& filename);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ void
+ save_table(const Image<I>& input_,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > > tableboxes,
+ const value::rgb8& bg_color,
+ const value::rgb8& bbox_color,
+ const std::string& filename)
+ {
+ trace::entering("scribo::debug::save_table_image");
+ const I& input = exact(input_);
+ mln_precondition(input.is_valid());
+
+ mln_ch_value(I,value::rgb8) out2(exact(input).domain());
+ data::fill(out2, bg_color);
+ draw::bounding_boxes(out2, tableboxes.first(), bbox_color);
+ draw::bounding_boxes(out2, tableboxes.second(), bbox_color);
+ io::ppm::save(out2, filename);
+
+ trace::exiting("scribo::internal::save_table");
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::debug
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_DEBUG_SAVE_TABLE_IMAGE_HH
diff --git a/milena/sandbox/scribo/debug/save_textbboxes_image.hh b/milena/sandbox/scribo/debug/save_textbboxes_image.hh
new file mode 100644
index 0000000..b210b39
--- /dev/null
+++ b/milena/sandbox/scribo/debug/save_textbboxes_image.hh
@@ -0,0 +1,90 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_DEBUG_SAVE_TEXTBBOXES_IMAGE_HH
+# define SCRIBO_DEBUG_SAVE_TEXTBBOXES_IMAGE_HH
+
+/// \file scribo/draw/bounding_boxes.hh
+///
+/// Draw a list of bounding boxes and their associated mass center.
+
+# include <mln/core/concept/image.hh>
+# include <mln/level/convert.hh>
+# include <mln/value/rgb8.hh>
+# include <mln/util/array.hh>
+# include <mln/io/ppm/save.hh>
+
+# include <scribo/draw/bounding_boxes.hh>
+
+
+namespace scribo
+{
+
+ namespace debug
+ {
+
+ using namespace mln;
+
+
+ /// Draw a list of bounding boxes and their associated mass center.
+ template <typename I>
+ void
+ save_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const value::rgb8& value,
+ const std::string& filename);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I>
+ inline
+ void
+ save_textbboxes_image(const Image<I>& input,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const value::rgb8& value,
+ const std::string& filename)
+ {
+ trace::entering("scribo::debug::save_textbboxes_image");
+ mln_precondition(exact(input).is_valid());
+
+ mln_ch_value(I,value::rgb8) tmp = level::convert(value::rgb8(), input);
+ draw::bounding_boxes(tmp, textbboxes, value);
+ io::ppm::save(tmp, filename);
+
+ trace::exiting("scribo::debug::save_textbboxes_image");
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::debug
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_DEBUG_SAVE_TEXTBBOXES_IMAGE_HH
diff --git a/milena/sandbox/scribo/draw/bounding_box_links.hh b/milena/sandbox/scribo/draw/bounding_box_links.hh
new file mode 100644
index 0000000..7cf57ac
--- /dev/null
+++ b/milena/sandbox/scribo/draw/bounding_box_links.hh
@@ -0,0 +1,197 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_DRAW_BOUNDING_BOX_LINKS_HH
+# define SCRIBO_DRAW_BOUNDING_BOX_LINKS_HH
+
+/// \file scribo/draw/bounding_boxes.hh
+///
+/// Draw a list of bounding box links.
+
+# include <mln/core/concept/image.hh>
+# include <mln/draw/line.hh>
+# include <mln/util/array.hh>
+# include <mln/canvas/browsing/depth_first_search.hh>
+
+# include <scribo/core/macros.hh>
+
+namespace scribo
+{
+
+ namespace draw
+ {
+
+ using namespace mln;
+
+ /// Draw a list of bounding box links.
+ template <typename I>
+ void
+ bounding_box_links(Image<I>& input_,
+ const util::array< box<mln_site(I)> >& bboxes,
+ const util::array<unsigned>& link_array,
+ const mln_value(I)& value);
+
+
+ template <typename I>
+ void
+ bounding_box_links(Image<I>& input,
+ const util::array< box<mln_site(I)> >& bboxes,
+ const util::array<unsigned>& left_link,
+ const util::array<unsigned>& right_link,
+ const mln_value(I)& left_link_value,
+ const mln_value(I)& right_link_value);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ namespace internal
+ {
+ /// Functor to be passed to depth_first_search.
+ template <typename I>
+ struct draw_graph_edges_functor
+ {
+
+ draw_graph_edges_functor(I& ima,
+ const util::array<box<mln_site(I)> >& textbboxes,
+ const mln_value(I)& value)
+ : ima_(ima), textbboxes_(textbboxes), value_(value)
+ {}
+
+ template <typename G>
+ void
+ init(const Graph<G>& g)
+ { deja_vu.resize(exact(g).v_nmax(), false); }
+
+ void final()
+ {}
+
+ void next_component()
+ {}
+
+ void new_component_from_vertex(unsigned)
+ {}
+
+ void added_to_queue(unsigned id)
+ {
+ deja_vu[id] = true;
+ mln::draw::line(ima_, textbboxes_[current_vertex].center(),
+ textbboxes_[id].center(), value_);
+ }
+
+ void process_vertex(unsigned id)
+ { current_vertex = id; }
+
+ bool to_be_treated(unsigned id)
+ { return ! deja_vu[id]; }
+
+ bool to_be_queued(unsigned id)
+ { return to_be_treated(id); }
+
+ I& ima_;
+ const util::array<box<mln_site(I)> >& textbboxes_;
+ mln_value(I) value_;
+ unsigned current_vertex;
+ std::vector<bool> deja_vu;
+ };
+
+ } // end of namespace scribo::text::grouping::internal
+
+
+ template <typename I>
+ inline
+ void
+ bounding_box_links(Image<I>& input_,
+ const util::array< box<mln_site(I)> >& bboxes,
+ const util::array<unsigned>& link_array,
+ 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, link_array)
+ if (link_array[i] != i)
+ mln::draw::line(input,
+ bboxes[i].center(),
+ bboxes[link_array[i]].center(),
+ value);
+
+ trace::exiting("scribo::draw::bounding_box_links");
+ }
+
+
+ template <typename I>
+ inline
+ void
+ bounding_box_links(Image<I>& input,
+ const util::array< box<mln_site(I)> >& bboxes,
+ const util::array<unsigned>& left_link,
+ const util::array<unsigned>& right_link,
+ const mln_value(I)& left_link_value,
+ const mln_value(I)& right_link_value)
+ {
+ trace::entering("scribo::draw::bounding_box_links");
+ mln_precondition(exact(input).is_valid());
+
+ bounding_box_links(input, bboxes, left_link, left_link_value);
+ bounding_box_links(input, bboxes, right_link, right_link_value);
+
+ trace::exiting("scribo::draw::bounding_box_links");
+ }
+
+
+ template <typename I, typename G>
+ inline
+ void
+ bounding_box_links(Image<I>& input,
+ const util::array< box<mln_site(I)> >& bboxes,
+ const Graph<G>& g,
+ const mln_value(I)& link_value)
+ {
+ trace::entering("scribo::draw::bounding_box_links");
+ mln_precondition(exact(input).is_valid());
+ 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);
+
+ trace::exiting("scribo::draw::bounding_box_links");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::draw
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_DRAW_BOUNDING_BOX_LINKS_HH
diff --git a/milena/sandbox/scribo/draw/bounding_boxes.hh b/milena/sandbox/scribo/draw/bounding_boxes.hh
new file mode 100644
index 0000000..0db60a4
--- /dev/null
+++ b/milena/sandbox/scribo/draw/bounding_boxes.hh
@@ -0,0 +1,93 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_DRAW_BOUNDING_BOXES_HH
+# define SCRIBO_DRAW_BOUNDING_BOXES_HH
+
+/// \file scribo/draw/bounding_boxes.hh
+///
+/// Draw a list of bounding boxes and their associated mass center.
+
+# include <mln/core/concept/image.hh>
+# include <mln/draw/box.hh>
+# include <mln/util/array.hh>
+
+# include <scribo/core/macros.hh>
+
+namespace scribo
+{
+
+ namespace draw
+ {
+
+ using namespace mln;
+
+ /// Draw a list of bounding boxes and their associated mass center.
+ template <typename I>
+ void
+ bounding_boxes(Image<I>& input_,
+ const util::array< box<mln_site(I)> >& boxes,
+ const mln_value(I)& value);
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ inline
+ void
+ bounding_boxes(Image<I>& input_,
+ const util::array< box<mln_site(I)> >& boxes,
+ const mln_value(I)& value)
+ {
+ trace::entering("scribo::draw::bounding_boxes");
+
+ I& input = exact(input_);
+
+ mln_precondition(input.is_valid());
+
+ 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");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::draw
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_DRAW_BOUNDING_BOXES_HH
diff --git a/milena/sandbox/scribo/photo.cc b/milena/sandbox/scribo/make/debug_filename.hh
similarity index 52%
copy from milena/sandbox/scribo/photo.cc
copy to milena/sandbox/scribo/make/debug_filename.hh
index a173750..b159328 100644
--- a/milena/sandbox/scribo/photo.cc
+++ b/milena/sandbox/scribo/make/debug_filename.hh
@@ -1,4 +1,5 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -26,39 +27,61 @@
// Public License.
-#include "demat.hh"
+#ifndef SCRIBO_MAKE_DEBUG_FILENAME_HH
+# define SCRIBO_MAKE_DEBUG_FILENAME_HH
-int main(int argc, char*argv[])
+/// \file scribo/make/debug_filename.hh
+///
+/// Construct and returns a formated output file name.
+
+# include <sstream>
+
+
+namespace scribo
{
- using namespace mln;
- using value::int_u8;
- if (argc < 2)
+ namespace make
{
- std::cout << argv[0] << " <in.pbm> <out.pgm> <l> <bbox_larger> <bbox_distance> <min_comp_nsites>" << std::endl
- << std::endl << std::endl
- << std::endl
- << "=========="
- << std::endl << std::endl
- << "<in.pbm> B/W inverted input image."
- << std::endl << std::endl
-/* << "<out.ppm> RGB8 output image."
- << std::endl << std::endl
- << "<bbox_distance> Maximum distance between character bounding boxes. Used for bbox grouping."
- << std::endl << std::endl
- << "<min_comp_nsites> Minimum site count of a character/text component."
- << std::endl
- << " If a component have a site count lesser than this value, it is erased."
- << std::endl << std::endl
- << std::endl*/
- << "=========="
- << std::endl << std::endl
- << "HINT: compile with -DNOUT to avoid debug images."
- << std::endl << std::endl;
- return 1;
- }
-
- scribo::demat_photo(argv);
-
- return 0;
-}
+
+ /// Construct and returns a formated output file name:
+ ///
+ /// `input_filename`_`id`_`name`
+ std::string
+ debug_filename(const char *input_filename,
+ const char *name);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ inline
+ std::string
+ debug_filename(const char *input_filename,
+ const char *name)
+ {
+ static int file_id = 1;
+
+ std::ostringstream os;
+ os << "./"
+ << input_filename
+ << "_";
+
+ if (file_id < 10)
+ os << "0";
+
+ os << file_id++
+ << "_"
+ << name;
+ return os.str();
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::make
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_MAKE_DEBUG_FILENAME_HH
diff --git a/milena/sandbox/scribo/make/influence_zone_graph.hh b/milena/sandbox/scribo/make/influence_zone_graph.hh
new file mode 100644
index 0000000..c3ad15e
--- /dev/null
+++ b/milena/sandbox/scribo/make/influence_zone_graph.hh
@@ -0,0 +1,121 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_MAKE_INFLUENCE_ZONE_GRAPH_HH
+# define SCRIBO_MAKE_INFLUENCE_ZONE_GRAPH_HH
+
+/// \file scribo/make/influence_zone_graph.hh
+///
+/// Create a region adjacency graph from the influence zone image
+/// of binary image.
+
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/neighborhood.hh>
+
+# include <mln/labeling/blobs.hh>
+
+# include <mln/transform/influence_zone_geodesic.hh>
+
+# include <mln/util/graph.hh>
+
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ using namespace mln;
+
+
+ /// Compute a labeled image of input, then compute an influence
+ /// zone image and make a graph from it.
+ ///
+ /// \param[in] input_ a binary image.
+ /// \param[in] nbh_ a neighbordhood.
+ /// \param[in] label_type The type of this argument is used
+ /// as label type while labeling the image.
+ /// \param[in] iz_dmax Max distance of the influence zone.
+ ///
+ /// \return a region adjacency graph.
+ template <typename I, typename V>
+ util::graph
+ influence_zone_graph(const Image<I>& input_,
+ const Neighborhood<N>& nbh_,
+ const V& label_type,
+ unsigned iz_dmax);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename V>
+ util::graph
+ influence_zone_graph(const Image<I>& input_,
+ const Neighborhood<N>& nbh_,
+ const V& label_type,
+ unsigned iz_dmax)
+ {
+ trace::entering("scribo::make::influence_zone_graph");
+
+ (void) label_type;
+ I& input = exact(input_);
+ const N& nbh = exact(nbh_);
+
+ mlc_is_equal(mln_value(I), bool)::check();
+ mln_assertion(input.is_valid());
+ mln_assertion(nbh.is_valid());
+
+ V nlabels;
+ typedef mln_ch_value(I,V) lbl_t;
+ lbl_t lbl = labeling::blobs(input, nbh, nlabels);
+
+ lbl_t iz = transform::influence_zone_geodesic(lbl, nbh, iz_dmax);
+
+ util::graph g = make::graph(iz | (pw::value(iz) != pw::cst(literal::zero)),
+ nbh, nlabels);
+
+ trace::exiting("scribo::make::influence_zone_graph");
+ return g;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+
+
+#endif // ! SCRIBO_MAKE_INFLUENCE_ZONE_GRAPH_HH
+
diff --git a/milena/sandbox/scribo/src/extract_text_double_link.cc b/milena/sandbox/scribo/src/extract_text_double_link.cc
new file mode 100644
index 0000000..26fccff
--- /dev/null
+++ b/milena/sandbox/scribo/src/extract_text_double_link.cc
@@ -0,0 +1,109 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to
+// produce an executable, this file does not by itself cause the
+// resulting executable to be covered by the GNU General Public
+// License. This exception does not however invalidate any other
+// reasons why the executable file might be covered by the GNU General
+// Public License.
+
+#include <iostream>
+
+#include <mln/essential/2d.hh>
+
+#include <scribo/text/extract_bboxes.hh>
+#include <scribo/text/grouping/group_with_single_left_link.hh>
+#include <scribo/text/grouping/group_with_single_right_link.hh>
+#include <scribo/debug/save_linked_textbboxes_image.hh>
+#include <scribo/text/grouping/group_from_double_link.hh>
+
+#include <scribo/debug/save_textbboxes_image.hh>
+
+int usage(const char *name)
+{
+ std::cout << "Usage: " << name << " <input.pbm> " << std::endl;
+ return 1;
+}
+
+
+namespace scribo { namespace text { namespace grouping
+{
+ using namespace mln;
+
+ template <typename I>
+ util::array< box<mln_site(I)> >
+ group_from_double_link(const util::array< box<mln_site(I)> >& textbboxes,
+ util::array<unsigned>& left_link,
+ util::array<unsigned>& right_link);
+}}}
+
+int main(int argc, char* argv[])
+{
+ using namespace scribo;
+ using namespace mln;
+
+ if (argc < 1)
+ return usage(argv[0]);
+
+ image2d<bool> input;
+ io::pbm::load(input, argv[1]);
+
+ value::label_16 nbboxes;
+ util::array<box2d> textbboxes = text::extract_bboxes(input, c8(), nbboxes);
+
+ util::array<unsigned> left_link
+ = text::grouping::group_with_single_left_link(input,
+ c8(), nbboxes,
+ textbboxes, 30);
+ util::array<unsigned> right_link
+ = text::grouping::group_with_single_right_link(input,
+ c8(), nbboxes,
+ textbboxes, 30);
+
+ std::cout << "BEFORE - nbboxes = " << nbboxes << std::endl;
+
+ scribo::debug::save_linked_textbboxes_image(input,
+ textbboxes, left_link,
+ literal::red, literal::cyan,
+ "test_double_link_left_linked.ppm");
+ scribo::debug::save_linked_textbboxes_image(input,
+ textbboxes, right_link,
+ literal::red, literal::cyan,
+ "test_double_link_right_linked.ppm");
+
+ scribo::debug::save_linked_textbboxes_image(input,
+ textbboxes, left_link, right_link,
+ literal::red, literal::cyan,
+ literal::yellow,
+ "test_double_link_double_linked.ppm");
+
+ // With validation.
+ util::array< box<point2d> > grouped_textbboxes
+ = text::grouping::group_from_double_link(textbboxes, left_link, right_link);
+
+ std::cout << "AFTER double grouping - nbboxes = " << grouped_textbboxes.nelements() << std::endl;
+
+ scribo::debug::save_textbboxes_image(input, grouped_textbboxes,
+ literal::red,
+ "test_double_link_grouped_text.ppm");
+
+}
+
diff --git a/milena/sandbox/scribo/src/extract_text_multiple_links.cc b/milena/sandbox/scribo/src/extract_text_multiple_links.cc
new file mode 100644
index 0000000..9b181e6
--- /dev/null
+++ b/milena/sandbox/scribo/src/extract_text_multiple_links.cc
@@ -0,0 +1,78 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to
+// produce an executable, this file does not by itself cause the
+// resulting executable to be covered by the GNU General Public
+// License. This exception does not however invalidate any other
+// reasons why the executable file might be covered by the GNU General
+// Public License.
+
+#include <iostream>
+
+#include <mln/essential/2d.hh>
+
+#include <scribo/text/extract_bboxes.hh>
+#include <scribo/text/grouping/group_with_multiple_links.hh>
+#include <scribo/text/grouping/group_from_multiple_links.hh>
+
+#include <scribo/debug/save_textbboxes_image.hh>
+#include <scribo/debug/save_linked_textbboxes_image.hh>
+
+int usage(const char *name)
+{
+ std::cout << "Usage: " << name << " <input.pbm> " << std::endl;
+ return 1;
+}
+
+int main(int argc, char* argv[])
+{
+ using namespace scribo;
+ using namespace mln;
+
+ if (argc < 1)
+ return usage(argv[0]);
+
+ image2d<bool> input;
+ io::pbm::load(input, argv[1]);
+
+ value::label_16 nbboxes;
+ util::array<box2d> textbboxes = text::extract_bboxes(input, c8(), nbboxes);
+
+ util::graph g = text::grouping::group_with_multiple_links(input,
+ c8(), nbboxes,
+ textbboxes, 30);
+
+ std::cout << "BEFORE - nbboxes = " << nbboxes << std::endl;
+ scribo::debug::save_linked_textbboxes_image(input,
+ textbboxes, g,
+ literal::red, literal::cyan,
+ "test_multiple_links_left_linked.ppm");
+
+ util::array< box<point2d> > grouped_textbboxes
+ = text::grouping::group_from_multiple_links(textbboxes, g);
+
+ std::cout << "AFTER - nbboxes = " << grouped_textbboxes.nelements() << std::endl;
+
+ scribo::debug::save_textbboxes_image(input, grouped_textbboxes,
+ literal::red,
+ "test_multiple_links_grouped_text.ppm");
+}
+
diff --git a/milena/sandbox/scribo/src/extract_text_single_link.cc b/milena/sandbox/scribo/src/extract_text_single_link.cc
new file mode 100644
index 0000000..5b4e248
--- /dev/null
+++ b/milena/sandbox/scribo/src/extract_text_single_link.cc
@@ -0,0 +1,108 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to
+// produce an executable, this file does not by itself cause the
+// resulting executable to be covered by the GNU General Public
+// License. This exception does not however invalidate any other
+// reasons why the executable file might be covered by the GNU General
+// Public License.
+
+#include <iostream>
+
+#include <mln/essential/2d.hh>
+
+#include <scribo/text/extract_bboxes.hh>
+#include <scribo/text/grouping/group_with_single_left_link.hh>
+#include <scribo/text/grouping/group_with_single_right_link.hh>
+#include <scribo/text/grouping/group_from_single_link.hh>
+
+#include <scribo/debug/save_textbboxes_image.hh>
+#include <scribo/debug/save_linked_textbboxes_image.hh>
+
+int usage(const char *name)
+{
+ std::cout << "Usage: " << name << " <input.pbm> " << std::endl;
+ return 1;
+}
+
+int main(int argc, char* argv[])
+{
+ using namespace scribo;
+ using namespace mln;
+
+ if (argc < 1)
+ return usage(argv[0]);
+
+ image2d<bool> input;
+ io::pbm::load(input, argv[1]);
+
+ value::label_16 nbboxes;
+ util::array<box2d> textbboxes = text::extract_bboxes(input, c8(), nbboxes);
+
+ {
+ std::cout << "* Left grouping" << std::endl;
+ util::array<unsigned> left_link
+ = text::grouping::group_with_single_left_link(input,
+ c8(), nbboxes,
+ textbboxes, 30);
+
+ std::cout << "BEFORE - nbboxes = " << nbboxes << std::endl;
+ scribo::debug::save_linked_textbboxes_image(input,
+ textbboxes, left_link,
+ literal::red, literal::cyan,
+ "test_single_left_link_linked.ppm");
+
+ util::array< box<point2d> > grouped_textbboxes
+ = text::grouping::group_from_single_link(textbboxes, left_link);
+
+ std::cout << "AFTER - nbboxes = " << grouped_textbboxes.nelements() << std::endl;
+
+ scribo::debug::save_textbboxes_image(input, grouped_textbboxes,
+ literal::red,
+ "test_single_left_link_grouped_text.ppm");
+ }
+
+ {
+ std::cout << "* Left grouping" << std::endl;
+ util::array<unsigned> right_link
+ = text::grouping::group_with_single_right_link(input,
+ c8(), nbboxes,
+ textbboxes, 30);
+
+ std::cout << "BEFORE - nbboxes = " << nbboxes << std::endl;
+ scribo::debug::save_linked_textbboxes_image(input,
+ textbboxes, right_link,
+ literal::red, literal::cyan,
+ "test_single_right_link_linked.ppm");
+
+ util::array< box<point2d> > grouped_textbboxes
+ = text::grouping::group_from_single_link(textbboxes, right_link);
+
+ std::cout << "AFTER - nbboxes = " << grouped_textbboxes.nelements() << std::endl;
+
+ scribo::debug::save_textbboxes_image(input, grouped_textbboxes,
+ literal::red,
+ "test_single_right_link_grouped_text.ppm");
+ }
+
+
+}
+
diff --git a/milena/sandbox/scribo/photo.cc b/milena/sandbox/scribo/src/photo.cc
similarity index 100%
copy from milena/sandbox/scribo/photo.cc
copy to milena/sandbox/scribo/src/photo.cc
diff --git a/milena/sandbox/scribo/table.cc b/milena/sandbox/scribo/src/table.cc
similarity index 100%
rename from milena/sandbox/scribo/table.cc
rename to milena/sandbox/scribo/src/table.cc
diff --git a/milena/sandbox/scribo/table/align_lines_horizontaly.hh b/milena/sandbox/scribo/table/align_lines_horizontaly.hh
new file mode 100644
index 0000000..e75f2f2
--- /dev/null
+++ b/milena/sandbox/scribo/table/align_lines_horizontaly.hh
@@ -0,0 +1,97 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_ALIGN_LINES_HORIZONTALY_HH
+# define SCRIBO_TABLE_ALIGN_LINES_HORIZONTALY_HH
+
+/// \file scribo/table/align_lines_horizontaly.hh
+///
+/// Align line bounding boxes horizontaly.
+
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/site_set/box.hh>
+# include <mln/geom/nrows.hh>
+# include <mln/geom/min_nrow.hh>
+# include <mln/geom/max_nrow.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/table/internal/align_lines.hh>
+
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+ /// Align line bounding boxes horizontaly.
+ ///
+ /// \param[in] input Image from which the line bboxes are
+ /// extracted from.
+ /// \param[in, out] lines_bboxes horizontal lines bounding boxes.
+ ///
+ /// \return A list of the resulting aligned rows. Each integer is actually
+ /// a row number.
+ template <typename I>
+ util::array<int>
+ align_lines_horizontaly(const Image<I>& input,
+ util::array<box<mln_site(I)> >& lines_bboxes);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ util::array<int>
+ align_lines_horizontaly(const Image<I>& input,
+ util::array<box<mln_site(I)> >& lines_bboxes)
+ {
+ trace::entering("scribo::table::align_lines_horizontaly");
+
+ mln_precondition(exact(input).is_valid());
+ util::array<int> res = internal::align_lines(geom::nrows(input),
+ geom::min_row(input),
+ geom::max_row(input),
+ lines_bboxes, 0);
+
+ trace::exiting("scribo::table::align_lines_horizontaly");
+ return res;
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TABLE_ALIGN_LINES_HORIZONTALY_HH
diff --git a/milena/sandbox/scribo/table/align_lines_verticaly.hh b/milena/sandbox/scribo/table/align_lines_verticaly.hh
new file mode 100644
index 0000000..7e860d0
--- /dev/null
+++ b/milena/sandbox/scribo/table/align_lines_verticaly.hh
@@ -0,0 +1,98 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_ALIGN_LINES_VERTICALY_HH
+# define SCRIBO_TABLE_ALIGN_LINES_VERTICALY_HH
+
+/// \file scribo/table/align_lines_verticaly.hh
+///
+/// Align line bounding boxes verticaly.
+
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/site_set/box.hh>
+# include <mln/geom/ncols.hh>
+# include <mln/geom/min_ncol.hh>
+# include <mln/geom/max_ncol.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/table/internal/align_lines.hh>
+
+
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+ /// Align line bounding boxes verticaly.
+ ///
+ /// \param[in] input Image from which the line bboxes are
+ /// extracted from.
+ /// \param[in, out] lines_bboxes vertical lines bounding boxes.
+ ///
+ /// \return A list of the resulting aligned cols. Each integer is actually
+ /// a col number.
+ template <typename I>
+ util::array<int>
+ align_lines_verticaly(const Image<I>& input,
+ util::array<box<mln_site(I)> >& lines_bboxes);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ util::array<int>
+ align_lines_verticaly(const Image<I>& input,
+ util::array<box<mln_site(I)> >& lines_bboxes)
+ {
+ trace::entering("scribo::table::align_lines_horizontaly");
+
+ mln_precondition(exact(input).is_valid());
+ util::array<int> res = internal::align_lines(geom::ncols(input),
+ geom::min_col(input),
+ geom::max_col(input),
+ lines_bboxes, 1);
+
+ trace::exiting("scribo::table::align_lines_horizontaly");
+ return res;
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TABLE_ALIGN_LINES_VERTICALY_HH
diff --git a/milena/sandbox/scribo/table/connect_horizontal_lines.hh b/milena/sandbox/scribo/table/connect_horizontal_lines.hh
new file mode 100644
index 0000000..7dcf638
--- /dev/null
+++ b/milena/sandbox/scribo/table/connect_horizontal_lines.hh
@@ -0,0 +1,94 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_CONNECT_HORIZONTAL_LINES_HH
+# define SCRIBO_TABLE_CONNECT_HORIZONTAL_LINES_HH
+
+/// \file scribo/table/connect_horizontal_lines.hh
+///
+/// Connect horizontal lines with the new aligned columns.
+
+# include <mln/core/concept/image.hh>
+# include <mln/util/array.hh>
+# include <mln/util/couple.hh>
+
+# include <scribo/table/internal/connect_lines.hh>
+
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+
+ /// Connect horizontal lines with the new aligned columns.
+ ///
+ /// \param[in] aligned_cols a list of new aligned cols.
+ /// \param[in,out] tableboxes the vertical and horizontal lines
+ /// bounding boxes.
+ /// \param[in] input The image from where the lines are
+ /// extracted.
+ template <typename I>
+ void
+ connect_vertical_lines(const util::array<int>& aligned_rows,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > > tableboxes,
+ const Image<I>& input)
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ void
+ connect_horizontal_lines(const util::array<int>& aligned_cols,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > > tableboxes,
+ const Image<I>& input)
+ {
+ trace::entering("scribo::table::connect_horizontal_lines");
+ mln_precondition(exact(input).is_valid());
+
+ internal::connect_lines(aligned_cols, tableboxes.second(),
+ 1, exact(input).ncols());
+
+ trace::exiting("scribo::table::connect_horizontal_lines");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TABLE_CONNECT_HORIZONTAL_LINES_HH
diff --git a/milena/sandbox/scribo/table/connect_vertical_lines.hh b/milena/sandbox/scribo/table/connect_vertical_lines.hh
new file mode 100644
index 0000000..98c39f7
--- /dev/null
+++ b/milena/sandbox/scribo/table/connect_vertical_lines.hh
@@ -0,0 +1,95 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_CONNECT_VERTICAL_LINES_HH
+# define SCRIBO_TABLE_CONNECT_VERTICAL_LINES_HH
+
+/// \file scribo/table/connect_vertical_lines.hh
+///
+/// Connect vertical lines with aligned rows.
+
+# include <mln/core/concept/image.hh>
+# include <mln/util/array.hh>
+# include <mln/util/couple.hh>
+
+# include <scribo/table/internal/connect_lines.hh>
+
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+
+ /// Connect vertical lines with the new aligned rows.
+ ///
+ /// \param[in] aligned_rows a list of new aligned rows.
+ /// \param[in,out] tableboxes the vertical and horizontal lines
+ /// bounding boxes.
+ /// \param[in] input The image from where the lines are
+ /// extracted.
+ template <typename I>
+ void
+ connect_vertical_lines(const util::array<int>& aligned_rows,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > > tableboxes,
+ const Image<I>& input)
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ /// Connect vertical lines with the new aligned rows.
+ template <typename I>
+ void
+ connect_vertical_lines(const util::array<int>& aligned_rows,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > > tableboxes,
+ const Image<I>& input)
+ {
+ trace::entering("scribo::table::connect_vertical_lines");
+ mln_precondition(exact(input).is_valid());
+
+ internal::connect_lines(aligned_rows, tableboxes.first(),
+ 0, exact(input).nrows());
+
+ trace::exiting("scribo::table::connect_vertical_lines");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TABLE_CONNECT_VERTICAL_LINES_HH
diff --git a/milena/sandbox/scribo/table/erase.hh b/milena/sandbox/scribo/table/erase.hh
new file mode 100644
index 0000000..9d94edb
--- /dev/null
+++ b/milena/sandbox/scribo/table/erase.hh
@@ -0,0 +1,97 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_ERASE_HH
+# define SCRIBO_TABLE_ERASE_HH
+
+/// \file scribo/table/erase.hh
+///
+/// Erase the table lines in an image.
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/site_set/box.hh>
+# include <mln/core/routine/duplicate.hh>
+
+# include <mln/util/array.hh>
+# include <mln/util/couple.hh>
+
+# include <scribo/core/erase_bboxes.hh>
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+ /// Erase table line bboxes from an image.
+ ///
+ /// \param[in] line_bboxes vertical and horizontal line bounding
+ /// boxes.
+ /// \param[in] in A binary image from which the table line
+ /// bboxes are extracted.
+ ///
+ ///
+ /// \return A copy of \p in where the table lines are removed.
+ template <typename I>
+ mln_concrete(I)
+ erase(const Image<I>& in,
+ const util::couple<util::array< box<mln_site(I)> >,
+ util::array< box<mln_site(I)> > >& line_bboxes);
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ mln_concrete(I)
+ erase(const Image<I>& in,
+ const util::couple<util::array< box<mln_site(I)> >,
+ util::array< box<mln_site(I)> > >& line_bboxes)
+ {
+ trace::entering("scribo::internal::erase_table");
+ mlc_equal(mln_value(I),bool)::check();
+ mln_precondition(exact(in).is_valid());
+
+ I output = duplicate(in);
+
+ erase_bboxes(output, line_bboxes.first());
+ erase_bboxes(output, line_bboxes.second());
+
+ trace::exiting("scribo::internal::erase_table");
+ return output;
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TABLE_ERASE_HH
diff --git a/milena/sandbox/scribo/table/extract_lines_with_rank.hh b/milena/sandbox/scribo/table/extract_lines_with_rank.hh
new file mode 100644
index 0000000..242dc30
--- /dev/null
+++ b/milena/sandbox/scribo/table/extract_lines_with_rank.hh
@@ -0,0 +1,127 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_EXTRACT_LINES_WITH_RANK_HH
+# define SCRIBO_TABLE_EXTRACT_LINES_WITH_RANK_HH
+
+/// \file scribo/table/extract_lines_with_rank.hh
+///
+/// Extract table lines using a rank filter.
+
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/window.hh>
+# include <mln/core/concept/neighborhood.hh>
+# include <mln/core/site_set/box.hh>
+
+# include <mln/morpho/rank_filter.hh>
+
+# include <mln/accu/bbox.hh>
+
+# include <mln/util/array.hh>
+# include <mln/util/couple.hh>
+
+
+# include <scribo/core/component_bboxes.hh>
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+ /// Find table bboxes thanks to a rank filter.
+ /*!
+ *
+ * \param[in] input_ A binary image.
+ * \param[in] nbh_ The neighborhood used for labeling image components.
+ * \param[in] label_type The type used to store the labels.
+ * \param[in] vwin Window used to extract the vertical lines in the rank
+ * filter.
+ * \param[in] hwin Window used to extract the horizontal lines in the rank
+ * filter.
+ * \param[in] vrank_k Rank used for vertical lines filtering.
+ * \param[in] hrank_k Rank used for horizontal lines filtering.
+ *
+ * \return pair of array of bounding boxes. The first array holds the
+ * vertical lines bounding boxes and the second one the
+ * horizontal lines bounding boxes.
+ */
+ template <typename I, typename N, typename V, typename HW, typename VW>
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > >
+ extract_lines_with_rank(const Image<I>& input_,
+ const Neighborhood<N>& nbh_, const V& label_type,
+ const Window<HW>& vwin, const Window<VW>& hwin,
+ unsigned vrank_k, unsigned hrank_k);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename N, typename V, typename HW, typename VW>
+ inline
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > >
+ extract_lines_with_rank(const Image<I>& input_,
+ const Neighborhood<N>& nbh_, const V& label_type,
+ const Window<HW>& vwin, const Window<VW>& hwin,
+ unsigned vrank_k, unsigned hrank_k)
+ {
+ trace::entering("scribo::table::extract_lines_with_rank");
+
+ mlc_equal(mln_value(I),bool)::check();
+ mlc_is_a(V, mln::value::Symbolic)::check();
+ const I& input = exact(input_);
+ const N& nbh = exact(nbh_);
+ mln_precondition(input.is_valid());
+ mln_precondition(nbh.is_valid());
+ mln_precondition(exact(vwin).is_valid());
+ mln_precondition(exact(hwin).is_valid());
+
+ typedef accu::bbox<mln_psite(I)> A;
+ typedef util::array<mln_result(A)> boxes_t;
+
+ // Vertical lines
+ mln_ch_value(I,bool) vfilter = morpho::rank_filter(input, vwin, vrank_k);
+ boxes_t vboxes = component_bboxes(vfilter, nbh, label_type);
+
+ // Horizontal lines.
+ mln_ch_value(I,bool) hfilter = morpho::rank_filter(input, hwin, hrank_k);
+ boxes_t hboxes = component_bboxes(hfilter, nbh, label_type);
+
+ return mln::make::couple(vboxes, hboxes);
+ }
+
+# endif // !MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TABLE_EXTRACT_LINES_WITH_RANK_HH
diff --git a/milena/sandbox/scribo/table/internal/align_lines.hh b/milena/sandbox/scribo/table/internal/align_lines.hh
new file mode 100644
index 0000000..aaad9fa
--- /dev/null
+++ b/milena/sandbox/scribo/table/internal/align_lines.hh
@@ -0,0 +1,183 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_INTERNAL_ALIGN_LINES_HH
+# define SCRIBO_TABLE_INTERNAL_ALIGN_LINES_HH
+
+/// \file scribo/table/internal/align_lines.hh
+///
+/// Align table lines verticaly or horizontaly.
+
+
+# include <mln/core/site_set/box.hh>
+# include <mln/util/array.hh>
+# include <mln/util/set.hh>
+
+# include <scribo/core/macros.hh>
+
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+ namespace internal
+ {
+
+ /// Align table lines bboxes according to a given dimension.
+ ///
+ /// \return A list of the resulting aligned cols. Each integer is actually
+ /// a col number.
+ /*
+ **
+ ** 0 1 3 4 5 6
+ ** ------------ -------
+ ** 0 |- - - - - | | {0,1} |
+ ** 1 | - - | | {0,1} |
+ ** 2 | | | {1} |
+ ** 3 | | | |
+ ** 4 | | | {2} |
+ ** 5 |- - | | {2} |
+ ** 6 | | | {2} |
+ **
+ ** \p hboxes contains all the table lines bboxes. Each bbox is
+ ** associated with an id, its location in the array.
+ **
+ ** For each bbox, its id is marked in a vector. The location is defined,
+ ** according to the given parameter \p dim, either by the row or the col
+ ** value of the pmin site.
+ **
+ ** Ids are then propagated in the vector according a small delta value.
+ ** if bbox ids are at the same location in the vector, their related bboxes
+ ** are likely to be on the same line.
+ **
+ ** Finally, iterate over the vector until all bboxes have been treated.
+ ** For each iteration, the set with a specific number of elements is found
+ ** and all bboxes referenced in this set are aligned on the same row or col.
+ **
+ */
+ template <typename P>
+ util::array<int>
+ align_lines(unsigned nsites,
+ int min_coord,
+ int max_coord,
+ util::array<box<P> >& line_boxes,
+ unsigned dim);
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename P>
+ util::array<int>
+ align_lines(unsigned nsites,
+ int min_coord,
+ int max_coord,
+ util::array<box<P> >& line_boxes,
+ unsigned dim)
+ {
+ trace::entering("scribo::internal::align_lines");
+
+ mln_precondition(nsites > 0);
+
+ util::array< util::set<unsigned> > lines;
+ lines.resize(nsites);
+
+ // Map components with actual lines.
+ for_all_components(i, line_boxes)
+ {
+ int minline = line_boxes[i].pmin()[dim] - 5;
+ minline = (minline < min_coord ? min_coord : minline);
+ int maxline = line_boxes[i].pmax()[dim] + 5;
+ maxline = (maxline > max_coord ? max_coord : maxline);
+
+ for (int line = minline;
+ line <= maxline; ++line)
+ lines[line].insert(i);
+ }
+
+ // Init box2line
+ util::array<int> box2line;
+ box2line.resize(line_boxes.nelements());
+ for_all_elements(i, box2line)
+ box2line[i] = -1;
+
+ // Find the line with the highest element count.
+ unsigned max_nelts = 0;
+ for_all_elements(i, lines)
+ if (max_nelts < lines[i].nelements())
+ max_nelts = lines[i].nelements();
+
+ // Aligning lines
+ // FIXME: not optimal... Make it faster!
+ // We may do too much iterations (while loop) and some of them may
+ // be done for nothing...
+ util::array<int> newlines;
+ while (max_nelts > 0)
+ {
+ for_all_elements(i, lines)
+ if (lines[i].nelements() == max_nelts)
+ {
+ accu::mean<unsigned> mean;
+ for_all_elements(j, lines[i])
+ if (box2line[lines[i][j]] == -1)
+ mean.take(line_boxes[lines[i][j]].center()[dim]);
+
+ if (mean.is_valid())
+ {
+ for_all_elements(j, lines[i])
+ if (box2line[lines[i][j]] == -1)
+ {
+ line_boxes[lines[i][j]].pmin()[dim] = mean.to_result();
+ line_boxes[lines[i][j]].pmax()[dim] = mean.to_result();
+ box2line[lines[i][j]] = mean.to_result();
+ }
+ newlines.append(mean.to_result());
+ }
+ }
+ --max_nelts;
+ }
+
+ trace::exiting("scribo::internal::align_lines");
+ return newlines;
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::table::internal
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TABLE_INTERNAL_ALIGN_LINES_HH
diff --git a/milena/sandbox/scribo/table/internal/connect_lines.hh b/milena/sandbox/scribo/table/internal/connect_lines.hh
new file mode 100644
index 0000000..d510fe2
--- /dev/null
+++ b/milena/sandbox/scribo/table/internal/connect_lines.hh
@@ -0,0 +1,118 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_INTERNAL_CONNECT_LINES_HH
+# define SCRIBO_TABLE_INTERNAL_CONNECT_LINES_HH
+
+/// \file scribo/table/connect_vertical_lines.hh
+///
+/// Connect vertical lines with aligned rows.
+
+# include <mln/core/image/image1d.hh>
+
+# include <mln/data/fill.hh>
+
+# include <mln/morpho/elementary/dilation.hh>
+# include <mln/util/array.hh>
+# include <mln/util/couple.hh>
+
+# include <mln/opt/at.hh>
+
+# include <scribo/core/macros.hh>
+
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+ namespace internal
+ {
+
+ /// Connect vertical and horizontal lines if they are close to each other.
+ ///
+ /// ------ ------
+ /// ---> |
+ /// | |
+ /// | |
+ ///
+ ///
+ /// FIXME: doc arguments.
+ template <typename P>
+ void
+ connect_lines(const util::array<int>& aligned_lines,
+ util::array< box<P> >& boxes,
+ unsigned dim,
+ unsigned dim_size);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename P>
+ void
+ connect_lines(const util::array<int>& aligned_lines,
+ util::array< box<P> >& boxes,
+ unsigned dim,
+ unsigned dim_size)
+ {
+ trace::entering("scribo::table::internal::connect_lines");
+
+ image1d<int> l(dim_size);
+ data::fill(l, -1);
+
+ for_all_elements(i, aligned_lines)
+ opt::at(l, aligned_lines[i]) = i;
+
+ for (unsigned i = 0; i < settings.max_dist_lines; ++i)
+ l = morpho::elementary::dilation(l, c2());
+
+ for_all_components(i, boxes)
+ {
+ util::couple<point2d, point2d> cp = central_sites(boxes[i], dim);
+ if (opt::at(l, cp.first()[dim]) != -1)
+ boxes[i].pmin()[dim] = aligned_lines[opt::at(l, cp.first()[dim])];
+ if (opt::at(l, cp.second()[dim]) != -1)
+ boxes[i].pmax()[dim] = aligned_lines[opt::at(l, cp.second()[dim])];
+ }
+
+ trace::exiting("scribo::table::internal::connect_lines");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TABLE_INTERNAL_CONNECT_LINES_HH
diff --git a/milena/sandbox/scribo/table/internal/repair_lines.hh b/milena/sandbox/scribo/table/internal/repair_lines.hh
new file mode 100644
index 0000000..87f0933
--- /dev/null
+++ b/milena/sandbox/scribo/table/internal/repair_lines.hh
@@ -0,0 +1,132 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_INTERNAL_REPAIR_LINES_HH
+# define SCRIBO_TABLE_INTERNAL_REPAIR_LINES_HH
+
+/// \file scribo/table/internal/repair_lines.hh
+///
+/// Repair lines which have small discontinuities.
+
+# include <vector>
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/image/extension_val.hh>
+# include <mln/core/site_set/box.hh>
+# include <mln/data/fill.hh>
+# include <mln/util/couple.hh>
+# include <mln/util/array.hh>
+# include <mln/win/line.hh>
+# include <mln/pw/all.hh>
+
+# include <scribo/core/central_sites.hh>
+# include <scribo/table/internal/repair_lines.hh>
+
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+ namespace internal
+ {
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ /// Repair lines which have small discontinuities.
+ /// FIXME: buggy. Sometimes few lines move or shrink!
+ template <unsigned axis, typename I>
+ void
+ repair_lines(const Image<I>& input_,
+ util::array<box<mln_site(I)> >& tableboxes)
+ {
+ trace::entering("scribo::table::internal::repair_lines");
+
+ const I& input = exact(input_);
+ mln_precondition(input.is_valid());
+
+ typedef mln_site(I) P;
+ typedef win::line<mln_grid(P), axis, mln_coord(P)> line_t;
+
+ // Initialization
+ mln_ch_value(I,unsigned) l(input.domain());
+ data::fill(l, literal::zero);
+ for_all_components(i, tableboxes)
+ {
+ util::couple<P,P> cp = central_sites(tableboxes[i], axis);
+ l(cp.first()) = i;
+ l(cp.second()) = i;
+ }
+
+ // Repair
+ extension_val<mln_ch_value(I,unsigned)> l_ext(l, literal::zero);
+
+ util::array<box<P> > result;
+ std::vector<bool> to_keep(tableboxes.nelements(), true);
+
+ mln_VAR(tbb_ima, extend(l | pw::value(l) != literal::zero, l));
+ //FIXME: use a half window, just the bottom of the vertical line.
+ line_t vl(settings.repair_max_dist);
+ mln_piter(tbb_ima_t) p(tbb_ima.domain());
+ mln_qiter(line_t) q(vl, p);
+ for_all(p)
+ for_all(q)
+ if (l_ext(q) != literal::zero && l_ext(q) != l_ext(p))
+ {
+ to_keep[l_ext(q)] = false;
+
+ tableboxes[l_ext(p)].pmax() = tableboxes[l_ext(q)].pmax();
+
+ util::couple<P,P> cp = central_sites(tableboxes[l_ext(q)], axis);
+ l_ext(cp.first()) = l_ext(p);
+ l_ext(cp.second()) = l_ext(p);
+ }
+
+
+ // Remove merged boxes.
+ for_all_elements(i, tableboxes)
+ if (to_keep[i])
+ result.append(tableboxes[i]);
+
+ tableboxes = result;
+ trace::exiting("scribo::table::internal::repair_lines");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::table::internal
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TABLE_INTERNAL_REPAIR_LINES_HH
diff --git a/milena/sandbox/scribo/table/repair_horizontal_lines.hh b/milena/sandbox/scribo/table/repair_horizontal_lines.hh
new file mode 100644
index 0000000..7c1edbd
--- /dev/null
+++ b/milena/sandbox/scribo/table/repair_horizontal_lines.hh
@@ -0,0 +1,92 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_REPAIR_HORIZONTAL_LINES_HH
+# define SCRIBO_TABLE_REPAIR_HORIZONTAL_LINES_HH
+
+/// \file scribo/table/repair_horizontal_lines.hh
+///
+/// Repair horizontal lines which have small discontinuities.
+
+# include <mln/core/concept/image.hh>
+# include <mln/util/couple.hh>
+# include <mln/util/array.hh>
+
+# include <scribo/table/internal/repair_lines.hh>
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+
+ /// Repair horizontal lines which have small discontinuities.
+ /*!
+ * ---- ---- ==> ----------
+ *
+ * \param[in] input Image from which the table bounding
+ * boxes are extracted.
+ * \param[in,out] tablesboxes Table line bounding boxes.
+ * \param[in] max_discontinuity Repair discontinuity which are smaller
+ * than this value.
+ */
+ template <typename I>
+ void
+ repair_horizontal_lines(const Image<I>& input,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > >& tableboxes,
+ unsigned max_discontinuity);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I>
+ inline
+ void
+ repair_horizontal_lines(const Image<I>& input,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > >& tableboxes,
+ unsigned max_discontinuity)
+ {
+ trace::entering("scribo::table::repair_horizontal_lines");
+ mln_precondition(exact(input).is_valid());
+
+ internal::repair_lines<1>(input, tableboxes.second(), max_discontinuity);
+
+ trace::exiting("scribo::table::repair_horizontal_lines");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TABLE_REPAIR_HORIZONTAL_LINES_HH
diff --git a/milena/sandbox/scribo/table/repair_vertical_lines.hh b/milena/sandbox/scribo/table/repair_vertical_lines.hh
new file mode 100644
index 0000000..94ae3f1
--- /dev/null
+++ b/milena/sandbox/scribo/table/repair_vertical_lines.hh
@@ -0,0 +1,98 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TABLE_REPAIR_VERTICAL_LINES_HH
+# define SCRIBO_TABLE_REPAIR_VERTICAL_LINES_HH
+
+/// \file scribo/table/repair_vertical_lines.hh
+///
+/// Repair vertical lines which have small discontinuities.
+
+# include <mln/core/concept/image.hh>
+# include <mln/util/couple.hh>
+# include <mln/util/array.hh>
+
+# include <scribo/table/internal/repair_lines.hh>
+
+namespace scribo
+{
+
+ namespace table
+ {
+
+
+ /// Repair vertical lines which have small discontinuities.
+ /*!
+ *
+ * | | \n
+ * | | \n
+ * ==> | \n
+ * | | \n
+ * | | \n
+ *
+ *
+ * \param[in] input Image from which the table bounding
+ * boxes are extracted.
+ * \param[in,out] tablesboxes Table line bounding boxes.
+ * \param[in] max_discontinuity Repair discontinuity which are smaller
+ * than this value.
+ */
+ template <typename I>
+ void
+ repair_vertical_lines(const Image<I>& input,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > >& tblboxes,
+ unsigned max_discontinuity);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I>
+ inline
+ void
+ repair_vertical_lines(const Image<I>& input,
+ util::couple<util::array<box<mln_site(I)> >,
+ util::array<box<mln_site(I)> > >& tblboxes,
+ unsigned max_discontinuity)
+ {
+ trace::entering("scribo::table::repair_vertical_lines");
+ mln_precondition(exact(input).is_valid());
+
+ internal::repair_lines<0>(input, tblboxes.first(), max_discontinuity);
+
+ trace::exiting("scribo::table::repair_vertical_lines");
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::table
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TABLE_REPAIR_VERTICAL_LINES_HH
diff --git a/milena/sandbox/scribo/text/extract_bboxes.hh b/milena/sandbox/scribo/text/extract_bboxes.hh
new file mode 100644
index 0000000..0c88880
--- /dev/null
+++ b/milena/sandbox/scribo/text/extract_bboxes.hh
@@ -0,0 +1,95 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_EXTRACT_BBOXES_HH
+# define SCRIBO_TEXT_GROUPING_EXTRACT_BBOXES_HH
+
+/// \file scribo/text/grouping/group_with_single_link.hh
+///
+/// Extract text bounding boxes from a binary image.
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/neighborhood.hh>
+# include <mln/core/site_set/box.hh>
+# include <mln/labeling/blobs.hh>
+# include <mln/labeling/compute.hh>
+# include <mln/util/array.hh>
+
+# include <scribo/core/component_bboxes.hh>
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ using namespace mln;
+
+ /// Extract text bounding boxes from a binary image.
+ ///
+ /// \param[in] input_ A binary image.
+ ///
+ /// \return an array of bounding boxes. The first bounding box is
+ /// the background's.
+ template <typename I, typename N, typename V>
+ inline
+ util::array< box<mln_site(I)> >
+ extract_bboxes(const Image<I>& input_,
+ const Neighborhood<N>& nbh, V& nbboxes);
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I, typename N, typename V>
+ inline
+ util::array< box<mln_site(I)> >
+ extract_bboxes(const Image<I>& input_,
+ const Neighborhood<N>& nbh, V& nbboxes)
+ {
+ trace::entering("scribo::text::extract_bboxes");
+
+ const I& input = exact(input_);
+
+ mlc_equal(mln_value(I), bool)::check();
+ mln_precondition(input.is_valid());
+
+ typedef util::array< box<mln_site(I)> > bboxes_t;
+ bboxes_t bboxes = component_bboxes(input, nbh, nbboxes);
+
+ trace::exiting("scribo::text::extract_bboxes");
+ return bboxes;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_GROUPING_EXTRACT_BBOXES_HH
diff --git a/milena/sandbox/scribo/text/grouping/group_from_double_link.hh b/milena/sandbox/scribo/text/grouping/group_from_double_link.hh
new file mode 100644
index 0000000..d178a80
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/group_from_double_link.hh
@@ -0,0 +1,108 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_GROUP_FROM_DOUBLE_LINK_HH
+# define SCRIBO_TEXT_GROUPING_GROUP_FROM_DOUBLE_LINK_HH
+
+/// \file scribo/text/grouping/group_from_double_link.hh
+///
+/// Link text bounding boxes with their left neighbor.
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/site_set/box.hh>
+
+# include <mln/accu/bbox.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/text/grouping/internal/find_root.hh>
+
+# include <scribo/core/macros.hh>
+
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ /// FIXME: Add much more doc!
+ template <typename P>
+ util::array< box<P> >
+ group_from_double_link(const util::array< box<P> >& textbboxes,
+ util::array<unsigned>& left_link,
+ util::array<unsigned>& right_link);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename P>
+ inline
+ util::array< box<P> >
+ group_from_double_link(const util::array< box<P> >& textbboxes,
+ util::array<unsigned>& left_link,
+ util::array<unsigned>& right_link)
+ {
+ trace::entering("scribo::text::grouping::group_from_double_link");
+
+ mln_precondition(left_link.nelements() == right_link.nelements());
+
+ util::array< accu::bbox<P> > tboxes;
+ tboxes.resize(textbboxes.nelements());
+ for_all_components(i, textbboxes)
+ {
+ unsigned nbh = right_link[left_link[i]];
+ if (nbh == i)
+ tboxes[left_link[i]].take(textbboxes[i]);
+ else
+ tboxes[i].take(textbboxes[i]);
+ }
+
+ util::array< box<P> > result;
+ // component 0, the background, has an invalid box.
+ result.append(box<P>());
+ for_all_components(i, tboxes)
+ if (tboxes[i].is_valid())
+ result.append(tboxes[i]);
+
+ trace::exiting("scribo::text::grouping::group_from_double_link");
+ return result;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_GROUPING_GROUP_FROM_DOUBLE_LINK_HH
diff --git a/milena/sandbox/scribo/text/grouping/group_from_multiple_links.hh b/milena/sandbox/scribo/text/grouping/group_from_multiple_links.hh
new file mode 100644
index 0000000..612fb87
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/group_from_multiple_links.hh
@@ -0,0 +1,154 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_GROUP_FROM_MULTIPLE_LINKS_HH
+# define SCRIBO_TEXT_GROUPING_GROUP_FROM_MULTIPLE_LINKS_HH
+
+/// \file scribo/text/grouping/group_from_multiple_links.hh
+///
+/// Link text bounding boxes with their neighbors.
+
+# include <mln/core/concept/graph.hh>
+# include <mln/core/concept/image.hh>
+# include <mln/core/site_set/box.hh>
+
+# include <mln/canvas/browsing/depth_first_search.hh>
+
+# include <mln/accu/bbox.hh>
+
+# include <mln/pw/all.hh>
+
+# include <mln/fun/i2v/array.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/core/macros.hh>
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ /// FIXME: Add much more doc!
+ template <typename G, typename P>
+ util::array<box<P> >
+ group_from_multiple_links(util::array<box<P> >& textbboxes,
+ const Graph<G>& g_);
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ namespace internal
+ {
+
+ /// Functor to be passed to depth_first_search.
+ /// Map each component vertex with its representative vertex id.
+ struct map_vertex_to_component_id_functor
+ {
+ template <typename G>
+ void init(const Graph<G>& g)
+ {
+ vertextocomp.resize(exact(g).v_nmax(), mln_max(unsigned));
+ ncomp = 0;
+ }
+
+ void final()
+ {}
+
+ void next_component()
+ { ++ncomp; }
+
+ void new_component_from_vertex(unsigned id)
+ { vertextocomp(id) = ncomp; }
+
+ void added_to_queue(unsigned id)
+ { new_component_from_vertex(id); }
+
+ void process_vertex(unsigned)
+ {}
+
+ bool to_be_treated(unsigned id)
+ { return vertextocomp(id) == mln_max(unsigned); }
+
+ bool to_be_queued(unsigned id)
+ { return to_be_treated(id); }
+
+ unsigned ncomp;
+ fun::i2v::array<unsigned> vertextocomp;
+ };
+
+ } // end of namespace scribo::text::grouping::internal
+
+
+
+ template <typename G, typename P>
+ inline
+ util::array<box<P> >
+ group_from_multiple_links(util::array<box<P> >& textbboxes,
+ const Graph<G>& g_)
+ {
+ trace::entering("scribo::text::grouping::group_from_multiple_links");
+
+ const G& g = exact(g_);
+
+ mln_assertion(g.is_valid());
+
+ internal::map_vertex_to_component_id_functor f;
+ canvas::browsing::depth_first_search(g, f);
+
+ util::array< accu::bbox<P> > tboxes;
+ tboxes.resize(textbboxes.nelements());
+ for_all_components(i, textbboxes)
+ tboxes[f.vertextocomp(i)].take(textbboxes[i]);
+
+ util::array< box<P> > result;
+ // Component 0 - the background has not valid bboxes.
+ result.append(box<P>());
+ for_all_components(i, textbboxes)
+ if (tboxes[i].is_valid())
+ result.append(tboxes[i].to_result());
+
+ mln_assertion(result.nelements() == f.ncomp);
+
+ trace::exiting("scribo::text::grouping::group_from_multiple_links");
+ return result;
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_GROUPING_GROUP_FROM_MULTIPLE_LINKS_HH
diff --git a/milena/sandbox/scribo/text/grouping/group_from_single_link.hh b/milena/sandbox/scribo/text/grouping/group_from_single_link.hh
new file mode 100644
index 0000000..eccde96
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/group_from_single_link.hh
@@ -0,0 +1,101 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_GROUP_FROM_SINGLE_LINK_HH
+# define SCRIBO_TEXT_GROUPING_GROUP_FROM_SINGLE_LINK_HH
+
+/// \file scribo/text/grouping/group_from_single_link.hh
+///
+/// Link text bounding boxes with their left neighbor.
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/site_set/box.hh>
+
+# include <mln/accu/bbox.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/text/grouping/internal/find_root.hh>
+
+# include <scribo/core/macros.hh>
+
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ /// FIXME: Add much more doc!
+ template <typename P>
+ util::array< box<P> >
+ group_from_single_link(const util::array< box<P> >& textbboxes,
+ util::array<unsigned>& link_array);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename P>
+ inline
+ util::array< box<P> >
+ group_from_single_link(const util::array< box<P> >& textbboxes,
+ util::array<unsigned>& link_array)
+ {
+ trace::entering("scribo::text::grouping::group_from_single_link");
+
+ for (unsigned i = 0; i < link_array.nelements(); ++i)
+ link_array[i] = internal::find_root(link_array, i);
+
+ util::array< accu::bbox<P> > tboxes;
+ tboxes.resize(textbboxes.nelements());
+ for_all_components(i, textbboxes)
+ tboxes[link_array[i]].take(textbboxes[i]);
+
+ util::array< box<P> > result;
+ // component 0, the background, has an invalid box.
+ result.append(box<P>());
+ for_all_components(i, tboxes)
+ if (tboxes[i].is_valid())
+ result.append(tboxes[i]);
+
+ trace::exiting("scribo::text::grouping::group_from_single_link");
+ return result;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_GROUPING_GROUP_FROM_SINGLE_LINK_HH
diff --git a/milena/sandbox/scribo/text/grouping/group_with_multiple_links.hh b/milena/sandbox/scribo/text/grouping/group_with_multiple_links.hh
new file mode 100644
index 0000000..2f769fc
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/group_with_multiple_links.hh
@@ -0,0 +1,115 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_GROUP_WITH_MULTIPLE_LINKS_HH
+# define SCRIBO_TEXT_GROUPING_GROUP_WITH_MULTIPLE_LINKS_HH
+
+/// \file scribo/text/grouping/group_with_multiple_links.hh
+///
+/// Group character bounding boxes with multiple links.
+
+# include <mln/core/concept/image.hh>
+
+# include <mln/math/abs.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/core/macros.hh>
+# include <scribo/text/grouping/internal/init_link_array.hh>
+# include <scribo/text/grouping/internal/update_link_graph.hh>
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ /// Group character bounding boxes with multiple links.
+ /// Look up for neighbors on the left of each box.
+ template <typename I, typename N, typename V>
+ util::graph
+ group_with_multiple_links(const Image<I>& input_,
+ const Neighborhood<N>& nbh, V& nbboxes,
+ const util::array<box<mln_site(I)> >& textbboxes,
+ unsigned neighb_max_distance);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename N, typename V>
+ util::graph
+ group_with_multiple_links(const Image<I>& input_,
+ const Neighborhood<N>& nbh, V& nbboxes,
+ const util::array<box<mln_site(I)> >& textbboxes,
+ unsigned neighb_max_distance)
+ {
+ trace::entering("scribo::text::grouping::group_with_multiple_links");
+
+ const I& input = exact(input_);
+
+ mlc_equal(mln_value(I), bool)::check();
+ mln_assertion(input.is_valid());
+
+ typedef mln_ch_value(I,V) lbl_t;
+ lbl_t lbl = labeling::blobs(input, nbh, nbboxes);
+
+ util::graph g(nbboxes.next());
+
+ for_all_ncomponents(i, nbboxes)
+ {
+ unsigned midcol = (textbboxes[i].pmax().col()
+ - textbboxes[i].pmin().col()) / 2;
+ int dmax = midcol + neighb_max_distance;
+ mln_site(I) c = textbboxes[i].center();
+
+ /// First site on the right of the central site
+ mln_site(I) p = c + right;
+
+ while (lbl.domain().has(p) && (lbl(p) == literal::zero || lbl(p) == i)
+ && math::abs(p.col() - c.col()) < dmax)
+ ++p.col();
+
+ internal::update_link_graph(lbl, g, p, c, i, dmax);
+ }
+
+ trace::exiting("scribo::text::grouping::group_with_multiple_links");
+ return g;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_GROUPING_GROUP_WITH_MULTIPLE_LINKS_HH
diff --git a/milena/sandbox/scribo/text/grouping/group_with_single_left_link.hh b/milena/sandbox/scribo/text/grouping/group_with_single_left_link.hh
new file mode 100644
index 0000000..f1a3013
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/group_with_single_left_link.hh
@@ -0,0 +1,135 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_GROUP_WITH_SINGLE_LEFT_LINK_HH
+# define SCRIBO_TEXT_GROUPING_GROUP_WITH_SINGLE_LEFT_LINK_HH
+
+/// \file scribo/text/grouping/group_with_single_left_link.hh
+///
+/// Link text bounding boxes with their left neighbor.
+///
+/// Merge code with text::grouping::group_with_single_right_link.hh
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/neighborhood.hh>
+
+# include <mln/math/abs.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/core/macros.hh>
+# include <scribo/text/grouping/internal/init_link_array.hh>
+# include <scribo/text/grouping/internal/update_link_array.hh>
+
+//FIXME: not generic.
+# include <mln/core/alias/dpoint2d.hh>
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ /// Map each character bounding box to its left bounding box neighbor
+ /// if possible.
+ /// Iterate to the right but link boxes to the left.
+ ///
+ /// \return an util::array. Map a bounding box to its left neighbor.
+ template <typename I, typename N, typename V>
+ inline
+ util::array<unsigned>
+ group_with_single_left_link(const Image<I>& input_,
+ const Neighborhood<N>& nbh, V& nbboxes,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ unsigned neighb_max_distance);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename N, typename V>
+ inline
+ util::array<unsigned>
+ group_with_single_left_link(const Image<I>& input_,
+ const Neighborhood<N>& nbh_, V& nbboxes,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ unsigned neighb_max_distance)
+ {
+ trace::entering("scribo::text::grouping::group_with_single_left_link");
+
+ const I& input = exact(input_);
+ const N& nbh = exact(nbh_);
+
+ mlc_equal(mln_value(I), bool)::check();
+ mln_assertion(input.is_valid());
+ mln_precondition(nbh.is_valid());
+
+ typedef mln_ch_value(I,V) lbl_t;
+ lbl_t lbl = labeling::blobs(input, nbh, nbboxes);
+
+ util::array<unsigned> left_link(nbboxes.next());
+ internal::init_link_array(left_link);
+
+ for_all_ncomponents(i, nbboxes)
+ {
+ unsigned midcol = (textbboxes[i].pmax().col()
+ - textbboxes[i].pmin().col()) / 2;
+ int dmax = midcol + neighb_max_distance;
+ mln_site(I) c = textbboxes[i].center();
+
+ ///
+ /// Find a neighbor on the right
+ ///
+
+ ///FIXME: the following code is not generic...
+ /// First site on the right of the central site
+ mln_site(I) p = c + right;
+
+ while (lbl.domain().has(p) && (lbl(p) == literal::zero || lbl(p) == i)
+ && math::abs(p.col() - c.col()) < dmax)
+ ++p.col();
+
+ internal::update_link_array(lbl, left_link, p, c, i, dmax);
+
+ }
+
+ trace::exiting("scribo::text::grouping::group_with_single_left_link");
+ return left_link;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_GROUPING_GROUP_WITH_SINGLE_LEFT_LINK_HH
diff --git a/milena/sandbox/scribo/text/grouping/group_with_single_right_link.hh b/milena/sandbox/scribo/text/grouping/group_with_single_right_link.hh
new file mode 100644
index 0000000..7f1eeac
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/group_with_single_right_link.hh
@@ -0,0 +1,135 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_GROUP_WITH_SINGLE_RIGHT_LINK_HH
+# define SCRIBO_TEXT_GROUPING_GROUP_WITH_SINGLE_RIGHT_LINK_HH
+
+/// \file scribo/text/grouping/group_with_single_right_link.hh
+///
+/// Link text bounding boxes with their right neighbor.
+///
+/// Merge code with text::grouping::group_with_single_right_link.hh
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/neighborhood.hh>
+
+# include <mln/math/abs.hh>
+
+# include <mln/util/array.hh>
+
+# include <scribo/core/macros.hh>
+# include <scribo/text/grouping/internal/init_link_array.hh>
+# include <scribo/text/grouping/internal/update_link_array.hh>
+
+//FIXME: not generic.
+# include <mln/core/alias/dpoint2d.hh>
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ /// Map each character bounding box to its right bounding box neighbor
+ /// if possible.
+ /// Iterate to the right but link boxes to the right.
+ ///
+ /// \return an util::array. Map a bounding box to its right neighbor.
+ template <typename I, typename N, typename V>
+ inline
+ util::array<unsigned>
+ group_with_single_right_link(const Image<I>& input_,
+ const Neighborhood<N>& nbh, V& nbboxes,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ unsigned neighb_max_distance);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename N, typename V>
+ inline
+ util::array<unsigned>
+ group_with_single_right_link(const Image<I>& input_,
+ const Neighborhood<N>& nbh_, V& nbboxes,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ unsigned neighb_max_distance)
+ {
+ trace::entering("scribo::text::grouping::group_with_single_right_link");
+
+ const I& input = exact(input_);
+ const N& nbh = exact(nbh_);
+
+ mlc_equal(mln_value(I), bool)::check();
+ mln_assertion(input.is_valid());
+ mln_precondition(nbh.is_valid());
+
+ typedef mln_ch_value(I,V) lbl_t;
+ lbl_t lbl = labeling::blobs(input, nbh, nbboxes);
+
+ util::array<unsigned> right_link(nbboxes.next());
+ internal::init_link_array(right_link);
+
+ for_all_ncomponents(i, nbboxes)
+ {
+ unsigned midcol = (textbboxes[i].pmax().col()
+ - textbboxes[i].pmin().col()) / 2;
+ int dmax = midcol + neighb_max_distance;
+ mln_site(I) c = textbboxes[i].center();
+
+ ///
+ /// Find a neighbor on the left
+ ///
+
+ ///FIXME: the following code is not generic...
+ /// First site on the left of the central site
+ mln_site(I) p = c + left;
+
+ while (lbl.domain().has(p) && (lbl(p) == literal::zero || lbl(p) == i)
+ && math::abs(p.col() - c.col()) < dmax)
+ --p.col();
+
+ internal::update_link_array(lbl, right_link, p, c, i, dmax);
+
+ }
+
+ trace::exiting("scribo::text::grouping::group_with_single_right_link");
+ return right_link;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_GROUPING_GROUP_WITH_SINGLE_RIGHT_LINK_HH
diff --git a/milena/sandbox/scribo/photo.cc b/milena/sandbox/scribo/text/grouping/internal/find_root.hh
similarity index 52%
copy from milena/sandbox/scribo/photo.cc
copy to milena/sandbox/scribo/text/grouping/internal/find_root.hh
index a173750..0b1e307 100644
--- a/milena/sandbox/scribo/photo.cc
+++ b/milena/sandbox/scribo/text/grouping/internal/find_root.hh
@@ -1,4 +1,5 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -26,39 +27,54 @@
// Public License.
-#include "demat.hh"
+#ifndef SCRIBO_TEXT_GROUPING_INTERNAL_FIND_ROOT_LINK_ARRAY_HH
+# define SCRIBO_TEXT_GROUPING_INTERNAL_FIND_ROOT_LINK_ARRAY_HH
-int main(int argc, char*argv[])
+/// \file scribo/text/grouping/internal/find_root.hh
+///
+/// Find root in a parent array arrays.
+
+
+# include <mln/util/array.hh>
+
+
+namespace scribo
{
- using namespace mln;
- using value::int_u8;
- if (argc < 2)
+ namespace text
{
- std::cout << argv[0] << " <in.pbm> <out.pgm> <l> <bbox_larger> <bbox_distance> <min_comp_nsites>" << std::endl
- << std::endl << std::endl
- << std::endl
- << "=========="
- << std::endl << std::endl
- << "<in.pbm> B/W inverted input image."
- << std::endl << std::endl
-/* << "<out.ppm> RGB8 output image."
- << std::endl << std::endl
- << "<bbox_distance> Maximum distance between character bounding boxes. Used for bbox grouping."
- << std::endl << std::endl
- << "<min_comp_nsites> Minimum site count of a character/text component."
- << std::endl
- << " If a component have a site count lesser than this value, it is erased."
- << std::endl << std::endl
- << std::endl*/
- << "=========="
- << std::endl << std::endl
- << "HINT: compile with -DNOUT to avoid debug images."
- << std::endl << std::endl;
- return 1;
- }
-
- scribo::demat_photo(argv);
-
- return 0;
-}
+
+ namespace grouping
+ {
+
+ namespace internal
+ {
+
+ /// Find root in a parent array arrays.
+ unsigned
+ find_root(util::array<unsigned>& parent, unsigned x);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ inline
+ unsigned
+ find_root(util::array<unsigned>& parent, unsigned x)
+ {
+ if (parent[x] == x)
+ return x;
+ else
+ return parent[x] = find_root(parent, parent[x]);
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping::internal
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TEXT_GROUPING_INTERNAL_FIND_ROOT_LINK_ARRAY_HH
diff --git a/milena/sandbox/scribo/photo.cc b/milena/sandbox/scribo/text/grouping/internal/init_link_array.hh
similarity index 52%
rename from milena/sandbox/scribo/photo.cc
rename to milena/sandbox/scribo/text/grouping/internal/init_link_array.hh
index a173750..ba197f9 100644
--- a/milena/sandbox/scribo/photo.cc
+++ b/milena/sandbox/scribo/text/grouping/internal/init_link_array.hh
@@ -1,4 +1,5 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -26,39 +27,51 @@
// Public License.
-#include "demat.hh"
+#ifndef SCRIBO_TEXT_GROUPING_INTERNAL_INIT_LINK_ARRAY_HH
+# define SCRIBO_TEXT_GROUPING_INTERNAL_INIT_LINK_ARRAY_HH
-int main(int argc, char*argv[])
+/// \file scribo/text/grouping/internal/init_link_array.hh
+///
+/// Initialize a link array.
+
+
+# include <mln/util/array.hh>
+
+
+namespace scribo
{
- using namespace mln;
- using value::int_u8;
- if (argc < 2)
+ namespace text
{
- std::cout << argv[0] << " <in.pbm> <out.pgm> <l> <bbox_larger> <bbox_distance> <min_comp_nsites>" << std::endl
- << std::endl << std::endl
- << std::endl
- << "=========="
- << std::endl << std::endl
- << "<in.pbm> B/W inverted input image."
- << std::endl << std::endl
-/* << "<out.ppm> RGB8 output image."
- << std::endl << std::endl
- << "<bbox_distance> Maximum distance between character bounding boxes. Used for bbox grouping."
- << std::endl << std::endl
- << "<min_comp_nsites> Minimum site count of a character/text component."
- << std::endl
- << " If a component have a site count lesser than this value, it is erased."
- << std::endl << std::endl
- << std::endl*/
- << "=========="
- << std::endl << std::endl
- << "HINT: compile with -DNOUT to avoid debug images."
- << std::endl << std::endl;
- return 1;
- }
-
- scribo::demat_photo(argv);
-
- return 0;
-}
+
+ namespace grouping
+ {
+
+ namespace internal
+ {
+
+ /// Initialize a link array.
+ void init_link_array(util::array<unsigned>& link_array);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ inline
+ void
+ init_link_array(util::array<unsigned>& link_array)
+ {
+ for (unsigned i = 0; i < link_array.nelements(); ++i)
+ link_array[i] = i;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping::internal
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TEXT_GROUPING_INTERNAL_INIT_LINK_ARRAY_HH
diff --git a/milena/sandbox/scribo/text/grouping/internal/update_link_array.hh b/milena/sandbox/scribo/text/grouping/internal/update_link_array.hh
new file mode 100644
index 0000000..242d18f
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/internal/update_link_array.hh
@@ -0,0 +1,93 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_INTERNAL_UPDATE_LINK_ARRAY_HH
+# define SCRIBO_TEXT_GROUPING_INTERNAL_UPDATE_LINK_ARRAY_HH
+
+/// \file scribo/text/grouping/internal/update_link_array.hh
+///
+/// Update a lookup table if a neighbor is found on the right of
+/// the current bbox.
+
+
+# include <mln/core/concept/image.hh>
+# include <mln/util/array.hh>
+
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ namespace internal
+ {
+
+ /// Update the lookup table \p link_array if a neighbor is found
+ /// on the right of the current bbox.
+ template <typename I>
+ void
+ update_link_array(const Image<I>& lbl, util::array<unsigned>& link_array,
+ const mln_site(I)& p, const mln_site(I)& c,
+ unsigned i, int dmax);
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I>
+ inline
+ void
+ update_link_array(const Image<I>& lbl_, util::array<unsigned>& link_array,
+ const mln_site(I)& p, const mln_site(I)& c,
+ unsigned i, int dmax)
+ {
+ const I& lbl = exact(lbl_);
+
+ mlc_is_a(mln_value(I), mln::value::Symbolic)::check();
+ mln_assertion(lbl.is_valid());
+
+ if (lbl.domain().has(p) && lbl(p) != literal::zero && lbl(p) != i
+ && (math::abs(p.col() - c.col())) < dmax && link_array[lbl(p)] == lbl(p))
+ link_array[lbl(p)] = i;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping::internal
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TEXT_GROUPING_INTERNAL_UPDATE_LINK_ARRAY_HH
diff --git a/milena/sandbox/scribo/text/grouping/internal/update_link_graph.hh b/milena/sandbox/scribo/text/grouping/internal/update_link_graph.hh
new file mode 100644
index 0000000..e31c5e8
--- /dev/null
+++ b/milena/sandbox/scribo/text/grouping/internal/update_link_graph.hh
@@ -0,0 +1,92 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_GROUPING_INTERNAL_UPDATE_LINK_GRAPH_HH
+# define SCRIBO_TEXT_GROUPING_INTERNAL_UPDATE_LINK_GRAPH_HH
+
+/// \file scribo/text/grouping/internal/update_link_array.hh
+///
+/// Update graph edges if a valid neighbor is found.
+
+# include <mln/core/concept/image.hh>
+# include <mln/util/graph.hh>
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ namespace grouping
+ {
+
+ namespace internal
+ {
+
+ /// Update graph edges if a valid neighbor is found.
+ template <typename I>
+ void
+ update_link_graph(Image<I>& lbl_, util::graph& g,
+ const mln_site(I)& p, const mln_site(I)& c,
+ unsigned i, int dmax);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename I>
+ inline
+ void
+ update_link_graph(Image<I>& lbl_, util::graph& g,
+ const mln_site(I)& p, const mln_site(I)& c,
+ unsigned i, int dmax)
+ {
+ const I& lbl = exact(lbl_);
+
+ mlc_is_a(mln_value(I), mln::value::Symbolic)::check();
+ mln_precondition(exact(lbl).is_valid());
+
+ if (lbl.domain().has(p) && lbl(p) != 0u && lbl(p) != i
+ && (math::abs(p.col() - c.col())) < dmax)
+ g.add_edge(lbl(p), i);
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text::grouping::internal
+
+ } // end of namespace scribo::text::grouping
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+
+#endif // ! SCRIBO_TEXT_GROUPING_INTERNAL_UPDATE_LINK_GRAPH_HH
diff --git a/milena/sandbox/scribo/text/recognition.hh b/milena/sandbox/scribo/text/recognition.hh
new file mode 100644
index 0000000..98c3b67
--- /dev/null
+++ b/milena/sandbox/scribo/text/recognition.hh
@@ -0,0 +1,142 @@
+// Copyright (C) 2009 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library 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 this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library 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_TEXT_RECOGNITION_HH
+# define SCRIBO_TEXT_RECOGNITION_HH
+
+/// \file scribo/text/recognition.hh
+///
+/// Passes the text bounding boxes to an OCR (Tesseract).
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/neighborhood.hh>
+# include <mln/core/site_set/box.hh>
+# include <mln/util/array.hh>
+# include <mln/labeling/blobs.hh>
+# include <mln/data/fill.hh>
+# include <mln/pw/all.hh>
+# include <mln/debug/put_words.hh>
+
+# include <scribo/core/macros.hh>
+
+# include <tesseract/baseapi.h>
+
+
+
+namespace scribo
+{
+
+ namespace text
+ {
+
+ /// Passes the text bboxes to Tesseract (OCR) and store the result in
+ /// an image of characters.
+ ///
+ /// \param[in] input_ image from where the text bboxes are extracted.
+ /// \param[in] nbh_ The neighborhood used to label \p input_.
+ /// \param[in] nbboxes The value type used in the labeled image.
+ /// \param[in] textbboxes array of text bounding boxes.
+ /// \param[in] language the language which should be recognized by Tesseract.
+ /// (fra, en, ...)
+ ///
+ /// \return An image of characters.
+ ///
+ /// FIXME: For each text bbox, we create a new image. We may like to avoid that.
+ /// FIXME: Do not store the result in an image?
+ template <typename I, typename N, typename V>
+ mln_ch_value(I,char)
+ text_recognition(const Image<I>& input_,
+ const Neighborhood<N>& nbh_, V& nbboxes,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const char *language);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename N, typename V>
+ mln_ch_value(I,char)
+ text_recognition(const Image<I>& input_,
+ const Neighborhood<N>& nbh_, V& nbboxes,
+ const util::array< box<mln_site(I)> >& textbboxes,
+ const char *language)
+ {
+ trace::entering("scribo::text::recognition");
+
+ mlc_equal(mln_value(I), bool)::check();
+ const I& input = exact(input_);
+ const N& nbh = exact(nbh_);
+ mln_precondition(input.is_valid());
+ mln_precondition(nbh.is_valid());
+
+ mln_ch_value(I,V) lbl = labeling::blobs(input, nbh, nbboxes);
+
+ /// Use text bboxes with Tesseract
+ TessBaseAPI::InitWithLanguage(NULL, NULL, language, NULL, false, 0, NULL);
+ mln_ch_value(I,char) txt(input.domain());
+ data::fill(txt, ' ');
+
+ for_all_components(i, textbboxes)
+ {
+ if (textbboxes[i].is_valid())
+ {
+ mln_ch_value(I,bool) b(textbboxes[i], 0);
+ data::fill(b, false);
+ data::fill((b | (pw::value(lbl) == pw::cst(i))).rw(), true);
+
+ char* s = TessBaseAPI::TesseractRect(
+ (unsigned char*) b.buffer(),
+ sizeof (bool), // Pixel size.
+ b.ncols() * sizeof (bool), // Row_offset
+ 0, // Left
+ 0, // Top
+ b.ncols(), // n cols
+ b.nrows()); // n rows
+
+
+
+ mln_site(I) p = textbboxes[i].center();
+ p.col() -= (textbboxes[i].pmax().col()
+ - textbboxes[i].pmin().col()) / 2;
+ if (s != 0)
+ debug::put_word(txt, p, s);
+ free(s);
+ }
+ }
+
+ trace::exiting("scribo::text::recognition");
+ return text;
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace scribo::text
+
+} // end of namespace scribo
+
+#endif // ! SCRIBO_TEXT_RECOGNITION_HH
--
1.5.6.5
1
0
URL: https://svn.lrde.epita.fr/svn/oln/trunk/milena/sandbox
ChangeLog:
2009-03-10 Fabien Freling <fabien.freling(a)lrde.epita.fr>
Implement 3D watershed and various tools.
* fabien/bin/dicom2pgm.cc: New tool.
* fabien/bin/dump2pgm.cc: New tool.
* fabien/bin/dump2pgm8b.cc: New tool.
* fabien/bin/dump_mask.cc: New tool.
* fabien/bin/filetype.hh: New.
* fabien/bin/pnms2dump.cc: New tool.
* fabien/igr/Makefile: Update.
* fabien/igr/check2d_wsd.sh: Shell script for testing.
* fabien/igr/check3d_wsd.sh: Shell script for testing.
* fabien/igr/watershed.cc: Rename this...
* fabien/igr/watershed.hh: ...into this.
* fabien/igr/watershed2d.cc: Implement 2D watershed.
* fabien/igr/watershed3d.cc: Implement 3D watershed.
---
TODO | 7 -
bin/dicom2pgm.cc | 34 +++++
bin/dump2pgm.cc | 37 +++++
bin/dump2pgm8b.cc | 38 ++++++
bin/dump_mask.cc | 86 +++++++++++++
bin/filetype.hh | 54 ++++++++
bin/pnms2dump.cc | 97 +++++++++++++++
igr/Makefile | 9 -
igr/check2d_wsd.sh | 32 +++++
igr/check3d_wsd.sh | 34 +++++
igr/watershed.hh | 331 ++++++++++++++++++++++++++++++++++++++++++++++++++++
igr/watershed2d.cc | 331 ++++++++++++++++++++++++++++++++++++++++++++++++++++
igr/watershed3d.cc | 334 +++++++++++++++++++++++++++++++++++++++++++++++++++++
13 files changed, 1419 insertions(+), 5 deletions(-)
Index: trunk/milena/sandbox/fabien/igr/watershed.cc (deleted)
===================================================================
Index: trunk/milena/sandbox/fabien/igr/watershed2d.cc
===================================================================
--- trunk/milena/sandbox/fabien/igr/watershed2d.cc (revision 0)
+++ trunk/milena/sandbox/fabien/igr/watershed2d.cc (revision 3503)
@@ -0,0 +1,331 @@
+#include <iostream>
+#include <mln/core/image/image2d.hh>
+
+#include <mln/core/alias/neighb2d.hh>
+#include <mln/core/alias/window2d.hh>
+#include <mln/core/image/image_if.hh>
+
+#include <mln/io/ppm/save.hh>
+#include <mln/io/ppm/load.hh>
+#include <mln/io/pgm/load.hh>
+#include <mln/io/dicom/load.hh>
+#include <mln/io/pgm/save.hh>
+#include <mln/io/dump/save.hh>
+
+#include <mln/value/rgb8.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u12.hh>
+#include <mln/value/label_16.hh>
+
+#include <mln/level/transform.hh>
+#include <mln/level/stretch.hh>
+
+#include <mln/labeling/mean_values.hh>
+
+#include <mln/convert/to_fun.hh>
+
+#include <mln/make/graph.hh>
+
+#include <mln/morpho/gradient.hh>
+#include <mln/morpho/closing/area.hh>
+#include <mln/morpho/meyer_wst.hh>
+
+#include <mln/fun/l2l/wrap.hh>
+
+#include <mln/core/var.hh>
+#include <mln/morpho/elementary/dilation.hh>
+
+#include <mln/core/routine/extend.hh>
+
+#include <mln/util/graph.hh>
+
+#include <mln/essential/2d.hh>
+#include <mln/core/alias/vec3d.hh>
+#include <mln/debug/draw_graph.hh>
+#include <mln/util/graph.hh>
+#include <mln/accu/center.hh>
+#include <mln/io/dump/all.hh>
+#include <mln/value/label_8.hh>
+#include <mln/value/rgb16.hh>
+#include <mln/accu/compute.hh>
+#include <mln/core/alias/dpoint2d.hh>
+#include <mln/draw/box.hh>
+#include <mln/level/stretch.hh>
+#include <mln/fun/v2v/id.hh>
+#include <mln/fun/l2l/wrap.hh>
+#include <mln/core/image/line_graph_elt_neighborhood.hh>
+#include <mln/morpho/elementary/dilation.hh>
+#include <mln/labeling/mean_values.hh>
+#include <mln/extension/adjust_fill.hh>
+#include <mln/extract/all.hh>
+#include <mln/make/region_adjacency_graph.hh>
+
+
+
+// Given a color image and a wshed image, computes the component graph.
+// Vertex values are computed thanks to a RGB image.
+
+namespace mln
+{
+
+ template <typename V>
+ value::int_u8 dist(const V& c1, const V& c2)
+ {
+ unsigned d = math::diff_abs(c1.red(), c2.red());
+ unsigned d_;
+ d_ = math::diff_abs(c1.green(), c2.green());
+
+ if (d_ > d)
+ d = d_;
+
+ d_ = math::diff_abs(c1.blue(), c2.blue());
+
+ if (d_ > d)
+ d = d_;
+ return d;
+ }
+
+
+ // ima_v, image on graph vertices; value = mean color per vertex (watershed basin)
+ template <typename I>
+ inline
+ pw::image<fun::i2v::array<value::int_u8>,
+ p_edges<util::graph, fun::i2v::array<mln_site(I)> > >
+ make_edge_graph_image(const I& ima_v, const util::graph& g)
+ {
+ // edge sites.
+ typedef fun::i2v::array<mln_site(I)> edge_site_t;
+ edge_site_t edge_site(g.e_nmax(), literal::origin);
+ typedef p_edges<util::graph, edge_site_t > pe_t;
+ pe_t pe(g, edge_site);
+
+ // edge values
+ typedef fun::i2v::array<value::int_u8> edge_values_t;
+ edge_values_t edge_values(g.e_nmax());
+
+ // image on graph edges
+ typedef pw::image<edge_values_t, pe_t> ima_e_t;
+ ima_e_t ima_e = (edge_values | pe);
+
+ mln_piter(ima_e_t) e(ima_e.domain());
+ for_all(e) // in ima_e
+ ima_e(e) = math::diff_abs(ima_v.function()(e.element().v1()), ima_v.function()(e.element().v2()));
+
+ return ima_e;
+ }
+
+
+ template <typename I, typename J>
+ inline
+ util::array<mln_value(I)>
+ mean_color_values(const I& input, const J& w, mln_value(J) nbasins)
+ {
+ // Cf. sandbox/theo/color/segment_rgb_pixels.cc
+
+ util::array<float> m_3f = labeling::compute(accu::mean<mln_value(I)>(),
+ input, // input color image
+ w, // watershed labeling
+ nbasins);
+ m_3f[0] = literal::zero;
+
+ util::array<mln_value(I)> m;
+ convert::from_to(m_3f, m);
+ m[0] = 150u;
+
+ /*io::ppm::save(level::transform(w,
+ convert::to< fun::i2v::array<mln_value(I)> >(m)),
+ "wst_rag_wshd_color.ppm");*/
+
+ return m;
+ }
+
+
+ template <typename I, typename J>
+ pw::image<fun::i2v::array<mln_value(I)>, p_vertices<util::graph, fun::i2v::array<mln_site(I)> > >
+ make_vertex_graph_image(const util::graph& g, const I&input, const J& w, const mln_value(J)& nbasins)
+ {
+ typedef util::array<mln_site(I)> vertex_sites_t;
+ vertex_sites_t site_values;
+ convert::from_to(labeling::compute(accu::center<mln_site(I)>(), w, nbasins),
+ site_values);
+
+ typedef fun::i2v::array<mln_site(J)> f_sites_t;
+ f_sites_t sites;
+ convert::from_to(site_values, sites);
+
+ // p_vertices
+ typedef p_vertices<util::graph, f_sites_t> S;
+ S pv(g, sites);
+
+
+ typedef fun::i2v::array<mln_value(I)> vertex_values_t;
+ vertex_values_t vertex_values;
+ convert::from_to(mean_color_values(input, w, nbasins), vertex_values);
+
+ mln_VAR(ima_v, (vertex_values | pv));
+
+ return ima_v;
+ }
+
+
+ template <typename I, typename V>
+ struct edge_to_color : Function_p2v< edge_to_color<I,V> >
+ {
+ typedef V result;
+
+ edge_to_color(const I& ima)
+ : ima_(ima)
+ {
+ }
+
+ V
+ operator()(const unsigned& e) const
+ {
+ return convert::to<V>(ima_.function()(e));
+ }
+
+ const I& ima_;
+ };
+
+ template <typename V>
+ inline
+ unsigned
+ find_root(util::array<V>& parent, const unsigned& x)
+ {
+ if (parent[x] == x)
+ return x;
+ else
+ return parent[x] = find_root(parent, parent[x]);
+ }
+
+
+ template <typename I, typename V, typename E>
+ inline
+ image2d<mln_value(I)>
+ make_debug_graph_image(const I& input,
+ const V& ima_v, const E& ima_e,
+ unsigned box_size, const value::int_u12& bg)
+ {
+ image2d<mln_value(I)> ima;
+ initialize(ima, input);
+
+ data::fill(ima, bg);
+ debug::draw_graph(ima, ima_v.domain(),
+ pw::cst(150u),
+ edge_to_color<E, mln_value(I)>(ima_e));
+
+ dpoint2d tl(-box_size,-box_size);
+ dpoint2d br(box_size,box_size);
+ mln_piter(V) p(ima_v.domain());
+ for_all(p)
+ {
+ box2d b(p + tl, p + br);
+ b.crop_wrt(ima.domain());
+ data::fill((ima | b).rw(), convert::to<mln_value(I)>(ima_v(p)));
+ }
+
+ return ima;
+ }
+
+}
+
+
+///////////////////
+// //
+// Main Function //
+// //
+///////////////////
+
+
+int main(int argc, char *argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+ using value::int_u12;
+ using value::rgb8;
+ using value::label_16;
+
+ if (argc < 4)
+ {
+ std::cout << "Usage: " << argv[0] << " <ima.dcm> <closure_lambda> <box_size> <dist_max>"
+ << std::endl;
+ return 1;
+ }
+
+ unsigned closure_lambda = atoi(argv[2]);
+ unsigned box_size = atoi(argv[3]);
+ unsigned dist_max = atoi(argv[4]);
+
+ image2d<int_u12> dcm;
+ io::dicom::load(dcm, argv[1]);
+
+ io::pgm::save(level::stretch(int_u8(), dcm), "wsd_01_src.pgm");
+
+ image2d<int_u12> grad = morpho::gradient(dcm, win_c4p());
+ image2d<int_u12> clo = morpho::closing::area(grad, c4(), closure_lambda);
+
+ label_16 nbasins;
+ image2d<label_16> wshed = morpho::meyer_wst(clo, c4(), nbasins);
+
+ io::pgm::save(level::stretch(int_u8(), clo), "wsd_02.pgm");
+ io::pgm::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_03.pgm");
+
+ mln_VAR(vol2_, morpho::elementary::dilation(extend(wshed | (pw::value(wshed) == 0u), wshed), c8()));
+
+ data::fill((wshed | (pw::value(wshed) == 0u)).rw(), vol2_);
+
+ io::pgm::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_04.pgm");
+
+ /// Build graph
+ util::graph g = make::graph(wshed, c4(), nbasins);
+ // Build graph images and compute distance values with a RGB image.
+ mln_VAR(ima_v, make_vertex_graph_image(g, dcm, wshed, nbasins));
+ mln_VAR(ima_e, make_edge_graph_image(ima_v, g));
+
+ /// Try to merge vertices.
+ mln_piter_(ima_e_t) e(ima_e.domain());
+ util::array<label_16> parent(g.v_nmax());
+ for (unsigned i = 0; i < parent.nelements(); ++i)
+ parent[i] = i;
+
+ for_all(e)
+ {
+ unsigned v1 = e.element().v1();
+ unsigned v2 = e.element().v2();
+ if (ima_e(e) <= dist_max && find_root(parent, v1) != find_root(parent, v2))
+ parent[find_root(parent, v1)] = find_root(parent, v2);
+ }
+
+ fun::i2v::array<label_16> f(parent.nelements());
+ std::vector<unsigned> new_label(parent.nelements(), 0);
+ unsigned nbasins2 = 0;
+ for (unsigned i = 0; i < parent.nelements(); ++i)
+ {
+ unsigned p = find_root(parent, i);
+ mln_assertion(parent[p] == find_root(parent, i));
+ if (new_label[p] == 0)
+ new_label[p] = nbasins2++;
+ f(i) = new_label[p];
+ }
+ mln_invariant(f(0) == 0u);
+ --nbasins2; // nbasins2 does not count the basin with label 0.
+ image2d<label_16> wsd2 = level::transform(wshed, f);
+
+ io::pgm::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_05.pgm");
+
+ /// Reconstruct a graph from the simplified image.
+ util::graph g2 = make::graph(wsd2, c4(), nbasins2);
+
+ // Compute distance values with a RGB image.
+ mln_VAR(ima_v2, make_vertex_graph_image(g2, dcm, wsd2, nbasins2));
+ mln_VAR(ima_e2, make_edge_graph_image(ima_v2, g2));
+
+ mln_VAR(wsd2_, morpho::elementary::dilation(extend(wsd2 | (pw::value(wsd2) == 0u), wsd2), c8()));
+
+ data::fill((wsd2 | (pw::value(wsd2) == 0u)).rw(), wsd2_);
+
+ io::pgm::save(level::transform(labeling::mean_values(dcm, wsd2, nbasins2), fun::l2l::wrap<int_u8>()), "wsd_06_mean_colors.pgm");
+ io::pgm::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 4095)), "wsd_07_graph_image2_white.pgm");
+ io::pgm::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 0)), "wsd_08_graph_image2_black.pgm");
+ io::pgm::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_99_result.pgm");
+}
Index: trunk/milena/sandbox/fabien/igr/watershed3d.cc
===================================================================
--- trunk/milena/sandbox/fabien/igr/watershed3d.cc (revision 0)
+++ trunk/milena/sandbox/fabien/igr/watershed3d.cc (revision 3503)
@@ -0,0 +1,334 @@
+#include <iostream>
+#include <mln/core/image/image2d.hh>
+#include <mln/core/image/image3d.hh>
+
+#include <mln/core/alias/neighb2d.hh>
+#include <mln/core/alias/window2d.hh>
+#include <mln/core/alias/neighb3d.hh>
+#include <mln/core/alias/window3d.hh>
+#include <mln/core/image/image_if.hh>
+
+#include <mln/io/ppm/save.hh>
+#include <mln/io/ppm/load.hh>
+#include <mln/io/pgm/load.hh>
+#include <mln/io/dicom/load.hh>
+#include <mln/io/pgm/save.hh>
+#include <mln/io/dump/save.hh>
+
+#include <mln/value/rgb8.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u12.hh>
+#include <mln/value/label_16.hh>
+
+#include <mln/level/transform.hh>
+#include <mln/level/stretch.hh>
+
+#include <mln/labeling/mean_values.hh>
+
+#include <mln/convert/to_fun.hh>
+
+#include <mln/make/graph.hh>
+
+#include <mln/morpho/gradient.hh>
+#include <mln/morpho/closing/area.hh>
+#include <mln/morpho/meyer_wst.hh>
+
+#include <mln/fun/l2l/wrap.hh>
+
+#include <mln/core/var.hh>
+#include <mln/morpho/elementary/dilation.hh>
+
+#include <mln/core/routine/extend.hh>
+
+#include <mln/util/graph.hh>
+
+#include <mln/essential/2d.hh>
+#include <mln/core/alias/vec3d.hh>
+#include <mln/debug/draw_graph.hh>
+#include <mln/util/graph.hh>
+#include <mln/accu/center.hh>
+#include <mln/io/dump/all.hh>
+#include <mln/value/label_8.hh>
+#include <mln/value/rgb16.hh>
+#include <mln/accu/compute.hh>
+#include <mln/core/alias/dpoint2d.hh>
+#include <mln/draw/box.hh>
+#include <mln/level/stretch.hh>
+#include <mln/fun/v2v/id.hh>
+#include <mln/fun/l2l/wrap.hh>
+#include <mln/core/image/line_graph_elt_neighborhood.hh>
+#include <mln/morpho/elementary/dilation.hh>
+#include <mln/labeling/mean_values.hh>
+#include <mln/extension/adjust_fill.hh>
+#include <mln/extract/all.hh>
+#include <mln/make/region_adjacency_graph.hh>
+
+
+
+// Given a color image and a wshed image, computes the component graph.
+// Vertex values are computed thanks to a RGB image.
+
+namespace mln
+{
+
+ template <typename V>
+ value::int_u8 dist(const V& c1, const V& c2)
+ {
+ unsigned d = math::diff_abs(c1.red(), c2.red());
+ unsigned d_;
+ d_ = math::diff_abs(c1.green(), c2.green());
+
+ if (d_ > d)
+ d = d_;
+
+ d_ = math::diff_abs(c1.blue(), c2.blue());
+
+ if (d_ > d)
+ d = d_;
+ return d;
+ }
+
+
+ // ima_v, image on graph vertices; value = mean color per vertex (watershed basin)
+ template <typename I>
+ inline
+ pw::image<fun::i2v::array<value::int_u8>,
+ p_edges<util::graph, fun::i2v::array<mln_site(I)> > >
+ make_edge_graph_image(const I& ima_v, const util::graph& g)
+ {
+ // edge sites.
+ typedef fun::i2v::array<mln_site(I)> edge_site_t;
+ edge_site_t edge_site(g.e_nmax(), literal::origin);
+ typedef p_edges<util::graph, edge_site_t > pe_t;
+ pe_t pe(g, edge_site);
+
+ // edge values
+ typedef fun::i2v::array<value::int_u8> edge_values_t;
+ edge_values_t edge_values(g.e_nmax());
+
+ // image on graph edges
+ typedef pw::image<edge_values_t, pe_t> ima_e_t;
+ ima_e_t ima_e = (edge_values | pe);
+
+ mln_piter(ima_e_t) e(ima_e.domain());
+ for_all(e) // in ima_e
+ ima_e(e) = math::diff_abs(ima_v.function()(e.element().v1()), ima_v.function()(e.element().v2()));
+
+ return ima_e;
+ }
+
+
+ template <typename I, typename J>
+ inline
+ util::array<mln_value(I)>
+ mean_color_values(const I& input, const J& w, mln_value(J) nbasins)
+ {
+ // Cf. sandbox/theo/color/segment_rgb_pixels.cc
+
+ util::array<float> m_3f = labeling::compute(accu::mean<mln_value(I)>(),
+ input, // input color image
+ w, // watershed labeling
+ nbasins);
+ m_3f[0] = literal::zero;
+
+ util::array<mln_value(I)> m;
+ convert::from_to(m_3f, m);
+ m[0] = 150u;
+
+ /*io::ppm::save(level::transform(w,
+ convert::to< fun::i2v::array<mln_value(I)> >(m)),
+ "wst_rag_wshd_color.ppm");*/
+
+ return m;
+ }
+
+
+ template <typename I, typename J>
+ pw::image<fun::i2v::array<mln_value(I)>, p_vertices<util::graph, fun::i2v::array<mln_site(I)> > >
+ make_vertex_graph_image(const util::graph& g, const I&input, const J& w, const mln_value(J)& nbasins)
+ {
+ typedef util::array<mln_site(I)> vertex_sites_t;
+ vertex_sites_t site_values;
+ convert::from_to(labeling::compute(accu::center<mln_site(I)>(), w, nbasins),
+ site_values);
+
+ typedef fun::i2v::array<mln_site(J)> f_sites_t;
+ f_sites_t sites;
+ convert::from_to(site_values, sites);
+
+ // p_vertices
+ typedef p_vertices<util::graph, f_sites_t> S;
+ S pv(g, sites);
+
+
+ typedef fun::i2v::array<mln_value(I)> vertex_values_t;
+ vertex_values_t vertex_values;
+ convert::from_to(mean_color_values(input, w, nbasins), vertex_values);
+
+ mln_VAR(ima_v, (vertex_values | pv));
+
+ return ima_v;
+ }
+
+
+ template <typename I, typename V>
+ struct edge_to_color : Function_p2v< edge_to_color<I,V> >
+ {
+ typedef V result;
+
+ edge_to_color(const I& ima)
+ : ima_(ima)
+ {
+ }
+
+ V
+ operator()(const unsigned& e) const
+ {
+ return convert::to<V>(ima_.function()(e));
+ }
+
+ const I& ima_;
+ };
+
+ template <typename V>
+ inline
+ unsigned
+ find_root(util::array<V>& parent, const unsigned& x)
+ {
+ if (parent[x] == x)
+ return x;
+ else
+ return parent[x] = find_root(parent, parent[x]);
+ }
+
+
+ template <typename I, typename V, typename E>
+ inline
+ image3d<mln_value(I)>
+ make_debug_graph_image(const I& input,
+ const V& ima_v, const E& ima_e,
+ unsigned box_size, const value::int_u12& bg)
+ {
+ image3d<mln_value(I)> ima;
+ initialize(ima, input);
+
+ data::fill(ima, bg);
+ debug::draw_graph(ima, ima_v.domain(),
+ pw::cst(150u),
+ edge_to_color<E, mln_value(I)>(ima_e));
+
+ dpoint3d tl(-box_size,-box_size, -box_size);
+ dpoint3d br(box_size,box_size, -box_size);
+ mln_piter(V) p(ima_v.domain());
+ for_all(p)
+ {
+ box3d b(p + tl, p + br);
+ b.crop_wrt(ima.domain());
+ data::fill((ima | b).rw(), convert::to<mln_value(I)>(ima_v(p)));
+ }
+
+ return ima;
+ }
+
+}
+
+
+///////////////////
+// //
+// Main Function //
+// //
+///////////////////
+
+
+int main(int argc, char *argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+ using value::int_u12;
+ using value::rgb8;
+ using value::label_16;
+
+ if (argc < 4)
+ {
+ std::cout << "Usage: " << argv[0] << " <ima.dcm> <closure_lambda> <box_size> <dist_max>"
+ << std::endl;
+ return 1;
+ }
+
+ unsigned closure_lambda = atoi(argv[2]);
+ unsigned box_size = atoi(argv[3]);
+ unsigned dist_max = atoi(argv[4]);
+
+ image3d<int_u12> dcm;
+ io::dicom::load(dcm, argv[1]);
+
+ io::dump::save(level::stretch(int_u8(), dcm), "wsd_01_src.dump");
+
+ image3d<int_u12> grad = morpho::gradient(dcm, win_c4p_3d());
+ image3d<int_u12> clo = morpho::closing::area(grad, c6(), closure_lambda);
+
+ label_16 nbasins;
+ image3d<label_16> wshed = morpho::meyer_wst(clo, c6(), nbasins);
+
+ io::dump::save(level::stretch(int_u8(), clo), "wsd_02.dump");
+ io::dump::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_03.dump");
+
+ mln_VAR(vol2_, morpho::elementary::dilation(extend(wshed | (pw::value(wshed) == 0u), wshed), c26()));
+
+ data::fill((wshed | (pw::value(wshed) == 0u)).rw(), vol2_);
+
+ io::dump::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_04.dump");
+
+ /// Build graph
+ util::graph g = make::graph(wshed, c6(), nbasins);
+ // Build graph images and compute distance values with a RGB image.
+ mln_VAR(ima_v, make_vertex_graph_image(g, dcm, wshed, nbasins));
+ mln_VAR(ima_e, make_edge_graph_image(ima_v, g));
+
+ /// Try to merge vertices.
+ mln_piter_(ima_e_t) e(ima_e.domain());
+ util::array<label_16> parent(g.v_nmax());
+ for (unsigned i = 0; i < parent.nelements(); ++i)
+ parent[i] = i;
+
+ for_all(e)
+ {
+ unsigned v1 = e.element().v1();
+ unsigned v2 = e.element().v2();
+ if (ima_e(e) <= dist_max && find_root(parent, v1) != find_root(parent, v2))
+ parent[find_root(parent, v1)] = find_root(parent, v2);
+ }
+
+ fun::i2v::array<label_16> f(parent.nelements());
+ std::vector<unsigned> new_label(parent.nelements(), 0);
+ unsigned nbasins2 = 0;
+ for (unsigned i = 0; i < parent.nelements(); ++i)
+ {
+ unsigned p = find_root(parent, i);
+ mln_assertion(parent[p] == find_root(parent, i));
+ if (new_label[p] == 0)
+ new_label[p] = nbasins2++;
+ f(i) = new_label[p];
+ }
+ mln_invariant(f(0) == 0u);
+ --nbasins2; // nbasins2 does not count the basin with label 0.
+ image3d<label_16> wsd2 = level::transform(wshed, f);
+
+ io::dump::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_05.dump");
+
+ /// Reconstruct a graph from the simplified image.
+ util::graph g2 = make::graph(wsd2, c6(), nbasins2);
+
+ // Compute distance values with a RGB image.
+ mln_VAR(ima_v2, make_vertex_graph_image(g2, dcm, wsd2, nbasins2));
+ mln_VAR(ima_e2, make_edge_graph_image(ima_v2, g2));
+
+ mln_VAR(wsd2_, morpho::elementary::dilation(extend(wsd2 | (pw::value(wsd2) == 0u), wsd2), c26()));
+
+ data::fill((wsd2 | (pw::value(wsd2) == 0u)).rw(), wsd2_);
+
+ io::dump::save(level::transform(labeling::mean_values(dcm, wsd2, nbasins2), fun::l2l::wrap<int_u8>()), "wsd_06_mean_colors.dump");
+ //io::dump::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 4095)), "wsd_07_graph_image2_white.dump");
+ //io::dump::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 0)), "wsd_08_graph_image2_black.dump");
+ io::dump::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_99_result.dump");
+}
Index: trunk/milena/sandbox/fabien/igr/watershed.hh
===================================================================
--- trunk/milena/sandbox/fabien/igr/watershed.hh (revision 0)
+++ trunk/milena/sandbox/fabien/igr/watershed.hh (revision 3503)
@@ -0,0 +1,331 @@
+#include <iostream>
+#include <mln/core/image/image2d.hh>
+
+#include <mln/core/alias/neighb2d.hh>
+#include <mln/core/alias/window2d.hh>
+#include <mln/core/image/image_if.hh>
+
+#include <mln/io/ppm/save.hh>
+#include <mln/io/ppm/load.hh>
+#include <mln/io/pgm/load.hh>
+#include <mln/io/dicom/load.hh>
+#include <mln/io/pgm/save.hh>
+#include <mln/io/dump/save.hh>
+
+#include <mln/value/rgb8.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u12.hh>
+#include <mln/value/label_16.hh>
+
+#include <mln/level/transform.hh>
+#include <mln/level/stretch.hh>
+
+#include <mln/labeling/mean_values.hh>
+
+#include <mln/convert/to_fun.hh>
+
+#include <mln/make/graph.hh>
+
+#include <mln/morpho/gradient.hh>
+#include <mln/morpho/closing/area.hh>
+#include <mln/morpho/meyer_wst.hh>
+
+#include <mln/fun/l2l/wrap.hh>
+
+#include <mln/core/var.hh>
+#include <mln/morpho/elementary/dilation.hh>
+
+#include <mln/core/routine/extend.hh>
+
+#include <mln/util/graph.hh>
+
+#include <mln/essential/2d.hh>
+#include <mln/core/alias/vec3d.hh>
+#include <mln/debug/draw_graph.hh>
+#include <mln/util/graph.hh>
+#include <mln/accu/center.hh>
+#include <mln/io/dump/all.hh>
+#include <mln/value/label_8.hh>
+#include <mln/value/rgb16.hh>
+#include <mln/accu/compute.hh>
+#include <mln/core/alias/dpoint2d.hh>
+#include <mln/draw/box.hh>
+#include <mln/level/stretch.hh>
+#include <mln/fun/v2v/id.hh>
+#include <mln/fun/l2l/wrap.hh>
+#include <mln/core/image/line_graph_elt_neighborhood.hh>
+#include <mln/morpho/elementary/dilation.hh>
+#include <mln/labeling/mean_values.hh>
+#include <mln/extension/adjust_fill.hh>
+#include <mln/extract/all.hh>
+#include <mln/make/region_adjacency_graph.hh>
+
+
+
+// Given a color image and a wshed image, computes the component graph.
+// Vertex values are computed thanks to a RGB image.
+
+namespace mln
+{
+
+ template <typename V>
+ value::int_u8 dist(const V& c1, const V& c2)
+ {
+ unsigned d = math::diff_abs(c1.red(), c2.red());
+ unsigned d_;
+ d_ = math::diff_abs(c1.green(), c2.green());
+
+ if (d_ > d)
+ d = d_;
+
+ d_ = math::diff_abs(c1.blue(), c2.blue());
+
+ if (d_ > d)
+ d = d_;
+ return d;
+ }
+
+
+ // ima_v, image on graph vertices; value = mean color per vertex (watershed basin)
+ template <typename I>
+ inline
+ pw::image<fun::i2v::array<value::int_u8>,
+ p_edges<util::graph, fun::i2v::array<mln_site(I)> > >
+ make_edge_graph_image(const I& ima_v, const util::graph& g)
+ {
+ // edge sites.
+ typedef fun::i2v::array<mln_site(I)> edge_site_t;
+ edge_site_t edge_site(g.e_nmax(), literal::origin);
+ typedef p_edges<util::graph, edge_site_t > pe_t;
+ pe_t pe(g, edge_site);
+
+ // edge values
+ typedef fun::i2v::array<value::int_u8> edge_values_t;
+ edge_values_t edge_values(g.e_nmax());
+
+ // image on graph edges
+ typedef pw::image<edge_values_t, pe_t> ima_e_t;
+ ima_e_t ima_e = (edge_values | pe);
+
+ mln_piter(ima_e_t) e(ima_e.domain());
+ for_all(e) // in ima_e
+ ima_e(e) = math::diff_abs(ima_v.function()(e.element().v1()), ima_v.function()(e.element().v2()));
+
+ return ima_e;
+ }
+
+
+ template <typename I, typename J>
+ inline
+ util::array<mln_value(I)>
+ mean_color_values(const I& input, const J& w, mln_value(J) nbasins)
+ {
+ // Cf. sandbox/theo/color/segment_rgb_pixels.cc
+
+ util::array<float> m_3f = labeling::compute(accu::mean<mln_value(I)>(),
+ input, // input color image
+ w, // watershed labeling
+ nbasins);
+ m_3f[0] = literal::zero;
+
+ util::array<mln_value(I)> m;
+ convert::from_to(m_3f, m);
+ m[0] = 150u;
+
+ /*io::ppm::save(level::transform(w,
+ convert::to< fun::i2v::array<mln_value(I)> >(m)),
+ "wst_rag_wshd_color.ppm");*/
+
+ return m;
+ }
+
+
+ template <typename I, typename J>
+ pw::image<fun::i2v::array<mln_value(I)>, p_vertices<util::graph, fun::i2v::array<mln_site(I)> > >
+ make_vertex_graph_image(const util::graph& g, const I&input, const J& w, const mln_value(J)& nbasins)
+ {
+ typedef util::array<mln_site(I)> vertex_sites_t;
+ vertex_sites_t site_values;
+ convert::from_to(labeling::compute(accu::center<mln_site(I)>(), w, nbasins),
+ site_values);
+
+ typedef fun::i2v::array<mln_site(J)> f_sites_t;
+ f_sites_t sites;
+ convert::from_to(site_values, sites);
+
+ // p_vertices
+ typedef p_vertices<util::graph, f_sites_t> S;
+ S pv(g, sites);
+
+
+ typedef fun::i2v::array<mln_value(I)> vertex_values_t;
+ vertex_values_t vertex_values;
+ convert::from_to(mean_color_values(input, w, nbasins), vertex_values);
+
+ mln_VAR(ima_v, (vertex_values | pv));
+
+ return ima_v;
+ }
+
+
+ template <typename I, typename V>
+ struct edge_to_color : Function_p2v< edge_to_color<I,V> >
+ {
+ typedef V result;
+
+ edge_to_color(const I& ima)
+ : ima_(ima)
+ {
+ }
+
+ V
+ operator()(const unsigned& e) const
+ {
+ return convert::to<V>(ima_.function()(e));
+ }
+
+ const I& ima_;
+ };
+
+ template <typename V>
+ inline
+ unsigned
+ find_root(util::array<V>& parent, const unsigned& x)
+ {
+ if (parent[x] == x)
+ return x;
+ else
+ return parent[x] = find_root(parent, parent[x]);
+ }
+
+
+ template <typename I, typename V, typename E>
+ inline
+ image2d<mln_value(I)>
+ make_debug_graph_image(const I& input,
+ const V& ima_v, const E& ima_e,
+ unsigned box_size, const value::int_u12& bg)
+ {
+ image2d<mln_value(I)> ima;
+ initialize(ima, input);
+
+ data::fill(ima, bg);
+ debug::draw_graph(ima, ima_v.domain(),
+ pw::cst(150u),
+ edge_to_color<E, mln_value(I)>(ima_e));
+
+ dpoint2d tl(-box_size,-box_size);
+ dpoint2d br(box_size,box_size);
+ mln_piter(V) p(ima_v.domain());
+ for_all(p)
+ {
+ box2d b(p + tl, p + br);
+ b.crop_wrt(ima.domain());
+ data::fill((ima | b).rw(), convert::to<mln_value(I)>(ima_v(p)));
+ }
+
+ return ima;
+ }
+
+}
+
+
+///////////////////
+// //
+// Main Function //
+// //
+///////////////////
+
+
+int main(int argc, char *argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+ using value::int_u12;
+ using value::rgb8;
+ using value::label_16;
+
+ if (argc < 4)
+ {
+ std::cout << "Usage: " << argv[0] << " <ima.dcm> <closure_lambda> <box_size> <dist_max>"
+ << std::endl;
+ return 1;
+ }
+
+ unsigned closure_lambda = atoi(argv[2]);
+ unsigned box_size = atoi(argv[3]);
+ unsigned dist_max = atoi(argv[4]);
+
+ image2d<int_u12> dcm;
+ io::dicom::load(dcm, argv[1]);
+
+ io::pgm::save(level::stretch(int_u8(), dcm), "wsd_01_src.pgm");
+
+ image2d<int_u12> grad = morpho::gradient(dcm, win_c4p());
+ image2d<int_u12> clo = morpho::closing::area(grad, c4(), closure_lambda);
+
+ label_16 nbasins;
+ image2d<label_16> wshed = morpho::meyer_wst(clo, c4(), nbasins);
+
+ io::pgm::save(level::stretch(int_u8(), clo), "wsd_02.pgm");
+ io::pgm::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_03.pgm");
+
+ mln_VAR(vol2_, morpho::elementary::dilation(extend(wshed | (pw::value(wshed) == 0u), wshed), c8()));
+
+ data::fill((wshed | (pw::value(wshed) == 0u)).rw(), vol2_);
+
+ io::pgm::save(level::transform(wshed, fun::l2l::wrap<int_u8>()), "wsd_04.pgm");
+
+ /// Build graph
+ util::graph g = make::graph(wshed, c4(), nbasins);
+ // Build graph images and compute distance values with a RGB image.
+ mln_VAR(ima_v, make_vertex_graph_image(g, dcm, wshed, nbasins));
+ mln_VAR(ima_e, make_edge_graph_image(ima_v, g));
+
+ /// Try to merge vertices.
+ mln_piter_(ima_e_t) e(ima_e.domain());
+ util::array<label_16> parent(g.v_nmax());
+ for (unsigned i = 0; i < parent.nelements(); ++i)
+ parent[i] = i;
+
+ for_all(e)
+ {
+ unsigned v1 = e.element().v1();
+ unsigned v2 = e.element().v2();
+ if (ima_e(e) <= dist_max && find_root(parent, v1) != find_root(parent, v2))
+ parent[find_root(parent, v1)] = find_root(parent, v2);
+ }
+
+ fun::i2v::array<label_16> f(parent.nelements());
+ std::vector<unsigned> new_label(parent.nelements(), 0);
+ unsigned nbasins2 = 0;
+ for (unsigned i = 0; i < parent.nelements(); ++i)
+ {
+ unsigned p = find_root(parent, i);
+ mln_assertion(parent[p] == find_root(parent, i));
+ if (new_label[p] == 0)
+ new_label[p] = nbasins2++;
+ f(i) = new_label[p];
+ }
+ mln_invariant(f(0) == 0u);
+ --nbasins2; // nbasins2 does not count the basin with label 0.
+ image2d<label_16> wsd2 = level::transform(wshed, f);
+
+ io::pgm::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_05.pgm");
+
+ /// Reconstruct a graph from the simplified image.
+ util::graph g2 = make::graph(wsd2, c4(), nbasins2);
+
+ // Compute distance values with a RGB image.
+ mln_VAR(ima_v2, make_vertex_graph_image(g2, dcm, wsd2, nbasins2));
+ mln_VAR(ima_e2, make_edge_graph_image(ima_v2, g2));
+
+ mln_VAR(wsd2_, morpho::elementary::dilation(extend(wsd2 | (pw::value(wsd2) == 0u), wsd2), c8()));
+
+ data::fill((wsd2 | (pw::value(wsd2) == 0u)).rw(), wsd2_);
+
+ io::pgm::save(level::transform(labeling::mean_values(dcm, wsd2, nbasins2), fun::l2l::wrap<int_u8>()), "wsd_06_mean_colors.pgm");
+ io::pgm::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 4095)), "wsd_07_graph_image2_white.pgm");
+ io::pgm::save(level::stretch(int_u8(), make_debug_graph_image(dcm, ima_v2, ima_e2, box_size, 0)), "wsd_08_graph_image2_black.pgm");
+ io::pgm::save(level::transform(wsd2, fun::l2l::wrap<int_u8>()), "wsd_99_result.pgm");
+}
Index: trunk/milena/sandbox/fabien/igr/check2d_wsd.sh
===================================================================
--- trunk/milena/sandbox/fabien/igr/check2d_wsd.sh (revision 0)
+++ trunk/milena/sandbox/fabien/igr/check2d_wsd.sh (revision 3503)
@@ -0,0 +1,32 @@
+#!/bin/zsh
+
+process_file ()
+{
+ echo "Processing $2..."
+ box_size=2
+
+ for lambda_closure in 10 50 100 500 1000; do
+ echo " for lambda_closure = ${lambda_closure}";
+
+ for dist_max in 5 10 50 100 500; do
+ echo " for lambda_dist = ${dist_max}";
+
+ ./wsd2d $1 $lambda_closure $box_size $dist_max
+
+ mv wsd_01_src.pgm results/${2}_${lambda_closure}_${dist_max}_01.pgm
+ mv wsd_02.pgm results/${2}_${lambda_closure}_${dist_max}_02.pgm
+ mv wsd_03.pgm results/${2}_${lambda_closure}_${dist_max}_03.pgm
+ mv wsd_04.pgm results/${2}_${lambda_closure}_${dist_max}_04.pgm
+ mv wsd_05.pgm results/${2}_${lambda_closure}_${dist_max}_05.pgm
+ mv wsd_06_mean_colors.pgm results/${2}_${lambda_closure}_${dist_max}_06.pgm
+ mv wsd_07_graph_image2_white.pgm results/${2}_${lambda_closure}_${dist_max}_07.pgm
+ mv wsd_08_graph_image2_black.pgm results/${2}_${lambda_closure}_${dist_max}_08.pgm
+ mv wsd_99_result.pgm results/${2}_${lambda_closure}_${dist_max}_99.pgm
+
+ done;
+ done
+}
+
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0049.dcm" "49"
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0055.dcm" "55"
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0058.dcm" "58"
Property changes on: trunk/milena/sandbox/fabien/igr/check2d_wsd.sh
___________________________________________________________________
Name: svn:executable
+ *
Index: trunk/milena/sandbox/fabien/igr/check3d_wsd.sh
===================================================================
--- trunk/milena/sandbox/fabien/igr/check3d_wsd.sh (revision 0)
+++ trunk/milena/sandbox/fabien/igr/check3d_wsd.sh (revision 3503)
@@ -0,0 +1,34 @@
+#!/bin/zsh
+
+process_file ()
+{
+ echo "Processing $2..."
+ box_size=2
+
+ for lambda_closure in 10 50 100 500 1000; do
+ echo " for lambda_closure = ${lambda_closure}";
+
+ for dist_max in 5 10 50 100 500; do
+ echo " for lambda_dist = ${dist_max}";
+
+ ./wsd3d $1 $lambda_closure $box_size $dist_max
+
+ ../bin/dump2pgm8b wsd_01_src.dump results/${2}_${lambda_closure}_${dist_max}_01.pgm
+ ../bin/dump2pgm8b wsd_02.dump results/${2}_${lambda_closure}_${dist_max}_02.pgm
+ ../bin/dump2pgm8b wsd_03.dump results/${2}_${lambda_closure}_${dist_max}_03.pgm
+ ../bin/dump2pgm8b wsd_04.dump results/${2}_${lambda_closure}_${dist_max}_04.pgm
+ ../bin/dump2pgm8b wsd_05.dump results/${2}_${lambda_closure}_${dist_max}_05.pgm
+ ../bin/dump2pgm8b wsd_06_mean_colors.dump results/${2}_${lambda_closure}_${dist_max}_06.pgm
+#../bin/dump2pgm8b wsd_07_graph_image2_white.dump results/${2}_${lambda_closure}_${dist_max}_07.pgm
+#../bin/dump2pgm8b wsd_08_graph_image2_black.dump results/${2}_${lambda_closure}_${dist_max}_08.pgm
+ ../bin/dump2pgm8b wsd_99_result.dump results/${2}_${lambda_closure}_${dist_max}_99.pgm
+
+ rm *.dump
+
+ done;
+ done
+}
+
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0052.dcm" "52"
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0061.dcm" "61"
+process_file "/Users/HiSoKa/Work/IGR/souris18/irm/IM_0064.dcm" "64"
Property changes on: trunk/milena/sandbox/fabien/igr/check3d_wsd.sh
___________________________________________________________________
Name: svn:executable
+ *
Index: trunk/milena/sandbox/fabien/igr/Makefile
===================================================================
--- trunk/milena/sandbox/fabien/igr/Makefile (revision 3502)
+++ trunk/milena/sandbox/fabien/igr/Makefile (revision 3503)
@@ -8,7 +8,7 @@
-framework CoreFoundation
CXXFLAGS = -DNDEBUG -O1
-all: 2d 3d wsd
+all: 2d 3d wsd2d wsd3d
2d: seg_vol_irm.hh seg2d.cc
g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} seg2d.cc -o seg2d
@@ -16,8 +16,11 @@
3d: seg_vol_irm.hh seg3d.cc
g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} seg3d.cc -o seg3d
-wsd: watershed.cc
- g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} $^ -o wsd
+wsd2d: watershed.hh watershed2d.cc
+ g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} $^ -o wsd2d
+
+wsd3d: watershed.hh watershed3d.cc
+ g++ -I../../../ ${DICOM_INC} ${DICOM_LIB} ${CXXFLAGS} $^ -o wsd3d
clean:
rm -rf *.dump *.p?m *.plot *.log *.csv
Index: trunk/milena/sandbox/fabien/TODO
===================================================================
--- trunk/milena/sandbox/fabien/TODO (revision 3502)
+++ trunk/milena/sandbox/fabien/TODO (revision 3503)
@@ -13,7 +13,7 @@
[X] Generate histograms (normal, bg, obj, p_bg, p_obj)
[ ] Test processing chain on US
[X] Create README file for special images
-[ ] Implement watershed
+[X] Implement watershed
[X] Create tool for dicom mask
[X] Check conversion for mask (everything except int_u12(0))
[ ] Extract ROI (projection or fill holes)
@@ -22,4 +22,7 @@
[ ] After threshold, take biggest object and then erode, dilate
[ ] Fix n_max
[ ] Create routine for binary images (keep n big bg & m big objects)
-[ ] US: projection of internal gradient
+[X] US: projection of internal gradient
+[X] Create 3D US morpho with 2D stack
+[ ] Create macro for_all_slice
+[ ] Batch process watershed with 2D, 3D and any combination of parameters
Index: trunk/milena/sandbox/fabien/bin/dump2pgm.cc
===================================================================
--- trunk/milena/sandbox/fabien/bin/dump2pgm.cc (revision 0)
+++ trunk/milena/sandbox/fabien/bin/dump2pgm.cc (revision 3503)
@@ -0,0 +1,37 @@
+#include <mln/core/image/image2d.hh>
+#include <mln/make/image3d.hh>
+#include <mln/debug/slices_2d.hh>
+
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u12.hh>
+#include <mln/io/dump/load.hh>
+#include <mln/io/pgm/save.hh>
+
+#include <mln/literal/colors.hh>
+
+
+int usage(char* argv[])
+{
+ std::cerr << "usage: " << argv[0] << " input.dump output.pgm" << std::endl;
+ return 1;
+}
+
+
+
+int main(int argc, char* argv[])
+{
+ using namespace mln;
+ using value::rgb8;
+
+ if (argc != 3)
+ return usage(argv);
+
+ image3d<int_u12> vol;
+ io::dump::load(vol, argv[1]);
+
+ rgb8 bg = literal::black;
+ image2d<int_u8> ima = debug::slices_2d(vol, 1.f, bg);
+ io::pgm::save(ima, argv[2]);
+
+ return 0;
+}
Index: trunk/milena/sandbox/fabien/bin/filetype.hh
===================================================================
--- trunk/milena/sandbox/fabien/bin/filetype.hh (revision 0)
+++ trunk/milena/sandbox/fabien/bin/filetype.hh (revision 3503)
@@ -0,0 +1,54 @@
+#include <string>
+
+// 2d
+#include <mln/core/image/image2d.hh>
+#include <mln/core/alias/neighb2d.hh>
+
+// 3d
+#include <mln/core/image/image3d.hh>
+#include <mln/core/alias/neighb3d.hh>
+
+
+// pbm
+#include <mln/io/pbm/load.hh>
+#include <mln/io/pbm/save.hh>
+
+// pgm
+#include <mln/io/pgm/load.hh>
+#include <mln/io/pgm/save.hh>
+
+// ppm
+#include <mln/io/ppm/load.hh>
+#include <mln/io/ppm/save.hh>
+
+
+//dump
+#include <mln/io/dump/load.hh>
+#include <mln/io/dump/save.hh>
+
+
+namespace mln
+{
+
+ namespace filetype
+ {
+ enum id { pbm, pgm, ppm, dump, unknown };
+ }
+
+ filetype::id
+ get_filetype(const std::string& filename)
+ {
+ if (filename.find(".pbm") == filename.length() - 4)
+ return filetype::pbm;
+ if (filename.find(".pgm") == filename.length() - 4)
+ return filetype::pgm;
+ if (filename.find(".ppm") == filename.length() - 4)
+ return filetype::ppm;
+ if (filename.find(".dump") == filename.length() - 5)
+ return filetype::dump;
+ return filetype::unknown;
+ }
+
+} // mln
+
+
Index: trunk/milena/sandbox/fabien/bin/dump_mask.cc
===================================================================
--- trunk/milena/sandbox/fabien/bin/dump_mask.cc (revision 0)
+++ trunk/milena/sandbox/fabien/bin/dump_mask.cc (revision 3503)
@@ -0,0 +1,86 @@
+#include <mln/core/concept/image.hh>
+#include <mln/core/image/image2d.hh>
+#include <mln/core/image/image3d.hh>
+#include <mln/core/image/slice_image.hh>
+#include <mln/core/alias/neighb2d.hh>
+#include <mln/core/alias/neighb3d.hh>
+#include <mln/core/var.hh>
+
+#include <mln/geom/ncols.hh>
+#include <mln/geom/nrows.hh>
+
+#include <mln/value/int_u8.hh>
+#include <mln/io/dump/load.hh>
+#include <mln/io/pbm/save.hh>
+
+#include <mln/literal/colors.hh>
+#include <mln/morpho/elementary/gradient_internal.hh>
+
+#include <mln/level/transform.hh>
+#include <mln/fun/v2b/threshold.hh>
+
+#include <mln/data/fill.hh>
+#include <mln/pw/all.hh>
+
+
+int usage(char* argv[])
+{
+ std::cerr << "usage: " << argv[0] << " input.dump" << std::endl;
+ return 1;
+}
+
+
+
+int main(int argc, char* argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+
+ if (argc != 2)
+ return usage(argv);
+
+ image3d<int_u8> input;
+ io::dump::load(input, argv[1]);
+
+ image3d<bool> ima = level::transform(input, fun::v2b::threshold<int_u8>(1));
+ mln_VAR(grad_int, morpho::elementary::gradient_internal(ima, c6()));
+
+ util::array<unsigned> xproj(ima.nrows(), 0);
+ util::array<unsigned> yproj(ima.ncols(), 0);
+ util::array<unsigned> xgradproj(grad_int.nrows(), 0);
+ util::array<unsigned> ygradproj(grad_int.ncols(), 0);
+
+ mln_piter_(image3d<bool>) p(ima.domain());
+ for_all(p)
+ {
+ if (ima(p))
+ {
+ ++xproj[p.row()];
+ ++yproj[p.col()];
+ }
+ if (grad_int(p))
+ {
+ ++xgradproj[p.row()];
+ ++ygradproj[p.col()];
+ }
+ }
+
+ // Plot files
+ std::ofstream fout_x("x.plot");
+ std::ofstream fout_xgrad("xgrad.plot");
+ for (unsigned int i = 0; i < xproj.nelements(); ++i)
+ {
+ fout_x << i << " " << xproj[i] << std::endl;
+ fout_xgrad << i << " " << xgradproj[i] << std::endl;
+ }
+
+ std::ofstream fout_y("y.plot");
+ std::ofstream fout_ygrad("ygrad.plot");
+ for (unsigned int i = 0; i < yproj.nelements(); ++i)
+ {
+ fout_y << i << " " << yproj[i] << std::endl;
+ fout_ygrad << i << " " << ygradproj[i] << std::endl;
+ }
+
+ return 0;
+}
Index: trunk/milena/sandbox/fabien/bin/dicom2pgm.cc
===================================================================
--- trunk/milena/sandbox/fabien/bin/dicom2pgm.cc (revision 0)
+++ trunk/milena/sandbox/fabien/bin/dicom2pgm.cc (revision 3503)
@@ -0,0 +1,34 @@
+#include <mln/core/concept/image.hh>
+#include <mln/core/image/image2d.hh>
+#include <mln/core/image/image3d.hh>
+
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u12.hh>
+#include <mln/io/dicom/load.hh>
+#include <mln/io/pgm/save.hh>
+
+
+
+int usage(char* argv[])
+{
+ std::cerr << "usage: " << argv[0] << " input.dcm output.dump" << std::endl;
+ std::cerr << "\t work for 2D images encoded in int_u8" << std::endl;
+ return 1;
+}
+
+
+int main(int argc, char* argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+ using value::int_u12;
+
+ if (argc != 3)
+ return usage(argv);
+
+ image2d<int_u8> ima;
+ io::dicom::load(ima, argv[1]);
+ io::pgm::save(ima, argv[2]);
+
+ return 0;
+}
Index: trunk/milena/sandbox/fabien/bin/dump2pgm8b.cc
===================================================================
--- trunk/milena/sandbox/fabien/bin/dump2pgm8b.cc (revision 0)
+++ trunk/milena/sandbox/fabien/bin/dump2pgm8b.cc (revision 3503)
@@ -0,0 +1,38 @@
+#include <mln/core/image/image2d.hh>
+#include <mln/make/image3d.hh>
+#include <mln/debug/slices_2d.hh>
+
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u12.hh>
+#include <mln/io/dump/load.hh>
+#include <mln/io/pgm/save.hh>
+
+#include <mln/literal/colors.hh>
+
+
+int usage(char* argv[])
+{
+ std::cerr << "usage: " << argv[0] << " input.dump output.pgm" << std::endl;
+ return 1;
+}
+
+
+
+int main(int argc, char* argv[])
+{
+ using namespace mln;
+ using value::rgb8;
+ using value::int_u8;
+
+ if (argc != 3)
+ return usage(argv);
+
+ image3d<int_u8> vol;
+ io::dump::load(vol, argv[1]);
+
+ rgb8 bg = literal::black;
+ image2d<int_u8> ima = debug::slices_2d(vol, 1.f, 0);
+ io::pgm::save(ima, argv[2]);
+
+ return 0;
+}
Index: trunk/milena/sandbox/fabien/bin/pnms2dump.cc
===================================================================
--- trunk/milena/sandbox/fabien/bin/pnms2dump.cc (revision 0)
+++ trunk/milena/sandbox/fabien/bin/pnms2dump.cc (revision 3503)
@@ -0,0 +1,97 @@
+#include "filetype.hh"
+
+#include <mln/make/image3d.hh>
+
+
+
+
+void usage(char* argv[])
+{
+ std::cerr << "usage: " << argv[0] << " output.dump input1.xxx .. inputn.xxx" << std::endl;
+ std::cerr << " It works with binary (pbm), gray-level (int_u8), and color (rgb8) images." << std::endl;
+ abort();
+}
+
+
+
+int main(int argc, char* argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+
+ if (argc < 3)
+ usage(argv);
+
+ trace::entering("main");
+
+ std::string filename = argv[2];
+
+ switch (get_filetype(argv[2]))
+ {
+ case filetype::pbm:
+ {
+ typedef image2d<bool> I;
+ util::array<I> arr;
+ for (int i = 2; i < argc; ++i)
+ {
+ I ima;
+ io::pbm::load(ima, argv[i]);
+ arr.append(ima);
+ }
+ image3d<bool> vol = make::image3d(arr);
+ io::dump::save(vol, argv[1]);
+ }
+ break;
+
+ case filetype::pgm:
+ {
+ using value::int_u8;
+ typedef image2d<int_u8> I;
+ util::array<I> arr;
+ for (int i = 2; i < argc; ++i)
+ {
+ I ima;
+ io::pgm::load(ima, argv[i]);
+ arr.append(ima);
+ }
+ image3d<int_u8> vol = make::image3d(arr);
+ io::dump::save(vol, argv[1]);
+ }
+ break;
+
+ case filetype::ppm:
+ {
+ using value::rgb8;
+ typedef image2d<rgb8> I;
+ util::array<I> arr;
+ for (int i = 2; i < argc; ++i)
+ {
+ I ima;
+ io::ppm::load(ima, argv[i]);
+ arr.append(ima);
+ }
+ image3d<rgb8> vol = make::image3d(arr);
+ io::dump::save(vol, argv[1]);
+ }
+ break;
+
+ case filetype::dump:
+ {
+ std::cerr << "Output shall not be a dump file!" << std::endl;
+ usage(argv);
+ }
+ break;
+
+ case filetype::unknown:
+ std::cerr << "unknown filename extension!" << std::endl;
+ usage(argv);
+ break;
+
+ default:
+ std::cerr << "file type not handled!" << std::endl;
+ usage(argv);
+ }
+
+ trace::exiting("main");
+
+}
1
0