135 lines
3.4 KiB
C++
135 lines
3.4 KiB
C++
/**
|
|
*******************************************************************************
|
|
* @file ewol/openGL/Program.cpp
|
|
* @brief ewol openGl Program shader system (Sources)
|
|
* @author Edouard DUPIN
|
|
* @date 24/08/2012
|
|
* @par Project
|
|
* ewol
|
|
*
|
|
* @par Copyright
|
|
* Copyright 2011 Edouard DUPIN, all right reserved
|
|
*
|
|
* This software is distributed in the hope that it will be useful, but WITHOUT
|
|
* ANY WARRANTY.
|
|
*
|
|
* Licence summary :
|
|
* You can modify and redistribute the sources code and binaries.
|
|
* You can send me the bug-fix
|
|
*
|
|
* Term of the licence in in the file licence.txt.
|
|
*
|
|
*******************************************************************************
|
|
*/
|
|
|
|
#include <etk/Types.h>
|
|
#include <ewol/Debug.h>
|
|
#include <ewol/openGL/Program.h>
|
|
#include <ewol/ResourceManager.h>
|
|
|
|
ewol::Program::Program(etk::UString& filename) :
|
|
ewol::Resource(filename),
|
|
m_program(0)
|
|
{
|
|
|
|
// load data from file "all the time ..."
|
|
|
|
etk::File file(m_name, etk::FILE_TYPE_DATA);
|
|
if (false == file.Exist()) {
|
|
EWOL_ERROR("File does not Exist : \"" << file << "\"");
|
|
return;
|
|
}
|
|
|
|
etk::UString fileExtention = file.GetExtention();
|
|
if (fileExtention != "prog") {
|
|
EWOL_ERROR("File does not have extention \".prog\" for program but : \"" << fileExtention << "\"");
|
|
return;
|
|
}
|
|
if (false == file.fOpenRead()) {
|
|
EWOL_ERROR("Can not open the file : " << file);
|
|
return;
|
|
}
|
|
#define MAX_LINE_SIZE (2048)
|
|
char tmpData[MAX_LINE_SIZE];
|
|
while (file.fGets(tmpData, MAX_LINE_SIZE) != NULL) {
|
|
int32_t len = strlen(tmpData);
|
|
if( tmpData[len-1] == '\n'
|
|
|| tmpData[len-1] == '\r') {
|
|
tmpData[len-1] = '\0';
|
|
len--;
|
|
}
|
|
if (len == 0) {
|
|
continue;
|
|
}
|
|
etk::UString tmpFilename = tmpData;
|
|
ewol::Shader* tmpShader = NULL;
|
|
if (false == ewol::resource::Keep(tmpFilename, tmpShader)) {
|
|
EWOL_CRITICAL("Error while getting a specific shader filename : " << tmpFilename);
|
|
} else {
|
|
EWOL_DEBUG("Add shader on program : "<< tmpFilename);
|
|
m_shaderList.PushBack(tmpShader);
|
|
}
|
|
|
|
}
|
|
// close the file:
|
|
file.fClose();
|
|
|
|
CreateAndLink();
|
|
|
|
}
|
|
|
|
ewol::Program::~Program(void)
|
|
{
|
|
for (int32_t iii=0; iii<m_shaderList.Size(); iii++) {
|
|
ewol::resource::Release(m_shaderList[iii]);
|
|
m_shaderList[iii] = 0;
|
|
}
|
|
m_shaderList.Clear();
|
|
if (0!=m_program) {
|
|
glDeleteProgram(m_program);
|
|
m_program = 0;
|
|
}
|
|
}
|
|
|
|
static void checkGlError(const char* op)
|
|
{
|
|
for (GLint error = glGetError(); error; error = glGetError()) {
|
|
EWOL_INFO("after " << op << "() glError (" << error << ")");
|
|
}
|
|
}
|
|
|
|
#define LOG_OGL_INTERNAL_BUFFER_LEN (8192)
|
|
static char l_bufferDisplayError[LOG_OGL_INTERNAL_BUFFER_LEN] = "";
|
|
|
|
bool ewol::Program::CreateAndLink(void)
|
|
{
|
|
EWOL_INFO("Create the Program ...");
|
|
m_program = glCreateProgram();
|
|
if (0 == m_program) {
|
|
EWOL_ERROR("program creation return error ...");
|
|
return false;
|
|
}
|
|
|
|
for (int32_t iii=0; iii<m_shaderList.Size(); iii++) {
|
|
if (NULL != m_shaderList[iii]) {
|
|
glAttachShader(m_program, m_shaderList[iii]->GetGL_ID());
|
|
checkGlError("glAttachShader");
|
|
}
|
|
}
|
|
glLinkProgram(m_program);
|
|
GLint linkStatus = GL_FALSE;
|
|
glGetProgramiv(m_program, GL_LINK_STATUS, &linkStatus);
|
|
if (linkStatus != GL_TRUE) {
|
|
GLint bufLength = 0;
|
|
l_bufferDisplayError[0] = '\0';
|
|
glGetProgramInfoLog(m_program, LOG_OGL_INTERNAL_BUFFER_LEN, &bufLength, l_bufferDisplayError);
|
|
EWOL_ERROR("Could not compile \"PROGRAM\": " << l_bufferDisplayError);
|
|
glDeleteProgram(m_program);
|
|
m_program = 0;
|
|
return false;
|
|
}
|
|
return true;
|
|
}
|
|
|
|
|