Index: trunk/src/formats/nmd_loader.cc
===================================================================
--- trunk/src/formats/nmd_loader.cc	(revision 421)
+++ trunk/src/formats/nmd_loader.cc	(revision 423)
@@ -28,5 +28,5 @@
 		case nmd_type::MESH           : load_mesh( source, element_header ); break;
 		case nmd_type::ANIMATION      : load_animation( source, element_header ); break;
-//		case nmd_type::STRING_TABLE   : load_strings( source ); break;
+		case nmd_type::STRINGS        : load_strings( source ); break;
 		default: NV_ASSERT( false, "UNKNOWN NMD ELEMENT!" ); break;
 		}
@@ -68,5 +68,5 @@
 {
 	for ( auto mesh : m_meshes ) if ( mesh ) delete mesh;
-//	if ( m_strings )   delete m_strings;
+	if ( m_strings )   delete m_strings;
 	if ( m_node_data ) delete m_node_data;
 	m_meshes.clear();
@@ -76,5 +76,5 @@
 	m_node_data  = nullptr;
 	m_node_array = nullptr;
-//	m_strings    = nullptr;
+	m_strings    = nullptr;
 }
 
@@ -90,8 +90,9 @@
 }
 
-bool nv::nmd_loader::load_strings( stream& /*source*/ )
-{
-//	NV_ASSERT( m_strings == nullptr, "MULTIPLE STRING ENTRIES!" );
-//	m_strings = new string_table( &source );
+bool nv::nmd_loader::load_strings( stream& source )
+{
+	NV_ASSERT( m_strings == nullptr, "MULTIPLE STRING ENTRIES!" );
+	// TODO: load strings optionally
+	m_strings = new string_table( source );
 	return true;
 }
@@ -112,5 +113,5 @@
 		load_node( source, &m_node_array[i], element_header );
 	}
-	m_node_data = new mesh_nodes_data( "animation", e.children, m_node_array, animation_header.frame_rate, animation_header.duration, animation_header.flat );
+	m_node_data = new mesh_nodes_data( e.name, e.children, m_node_array, animation_header.frame_rate, animation_header.duration, animation_header.flat );
 	return true;
 }
@@ -118,5 +119,5 @@
 bool nv::nmd_loader::load_node( stream& source, mesh_node_data* data, const nmd_element_header& e )
 {
-	data->name_hash = e.name_hash;
+	data->name = e.name;
 	data->parent_id = e.parent_id;
 	data->transform = e.transform;
@@ -190,26 +191,4 @@
 }
 
-static void nmd_dump_mesh( const data_channel_set* mesh, stream& stream_out )
-{
-	uint32 size = 0;
-	for ( auto& chan : *mesh )
-	{
-		size += sizeof( nmd_channel_header );
-		size += chan.raw_size();
-	}
-
-	nmd_element_header eheader;
-	eheader.type       = nmd_type::MESH;
-//	eheader.name       = 0;
-	eheader.children   = static_cast< uint16 >( mesh->size() );
-	eheader.size       = size;
-	eheader.name_hash  = 0;
-	eheader.transform  = mat4();
-	eheader.parent_id  = -1;
-	eheader.attributes = 0;
-	stream_out.write( &eheader, sizeof( eheader ), 1 );
-	nmd_dump_channel_set( mesh, stream_out );
-}
-
 static void nmd_dump_node( const mesh_node_data* node, stream& stream_out )
 {
@@ -227,5 +206,5 @@
 	eheader.children   = static_cast<uint16>( chan_count );
 	eheader.size       = chan_size;
-	eheader.name_hash  = node->name_hash;
+	eheader.name       = node->name;
 	eheader.parent_id  = node->parent_id;
 	eheader.transform  = node->transform;
@@ -235,10 +214,46 @@
 }
 
