paysages : Cache system for bruneton precomputations.

git-svn-id: https://subversion.assembla.com/svn/thunderk/paysages@480 b1fd45b6-86a6-48da-8261-f70d1f35bdcc
This commit is contained in:
Michaël Lemaire 2012-12-14 16:16:09 +00:00 committed by ThunderK
parent d5dddf40e1
commit 9da260a5e8
7 changed files with 276 additions and 42 deletions

View file

@ -10,6 +10,7 @@
#include <QTranslator>
#include <QLocale>
#include <QMessageBox>
#include <QSplashScreen>
#include "basepreview.h"
#include "formclouds.h"
@ -31,12 +32,14 @@
int main(int argc, char** argv)
{
MainWindow* window;
QSplashScreen* splash;
int result;
paysagesInit();
QApplication app(argc, argv);
splash = new QSplashScreen(QPixmap("images/logo_256.png"));
splash->show();
QTranslator qtTranslator;
QTranslator myTranslator;
@ -53,10 +56,17 @@ int main(int argc, char** argv)
app.installTranslator(&qtTranslator);
}
splash->showMessage(app.tr("Preloading environment...\n(may take some time on the first launch)"), Qt::AlignCenter, Qt::white);
app.processEvents();
paysagesInit();
BasePreview::initDrawers();
window = new MainWindow();
window->show();
splash->finish(window);
delete splash;
result = app.exec();

View file

