ATMOsphere
Well, there is no license, it is free to use or edit. I just want to keep credits that i wrote original. BTW, sun calculation formulas are not mine, credits are in source. I would like to see it in irrExt if someone could update it.
My project in forum- ATMOsphere - new dynamic sky dome for Irrlicht
under irrlicht sdk 1.6.1 under linux
ATOMSphere.cpp
main.cpp
makefile
hope this helps someone, a bit resource hungry for me only 300fps but no models are rendered yet even
ATOMSphere.cpp
Code: Select all
/*
Autor: Jonas Abramavicius aka Pazystamo
Unfinished version
2006 06 01
*/
#include <irrlicht.h>
#include <IVideoDriver.h>
#include <math.h>
#include <ITimer.h>
using namespace irr;
using namespace scene;
using namespace video;
using namespace core;
class CATMOskySceneNode : public scene::ISceneNode
{
core::aabbox3d<f32> Box;
video::S3DVertex *Vertices;
video::SMaterial Material;
u16 *indices;
s32 vert;//number of vertices
s32 face;//number of faces
f32 posX,sizeX;
f32 uvX;
public:
CATMOskySceneNode(video::ITexture* tex,scene::ISceneNode* parent, scene::ISceneManager* mgr,s32 faces, s32 id)
: scene::ISceneNode(parent, mgr, id)
{
//AutomaticCullingEnabled = false;
video::SMaterial mat;
mat.Lighting = false;
//mat.Wireframe = true;
mat.ZBuffer = false;
//mat.ZWriteEnable = false;
mat.setFlag(EMF_BILINEAR_FILTER,true);
//mat.NormalizeNormals=true;
//mat.AnisotropicFilter=true;
//mat.GouraudShading=false;
//mat.TrilinearFilter = true;
//mat.BackfaceCulling = false;
face=faces;
Vertices = new video::S3DVertex[face+1];
indices = new u16[face*3];
Material = mat;
Material.setTexture(0,tex);
f64 angle = 0.0f; //start positions
f64 angle2 = 360.0f/face; //angle to add
vert=0; //vertice nr
s32 nr = -3; //indices nr
//top vertice
Vertices[0]=video::S3DVertex(0.0f, 100.0f, -0.0f,
0.0568988f, 0.688538f, -0.722965f,
video::SColor(255,255,255,255), 0.0f, 0.1f);
for (u16 n=1;n<face+1;n++){
vert=vert+1;
nr=nr+3; //indices number
f64 x=cos(angle*0.017453292519943295769236907684886f)*100;//vertice x coord
f64 z=sin(angle*0.017453292519943295769236907684886f)*100;//vertice z coord
Vertices[vert]=video::S3DVertex(x, -5.0f, z,
0.0568988f, 0.688538f, -0.722965f,
video::SColor(255,255,255,255), 0.0f, 0.9f);
angle=angle+angle2;
//connects face
indices[nr]=0; //top vertice
indices[nr+1]=vert; //bottom vertice
indices[nr+2]=vert+1; //next bottom vertice
}
indices[nr+2]=1; //connect last bottom vertice with first
}
virtual void OnRegisterSceneNode()
{
if (IsVisible)
SceneManager->registerNodeForRendering(this,ESNRP_SKY_BOX);
ISceneNode::OnRegisterSceneNode();
}
virtual void render()
{
video::IVideoDriver* driver = SceneManager->getVideoDriver();
scene::ICameraSceneNode* camera = SceneManager->getActiveCamera();
if (!camera || !driver)
return;
core::matrix4 mat;
mat.setTranslation(camera->getAbsolutePosition());
//attach node to camera
driver->setTransform(video::ETS_WORLD, mat);
//don't attach camera
//driver->setTransform(video::ETS_WORLD, AbsoluteTransformation);
driver->setMaterial(Material);
//update uv maping
for (int i=1;i<face+1;i++){
Vertices[i].TCoords=core::vector2d< f32 >(uvX,0.98f);
}
Vertices[0].TCoords=core::vector2d< f32 >(uvX,0.01f);
driver->drawIndexedTriangleList(&Vertices[0],vert+1,&indices[0],face);
}
virtual const core::aabbox3d<f32>& getBoundingBox() const
{
return Box;
}
virtual u32 getMaterialCount() const
{
return 1;
}
virtual video::SMaterial& getMaterial(u32 i)
{
return Material;
}
//change sky texture
virtual SMaterial& setMaterial(ITexture* tex)
{
Material.setTexture(0, tex);
return Material;
}
//update uv maping x coordinate
void setuvX(f64 v)
{
uvX=v;
}
};
//******************************************************************************
//almost all code from CBillboardSceneNode
class CATMOstarSceneNode : public scene::ISceneNode
{
core::aabbox3d<f32> BBox;
core::dimension2d<f32> Size;
video::S3DVertex Vertices[4];
video::SMaterial Material;
u16 indices[6];
video::S3DVertex vertices[4];
public:
CATMOstarSceneNode(scene::ISceneNode* parent, scene::ISceneManager* mgr,
s32 id,vector3df position,const core::dimension2d<f32>& size)
: scene::ISceneNode(parent, mgr, id,position)
{
Material.ZBuffer = false;
setSize(size);
// AutomaticCullingEnabled = false;
indices[0] = 0;
indices[1] = 2;
indices[2] = 1;
indices[3] = 0;
indices[4] = 3;
indices[5] = 2;
vertices[0].TCoords.set(1.0f, 1.0f);
vertices[0].Color = 0xffffffff;
vertices[1].TCoords.set(1.0f, 0.0f);
vertices[1].Color = 0xffffffff;
vertices[2].TCoords.set(0.0f, 0.0f);
vertices[2].Color = 0xffffffff;
vertices[3].TCoords.set(0.0f, 1.0f);
vertices[3].Color = 0xffffffff;
}
//virtual void setSize(const core::dimension2d<f32>& size);
virtual void OnRegisterSceneNode()
{
if (IsVisible)
SceneManager->registerNodeForRendering(this,ESNRP_SKY_BOX);
ISceneNode::updateAbsolutePosition();//realy helps from sun pos lag
ISceneNode::OnRegisterSceneNode();
}
virtual void render()
{
video::IVideoDriver* driver = SceneManager->getVideoDriver();
ICameraSceneNode* camera = SceneManager->getActiveCamera();
if (!camera || !driver)
return;
// make billboard look to camera
core::vector3df pos = getAbsolutePosition();
core::vector3df campos = camera->getAbsolutePosition();
core::vector3df target = camera->getTarget();
core::vector3df up = camera->getUpVector();
core::vector3df view = target - campos;
view.normalize();
core::vector3df horizontal = up.crossProduct(view);
horizontal.normalize();
core::vector3df vertical = horizontal.crossProduct(view);
vertical.normalize();
horizontal *= 0.5f * Size.Width;
vertical *= 0.5f * Size.Height;
vertices[0].Pos = pos + horizontal + vertical;
vertices[1].Pos = pos + horizontal - vertical;
vertices[2].Pos = pos - horizontal - vertical;
vertices[3].Pos = pos - horizontal + vertical;
view *= -1.0f;
for (s32 i=0; i<4; ++i)
vertices[i].Normal = view;
// draw
if (DebugDataVisible)
{
driver->setTransform(video::ETS_WORLD, AbsoluteTransformation);
video::SMaterial m;
m.Lighting = false;
driver->setMaterial(m);
driver->draw3DBox(BBox, video::SColor(0,208,195,152));
}
core::matrix4 mat;
driver->setTransform(video::ETS_WORLD, mat);
driver->setMaterial(Material);
driver->drawIndexedTriangleList(vertices, 4, indices, 2);
}
virtual const core::aabbox3d<f32>& getBoundingBox() const
{
return BBox;
}
//! sets the size of the billboard
void setSize(const core::dimension2d<f32>& size)
{
Size = size;
if (Size.Width == 0.0f)
Size.Width = 1.0f;
if (Size.Height == 0.0f )
Size.Height = 1.0f;
f32 avg = (size.Width + size.Height)/6;
BBox.MinEdge.set(-avg,-avg,-avg);
BBox.MaxEdge.set(avg,avg,avg);
}
virtual u32 getMaterialCount() const
{
return 1;
}
virtual video::SMaterial& getMaterial(u32 i)
{
return Material;
}
//change sky texture
virtual video::SMaterial& setMaterial(video::ITexture* tex)
{
Material.setTexture(0,tex);
return Material;
}
//update uv maping x coordinate
const core::dimension2d<f32>& getSize()
{
return Size;
}
};
//******************************************************************************
class ATMOsphere{
struct PIXEL
{
u8 B,G,R,A;
};
CATMOstarSceneNode* bill;
u32 kin,ilgis;
u32 i;
//u8 palete[256][3];
//u8 prspalva[3];
//u8 pbspalva[3];
//u8 vspalva[3];
float step[3];
float pspalva[3];
CATMOskySceneNode *Sky;
CATMOstarSceneNode *Sun;
scene::ILightSceneNode *sunlight;
video::IImage* image;
s32 skyid;
video::ITexture* dangus;
IrrlichtDevice* device;
IVideoDriver* driver;
scene::ISceneManager* smgr;
double rad;//radian
u32 tex_size;//texture size
u32 half_tex;//half texture size
//--Timer----
ITimer *Atimer;//ATMOsphere timer
f32 currentTime, startTime, dTime;
//how many virtual day per real day. 1440 = day per 1 min.
//24*60=1440/dayspeed=1day-1min
f64 dayspeed; // how long goes day in minutes
u32 ptime,gtime;
f64 time_int_step;//sun place interpolation position (0-1)
f64 counter_time;//loop variable,count time from interpolation start in J
f64 J1minute;
//--Sun position---
double J;//julias date
double sun_angle[2];//sun pos in angles
f32 sun_interpolation_speed;//how minutes in virtual time takes interpolate sun from start to end position
double J1;
vector3df sun_pos_from,sun_pos_to;//interpolations points
f64 sun_angle_from,sun_angle_to;//sun height angle for interpolation
//--Sky texture----
//setSkyImage
video::IImage* skyimage;//sky texture
PIXEL *pixels;//palete
f32 uvX;
//---Date conversions
u16 Ndate[5];//stores date converted from Julian calendar
//-------------
public:
ATMOsphere(){
//default values
kin=0;
ilgis=0;
uvX=0.0f;
i=0;
rad=0.017453292519943295769236907684886f;//degree to radian (PI/180);
/* prspalva[0]=0;//tamsi
prspalva[1]=128;
prspalva[2]=255;
pbspalva[0]=128;//sviesi
pbspalva[1]=255;
pbspalva[2]=255;
vspalva[0]=113;//vidurys
vspalva[1]=184;
vspalva[2]=255;*/
J=DateToJulian(2009,6,29,7,50);//start time
dayspeed=60.0f;
time_int_step=0.0f;//start sun pos interpolation
sun_interpolation_speed=30.0f;//make sun pos interpolation every 30 virtual min
J1minute=1.0f/1440.0f;//one minute in Julian time
}
//###rounds angle to fit 360 degrees
f32 round360(f32 angle){
if (angle>360){
while (angle>360){
angle-=360;
}
}
return angle;
}
vector3df getInterpolated3df(vector3df from,vector3df to, f32 d)
{
f32 inv = 1.0f - d;
vector3df rez;
rez.X=from.X *inv + to.X*d;
rez.Y=from.Y*inv + to.Y*d;
rez.Z=from.Z*inv + to.Z*d;
return rez;
}
//prepare sun position interpolation (find start and end positions)
void prep_interpolation(f64 Jdate, f64 time)//time-time from 1st sun pos to 2nd
{
core::matrix4 mat;
core::vector3df kampas;
saule(52.0f,-5.0f,Jdate);//52.0 -5.0 kaunas 54.54 -23.54
kampas.X=-sun_angle[1];//heigh
kampas.Y=sun_angle[0];//0.0f;-
kampas.Z=0.0f;
mat.setRotationDegrees(kampas);
f32 vieta[4];
vieta[0]=0.0f;
vieta[1]=0.0f;
vieta[2]=1000.0f;
vieta[3]=0.0f;
mat.multiplyWith1x4Matrix(vieta);
sun_pos_from.X=vieta[0];
sun_pos_from.Y=vieta[1];
sun_pos_from.Z=vieta[2];
sun_angle_from=sun_angle[1];
saule(52.0f,-5.0f,Jdate+time);//52.0 -5.0 kaunas 54.54 -23.54
kampas.X=-sun_angle[1];//heigh
kampas.Y=sun_angle[0];//0.0f;-
kampas.Z=0.0f;
core::matrix4 mat2;
mat2.setRotationDegrees(kampas);
vieta[0]=0.0f;
vieta[1]=0.0f;
vieta[2]=1000.0f;
vieta[3]=0.0f;
sun_angle_to=sun_angle[1];
mat2.multiplyWith1x4Matrix(vieta);
sun_pos_to.X=vieta[0];
sun_pos_to.Y=vieta[1];
sun_pos_to.Z=vieta[2];
}
//calculate sun position
void saule(f64 pl,f64 lw,f64 J){
//lw - longitude
//pl - latitude
//double J=2453097;
f64 M = 357.5291f + 0.98560028*(J - 2451545);//degree
M=round360(M);//degree
f64 Mrad=M*rad;//radian
f64 C = 1.9148f* sin(Mrad) + 0.02f* sin(2*Mrad) + 0.0003f*sin(3* Mrad);//degree
//printf("C %3.4f\n",C);
C=round360(C);//degree
//f64 Crad=C*rad;//radian
f64 lemda = M + 102.9372f + C + 180.0f;//degree
lemda=round360(lemda);//degree
f64 lemdarad=lemda*rad;//radian
f64 alfa =lemda - 2.468f *sin(2* lemdarad) + 0.053f* sin(4* lemdarad)-0.0014f *sin(6 *lemdarad);//degree
alfa=round360(alfa);//degree
f64 sigma=22.8008f* sin(lemdarad) + 0.5999f* sin(lemdarad)*sin(lemdarad)*sin(lemdarad)
+ 0.0493f* sin(lemdarad)*sin(lemdarad)*sin(lemdarad)*sin(lemdarad)*sin(lemdarad);//degree
sigma=round360(sigma);//degree
f64 sigmarad=sigma*rad;//radian
f64 zv=280.16f+360.9856235f*(J-2451545.0f)-lw;//degree
zv=round360(zv);//degree
f64 H = zv - alfa;//degree
H=round360(H);//degree
f64 Hrad=H*rad;//radian
f64 A = atan2(sin(Hrad), cos(Hrad)* sin(pl*rad) - tan(sigmarad)*cos(pl*rad))/rad;
f64 h = asin(sin(pl*rad)*sin(sigmarad) + cos(pl*rad)*cos(sigmarad)*cos(Hrad))/rad;
//A from 0..180,-180..0
//printf("M %3.4f C %3.4f lemda %3.4f alfa %3.4f sigma %3.4f\n",M,C,lemda,alfa,sigma);
//printf("zv %3.4f H %3.4f A %3.4f h %3.15f\n",zv,H,A,h);
sun_angle[0]=A;
sun_angle[1]=h;//height
}
void setSkyImage(const char *filename){
skyimage=driver->createImageFromFile(filename);
}
void CreateSkyPallete(){//Psize-paletes dydis
if (dangus!=NULL){
driver->removeTexture(dangus);
}
dangus=driver->getTexture("../../media/sky2.tga");
//stars box
smgr->addSkyBoxSceneNode(
driver->getTexture("../../media/stars.bmp"),
driver->getTexture("../../media/stars.bmp"),
driver->getTexture("../../media/stars.bmp"),
driver->getTexture("../../media/stars.bmp"),
driver->getTexture("../../media/stars.bmp"),
driver->getTexture("../../media/stars.bmp"));
Sky = new CATMOskySceneNode(dangus,smgr->getRootSceneNode(), smgr,80, skyid);
//sun billboard
bill=new CATMOstarSceneNode(smgr->getRootSceneNode(),smgr,0, core::vector3df(0,0,0),core::dimension2d<f32>(150,150));
bill->setMaterialFlag(video::EMF_LIGHTING, false);
bill->setMaterialTexture(0, driver->getTexture("../../media/sun.tga"));
bill->getMaterial(0).MaterialTypeParam = 0.01f;
bill->setMaterialType(video::EMT_TRANSPARENT_ALPHA_CHANNEL);
Sky->getMaterial(0).MaterialTypeParam = 0.01f;
Sky->setMaterialType(video::EMT_TRANSPARENT_ALPHA_CHANNEL);
sunlight = smgr->addLightSceneNode(bill, core::vector3df(0,100,0),
video::SColorf(1.0f, 0.6f, 0.7f, 1.0f), 10000.0f);
}
//###Starts ATMOsphere and prepares for work
void start(IrrlichtDevice* device2,video::IVideoDriver* Driver,scene::ISceneNode* parent, scene::ISceneManager* mgr, s32 id)
{
skyid=id;
device=device2;
driver=Driver;
smgr=mgr;
setSkyImage("../../media/sky2.tga");
CreateSkyPallete();
startTimer();
setAmbientLight2(SColor(255,255,255,255));//bug fix
}
//###starts timer
void startTimer(){
// Atimer=new ITimer();
Atimer=device->getTimer();
// Atimer->start();
//Atimer->setTime(0);
currentTime=Atimer->getRealTime();
startTime=Atimer->getRealTime();
dTime=0.0f;
J1=J;//force update sun first time
ptime=Atimer->getRealTime();
gtime=Atimer->getRealTime();
JulianToDate(J);
}
//###Calculates delta time (time from last frame) for timer
void updateTimer(){
currentTime =Atimer->getRealTime();
dTime=currentTime-startTime;
}
//###returns sun rotation about y axis
f64 getSunXAngle(){
return sun_angle[0]*rad;//angle in radians
}
//###returns sun rotation about x axis (sun height above horizont)
f64 getSunYAngle(){
return sun_angle[1]*rad;// angle in radians
}
void setDaysPerDay(f64 days){
dayspeed=days;
}
f64 getDayspeed(){
return dayspeed;
}
void update(video::IVideoDriver* driver)
{
updateTimer();
SColor sp;
J=J+(((double)dayspeed/86400)/1000.0f)*dTime;
//if interpolation is finished then start again
if(time_int_step==0.0f){//calculate sun interpolation positions
prep_interpolation(J,sun_interpolation_speed*J1minute);
JulianToDate(J);
counter_time=0.0f;
}//1440
//printf("%8.4f %4.8f\n",J,time_int_step);
//---move sun billboard to sun place
counter_time+=J-J1;//1440
time_int_step=counter_time/(sun_interpolation_speed*J1minute);//(1.0f/(sun_interpolation_speed*(1.0f/1440.0f)))*dTime;
vector3df sun_place=getInterpolated3df(sun_pos_from,sun_pos_to, time_int_step);
J1=J;
ICameraSceneNode *cam=smgr->getActiveCamera();
core::vector3df cameraPos = cam->getAbsolutePosition();
core::vector3df vt;//billboard position
vt.X=sun_place.X+cameraPos.X;
vt.Y=sun_place.Y+cameraPos.Y;
vt.Z=sun_place.Z+cameraPos.Z;
bill->setPosition(vt);
// sunlight->setPosition(vt);
//---sun movement end
f32 inv = 1.0f - time_int_step;
uvX=((sun_angle_from *inv + sun_angle_to*time_int_step)+90.0f)/180;
if(time_int_step>=1.0f){
time_int_step=0.0f;
}
sp=skyimage->getPixel((int)round(128*uvX),123);
//driver->setAmbientLight(SColor(255,sp.getRed(),sp.getGreen(),sp.getBlue()));
//printf("vt %3.4f",getSunYAngle());
if (getSunYAngle()<0.0042){//isjungti lenpa kai naktis
sunlight->setVisible(false);
setAmbientLight2(SColor(255,sp.getRed(),sp.getGreen(),sp.getBlue()));
}
else{
sunlight->setVisible(true);
setAmbientLight2(SColor(255,sp.getRed(),sp.getGreen(),sp.getBlue()));//bug fix
}
// smgr->setShadowColor(SColor(50,sp.getRed(),sp.getGreen(),sp.getBlue()));
//sunlight->getLightData().DiffuseColor=SColor(255,sp.getRed(),sp.getGreen(),sp.getBlue());
Sky->setuvX(uvX);
startTime = currentTime;
}
wchar_t getTextDate(){
JulianToDate(J);
return 1;
}
//###Converts normal date tu Julian calendar date
f64 DateToJulian(u16 y,u16 m,u16 d,u16 h,u16 min){
//http://www.phys.uu.nl/~strous/AA/en//reken/juliaansedag.html
f64 hh=h*60+min; //to minutes
f64 dd=d+(hh/1440.0f);
printf("dd= %8.8f %8.8f\n",dd,hh);
if (m<3){
m=m+12;
y=y-1;
}
f64 c=2-floor(y/100)+floor(y/400);
f64 dt=floor(1461.0f*(y+4716.0f)/4)+floor(153*(m+1)/5)+dd+c-1524.5f;
return dt;
}
//###Converts Julian calendar date to normal calendar date
void JulianToDate(f64 x){
//http://www.phys.uu.nl/~strous/AA/en//reken/juliaansedag.html
f64 p = floor(x + 0.5);
f64 s1 = p + 68569;
f64 n = floor(4*s1/146097);
f64 s2 = s1 - floor((146097*n + 3)/4);
f64 i = floor(4000*(s2 + 1)/1461001);
f64 s3 = s2 - floor(1461*i/4) + 31;
f64 q = floor(80*s3/2447);
f64 e = s3 - floor(2447*q/80);
f64 s4 = floor(q/11);
f64 m = q + 2 - 12*s4;
f64 y = 100*(n - 49) + i + s4;
f64 d = e + x - p + 0.5;
double rr;
f64 h = ((modf(d,&rr)*1440)/60);
d=floor(d);
f64 min=floor(modf(h,&rr)*60);
h=floor(h);
printf("update time:%4.0f %2.0f %2.0f %2.0f %2.0f\n",y,m,d,h,min);
Ndate[0]=(u16)y;
Ndate[1]=(u16)m;
Ndate[2]=(u16)d;
Ndate[3]=(u16)h;
Ndate[4]=(u16)min;
}
void setAmbientLight2(video::SColor color)
{
io::IFileSystem* files=device->getFileSystem();
io::IAttributes* a = files->createEmptyAttributes();
// get the current attributes
scene::ISceneNode* self = smgr->getRootSceneNode();
self->serializeAttributes(a);
// set the color attribute
a->setAttribute("AmbientLight", color);
self->deserializeAttributes(a);
// destroy attributes
a->drop();
}
};
Code: Select all
#include <stdio.h>
#include <math.h>
#include <wchar.h>
#include <irrlicht.h>
#include <IGUIFont.h>
#include "ATMOSphere.cpp"
// hide console window
using namespace irr;
using namespace core;
using namespace video;
using namespace gui;
scene::ISceneNode* node = 0;
IrrlichtDevice* device = 0;
bool kursorius=false;
bool kamera=true;
scene::ISceneManager* smgr;
scene::ICameraSceneNode* camera = 0;
scene::ICameraSceneNode* camera2 = 0;
ATMOsphere *atmo;
class MyEventReceiver : public IEventReceiver
{
public:
virtual bool OnEvent(const SEvent& event)
{
/*
If the key 'W' or 'S' was left up, we get the position of the scene node,
and modify the Y coordinate a little bit. So if you press 'W', the node
moves up, and if you press 'S' it moves down.*/
if (event.EventType == irr::EET_KEY_INPUT_EVENT&&
event.KeyInput.PressedDown)
{
switch(event.KeyInput.Key)
{
case KEY_ESCAPE:{device->closeDevice();}
case KEY_SPACE:{
kursorius=!kursorius;
device->getCursorControl()->setVisible(kursorius);
kamera=!kamera;
core::vector3df targ;
if (kamera){
device->getCursorControl()->setPosition(0.5f,0.5f);
smgr->setActiveCamera(camera);
camera->setInputReceiverEnabled(true);
}
else {
camera->setInputReceiverEnabled(false);
targ=camera->getTarget();
camera2->setTarget(targ);
camera2->setPosition(camera->getPosition());
smgr->setActiveCamera(camera2);
}
}
case KEY_KEY_S:
{
// core::vector3df v = node->getPosition();
// v.Y += event.KeyInput.Key == KEY_KEY_W ? 2.0f : -2.0f;
// node->setPosition(v);
}
default:
break;
return true;
}
}
if (event.EventType == EET_GUI_EVENT)
{
s32 id = event.GUIEvent.Caller->getID();
//IGUIEnvironment* env = device->getGUIEnvironment();
switch(event.GUIEvent.EventType)
{
case EGET_SCROLL_BAR_CHANGED:
if (id == 104)
{
s32 pos = ((IGUIScrollBar*)event.GUIEvent.Caller)->getPos();
atmo->setDaysPerDay((f64)pos/10.0f);//day speed
}
break;
default:
break;
}return true;
}
return false;
}
};
/*
The event receiver for moving a scene node is ready. So lets just create
an Irrlicht Device and the scene node we want to move. We also create some
other additional scene nodes, to show that there are also some different
possibilities to move and animate scene nodes.
*/
int main()
{
MyEventReceiver receiver;
device = createDevice(video::EDT_OPENGL, core::dimension2d<u32>(800, 600),32,false, true, false, &receiver);//EDT_DIRECT3D9
device->setEventReceiver(&receiver);
video::IVideoDriver* driver = device->getVideoDriver();
IGUIEnvironment* env = device->getGUIEnvironment();
driver->setTextureCreationFlag(ETCF_ALWAYS_32_BIT,true);
smgr = device->getSceneManager();
IGUIScrollBar* scrollbar = env->addScrollBar(true, rect<s32>(150, 45, 350, 60), 0, 104);
scrollbar->setMax(50000);
scrollbar->setPos(600);
IGUIStaticText *textinfo;
textinfo=env->addStaticText(L"Dayspeed in minutes", rect<s32>(150,25,350,40), true);
IGUIStaticText *textinfo3;
textinfo3=env->addStaticText(L"Press spacebar for mouse cursor and again spacebar for mouse rotate.Arrows to move.", rect<s32>(50,5,550,20), true);
IGUIStaticText *textinfo2;
textinfo2=env->addStaticText(L"Dayspeed is how long virtual day takes in real day(1440 min) in minutes.\nExample: 2880(dayspeed) / const 1440(day in minutes) = 2 days per 1 minute", rect<s32>(50,70,550,100), true);
/*
To make the font a little bit nicer, we load an external font
and set it as new font in the skin. An at last, we create a
nice Irrlicht Engine logo in the top left corner.
*/
IGUISkin* skin = env->getSkin();
IGUIFont* font = env->getFont("../../media/fonthaettenschweiler.bmp");
if (font)
skin->setFont(font);
camera = smgr->getActiveCamera();
if (camera)
{
smgr->setActiveCamera(0);
camera->remove();
}
camera2 = smgr->addCameraSceneNode();
camera2->setFOV(45.0f*180.0f/irr::core::DEGTORAD);//make correct FOV
camera2->setFarValue(120000.0f);
camera = smgr->addCameraSceneNodeFPS(0, 100, 5.0);
camera->setFOV(45.0f*180.0f/irr::core::DEGTORAD);
camera->setFarValue(120000.0f);
camera->setPosition(core::vector3df(0,20,20));
//----------------------------------
atmo=new ATMOsphere;
atmo->start(device,driver,smgr->getRootSceneNode(),smgr,666);
//int laikas=-1;
//u8 spalva=0;
//**************************
scene::ITerrainSceneNode* terrain = smgr->addTerrainSceneNode("../../media/terrain-heightmap.bmp");
terrain->setScale(core::vector3df(10, 1.0f, 10));
terrain->setMaterialFlag(video::EMF_LIGHTING, true);
terrain->setPosition(core::vector3df(-1200,-50,-1400));
terrain->setMaterialType(terrain->getMaterial(0).MaterialType == video::EMT_SOLID ?
video::EMT_DETAIL_MAP : video::EMT_SOLID);
terrain->setMaterialTexture(0, driver->getTexture("../../media/terrain-texture.jpg"));
terrain->setMaterialTexture(1, driver->getTexture("../../media/detailmap3.jpg"));
//terrain->setMaterialType(video::EMT_DETAIL_MAP);
terrain->scaleTexture(1.0f, 50.0f);
// create triangle selector for the terrain
scene::ITriangleSelector* selector
= smgr->createTerrainTriangleSelector(terrain, 0);
terrain->setTriangleSelector(selector);
// create collision response animator and attach it to the camera
scene::ISceneNodeAnimator* anim = smgr->createCollisionResponseAnimator(
selector, camera, core::vector3df(60,100,60),
core::vector3df(0,0,0),
core::vector3df(0,50,0));
selector->drop();
camera->addAnimator(anim);
anim->drop();
device->getCursorControl()->setVisible(false);
int lastFPS = -1;
while(device->run())
{
atmo->update(driver);//update all sky/sun
driver->beginScene(true, true, video::SColor(255,113,113,133));
smgr->drawAll();
env->drawAll();
driver->endScene();
int fps = driver->getFPS();
wchar_t tmp[1024];int fp;
if (lastFPS != fps)
{
fp=fps;
lastFPS = fps;
}
swprintf(tmp, 1024, L" [%s] fps: %d dayspeed: %5.3f",driver->getName(),fp,atmo->getDayspeed());
stringw str = "FPS= ";
str += fp;
font->draw(str.c_str(),rect<s32>(5,5,30,30),SColor(255,255,0,100));
device->setWindowCaption(tmp);
}
device->drop();
return 0;
}
Code: Select all
# Makefile for Irrlicht Examples
# It's usually sufficient to change just the target name and source file list
# and be sure that CXX is set to a valid compiler
Target = 22.ATMOSphere
Sources = main.cpp ATMOSphere.cpp
# general compiler settings
CPPFLAGS = -I../../include -I/usr/X11R6/include
CXXFLAGS = -O3 -ffast-math
#CXXFLAGS = -g -Wall
#default target is Linux
all: all_linux
ifeq ($(HOSTTYPE), x86_64)
LIBSELECT=64
endif
# target specific settings
all_linux: LDFLAGS = -L/usr/X11R6/lib$(LIBSELECT) -L../../lib/Linux -lIrrlicht -lGL -lXxf86vm -lXext -lX11
all_linux clean_linux: SYSTEM=Linux
all_win32: LDFLAGS = -L../../lib/Win32-gcc -lIrrlicht -lopengl32 -lm
all_win32 clean_win32: SYSTEM=Win32-gcc
all_win32 clean_win32: SUF=.exe
# name of the binary - only valid for targets which set SYSTEM
DESTPATH = ../../bin/$(SYSTEM)/$(Target)$(SUF)
all_linux all_win32:
$(warning Building...)
$(CXX) $(CPPFLAGS) $(CXXFLAGS) $(Sources) -o $(DESTPATH) $(LDFLAGS)
clean: clean_linux clean_win32
$(warning Cleaning...)
clean_linux clean_win32:
@$(RM) $(DESTPATH)
.PHONY: all all_win32 clean clean_linux clean_win32
Nice to see that it is still usable after 4 years.
This weekend i (and a team) created mini game on global game jam. My part was game logic and other programmer programed GUI and sound. We used irrlich and openal, game created in about 46 hours (including ~5hours to sleep ) It's not finished yet, but playable. You can download it from http://www.globalgamejam.org/2010/technomemo with source (need to clean it up) . I hope to finish it on next week.
This weekend i (and a team) created mini game on global game jam. My part was game logic and other programmer programed GUI and sound. We used irrlich and openal, game created in about 46 hours (including ~5hours to sleep ) It's not finished yet, but playable. You can download it from http://www.globalgamejam.org/2010/technomemo with source (need to clean it up) . I hope to finish it on next week.
My project in forum- ATMOsphere - new dynamic sky dome for Irrlicht
i had to comment out //sounds.Sukurti(); and fix a bunch of header stuff, here's your linux port - everything in it should still compile for windows i hope.
http://www.xup.in/dl,26982972/TechnoMemo.7z/
http://www.xup.in/dl,26982972/TechnoMemo.7z/
Game updated, added frame rotation, now its harder to match pairs
http://www.globalgamejam.org/2010/technomemo
http://www.globalgamejam.org/2010/technomemo
My project in forum- ATMOsphere - new dynamic sky dome for Irrlicht
Last time i checked devsh's code, he uses a full moon image and place it in the opposite direction of the sun (-sun_place.x, -sun_place.y, -sun_place.z).loki1985 wrote:@devsh: does your moon have correct position (and maybe even appearance) according to date and time? if so, would you share your code?
It is not the correct position but that way it comes out only at night so you don' t have to hide it when it is in a visible position during the day.
A better approach would be to place it behind the skyNode. That way it will "fade away" like the stars do and it will be more realistic in my opinion. So if you put it in the correct position you wont have a problem during the day (I did that and worked fine).
I also tried to make it change phases adding 28 different textures and some code i found somewhere to calculate the correct moonphase in a current date. I also put a dark texture behind the others to block out the stars behind the dark moon as bitplane suggests somewhere in this thread.
Now i am trying to put it in the correct position from a link provided by Pazystamo.
I also used the CRTTSkyBoxSceneNode and a list of star positions and types i found somewhere in the irrlicht forums to produce a more accurate and star-rich skybox. Rotating the star skybox according the dayspeed also adds a little bit more realism.
I could not solve the "jerky movement" of the sun when you move the FPSCamera (same thing happens with the moon) but if you increece the distance of the sun from the camera the problem is eliminated (i know this is not a real solution...).
Some "glowing" shaders for the sun-moon-stars would also be nice but i cannot do this myself (i think devsh also did something like that).
If i manage to make it work good enough and clean the code (as much as i can ) i will certainly post the source. In the meantime i can post the links for the things i used to improve this if someone wants to do this himself.
I think this is one of the nicest projects here and one of the most accurate atmosphere simulations i have seen in a 3d engine so am glad it is not dead yet. Congratz Pazystamo!!
Last edited by sprocket on Wed Feb 03, 2010 5:52 pm, edited 1 time in total.
Sure loki1985!
the links:
Render To Texture Skybox: http://irrlicht.sourceforge.net/phpBB2/ ... hp?t=13288
The Star Catalog used with Render To Texture Skybox: http://irrlicht.sourceforge.net/phpBB2/ ... hp?t=32815
Moon position calculation: http://www.phys.uu.nl/~strous/AA/en/rek ... tie.html#2
Moon phase calculation source code: http://planet-source-code.com/vb/script ... 8&lngWId=3
the links:
Render To Texture Skybox: http://irrlicht.sourceforge.net/phpBB2/ ... hp?t=13288
The Star Catalog used with Render To Texture Skybox: http://irrlicht.sourceforge.net/phpBB2/ ... hp?t=32815
Moon position calculation: http://www.phys.uu.nl/~strous/AA/en/rek ... tie.html#2
Moon phase calculation source code: http://planet-source-code.com/vb/script ... 8&lngWId=3
not sure if its something simple or not, something changed and now the tower is tiny and the house is normal .. when i try increasing the size it makes the shadow huge... any ideas ?
updated for 1.7.1
http://www.xup.in/dl,10066452/Atmosphere-demo.7z/
updated for 1.7.1
http://www.xup.in/dl,10066452/Atmosphere-demo.7z/
Live long and phosphor!
-- https://github.com/netpipe/Luna Game Engine Status 95%
-- https://github.com/netpipe/Luna Game Engine Status 95%