Index: /trunk/nv.lua
===================================================================
--- /trunk/nv.lua	(revision 536)
+++ /trunk/nv.lua	(revision 537)
@@ -6,5 +6,5 @@
 	kind "StaticLib"
 	includedirs { "." }
-	files { "nv/common.hh", "nv/base/**.hh", "nv/core/**.hh", "nv/stl/**.hh", "nv/interface/**.hh", "nv/detail/**.inc", "src/core/**.cc", "src/stl/**.cc"  }
+	files { "nv/common.hh", "nv/base/**.hh", "nv/ecs/**.hh", "nv/core/**.hh", "nv/stl/**.hh", "nv/interface/**.hh", "nv/detail/**.inc", "src/core/**.cc", "src/stl/**.cc"  }
 
 project "nv-lib"
Index: /trunk/nv/ecs/component.hh
===================================================================
--- /trunk/nv/ecs/component.hh	(revision 537)
+++ /trunk/nv/ecs/component.hh	(revision 537)
@@ -0,0 +1,133 @@
+// Copyright (C) 2017-2017 ChaosForge Ltd
+// http://chaosforge.org/
+//
+// This file is part of Nova libraries. 
+// For conditions of distribution and use, see copying.txt file in root folder.
+
+/**
+* @file component_storage.hh
+* @author Kornel Kisielewicz epyon@chaosforge.org
+* @brief Data-driven Entity Component System
+*/
+
+#ifndef NV_ECS_COMPONENT_HH
+#define NV_ECS_COMPONENT_HH
+
+#include <nv/common.hh>
+#include <nv/stl/string.hh>
+#include <nv/stl/handle.hh>
+#include <nv/stl/index_table.hh>
+#include <nv/stl/priority_queue.hh>
+#include <nv/stl/range.hh>
+#include <nv/core/types.hh>
+#include <nv/ecs/component_storage.hh>
+
+namespace nv
+{
+
+	namespace ecs
+	{
+
+		template < typename Ecs, typename Component >
+		class component : public Ecs::component_interface
+		{
+		public:
+			typedef Ecs                                      ecs_type;
+			typedef typename ecs_type::message               message_type;
+			typedef typename ecs_type::handle_type           handle_type;
+			typedef typename ecs_type::time_type             time_type;
+			typedef Component                                value_type;
+			typedef Component                                component_type;
+			typedef index_storage< handle_type, value_type > storage_type;
+			typedef typename storage_type::index_type        index_type;
+
+			typedef typename storage_type::iterator          iterator;
+			typedef typename storage_type::const_iterator    const_iterator;
+			typedef typename storage_type::reference         reference;
+			typedef typename storage_type::const_reference   const_reference;
+
+			component( ecs_type& a_ecs, string_view a_name, uint32 reserve = 0 ) 
+				: m_ecs( a_ecs ), m_data( reserve )
+			{
+				m_ecs.register_component<component_type>( a_name, this );
+			}
+
+			inline value_type& insert( handle_type h ) { return m_data.insert( h ); }
+
+			template < typename ...Args >
+			value_type& insert( handle_type h, Args&&... args )
+			{
+				return m_data.insert( h, nv::forward<Args>( args )... );
+			}
+
+			bool exists( handle_type h )
+			{
+				return m_data.exists( h );
+			}
+
+			virtual void update( time_type /*dtime*/ )
+			{
+				// no-op
+			}
+
+			virtual void clear()
+			{
+				for ( uint32 i = 0; i < size(); ++i )
+					destroy( &m_data[i] );
+				m_data.clear();
+			}
+
+			value_type* get( handle_type h ) { return m_data.get(h); }
+			const value_type* get( handle_type h ) const { return m_data.get( h ); }
+
+			void* get_raw( handle_type h ) { return get( h ); }
+			const void* get_raw( handle_type h ) const { return get( h ); }
+
+			virtual void remove( handle_type h )
+			{
+				value_type* v = m_data.get( h );
+				if ( v == nullptr ) return;
+				destroy( v );
+				m_data.remove( h );
+			}
+
+			virtual void destroy( value_type* )
+			{
+				// cleanup
+			}
+
+			virtual bool handle_message( const message_type& )
+			{
+				return true;
+			}
+
+			~component()
+			{
+				clear();
+			}
+
+
+			inline handle_type get_handle( index_type i ) const { return m_data.get_handle( i ); }
+
+			inline const value_type& operator[] ( index_type i ) const { return m_data[i]; }
+			inline value_type& operator[] ( index_type i ) { return m_data[i]; }
+
+			inline size_t size() const { return m_data.size(); }
+
+			inline iterator        begin() { return m_data.begin(); }
+			inline const_iterator  begin()  const { return m_data.begin(); }
+			inline const_iterator  cbegin() const { return m_data.begin(); }
+
+			inline iterator        end() { return m_data.end(); }
+			inline const_iterator  end()  const { return m_data.end(); }
+			inline const_iterator  cend() const { return m_data.end(); }
+		protected:
+			ecs_type&        m_ecs;
+			storage_type     m_data;
+		};
+
+	}
+
+}
+
+#endif // NV_ECS_COMPONENT_HH
Index: /trunk/nv/ecs/component_storage.hh
===================================================================
--- /trunk/nv/ecs/component_storage.hh	(revision 537)
+++ /trunk/nv/ecs/component_storage.hh	(revision 537)
@@ -0,0 +1,306 @@
+// Copyright (C) 2017-2017 ChaosForge Ltd
+// http://chaosforge.org/
+//
+// This file is part of Nova libraries. 
+// For conditions of distribution and use, see copying.txt file in root folder.
+
+/**
+* @file component_storage.hh
+* @author Kornel Kisielewicz epyon@chaosforge.org
+* @brief Data-driven Entity Component System
+*/
+
+#ifndef NV_ECS_COMPONENT_STORAGE_HH
+#define NV_ECS_COMPONENT_STORAGE_HH
+
+#include <nv/common.hh>
+#include <nv/stl/handle.hh>
+#include <nv/stl/index_table.hh>
+#include <nv/stl/handle_manager.hh>
+
+namespace nv
+{
+
+	namespace ecs
+	{
+
+		template < typename Handle, typename Component >
+		class index_storage 
+		{
+		public:
+			typedef Handle                                 handle_type;
+			typedef Component                              value_type;
+			typedef vector< value_type >                   storage_type;
+			typedef index_table< handle_type >             index_table_type;
+			typedef typename index_table_type::index_type  index_type;
+			typedef typename storage_type::iterator        iterator;
+			typedef typename storage_type::const_iterator  const_iterator;
+			typedef typename storage_type::reference       reference;
+			typedef typename storage_type::const_reference const_reference;
+
+			explicit index_storage( uint32 reserve = 0 )
+			{
+				if ( reserve != 0 )
+				{
+					m_data.reserve( reserve );
+				}
+			}
+
+			inline value_type& insert( handle_type h )
+			{
+				insert_index( h );
+				m_data.emplace_back();
+				return m_data.back();
+			}
+
+			template < typename ...Args >
+			inline value_type& insert( handle_type h, Args&&... args )
+			{
+				insert_index( h );
+				m_data.emplace_back( nv::forward<Args>( args )... );
+				return m_data.back();
+			}
+
+			inline bool exists( handle_type h )
+			{
+				if ( h.is_nil() || h.index() >= m_indexes.size() ) return false;
+				return m_indexes[h.index()] >= 0;
+			}
+
+			value_type* get( handle_type h )
+			{
+				if ( h.is_nil() || h.index() >= m_indexes.size() ) return nullptr;
+				index_type i = m_indexes[h.index()];
+				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
+			}
+
+			const value_type* get( handle_type h ) const
+			{
+				if ( h.is_nil() || h.index() >= m_indexes.size() ) return nullptr;
+				index_type i = m_indexes[h.index()];
+				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
+			}
+
+			void clear()
+			{
+				m_handles.clear();
+				m_indexes.clear();
+				m_data.clear();
+			}
+
+			void remove( handle_type h )
+			{
+				if ( h.is_nil() || h.index() >= m_indexes.size() || m_indexes[h.index()] == -1 )
+					return;
+				handle_type swap_handle = m_handles.back();
+				index_type  dead_eindex = m_indexes[h.index()];
+				if ( dead_eindex != static_cast<index_type>( m_handles.size() - 1 ) )
+				{
+					m_handles[unsigned( dead_eindex )] = swap_handle;
+					m_indexes[swap_handle.index()] = dead_eindex;
+					m_data[unsigned( dead_eindex )] = move( m_data.back() );
+				}
+				m_handles.pop_back();
+				m_data.pop_back();
+				m_indexes[h.index()] = -1;
+
+			}
+
+			inline handle_type get_handle( index_type i ) const { return m_handles[unsigned( i )]; }
+
+			inline const value_type& operator[] ( index_type i ) const { return m_data[i]; }
+			inline value_type& operator[] ( index_type i ) { return m_data[i]; }
+
+			inline size_t size() const { return m_data.size(); }
+
+			inline iterator        begin() { return m_data.begin(); }
+			inline const_iterator  begin()  const { return m_data.cbegin(); }
+
+			inline iterator        end() { return m_data.end(); }
+			inline const_iterator  end()  const { return m_data.cend(); }
+
+		protected:
+			void insert_index( handle_type h )
+			{
+				NV_ASSERT( !exists( h ), "Reinserting handle!" );
+				resize_indexes_to( index_type( h.index() ) );
+				index_type lindex = m_handles.size();
+				m_indexes[h.index()] = index_type( lindex );
+				m_handles.push_back( h );
+				NV_ASSERT( lindex == index_type( m_data.size() ), "Fail!" );
+			}
+
+			void resize_indexes_to( index_type i )
+			{
+				index_type size = index_type( m_indexes.size() );
+				if ( i >= size )
+				{
+					if ( size == 0 ) size = 1;
+					while ( i >= size ) size = size * 2;
+					m_indexes.resize( static_cast<uint32>( size ), -1 );
+				}
+			}
+
+			vector< handle_type > m_handles;
+			vector< index_type >  m_indexes;
+			vector< value_type >  m_data;
+		};
+
+		template < typename Handle, typename Component >
+		class index_multi_storage
+		{
+		public:
+			typedef Handle                                 handle_type;
+			typedef Component                              value_type;
+			typedef vector< value_type >                   storage_type;
+			typedef index_table< handle_type >             index_table_type;
+			typedef typename index_table_type::index_type  index_type;
+			typedef typename storage_type::iterator        iterator;
+			typedef typename storage_type::const_iterator  const_iterator;
+			typedef typename storage_type::reference       reference;
+			typedef typename storage_type::const_reference const_reference;
+
+			explicit index_multi_storage( uint32 reserve = 0 )
+			{
+				if ( reserve != 0 )
+				{
+					m_data.reserve( reserve );
+				}
+			}
+
+			inline value_type& insert( handle_type h )
+			{
+				insert_index( h );
+				m_data.emplace_back();
+				return m_data.back();
+			}
+
+			template < typename ...Args >
+			inline value_type& insert( handle_type h, Args&&... args )
+			{
+				insert_index( h );
+				m_data.emplace_back( nv::forward<Args>( args )... );
+				return m_data.back();
+			}
+
+			inline bool exists( handle_type h )
+			{
+				if ( h.is_nil() || h.index() >= m_indexes.size() ) return false;
+				return m_indexes[h.index()] >= 0;
+			}
+
+			value_type* get( handle_type h )
+			{
+				if ( h.is_nil() || h.index() >= m_indexes.size() ) return nullptr;
+				index_type i = m_indexes[h.index()];
+				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
+			}
+
+			const value_type* get( handle_type h ) const
+			{
+				if ( h.is_nil() || h.index() >= m_indexes.size() ) return nullptr;
+				index_type i = m_indexes[h.index()];
+				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
+			}
+
+			void clear()
+			{
+				m_entries.clear();
+				m_indexes.clear();
+				m_data.clear();
+			}
+
+// 			void remove( handle_type h )
+// 			{
+// 				if ( h.is_nil() || h.index() >= m_indexes.size() || m_indexes[h.index()] == -1 )
+// 					return;
+// 
+// 				// this can be done more efficiently
+// 				while ( m_indexes[h.index()] >= 0 )
+// 				{
+// 					remove_component( h.index() );
+// 				}
+// 			}
+
+			inline handle_type get_handle( index_type i ) const { return m_entries[unsigned( i )].handle; }
+
+			inline const value_type& operator[] ( index_type i ) const { return m_data[i]; }
+			inline value_type& operator[] ( index_type i ) { return m_data[i]; }
+
+			inline size_t size() const { return m_data.size(); }
+
+			inline iterator        begin() { return m_data.begin(); }
+			inline const_iterator  begin()  const { return m_data.cbegin(); }
+
+			inline iterator        end() { return m_data.end(); }
+			inline const_iterator  end()  const { return m_data.cend(); }
+
+		protected:
+
+//  			void swap_to_end( handle_type h )
+//  			{
+// 				NV_ASSERT( !h.is_nil() && h.index() < m_indexes.size() && m_indexes[h.index()] != -1, "Bad parameter passed" );
+// 				handle_type swap_handle = m_handles.back();
+// 				index_type  dead_eindex = m_indexes[h.index()];
+// 				if ( dead_eindex != static_cast<index_type>( m_handles.size() - 1 ) )
+// 				{
+// 					m_handles[unsigned( dead_eindex )] = swap_handle;
+// 					m_indexes[swap_handle.index()]     = dead_eindex;
+// 					m_data[unsigned( dead_eindex )]    = move( m_data.back() );
+// 				}
+// 				m_indexes[h.index()] = -1;
+//  			}
+
+			void insert_index( handle_type h )
+			{
+				NV_ASSERT( h, "Bad handle!" );
+				index_type i = index_type( h.index() )
+				resize_indexes_to( i );
+				index_type lindex = m_entries.size();
+				m_entries.push_back( h );
+				index_type next = m_indexes[h.index()];
+				if ( next >= 0 ) // exists
+				{
+					entry_type& e = m_entries[next];
+					e.prev = lindex;
+				}
+				m_indexes[h.index()] = index_type( lindex );
+				m_entries.back().next = next;
+				NV_ASSERT( lindex == index_type( m_data.size() ), "Fail!" );
+			}
+
+			void resize_indexes_to( index_type i )
+			{
+				index_type size = index_type( m_indexes.size() );
+				if ( i >= size )
+				{
+					if ( size == 0 ) size = 1;
+					while ( i >= size ) size = size * 2;
+					m_indexes.resize( static_cast<uint32>( size ), -1 );
+				}
+			}
+
+			struct entry_type
+			{
+				handle_type handle;
+				index_type  next;
+				index_type  prev;
+
+				entry_type() : handle(), next( -1 ), prev( -1 ) {}
+				entry_type( handle_type h ) : handle( h ), next( -1 ), prev( -1 ) {}
+			};
+
+			vector< entry_type > m_entries;
+			vector< index_type > m_indexes;
+			vector< value_type > m_data;
+		};
+
+		class direct_storage;
+		class hash_storage;
+		class hash_multi_storage;
+
+	}
+
+}
+
+#endif // NV_ECS_COMPONENT_STORAGE_HH
Index: /trunk/nv/ecs/ecs.hh
===================================================================
--- /trunk/nv/ecs/ecs.hh	(revision 536)
+++ /trunk/nv/ecs/ecs.hh	(revision 537)
@@ -20,4 +20,5 @@
 #include <nv/stl/priority_queue.hh>
 #include <nv/stl/handle_manager.hh>
