summaryrefslogtreecommitdiffstats
path: root/src/graphics
diff options
context:
space:
mode:
authorPiotr Dziwinski <piotrdz@gmail.com>2012-08-10 23:31:42 +0200
committerPiotr Dziwinski <piotrdz@gmail.com>2012-08-10 23:31:42 +0200
commit63257034c946d40fb3ecc73a9ee3dc9d1e0a1e34 (patch)
treeaa1fcf2928e2c9d5f89022242fbe3ff6d7d64bbb /src/graphics
parentc3ab23ac9dc02d59180f2f1af5f3aa5b50f9f8d8 (diff)
downloadcolobot-63257034c946d40fb3ecc73a9ee3dc9d1e0a1e34.tar.gz
colobot-63257034c946d40fb3ecc73a9ee3dc9d1e0a1e34.tar.bz2
colobot-63257034c946d40fb3ecc73a9ee3dc9d1e0a1e34.zip
Partial CEngine implementation
- added rewritten implementation for basic modesetting in CEngine - started rewriting proper rendering and object handling in CEngine
Diffstat (limited to 'src/graphics')
-rw-r--r--src/graphics/core/color.h6
-rw-r--r--src/graphics/engine/engine.cpp2236
-rw-r--r--src/graphics/engine/engine.h477
3 files changed, 2318 insertions, 401 deletions
diff --git a/src/graphics/core/color.h b/src/graphics/core/color.h
index 6973644..0e08de3 100644
--- a/src/graphics/core/color.h
+++ b/src/graphics/core/color.h
@@ -18,7 +18,6 @@
#pragma once
-
#include <sstream>
@@ -66,6 +65,11 @@ struct Color
{
return r == other.r && g == other.g && b == other.b && a == other.a;
}
+
+ inline bool operator!=(const Gfx::Color &other) const
+ {
+ return ! this->operator==(other);
+ }
};
/**
diff --git a/src/graphics/engine/engine.cpp b/src/graphics/engine/engine.cpp
index c8fa05c..4244fb2 100644
--- a/src/graphics/engine/engine.cpp
+++ b/src/graphics/engine/engine.cpp
@@ -36,6 +36,8 @@
#include "graphics/engine/text.h"
#include "graphics/engine/water.h"
#include "math/geometry.h"
+#include "sound/sound.h"
+
// Initial size of various vectors
const int OBJECT_PREALLOCATE_COUNT = 1200;
@@ -50,6 +52,13 @@ const int LEVEL5_PREALLOCATE_COUNT = 100;
const int LEVEL5_VERTEX_PREALLOCATE_COUNT = 200;
+// TODO: temporary stub for CInterface
+class CInterface
+{
+public:
+ void Draw() {}
+};
+
Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
{
m_iMan = iMan;
@@ -60,7 +69,7 @@ Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
m_iMan->AddInstance(CLASS_ENGINE, this);
m_app = app;
- m_lightMan = nullptr;
+ m_lightMan = nullptr;
m_text = nullptr;
m_particle = nullptr;
m_water = nullptr;
@@ -107,15 +116,14 @@ Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
m_overFront = true;
m_overColor = 0;
m_overMode = ENG_RSTATE_TCOLOR_BLACK;
- m_frontsizeName = ""; // no front image
- m_hiliteRank[0] = -1; // empty list
+ m_highlightRank[0] = -1; // empty list
m_eyePt = Math::Vector(0.0f, 0.0f, 0.0f);
m_lookatPt = Math::Vector(0.0f, 0.0f, 1.0f);
m_drawWorld = true;
m_drawFront = false;
m_limitLOD[0] = 100.0f;
m_limitLOD[1] = 200.0f;
- m_particuleDensity = 1.0f;
+ m_particleDensity = 1.0f;
m_clippingDistance = 1.0f;
m_lastClippingDistance = m_clippingDistance;
m_objectDetail = 1.0f;
@@ -186,11 +194,10 @@ Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
Gfx::CEngine::~CEngine()
{
- m_iMan = nullptr;
- m_app = nullptr;
- m_device = nullptr;
-
- m_sound = nullptr;
+ m_iMan = nullptr;
+ m_app = nullptr;
+ m_device = nullptr;
+ m_sound = nullptr;
m_terrain = nullptr;
}
@@ -209,6 +216,16 @@ Gfx::CDevice* Gfx::CEngine::GetDevice()
return m_device;
}
+void Gfx::CEngine::SetTerrain(Gfx::CTerrain* terrain)
+{
+ m_terrain = terrain;
+}
+
+Gfx::CText* Gfx::CEngine::GetText()
+{
+ return m_text;
+}
+
bool Gfx::CEngine::Create()
{
m_size = m_lastSize = m_app->GetVideoConfig().size;
@@ -228,14 +245,17 @@ bool Gfx::CEngine::Create()
return false;
}
+ m_device->SetClearColor(Gfx::Color(0.0f, 0.0f, 0.0f, 0.0f));
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_TEST, false);
+ m_device->SetShadeModel(Gfx::SHADE_SMOOTH);
+ m_device->SetFillMode(Gfx::FILL_FILL);
+
+ SetFocus(m_focus);
m_matWorldInterface.LoadIdentity();
m_matViewInterface.LoadIdentity();
- Math::LoadOrthoProjectionMatrix(m_matProjInterface, 0.0f, 1.0f, 0.0f, 1.0f, -1.0f, 1.0f);
-
- m_device->SetClearColor(Gfx::Color(0.0f, 0.0f, 0.0f, 0.0f));
- m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_TEST, false);
+ Math::LoadOrthoProjectionMatrix(m_matProjInterface, 0.0f, 1.0f, 0.0f, 1.0f, -1.0f, 1.0f);
Gfx::TextureCreateParams params;
params.format = Gfx::TEX_IMG_RGB;
@@ -275,70 +295,598 @@ void Gfx::CEngine::Destroy()
void Gfx::CEngine::ResetAfterDeviceChanged()
{
- // TODO
+ // TODO reload textures, reset device state, etc.
}
-Gfx::Texture Gfx::CEngine::CreateTexture(const std::string &texName, const Gfx::TextureCreateParams &params)
+bool Gfx::CEngine::ProcessEvent(const Event &event)
{
- CImage img;
- if (! img.Load(m_app->GetDataFilePath(m_texPath, texName)))
+ if (event.type == EVENT_MOUSE_MOVE)
{
- std::stringstream str;
- str << "Couldn't load texture '" << texName << "': " << img.GetError();
- m_error = str.str();
- return Gfx::Texture(); // invalid texture
+ m_mousePos = event.mouseMove.pos;
}
+ else if (event.type == EVENT_KEY_DOWN)
+ {
+ // !! Debug, to be removed later !!
- Gfx::Texture result = m_device->CreateTexture(&img, params);
+ if (event.key.key == KEY(F1))
+ {
+ m_mouseVisible = !m_mouseVisible;
+ m_app->SetSystemMouseVisible(! m_app->GetSystemMouseVisibile());
+ }
+ else if (event.key.key == KEY(F2))
+ {
+ int index = static_cast<int>(m_mouseType);
+ m_mouseType = static_cast<Gfx::EngineMouseType>( (index + 1) % Gfx::ENG_MOUSE_COUNT );
+ }
+ }
- if (! result.valid)
+ // By default, pass on all events
+ return true;
+}
+
+void Gfx::CEngine::FrameMove(float rTime)
+{
+ m_lightMan->UpdateProgression(rTime);
+ m_particle->FrameParticle(rTime);
+ ComputeDistance();
+ UpdateGeometry();
+
+ if (m_groundMark.draw)
{
- std::stringstream str;
- str << "Couldn't load texture '" << texName << "': " << m_device->GetError();
- m_error = str.str();
- return result;
+ if (m_groundMark.phase == Gfx::ENG_GR_MARK_PHASE_INC) // growing?
+ {
+ m_groundMark.intensity += rTime*(1.0f/m_groundMark.delay[0]);
+ if (m_groundMark.intensity >= 1.0f)
+ {
+ m_groundMark.intensity = 1.0f;
+ m_groundMark.fix = 0.0f;
+ m_groundMark.phase = Gfx::ENG_GR_MARK_PHASE_FIX;
+ }
+ }
+ else if (m_groundMark.phase == Gfx::ENG_GR_MARK_PHASE_FIX) // fixed?
+ {
+ m_groundMark.fix += rTime*(1.0f/m_groundMark.delay[1]);
+ if (m_groundMark.fix >= 1.0f)
+ m_groundMark.phase = Gfx::ENG_GR_MARK_PHASE_DEC;
+ }
+ else if (m_groundMark.phase == Gfx::ENG_GR_MARK_PHASE_DEC) // decay?
+ {
+ m_groundMark.intensity -= rTime*(1.0f/m_groundMark.delay[2]);
+ if (m_groundMark.intensity < 0.0f)
+ {
+ m_groundMark.intensity = 0.0f;
+ m_groundMark.phase = Gfx::ENG_GR_MARK_PHASE_NULL;
+ m_groundMark.draw = false;
+ }
+ }
}
- m_texNameMap[texName] = result;
- m_revTexNameMap[result] = texName;
+ if (m_sound == nullptr)
+ m_sound = static_cast<CSoundInterface*>( m_iMan->SearchInstance(CLASS_SOUND) );
- return result;
+ m_sound->FrameMove(rTime);
}
-Gfx::Texture Gfx::CEngine::CreateTexture(const std::string &texName)
+void Gfx::CEngine::StepSimulation(float rTime)
{
- return CreateTexture(texName, m_defaultTexParams);
+ m_app->StepSimulation(rTime);
}
-void Gfx::CEngine::DestroyTexture(const std::string &texName)
+void Gfx::CEngine::TimeInit()
{
- std::map<std::string, Gfx::Texture>::iterator it = m_texNameMap.find(texName);
- if (it == m_texNameMap.end())
- return;
+ /* TODO!
+ m_baseTime = timeGetTime();
+ m_lastTime = 0;
+ m_absTime = 0.0f;*/
+}
- std::map<Gfx::Texture, std::string>::iterator revIt = m_revTexNameMap.find((*it).second);
+void Gfx::CEngine::TimeEnterGel()
+{
+ /* TODO!
+ m_stopTime = timeGetTime();*/
+}
- m_device->DestroyTexture((*it).second);
+void Gfx::CEngine::TimeExitGel()
+{
+ /* TODO!
+ m_baseTime += timeGetTime() - m_stopTime;*/
+}
- m_revTexNameMap.erase(revIt);
- m_texNameMap.erase(it);
+float Gfx::CEngine::TimeGet()
+{
+ /* TODO!
+ float aTime = (timeGetTime()-m_baseTime)*0.001f; // in ms
+ float rTime = (aTime - m_lastTime)*m_speed;
+ m_absTime += rTime;
+ m_lastTime = aTime;
+
+ return rTime;*/
+ return 0.0f;
}
-void Gfx::CEngine::SetTexture(const std::string &name, int stage)
+bool Gfx::CEngine::WriteScreenShot(const std::string& fileName, int width, int height)
{
- std::map<std::string, Gfx::Texture>::iterator it = m_texNameMap.find(name);
- if (it != m_texNameMap.end())
- m_device->SetTexture(stage, (*it).second);
+ // TODO!
+ return true;
+}
- // TODO if not present...
+bool Gfx::CEngine::ReadSettings()
+{
+ // TODO!
+ return true;
}
-void Gfx::CEngine::SetMaterial(const Gfx::Material &mat)
+bool Gfx::CEngine::WriteSettings()
{
- m_device->SetMaterial(mat);
+ // TODO!
+ return true;
+}
+
+void Gfx::CEngine::SetPause(bool pause)
+{
+ m_pause = pause;
+}
+
+bool Gfx::CEngine::GetPause()
+{
+ return m_pause;
+}
+
+void Gfx::CEngine::SetMovieLock(bool lock)
+{
+ m_movieLock = lock;
+}
+
+bool Gfx::CEngine::GetMovieLock()
+{
+ return m_movieLock;
+}
+
+void Gfx::CEngine::SetShowStats(bool show)
+{
+ m_showStats = show;
+}
+
+bool Gfx::CEngine::GetShowStats()
+{
+ return m_showStats;
+}
+
+void Gfx::CEngine::SetRenderEnable(bool enable)
+{
+ m_render = enable;
+}
+
+Math::IntSize Gfx::CEngine::GetWindowSize()
+{
+ return m_size;
+}
+
+Math::IntSize Gfx::CEngine::GetLastWindowSize()
+{
+ return m_lastSize;
+}
+
+Math::Point Gfx::CEngine::WindowToInterfaceCoords(Math::IntPoint pos)
+{
+ return Math::Point( static_cast<float>(pos.x) / static_cast<float>(m_size.w),
+ 1.0f - static_cast<float>(pos.y) / static_cast<float>(m_size.h) );
+}
+
+Math::IntPoint Gfx::CEngine::InterfaceToWindowCoords(Math::Point pos)
+{
+ return Math::IntPoint(static_cast<int>(pos.x * m_size.w),
+ static_cast<int>((1.0f - pos.y) * m_size.h));
+}
+
+Math::Size Gfx::CEngine::WindowToInterfaceSize(Math::IntSize size)
+{
+ return Math::Size( static_cast<float>(size.w) / static_cast<float>(m_size.w),
+ static_cast<float>(size.h) / static_cast<float>(m_size.h) );
+}
+
+Math::IntSize Gfx::CEngine::InterfaceToWindowSize(Math::Size size)
+{
+ return Math::IntSize(static_cast<int>(size.w * m_size.w),
+ static_cast<int>(size.h * m_size.h));
+}
+
+std::string Gfx::CEngine::GetTextureDir()
+{
+ return m_texPath;
+}
+
+void Gfx::CEngine::AddStatisticTriangle(int count)
+{
+ m_statisticTriangle += count;
+}
+
+int Gfx::CEngine::GetStatisticTriangle()
+{
+ return m_statisticTriangle;
+}
+
+
+
+/*******************************************************
+ Object management
+ *******************************************************/
+
+
+
+int Gfx::CEngine::CreateObject()
+{
+ // TODO!
+ return 0;
+}
+
+void Gfx::CEngine::FlushObject()
+{
+ // TODO!
+}
+
+bool Gfx::CEngine::DeleteObject(int objRank)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetDrawWorld(int objRank, bool draw)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetDrawFront(int objRank, bool draw)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::AddTriangle(int objRank, Gfx::VertexTex2* vertex, int nb,
+ const Gfx::Material& mat, int state,
+ std::string texName1, std::string texName2,
+ float min, float max, bool globalUpdate)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::AddSurface(int objRank, Gfx::VertexTex2* vertex, int nb,
+ const Gfx::Material& mat, int state,
+ std::string texName1, std::string texName2,
+ float min, float max, bool globalUpdate)
+{
+ // TODO!
+ return true;
}
-void Gfx::CEngine::SetState(int state, Gfx::Color color)
+bool Gfx::CEngine::AddQuick(int objRank, const Gfx::EngineObjLevel5& buffer,
+ std::string texName1, std::string texName2,
+ float min, float max, bool globalUpdate)
+{
+ // TODO!
+ return true;
+}
+
+Gfx::EngineObjLevel5* Gfx::CEngine::SearchTriangle(int objRank, const Gfx::Material& mat,
+ int state, std::string texName1,
+ std::string texName2, float min, float max)
+{
+ // TODO!
+ return nullptr;
+}
+
+void Gfx::CEngine::ChangeLOD()
+{
+ // TODO!
+}
+
+bool Gfx::CEngine::ChangeSecondTexture(int objRank, const std::string& texName2)
+{
+ // TODO!
+ return true;
+}
+
+int Gfx::CEngine::GetTotalTriangles(int objRank)
+{
+ // TODO!
+ return 0;
+}
+
+int Gfx::CEngine::GetTriangles(int objRank, float min, float max, Gfx::EngineTriangle* buffer, int size, float percent)
+{
+ // TODO!
+ return 0;
+}
+
+bool Gfx::CEngine::GetBBox(int objRank, Math::Vector& min, Math::Vector& max)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::ChangeTextureMapping(int objRank, const Gfx::Material& mat, int state,
+ const std::string& texName1, const std::string& texName2,
+ float min, float max, Gfx::EngineTextureMapping mode,
+ float au, float bu, float av, float bv)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::TrackTextureMapping(int objRank, const Gfx::Material& mat, int state,
+ const std::string& texName1, const std::string& texName2,
+ float min, float max, Gfx::EngineTextureMapping mode,
+ float pos, float factor, float tl, float ts, float tt)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectTransform(int objRank, const Math::Matrix& transform)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::GetObjectTransform(int objRank, Math::Matrix& transform)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectType(int objRank, Gfx::EngineObjectType type)
+{
+ // TODO!
+ return true;
+}
+
+Gfx::EngineObjectType Gfx::CEngine::GetObjectType(int objRank)
+{
+ // TODO!
+ return Gfx::ENG_OBJTYPE_FIX;
+}
+
+bool Gfx::CEngine::SetObjectTransparency(int objRank, float value)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::ShadowCreate(int objRank)
+{
+ // TODO!
+ return true;
+}
+
+void Gfx::CEngine::ShadowDelete(int objRank)
+{
+ // TODO!
+}
+
+bool Gfx::CEngine::SetObjectShadowHide(int objRank, bool hide)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectShadowType(int objRank, Gfx::EngineShadowType type)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectShadowPos(int objRank, const Math::Vector& pos)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectShadowNormal(int objRank, const Math::Vector& n)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectShadowAngle(int objRank, float angle)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectShadowRadius(int objRank, float radius)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectShadowIntensity(int objRank, float intensity)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectShadowHeight(int objRank, float h)
+{
+ // TODO!
+ return true;
+}
+
+float Gfx::CEngine::GetObjectShadowRadius(int objRank)
+{
+ // TODO!
+ return 0.0f;
+}
+
+bool Gfx::CEngine::GetHighlight(Math::Point &p1, Math::Point &p2)
+{
+ p1 = m_highlightP1;
+ p2 = m_highlightP2;
+ return m_highlight;
+}
+
+void Gfx::CEngine::SetHighlightRank(int *rankList)
+{
+ int i = 0;
+ while ( *rankList != -1 )
+ {
+ m_highlightRank[i++] = *rankList++;
+ }
+ m_highlightRank[i] = -1; // terminator
+}
+
+bool Gfx::CEngine::GetBBox2D(int objRank, Math::Point &min, Math::Point &max)
+{
+ min.x = 1000000.0f;
+ min.y = 1000000.0f;
+ max.x = -1000000.0f;
+ max.y = -1000000.0f;
+
+ for (int i = 0; i < 8; i++)
+ {
+ Math::Vector p;
+
+ if ( i & (1<<0) ) p.x = m_objects[objRank].bboxMin.x;
+ else p.x = m_objects[objRank].bboxMax.x;
+ if ( i & (1<<1) ) p.y = m_objects[objRank].bboxMin.y;
+ else p.y = m_objects[objRank].bboxMax.y;
+ if ( i & (1<<2) ) p.z = m_objects[objRank].bboxMin.z;
+ else p.z = m_objects[objRank].bboxMax.z;
+
+ Math::Vector pp;
+ if (TransformPoint(pp, objRank, p))
+ {
+ if (pp.x < min.x) min.x = pp.x;
+ if (pp.x > max.x) max.x = pp.x;
+ if (pp.y < min.y) min.y = pp.y;
+ if (pp.y > max.y) max.y = pp.y;
+ }
+ }
+
+ if ( min.x == 1000000.0f ||
+ min.y == 1000000.0f ||
+ max.x == -1000000.0f ||
+ max.y == -1000000.0f ) return false;
+
+ return true;
+}
+
+void Gfx::CEngine::GroundSpotFlush()
+{
+ // TODO
+}
+
+int Gfx::CEngine::GroundSpotCreate()
+{
+ // TODO!
+ return 0;
+}
+
+void Gfx::CEngine::GroundSpotDelete(int rank)
+{
+ // TODO!
+}
+
+bool Gfx::CEngine::SetObjectGroundSpotPos(int rank, const Math::Vector& pos)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectGroundSpotRadius(int rank, float radius)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectGroundSpotColor(int rank, const Gfx::Color& color)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectGroundSpotMinMax(int rank, float min, float max)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::SetObjectGroundSpotSmooth(int rank, float smooth)
+{
+ // TODO!
+ return true;
+}
+
+int Gfx::CEngine::GroundMarkCreate(Math::Vector pos, float radius,
+ float delay1, float delay2, float delay3,
+ int dx, int dy, char* table)
+{
+ // TODO!
+ return 0;
+}
+
+bool Gfx::CEngine::GroundMarkDelete(int rank)
+{
+ // TODO!
+ return true;
+}
+
+void Gfx::CEngine::ComputeDistance()
+{
+ // TODO!
+}
+
+void Gfx::CEngine::UpdateGeometry()
+{
+ // TODO!
+}
+
+void Gfx::CEngine::Update()
+{
+ ComputeDistance();
+ UpdateGeometry();
+}
+
+bool Gfx::CEngine::DetectBBox(int objRank, Math::Point mouse)
+{
+ // TODO!
+ return true;
+}
+
+int Gfx::CEngine::DetectObject(Math::Point mouse)
+{
+ // TODO!
+ return 0;
+}
+
+bool Gfx::CEngine::DetectTriangle(Math::Point mouse, Gfx::VertexTex2* triangle, int objRank, float& dist)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::IsVisible(int objRank)
+{
+ // TODO!
+ return true;
+}
+
+bool Gfx::CEngine::TransformPoint(Math::Vector& p2D, int objRank, Math::Vector p3D)
+{
+ // TODO!
+ return true;
+}
+
+
+
+/*******************************************************
+ Mode setting
+ *******************************************************/
+
+
+
+void Gfx::CEngine::SetState(int state, const Gfx::Color& color)
{
if ( state == m_lastState && color == m_lastColor )
return;
@@ -545,227 +1093,519 @@ void Gfx::CEngine::SetState(int state, Gfx::Color color)
m_device->SetGlobalAmbient(m_ambientColor[m_rankView]);
}
-bool Gfx::CEngine::ProcessEvent(const Event &event)
+void Gfx::CEngine::SetMaterial(const Gfx::Material &mat)
{
- if (event.type == EVENT_MOUSE_MOVE)
+ m_device->SetMaterial(mat);
+}
+
+void Gfx::CEngine::SetViewParams(const Math::Vector& eyePt, const Math::Vector& lookatPt,
+ const Math::Vector& upVec, float eyeDistance)
+{
+ m_eyePt = eyePt;
+ m_lookatPt = lookatPt;
+ m_eyeDirH = Math::RotateAngle(eyePt.x - lookatPt.x, eyePt.z - lookatPt.z);
+ m_eyeDirV = Math::RotateAngle(Math::DistanceProjected(eyePt, lookatPt), eyePt.y - lookatPt.y);
+
+ Math::LoadViewMatrix(m_matView, eyePt, lookatPt, upVec);
+
+ if (m_sound == nullptr)
+ m_sound = static_cast<CSoundInterface*>( m_iMan->SearchInstance(CLASS_SOUND) );
+
+ m_sound->SetListener(eyePt, lookatPt);
+}
+
+Gfx::Texture Gfx::CEngine::CreateTexture(const std::string &texName, const Gfx::TextureCreateParams &params)
+{
+ CImage img;
+ if (! img.Load(m_app->GetDataFilePath(m_texPath, texName)))
{
- m_mousePos = event.mouseMove.pos;
+ std::stringstream str;
+ str << "Couldn't load texture '" << texName << "': " << img.GetError();
+ m_error = str.str();
+ return Gfx::Texture(); // invalid texture
}
- else if (event.type == EVENT_KEY_DOWN)
+
+ Gfx::Texture result = m_device->CreateTexture(&img, params);
+
+ if (! result.valid)
{
- // !! Debug, to be removed later !!
+ std::stringstream str;
+ str << "Couldn't load texture '" << texName << "': " << m_device->GetError();
+ m_error = str.str();
+ return result;
+ }
- if (event.key.key == KEY(F1))
- {
- m_mouseVisible = !m_mouseVisible;
- m_app->SetSystemMouseVisible(! m_app->GetSystemMouseVisibile());
- }
- else if (event.key.key == KEY(F2))
- {
- int index = static_cast<int>(m_mouseType);
- m_mouseType = static_cast<Gfx::EngineMouseType>( (index + 1) % Gfx::ENG_MOUSE_COUNT );
- }
+ m_texNameMap[texName] = result;
+ m_revTexNameMap[result] = texName;
+
+ return result;
+}
+
+Gfx::Texture Gfx::CEngine::CreateTexture(const std::string &texName)
+{
+ return CreateTexture(texName, m_defaultTexParams);
+}
+
+void Gfx::CEngine::DestroyTexture(const std::string &texName)
+{
+ std::map<std::string, Gfx::Texture>::iterator it = m_texNameMap.find(texName);
+ if (it == m_texNameMap.end())
+ return;
+
+ std::map<Gfx::Texture, std::string>::iterator revIt = m_revTexNameMap.find((*it).second);
+
+ m_device->DestroyTexture((*it).second);
+
+ m_revTexNameMap.erase(revIt);
+ m_texNameMap.erase(it);
+}
+
+bool Gfx::CEngine::LoadTexture(const std::string& name, int stage)
+{
+ std::map<std::string, Gfx::Texture>::iterator it = m_texNameMap.find(name);
+ if (it != m_texNameMap.end())
+ {
+ m_device->SetTexture(stage, (*it).second);
+ return true;
}
- // By default, pass on all events
+ // TODO if not present...
+ return false;
+}
+
+bool Gfx::CEngine::LoadAllTextures()
+{
+ // TODO!
return true;
}
-bool Gfx::CEngine::Render()
+bool Gfx::CEngine::SetTexture(const std::string& name, int stage)
{
- m_statisticTriangle = 0;
+ // TODO!
+ return true;
+}
- m_lastState = -1;
- SetState(Gfx::ENG_RSTATE_NORMAL);
+void Gfx::CEngine::SetLimitLOD(int rank, float limit)
+{
+ m_limitLOD[rank] = limit;
+}
- m_device->BeginScene();
+float Gfx::CEngine::GetLimitLOD(int rank, bool last)
+{
+ float limit = 0.0f;
- SetUp3DView();
+ if (last)
+ {
+ limit = m_limitLOD[rank];
+ limit *= m_lastSize.w/640.0f; // limit further if large window!
+ limit += m_limitLOD[0]*(m_lastObjectDetail*2.0f);
+ }
+ else
+ {
+ limit = m_limitLOD[rank];
+ limit *= m_size.w/640.0f; // limit further if large window!
+ limit += m_limitLOD[0]*(m_objectDetail*2.0f);
+ }
- if (! Draw3DScene() )
- return false;
+ if (limit < 0.0f) limit = 0.0f;
- SetUpInterfaceView();
+ return limit;
+}
- if (! DrawInterface() )
- return false;
+void Gfx::CEngine::SetTerrainVision(float vision)
+{
+ m_terrainVision = vision;
+}
- m_device->EndScene();
+void Gfx::CEngine::SetFocus(float focus)
+{
+ m_focus = focus;
+ m_size = m_app->GetVideoConfig().size;
- return true;
+ float aspect = (static_cast<float>(m_size.h)) / m_size.w;
+ Math::LoadProjectionMatrix(m_matProj, m_focus, aspect, 0.5f, m_deepView[0]);
}
-void Gfx::CEngine::SetUp3DView()
+float Gfx::CEngine::GetFocus()
{
- // TODO
+ return m_focus;
}
-bool Gfx::CEngine::Draw3DScene()
+void Gfx::CEngine::SetGroundSpot(bool mode)
{
- // TODO
- return true;
+ m_groundSpotVisible = mode;
}
-void Gfx::CEngine::SetUpInterfaceView()
+bool Gfx::CEngine::GetGroundSpot()
{
- m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
- m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
- m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ return m_groundSpotVisible;
}
-bool Gfx::CEngine::DrawInterface()
+void Gfx::CEngine::SetShadow(bool mode)
{
- Gfx::VertexCol vertices[3] =
- {
- Gfx::VertexCol(Math::Vector( 0.25f, 0.25f, 0.0f), Gfx::Color(1.0f, 0.0f, 0.0f)),
- Gfx::VertexCol(Math::Vector( 0.75f, 0.25f, 0.0f), Gfx::Color(0.0f, 1.0f, 0.0f)),
- Gfx::VertexCol(Math::Vector( 0.5f, 0.75f, 0.0f), Gfx::Color(0.0f, 0.0f, 1.0f))
- };
+ m_shadowVisible = mode;
+}
+
+bool Gfx::CEngine::GetShadow()
+{
+ return m_shadowVisible;
+}
- m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLES, vertices, 3);
+void Gfx::CEngine::SetDirty(bool mode)
+{
+ m_dirty = mode;
+}
- DrawMouse();
+bool Gfx::CEngine::GetDirty()
+{
+ return m_dirty;
+}
- std::vector<Gfx::FontMetaChar> format;
- for (int i = 0; i < 10; ++i)
- format.push_back(Gfx::FONT_COLOBOT_BOLD | Gfx::FONT_HIGHLIGHT_CONST);
- for (int i = 0; i < 10; ++i)
- format.push_back(Gfx::FONT_COLOBOT_ITALIC | Gfx::FONT_HIGHLIGHT_KEY);
- for (int i = 0; i < 10; ++i)
- format.push_back(Gfx::FONT_COURIER | Gfx::FONT_HIGHLIGHT_LINK);
- for (int i = 0; i < 5; ++i)
- format.push_back(Gfx::FONT_COURIER_BOLD | Gfx::FONT_HIGHLIGHT_REM);
+void Gfx::CEngine::SetFog(bool mode)
+{
+ m_fog = mode;
+}
- m_text->DrawText("abcdefghijklmnopqrstuvwxyz ąęśćółńż", Gfx::FONT_COLOBOT, 15.0f, Math::Point(0.25f, 0.2f), 1.0f, Gfx::TEXT_ALIGN_LEFT, 0);
- float h = m_text->GetHeight(Gfx::FONT_COLOBOT, 15.0f);
- m_text->DrawText("abcdefghijklmnopqrstuvwxyz ąęśćółńż", format, 13.0f, Math::Point(0.25f, 0.2f - h), 1.0f, Gfx::TEXT_ALIGN_LEFT, 0);
+bool Gfx::CEngine::GetFog()
+{
+ return m_fog;
+}
- return true;
+bool Gfx::CEngine::GetStateColor()
+{
+ return m_stateColor;
}
-Math::IntSize Gfx::CEngine::GetWindowSize()
+void Gfx::CEngine::SetSecondTexture(int texNum)
{
- return m_size;
+ m_secondTexNum = texNum;
}
-Math::IntSize Gfx::CEngine::GetLastWindowSize()
+int Gfx::CEngine::GetSecondTexture()
{
- return m_lastSize;
+ return m_secondTexNum;
}
-/** Conversion of the position of the mouse from window coords to interface coords:
- - x: 0=left, 1=right
- - y: 0=down, 1=up */
-Math::Point Gfx::CEngine::WindowToInterfaceCoords(Math::IntPoint pos)
+void Gfx::CEngine::SetRankView(int rank)
{
- return Math::Point( static_cast<float>(pos.x) / static_cast<float>(m_size.w),
- 1.0f - static_cast<float>(pos.y) / static_cast<float>(m_size.h) );
+ if (rank < 0) rank = 0;
+ if (rank > 1) rank = 1;
+
+ if (m_rankView == 0 && rank == 1) // enters the water?
+ m_lightMan->AdaptLightColor(m_waterAddColor, +1.0f);
+
+ if (m_rankView == 1 && rank == 0) // out of the water?
+ m_lightMan->AdaptLightColor(m_waterAddColor, -1.0f);
+
+ m_rankView = rank;
}
-Math::IntPoint Gfx::CEngine::InterfaceToWindowCoords(Math::Point pos)
+int Gfx::CEngine::GetRankView()
{
- return Math::IntPoint(static_cast<int>(pos.x * m_size.w),
- static_cast<int>((1.0f - pos.y) * m_size.h));
+ return m_rankView;
}
-Math::Size Gfx::CEngine::WindowToInterfaceSize(Math::IntSize size)
+void Gfx::CEngine::SetDrawWorld(bool draw)
{
- return Math::Size( static_cast<float>(size.w) / static_cast<float>(m_size.w),
- static_cast<float>(size.h) / static_cast<float>(m_size.h) );
+ m_drawWorld = draw;
}
-Math::IntSize Gfx::CEngine::InterfaceToWindowSize(Math::Size size)
+void Gfx::CEngine::SetDrawFront(bool draw)
{
- return Math::IntSize(static_cast<int>(size.w * m_size.w),
- static_cast<int>(size.h * m_size.h));
+ m_drawFront = draw;
}
-std::string Gfx::CEngine::GetTextureDir()
+void Gfx::CEngine::SetAmbientColor(const Gfx::Color& color, int rank)
{
- return m_texPath;
+ m_ambientColor[rank] = color;
}
-void Gfx::CEngine::DrawMouse()
+Gfx::Color Gfx::CEngine::GetAmbientColor(int rank)
{
- if (! m_mouseVisible)
- return;
+ return m_ambientColor[rank];
+}
- if (m_app->GetSystemMouseVisibile())
- return;
+void Gfx::CEngine::SetWaterAddColor(const Gfx::Color& color)
+{
+ m_waterAddColor = color;
+}
- Gfx::Material material;
- material.diffuse = Gfx::Color(1.0f, 1.0f, 1.0f);
- material.ambient = Gfx::Color(0.5f, 0.5f, 0.5f);
+Gfx::Color Gfx::CEngine::GetWaterAddColor()
+{
+ return m_waterAddColor;
+}
- m_device->SetMaterial(material);
- m_device->SetTexture(0, m_miceTexture);
+void Gfx::CEngine::SetFogColor(const Gfx::Color& color, int rank)
+{
+ m_fogColor[rank] = color;
+}
- int index = static_cast<int>(m_mouseType);
+Gfx::Color Gfx::CEngine::GetFogColor(int rank)
+{
+ return m_fogColor[rank];
+}
- Math::Point pos = m_mousePos;
- pos.x = m_mousePos.x - (m_mice[index].hotPoint.x * m_mouseSize.x) / 32.0f;
- pos.y = m_mousePos.y - ((32.0f - m_mice[index].hotPoint.y) * m_mouseSize.y) / 32.0f;
+void Gfx::CEngine::SetDeepView(float length, int rank, bool ref)
+{
+ if (ref)
+ length *= m_clippingDistance;
- Math::Point shadowPos;
- shadowPos.x = pos.x + (4.0f/800.0f);
- shadowPos.y = pos.y - (3.0f/600.0f);
+ m_deepView[rank] = length;
+}
- SetState(Gfx::ENG_RSTATE_TCOLOR_WHITE);
- DrawMouseSprite(shadowPos, m_mouseSize, m_mice[index].iconShadow);
+float Gfx::CEngine::GetDeepView(int rank)
+{
+ return m_deepView[rank];
+}
- SetState(m_mice[index].mode1);
- DrawMouseSprite(pos, m_mouseSize, m_mice[index].icon1);
+void Gfx::CEngine::SetFogStart(float start, int rank)
+{
+ m_fogStart[rank] = start;
+}
- SetState(m_mice[index].mode2);
- DrawMouseSprite(pos, m_mouseSize, m_mice[index].icon2);
+float Gfx::CEngine::GetFogStart(int rank)
+{
+ return m_fogStart[rank];
}
-void Gfx::CEngine::DrawMouseSprite(Math::Point pos, Math::Point size, int icon)
+
+void Gfx::CEngine::SetBackground(const std::string& name, Gfx::Color up, Gfx::Color down,
+ Gfx::Color cloudUp, Gfx::Color cloudDown,
+ bool full, bool quarter)
{
- if (icon == -1)
- return;
+ m_backgroundName = name;
+ m_backgroundColorUp = up;
+ m_backgroundColorDown = down;
+ m_backgroundCloudUp = cloudUp;
+ m_backgroundCloudDown = cloudDown;
+ m_backgroundFull = full;
+ m_backgroundQuarter = quarter;
+}
- Math::Point p1 = pos;
- Math::Point p2 = p1 + size;
+void Gfx::CEngine::GetBackground(std::string& name, Gfx::Color& up, Gfx::Color& down,
+ Gfx::Color& cloudUp, Gfx::Color& cloudDown,
+ bool &full, bool &quarter)
+{
+ name = m_backgroundName;
+ up = m_backgroundColorUp;
+ down = m_backgroundColorDown;
+ cloudUp = m_backgroundCloudUp;
+ cloudDown = m_backgroundCloudDown;
+ full = m_backgroundFull;
+ quarter = m_backgroundQuarter;
+}
- float u1 = (32.0f / 256.0f) * (icon % 8);
- float v1 = (32.0f / 256.0f) * (icon / 8);
- float u2 = u1 + (32.0f / 256.0f);
- float v2 = v1 + (32.0f / 256.0f);
+void Gfx::CEngine::SetForegroundImageName(const std::string& name)
+{
+ if (! m_foregroundImageName.empty())
+ DestroyTexture(m_foregroundImageName);
- float dp = 0.5f / 256.0f;
- u1 += dp;
- v1 += dp;
- u2 -= dp;
- v2 -= dp;
+ m_foregroundImageName = name;
+}
- Math::Vector normal(0.0f, 0.0f, -1.0f);
+void Gfx::CEngine::SetOverFront(bool front)
+{
+ m_overFront = front;
+}
- Gfx::Vertex vertex[4] =
+void Gfx::CEngine::SetOverColor(const Gfx::Color& color, int mode)
+{
+ m_overColor = color;
+ m_overMode = mode;
+}
+
+void Gfx::CEngine::SetParticleDensity(float value)
+{
+ if (value < 0.0f) value = 0.0f;
+ if (value > 2.0f) value = 2.0f;
+ m_particleDensity = value;
+}
+
+float Gfx::CEngine::GetParticleDensity()
+{
+ return m_particleDensity;
+}
+
+float Gfx::CEngine::ParticleAdapt(float factor)
+{
+ if (m_particleDensity == 0.0f)
+ return 1000000.0f;
+
+ return factor / m_particleDensity;
+}
+
+void Gfx::CEngine::SetClippingDistance(float value)
+{
+ if (value < 0.5f) value = 0.5f;
+ if (value > 2.0f) value = 2.0f;
+ m_clippingDistance = value;
+}
+
+float Gfx::CEngine::GetClippingDistance()
+{
+ return m_clippingDistance;
+}
+
+void Gfx::CEngine::SetObjectDetail(float value)
+{
+ if ( value < 0.0f ) value = 0.0f;
+ if ( value > 2.0f ) value = 2.0f;
+ m_objectDetail = value;
+}
+
+float Gfx::CEngine::GetObjectDetail()
+{
+ return m_objectDetail;
+}
+
+void Gfx::CEngine::SetGadgetQuantity(float value)
+{
+ if (value < 0.0f) value = 0.0f;
+ if (value > 1.0f) value = 1.0f;
+
+ m_gadgetQuantity = value;
+}
+
+float Gfx::CEngine::GetGadgetQuantity()
+{
+ return m_gadgetQuantity;
+}
+
+void Gfx::CEngine::SetTextureQuality(int value)
+{
+ if (value < 0) value = 0;
+ if (value > 2) value = 2;
+
+ if (value != m_textureQuality)
{
- Gfx::Vertex(Math::Vector(p1.x, p1.y, 0.0f), normal, Math::Point(u1, v2)),
- Gfx::Vertex(Math::Vector(p2.x, p1.y, 0.0f), normal, Math::Point(u2, v2)),
- Gfx::Vertex(Math::Vector(p1.x, p2.y, 0.0f), normal, Math::Point(u1, v1)),
- Gfx::Vertex(Math::Vector(p2.x, p2.y, 0.0f), normal, Math::Point(u2, v1))
- };
+ m_textureQuality = value;
+ LoadAllTextures();
+ }
+}
- m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLE_STRIP, vertex, 4);
- AddStatisticTriangle(2);
+int Gfx::CEngine::GetTextureQuality()
+{
+ return m_textureQuality;
}
-bool Gfx::CEngine::GetPause()
+void Gfx::CEngine::SetTotoMode(bool present)
{
- return m_pause;
+ m_totoMode = present;
}
-Math::Vector Gfx::CEngine::GetLookatPt()
+bool Gfx::CEngine::GetTotoMode()
{
- return m_lookatPt;
+ return m_totoMode;
}
-Math::Vector Gfx::CEngine::GetEyePt()
+void Gfx::CEngine::SetLensMode(bool present)
{
- return m_eyePt;
+ m_lensMode = present;
+}
+
+bool Gfx::CEngine::GetLensMode()
+{
+ return m_lensMode;
+}
+
+void Gfx::CEngine::SetWaterMode(bool present)
+{
+ m_waterMode = present;
+}
+
+bool Gfx::CEngine::GetWaterMode()
+{
+ return m_waterMode;
+}
+
+void Gfx::CEngine::SetLightingMode(bool present)
+{
+ m_lightMode = present;
+}
+
+bool Gfx::CEngine::GetLightingMode()
+{
+ return m_lightMode;
+}
+
+void Gfx::CEngine::SetSkyMode(bool present)
+{
+ m_skyMode = present;
+}
+
+bool Gfx::CEngine::GetSkyMode()
+{
+ return m_skyMode;
+}
+
+void Gfx::CEngine::SetBackForce(bool present)
+{
+ m_backForce = present;
+}
+
+bool Gfx::CEngine::GetBackForce()
+{
+ return m_backForce;
+}
+
+void Gfx::CEngine::SetPlanetMode(bool present)
+{
+ m_planetMode = present;
+}
+
+bool Gfx::CEngine::GetPlanetMode()
+{
+ return m_planetMode;
+}
+
+void Gfx::CEngine::SetLightMode(bool present)
+{
+ m_lightMode = present;
+}
+
+bool Gfx::CEngine::GetLightMode()
+{
+ return m_lightMode;
+}
+
+void Gfx::CEngine::SetEditIndentMode(bool autoIndent)
+{
+ m_editIndentMode = autoIndent;
+}
+
+bool Gfx::CEngine::GetEditIndentMode()
+{
+ return m_editIndentMode;
+}
+
+void Gfx::CEngine::SetEditIndentValue(int value)
+{
+ m_editIndentValue = value;
+}
+
+int Gfx::CEngine::GetEditIndentValue()
+{
+ return m_editIndentValue;
+}
+
+void Gfx::CEngine::SetSpeed(float speed)
+{
+ m_speed = speed;
+}
+
+float Gfx::CEngine::GetSpeed()
+{
+ return m_speed;
+}
+
+void Gfx::CEngine::SetTracePrecision(float factor)
+{
+ m_tracePrecision = factor;
+}
+
+float Gfx::CEngine::GetTracePrecision()
+{
+ return m_tracePrecision;
}
void Gfx::CEngine::SetMouseVisible(bool visible)
@@ -798,133 +1638,1049 @@ Gfx::EngineMouseType Gfx::CEngine::GetMouseType()
return m_mouseType;
}
-void Gfx::CEngine::AddStatisticTriangle(int count)
+const Math::Matrix& Gfx::CEngine::GetMatView()
{
- m_statisticTriangle += count;
+ return m_matView;
}
-void Gfx::CEngine::SetShowStat(bool show)
+Math::Vector Gfx::CEngine::GetEyePt()
{
- m_showStats = show;
+ return m_eyePt;
}
-bool Gfx::CEngine::GetShowStat()
+Math::Vector Gfx::CEngine::GetLookatPt()
{
- return m_showStats;
+ return m_lookatPt;
}
-void Gfx::CEngine::SetFocus(float focus)
+float Gfx::CEngine::GetEyeDirH()
{
- m_focus = focus;
+ return m_eyeDirH;
}
-
-void Gfx::CEngine::SetOverColor(const Gfx::Color& color, int mode)
+float Gfx::CEngine::GetEyeDirV()
{
- // TODO!
+ return m_eyeDirV;
}
-void Gfx::CEngine::SetFogColor(const Gfx::Color& color, int rank)
+bool Gfx::CEngine::IsVisiblePoint(const Math::Vector &pos)
{
- // TODO!
+ return Math::Distance(m_eyePt, pos) <= m_deepView[0];
}
-Gfx::Color Gfx::CEngine::GetFogColor(int rank)
+void Gfx::CEngine::UpdateMatProj()
{
- // TODO!
- return Gfx::Color();
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProj);
}
-void Gfx::CEngine::SetViewParams(const Math::Vector& eyePt, const Math::Vector& lookatPt,
- const Math::Vector& upVec, float eyeDistance)
+void Gfx::CEngine::ApplyChange()
{
- // TODO!
+ m_deepView[0] /= m_lastClippingDistance;
+ m_deepView[1] /= m_lastClippingDistance;
+
+ SetFocus(m_focus);
+ ChangeLOD();
+
+ m_deepView[0] *= m_clippingDistance;
+ m_deepView[1] *= m_clippingDistance;
}
-void Gfx::CEngine::SetRankView(int rank)
+
+
+/*******************************************************
+ Rendering
+ *******************************************************/
+
+
+
+/**
+ This function sets up render states, clears the
+ viewport, and renders the scene. */
+void Gfx::CEngine::Render()
{
- m_rankView = rank;
+ /* TODO!
+ D3DObjLevel1* p1;
+ D3DObjLevel2* p2;
+ D3DObjLevel3* p3;
+ D3DObjLevel4* p4;
+ D3DObjLevel5* p5;
+ D3DVERTEX2* pv;
+ int l1, l2, l3, l4, l5, objRank;*/
+
+ if (! m_render) return;
+
+ m_statisticTriangle = 0;
+ m_lastState = -1;
+ m_lastColor = 999;
+ m_lastMaterial = Gfx::Material();
+
+ m_lightMan->UpdateLights();
+
+ Gfx::Color color;
+ if (m_skyMode && m_cloud->GetLevel() != 0.0f) // clouds?
+ color = m_backgroundCloudDown;
+ else
+ color = m_backgroundColorDown;
+
+ m_device->SetClearColor(color);
+
+ // Begin the scene
+ m_device->BeginScene();
+
+
+ if (m_drawWorld)
+ {
+ Draw3DScene();
+ }
+
+
+ DrawInterface();
+
+ // End the scene
+ m_device->EndScene();
}
-float Gfx::CEngine::GetEyeDirH()
+void Gfx::CEngine::Draw3DScene()
{
- return m_eyeDirH;
+ if (m_groundSpotVisible)
+ UpdateGroundSpotTextures();
+
+ DrawBackground(); // draws the background
+ if (m_planetMode) DrawPlanet(); // draws the planets
+ if (m_skyMode) m_cloud->Draw(); // draws the clouds
+
+
+ // Display the objects
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_TEST, true);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, true);
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, true);
+
+ float fogStart = m_deepView[m_rankView]*m_fogStart[m_rankView];
+ float fogEnd = m_deepView[m_rankView];
+ m_device->SetFogParams(Gfx::FOG_LINEAR, m_fogColor[m_rankView], fogStart, fogEnd, 1.0f);
+
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProj);
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matView);
+
+ if (m_waterMode) m_water->DrawBack(); // draws water background
+
+ if (m_shadowVisible)
+ {
+ // Draw the field
+ // TODO!
+ /*
+ p1 = m_objectPointer;
+ for ( l1=0 ; l1<p1->totalUsed ; l1++ )
+ {
+ p2 = p1->table[l1];
+ if ( p2 == 0 ) continue;
+ SetTexture(p2->texName1, 0);
+ SetTexture(p2->texName2, 1);
+ for ( l2=0 ; l2<p2->totalUsed ; l2++ )
+ {
+ p3 = p2->table[l2];
+ if ( p3 == 0 ) continue;
+ objRank = p3->objRank;
+ if ( m_objectParam[objRank].type != TYPETERRAIN ) continue;
+ if ( !m_objectParam[objRank].bDrawWorld ) continue;
+
+ {
+ D3DMATRIX mat = MAT_TO_D3DMAT(m_objectParam[objRank].transform);
+ m_pD3DDevice->SetTransform(D3DTRANSFORMSTATE_WORLD, &mat);
+ }
+
+ if ( !IsVisible(objRank) ) continue;
+ m_light->LightUpdate(m_objectParam[objRank].type);
+ for ( l3=0 ; l3<p3->totalUsed ; l3++ )
+ {
+ p4 = p3->table[l3];
+ if ( p4 == 0 ) continue;
+ if ( m_objectParam[objRank].distance < p4->min ||
+ m_objectParam[objRank].distance >= p4->max ) continue;
+ for ( l4=0 ; l4<p4->totalUsed ; l4++ )
+ {
+ p5 = p4->table[l4];
+ if ( p5 == 0 ) continue;
+ for ( l5=0 ; l5<p5->totalUsed ; l5++ )
+ {
+ p6 = p5->table[l5];
+ if ( p6 == 0 ) continue;
+ SetMaterial(p6->material);
+ SetState(p6->state);
+ if ( p6->type == D3DTYPE6T )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLELIST,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed/3;
+ }
+ if ( p6->type == D3DTYPE6S )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed-2;
+ }
+ }
+ }
+ }
+ }
+ }*/
+
+ // Draws the shadows
+ DrawShadow();
+ }
+
+ // Draw objects
+ bool transparent = false;
+ /* TODO!
+ p1 = m_objectPointer;
+ for ( l1=0 ; l1<p1->totalUsed ; l1++ )
+ {
+ p2 = p1->table[l1];
+ if ( p2 == 0 ) continue;
+ SetTexture(p2->texName1, 0);
+ SetTexture(p2->texName2, 1);
+ for ( l2=0 ; l2<p2->totalUsed ; l2++ )
+ {
+ p3 = p2->table[l2];
+ if ( p3 == 0 ) continue;
+ objRank = p3->objRank;
+ if ( m_bShadow && m_objectParam[objRank].type == TYPETERRAIN ) continue;
+ if ( !m_objectParam[objRank].bDrawWorld ) continue;
+
+ {
+ D3DMATRIX mat = MAT_TO_D3DMAT(m_objectParam[objRank].transform);
+ m_pD3DDevice->SetTransform(D3DTRANSFORMSTATE_WORLD, &mat);
+ }
+
+ if ( !IsVisible(objRank) ) continue;
+ m_light->LightUpdate(m_objectParam[objRank].type);
+ for ( l3=0 ; l3<p3->totalUsed ; l3++ )
+ {
+ p4 = p3->table[l3];
+ if ( p4 == 0 ) continue;
+ if ( m_objectParam[objRank].distance < p4->min ||
+ m_objectParam[objRank].distance >= p4->max ) continue;
+ for ( l4=0 ; l4<p4->totalUsed ; l4++ )
+ {
+ p5 = p4->table[l4];
+ if ( p5 == 0 ) continue;
+ for ( l5=0 ; l5<p5->totalUsed ; l5++ )
+ {
+ p6 = p5->table[l5];
+ if ( p6 == 0 ) continue;
+ SetMaterial(p6->material);
+ if ( m_objectParam[objRank].transparency != 0.0f ) // transparent ?
+ {
+ transparent = true;
+ continue;
+ }
+ SetState(p6->state);
+ if ( p6->type == D3DTYPE6T )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLELIST,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed/3;
+ }
+ if ( p6->type == D3DTYPE6S )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed-2;
+ }
+ }
+ }
+ }
+ }
+ }*/
+
+ if (transparent)
+ {
+ int tState = 0;
+ Gfx::Color tColor;
+ if (m_stateColor)
+ {
+ tState = Gfx::ENG_RSTATE_TTEXTURE_BLACK | Gfx::ENG_RSTATE_2FACE;
+ tColor = Gfx::Color(68.0f / 255.0f, 68.0f / 255.0f, 68.0f / 255.0f, 68.0f / 255.0f);
+ }
+ else
+ {
+ tState = Gfx::ENG_RSTATE_TCOLOR_BLACK;
+ tColor = Gfx::Color(136.0f / 255.0f, 136.0f / 255.0f, 136.0f / 255.0f, 136.0f / 255.0f);
+ }
+
+ // Draw transparent objects.
+ /* TODO!
+ p1 = m_objectPointer;
+ for ( l1=0 ; l1<p1->totalUsed ; l1++ )
+ {
+ p2 = p1->table[l1];
+ if ( p2 == 0 ) continue;
+ SetTexture(p2->texName1, 0);
+ SetTexture(p2->texName2, 1);
+ for ( l2=0 ; l2<p2->totalUsed ; l2++ )
+ {
+ p3 = p2->table[l2];
+ if ( p3 == 0 ) continue;
+ objRank = p3->objRank;
+ if ( m_bShadow && m_objectParam[objRank].type == TYPETERRAIN ) continue;
+ if ( !m_objectParam[objRank].bDrawWorld ) continue;
+
+ {
+ D3DMATRIX mat = MAT_TO_D3DMAT(m_objectParam[objRank].transform);
+ m_pD3DDevice->SetTransform(D3DTRANSFORMSTATE_WORLD, &mat);
+ }
+
+ if ( !IsVisible(objRank) ) continue;
+ m_light->LightUpdate(m_objectParam[objRank].type);
+ for ( l3=0 ; l3<p3->totalUsed ; l3++ )
+ {
+ p4 = p3->table[l3];
+ if ( p4 == 0 ) continue;
+ if ( m_objectParam[objRank].distance < p4->min ||
+ m_objectParam[objRank].distance >= p4->max ) continue;
+ for ( l4=0 ; l4<p4->totalUsed ; l4++ )
+ {
+ p5 = p4->table[l4];
+ if ( p5 == 0 ) continue;
+ for ( l5=0 ; l5<p5->totalUsed ; l5++ )
+ {
+ p6 = p5->table[l5];
+ if ( p6 == 0 ) continue;
+ SetMaterial(p6->material);
+ if ( m_objectParam[objRank].transparency == 0.0f ) continue;
+ SetState(tState, tColor);
+ if ( p6->type == D3DTYPE6T )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLELIST,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed/3;
+ }
+ if ( p6->type == D3DTYPE6S )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed-2;
+ }
+ }
+ }
+ }
+ }
+ } */
+ }
+
+ m_lightMan->UpdateLightsEnableState(Gfx::ENG_OBJTYPE_TERRAIN);
+
+ if (m_waterMode) m_water->DrawSurf(); // draws water surface
+
+ m_particle->DrawParticle(Gfx::SH_WORLD); // draws the particles of the 3D world
+ m_lightning->Draw(); // draws lightning
+ if (m_lensMode) DrawForegroundImage(); // draws the foreground
+ if (! m_overFront) DrawOverColor(); // draws the foreground color
}
-float Gfx::CEngine::GetEyeDirV()
+void Gfx::CEngine::DrawInterface()
{
- return m_eyeDirV;
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_TEST, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
+
+ // Draw the entire interface
+ CInterface* interface = static_cast<CInterface*>( m_iMan->SearchInstance(CLASS_INTERFACE) );
+ if (interface != nullptr)
+ interface->Draw();
+
+ m_particle->DrawParticle(Gfx::SH_INTERFACE); // draws the particles of the interface
+
+ // 3D objects drawn in front of interface
+ if (m_drawFront)
+ {
+ // Display the objects
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_TEST, true);
+
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProj);
+
+ m_device->SetGlobalAmbient(m_ambientColor[m_rankView]);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, true);
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, true);
+
+ float fogStart = m_deepView[m_rankView]*m_fogStart[m_rankView];
+ float fogEnd = m_deepView[m_rankView];
+ m_device->SetFogParams(Gfx::FOG_LINEAR, m_fogColor[m_rankView], fogStart, fogEnd, 1.0f);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matView);
+
+ // TODO!
+ /*
+ for (int l1 = 0; l1 < m_objectTree.size(); l1++)
+ {
+ Gfx::EngineObjLevel1* p1 = &m_objectTree[l1];
+ p2 = p1->table[l1];
+ if ( p2 == 0 ) continue;
+ SetTexture(p2->texName1, 0);
+ SetTexture(p2->texName2, 1);
+ for ( l2=0 ; l2<p2->totalUsed ; l2++ )
+ {
+ p3 = p2->table[l2];
+ if ( p3 == 0 ) continue;
+ objRank = p3->objRank;
+ if ( !m_objectParam[objRank].bDrawFront ) continue;
+
+ {
+ D3DMATRIX mat = MAT_TO_D3DMAT(m_objectParam[objRank].transform);
+ m_pD3DDevice->SetTransform(D3DTRANSFORMSTATE_WORLD, &mat);
+ }
+
+ if ( !IsVisible(objRank) ) continue;
+ m_light->LightUpdate(m_objectParam[objRank].type);
+ for ( l3=0 ; l3<p3->totalUsed ; l3++ )
+ {
+ p4 = p3->table[l3];
+ if ( p4 == 0 ) continue;
+ if ( m_objectParam[objRank].distance < p4->min ||
+ m_objectParam[objRank].distance >= p4->max ) continue;
+ for ( l4=0 ; l4<p4->totalUsed ; l4++ )
+ {
+ p5 = p4->table[l4];
+ if ( p5 == 0 ) continue;
+ for ( l5=0 ; l5<p5->totalUsed ; l5++ )
+ {
+ p6 = p5->table[l5];
+ if ( p6 == 0 ) continue;
+ SetMaterial(p6->material);
+ SetState(p6->state);
+ if ( p6->type == D3DTYPE6T )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLELIST,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed/3;
+ }
+ if ( p6->type == D3DTYPE6S )
+ {
+ pv = &p6->vertex[0];
+ m_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP,
+ D3DFVF_VERTEX2,
+ pv, p6->totalUsed,
+ NULL);
+ m_statisticTriangle += p6->totalUsed-2;
+ }
+ }
+ }
+ }
+ }
+ }*/
+
+ m_particle->DrawParticle(Gfx::SH_FRONT); // draws the particles of the 3D world
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_TEST, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
+ }
+
+ // Draw foreground color
+ if (m_overFront)
+ DrawOverColor();
+
+ // Mouse & highlight at the end
+ DrawMouse();
+ DrawHighlight();
}
-float Gfx::CEngine::GetClippingDistance()
+void Gfx::CEngine::UpdateGroundSpotTextures()
{
- return m_clippingDistance;
+ // TODO!
}
-bool Gfx::CEngine::GetGroundSpot()
+void Gfx::CEngine::DrawShadow()
{
- return m_groundSpotVisible;
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false);
+
+ Math::Matrix matrix;
+ matrix.LoadIdentity();
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, matrix);
+
+
+ Gfx::Material material;
+ material.diffuse = Gfx::Color(1.0f, 1.0f, 1.0f);
+ material.ambient = Gfx::Color(0.5f, 0.5f, 0.5f);
+ SetMaterial(material);
+
+ // TODO: wtf?
+ SetTexture("text.png");
+
+ Math::Point ts, ti;
+
+ float dp = 0.5f/256.0f;
+ ts.y = 192.0f/256.0f;
+ ti.y = 224.0f/256.0f;
+ ts.y += dp;
+ ti.y -= dp;
+
+ Math::Vector n(0.0f, 1.0f, 0.0f);
+
+ float startDeepView = m_deepView[m_rankView]*m_fogStart[m_rankView];
+ float endDeepView = m_deepView[m_rankView];
+
+ float lastIntensity = -1.0f;
+ for (int i = 0; i < static_cast<int>( m_shadow.size() ); i++)
+ {
+ if (m_shadow[i].hide) continue;
+
+ Math::Vector pos = m_shadow[i].pos; // pos = center of the shadow on the ground
+
+ if (m_eyePt.y == pos.y) continue; // camera at the same level?
+
+ float d = 0.0f;
+ float D = 0.0f;
+
+ // h is the height above the ground to which the shadow
+ // will be drawn.
+ if (m_eyePt.y > pos.y) // camera on?
+ {
+ float height = m_eyePt.y-pos.y;
+ float h = m_shadow[i].radius;
+ float max = height*0.5f;
+ if ( h > max ) h = max;
+ if ( h > 4.0f ) h = 4.0f;
+
+ D = Math::Distance(m_eyePt, pos);
+ if ( D >= endDeepView ) continue;
+ d = D*h/height;
+
+ pos.x += (m_eyePt.x-pos.x)*d/D;
+ pos.z += (m_eyePt.z-pos.z)*d/D;
+ pos.y += h;
+ }
+ else // camera underneath?
+ {
+ float height = pos.y-m_eyePt.y;
+ float h = m_shadow[i].radius;
+ float max = height*0.1f;
+ if ( h > max ) h = max;
+ if ( h > 4.0f ) h = 4.0f;
+
+ D = Math::Distance(m_eyePt, pos);
+ if ( D >= endDeepView ) continue;
+ d = D*h/height;
+
+ pos.x += (m_eyePt.x-pos.x)*d/D;
+ pos.z += (m_eyePt.z-pos.z)*d/D;
+ pos.y -= h;
+ }
+
+ // The hFactor decreases the intensity and size increases more
+ // the object is high relative to the ground.
+ float hFactor = m_shadow[i].height/20.0f;
+ if ( hFactor < 0.0f ) hFactor = 0.0f;
+ if ( hFactor > 1.0f ) hFactor = 1.0f;
+ hFactor = powf(1.0f-hFactor, 2.0f);
+ if ( hFactor < 0.2f ) hFactor = 0.2f;
+
+ float radius = m_shadow[i].radius*1.5f;
+ radius *= 2.0f-hFactor; // greater if high
+ radius *= 1.0f-d/D; // smaller if close
+
+
+ Math::Vector corner[4];
+
+ if (m_shadow[i].type == Gfx::ENG_SHADOW_NORM)
+ {
+ corner[0].x = +radius;
+ corner[0].z = +radius;
+ corner[0].y = 0.0f;
+
+ corner[1].x = -radius;
+ corner[1].z = +radius;
+ corner[1].y = 0.0f;
+
+ corner[2].x = +radius;
+ corner[2].z = -radius;
+ corner[2].y = 0.0f;
+
+ corner[3].x = -radius;
+ corner[3].z = -radius;
+ corner[3].y = 0.0f;
+
+ ts.x = 64.0f/256.0f;
+ ti.x = 96.0f/256.0f;
+ }
+ else
+ {
+ Math::Point rot;
+
+ rot = Math::RotatePoint(-m_shadow[i].angle, Math::Point(radius, radius));
+ corner[0].x = rot.x;
+ corner[0].z = rot.y;
+ corner[0].y = 0.0f;
+
+ rot = Math::RotatePoint(-m_shadow[i].angle, Math::Point(-radius, radius));
+ corner[1].x = rot.x;
+ corner[1].z = rot.y;
+ corner[1].y = 0.0f;
+
+ rot = Math::RotatePoint(-m_shadow[i].angle, Math::Point(radius, -radius));
+ corner[2].x = rot.x;
+ corner[2].z = rot.y;
+ corner[2].y = 0.0f;
+
+ rot = Math::RotatePoint(-m_shadow[i].angle, Math::Point(-radius, -radius));
+ corner[3].x = rot.x;
+ corner[3].z = rot.y;
+ corner[3].y = 0.0f;
+
+ if (m_shadow[i].type == Gfx::ENG_SHADOW_WORM)
+ {
+ ts.x = 96.0f/256.0f;
+ ti.x = 128.0f/256.0f;
+ }
+ else
+ {
+ ts.x = 64.0f/256.0f;
+ ti.x = 96.0f/256.0f;
+ }
+ }
+
+ corner[0] = Math::CrossProduct(corner[0], m_shadow[i].normal);
+ corner[1] = Math::CrossProduct(corner[1], m_shadow[i].normal);
+ corner[2] = Math::CrossProduct(corner[2], m_shadow[i].normal);
+ corner[3] = Math::CrossProduct(corner[3], m_shadow[i].normal);
+
+ corner[0] += pos;
+ corner[1] += pos;
+ corner[2] += pos;
+ corner[3] += pos;
+
+ ts.x += dp;
+ ti.x -= dp;
+
+ Gfx::Vertex vertex[4] =
+ {
+ Gfx::Vertex(corner[1], n, Math::Point(ts.x, ts.y)),
+ Gfx::Vertex(corner[0], n, Math::Point(ti.x, ts.y)),
+ Gfx::Vertex(corner[3], n, Math::Point(ts.x, ti.y)),
+ Gfx::Vertex(corner[2], n, Math::Point(ti.x, ti.y))
+ };
+
+ float intensity = (0.5f+m_shadow[i].intensity*0.5f)*hFactor;
+
+ // Decreases the intensity of the shade if you're in the area
+ // between the beginning and the end of the fog.
+ if ( D > startDeepView )
+ intensity *= 1.0f-(D-startDeepView)/(endDeepView-startDeepView);
+
+ if (intensity == 0.0f) continue;
+
+ if (lastIntensity != intensity) // intensity changed?
+ {
+ lastIntensity = intensity;
+ SetState(Gfx::ENG_RSTATE_TTEXTURE_WHITE, Gfx::Color(intensity, intensity, intensity, intensity));
+ }
+
+ m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLE_STRIP, vertex, 4);
+ AddStatisticTriangle(2);
+ }
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, true);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, true);
}
-void Gfx::CEngine::SetTerrain(Gfx::CTerrain* terrain)
+void Gfx::CEngine::DrawBackground()
{
- m_terrain = terrain;
+ if (m_skyMode && m_cloud->GetLevel() != 0.0f) // clouds ?
+ {
+ if (m_backgroundCloudUp != m_backgroundCloudDown) // degraded?
+ DrawBackgroundGradient(m_backgroundCloudUp, m_backgroundCloudDown);
+ }
+ else
+ {
+ if (m_backgroundColorUp != m_backgroundColorDown) // degraded?
+ DrawBackgroundGradient(m_backgroundColorUp, m_backgroundColorDown);
+ }
+
+ if (m_backForce || (m_skyMode && m_backgroundName[0] != 0) )
+ {
+ DrawBackgroundImage(); // image
+ }
}
-void Gfx::CEngine::SetTerrainVision(float vision)
+void Gfx::CEngine::DrawBackgroundGradient(const Gfx::Color& up, const Gfx::Color& down)
{
- // TODO!
+ Math::Point p1(0.0f, 0.5f);
+ Math::Point p2(1.0f, 1.0f);
+
+ Gfx::Color color[3] =
+ {
+ up,
+ down,
+ Gfx::Color(0.0f, 0.0f, 0.0f, 0.0f)
+ };
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_TEXTURING, false);
+
+ SetState(Gfx::ENG_RSTATE_NORMAL);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
+
+ Gfx::VertexCol vertex[4] =
+ {
+ Gfx::VertexCol(Math::Vector(p1.x, p1.y, 0.0f), color[1], color[2]),
+ Gfx::VertexCol(Math::Vector(p1.x, p2.y, 0.0f), color[0], color[2]),
+ Gfx::VertexCol(Math::Vector(p2.x, p1.y, 0.0f), color[1], color[2]),
+ Gfx::VertexCol(Math::Vector(p2.x, p2.y, 0.0f), color[0], color[2])
+ };
+
+ m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLE_STRIP, vertex, 4);
+ AddStatisticTriangle(2);
}
-bool Gfx::CEngine::LoadTexture(const std::string& name, int stage)
+void Gfx::CEngine::DrawBackgroundImageQuarter(Math::Point p1, Math::Point p2, const std::string& name)
{
- // TODO!
- return true;
+ Math::Vector n = Math::Vector(0.0f, 0.0f, -1.0f); // normal
+
+ float u1, u2, v1, v2;
+ if (m_backgroundFull)
+ {
+ u1 = 0.0f;
+ v1 = 0.0f;
+ u2 = 1.0f;
+ v2 = 1.0f;
+
+ if (m_backgroundQuarter)
+ {
+ u1 += 0.5f/512.0f;
+ v1 += 0.5f/384.0f;
+ u2 -= 0.5f/512.0f;
+ v2 -= 0.5f/384.0f;
+ }
+ }
+ else
+ {
+ float h = 0.5f; // visible area vertically (1=all)
+ float a = m_eyeDirV-Math::PI*0.15f;
+ if (a > Math::PI ) a -= Math::PI*2.0f; // a = -Math::PI..Math::PI
+ if (a > Math::PI/4.0f) a = Math::PI/4.0f;
+ if (a < -Math::PI/4.0f) a = -Math::PI/4.0f;
+
+ u1 = -m_eyeDirH/Math::PI;
+ u2 = u1+1.0f/Math::PI;
+
+ v1 = (1.0f-h)*(0.5f+a/(2.0f*Math::PI/4.0f))+0.1f;
+ v2 = v1+h;
+ }
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
+
+ SetTexture(name);
+ SetState(Gfx::ENG_RSTATE_WRAP);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
+
+ Gfx::Vertex vertex[4] =
+ {
+ Gfx::Vertex(Math::Vector(p1.x, p1.y, 0.0f), n, Math::Point(u1, v2)),
+ Gfx::Vertex(Math::Vector(p1.x, p2.y, 0.0f), n, Math::Point(u1, v1)),
+ Gfx::Vertex(Math::Vector(p2.x, p1.y, 0.0f), n, Math::Point(u2, v2)),
+ Gfx::Vertex(Math::Vector(p2.x, p2.y, 0.0f), n, Math::Point(u2, v1))
+ };
+
+ m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLE_STRIP, vertex, 4);
+ AddStatisticTriangle(2);
}
-float Gfx::CEngine::ParticleAdapt(float factor)
+void QuarterName(std::string& buffer, const std::string& name, int quarter)
{
- // TODO!
- return 0.0f;
+ size_t pos = name.find('.');
+ if (pos == std::string::npos)
+ {
+ buffer = name;
+ return;
+ }
+
+ buffer = name.substr(0, pos) + std::string(1, static_cast<char>('a' + quarter)) + name.substr(pos);
}
-bool Gfx::CEngine::SetObjectType(int objRank, Gfx::EngineObjectType type)
+void Gfx::CEngine::DrawBackgroundImage()
{
- // TODO!
- return true;
+ Math::Point p1, p2;
+ std::string name;
+
+ if (m_backgroundQuarter)
+ {
+ p1.x = 0.0f;
+ p1.y = 0.5f;
+ p2.x = 0.5f;
+ p2.y = 1.0f;
+ QuarterName(name, m_backgroundName, 0);
+ DrawBackgroundImageQuarter(p1, p2, name);
+
+ p1.x = 0.5f;
+ p1.y = 0.5f;
+ p2.x = 1.0f;
+ p2.y = 1.0f;
+ QuarterName(name, m_backgroundName, 1);
+ DrawBackgroundImageQuarter(p1, p2, name);
+
+ p1.x = 0.0f;
+ p1.y = 0.0f;
+ p2.x = 0.5f;
+ p2.y = 0.5f;
+ QuarterName(name, m_backgroundName, 2);
+ DrawBackgroundImageQuarter(p1, p2, name);
+
+ p1.x = 0.5f;
+ p1.y = 0.0f;
+ p2.x = 1.0f;
+ p2.y = 0.5f;
+ QuarterName(name, m_backgroundName, 3);
+ DrawBackgroundImageQuarter(p1, p2, name);
+ }
+ else
+ {
+ p1.x = 0.0f;
+ p1.y = 0.0f;
+ p2.x = 1.0f;
+ p2.y = 1.0f;
+ DrawBackgroundImageQuarter(p1, p2, m_backgroundName);
+ }
}
-bool Gfx::CEngine::SetObjectTransform(int objRank, const Math::Matrix& transform)
+void Gfx::CEngine::DrawPlanet()
{
- // TODO!
- return true;
+ if (! m_planet->PlanetExist()) return;
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
+
+ m_planet->Draw(); // draws the planets
}
-int Gfx::CEngine::CreateObject()
+void Gfx::CEngine::DrawForegroundImage()
{
- // TODO!
- return 0;
+ if (m_foregroundImageName.empty()) return;
+
+ Math::Vector n = Math::Vector(0.0f, 0.0f, -1.0f); // normal
+
+ Math::Point p1(0.0f, 0.0f);
+ Math::Point p2(1.0f, 1.0f);
+
+ float u1 = -m_eyeDirH/(Math::PI*0.6f)+Math::PI*0.5f;
+ float u2 = u1+0.50f;
+
+ float v1 = 0.2f;
+ float v2 = 1.0f;
+
+
+ Gfx::Vertex vertex[4] =
+ {
+ Gfx::Vertex(Math::Vector(p1.x, p1.y, 0.0f), n, Math::Point(u1, v2)),
+ Gfx::Vertex(Math::Vector(p1.x, p2.y, 0.0f), n, Math::Point(u1, v1)),
+ Gfx::Vertex(Math::Vector(p2.x, p1.y, 0.0f), n, Math::Point(u2, v2)),
+ Gfx::Vertex(Math::Vector(p2.x, p2.y, 0.0f), n, Math::Point(u2, v1))
+ };
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false );
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
+
+ SetTexture(m_foregroundImageName);
+ SetState(Gfx::ENG_RSTATE_CLAMP | Gfx::ENG_RSTATE_TTEXTURE_BLACK);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
+
+ m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLE_STRIP, vertex, 4);
+ AddStatisticTriangle(2);
}
-bool Gfx::CEngine::DeleteObject(int objRank)
+void Gfx::CEngine::DrawOverColor()
{
- // TODO!
- return true;
+ if (! m_stateColor) return;
+
+ // TODO: fuzzy compare?
+ if ( (m_overColor == Gfx::Color(0.0f, 0.0f, 0.0f, 0.0f) && m_overMode == Gfx::ENG_RSTATE_TCOLOR_BLACK) ||
+ (m_overColor == Gfx::Color(1.0f, 1.0f, 1.0f, 1.0f) && m_overMode == Gfx::ENG_RSTATE_TCOLOR_WHITE) ) return;
+
+ Math::Point p1(0.0f, 0.0f);
+ Math::Point p2(1.0f, 1.0f);
+
+ Gfx::Color color[3] =
+ {
+ m_overColor,
+ m_overColor,
+ Gfx::Color(0.0f, 0.0f, 0.0f, 0.0f)
+ };
+
+ m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
+ m_device->SetRenderState(Gfx::RENDER_STATE_TEXTURING, false);
+
+ SetState(m_overMode);
+
+ m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
+ m_device->SetTransform(Gfx::TRANSFORM_WORLD, m_matWorldInterface);
+
+ Gfx::VertexCol vertex[4] =
+ {
+ Gfx::VertexCol(Math::Vector(p1.x, p1.y, 0.0f), color[1],color[2]),
+ Gfx::VertexCol(Math::Vector(p1.x, p2.y, 0.0f), color[0],color[2]),
+ Gfx::VertexCol(Math::Vector(p2.x, p1.y, 0.0f), color[1],color[2]),
+ Gfx::VertexCol(Math::Vector(p2.x, p2.y, 0.0f), color[0],color[2])
+ };
+
+ m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLE_STRIP, vertex, 4);
+ AddStatisticTriangle(2);
}
-int Gfx::CEngine::GroundMarkCreate(Math::Vector pos, float radius, float delay1, float delay2, float delay3, int dx, int dy, char* table)
+void Gfx::CEngine::DrawHighlight()
{
- // TODO!
- return 0;
+ Math::Point min, max;
+ min.x = 1000000.0f;
+ min.y = 1000000.0f;
+ max.x = -1000000.0f;
+ max.y = -1000000.0f;
+
+ int i = 0;
+ while (m_highlightRank[i] != -1)
+ {
+ Math::Point omin, omax;
+ if (GetBBox2D(m_highlightRank[i++], omin, omax))
+ {
+ min.x = Math::Min(min.x, omin.x);
+ min.y = Math::Min(min.y, omin.y);
+ max.x = Math::Max(max.x, omax.x);
+ max.y = Math::Max(max.y, omax.y);
+ }
+ }
+
+ if ( min.x == 1000000.0f ||
+ min.y == 1000000.0f ||
+ max.x == -1000000.0f ||
+ max.y == -1000000.0f )
+ {
+ m_highlight = false; // not highlighted
+ }
+ else
+ {
+ m_highlightP1 = min;
+ m_highlightP2 = max;
+ m_highlight = true;
+ }
+
+ // TODO: draw highlight!
}
-bool Gfx::CEngine::AddQuick(int objRank, const Gfx::EngineObjLevel5& buffer, std::string texName1, std::string texName2, float min, float max, bool globalUpdate)
+void Gfx::CEngine::DrawMouse()
{
- // TODO!
- return false;
+ if (! m_mouseVisible)
+ return;
+
+ if (m_app->GetSystemMouseVisibile())
+ return;
+
+ Gfx::Material material;
+ material.diffuse = Gfx::Color(1.0f, 1.0f, 1.0f);
+ material.ambient = Gfx::Color(0.5f, 0.5f, 0.5f);
+
+ m_device->SetMaterial(material);
+ m_device->SetTexture(0, m_miceTexture);
+
+ int index = static_cast<int>(m_mouseType);
+
+ Math::Point pos = m_mousePos;
+ pos.x = m_mousePos.x - (m_mice[index].hotPoint.x * m_mouseSize.x) / 32.0f;
+ pos.y = m_mousePos.y - ((32.0f - m_mice[index].hotPoint.y) * m_mouseSize.y) / 32.0f;
+
+ Math::Point shadowPos;
+ shadowPos.x = pos.x + (4.0f/800.0f);
+ shadowPos.y = pos.y - (3.0f/600.0f);
+
+ SetState(Gfx::ENG_RSTATE_TCOLOR_WHITE);
+ DrawMouseSprite(shadowPos, m_mouseSize, m_mice[index].iconShadow);
+
+ SetState(m_mice[index].mode1);
+ DrawMouseSprite(pos, m_mouseSize, m_mice[index].icon1);
+
+ SetState(m_mice[index].mode2);
+ DrawMouseSprite(pos, m_mouseSize, m_mice[index].icon2);
}
-void Gfx::CEngine::Update()
+void Gfx::CEngine::DrawMouseSprite(Math::Point pos, Math::Point size, int icon)
{
- // TODO!
+ if (icon == -1)
+ return;
+
+ Math::Point p1 = pos;
+ Math::Point p2 = p1 + size;
+
+ float u1 = (32.0f / 256.0f) * (icon % 8);
+ float v1 = (32.0f / 256.0f) * (icon / 8);
+ float u2 = u1 + (32.0f / 256.0f);
+ float v2 = v1 + (32.0f / 256.0f);
+
+ float dp = 0.5f / 256.0f;
+ u1 += dp;
+ v1 += dp;
+ u2 -= dp;
+ v2 -= dp;
+
+ Math::Vector normal(0.0f, 0.0f, -1.0f);
+
+ Gfx::Vertex vertex[4] =
+ {
+ Gfx::Vertex(Math::Vector(p1.x, p1.y, 0.0f), normal, Math::Point(u1, v2)),
+ Gfx::Vertex(Math::Vector(p2.x, p1.y, 0.0f), normal, Math::Point(u2, v2)),
+ Gfx::Vertex(Math::Vector(p1.x, p2.y, 0.0f), normal, Math::Point(u1, v1)),
+ Gfx::Vertex(Math::Vector(p2.x, p2.y, 0.0f), normal, Math::Point(u2, v1))
+ };
+
+ m_device->DrawPrimitive(Gfx::PRIMITIVE_TRIANGLE_STRIP, vertex, 4);
+ AddStatisticTriangle(2);
}
diff --git a/src/graphics/engine/engine.h b/src/graphics/engine/engine.h
index e61aca6..d01a679 100644
--- a/src/graphics/engine/engine.h
+++ b/src/graphics/engine/engine.h
@@ -1,5 +1,5 @@
// * This file is part of the COLOBOT source code
-// * Copyright (C) 2001-2008, Daniel ROUX & EPSITEC SA, www.epsitec.ch
+// * Copyright (C) 2001-2008, Daniel ROUX& EPSITEC SA, www.epsitec.ch
// * Copyright (C) 2012, Polish Portal of Colobot (PPC)
// *
// * This program is free software: you can redistribute it and/or modify
@@ -41,7 +41,7 @@
class CApplication;
class CInstanceManager;
class CObject;
-class CSound;
+class CSoundInterface;
namespace Gfx {
@@ -310,12 +310,14 @@ struct EngineGroundSpot
\brief Phase of life of an EngineGroundMark */
enum EngineGroundMarkPhase
{
+ //! Null phase
+ ENG_GR_MARK_PHASE_NULL = 0,
//! Increase
ENG_GR_MARK_PHASE_INC = 1,
//! Fixed
ENG_GR_MARK_PHASE_FIX = 2,
//! Decrease
- ENG_GR_MARK_PHASE_DEC = 2
+ ENG_GR_MARK_PHASE_DEC = 3
};
/**
@@ -526,17 +528,24 @@ struct EngineMouse
class CEngine
{
public:
- CEngine(CInstanceManager *iMan, CApplication *app);
+ CEngine(CInstanceManager* iMan, CApplication* app);
~CEngine();
//! Returns the last error encountered
std::string GetError();
//! Sets the device to be used
- void SetDevice(Gfx::CDevice *device);
+ void SetDevice(Gfx::CDevice* device);
//! Returns the current device
Gfx::CDevice* GetDevice();
+ //! Sets the terrain object
+ void SetTerrain(Gfx::CTerrain* terrain);
+
+ //! Returns the text rendering engine
+ CText* GetText();
+
+
//! Performs the initialization; must be called after device was set
bool Create();
//! Frees all resources before exit
@@ -545,102 +554,122 @@ public:
//! Resets some states and flushes textures after device was changed (e.g. resoulution changed)
void ResetAfterDeviceChanged();
- void SetTerrain(Gfx::CTerrain* terrain);
+
+ //! Called once per frame, the call is the entry point for rendering
+ void Render();
+
//! Processes incoming event
- bool ProcessEvent(const Event &event);
+ bool ProcessEvent(const Event& event);
- //! Renders a single frame
- bool Render();
+ //! Called once per frame, the call is the entry point for animating the scene
+ void FrameMove(float rTime);
+ //! Evolved throughout the game
+ void StepSimulation(float rTime);
+ //! Initialize timestamps at the beginning of animation
+ void TimeInit();
+ //! Suspend animation
+ void TimeEnterGel();
+ //! Resume animation
+ void TimeExitGel();
+ //! Returns the relative time since last animation update
+ float TimeGet();
- //! Converts window coords to interface coords
- Math::Point WindowToInterfaceCoords(Math::IntPoint pos);
- //! Converts interface coords to window coords
- Math::IntPoint InterfaceToWindowCoords(Math::Point pos);
- //! Converts window size to interface size
- Math::Size WindowToInterfaceSize(Math::IntSize size);
- //! Converts interface size to window size
- Math::IntSize InterfaceToWindowSize(Math::Size size);
+ //! Writes a screenshot containing the current frame
+ bool WriteScreenShot(const std::string& fileName, int width, int height);
- std::string GetTextureDir();
- bool WriteProfile();
+ //! Reads settings from INI
+ bool ReadSettings();
+ //! Writes settings to INI
+ bool WriteSettings();
+ //@{
+ //! Management of game pause mode
void SetPause(bool pause);
bool GetPause();
+ //@}
+ //@{
+ //! Management of lock for the duration of movie sequence
void SetMovieLock(bool lock);
bool GetMovieLock();
+ //@}
- void SetShowStat(bool show);
- bool GetShowStat();
+ //@{
+ //! Management of displaying statistic information
+ void SetShowStats(bool show);
+ bool GetShowStats();
+ //@}
+ //! Enables/disables rendering
void SetRenderEnable(bool enable);
- int OneTimeSceneInit();
- int InitDeviceObjects();
- int DeleteDeviceObjects();
- int RestoreSurfaces();
- int FrameMove(float rTime);
- void StepSimulation(float rTime);
- int FinalCleanup();
+ //! Returns current size of viewport window
+ Math::IntSize GetWindowSize();
+ //! Returns the last size of viewport window
+ Math::IntSize GetLastWindowSize();
+
+ //! Converts window coords to interface coords
+ /** Conversion of the position of the mouse from window coords to interface coords:
+ - x: 0=left, 1=right
+ - y: 0=down, 1=up */
+ Math::Point WindowToInterfaceCoords(Math::IntPoint pos);
+ //! Converts interface coords to window coords
+ Math::IntPoint InterfaceToWindowCoords(Math::Point pos);
+
+ //! Converts window size to interface size
+ Math::Size WindowToInterfaceSize(Math::IntSize size);
+ //! Converts interface size to window size
+ Math::IntSize InterfaceToWindowSize(Math::Size size);
+
+ //! Returns the name of directory with textures
+ std::string GetTextureDir();
+
+ //! Increments the triangle counter for the current frame
void AddStatisticTriangle(int nb);
+ //! Returns the number of triangles in current frame
int GetStatisticTriangle();
- void SetHiliteRank(int *rankList);
- bool GetHilite(Math::Point &p1, Math::Point &p2);
- bool GetSpriteCoord(int &x, int &y);
- void SetInfoText(int line, char* text);
- char* GetInfoText(int line);
- void FirstExecuteAdapt(bool first);
- bool GetFullScreen();
- Math::Matrix* GetMatView();
- Math::Matrix* GetMatLeftView();
- Math::Matrix* GetMatRightView();
+ /* *************** Object management *************** */
- void TimeInit();
- void TimeEnterGel();
- void TimeExitGel();
- float TimeGet();
-
- int GetRestCreate();
int CreateObject();
void FlushObject();
bool DeleteObject(int objRank);
bool SetDrawWorld(int objRank, bool draw);
bool SetDrawFront(int objRank, bool draw);
- bool AddTriangle(int objRank, Gfx::VertexTex2* vertex, int nb, const Gfx::Material &mat,
+ bool AddTriangle(int objRank, Gfx::VertexTex2* vertex, int nb, const Gfx::Material& mat,
int state, std::string texName1, std::string texName2,
float min, float max, bool globalUpdate);
- bool AddSurface(int objRank, Gfx::VertexTex2* vertex, int nb, const Gfx::Material &mat,
+ bool AddSurface(int objRank, Gfx::VertexTex2* vertex, int nb, const Gfx::Material& mat,
int state, std::string texName1, std::string texName2,
float min, float max, bool globalUpdate);
bool AddQuick(int objRank, const Gfx::EngineObjLevel5& buffer,
std::string texName1, std::string texName2,
float min, float max, bool globalUpdate);
- Gfx::EngineObjLevel5* SearchTriangle(int objRank, const Gfx::Material &mat,
+ Gfx::EngineObjLevel5* SearchTriangle(int objRank, const Gfx::Material& mat,
int state, std::string texName1, std::string texName2,
float min, float max);
void ChangeLOD();
- bool ChangeSecondTexture(int objRank, char* texName2);
+ bool ChangeSecondTexture(int objRank, const std::string& texName2);
int GetTotalTriangles(int objRank);
int GetTriangles(int objRank, float min, float max, Gfx::EngineTriangle* buffer, int size, float percent);
- bool GetBBox(int objRank, Math::Vector &min, Math::Vector &max);
- bool ChangeTextureMapping(int objRank, const Gfx::Material &mat, int state,
- const std::string &texName1, const std::string &texName2,
+ bool GetBBox(int objRank, Math::Vector& min, Math::Vector& max);
+ bool ChangeTextureMapping(int objRank, const Gfx::Material& mat, int state,
+ const std::string& texName1, const std::string& texName2,
float min, float max, Gfx::EngineTextureMapping mode,
float au, float bu, float av, float bv);
- bool TrackTextureMapping(int objRank, const Gfx::Material &mat, int state,
- const std::string &texName1, const std::string &texName2,
+ bool TrackTextureMapping(int objRank, const Gfx::Material& mat, int state,
+ const std::string& texName1, const std::string& texName2,
float min, float max, Gfx::EngineTextureMapping mode,
float pos, float factor, float tl, float ts, float tt);
- bool SetObjectTransform(int objRank, const Math::Matrix &transform);
- bool GetObjectTransform(int objRank, Math::Matrix &transform);
+ bool SetObjectTransform(int objRank, const Math::Matrix& transform);
+ bool GetObjectTransform(int objRank, Math::Matrix& transform);
bool SetObjectType(int objRank, Gfx::EngineObjectType type);
Gfx::EngineObjectType GetObjectType(int objRank);
bool SetObjectTransparency(int objRank, float value);
@@ -649,20 +678,25 @@ public:
void ShadowDelete(int objRank);
bool SetObjectShadowHide(int objRank, bool hide);
bool SetObjectShadowType(int objRank, Gfx::EngineShadowType type);
- bool SetObjectShadowPos(int objRank, const Math::Vector &pos);
- bool SetObjectShadowNormal(int objRank, const Math::Vector &n);
+ bool SetObjectShadowPos(int objRank, const Math::Vector& pos);
+ bool SetObjectShadowNormal(int objRank, const Math::Vector& n);
bool SetObjectShadowAngle(int objRank, float angle);
bool SetObjectShadowRadius(int objRank, float radius);
bool SetObjectShadowIntensity(int objRank, float intensity);
bool SetObjectShadowHeight(int objRank, float h);
float GetObjectShadowRadius(int objRank);
+ //! Lists the ranks of objects and subobjects selected
+ void SetHighlightRank(int* rankList);
+ //! Returns the highlighted rectangle
+ bool GetHighlight(Math::Point& p1, Math::Point& p2);
+
void GroundSpotFlush();
int GroundSpotCreate();
void GroundSpotDelete(int rank);
- bool SetObjectGroundSpotPos(int rank, const Math::Vector &pos);
+ bool SetObjectGroundSpotPos(int rank, const Math::Vector& pos);
bool SetObjectGroundSpotRadius(int rank, float radius);
- bool SetObjectGroundSpotColor(int rank, const Gfx::Color &color);
+ bool SetObjectGroundSpotColor(int rank, const Gfx::Color& color);
bool SetObjectGroundSpotMinMax(int rank, float min, float max);
bool SetObjectGroundSpotSmooth(int rank, float smooth);
@@ -671,217 +705,347 @@ public:
int dx, int dy, char* table);
bool GroundMarkDelete(int rank);
+ //! Updates the state after creating objects
void Update();
- void SetViewParams(const Math::Vector &eyePt, const Math::Vector &lookatPt,
- const Math::Vector &upVec, float eyeDistance);
- Gfx::Texture CreateTexture(const std::string &texName,
- const Gfx::TextureCreateParams &params);
- Gfx::Texture CreateTexture(const std::string &texName);
- void DestroyTexture(const std::string &texName);
+ /* *************** Mode setting *************** */
+
+ //! Sets the current rendering state
+ void SetState(int state, const Gfx::Color& color = Gfx::Color(1.0f, 1.0f, 1.0f, 1.0f));
+
+ //! Sets the current material
+ void SetMaterial(const Gfx::Material& mat);
+
+ //! Specifies the location and direction of view
+ void SetViewParams(const Math::Vector& eyePt, const Math::Vector& lookatPt,
+ const Math::Vector& upVec, float eyeDistance);
- bool LoadTexture(const std::string &name, int stage = 0);
+ Gfx::Texture CreateTexture(const std::string& texName,
+ const Gfx::TextureCreateParams& params);
+ Gfx::Texture CreateTexture(const std::string& texName);
+ void DestroyTexture(const std::string& texName);
+ bool LoadTexture(const std::string& name, int stage = 0);
bool LoadAllTextures();
+ bool SetTexture(const std::string& name, int stage = 0);
+ //@{
+ //! Border management (distance limits) depends of the resolution (LOD = level-of-detail)
void SetLimitLOD(int rank, float limit);
float GetLimitLOD(int rank, bool last=false);
+ //@}
+ //! Defines of the distance field of vision
void SetTerrainVision(float vision);
+ //@{
+ //! Management of camera angle
+ /**
+ 0.75 = normal
+ 1.50 = wide-angle */
+ void SetFocus(float focus);
+ float GetFocus();
+ //@}
+
+ //@{
+ //! Management of the global mode of marking
void SetGroundSpot(bool mode);
bool GetGroundSpot();
+ //@}
+
+ //@{
+ //! Management of the global mode of shading
void SetShadow(bool mode);
bool GetShadow();
+ //@}
+
+ //@{
+ //! Management of the global mode of contamination
void SetDirty(bool mode);
bool GetDirty();
+ //@}
+
+ //@{
+ //! Management of the global mode of horizontal fog patches
void SetFog(bool mode);
bool GetFog();
+ //@}
+
+ //! Indicates whether it is possible to give a color SetState
bool GetStateColor();
+ //@{
+ //! Management of the global mode of secondary texturing
void SetSecondTexture(int texNum);
int GetSecondTexture();
+ //@}
+ //@{
+ //! Management of view mode
void SetRankView(int rank);
int GetRankView();
+ //@}
+ //! Whether to draw the world
void SetDrawWorld(bool draw);
+
+ //! Whether to draw the world on the interface
void SetDrawFront(bool draw);
- void SetAmbientColor(const Gfx::Color &color, int rank = 0);
+ //@{
+ //! Ambient color management
+ void SetAmbientColor(const Gfx::Color& color, int rank = 0);
Gfx::Color GetAmbientColor(int rank = 0);
+ //@}
- void SetWaterAddColor(const Gfx::Color &color);
+ //@{
+ //! Color management under water
+ void SetWaterAddColor(const Gfx::Color& color);
Gfx::Color GetWaterAddColor();
+ //@}
- void SetFogColor(const Gfx::Color &color, int rank = 0);
+ //@{
+ //! Management of the fog color
+ void SetFogColor(const Gfx::Color& color, int rank = 0);
Gfx::Color GetFogColor(int rank = 0);
+ //@}
+ //@{
+ //! Management of the depth of field.
+ /** Beyond this distance, nothing is visible.
+ Shortly (according SetFogStart), one enters the fog. */
void SetDeepView(float length, int rank = 0, bool ref=false);
float GetDeepView(int rank = 0);
+ //@}
+
+ //@{
+ //! Management the start of fog.
+ /** With 0.0, the fog from the point of view (fog max).
+ With 1.0, the fog from the depth of field (no fog). */
void SetFogStart(float start, int rank = 0);
float GetFogStart(int rank = 0);
+ //@}
- void SetBackground(const std::string &name, Gfx::Color up = Gfx::Color(), Gfx::Color down = Gfx::Color(),
+ //@{
+ //! Management of the background image to use
+ void SetBackground(const std::string& name, Gfx::Color up = Gfx::Color(), Gfx::Color down = Gfx::Color(),
Gfx::Color cloudUp = Gfx::Color(), Gfx::Color cloudDown = Gfx::Color(),
bool full = false, bool quarter = false);
- void GetBackground(const std::string &name, Gfx::Color &up, Gfx::Color &down,
- Gfx::Color &cloudUp, Gfx::Color &cloudDown,
- bool &full, bool &quarter);
- void SetFrontsizeName(char *name);
+ void GetBackground(std::string& name, Gfx::Color& up, Gfx::Color& down,
+ Gfx::Color& cloudUp, Gfx::Color& cloudDown,
+ bool& full, bool& quarter);
+ //@}
+
+ //! Specifies the foreground image
+ void SetForegroundImageName(const std::string& name);
+ //! Specifies whether to draw the foreground
void SetOverFront(bool front);
- void SetOverColor(const Gfx::Color &color = Gfx::Color(), int mode = ENG_RSTATE_TCOLOR_BLACK);
+ //! Sets the foreground overlay color
+ void SetOverColor(const Gfx::Color& color = Gfx::Color(), int mode = ENG_RSTATE_TCOLOR_BLACK);
+ //@{
+ //! Management of the particle density
void SetParticleDensity(float value);
float GetParticleDensity();
+ //@}
+
+ //! Adapts particle factor according to particle density
float ParticleAdapt(float factor);
+ //@{
+ //! Management of the distance of clipping.
void SetClippingDistance(float value);
float GetClippingDistance();
+ //@}
+ //@{
+ //! Management of objects detals.
void SetObjectDetail(float value);
float GetObjectDetail();
+ //@}
+ //@{
+ //! The amount of management objects gadgets
void SetGadgetQuantity(float value);
float GetGadgetQuantity();
+ //@}
+ //@{
+ //! Management the quality of textures
void SetTextureQuality(int value);
int GetTextureQuality();
+ //@}
+ //@{
+ //! Management mode of toto
void SetTotoMode(bool present);
bool GetTotoMode();
+ //@}
+ //@{
+ //! Management the mode of foreground
void SetLensMode(bool present);
bool GetLensMode();
+ //@}
+ //@{
+ //! Management the mode of water
void SetWaterMode(bool present);
bool GetWaterMode();
+ //@}
void SetLightingMode(bool present);
bool GetLightingMode();
+ //@{
+ //! Management the mode of sky
void SetSkyMode(bool present);
bool GetSkyMode();
+ //@}
+ //@{
+ //! Management the mode of background
void SetBackForce(bool present);
bool GetBackForce();
+ //@}
+ //@{
+ //! Management the mode of planets
void SetPlanetMode(bool present);
bool GetPlanetMode();
+ //@}
+ //@{
+ //! Managing the mode of dynamic lights.
void SetLightMode(bool present);
bool GetLightMode();
+ //@}
+ //@{
+ // TODO: move to more appropriate class ?
+ //! Management of the indentation mode while editing (CEdit)
void SetEditIndentMode(bool autoIndent);
bool GetEditIndentMode();
+ //@}
+ //@{
+ // TODO: move to more appropriate class ?
+ //! Management of tab indent when editing (CEdit)
void SetEditIndentValue(int value);
int GetEditIndentValue();
+ //@}
+ //@{
+ //! Management of game speed
void SetSpeed(float speed);
float GetSpeed();
+ //@{
+ //! Management of precision of robot tracks
void SetTracePrecision(float factor);
float GetTracePrecision();
+ //@}
- void SetFocus(float focus);
- float GetFocus();
- Math::Vector GetEyePt();
- Math::Vector GetLookatPt();
- float GetEyeDirH();
- float GetEyeDirV();
- Math::IntSize GetWindowSize();
- Math::IntSize GetLastWindowSize();
- void UpdateMatProj();
-
- void ApplyChange();
-
- void FlushPressKey();
- void ResetKey();
- void SetKey(int keyRank, int option, int key);
- int GetKey(int keyRank, int option);
-
- void SetJoystick(bool enable);
- bool GetJoystick();
-
- void SetDebugMode(bool mode);
- bool GetDebugMode();
- bool GetSetupMode();
-
- bool IsVisiblePoint(const Math::Vector &pos);
-
- int DetectObject(Math::Point mouse);
- void SetState(int state, Gfx::Color color = Gfx::Color(1.0f, 1.0f, 1.0f, 1.0f));
- void SetTexture(const std::string &name, int stage = 0);
- void SetMaterial(const Gfx::Material &mat);
-
+ //@{
+ //! Management of mouse cursor visibility
void SetMouseVisible(bool show);
bool GetMouseVisible();
+ //@}
+
+ //@{
+ //! Management of mouse cursor position
void SetMousePos(Math::Point pos);
Math::Point GetMousePos();
+ //@}
+
+ //@{
+ //! Management of mouse cursor type
void SetMouseType(Gfx::EngineMouseType type);
Gfx::EngineMouseType GetMouseType();
+ //@}
- CText* GetText();
+ //! Returns the view matrix
+ const Math::Matrix& GetMatView();
+ //! Returns the camera center point
+ Math::Vector GetEyePt();
+ //! Returns the camera target point
+ Math::Vector GetLookatPt();
+ //! Returns the horizontal direction angle of view
+ float GetEyeDirH();
+ //! Returns the vertical direction angle of view
+ float GetEyeDirV();
+ //! Indicates whether a point is visible
+ bool IsVisiblePoint(const Math::Vector& pos);
- bool ChangeColor(char *name, Gfx::Color colorRef1, Gfx::Color colorNew1,
- Gfx::Color colorRef2, Gfx::Color colorNew2,
- float tolerance1, float tolerance2,
- Math::Point ts, Math::Point ti,
- Math::Point *pExclu=0, float shift=0.0f, bool hSV=false);
- bool OpenImage(char *name);
- bool CopyImage();
- bool LoadImage();
- bool ScrollImage(int dx, int dy);
- bool SetDot(int x, int y, Gfx::Color color);
- bool CloseImage();
- bool WriteScreenShot(char *filename, int width, int height);
- //bool GetRenderDC(HDC &hDC);
- //bool ReleaseRenderDC(HDC &hDC);
- //PBITMAPINFO CreateBitmapInfoStruct(HBITMAP hBmp);
- //bool CreateBMPFile(LPTSTR pszFile, PBITMAPINFO pbi, HBITMAP hBMP, HDC hDC);
+ //! Resets the projection matrix after changes
+ void UpdateMatProj();
-protected:
+ //! Updates the scene after a change of parameters
+ void ApplyChange();
- void SetUp3DView();
- bool Draw3DScene();
+protected:
+ //! Prepares the interface for 3D scene
+ void Draw3DScene();
+ //! Draws the user interface over the scene
+ void DrawInterface();
- void SetUpInterfaceView();
- bool DrawInterface();
+ //! Updates the textures used for drawing ground spot
+ void UpdateGroundSpotTextures();
- void DrawGroundSpot();
+ //! Draws shadows
void DrawShadow();
+ //! Draws the gradient background
void DrawBackground();
- void DrawBackgroundGradient(Gfx::Color up, Gfx::Color down);
- void DrawBackgroundImageQuarter(Math::Point p1, Math::Point p2, char *name);
+ //! Draws the gradient background
+ void DrawBackgroundGradient(const Gfx::Color& up, const Gfx::Color& down);
+ //! Draws a portion of the image background
+ void DrawBackgroundImageQuarter(Math::Point p1, Math::Point p2, const std::string& name);
+ //! Draws the image background
void DrawBackgroundImage();
+ //! Draws all the planets
void DrawPlanet();
- void DrawFrontsize();
+ //! Draws the image foreground
+ void DrawForegroundImage();
+ //! Draws the foreground color
void DrawOverColor();
- void DrawHilite();
+ //! Draws the rectangle of the object highlighted
+ void DrawHighlight();
+ //! Draws the mouse cursor
void DrawMouse();
+ //! Draw part of mouse cursor sprite
void DrawMouseSprite(Math::Point pos, Math::Point dim, int icon);
- /*
- Gfx::ObjLevel2* AddLevel1(Gfx::ObjLevel1 *&p1, char* texName1, char* texName2);
- Gfx::ObjLevel3* AddLevel2(Gfx::ObjLevel2 *&p2, int objRank);
- Gfx::ObjLevel4* AddLevel3(Gfx::ObjLevel3 *&p3, float min, float max);
- Gfx::ObjLevel5* AddLevel4(Gfx::ObjLevel4 *&p4, int reserve);
- Gfx::ObjLevel6* AddLevel5(Gfx::ObjLevel5 *&p5, Gfx::TriangleType type, const Gfx::Material &mat, int state, int nb);*/
-
+ //! Tests whether the given object is visible
bool IsVisible(int objRank);
+
+ //! Detects whether an object is affected by the mouse
bool DetectBBox(int objRank, Math::Point mouse);
- bool GetBBox2D(int objRank, Math::Point &min, Math::Point &max);
- bool DetectTriangle(Math::Point mouse, Gfx::VertexTex2 *triangle, int objRank, float &dist);
- bool TransformPoint(Math::Vector &p2D, int objRank, Math::Vector p3D);
+
+ //! Compute and return the 2D box on screen of any object
+ bool GetBBox2D(int objRank, Math::Point& min, Math::Point& max);
+
+ //! Detects the target object that is selected with the mouse
+ /** Returns the rank of the object or -1. */
+ int DetectObject(Math::Point mouse);
+
+ //! Detects whether the mouse is in a triangle.
+ bool DetectTriangle(Math::Point mouse, Gfx::VertexTex2* triangle, int objRank, float& dist);
+
+ //! Transforms a 3D point (x, y, z) in 2D space (x, y, -) of the window
+ /** The coordinated p2D.z gives the distance. */
+ bool TransformPoint(Math::Vector& p2D, int objRank, Math::Vector p3D);
+
+ //! Calculates the distances between the viewpoint and the origin of different objects
void ComputeDistance();
+
+ //! Updates all the geometric parameters of objects
void UpdateGeometry();
protected:
CInstanceManager* m_iMan;
CApplication* m_app;
- CSound* m_sound;
+ CSoundInterface* m_sound;
Gfx::CDevice* m_device;
Gfx::CText* m_text;
Gfx::CLightManager* m_lightMan;
@@ -892,7 +1056,7 @@ protected:
Gfx::CPlanet* m_planet;
Gfx::CTerrain* m_terrain;
- bool m_wasInit;
+ //! Last encountered error
std::string m_error;
//! Whether to show stats (FPS, etc)
@@ -926,9 +1090,9 @@ protected:
bool m_render;
bool m_movieLock;
- //! Current size of viewport
+ //! Current size of viewport window
Math::IntSize m_size;
- //! Previous size of viewport
+ //! Previous size of viewport window
Math::IntSize m_lastSize;
std::vector<Gfx::EngineObjLevel1> m_objectTree;
@@ -950,7 +1114,6 @@ protected:
Gfx::Color m_waterAddColor;
int m_statisticTriangle;
bool m_updateGeometry;
- //char m_infoText[10][200];
int m_alphaMode;
bool m_stateColor;
bool m_forceStateColor;
@@ -970,11 +1133,11 @@ protected:
bool m_overFront;
Gfx::Color m_overColor;
int m_overMode;
- std::string m_frontsizeName;
+ std::string m_foregroundImageName;
bool m_drawWorld;
bool m_drawFront;
float m_limitLOD[2];
- float m_particuleDensity;
+ float m_particleDensity;
float m_clippingDistance;
float m_lastClippingDistance;
float m_objectDetail;
@@ -993,10 +1156,10 @@ protected:
int m_editIndentValue;
float m_tracePrecision;
- int m_hiliteRank[100];
- bool m_hilite;
- Math::Point m_hiliteP1;
- Math::Point m_hiliteP2;
+ int m_highlightRank[100];
+ bool m_highlight;
+ Math::Point m_highlightP1;
+ Math::Point m_highlightP2;
int m_lastState;
Gfx::Color m_lastColor;
@@ -1015,12 +1178,6 @@ protected:
Gfx::EngineMouseType m_mouseType;
Math::Point m_mousePos;
bool m_mouseVisible;
-
- //LPDIRECTDRAWSURFACE7 m_imageSurface;
- //DDSURFACEDESC2 m_imageDDSD;
- //WORD* m_imageCopy;
- //int m_imageDX;
- //int m_imageDY;
};
}; // namespace Gfx