Fixes & testing in CEngine

- fixed bugs in settings modes, etc.
- some additions and minor refactoring
dev-ui
Piotr Dziwinski 2012-08-12 10:45:04 +02:00
parent 1996507fd3
commit b4b74c30e9
10 changed files with 336 additions and 131 deletions

View File

@ -215,8 +215,7 @@ bool CApplication::Create()
if (! m_device->Create() )
{
SystemDialog( SDT_ERROR, "COLOBT - Fatal Error",
std::string("Error in CDevice::Create() :\n") +
std::string(m_device->GetError()) );
std::string("Error in CDevice::Create()") );
m_exitCode = 1;
return false;
}
@ -229,8 +228,7 @@ bool CApplication::Create()
if (! m_engine->Create() )
{
SystemDialog( SDT_ERROR, "COLOBT - Fatal Error",
std::string("Error in CEngine::Init() :\n") +
std::string(m_engine->GetError()) );
std::string("Error in CEngine::Init()") );
m_exitCode = 1;
return false;
}
@ -498,6 +496,14 @@ void CApplication::UpdateJoystick()
}
}
void CApplication::UpdateMouse()
{
Math::IntPoint pos;
SDL_GetMouseState(&pos.x, &pos.y);
m_systemMousePos = m_engine->WindowToInterfaceCoords(pos);
m_engine->SetMousePos(m_systemMousePos);
}
int CApplication::Run()
{
m_active = true;
@ -572,6 +578,10 @@ int CApplication::Run()
m_robotMain->ProcessEvent(event); */
}
/* Update mouse position explicitly right before rendering
* because mouse events are usually way behind */
UpdateMouse();
// Update game and render a frame during idle time (no messages are waiting)
Render();
}
@ -857,7 +867,6 @@ bool CApplication::GetSystemMouseVisibile()
return result == SDL_ENABLE;
}
void CApplication::SetSystemMousePos(Math::Point pos)
{
Math::IntPoint windowPos = m_engine->InterfaceToWindowCoords(pos);

View File

@ -164,6 +164,9 @@ public:
//! Polls the state of joystick axes and buttons
void UpdateJoystick();
//! Updates the mouse position explicitly
void UpdateMouse();
void FlushPressKey();
void ResetKey();
void SetKey(int keyRank, int option, int key);

View File

@ -153,9 +153,9 @@ enum FogMode
\brief Culling mode for polygons */
enum CullMode
{
//! Cull clockwise side
//! Cull clockwise faces
CULL_CW,
//! Cull counter-clockwise side
//! Cull counter-clockwise faces
CULL_CCW
};
@ -278,6 +278,9 @@ class CDevice
public:
virtual ~CDevice() {}
//! Provides a hook to debug graphics code (implementation-specific)
virtual void DebugHook() = 0;
//! Initializes the device, setting the initial state
virtual bool Create() = 0;
//! Destroys the device, releasing every acquired resource

View File

@ -231,10 +231,7 @@ void Gfx::CCloud::Create(const std::string& fileName,
m_fileName = fileName;
if (! m_fileName.empty())
{
m_engine->LoadTexture(m_fileName, 0);
m_engine->LoadTexture(m_fileName, 1);
}
m_engine->LoadTexture(m_fileName);
if (m_terrain == nullptr)
m_terrain = static_cast<CTerrain*>(m_iMan->SearchInstance(CLASS_TERRAIN));

View File

@ -115,6 +115,7 @@ Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
m_overColor = 0;
m_overMode = ENG_RSTATE_TCOLOR_BLACK;
m_highlightRank[0] = -1; // empty list
m_highlightTime = 0.0f;
m_eyePt = Math::Vector(0.0f, 0.0f, 0.0f);
m_lookatPt = Math::Vector(0.0f, 0.0f, 1.0f);
m_drawWorld = true;
@ -133,7 +134,7 @@ Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
m_lensMode = true;
m_waterMode = true;
m_skyMode = true;
m_backForce = true;
m_backForce = false; // TODO: change to true?
m_planetMode = true;
m_lightMode = true;
m_editIndentMode = true;
@ -147,22 +148,22 @@ Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
m_updateGeometry = false;
m_mice[Gfx::ENG_MOUSE_NORM] = Gfx::EngineMouse( 0, 1, 32, Gfx::ENG_RSTATE_TCOLOR_WHITE, Gfx::ENG_RSTATE_TCOLOR_BLACK, Math::Point( 1.0f, 1.0f));
m_mice[Gfx::ENG_MOUSE_WAIT] = Gfx::EngineMouse( 2, 3, 33, Gfx::ENG_RSTATE_TCOLOR_WHITE, Gfx::ENG_RSTATE_TCOLOR_BLACK, Math::Point( 8.0f, 12.0f));
m_mice[Gfx::ENG_MOUSE_HAND] = Gfx::EngineMouse( 4, 5, 34, Gfx::ENG_RSTATE_TCOLOR_WHITE, Gfx::ENG_RSTATE_TCOLOR_BLACK, Math::Point( 7.0f, 2.0f));
m_mice[Gfx::ENG_MOUSE_NO] = Gfx::EngineMouse( 6, 7, 35, Gfx::ENG_RSTATE_TCOLOR_WHITE, Gfx::ENG_RSTATE_TCOLOR_BLACK, Math::Point(10.0f, 10.0f));
m_mice[Gfx::ENG_MOUSE_EDIT] = Gfx::EngineMouse( 8, 9, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point( 6.0f, 10.0f));
m_mice[Gfx::ENG_MOUSE_CROSS] = Gfx::EngineMouse(10, 11, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point(10.0f, 10.0f));
m_mice[Gfx::ENG_MOUSE_MOVEV] = Gfx::EngineMouse(12, 13, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point( 5.0f, 11.0f));
m_mice[Gfx::ENG_MOUSE_MOVEH] = Gfx::EngineMouse(14, 15, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point(11.0f, 5.0f));
m_mice[Gfx::ENG_MOUSE_MOVED] = Gfx::EngineMouse(16, 17, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point( 9.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_MOVEI] = Gfx::EngineMouse(18, 19, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point( 9.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_MOVE] = Gfx::EngineMouse(20, 21, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point(11.0f, 11.0f));
m_mice[Gfx::ENG_MOUSE_TARGET] = Gfx::EngineMouse(22, 23, -1, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point(15.0f, 15.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLL] = Gfx::EngineMouse(24, 25, 43, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point( 2.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLR] = Gfx::EngineMouse(26, 27, 44, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point(17.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLU] = Gfx::EngineMouse(28, 29, 45, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point( 9.0f, 2.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLD] = Gfx::EngineMouse(30, 31, 46, Gfx::ENG_RSTATE_TCOLOR_BLACK, Gfx::ENG_RSTATE_TCOLOR_WHITE, Math::Point( 9.0f, 17.0f));
m_mice[Gfx::ENG_MOUSE_NORM] = Gfx::EngineMouse( 0, 1, 32, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Math::Point( 1.0f, 1.0f));
m_mice[Gfx::ENG_MOUSE_WAIT] = Gfx::EngineMouse( 2, 3, 33, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Math::Point( 8.0f, 12.0f));
m_mice[Gfx::ENG_MOUSE_HAND] = Gfx::EngineMouse( 4, 5, 34, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Math::Point( 7.0f, 2.0f));
m_mice[Gfx::ENG_MOUSE_NO] = Gfx::EngineMouse( 6, 7, 35, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Math::Point(10.0f, 10.0f));
m_mice[Gfx::ENG_MOUSE_EDIT] = Gfx::EngineMouse( 8, 9, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point( 6.0f, 10.0f));
m_mice[Gfx::ENG_MOUSE_CROSS] = Gfx::EngineMouse(10, 11, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point(10.0f, 10.0f));
m_mice[Gfx::ENG_MOUSE_MOVEV] = Gfx::EngineMouse(12, 13, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point( 5.0f, 11.0f));
m_mice[Gfx::ENG_MOUSE_MOVEH] = Gfx::EngineMouse(14, 15, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point(11.0f, 5.0f));
m_mice[Gfx::ENG_MOUSE_MOVED] = Gfx::EngineMouse(16, 17, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point( 9.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_MOVEI] = Gfx::EngineMouse(18, 19, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point( 9.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_MOVE] = Gfx::EngineMouse(20, 21, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point(11.0f, 11.0f));
m_mice[Gfx::ENG_MOUSE_TARGET] = Gfx::EngineMouse(22, 23, -1, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point(15.0f, 15.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLL] = Gfx::EngineMouse(24, 25, 43, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point( 2.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLR] = Gfx::EngineMouse(26, 27, 44, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point(17.0f, 9.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLU] = Gfx::EngineMouse(28, 29, 45, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point( 9.0f, 2.0f));
m_mice[Gfx::ENG_MOUSE_SCROLLD] = Gfx::EngineMouse(30, 31, 46, Gfx::ENG_RSTATE_TTEXTURE_BLACK, Gfx::ENG_RSTATE_TTEXTURE_WHITE, Math::Point( 9.0f, 17.0f));
m_mouseSize = Math::Point(0.04f, 0.04f * (800.0f / 600.0f));
m_mousePos = Math::Point(0.5f, 0.5f);
@ -170,7 +171,7 @@ Gfx::CEngine::CEngine(CInstanceManager *iMan, CApplication *app)
m_mouseVisible = false;
m_texPath = "textures/";
m_defaultTexParams.format = Gfx::TEX_IMG_RGBA;
m_defaultTexParams.format = Gfx::TEX_IMG_RGB;
m_defaultTexParams.mipmap = true;
m_defaultTexParams.minFilter = Gfx::TEX_MIN_FILTER_LINEAR_MIPMAP_LINEAR;
m_defaultTexParams.magFilter = Gfx::TEX_MAG_FILTER_LINEAR;
@ -190,11 +191,6 @@ Gfx::CEngine::~CEngine()
m_terrain = nullptr;
}
std::string Gfx::CEngine::GetError()
{
return m_error;
}
void Gfx::CEngine::SetDevice(Gfx::CDevice *device)
{
m_device = device;
@ -230,12 +226,12 @@ bool Gfx::CEngine::Create()
m_text->SetDevice(m_device);
if (! m_text->Create())
{
m_error = std::string("Error creating CText: ") + m_text->GetError();
std::string error = m_text->GetError();
GetLogger()->Error("Error creating CText: %s\n", error.c_str());
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);
@ -289,11 +285,7 @@ void Gfx::CEngine::ResetAfterDeviceChanged()
bool Gfx::CEngine::ProcessEvent(const Event &event)
{
if (event.type == EVENT_MOUSE_MOVE)
{
m_mousePos = event.mouseMove.pos;
}
else if (event.type == EVENT_KEY_DOWN)
if (event.type == EVENT_KEY_DOWN)
{
// !! Debug, to be removed later !!
@ -307,6 +299,37 @@ bool Gfx::CEngine::ProcessEvent(const Event &event)
int index = static_cast<int>(m_mouseType);
m_mouseType = static_cast<Gfx::EngineMouseType>( (index + 1) % Gfx::ENG_MOUSE_COUNT );
}
else if (event.key.key == KEY(F3))
{
m_backgroundQuarter = !m_backgroundQuarter;
if (m_backgroundQuarter)
{
m_backgroundFull = true;
m_backgroundName = "geneda.png";
}
else
{
m_backgroundFull = false;
m_backgroundName = "";
}
}
else if (event.key.key == KEY(F4))
{
m_backForce = !m_backForce;
if (m_backForce)
{
m_backgroundColorDown = Gfx::Color(0.2f, 0.2f, 0.2f);
m_backgroundColorUp = Gfx::Color(0.8f, 0.8f, 0.8f);
}
else
{
m_backgroundColorDown = m_backgroundColorUp = Gfx::Color(0.0f, 0.0f, 0.0f);
}
}
}
else if (event.type == EVENT_FRAME)
{
m_highlightTime += event.rTime;
}
// By default, pass on all events
@ -954,10 +977,28 @@ void Gfx::CEngine::SetState(int state, const Gfx::Color& color)
m_device->SetTextureEnabled(0, true);
m_device->SetTextureStageParams(0, params);
}
else if (state & Gfx::ENG_RSTATE_OPAQUE_TEXTURE) // opaque texture ?
{
m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
m_device->SetRenderState(Gfx::RENDER_STATE_ALPHA_TEST, false);
m_device->SetRenderState(Gfx::RENDER_STATE_BLENDING, false);
m_device->SetRenderState(Gfx::RENDER_STATE_TEXTURING, true);
m_device->SetTextureEnabled(0, true);
m_device->SetTextureStageParams(0, Gfx::TextureStageParams()); // default operation
}
else if (state & Gfx::ENG_RSTATE_OPAQUE_COLOR) // opaque color ?
{
m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
m_device->SetRenderState(Gfx::RENDER_STATE_ALPHA_TEST, false);
m_device->SetRenderState(Gfx::RENDER_STATE_BLENDING, false);
m_device->SetRenderState(Gfx::RENDER_STATE_TEXTURING, false);
}
else if (state & Gfx::ENG_RSTATE_TEXT) // font rendering?
{
m_device->SetRenderState(Gfx::RENDER_STATE_FOG, false);
m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_TEST, false); // TODO: depth test setting elsewhere!
m_device->SetRenderState(Gfx::RENDER_STATE_DEPTH_WRITE, false);
m_device->SetRenderState(Gfx::RENDER_STATE_ALPHA_TEST, false);
@ -1091,6 +1132,7 @@ void Gfx::CEngine::SetState(int state, const Gfx::Color& color)
void Gfx::CEngine::SetMaterial(const Gfx::Material &mat)
{
m_lastMaterial = mat;
m_device->SetMaterial(mat);
}
@ -1112,12 +1154,18 @@ void Gfx::CEngine::SetViewParams(const Math::Vector& eyePt, const Math::Vector&
Gfx::Texture Gfx::CEngine::CreateTexture(const std::string &texName, const Gfx::TextureCreateParams &params)
{
if (m_texBlacklist.find(texName) != m_texBlacklist.end())
return Gfx::Texture(); // invalid texture
// TODO: detect alpha channel?
CImage img;
if (! img.Load(m_app->GetDataFilePath(m_texPath, texName)))
{
std::stringstream str;
str << "Couldn't load texture '" << texName << "': " << img.GetError();
m_error = str.str();
std::string error = img.GetError();
GetLogger()->Error("Couldn't load texture '%s': %s\n", texName.c_str(), error.c_str());
GetLogger()->Error("Blacklisting texture '%s'\n", texName.c_str());
m_texBlacklist.insert(texName);
return Gfx::Texture(); // invalid texture
}
@ -1125,9 +1173,10 @@ Gfx::Texture Gfx::CEngine::CreateTexture(const std::string &texName, const Gfx::
if (! result.valid)
{
std::stringstream str;
str << "Couldn't load texture '" << texName << "': " << m_device->GetError();
m_error = str.str();
std::string error = m_device->GetError();
GetLogger()->Error("Couldn't load texture '%s': %s\n", texName.c_str(), error.c_str());
GetLogger()->Error("Blacklisting texture '%s'\n", texName.c_str());
m_texBlacklist.insert(texName);
return result;
}
@ -1156,29 +1205,115 @@ void Gfx::CEngine::DestroyTexture(const std::string &texName)
m_texNameMap.erase(it);
}
bool Gfx::CEngine::LoadTexture(const std::string& name, int stage)
bool Gfx::CEngine::LoadTexture(const std::string& name)
{
if (m_texBlacklist.find(name) != m_texBlacklist.end())
return false;
std::map<std::string, Gfx::Texture>::iterator it = m_texNameMap.find(name);
if (it != m_texNameMap.end())
return true;
Gfx::Texture tex = CreateTexture(name);
return tex.valid;
}
// TODO: create separate variables for 4 quarter names
void QuarterName(std::string& buffer, const std::string& name, int quarter)
{
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::LoadAllTextures()
{
LoadTexture("text.png");
LoadTexture("mouse.png");
LoadTexture("button1.png");
LoadTexture("button2.png");
LoadTexture("button3.png");
LoadTexture("effect00.png");
LoadTexture("effect01.png");
LoadTexture("effect02.png");
LoadTexture("map.png");
if (! m_backgroundName.empty())
{
if (m_backgroundQuarter) // image into 4 pieces?
{
for (int i = 0; i < 4; i++)
{
std::string name;
QuarterName(name, m_backgroundName, i);
LoadTexture(name);
}
}
else
{
LoadTexture(m_backgroundName);
}
}
if (! m_foregroundName.empty())
LoadTexture(m_foregroundName);
m_planet->LoadTexture();
bool ok = true;
/* TODO
D3DObjLevel1* p1;
D3DObjLevel2* p2;
int l1;
p1 = m_objectPointer;
for ( l1=0 ; l1<p1->totalUsed ; l1++ )
{
p2 = p1->table[l1];
if ( p2 == 0 || p2->texName1[0] != 0 )
{
if ( !LoadTexture(p2->texName1) ) ok = false;
}
if ( p2 == 0 || p2->texName2[0] != 0 )
{
if ( !LoadTexture(p2->texName2) ) ok = false;
}
}*/
return ok;
}
bool Gfx::CEngine::SetTexture(const std::string& name, int stage)
{
auto it = m_texNameMap.find(name);
if (it != m_texNameMap.end())
{
m_device->SetTexture(stage, (*it).second);
return true;
}
// TODO if not present...
return false;
}
if (! LoadTexture(name))
{
m_device->SetTexture(stage, 0); // invalid texture
return false;
}
bool Gfx::CEngine::LoadAllTextures()
{
// TODO!
return true;
}
it = m_texNameMap.find(name);
if (it != m_texNameMap.end())
{
m_device->SetTexture(stage, (*it).second);
return true;
}
bool Gfx::CEngine::SetTexture(const std::string& name, int stage)
{
// TODO!
return true;
m_device->SetTexture(stage, 0); // invalid texture
return false; // should not happen normally
}
void Gfx::CEngine::SetLimitLOD(int rank, float limit)
@ -1364,7 +1499,6 @@ float Gfx::CEngine::GetFogStart(int rank)
return m_fogStart[rank];
}
void Gfx::CEngine::SetBackground(const std::string& name, Gfx::Color up, Gfx::Color down,
Gfx::Color cloudUp, Gfx::Color cloudDown,
bool full, bool quarter)
@ -1391,12 +1525,12 @@ void Gfx::CEngine::GetBackground(std::string& name, Gfx::Color& up, Gfx::Color&
quarter = m_backgroundQuarter;
}
void Gfx::CEngine::SetForegroundImageName(const std::string& name)
void Gfx::CEngine::SetForegroundName(const std::string& name)
{
if (! m_foregroundImageName.empty())
DestroyTexture(m_foregroundImageName);
if (! m_foregroundName.empty())
DestroyTexture(m_foregroundName);
m_foregroundImageName = name;
m_foregroundName = name;
}
void Gfx::CEngine::SetOverFront(bool front)
@ -1714,14 +1848,11 @@ void Gfx::CEngine::Render()
// Begin the scene
m_device->BeginScene();
if (m_drawWorld)
Draw3DScene();
DrawInterface();
// End the scene
m_device->EndScene();
}
@ -2113,7 +2244,8 @@ void Gfx::CEngine::DrawInterface()
void Gfx::CEngine::UpdateGroundSpotTextures()
{
// TODO!
// TODO the original code modifying the textures is very complex, so stub for now
GetLogger()->Info("CEngine::UpdateGroundSpotTextures(): stub!\n");
}
void Gfx::CEngine::DrawShadow()
@ -2131,7 +2263,7 @@ void Gfx::CEngine::DrawShadow()
material.ambient = Gfx::Color(0.5f, 0.5f, 0.5f);
SetMaterial(material);
// TODO: wtf?
// TODO: create a separate texture
SetTexture("text.png");
Math::Point ts, ti;
@ -2310,6 +2442,7 @@ void Gfx::CEngine::DrawShadow()
m_device->SetRenderState(Gfx::RENDER_STATE_LIGHTING, true);
}
// STATUS: TESTED, VERIFIED
void Gfx::CEngine::DrawBackground()
{
if (m_skyMode && m_cloud->GetLevel() != 0.0f) // clouds ?
@ -2323,12 +2456,13 @@ void Gfx::CEngine::DrawBackground()
DrawBackgroundGradient(m_backgroundColorUp, m_backgroundColorDown);
}
if (m_backForce || (m_skyMode && m_backgroundName[0] != 0) )
if (m_backForce || (m_skyMode && !m_backgroundName.empty()) )
{
DrawBackgroundImage(); // image
}
}
// STATUS: TESTED
void Gfx::CEngine::DrawBackgroundGradient(const Gfx::Color& up, const Gfx::Color& down)
{
Math::Point p1(0.0f, 0.5f);
@ -2341,12 +2475,7 @@ void Gfx::CEngine::DrawBackgroundGradient(const Gfx::Color& up, const Gfx::Color
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);
SetState(Gfx::ENG_RSTATE_OPAQUE_COLOR);
m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
@ -2364,6 +2493,7 @@ void Gfx::CEngine::DrawBackgroundGradient(const Gfx::Color& up, const Gfx::Color
AddStatisticTriangle(2);
}
// Status: PART_TESTED
void Gfx::CEngine::DrawBackgroundImageQuarter(Math::Point p1, Math::Point p2, const std::string& name)
{
Math::Vector n = Math::Vector(0.0f, 0.0f, -1.0f); // normal
@ -2399,12 +2529,8 @@ void Gfx::CEngine::DrawBackgroundImageQuarter(Math::Point p1, Math::Point p2, co
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);
SetState(Gfx::ENG_RSTATE_OPAQUE_TEXTURE | Gfx::ENG_RSTATE_WRAP);
m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
m_device->SetTransform(Gfx::TRANSFORM_PROJECTION, m_matProjInterface);
@ -2422,18 +2548,7 @@ void Gfx::CEngine::DrawBackgroundImageQuarter(Math::Point p1, Math::Point p2, co
AddStatisticTriangle(2);
}
void QuarterName(std::string& buffer, const std::string& name, int quarter)
{
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);
}
// Status: TESTED, VERIFIED
void Gfx::CEngine::DrawBackgroundImage()
{
Math::Point p1, p2;
@ -2494,9 +2609,10 @@ void Gfx::CEngine::DrawPlanet()
m_planet->Draw(); // draws the planets
}
// Status: PART_TESTED
void Gfx::CEngine::DrawForegroundImage()
{
if (m_foregroundImageName.empty()) return;
if (m_foregroundName.empty()) return;
Math::Vector n = Math::Vector(0.0f, 0.0f, -1.0f); // normal
@ -2518,11 +2634,7 @@ void Gfx::CEngine::DrawForegroundImage()
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);
SetTexture(m_foregroundName);
SetState(Gfx::ENG_RSTATE_CLAMP | Gfx::ENG_RSTATE_TTEXTURE_BLACK);
m_device->SetTransform(Gfx::TRANSFORM_VIEW, m_matViewInterface);
@ -2533,6 +2645,7 @@ void Gfx::CEngine::DrawForegroundImage()
AddStatisticTriangle(2);
}
// Status: PART_TESTED
void Gfx::CEngine::DrawOverColor()
{
if (! m_stateColor) return;
@ -2551,29 +2664,31 @@ void Gfx::CEngine::DrawOverColor()
Gfx::Color(0.0f, 0.0f, 0.0f, 0.0f)
};
SetState(m_overMode);
// TODO: set also with m_overMode ?
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])
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);
}
// Status: TESTED, VERIFIED
void Gfx::CEngine::DrawHighlight()
{
Math::Point min, max;
@ -2609,9 +2724,63 @@ void Gfx::CEngine::DrawHighlight()
m_highlight = true;
}
// TODO: draw highlight!
if (! m_highlight)
return;
Math::Point p1 = m_highlightP1;
Math::Point p2 = m_highlightP2;
int nbOut = 0;
if (p1.x < 0.0f || p1.x > 1.0f) nbOut++;
if (p1.y < 0.0f || p1.y > 1.0f) nbOut++;
if (p2.x < 0.0f || p2.x > 1.0f) nbOut++;
if (p2.y < 0.0f || p2.y > 1.0f) nbOut++;
if (nbOut > 2)
return;
SetState(Gfx::ENG_RSTATE_OPAQUE_COLOR);
float d = 0.5f+sinf(m_highlightTime*6.0f)*0.5f;
d *= (p2.x-p1.x)*0.1f;
p1.x += d;
p1.y += d;
p2.x -= d;
p2.y -= d;
Gfx::Color color(1.0f, 1.0f, 0.0f); // yellow
Gfx::VertexCol line[3] =
{
Gfx::VertexCol(Math::Vector(), color),
Gfx::VertexCol(Math::Vector(), color),
Gfx::VertexCol(Math::Vector(), color)
};
float dx = (p2.x - p1.x) / 5.0f;
float dy = (p2.y - p1.y) / 5.0f;
line[0].coord = Math::Vector(p1.x, p1.y + dy, 0.0f);
line[1].coord = Math::Vector(p1.x, p1.y, 0.0f);
line[2].coord = Math::Vector(p1.x + dx, p1.y, 0.0f);
m_device->DrawPrimitive(Gfx::PRIMITIVE_LINE_STRIP, line, 3);
line[0].coord = Math::Vector(p2.x - dx, p1.y, 0.0f);
line[1].coord = Math::Vector(p2.x, p1.y, 0.0f);
line[2].coord = Math::Vector(p2.x, p1.y + dy, 0.0f);
m_device->DrawPrimitive(Gfx::PRIMITIVE_LINE_STRIP, line, 3);
line[0].coord = Math::Vector(p2.x, p2.y - dy, 0.0f);
line[1].coord = Math::Vector(p2.x, p2.y, 0.0f);
line[2].coord = Math::Vector(p2.x - dx, p2.y, 0.0f);
m_device->DrawPrimitive(Gfx::PRIMITIVE_LINE_STRIP, line, 3);
line[0].coord = Math::Vector(p1.x + dx, p2.y, 0.0f);
line[1].coord = Math::Vector(p1.x, p2.y, 0.0f);
line[2].coord = Math::Vector(p1.x, p2.y - dy, 0.0f);
m_device->DrawPrimitive(Gfx::PRIMITIVE_LINE_STRIP, line, 3);
}
// Status: TESTED, VERIFIED
void Gfx::CEngine::DrawMouse()
{
if (! m_mouseVisible)
@ -2647,6 +2816,7 @@ void Gfx::CEngine::DrawMouse()
DrawMouseSprite(pos, m_mouseSize, m_mice[index].icon2);
}
// Status: TESTED, VERIFIED
void Gfx::CEngine::DrawMouseSprite(Math::Point pos, Math::Point size, int icon)
{
if (icon == -1)
@ -2671,8 +2841,8 @@ void Gfx::CEngine::DrawMouseSprite(Math::Point pos, Math::Point size, int icon)
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, p1.y, 0.0f), normal, Math::Point(u2, v2)),
Gfx::Vertex(Math::Vector(p2.x, p2.y, 0.0f), normal, Math::Point(u2, v1))
};

View File

@ -37,6 +37,7 @@
#include <string>
#include <vector>
#include <map>
#include <set>
class CApplication;
@ -78,7 +79,7 @@ struct EngineTriangle
Gfx::VertexTex2 triangle[3];
//! Material
Gfx::Material material;
//! Render state (TODO: ?)
//! Render state
int state;
//! 1st texture
Gfx::Texture tex1;
@ -425,7 +426,11 @@ enum EngineRenderState
//! The transparent color (white = no)
ENG_RSTATE_TCOLOR_WHITE = (1<<17),
//! Mode for rendering text
ENG_RSTATE_TEXT = (1<<18)
ENG_RSTATE_TEXT = (1<<18),
//! Only opaque texture, no blending, etc.
ENG_RSTATE_OPAQUE_TEXTURE = (1<<19),
//! Only opaque color, no texture, blending, etc.
ENG_RSTATE_OPAQUE_COLOR = (1<<20)
};
@ -532,9 +537,6 @@ public:
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);
//! Returns the current device
@ -715,12 +717,21 @@ public:
void SetViewParams(const Math::Vector& eyePt, const Math::Vector& lookatPt,
const Math::Vector& upVec, float eyeDistance);
//! Creates texture with the specified params
Gfx::Texture CreateTexture(const std::string& texName,
const Gfx::TextureCreateParams& params);
//! Creates texture
Gfx::Texture CreateTexture(const std::string& texName);
//! Destroys texture, unloading it and removing from cache
void DestroyTexture(const std::string& texName);
bool LoadTexture(const std::string& name, int stage = 0);
//! Loads texture, creating it if not already present
bool LoadTexture(const std::string& name);
//! Loads all necessary textures
bool LoadAllTextures();
//! Sets texture for given stage; if not present in cache, the texture is loaded
bool SetTexture(const std::string& name, int stage = 0);
//@{
@ -831,8 +842,8 @@ public:
bool& full, bool& quarter);
//@}
//! Specifies the foreground image
void SetForegroundImageName(const std::string& name);
//! Specifies the name of foreground texture
void SetForegroundName(const std::string& name);
//! Specifies whether to draw the foreground
void SetOverFront(bool front);
//! Sets the foreground overlay color
@ -1129,7 +1140,7 @@ protected:
bool m_overFront;
Gfx::Color m_overColor;
int m_overMode;
std::string m_foregroundImageName;
std::string m_foregroundName;
bool m_drawWorld;
bool m_drawFront;
float m_limitLOD[2];
@ -1156,6 +1167,8 @@ protected:
int m_highlightRank[100];
//! Highlight visible?
bool m_highlight;
//! Time counter for highlight animation
float m_highlightTime;
//@{
//! Highlight rectangle points
Math::Point m_highlightP1;
@ -1171,6 +1184,10 @@ protected:
std::map<std::string, Gfx::Texture> m_texNameMap;
//! Reverse map of loaded textures (by texture)
std::map<Gfx::Texture, std::string> m_revTexNameMap;
//! Blacklist map of textures
/** Textures on this list were not successful in first loading,
* so are disabled for subsequent load calls. */
std::set<std::string> m_texBlacklist;
//! Mouse cursor definitions
Gfx::EngineMouse m_mice[Gfx::ENG_MOUSE_COUNT];

View File

@ -649,8 +649,8 @@ void Gfx::CText::DrawHighlight(Gfx::FontHighlight hl, Math::Point pos, Math::Poi
Gfx::VertexCol quad[] =
{
Gfx::VertexCol(Math::Vector(p1.x, p1.y, 0.0f), grad[3]),
Gfx::VertexCol(Math::Vector(p2.x, p1.y, 0.0f), grad[2]),
Gfx::VertexCol(Math::Vector(p1.x, p2.y, 0.0f), grad[0]),
Gfx::VertexCol(Math::Vector(p2.x, p1.y, 0.0f), grad[2]),
Gfx::VertexCol(Math::Vector(p2.x, p2.y, 0.0f), grad[1])
};
@ -688,8 +688,6 @@ void Gfx::CText::DrawChar(Gfx::UTF8Char ch, Gfx::FontType font, float size, Math
cf->cache[ch] = tex;
}
m_device->SetRenderState(Gfx::RENDER_STATE_CULLING, false);
Math::Point p1(pos.x, pos.y + tex.charSize.y - tex.texSize.y);
Math::Point p2(pos.x + tex.texSize.x, pos.y + tex.charSize.y);
@ -698,8 +696,8 @@ void Gfx::CText::DrawChar(Gfx::UTF8Char ch, Gfx::FontType font, float size, Math
Gfx::Vertex quad[4] =
{
Gfx::Vertex(Math::Vector(p1.x, p1.y, 0.0f), n, Math::Point(0.0f, 1.0f)),
Gfx::Vertex(Math::Vector(p2.x, p1.y, 0.0f), n, Math::Point(1.0f, 1.0f)),
Gfx::Vertex(Math::Vector(p1.x, p2.y, 0.0f), n, Math::Point(0.0f, 0.0f)),
Gfx::Vertex(Math::Vector(p2.x, p1.y, 0.0f), n, Math::Point(1.0f, 1.0f)),
Gfx::Vertex(Math::Vector(p2.x, p2.y, 0.0f), n, Math::Point(1.0f, 0.0f))
};

View File

@ -519,10 +519,7 @@ void Gfx::CWater::Create(Gfx::WaterType type1, Gfx::WaterType type2, const std::
VaporFlush();
if (! m_fileName.empty())
{
m_engine->LoadTexture(m_fileName, 0);
m_engine->LoadTexture(m_fileName, 1);
}
m_engine->LoadTexture(m_fileName);
if (m_terrain == nullptr)
m_terrain = static_cast<CTerrain*>(m_iMan->SearchInstance(CLASS_TERRAIN));

View File

@ -73,6 +73,13 @@ Gfx::CGLDevice::~CGLDevice()
{
}
void Gfx::CGLDevice::DebugHook()
{
/* This function is only called here, so it can be used
* as a breakpoint when debugging using gDEBugger */
glColor3i(0, 0, 0);
}
std::string Gfx::CGLDevice::GetError()
{
return m_error;
@ -1172,17 +1179,19 @@ void Gfx::CGLDevice::GetFogParams(Gfx::FogMode &mode, Gfx::Color &color, float &
void Gfx::CGLDevice::SetCullMode(Gfx::CullMode mode)
{
if (mode == Gfx::CULL_CW) glCullFace(GL_CW);
else if (mode == Gfx::CULL_CCW) glCullFace(GL_CCW);
// Cull clockwise back faces, so front face is the opposite
// (assuming GL_CULL_FACE is GL_BACK)
if (mode == Gfx::CULL_CW ) glFrontFace(GL_CCW);
else if (mode == Gfx::CULL_CCW) glFrontFace(GL_CW);
else assert(false);
}
Gfx::CullMode Gfx::CGLDevice::GetCullMode()
{
GLint flag = 0;
glGetIntegerv(GL_CULL_FACE, &flag);
if (flag == GL_CW) return Gfx::CULL_CW;
else if (flag == GL_CCW) return Gfx::CULL_CCW;
glGetIntegerv(GL_FRONT_FACE, &flag);
if (flag == GL_CW) return Gfx::CULL_CCW;
else if (flag == GL_CCW) return Gfx::CULL_CW;
else assert(false);
return Gfx::CULL_CW;
}

View File

@ -76,6 +76,8 @@ public:
CGLDevice(const Gfx::GLDeviceConfig &config);
virtual ~CGLDevice();
virtual void DebugHook();
virtual std::string GetError();
virtual bool Create();