open source
This commit is contained in:
@@ -0,0 +1,308 @@
|
||||
/**
|
||||
@file JCGlobalValue.cpp
|
||||
@brief
|
||||
@author James
|
||||
@version 1.0
|
||||
@date 2018_5_30
|
||||
*/
|
||||
|
||||
#include "JCGlobalValue.h"
|
||||
#include <util/Log.h>
|
||||
#include <math/Matrix32.h>
|
||||
#include <memory.h>
|
||||
#include <string.h>
|
||||
#if __APPLE__
|
||||
#include <OpenGLES/ES3/gl.h>
|
||||
#include <OpenGLES/ES3/glext.h>
|
||||
#else
|
||||
#include <GLES3/gl3.h>
|
||||
#include <EGL/egl.h>
|
||||
#include <EGL/eglext.h>
|
||||
#endif
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
namespace laya
|
||||
{
|
||||
#define SAVE_DATA_NUM 20
|
||||
JCGlobalValue::JCGlobalValue()
|
||||
{
|
||||
m_nStrideSize = 0;
|
||||
m_pCurrentValue = NULL;
|
||||
m_pBuffer = NULL;
|
||||
m_nCurrentBufferPos = 0;
|
||||
m_nSaveDataSize = 0;
|
||||
m_pDefaultValue = NULL;
|
||||
}
|
||||
JCGlobalValue::~JCGlobalValue()
|
||||
{
|
||||
for (int i = 0, n = m_vValueDesc.size(); i < n; i++)
|
||||
{
|
||||
delete m_vValueDesc[i];
|
||||
m_vValueDesc[i] = NULL;
|
||||
}
|
||||
m_vValueDesc.clear();
|
||||
if (m_pBuffer)
|
||||
{
|
||||
delete[] m_pBuffer;
|
||||
m_pBuffer = NULL;
|
||||
}
|
||||
if (m_pDefaultValue)
|
||||
{
|
||||
delete m_pDefaultValue;
|
||||
m_pDefaultValue = NULL;
|
||||
}
|
||||
m_pCurrentValue = NULL;
|
||||
}
|
||||
ValueDesc* JCGlobalValue::getValueDesc(int nID)
|
||||
{
|
||||
return m_vValueDesc[nID];
|
||||
}
|
||||
void JCGlobalValue::createDefaultValue()
|
||||
{
|
||||
//计算总体的大小
|
||||
ValueDesc* pLast = m_vValueDesc[m_vValueDesc.size() - 1];
|
||||
m_nStrideSize = pLast->m_nOffset + pLast->m_nDataSize;
|
||||
|
||||
//分配好默认的值
|
||||
m_pDefaultValue = new char[m_nStrideSize];
|
||||
for (int i = 0, n = m_vValueDesc.size(); i < n; i++)
|
||||
{
|
||||
ValueDesc* pValueDesc = m_vValueDesc[i];
|
||||
memcpy(m_pDefaultValue + pValueDesc->m_nOffset, pValueDesc->m_pDefaultValue, pValueDesc->m_nDataSize);
|
||||
//这段数据可以不要了
|
||||
delete pValueDesc->m_pDefaultValue;
|
||||
pValueDesc->m_pDefaultValue = NULL;
|
||||
}
|
||||
}
|
||||
void JCGlobalValue::clone(JCGlobalValue* pValueData)
|
||||
{
|
||||
m_nStrideSize = pValueData->m_nStrideSize;
|
||||
m_pDefaultValue = new char[m_nStrideSize];
|
||||
memcpy(m_pDefaultValue,pValueData->m_pDefaultValue,m_nStrideSize);
|
||||
int n = pValueData->m_vValueDesc.size();
|
||||
m_vValueDesc.resize(n);
|
||||
for (int i = VALUE_INTERIOR_TYPE_COUNT; i < n; i++)
|
||||
{
|
||||
ValueDesc* pTemp = pValueData->m_vValueDesc[i];
|
||||
ValueDesc* pValueDesc = new ValueDesc();
|
||||
pValueDesc->m_nModifyType = pTemp->m_nModifyType;
|
||||
pValueDesc->m_nDataType = pTemp->m_nDataType;
|
||||
pValueDesc->m_nSize = pTemp->m_nSize;
|
||||
pValueDesc->m_nDataSize = pTemp->m_nDataSize;
|
||||
pValueDesc->m_nOffset = pTemp->m_nOffset;
|
||||
pValueDesc->m_pDefaultValue = NULL;
|
||||
m_vValueDesc[i] = pValueDesc;
|
||||
}
|
||||
//分配整体的buffer
|
||||
m_nSaveDataSize = SAVE_DATA_NUM * m_nStrideSize;
|
||||
m_pBuffer = new char[m_nSaveDataSize];
|
||||
reset();
|
||||
}
|
||||
void JCGlobalValue::endValueDefine()
|
||||
{
|
||||
createDefaultValue();
|
||||
//分配整体的buffer
|
||||
m_nSaveDataSize = SAVE_DATA_NUM * m_nStrideSize;
|
||||
m_pBuffer = new char[m_nSaveDataSize];
|
||||
reset();
|
||||
}
|
||||
int JCGlobalValue::addValueDefine(VALUE_MODIFY_TYPE nModifyType, int nDataType, int nSize, char* pDefaultValue,int nDefaultValueSize)
|
||||
{
|
||||
ValueDesc* pValueDesc = new ValueDesc();
|
||||
pValueDesc->m_nModifyType = nModifyType;
|
||||
pValueDesc->m_nSize = nSize;
|
||||
pValueDesc->m_nDataType = nDataType;
|
||||
pValueDesc->m_nDataSize = nSize * 4;
|
||||
//new 默认值
|
||||
pValueDesc->m_pDefaultValue = new char[pValueDesc->m_nDataSize];
|
||||
memset(pValueDesc->m_pDefaultValue, 0, pValueDesc->m_nDataSize);
|
||||
if (nDefaultValueSize == pValueDesc->m_nDataSize)
|
||||
{
|
||||
memcpy(pValueDesc->m_pDefaultValue, pDefaultValue, pValueDesc->m_nDataSize);
|
||||
}
|
||||
int nVectorSize = m_vValueDesc.size();
|
||||
if (nVectorSize == 0)
|
||||
{
|
||||
pValueDesc->m_nOffset = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
ValueDesc* pLast = m_vValueDesc[nVectorSize - 1];
|
||||
pValueDesc->m_nOffset = pLast->m_nOffset + pLast->m_nDataSize;
|
||||
}
|
||||
m_vValueDesc.push_back(pValueDesc);
|
||||
return nVectorSize;
|
||||
}
|
||||
bool JCGlobalValue::reset()
|
||||
{
|
||||
memset(m_pBuffer, 0, m_nSaveDataSize);
|
||||
//放入一段默认的
|
||||
memcpy(m_pBuffer, m_pDefaultValue, m_nStrideSize);
|
||||
//当前的data指向默认
|
||||
m_pCurrentValue = m_pBuffer;
|
||||
m_nCurrentBufferPos = 0;
|
||||
return true;
|
||||
}
|
||||
bool JCGlobalValue::save()
|
||||
{
|
||||
m_nCurrentBufferPos += m_nStrideSize;
|
||||
if (m_nCurrentBufferPos >= m_nSaveDataSize )
|
||||
{
|
||||
int nEnlargeSize = SAVE_DATA_NUM * m_nStrideSize;
|
||||
char* pBuffer = new char[m_nSaveDataSize + nEnlargeSize];
|
||||
memset(pBuffer, 0, m_nSaveDataSize + nEnlargeSize);
|
||||
memcpy(pBuffer, m_pBuffer, m_nSaveDataSize);
|
||||
m_nSaveDataSize += nEnlargeSize;
|
||||
memcpy(pBuffer + m_nCurrentBufferPos, m_pCurrentValue, m_nStrideSize);
|
||||
if (m_pBuffer)
|
||||
{
|
||||
delete[] m_pBuffer;
|
||||
m_pBuffer = NULL;
|
||||
}
|
||||
m_pBuffer = pBuffer;
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(m_pBuffer + m_nCurrentBufferPos, m_pCurrentValue, m_nStrideSize);
|
||||
}
|
||||
//重新指向新的位置
|
||||
m_pCurrentValue = m_pBuffer + m_nCurrentBufferPos;
|
||||
return true;
|
||||
}
|
||||
bool JCGlobalValue::restore()
|
||||
{
|
||||
if (m_nCurrentBufferPos > 0)
|
||||
{
|
||||
m_nCurrentBufferPos -= m_nStrideSize;
|
||||
m_pCurrentValue = m_pBuffer + m_nCurrentBufferPos;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
LOGE("JCContextSaveData::restore save and restore don't make a pair.");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
ValueDesc* JCGlobalValue::setValue(int nValueID, char* pData, VALUE_OPERATE_TYPE nOpreateType)
|
||||
{
|
||||
ValueDesc* pValueDesc = m_vValueDesc[nValueID];
|
||||
if (pValueDesc->m_nDataType == GL_INT )
|
||||
{
|
||||
int* iCurData = (int*)(m_pCurrentValue + pValueDesc->m_nOffset);
|
||||
int* iData = (int*)pData;
|
||||
switch (nOpreateType)
|
||||
{
|
||||
case VALUE_OPERATE_ADD:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)iCurData[i] *= iData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_SUB:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)iCurData[i] -= iData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_MUL:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)iCurData[i] *= iData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_DIV:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)iCurData[i] /= iData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_SET:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)iCurData[i] = iData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_BYTE4_COLOR_MUL:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)
|
||||
{
|
||||
int color1 = iCurData[i];
|
||||
int color2 = iData[i];
|
||||
int b = color1 & 255;
|
||||
int g = (color1 >> 8) & 255;
|
||||
int r = (color1 >> 16) & 255;
|
||||
int a = (color1 >> 24) & 255;
|
||||
int b1 = color2 & 255;
|
||||
int g1 = (color2 >> 8) & 255;
|
||||
int r1 = (color2 >> 16) & 255;
|
||||
int a1 = (color2 >> 24) & 255;
|
||||
b *= b1 / 255.0f;
|
||||
g *= g1 / 255.0f;
|
||||
r *= r1 / 255.0f;
|
||||
a *= a1 / 255.0f;
|
||||
iCurData[i] = (a << 24) + (r << 16) + (g << 8) + b;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if (pValueDesc->m_nDataType == GL_FLOAT)
|
||||
{
|
||||
float* fCurData = (float*)(m_pCurrentValue + pValueDesc->m_nOffset);
|
||||
float* fData = (float*)pData;
|
||||
switch (nOpreateType)
|
||||
{
|
||||
case VALUE_OPERATE_ADD:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)fCurData[i] *= fData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_SUB:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)fCurData[i] -= fData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_MUL:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)fCurData[i] *= fData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_DIV:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)fCurData[i] /= fData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_SET:
|
||||
for (int i = 0; i < pValueDesc->m_nSize; i++)fCurData[i] = fData[i];
|
||||
break;
|
||||
case VALUE_OPERATE_M2_MUL:
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
break;
|
||||
case VALUE_OPERATE_M3_MUL:
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
break;
|
||||
case VALUE_OPERATE_M4_MUL:
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
break;
|
||||
case VALUE_OPERATE_M32_MUL:
|
||||
Matrix32::mul(fCurData, fData,fCurData);
|
||||
break;
|
||||
case VALUE_OPERATE_M32_TRANSLATE:
|
||||
Matrix32::translate(fCurData, fData[0], fData[1]);
|
||||
break;
|
||||
case VALUE_OPERATE_M32_SCALE:
|
||||
Matrix32::scale(fCurData, fData[0], fData[1]);
|
||||
break;
|
||||
case VALUE_OPERATE_M32_ROTATE:
|
||||
Matrix32::rotate(fCurData, fData[0]);
|
||||
break;
|
||||
case VALUE_OPERATE_M32_SCALE_PIVOT:
|
||||
Matrix32::translate(fCurData,fData[2], fData[3]);
|
||||
Matrix32::scale(fCurData, fData[0], fData[1]);
|
||||
Matrix32::translate(fCurData, -fData[2], -fData[3]);
|
||||
break;
|
||||
case VALUE_OPERATE_M32_ROTATE_PIVOT:
|
||||
Matrix32::translate(fCurData, fData[1], fData[2]);
|
||||
Matrix32::rotate(fCurData, fData[0]);
|
||||
Matrix32::translate(fCurData, -fData[1], -fData[2]);
|
||||
break;
|
||||
case VALUE_OPERATE_M32_TRANSFORM_PIVOT:
|
||||
Matrix32::translate(fCurData, fData[6], fData[7]);
|
||||
Matrix32::mul(fCurData, fData, fCurData);
|
||||
Matrix32::translate(fCurData, -fData[6], -fData[7]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
return pValueDesc;
|
||||
}
|
||||
void JCGlobalValue::copyValue(int nValueID, char* pData, int nDataLength)
|
||||
{
|
||||
ValueDesc* pValueDesc = m_vValueDesc[nValueID];
|
||||
memcpy(m_pCurrentValue + pValueDesc->m_nOffset, pData, nDataLength);
|
||||
}
|
||||
}
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
|
||||
//-----------------------------END FILE--------------------------------
|
||||
@@ -0,0 +1,197 @@
|
||||
/**
|
||||
@file JCGlobalValue.h
|
||||
@brief
|
||||
@author James
|
||||
@version 1.0
|
||||
@date 2018_5_30
|
||||
*/
|
||||
|
||||
#ifndef __JCGlobalValue_H__
|
||||
#define __JCGlobalValue_H__
|
||||
|
||||
#include <stdio.h>
|
||||
#include <vector>
|
||||
|
||||
namespace laya
|
||||
{
|
||||
enum VALUE_TYPE
|
||||
{
|
||||
VALUE_TYPE_NORMAL,
|
||||
VALUE_TYPE_MAT32,
|
||||
VALUE_TYPE_MAT2,
|
||||
VALUE_TYPE_MAT3,
|
||||
VALUE_TYPE_MAT4,
|
||||
};
|
||||
enum EXECUTE_TYPE
|
||||
{
|
||||
EXECUTE_JS_TRHEAD_BUFFER = 0,
|
||||
EXECUTE_RENDER_THREAD_BUFFER,
|
||||
EXECUTE_COPY_TO_RENDER,
|
||||
EXECUTE_COPY_TO_RENDER3D
|
||||
};
|
||||
enum VALUE_OPERATE_TYPE
|
||||
{
|
||||
VALUE_OPERATE_ADD = 0,
|
||||
VALUE_OPERATE_SUB,
|
||||
VALUE_OPERATE_MUL,
|
||||
VALUE_OPERATE_DIV,
|
||||
VALUE_OPERATE_M2_MUL,
|
||||
VALUE_OPERATE_M3_MUL,
|
||||
VALUE_OPERATE_M4_MUL,
|
||||
VALUE_OPERATE_M32_MUL,
|
||||
VALUE_OPERATE_SET,
|
||||
VALUE_OPERATE_M32_TRANSLATE,
|
||||
VALUE_OPERATE_M32_SCALE,
|
||||
VALUE_OPERATE_M32_ROTATE,
|
||||
VALUE_OPERATE_M32_SCALE_PIVOT,
|
||||
VALUE_OPERATE_M32_ROTATE_PIVOT,
|
||||
VALUE_OPERATE_M32_TRANSFORM_PIVOT,
|
||||
VALUE_OPERATE_BYTE4_COLOR_MUL,
|
||||
};
|
||||
|
||||
enum VALUE_MODIFY_TYPE
|
||||
{
|
||||
VALUE_MODIFY_MESH, //修改mesh的
|
||||
VALUE_MODIFY_SHADER, //修改shader uniform的
|
||||
VALUE_MODIFY_DATA_LOCATION, //数据区的位置
|
||||
};
|
||||
|
||||
enum VALUE_INTERIOR_TYPE
|
||||
{
|
||||
VALUE_INTERIOR_TYPE_COUNT = 0,
|
||||
};
|
||||
|
||||
struct ValueDesc
|
||||
{
|
||||
/*
|
||||
* VALUE_MODIFY_MESH,VALUE_MODIFY_SHADER
|
||||
*/
|
||||
VALUE_MODIFY_TYPE m_nModifyType;
|
||||
|
||||
/*
|
||||
* 只能是4字节对其的,不支持short
|
||||
* GL_INT, GL_FLOAT
|
||||
*/
|
||||
int m_nDataType;
|
||||
|
||||
/*
|
||||
* size传入的size
|
||||
*/
|
||||
int m_nSize;
|
||||
|
||||
/*
|
||||
* dataSize,单位是byte
|
||||
*/
|
||||
int m_nDataSize;
|
||||
|
||||
/*
|
||||
* offsetSize 偏移值为byte
|
||||
*/
|
||||
int m_nOffset;
|
||||
|
||||
/*
|
||||
* offsetSize 偏移值为byte
|
||||
*/
|
||||
char* m_pDefaultValue;
|
||||
|
||||
/*
|
||||
* 数据类型
|
||||
*/
|
||||
VALUE_TYPE m_nValueType;
|
||||
|
||||
ValueDesc()
|
||||
{
|
||||
m_nModifyType = VALUE_MODIFY_MESH;
|
||||
m_nDataType = 0;
|
||||
m_nSize = 0;
|
||||
m_nDataSize = 0;
|
||||
m_nOffset = 0;
|
||||
m_pDefaultValue = NULL;
|
||||
m_nValueType = VALUE_TYPE_NORMAL;
|
||||
}
|
||||
|
||||
~ValueDesc()
|
||||
{
|
||||
if (m_pDefaultValue)
|
||||
{
|
||||
delete[] m_pDefaultValue;
|
||||
m_pDefaultValue = NULL;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief
|
||||
*/
|
||||
class JCGlobalValue
|
||||
{
|
||||
public:
|
||||
|
||||
struct Point
|
||||
{
|
||||
float x, y;
|
||||
};
|
||||
|
||||
public:
|
||||
|
||||
/** @brief构造函数
|
||||
*/
|
||||
JCGlobalValue();
|
||||
|
||||
/** @brief析构函数
|
||||
*/
|
||||
~JCGlobalValue();
|
||||
|
||||
|
||||
bool reset();
|
||||
|
||||
|
||||
/** @brief save保存状态
|
||||
* @return 返回成功失败
|
||||
*/
|
||||
bool save();
|
||||
|
||||
|
||||
/** @brief 恢复函数
|
||||
* @return 返回成功失败
|
||||
*/
|
||||
bool restore();
|
||||
|
||||
public:
|
||||
|
||||
ValueDesc* getValueDesc(int nID);
|
||||
|
||||
int addValueDefine(VALUE_MODIFY_TYPE nModifyType, int nDataType, int nSize,char* pDefaultValue,int nDefaultValueSize);
|
||||
|
||||
void endValueDefine();
|
||||
|
||||
void clone( JCGlobalValue* pValueData );
|
||||
|
||||
ValueDesc* setValue(int nValueID, char* pData, VALUE_OPERATE_TYPE nOpreateType);
|
||||
|
||||
void copyValue(int nValueID, char* pData,int nDataLenght);
|
||||
|
||||
private:
|
||||
|
||||
void createDefaultValue();
|
||||
|
||||
public:
|
||||
|
||||
char* m_pCurrentValue; ///<当前的ValueData
|
||||
|
||||
public:
|
||||
|
||||
char* m_pBuffer; ///<保存的buffer
|
||||
int m_nCurrentBufferPos; ///<当前的bufferPos
|
||||
int m_nSaveDataSize; ///<存储的dataSize
|
||||
int m_nStrideSize; ///<单个save的数据长度
|
||||
std::vector<ValueDesc*> m_vValueDesc; ///<数据描述信息
|
||||
char* m_pDefaultValue; ///<数据默认值
|
||||
};
|
||||
}
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
|
||||
#endif //__JCGlobalValue_H__
|
||||
|
||||
//-----------------------------END FILE--------------------------------
|
||||
@@ -0,0 +1,204 @@
|
||||
/**
|
||||
@file JCGpuProgram.cpp
|
||||
@brief
|
||||
@author James
|
||||
@version 1.0
|
||||
@date 2017_11_28
|
||||
*/
|
||||
|
||||
#include "JCGpuProgram.h"
|
||||
#include <util/Log.h>
|
||||
#include <stdio.h>
|
||||
|
||||
namespace laya{
|
||||
|
||||
JCGpuProgramTemplate::JCGpuProgramTemplate(const char* sVS, const char* sPS, std::vector<std::string>& vBindAtrrib)
|
||||
{
|
||||
setSrc(sVS, sPS);
|
||||
m_vAttribBind = vBindAtrrib;
|
||||
}
|
||||
JCGpuProgramTemplate::~JCGpuProgramTemplate()
|
||||
{
|
||||
freeGLResource();
|
||||
for (auto& v : m_vShaderCache)
|
||||
{
|
||||
delete v.second;
|
||||
}
|
||||
m_vShaderCache.clear();
|
||||
}
|
||||
void JCGpuProgramTemplate::setSrc(const char* sVS, const char* sPS)
|
||||
{
|
||||
if (!sVS || !sPS)return;
|
||||
m_sVS = sVS;
|
||||
m_sPS = sPS;
|
||||
}
|
||||
JCGpuProgram* JCGpuProgramTemplate::getInstance(const char* sMacro)
|
||||
{
|
||||
std::map<std::string, JCGpuProgram*>::iterator iter = m_vShaderCache.find(sMacro);
|
||||
if (iter != m_vShaderCache.end())
|
||||
{
|
||||
return (*iter).second;
|
||||
}
|
||||
JCGpuProgram* pRet = new JCGpuProgram();
|
||||
pRet->m_sMacro = sMacro ? sMacro : "";
|
||||
m_vShaderCache[sMacro] = pRet;
|
||||
pRet->m_pTemplate = this;
|
||||
return pRet;
|
||||
}
|
||||
void JCGpuProgramTemplate::freeGLResource()
|
||||
{
|
||||
for (auto& v : m_vShaderCache)
|
||||
{
|
||||
(v.second)->freeGLResource();
|
||||
}
|
||||
}
|
||||
JCGpuProgram::JCGpuProgram()
|
||||
{
|
||||
m_nVS = m_nPS = m_nProgram = 0;
|
||||
m_pTemplate = NULL;
|
||||
m_pUniformDesc = NULL;
|
||||
}
|
||||
JCGpuProgram::~JCGpuProgram()
|
||||
{
|
||||
freeGLResource();
|
||||
if (m_pUniformDesc)
|
||||
{
|
||||
delete (void *)m_pUniformDesc;
|
||||
}
|
||||
}
|
||||
bool JCGpuProgram::checkCompile(int nShader, char* sDesc)
|
||||
{
|
||||
GLint compiled = 0;
|
||||
glGetShaderiv(nShader, GL_COMPILE_STATUS, &compiled);
|
||||
if (!compiled)
|
||||
{
|
||||
GLint infoLen = 0;
|
||||
glGetShaderiv(nShader, GL_INFO_LOG_LENGTH, &infoLen);
|
||||
if (infoLen)
|
||||
{
|
||||
char* buf = new char[infoLen];
|
||||
if (buf)
|
||||
{
|
||||
glGetShaderInfoLog(nShader, infoLen, NULL, buf);
|
||||
LOGE("JCGpuProgram::checkCompile Could not compile shader %s:\n%s\n", sDesc ? sDesc : "", buf);
|
||||
delete[] buf;
|
||||
}
|
||||
glDeleteShader(nShader);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
void JCGpuProgram::useProgram()
|
||||
{
|
||||
if( m_nProgram <= 0 )
|
||||
{
|
||||
compile();
|
||||
if(m_nProgram<=0)return;
|
||||
}
|
||||
glUseProgram( m_nProgram );
|
||||
}
|
||||
void JCGpuProgram::freeGLResource()
|
||||
{
|
||||
if( m_nVS>0 )
|
||||
{
|
||||
glDeleteShader(m_nVS);
|
||||
m_nVS = 0;
|
||||
}
|
||||
if( m_nPS )
|
||||
{
|
||||
glDeleteShader( m_nPS);
|
||||
m_nPS = 0;
|
||||
}
|
||||
glDeleteProgram( m_nProgram );
|
||||
m_nProgram = 0;
|
||||
}
|
||||
bool JCGpuProgramTemplate::splitKeyValue(const char* pSems, std::map<std::string, std::string>& vOut)
|
||||
{
|
||||
char strVarName[64];
|
||||
const char* pCur = pSems;
|
||||
char* pDes = strVarName;
|
||||
std::string* pSemNameInMap = nullptr;
|
||||
while (true)
|
||||
{
|
||||
if (*pCur != ',' && *pCur != 0)
|
||||
{
|
||||
*pDes++ = *pCur;
|
||||
}
|
||||
else
|
||||
{
|
||||
*pDes = 0;
|
||||
if (pSemNameInMap == nullptr)
|
||||
pSemNameInMap = &(vOut[strVarName]);
|
||||
else
|
||||
{
|
||||
*pSemNameInMap = strVarName;
|
||||
pSemNameInMap = nullptr;
|
||||
}
|
||||
pDes = strVarName;
|
||||
if (*pCur == 0)
|
||||
break;
|
||||
}
|
||||
pCur++;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
bool JCGpuProgram::compile()
|
||||
{
|
||||
int nGLVS, nGLPS;
|
||||
nGLVS = glCreateShader(GL_VERTEX_SHADER);
|
||||
const char* strShaders[2] = { m_sMacro.c_str(), m_pTemplate->m_sVS.c_str() };
|
||||
glShaderSource(nGLVS, 2, strShaders, NULL);
|
||||
glCompileShader(nGLVS);
|
||||
if (!checkCompile(nGLVS, "VS"))return false;
|
||||
nGLPS = glCreateShader(GL_FRAGMENT_SHADER);
|
||||
strShaders[1] = m_pTemplate->m_sPS.c_str();
|
||||
glShaderSource(nGLPS, 2, strShaders, NULL);
|
||||
glCompileShader(nGLPS);
|
||||
if (!checkCompile(nGLPS, "PS"))return false;
|
||||
int nProgram = glCreateProgram();
|
||||
glAttachShader(nProgram, nGLVS);
|
||||
glAttachShader(nProgram, nGLPS);
|
||||
|
||||
//bind attribute location
|
||||
for (size_t i = 0; i < m_pTemplate->m_vAttribBind.size(); i++)
|
||||
{
|
||||
glBindAttribLocation(nProgram, i, m_pTemplate->m_vAttribBind[i].c_str());
|
||||
}
|
||||
glLinkProgram(nProgram);
|
||||
GLint linkStatus = GL_FALSE;
|
||||
glGetProgramiv(nProgram, GL_LINK_STATUS, &linkStatus);
|
||||
if (linkStatus != GL_TRUE)
|
||||
{
|
||||
GLint bufLength = 0;
|
||||
glGetProgramiv(nProgram, GL_INFO_LOG_LENGTH, &bufLength);
|
||||
if (bufLength)
|
||||
{
|
||||
char* buf = new char[bufLength];
|
||||
if (buf)
|
||||
{
|
||||
glGetProgramInfoLog(nProgram, bufLength, NULL, buf);
|
||||
LOGE("JCGpuProgram::compile Could not link program:\n%s\n", buf);
|
||||
delete[] buf;
|
||||
}
|
||||
}
|
||||
glDeleteProgram(nProgram);
|
||||
nProgram = 0;
|
||||
}
|
||||
m_nVS = nGLVS;
|
||||
m_nPS = nGLPS;
|
||||
m_nProgram = nProgram;
|
||||
return true;
|
||||
}
|
||||
GLuint JCGpuProgram::getGpuProgram()
|
||||
{
|
||||
if (m_nProgram > 0)return m_nProgram;
|
||||
compile();
|
||||
return m_nProgram;
|
||||
}
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
|
||||
//-----------------------------END FILE--------------------------------
|
||||
@@ -0,0 +1,86 @@
|
||||
/**
|
||||
@file JCGpuProgram.h
|
||||
@brief
|
||||
@author James
|
||||
@version 1.0
|
||||
@date 2017_11_28
|
||||
*/
|
||||
|
||||
#ifndef __JCGpuProgram_H__
|
||||
#define __JCGpuProgram_H__
|
||||
|
||||
#if __APPLE__
|
||||
#include <OpenGLES/ES3/gl.h>
|
||||
#include <OpenGLES/ES3/glext.h>
|
||||
#else
|
||||
#include <GLES3/gl3.h>
|
||||
#endif
|
||||
#include <string>
|
||||
#include <map>
|
||||
#include <vector>
|
||||
|
||||
namespace laya
|
||||
{
|
||||
class JCNamedData;
|
||||
class JCGpuProgram;
|
||||
class JCGpuProgramTemplate
|
||||
{
|
||||
public:
|
||||
|
||||
JCGpuProgramTemplate(const char* sVS, const char* sPS, std::vector<std::string>& vBindAtrrib);
|
||||
|
||||
~JCGpuProgramTemplate();
|
||||
|
||||
void setSrc(const char* sVS, const char* sPS);
|
||||
|
||||
JCGpuProgram* getInstance(const char* sMacro);
|
||||
|
||||
void freeGLResource();
|
||||
|
||||
bool splitKeyValue(const char* sBuffer, std::map<std::string, std::string>& vOut);
|
||||
|
||||
public:
|
||||
std::string m_sVS;
|
||||
std::string m_sPS;
|
||||
std::map<std::string, JCGpuProgram*> m_vShaderCache;
|
||||
std::vector<std::string> m_vAttribBind;
|
||||
};
|
||||
|
||||
/*
|
||||
gpuProgram 是一种资源,为了恢复,需要保留源代码或者对应的文件
|
||||
*/
|
||||
class JCGpuProgram
|
||||
{
|
||||
public:
|
||||
|
||||
JCGpuProgram();
|
||||
|
||||
~JCGpuProgram();
|
||||
|
||||
bool checkCompile(int nShader, char* sDesc);
|
||||
|
||||
void freeGLResource();
|
||||
|
||||
void useProgram();
|
||||
|
||||
GLuint getGpuProgram();
|
||||
|
||||
bool compile();
|
||||
|
||||
public:
|
||||
int m_nVS;
|
||||
int m_nPS;
|
||||
JCGpuProgramTemplate* m_pTemplate;
|
||||
JCNamedData* m_pUniformDesc;
|
||||
std::string m_sMacro;
|
||||
private:
|
||||
GLuint m_nProgram;
|
||||
};
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
|
||||
#endif //__JCGpuProgram_H__
|
||||
|
||||
//-----------------------------END FILE--------------------------------
|
||||
@@ -0,0 +1,35 @@
|
||||
/**
|
||||
@file JCRegister.cpp
|
||||
@brief
|
||||
@author James
|
||||
@version 1.0
|
||||
@date 2018_6_25
|
||||
*/
|
||||
|
||||
#include "JCRegister.h"
|
||||
|
||||
namespace laya
|
||||
{
|
||||
JCRegister::JCRegister(int nRegNum)
|
||||
{
|
||||
m_nRegNum = nRegNum;
|
||||
m_vRegPool.resize(m_nRegNum);
|
||||
int nMaxSize = sizeof(float) * 16;
|
||||
for (int i = 0; i < m_nRegNum; i++)
|
||||
{
|
||||
m_vRegPool[i] = new char[nMaxSize];
|
||||
}
|
||||
}
|
||||
JCRegister::~JCRegister()
|
||||
{
|
||||
for (int i = 0; i < m_nRegNum; i++)
|
||||
{
|
||||
delete[] m_vRegPool[i];
|
||||
}
|
||||
m_vRegPool.clear();
|
||||
}
|
||||
}
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
|
||||
//-----------------------------END FILE--------------------------------
|
||||
@@ -0,0 +1,149 @@
|
||||
/**
|
||||
@file JCRegister.h
|
||||
@brief
|
||||
@author James
|
||||
@version 1.0
|
||||
@date 2018_6_25
|
||||
*/
|
||||
|
||||
#ifndef __JCRegister_H__
|
||||
#define __JCRegister_H__
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <math/Matrix32.h>
|
||||
#include "JCGlobalValue.h"
|
||||
|
||||
#if __APPLE__
|
||||
#include <OpenGLES/ES2/gl.h>
|
||||
#include <OpenGLES/ES2/glext.h>
|
||||
#else
|
||||
#include <GLES3/gl3.h>
|
||||
#include <EGL/egl.h>
|
||||
#include <EGL/eglext.h>
|
||||
#endif
|
||||
|
||||
namespace laya
|
||||
{
|
||||
enum RELATION_ZERO
|
||||
{
|
||||
RZ_LESS = 0, //小于
|
||||
RZ_EQUAL, //等于
|
||||
RZ_GREATER, //大于
|
||||
RZ_LEQUAL, //小于等于
|
||||
RZ_GEQUAL, //大于等于
|
||||
RZ_NOTEQUAL //不等于
|
||||
};
|
||||
class JCRegister
|
||||
{
|
||||
public:
|
||||
|
||||
JCRegister(int nRegNum=32);
|
||||
|
||||
virtual ~JCRegister();
|
||||
|
||||
inline char* getReg(int nIndex)
|
||||
{
|
||||
return m_vRegPool[nIndex];
|
||||
}
|
||||
|
||||
inline bool loadData(int nIndex, char* pData, int nDataSize)
|
||||
{
|
||||
char* pReg = m_vRegPool[nIndex];
|
||||
memcpy(pReg, pData, nDataSize);
|
||||
return true;
|
||||
}
|
||||
inline bool storeData(int nIndex, char* pData, int nDataSize)
|
||||
{
|
||||
if (nIndex >= m_nRegNum) return false;
|
||||
char* pReg = m_vRegPool[nIndex];
|
||||
memcpy(pData, pReg, nDataSize);
|
||||
return true;
|
||||
}
|
||||
inline bool operateReg(int nRegOut, int nReg1, int nReg2, int nSize, VALUE_OPERATE_TYPE nOperateType, int nDataType)
|
||||
{
|
||||
if (nRegOut >= m_nRegNum || nReg1 >= m_nRegNum || nReg2 >= m_nRegNum) return false;
|
||||
char* pReg1 = m_vRegPool[nReg1];
|
||||
char* pReg2 = m_vRegPool[nReg2];
|
||||
char* pRegOut = m_vRegPool[nRegOut];
|
||||
if (nDataType == GL_INT)
|
||||
{
|
||||
int* iReg1 = (int*)pReg1;
|
||||
int* iReg2 = (int*)pReg2;
|
||||
int* iRegOut = (int*)pRegOut;
|
||||
int size = nSize / sizeof(int);
|
||||
switch (nOperateType)
|
||||
{
|
||||
case VALUE_OPERATE_ADD:
|
||||
for (int i = 0; i < size; i++)iRegOut[i] = iReg1[i] + iReg2[i];
|
||||
break;
|
||||
case VALUE_OPERATE_SUB:
|
||||
for (int i = 0; i < size; i++)iRegOut[i] = iReg1[i] - iReg2[i];
|
||||
break;
|
||||
case VALUE_OPERATE_MUL:
|
||||
for (int i = 0; i < size; i++)iRegOut[i] = iReg1[i] / iReg2[i];
|
||||
break;
|
||||
case VALUE_OPERATE_DIV:
|
||||
for (int i = 0; i < size; i++)iRegOut[i] = iReg1[i] * iReg2[i];
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if (nDataType == GL_FLOAT)
|
||||
{
|
||||
float* fReg1 = (float*)pReg1;
|
||||
float* fReg2 = (float*)pReg2;
|
||||
float* fRegOut = (float*)pRegOut;
|
||||
int size = nSize / sizeof(float);
|
||||
switch (nOperateType)
|
||||
{
|
||||
case VALUE_OPERATE_ADD:
|
||||
for (int i = 0; i < size; i++)fRegOut[i] = fReg1[i] + fReg2[i];
|
||||
break;
|
||||
case VALUE_OPERATE_SUB:
|
||||
for (int i = 0; i < size; i++)fRegOut[i] = fReg1[i] - fReg2[i];
|
||||
break;
|
||||
case VALUE_OPERATE_MUL:
|
||||
for (int i = 0; i < size; i++)fRegOut[i] = fReg1[i] * fReg2[i];
|
||||
break;
|
||||
case VALUE_OPERATE_DIV:
|
||||
for (int i = 0; i < size; i++)fRegOut[i] = fReg1[i] / fReg2[i];
|
||||
break;
|
||||
case VALUE_OPERATE_M2_MUL:
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
break;
|
||||
case VALUE_OPERATE_M3_MUL:
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
break;
|
||||
case VALUE_OPERATE_M4_MUL:
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
break;
|
||||
case VALUE_OPERATE_M32_MUL:
|
||||
Matrix32::mul(fRegOut, fReg1, fReg2);
|
||||
break;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
int m_nRegNum; ///<寄存器的个数
|
||||
std::vector<char*> m_vRegPool; ///<寄存器的池子
|
||||
|
||||
};
|
||||
}
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
|
||||
#endif //__JCRegister_H__
|
||||
|
||||
//-----------------------------END FILE--------------------------------
|
||||
Reference in New Issue
Block a user