Index: /trunk/nv/core/arcball.hh
===================================================================
--- /trunk/nv/core/arcball.hh	(revision 452)
+++ /trunk/nv/core/arcball.hh	(revision 453)
@@ -50,5 +50,5 @@
 			vec3 vb = get_arcball_vector( nposition );
 
-			m_angle = math::acos( glm::min( 1.0f, glm::dot( va, vb ) ) );
+			m_angle = math::acos( glm::min( 1.0f, math::dot( va, vb ) ) );
 			m_axis  = glm::cross( va, vb );
 			m_last  = nposition;
Index: /trunk/nv/interface/camera.hh
===================================================================
--- /trunk/nv/interface/camera.hh	(revision 452)
+++ /trunk/nv/interface/camera.hh	(revision 453)
@@ -33,5 +33,5 @@
 		void set_perspective( f32 fov, f32 aspect, f32 near, f32 far )
 		{
-			m_projection = math::perspective( glm::radians( fov ), aspect, near, far );
+			m_projection = math::perspective( math::radians( fov ), aspect, near, far );
 		}
 		void set_ortho( f32 left, f32 right, f32 bottom, f32 top, f32 near = -1.0f, f32 far = 1.0f )
Index: /trunk/nv/stl/math.hh
===================================================================
--- /trunk/nv/stl/math.hh	(revision 452)
+++ /trunk/nv/stl/math.hh	(revision 453)
@@ -13,4 +13,5 @@
 #include <nv/stl/math/common.hh>
 #include <nv/stl/math/constants.hh>
+#include <nv/stl/math/geometric.hh>
 #include <nv/stl/math/matrix_transform.hh>
 #include <nv/stl/math/cast.hh>
Index: /trunk/nv/stl/math/common.hh
===================================================================
--- /trunk/nv/stl/math/common.hh	(revision 452)
+++ /trunk/nv/stl/math/common.hh	(revision 453)
@@ -15,4 +15,5 @@
 
 #include <nv/common.hh>
+#include <nv/stl/type_traits/common.hh>
 
 #if NV_COMPILER == NV_GNUC
@@ -44,4 +45,5 @@
 		using ::floor;
 		using ::ceil;
+		using ::round;
 #if 0
 		template < typename T > using tvec2 = ::glm::detail::tvec2<T, glm::precision::highp>;
@@ -65,4 +67,28 @@
 		using glm::ctor;
 	}
+
+	template < typename T >
+	struct is_math_vector : false_type {};
+
+	template < typename T >
+	struct is_math_matrix : false_type {};
+
+	template < typename T >
+	struct is_math_quat : false_type {};
+
+	template < typename T >
+	struct is_math_class : bool_constant< 
+		is_math_vector< T >::value || 
+		is_math_matrix< T >::value ||
+		is_math_quat< T >::value
+	> {};
+
+	template < typename T > struct is_math_vector< math::tvec2< T > > : true_type {};
+	template < typename T > struct is_math_vector< math::tvec3< T > > : true_type {};
+	template < typename T > struct is_math_vector< math::tvec4< T > > : true_type {};
+	template < typename T > struct is_math_matrix< math::tmat2< T > > : true_type {};
+	template < typename T > struct is_math_matrix< math::tmat3< T > > : true_type {};
+	template < typename T > struct is_math_matrix< math::tmat4< T > > : true_type {};
+	template < typename T > struct is_math_quat  < math::tquat< T > > : true_type {};
 
 	typedef math::tvec2<sint8> i8vec2;
Index: /trunk/nv/stl/math/constants.hh
===================================================================
--- /trunk/nv/stl/math/constants.hh	(revision 452)
+++ /trunk/nv/stl/math/constants.hh	(revision 453)
@@ -197,4 +197,18 @@
 		}
 