+#include <nv/stl/range.hh>
 #include <nv/core/types.hh>
 
@@ -27,5 +28,4 @@
 	namespace ecs
 	{
-
 
 		template < typename Handle, typename Time = f32 >
@@ -68,4 +68,24 @@
 				virtual void* get_raw( handle_type h ) = 0;
 				virtual const void* get_raw( handle_type h ) const = 0;
+			};
+
+			class enumerator : public value_enumerator_base < handle_type >
+			{
+			public:
+				typedef value_enumerator_base < handle_type > base_class;
+				explicit enumerator( const ecs& aecs, handle_type current = handle_type() ) : base_class( current ), m_ecs( aecs ) {}
+				enumerator& operator++ ()
+				{
+					base_class::m_value = m_ecs.next( base_class::m_value );
+					return *this;
+				}
+				value_enumerator_base operator++ ( int )
+				{
+					auto result = *this;
+					base_class::m_value = m_ecs.next( base_class::m_value );
+					return result;
+				}
+			private:
+				const ecs& m_ecs;
 			};
 
@@ -198,7 +218,15 @@
 			}
 
-			handle_type first( handle_type h ) const
+			handle_type first_child( handle_type h ) const
 			{
 				return h ? m_handles.first( h ) : handle_type();
+			}
+
+			enumerator_provider< enumerator > children( handle_type h ) const
+			{
+				return enumerator_provider< enumerator >(
+					enumerator( *this, first_child( h ) ),
+					enumerator( *this )
+				);
 			}
 