@ -8,8 +8,10 @@
#if 1
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include "../system.h"
#include "../tools/cache.h"
#include "../tools/texture.h"
/*********************** Constants ***********************/
@ -400,13 +402,10 @@ static void _getMuMuSNu(double x, double y, double r, Color dhdH, double* mu, do
/*********************** Texture precomputing ***********************/
static Texture2D* _precomputeTransmittanceTexture()
static void _precomputeTransmittanceTexture()
{
Texture2D* result;
int x, y;
result = texture2DCreate(TRANSMITTANCE_W, TRANSMITTANCE_H);
for (x = 0; x < TRANSMITTANCE_W; x++)
{
for (y = 0; y < TRANSMITTANCE_H; y++)
@ -420,20 +419,15 @@ static Texture2D* _precomputeTransmittanceTexture()
trans.g = exp(-(betaR.g * depth1 + betaMEx.y * depth2));
trans.b = exp(-(betaR.b * depth1 + betaMEx.z * depth2));
trans.a = 1.0;
texture2DSetPixel(result, x, y, trans); /* Eq (5) */
texture2DSetPixel(_transmittanceTexture, x, y, trans); /* Eq (5) */
}
}
return result;
}
static Texture2D* _precomputeIrrDeltaETexture()
static void _precomputeIrrDeltaETexture()
{
Texture2D* result;
int x, y;
result = texture2DCreate(SKY_W, SKY_H);
/* Irradiance program */
for (x = 0; x < SKY_W; x++)
{
@ -452,11 +446,9 @@ static Texture2D* _precomputeIrrDeltaETexture()
irr.b = trans.b * max(muS, 0.0);
irr.a = 1.0;
texture2DSetPixel(result, x, y, irr);
texture2DSetPixel(_irrDeltaETexture, x, y, irr);
}
}
return result;
}
static void _setLayer(int layer)
@ -735,32 +727,117 @@ static Color _sunColor(Vector3 x, double t, Vector3 v, Vector3 s, double r, doub
}
}
/*********************** Cache methods ***********************/
static int _tryLoadCache2D(Texture2D* tex, const char* tag)
{
CacheFile* cache;
int xsize, ysize;
texture2DGetSize(tex, &xsize, &ysize);
cache = cacheFileCreateAccessor("atmo-br", "png", tag, xsize, ysize, 0);
if (cacheFileIsReadable(cache))
{
texture2DLoadFromFile(tex, cacheFileGetPath(cache));
cacheFileDeleteAccessor(cache);
return 1;
}
else
{
cacheFileDeleteAccessor(cache);
return 0;
}
}
static void _saveCache2D(Texture2D* tex, const char* tag)
{
CacheFile* cache;
int xsize, ysize;
texture2DGetSize(tex, &xsize, &ysize);
cache = cacheFileCreateAccessor("atmo-br", "png", tag, xsize, ysize, 0);
if (cacheFileIsWritable(cache))
{
texture2DSaveToFile(tex, cacheFileGetPath(cache));
}
cacheFileDeleteAccessor(cache);
}
static int _tryLoadCache3D(Texture3D* tex, const char* tag)
{
CacheFile* cache;
int xsize, ysize, zsize;
texture3DGetSize(tex, &xsize, &ysize, &zsize);
cache = cacheFileCreateAccessor("atmo-br", "png", tag, xsize, ysize, zsize);
if (cacheFileIsReadable(cache))
{
texture3DLoadFromFile(tex, cacheFileGetPath(cache));
cacheFileDeleteAccessor(cache);
return 1;
}
else
{
cacheFileDeleteAccessor(cache);
return 0;
}
}
static void _saveCache3D(Texture3D* tex, const char* tag)
{
CacheFile* cache;
int xsize, ysize, zsize;
texture3DGetSize(tex, &xsize, &ysize, &zsize);
cache = cacheFileCreateAccessor("atmo-br", "png", tag, xsize, ysize, zsize);
if (cacheFileIsWritable(cache))
{
texture3DSaveToFile(tex, cacheFileGetPath(cache));
}
cacheFileDeleteAccessor(cache);
}
/*********************** Public methods ***********************/
void brunetonInit()
{
int layer, x, y, z;
int layer, x, y, z, order;
if (_transmittanceTexture == NULL) /* TEMP */
{
/* TODO Deletes */
/* computes transmittance texture T (line 1 in algorithm 4.1) */
_transmittanceTexture = _precomputeTransmittanceTexture();
_transmittanceTexture = texture2DCreate(TRANSMITTANCE_W, TRANSMITTANCE_H);
if (!_tryLoadCache2D(_transmittanceTexture, "transmittance"))
{
_precomputeTransmittanceTexture();
_saveCache2D(_transmittanceTexture, "transmittance");
}
/* computes irradiance texture deltaE (line 2 in algorithm 4.1) */
_irrDeltaETexture = _precomputeIrrDeltaETexture();
_irrDeltaETexture = texture2DCreate(SKY_W, SKY_H);
if (!_tryLoadCache2D(_irrDeltaETexture, "irradianceDeltaE"))
{
_precomputeIrrDeltaETexture();
_saveCache2D(_irrDeltaETexture, "irradianceDeltaE");
}
/* computes single scattering texture deltaS (line 3 in algorithm 4.1)
* Rayleigh and Mie separated in deltaSR + deltaSM */
_deltaSRTexture = texture3DCreate(RES_MU_S * RES_NU, RES_MU, RES_R);
_deltaSMTexture = texture3DCreate(RES_MU_S * RES_NU, RES_MU, RES_R);
if (!_tryLoadCache3D(_deltaSRTexture, "deltaSR") || !_tryLoadCache3D(_deltaSMTexture, "deltaSM"))
{
for (layer = 0; layer < RES_R; ++layer)
{
printf("%d\n", layer);
_setLayer(layer);
_inscatter1Prog(_deltaSRTexture, _deltaSMTexture);
}
_saveCache3D(_deltaSRTexture, "deltaSR");
_saveCache3D(_deltaSMTexture, "deltaSM");
}
/* copies deltaE into irradiance texture E (line 4 in algorithm 4.1) */
/* ??? all black texture ??? */
@ -769,6 +846,8 @@ void brunetonInit()
/* copies deltaS into inscatter texture S (line 5 in algorithm 4.1) */
_inscatterTexture = texture3DCreate(RES_MU_S * RES_NU, RES_MU, RES_R);
if (!_tryLoadCache3D(_inscatterTexture, "inscatter"))
{
for (x = 0; x < RES_MU_S * RES_NU; x++)
{
for (y = 0; y < RES_MU; y++)
@ -782,9 +861,11 @@ void brunetonInit()
}
}
}
_saveCache3D(_inscatterTexture, "inscatter");
}
/* loop for each scattering order (line 6 in algorithm 4.1) */
for (int order = 2; order <= 4; ++order) {
for (order = 2; order <= 4; ++order) {
/* computes deltaJ (line 7 in algorithm 4.1) */
/*glFramebufferTextureEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, deltaJTexture, 0);
@ -848,11 +929,6 @@ void brunetonInit()
}
/* DEBUG */
texture2DSaveToFile(_transmittanceTexture, "transmittance.png");
texture2DSaveToFile(_irrDeltaETexture, "irrdeltae.png");
texture3DSaveToFile(_deltaSRTexture, "deltasr.png");
texture3DSaveToFile(_deltaSMTexture, "deltasm.png");
texture3DSaveToFile(_inscatterTexture, "inscatter.png");
exit(1);
}

View file

@ -56,6 +56,8 @@ void systemInit()
_core_count = _getCoreCount();
ilInit();
iluInit();
ilOriginFunc(IL_ORIGIN_LOWER_LEFT);
ilEnable(IL_ORIGIN_SET);
}
int systemGetCoreCount()
@ -117,7 +119,10 @@ int systemLoadPictureFile(const char* filepath, PictureCallbackLoadStarted callb
{
width = ilGetInteger(IL_IMAGE_WIDTH);
height = ilGetInteger(IL_IMAGE_HEIGHT);
if (callback_start)
{
callback_start(data, width, height);
}
pixels = malloc(sizeof(ILuint) * width * height);
ilCopyPixels(0, 0, 0, width, height, 1, IL_RGBA, IL_UNSIGNED_BYTE, pixels);

View file

@ -0,0 +1,65 @@
#include <stdio.h>
#include "cache.h"
#include <stdio.h>
#include <stdlib.h>
#include "../tools.h"
struct CacheFile
{
char* filepath;
};
CacheFile* cacheFileCreateAccessor(const char* module, const char* ext, const char* tag1, int tag2, int tag3, int tag4)
{
CacheFile* result;
result = (CacheFile*)malloc(sizeof(CacheFile));
result->filepath = malloc(sizeof(char) * 501);
snprintf(result->filepath, 500, "./cache/%s-%s-%d-%d-%d.%s", module, tag1, tag2, tag3, tag4, ext);
return result;
}
void cacheFileDeleteAccessor(CacheFile* cache)
{
free(cache->filepath);
free(cache);
}
int cacheFileIsReadable(CacheFile* cache)
{
FILE* f = fopen(cache->filepath, "rb");
if (f)
{
fclose(f);
return 1;
}
else
{
return 0;
}
}
int cacheFileIsWritable(CacheFile* cache)
{
UNUSED(cache);
FILE* f = fopen("./cache/.test", "wb");
if (f)
{
fclose(f);
return 1;
}
else
{
return 0;
}
}
const char* cacheFileGetPath(CacheFile* cache)
{
return cache->filepath;
}

View file

@ -0,0 +1,24 @@
#ifndef _PAYSAGES_TOOLS_CACHE_H_
#define _PAYSAGES_TOOLS_CACHE_H_
/*
* Cache management.
*/
#ifdef __cplusplus
extern "C" {
#endif
typedef struct CacheFile CacheFile;
CacheFile* cacheFileCreateAccessor(const char* module, const char* ext, const char* tag1, int tag2, int tag3, int tag4);
void cacheFileDeleteAccessor(CacheFile* cache);
int cacheFileIsReadable(CacheFile* cache);
int cacheFileIsWritable(CacheFile* cache);
const char* cacheFileGetPath(CacheFile* cache);
#ifdef __cplusplus
}
#endif
#endif

View file

@ -26,6 +26,8 @@ Texture2D* texture2DCreate(int xsize, int ysize)
{
Texture2D* result;
assert(xsize > 0 && ysize > 0);
result = (Texture2D*)malloc(sizeof(Texture2D));
result->xsize = xsize;
result->ysize = ysize;
@ -40,6 +42,12 @@ void texture2DDelete(Texture2D* tex)
free(tex);
}
void texture2DGetSize(Texture2D* tex, int* xsize, int* ysize)
{
*xsize = tex->xsize;
*ysize = tex->ysize;
}
void texture2DSetPixel(Texture2D* tex, int x, int y, Color col)
{
assert(x >= 0 && x < tex->xsize);
@ -89,6 +97,19 @@ void texture2DSaveToFile(Texture2D* tex, const char* filepath)
systemSavePictureFile(filepath, (PictureCallbackSavePixel)texture2DGetPixel, tex, tex->xsize, tex->ysize);
}
static void _callbackTex2dLoad(Texture2D* tex, int x, int y, Color col)
{
if (x >= 0 && x < tex->xsize && y >= 0 && y < tex->ysize)
{
tex->data[y * tex->xsize + x] = col;
}
}
void texture2DLoadFromFile(Texture2D* tex, const char* filepath)
{
systemLoadPictureFile(filepath, NULL, (PictureCallbackLoadPixel)_callbackTex2dLoad, tex);
}
@ -96,6 +117,8 @@ Texture3D* texture3DCreate(int xsize, int ysize, int zsize)
{
Texture3D* result;
assert(xsize > 0 && ysize > 0 && zsize > 0);
result = (Texture3D*)malloc(sizeof(Texture3D));
result->xsize = xsize;
result->ysize = ysize;
@ -111,6 +134,13 @@ void texture3DDelete(Texture3D* tex)
free(tex);
}
void texture3DGetSize(Texture3D* tex, int* xsize, int* ysize, int* zsize)
{
*xsize = tex->xsize;
*ysize = tex->ysize;
*zsize = tex->zsize;
}
void texture3DSetPixel(Texture3D* tex, int x, int y, int z, Color col)
{
assert(x >= 0 && x < tex->xsize);
@ -167,8 +197,8 @@ static Color _callbackTex3dSave(Texture3D* tex, int x, int y)
y = y % tex->ysize;
assert(x >= 0 && x < tex->xsize);
assert(y >= 0 && y < tex->xsize);
assert(z >= 0 && z < tex->xsize);
assert(y >= 0 && y < tex->ysize);
assert(z >= 0 && z < tex->zsize);
return tex->data[z * tex->xsize * tex->ysize + y * tex->xsize + x];
}
@ -177,3 +207,19 @@ void texture3DSaveToFile(Texture3D* tex, const char* filepath)
{
systemSavePictureFile(filepath, (PictureCallbackSavePixel)_callbackTex3dSave, tex, tex->xsize, tex->ysize * tex->zsize);
}
static void _callbackTex3dLoad(Texture3D* tex, int x, int y, Color col)
{
int z = y / tex->ysize;
y = y % tex->ysize;
if (x >= 0 && x < tex->xsize && y >= 0 && y < tex->ysize && z >= 0 && z < tex->zsize)
{
tex->data[z * tex->xsize * tex->ysize + y * tex->xsize + x] = col;
}
}
void texture3DLoadFromFile(Texture3D* tex, const char* filepath)
{
systemLoadPictureFile(filepath, NULL, (PictureCallbackLoadPixel)_callbackTex3dLoad, tex);
}

View file

@ -1,6 +1,10 @@
#ifndef _PAYSAGES_TOOLS_TEXTURE_H_
#define _PAYSAGES_TOOLS_TEXTURE_H_
/*
* Pixel based textures.
*/
#ifdef __cplusplus
extern "C" {
#endif
@ -12,21 +16,25 @@ typedef struct Texture3D Texture3D;
Texture2D* texture2DCreate(int xsize, int ysize);
void texture2DDelete(Texture2D* tex);
void texture2DGetSize(Texture2D* tex, int* xsize, int* ysize);
void texture2DSetPixel(Texture2D* tex, int x, int y, Color col);
Color texture2DGetPixel(Texture2D* tex, int x, int y);
Color texture2DGetNearest(Texture2D* tex, double dx, double dy);
Color texture2DGetLinear(Texture2D* tex, double dx, double dy);
Color texture2DGetCubic(Texture2D* tex, double dx, double dy);
void texture2DSaveToFile(Texture2D* tex, const char* filepath);
void texture2DLoadFromFile(Texture2D* tex, const char* filepath);
Texture3D* texture3DCreate(int xsize, int ysize, int zsize);
void texture3DDelete(Texture3D* tex);
void texture3DGetSize(Texture3D* tex, int* xsize, int* ysize, int* zsize);
void texture3DSetPixel(Texture3D* tex, int x, int y, int z, Color col);
Color texture3DGetPixel(Texture3D* tex, int x, int y, int z);
Color texture3DGetNearest(Texture3D* tex, double dx, double dy, double dz);
Color texture3DGetLinear(Texture3D* tex, double dx, double dy, double dz);
Color texture3DGetCubic(Texture3D* tex, double dx, double dy, double dz);
void texture3DSaveToFile(Texture3D* tex, const char* filepath);
void texture3DLoadFromFile(Texture3D* tex, const char* filepath);
#ifdef __cplusplus
}