+		template < typename T >
+		constexpr T radians( T degrees )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return degrees * static_cast<T>( 0.01745329251994329576923690768489 );
+		}
+
+		template < typename T >
+		constexpr T degrees( T radians )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return radians * static_cast<T>( 57.295779513082320876798154814105 );
+		}
+
 	}
 }
Index: /trunk/nv/stl/math/geometric.hh
===================================================================
--- /trunk/nv/stl/math/geometric.hh	(revision 453)
+++ /trunk/nv/stl/math/geometric.hh	(revision 453)
@@ -0,0 +1,174 @@
+// Copyright (C) 2015-2015 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 geometric.hh
+* @author Kornel Kisielewicz epyon@chaosforge.org
+* @brief geometric math ops
+*/
+
+#ifndef NV_STL_MATH_GEOMERTIC_HH
+#define NV_STL_MATH_GEOMERTIC_HH
+
+#include <nv/stl/math/common.hh>
+
+namespace nv
+{
+
+	namespace math
+	{
+
+		namespace detail
+		{
+			template < typename T >
+			struct dot_impl {};
+
+			template < typename T >
+			struct dot_impl< tvec2< T > >
+			{
+				inline static T get( const tvec2<T>& a, const tvec2<T>& b )
+				{
+					tvec2<T, P> tmp( a * b );
+					return tmp.x + tmp.y;
+				}
+			};
+
+			template < typename T >
+			struct dot_impl< tvec3< T > >
+			{
+				inline static T get( const tvec3<T>& a, const tvec3<T>& b )
+				{
+					tvec3<T> tmp( a * b );
+					return tmp.x + tmp.y + tmp.z;
+				}
+			};
+
+			template < typename T >
+			struct dot_impl< tvec4< T > >
+			{
+				inline static T get( const tvec4<T>& a, const tvec4<T>& b )
+				{
+					tvec4<T> tmp( a * b );
+					return ( tmp.x + tmp.y ) + ( tmp.z + tmp.w );
+				}
+			};
+		}
+
+		template < typename T >
+		inline T length( T x )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return abs( x );
+		}
+
+		template < typename T, template <typename> class Vec >
+		inline T length( const Vec<T>& v )
+		{
+			static_assert( is_math_vector< Vec<T> >::value, "math::vecX expected!" );
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return sqrt( dot( v, v ) );
+		}
+
+		template <typename T>
+		inline T distance( const T& a, const T& b )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return length( b - a );
+		}
+
+		template < typename T, template <typename> class Vec >
+		inline T distance( const Vec<T>& a, const Vec<T>& b )
+		{
+			static_assert( is_math_vector< Vec<T> >::value, "math::vecX expected!" );
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return length( b - a );
+		}
+
+		template < typename T >
+		inline T dot( T a, T b )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return a * b;
+		}
+
+		template < typename T, template <typename> class Vec >
+		inline T dot( const Vec<T>& a, const Vec<T>& b )
+		{
+			static_assert( is_math_vector< Vec<T> >::value, "math::vecX expected!" );
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return detail::dot_impl< Vec, T >::get( a, b );
+		}
+
+		template < typename T >
+		inline tvec3<T> cross( const tvec3<T>& a, const tvec3<T>& b )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return tvec3<T>(
+				a.y * b.z - y.y * b.z,
+				a.z * b.x - y.z * b.x,
+				a.x * b.y - y.x * b.y
+			);
+		}
+
+		template < typename T >
+		inline T normalize( const T& x )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return x < T( 0 ) ? T( -1 ) : T( 1 );
+		}
+
+		template < typename T, template <typename> class Vec >
+		inline Vec<T> normalize( const Vec<T>& x )
+		{
+			static_assert( is_math_vector< Vec<T> >::value, "math::vecX expected!" );
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+			return x * inversesqrt( dot( x, x ) );
+		}
+
+		template < typename T >
+		inline T faceforward( const T& n, const T& i, const T& nref )
+		{
+			return dot( nref, i ) < static_cast<T>( 0 ) ? n : -n;
+		}
+
+		template < typename T, template <typename> class Vec >
+		inline Vec<T> faceforward( const Vec<T>& n, const Vec<T>& i, const Vec<T>& nref )
+		{
+			static_assert( is_math_vector< Vec<T> >::value, "math::vecX expected!" );
+			return dot( nref, i ) < static_cast<T>( 0 ) ? n : -n;
+		}
+
+		template < typename T >
+		inline T reflect( const T& i, const T& n )
+		{
+			return i - n * dot( n, i ) * static_cast<T>( 2 );
+		}
+
+		template < typename T >
+		inline T refract( const T& i, const T& n, const T& eta )
+		{
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+
+			const T dotv( dot( n, i ) );
+			const T k( static_cast<T>( 1 ) - eta * eta * ( static_cast<T>( 1 ) - dotv * dotv ) );
+			return ( eta * i - ( eta * dotv + sqrt( k ) ) * n ) * static_cast<T>( k >= static_cast<T>( 0 ) );
+		}
+
+		template < typename T, template <typename> class Vec >
+		inline Vec<T> refract( const Vec<T>& i, const Vec<T>& n, T eta )
+		{
+			static_assert( is_math_vector< Vec<T> >::value, "math::vecX expected!" );
+			static_assert( is_floating_point<T>::value, "Type expected to be floating point!" );
+
+			T const dotv( dot( n, i ) );
+			T const k( static_cast<T>( 1 ) - eta * eta * ( static_cast<T>( 1 ) - dotv * dotv ) );
+			return ( eta * i - ( eta * dotv + sqrt( k ) ) * n ) * static_cast<T>( k >= static_cast<T>( 0 ) );
+		}
+
+	}
+}
+
+#endif // NV_STL_MATH_GEOMERTIC_HH
Index: /trunk/src/engine/particle_engine.cc
===================================================================
--- /trunk/src/engine/particle_engine.cc	(revision 452)
+++ /trunk/src/engine/particle_engine.cc	(revision 453)
@@ -749,5 +749,5 @@
 					if ( edata.angle > 0.0f )
 					{
-						float emission_angle = glm::radians( edata.angle );
+						float emission_angle = math::radians( edata.angle );
 						float cos_theta = r.frange( math::cos( emission_angle ), 1.0f );
 						float sin_theta = math::sqrt(1.0f - cos_theta * cos_theta );
Index: /trunk/src/rocket/rocket_interface.cc
===================================================================
--- /trunk/src/rocket/rocket_interface.cc	(revision 452)
+++ /trunk/src/rocket/rocket_interface.cc	(revision 453)
@@ -273,5 +273,5 @@
 	nv::vertex_array m_va = m_context->create_vertex_array( rv, num_vertices, (unsigned*)indices, num_indices, nv::STATIC_DRAW );
 	//if ( info )	m_device->set_uniform( m_program, "texsize", nv::vec2( info->size ) );
-	m_state.set_model( glm::translate( glm::mat4(), nv::vec3( translation.x, translation.y, 0.0f ) ) );
+	m_state.set_model( nv::math::translate( nv::mat4(), nv::vec3( translation.x, translation.y, 0.0f ) ) );
 	m_context->draw( nv::TRIANGLES, m_rstate, m_state, m_program, m_va, num_indices );
 	m_context->release( m_va );
Index: /trunk/src/sdl/sdl_audio.cc
===================================================================
--- /trunk/src/sdl/sdl_audio.cc	(revision 452)
+++ /trunk/src/sdl/sdl_audio.cc	(revision 453)
@@ -75,5 +75,5 @@
 			if ( relative != vec3() )
 			{
-				angle = glm::degrees( -glm::orientedAngle( m_forward, glm::normalize( relative ), m_up ) );
+				angle = math::degrees( -glm::orientedAngle( m_forward, glm::normalize( relative ), m_up ) );
 				distance = glm::clamp( 20.0f * glm::length( relative ), 0.0f, 255.0f );
 			}
