31 #include <mln/core/image/image2d.hh>
32 #include <mln/core/routine/duplicate.hh>
33 #include <mln/core/alias/neighb2d.hh>
34 #include <mln/core/site_set/p_queue_fast.hh>
35 #include <mln/labeling/blobs.hh>
36 #include <mln/io/pgm/load.hh>
37 #include <mln/debug/println.hh>
38 #include <mln/draw/line.hh>
39 #include <mln/pw/all.hh>
40 #include <mln/binarization/threshold.hh>
42 #include <mln/value/int_u8.hh>
43 #include <mln/value/label_8.hh>
44 #include <mln/core/alias/point2d.hh>
46 #include <mln/core/site_set/p_faces.hh>
47 #include <mln/core/image/complex_image.hh>
48 #include <mln/core/alias/complex_geometry.hh>
49 #include <mln/core/alias/complex_image.hh>
52 #include <mln/core/image/complex_neighborhoods.hh>
53 #include <mln/core/image/complex_neighborhood_piter.hh>
54 #include <mln/core/image/complex_windows.hh>
56 #include <mln/data/fill.hh>
57 #include <mln/morpho/gradient.hh>
58 #include <mln/labeling/colorize.hh>
68 template <
typename I,
typename N>
70 influence_zones(const I& input, const N& nbh)
72 mln_concrete(I) output =
duplicate(input);
74 p_queue_fast<mln_site(I)> q;
78 mln_piter(I) p(input.domain());
79 mln_niter(N) n(nbh, p);
82 for_all(n) if (input.has(n))
92 mln_niter(N) n(nbh, p);
93 while (! q.is_empty())
96 mln_invariant(output(p) != 0);
97 for_all(n) if (input.has(n))
100 output(n) = output(p);
122 const std::string& filename,
123 const std::string& bgcolor =
"#0000C0",
124 const std::string& fontcolor =
"#0000C0",
125 bool empty_vertex_label =
true)
128 typedef complex_image<1, discrete_plane_1complex_geometry, V> I;
129 const unsigned D = 1;
132 std::ofstream g(filename.c_str());
133 g <<
"graph wst" << std::endl
135 <<
" graph [bgcolor = \"" << bgcolor <<
"\"]" << std::endl
136 <<
" edge [color = \"#FFFFFF\"]" << std::endl
137 <<
" node [color = \"#FFFFFF\", height=\"5\", width=\"5\","
138 <<
" fontsize=\"100\", fontcolor = \"" << fontcolor <<
"\"]"
142 p_n_faces_fwd_piter<D, G> v(ima.domain(), 0);
143 typedef complex_higher_neighborhood<D, G> e_nbh_t;
147 V vertex_color = ima(v);
148 std::ostringstream vertex_color_str;
150 vertex_color_str <<
'#'
153 << std::setw(2) << vertex_color
154 << std::setw(2) << vertex_color
155 << std::setw(2) << vertex_color
158 g <<
" v" << v.unproxy_().face_id()
160 << std::fixed << std::setprecision(1)
161 << (float)v.to_site().front()[1] <<
", "
162 << -(float)v.to_site().front()[0]
163 <<
"\", color = \"" << vertex_color_str.str()
164 <<
"\", fillcolor = \"" << vertex_color_str.str()
165 <<
"\", pin = \"true\", style=\"filled,setlinewidth(3)\"";
166 if (empty_vertex_label)
167 g <<
", label = \"\"";
173 p_n_faces_fwd_piter<D, G> e(ima.domain(), 1);
174 typedef complex_lower_neighborhood<D, G> v_nbh_t;
176 mln_niter_(v_nbh_t) adj_v(v_nbh, e);
179 V edge_color = ima(e);
180 std::ostringstream edge_color_str;
181 edge_color_str <<
'#'
184 << std::setw(2) << edge_color
185 << std::setw(2) << edge_color
186 << std::setw(2) << edge_color
191 topo::face<1> v1 = adj_v.unproxy_().face();
192 point2d p1 = adj_v.to_site().front();
194 topo::face<1> v2 = adj_v.unproxy_().face();
195 point2d p2 = adj_v.to_site().front();
197 mln_invariant(!adj_v.is_valid());
199 g <<
" v" << v1.face_id() <<
" -- v" << v2.face_id() <<
" ";
200 g <<
"[color = \"" << edge_color_str.str()
201 <<
"\", style=\"setlinewidth(10)\"];" << std::endl;
204 g <<
"}" << std::endl;
212 const std::string& filename,
213 const std::string& bgcolor =
"#0000C0",
214 const std::string& fontcolor =
"#0000C0",
215 bool empty_vertex_label =
true)
218 typedef complex_image<1, discrete_plane_1complex_geometry, V> I;
219 const unsigned D = 1;
222 std::ofstream g(filename.c_str());
223 g <<
"graph wst" << std::endl
225 <<
" graph [bgcolor = \"" << bgcolor <<
"\"]" << std::endl
226 <<
" edge [color = \"#FFFFFF\"]" << std::endl
227 <<
" node [color = \"#FFFFFF\", height=\"5\", width=\"5\","
228 <<
" fontsize=\"100\", fontcolor = \"" << fontcolor <<
"\"]"
232 p_n_faces_fwd_piter<D, G> v(ima.domain(), 0);
233 typedef complex_higher_neighborhood<D, G> e_nbh_t;
237 V vertex_color = ima(v);
238 std::ostringstream vertex_color_str;
240 vertex_color_str <<
'#'
243 << std::setw(2) << vertex_color.red()
244 << std::setw(2) << vertex_color.green()
245 << std::setw(2) << vertex_color.blue()
248 g <<
" v" << v.unproxy_().face_id()
250 << std::fixed << std::setprecision(1)
251 << (float)v.to_site().front()[1] <<
", "
252 << -(float)v.to_site().front()[0]
253 <<
"\", color = \"" << vertex_color_str.str()
254 <<
"\", fillcolor = \"" << vertex_color_str.str()
255 <<
"\", pin = \"true\", style=\"filled,setlinewidth(3)\"";
256 if (empty_vertex_label)
257 g <<
", label = \"\"";
263 p_n_faces_fwd_piter<D, G> e(ima.domain(), 1);
264 typedef complex_lower_neighborhood<D, G> v_nbh_t;
266 mln_niter_(v_nbh_t) adj_v(v_nbh, e);
269 V edge_color = ima(e);
270 std::ostringstream edge_color_str;
271 edge_color_str <<
'#'
274 << std::setw(2) << edge_color.red()
275 << std::setw(2) << edge_color.green()
276 << std::setw(2) << edge_color.blue()
281 topo::face<1> v1 = adj_v.unproxy_().face();
282 point2d p1 = adj_v.to_site().front();
284 topo::face<1> v2 = adj_v.unproxy_().face();
285 point2d p2 = adj_v.to_site().front();
287 mln_invariant(!adj_v.is_valid());
289 g <<
" v" << v1.face_id() <<
" -- v" << v2.face_id() <<
" ";
290 g <<
"[color = \"" << edge_color_str.str()
291 <<
"\", style=\"setlinewidth(10)\"];" << std::endl;
294 g <<
"}" << std::endl;
316 border::thickness = 0;
322 std::cout <<
"n seeds = " << nlabels << std::endl;
337 std::vector< std::vector<bool> > adj(nlabels + 1);
338 for (
unsigned l = 1; l <= nlabels; ++l)
339 adj[l].
resize(nlabels + 1,
false);
345 point2d r = p + right, b = p + down;
346 if (iz.has(r) && iz(p) != iz(r))
349 adj[iz(p)][iz(r)] =
true;
351 adj[iz(r)][iz(p)] =
true;
353 if (iz.has(b) && iz(p) != iz(b))
356 adj[iz(p)][iz(b)] =
true;
358 adj[iz(b)][iz(p)] =
true;
366 const unsigned D = 1;
381 std::vector<vertex> v;
387 geom.add_location(p);
388 v.push_back(c.add_face());
392 std::cout <<
"v size = " << v.size() << std::endl;
397 for (
unsigned l = 1; l <= nlabels; ++l)
398 for (
unsigned ll = l + 1; ll <= nlabels; ++ll)
400 e.push_back( c.add_face(-v[l-1] + v[ll-1]) );
403 std::cout <<
"e size = " << e.size() << std::endl;
428 output(v) = input(v.to_site().front());
440 template <
unsigned D, typename G, typename V>
441 mln::complex_higher_dim_connected_n_face_window_p<D, G>
444 return mln::complex_higher_dim_connected_n_face_window_p<D, G>();
448 template <
unsigned D,
typename G,
typename V>
449 mln::complex_higher_dim_connected_n_face_neighborhood<D, G>
452 return mln::complex_higher_dim_connected_n_face_neighborhood<D, G>();
456 int main(
int argc,
char* argv[])
460 std::cerr <<
"usage: " << argv[0] <<
" seeds.pgm lambda output.neato"
464 std::string input_filename = argv[1];
465 unsigned lambda = atoi(argv[2]);
466 std::string output_filename = argv[3];
473 typedef int_u8_graph_image2d input;
475 typedef mln_ch_value_(input, label) output;
479 image2d<int_u8> seeds = io::pgm::load<int_u8>(input_filename);
481 typedef int_u8_graph_image2d ima_t;
482 ima_t ima = make_complex_image(seeds);
483 io::neato::save(ima, "apps/graph.neato");
486 input g = morpho::gradient(ima, make_elt_win(ima));
490 io::neato::save(g,
"apps/graph-g.neato");
494 output s = chain(g, make_elt_nbh(g), lambda, nbasins);