#include "stdafx.h"
#include "GlVBO.h"

#define VBO_BUFFER_OFFSET(bytes) ((GLubyte *)NULL + (bytes))



GlVBO::GlVBO(GLenum target) :
	m_Target(target)
{
	m_BufID = 0;
}

GlVBO::~GlVBO(void)
{
	ReleaseBufferElement();
}

void GlVBO::GenerateBuffer(void)
{
	glGenBuffers(1, &m_BufID);
}

GLuint GlVBO::GetID(void)
{
	return m_BufID;
}

void GlVBO::ReleaseBufferElement(void)
{
	if(m_BufID == 0)
		return;

	glDeleteBuffers(1, &m_BufID);
	m_BufID = 0;
}

bool GlVBO::HasBuffer(void) const
{
	return m_BufID != 0;
}

void GlVBO::Bind(void)
{
	glBindBuffer(m_Target, m_BufID);
}

void GlVBO::AssginBuffer2f(const std::vector<lm::vec2f>& buf)
{
	int num_elems = 2;

	GenerateBuffer();
	Bind();
	glBufferData(GL_ARRAY_BUFFER, buf.size() * num_elems * 4, buf[0].v(), GL_STATIC_DRAW);
}

void GlVBO::AssginBuffer3f(const std::vector<lm::vec3f>& buf)
{
	int num_elems = 3;

	GenerateBuffer();
	Bind();
	glBufferData(GL_ARRAY_BUFFER, buf.size() * num_elems * 4, buf[0].v(), GL_STATIC_DRAW);
}

void GlVBO::AssginBufferi(const std::vector<GLuint>& buf)
{
	GenerateBuffer();
	Bind();
	glBufferData(GL_ELEMENT_ARRAY_BUFFER, buf.size() * 4, &buf[0], GL_STATIC_DRAW);
}

void GlVBO::BindPtrAsNoral(void)
{
	glEnableClientState(GL_NORMAL_ARRAY);
	Bind();
	glNormalPointer(GL_FLOAT, 0, VBO_BUFFER_OFFSET(0));
}

void GlVBO::BindPtrAsColor(void)
{
	glEnableClientState(GL_COLOR_ARRAY);
	Bind();
	glColorPointer(3, GL_FLOAT, 0, VBO_BUFFER_OFFSET(0));
}

void GlVBO::BindPtrAsTexcoord(void)
{
	glEnableClientState(GL_TEXTURE_COORD_ARRAY);
	Bind();
	glTexCoordPointer(2, GL_FLOAT, 0, VBO_BUFFER_OFFSET(0));
}

void GlVBO::BindPtrAsAttrib3f(GLint buf_id)
{
	glEnableVertexAttribArray(buf_id);
	Bind();
	glVertexAttribPointer(buf_id, 3, GL_FLOAT, GL_FALSE, sizeof(float) * 3, VBO_BUFFER_OFFSET(0));
}
