Commit 22b98fe9 authored by David Llewellyn-Jones's avatar David Llewellyn-Jones

Function shaders, variables and transforms introduced to support shadow rendering.

parent 384783a1
......@@ -559,9 +559,41 @@ char * CartesianGenerateFragmentShader (FuncPersist * psFuncData) {
return szShader;
}
char * CartesianGenerateVertexShaderShadow (FuncPersist * psFuncData) {
char * szShader;
//CartesianPersist * psCartesianData = psFuncData->Func.psCartesianData;
if (psFuncData->szShaderShadowVertexSource) {
szShader = ReplaceTextCopy (psFuncData->szShaderShadowVertexSource, "function", psFuncData->szShaderFunction->str);
}
else {
szShader = NULL;
}
return szShader;
}
char * CartesianGenerateFragmentShaderShadow (FuncPersist * psFuncData) {
char * szShader;
//CartesianPersist * psCartesianData = psFuncData->Func.psCartesianData;
if (psFuncData->szShaderShadowFragmentSource) {
szShader = CopyText (psFuncData->szShaderShadowFragmentSource);
}
else {
szShader = NULL;
}
return szShader;
}
void CartesianInitShader (FuncPersist * psFuncData) {
LoadVertexShader (FUNCTYDIR "/cartesian.vs", psFuncData);
LoadFragmentShader (FUNCTYDIR "/cartesian.fs", psFuncData);
LoadVertexShaderShadow (FUNCTYDIR "/cartesian-shadow.vs", psFuncData);
LoadFragmentShaderShadow (FUNCTYDIR "/cartesian-shadow.fs", psFuncData);
FunctionShadersRegenerate (psFuncData);
}
......@@ -571,6 +603,13 @@ void CartesianSetShaderActive (bool boActive, FuncPersist * psFuncData) {
CartesianPopulateVertices (psFuncData);
}
void CartesianSetShaderShadowActive (bool boActive, FuncPersist * psFuncData) {
SetShaderActive (boActive, psFuncData->psShaderShadowData);
// TODO: Check whether we actually need to do this
CartesianPopulateVertices (psFuncData);
}
void CartesianUpdateCentre (FuncPersist * psFuncData) {
// Do nothing
}
......
......@@ -41,8 +41,11 @@ void CartesianGenerateVertices (FuncPersist * psFuncData);
void CartesianSetFunctionPosition (double fXMin, double fYMin, double fZMin, FuncPersist * psFuncData);
char * CartesianGenerateVertexShader (FuncPersist * psFuncData);
char * CartesianGenerateFragmentShader (FuncPersist * psFuncData);
char * CartesianGenerateVertexShaderShadow (FuncPersist * psFuncData);
char * CartesianGenerateFragmentShaderShadow (FuncPersist * psFuncData);
void CartesianInitShader (FuncPersist * psFuncData);
void CartesianSetShaderActive (bool boActive, FuncPersist * psFuncData);
void CartesianSetShaderShadowActive (bool boActive, FuncPersist * psFuncData);
void CartesianUpdateCentre (FuncPersist * psFuncData);
void CartesianSetFunctionCentre (char const * const szXCentre, char const * const szYCentre, char const * const szZCentre, FuncPersist * psFuncData);
void CartesianGetCentre (double * afCentre, FuncPersist const * psFuncData);
......
......@@ -1083,9 +1083,53 @@ char * CurveGenerateFragmentShader (FuncPersist * psFuncData) {
return szShader;
}
char * CurveGenerateVertexShaderShadow (FuncPersist * psFuncData) {
char * szShader;
CurvePersist * psCurveData = psFuncData->Func.psCurveData;
if (psFuncData->szShaderShadowVertexSource) {
szShader = ReplaceTextCopy (psFuncData->szShaderShadowVertexSource, "function", psFuncData->szShaderFunction->str);
szShader = ReplaceTextMove (szShader, "curveX", psCurveData->szShaderCurveX->str);
szShader = ReplaceTextMove (szShader, "curveY", psCurveData->szShaderCurveY->str);
szShader = ReplaceTextMove (szShader, "curveZ", psCurveData->szShaderCurveZ->str);
szShader = ReplaceTextMove (szShader, "diffAX", psCurveData->szShaderDiffWrtAX->str);
szShader = ReplaceTextMove (szShader, "diffAY", psCurveData->szShaderDiffWrtAY->str);
szShader = ReplaceTextMove (szShader, "diffAZ", psCurveData->szShaderDiffWrtAZ->str);
szShader = ReplaceTextMove (szShader, "diff2AX", psCurveData->szShaderDiff2WrtAX->str);
szShader = ReplaceTextMove (szShader, "diff2AY", psCurveData->szShaderDiff2WrtAY->str);
szShader = ReplaceTextMove (szShader, "diff2AZ", psCurveData->szShaderDiff2WrtAZ->str);
}
else {
szShader = NULL;
}
return szShader;
}
char * CurveGenerateFragmentShaderShadow (FuncPersist * psFuncData) {
char * szShader;
//CurvePersist * psCurveData = psFuncData->Func.psCurveData;
if (psFuncData->szShaderShadowFragmentSource) {
szShader = CopyText (psFuncData->szShaderShadowFragmentSource);
}
else {
szShader = NULL;
}
return szShader;
}
void CurveInitShader (FuncPersist * psFuncData) {
LoadVertexShader (FUNCTYDIR "/curve.vs", psFuncData);
LoadFragmentShader (FUNCTYDIR "/curve.fs", psFuncData);
LoadVertexShaderShadow (FUNCTYDIR "/curve-shadow.vs", psFuncData);
LoadFragmentShaderShadow (FUNCTYDIR "/curve-shadow.fs", psFuncData);
FunctionShadersRegenerate (psFuncData);
}
......@@ -1095,6 +1139,13 @@ void CurveSetShaderActive (bool boActive, FuncPersist * psFuncData) {
CurvePopulateVertices (psFuncData);
}
void CurveSetShaderShadowActive (bool boActive, FuncPersist * psFuncData) {
SetShaderActive (boActive, psFuncData->psShaderShadowData);
// TODO: Check whether we actually need to do this
CurvePopulateVertices (psFuncData);
}
void CurveSetFunctionAccuracyRadius (double fAccuracy, FuncPersist * psFuncData) {
CurvePersist * psCurveData = psFuncData->Func.psCurveData;
......
......@@ -46,8 +46,11 @@ char const * CurveGetRadiusString (FuncPersist * psFuncData);
void CurveSetFunctionPosition (double fXMin, double fYMin, double fZMin, FuncPersist * psFuncData);
char * CurveGenerateVertexShader (FuncPersist * psFuncData);
char * CurveGenerateFragmentShader (FuncPersist * psFuncData);
char * CurveGenerateVertexShaderShadow (FuncPersist * psFuncData);
char * CurveGenerateFragmentShaderShadow (FuncPersist * psFuncData);
void CurveInitShader (FuncPersist * psFuncData);
void CurveSetShaderActive (bool boActive, FuncPersist * psFuncData);
void CurveSetShaderShadowActive (bool boActive, FuncPersist * psFuncData);
void CurveSetFunctionAccuracyRadius (double fAccuracy, FuncPersist * psFuncData);
double CurveGetFunctionAccuracyRadius (FuncPersist * psFuncData);
char const * CurveGetXCentreString (FuncPersist * psFuncData);
......
......@@ -32,7 +32,6 @@
// Function prototypes
void GenerateVertices (FuncPersist * psFuncData);
char * ShaderAddControlVars (char * szShader, FnControlPersist * psFnControlData, FuncPersist * psFuncData);
///////////////////////////////////////////////////////////////////
// Function definitions
......@@ -66,6 +65,9 @@ FuncPersist * NewFuncPersist (FUNCTYPE eType) {
psFuncData->fZWidth = 40.0;
psFuncData->fAccuracy = ACCURACY_NEW;
MatrixSetIdentity4 (& psFuncData->mStructureTransform);
psFuncData->afVertices = NULL;
psFuncData->afNormals = NULL;
psFuncData->auIndices = NULL;
......@@ -109,6 +111,10 @@ FuncPersist * NewFuncPersist (FUNCTYPE eType) {
psFuncData->szShaderBlue = g_string_new ("1");
psFuncData->szShaderAlpha = g_string_new ("1");
psFuncData->psShaderShadowData = NULL;
psFuncData->szShaderShadowVertexSource = NULL;
psFuncData->szShaderShadowFragmentSource = NULL;
psFuncData->psFnControlData = NULL;
InitShader (psFuncData);
......@@ -118,6 +124,9 @@ FuncPersist * NewFuncPersist (FUNCTYPE eType) {
GenerateVertices (psFuncData);
PopulateVertices (psFuncData);
// Shadow data
psFuncData->psShadowData = NULL;
return psFuncData;
}
......@@ -228,13 +237,35 @@ void DeleteFuncPersist (FuncPersist * psFuncData) {
g_string_free (psFuncData->szShaderAlpha, TRUE);
}
if (psFuncData->psShaderShadowData) {
DeleteShaderPersist (psFuncData->psShaderShadowData);
psFuncData->psShaderShadowData = NULL;
}
if (psFuncData->szShaderShadowVertexSource) {
g_free (psFuncData->szShaderShadowVertexSource);
psFuncData->szShaderShadowVertexSource = NULL;
}
if (psFuncData->szShaderShadowFragmentSource) {
g_free (psFuncData->szShaderShadowFragmentSource);
psFuncData->szShaderShadowFragmentSource = NULL;
}
// Clear the shadow data (will be freed in vis)
psFuncData->psShadowData = NULL;
g_free (psFuncData);
}
void InitShader (FuncPersist * psFuncData) {
if (psFuncData->psShaderData == NULL) {
psFuncData->psShaderData = NewShaderPersist ();
SetShaderControlVars (psFuncData->psFnControlData, psFuncData->psShaderData);
//SetShaderControlVars (psFuncData->psFnControlData, psFuncData->psShaderData);
}
if (psFuncData->psShaderShadowData == NULL) {
psFuncData->psShaderShadowData = NewShaderPersist ();
}
switch (psFuncData->eType) {
......@@ -259,6 +290,10 @@ void SetFunctionControlVars (FnControlPersist * psFnControlData, FuncPersist * p
if (psFuncData->psShaderData) {
SetShaderControlVars (psFnControlData, psFuncData->psShaderData);
}
if (psFuncData->psShaderShadowData) {
SetShaderControlVars (psFnControlData, psFuncData->psShaderShadowData);
}
}
void LoadVertexShader (char const * const szFilename, FuncPersist * psFuncData) {
......@@ -281,6 +316,27 @@ void LoadFragmentShader (char const * const szFilename, FuncPersist * psFuncData
psFuncData->szShaderFragmentSource = LoadShaderFile (szFilename);
}
void LoadVertexShaderShadow (char const * const szFilename, FuncPersist * psFuncData) {
// Free up any previously loaded shadow shader source
if (psFuncData->szShaderShadowVertexSource) {
g_free (psFuncData->szShaderShadowVertexSource);
psFuncData->szShaderShadowVertexSource = NULL;
}
psFuncData->szShaderShadowVertexSource = LoadShaderFile (szFilename);
}
void LoadFragmentShaderShadow (char const * const szFilename, FuncPersist * psFuncData) {
// Free up any previously loaded shadow shader source
if (psFuncData->szShaderShadowFragmentSource) {
g_free (psFuncData->szShaderShadowFragmentSource);
psFuncData->szShaderShadowFragmentSource = NULL;
}
psFuncData->szShaderShadowFragmentSource = LoadShaderFile (szFilename);
}
void ActivateFunctionShader (FuncPersist * psFuncData) {
ActivateShader (psFuncData->psShaderData);
}
......@@ -289,6 +345,14 @@ void DeactivateFunctionShader (FuncPersist * psFuncData) {
DeactivateShader (psFuncData->psShaderData);
}
void ActivateFunctionShaderShadow (FuncPersist * psFuncData) {
ActivateShader (psFuncData->psShaderShadowData);
}
void DeactivateFunctionShaderShadow (FuncPersist * psFuncData) {
DeactivateShader (psFuncData->psShaderShadowData);
}
void SetFunctionShaderActive (bool boActive, FuncPersist * psFuncData) {
switch (psFuncData->eType) {
case FUNCTYPE_CARTESIAN:
......@@ -306,6 +370,23 @@ void SetFunctionShaderActive (bool boActive, FuncPersist * psFuncData) {
}
}
void SetFunctionShaderShadowActive (bool boActive, FuncPersist * psFuncData) {
switch (psFuncData->eType) {
case FUNCTYPE_CARTESIAN:
CartesianSetShaderShadowActive (boActive, psFuncData);
break;
case FUNCTYPE_SPHERICAL:
SphericalSetShaderShadowActive (boActive, psFuncData);
break;
case FUNCTYPE_CURVE:
CurveSetShaderShadowActive (boActive, psFuncData);
break;
default:
// Do absolutely nothing
break;
}
}
void SetFunction (char const * const szFunction, FuncPersist * psFuncData) {
switch (psFuncData->eType) {
case FUNCTYPE_CARTESIAN:
......@@ -364,7 +445,7 @@ void FunctionShadersRegenerate (FuncPersist * psFuncData) {
// Do absolutely nothing
break;
}
szShader = ShaderAddControlVars (szShader, psFuncData->psFnControlData, psFuncData);
szShader = ShaderAddControlVars (szShader, psFuncData->psShaderData);
ShaderRegenerateVertex (szShader, psFuncData->psShaderData);
if (szShader) {
......@@ -387,16 +468,64 @@ void FunctionShadersRegenerate (FuncPersist * psFuncData) {
// Do absolutely nothing
break;
}
szShader = ShaderAddControlVars (szShader, psFuncData->psFnControlData, psFuncData);
szShader = ShaderAddControlVars (szShader, psFuncData->psShaderData);
ShaderRegenerateFragment (szShader, psFuncData->psShaderData);
if (szShader) {
g_free (szShader);
szShader = NULL;
}
printf ("Shaders regenerated.\n");
}
if (psFuncData->psShaderShadowData) {
// Generate a vertex shader
switch (psFuncData->eType) {
case FUNCTYPE_CARTESIAN:
szShader = CartesianGenerateVertexShaderShadow (psFuncData);
break;
case FUNCTYPE_SPHERICAL:
szShader = SphericalGenerateVertexShaderShadow (psFuncData);
break;
case FUNCTYPE_CURVE:
szShader = CurveGenerateVertexShaderShadow (psFuncData);
break;
default:
// Do absolutely nothing
break;
}
szShader = ShaderAddControlVars (szShader, psFuncData->psShaderShadowData);
ShaderRegenerateVertex (szShader, psFuncData->psShaderShadowData);
if (szShader) {
g_free (szShader);
szShader = NULL;
}
// Generate a fragment shader
switch (psFuncData->eType) {
case FUNCTYPE_CARTESIAN:
szShader = CartesianGenerateFragmentShaderShadow (psFuncData);
break;
case FUNCTYPE_SPHERICAL:
szShader = SphericalGenerateFragmentShaderShadow (psFuncData);
break;
case FUNCTYPE_CURVE:
szShader = CurveGenerateFragmentShaderShadow (psFuncData);
break;
default:
// Do absolutely nothing
break;
}
szShader = ShaderAddControlVars (szShader, psFuncData->psShaderShadowData);
ShaderRegenerateFragment (szShader, psFuncData->psShaderShadowData);
if (szShader) {
g_free (szShader);
szShader = NULL;
}
printf ("Shadow shaders regenerated.\n");
}
}
char const * GetFunctionString (FuncPersist * psFuncData) {
......@@ -858,6 +987,22 @@ int CountStoredFaces (double fMultiplier, FuncPersist const * psFuncData) {
return nFaces;
}
void RecentreGraph (FuncPersist * psFuncData) {
GLdouble afCentre[3];
Vector3 vTranslate;
double afRange[6];
GetCentre (afCentre, psFuncData);
GetFunctionRange (afRange, psFuncData);
vTranslate.fX = (((afCentre[0] - afRange[0]) * (2 * AXIS_XHSIZE)) / (afRange[3]));
vTranslate.fY = (((afCentre[1] - afRange[1]) * (2 * AXIS_YHSIZE)) / (afRange[4]));
vTranslate.fZ = (((afCentre[2] - afRange[2]) * (2 * AXIS_ZHSIZE)) / (afRange[5]));
glTranslatef (vTranslate.fX, vTranslate.fY, vTranslate.fZ);
MatrixTranslate4 (& psFuncData->mStructureTransform, & vTranslate);
}
void AssignControlVarsToFunction (FnControlPersist * psFnControlData, FuncPersist * psFuncData) {
AssignControlVarsToVariables (psFuncData->psVariables, psFnControlData);
......@@ -903,31 +1048,16 @@ void AssignControlVarsToFunctionPopulate (FnControlPersist * psFnControlData, Fu
}
}
char * ShaderAddControlVars (char * szShader, FnControlPersist * psFnControlData, FuncPersist * psFuncData) {
GString * szControlVarBlock;
char const * szVarName;
GSList * psControlvarList;
if (psFnControlData) {
szControlVarBlock = g_string_new ("");
// First check whether the varaible is already there
psControlvarList = psFnControlData->psControlvarList;
while (psControlvarList) {
szVarName = GetControlvarName (((ControlvarPersist *)(psControlvarList->data)));
g_string_append_printf (szControlVarBlock, "uniform float %s;\n", szVarName);
psControlvarList = g_slist_next (psControlvarList);
}
void SetFunctionShadowData (ShadowPersist * psShadowData, FuncPersist * psFuncData) {
psFuncData->psShadowData = psShadowData;
}
if (szShader) {
szShader = ReplaceTextMove (szShader, "controlvars", szControlVarBlock->str);
}
g_string_free (szControlVarBlock, TRUE);
}
void SetFunctionTransform (Matrix4 const * pmTransform, FuncPersist * psFuncData) {
psFuncData->mStructureTransform = *pmTransform;
}
return szShader;
Matrix4 * GetFunctionTransform (FuncPersist * psFuncData) {
return & psFuncData->mStructureTransform;
}
......
......@@ -16,6 +16,7 @@
#include "recall.h"
#include "controlvar.h"
#include "shadow.h"
///////////////////////////////////////////////////////////////////
// Defines
......@@ -80,8 +81,11 @@ GLuint GetFunctionTexture (FuncPersist * psFuncData);
void SetTextureValues (char const * const szFilename, char const * const szXScale, char const * const szYScale, char const * const szXOffset, char const * const szYOffset, FuncPersist * psFuncData);
void InitShader (FuncPersist * psFuncData);
void SetFunctionShaderActive (bool boActive, FuncPersist * psFuncData);
void SetFunctionShaderShadowActive (bool boActive, FuncPersist * psFuncData);
void ActivateFunctionShader (FuncPersist * psFuncData);
void DeactivateFunctionShader (FuncPersist * psFuncData);
void ActivateFunctionShaderShadow (FuncPersist * psFuncData);
void DeactivateFunctionShaderShadow (FuncPersist * psFuncData);
void FunctionShadersRegenerate (FuncPersist * psFuncData);
void UpdateCentre (FuncPersist * psFuncData);
void SetFunctionCentre (char const * const szXCentre, char const * const szYCentre, char const * const szZCentre, FuncPersist * psFuncData);
......@@ -93,9 +97,13 @@ int OutputStoredVertices (Recall * hFile, bool boBinary, bool boScreenCoords, bo
int OutputStoredIndices (Recall * hFile, bool boBinary, double fMultiplier, int nOffset, FuncPersist const * psFuncData);
int CountStoredVertices (double fMultiplier, FuncPersist const * psFuncData);
int CountStoredFaces (double fMultiplier, FuncPersist const * psFuncData);
void RecentreGraph (FuncPersist * psFuncData);
void AssignControlVarsToFunction (FnControlPersist * psFnControlData, FuncPersist * psFuncData);
void AssignControlVarsToFunctionPopulate (FnControlPersist * psFnControlData, FuncPersist * psFuncData);
void SetFunctionControlVars (FnControlPersist * psFnControlData, FuncPersist * psFuncData);
void SetFunctionShadowData (ShadowPersist * psShadowData, FuncPersist * psFuncData);
void SetFunctionTransform (Matrix4 const * pmTransform, FuncPersist * psFuncData);
Matrix4 * GetFunctionTransform (FuncPersist * psFuncData);
///////////////////////////////////////////////////////////////////
// Function definitions
......
......@@ -46,6 +46,7 @@ struct _FuncPersist {
// The following relate to screen coordinates
double fAccuracy;
Matrix4 mStructureTransform;
// The actual function
Operation * psFunction;
......@@ -97,9 +98,15 @@ struct _FuncPersist {
GString * szShaderGreen;
GString * szShaderBlue;
GString * szShaderAlpha;
char * szShaderShadowVertexSource;
char * szShaderShadowFragmentSource;
ShaderPersist * psShaderShadowData;
// Control variables - this is only a pointer, do doesn't need to be freed
FnControlPersist * psFnControlData;
// Shadow variables
ShadowPersist * psShadowData;
};
///////////////////////////////////////////////////////////////////
......@@ -111,6 +118,9 @@ struct _FuncPersist {
void LoadVertexShader (char const * const szFilename, FuncPersist * psFuncData);
void LoadFragmentShader (char const * const szFilename, FuncPersist * psFuncData);
void FreeVertexBuffers (FuncPersist * psFuncData);
void LoadVertexShaderShadow (char const * const szFilename, FuncPersist * psFuncData);
void LoadFragmentShaderShadow (char const * const szFilename, FuncPersist * psFuncData);
///////////////////////////////////////////////////////////////////
// Function definitions
......
......@@ -389,4 +389,47 @@ GLuint GetShaderProgram (ShaderPersist * psShaderData) {
return psShaderData->uProgram;
}
char * CopyText (char const * const szText) {
int nTextLen;
char * szNewCopy;
nTextLen = 0;
while (szText[nTextLen] != '\0') {
nTextLen++;
}
szNewCopy = (char *)malloc (nTextLen + 1);
strncpy (szNewCopy, szText, nTextLen);
szNewCopy[nTextLen] = '\0';
return szNewCopy;
}
char * ShaderAddControlVars (char * szShader, ShaderPersist * psShaderData) {
GString * szControlVarBlock;
char const * szVarName;
GSList * psControlvarList;
if (psShaderData->psFnControlData) {
szControlVarBlock = g_string_new ("");
// First check whether the varaible is already there
psControlvarList = psShaderData->psFnControlData->psControlvarList;
while (psControlvarList) {
szVarName = GetControlvarName (((ControlvarPersist *)(psControlvarList->data)));
g_string_append_printf (szControlVarBlock, "uniform float %s;\n", szVarName);
psControlvarList = g_slist_next (psControlvarList);
}
if (szShader) {
szShader = ReplaceTextMove (szShader, "controlvars", szControlVarBlock->str);
}
g_string_free (szControlVarBlock, TRUE);
}
return szShader;
}
......@@ -39,8 +39,10 @@ bool GetShaderActive (ShaderPersist * psShaderData);
char * LoadShaderFile (char const * const szFilename);
char * ReplaceTextCopy (char const * const szText, char const * const szToken, char const * const szReplace);
char * ReplaceTextMove (char * szText, char const * const szToken, char const * const szReplace);
char * CopyText (char const * const szText);
GLuint GetShaderProgram (ShaderPersist * psShaderData);
void SetShaderControlVars (FnControlPersist * psFnControlData, ShaderPersist * psShaderData);
char * ShaderAddControlVars (char * szShader, ShaderPersist * psShaderData);
#endif /* SHADER_H */
......@@ -745,9 +745,41 @@ char * SphericalGenerateFragmentShader (FuncPersist * psFuncData) {
return szShader;
}
char * SphericalGenerateVertexShaderShadow (FuncPersist * psFuncData) {
char * szShader;
//SphericalPersist * psSphericalData = psFuncData->Func.psSphericalData;
if (psFuncData->szShaderShadowVertexSource) {
szShader = ReplaceTextCopy (psFuncData->szShaderShadowVertexSource, "function", psFuncData->szShaderFunction->str);
}
else {
szShader = NULL;
}
return szShader;
}
char * SphericalGenerateFragmentShaderShadow (FuncPersist * psFuncData) {
char * szShader;
//SphericalPersist * psSphericalData = psFuncData->Func.psSphericalData;
if (psFuncData->szShaderShadowFragmentSource) {
szShader = CopyText (psFuncData->szShaderShadowFragmentSource);
}
else {
szShader = NULL;
}
return szShader;
}
void SphericalInitShader (FuncPersist * psFuncData) {
LoadVertexShader (FUNCTYDIR "/spherical.vs", psFuncData);
LoadFragmentShader (FUNCTYDIR "/spherical.fs", psFuncData);
LoadVertexShaderShadow (FUNCTYDIR "/spherical-shadow.vs", psFuncData);
LoadFragmentShaderShadow (FUNCTYDIR "/spherical-shadow.fs", psFuncData);
FunctionShadersRegenerate (psFuncData);
}
......@@ -757,6 +789,13 @@ void SphericalSetShaderActive (bool boActive, FuncPersist * psFuncData) {
SphericalPopulateVertices (psFuncData);
}
void SphericalSetShaderShadowActive (bool boActive, FuncPersist * psFuncData) {
SetShaderActive (boActive, psFuncData->psShaderShadowData);
// TODO: Check whether we actually need to do this
SphericalPopulateVertices (psFuncData);
}
int SphericalOutputStoredVertices (Recall * hFile, bool boBinary, bool boScreenCoords, bool boExportAlpha, double fMultiplier, double fScale, FuncPersist const * psFuncData) {
SphericalPersist * psSphericalData = psFuncData->Func.psSphericalData;
int nVertex;
......
......@@ -49,8 +49,11 @@ void SphericalSetFunctionTime (double fTime, FuncPersist * psFuncData);
void SphericalSetFunctionPosition (double fXMin, double fYMin, double fZMin, FuncPersist * psFuncData);
char * SphericalGenerateVertexShader (FuncPersist * psFuncData);
char * SphericalGenerateFragmentShader (FuncPersist * psFuncData);
char * SphericalGenerateVertexShaderShadow (FuncPersist * psFuncData);
char * SphericalGenerateFragmentShaderShadow (FuncPersist * psFuncData);
void SphericalInitShader (FuncPersist * psFuncData);
void SphericalSetShaderActive (bool boActive, FuncPersist * psFuncData);
void SphericalSetShaderShadowActive (bool boActive, FuncPersist * psFuncData);
int SphericalOutputStoredVertices (Recall * hFile, bool boBinary, bool boScreenCoords, bool boExportAlpha, double fMultiplier, double fScale, FuncPersist const * psFuncData);
int SphericalOutputStoredIndices (Recall * hFile, bool boBinary, double fMultiplier, int nOffset, FuncPersist const * psFuncData);
int SphericalCountStoredVertices (double fMultiplier, FuncPersist const * psFuncData);
......
......@@ -274,4 +274,136 @@ void MultMatrixMatrix4 (Matrix4 * pmResult, Matrix4 const * pm1, Matrix4 const *
}
}
void MatrixCopy4 (Matrix4 * pmTo, Matrix4 * pmFrom) {
int nRow;
int nCol;
for (nRow = 0; nRow < 4; nRow++) {
for (nCol = 0; nCol < 4; nCol++) {
pmTo->aafM[nRow][nCol] = pmFrom->aafM[nRow][nCol];
}
}
}
void MatrixSetIdentity4 (Matrix4 * pm1) {
int nRow;
int nCol;
for (nRow = 0; nRow < 4; nRow++) {
for (nCol = 0; nCol < 4; nCol++) {
pm1->aafM[nRow][nCol] = (nRow == nCol);
}
}
}
void MatrixTranslate4 (Matrix4 * pm1, Vector3 const * pvTranslate) {
Matrix4 mTranslate;
Matrix4 mOriginal;
MatrixSetIdentity4 (& mTranslate);
mTranslate.aafM[3][0] = pvTranslate->fX;
mTranslate.aafM[3][1] = pvTranslate->fY;
mTranslate.aafM[3][2] = pvTranslate->fZ;
MatrixCopy4 (& mOriginal, pm1);
MultMatrixMatrix4 (pm1, & mOriginal, & mTranslate);
}
void MatrixScale4 (Matrix4 * pm1, Vector3 const * pvScale) {
Matrix4 mScale;
Matrix4 mOriginal;
int nRow;
int nCol;
for (nRow = 0; nRow < 4; nRow++) {
for (nCol = 0; nCol < 4; nCol++) {
if (nRow == nCol) {
if (nRow < 3) {
mScale.aafM[nRow][nCol] = pvScale->afV[nRow];
}
else {
mScale.aafM[nRow][nCol] = 1.0f;
}
}
else {
mScale.aafM[nRow][nCol] = 0.0f;
}
}
}
MatrixCopy4 (& mOriginal, pm1);
MultMatrixMatrix4 (pm1, & mOriginal, & mScale);
}
void MatrixRotate4 (Matrix4 * pm1, float fAngle, Vector3 const * pvAxis) {
float fCosine;
float fSine;
Vector3 vNormal;
Matrix4 mRotate;
Matrix4 mOriginal;
vNormal.fX = pvAxis->fX;
vNormal.fY = pvAxis->fY;
vNormal.fZ = pvAxis->fZ;
Normalise (& vNormal);
fCosine = cos (fAngle * M_PI / 180.0f);
fSine = sin (fAngle * M_PI / 180.0f);
mRotate.aafM[0][0] = (vNormal.fX * vNormal.fX * (1.0f - fCosine)) + (fCosine);
mRotate.aafM[0][1] = (vNormal.fY * vNormal.fX * (1.0f - fCosine)) + (vNormal.fZ * fSine);
mRotate.aafM[0][2] = (vNormal.fZ * vNormal.fX * (1.0f - fCosine)) - (vNormal.fY * fSine);
mRotate.aafM[0][3] = 0.0f;
mRotate.aafM[1][0] = (vNormal.fX * vNormal.fY * (1.0f - fCosine)) - (vNormal.fZ * fSine);
mRotate.aafM[1][1] = (vNormal.fY * vNormal.fY * (1.0f - fCosine)) + (fCosine);
mRotate.aafM[1][2] = (vNormal.fZ * vNormal.fY * (1.0f - fCosine)) + (vNormal.fX * fSine);
mRotate.aafM[1][3] = 0.0f;
mRotate.aafM[2][0] = (vNormal.fX * vNormal.fZ * (1.0f - fCosine)) + (vNormal.fY * fSine);
mRotate.aafM[2][1] = (vNormal.fY * vNormal.fZ * (1.0f - fCosine)) - (vNormal.fX * fSine);
mRotate.aafM[2][2] = (vNormal.fZ * vNormal.fZ * (1.0f - fCosine)) + (fCosine);
mRotate.aafM[2][3] = 0.0f;