-static void nmd_dump_nodes_data( const mesh_nodes_data* nodes, stream& stream_out, string_table_creator* /*strings*/ )
+void nv::nmd_dump_header( stream& stream_out, uint32 elements, uint64 name )
+{
+	nmd_header header;
+	header.id = four_cc<'n', 'm', 'f', '1'>::value;
+	header.elements = elements; // +1 string array
+	header.name = name;
+	header.version = 1;
+	header.attributes = 0;
+	stream_out.write( &header, sizeof( header ), 1 );
+}
+
+void nv::nmd_dump_mesh( stream& stream_out, const data_channel_set& mesh )
+{
+	uint32 size = 0;
+	for ( auto& chan : mesh )
+	{
+		size += sizeof( nmd_channel_header );
+		size += chan.raw_size();
+	}
+
+	nmd_element_header eheader;
+	eheader.type       = nmd_type::MESH;
+	eheader.children   = static_cast<uint16>( mesh.size() );
+	eheader.size       = size;
+	int uncomment;
+// 	eheader.name       = mesh.get_name();
+// 	eheader.transform  = mesh.get_transform();
+// 	eheader.parent_id  = mesh.get_parent_id();
+ 	eheader.name       = 0;
+ 	eheader.transform  = mat4();
+ 	eheader.parent_id  = -1;
+	eheader.attributes = 0;
+	stream_out.write( &eheader, sizeof( eheader ), 1 );
+	nmd_dump_channel_set( &mesh, stream_out );
+}
+
+void nv::nmd_dump_nodes( stream& stream_out, const mesh_nodes_data& nodes )
 {
 	uint32 total = sizeof( nmd_animation_header );
-	for ( uint32 i = 0; i < nodes->get_count(); ++i )
-	{
-		const mesh_node_data* node = nodes->get_node(i);
+	for ( uint32 i = 0; i < nodes.get_count(); ++i )
+	{
+		const mesh_node_data* node = nodes.get_node( i );
 		total += sizeof( nmd_element_header );
 		if ( node->data )
@@ -246,16 +261,15 @@
 			{
 				total += sizeof( nmd_channel_header );
-				total += node->data->get_channel(c)->raw_size();
+				total += node->data->get_channel( c )->raw_size();
 			}
 	}
 
 	nmd_element_header header;
-//	header.name       = 0;
-	header.type       = nmd_type::ANIMATION;
-	header.children   = static_cast< uint16 >( nodes->get_count() );
-	header.size       = total;
-	header.name_hash  = 0;
-	header.transform  = mat4();
-	header.parent_id  = -1;
+	header.type = nmd_type::ANIMATION;
+	header.children = static_cast<uint16>( nodes.get_count() );
+	header.size = total;
+	header.name = nodes.get_name();
+	header.transform = mat4();
+	header.parent_id = -1;
 	header.attributes = 0;
 
@@ -263,48 +277,48 @@
 
 	nmd_animation_header aheader;
-	aheader.frame_rate  = nodes->get_frame_rate();
-	aheader.duration    = nodes->get_duration();
-	aheader.flat        = nodes->is_flat();
+	aheader.frame_rate = nodes.get_frame_rate();
+	aheader.duration = nodes.get_duration();
+	aheader.flat = nodes.is_flat();
 	stream_out.write( &aheader, sizeof( aheader ), 1 );
 
-	for ( uint32 i = 0; i < nodes->get_count(); ++i )
-	{
-		nmd_dump_node( nodes->get_node( i ), stream_out );
-	}
-}
-
-void nv::nmd_dump( const mesh_data_pack* model, stream& stream_out )
-{
-	string_table_creator strings;
-	{
-		nmd_header header;
-		header.id       = four_cc<'n','m','f','1'>::value;
-		header.elements = 0; // +1 string array
-		header.elements += model->get_count();
-		if ( model->get_nodes() && model->get_nodes()->get_count() > 0 ) 
-			header.elements += 1;//  +1 bone array
-		header.version  = 1;
-		header.attributes = 0;
-		stream_out.write( &header, sizeof( header ), 1 );
-	}
+	for ( uint32 i = 0; i < nodes.get_count(); ++i )
+	{
+		nmd_dump_node( nodes.get_node( i ), stream_out );
+	}
+}
+
+void nv::nmd_dump_strings( stream& stream_out, const string_table& strings )
+{
+	nmd_element_header sheader;
+	sheader.type       = nv::nmd_type::STRINGS;
+	sheader.children   = 0;
+	sheader.size       = strings.dump_size();
+	sheader.name       = 0;
+	sheader.parent_id  = -1;
+    sheader.attributes = 0;
+	stream_out.write( &sheader, sizeof( sheader ), 1 );
+	strings.dump( stream_out );
+}
+
+void nv::nmd_dump( stream& stream_out, const mesh_data_pack* model, const string_table* strings, uint64 name )
+{
+	uint32 elements = ( strings ? 1 : 0 ) // +1 string array
+		+ model->get_count() // meshes
+		+ ( model->get_node_count() > 0 ? 1 : 0 ); // nodes
+	nmd_dump_header( stream_out, elements, name );
 
 	for ( uint32 i = 0; i < model->get_count(); ++i )
 	{
-		const data_channel_set* mesh = model->get_mesh(i);
-		nmd_dump_mesh( mesh, stream_out );
-	}
-
-	if ( model->get_nodes() && model->get_nodes()->get_count() > 0 )
-	{
-		nmd_dump_nodes_data( model->get_nodes(), stream_out, &strings );
-	}
-
-// 	nmd_element_header sheader;
-// 	sheader.type     = nv::nmd_type::STRING_TABLE;
-// 	sheader.name     = 0;
-// 	sheader.size     = strings.dump_size();
-// 	sheader.children = 0;
-//  sheader.attributes = 0;
-// 	stream_out.write( &sheader, sizeof( sheader ), 1 );
-// 	strings.dump( &stream_out );
-}
+		nmd_dump_mesh( stream_out, *model->get_mesh( i ) );
+	}
+
+	if ( model->get_node_count() > 0 )
+	{
+		nmd_dump_nodes( stream_out, *model->get_nodes() );
+	}
+
+	if ( strings )
+	{
+		nmd_dump_strings( stream_out, *strings );
+	}
+}
