]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | #ifndef BOOST_RANGE_MFC_HPP |
2 | #define BOOST_RANGE_MFC_HPP | |
3 | ||
4 | ||
5 | ||
6 | ||
7 | // Boost.Range MFC Extension | |
8 | // | |
9 | // Copyright Shunsuke Sogame 2005-2006. | |
10 | // Distributed under the Boost Software License, Version 1.0. | |
11 | // (See accompanying file LICENSE_1_0.txt or copy at | |
12 | // http://www.boost.org/LICENSE_1_0.txt) | |
13 | ||
14 | ||
15 | ||
16 | ||
17 | // config | |
18 | // | |
19 | ||
20 | ||
21 | #include <afx.h> // _MFC_VER | |
22 | ||
23 | ||
24 | #if !defined(BOOST_RANGE_MFC_NO_CPAIR) | |
25 | #if (_MFC_VER < 0x0700) // dubious | |
26 | #define BOOST_RANGE_MFC_NO_CPAIR | |
27 | #endif | |
28 | #endif | |
29 | ||
30 | ||
31 | #if !defined(BOOST_RANGE_MFC_HAS_LEGACY_STRING) | |
32 | #if (_MFC_VER < 0x0700) // dubious | |
33 | #define BOOST_RANGE_MFC_HAS_LEGACY_STRING | |
34 | #endif | |
35 | #endif | |
36 | ||
37 | ||
38 | // A const collection of old MFC doesn't return const reference. | |
39 | // | |
40 | #if !defined(BOOST_RANGE_MFC_CONST_COL_RETURNS_NON_REF) | |
41 | #if (_MFC_VER < 0x0700) // dubious | |
42 | #define BOOST_RANGE_MFC_CONST_COL_RETURNS_NON_REF | |
43 | #endif | |
44 | #endif | |
45 | ||
46 | ||
47 | ||
48 | ||
49 | // forward declarations | |
50 | // | |
51 | ||
52 | ||
53 | template< class Type, class ArgType > | |
54 | class CArray; | |
55 | ||
56 | template< class Type, class ArgType > | |
57 | class CList; | |
58 | ||
59 | template< class Key, class ArgKey, class Mapped, class ArgMapped > | |
60 | class CMap; | |
61 | ||
62 | template< class BaseClass, class PtrType > | |
63 | class CTypedPtrArray; | |
64 | ||
65 | template< class BaseClass, class PtrType > | |
66 | class CTypedPtrList; | |
67 | ||
68 | template< class BaseClass, class KeyPtrType, class MappedPtrType > | |
69 | class CTypedPtrMap; | |
70 | ||
71 | ||
72 | ||
73 | ||
74 | // extended customizations | |
75 | // | |
76 | ||
77 | ||
78 | #include <cstddef> // ptrdiff_t | |
79 | #include <utility> // pair | |
80 | #include <boost/assert.hpp> | |
81 | #include <boost/mpl/if.hpp> | |
82 | #include <boost/range/atl.hpp> | |
83 | #include <boost/range/begin.hpp> | |
84 | #include <boost/range/const_iterator.hpp> | |
85 | #include <boost/range/detail/microsoft.hpp> | |
86 | #include <boost/range/end.hpp> | |
87 | #include <boost/iterator/iterator_adaptor.hpp> | |
88 | #include <boost/iterator/iterator_categories.hpp> | |
89 | #include <boost/iterator/iterator_facade.hpp> | |
90 | #include <boost/iterator/transform_iterator.hpp> | |
91 | #include <boost/type_traits/is_const.hpp> | |
92 | #include <boost/type_traits/remove_pointer.hpp> | |
93 | #include <boost/utility/addressof.hpp> | |
94 | #include <afx.h> // legacy CString | |
95 | #include <afxcoll.h> // CXXXArray, CXXXList, CMapXXXToXXX | |
96 | #include <tchar.h> | |
97 | ||
98 | ||
99 | namespace boost { namespace range_detail_microsoft { | |
100 | ||
101 | ||
102 | // mfc_ptr_array_iterator | |
103 | // | |
104 | // 'void **' is not convertible to 'void const **', | |
105 | // so we define... | |
106 | // | |
107 | ||
108 | template< class ArrayT, class PtrType > | |
109 | struct mfc_ptr_array_iterator; | |
110 | ||
111 | template< class ArrayT, class PtrType > | |
112 | struct mfc_ptr_array_iterator_super | |
113 | { | |
114 | typedef iterator_adaptor< | |
115 | mfc_ptr_array_iterator<ArrayT, PtrType>, | |
116 | std::ptrdiff_t, // Base! | |
117 | PtrType, // Value | |
118 | random_access_traversal_tag, | |
119 | use_default, | |
120 | std::ptrdiff_t // Difference | |
121 | > type; | |
122 | }; | |
123 | ||
124 | template< class ArrayT, class PtrType > | |
125 | struct mfc_ptr_array_iterator : | |
126 | mfc_ptr_array_iterator_super<ArrayT, PtrType>::type | |
127 | { | |
128 | private: | |
129 | typedef mfc_ptr_array_iterator self_t; | |
130 | typedef typename mfc_ptr_array_iterator_super<ArrayT, PtrType>::type super_t; | |
131 | typedef typename super_t::reference ref_t; | |
132 | ||
133 | public: | |
134 | explicit mfc_ptr_array_iterator() | |
135 | { } | |
136 | ||
137 | explicit mfc_ptr_array_iterator(ArrayT& arr, INT_PTR index) : | |
138 | super_t(index), m_parr(boost::addressof(arr)) | |
139 | { } | |
140 | ||
141 | template< class, class > friend struct mfc_ptr_array_iterator; | |
142 | template< class ArrayT_, class PtrType_ > | |
143 | mfc_ptr_array_iterator(mfc_ptr_array_iterator<ArrayT_, PtrType_> const& other) : | |
144 | super_t(other.base()), m_parr(other.m_parr) | |
145 | { } | |
146 | ||
147 | private: | |
148 | ArrayT *m_parr; | |
149 | ||
150 | friend class iterator_core_access; | |
151 | ref_t dereference() const | |
152 | { | |
153 | BOOST_ASSERT(0 <= this->base() && this->base() < m_parr->GetSize() && "out of range"); | |
154 | return *( m_parr->GetData() + this->base() ); | |
155 | } | |
156 | ||
157 | bool equal(self_t const& other) const | |
158 | { | |
159 | BOOST_ASSERT(m_parr == other.m_parr && "iterators incompatible"); | |
160 | return this->base() == other.base(); | |
161 | } | |
162 | }; | |
163 | ||
164 | struct mfc_ptr_array_functions | |
165 | { | |
166 | template< class Iterator, class X > | |
167 | Iterator begin(X& x) | |
168 | { | |
169 | return Iterator(x, 0); | |
170 | } | |
171 | ||
172 | template< class Iterator, class X > | |
173 | Iterator end(X& x) | |
174 | { | |
175 | return Iterator(x, x.GetSize()); | |
176 | } | |
177 | }; | |
178 | ||
179 | ||
180 | // arrays | |
181 | // | |
182 | ||
183 | template< > | |
184 | struct customization< ::CByteArray > : | |
185 | array_functions | |
186 | { | |
187 | template< class X > | |
188 | struct meta | |
189 | { | |
190 | typedef BYTE val_t; | |
191 | ||
192 | typedef val_t *mutable_iterator; | |
193 | typedef val_t const *const_iterator; | |
194 | }; | |
195 | }; | |
196 | ||
197 | ||
198 | template< > | |
199 | struct customization< ::CDWordArray > : | |
200 | array_functions | |
201 | { | |
202 | template< class X > | |
203 | struct meta | |
204 | { | |
205 | typedef DWORD val_t; | |
206 | ||
207 | typedef val_t *mutable_iterator; | |
208 | typedef val_t const *const_iterator; | |
209 | }; | |
210 | }; | |
211 | ||
212 | ||
213 | template< > | |
214 | struct customization< ::CObArray > : | |
215 | mfc_ptr_array_functions | |
216 | { | |
217 | template< class X > | |
218 | struct meta | |
219 | { | |
220 | typedef mfc_ptr_array_iterator<X, CObject *> mutable_iterator; | |
221 | typedef mfc_ptr_array_iterator<X const, CObject const *> const_iterator; | |
222 | }; | |
223 | }; | |
224 | ||
225 | ||
226 | template< > | |
227 | struct customization< ::CPtrArray > : | |
228 | mfc_ptr_array_functions | |
229 | { | |
230 | template< class X > | |
231 | struct meta | |
232 | { | |
233 | typedef mfc_ptr_array_iterator<X, void *> mutable_iterator; | |
234 | typedef mfc_ptr_array_iterator<X const, void const *> const_iterator; | |
235 | }; | |
236 | }; | |
237 | ||
238 | ||
239 | template< > | |
240 | struct customization< ::CStringArray > : | |
241 | array_functions | |
242 | { | |
243 | template< class X > | |
244 | struct meta | |
245 | { | |
246 | typedef ::CString val_t; | |
247 | ||
248 | typedef val_t *mutable_iterator; | |
249 | typedef val_t const *const_iterator; | |
250 | }; | |
251 | }; | |
252 | ||
253 | ||
254 | template< > | |
255 | struct customization< ::CUIntArray > : | |
256 | array_functions | |
257 | { | |
258 | template< class X > | |
259 | struct meta | |
260 | { | |
261 | typedef UINT val_t; | |
262 | ||
263 | typedef val_t *mutable_iterator; | |
264 | typedef val_t const *const_iterator; | |
265 | }; | |
266 | }; | |
267 | ||
268 | ||
269 | template< > | |
270 | struct customization< ::CWordArray > : | |
271 | array_functions | |
272 | { | |
273 | template< class X > | |
274 | struct meta | |
275 | { | |
276 | typedef WORD val_t; | |
277 | ||
278 | typedef val_t *mutable_iterator; | |
279 | typedef val_t const *const_iterator; | |
280 | }; | |
281 | }; | |
282 | ||
283 | ||
284 | // lists | |
285 | // | |
286 | ||
287 | template< > | |
288 | struct customization< ::CObList > : | |
289 | list_functions | |
290 | { | |
291 | template< class X > | |
292 | struct meta | |
293 | { | |
294 | typedef list_iterator<X, ::CObject *> mutable_iterator; | |
295 | #if !defined(BOOST_RANGE_MFC_CONST_COL_RETURNS_NON_REF) | |
296 | typedef list_iterator<X const, ::CObject const *> const_iterator; | |
297 | #else | |
298 | typedef list_iterator<X const, ::CObject const * const, ::CObject const * const> const_iterator; | |
299 | #endif | |
300 | }; | |
301 | }; | |
302 | ||
303 | ||
304 | template< > | |
305 | struct customization< ::CPtrList > : | |
306 | list_functions | |
307 | { | |
308 | template< class X > | |
309 | struct meta | |
310 | { | |
311 | typedef list_iterator<X, void *> mutable_iterator; | |
312 | #if !defined(BOOST_RANGE_MFC_CONST_COL_RETURNS_NON_REF) | |
313 | typedef list_iterator<X const, void const *> const_iterator; | |
314 | #else | |
315 | typedef list_iterator<X const, void const * const, void const * const> const_iterator; | |
316 | #endif | |
317 | }; | |
318 | }; | |
319 | ||
320 | ||
321 | template< > | |
322 | struct customization< ::CStringList > : | |
323 | list_functions | |
324 | { | |
325 | template< class X > | |
326 | struct meta | |
327 | { | |
328 | typedef ::CString val_t; | |
329 | ||
330 | typedef list_iterator<X, val_t> mutable_iterator; | |
331 | #if !defined(BOOST_RANGE_MFC_CONST_COL_RETURNS_NON_REF) | |
332 | typedef list_iterator<X const, val_t const> const_iterator; | |
333 | #else | |
334 | typedef list_iterator<X const, val_t const, val_t const> const_iterator; | |
335 | #endif | |
336 | }; | |
337 | }; | |
338 | ||
339 | ||
340 | // mfc_map_iterator | |
341 | // | |
342 | ||
343 | template< class MapT, class KeyT, class MappedT > | |
344 | struct mfc_map_iterator; | |
345 | ||
346 | template< class MapT, class KeyT, class MappedT > | |
347 | struct mfc_map_iterator_super | |
348 | { | |
349 | typedef iterator_facade< | |
350 | mfc_map_iterator<MapT, KeyT, MappedT>, | |
351 | std::pair<KeyT, MappedT>, | |
352 | forward_traversal_tag, | |
353 | std::pair<KeyT, MappedT> const | |
354 | > type; | |
355 | }; | |
356 | ||
357 | template< class MapT, class KeyT, class MappedT > | |
358 | struct mfc_map_iterator : | |
359 | mfc_map_iterator_super<MapT, KeyT, MappedT>::type | |
360 | { | |
361 | private: | |
362 | typedef mfc_map_iterator self_t; | |
363 | typedef typename mfc_map_iterator_super<MapT, KeyT, MappedT>::type super_t; | |
364 | typedef typename super_t::reference ref_t; | |
365 | ||
366 | public: | |
367 | explicit mfc_map_iterator() | |
368 | { } | |
369 | ||
370 | explicit mfc_map_iterator(MapT const& map, POSITION pos) : | |
371 | m_pmap(boost::addressof(map)), m_posNext(pos) | |
372 | { | |
373 | increment(); | |
374 | } | |
375 | ||
376 | explicit mfc_map_iterator(MapT const& map) : | |
377 | m_pmap(&map), m_pos(0) // end iterator | |
378 | { } | |
379 | ||
380 | template< class, class, class > friend struct mfc_map_iterator; | |
381 | template< class MapT_, class KeyT_, class MappedT_> | |
382 | mfc_map_iterator(mfc_map_iterator<MapT_, KeyT_, MappedT_> const& other) : | |
383 | m_pmap(other.m_pmap), | |
384 | m_pos(other.m_pos), m_posNext(other.m_posNext), | |
385 | m_key(other.m_key), m_mapped(other.m_mapped) | |
386 | { } | |
387 | ||
388 | private: | |
389 | MapT const *m_pmap; | |
390 | POSITION m_pos, m_posNext; | |
391 | KeyT m_key; MappedT m_mapped; | |
392 | ||
393 | friend class iterator_core_access; | |
394 | ref_t dereference() const | |
395 | { | |
396 | BOOST_ASSERT(m_pos != 0 && "out of range"); | |
397 | return std::make_pair(m_key, m_mapped); | |
398 | } | |
399 | ||
400 | void increment() | |
401 | { | |
402 | BOOST_ASSERT(m_pos != 0 && "out of range"); | |
403 | ||
404 | if (m_posNext == 0) { | |
405 | m_pos = 0; | |
406 | return; | |
407 | } | |
408 | ||
409 | m_pos = m_posNext; | |
410 | m_pmap->GetNextAssoc(m_posNext, m_key, m_mapped); | |
411 | } | |
412 | ||
413 | bool equal(self_t const& other) const | |
414 | { | |
415 | BOOST_ASSERT(m_pmap == other.m_pmap && "iterators incompatible"); | |
416 | return m_pos == other.m_pos; | |
417 | } | |
418 | }; | |
419 | ||
420 | struct mfc_map_functions | |
421 | { | |
422 | template< class Iterator, class X > | |
423 | Iterator begin(X& x) | |
424 | { | |
425 | return Iterator(x, x.GetStartPosition()); | |
426 | } | |
427 | ||
428 | template< class Iterator, class X > | |
429 | Iterator end(X& x) | |
430 | { | |
431 | return Iterator(x); | |
432 | } | |
433 | }; | |
434 | ||
435 | ||
436 | #if !defined(BOOST_RANGE_MFC_NO_CPAIR) | |
437 | ||
438 | ||
439 | // mfc_cpair_map_iterator | |
440 | // | |
441 | // used by ::CMap and ::CMapStringToString | |
442 | // | |
443 | ||
444 | template< class MapT, class PairT > | |
445 | struct mfc_cpair_map_iterator; | |
446 | ||
447 | template< class MapT, class PairT > | |
448 | struct mfc_pget_map_iterator_super | |
449 | { | |
450 | typedef iterator_facade< | |
451 | mfc_cpair_map_iterator<MapT, PairT>, | |
452 | PairT, | |
453 | forward_traversal_tag | |
454 | > type; | |
455 | }; | |
456 | ||
457 | template< class MapT, class PairT > | |
458 | struct mfc_cpair_map_iterator : | |
459 | mfc_pget_map_iterator_super<MapT, PairT>::type | |
460 | { | |
461 | private: | |
462 | typedef mfc_cpair_map_iterator self_t; | |
463 | typedef typename mfc_pget_map_iterator_super<MapT, PairT>::type super_t; | |
464 | typedef typename super_t::reference ref_t; | |
465 | ||
466 | public: | |
467 | explicit mfc_cpair_map_iterator() | |
468 | { } | |
469 | ||
470 | explicit mfc_cpair_map_iterator(MapT& map, PairT *pp) : | |
471 | m_pmap(boost::addressof(map)), m_pp(pp) | |
472 | { } | |
473 | ||
474 | template< class, class > friend struct mfc_cpair_map_iterator; | |
475 | template< class MapT_, class PairT_> | |
476 | mfc_cpair_map_iterator(mfc_cpair_map_iterator<MapT_, PairT_> const& other) : | |
477 | m_pmap(other.m_pmap), m_pp(other.m_pp) | |
478 | { } | |
479 | ||
480 | private: | |
481 | MapT *m_pmap; | |
482 | PairT *m_pp; | |
483 | ||
484 | friend class iterator_core_access; | |
485 | ref_t dereference() const | |
486 | { | |
487 | BOOST_ASSERT(m_pp != 0 && "out of range"); | |
488 | return *m_pp; | |
489 | } | |
490 | ||
491 | void increment() | |
492 | { | |
493 | BOOST_ASSERT(m_pp != 0 && "out of range"); | |
494 | m_pp = m_pmap->PGetNextAssoc(m_pp); | |
495 | } | |
496 | ||
497 | bool equal(self_t const& other) const | |
498 | { | |
499 | BOOST_ASSERT(m_pmap == other.m_pmap && "iterators incompatible"); | |
500 | return m_pp == other.m_pp; | |
501 | } | |
502 | }; | |
503 | ||
504 | struct mfc_cpair_map_functions | |
505 | { | |
506 | template< class Iterator, class X > | |
507 | Iterator begin(X& x) | |
508 | { | |
509 | // Workaround: | |
510 | // Assertion fails if empty. | |
511 | // MFC document is wrong. | |
512 | #if !defined(NDEBUG) | |
513 | if (x.GetCount() == 0) | |
514 | return Iterator(x, 0); | |
515 | #endif | |
516 | ||
517 | return Iterator(x, x.PGetFirstAssoc()); | |
518 | } | |
519 | ||
520 | template< class Iterator, class X > | |
521 | Iterator end(X& x) | |
522 | { | |
523 | return Iterator(x, 0); | |
524 | } | |
525 | }; | |
526 | ||
527 | ||
528 | #endif // !defined(BOOST_RANGE_MFC_NO_CPAIR) | |
529 | ||
530 | ||
531 | // maps | |
532 | // | |
533 | ||
534 | template< > | |
535 | struct customization< ::CMapPtrToWord > : | |
536 | mfc_map_functions | |
537 | { | |
538 | template< class X > | |
539 | struct meta | |
540 | { | |
541 | typedef void *key_t; | |
542 | typedef WORD mapped_t; | |
543 | ||
544 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
545 | typedef mutable_iterator const_iterator; | |
546 | }; | |
547 | }; | |
548 | ||
549 | ||
550 | template< > | |
551 | struct customization< ::CMapPtrToPtr > : | |
552 | mfc_map_functions | |
553 | { | |
554 | template< class X > | |
555 | struct meta | |
556 | { | |
557 | typedef void *key_t; | |
558 | typedef void *mapped_t; | |
559 | ||
560 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
561 | typedef mutable_iterator const_iterator; | |
562 | }; | |
563 | }; | |
564 | ||
565 | ||
566 | template< > | |
567 | struct customization< ::CMapStringToOb > : | |
568 | mfc_map_functions | |
569 | { | |
570 | template< class X > | |
571 | struct meta | |
572 | { | |
573 | typedef ::CString key_t; | |
574 | typedef ::CObject *mapped_t; | |
575 | ||
576 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
577 | typedef mutable_iterator const_iterator; | |
578 | }; | |
579 | }; | |
580 | ||
581 | ||
582 | template< > | |
583 | struct customization< ::CMapStringToPtr > : | |
584 | mfc_map_functions | |
585 | { | |
586 | template< class X > | |
587 | struct meta | |
588 | { | |
589 | typedef ::CString key_t; | |
590 | typedef void *mapped_t; | |
591 | ||
592 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
593 | typedef mutable_iterator const_iterator; | |
594 | }; | |
595 | }; | |
596 | ||
597 | ||
598 | template< > | |
599 | struct customization< ::CMapStringToString > : | |
600 | #if !defined(BOOST_RANGE_MFC_NO_CPAIR) | |
601 | mfc_cpair_map_functions | |
602 | #else | |
603 | mfc_map_functions | |
604 | #endif | |
605 | { | |
606 | template< class X > | |
607 | struct meta | |
608 | { | |
609 | #if !defined(BOOST_RANGE_MFC_NO_CPAIR) | |
610 | typedef typename X::CPair pair_t; | |
611 | ||
612 | typedef mfc_cpair_map_iterator<X, pair_t> mutable_iterator; | |
613 | typedef mfc_cpair_map_iterator<X const, pair_t const> const_iterator; | |
614 | #else | |
615 | typedef ::CString key_t; | |
616 | typedef ::CString mapped_t; | |
617 | ||
618 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
619 | typedef mutable_iterator const_iterator; | |
620 | #endif | |
621 | }; | |
622 | }; | |
623 | ||
624 | ||
625 | template< > | |
626 | struct customization< ::CMapWordToOb > : | |
627 | mfc_map_functions | |
628 | { | |
629 | template< class X > | |
630 | struct meta | |
631 | { | |
632 | typedef WORD key_t; | |
633 | typedef ::CObject *mapped_t; | |
634 | ||
635 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
636 | typedef mutable_iterator const_iterator; | |
637 | }; | |
638 | }; | |
639 | ||
640 | ||
641 | template< > | |
642 | struct customization< ::CMapWordToPtr > : | |
643 | mfc_map_functions | |
644 | { | |
645 | template< class X > | |
646 | struct meta | |
647 | { | |
648 | typedef WORD key_t; | |
649 | typedef void *mapped_t; | |
650 | ||
651 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
652 | typedef mutable_iterator const_iterator; | |
653 | }; | |
654 | }; | |
655 | ||
656 | ||
657 | // templates | |
658 | // | |
659 | ||
660 | template< class Type, class ArgType > | |
661 | struct customization< ::CArray<Type, ArgType> > : | |
662 | array_functions | |
663 | { | |
664 | template< class X > | |
665 | struct meta | |
666 | { | |
667 | typedef Type val_t; | |
668 | ||
669 | typedef val_t *mutable_iterator; | |
670 | typedef val_t const *const_iterator; | |
671 | }; | |
672 | }; | |
673 | ||
674 | ||
675 | template< class Type, class ArgType > | |
676 | struct customization< ::CList<Type, ArgType> > : | |
677 | list_functions | |
678 | { | |
679 | template< class X > | |
680 | struct meta | |
681 | { | |
682 | typedef Type val_t; | |
683 | ||
684 | typedef list_iterator<X, val_t> mutable_iterator; | |
685 | #if !defined(BOOST_RANGE_MFC_CONST_COL_RETURNS_NON_REF) | |
686 | typedef list_iterator<X const, val_t const> const_iterator; | |
687 | #else | |
688 | typedef list_iterator<X const, val_t const, val_t const> const_iterator; | |
689 | #endif | |
690 | }; | |
691 | }; | |
692 | ||
693 | ||
694 | template< class Key, class ArgKey, class Mapped, class ArgMapped > | |
695 | struct customization< ::CMap<Key, ArgKey, Mapped, ArgMapped> > : | |
696 | #if !defined(BOOST_RANGE_MFC_NO_CPAIR) | |
697 | mfc_cpair_map_functions | |
698 | #else | |
699 | mfc_map_functions | |
700 | #endif | |
701 | { | |
702 | template< class X > | |
703 | struct meta | |
704 | { | |
705 | #if !defined(BOOST_RANGE_MFC_NO_CPAIR) | |
706 | typedef typename X::CPair pair_t; | |
707 | ||
708 | typedef mfc_cpair_map_iterator<X, pair_t> mutable_iterator; | |
709 | typedef mfc_cpair_map_iterator<X const, pair_t const> const_iterator; | |
710 | #else | |
711 | typedef Key key_t; | |
712 | typedef Mapped mapped_t; | |
713 | ||
714 | typedef mfc_map_iterator<X, key_t, mapped_t> mutable_iterator; | |
715 | typedef mutable_iterator const_iterator; | |
716 | #endif | |
717 | }; | |
718 | }; | |
719 | ||
720 | ||
721 | template< class BaseClass, class PtrType > | |
722 | struct customization< ::CTypedPtrArray<BaseClass, PtrType> > | |
723 | { | |
724 | template< class X > | |
725 | struct fun | |
726 | { | |
727 | typedef typename remove_pointer<PtrType>::type val_t; | |
728 | ||
729 | typedef typename mpl::if_< is_const<X>, | |
730 | val_t const, | |
731 | val_t | |
732 | >::type val_t_; | |
733 | ||
734 | typedef val_t_ * const result_type; | |
735 | ||
736 | template< class PtrType_ > | |
737 | result_type operator()(PtrType_ p) const | |
738 | { | |
739 | return static_cast<result_type>(p); | |
740 | } | |
741 | }; | |
742 | ||
743 | template< class X > | |
744 | struct meta | |
745 | { | |
746 | typedef typename compatible_mutable_iterator<BaseClass>::type miter_t; | |
747 | typedef typename range_const_iterator<BaseClass>::type citer_t; | |
748 | ||
749 | typedef transform_iterator<fun<X>, miter_t> mutable_iterator; | |
750 | typedef transform_iterator<fun<X const>, citer_t> const_iterator; | |
751 | }; | |
752 | ||
753 | template< class Iterator, class X > | |
754 | Iterator begin(X& x) | |
755 | { | |
756 | return Iterator(boost::begin<BaseClass>(x), fun<X>()); | |
757 | } | |
758 | ||
759 | template< class Iterator, class X > | |
760 | Iterator end(X& x) | |
761 | { | |
762 | return Iterator(boost::end<BaseClass>(x), fun<X>()); | |
763 | } | |
764 | }; | |
765 | ||
766 | ||
767 | template< class BaseClass, class PtrType > | |
768 | struct customization< ::CTypedPtrList<BaseClass, PtrType> > : | |
769 | list_functions | |
770 | { | |
771 | template< class X > | |
772 | struct meta | |
773 | { | |
774 | typedef typename remove_pointer<PtrType>::type val_t; | |
775 | ||
776 | // not l-value | |
777 | typedef list_iterator<X, val_t * const, val_t * const> mutable_iterator; | |
778 | typedef list_iterator<X const, val_t const * const, val_t const * const> const_iterator; | |
779 | }; | |
780 | }; | |
781 | ||
782 | ||
783 | template< class BaseClass, class KeyPtrType, class MappedPtrType > | |
784 | struct customization< ::CTypedPtrMap<BaseClass, KeyPtrType, MappedPtrType> > : | |
785 | mfc_map_functions | |
786 | { | |
787 | template< class X > | |
788 | struct meta | |
789 | { | |
790 | typedef mfc_map_iterator<X, KeyPtrType, MappedPtrType> mutable_iterator; | |
791 | typedef mutable_iterator const_iterator; | |
792 | }; | |
793 | }; | |
794 | ||
795 | ||
796 | // strings | |
797 | // | |
798 | ||
799 | #if defined(BOOST_RANGE_MFC_HAS_LEGACY_STRING) | |
800 | ||
801 | template< > | |
802 | struct customization< ::CString > | |
803 | { | |
804 | template< class X > | |
805 | struct meta | |
806 | { | |
807 | // LPTSTR/LPCTSTR is not always defined in <tchar.h>. | |
808 | typedef TCHAR *mutable_iterator; | |
809 | typedef TCHAR const *const_iterator; | |
810 | }; | |
811 | ||
812 | template< class Iterator, class X > | |
813 | typename mutable_<Iterator, X>::type begin(X& x) | |
814 | { | |
815 | return x.GetBuffer(0); | |
816 | } | |
817 | ||
818 | template< class Iterator, class X > | |
819 | Iterator begin(X const& x) | |
820 | { | |
821 | return x; | |
822 | } | |
823 | ||
824 | template< class Iterator, class X > | |
825 | Iterator end(X& x) | |
826 | { | |
827 | return begin<Iterator>(x) + x.GetLength(); | |
828 | } | |
829 | }; | |
830 | ||
831 | #endif // defined(BOOST_RANGE_MFC_HAS_LEGACY_STRING) | |
832 | ||
833 | ||
834 | } } // namespace boost::range_detail_microsoft | |
835 | ||
836 | ||
837 | ||
838 | ||
839 | // range customizations | |
840 | // | |
841 | ||
842 | ||
843 | // arrays | |
844 | // | |
845 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
846 | boost::range_detail_microsoft::using_type_as_tag, | |
847 | BOOST_PP_NIL, CByteArray | |
848 | ) | |
849 | ||
850 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
851 | boost::range_detail_microsoft::using_type_as_tag, | |
852 | BOOST_PP_NIL, CDWordArray | |
853 | ) | |
854 | ||
855 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
856 | boost::range_detail_microsoft::using_type_as_tag, | |
857 | BOOST_PP_NIL, CStringArray | |
858 | ) | |
859 | ||
860 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
861 | boost::range_detail_microsoft::using_type_as_tag, | |
862 | BOOST_PP_NIL, CUIntArray | |
863 | ) | |
864 | ||
865 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
866 | boost::range_detail_microsoft::using_type_as_tag, | |
867 | BOOST_PP_NIL, CWordArray | |
868 | ) | |
869 | ||
870 | ||
871 | // lists | |
872 | // | |
873 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
874 | boost::range_detail_microsoft::using_type_as_tag, | |
875 | BOOST_PP_NIL, CObList | |
876 | ) | |
877 | ||
878 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
879 | boost::range_detail_microsoft::using_type_as_tag, | |
880 | BOOST_PP_NIL, CPtrList | |
881 | ) | |
882 | ||
883 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
884 | boost::range_detail_microsoft::using_type_as_tag, | |
885 | BOOST_PP_NIL, CStringList | |
886 | ) | |
887 | ||
888 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
889 | boost::range_detail_microsoft::using_type_as_tag, | |
890 | BOOST_PP_NIL, CObArray | |
891 | ) | |
892 | ||
893 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
894 | boost::range_detail_microsoft::using_type_as_tag, | |
895 | BOOST_PP_NIL, CPtrArray | |
896 | ) | |
897 | ||
898 | ||
899 | // maps | |
900 | // | |
901 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
902 | boost::range_detail_microsoft::using_type_as_tag, | |
903 | BOOST_PP_NIL, CMapPtrToWord | |
904 | ) | |
905 | ||
906 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
907 | boost::range_detail_microsoft::using_type_as_tag, | |
908 | BOOST_PP_NIL, CMapPtrToPtr | |
909 | ) | |
910 | ||
911 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
912 | boost::range_detail_microsoft::using_type_as_tag, | |
913 | BOOST_PP_NIL, CMapStringToOb | |
914 | ) | |
915 | ||
916 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
917 | boost::range_detail_microsoft::using_type_as_tag, | |
918 | BOOST_PP_NIL, CMapStringToPtr | |
919 | ) | |
920 | ||
921 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
922 | boost::range_detail_microsoft::using_type_as_tag, | |
923 | BOOST_PP_NIL, CMapStringToString | |
924 | ) | |
925 | ||
926 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
927 | boost::range_detail_microsoft::using_type_as_tag, | |
928 | BOOST_PP_NIL, CMapWordToOb | |
929 | ) | |
930 | ||
931 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
932 | boost::range_detail_microsoft::using_type_as_tag, | |
933 | BOOST_PP_NIL, CMapWordToPtr | |
934 | ) | |
935 | ||
936 | ||
937 | // templates | |
938 | // | |
939 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( | |
940 | boost::range_detail_microsoft::using_type_as_tag, | |
941 | BOOST_PP_NIL, CArray, 2 | |
942 | ) | |
943 | ||
944 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( | |
945 | boost::range_detail_microsoft::using_type_as_tag, | |
946 | BOOST_PP_NIL, CList, 2 | |
947 | ) | |
948 | ||
949 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( | |
950 | boost::range_detail_microsoft::using_type_as_tag, | |
951 | BOOST_PP_NIL, CMap, 4 | |
952 | ) | |
953 | ||
954 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( | |
955 | boost::range_detail_microsoft::using_type_as_tag, | |
956 | BOOST_PP_NIL, CTypedPtrArray, 2 | |
957 | ) | |
958 | ||
959 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( | |
960 | boost::range_detail_microsoft::using_type_as_tag, | |
961 | BOOST_PP_NIL, CTypedPtrList, 2 | |
962 | ) | |
963 | ||
964 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( | |
965 | boost::range_detail_microsoft::using_type_as_tag, | |
966 | BOOST_PP_NIL, CTypedPtrMap, 3 | |
967 | ) | |
968 | ||
969 | ||
970 | // strings | |
971 | // | |
972 | #if defined(BOOST_RANGE_MFC_HAS_LEGACY_STRING) | |
973 | ||
974 | BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( | |
975 | boost::range_detail_microsoft::using_type_as_tag, | |
976 | BOOST_PP_NIL, CString | |
977 | ) | |
978 | ||
979 | #endif | |
980 | ||
981 | ||
982 | ||
983 | ||
984 | #endif |