@@ -241,143 +269,4 @@
 			time_type                                   m_time = time_type(0);
 			priority_queue< message, vector< message >, message_compare_type > m_pqueue;
-		};
-
-		template < typename Ecs, typename Component >
-		class component : public Ecs::component_interface
-		{
-		public:
-			typedef Ecs                                    ecs_type;
-			typedef typename ecs_type::message             message_type;
-			typedef typename ecs_type::handle_type         handle_type;
-			typedef typename ecs_type::time_type           time_type;
-			typedef index_table< handle_type >             index_table_type;
-			typedef Component                              value_type;
-			typedef Component                              component_type;
-			typedef vector< value_type >                   storage_type;
-			typedef typename index_table_type::index_type  index_type;
-
-			typedef typename storage_type::iterator        iterator;
-			typedef typename storage_type::const_iterator  const_iterator;
-			typedef typename storage_type::reference       reference;
-			typedef typename storage_type::const_reference const_reference;
-
-			component( ecs_type& a_ecs, string_view a_name, uint32 reserve = 0 ) : m_ecs( a_ecs )
-			{
-				m_ecs.register_component<component_type>( a_name, this );
-				if ( reserve != 0 )
-				{
-					m_data.reserve( reserve );
-				}
-			}
-
-			value_type& insert( handle_type h )
-			{
-				index_type i = m_index.insert( h );
-				NV_ASSERT( i == index_type( m_data.size() ), "Fail!" );
-				NV_UNUSED( i );
-				m_data.emplace_back();
-				return m_data.back();
-			}
-
-			template < typename ...Args >
-			value_type& insert( handle_type h, Args&&... args )
-			{
-				index_type i = m_index.insert( h );
-				NV_ASSERT( i == index_type( m_data.size() ), "Fail!" );
-				NV_UNUSED( i );
-				m_data.emplace_back( nv::forward<Args>( args )... );
-				return m_data.back();
-			}
-
-			bool exists( handle_type h )
-			{
-				return m_index.exists( h );
-			}
-
-			virtual void update( time_type /*dtime*/ )
-			{
-				// no-op
-			}
-
-			virtual void clear()
-			{
-				for ( uint32 i = 0; i < m_index.size(); ++i )
-					destroy( &m_data[i] );
-				m_index.clear();
-				m_data.clear();
-			}
-			
-			value_type* get( handle_type h )
-			{
-				index_type i = m_index.get( h );
-				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
-			}
-
-			const value_type* get( handle_type h ) const
-			{
-				index_type i = m_index.get( h );
-				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
-			}
-
-			void* get_raw( handle_type h )
-			{
-				index_type i = m_index.get( h );
-				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
-			}
-
-			const void* get_raw( handle_type h ) const
-			{
-				index_type i = m_index.get( h );
-				return i >= 0 ? &( m_data[unsigned( i )] ) : nullptr;
-			}
-
-			virtual void remove( handle_type h )
-			{
-				value_type* v = get( h );
-				if ( v == nullptr ) return;
-				destroy( v );
-				index_type dead_eindex = m_index.remove_swap( h );
-				if ( dead_eindex == -1 ) return;
-				if ( dead_eindex != static_cast<index_type>( m_data.size() - 1 ) )
-				{
-					m_data[unsigned( dead_eindex )] = move( m_data.back() );
-				}
-				m_data.pop_back();
-			}
-
-			virtual void destroy( value_type* )
-			{
-				// cleanup
-			}
-
-			virtual bool handle_message( const message_type& )
-			{
-				return true;
-			}
-
-			~component()
-			{
-				clear();
-			}
-
-
-			handle_type get_handle( index_type i ) const { return m_index.get_handle( i ); }
-
-			const value_type& operator[] ( index_type i ) const { return m_data[i]; }
-			value_type& operator[] ( index_type i ) { return m_data[i]; }
-
-			size_t size() const { return m_data.size(); }
-
-			iterator        begin() { return m_data.begin(); }
-			const_iterator  begin()  const { return m_data.cbegin(); }
-			const_iterator  cbegin() const { return m_data.cbegin(); }
-
-			iterator        end() { return m_data.end(); }
-			const_iterator  end()  const { return m_data.cend(); }
-			const_iterator  cend() const { return m_data.cend(); }
-		protected:
-			ecs_type&        m_ecs;
-			index_table_type m_index;
-			storage_type     m_data;
 		};
 
