Index: /trunk/nv/interface/device.hh
===================================================================
--- /trunk/nv/interface/device.hh	(revision 460)
+++ /trunk/nv/interface/device.hh	(revision 461)
@@ -56,4 +56,5 @@
 		TEX_SPECULAR = 1,
 		TEX_NORMAL   = 2,
+		TEX_GLOSS    = 3,
 		TEXTURE_0    = 0,
 		TEXTURE_1    = 1,
@@ -295,4 +296,5 @@
 			factory_link_map[ "nv_t_specular"] = new engine_link_uniform_int<1>();
 			factory_link_map[ "nv_t_normal"  ] = new engine_link_uniform_int<2>();
+			factory_link_map[ "nv_t_gloss"   ] = new engine_link_uniform_int<3>();
 		}
 		void destroy_engine_uniforms()
Index: /trunk/nv/interface/image_data.hh
===================================================================
--- /trunk/nv/interface/image_data.hh	(revision 460)
+++ /trunk/nv/interface/image_data.hh	(revision 461)
@@ -30,4 +30,5 @@
 		BGR,
 		BGRA,
+		RED,
 	};
 	
@@ -50,5 +51,5 @@
 		const ivec2 get_size() const { return m_size; }
 		// TODO : better depth check (template?)
-		size_t get_depth()    const { return m_format.format == RGB || m_format.format == BGR ? 3 : 4; }
+		size_t get_depth() const { return m_format.format == RGB || m_format.format == BGR ? 3 : ( m_format.format == RED ? 1 : 4 ); }
 		image_format get_format() const { return m_format; }
 		~image_data() {	if (m_data) delete[] m_data; }
Index: /trunk/nv/stl/math/quaternion.hh
===================================================================
--- /trunk/nv/stl/math/quaternion.hh	(revision 460)
+++ /trunk/nv/stl/math/quaternion.hh	(revision 461)
@@ -48,5 +48,5 @@
 
 			constexpr tquat() 
-				: x( 0 ), y( 0 ), z( 0 ), w( 0 ) {};
+				: x( 0 ), y( 0 ), z( 0 ), w( 1 ) {};
 			constexpr tquat( const tquat<T>& q ) 
 				: x( q.x ), y( q.y ), z( q.z ), w( q.w ) {}
@@ -83,8 +83,10 @@
 			inline tquat<T>& operator*=( const tquat<T>& q )
 			{
-				this->w = w * q.w - x * q.x - y * q.y - z * q.z;
-				this->x = w * q.x + x * q.w + y * q.z - z * q.y;
-				this->y = w * q.y + y * q.w + z * q.x - x * q.z;
-				this->z = w * q.z + z * q.w + x * q.y - y * q.x;
+				tquat<T> p( *this );
+				
+				this->w = p.w * q.w - p.x * q.x - p.y * q.y - p.z * q.z;
+				this->x = p.w * q.x + p.x * q.w + p.y * q.z - p.z * q.y;
+				this->y = p.w * q.y + p.y * q.w + p.z * q.x - p.x * q.z;
+				this->z = p.w * q.z + p.z * q.w + p.x * q.y - p.y * q.x;
 				return *this;
 			}
@@ -159,5 +161,5 @@
 		inline tquat<T> normalize( const tquat<T>& q )
 		{
-			T len = length( q );
+			T len = math::length( q );
 			if ( len <= T( 0 ) ) return tquat<T>( 1, 0, 0, 0 );
 			T rlen = T( 1 ) / len;
@@ -392,5 +394,5 @@
 			tquat<T> result( ctor::uninitialize );
 			T sina = sin( angle * static_cast<T>( 0.5 ) );
-			result.w = ( angle * static_cast<T>( 0.5 ) );
+			result.w = cos( angle * static_cast<T>( 0.5 ) );
 			result.x = v.x * sina;
 			result.y = v.y * sina;
Index: /trunk/src/gl/gl_device.cc
===================================================================
--- /trunk/src/gl/gl_device.cc	(revision 460)
+++ /trunk/src/gl/gl_device.cc	(revision 461)
@@ -51,6 +51,13 @@
 	}
 	// TODO: BGR vs RGB, single channel
-	assert( image->format->BytesPerPixel > 2 );
-	image_format format(image->format->BytesPerPixel == 3 ? RGB : RGBA, UBYTE );
+	pixel_format pformat = RGBA;
+	switch ( image->format->BytesPerPixel )
+	{
+	case 4: pformat = RGBA; break;
+	case 3: pformat = RGB; break;
+	case 1: pformat = RED; break;
+	default: NV_ASSERT( false, "BytesPerPixel != 4,3 or 1!" );
+	}
+	image_format format( pformat, UBYTE );
 	image_data* data = new image_data( format, ivec2( image->w, image->h ), static_cast<nv::uint8*>( image->pixels ) );
 	return data;
Index: /trunk/src/gl/gl_enum.cc
===================================================================
--- /trunk/src/gl/gl_enum.cc	(revision 460)
+++ /trunk/src/gl/gl_enum.cc	(revision 461)
@@ -184,4 +184,5 @@
 	case BGR     : return GL_BGR;
 	case BGRA    : return GL_BGRA;
+	case RED     : return GL_RED;
 	NV_RETURN_COVERED_DEFAULT( 0 );
 	}
@@ -200,4 +201,6 @@
 	case BGR     : return GL_RGB8;
 	case BGRA    : return GL_RGBA8;
+	case RED     : return 0x8040; // GL_LUMINANCE8; // TODO: change to GL_R8!
+
 	NV_RETURN_COVERED_DEFAULT( 0 );
 	}
