]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | /* |
2 | Copyright 2008 Intel Corporation | |
3 | ||
4 | Use, modification and distribution are subject to the Boost Software License, | |
5 | Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at | |
6 | http://www.boost.org/LICENSE_1_0.txt). | |
7 | */ | |
8 | #ifndef BOOST_POLYGON_POLYGON_90_SET_CONCEPT_HPP | |
9 | #define BOOST_POLYGON_POLYGON_90_SET_CONCEPT_HPP | |
10 | #include "polygon_90_set_data.hpp" | |
11 | #include "polygon_90_set_traits.hpp" | |
12 | namespace boost { namespace polygon{ | |
13 | ||
14 | template <typename polygon_set_type> | |
15 | typename enable_if< typename is_polygon_90_set_type<polygon_set_type>::type, | |
16 | typename polygon_90_set_traits<polygon_set_type>::iterator_type>::type | |
17 | begin_90_set_data(const polygon_set_type& polygon_set) { | |
18 | return polygon_90_set_traits<polygon_set_type>::begin(polygon_set); | |
19 | } | |
20 | ||
21 | template <typename polygon_set_type> | |
22 | typename enable_if< typename is_polygon_90_set_type<polygon_set_type>::type, | |
23 | typename polygon_90_set_traits<polygon_set_type>::iterator_type>::type | |
24 | end_90_set_data(const polygon_set_type& polygon_set) { | |
25 | return polygon_90_set_traits<polygon_set_type>::end(polygon_set); | |
26 | } | |
27 | ||
28 | template <typename polygon_set_type> | |
29 | typename enable_if< typename is_polygon_90_set_type<polygon_set_type>::type, | |
30 | orientation_2d>::type | |
31 | scanline_orientation(const polygon_set_type& polygon_set) { | |
32 | return polygon_90_set_traits<polygon_set_type>::orient(polygon_set); | |
33 | } | |
34 | ||
35 | template <typename polygon_set_type> | |
36 | typename enable_if< typename is_polygon_90_set_type<polygon_set_type>::type, | |
37 | bool>::type | |
38 | clean(const polygon_set_type& polygon_set) { | |
39 | return polygon_90_set_traits<polygon_set_type>::clean(polygon_set); | |
40 | } | |
41 | ||
42 | //assign | |
43 | template <typename polygon_set_type_1, typename polygon_set_type_2> | |
44 | typename enable_if < | |
45 | typename gtl_and< | |
46 | typename is_mutable_polygon_90_set_type<polygon_set_type_1>::type, | |
47 | typename is_polygon_90_set_type<polygon_set_type_2>::type>::type, | |
48 | polygon_set_type_1>::type & | |
49 | assign(polygon_set_type_1& lvalue, const polygon_set_type_2& rvalue) { | |
50 | polygon_90_set_mutable_traits<polygon_set_type_1>::set(lvalue, begin_90_set_data(rvalue), end_90_set_data(rvalue), | |
51 | scanline_orientation(rvalue)); | |
52 | return lvalue; | |
53 | } | |
54 | ||
55 | template <typename T1, typename T2> | |
56 | struct are_not_both_rectangle_concept { typedef gtl_yes type; }; | |
57 | template <> | |
58 | struct are_not_both_rectangle_concept<rectangle_concept, rectangle_concept> { typedef gtl_no type; }; | |
59 | ||
60 | //equivalence | |
61 | template <typename polygon_set_type_1, typename polygon_set_type_2> | |
62 | typename enable_if< typename gtl_and_3< | |
63 | typename is_polygon_90_set_type<polygon_set_type_1>::type, | |
64 | typename is_polygon_90_set_type<polygon_set_type_2>::type, | |
65 | typename are_not_both_rectangle_concept<typename geometry_concept<polygon_set_type_1>::type, | |
66 | typename geometry_concept<polygon_set_type_2>::type>::type>::type, | |
67 | bool>::type | |
68 | equivalence(const polygon_set_type_1& lvalue, | |
69 | const polygon_set_type_2& rvalue) { | |
70 | polygon_90_set_data<typename polygon_90_set_traits<polygon_set_type_1>::coordinate_type> ps1; | |
71 | assign(ps1, lvalue); | |
72 | polygon_90_set_data<typename polygon_90_set_traits<polygon_set_type_2>::coordinate_type> ps2; | |
73 | assign(ps2, rvalue); | |
74 | return ps1 == ps2; | |
75 | } | |
76 | ||
77 | ||
78 | //get rectangle tiles (slicing orientation is vertical) | |
79 | template <typename output_container_type, typename polygon_set_type> | |
80 | typename enable_if< typename gtl_if<typename is_polygon_90_set_type<polygon_set_type>::type>::type, | |
81 | void>::type | |
82 | get_rectangles(output_container_type& output, const polygon_set_type& polygon_set) { | |
83 | clean(polygon_set); | |
84 | polygon_90_set_data<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> ps(VERTICAL); | |
85 | assign(ps, polygon_set); | |
86 | ps.get_rectangles(output); | |
87 | } | |
88 | ||
89 | //get rectangle tiles | |
90 | template <typename output_container_type, typename polygon_set_type> | |
91 | typename enable_if< typename gtl_if<typename is_polygon_90_set_type<polygon_set_type>::type>::type, | |
92 | void>::type | |
93 | get_rectangles(output_container_type& output, const polygon_set_type& polygon_set, orientation_2d slicing_orientation) { | |
94 | clean(polygon_set); | |
95 | polygon_90_set_data<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> ps; | |
96 | assign(ps, polygon_set); | |
97 | ps.get_rectangles(output, slicing_orientation); | |
98 | } | |
99 | ||
100 | //get: min_rectangles max_rectangles | |
101 | template <typename output_container_type, typename polygon_set_type> | |
102 | typename enable_if <typename gtl_and< | |
103 | typename is_polygon_90_set_type<polygon_set_type>::type, | |
104 | typename gtl_same_type<rectangle_concept, | |
105 | typename geometry_concept | |
106 | <typename std::iterator_traits | |
107 | <typename output_container_type::iterator>::value_type>::type>::type>::type, | |
108 | void>::type | |
109 | get_max_rectangles(output_container_type& output, const polygon_set_type& polygon_set) { | |
110 | std::vector<rectangle_data<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> > rects; | |
111 | assign(rects, polygon_set); | |
112 | MaxCover<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::getMaxCover(output, rects, scanline_orientation(polygon_set)); | |
113 | } | |
114 | ||
115 | //clear | |
116 | template <typename polygon_set_type> | |
117 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
118 | void>::type | |
119 | clear(polygon_set_type& polygon_set) { | |
120 | polygon_90_set_data<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> ps(scanline_orientation(polygon_set)); | |
121 | assign(polygon_set, ps); | |
122 | } | |
123 | ||
124 | //empty | |
125 | template <typename polygon_set_type> | |
126 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
127 | bool>::type | |
128 | empty(const polygon_set_type& polygon_set) { | |
129 | if(clean(polygon_set)) return begin_90_set_data(polygon_set) == end_90_set_data(polygon_set); | |
130 | polygon_90_set_data<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> ps; | |
131 | assign(ps, polygon_set); | |
132 | ps.clean(); | |
133 | return ps.empty(); | |
134 | } | |
135 | ||
136 | //extents | |
137 | template <typename polygon_set_type, typename rectangle_type> | |
138 | typename enable_if <typename gtl_and< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
139 | typename is_mutable_rectangle_concept<typename geometry_concept<rectangle_type>::type>::type>::type, | |
140 | bool>::type | |
141 | extents(rectangle_type& extents_rectangle, | |
142 | const polygon_set_type& polygon_set) { | |
143 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
144 | polygon_90_set_data<Unit> ps; | |
145 | assign(ps, polygon_set); | |
146 | return ps.extents(extents_rectangle); | |
147 | } | |
148 | ||
149 | //area | |
150 | template <typename polygon_set_type> | |
151 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
152 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::manhattan_area_type>::type | |
153 | area(const polygon_set_type& polygon_set) { | |
154 | typedef rectangle_data<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> rectangle_type; | |
155 | typedef typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::manhattan_area_type area_type; | |
156 | std::vector<rectangle_type> rects; | |
157 | assign(rects, polygon_set); | |
158 | area_type retval = (area_type)0; | |
159 | for(std::size_t i = 0; i < rects.size(); ++i) { | |
160 | retval += (area_type)area(rects[i]); | |
161 | } | |
162 | return retval; | |
163 | } | |
164 | ||
165 | //interact | |
166 | template <typename polygon_set_type_1, typename polygon_set_type_2> | |
167 | typename enable_if <typename gtl_and< typename is_mutable_polygon_90_set_type<polygon_set_type_1>::type, | |
168 | typename is_mutable_polygon_90_set_type<polygon_set_type_2>::type>::type, | |
169 | polygon_set_type_1>::type& | |
170 | interact(polygon_set_type_1& polygon_set_1, const polygon_set_type_2& polygon_set_2) { | |
171 | typedef typename polygon_90_set_traits<polygon_set_type_1>::coordinate_type Unit; | |
172 | polygon_90_set_data<Unit> ps(scanline_orientation(polygon_set_2)); | |
173 | polygon_90_set_data<Unit> ps2(ps); | |
174 | ps.insert(polygon_set_1); | |
175 | ps2.insert(polygon_set_2); | |
176 | ps.interact(ps2); | |
177 | assign(polygon_set_1, ps); | |
178 | return polygon_set_1; | |
179 | } | |
180 | ||
181 | //self_intersect | |
182 | template <typename polygon_set_type> | |
183 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
184 | polygon_set_type>::type & | |
185 | self_intersect(polygon_set_type& polygon_set) { | |
186 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
187 | polygon_90_set_data<Unit> ps; | |
188 | assign(ps, polygon_set); | |
189 | ps.self_intersect(); | |
190 | assign(polygon_set, ps); | |
191 | return polygon_set; | |
192 | } | |
193 | ||
194 | //self_xor | |
195 | template <typename polygon_set_type> | |
196 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
197 | polygon_set_type>::type & | |
198 | self_xor(polygon_set_type& polygon_set) { | |
199 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
200 | polygon_90_set_data<Unit> ps; | |
201 | assign(ps, polygon_set); | |
202 | ps.self_xor(); | |
203 | assign(polygon_set, ps); | |
204 | return polygon_set; | |
205 | } | |
206 | ||
207 | template <typename polygon_set_type> | |
208 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
209 | polygon_set_type>::type & | |
210 | bloat(polygon_set_type& polygon_set, | |
211 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type bloating) { | |
212 | return bloat(polygon_set, bloating, bloating, bloating, bloating); | |
213 | } | |
214 | ||
215 | template <typename polygon_set_type> | |
216 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
217 | polygon_set_type>::type & | |
218 | bloat(polygon_set_type& polygon_set, orientation_2d orient, | |
219 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type bloating) { | |
220 | if(orient == orientation_2d(HORIZONTAL)) | |
221 | return bloat(polygon_set, bloating, bloating, 0, 0); | |
222 | return bloat(polygon_set, 0, 0, bloating, bloating); | |
223 | } | |
224 | ||
225 | template <typename polygon_set_type> | |
226 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
227 | polygon_set_type>::type & | |
228 | bloat(polygon_set_type& polygon_set, orientation_2d orient, | |
229 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type low_bloating, | |
230 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type high_bloating) { | |
231 | if(orient == orientation_2d(HORIZONTAL)) | |
232 | return bloat(polygon_set, low_bloating, high_bloating, 0, 0); | |
233 | return bloat(polygon_set, 0, 0, low_bloating, high_bloating); | |
234 | } | |
235 | ||
236 | template <typename polygon_set_type> | |
237 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
238 | polygon_set_type>::type & | |
239 | bloat(polygon_set_type& polygon_set, direction_2d dir, | |
240 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type bloating) { | |
241 | if(dir == direction_2d(EAST)) | |
242 | return bloat(polygon_set, 0, bloating, 0, 0); | |
243 | if(dir == direction_2d(WEST)) | |
244 | return bloat(polygon_set, bloating, 0, 0, 0); | |
245 | if(dir == direction_2d(SOUTH)) | |
246 | return bloat(polygon_set, 0, 0, bloating, 0); | |
247 | return bloat(polygon_set, 0, 0, 0, bloating); | |
248 | } | |
249 | ||
250 | template <typename polygon_set_type> | |
251 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
252 | polygon_set_type>::type & | |
253 | bloat(polygon_set_type& polygon_set, | |
254 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type west_bloating, | |
255 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type east_bloating, | |
256 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type south_bloating, | |
257 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type north_bloating) { | |
258 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
259 | polygon_90_set_data<Unit> ps; | |
260 | assign(ps, polygon_set); | |
261 | ps.bloat(west_bloating, east_bloating, south_bloating, north_bloating); | |
262 | ps.clean(); | |
263 | assign(polygon_set, ps); | |
264 | return polygon_set; | |
265 | } | |
266 | ||
267 | template <typename polygon_set_type> | |
268 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
269 | polygon_set_type>::type & | |
270 | shrink(polygon_set_type& polygon_set, | |
271 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type shrinking) { | |
272 | return shrink(polygon_set, shrinking, shrinking, shrinking, shrinking); | |
273 | } | |
274 | ||
275 | template <typename polygon_set_type> | |
276 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
277 | polygon_set_type>::type & | |
278 | shrink(polygon_set_type& polygon_set, orientation_2d orient, | |
279 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type shrinking) { | |
280 | if(orient == orientation_2d(HORIZONTAL)) | |
281 | return shrink(polygon_set, shrinking, shrinking, 0, 0); | |
282 | return shrink(polygon_set, 0, 0, shrinking, shrinking); | |
283 | } | |
284 | ||
285 | template <typename polygon_set_type> | |
286 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
287 | polygon_set_type>::type & | |
288 | shrink(polygon_set_type& polygon_set, orientation_2d orient, | |
289 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type low_shrinking, | |
290 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type high_shrinking) { | |
291 | if(orient == orientation_2d(HORIZONTAL)) | |
292 | return shrink(polygon_set, low_shrinking, high_shrinking, 0, 0); | |
293 | return shrink(polygon_set, 0, 0, low_shrinking, high_shrinking); | |
294 | } | |
295 | ||
296 | template <typename polygon_set_type> | |
297 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
298 | polygon_set_type>::type & | |
299 | shrink(polygon_set_type& polygon_set, direction_2d dir, | |
300 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type shrinking) { | |
301 | if(dir == direction_2d(EAST)) | |
302 | return shrink(polygon_set, 0, shrinking, 0, 0); | |
303 | if(dir == direction_2d(WEST)) | |
304 | return shrink(polygon_set, shrinking, 0, 0, 0); | |
305 | if(dir == direction_2d(SOUTH)) | |
306 | return shrink(polygon_set, 0, 0, shrinking, 0); | |
307 | return shrink(polygon_set, 0, 0, 0, shrinking); | |
308 | } | |
309 | ||
310 | template <typename polygon_set_type> | |
311 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
312 | polygon_set_type>::type & | |
313 | shrink(polygon_set_type& polygon_set, | |
314 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type west_shrinking, | |
315 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type east_shrinking, | |
316 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type south_shrinking, | |
317 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type north_shrinking) { | |
318 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
319 | polygon_90_set_data<Unit> ps; | |
320 | assign(ps, polygon_set); | |
321 | ps.shrink(west_shrinking, east_shrinking, south_shrinking, north_shrinking); | |
322 | ps.clean(); | |
323 | assign(polygon_set, ps); | |
324 | return polygon_set; | |
325 | } | |
326 | ||
327 | template <typename polygon_set_type, typename coord_type> | |
328 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
329 | polygon_set_type>::type & | |
330 | resize(polygon_set_type& polygon_set, coord_type resizing) { | |
331 | if(resizing > 0) { | |
332 | return bloat(polygon_set, resizing); | |
333 | } | |
334 | if(resizing < 0) { | |
335 | return shrink(polygon_set, -resizing); | |
336 | } | |
337 | return polygon_set; | |
338 | } | |
339 | ||
340 | //positive or negative values allow for any and all directions of sizing | |
341 | template <typename polygon_set_type, typename coord_type> | |
342 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
343 | polygon_set_type>::type & | |
344 | resize(polygon_set_type& polygon_set, coord_type west, coord_type east, coord_type south, coord_type north) { | |
345 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
346 | polygon_90_set_data<Unit> ps; | |
347 | assign(ps, polygon_set); | |
348 | ps.resize(west, east, south, north); | |
349 | assign(polygon_set, ps); | |
350 | return polygon_set; | |
351 | } | |
352 | ||
353 | template <typename polygon_set_type> | |
354 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
355 | polygon_set_type>::type & | |
356 | grow_and(polygon_set_type& polygon_set, | |
357 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type bloating) { | |
358 | return grow_and(polygon_set, bloating, bloating, bloating, bloating); | |
359 | } | |
360 | ||
361 | template <typename polygon_set_type> | |
362 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
363 | polygon_set_type>::type & | |
364 | grow_and(polygon_set_type& polygon_set, orientation_2d orient, | |
365 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type bloating) { | |
366 | if(orient == orientation_2d(HORIZONTAL)) | |
367 | return grow_and(polygon_set, bloating, bloating, 0, 0); | |
368 | return grow_and(polygon_set, 0, 0, bloating, bloating); | |
369 | } | |
370 | ||
371 | template <typename polygon_set_type> | |
372 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
373 | polygon_set_type>::type & | |
374 | grow_and(polygon_set_type& polygon_set, orientation_2d orient, | |
375 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type low_bloating, | |
376 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type high_bloating) { | |
377 | if(orient == orientation_2d(HORIZONTAL)) | |
378 | return grow_and(polygon_set, low_bloating, high_bloating, 0, 0); | |
379 | return grow_and(polygon_set, 0, 0, low_bloating, high_bloating); | |
380 | } | |
381 | ||
382 | template <typename polygon_set_type> | |
383 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
384 | polygon_set_type>::type & | |
385 | grow_and(polygon_set_type& polygon_set, direction_2d dir, | |
386 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type bloating) { | |
387 | if(dir == direction_2d(EAST)) | |
388 | return grow_and(polygon_set, 0, bloating, 0, 0); | |
389 | if(dir == direction_2d(WEST)) | |
390 | return grow_and(polygon_set, bloating, 0, 0, 0); | |
391 | if(dir == direction_2d(SOUTH)) | |
392 | return grow_and(polygon_set, 0, 0, bloating, 0); | |
393 | return grow_and(polygon_set, 0, 0, 0, bloating); | |
394 | } | |
395 | ||
396 | template <typename polygon_set_type> | |
397 | typename enable_if< typename gtl_if<typename is_mutable_polygon_90_set_type<polygon_set_type>::type>::type, | |
398 | polygon_set_type>::type & | |
399 | grow_and(polygon_set_type& polygon_set, | |
400 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type west_bloating, | |
401 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type east_bloating, | |
402 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type south_bloating, | |
403 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type north_bloating) { | |
404 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
405 | std::vector<polygon_90_data<Unit> > polys; | |
406 | assign(polys, polygon_set); | |
407 | clear(polygon_set); | |
408 | polygon_90_set_data<Unit> ps(scanline_orientation(polygon_set)); | |
409 | for(std::size_t i = 0; i < polys.size(); ++i) { | |
410 | polygon_90_set_data<Unit> tmpPs(scanline_orientation(polygon_set)); | |
411 | tmpPs.insert(polys[i]); | |
412 | bloat(tmpPs, west_bloating, east_bloating, south_bloating, north_bloating); | |
413 | tmpPs.clean(); //apply implicit OR on tmp polygon set | |
414 | ps.insert(tmpPs); | |
415 | } | |
416 | self_intersect(ps); | |
417 | assign(polygon_set, ps); | |
418 | return polygon_set; | |
419 | } | |
420 | ||
421 | template <typename polygon_set_type> | |
422 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
423 | polygon_set_type>::type & | |
424 | scale_up(polygon_set_type& polygon_set, | |
425 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> | |
426 | ::unsigned_area_type factor) { | |
427 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
428 | polygon_90_set_data<Unit> ps; | |
429 | assign(ps, polygon_set); | |
430 | ps.scale_up(factor); | |
431 | assign(polygon_set, ps); | |
432 | return polygon_set; | |
433 | } | |
434 | ||
435 | template <typename polygon_set_type> | |
436 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
437 | polygon_set_type>::type & | |
438 | scale_down(polygon_set_type& polygon_set, | |
439 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type> | |
440 | ::unsigned_area_type factor) { | |
441 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
442 | polygon_90_set_data<Unit> ps; | |
443 | assign(ps, polygon_set); | |
444 | ps.scale_down(factor); | |
445 | assign(polygon_set, ps); | |
446 | return polygon_set; | |
447 | } | |
448 | ||
449 | template <typename polygon_set_type, typename scaling_type> | |
450 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
451 | polygon_set_type>::type & | |
452 | scale(polygon_set_type& polygon_set, | |
453 | const scaling_type& scaling) { | |
454 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
455 | polygon_90_set_data<Unit> ps; | |
456 | assign(ps, polygon_set); | |
457 | ps.scale(scaling); | |
458 | assign(polygon_set, ps); | |
459 | return polygon_set; | |
460 | } | |
461 | ||
462 | struct y_p_s_move : gtl_yes {}; | |
463 | ||
464 | //move | |
465 | template <typename polygon_set_type> | |
466 | typename enable_if< typename gtl_and<y_p_s_move, typename gtl_if<typename is_mutable_polygon_90_set_type<polygon_set_type>::type>::type>::type, | |
467 | polygon_set_type>::type & | |
468 | move(polygon_set_type& polygon_set, | |
469 | orientation_2d orient, typename polygon_90_set_traits<polygon_set_type>::coordinate_type displacement) { | |
470 | if(orient == HORIZONTAL) | |
471 | return move(polygon_set, displacement, 0); | |
472 | else | |
473 | return move(polygon_set, 0, displacement); | |
474 | } | |
475 | ||
476 | struct y_p_s_move2 : gtl_yes {}; | |
477 | ||
478 | template <typename polygon_set_type> | |
479 | typename enable_if< typename gtl_and<y_p_s_move2, typename gtl_if<typename is_mutable_polygon_90_set_type<polygon_set_type>::type>::type>::type, | |
480 | polygon_set_type>::type & | |
481 | move(polygon_set_type& polygon_set, typename polygon_90_set_traits<polygon_set_type>::coordinate_type x_displacement, | |
482 | typename polygon_90_set_traits<polygon_set_type>::coordinate_type y_displacement) { | |
483 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
484 | polygon_90_set_data<Unit> ps; | |
485 | assign(ps, polygon_set); | |
486 | ps.move(x_displacement, y_displacement); | |
487 | ps.clean(); | |
488 | assign(polygon_set, ps); | |
489 | return polygon_set; | |
490 | } | |
491 | ||
492 | //transform | |
493 | template <typename polygon_set_type, typename transformation_type> | |
494 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
495 | polygon_set_type>::type & | |
496 | transform(polygon_set_type& polygon_set, | |
497 | const transformation_type& transformation) { | |
498 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
499 | polygon_90_set_data<Unit> ps; | |
500 | assign(ps, polygon_set); | |
501 | ps.transform(transformation); | |
502 | ps.clean(); | |
503 | assign(polygon_set, ps); | |
504 | return polygon_set; | |
505 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
506 | } | |
507 | ||
508 | //keep | |
509 | template <typename polygon_set_type> | |
510 | typename enable_if< typename is_mutable_polygon_90_set_type<polygon_set_type>::type, | |
511 | polygon_set_type>::type & | |
512 | keep(polygon_set_type& polygon_set, | |
513 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type min_area, | |
514 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type max_area, | |
515 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type min_width, | |
516 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type max_width, | |
517 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type min_height, | |
518 | typename coordinate_traits<typename polygon_90_set_traits<polygon_set_type>::coordinate_type>::unsigned_area_type max_height) { | |
519 | typedef typename polygon_90_set_traits<polygon_set_type>::coordinate_type Unit; | |
520 | typedef typename coordinate_traits<Unit>::unsigned_area_type uat; | |
521 | std::list<polygon_90_data<Unit> > polys; | |
522 | assign(polys, polygon_set); | |
523 | clear(polygon_set); | |
524 | typename std::list<polygon_90_data<Unit> >::iterator itr_nxt; | |
525 | for(typename std::list<polygon_90_data<Unit> >::iterator itr = polys.begin(); itr != polys.end(); itr = itr_nxt){ | |
526 | itr_nxt = itr; | |
527 | ++itr_nxt; | |
528 | rectangle_data<Unit> bbox; | |
529 | extents(bbox, *itr); | |
530 | uat pwidth = delta(bbox, HORIZONTAL); | |
531 | if(pwidth > min_width && pwidth <= max_width){ | |
532 | uat pheight = delta(bbox, VERTICAL); | |
533 | if(pheight > min_height && pheight <= max_height){ | |
534 | uat parea = area(*itr); | |
535 | if(parea <= max_area && parea >= min_area) { | |
536 | continue; | |
537 | } | |
538 | } | |
539 | } | |
540 | polys.erase(itr); | |
541 | } | |
542 | assign(polygon_set, polys); | |
543 | return polygon_set; | |
544 | } | |
545 | ||
546 | ||
547 | } | |
548 | } | |
549 | #include "detail/polygon_90_set_view.hpp" | |
550 | #endif |