@@ -411,4 +300,5 @@
 			ecs_type&        m_ecs;
 		};
+
 	}
 
Index: /trunk/nv/stl/index_table.hh
===================================================================
--- /trunk/nv/stl/index_table.hh	(revision 536)
+++ /trunk/nv/stl/index_table.hh	(revision 537)
@@ -116,4 +116,5 @@
 	};
 
+
 }
 
Index: /trunk/nv/stl/range.hh
===================================================================
--- /trunk/nv/stl/range.hh	(revision 536)
+++ /trunk/nv/stl/range.hh	(revision 537)
@@ -1,3 +1,3 @@
-// Copyright (C) 2014-2015 ChaosForge Ltd
+// Copyright (C) 2014-2017 ChaosForge Ltd
 // http://chaosforge.org/
 //
@@ -17,4 +17,5 @@
 #include <nv/stl/math.hh>
 #include <nv/stl/iterator.hh>
+#include <nv/stl/utility/enumerator.hh>
 #include <nv/stl/type_traits/transforms.hh>
 
@@ -26,29 +27,10 @@
 
 		template < typename T >
-		class forward_iterator_base : public iterator< input_iterator_tag, T >
-		{
-		public:
-			forward_iterator_base( T value ) : m_value( value ) {}
-			T operator* () const { return m_value; }
-			T const* operator-> () const { return &m_value; }
-			bool operator== ( const forward_iterator_base& rhs ) const
-			{
-				return m_value == rhs.m_value;
-			}
-			bool operator!= ( const forward_iterator_base& rhs ) const
-			{
-				return !( *this == rhs );
-			}
-		protected:
-			T m_value;
-		};
-
-		template < typename T >
-		class range_iterator_base : public forward_iterator_base< T >
-		{
-		public:
-			typedef forward_iterator_base< T > base_class;
-
-			range_iterator_base( T value ) : forward_iterator_base<T>( value ) {}
+		class range_iterator_base : public value_enumerator_base< T >
+		{
+		public:
+			typedef value_enumerator_base< T > base_class;
+
+			range_iterator_base( T value ) : value_enumerator_base<T>( value ) {}
 			range_iterator_base& operator++ () 
 			{
@@ -66,11 +48,11 @@
 		template < typename T >
 		class range2d_iterator_base 
-			: public forward_iterator_base< math::tvec2<T> >
-		{
-		public:
-			typedef forward_iterator_base< math::tvec2<T> > base_class;
+			: public value_enumerator_base< math::tvec2<T> >
+		{
+		public:
+			typedef value_enumerator_base< math::tvec2<T> > base_class;
 
 			range2d_iterator_base( math::tvec2<T> value, T min, T max )
-				: forward_iterator_base< math::tvec2<T> >( value ), m_min(min), m_max(max) {}
+				: base_class( value ), m_min(min), m_max(max) {}
 			range2d_iterator_base& operator++ () 
 			{
@@ -95,9 +77,9 @@
 
 		template < typename T >
-		class bits_iterator_base : public forward_iterator_base< T >
+		class bits_iterator_base : public value_enumerator_base< T >
 		{
 		public:
 			typedef make_underlying_type_t< T > base_type;
-			typedef forward_iterator_base< T > base_class;
+			typedef value_enumerator_base< T > base_class;
 
 			static const T invalid = T( 0 );
@@ -136,14 +118,22 @@
 
 	template < typename T >
-	class range_iterator_provider
+	using range_iterator_provider = enumerator_provider<
+		detail::range_iterator_base<T> >;
+
+	template < typename T >
+	class range2d_iterator_provider
 	{
 	public:
-		class iterator : public detail::range_iterator_base<T>
-		{
-		public:
-			iterator( T value ) : detail::range_iterator_base<T>(value) {}
-		};
-
-		range_iterator_provider( T begin, T end ) : m_begin( begin ), m_end( end ) {}
+		typedef T value_type;
+		typedef typename T::value_type element_type;
+
+		class iterator : public detail::range2d_iterator_base<element_type>
+		{
+		public:
+			iterator( value_type begin, element_type min, element_type max ) 
+				: detail::range2d_iterator_base<element_type>(begin, min, max) {}
+		};
+
+		range2d_iterator_provider( value_type begin, value_type end ) : m_begin( begin, begin.x, end.x ), m_end( T(begin.x, ++end.y ), begin.x, end.x ) {}
 		iterator begin() { return m_begin; }
 		iterator end() { return m_end; }
@@ -155,27 +145,4 @@
 
 	template < typename T >
-	class range2d_iterator_provider
-	{
-	public:
-		typedef T value_type;
-		typedef typename T::value_type element_type;
-
-		class iterator : public detail::range2d_iterator_base<element_type>
-		{
-		public:
-			iterator( value_type begin, element_type min, element_type max ) 
-				: detail::range2d_iterator_base<element_type>(begin, min, max) {}
-		};
-
-		range2d_iterator_provider( value_type begin, value_type end ) : m_begin( begin, begin.x, end.x ), m_end( T(begin.x, ++end.y ), begin.x, end.x ) {}
-		iterator begin() { return m_begin; }
-		iterator end() { return m_end; }
-
-	protected:
-		iterator m_begin;
-		iterator m_end;
-	};
-
-	template < typename T >
 	class bits_iterator_provider
 	{
