#include <mof/Graphics3D.hpp>
#include <mof/private/GraphicsDeviceImpl.hpp>
#include <mof/VertexBuffer_impl.hpp>
#include <mof/VertexTypes.hpp>
#include <stdexcept>

namespace
{
	class vertex_buffer_component : public mof::Graphics3D
	{
		mof::Texture::ptr texture_;
		mof::Material material_;
		mof::VertexBuffer<mof::VertexXYZCUV> buffer_;
		size_t length_;///< プリミティブの数
	public :
//{{{ constructor
		vertex_buffer_component
		(
		 	const std::vector<mof::VertexXYZCUV>& vertices,
			const mof::Texture::ptr& texture, 
			const mof::Material& material
		)
		: 
			buffer_(vertices.front(), vertices.back(), mof::PRIMITIVE_TYPE_TRIANGLELIST),
			texture_(texture),
			material_(material)
		{
		}
//}}}
//{{{ destructor
		virtual ~vertex_buffer_component()
		{
		}
//}}}
//{{{ update
		virtual void update()
		{
			world_transform_.update();
		}
//}}}
//{{{ setVisible
		virtual void setVisible(bool visible)	
		{
			// TODO
		}
//}}}
//{{{ setTexture
		virtual void setTexture
		( 
			unsigned int num,
			const std::shared_ptr<mof::Texture>& pTexture
		)
		{
			// TODO
		}
//}}}
//{{{ setMaterialBuilder
		/*
		virtual void setMaterialBuilder
		( 
			unsigned int num,
			const std::shared_ptr<mof::MaterialBuilder>& material_builder
		)
		{
			// TODO
		}
		*/
//}}}
//{{{ draw
		virtual void draw() const
		{
			mof::GraphicsDevice::setWorldTransform(world_transform_.value());
			mof::GraphicsDevice::setTexture(texture_.get());
			mof::GraphicsDevice::setMaterial(material_);
			buffer_.draw();
		}
//}}}
	};

}


namespace mof
{
//{{{ create_graphics3d
	std::unique_ptr<Graphics3D> Graphics3D::create_graphics3d
	(
		const std::vector<VertexXYZCUV>& vertices,
		const Texture::ptr& texture,
		const Material& material
	)
	{
		return std::unique_ptr<vertex_buffer_component>
			(
			 	new vertex_buffer_component
				(
			 		vertices,
					texture,
					material
				)
			);
	}
//}}}
}// namespace mof

