27 #ifndef MLN_BORDER_DUPLICATE_HH
28 # define MLN_BORDER_DUPLICATE_HH
34 # include <mln/core/concept/image.hh>
35 # include <mln/core/routine/primary.hh>
36 # include <mln/core/box_runstart_piter.hh>
37 # include <mln/border/get.hh>
38 # include <mln/opt/element.hh>
60 # ifndef MLN_INCLUDE_ONLY
67 void duplicate_1D(I& ima)
69 trace::entering(
"border::impl::duplicate_1D");
71 typedef mln_psite(I) P;
72 mln_box_runstart_piter(I) pl(ima.domain());
73 unsigned len_c = ima.bbox().len(P::dim - 1);
74 unsigned border = ima.border();
76 for (
unsigned i = 0; i < border; ++i)
77 opt::element(ima, i) = opt::element(ima, border);
79 unsigned st = border + len_c - 1;
80 for (
unsigned i = st + 1; i < opt::nelements(ima); ++i)
81 opt::element(ima, i) = opt::element(ima, st);
83 trace::exiting("border::impl::duplicate_1D");
88 void duplicate_2D(I& ima)
90 trace::entering(
"border::impl::duplicate_2D");
92 typedef mln_psite(I) P;
93 mln_box_runstart_piter(I) pl(ima.domain());
94 unsigned border = ima.border();
95 unsigned border_2x = 2 * ima.border();
96 unsigned len_c = ima.bbox().len(1);
97 unsigned len_r = ima.bbox().len(0);
98 unsigned real_len_c = len_c + border_2x;
104 st = ima.index_of_point (pl);
105 for (
unsigned i = 1; i <= border; ++i)
106 opt::element(ima, st - i) = opt::element(ima, st);
108 for (
unsigned i = 1; i <= border; ++i)
109 opt::element(ima, st + i) = opt::element(ima, st);
113 st = real_len_c * border;
114 for (
unsigned k = 0; k < border; ++k)
115 for (
unsigned i = 0; i < real_len_c; ++i)
116 opt::element(ima, k * real_len_c + i) = opt::element(ima, st + i);
119 st = real_len_c * (border + len_r - 1);
120 for (
unsigned k = 1; k <= border; ++k)
121 for (
unsigned i = st; i < st + real_len_c; ++i)
122 opt::element(ima, k * real_len_c + i) = opt::element(ima, i);
124 trace::exiting(
"border::impl::duplicate_2D");
127 template <
typename I>
129 void duplicate_3D(I& ima)
131 trace::entering(
"border::impl::duplicate_3D");
133 mln_precondition(ima.is_valid());
135 typedef mln_psite(I) P;
136 mln_box_runstart_piter(I) pl(ima.domain());
137 unsigned border = ima.border();
138 unsigned border_2x = 2 * ima.border();
139 unsigned len_c = ima.bbox().len(P::dim - 1);
140 unsigned len_r = ima.bbox().len(1);
141 unsigned len_s = ima.bbox().len(0);
142 unsigned real_len_c = len_c + border_2x;
143 unsigned real_len_r = len_r + border_2x;
144 unsigned face = real_len_c * real_len_r;
149 for (
unsigned k = 0; k < len_s; ++k)
153 for (
unsigned j = 0; j < len_r; ++j)
155 st = ima.index_of_point (pl);
156 for (
unsigned i = 1; i <= border; ++i)
157 opt::element(ima, st - i) = opt::element(ima, st);
159 for (
unsigned i = 1; i <= border; ++i)
160 opt::element(ima, st + i) = opt::element(ima, st);
165 st = border * face + k * face + border * real_len_c ;
166 for (
unsigned j = 1; j <= border; ++j)
167 for (
unsigned i = 0; i < real_len_c; ++i)
168 opt::element(ima, st - j * real_len_c + i) =
169 opt::element(ima, st + i);
172 st = border * face + k * face + (len_r + border - 1) * real_len_c ;
173 for (
unsigned j = 1; j <= border; ++j)
174 for (
unsigned i = 0; i < real_len_c; ++i)
175 opt::element(ima, st + j * real_len_c + i) =
176 opt::element(ima, st + i);
181 for (
unsigned k = 0; k < border; ++k)
182 for (
unsigned i = 0; i < face; ++i)
183 opt::element(ima, k * face + i) = opt::element(ima, st + i);
186 st = (len_s + border - 1) * face;
187 for (
unsigned k = 1; k <= border; ++k)
188 for (
unsigned i = 0; i < face; ++i)
189 opt::element(ima, st + k * face + i) = opt::element(ima, st + i);
191 trace::exiting(
"border::impl::duplicate_3D");
200 template <
typename I>
201 void duplicate_dispatch_on(metal::int_<1>, I& ima)
203 impl::duplicate_1D(ima);
206 template <
typename I>
207 void duplicate_dispatch_on(metal::int_<2>, I& ima)
209 impl::duplicate_2D(ima);
212 template <
typename I>
213 void duplicate_dispatch_on(metal::int_<3>, I& ima)
215 impl::duplicate_3D(ima);
218 template <
typename I>
219 void duplicate_dispatch_on(trait::image::speed::fastest,
222 typedef mln_site(I) P;
223 duplicate_dispatch_on(metal::int_<P::dim>(),
224 const_cast<I&>(exact(ima)));
227 template <typename I>
228 void duplicate_dispatch_on(trait::image::speed::any,
235 template <
typename I>
236 void duplicate_dispatch_on(
const Image<I>& ima)
238 duplicate_dispatch_on(mln_trait_image_speed(I)(),
242 template <
typename I>
243 void duplicate_dispatch(
const Image<I>& ima)
245 duplicate_dispatch_on(
primary(ima));
253 template <
typename I>
256 trace::entering(
"border::duplicate");
257 mln_precondition(exact(ima).is_valid());
260 internal::duplicate_dispatch(ima);
262 trace::exiting(
"border::duplicate");
266 # endif // ! MLN_INCLUDE_ONLY
273 #endif // ! MLN_BORDER_DUPLICATE_HH