Amazing merge with server

This commit is contained in:
Robin Engman 2014-02-10 12:42:31 +01:00
commit ba0d6ca73a
84 changed files with 2852 additions and 1007 deletions

View File

@ -56,6 +56,7 @@ namespace DanBias
{ {
WindowShell::CreateConsoleWindow(); WindowShell::CreateConsoleWindow();
//if(! m_data->window->CreateWin(WindowShell::WINDOW_INIT_DESC(L"Window", cPOINT(1600, 900), cPOINT())))
if(! m_data->window->CreateWin(WindowShell::WINDOW_INIT_DESC())) if(! m_data->window->CreateWin(WindowShell::WINDOW_INIT_DESC()))
return DanBiasClientReturn_Error; return DanBiasClientReturn_Error;
@ -114,6 +115,10 @@ namespace DanBias
{ {
if(Oyster::Graphics::API::Init(m_data->window->GetHWND(), false, false, Oyster::Math::Float2( 1024, 768)) != Oyster::Graphics::API::Sucsess) if(Oyster::Graphics::API::Init(m_data->window->GetHWND(), false, false, Oyster::Math::Float2( 1024, 768)) != Oyster::Graphics::API::Sucsess)
return E_FAIL; return E_FAIL;
Oyster::Graphics::API::Option p;
p.modelPath = L"..\\Content\\Models\\";
p.texturePath = L"..\\Content\\Textures\\";
Oyster::Graphics::API::SetOptions(p);
return S_OK; return S_OK;
} }
@ -147,6 +152,7 @@ namespace DanBias
if(state != Client::GameClientState::ClientState_Same) if(state != Client::GameClientState::ClientState_Same)
{ {
bool stateVal = false;
m_data->recieverObj->gameClientState->Release(); m_data->recieverObj->gameClientState->Release();
delete m_data->recieverObj->gameClientState; delete m_data->recieverObj->gameClientState;
m_data->recieverObj->gameClientState = NULL; m_data->recieverObj->gameClientState = NULL;
@ -155,23 +161,27 @@ namespace DanBias
{ {
case Client::GameClientState::ClientState_LobbyCreated: case Client::GameClientState::ClientState_LobbyCreated:
m_data->serverOwner = true; m_data->serverOwner = true;
stateVal = true;
case Client::GameClientState::ClientState_Lobby: case Client::GameClientState::ClientState_Lobby:
m_data->recieverObj->gameClientState = new Client::LobbyState(); m_data->recieverObj->gameClientState = new Client::LobbyState();
stateVal = true;
break; break;
case Client::GameClientState::ClientState_Game: case Client::GameClientState::ClientState_Game:
if(m_data->serverOwner)
DanBias::GameServerAPI::GameStart();
m_data->recieverObj->gameClientState = new Client::GameState();
if(m_data->serverOwner)
((Client::GameState*)m_data->recieverObj->gameClientState)->setClientId(0);
else
((Client::GameState*)m_data->recieverObj->gameClientState)->setClientId(1);
break; break;
default: default:
return E_FAIL; return E_FAIL;
break; break;
} }
m_data->recieverObj->gameClientState->Init(m_data->recieverObj); // send game client
if(stateVal)
{
m_data->recieverObj->gameClientState->Init(m_data->recieverObj); // send game client
}
else
{
}
} }
return S_OK; return S_OK;
@ -179,15 +189,7 @@ namespace DanBias
HRESULT DanBiasGame::Render(float deltaTime) HRESULT DanBiasGame::Render(float deltaTime)
{ {
int isPressed = 0;
if(m_data->inputObj->IsKeyPressed(DIK_A))
{
isPressed = 1;
}
wchar_t title[255];
swprintf(title, sizeof(title), L"| Pressing A: %d | \n", (int)(isPressed));
SetWindowText(m_data->window->GetHWND(), title);
m_data->recieverObj->gameClientState->Render(); m_data->recieverObj->gameClientState->Render();
@ -202,9 +204,11 @@ namespace DanBias
delete m_data->recieverObj; delete m_data->recieverObj;
delete m_data->inputObj; delete m_data->inputObj;
delete m_data; delete m_data;
Oyster::Graphics::API::Clean(); Oyster::Graphics::API::Clean();
GameServerAPI::ServerStop();
return S_OK; return S_OK;
} }

View File

@ -4,6 +4,8 @@
//WTF!? No headers included??? //WTF!? No headers included???
#include "../DanBiasGame/Include/DanBiasGame.h" #include "../DanBiasGame/Include/DanBiasGame.h"
#include "../GameProtocols/GeneralProtocols.h" #include "../GameProtocols/GeneralProtocols.h"
#include "..\GameProtocols\Protocols.h"
#include <Utilities.h>
namespace DanBias namespace DanBias
{ {
@ -14,9 +16,15 @@ namespace DanBias
// receiver function for server messages // receiver function for server messages
// parsing protocols and sending it to the gameState // parsing protocols and sending it to the gameState
void NetworkCallback(Oyster::Network::CustomNetProtocol& p) override //void NetworkCallback(Oyster::Network::CustomNetProtocol& p) override
void GameRecieverObject::DataRecieved(Oyster::Network::NetEvent<Oyster::Network::NetworkClient*, Oyster::Network::NetworkClient::ClientEventArgs> e) override
{ {
Oyster::Network::CustomNetProtocol p = e.args.data.protocol;
int pType = p[0].value.netInt; int pType = p[0].value.netInt;
//printf("Message(%i) arrived at client(%i)\n", pType, this->GetID());
switch (pType) switch (pType)
{ {
case protocol_General_Status: case protocol_General_Status:
@ -60,20 +68,20 @@ namespace DanBias
case protocol_Gameplay_ObjectCreate: case protocol_Gameplay_ObjectCreate:
{ {
Client::GameClientState::NewObj* protocolData = new Client::GameClientState::NewObj; Client::GameClientState::NewObj protocolData;// = new Client::GameClientState::NewObj;
protocolData->object_ID = p[1].value.netInt; protocolData.object_ID = p[1].value.netInt;
protocolData->path = p[2].value.netCharPtr; protocolData.path = p[2].value.netCharPtr;
for(int i = 0; i< 16; i++) for(int i = 0; i< 16; i++)
{ {
protocolData->worldPos[i] = p[i+3].value.netFloat; protocolData.worldPos[i] = p[i+3].value.netFloat;
} }
if(dynamic_cast<Client::GameState*>(gameClientState)) if(dynamic_cast<Client::GameState*>(gameClientState))
((Client::GameState*)gameClientState)->Protocol(protocolData); ((Client::GameState*)gameClientState)->Protocol(&protocolData);
delete p[2].value.netCharPtr; //delete char array //delete p[2].value.netCharPtr; //delete char array
delete protocolData; //delete protocolData;
protocolData = NULL; //protocolData = NULL;
} }
break; break;
case protocol_Gameplay_ObjectDisabled: case protocol_Gameplay_ObjectDisabled:
@ -102,16 +110,42 @@ namespace DanBias
((Client::GameState*)gameClientState)->Protocol(&protocolData); ((Client::GameState*)gameClientState)->Protocol(&protocolData);
} }
break; break;
case protocol_Lobby_Start: case protocol_Lobby_Create:
{ {
/*
if(dynamic_cast<Client::LobbyState*>(gameClientState)) if(dynamic_cast<Client::LobbyState*>(gameClientState))
{ {
GameLogic::Protocol_LobbyCreateGame tp();
int id = p.Get(1).value.netInt;
std::string name = p.Get(19).value.netCharPtr;
Oyster::Math::Float4x4 w;
for(int i = 0; i< 16; i++)
{
w[i] = p[i+2].value.netFloat;
}
gameClientState->Release(); gameClientState->Release();
delete gameClientState; delete gameClientState;
gameClientState = new Client::GameState(); gameClientState = new Client::GameState();
gameClientState->Init(m_data->recieverObj); gameClientState->Init(this);
}*/ std::wstring temp;
Utility::String::StringToWstring(name, temp);
((Client::GameState*)gameClientState)->InitiatePlayer(id, temp, w);
//Do some wait state?
}
}
break;
case protocol_Lobby_Start:
{
if(dynamic_cast<Client::GameState*>(gameClientState))
{
//Game state should start in n seconds
GameLogic::Protocol_LobbyStartGame p(p);
p.seconds;
//Sleep((int)(p.seconds * 1000));
}
} }
break; break;

View File

@ -15,7 +15,6 @@ struct GameState::myData
Oyster::Math3D::Float4x4 view; Oyster::Math3D::Float4x4 view;
Oyster::Math3D::Float4x4 proj; Oyster::Math3D::Float4x4 proj;
std::vector<C_Object*> object; std::vector<C_Object*> object;
int modelCount;
Oyster::Network::NetworkClient* nwClient; Oyster::Network::NetworkClient* nwClient;
gameStateState state; gameStateState state;
@ -33,7 +32,8 @@ GameState::GameState(void)
GameState::~GameState(void) GameState::~GameState(void)
{ {
delete this->camera;
delete this->privData;
} }
bool GameState::Init(Oyster::Network::NetworkClient* nwClient) bool GameState::Init(Oyster::Network::NetworkClient* nwClient)
{ {
@ -44,6 +44,10 @@ bool GameState::Init(Oyster::Network::NetworkClient* nwClient)
privData->nwClient = nwClient; privData->nwClient = nwClient;
privData->state = LoadGame(); privData->state = LoadGame();
pitch = 0; pitch = 0;
//tELL SERver ready
nwClient->Send(GameLogic::Protocol_General_Status(GameLogic::Protocol_General_Status::States_ready));
return true; return true;
} }
GameState::gameStateState GameState::LoadGame() GameState::gameStateState GameState::LoadGame()
@ -84,11 +88,10 @@ bool GameState::LoadModels(std::wstring mapFile)
// open file // open file
// read file // read file
// init models // init models
int nrOfBoxex = 20; int nrOfBoxex = 5;
privData->modelCount = 3+nrOfBoxex; int id = 100;
myId += privData->modelCount;
int id = 0; // add world model
// add world model
ModelInitData modelData; ModelInitData modelData;
Oyster::Math3D::Float4x4 translate; Oyster::Math3D::Float4x4 translate;
C_Object* obj; C_Object* obj;
@ -104,7 +107,8 @@ bool GameState::LoadModels(std::wstring mapFile)
privData->object.push_back(obj); privData->object.push_back(obj);
privData->object[privData->object.size() -1 ]->Init(modelData); privData->object[privData->object.size() -1 ]->Init(modelData);
// add box model
// add box model
modelData.world = Oyster::Math3D::Float4x4::identity; modelData.world = Oyster::Math3D::Float4x4::identity;
modelData.modelPath = L"crate_colonists.dan"; modelData.modelPath = L"crate_colonists.dan";
@ -120,89 +124,63 @@ bool GameState::LoadModels(std::wstring mapFile)
privData->object[privData->object.size() -1 ]->Init(modelData); privData->object[privData->object.size() -1 ]->Init(modelData);
modelData.world = Oyster::Math3D::Float4x4::identity; modelData.world = Oyster::Math3D::Float4x4::identity;
} }
//
// add crystal model //// add crystal model
modelData.world = Oyster::Math3D::Float4x4::identity; // modelData.world = Oyster::Math3D::Float4x4::identity;
translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(10, 301, 0)); // translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(10, 301, 0));
//
modelData.world = modelData.world * translate; // modelData.world = modelData.world * translate;
modelData.visible = true; // modelData.visible = true;
modelData.modelPath = L"crystalformation_b.dan"; // modelData.modelPath = L"crystalformation_b.dan";
modelData.id = id++; // modelData.id = id++;
// load models // // load models
obj = new C_Player(); // obj = new C_Player();
privData->object.push_back(obj); // privData->object.push_back(obj);
privData->object[privData->object.size() -1 ]->Init(modelData); // privData->object[privData->object.size() -1 ]->Init(modelData);
//
// add house model //// add house model
modelData.world = Oyster::Math3D::Float4x4::identity; // modelData.world = Oyster::Math3D::Float4x4::identity;
translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(-50, 290, 0)); // translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(-50, 290, 0));
Oyster::Math3D::Float4x4 rot = Oyster::Math3D::RotationMatrix(Oyster::Math::Float3(0 ,Utility::Value::Radian(90.0f), 0)); // Oyster::Math3D::Float4x4 rot = Oyster::Math3D::RotationMatrix(Oyster::Math::Float3(0 ,Utility::Value::Radian(90.0f), 0));
//
modelData.world = modelData.world * translate * rot; // modelData.world = modelData.world * translate * rot;
modelData.visible = true; // modelData.visible = true;
modelData.modelPath = L"building_corporation.dan"; // modelData.modelPath = L"building_corporation.dan";
modelData.id = id++; // modelData.id = id++;
// load models // // load models
obj = new C_Player(); // obj = new C_Player();
privData->object.push_back(obj); // privData->object.push_back(obj);
privData->object[privData->object.size() -1 ]->Init(modelData); // privData->object[privData->object.size() -1 ]->Init(modelData);
//
//
// add player model // // add jumppad
modelData.world = Oyster::Math3D::Float4x4::identity; // modelData.world = Oyster::Math3D::Float4x4::identity;
translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(0, 320, 0)); // translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(4, 300.3, 0));
// //Oyster::Math3D::RotationMatrix_AxisZ()
modelData.world = modelData.world * translate; // modelData.world = modelData.world * translate;
modelData.visible = true; // modelData.visible = true;
modelData.modelPath = L"char_still_sizeref.dan"; // modelData.modelPath = L"jumppad_round.dan";
modelData.id = id++; // modelData.id = id++;
// load models // // load models
obj = new C_Player(); // obj = new C_Player();
privData->object.push_back(obj); // privData->object.push_back(obj);
privData->object[privData->object.size() -1 ]->Init(modelData); // privData->object[privData->object.size() -1 ]->Init(modelData);
//
// add player model 2 // // add sky sphere
modelData.world = Oyster::Math3D::Float4x4::identity; // modelData.world = Oyster::Math3D::Float4x4::identity;
translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(50, 320, 0)); // translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(0, 0, 0));
// //Oyster::Math3D::RotationMatrix_AxisZ()
modelData.world = modelData.world * translate; // modelData.world = modelData.world * translate;
modelData.visible = true; // modelData.world.v[0].x = 800;
modelData.modelPath = L"char_still_sizeref.dan"; // modelData.world.v[1].y = 800;
modelData.id = id++; // modelData.world.v[2].z = 800;
// load models // modelData.visible = true;
obj = new C_Player(); // modelData.modelPath = L"skysphere.dan";
privData->object.push_back(obj); // modelData.id = id++;
privData->object[privData->object.size() -1 ]->Init(modelData); // // load models
// obj = new C_Player();
// add jumppad // privData->object.push_back(obj);
modelData.world = Oyster::Math3D::Float4x4::identity; // privData->object[privData->object.size() -1 ]->Init(modelData);
translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(4, 300.3, 0));
//Oyster::Math3D::RotationMatrix_AxisZ()
modelData.world = modelData.world * translate;
modelData.visible = true;
modelData.modelPath = L"jumppad_round.dan";
modelData.id = id++;
// load models
obj = new C_Player();
privData->object.push_back(obj);
privData->object[privData->object.size() -1 ]->Init(modelData);
// add sky sphere
modelData.world = Oyster::Math3D::Float4x4::identity;
translate = Oyster::Math3D::TranslationMatrix(Oyster::Math::Float3(0, 0, 0));
//Oyster::Math3D::RotationMatrix_AxisZ()
modelData.world = modelData.world * translate;
modelData.world.v[0].x = 800;
modelData.world.v[1].y = 800;
modelData.world.v[2].z = 800;
modelData.visible = true;
modelData.modelPath = L"skysphere.dan";
modelData.id = id++;
// load models
obj = new C_Player();
privData->object.push_back(obj);
privData->object[privData->object.size() -1 ]->Init(modelData);
return true; return true;
} }
@ -215,7 +193,7 @@ bool GameState::InitCamera(Oyster::Math::Float3 startPos)
camera->LookAt(pos, dir, up); camera->LookAt(pos, dir, up);
camera->SetLens(3.14f/2, 1024/768, 1, 1000); camera->SetLens(3.14f/2, 1024/768, 1, 1000);
privData->proj = Oyster::Math3D::ProjectionMatrix_Perspective(Oyster::Math::pi/4,1024.0f/768.0f,.1f,1000); privData->proj = Oyster::Math3D::ProjectionMatrix_Perspective(Oyster::Math::pi / 4, 1024.0f / 768.0f, .1f,1000);
//privData->proj = Oyster::Math3D::ProjectionMatrix_Orthographic(1024, 768, 1, 1000); //privData->proj = Oyster::Math3D::ProjectionMatrix_Orthographic(1024, 768, 1, 1000);
Oyster::Graphics::API::SetProjection(privData->proj); Oyster::Graphics::API::SetProjection(privData->proj);
camera->UpdateViewMatrix(); camera->UpdateViewMatrix();
@ -225,15 +203,55 @@ bool GameState::InitCamera(Oyster::Math::Float3 startPos)
privData->view = Oyster::Math3D::InverseOrientationMatrix(privData->view); privData->view = Oyster::Math3D::InverseOrientationMatrix(privData->view);
return true; return true;
} }
void GameState::setClientId(int id) void GameState::InitiatePlayer(int id, std::wstring modelName, Oyster::Math::Float4x4 world)
{ {
myId = id; myId = id;
ModelInitData modelData;
C_Object* obj;
modelData.visible = true;
modelData.world = world;
modelData.modelPath = modelName;
modelData.id = myId;
obj = new C_Player();
privData->object.push_back(obj);
privData->object[privData->object.size() -1 ]->Init(modelData);
//printf("Move message recieved!");
Oyster::Math::Float3 right = Oyster::Math::Float3(world[0], world[1], world[2]);
Oyster::Math::Float3 up = Oyster::Math::Float3(world[4], world[5], world[6]);
Oyster::Math::Float3 objForward = (Oyster::Math::Float3(world[8], world[9], world[10]));
Oyster::Math::Float3 pos = Oyster::Math::Float3(world[12], world[13], world[14]);
Oyster::Math::Float3 cameraLook = camera->GetLook();
Oyster::Math::Float3 cameraUp = camera->GetUp();
/*Oyster::Math::Float3 newUp = cameraUp.Dot(up);
up *= newUp;
up.Normalize();
Oyster::Math::Float3 newLook = up.Cross(right);
newLook.Normalize();*/
camera->setRight(right);
camera->setUp(up);
camera->setLook(objForward);
up *= 2;
objForward *= -3;
Oyster::Math::Float3 cameraPos = up + pos + objForward;
camera->SetPosition(cameraPos);
camera->UpdateViewMatrix();
} }
GameClientState::ClientState GameState::Update(float deltaTime, InputClass* KeyInput) GameClientState::ClientState GameState::Update(float deltaTime, InputClass* KeyInput)
{ {
switch (privData->state) switch (privData->state)
{ {
case gameStateState_loading: case gameStateState_loading: //Will this ever happen in this scope??
{ {
// load map // load map
// wait for all players // wait for all players
@ -465,9 +483,10 @@ void GameState::Protocol( ObjPos* pos )
if(privData->object[i]->GetId() == pos->object_ID) if(privData->object[i]->GetId() == pos->object_ID)
{ {
privData->object[i]->setPos(world); privData->object[i]->setPos(world);
Oyster::Math::Float3 pos = Oyster::Math::Float3(0, 600, 15); Oyster::Math::Float3 position = Oyster::Math::Float3(0, 605, 15);
if(i == myId) // playerobj if(pos->object_ID == myId) // playerobj
{ {
//printf("Move message recieved!");
Oyster::Math::Float3 right = Oyster::Math::Float3(world[0], world[1], world[2]); Oyster::Math::Float3 right = Oyster::Math::Float3(world[0], world[1], world[2]);
Oyster::Math::Float3 up = Oyster::Math::Float3(world[4], world[5], world[6]); Oyster::Math::Float3 up = Oyster::Math::Float3(world[4], world[5], world[6]);
Oyster::Math::Float3 objForward = (Oyster::Math::Float3(world[8], world[9], world[10])); Oyster::Math::Float3 objForward = (Oyster::Math::Float3(world[8], world[9], world[10]));
@ -491,12 +510,13 @@ void GameState::Protocol( ObjPos* pos )
up *= 1; up *= 1;
objForward *= -2; objForward *= -2;
Oyster::Math::Float3 cameraPos = pos + up + objForward; Oyster::Math::Float3 cameraPos = position + up + objForward;
camera->SetPosition(cameraPos); //camera->SetPosition(cameraPos);
camera->UpdateViewMatrix();
} }
camera->SetPosition(pos); camera->SetPosition(position);
//camera->UpdateViewMatrix();
} }
} }
} }

View File

@ -37,8 +37,8 @@ public:
GameClientState::ClientState Update(float deltaTime, InputClass* KeyInput) override; GameClientState::ClientState Update(float deltaTime, InputClass* KeyInput) override;
bool LoadModels(std::wstring mapFile) ; bool LoadModels(std::wstring mapFile) ;
bool InitCamera(Oyster::Math::Float3 startPos) ; bool InitCamera(Oyster::Math::Float3 startPos) ;
void InitiatePlayer(int id, std::wstring modelName, Oyster::Math::Float4x4 world);
gameStateState LoadGame(); gameStateState LoadGame();
void setClientId(int id);
void readKeyInput(InputClass* KeyInput); void readKeyInput(InputClass* KeyInput);
bool Render()override; bool Render()override;
bool Release()override; bool Release()override;

View File

@ -5,6 +5,7 @@
#include "C_obj/C_StaticObj.h" #include "C_obj/C_StaticObj.h"
#include "C_obj/C_DynamicObj.h" #include "C_obj/C_DynamicObj.h"
#include <GameServerAPI.h> #include <GameServerAPI.h>
#include <Protocols.h>
using namespace DanBias::Client; using namespace DanBias::Client;
@ -88,9 +89,15 @@ GameClientState::ClientState LobbyState::Update(float deltaTime, InputClass* Key
// send data to server // send data to server
// check data from server // check data from server
if( KeyInput->IsKeyPressed(DIK_G)) if(GameServerAPI::ServerIsRunning() && GameServerAPI::ServerIsRunning()) //May be a problem if server is not shut down properly after lan session.
{ {
return ClientState_Game; if( KeyInput->IsKeyPressed(DIK_G))
{
if(!DanBias::GameServerAPI::GameStart())
{
//this->nwClient->Send(GameLogic::Protocol_LobbyStartGame());
}
}
} }
return ClientState_Same; return ClientState_Same;

View File

@ -105,7 +105,7 @@ GameClientState::ClientState LoginState::Update(float deltaTime, InputClass* Key
DanBias::GameServerAPI::ServerInitiate(desc); DanBias::GameServerAPI::ServerInitiate(desc);
DanBias::GameServerAPI::ServerStart(); DanBias::GameServerAPI::ServerStart();
// my ip // my ip
nwClient->Connect(15151, "127.0.0.1"); nwClient->Connect(15152, "127.0.0.1");
if (!nwClient->IsConnected()) if (!nwClient->IsConnected())
{ {
@ -118,7 +118,7 @@ GameClientState::ClientState LoginState::Update(float deltaTime, InputClass* Key
if( KeyInput->IsKeyPressed(DIK_J)) if( KeyInput->IsKeyPressed(DIK_J))
{ {
// game ip // game ip
nwClient->Connect(15151, "127.0.0.1"); nwClient->Connect(15152, "127.0.0.1");
if (!nwClient->IsConnected()) if (!nwClient->IsConnected())
{ {

View File

@ -14,7 +14,10 @@ AttatchmentSocket::AttatchmentSocket(void)
AttatchmentSocket::~AttatchmentSocket(void) AttatchmentSocket::~AttatchmentSocket(void)
{ {
if(this->attatchment)
delete this->attatchment;
this->attatchment = 0;
} }
IAttatchment* AttatchmentSocket::GetAttatchment() IAttatchment* AttatchmentSocket::GetAttatchment()

View File

@ -83,7 +83,7 @@ using namespace GameLogic;
if(kineticEnergyLoss > forceThreashHold) //should only take damage if the force is high enough if(kineticEnergyLoss > forceThreashHold) //should only take damage if the force is high enough
{ {
damageDone = kineticEnergyLoss * 0.10f; damageDone = (int)(kineticEnergyLoss * 0.10f);
//player.DamageLife(damageDone); //player.DamageLife(damageDone);
} }

View File

@ -68,12 +68,12 @@ void Game::GetAllPlayerPositions() const
Game::PlayerData* Game::CreatePlayer() Game::PlayerData* Game::CreatePlayer()
{ {
// Find a free space in array or insert at end // Find a free space in array or insert at end
int id = InsertObject(this->players, (PlayerData*)0); int i = InsertObject(this->players, (PlayerData*)0);
this->players[id] = new PlayerData(); this->players[i] = new PlayerData();
//this->players[id]->player->GetRigidBody()->SetSubscription(Game::PhysicsOnMove); //this->players[i]->player->GetRigidBody()->SetSubscription(Game::PhysicsOnMove);
return this->players[id]; return this->players[i];
} }
Game::LevelData* Game::CreateLevel() Game::LevelData* Game::CreateLevel()
@ -93,7 +93,6 @@ void Game::CreateTeam()
bool Game::NewFrame() bool Game::NewFrame()
{ {
for (unsigned int i = 0; i < this->players.Size(); i++) for (unsigned int i = 0; i < this->players.Size(); i++)
{ {
if(this->players[i]->player) this->players[i]->player->BeginFrame(); if(this->players[i]->player) this->players[i]->player->BeginFrame();
@ -104,31 +103,10 @@ bool Game::NewFrame()
for (unsigned int i = 0; i < this->players.Size(); i++) for (unsigned int i = 0; i < this->players.Size(); i++)
{ {
if(this->players[i]->player) this->players[i]->player->EndFrame(); if(this->players[i]->player) this->players[i]->player->EndFrame();
} gameInstance.onMoveFnc(this->players[i]);
for (unsigned int i = 0; i < this->players.Size(); i++)
{
if(this->players[i]->player) this->players[i]->player->BeginFrame();
} }
API::Instance().UpdateWorld();
for (unsigned int i = 0; i < this->players.Size(); i++)
{
if(this->players[i]->player) this->players[i]->player->EndFrame();
}
for (unsigned int i = 0; i < this->players.Size(); i++)
{
if(this->players[i]->player) this->players[i]->player->BeginFrame();
}
API::Instance().UpdateWorld();
for (unsigned int i = 0; i < this->players.Size(); i++)
{
if(this->players[i]->player) this->players[i]->player->EndFrame();
}
gameInstance.onMoveFnc(this->level);
return true; return true;
} }
@ -143,24 +121,21 @@ void Game::SetFrameTimeLength( float seconds )
this->frameTime = seconds; this->frameTime = seconds;
} }
void Game::SetSubscription(GameEvent::ObjectEventFunctionType type, GameEvent::ObjectEventFunction functionPointer) void Game::SetSubscription(GameEvent::ObjectMovedFunction functionPointer)
{ {
switch (type) this->onMoveFnc = functionPointer;
{ }
case GameLogic::GameEvent::ObjectEventFunctionType_OnMove: void Game::SetSubscription(GameEvent::ObjectDisabledFunction functionPointer)
this->onMoveFnc = functionPointer; {
break; this->onDisableFnc = functionPointer;
case GameLogic::GameEvent::ObjectEventFunctionType_OnDead:
this->onDisableFnc = functionPointer;
break;
}
} }
bool Game::Initiate() bool Game::Initiate()
{ {
API::Instance().Init(); API::Instance().Init();
//API::Instance().SetSubscription(Game::PhysicsOnDestroy); //API::Instance().SetSubscription(Game::PhysicsOnDestroy);
//API::Instance().SetFrameTimeLength(this->frameTime);
this->initiated = true; this->initiated = true;
return true; return true;
} }
@ -183,6 +158,6 @@ void Game::PhysicsOnMove(const ICustomBody *object)
} }
void Game::PhysicsOnDestroy(::Utility::DynamicMemory::UniquePointer<ICustomBody> proto) void Game::PhysicsOnDestroy(::Utility::DynamicMemory::UniquePointer<ICustomBody> proto)
{ {
if(gameInstance.onDisableFnc) gameInstance.onDisableFnc(0); if(gameInstance.onDisableFnc) gameInstance.onDisableFnc(0, 0);
} }

View File

@ -69,7 +69,8 @@ namespace GameLogic
bool NewFrame() override; bool NewFrame() override;
void SetFPS( int FPS ) override; void SetFPS( int FPS ) override;
void SetFrameTimeLength( float seconds ) override; void SetFrameTimeLength( float seconds ) override;
void SetSubscription(GameEvent::ObjectEventFunctionType type, GameEvent::ObjectEventFunction functionPointer) override; void SetSubscription(GameEvent::ObjectMovedFunction functionPointer) override;
void SetSubscription(GameEvent::ObjectDisabledFunction functionPointer) override;
bool Initiate() override; bool Initiate() override;
float GetFrameTime() const; float GetFrameTime() const;
@ -81,8 +82,8 @@ namespace GameLogic
LevelData* level; LevelData* level;
float frameTime; float frameTime;
bool initiated; bool initiated;
GameEvent::ObjectEventFunction onDisableFnc; GameEvent::ObjectDisabledFunction onDisableFnc;
GameEvent::ObjectEventFunction onMoveFnc; GameEvent::ObjectMovedFunction onMoveFnc;
}; };
} }

View File

@ -23,16 +23,8 @@ namespace GameLogic
*/ */
namespace GameEvent namespace GameEvent
{ {
/** typedef void(*ObjectMovedFunction)(IObjectData* object); // Callback method that recieves and object
* The type of event to listen on. typedef void(*ObjectDisabledFunction)(IObjectData* object, float seconds); // Callback method that recieves and object
*/
enum ObjectEventFunctionType
{
ObjectEventFunctionType_OnMove,
ObjectEventFunctionType_OnDead,
};
typedef void(*ObjectEventFunction)(IObjectData* object); // Callback method that recieves and object
//etc... //etc...
}; };
@ -147,17 +139,22 @@ namespace GameLogic
/** Set the frame time in fps /** Set the frame time in fps
* @param FPS The fps to set * @param FPS The fps to set
*/ */
virtual void SetFPS( int FPS = 60 ) = 0; virtual void SetFPS( int FPS = 120 ) = 0;
/** Set the frames time in seconds /** Set the frames time in seconds
* @param seconds The frame length * @param seconds The frame length
*/ */
virtual void SetFrameTimeLength( float seconds ) = 0; virtual void SetFrameTimeLength( float seconds = (1.0f/120.0f) ) = 0;
/** Set a specific object event subscription callback /** Set a specific object event subscription callback
* @param * @param
*/ */
virtual void SetSubscription(GameEvent::ObjectEventFunctionType type, GameEvent::ObjectEventFunction functionPointer) = 0; virtual void SetSubscription(GameEvent::ObjectMovedFunction functionPointer) = 0;
/** Set a specific object event subscription callback
* @param
*/
virtual void SetSubscription(GameEvent::ObjectDisabledFunction functionPointer) = 0;
}; };
} }

View File

@ -1,7 +1,7 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup> <PropertyGroup>
<ShowAllFiles>false</ShowAllFiles> <ShowAllFiles>true</ShowAllFiles>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<LocalDebuggerWorkingDirectory>$(OutDir)</LocalDebuggerWorkingDirectory> <LocalDebuggerWorkingDirectory>$(OutDir)</LocalDebuggerWorkingDirectory>

View File

@ -1,5 +1,6 @@
#include "Level.h" #include "Level.h"
#include "CollisionManager.h" #include "CollisionManager.h"
#include "Game.h"
using namespace GameLogic; using namespace GameLogic;
using namespace Utility::DynamicMemory; using namespace Utility::DynamicMemory;
@ -50,6 +51,7 @@ void Level::InitiateLevel(float radius)
z /= norm; z /= norm;
} }
int idCount = 100;
// add level sphere // add level sphere
ICustomBody* rigidBody = API::Instance().AddCollisionSphere(599.2f, Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(0, 0, 0), 0); ICustomBody* rigidBody = API::Instance().AddCollisionSphere(599.2f, Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(0, 0, 0), 0);
@ -58,24 +60,23 @@ void Level::InitiateLevel(float radius)
state.restitutionCoeff = 0.2f; state.restitutionCoeff = 0.2f;
rigidBody->SetState(state); rigidBody->SetState(state);
levelObj = new StaticObject(rigidBody, LevelCollisionBefore, LevelCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_WORLD); levelObj = new StaticObject(rigidBody, LevelCollisionBefore, LevelCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_WORLD);
this->levelObj->objectID = idCount++;
rigidBody->SetCustomTag(levelObj); rigidBody->SetCustomTag(levelObj);
ICustomBody* rigidBody_TestBox; ICustomBody* rigidBody_TestBox;
int nrOfBoxex = 5; int nrOfBoxex = 5;
int offset = 0; int offset = 0;
for(int i =0; i< nrOfBoxex; i ++) for(int i =0; i< nrOfBoxex; i ++)
{ {
rigidBody_TestBox = API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(0, 605 + i*5, 5), 5); rigidBody_TestBox = API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(0, 605 + i*5, -10), 5);
this->dynamicObjects.Push(new DynamicObject(rigidBody_TestBox,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_BOX)); this->dynamicObjects.Push(new DynamicObject(rigidBody_TestBox,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_BOX));
this->dynamicObjects[i]->objectID = idCount++;
rigidBody_TestBox->SetCustomTag(this->dynamicObjects[i]); rigidBody_TestBox->SetCustomTag(this->dynamicObjects[i]);
} }
offset += nrOfBoxex; /*offset += nrOfBoxex;
for(int i =0; i< nrOfBoxex; i ++) for(int i =0; i< nrOfBoxex; i ++)
{ {
rigidBody_TestBox = API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(0,5, -605 -( i*5)), 5); rigidBody_TestBox = API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(0,5, -605 -( i*5)), 5);
@ -100,26 +101,26 @@ void Level::InitiateLevel(float radius)
this->dynamicObjects.Push(new DynamicObject(rigidBody_TestBox,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_BOX)); this->dynamicObjects.Push(new DynamicObject(rigidBody_TestBox,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_BOX));
rigidBody_TestBox->SetCustomTag(this->dynamicObjects[i]); rigidBody_TestBox->SetCustomTag(this->dynamicObjects[i]);
} }*/
// add crystal //// add crystal
ICustomBody* rigidBody_Crystal = API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(10, 605, 0), 5); //ICustomBody* rigidBody_Crystal = API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(10, 605, 0), 5);
this->dynamicObjects.Push(new DynamicObject(rigidBody_Crystal,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_BOX)); //this->dynamicObjects.Push(new DynamicObject(rigidBody_Crystal,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_BOX));
rigidBody_Crystal->SetCustomTag(this->dynamicObjects[nrOfBoxex]); //rigidBody_Crystal->SetCustomTag(this->dynamicObjects[nrOfBoxex]);
//
// add house //// add house
ICustomBody* rigidBody_House =API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(10, 905, 0), 0); //ICustomBody* rigidBody_House =API::Instance().AddCollisionBox(Oyster::Math::Float3(0.5f, 0.5f, 0.5f), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(10, 905, 0), 0);
this->staticObjects.Push(new StaticObject(rigidBody_House,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_GENERIC)); //this->staticObjects.Push(new StaticObject(rigidBody_House,Object::DefaultCollisionBefore, Object::DefaultCollisionAfter, OBJECT_TYPE::OBJECT_TYPE_GENERIC));
rigidBody_House->SetCustomTag(this->staticObjects[0]); //rigidBody_House->SetCustomTag(this->staticObjects[0]);
} }
void Level::AddPlayerToTeam(Player *player, int teamID) void Level::AddPlayerToTeam(Player *player, int teamID)
@ -154,4 +155,6 @@ void Level::PhysicsOnMoveLevel(const ICustomBody *object)
{ {
// function call from physics update when object was moved // function call from physics update when object was moved
Object* temp = (Object*)object->GetCustomTag(); Object* temp = (Object*)object->GetCustomTag();
((Game*)&Game::Instance())->onMoveFnc(temp);
} }

View File

@ -1,3 +1,7 @@
/////////////////////////////////////
// Created by Pontus Fransson 2013 //
/////////////////////////////////////
#include "LevelParser.h" #include "LevelParser.h"
#include "Loader.h" #include "Loader.h"
@ -9,7 +13,7 @@ using namespace Utility::DynamicMemory;
LevelParser::LevelParser() LevelParser::LevelParser()
{ {
formatVersion.formatVersionMajor = 1; formatVersion.formatVersionMajor = 2;
formatVersion.formatVersionMinor = 0; formatVersion.formatVersionMinor = 0;
} }
@ -29,35 +33,100 @@ std::vector<SmartPointer<ObjectTypeHeader>> LevelParser::Parse(std::string filen
char* buffer = (char*)loader.LoadFile(filename.c_str(), bufferSize); char* buffer = (char*)loader.LoadFile(filename.c_str(), bufferSize);
//Read format version //Read format version
FormatVersion levelFormatVersion; LevelLoaderInternal::FormatVersion levelFormatVersion;
ParseObject(&buffer[counter], &levelFormatVersion, sizeof(levelFormatVersion)); ParseObject(&buffer[counter], &levelFormatVersion, sizeof(levelFormatVersion));
counter += sizeof(levelFormatVersion); counter += sizeof(levelFormatVersion);
if(this->formatVersion != levelFormatVersion) if(this->formatVersion != levelFormatVersion)
{ {
//Do something if it's not the same version //Do something if it's not the same version
//Returns an empty vector, because it will most likely fail to read the level format.
return objects;
} }
while(counter < bufferSize) while(counter < bufferSize)
{ {
//Get typeID //Get typeID
ObjectTypeHeader typeID; ObjectType typeID;
ParseObject(&buffer[counter], &typeID, sizeof(typeID)); ParseObject(&buffer[counter], &typeID, sizeof(typeID));
switch((int)typeID.typeID) switch((int)typeID)
{ {
case ObjectType_LevelMetaData: case ObjectType_LevelMetaData:
{ {
LevelMetaData* header = new LevelMetaData; SmartPointer<ObjectTypeHeader> header = new LevelMetaData;
ParseLevelMetaData(&buffer[counter], *header, counter); ParseLevelMetaData(&buffer[counter], *(LevelMetaData*)header.Get(), counter);
objects.push_back(header); objects.push_back(header);
break; break;
} }
//This is by design, static and dynamic is using the same converter. Do not add anything inbetween them. //This is by design, static and dynamic is using the same converter. Do not add anything inbetween them.
//Unless they are changed to not be the same.
case ObjectType_Static: case ObjectType_Dynamic: case ObjectType_Static: case ObjectType_Dynamic:
{ {
ObjectHeader* header = new ObjectHeader; //Get specialType.
ParseObject(&buffer[counter], *header, counter); ObjectSpecialType specialType;
objects.push_back(header); ParseObject(&buffer[counter+4], &specialType, sizeof(typeID));
switch(specialType)
{
//These three does not have any specail variables at this time.
//There for they are using the same 'parser'.
case ObjectSpecialType_World:
case ObjectSpecialType_Building:
case ObjectSpecialType_Damaging:
case ObjectSpecialType_Explosive:
{
ObjectHeader* header = new ObjectHeader;
ParseObject(&buffer[counter], *header, counter);
objects.push_back(header);
break;
}
case ObjectSpecialType_JumpPad:
{
JumpPadAttributes* header = new JumpPadAttributes;
ParseObject(&buffer[counter], *header, counter);
//Read the spec
ParseObject(&buffer[counter], header->direction, 16);
objects.push_back(header);
break;
}
case ObjectSpecialType_BoostPad:
{
JumpPadAttributes* header = new JumpPadAttributes;
ParseObject(&buffer[counter], *header, counter);
ParseObject(&buffer[counter], header->direction, 16);
objects.push_back(header);
break;
}
case ObjectSpecialType_Portal:
{
PortalAttributes* header = new PortalAttributes;
ParseObject(&buffer[counter], *header, counter);
ParseObject(&buffer[counter], header->destination, 12);
objects.push_back(header);
break;
}
case ObjectSpecialType_SpawnPoint:
{
SpawnPointAttributes* header = new SpawnPointAttributes;
ParseObject(&buffer[counter], *header, counter);
ParseObject(&buffer[counter], header->spawnPosition, 12);
objects.push_back(header);
break;
}
default:
//Couldn't find specialType
break;
}
break; break;
} }
@ -68,7 +137,12 @@ std::vector<SmartPointer<ObjectTypeHeader>> LevelParser::Parse(std::string filen
//Get Light type //Get Light type
ParseObject(&buffer[counter+4], &lightType, sizeof(lightType)); ParseObject(&buffer[counter+4], &lightType, sizeof(lightType));
switch(lightType) //We only support PointLight for now.
BasicLight* header = new BasicLight;
ParseObject(&buffer[counter], header, sizeof(*header));
counter += sizeof(*header);
objects.push_back(header);
/*switch(lightType)
{ {
case LightType_PointLight: case LightType_PointLight:
{ {
@ -98,7 +172,7 @@ std::vector<SmartPointer<ObjectTypeHeader>> LevelParser::Parse(std::string filen
//Undefined LightType. //Undefined LightType.
break; break;
} }
break; break;*/
} }
default: default:
//Couldn't find typeID. FAIL!!!!!! //Couldn't find typeID. FAIL!!!!!!
@ -123,21 +197,25 @@ LevelMetaData LevelParser::ParseHeader(std::string filename)
char* buffer = (char*)loader.LoadFile(filename.c_str(), bufferSize); char* buffer = (char*)loader.LoadFile(filename.c_str(), bufferSize);
//Read format version //Read format version
FormatVersion levelFormatVersion; LevelLoaderInternal::FormatVersion levelFormatVersion;
ParseObject(&buffer[counter], &levelFormatVersion, sizeof(formatVersion)); ParseObject(&buffer[counter], &levelFormatVersion, sizeof(formatVersion));
counter += sizeof(levelFormatVersion); counter += sizeof(levelFormatVersion);
if(this->formatVersion != levelFormatVersion) if(this->formatVersion != levelFormatVersion)
{ {
//Do something if it's not the same version //Do something if it's not the same version
//Returns an empty levelHeader with ObjectType_Unknown.
//Because it will not be able to read another version of the level format.
return levelHeader;
} }
//Find the header in the returned string. //Find the header in the returned string.
while(counter < bufferSize) while(counter < bufferSize)
{ {
ObjectTypeHeader typeID; ObjectType typeID;
ParseObject(&buffer[counter], &typeID, sizeof(typeID)); ParseObject(&buffer[counter], &typeID, sizeof(typeID));
switch(typeID.typeID) switch(typeID)
{ {
case ObjectType_LevelMetaData: case ObjectType_LevelMetaData:
ParseLevelMetaData(&buffer[counter], levelHeader, counter); ParseLevelMetaData(&buffer[counter], levelHeader, counter);
@ -149,6 +227,24 @@ LevelMetaData LevelParser::ParseHeader(std::string filename)
{ {
ObjectHeader header; ObjectHeader header;
ParseObject(&buffer[counter], header, counter); ParseObject(&buffer[counter], header, counter);
switch(header.specialTypeID)
{
case ObjectSpecialType_JumpPad:
counter += sizeof(16);
break;
case ObjectSpecialType_BoostPad:
counter += sizeof(16);
break;
case ObjectSpecialType_Portal:
counter += sizeof(12);
break;
case ObjectSpecialType_SpawnPoint:
counter += sizeof(12);
break;
default:
break;
}
break; break;
} }
@ -157,6 +253,9 @@ LevelMetaData LevelParser::ParseHeader(std::string filename)
LightType lightType; LightType lightType;
ParseObject(&buffer[counter+4], &lightType, sizeof(lightType)); ParseObject(&buffer[counter+4], &lightType, sizeof(lightType));
//We only support pointlight for now.
counter += sizeof(BasicLight);
/*
switch(lightType) switch(lightType)
{ {
case LightType_PointLight: case LightType_PointLight:
@ -177,7 +276,7 @@ LevelMetaData LevelParser::ParseHeader(std::string filename)
default: default:
//Undefined LightType. //Undefined LightType.
break; break;
} }*/
} }
default: default:

View File

@ -23,7 +23,7 @@ namespace GameLogic
LevelMetaData ParseHeader(std::string filename); LevelMetaData ParseHeader(std::string filename);
private: private:
FormatVersion formatVersion; LevelLoaderInternal::FormatVersion formatVersion;
}; };
} }

View File

@ -9,7 +9,7 @@ namespace GameLogic
/************************************ /************************************
Enums Enums
*************************************/ *************************************/
enum ObjectType enum ObjectType
{ {
ObjectType_LevelMetaData, ObjectType_LevelMetaData,
@ -23,6 +23,21 @@ namespace GameLogic
ObjectType_Unknown = -1 ObjectType_Unknown = -1
}; };
enum ObjectSpecialType
{
ObjectSpecialType_World, //Always the main celestial body
ObjectSpecialType_Building,
ObjectSpecialType_Damaging,
ObjectSpecialType_Explosive,
ObjectSpecialType_JumpPad,
ObjectSpecialType_BoostPad,
ObjectSpecialType_Portal,
ObjectSpecialType_SpawnPoint,
ObjectSpecialType_Count,
ObjectSpecialType_Unknown = -1
};
enum UsePhysics enum UsePhysics
{ {
UsePhysics_UseFullPhysics, UsePhysics_UseFullPhysics,
@ -38,16 +53,18 @@ namespace GameLogic
{ {
CollisionGeometryType_Box, CollisionGeometryType_Box,
CollisionGeometryType_Sphere, CollisionGeometryType_Sphere,
CollisionGeometryType_Cylinder,
CollisionGeometryType_Count, CollisionGeometryType_Count,
CollisionGeometryType_Unknown = -1 CollisionGeometryType_Unknown = -1
}; };
//Only supports Pointlight right now.
enum LightType enum LightType
{ {
LightType_PointLight, LightType_PointLight,
LightType_DirectionalLight, //LightType_DirectionalLight,
LightType_SpotLight, //LightType_SpotLight,
LightType_Count, LightType_Count,
LightType_Unknown = -1 LightType_Unknown = -1
@ -80,38 +97,93 @@ namespace GameLogic
/************************************ /************************************
Structs Structs
*************************************/ *************************************/
namespace LevelLoaderInternal
struct FormatVersion
{ {
unsigned int formatVersionMajor; struct FormatVersion
unsigned int formatVersionMinor;
bool operator ==(const FormatVersion& obj)
{ {
return (this->formatVersionMajor != obj.formatVersionMajor && this->formatVersionMinor != obj.formatVersionMinor); unsigned int formatVersionMajor;
} unsigned int formatVersionMinor;
FormatVersion()
: formatVersionMajor(0), formatVersionMinor(0)
{}
bool operator !=(const FormatVersion& obj) FormatVersion(unsigned int major, unsigned int minor)
{ : formatVersionMajor(major), formatVersionMinor(minor)
return !(*this == obj); {}
}
}; bool operator ==(const FormatVersion& obj)
{
return (this->formatVersionMajor == obj.formatVersionMajor && this->formatVersionMinor == obj.formatVersionMinor);
}
bool operator !=(const FormatVersion& obj)
{
return !(*this == obj);
}
};
}
struct ObjectTypeHeader struct ObjectTypeHeader
{ {
ObjectType typeID; ObjectType typeID;
//Unless this is here the object destructor wont be called.
virtual ~ObjectTypeHeader(){}
}; };
struct PhysicsObject namespace LevelLoaderInternal
{ {
UsePhysics usePhysics; const FormatVersion boundingVolumeVersion(1, 0);
float mass;
float inertiaMagnitude[3]; struct BoundingVolumeBase
float inertiaRotation[3]; {
float frictionCoeffStatic; float position[3];
float frictionCoeffDynamic; };
CollisionGeometryType geometryType;
}; struct BoundingVolumeBox : public BoundingVolumeBase
{
float size[3];
float angularAxis[3];
float angle;
};
struct BoundingVolumeSphere : public BoundingVolumeBase
{
float radius;
};
struct BoundingVolumeCylinder : public BoundingVolumeBase
{
float length;
float angularAxis[3];
float angle;
float radius;
};
struct BoundingVolume
{
CollisionGeometryType geoType;
union
{
LevelLoaderInternal::BoundingVolumeBox box;
LevelLoaderInternal::BoundingVolumeSphere sphere;
LevelLoaderInternal::BoundingVolumeCylinder cylinder;
};
};
struct PhysicsObject
{
UsePhysics usePhysics;
float mass;
float inertiaMagnitude[3];
float inertiaRotation[3];
float frictionCoeffStatic;
float frictionCoeffDynamic;
float restitutionCoeff;
BoundingVolume boundingVolume;
};
}
struct LevelMetaData : public ObjectTypeHeader struct LevelMetaData : public ObjectTypeHeader
{ {
@ -123,10 +195,15 @@ namespace GameLogic
WorldSize worldSize; WorldSize worldSize;
std::string overviewPicturePath; std::string overviewPicturePath;
std::vector<GameMode> gameModesSupported; std::vector<GameMode> gameModesSupported;
virtual ~LevelMetaData(){}
}; };
struct ObjectHeader : public ObjectTypeHeader, public PhysicsObject struct ObjectHeader : public ObjectTypeHeader, public LevelLoaderInternal::PhysicsObject
{ {
//Special type id for special objects: portal, jumppad, exploding objects, etc.
ObjectSpecialType specialTypeID;
//Model, //Model,
std::string ModelFile; std::string ModelFile;
//Position //Position
@ -136,8 +213,29 @@ namespace GameLogic
float angle; float angle;
//Scale //Scale
float scale[3]; float scale[3];
virtual ~ObjectHeader(){}
}; };
/************************************
Special objects
*************************************/
struct JumpPadAttributes : public ObjectHeader
{
float direction[3];
float power;
};
struct PortalAttributes : public ObjectHeader
{
float destination[3];
};
struct SpawnPointAttributes : public ObjectHeader
{
float spawnPosition[3];
};
/************************************ /************************************
Lights Lights
@ -145,12 +243,13 @@ namespace GameLogic
struct BasicLight : public ObjectTypeHeader struct BasicLight : public ObjectTypeHeader
{ {
LightType lightType; LightType lightType; //Is not used right now
float ambientColor[3]; float color[3];
float diffuseColor[3]; float position[3];
float specularColor[3]; float raduis;
float intensity;
}; };
/* We only support pointlight right now.
struct PointLight : public BasicLight struct PointLight : public BasicLight
{ {
float position[3]; float position[3];
@ -166,7 +265,7 @@ namespace GameLogic
float direction[3]; float direction[3];
float range; float range;
float attenuation[3]; float attenuation[3];
}; };*/
} }
#endif #endif

View File

@ -4,6 +4,7 @@
#include "ParseFunctions.h" #include "ParseFunctions.h"
#include "../../../Misc/Packing/Packing.h" #include "../../../Misc/Packing/Packing.h"
#include "Loader.h"
#include <string> #include <string>
using namespace Oyster::Packing; using namespace Oyster::Packing;
@ -29,6 +30,9 @@ namespace GameLogic
memcpy(&header.typeID, &buffer[start], 4); memcpy(&header.typeID, &buffer[start], 4);
start += 4; start += 4;
memcpy(&header.specialTypeID, &buffer[start], 4);
start += 4;
memcpy(&tempSize, &buffer[start], 4); memcpy(&tempSize, &buffer[start], 4);
start += 4; start += 4;
@ -36,13 +40,18 @@ namespace GameLogic
header.ModelFile.assign(&tempName[0], &tempName[tempSize]); header.ModelFile.assign(&tempName[0], &tempName[tempSize]);
start += tempSize; start += tempSize;
//The reset of the object struct
//3 float[3], 1 float //3 float[3], 1 float
memcpy(&header.position, &buffer[start], 40); memcpy(&header.position, &buffer[start], 40);
start += 40; start += 40;
//2 float[3], 3 float, 2 uint //Physics struct
//2 float[3], 4 float, 1 uint
memcpy(&header.usePhysics, &buffer[start], 44); memcpy(&header.usePhysics, &buffer[start], 44);
start += 44; start += 44;
//Read path for bounding volume
ParseBoundingVolume(&buffer[start], header.boundingVolume, start);
size += start; size += start;
} }
@ -107,5 +116,55 @@ namespace GameLogic
size += start; size += start;
} }
void ParseBoundingVolume(char* buffer, LevelLoaderInternal::BoundingVolume& volume, int &size)
{
int start = 0;
int tempSize = 0;
char tempName[128];
memcpy(&tempSize, &buffer[start], 4);
start += 4;
memcpy(&tempName, &buffer[start], tempSize);
string fileName;
fileName.assign(&tempName[0], &tempName[tempSize]);
start += tempSize;
//Läs in filen.
int fileLength = 0;
Loader loader;
char* buf = loader.LoadFile("E:\\Dropbox\\Programming\\Github\\Danbias\\Bin\\Content\\Worlds\\cgf\\"+ fileName, fileLength);
LevelLoaderInternal::FormatVersion version;
memcpy(&version, &buffer[0], sizeof(version));
memcpy(&volume.geoType, &buf[8], sizeof(volume.geoType));
//start += sizeof(volume.geoType);
switch(volume.geoType)
{
case CollisionGeometryType_Box:
memcpy(&volume.box, &buf[12], sizeof(volume.box));
//start += sizeof(volume.box);
break;
case CollisionGeometryType_Sphere:
memcpy(&volume.sphere, &buf[12], sizeof(volume.sphere));
//start += sizeof(volume.sphere);
break;
case CollisionGeometryType_Cylinder:
memcpy(&volume.cylinder, &buf[12], sizeof(volume.cylinder));
//start += sizeof(volume.cylinder);
break;
default:
break;
}
size += start;
}
} }
} }

View File

@ -21,6 +21,7 @@ namespace GameLogic
void ParseObject(char* buffer, void *header, int size); void ParseObject(char* buffer, void *header, int size);
void ParseObject(char* buffer, ObjectHeader& header, int& size); void ParseObject(char* buffer, ObjectHeader& header, int& size);
void ParseLevelMetaData(char* buffer, LevelMetaData &header, int &size); void ParseLevelMetaData(char* buffer, LevelMetaData &header, int &size);
void ParseBoundingVolume(char* buffer, LevelLoaderInternal::BoundingVolume& volume, int &size);
} }
} }

View File

@ -102,8 +102,6 @@ Oyster::Physics::ICustomBody* Object::GetRigidBody()
void Object::BeginFrame() void Object::BeginFrame()
{ {
this->rigidBody->SetState(this->newPhysicsState); this->rigidBody->SetState(this->newPhysicsState);
} }
// update physic // update physic

View File

@ -43,7 +43,8 @@ namespace GameLogic
static Oyster::Physics::ICustomBody::SubscriptMessage DefaultCollisionBefore(Oyster::Physics::ICustomBody *rigidBodyLevel, Oyster::Physics::ICustomBody *obj); static Oyster::Physics::ICustomBody::SubscriptMessage DefaultCollisionBefore(Oyster::Physics::ICustomBody *rigidBodyLevel, Oyster::Physics::ICustomBody *obj);
static Oyster::Physics::ICustomBody::SubscriptMessage DefaultCollisionAfter(Oyster::Physics::ICustomBody *rigidBodyLevel, Oyster::Physics::ICustomBody *obj, Oyster::Math::Float kineticEnergyLoss); static Oyster::Physics::ICustomBody::SubscriptMessage DefaultCollisionAfter(Oyster::Physics::ICustomBody *rigidBodyLevel, Oyster::Physics::ICustomBody *obj, Oyster::Math::Float kineticEnergyLoss);
private:
public: //TODO: Hax This should be private when level is dynamic
OBJECT_TYPE type; OBJECT_TYPE type;
int objectID; int objectID;

View File

@ -208,7 +208,7 @@ void Player::DamageLife(int damage)
{ {
this->life = 0; this->life = 0;
playerState = PLAYER_STATE_DEAD; playerState = PLAYER_STATE_DEAD;
this->gameInstance->onDisableFnc(this); this->gameInstance->onDisableFnc(this, 0.0f);
} }
} }

View File

@ -85,8 +85,8 @@ namespace GameLogic
int teamID; int teamID;
Weapon *weapon; Weapon *weapon;
PLAYER_STATE playerState; PLAYER_STATE playerState;
Oyster::Math::Float3 lookDir; Oyster::Math::Float3 lookDir; //Duplicate in Object.h?
Oyster::Math::Float dx; Oyster::Math::Float dx; //dx of what?
bool hasTakenDamage; bool hasTakenDamage;
float invincibleCooldown; float invincibleCooldown;

View File

@ -35,13 +35,11 @@ TeamManager::~TeamManager(void)
void TeamManager::RespawnPlayerRandom(Player *player) void TeamManager::RespawnPlayerRandom(Player *player)
{ {
// Whats going on here? int teamID = player->GetTeamID();
int teamID = player->GetTeamID(); // ?
// ? Player *respawnOnThis = this->teams[teamID]->GetPlayer(0);
Player *respawnOnThis = this->teams[teamID]->GetPlayer(0); // ?
// ? player->Respawn(respawnOnThis->GetPosition());
player->Respawn(respawnOnThis->GetPosition()); // ?
// player->Respawn(player->GetPosition()); ?
} }
void TeamManager::CreateTeam(int teamSize) void TeamManager::CreateTeam(int teamSize)

View File

@ -18,9 +18,17 @@ Weapon::Weapon()
Weapon::Weapon(int MaxNrOfSockets,Player *owner) Weapon::Weapon(int MaxNrOfSockets,Player *owner)
{ {
if(MaxNrOfSockets > 1) return;
attatchmentSockets.Resize(MaxNrOfSockets); attatchmentSockets.Resize(MaxNrOfSockets);
attatchmentSockets[0] = new AttatchmentSocket(); attatchmentSockets[0] = new AttatchmentSocket();
for (int i = 0; i < MaxNrOfSockets; i++)
{
this->attatchmentSockets[i] = 0;
}
weaponState = WEAPON_STATE_IDLE; weaponState = WEAPON_STATE_IDLE;
currentNrOfAttatchments = 0; currentNrOfAttatchments = 0;
selectedAttatchment = 0; selectedAttatchment = 0;
@ -36,7 +44,11 @@ Weapon::Weapon(int MaxNrOfSockets,Player *owner)
Weapon::~Weapon(void) Weapon::~Weapon(void)
{ {
for (unsigned int i = 0; i < this->attatchmentSockets.Size(); i++)
{
delete this->attatchmentSockets[i];
this->attatchmentSockets[i] = 0;
}
} }
/******************************************************** /********************************************************
@ -129,5 +141,7 @@ void Weapon::SelectAttatchment(int socketID)
void Weapon::Update(float dt) void Weapon::Update(float dt)
{ {
if(!selectedAttatchment) return;
selectedAttatchment->Update(dt); selectedAttatchment->Update(dt);
} }

View File

@ -69,25 +69,25 @@
<OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir> <OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir> <IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)D</TargetName> <TargetName>$(ProjectName)_$(PlatformShortName)D</TargetName>
<IncludePath>$(SolutionDir)Network\NetworkAPI\;$(IncludePath)</IncludePath> <IncludePath>$(SolutionDir)Network\NetworkAPI\;$(SolutionDir)Misc;$(IncludePath)</IncludePath>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir> <OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir> <IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)</TargetName> <TargetName>$(ProjectName)_$(PlatformShortName)</TargetName>
<IncludePath>$(SolutionDir)Network\NetworkAPI\;$(IncludePath)</IncludePath> <IncludePath>$(SolutionDir)Network\NetworkAPI\;$(SolutionDir)Misc;$(IncludePath)</IncludePath>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir> <OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir> <IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)D</TargetName> <TargetName>$(ProjectName)_$(PlatformShortName)D</TargetName>
<IncludePath>$(SolutionDir)Network\NetworkAPI\;$(IncludePath)</IncludePath> <IncludePath>$(SolutionDir)Network\NetworkAPI\;$(SolutionDir)Misc;$(IncludePath)</IncludePath>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir> <OutDir>$(SolutionDir)..\External\Lib\$(ProjectName)\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir> <IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)</TargetName> <TargetName>$(ProjectName)_$(PlatformShortName)</TargetName>
<IncludePath>$(SolutionDir)Network\NetworkAPI\;$(IncludePath)</IncludePath> <IncludePath>$(SolutionDir)Network\NetworkAPI\;$(SolutionDir)Misc;$(IncludePath)</IncludePath>
</PropertyGroup> </PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<ClCompile> <ClCompile>

View File

@ -24,23 +24,24 @@ namespace GameLogic
this->protocol[1].type = Oyster::Network::NetAttributeType_Short; this->protocol[1].type = Oyster::Network::NetAttributeType_Short;
} }
Protocol_General_Status(Oyster::Network::CustomNetProtocol& p)
{
this->protocol = p;
status = (States)p[1].value.netShort;
}
Protocol_General_Status(States state) Protocol_General_Status(States state)
{ {
this->protocol[0].value = protocol_General_Status; this->protocol[0].value = protocol_General_Status;
this->protocol[0].type = Oyster::Network::NetAttributeType_Short; this->protocol[0].type = Oyster::Network::NetAttributeType_Short;
this->status = state;
this->protocol[1].type = Oyster::Network::NetAttributeType_Short; this->protocol[1].type = Oyster::Network::NetAttributeType_Short;
this->status = state;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override
Protocol_General_Status(Oyster::Network::CustomNetProtocol& p)
{
status = (States)this->protocol[1].value.netShort;
}
Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = status; this->protocol[1].value = status;
return &protocol; return protocol;
} }
private: private:
@ -59,12 +60,12 @@ namespace GameLogic
destination = p.Get(1).value.netInt; destination = p.Get(1).value.netInt;
text = p.Get(2).value.netCharPtr; text = p.Get(2).value.netCharPtr;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol.Set(0, protocol_General_Text, Oyster::Network::NetAttributeType_Short); this->protocol.Set(0, protocol_General_Text, Oyster::Network::NetAttributeType_Short);
this->protocol.Set(1, destination, Oyster::Network::NetAttributeType_Int); this->protocol.Set(1, destination, Oyster::Network::NetAttributeType_Int);
this->protocol.Set(2, text); this->protocol.Set(2, text);
return &protocol; return protocol;
} }
private: private:

View File

@ -12,61 +12,111 @@
#include <DynamicArray.h> #include <DynamicArray.h>
/** OBS!
** It seems like if a string is set in the middle of a data set,
** the reciever will crach when trying to use the protocol.
** Only tested on Protocol_LobbyStartGame.
**/
namespace GameLogic namespace GameLogic
{ {
/*
struct Protocol_LobbyCreateGame :public Oyster::Network::CustomProtocolObject struct Protocol_LobbyCreateGame :public Oyster::Network::CustomProtocolObject
{ {
char* mapName; short clientID; // The unuiqe id reprsenting a specific client
char gameId; std::string modelName;
float worldMatrix[16];
Protocol_LobbyCreateGame() Protocol_LobbyCreateGame()
{ {
this->protocol[0].value = protocol_Lobby_Create; int c = 0;
this->protocol[0].type = Oyster::Network::NetAttributeType_Short; this->protocol[c].value = protocol_Lobby_Create;
this->protocol[c++].type = Oyster::Network::NetAttributeType_Short;
this->protocol[1].type = Oyster::Network::NetAttributeType_CharArray; this->protocol[c++].type = Oyster::Network::NetAttributeType_Short;
this->protocol[2].type = Oyster::Network::NetAttributeType_Char; for (int i = 0; i <= 16; i++)
{
this->protocol[c++].type = Oyster::Network::NetAttributeType_Float;
}
this->protocol[c++].type = Oyster::Network::NetAttributeType_CharArray;
} }
Protocol_LobbyCreateGame(Oyster::Network::CustomNetProtocol& o) Protocol_LobbyCreateGame(short _clientID, std::string name, float world[16])
{ {
mapName = o[1].value.netCharPtr; int c = 0;
gameId = o[2].value.netChar; this->protocol[c].value = protocol_Lobby_Create;
this->protocol[c++].type = Oyster::Network::NetAttributeType_Short;
this->protocol[c++].type = Oyster::Network::NetAttributeType_Short;
for (int i = 0; i <= 16; i++)
{
this->protocol[c++].type = Oyster::Network::NetAttributeType_Float;
}
this->protocol[c++].type = Oyster::Network::NetAttributeType_CharArray;
clientID = _clientID;
modelName = name;
memcpy(&worldMatrix[0], &world[0], sizeof(float) * 16);
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Protocol_LobbyCreateGame(Oyster::Network::CustomNetProtocol o)
{ {
protocol[1].value = mapName; int c = 1;
protocol[2].value = gameId; clientID = o[c++].value.netInt;
return &protocol; for (int i = 0; i <= 16; i++)
{
this->worldMatrix[i] = o[c++].value.netFloat;
}
modelName.assign(o[c++].value.netCharPtr);
}
Oyster::Network::CustomNetProtocol GetProtocol() override
{
int c = 1;
protocol[c++].value = clientID;
for (int i = 0; i <= 16; i++)
{
this->protocol[c++].value = this->worldMatrix[i];
}
protocol.Set(c++, this->modelName);
return protocol;
} }
private: private:
Oyster::Network::CustomNetProtocol protocol; Oyster::Network::CustomNetProtocol protocol;
}; };
*/
struct Protocol_LobbyStartGame :public Oyster::Network::CustomProtocolObject struct Protocol_LobbyStartGame :public Oyster::Network::CustomProtocolObject
{ {
short gameId; float seconds;
Protocol_LobbyStartGame() Protocol_LobbyStartGame()
{ {
this->protocol[0].value = protocol_Lobby_Start; this->protocol[0].value = protocol_Lobby_Start;
this->protocol[0].type = Oyster::Network::NetAttributeType_Short; this->protocol[0].type = Oyster::Network::NetAttributeType_Short;
this->protocol[1].type = Oyster::Network::NetAttributeType_Float;
this->protocol[1].type = Oyster::Network::NetAttributeType_Short; seconds = 0;
}
Protocol_LobbyStartGame(float _seconds)
{
this->protocol[0].value = protocol_Lobby_Start;
this->protocol[0].type = Oyster::Network::NetAttributeType_Short;
this->protocol[1].type = Oyster::Network::NetAttributeType_Float;
seconds = _seconds;
} }
Protocol_LobbyStartGame(Oyster::Network::CustomNetProtocol& o) Protocol_LobbyStartGame(Oyster::Network::CustomNetProtocol& o)
{ {
gameId = o[1].value.netInt; seconds = o[1].value.netFloat;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
protocol[1].value = gameId; this->protocol[1].value = seconds;
return &protocol; return protocol;
} }
private: private:
Oyster::Network::CustomNetProtocol protocol; Oyster::Network::CustomNetProtocol protocol;
}; };
struct Protocol_LobbyLogin :public Oyster::Network::CustomProtocolObject struct Protocol_LobbyLogin :public Oyster::Network::CustomProtocolObject
@ -83,9 +133,9 @@ namespace GameLogic
{ {
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
return &protocol; return protocol;
} }
private: private:
@ -109,7 +159,7 @@ namespace GameLogic
// this->protocol[1].type = Oyster::Network::NetAttributeType_Short; // this->protocol[1].type = Oyster::Network::NetAttributeType_Short;
// value = p[1].value.netShort; // value = p[1].value.netShort;
// } // }
// Oyster::Network::CustomNetProtocol* GetProtocol() override // Oyster::Network::CustomNetProtocol GetProtocol() override
// { // {
// protocol[1].value = value; // protocol[1].value = value;
// return &protocol; // return &protocol;
@ -130,8 +180,8 @@ namespace GameLogic
{ {
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ return &protocol; } { return protocol; }
private: private:
Oyster::Network::CustomNetProtocol protocol; Oyster::Network::CustomNetProtocol protocol;
@ -175,7 +225,7 @@ namespace GameLogic
list.Push(d); list.Push(d);
} }
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = list.Size(); this->protocol[1].value = list.Size();
@ -195,7 +245,7 @@ namespace GameLogic
this->protocol.Set(a++, list[i].ip); this->protocol.Set(a++, list[i].ip);
} }
return &protocol; return protocol;
} }
private: private:
@ -223,13 +273,13 @@ namespace GameLogic
minorVersion = (int)p.Get(2).value.netInt; minorVersion = (int)p.Get(2).value.netInt;
mapName = p.Get(3).value.netCharPtr; mapName = p.Get(3).value.netCharPtr;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = majorVersion; this->protocol[1].value = majorVersion;
this->protocol[2].value = minorVersion; this->protocol[2].value = minorVersion;
this->protocol.Set(3, mapName.c_str()); this->protocol.Set(3, mapName.c_str());
return &protocol; return protocol;
} }
private: private:
@ -254,7 +304,7 @@ namespace GameLogic
// { // {
// //
// } // }
// Oyster::Network::CustomNetProtocol* GetProtocol() override // Oyster::Network::CustomNetProtocol GetProtocol() override
// { // {
// return &protocol; // return &protocol;
// } // }

View File

@ -39,11 +39,11 @@ namespace GameLogic
pickup_ID = pickupID; pickup_ID = pickupID;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = object_ID; this->protocol[1].value = object_ID;
this->protocol[2].value = pickup_ID; this->protocol[2].value = pickup_ID;
return &protocol; return protocol;
} }
private: private:
@ -80,11 +80,11 @@ namespace GameLogic
object_ID = id; object_ID = id;
health = hp; health = hp;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = object_ID; this->protocol[1].value = object_ID;
this->protocol[2].value = health; this->protocol[2].value = health;
return &protocol; return protocol;
} }
private: private:
@ -129,14 +129,14 @@ namespace GameLogic
object_ID = id; object_ID = id;
memcpy(&worldMatrix[0], &m[0], sizeof(float)*16); memcpy(&worldMatrix[0], &m[0], sizeof(float)*16);
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = object_ID; this->protocol[1].value = object_ID;
for (int i = 2; i <= 17; i++) for (int i = 2; i <= 17; i++)
{ {
this->protocol[i].value = worldMatrix[i-2]; this->protocol[i].value = worldMatrix[i-2];
} }
return &protocol; return protocol;
} }
private: private:
@ -179,14 +179,14 @@ namespace GameLogic
object_ID = id; object_ID = id;
memcpy(&worldMatrix[0], &m[0], sizeof(float)*16); memcpy(&worldMatrix[0], &m[0], sizeof(float)*16);
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = object_ID; this->protocol[1].value = object_ID;
for (int i = 2; i <= 17; i++) for (int i = 2; i <= 17; i++)
{ {
this->protocol[i].value = worldMatrix[i-2]; this->protocol[i].value = worldMatrix[i-2];
} }
return &protocol; return protocol;
} }
private: private:
@ -221,11 +221,11 @@ namespace GameLogic
object_ID = id; object_ID = id;
timer = time; timer = time;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = object_ID; this->protocol[1].value = object_ID;
this->protocol[2].value = timer; this->protocol[2].value = timer;
return &protocol; return protocol;
} }
private: private:
@ -234,8 +234,9 @@ namespace GameLogic
struct Protocol_ObjectCreate :public Oyster::Network::CustomProtocolObject struct Protocol_ObjectCreate :public Oyster::Network::CustomProtocolObject
{ {
//ObjectType type; //ie player, box or whatever
int object_ID; int object_ID;
char *name; std::string name;
float worldMatrix[16]; float worldMatrix[16];
Protocol_ObjectCreate() Protocol_ObjectCreate()
@ -244,7 +245,7 @@ namespace GameLogic
this->protocol[0].type = Oyster::Network::NetAttributeType_Short; this->protocol[0].type = Oyster::Network::NetAttributeType_Short;
this->protocol[1].type = Oyster::Network::NetAttributeType_Int; this->protocol[1].type = Oyster::Network::NetAttributeType_Int;
this->protocol[2].type = Oyster::Network::NetAttributeType_CharArray; this->protocol[2].type = Oyster::Network::NetAttributeType_CharArray;
for (int i = 3; i <= 18; i++) for (int i = 3; i <= 18; i++)
{ {
@ -272,11 +273,11 @@ namespace GameLogic
this->name = path; this->name = path;
memcpy(&worldMatrix[0], &m[0], sizeof(float)*16); memcpy(&worldMatrix[0], &m[0], sizeof(float)*16);
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = object_ID; this->protocol[1].value = object_ID;
this->protocol[2].value = name; this->protocol.Set(2, name);
this->protocol[3].value = worldMatrix[0]; this->protocol[3].value = worldMatrix[0];
this->protocol[4].value = worldMatrix[1]; this->protocol[4].value = worldMatrix[1];
this->protocol[5].value = worldMatrix[2]; this->protocol[5].value = worldMatrix[2];
@ -297,7 +298,7 @@ namespace GameLogic
return &protocol; return protocol;
} }
private: private:

View File

@ -49,14 +49,14 @@ namespace GameLogic
return *this; return *this;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = bForward; this->protocol[1].value = bForward;
this->protocol[2].value = bBackward; this->protocol[2].value = bBackward;
this->protocol[3].value = bLeft; this->protocol[3].value = bLeft;
this->protocol[4].value = bRight; this->protocol[4].value = bRight;
return &protocol; return protocol;
} }
private: private:
@ -98,7 +98,7 @@ namespace GameLogic
return *this; return *this;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = lookDirX; this->protocol[1].value = lookDirX;
this->protocol[2].value = lookDirY; this->protocol[2].value = lookDirY;
@ -106,7 +106,7 @@ namespace GameLogic
this->protocol[4].value = deltaX; this->protocol[4].value = deltaX;
return &protocol; return protocol;
} }
private: private:
@ -131,9 +131,9 @@ namespace GameLogic
{ {
return *this; return *this;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
return &protocol; return protocol;
} }
private: private:
@ -168,12 +168,12 @@ namespace GameLogic
utilityPressed = val[3].value.netBool; utilityPressed = val[3].value.netBool;
return *this; return *this;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = primaryPressed; this->protocol[1].value = primaryPressed;
this->protocol[2].value = secondaryPressed; this->protocol[2].value = secondaryPressed;
this->protocol[3].value = utilityPressed; this->protocol[3].value = utilityPressed;
return &protocol; return protocol;
} }
private: private:
@ -200,10 +200,10 @@ namespace GameLogic
hasJumped = val[1].value.netBool; hasJumped = val[1].value.netBool;
return *this; return *this;
} }
Oyster::Network::CustomNetProtocol* GetProtocol() override Oyster::Network::CustomNetProtocol GetProtocol() override
{ {
this->protocol[1].value = hasJumped; this->protocol[1].value = hasJumped;
return &protocol; return protocol;
} }
private: private:

View File

@ -24,14 +24,19 @@ namespace DanBias
GameLogic::IPlayerData* ReleasePlayer(); GameLogic::IPlayerData* ReleasePlayer();
Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> GetClient(); Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> GetClient();
Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> ReleaseClient(); Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> ReleaseClient();
int GetID() const;
float GetSinceLastResponse() const;
bool IsReady() const;
bool Equals(const Oyster::Network::NetworkClient* c); bool Equals(const Oyster::Network::NetworkClient* c);
void SetReadyState(bool isReady);
void SetSinceLastResponse(float seconds);
private: private:
GameLogic::IPlayerData* player; GameLogic::IPlayerData* player;
Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> client; Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> client;
int id; bool isReady;
float secondsSinceLastResponse;
}; };
}//End namespace DanBias }//End namespace DanBias

View File

@ -52,8 +52,10 @@ namespace DanBias
private: private:
Utility::WinTimer timer; Utility::WinTimer timer;
float refreshFrequency; float refreshFrequency;
GameSession gameSession; GameSession gameSession;
LobbyLevelData description; LobbyLevelData description;
Utility::DynamicMemory::SmartPointer<DanBias::GameClient> sessionOwner;
}; };
}//End namespace DanBias }//End namespace DanBias
#endif // !DANBIASGAME_GAMELOBBY_H #endif // !DANBIASGAME_GAMELOBBY_H

View File

@ -32,9 +32,11 @@ namespace DanBias
{ {
char* serverName; char* serverName;
int listenPort; int listenPort;
bool broadcast; //Not fully implemented!
ServerInitDesc() ServerInitDesc()
: serverName("Game Server") : serverName("Game Server")
, listenPort(15151) , listenPort(15152)
, broadcast(true)
{}; {};
}; };
struct GameServerInfo struct GameServerInfo
@ -49,6 +51,7 @@ namespace DanBias
static void ServerStop(); static void ServerStop();
static void ServerUpdate(); static void ServerUpdate();
static GameServerInfo ServerGetInfo(); static GameServerInfo ServerGetInfo();
static bool ServerIsRunning();
static void GameSetMapId(const int& val); static void GameSetMapId(const int& val);
static void GameSetMaxClients(const int& val); static void GameSetMaxClients(const int& val);

View File

@ -52,24 +52,27 @@ namespace DanBias
* @param client The client to attach to the session * @param client The client to attach to the session
*/ */
bool Attach(Oyster::Network::NetClient client) override; bool Attach(Oyster::Network::NetClient client) override;
void CloseSession( bool dissconnectClients ) override;
inline bool IsCreated() const { return this->isCreated; } inline bool IsCreated() const { return this->isCreated; }
inline bool IsRunning() const { return this->isRunning; } inline bool IsRunning() const { return this->isRunning; }
operator bool() { return (this->isCreated && this->isCreated); }
//Private member functions //Private member functions
private: private:
// TODO: find out what this method does.. // TODO: find out what this method does..
void ClientEventCallback(Oyster::Network::NetEvent<Oyster::Network::NetworkClient*, Oyster::Network::NetworkClient::ClientEventArgs> e) override; void ClientEventCallback(Oyster::Network::NetEvent<Oyster::Network::NetworkClient*, Oyster::Network::NetworkClient::ClientEventArgs> e) override;
//Sends a client to the owner, if obj is NULL then all clients is sent //Sends a client to the owner, if obj is NULL then all clients is sent
void SendToOwner(DanBias::GameClient* obj); void SendToOwner(DanBias::GameClient* obj);
//Frame function, derived from IThreadObject //Derived from IThreadObject
void ThreadEntry() override;
bool DoWork ( ) override; bool DoWork ( ) override;
private: private:
void ParseProtocol (Oyster::Network::CustomNetProtocol& p, DanBias::GameClient* c); void ParseProtocol ( Oyster::Network::CustomNetProtocol& p, DanBias::GameClient* c );
void Gameplay_PlayerMovement ( GameLogic::Protocol_PlayerMovement& p, DanBias::GameClient* c ); void Gameplay_PlayerMovement ( GameLogic::Protocol_PlayerMovement& p, DanBias::GameClient* c );
void Gameplay_PlayerLookDir ( GameLogic::Protocol_PlayerLook& p, DanBias::GameClient* c ); void Gameplay_PlayerLookDir ( GameLogic::Protocol_PlayerLook& p, DanBias::GameClient* c );
@ -86,18 +89,23 @@ namespace DanBias
void General_Text ( GameLogic::Protocol_General_Text& p, DanBias::GameClient* c ); void General_Text ( GameLogic::Protocol_General_Text& p, DanBias::GameClient* c );
//Callback method recieving from gamelogic //Callback method recieving from gamelogic
static void ObjectMove(GameLogic::IObjectData* movedObject); static void ObjectMove ( GameLogic::IObjectData* movedObject );
static void ObjectDisabled ( GameLogic::IObjectData* movedObject, float seconds );
//Private member variables //Private member variables
private: private:
Utility::DynamicMemory::DynamicArray<Utility::DynamicMemory::SmartPointer<GameClient>> clients; Utility::DynamicMemory::DynamicArray<Utility::DynamicMemory::SmartPointer<GameClient>> clients;
Utility::DynamicMemory::SmartPointer<DanBias::GameClient> sessionOwner;
Oyster::Thread::OysterThread worker; Oyster::Thread::OysterThread worker;
GameLogic::GameAPI& gameInstance; GameLogic::GameAPI& gameInstance;
GameLogic::ILevelData *levelData; GameLogic::ILevelData *levelData;
NetworkSession* owner; NetworkSession* owner;
bool isCreated; bool isCreated;
bool isRunning; bool isRunning;
Utility::WinTimer timer; float logicFrameTime;
float networkFrameTime;
Utility::WinTimer logicTimer;
Utility::WinTimer networkTimer;
GameDescription description; GameDescription description;
//TODO: Remove this uggly hax //TODO: Remove this uggly hax

View File

@ -11,19 +11,18 @@ using namespace Oyster::Network;
using namespace DanBias; using namespace DanBias;
using namespace GameLogic; using namespace GameLogic;
static int gameClientIDCount = 1;
GameClient::GameClient(SmartPointer<NetworkClient> client, GameLogic::IPlayerData* player) GameClient::GameClient(SmartPointer<NetworkClient> client, GameLogic::IPlayerData* player)
{ {
this->client = client; this->client = client;
this->id = gameClientIDCount++;
this->player = player; this->player = player;
isReady = false;
} }
GameClient::~GameClient() GameClient::~GameClient()
{ {
this->client->Disconnect(); this->client->Disconnect();
this->player = 0; this->player = 0;
this->id = -1; isReady = false;
} }
GameLogic::IPlayerData* GameClient::GetPlayer() GameLogic::IPlayerData* GameClient::GetPlayer()
@ -46,13 +45,26 @@ SmartPointer<Oyster::Network::NetworkClient> GameClient::ReleaseClient()
this->client = 0; this->client = 0;
return temp; return temp;
} }
int GameClient::GetID() const
float GameClient::GetSinceLastResponse() const
{ {
return this->id; return this->secondsSinceLastResponse;
}
bool GameClient::IsReady() const
{
return this->isReady;
} }
bool GameClient::Equals(const NetworkClient* c) bool GameClient::Equals(const NetworkClient* c)
{ {
return (c->GetID() == this->client->GetID()); return (c->GetID() == this->client->GetID());
} }
void GameClient::SetReadyState(bool r)
{
this->isReady = r;
}
void GameClient::SetSinceLastResponse(float s)
{
this->secondsSinceLastResponse = s;
}

View File

@ -17,18 +17,18 @@ namespace DanBias
{ } { }
GameLobby::~GameLobby() GameLobby::~GameLobby()
{ } {
this->clients.Clear();
}
void GameLobby::Release() void GameLobby::Release()
{ {
NetworkSession::CloseSession(true); NetworkSession::CloseSession(true);
this->gameSession.CloseSession(true);
} }
void GameLobby::Update() void GameLobby::Update()
{ {
if(GetAsyncKeyState(VK_DOWN)) //TODO: Dont forget to remove this...
this->Send(*GameLogic::Protocol_General_Status().GetProtocol());
this->ProcessClients(); this->ProcessClients();
} }
void GameLobby::SetGameDesc(const LobbyLevelData& desc) void GameLobby::SetGameDesc(const LobbyLevelData& desc)
@ -45,20 +45,21 @@ namespace DanBias
desc.mapNumber = this->description.mapNumber; desc.mapNumber = this->description.mapNumber;
desc.maxClients = this->description.maxClients; desc.maxClients = this->description.maxClients;
} }
bool GameLobby::StartGameSession() bool GameLobby::StartGameSession( )
{ {
GameSession::GameDescription desc; GameSession::GameDescription desc;
desc.gameMode = this->description.gameMode; desc.gameMode = this->description.gameMode;
desc.gameTime = this->description.gameTime; desc.gameTime = this->description.gameTime;
desc.mapNumber = this->description.mapNumber; desc.mapNumber = this->description.mapNumber;
desc.owner = this; desc.owner = this;
desc.clients = this->clients; desc.clients = this->clients;
this->clients.Clear(); this->clients.Clear(); //Remove clients from lobby list
if(this->gameSession.Create(desc)) if(this->gameSession.Create(desc))
{ {
this->gameSession.Run(); this->gameSession.Run();
return true; return true;
} }
return false; return false;
@ -85,29 +86,36 @@ namespace DanBias
void GameLobby::ClientConnectedEvent(Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> client) void GameLobby::ClientConnectedEvent(Utility::DynamicMemory::SmartPointer<Oyster::Network::NetworkClient> client)
{ {
printf("New client(%i) connected - %s \n", client->GetID(), client->GetIpAddress().c_str()); printf("New client(%i) connected - %s \n", client->GetID(), client->GetIpAddress().c_str());
Attach(client);
Protocol_LobbyClientData p1; if(this->gameSession)
Protocol_LobbyGameData p2;
for (unsigned int i = 0; i < this->clients.Size(); i++)
{ {
if(this->clients[i]) this->gameSession.Attach(client);
{
Protocol_LobbyClientData::PlayerData t;
t.id = this->clients[i]->GetID();
t.ip = this->clients[i]->GetIpAddress();
t.team = 0;
t.name = "DennisÄrKung";
p1.list.Push(t);
}
} }
p2.majorVersion = 1; else
p2.minorVersion = 0; {
p2.mapName = "BetsMap"; Attach(client);
Protocol_LobbyClientData p1;
Protocol_LobbyGameData p2;
for (unsigned int i = 0; i < this->clients.Size(); i++)
{
if(this->clients[i])
{
Protocol_LobbyClientData::PlayerData t;
t.id = this->clients[i]->GetID();
t.ip = this->clients[i]->GetIpAddress();
t.team = 0;
t.name = "Dennis är kung tycker Erik!";
p1.list.Push(t);
}
}
p2.majorVersion = 1;
p2.minorVersion = 0;
p2.mapName = "Dennis är kung tycker Erik!";
client->Send(p1.GetProtocol()); client->Send(p1.GetProtocol());
client->Send(p2.GetProtocol()); client->Send(p2.GetProtocol());
}
} }
}//End namespace DanBias }//End namespace DanBias

View File

@ -62,7 +62,14 @@ void GameLobby::GeneralText(GameLogic::Protocol_General_Text& p, Oyster::Network
//} //}
void GameLobby::LobbyStartGame(GameLogic::Protocol_LobbyStartGame& p, Oyster::Network::NetworkClient* c) void GameLobby::LobbyStartGame(GameLogic::Protocol_LobbyStartGame& p, Oyster::Network::NetworkClient* c)
{ {
//TODO: Prio 1 if(this->sessionOwner->GetClient()->GetID() == c->GetID())
{
}
else
{
//Someone else tried to start the server..
}
} }
//void GameLobby::LobbyJoin(GameLogic::Protocol_LobbyJoin& p, Oyster::Network::NetworkClient* c) //void GameLobby::LobbyJoin(GameLogic::Protocol_LobbyJoin& p, Oyster::Network::NetworkClient* c)
//{ //{

View File

@ -53,6 +53,7 @@ void GameServerAPI::ServerStart()
} }
void GameServerAPI::ServerStop() void GameServerAPI::ServerStop()
{ {
if(!server.IsRunning()) return;
lobby.Release(); lobby.Release();
server.Shutdown(); server.Shutdown();
@ -61,19 +62,19 @@ void GameServerAPI::ServerStop()
int time = (int)total; int time = (int)total;
int hour, min, sec; int hour, min, sec;
hour=time / 3600; hour = time / 3600;
time=time % 3600; time = time % 3600;
min=time / 60; min = time / 60;
time=time % 60; time = time % 60;
sec = time; sec = time;
printf( "Server has been running for: %i:%i:%i - [hh:mm:ss] \n\n", hour, min, sec ); printf( "Server has been running for: %i:%i:%i - [hh:mm:ss] \n\n", hour, min, sec );
printf( "Terminating in : "); //printf( "Terminating in : ");
for (int i = 0; i < 3; i++) //for (int i = 0; i < 3; i++)
{ //{
printf( "%i ", 3-i ); // printf( "%i ", 3-i );
Sleep(1000); // Sleep(1000);
} //}
printf( "\nServer terminated!" ); printf( "\nServer terminated!" );
} }
void GameServerAPI::ServerUpdate() void GameServerAPI::ServerUpdate()
@ -82,7 +83,6 @@ void GameServerAPI::ServerUpdate()
lobby.Update(); lobby.Update();
} }
GameServerAPI::GameServerInfo GameServerAPI::ServerGetInfo() GameServerAPI::GameServerInfo GameServerAPI::ServerGetInfo()
{ {
GameServerAPI::GameServerInfo i; GameServerAPI::GameServerInfo i;
@ -90,6 +90,11 @@ GameServerAPI::GameServerInfo GameServerAPI::ServerGetInfo()
i.listenPort = server.GetPort(); i.listenPort = server.GetPort();
return i; return i;
} }
bool GameServerAPI::ServerIsRunning()
{
return server.IsRunning();
}
void GameServerAPI::GameSetMapId(const int& val) void GameServerAPI::GameSetMapId(const int& val)
{ {
LobbyLevelData d; LobbyLevelData d;
@ -150,6 +155,11 @@ const char* GameServerAPI::GameGetGameName()
} }
bool GameServerAPI::GameStart() bool GameServerAPI::GameStart()
{ {
return lobby.StartGameSession(); if(lobby.StartGameSession())
{
return true;
}
return false;
} }

View File

@ -3,19 +3,16 @@
///////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////
#include "..\GameSession.h" #include "..\GameSession.h"
#include "..\GameClient.h" #include "..\GameClient.h"
#include <WinTimer.h>
#include <Protocols.h> #include <Protocols.h>
#include <PostBox\PostBox.h> #include <PostBox\PostBox.h>
#include <GameLogicStates.h> #include <GameLogicStates.h>
#include <OysterMath.h> #include <OysterMath.h>
#define NOMINMAX #define NOMINMAX
#include <Windows.h> #include <Windows.h>
#define DELTA_TIME_20 0.05f
#define DELTA_TIME_24 0.04166666666666666666666666666667f
#define DELTA_TIME_30 0.03333333333333333333333333333333f
#define DELTA_TIME_60 0.01666666666666666666666666666667f
#define DELTA_TIME_120 0.00833333333333333333333333333333f
using namespace Utility::DynamicMemory; using namespace Utility::DynamicMemory;
using namespace Oyster; using namespace Oyster;
@ -25,20 +22,20 @@ using namespace GameLogic;
namespace DanBias namespace DanBias
{ {
Utility::WinTimer testTimer;
int testID = -1;
bool GameSession::DoWork( ) bool GameSession::DoWork( )
{ {
if(this->isRunning) if(this->isRunning)
{ {
double dt = this->timer.getElapsedSeconds(); float dt = (float)this->logicTimer.getElapsedSeconds();
gameInstance.SetFrameTimeLength((float)dt); if( dt >= this->logicFrameTime )
if(dt >= DELTA_TIME_20)
{ {
this->ProcessClients(); this->ProcessClients();
this->gameInstance.NewFrame(); this->gameInstance.NewFrame();
this->timer.reset(); this->logicTimer.reset();
} }
} }
@ -71,11 +68,16 @@ namespace DanBias
case NetworkClient::ClientEventArgs::EventType_ProtocolFailedToRecieve: case NetworkClient::ClientEventArgs::EventType_ProtocolFailedToRecieve:
break; break;
case NetworkClient::ClientEventArgs::EventType_ProtocolFailedToSend: case NetworkClient::ClientEventArgs::EventType_ProtocolFailedToSend:
printf("\t(%i : %s) - EventType_ProtocolFailedToSend\n", e.sender->GetID(), e.sender->GetIpAddress().c_str()); printf("\t(%i : %s) - EventType_ProtocolFailedToSend\n", cl->GetClient()->GetID(), e.sender->GetIpAddress().c_str());
this->Detach(e.sender)->Disconnect(); this->Detach(e.sender);
break; break;
case NetworkClient::ClientEventArgs::EventType_ProtocolRecieved: case NetworkClient::ClientEventArgs::EventType_ProtocolRecieved:
printf("\t(%i : %s) - EventType_ProtocolRecieved\n", e.sender->GetID(), e.sender->GetIpAddress().c_str()); printf("\t(%i : %s) - EventType_ProtocolRecieved\n", cl->GetClient()->GetID(), e.sender->GetIpAddress().c_str());
testID = 2;
if(cl->GetPlayer()->GetID() == testID)//TODO: TEST
{
testTimer.reset();
}
this->ParseProtocol(e.args.data.protocol, cl); this->ParseProtocol(e.args.data.protocol, cl);
break; break;
} }
@ -83,38 +85,47 @@ namespace DanBias
void GameSession::ObjectMove(GameLogic::IObjectData* movedObject) void GameSession::ObjectMove(GameLogic::IObjectData* movedObject)
{ {
if(dynamic_cast<IPlayerData*> (movedObject)) float dt = GameSession::gameSession->networkTimer.getElapsedSeconds();
//Duh... This was causing alot of problems, it's in the wrong place...
//Need to figure out where to put this frame locker.
//We only need to send network packages when necessary, ie not 120 times per frame.
//I think it would be enough with 60-70 packages per second due to the nature of
//graphics update (60 fps) on the client side. To send more than this would be lost
//bandwidth.
//if( dt >= GameSession::gameSession->networkFrameTime )
{ {
IPlayerData* temp = (IPlayerData*)movedObject; GameSession::gameSession->networkTimer.reset();
int id = temp->GetID();
Oyster::Math::Float4x4 world = temp->GetOrientation();
Protocol_ObjectPosition p(world, id);
GameSession::gameSession->Send(*p.GetProtocol());
}
GameLogic::IObjectData* obj = NULL; GameLogic::IObjectData* obj = movedObject;
if(dynamic_cast<GameLogic::ILevelData*>(movedObject)) if(movedObject->GetID() == testID) //TODO: TEST
{
obj = ((GameLogic::ILevelData*)movedObject)->GetObjectAt(0);
if(obj)
{ {
if(obj->GetObjectType() == OBJECT_TYPE_WORLD) float sec = (float)testTimer.getElapsedSeconds();
{ sec = 0;
int id = obj->GetID();
Oyster::Math::Float4x4 world =obj->GetOrientation();
Protocol_ObjectPosition p(world, id);
//GameSession::gameSession->Send(*p.GetProtocol());
}
} }
obj = NULL; int id = obj->GetID();
int count = ((GameLogic::ILevelData*)movedObject)->getNrOfDynamicObj(); Protocol_ObjectPosition p(obj->GetOrientation(), id);
for( int i = 0; i < count; i++ ) //if(id != 1)
GameSession::gameSession->Send(p.GetProtocol());
/*
if(dynamic_cast<GameLogic::ILevelData*>(obj))
{ {
obj =((GameLogic::ILevelData*)movedObject)->GetObjectAt(i+1); obj = ((GameLogic::ILevelData*)movedObject)->GetObjectAt(0);
if(obj)
{
if(obj->GetObjectType() == OBJECT_TYPE_WORLD)
{
int id = obj->GetID();
Oyster::Math::Float4x4 world =obj->GetOrientation();
Protocol_ObjectPosition p(world, id);
gameSession->Send(p.GetProtocol());
}
}
obj =((GameLogic::ILevelData*)movedObject)->GetObjectAt(1);
if(obj) if(obj)
{ {
if(obj->GetObjectType() == OBJECT_TYPE_BOX) if(obj->GetObjectType() == OBJECT_TYPE_BOX)
@ -122,13 +133,30 @@ namespace DanBias
int id = obj->GetID(); int id = obj->GetID();
Oyster::Math::Float4x4 world = obj->GetOrientation(); Oyster::Math::Float4x4 world = obj->GetOrientation();
Protocol_ObjectPosition p(world, id); Protocol_ObjectPosition p(world, id);
GameSession::gameSession->Send(*p.GetProtocol()); gameSession->Send(p.GetProtocol());
}
}
obj =((GameLogic::ILevelData*)movedObject)->GetObjectAt(2);
if(obj)
{
if(obj->GetObjectType() == OBJECT_TYPE_BOX)
{
int id = obj->GetID();
Oyster::Math::Float4x4 world = obj->GetOrientation();
Protocol_ObjectPosition p(world, id);
GameSession::gameSession->Send(p.GetProtocol());
} }
} }
} }
*/
} }
} }
void GameSession::ObjectDisabled( GameLogic::IObjectData* movedObject, float seconds )
{
GameSession::gameSession->Send(Protocol_ObjectDisable(movedObject->GetID(), seconds).GetProtocol());
}
//*****************************************************// //*****************************************************//
//****************** Protocol methods *****************// //****************** Protocol methods *****************//
@ -136,6 +164,8 @@ namespace DanBias
void GameSession::ParseProtocol(Oyster::Network::CustomNetProtocol& p, DanBias::GameClient* c) void GameSession::ParseProtocol(Oyster::Network::CustomNetProtocol& p, DanBias::GameClient* c)
{ {
//TODO: Update response timer
switch (p[0].value.netShort) switch (p[0].value.netShort)
{ {
case protocol_Gameplay_PlayerMovement: this->Gameplay_PlayerMovement ( Protocol_PlayerMovement (p), c ); case protocol_Gameplay_PlayerMovement: this->Gameplay_PlayerMovement ( Protocol_PlayerMovement (p), c );
@ -228,6 +258,8 @@ namespace DanBias
{ {
case GameLogic::Protocol_General_Status::States_disconected: case GameLogic::Protocol_General_Status::States_disconected:
printf("Client with ID [%i] dissconnected\n", c->GetClient()->GetID()); printf("Client with ID [%i] dissconnected\n", c->GetClient()->GetID());
//TODO: Tell other clients
//Protocol_
this->Detach(c->GetClient()->GetID()); this->Detach(c->GetClient()->GetID());
break; break;
@ -236,7 +268,7 @@ namespace DanBias
break; break;
case GameLogic::Protocol_General_Status::States_ready: case GameLogic::Protocol_General_Status::States_ready:
c->SetReadyState(true);
break; break;
case GameLogic::Protocol_General_Status::States_leave: case GameLogic::Protocol_General_Status::States_leave:
@ -246,7 +278,7 @@ namespace DanBias
} }
void GameSession::General_Text ( Protocol_General_Text& p, DanBias::GameClient* c ) void GameSession::General_Text ( Protocol_General_Text& p, DanBias::GameClient* c )
{ {
printf("Message recieved from (%i):\t %s\n", c->GetID(), p.text.c_str()); printf("Message recieved from (%i):\t %s\n", c->GetClient()->GetID(), p.text.c_str());
} }
}//End namespace DanBias }//End namespace DanBias

View File

@ -9,6 +9,13 @@
#define NOMINMAX #define NOMINMAX
#include <Windows.h> #include <Windows.h>
#include <Queue.h>
#define DELTA_TIME_20 0.05f
#define DELTA_TIME_24 0.04166666666666666666666666666667f
#define DELTA_TIME_30 0.03333333333333333333333333333333f
#define DELTA_TIME_60 0.01666666666666666666666666666667f
#define DELTA_TIME_120 0.00833333333333333333333333333333f
using namespace Utility::DynamicMemory; using namespace Utility::DynamicMemory;
@ -28,6 +35,10 @@ namespace DanBias
this->isCreated = false; this->isCreated = false;
this->isRunning = false; this->isRunning = false;
this->gameSession = this; this->gameSession = this;
this->logicFrameTime = DELTA_TIME_20;
this->networkFrameTime = DELTA_TIME_20;
this->networkTimer.reset();
this->logicTimer.reset();
memset(&this->description, 0, sizeof(GameDescription)); memset(&this->description, 0, sizeof(GameDescription));
} }
@ -45,37 +56,30 @@ namespace DanBias
bool GameSession::Create(GameDescription& desc) bool GameSession::Create(GameDescription& desc)
{ {
this->description = desc; this->description = desc;
/* Do some error checking */ /* Do some error checking */
if(desc.clients.Size() == 0) return false; if(desc.clients.Size() == 0) return false;
if(!desc.owner) return false; if(!desc.owner) return false;
if(this->isCreated) return false; if(this->isCreated) return false;
/* standard initialization of some data */ /* standard initialization of some data */
NetworkSession::clients = desc.clients; NetworkSession::clients = desc.clients;
this->clients.Resize(desc.clients.Size()); this->clients.Reserve(desc.clients.Size());
this->owner = desc.owner; this->owner = desc.owner;
/* Initiate the game instance */ /* Initiate the game instance */
if(!this->gameInstance.Initiate()) if(!this->gameInstance.Initiate())
{ {
printf("Failed to initiate the game instance\n"); printf("Failed to initiate the game instance\n");
} }
/* Create the game level */ /* Create the players in the game instance */
if(!(this->levelData = this->gameInstance.CreateLevel()))
{
printf("Level not created!");
return false;
}
/* Create the players in the game instance */
GameLogic::IPlayerData* p = 0; GameLogic::IPlayerData* p = 0;
for (unsigned int i = 0; i < desc.clients.Size(); i++) for (unsigned int i = 0; i < desc.clients.Size(); i++)
{ {
if( (p = this->gameInstance.CreatePlayer()) ) if( (p = this->gameInstance.CreatePlayer()) )
{ {
desc.clients[i]->SetOwner(this); desc.clients[i]->SetOwner(this);
this->clients[i] = new GameClient(desc.clients[i], p); this->clients.Push(new GameClient(desc.clients[i], p));
} }
else else
{ {
@ -83,16 +87,26 @@ namespace DanBias
} }
} }
/* Create the game level */
if(!(this->levelData = this->gameInstance.CreateLevel()))
{
printf("Level not created!");
return false;
}
/* Set some game instance data options */
this->gameInstance.SetSubscription(GameSession::ObjectMove);
this->gameInstance.SetSubscription(GameSession::ObjectDisabled);
this->gameInstance.SetFPS(60);
this->description.clients.Clear();
this->isCreated = true;
/* Create the worker thread */ /* Create the worker thread */
if(this->worker.Create(this, false) != OYSTER_THREAD_ERROR_SUCCESS) if(this->worker.Create(this, false) != OYSTER_THREAD_ERROR_SUCCESS)
return false; return false;
this->worker.SetPriority(Oyster::Thread::OYSTER_THREAD_PRIORITY_3);
/* Set some game instance data options */
this->gameInstance.SetSubscription(GameLogic::GameEvent::ObjectEventFunctionType_OnMove, GameSession::ObjectMove);
this->isCreated = true;
return this->isCreated; return this->isCreated;
} }
@ -108,14 +122,71 @@ namespace DanBias
} }
} }
void GameSession::ThreadEntry( )
{
//List with clients that we are waiting on..
DynamicArray<SmartPointer<GameClient>> readyList = this->clients;
//First we need to clean invalid clients, if any, and tell them to start loading game data
for (unsigned int i = 0; i < readyList.Size(); i++)
{
if(!readyList[i])
{
readyList.Remove(i);
}
else
{
Protocol_LobbyCreateGame p(readyList[i]->GetPlayer()->GetID(), "char_white.dan", readyList[i]->GetPlayer()->GetOrientation());
readyList[i]->GetClient()->Send(p);
}
}
unsigned int readyCounter = readyList.Size();
//Sync with clients
while (readyCounter != 0)
{
this->ProcessClients();
for (unsigned int i = 0; i < readyList.Size(); i++)
{
if(readyList[i] && readyList[i]->IsReady())
{
//Need to send information about other players, to all players
for (unsigned int k = 0; k < this->clients.Size(); k++)
{
if((this->clients[k] && readyList[i]) && readyList[i]->GetClient()->GetID() != this->clients[k]->GetClient()->GetID())
{
Protocol_ObjectCreate p(this->clients[k]->GetPlayer()->GetOrientation(), this->clients[k]->GetPlayer()->GetID(), "char_white.dan"); //The model name will be custom later..
readyList[i]->GetClient()->Send(p);
}
}
readyCounter-- ;
readyList[i] = 0;
}
}
Sleep(5); //TODO: This might not be needed here.
}
for (unsigned int i = 0; i < this->clients.Size(); i++)
{
if(this->clients[i])
{
this->clients[i]->GetClient()->Send(GameLogic::Protocol_LobbyStartGame(5));
}
}
}
bool GameSession::Attach(Utility::DynamicMemory::SmartPointer<NetworkClient> client) bool GameSession::Attach(Utility::DynamicMemory::SmartPointer<NetworkClient> client)
{ {
if(!this->isCreated) return false; if(!this->isCreated) return false;
client->SetOwner(this); client->SetOwner(this);
SmartPointer<GameClient> obj = new GameClient(client, this->gameInstance.CreatePlayer());
IPlayerData* player = this->gameInstance.CreatePlayer();
if(!player) return false;
SmartPointer<GameClient> obj = new GameClient(client, player);
for (unsigned int i = 0; i < clients.Size(); i++) for (unsigned int i = 0; i < clients.Size(); i++)
{ {
@ -131,6 +202,13 @@ namespace DanBias
return true; return true;
} }
void GameSession::CloseSession( bool dissconnectClients )
{
this->worker.Terminate();
NetworkSession::CloseSession(true);
this->clients.Clear();
}
}//End namespace DanBias }//End namespace DanBias

View File

@ -52,6 +52,7 @@ namespace Oyster
{ {
return ::Oyster::Math3D::ViewMatrix( this->quaternion, (this->centerPos + offset) ); return ::Oyster::Math3D::ViewMatrix( this->quaternion, (this->centerPos + offset) );
} }
} }
} }
} }

View File

@ -30,6 +30,7 @@ namespace Oyster
::Oyster::Math::Float4x4 GetOrientation() const; ::Oyster::Math::Float4x4 GetOrientation() const;
::Oyster::Math::Float4x4 GetView() const; ::Oyster::Math::Float4x4 GetView() const;
::Oyster::Math::Float4x4 GetView( const ::Oyster::Math::Float3 &offset ) const; ::Oyster::Math::Float4x4 GetView( const ::Oyster::Math::Float3 &offset ) const;
void CustomBodyState::ApplyFriction( const ::Oyster::Math::Float3 &j);
// Variables for state // Variables for state
::Oyster::Math::Float mass, restitutionCoeff, staticFrictionCoeff, dynamicFrictionCoeff; ::Oyster::Math::Float mass, restitutionCoeff, staticFrictionCoeff, dynamicFrictionCoeff;

View File

@ -44,6 +44,11 @@ namespace Utility
unsigned int Size() const; unsigned int Size() const;
unsigned int Capacity() const; unsigned int Capacity() const;
bool IsEmpty() const;
T* begin();
T* end();
private: private:
void Expand(int elements = 0); void Expand(int elements = 0);
@ -112,7 +117,7 @@ namespace Utility
template <typename T> const T& DynamicArray<T>::operator[](unsigned int index) const template <typename T> const T& DynamicArray<T>::operator[](unsigned int index) const
{ {
assert(index < this->size); assert((int)index < this->size);
return this->data[index]; return this->data[index];
} }
@ -165,7 +170,7 @@ namespace Utility
template <typename T> void DynamicArray<T>::Remove(unsigned int index) template <typename T> void DynamicArray<T>::Remove(unsigned int index)
{ {
assert(index > this->size); assert(index > (unsigned int) this->size);
T* temp = new T[this->capacity - 1]; T* temp = new T[this->capacity - 1];
@ -181,7 +186,8 @@ namespace Utility
template <typename T> void DynamicArray<T>::Clear() template <typename T> void DynamicArray<T>::Clear()
{ {
delete [] this->data; if(this->data)
delete [] this->data;
this->data = 0; this->data = 0;
this->size = 0; this->size = 0;
@ -227,6 +233,11 @@ namespace Utility
return (unsigned int)this->capacity; return (unsigned int)this->capacity;
} }
template <typename T> bool DynamicArray<T>::IsEmpty() const
{
return (this->size == 0);
}
template <typename T> void DynamicArray<T>::Expand(int elements) template <typename T> void DynamicArray<T>::Expand(int elements)
{ {
if(elements < 1) return; if(elements < 1) return;
@ -248,6 +259,18 @@ namespace Utility
} }
} }
template <typename T> T* DynamicArray<T>::begin()
{
if(this->size == 0) return 0;
return &this->data[0];
}
template <typename T> T* DynamicArray<T>::end()
{
if(this->size == 0) return 0;
return ((&this->data[this->size - 1]) + 1);
}
#pragma endregion #pragma endregion
} }
} }

View File

@ -152,8 +152,10 @@
<ClCompile Include="Resource\OResourceHandler.cpp" /> <ClCompile Include="Resource\OResourceHandler.cpp" />
<ClCompile Include="Resource\OResource.cpp" /> <ClCompile Include="Resource\OResource.cpp" />
<ClCompile Include="Resource\ResourceManager.cpp"> <ClCompile Include="Resource\ResourceManager.cpp">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild> <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">false</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild> <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">false</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</ExcludedFromBuild>
</ClCompile> </ClCompile>
<ClCompile Include="Thread\OysterMutex.cpp" /> <ClCompile Include="Thread\OysterMutex.cpp" />
<ClCompile Include="Thread\OysterThread_Impl.cpp" /> <ClCompile Include="Thread\OysterThread_Impl.cpp" />
@ -172,8 +174,10 @@
<ClInclude Include="Resource\OysterResource.h" /> <ClInclude Include="Resource\OysterResource.h" />
<ClInclude Include="Resource\OResource.h" /> <ClInclude Include="Resource\OResource.h" />
<ClInclude Include="Resource\ResourceManager.h"> <ClInclude Include="Resource\ResourceManager.h">
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild> <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">false</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild> <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">false</ExcludedFromBuild>
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</ExcludedFromBuild>
</ClInclude> </ClInclude>
<ClInclude Include="ThreadSafeQueue.h" /> <ClInclude Include="ThreadSafeQueue.h" />
<ClInclude Include="Thread\IThreadObject.h" /> <ClInclude Include="Thread\IThreadObject.h" />

View File

@ -108,7 +108,7 @@ void SaveResource( std::map<std::wstring, ResourceData*>& resources, ResourceDat
} }
bool Release(std::map<std::wstring, ResourceData*>& resources, ResourceData* resource) bool Release(std::map<std::wstring, ResourceData*>& resources, ResourceData* resource)
{ {
if(resource->referenceCount.Decref() == 0) if(resource->referenceCount.Decref() < 1)
{ {
const wchar_t* temp = FindResourceKey(resources, resource->resource); const wchar_t* temp = FindResourceKey(resources, resource->resource);
@ -123,7 +123,7 @@ bool Release(std::map<std::wstring, ResourceData*>& resources, ResourceData* res
resource->resource = 0; resource->resource = 0;
break; break;
case Oyster::Resource::ResourceType_UNKNOWN: case Oyster::Resource::ResourceType_CUSTOM:
resource->unloadFnc(resource->resource); resource->unloadFnc(resource->resource);
resource->resource = 0; resource->resource = 0;
break; break;
@ -137,6 +137,13 @@ bool Release(std::map<std::wstring, ResourceData*>& resources, ResourceData* res
} }
ResourceData* Load(/*Out*/ResourceData* targetMem, /*in*/const wchar_t source[], /*in*/ResourceType type) ResourceData* Load(/*Out*/ResourceData* targetMem, /*in*/const wchar_t source[], /*in*/ResourceType type)
{ {
targetMem->resource = 0;
targetMem->loadFnc = 0;
targetMem->unloadFnc = 0;
targetMem->resourceID = 0;
targetMem->resourcetype = type;
targetMem->resourceSize = 0;
std::string sOut; std::string sOut;
bool success = false; bool success = false;
@ -182,13 +189,20 @@ ResourceData* Load(/*Out*/ResourceData* targetMem, /*in*/const wchar_t source[],
} }
ResourceData* Load(/*Out*/ResourceData* targetMem, /*in*/const wchar_t source[], LoadFunction loadFnc, UnloadFunction unloadFnc) ResourceData* Load(/*Out*/ResourceData* targetMem, /*in*/const wchar_t source[], LoadFunction loadFnc, UnloadFunction unloadFnc)
{ {
targetMem->resource = 0;
targetMem->loadFnc = 0;
targetMem->unloadFnc = 0;
targetMem->resourceID = 0;
targetMem->resourcetype = ResourceType_CUSTOM;
targetMem->resourceSize = 0;
if(loadFnc) if(loadFnc)
{ {
targetMem->resource = loadFnc(source); targetMem->resource = loadFnc(source);
if(targetMem->resource) if(targetMem->resource)
{ {
targetMem->resourceSize = 0; targetMem->resourceSize = 0;
targetMem->resourcetype = ResourceType_UNKNOWN; targetMem->resourcetype = ResourceType_CUSTOM;
targetMem->loadFnc = loadFnc; targetMem->loadFnc = loadFnc;
targetMem->unloadFnc = unloadFnc; targetMem->unloadFnc = unloadFnc;
} }
@ -208,7 +222,7 @@ ResourceData* Reload(std::map<std::wstring, ResourceData*> resources, ResourceDa
return Load(resource, filename, resource->loadFnc, resource->unloadFnc); return Load(resource, filename, resource->loadFnc, resource->unloadFnc);
break; break;
case Oyster::Resource::ResourceType_UNKNOWN: case Oyster::Resource::ResourceType_CUSTOM:
{ {
resource->unloadFnc(resource->resource); resource->unloadFnc(resource->resource);
@ -270,7 +284,7 @@ HRESOURCE ResourceManager::LoadResource(const wchar_t filename[], LoadFunction l
{ {
return 0; return 0;
} }
if(!loadFnc) if(!loadFnc || !unloadFnc)
{ {
return 0; return 0;
} }
@ -278,6 +292,8 @@ HRESOURCE ResourceManager::LoadResource(const wchar_t filename[], LoadFunction l
ResourceData *t = FindResource(this->resources, filename); ResourceData *t = FindResource(this->resources, filename);
if(t) if(t)
{ {
t->loadFnc = loadFnc;
t->unloadFnc = unloadFnc;
if(force) if(force)
{ {
return ResourceManager::ReloadResource(filename); return ResourceManager::ReloadResource(filename);
@ -292,7 +308,7 @@ HRESOURCE ResourceManager::LoadResource(const wchar_t filename[], LoadFunction l
else else
{ {
t = Load(new ResourceData(), filename, loadFnc, unloadFnc ); t = Load(new ResourceData(), filename, loadFnc, unloadFnc );
if(t) if(t && t->resource)
{ {
t->resourceID = (customId); t->resourceID = (customId);
SaveResource(this->resources, t, filename, true); SaveResource(this->resources, t, filename, true);
@ -300,6 +316,7 @@ HRESOURCE ResourceManager::LoadResource(const wchar_t filename[], LoadFunction l
else else
{ {
delete t; delete t;
t = 0;
} }
} }
if(!t) if(!t)
@ -333,24 +350,20 @@ void ResourceManager::Clean()
for (i; i != last; i++) for (i; i != last; i++)
{ {
//Remove all the references //Remove all the references
while (!Release(this->resources, i->second)); while (!Release(resources, i->second));
} }
resources.clear(); resources.clear();
} }
void ResourceManager::ReleaseResource(const HRESOURCE& resourceData) void ResourceManager::ReleaseResource(const HRESOURCE& resourceData)
{ {
ResourceData *t = FindResource(this->resources, resourceData); const wchar_t* temp = FindResourceKey(resources, resourceData);
if(t)
if(temp)
{ {
ResourceData *t = FindResource(this->resources, resourceData);
if(Release(resources, t)) if(Release(resources, t))
{ {
const wchar_t* temp = 0; resources.erase(temp);
if((temp = FindResourceKey(resources, resourceData)))
{
std::wstring ws = std::wstring(temp);
delete resources[ws];
resources.erase(ws);
}
} }
} }
} }
@ -361,7 +374,6 @@ void ResourceManager::ReleaseResource(const wchar_t filename[])
{ {
if(Release(resources, t)) if(Release(resources, t))
{ {
delete resources[filename];
resources.erase(filename); resources.erase(filename);
} }
} }

View File

@ -29,10 +29,8 @@ namespace Oyster
ResourceType_Byte_UNICODE, /**< Handle can be interpeted as char[] or char* */ ResourceType_Byte_UNICODE, /**< Handle can be interpeted as char[] or char* */
ResourceType_Byte_UTF16LE, /**< Handle can be interpeted as char[] or char* */ ResourceType_Byte_UTF16LE, /**< Handle can be interpeted as char[] or char* */
ResourceType_COUNT, /**< Handle can be interpeted as ? */ ResourceType_CUSTOM, /**< Handle can be interpeted as whatever */
ResourceType_INVALID, /**< Handle can be interpeted as whatever */
ResourceType_UNKNOWN = -1, /**< Handle can be interpeted as void* */
ResourceType_INVALID = -2, /**< Invalid or non existing resource */
}; };
/** A resource handler interface to interact with when loading resources. /** A resource handler interface to interact with when loading resources.

View File

@ -42,15 +42,10 @@ using namespace Utility::DynamicMemory;
}; };
struct ThreadData struct ThreadData
{ {
OYSTER_THREAD_STATE state; //<! The current thread state. OYSTER_THREAD_STATE state; //<! The current thread state.
OYSTER_THREAD_PRIORITY prio; //<! The thread priority OYSTER_THREAD_PRIORITY prio; //<! The thread priority
//IThreadObject *owner; //<! The worker object. OwnerContainer ownerObj; //
//Oyster::Callback::OysterCallback<bool, void> ownerObj; // int msec; //<! A timer in miliseconds.
OwnerContainer ownerObj; //
std::atomic<int> msec; //<! A timer in miliseconds.
//std::timed_mutex threadFunctionLock;
std::mutex threadStopMutex;
}; };
/** A typical Oyster thread function */ /** A typical Oyster thread function */
@ -58,7 +53,6 @@ using namespace Utility::DynamicMemory;
struct RefData struct RefData
{ {
std::mutex threadWaitFunctionLock;
bool isCreated; bool isCreated;
bool isAlive; bool isAlive;
ThreadData *threadData; ThreadData *threadData;
@ -79,11 +73,30 @@ using namespace Utility::DynamicMemory;
{ {
if(!threadData) return OYSTER_THREAD_ERROR_SUCCESS; if(!threadData) return OYSTER_THREAD_ERROR_SUCCESS;
this->threadData->state = OYSTER_THREAD_STATE_DEAD; if(std::this_thread::get_id() != this->workerThread.get_id())
if(this->workerThread.joinable())
{ {
this->workerThread.join(); //this->threadData->threadDataAcces.lock();
//{
this->threadData->state = OYSTER_THREAD_STATE_DEAD;
if(this->workerThread.joinable())
{
this->workerThread.join();
}
this->isCreated = false;
delete this->threadData;
this->threadData = 0;
//} this->threadData->threadDataAcces.unlock();
}
else
{
this->threadData->state = OYSTER_THREAD_STATE_DEAD;
if(this->workerThread.joinable())
{
this->workerThread.join();
}
this->isCreated = false; this->isCreated = false;
delete this->threadData; delete this->threadData;
this->threadData = 0; this->threadData = 0;
@ -102,12 +115,10 @@ using namespace Utility::DynamicMemory;
this->threadData->state = OYSTER_THREAD_STATE_IDLE; this->threadData->state = OYSTER_THREAD_STATE_IDLE;
threadData->ownerObj = worker; threadData->ownerObj = worker;
threadData->prio = OYSTER_THREAD_PRIORITY_2; threadData->prio = OYSTER_THREAD_PRIORITY_2;
threadData->msec = 0;
workerThread = std::thread(fnc, this->threadData); workerThread = std::thread(fnc, this->threadData);
//if(detach)
// this->workerThread.detach();
isCreated = true; isCreated = true;
return OYSTER_THREAD_ERROR_SUCCESS; return OYSTER_THREAD_ERROR_SUCCESS;
@ -145,6 +156,9 @@ using namespace Utility::DynamicMemory;
public: public:
static void CheckPriority(ThreadData* w) static void CheckPriority(ThreadData* w)
{ {
Oyster::Thread::OYSTER_THREAD_PRIORITY temp = w->prio;
switch (w->prio) switch (w->prio)
{ {
case Oyster::Thread::OYSTER_THREAD_PRIORITY_1: case Oyster::Thread::OYSTER_THREAD_PRIORITY_1:
@ -190,16 +204,18 @@ using namespace Utility::DynamicMemory;
while (w->state == OYSTER_THREAD_STATE_NORMAL) while (w->state == OYSTER_THREAD_STATE_NORMAL)
{ {
CheckPriority(w); //while (!w->threadDataAcces.try_lock());
if(!DoWork(w)) break;
CheckStatus(w); CheckPriority(w);
if(!DoWork(w)) break;
CheckStatus(w);
//w->threadDataAcces.unlock();
} }
if(w->ownerObj.value.obj) w->ownerObj.value.obj->ThreadExit(); if(w->ownerObj.value.obj) w->ownerObj.value.obj->ThreadExit();
w->state = OYSTER_THREAD_STATE_DEAD; w->state = OYSTER_THREAD_STATE_DEAD;
//delete w;
} }
}; };
@ -247,79 +263,114 @@ OYSTER_THREAD_ERROR OysterThread::Create(ThreadFnc worker, bool start, bool deta
OYSTER_THREAD_ERROR OysterThread::Start() OYSTER_THREAD_ERROR OysterThread::Start()
{ {
if(!this->privateData->data->threadData->ownerObj) OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
return OYSTER_THREAD_ERROR_ThreadHasNoWorker; //this->privateData->data->threadData->threadDataAcces.lock();{
if(this->privateData->data->threadData->state == OYSTER_THREAD_STATE_DEAD) if(!this->privateData->data->threadData->ownerObj)
return OYSTER_THREAD_ERROR_ThreadIsDead; val = OYSTER_THREAD_ERROR_ThreadHasNoWorker;
this->privateData->data->threadData->state = OYSTER_THREAD_STATE_NORMAL; if(this->privateData->data->threadData->state == OYSTER_THREAD_STATE_DEAD)
val = OYSTER_THREAD_ERROR_ThreadIsDead;
return OYSTER_THREAD_ERROR_SUCCESS; this->privateData->data->threadData->state = OYSTER_THREAD_STATE_NORMAL;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return val;
} }
OYSTER_THREAD_ERROR OysterThread::Stop() OYSTER_THREAD_ERROR OysterThread::Stop()
{ {
this->privateData->data->threadData->state = OYSTER_THREAD_STATE_IDLE; OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
return OYSTER_THREAD_ERROR_SUCCESS; //this->privateData->data->threadData->threadDataAcces.lock(); {
this->privateData->data->threadData->state = OYSTER_THREAD_STATE_IDLE;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return val;
} }
OYSTER_THREAD_ERROR OysterThread::Stop(int msec) OYSTER_THREAD_ERROR OysterThread::Stop(int msec)
{ {
this->privateData->data->threadData->msec = msec; OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
return OYSTER_THREAD_ERROR_SUCCESS; //this->privateData->data->threadData->threadDataAcces.lock(); {
this->privateData->data->threadData->msec = msec;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return val;
} }
OYSTER_THREAD_ERROR OysterThread::Resume() OYSTER_THREAD_ERROR OysterThread::Resume()
{ {
if(this->privateData->data->threadData->state == OYSTER_THREAD_STATE_DEAD) OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
return OYSTER_THREAD_ERROR_ThreadIsDead; //this->privateData->data->threadData->threadDataAcces.lock(); {
if(this->privateData->data->threadData->state == OYSTER_THREAD_STATE_DEAD)
val = OYSTER_THREAD_ERROR_ThreadIsDead;
this->privateData->data->threadData->state = OYSTER_THREAD_STATE_NORMAL; this->privateData->data->threadData->state = OYSTER_THREAD_STATE_NORMAL;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return OYSTER_THREAD_ERROR_SUCCESS; return val;
} }
OYSTER_THREAD_ERROR OysterThread::SetWorker(IThreadObject* worker) OYSTER_THREAD_ERROR OysterThread::SetWorker(IThreadObject* worker)
{ {
this->privateData->data->threadData->ownerObj.value = worker; OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
this->privateData->data->threadData->ownerObj.type = Oyster::Callback::CallbackType_Object; //this->privateData->data->threadData->threadDataAcces.lock();{
this->privateData->data->threadData->msec = 0; this->privateData->data->threadData->ownerObj.value = worker;
this->privateData->data->threadData->ownerObj.type = Oyster::Callback::CallbackType_Object;
return OYSTER_THREAD_ERROR_SUCCESS;; this->privateData->data->threadData->msec = 0;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return val;;
} }
OYSTER_THREAD_ERROR OysterThread::SetWorker(ThreadFnc worker) OYSTER_THREAD_ERROR OysterThread::SetWorker(ThreadFnc worker)
{ {
this->privateData->data->threadData->ownerObj.value = worker; OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
this->privateData->data->threadData->ownerObj.type = Oyster::Callback::CallbackType_Function; //this->privateData->data->threadData->threadDataAcces.lock();{
this->privateData->data->threadData->msec = 0; this->privateData->data->threadData->ownerObj.value = worker;
this->privateData->data->threadData->ownerObj.type = Oyster::Callback::CallbackType_Function;
return OYSTER_THREAD_ERROR_SUCCESS;; this->privateData->data->threadData->msec = 0;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return val;;
} }
OYSTER_THREAD_ERROR OysterThread::Terminate() OYSTER_THREAD_ERROR OysterThread::Terminate()
{ {
if(this->privateData) if(this->privateData)
return this->privateData->Terminate(); return this->privateData->Terminate();
return OYSTER_THREAD_ERROR_SUCCESS; return OYSTER_THREAD_ERROR_SUCCESS;
} }
OYSTER_THREAD_ERROR OysterThread::Wait() OYSTER_THREAD_ERROR OysterThread::Wait()
{ {
if(this->privateData->data->threadData->state == OYSTER_THREAD_STATE_DEAD) OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
return OYSTER_THREAD_ERROR_ThreadIsDead;
if( this->privateData->data->workerThread.get_id() == std::this_thread::get_id()) //this->privateData->data->threadData->threadDataAcces.lock();{
return OYSTER_THREAD_ERROR_ThreadCannotWaintOnItselfe;
return OYSTER_THREAD_ERROR_SUCCESS; if(this->privateData->data->threadData->state == OYSTER_THREAD_STATE_DEAD)
val = OYSTER_THREAD_ERROR_ThreadIsDead;
if( this->privateData->data->workerThread.get_id() == std::this_thread::get_id())
val = OYSTER_THREAD_ERROR_ThreadCannotWaintOnItselfe;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return val;
} }
OYSTER_THREAD_ERROR OysterThread::Wait(int msec) OYSTER_THREAD_ERROR OysterThread::Wait(int msec)
{ {
if(this->privateData->data->workerThread.get_id() == std::this_thread::get_id()) OYSTER_THREAD_ERROR val = OYSTER_THREAD_ERROR_SUCCESS;
return OYSTER_THREAD_ERROR_ThreadCannotWaintOnItselfe;
//this->privateData->data->threadData->threadDataAcces.lock();{
return OYSTER_THREAD_ERROR_SUCCESS; if(this->privateData->data->workerThread.get_id() == std::this_thread::get_id())
val = OYSTER_THREAD_ERROR_ThreadCannotWaintOnItselfe;
//} this->privateData->data->threadData->threadDataAcces.unlock();
return val;
} }
OYSTER_THREAD_ERROR OysterThread::Swap(const OysterThread* other) OYSTER_THREAD_ERROR OysterThread::Swap(const OysterThread* other)
{ {
this->privateData->data->workerThread.swap(other->privateData->data->workerThread); //this->privateData->data->threadData->threadDataAcces.lock();{
this->privateData->data->workerThread.swap(other->privateData->data->workerThread);
//} this->privateData->data->threadData->threadDataAcces.unlock();
return OYSTER_THREAD_ERROR_SUCCESS; return OYSTER_THREAD_ERROR_SUCCESS;
} }

View File

@ -34,12 +34,15 @@ namespace Utility
virtual bool IsEmpty(); virtual bool IsEmpty();
virtual void Swap( IQueue<Type> &queue ); virtual void Swap( IQueue<Type> &queue );
virtual void Clear();
private: private:
class Node class Node
{ {
public: public:
Type item; Type item;
Node *next; Node *next;
Node(){ this->next = NULL; };
Node(Type item){ this->item = item; this->next = NULL; }; Node(Type item){ this->item = item; this->next = NULL; };
~Node() {}; ~Node() {};
}; };
@ -215,6 +218,15 @@ namespace Utility
stdMutex.unlock(); stdMutex.unlock();
} }
template < typename Type >
void ThreadSafeQueue<Type>::Clear()
{
while (!IsEmpty())
{
Pop();
}
}
} }
} }

View File

@ -374,7 +374,191 @@ namespace Utility
return (this->_ptr != NULL) ? true : false; return (this->_ptr != NULL) ? true : false;
} }
#pragma endregion #pragma endregion
}
namespace Thread
{
#pragma region ThreadSafeSmartPointer
template<typename T> void ThreadSafeSmartPointer<T>::Destroy()
{
delete this->_rc.load();
this->_rc = NULL;
//Use default function for memory deallocation.
SafeDeleteInstance<T>(this->_ptr.load());
this->_ptr = NULL;
}
template<typename T> ThreadSafeSmartPointer<T>::ThreadSafeSmartPointer()
:_rc(0), _ptr(0)
{ }
template<typename T> ThreadSafeSmartPointer<T>::ThreadSafeSmartPointer(UniquePointer<T>& p)
:_ptr(p.Release())
{
this->_rc = new ReferenceCount();
this->_rc->Incref();
}
template<typename T> ThreadSafeSmartPointer<T>::ThreadSafeSmartPointer(T* p)
:_ptr(p)
{
this->_rc.store = new ReferenceCount();
this->_rc->Incref();
}
template<typename T> ThreadSafeSmartPointer<T>::ThreadSafeSmartPointer(const ThreadSafeSmartPointer& d)
:_ptr(d._ptr), _rc(d._rc)
{
if(this->_rc)
this->_rc->Incref();
}
template<typename T> ThreadSafeSmartPointer<T>::~ThreadSafeSmartPointer()
{
this->Release();
}
template<typename T> ThreadSafeSmartPointer<T>& ThreadSafeSmartPointer<T>::operator= (const ThreadSafeSmartPointer<T>& p)
{
if (this != &p)
{
//Last to go?
if(this->_rc.load() && this->_rc.load()->Decref() == 0)
{
//Call child specific
Destroy();
}
this->_ptr.store(p._ptr.load());
this->_rc.store(p._rc.load());
if(this->_rc.load()) this->_rc.load()->Incref();
}
return *this;
}
template<typename T> ThreadSafeSmartPointer<T>& ThreadSafeSmartPointer<T>::operator= (UniquePointer<T>& p)
{
//Last to go?
if(this->_rc)
{
if(this->_rc->Decref() == 0)
{
//Call child specific
Destroy();
this->_rc = new ReferenceCount();
}
}
else
{
if(p) this->_rc = new ReferenceCount();
}
if(this->_rc)
this->_rc->Incref();
this->_ptr = p.Release();
return *this;
}
template<typename T> ThreadSafeSmartPointer<T>& ThreadSafeSmartPointer<T>::operator= (T* p)
{
if (this->_ptr != p)
{
//Last to go?
if(this->_rc.load())
{
if(this->_rc.load()->Decref() == 0)
{
//Call child specific
Destroy();
if(p) this->_rc = new ReferenceCount();
}
}
else if(p)
{
this->_rc = new ReferenceCount();
}
this->_ptr = p;
if(p) this->_rc.load()->Incref();
else this->_rc = 0;
}
return *this;
}
template<typename T> inline bool ThreadSafeSmartPointer<T>::operator== (const ThreadSafeSmartPointer<T>& d) const
{
return d._ptr == this->_ptr;
}
template<typename T> inline bool ThreadSafeSmartPointer<T>::operator== (const T& p) const
{
return &p == this->_ptr;
}
template<typename T> inline bool ThreadSafeSmartPointer<T>::operator!= (const ThreadSafeSmartPointer<T>& d) const
{
return d._ptr != this->_ptr;
}
template<typename T> inline bool ThreadSafeSmartPointer<T>::operator!= (const T& p) const
{
return &p != this->_ptr;
}
template<typename T> inline T& ThreadSafeSmartPointer<T>::operator* ()
{
return *this->_ptr;
}
template<typename T> inline const T& ThreadSafeSmartPointer<T>::operator* () const
{
return *this->_ptr;
}
template<typename T> inline T* ThreadSafeSmartPointer<T>::operator-> ()
{
return this->_ptr;
}
template<typename T> inline const T* ThreadSafeSmartPointer<T>::operator-> () const
{
return this->_ptr;
}
template<typename T> inline ThreadSafeSmartPointer<T>::operator T* () const
{
return this->_ptr;
}
template<typename T> inline ThreadSafeSmartPointer<T>::operator const T* () const
{
return this->_ptr;
}
template<typename T> inline ThreadSafeSmartPointer<T>::operator T& () const
{
return *this->_ptr;
}
template<typename T> inline ThreadSafeSmartPointer<T>::operator bool() const
{
return (this->_ptr != 0);
}
template<typename T> inline T* ThreadSafeSmartPointer<T>::Get()
{
return this->_ptr;
}
template<typename T> inline T* ThreadSafeSmartPointer<T>::Get() const
{
return this->_ptr;
}
template<typename T> int ThreadSafeSmartPointer<T>::Release()
{
int returnVal = 0;
if(this->_rc.load() && ((returnVal = this->_rc.load()->Decref()) == 0))
{
Destroy();
}
return returnVal;
}
template<typename T> int ThreadSafeSmartPointer<T>::ReleaseDummy()
{
int val = this->_rc->Decref();
this->_rc->Incref();
return val;
}
template<typename T> inline bool ThreadSafeSmartPointer<T>::IsValid() const
{
return (this->_ptr != NULL) ? true : false;
}
#pragma endregion
} }
} }

View File

@ -300,7 +300,7 @@ namespace Utility
//To wstring //To wstring
::std::wstring & StringToWString( const ::std::string &str, ::std::wstring &wstr ) ::std::wstring & StringToWstring( const ::std::string &str, ::std::wstring &wstr )
{ {
const char *orig = str.c_str(); const char *orig = str.c_str();

View File

@ -408,7 +408,59 @@ namespace Utility
namespace Thread namespace Thread
{ {
//Utilities for threading using namespace DynamicMemory;
//! Wrapper to manage references on a pointer.
template<typename T> struct ThreadSafeSmartPointer
{
private:
std::atomic<ReferenceCount*> _rc;
std::atomic<T*> _ptr;
/** Destroys the pointer and returns the memory allocated. */
void Destroy();
public:
ThreadSafeSmartPointer();
ThreadSafeSmartPointer(UniquePointer<T>& up);
ThreadSafeSmartPointer(T* p);
ThreadSafeSmartPointer(const ThreadSafeSmartPointer& d);
virtual~ThreadSafeSmartPointer();
ThreadSafeSmartPointer<T>& operator= (const ThreadSafeSmartPointer<T>& p);
ThreadSafeSmartPointer<T>& operator= (UniquePointer<T>& p);
ThreadSafeSmartPointer<T>& operator= (T* p);
bool operator== (const ThreadSafeSmartPointer<T>& d) const;
bool operator== (const T& p) const;
bool operator!= (const ThreadSafeSmartPointer<T>& d) const;
bool operator!= (const T& p) const;
T& operator* ();
const T& operator* () const;
T* operator-> ();
const T* operator-> () const;
operator T* () const;
operator const T* () const;
operator T& () const;
operator bool() const;
/**
* Returns the connected pointer
*/
T* Get();
T* Get() const;
/**
* Releases one reference of the pointer and set value to null, making the current ThreadSafeSmartPointer invalid.
*/
int Release();
/**
* Only test to release to check reference count.
*/
int ReleaseDummy();
/** Checks if the pointer is valid (not NULL)
* Returns true for valid, else false.
*/
bool IsValid() const;
};
} }
} }

View File

@ -4,42 +4,31 @@
#include "CustomNetProtocol.h" #include "CustomNetProtocol.h"
#include <map> #include <map>
#include "Translator.h" #include "Translator.h"
#include "Utilities.h" #include <DynamicArray.h>
using namespace Oyster::Network; using namespace Oyster::Network;
using namespace Utility::DynamicMemory; using namespace Utility::DynamicMemory;
struct CustomNetProtocol::PrivateData struct CustomNetProtocol::PrivateData
{ {
std::map<int, NetAttributeContainer> attributes; //...Im an idiot //std::map<int, NetAttributeContainer> attributes; //...Im an idiot
Utility::DynamicMemory::ReferenceCount *c; DynamicArray<NetAttributeContainer> attributes; //...Im an idiot
PrivateData() PrivateData()
{ { }
//this->attributes = new std::map<int, NetAttributeContainer>();
this->c = new ReferenceCount();
c->Incref();
}
~PrivateData() ~PrivateData()
{ {
delete c; attributes.Clear();
c = 0;
for (auto i = attributes.begin(); i != attributes.end(); i++)
{
RemoveAttribute(i->first);
}
attributes.clear();
} }
void RemoveAttribute(int ID) void RemoveAttribute(NetAttributeContainer* i)
{ {
auto i = attributes.find(ID); if(!i) return;
if(i == attributes.end()) return;
switch (i->second.type) switch (i->type)
{ {
case NetAttributeType_CharArray: case NetAttributeType_CharArray:
delete [] i->second.value.netCharPtr; delete [] i->value.netCharPtr;
break; break;
} }
} }
@ -47,55 +36,42 @@ struct CustomNetProtocol::PrivateData
//Do network stuff //Do network stuff
}; };
CustomNetProtocol::CustomNetProtocol() CustomNetProtocol::CustomNetProtocol()
{ {
this->privateData = new PrivateData(); this->privateData = new PrivateData();
} }
CustomNetProtocol::CustomNetProtocol(const CustomNetProtocol& o) CustomNetProtocol::CustomNetProtocol(CustomNetProtocol& o)
{ {
this->privateData = o.privateData; this->privateData = new PrivateData();
if(this->privateData) this->privateData->attributes = o.privateData->attributes;
{
this->privateData->c = o.privateData->c;
this->privateData->c->Incref();
}
} }
const CustomNetProtocol& CustomNetProtocol::operator=(const CustomNetProtocol& o) const CustomNetProtocol& CustomNetProtocol::operator=(CustomNetProtocol& o)
{ {
if(this->privateData && this->privateData->c) if(this->privateData)
{ {
if(this->privateData->c->Decref() == 0) delete this->privateData;
{ this->privateData = 0;
delete this->privateData;
}
}
this->privateData = o.privateData;
if(this->privateData)
{
this->privateData->c = o.privateData->c;
this->privateData->c->Incref();
} }
this->privateData = new PrivateData();
this->privateData->attributes = o.privateData->attributes;
return *this; return *this;
} }
CustomNetProtocol::~CustomNetProtocol() CustomNetProtocol::~CustomNetProtocol()
{ {
if(this->privateData && this->privateData->c) delete this->privateData;
{ this->privateData = 0;
if(this->privateData->c->Decref() == 0)
{
delete this->privateData;
}
}
} }
NetAttributeContainer& CustomNetProtocol::operator[](int ID) NetAttributeContainer& CustomNetProtocol::operator[](int ID)
{ {
if(this->privateData->attributes.find(ID) == this->privateData->attributes.end()) //if(!this->privateData) this->privateData = new PrivateData();
if((unsigned int)ID >= this->privateData->attributes.Size())
{ {
this->privateData->attributes[ID]; NetAttributeContainer temp;
this->privateData->attributes[ID].type = NetAttributeType_UNKNOWN;
memset(&this->privateData->attributes[ID].value, 0, sizeof(NetAttributeValue)); temp.type = NetAttributeType_UNKNOWN;
memset(&temp.value, 0, sizeof(NetAttributeValue));
this->privateData->attributes.Push(ID, temp);
} }
return this->privateData->attributes[ID]; return this->privateData->attributes[ID];
@ -134,4 +110,115 @@ void CustomNetProtocol::Set(int ID, std::string s)
const NetAttributeContainer& CustomNetProtocol::Get(int id) const NetAttributeContainer& CustomNetProtocol::Get(int id)
{ {
return this->privateData->attributes[id]; return this->privateData->attributes[id];
} }
///////////////////////////////////////////////////////////////////////
//// Created by [Dennis Andersen] [2013]
///////////////////////////////////////////////////////////////////////
//#include "CustomNetProtocol.h"
//#include <map>
//#include "Translator.h"
//#include <DynamicArray.h>
//using namespace Oyster::Network;
//using namespace Utility::DynamicMemory;
//
//
//
//struct CustomNetProtocol::PrivateData
//{
// Utility::DynamicMemory::DynamicArray<NetAttributeContainer> attributes; //...Im an idiot
//
// PrivateData()
// { }
//
// ~PrivateData()
// {
// for (unsigned int i = 0; i < attributes.Size(); i++)
// {
// RemoveAttribute(i);
// }
//
// attributes.Clear();
// }
// void RemoveAttribute(int i)
// {
// switch (attributes[i].type)
// {
// case NetAttributeType_CharArray:
// delete [] attributes[i].value.netCharPtr;
// break;
// }
// }
//
// //Do network stuff
//};
//
//
//CustomNetProtocol::CustomNetProtocol()
//{
// this->privateData = new PrivateData();
//}
//CustomNetProtocol::CustomNetProtocol(const CustomNetProtocol& o)
//{
// this->privateData = o.privateData;
//}
//const CustomNetProtocol& CustomNetProtocol::operator=(const CustomNetProtocol& o)
//{
// this->privateData = o.privateData;
// return *this;
//}
//CustomNetProtocol::~CustomNetProtocol()
//{
//}
//NetAttributeContainer& CustomNetProtocol::operator[](int ID)
//{
// if(ID >= this->privateData->attributes.Size())
// this->privateData->attributes.Resize(
// if(this->privateData->attributes.find(ID) == this->privateData->attributes.end())
// {
// this->privateData->attributes[ID];
// this->privateData->attributes[ID].type = NetAttributeType_UNKNOWN;
// memset(&this->privateData->attributes[ID].value, 0, sizeof(NetAttributeValue));
// }
//
// return this->privateData->attributes[ID];
//}
//
//void CustomNetProtocol::Set(int ID, Oyster::Network::NetAttributeValue val, Oyster::Network::NetAttributeType type)
//{
// this->privateData->attributes[ID].type = type;
//
// switch (type)
// {
// case Oyster::Network::NetAttributeType_Bool:
// case Oyster::Network::NetAttributeType_Char:
// case Oyster::Network::NetAttributeType_UnsignedChar:
// case Oyster::Network::NetAttributeType_Short:
// case Oyster::Network::NetAttributeType_UnsignedShort:
// case Oyster::Network::NetAttributeType_Int:
// case Oyster::Network::NetAttributeType_UnsignedInt:
// case Oyster::Network::NetAttributeType_Int64:
// case Oyster::Network::NetAttributeType_UnsignedInt64:
// case Oyster::Network::NetAttributeType_Float:
// case Oyster::Network::NetAttributeType_Double:
// this->privateData->attributes[ID].value = val;
// break;
// }
//}
//void CustomNetProtocol::Set(int ID, std::string s)
//{
// if(s.size() == 0) return;
//
// this->privateData->attributes[ID].type = Oyster::Network::NetAttributeType_CharArray;
//
// this->privateData->attributes[ID].value.netCharPtr = new char[s.size() + 1];
// memcpy(&this->privateData->attributes[ID].value.netCharPtr[0], &s[0], s.size() + 1);
//}
//const NetAttributeContainer& CustomNetProtocol::Get(int id)
//{
// return this->privateData->attributes[id];
//}

View File

@ -4,7 +4,11 @@
#ifndef NETWORK_CUSTOM_NETWORK_PROTOCOL_H #ifndef NETWORK_CUSTOM_NETWORK_PROTOCOL_H
#define NETWORK_CUSTOM_NETWORK_PROTOCOL_H #define NETWORK_CUSTOM_NETWORK_PROTOCOL_H
//needs to have dll-interface to be used by clients of class 'Oyster::Network::NetworkSession'
#pragma warning(disable : 4251)
#include <string> #include <string>
#include "Utilities.h"
//#include <vld.h> //#include <vld.h>
#include "NetworkAPI_Preprocessor.h" #include "NetworkAPI_Preprocessor.h"
@ -65,12 +69,60 @@ namespace Oyster
{ {
NetAttributeType type; NetAttributeType type;
NetAttributeValue value; NetAttributeValue value;
NetAttributeContainer() { type = NetAttributeType_UNKNOWN; } NetAttributeContainer()
{ type = NetAttributeType_UNKNOWN; }
~NetAttributeContainer()
{
if (this->type == NetAttributeType_CharArray)
{
delete this->value.netCharPtr;
this->value.netCharPtr = 0;
}
}
NetAttributeContainer(NetAttributeContainer& p)
{
type = p.type;
if(type == NetAttributeType_CharArray && p.value.netCharPtr)
{
int len = 0;
if((len = strlen(p.value.netCharPtr)) == 0) return;
len++;
value.netCharPtr = new char[len];
memcpy(&value.netCharPtr[0], &p.value.netCharPtr[0], sizeof(p.value.netCharPtr[0]) * len);
}
else
{
value = p.value;
}
}
const NetAttributeContainer& operator=(const NetAttributeContainer& p)
{
if(this->type == NetAttributeType_CharArray)
{
delete this->value.netCharPtr;
this->value.netCharPtr = 0;
}
type = p.type;
if(type == NetAttributeType_CharArray && p.value.netCharPtr)
{
int len = 0;
if((len = strlen(p.value.netCharPtr)) == 0) return *this;
len++;
value.netCharPtr = new char[len];
memcpy(&value.netCharPtr[0], &p.value.netCharPtr[0], sizeof(p.value.netCharPtr[0]) * len);
}
else
{
value = p.value;
}
return *this;
}
}; };
class CustomNetProtocol; class CustomNetProtocol;
struct CustomProtocolObject struct CustomProtocolObject
{ {
virtual CustomNetProtocol* GetProtocol() = 0; virtual CustomNetProtocol GetProtocol() = 0;
}; };
class NET_API_EXPORT CustomNetProtocol class NET_API_EXPORT CustomNetProtocol
@ -78,8 +130,8 @@ namespace Oyster
public: public:
CustomNetProtocol(); CustomNetProtocol();
~CustomNetProtocol(); ~CustomNetProtocol();
CustomNetProtocol(const CustomNetProtocol& o); CustomNetProtocol(CustomNetProtocol& o);
const CustomNetProtocol& operator=(const CustomNetProtocol& o); const CustomNetProtocol& operator=(CustomNetProtocol& o);
NetAttributeContainer& operator[](int ID); NetAttributeContainer& operator[](int ID);
void Set(int id, Oyster::Network::NetAttributeValue val, Oyster::Network::NetAttributeType type); void Set(int id, Oyster::Network::NetAttributeValue val, Oyster::Network::NetAttributeType type);
@ -88,6 +140,8 @@ namespace Oyster
private: private:
struct PrivateData; struct PrivateData;
//Utility::DynamicMemory::SmartPointer<PrivateData> privateData;
//Utility::Thread::ThreadSafeSmartPointer<PrivateData> privateData;
PrivateData* privateData; PrivateData* privateData;
friend class Translator; friend class Translator;

View File

@ -19,6 +19,7 @@
#include "../../Misc/Packing/Packing.h" #include "../../Misc/Packing/Packing.h"
#include <queue> #include <queue>
#include <WinSock2.h>
using namespace Oyster::Network; using namespace Oyster::Network;
using namespace Oyster::Thread; using namespace Oyster::Thread;
@ -61,9 +62,10 @@ struct NetworkClient::PrivateData : public IThreadObject
} }
~PrivateData() ~PrivateData()
{ {
this->thread.Terminate();
ShutdownWinSock(); ShutdownWinSock();
this->connection.Disconnect(); this->connection.Disconnect();
this->thread.Terminate();
this->owner = 0; this->owner = 0;
this->parent = 0; this->parent = 0;
} }
@ -83,12 +85,13 @@ struct NetworkClient::PrivateData : public IThreadObject
if(!this->sendQueue.IsEmpty()) if(!this->sendQueue.IsEmpty())
{ {
SmartPointer<OysterByte> temp = new OysterByte(); //printf("\t(%i)\n", this->sendQueue.Size());
OysterByte temp;
CustomNetProtocol p = this->sendQueue.Pop(); CustomNetProtocol p = this->sendQueue.Pop();
this->translator.Pack(temp, p); this->translator.Pack(temp, p);
errorCode = this->connection.Send(temp); errorCode = this->connection.Send(temp);
if(errorCode != 0) if(errorCode != 0 && errorCode != WSAEWOULDBLOCK)
{ {
CEA parg; CEA parg;
parg.type = CEA::EventType_ProtocolFailedToSend; parg.type = CEA::EventType_ProtocolFailedToSend;
@ -204,7 +207,11 @@ struct NetworkClient::PrivateData : public IThreadObject
CEA parg; CEA parg;
parg.type = CEA::EventType_ProtocolRecieved; parg.type = CEA::EventType_ProtocolRecieved;
parg.data.protocol = protocol; parg.data.protocol = protocol;
NetEvent<NetworkClient*, NetworkClient::ClientEventArgs> e = { this->parent, parg }; NetEvent<NetworkClient*, NetworkClient::ClientEventArgs> e;
e.sender = this->parent;
e.args.data.protocol = parg.data.protocol;
e.args.type = parg.type;
this->recieveQueue.Push(e); this->recieveQueue.Push(e);
} }
} }
@ -247,9 +254,6 @@ void NetworkClient::Update()
this->DataRecieved(temp); this->DataRecieved(temp);
//--------- Deprecate ---------
this->NetworkCallback(temp.args.data.protocol);
//------------------------------
} }
} }
@ -291,18 +295,23 @@ bool NetworkClient::Connect(unsigned short port, const char serverIP[])
void NetworkClient::Disconnect() void NetworkClient::Disconnect()
{ {
privateData->connection.Disconnect(); if(!privateData) return;
privateData->thread.Terminate(); privateData->thread.Terminate();
privateData->connection.Disconnect();
this->privateData->sendQueue.Clear();
this->privateData->recieveQueue.Clear();
} }
void NetworkClient::Send(CustomProtocolObject& protocol) void NetworkClient::Send(CustomProtocolObject& protocol)
{ {
this->privateData->sendQueue.Push(*protocol.GetProtocol()); this->privateData->sendQueue.Push(protocol.GetProtocol());
} }
void NetworkClient::Send(CustomNetProtocol* protocol) void NetworkClient::Send(CustomNetProtocol& protocol)
{ {
this->privateData->sendQueue.Push(*protocol); this->privateData->sendQueue.Push(protocol);
} }
void NetworkClient::SetOwner(NetworkSession* owner) void NetworkClient::SetOwner(NetworkSession* owner)
@ -329,8 +338,8 @@ void NetworkClient::DataRecieved(NetEvent<NetworkClient*, ClientEventArgs> e)
} }
} }
void NetworkClient::NetworkCallback(Oyster::Network::CustomNetProtocol& p) //void NetworkClient::NetworkCallback(Oyster::Network::CustomNetProtocol& p)
{} //{}
std::string NetworkClient::GetIpAddress() std::string NetworkClient::GetIpAddress()
{ {

View File

@ -36,7 +36,33 @@ namespace Oyster
{ {
struct { Oyster::Network::CustomNetProtocol protocol; }; struct { Oyster::Network::CustomNetProtocol protocol; };
void * nothing; void * nothing;
EventData(){}
EventData(Oyster::Network::CustomNetProtocol& o)
{
protocol = o;
}
const EventData& operator=(EventData& o)
{
protocol = o.protocol;
return *this;
}
const EventData& operator=(Oyster::Network::CustomNetProtocol& o)
{
protocol = o; return *this;
}
} data; } data;
ClientEventArgs(){}
ClientEventArgs(ClientEventArgs& o)
{
type = o.type;
data = o.data;
}
const ClientEventArgs& operator=(ClientEventArgs& o)
{
type = o.type;
data = o.data;
return *this;
}
}; };
typedef void(*ClientEventFunction)(NetEvent<NetworkClient*, ClientEventArgs> e); typedef void(*ClientEventFunction)(NetEvent<NetworkClient*, ClientEventArgs> e);
@ -75,7 +101,7 @@ namespace Oyster
/** /**
* *
*/ */
void Send(CustomNetProtocol* protocol); void Send(CustomNetProtocol& protocol);
/** /**
* *
@ -101,7 +127,7 @@ namespace Oyster
* Do not use this furthermore, instead use void DataRecieved(NetEvent<NetworkClient*, ClientEventArgs> e); * Do not use this furthermore, instead use void DataRecieved(NetEvent<NetworkClient*, ClientEventArgs> e);
* @see DataRecieved * @see DataRecieved
*/ */
virtual void NetworkCallback(Oyster::Network::CustomNetProtocol& p); //virtual void NetworkCallback(Oyster::Network::CustomNetProtocol& p);
virtual std::string GetIpAddress(); virtual std::string GetIpAddress();

View File

@ -261,7 +261,7 @@ NetworkSession const* NetworkServer::ReleaseMainSession()
return temp; return temp;
} }
bool NetworkServer::IsStarted() const bool NetworkServer::IsRunning() const
{ {
return this->privateData->isRunning; return this->privateData->isRunning;
} }

View File

@ -77,7 +77,7 @@ namespace Oyster
/** /**
* *
*/ */
bool IsStarted() const; bool IsRunning() const;
/** /**
* *

View File

@ -26,7 +26,15 @@ struct NetworkSession::PrivateSessionData
{} {}
}; };
int FindClient(NetClientList& list, NetClient c)
{
for (unsigned int i = 0; i < list.Size(); i++)
{
if(c == list[i])
return i;
}
return -1;
}
NetworkSession::NetworkSession() NetworkSession::NetworkSession()
: data(new PrivateSessionData()) : data(new PrivateSessionData())
@ -125,7 +133,7 @@ NetClient NetworkSession::Detach(const NetworkClient* client)
for (unsigned int i = 0; i < this->clients.Size(); i++) for (unsigned int i = 0; i < this->clients.Size(); i++)
{ {
if(this->clients[i] && this->clients[0]->GetID() == client->GetID()) if(this->clients[i] && this->clients[i]->GetID() == client->GetID())
{ {
val = this->clients[i]; val = this->clients[i];
this->clients[i] = 0; this->clients[i] = 0;
@ -188,7 +196,7 @@ bool NetworkSession::Send(Oyster::Network::CustomNetProtocol& protocol)
{ {
if(this->clients[i]) if(this->clients[i])
{ {
this->clients[i]->Send(&protocol); this->clients[i]->Send(protocol);
returnValue = true; returnValue = true;
} }
} }
@ -202,7 +210,7 @@ bool NetworkSession::Send(Oyster::Network::CustomNetProtocol& protocol, int ID)
{ {
if(this->clients[i] && this->clients[i]->GetID() == ID) if(this->clients[i] && this->clients[i]->GetID() == ID)
{ {
this->clients[i]->Send(&protocol); this->clients[i]->Send(protocol);
return true; return true;
} }
} }
@ -237,5 +245,8 @@ void NetworkSession::SetOwner(NetworkSession* owner)
void NetworkSession::ClientConnectedEvent(NetClient client) void NetworkSession::ClientConnectedEvent(NetClient client)
{ {
this->Attach(client); this->Attach(client);
if(FindClient(this->clients, client) == -1)
NetworkSession::Attach(client);
} }

View File

@ -8,17 +8,18 @@
#include "../../Misc/Utilities.h" #include "../../Misc/Utilities.h"
#include "../NetworkDependencies/Messages/MessageHeader.h" #include "../NetworkDependencies/Messages/MessageHeader.h"
#include "../NetworkDependencies/OysterByte.h" #include "../NetworkDependencies/OysterByte.h"
#include <DynamicArray.h>
using namespace Oyster::Network; using namespace Oyster::Network;
using namespace ::Messages; using namespace ::Messages;
using namespace Utility::DynamicMemory; using namespace Utility::DynamicMemory;
using namespace std; using namespace std;
//TODO: Fix this uggly hack
struct MyCastingStruct struct MyCastingStruct
{ {
std::map<int, NetAttributeContainer> attributes; Utility::DynamicMemory::DynamicArray<NetAttributeContainer> attributes;
Utility::DynamicMemory::ReferenceCount *c;
}; };
// TODO: Check if the package has been packed correctly. // TODO: Check if the package has been packed correctly.
@ -43,7 +44,7 @@ struct Translator::PrivateData
//Find all the data types //Find all the data types
for(; it != end; it++) for(; it != end; it++)
{ {
headerString.push_back(it->second.type); headerString.push_back(it->type);
} }
message.PackShort(headerString.size(), bytes); message.PackShort(headerString.size(), bytes);
@ -68,40 +69,40 @@ struct Translator::PrivateData
switch((int)headerString.at(i)) switch((int)headerString.at(i))
{ {
case NetAttributeType_Bool: case NetAttributeType_Bool:
message.PackBool(it->second.value.netBool, bytes); message.PackBool(it->value.netBool, bytes);
break; break;
case NetAttributeType_Char: case NetAttributeType_Char:
message.PackChar(it->second.value.netChar, bytes); message.PackChar(it->value.netChar, bytes);
break; break;
case NetAttributeType_UnsignedChar: case NetAttributeType_UnsignedChar:
message.PackUnsignedChar(it->second.value.netUChar, bytes); message.PackUnsignedChar(it->value.netUChar, bytes);
break; break;
case NetAttributeType_Short: case NetAttributeType_Short:
message.PackShort(it->second.value.netShort, bytes); message.PackShort(it->value.netShort, bytes);
break; break;
case NetAttributeType_UnsignedShort: case NetAttributeType_UnsignedShort:
message.PackUnsignedShort(it->second.value.netUShort, bytes); message.PackUnsignedShort(it->value.netUShort, bytes);
break; break;
case NetAttributeType_Int: case NetAttributeType_Int:
message.PackInt(it->second.value.netInt, bytes); message.PackInt(it->value.netInt, bytes);
break; break;
case NetAttributeType_UnsignedInt: case NetAttributeType_UnsignedInt:
message.PackUnsignedInt(it->second.value.netUInt, bytes); message.PackUnsignedInt(it->value.netUInt, bytes);
break; break;
case NetAttributeType_Int64: case NetAttributeType_Int64:
message.PackInt64(it->second.value.netInt64, bytes); message.PackInt64(it->value.netInt64, bytes);
break; break;
case NetAttributeType_UnsignedInt64: case NetAttributeType_UnsignedInt64:
message.PackUnsignedInt64(it->second.value.netUInt64, bytes); message.PackUnsignedInt64(it->value.netUInt64, bytes);
break; break;
case NetAttributeType_Float: case NetAttributeType_Float:
message.PackFloat(it->second.value.netFloat, bytes); message.PackFloat(it->value.netFloat, bytes);
break; break;
case NetAttributeType_Double: case NetAttributeType_Double:
message.PackDouble(it->second.value.netDouble, bytes); message.PackDouble(it->value.netDouble, bytes);
break; break;
case NetAttributeType_CharArray: case NetAttributeType_CharArray:
message.PackStr(it->second.value.netCharPtr, bytes); message.PackStr(it->value.netCharPtr, bytes);
break; break;
default: default:
numberOfUnknownTypes++; numberOfUnknownTypes++;
@ -215,6 +216,7 @@ const Translator& Translator::operator=(const Translator& obj)
void Translator::Pack(OysterByte &bytes, CustomNetProtocol& protocol) void Translator::Pack(OysterByte &bytes, CustomNetProtocol& protocol)
{ {
privateData->headerString.clear(); privateData->headerString.clear();
privateData->PackHeader(bytes, protocol); privateData->PackHeader(bytes, protocol);

View File

@ -15,6 +15,11 @@ IDXGISwapChain* Core::swapChain = NULL;
std::stringstream Core::log; std::stringstream Core::log;
Oyster::Resource::ResourceManager Core::loader;
std::wstring Core::modelPath;
std::wstring Core::texturePath;
ID3D11RenderTargetView* Core::backBufferRTV = NULL; ID3D11RenderTargetView* Core::backBufferRTV = NULL;
ID3D11UnorderedAccessView* Core::backBufferUAV = NULL; ID3D11UnorderedAccessView* Core::backBufferUAV = NULL;

View File

@ -7,6 +7,7 @@
#include "Dx11Includes.h" #include "Dx11Includes.h"
#include <sstream> #include <sstream>
#include "OysterMath.h" #include "OysterMath.h"
#include "../Misc/Resource/ResourceManager.h"
//#include <vld.h> //#include <vld.h>
namespace Oyster namespace Oyster
@ -25,6 +26,10 @@ namespace Oyster
static std::stringstream log; static std::stringstream log;
static Resource::ResourceManager loader;
static std::wstring modelPath, texturePath;
//BackBufferRTV //BackBufferRTV
static ID3D11RenderTargetView* backBufferRTV; static ID3D11RenderTargetView* backBufferRTV;
//BackBufferUAV //BackBufferUAV

View File

@ -2,7 +2,6 @@
#include <fstream> #include <fstream>
#include <map> #include <map>
#include "../FileLoader/GeneralLoader.h" #include "../FileLoader/GeneralLoader.h"
#include "Resource\OysterResource.h"
const char* ShaderFunction = "main"; const char* ShaderFunction = "main";
@ -49,7 +48,7 @@ namespace Oyster
case Oyster::Graphics::Core::PipelineManager::Vertex: case Oyster::Graphics::Core::PipelineManager::Vertex:
if(!VSMap.count(name) || ForceReload) if(!VSMap.count(name) || ForceReload)
{ {
data = Resource::OysterResource::LoadResource(filename.c_str(),Loading::LoadShaderV, -1, ForceReload); data = Core::loader.LoadResource(filename.c_str(),Loading::LoadShaderV, Loading::UnloadShaderV, -1, ForceReload);
if(data) if(data)
{ {
if(ForceReload && VSMap.count(name)) if(ForceReload && VSMap.count(name))
@ -65,7 +64,7 @@ namespace Oyster
} }
break; break;
case Oyster::Graphics::Core::PipelineManager::Hull: case Oyster::Graphics::Core::PipelineManager::Hull:
data = Resource::OysterResource::LoadResource(filename.c_str(),Loading::LoadShaderH, -1, ForceReload); data = Core::loader.LoadResource(filename.c_str(),Loading::LoadShaderH, Loading::UnloadShaderH, -1, ForceReload);
if(!HSMap.count(name) || ForceReload) if(!HSMap.count(name) || ForceReload)
{ {
if(data!=0) if(data!=0)
@ -84,7 +83,7 @@ namespace Oyster
} }
break; break;
case Oyster::Graphics::Core::PipelineManager::Domain: case Oyster::Graphics::Core::PipelineManager::Domain:
data = Resource::OysterResource::LoadResource(filename.c_str(),Loading::LoadShaderD, -1, ForceReload); data = Core::loader.LoadResource(filename.c_str(),Loading::LoadShaderD, Loading::UnloadShaderD, -1, ForceReload);
if(!DSMap.count(name) || ForceReload) if(!DSMap.count(name) || ForceReload)
{ {
if(data!=0) if(data!=0)
@ -102,7 +101,7 @@ namespace Oyster
} }
break; break;
case Oyster::Graphics::Core::PipelineManager::Geometry: case Oyster::Graphics::Core::PipelineManager::Geometry:
data = Resource::OysterResource::LoadResource(filename.c_str(),Loading::LoadShaderG, -1, ForceReload); data = Core::loader.LoadResource(filename.c_str(),Loading::LoadShaderG, Loading::UnloadShaderG, -1, ForceReload);
if(!GSMap.count(name) || ForceReload) if(!GSMap.count(name) || ForceReload)
{ {
if(data!=0) if(data!=0)
@ -120,7 +119,7 @@ namespace Oyster
} }
break; break;
case Oyster::Graphics::Core::PipelineManager::Pixel: case Oyster::Graphics::Core::PipelineManager::Pixel:
data = Resource::OysterResource::LoadResource(filename.c_str(),Loading::LoadShaderP, -1, ForceReload); data = Core::loader.LoadResource(filename.c_str(),Loading::LoadShaderP, Loading::UnloadShaderP, -1, ForceReload);
if(!PSMap.count(name) || ForceReload) if(!PSMap.count(name) || ForceReload)
{ {
if(data!=0) if(data!=0)
@ -138,7 +137,7 @@ namespace Oyster
} }
break; break;
case Oyster::Graphics::Core::PipelineManager::Compute: case Oyster::Graphics::Core::PipelineManager::Compute:
data = Resource::OysterResource::LoadResource(filename.c_str(),Loading::LoadShaderC, -1, ForceReload); data = Core::loader.LoadResource(filename.c_str(),Loading::LoadShaderC, Loading::UnloadShaderC, -1, ForceReload);
if(!CSMap.count(name) || ForceReload) if(!CSMap.count(name) || ForceReload)
{ {
if(data!=0) if(data!=0)

View File

@ -14,12 +14,6 @@ namespace Oyster
Oyster::Math::Float3 normal; Oyster::Math::Float3 normal;
}; };
struct VP
{
Oyster::Math::Matrix V;
Oyster::Math::Matrix P;
};
struct PerModel struct PerModel
{ {
Math::Matrix WV; Math::Matrix WV;
@ -55,6 +49,13 @@ namespace Oyster
float Bright; float Bright;
}; };
struct AnimationData
{
Math::Float4x4 animatedData[100];
int Animated;
Math::Float3 Pad;
};
} }
} }
} }

View File

@ -4,7 +4,8 @@
#include "../Render/Resources/Deffered.h" #include "../Render/Resources/Deffered.h"
#include "../Render/Rendering/Render.h" #include "../Render/Rendering/Render.h"
#include "../FileLoader/ObjReader.h" #include "../FileLoader/ObjReader.h"
#include "../../Misc/Resource/OysterResource.h" //#include "../../Misc/Resource/OysterResource.h"
#include "../../Misc/Resource/ResourceManager.h"
#include "../FileLoader/GeneralLoader.h" #include "../FileLoader/GeneralLoader.h"
#include "../Model/ModelInfo.h" #include "../Model/ModelInfo.h"
#include <vld.h> #include <vld.h>
@ -73,6 +74,8 @@ namespace Oyster
API::State API::SetOptions(API::Option option) API::State API::SetOptions(API::Option option)
{ {
Core::modelPath = option.modelPath;
Core::texturePath = option.texturePath;
return API::Sucsess; return API::Sucsess;
} }
@ -82,8 +85,8 @@ namespace Oyster
Model::Model* m = new Model::Model(); Model::Model* m = new Model::Model();
m->WorldMatrix = Oyster::Math::Float4x4::identity; m->WorldMatrix = Oyster::Math::Float4x4::identity;
m->Visible = true; m->Visible = true;
m->AnimationPlaying = -1;
m->info = Oyster::Resource::OysterResource::LoadResource(filename.c_str(),Oyster::Graphics::Loading::LoadDAN); m->info = (Model::ModelInfo*)Core::loader.LoadResource((Core::modelPath + filename).c_str(),Oyster::Graphics::Loading::LoadDAN, Oyster::Graphics::Loading::UnloadDAN);
Model::ModelInfo* mi = (Model::ModelInfo*)m->info; Model::ModelInfo* mi = (Model::ModelInfo*)m->info;
if(!mi || mi->Vertices->GetBufferPointer() == NULL) if(!mi || mi->Vertices->GetBufferPointer() == NULL)
@ -101,13 +104,13 @@ namespace Oyster
return; return;
Model::ModelInfo* info = (Model::ModelInfo*)model->info; Model::ModelInfo* info = (Model::ModelInfo*)model->info;
delete model; delete model;
Oyster::Resource::OysterResource::ReleaseResource((Oyster::Resource::OHRESOURCE)info); Core::loader.ReleaseResource(info);
} }
void API::Clean() void API::Clean()
{ {
SAFE_DELETE(Core::viewPort); SAFE_DELETE(Core::viewPort);
Oyster::Resource::OysterResource::Clean(); Core::loader.Clean();
Oyster::Graphics::Core::PipelineManager::Clean(); Oyster::Graphics::Core::PipelineManager::Clean();
Oyster::Graphics::Render::Resources::Deffered::Clean(); Oyster::Graphics::Render::Resources::Deffered::Clean();

View File

@ -26,6 +26,7 @@ namespace Oyster
}; };
struct Option struct Option
{ {
std::wstring modelPath, texturePath;
}; };
static State Init(HWND Window, bool MSAA_Quality, bool Fullscreen, Oyster::Math::Float2 StartResulotion); static State Init(HWND Window, bool MSAA_Quality, bool Fullscreen, Oyster::Math::Float2 StartResulotion);

View File

@ -102,211 +102,320 @@ struct MaterialHeader
/// ///
struct SkeletonHeader struct SkeletonHeader
{ {
// do this... unsigned int numBones;
///
SkeletonHeader(char* data)
{
memcpy(&numBones, data, sizeof(unsigned int));
}
}; };
/// ///
struct AnimationHeader struct AnimationHeader
{ {
// do this... unsigned int numAnims;
};
struct Frame
{ AnimationHeader(char* data)
// do this... {
memcpy(&numAnims, data, sizeof(unsigned int));
}
}; };
/// ///
void Oyster::Graphics::Loading::UnloadDAN(void* data) void Oyster::Graphics::Loading::UnloadDAN(void* data)
{
Model::ModelInfo* info = (Model::ModelInfo*) data;
SAFE_DELETE(info->Vertices);
if(info->Indexed)
{
SAFE_DELETE(info->Indecies);
}
for(int i =0;i<info->Material.size();++i)
{
Oyster::Resource::OysterResource::ReleaseResource(info->Material[i]);
}
delete info;
}
static std::wstring charToWChar(const char* text)
{ {
// Convert to a wchar_t* Model::ModelInfo* info = (Model::ModelInfo*) data;
size_t origsize = strlen(text) + 1; SAFE_DELETE(info->Vertices);
size_t convertedChars = 0; if(info->Indexed)
//wchar_t* wcstring = new wchar_t[origsize]; {
std::wstring wcstring; wcstring.resize(origsize); SAFE_DELETE(info->Indecies);
mbstowcs_s(&convertedChars, &wcstring[0], origsize, text, _TRUNCATE); }
if(info->Animated)
{
//clean animation
delete[] info->bones;
for(int a = 0; a < info->AnimationCount; ++a)
{
for(int x = 0; x < info->Animations[a].Bones; ++x)
{
delete[] info->Animations[a].Keyframes[x];
}
delete[] info->Animations[a].Frames;
delete[] info->Animations[a].Keyframes;
}
delete[] info->Animations;
}
for(int i =0;i<info->Material.size();++i)
{
Core::loader.ReleaseResource(info->Material[i]);
}
delete info;
}
static wchar_t* charToWChar(const char* text)
{
// Convert to a wchar_t*
size_t origsize = strlen(text) + 1;
size_t convertedChars = 0;
wchar_t* wcstring = new wchar_t[origsize];
mbstowcs_s(&convertedChars, wcstring, origsize, text, _TRUNCATE);
return wcstring; return wcstring;
} }
/// static void ReadData(void* Destination, std::ifstream& file, int size)
void Oyster::Graphics::Loading::LoadDAN(const wchar_t filename[], Oyster::Resource::CustomData& out) {
{ char* buffer = new char[size];
// file.read(buffer,size);
Oyster::Graphics::Model::ModelInfo* modelInfo = new Oyster::Graphics::Model::ModelInfo(); memcpy(Destination,buffer,size);
modelInfo->Indexed = false; delete[] buffer;
// Open file in binary mode }
///
void* Oyster::Graphics::Loading::LoadDAN(const wchar_t filename[])
{
//
Oyster::Graphics::Model::ModelInfo* modelInfo = new Oyster::Graphics::Model::ModelInfo();
modelInfo->Indexed = false;
modelInfo->Animated = false;
// Open file in binary mode
std::ifstream danFile; std::ifstream danFile;
danFile.open(filename, std::ios::binary); danFile.open(filename, std::ios::binary);
if (!danFile.is_open()) if (!danFile.is_open())
return; return NULL;
// Read file header
char* buffer = new char[sizeof(FileHeader)];
danFile.read(buffer, sizeof(FileHeader));
FileHeader fileHeader(buffer);
delete[] buffer; // ( note: may crash here.)
// If problem with compatability then close file and return from method
if (fileHeader.versionMajor != DANFILEVERSIONMAJOR)
{
danFile.close();
return;
}
// Read the .dan-file
while (!danFile.eof())
{
// read header type
unsigned int headerType;
buffer = new char[4];
danFile.read(buffer, 4);
memcpy(&headerType, buffer, 4);
delete[] buffer; // ( note: may crash here.)
// handle header type
switch ((HeaderType)headerType)
{
// vertex header
case HeaderType::VERTEXHEADER:
{
// Fetch vertex header, number of vertices
buffer = new char[4];
danFile.read(buffer, 4);
VertexHeader vertexHeader(buffer);
delete[] buffer; // ( note: may crash here.)
// Fetch all vertices
Vertex* vertices = new Vertex[vertexHeader.numVertices];
unsigned int bufferSize = VERTEXSIZE * vertexHeader.numVertices;
buffer = new char[bufferSize];
danFile.read(buffer, bufferSize);
memcpy(vertices, buffer, bufferSize);
delete[] buffer; // ( note: may crash here.)
// Do the deed
Oyster::Graphics::Core::Buffer* vertexBuffer = new Oyster::Graphics::Core::Buffer();
Oyster::Graphics::Core::Buffer::BUFFER_INIT_DESC bufferInitDesc;
bufferInitDesc.ElementSize = sizeof(Vertex);
bufferInitDesc.InitData = vertices;
bufferInitDesc.NumElements = vertexHeader.numVertices;
bufferInitDesc.Type = Oyster::Graphics::Core::Buffer::BUFFER_TYPE::VERTEX_BUFFER;
bufferInitDesc.Usage = Oyster::Graphics::Core::Buffer::BUFFER_USAGE::BUFFER_DEFAULT;
vertexBuffer->Init(bufferInitDesc);
modelInfo->VertexCount = vertexHeader.numVertices;
modelInfo->Vertices = vertexBuffer;
delete[] vertices; // ( note: may crash here.)
break;
}
case HeaderType::INDEXHEADER:
{
// Fetch vertex header, number of vertices
buffer = new char[4];
danFile.read(buffer, 4);
IndexHeader indexHeader(buffer);
delete[] buffer; // ( note: may crash here.)
// Fetch all indices
unsigned int* indices = new unsigned int[indexHeader.numIndices];
unsigned int bufferSize = sizeof(unsigned int) * indexHeader.numIndices;
buffer = new char[bufferSize];
danFile.read(buffer, bufferSize);
memcpy(indices, buffer, bufferSize);
delete[] buffer; // ( note: may crash here.)
// Do the deed
Oyster::Graphics::Core::Buffer* indexBuffer = new Oyster::Graphics::Core::Buffer();
Oyster::Graphics::Core::Buffer::BUFFER_INIT_DESC bufferInitDesc;
bufferInitDesc.ElementSize = sizeof(unsigned int);
bufferInitDesc.InitData = indices;
bufferInitDesc.NumElements = indexHeader.numIndices;
bufferInitDesc.Type = Oyster::Graphics::Core::Buffer::BUFFER_TYPE::INDEX_BUFFER;
bufferInitDesc.Usage = Oyster::Graphics::Core::Buffer::BUFFER_USAGE::BUFFER_DEFAULT;
indexBuffer->Init(bufferInitDesc);
modelInfo->IndexCount = indexHeader.numIndices;
modelInfo->Indecies = indexBuffer;
modelInfo->Indexed = true;
delete[] indices; // ( note: may crash here.)
break;
}
// material header
case HeaderType::MATERIALHEADER:
{
// Fetch material header, 2 texture path strings
MaterialHeader materialHeader;
buffer = new char[4];
danFile.read(buffer, 4);
memcpy(&materialHeader.diffuseMapPathLength, buffer, 4);
delete[] buffer; // ( note: may crash here.)
buffer = new char[materialHeader.diffuseMapPathLength]; // Read file header
danFile.read(buffer, materialHeader.diffuseMapPathLength); char* buffer = new char[sizeof(FileHeader)];
danFile.read(buffer, sizeof(FileHeader));
FileHeader fileHeader(buffer);
delete[] buffer; // ( note: may crash here.)
// If problem with compatability then close file and return from method
if (fileHeader.versionMajor != DANFILEVERSIONMAJOR)
{
danFile.close();
return NULL;
}
// Read the .dan-file
while (!danFile.eof())
{
// read header type
unsigned int headerType;
ReadData(&headerType,danFile,4);
// handle header type
switch ((HeaderType)headerType)
{
// vertex header
case HeaderType::VERTEXHEADER:
{
// Fetch vertex header, number of vertices
buffer = new char[4];
danFile.read(buffer, 4);
VertexHeader vertexHeader(buffer);
delete[] buffer; // ( note: may crash here.)
// Fetch all vertices
unsigned int bufferSize = VERTEXSIZE * vertexHeader.numVertices;
buffer = new char[bufferSize];
danFile.read(buffer, bufferSize);
// Do the deed
Oyster::Graphics::Core::Buffer* vertexBuffer = new Oyster::Graphics::Core::Buffer();
Oyster::Graphics::Core::Buffer::BUFFER_INIT_DESC bufferInitDesc;
bufferInitDesc.ElementSize = sizeof(Vertex);
bufferInitDesc.InitData = buffer;
bufferInitDesc.NumElements = vertexHeader.numVertices;
bufferInitDesc.Type = Oyster::Graphics::Core::Buffer::BUFFER_TYPE::VERTEX_BUFFER;
bufferInitDesc.Usage = Oyster::Graphics::Core::Buffer::BUFFER_USAGE::BUFFER_DEFAULT;
vertexBuffer->Init(bufferInitDesc);
modelInfo->VertexCount = vertexHeader.numVertices;
modelInfo->Vertices = vertexBuffer;
delete[] buffer; // ( note: may crash here.)
break;
}
case HeaderType::INDEXHEADER:
{
// Fetch vertex header, number of vertices
buffer = new char[4];
danFile.read(buffer, 4);
IndexHeader indexHeader(buffer);
delete[] buffer; // ( note: may crash here.)
// Fetch all indices
unsigned int* indices = new unsigned int[indexHeader.numIndices];
unsigned int bufferSize = sizeof(unsigned int) * indexHeader.numIndices;
ReadData(indices,danFile,bufferSize);
// Do the deed
Oyster::Graphics::Core::Buffer* indexBuffer = new Oyster::Graphics::Core::Buffer();
Oyster::Graphics::Core::Buffer::BUFFER_INIT_DESC bufferInitDesc;
bufferInitDesc.ElementSize = sizeof(unsigned int);
bufferInitDesc.InitData = indices;
bufferInitDesc.NumElements = indexHeader.numIndices;
bufferInitDesc.Type = Oyster::Graphics::Core::Buffer::BUFFER_TYPE::INDEX_BUFFER;
bufferInitDesc.Usage = Oyster::Graphics::Core::Buffer::BUFFER_USAGE::BUFFER_DEFAULT;
indexBuffer->Init(bufferInitDesc);
modelInfo->IndexCount = indexHeader.numIndices;
modelInfo->Indecies = indexBuffer;
modelInfo->Indexed = true;
delete[] indices; // ( note: may crash here.)
break;
}
// material header
case HeaderType::MATERIALHEADER:
{
// Fetch material header, 2 texture path strings
MaterialHeader materialHeader;
//read difuse map name length
ReadData(&materialHeader.diffuseMapPathLength,danFile,4);
//read diffuse map name
materialHeader.diffuseMapPath = new char[materialHeader.diffuseMapPathLength+1]; materialHeader.diffuseMapPath = new char[materialHeader.diffuseMapPathLength+1];
memcpy(materialHeader.diffuseMapPath, buffer, materialHeader.diffuseMapPathLength); ReadData(materialHeader.diffuseMapPath,danFile,materialHeader.diffuseMapPathLength);
materialHeader.diffuseMapPath[materialHeader.diffuseMapPathLength] = 0; //null terminate
delete[] buffer; // ( note: may crash here.) materialHeader.diffuseMapPath[materialHeader.diffuseMapPathLength] = 0;
buffer = new char[4]; //read normal map name length
danFile.read(buffer, 4); ReadData(&materialHeader.normalMapPathLength,danFile,4);
memcpy(&materialHeader.normalMapPathLength, buffer, 4);
delete[] buffer; // ( note: may crash here.)
buffer = new char[materialHeader.normalMapPathLength]; //read difuse map name
danFile.read(buffer, materialHeader.normalMapPathLength);
materialHeader.normalMapPath = new char[materialHeader.normalMapPathLength + 1]; materialHeader.normalMapPath = new char[materialHeader.normalMapPathLength + 1];
memcpy(materialHeader.normalMapPath, buffer, materialHeader.normalMapPathLength); ReadData(materialHeader.normalMapPath,danFile,materialHeader.normalMapPathLength);
materialHeader.normalMapPath[materialHeader.normalMapPathLength] = 0; materialHeader.normalMapPath[materialHeader.normalMapPathLength] = 0;
delete[] buffer; // ( note: may crash here.)
//load diffuse map
// wchar_t* path = charToWChar(materialHeader.diffuseMapPath);
ID3D11ShaderResourceView* diffuseMap = (ID3D11ShaderResourceView*)Oyster::Resource::OysterResource::LoadResource(charToWChar(materialHeader.diffuseMapPath).c_str(), Oyster::Graphics::Loading::LoadTexture); ID3D11ShaderResourceView* diffuseMap = (ID3D11ShaderResourceView*)Core::loader.LoadResource((Core::texturePath + path).c_str(), Oyster::Graphics::Loading::LoadTexture, Oyster::Graphics::Loading::UnloadTexture);
ID3D11ShaderResourceView* normalMap = (ID3D11ShaderResourceView*)Oyster::Resource::OysterResource::LoadResource(charToWChar(materialHeader.normalMapPath).c_str(), Oyster::Graphics::Loading::LoadTexture); delete[] path;
modelInfo->Material.push_back(diffuseMap);
modelInfo->Material.push_back(normalMap); //load normal map
path = charToWChar(materialHeader.normalMapPath);
delete materialHeader.normalMapPath; ID3D11ShaderResourceView* normalMap = (ID3D11ShaderResourceView*)Core::loader.LoadResource((Core::texturePath + path).c_str(), Oyster::Graphics::Loading::LoadTexture, Oyster::Graphics::Loading::UnloadTexture);
delete materialHeader.diffuseMapPath; delete[] path;
break; //add to model
} modelInfo->Material.push_back(diffuseMap);
// skeleton header modelInfo->Material.push_back(normalMap);
case HeaderType::SKELETONHEADER:
{ //clean up
// not implemented... delete[] materialHeader.diffuseMapPath;
break; delete[] materialHeader.normalMapPath;
}
// animation header break;
case HeaderType::ANIMATIONHEADER: }
{
// not implemented... // skeleton header
break; case HeaderType::SKELETONHEADER:
} {
} // Fetch Skeleton header, number of Bones
} buffer = new char[4];
danFile.read(buffer, 4);
SkeletonHeader skeletonHeader(buffer);
// close file delete[] buffer; // ( note: may crash here.)
danFile.close();
//array for bone data
// Set modelinfo as output data Oyster::Graphics::Model::Bone* bones = new Oyster::Graphics::Model::Bone[skeletonHeader.numBones];
out.loadedData = modelInfo;
out.resourceUnloadFnc = Oyster::Graphics::Loading::UnloadDAN; //read bones
ReadData(bones,danFile,skeletonHeader.numBones * sizeof(Oyster::Graphics::Model::Bone));
//read skeleton Hiarchy
modelInfo->BoneCount = skeletonHeader.numBones;
modelInfo->bones = bones;
break;
}
// animation header
case HeaderType::ANIMATIONHEADER:
{
//get num anims
buffer = new char[4];
danFile.read(buffer, 4);
AnimationHeader animationHeader(buffer);
delete[] buffer;
Oyster::Graphics::Model::Animation* anims = new Oyster::Graphics::Model::Animation[animationHeader.numAnims];
for(int a = 0; a < animationHeader.numAnims; ++a)
{
//read name of animation
int nameLength;
ReadData(&nameLength,danFile,4);
char* name = new char[nameLength + 1];
ReadData(name,danFile,nameLength);
name[nameLength] = 0;
wchar_t* wName = charToWChar(name);
anims[a].name = std::wstring(wName);
delete[] wName;
delete name;
//read nr of bones in animation
ReadData(&anims[a].Bones,danFile,4);
//read duration
ReadData(&anims[a].duration,danFile,8);
//create Frame array and Bone part of KeyFrameArray;
anims[a].Frames = new int[anims[a].Bones];
anims[a].Keyframes = new Oyster::Graphics::Model::Frame*[anims[a].Bones];
//loop per bone and gather data
for(int b = 0; b < anims[a].Bones; ++b)
{
//read bone index
int boneIndex;
ReadData(&boneIndex,danFile,4);
//read nr of frames per bone
ReadData(&anims[a].Frames[b],danFile,4);
//create frame matrix
anims[a].Keyframes[b] = new Oyster::Graphics::Model::Frame[anims[a].Frames[b]];
for(int f = 0; f < anims[a].Frames[b]; ++f)
{
//write index of bone
anims[a].Keyframes[b][f].bone.Parent = boneIndex;
//read bone transform
ReadData(&anims[a].Keyframes[b][f].bone.Transform,danFile,sizeof(Oyster::Math::Matrix));
ReadData(&anims[a].Keyframes[b][f].time,danFile,sizeof(double));
}
}
}
modelInfo->AnimationCount = animationHeader.numAnims;
modelInfo->Animations = anims;
modelInfo->Animated = true;
break;
}
}
}
// close file
danFile.close();
// Set modelinfo as output data
return modelInfo;
} }

View File

@ -1,5 +1,4 @@
#pragma once #pragma once
#include "..\..\Misc\Resource\OysterResource.h"
namespace Oyster namespace Oyster
{ {
namespace Graphics namespace Graphics
@ -7,31 +6,31 @@ namespace Oyster
namespace Loading namespace Loading
{ {
void UnloadTexture(void* loadedData); void UnloadTexture(void* loadedData);
void LoadTexture(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadTexture(const wchar_t filename[]);
void UnloadShaderP(void* loadedData); void UnloadShaderP(void* loadedData);
void LoadShaderP(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadShaderP(const wchar_t filename[]);
void UnloadShaderG(void* loadedData); void UnloadShaderG(void* loadedData);
void LoadShaderG(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadShaderG(const wchar_t filename[]);
void UnloadShaderC(void* loadedData); void UnloadShaderC(void* loadedData);
void LoadShaderC(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadShaderC(const wchar_t filename[]);
void UnloadShaderV(void* loadedData); void UnloadShaderV(void* loadedData);
void LoadShaderV(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadShaderV(const wchar_t filename[]);
void UnloadShaderH(void* loadedData); void UnloadShaderH(void* loadedData);
void LoadShaderH(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadShaderH(const wchar_t filename[]);
void UnloadShaderD(void* loadedData); void UnloadShaderD(void* loadedData);
void LoadShaderD(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadShaderD(const wchar_t filename[]);
void UnloadOBJ(void* loadedData); void UnloadOBJ(void* loadedData);
void LoadOBJ(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadOBJ(const wchar_t filename[]);
void UnloadDAN(void* loadedData); void UnloadDAN(void* loadedData);
void LoadDAN(const wchar_t filename[], Oyster::Resource::CustomData& out); void* LoadDAN(const wchar_t filename[]);
} }
} }
} }

View File

@ -2,7 +2,6 @@
#include "..\Core\Dx11Includes.h" #include "..\Core\Dx11Includes.h"
#include "..\Core\Core.h" #include "..\Core\Core.h"
#include "ObjReader.h" #include "ObjReader.h"
#include "..\..\Misc\Resource\OysterResource.h"
HRESULT CreateWICTextureFromFileEx( ID3D11Device* d3dDevice, HRESULT CreateWICTextureFromFileEx( ID3D11Device* d3dDevice,
ID3D11DeviceContext* d3dContext, ID3D11DeviceContext* d3dContext,
@ -16,18 +15,17 @@ HRESULT CreateWICTextureFromFileEx( ID3D11Device* d3dDevice,
ID3D11Resource** texture, ID3D11Resource** texture,
ID3D11ShaderResourceView** textureView ); ID3D11ShaderResourceView** textureView );
void Oyster::Graphics::Loading::LoadTexture(const wchar_t filename[], Oyster::Resource::CustomData& out) void* Oyster::Graphics::Loading::LoadTexture(const wchar_t filename[])
{ {
ID3D11ShaderResourceView* srv = NULL; ID3D11ShaderResourceView* srv = NULL;
HRESULT hr = CreateWICTextureFromFileEx(Core::device,Core::deviceContext,filename,0,D3D11_USAGE_DEFAULT,D3D11_BIND_SHADER_RESOURCE,0,0,false,NULL,&srv); HRESULT hr = CreateWICTextureFromFileEx(Core::device,Core::deviceContext,filename,0,D3D11_USAGE_DEFAULT,D3D11_BIND_SHADER_RESOURCE,0,0,false,NULL,&srv);
if(hr!=S_OK) if(hr!=S_OK)
{ {
memset(&out,0,sizeof(out)); return NULL;
} }
else else
{ {
out.loadedData = (void*)srv; return srv;
out.resourceUnloadFnc = Loading::UnloadTexture;
} }
} }
@ -37,7 +35,7 @@ void Oyster::Graphics::Loading::UnloadTexture(void* data)
SAFE_RELEASE(srv); SAFE_RELEASE(srv);
} }
void Oyster::Graphics::Loading::LoadOBJ(const wchar_t filename[], Oyster::Resource::CustomData& out) void* Oyster::Graphics::Loading::LoadOBJ(const wchar_t filename[])
{ {
FileLoaders::ObjReader obj; FileLoaders::ObjReader obj;
obj.LoadFile(filename); obj.LoadFile(filename);
@ -57,12 +55,11 @@ void Oyster::Graphics::Loading::LoadOBJ(const wchar_t filename[], Oyster::Resour
info->Vertices->Init(desc); info->Vertices->Init(desc);
info->Indexed = false; info->Indexed = false;
void* texture = Oyster::Resource::OysterResource::LoadResource((std::wstring(filename)+ L".png").c_str(),Graphics::Loading::LoadTexture); void* texture = Core::loader.LoadResource((std::wstring(filename)+ L".png").c_str(),Graphics::Loading::LoadTexture, Graphics::Loading::UnloadTexture);
info->Material.push_back((ID3D11ShaderResourceView*)texture); info->Material.push_back((ID3D11ShaderResourceView*)texture);
out.loadedData = info; return info;
out.resourceUnloadFnc = Oyster::Graphics::Loading::UnloadOBJ;
} }
void Oyster::Graphics::Loading::UnloadOBJ(void* data) void Oyster::Graphics::Loading::UnloadOBJ(void* data)
@ -75,7 +72,7 @@ void Oyster::Graphics::Loading::UnloadOBJ(void* data)
} }
for(int i =0;i<info->Material.size();++i) for(int i =0;i<info->Material.size();++i)
{ {
Oyster::Resource::OysterResource::ReleaseResource(info->Material[i]); Core::loader.ReleaseResource(info->Material[i]);
} }
delete info; delete info;
} }

View File

@ -10,7 +10,7 @@ namespace Oyster
{ {
namespace Loading namespace Loading
{ {
void LoadShader(const wchar_t filename[], Oyster::Resource::CustomData& out, int type); void* LoadShader(const wchar_t filename[], int type);
void UnloadShaderP(void* loadedData) void UnloadShaderP(void* loadedData)
{ {
@ -48,78 +48,41 @@ namespace Oyster
SAFE_RELEASE(ps); SAFE_RELEASE(ps);
} }
void LoadShaderP(const wchar_t filename[], Oyster::Resource::CustomData& out) void* LoadShaderP(const wchar_t filename[])
{ {
LoadShader(filename,out,Core::PipelineManager::Pixel); return LoadShader(filename,Core::PipelineManager::Pixel);
if(out.loadedData==NULL)
{
memset(&out,0,sizeof(out));
return;
}
out.resourceUnloadFnc = UnloadShaderP;
} }
void LoadShaderG(const wchar_t filename[], Oyster::Resource::CustomData& out) void* LoadShaderG(const wchar_t filename[])
{ {
LoadShader(filename,out,Core::PipelineManager::Geometry); return LoadShader(filename,Core::PipelineManager::Geometry);
if(out.loadedData==NULL)
{
memset(&out,0,sizeof(out));
return;
}
out.resourceUnloadFnc = UnloadShaderG;
} }
void LoadShaderC(const wchar_t filename[], Oyster::Resource::CustomData& out) void* LoadShaderC(const wchar_t filename[])
{ {
LoadShader(filename,out,Core::PipelineManager::Compute); return LoadShader(filename,Core::PipelineManager::Compute);
if(out.loadedData==NULL)
{
memset(&out,0,sizeof(out));
return;
}
out.resourceUnloadFnc = UnloadShaderC;
} }
void LoadShaderH(const wchar_t filename[], Oyster::Resource::CustomData& out) void* LoadShaderH(const wchar_t filename[])
{ {
LoadShader(filename,out,Core::PipelineManager::Hull); return LoadShader(filename,Core::PipelineManager::Hull);
if(out.loadedData==NULL)
{
memset(&out,0,sizeof(out));
return;
}
out.resourceUnloadFnc = UnloadShaderH;
} }
void LoadShaderD(const wchar_t filename[], Oyster::Resource::CustomData& out) void* LoadShaderD(const wchar_t filename[])
{ {
LoadShader(filename,out,Core::PipelineManager::Domain); return LoadShader(filename,Core::PipelineManager::Domain);
if(out.loadedData==NULL)
{
memset(&out,0,sizeof(out));
return;
}
out.resourceUnloadFnc = UnloadShaderD;
} }
void LoadShaderV(const wchar_t filename[], Oyster::Resource::CustomData& out) void* LoadShaderV(const wchar_t filename[])
{ {
return LoadShader(filename,Core::PipelineManager::Vertex);
LoadShader(filename,out,Core::PipelineManager::Vertex);
if(out.loadedData==NULL)
{
memset(&out,0,sizeof(out));
return;
}
out.resourceUnloadFnc = UnloadShaderV;
} }
void LoadShader(const wchar_t filename[], Oyster::Resource::CustomData& out, int type) void* LoadShader(const wchar_t filename[], int type)
{ {
Core::PipelineManager::ShaderData data; Core::PipelineManager::ShaderData data;
#ifdef _DEBUG #ifdef _DEBUG
@ -159,8 +122,7 @@ namespace Oyster
{ {
Shader->Release(); Shader->Release();
} }
memset(&out,0,sizeof(out)); return NULL;
return;
} }
data.size = Shader->GetBufferSize(); data.size = Shader->GetBufferSize();
@ -181,11 +143,10 @@ namespace Oyster
} }
else else
{ {
memset(&out,0,sizeof(out)); return NULL;
return;
} }
#endif #endif
out.loadedData = Core::PipelineManager::CreateShader(data, Core::PipelineManager::ShaderType(type)); return Core::PipelineManager::CreateShader(data, Core::PipelineManager::ShaderType(type));
} }
} }
} }

View File

@ -9,14 +9,14 @@ namespace Oyster
{ {
namespace Model namespace Model
{ {
//struct ModelInfo; struct ModelInfo;
struct Model struct Model
{ {
//! do not Edit, linked to render data ModelInfo* info;
//ModelInfo* info;
void* info;
Oyster::Math::Float4x4 WorldMatrix; Oyster::Math::Float4x4 WorldMatrix;
bool Visible; bool Visible, LoopAnimation;
int AnimationPlaying;
float AnimationTime;
}; };
} }

View File

@ -11,12 +11,32 @@ namespace Oyster
{ {
namespace Model namespace Model
{ {
struct Bone
{
Math::Float4x4 Transform;
int Parent;
};
struct Frame
{
Bone bone;
double time;
};
struct Animation
{
std::wstring name;
int Bones;
int* Frames; //! Bone as index
Frame** Keyframes; //! @brief [Bone][Frame]
double duration;
};
struct ModelInfo struct ModelInfo
{ {
std::vector<ID3D11ShaderResourceView*> Material; std::vector<ID3D11ShaderResourceView*> Material;
Core::Buffer *Vertices,*Indecies; Core::Buffer *Vertices,*Indecies;
bool Indexed; bool Indexed, Animated;
int VertexCount, IndexCount; int VertexCount, IndexCount, BoneCount, AnimationCount;
Bone* bones;
Animation* Animations;
}; };
} }
} }

View File

@ -18,16 +18,10 @@ namespace Oyster
void Basic::NewFrame(Oyster::Math::Float4x4 View, Oyster::Math::Float4x4 Projection, Definitions::Pointlight* Lights, int numLights) void Basic::NewFrame(Oyster::Math::Float4x4 View, Oyster::Math::Float4x4 Projection, Definitions::Pointlight* Lights, int numLights)
{ {
Preparations::Basic::ClearBackBuffer(Oyster::Math::Float4(1,0,0,1)); Preparations::Basic::ClearBackBuffer(Oyster::Math::Float4(1,0,0,1));
Preparations::Basic::ClearRTV(Resources::Deffered::GBufferRTV,Resources::Deffered::GBufferSize,Math::Float4(1,0,0,1)); Preparations::Basic::ClearRTV(Resources::Deffered::GBufferRTV,Resources::Deffered::GBufferSize,Math::Float4(0,0,0,1));
Core::PipelineManager::SetRenderPass(Graphics::Render::Resources::Deffered::GeometryPass); Core::PipelineManager::SetRenderPass(Graphics::Render::Resources::Deffered::GeometryPass);
Definitions::VP vp; void* data;
vp.V = View;
vp.P = Projection;
void* data = Resources::Deffered::VPData.Map();
memcpy(data, &vp, sizeof(Definitions::VP));
Resources::Deffered::VPData.Unmap();
Definitions::LightConstants lc; Definitions::LightConstants lc;
lc.InvProj = Projection.GetInverse(); lc.InvProj = Projection.GetInverse();
@ -61,10 +55,79 @@ namespace Oyster
void* data = Resources::Deffered::ModelData.Map(); void* data = Resources::Deffered::ModelData.Map();
memcpy(data,&(pm),sizeof(pm)); memcpy(data,&(pm),sizeof(pm));
Resources::Deffered::ModelData.Unmap(); Resources::Deffered::ModelData.Unmap();
Model::ModelInfo* info = (Model::ModelInfo*)models[i].info; Model::ModelInfo* info = (Model::ModelInfo*)models[i].info;
Definitions::AnimationData am;
if(info->Animated && models[i].AnimationPlaying != -1)
{
Definitions::AnimationData am2;
//write default data
for (int b = 0; b < info->BoneCount; b++)
{
am2.animatedData[b] = info->bones[b].Transform;
}
//loop bones in animation
am.Animated = 1;
Model::Frame Prev, Next;
models[i].AnimationTime = fmod(models[i].AnimationTime,info->Animations[models[i].AnimationPlaying].duration);
for(int x = 0; x < info->Animations[models[i].AnimationPlaying].Bones; ++x)
{
//loop frame per bone
Prev.bone.Parent = 0;
Next = Prev;
for(int y = 0; y < info->Animations[models[i].AnimationPlaying].Frames[x]; ++y)
{
///TODO replace with binary search?
Model::Frame f = info->Animations[models[i].AnimationPlaying].Keyframes[x][y];
//if we hit frame
if(models[i].AnimationTime == f.time)
{
Prev = f;
Next = f;
break;
}
//if time is larger than frame time, store frames
if(models[i].AnimationTime < f.time)
{
Next = f;
Prev = info->Animations[models[i].AnimationPlaying].Keyframes[x][y-1];
break;
}
}
//calculate interpolated bone position
//rebase model time to between prev and next
float interpoation =(models[i].AnimationTime - Prev.time) / (Next.time - Prev.time);
//interpolate
Math::Matrix Interpolated;
Math3D::InterpolateOrientation_UsingNonRigidNlerp(Prev.bone.Transform,Next.bone.Transform,interpoation, Interpolated);
//write magic to animated data
am2.animatedData[Prev.bone.Parent] = Interpolated * am2.animatedData[info->bones[Prev.bone.Parent].Parent];
//sneaky write do correct data buffer
am.animatedData[x] = (am2.animatedData[Prev.bone.Parent] * info->bones[Prev.bone.Parent].Transform.GetInverse());
}
}
else
am.Animated = 0;
data = Resources::Deffered::AnimationData.Map();
memcpy(data,&am,sizeof(Definitions::AnimationData));
Resources::Deffered::AnimationData.Unmap();
if(info->Material.size()) if(info->Material.size())
{ {
Core::deviceContext->PSSetShaderResources(0,(UINT)info->Material.size(),&(info->Material[0])); Core::deviceContext->PSSetShaderResources(0,(UINT)info->Material.size(),&(info->Material[0]));
@ -84,6 +147,8 @@ namespace Oyster
} }
} }
} }
void Basic::EndFrame() void Basic::EndFrame()
{ {
Core::PipelineManager::SetRenderPass(Resources::Deffered::LightPass); Core::PipelineManager::SetRenderPass(Resources::Deffered::LightPass);

View File

@ -12,7 +12,7 @@ const std::wstring PathToHLSL = L"..\\..\\Code\\OysterGraphics\\Shader\\HLSL\\De
const std::wstring PathToCSO = L"..\\Content\\Shaders\\"; const std::wstring PathToCSO = L"..\\Content\\Shaders\\";
const int KernelSize = 10; const int KernelSize = 10;
const int SampleSpread = 8; const int SampleSpread = 16;
namespace Oyster namespace Oyster
{ {
@ -34,7 +34,7 @@ namespace Oyster
Shader::RenderPass Deffered::PostPass; Shader::RenderPass Deffered::PostPass;
Buffer Deffered::ModelData = Buffer(); Buffer Deffered::ModelData = Buffer();
Buffer Deffered::VPData = Buffer(); Buffer Deffered::AnimationData = Buffer();
Buffer Deffered::LightConstantsData = Buffer(); Buffer Deffered::LightConstantsData = Buffer();
Buffer Deffered::PointLightsData = Buffer(); Buffer Deffered::PointLightsData = Buffer();
@ -74,8 +74,9 @@ namespace Oyster
ModelData.Init(desc); ModelData.Init(desc);
desc.NumElements = 2; desc.NumElements = 1;
VPData.Init(desc); desc.ElementSize = sizeof(Definitions::AnimationData);
AnimationData.Init(desc);
desc.ElementSize = sizeof(Definitions::LightConstants); desc.ElementSize = sizeof(Definitions::LightConstants);
desc.NumElements = 1; desc.NumElements = 1;
@ -156,6 +157,7 @@ namespace Oyster
Core::Init::CreateLinkedShaderResourceFromStructuredBuffer(&b,&PointLightView,NULL); Core::Init::CreateLinkedShaderResourceFromStructuredBuffer(&b,&PointLightView,NULL);
srand((unsigned int)time(0)); srand((unsigned int)time(0));
//SSAO //SSAO
Math::Vector3 kernel[KernelSize]; Math::Vector3 kernel[KernelSize];
Math::Vector3 random[SampleSpread]; Math::Vector3 random[SampleSpread];
@ -186,13 +188,12 @@ namespace Oyster
{ {
random[i] = Oyster::Math::Vector3( random[i] = Oyster::Math::Vector3(
(float)rand() / (RAND_MAX + 1) * (1 - -1)+ -1, (float)rand() / (RAND_MAX + 1) * (1 - -1)+ -1,
(float)rand() / (RAND_MAX + 1) * (1 - -1)+ -1, /*(float)rand() / (RAND_MAX + 1) * (1 - -1)+ -1,*/
1.0f,
0.0f); 0.0f);
} }
random[i].Normalize(); random[i].Normalize();
} }
//kernel[0] = Math::Vector3(0,1,1);
//kernel[0].Normalize();
D3D11_TEXTURE1D_DESC T1desc; D3D11_TEXTURE1D_DESC T1desc;
T1desc.Width = KernelSize; T1desc.Width = KernelSize;
@ -208,17 +209,32 @@ namespace Oyster
D3D11_SUBRESOURCE_DATA rnd; D3D11_SUBRESOURCE_DATA rnd;
rnd.pSysMem = random; rnd.pSysMem = random;
rnd.SysMemPitch = sqrt(SampleSpread) * sizeof(Oyster::Math::Vector3);
ID3D11Texture1D *pTexture1[2]; ID3D11Texture1D *pTexture1;
Core::device->CreateTexture1D( &T1desc, &sphere, &pTexture1[0] ); Core::device->CreateTexture1D( &T1desc, &sphere, &pTexture1 );
Core::device->CreateShaderResourceView( pTexture1[0], 0, &SSAOKernel ); Core::device->CreateShaderResourceView( pTexture1, 0, &SSAOKernel );
pTexture1[0]->Release(); pTexture1->Release();
T1desc.Width = SampleSpread; D3D11_TEXTURE2D_DESC T2desc;
Core::device->CreateTexture1D( &T1desc, &rnd, &pTexture1[1] ); T2desc.Width = KernelSize;
Core::device->CreateShaderResourceView( (pTexture1[1]), 0, &SSAORandom ); T2desc.MipLevels = T2desc.ArraySize = 1;
pTexture1[1]->Release(); T2desc.Format = DXGI_FORMAT_R32G32B32_FLOAT;
T2desc.Usage = D3D11_USAGE_DEFAULT;
T2desc.BindFlags = D3D11_BIND_SHADER_RESOURCE;
T2desc.CPUAccessFlags = 0;
T2desc.MiscFlags = 0;
T2desc.Height = sqrt(SampleSpread);
T2desc.Width = SampleSpread/sqrt(SampleSpread);
T2desc.SampleDesc.Quality = 0;
T2desc.SampleDesc.Count = 1;
ID3D11Texture2D *pTexture2;
Core::device->CreateTexture2D( &T2desc, &rnd, &pTexture2 );
Core::device->CreateShaderResourceView( (pTexture2), 0, &SSAORandom );
pTexture2->Release();
////Create ShaderEffects ////Create ShaderEffects
@ -239,7 +255,7 @@ namespace Oyster
Shader::CreateInputLayout(indesc,7,GetShader::Vertex(L"Geometry"),GeometryPass.IAStage.Layout); Shader::CreateInputLayout(indesc,7,GetShader::Vertex(L"Geometry"),GeometryPass.IAStage.Layout);
GeometryPass.IAStage.Topology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST; GeometryPass.IAStage.Topology = D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST;
GeometryPass.CBuffers.Vertex.push_back(VPData); GeometryPass.CBuffers.Vertex.push_back(AnimationData);
GeometryPass.CBuffers.Vertex.push_back(ModelData); GeometryPass.CBuffers.Vertex.push_back(ModelData);
GeometryPass.RenderStates.Rasterizer = rs; GeometryPass.RenderStates.Rasterizer = rs;
GeometryPass.RenderStates.SampleCount = 1; GeometryPass.RenderStates.SampleCount = 1;
@ -281,7 +297,7 @@ namespace Oyster
void Deffered::Clean() void Deffered::Clean()
{ {
Resources::Deffered::ModelData.~Buffer(); Resources::Deffered::ModelData.~Buffer();
Resources::Deffered::VPData.~Buffer(); Resources::Deffered::AnimationData.~Buffer();
Resources::Deffered::LightConstantsData.~Buffer(); Resources::Deffered::LightConstantsData.~Buffer();
Resources::Deffered::PointLightsData.~Buffer(); Resources::Deffered::PointLightsData.~Buffer();
SAFE_RELEASE(Resources::Deffered::PointLightView); SAFE_RELEASE(Resources::Deffered::PointLightView);

View File

@ -18,12 +18,15 @@ namespace Oyster
static const int LBufferSize = 3; static const int LBufferSize = 3;
static const int MaxLightSize = 100; static const int MaxLightSize = 100;
//! GBuffers //! GBuffers
//! 0 = Diffuse + SpecKoeff //! 0 = Diffuse + Glow
//! 1 = Normal + Glow //! 1 = Normal + Spec
static ID3D11RenderTargetView* GBufferRTV[GBufferSize]; static ID3D11RenderTargetView* GBufferRTV[GBufferSize];
static ID3D11ShaderResourceView* GBufferSRV[GBufferSize]; static ID3D11ShaderResourceView* GBufferSRV[GBufferSize];
//! LBuffer
//! 0 = Diffuse
//! 1 = Specular
//! 2 = SSAO
static ID3D11UnorderedAccessView* LBufferUAV[LBufferSize]; static ID3D11UnorderedAccessView* LBufferUAV[LBufferSize];
static ID3D11ShaderResourceView* LBufferSRV[LBufferSize]; static ID3D11ShaderResourceView* LBufferSRV[LBufferSize];
@ -33,7 +36,7 @@ namespace Oyster
static Core::Buffer ModelData; static Core::Buffer ModelData;
static Core::Buffer VPData; static Core::Buffer AnimationData;
static Core::Buffer LightConstantsData; static Core::Buffer LightConstantsData;

View File

@ -32,10 +32,10 @@ Texture2D DepthTexture : register(t2);
StructuredBuffer<PointLight> Points : register(t3); StructuredBuffer<PointLight> Points : register(t3);
Texture1D SSAOKernel : register(t4); Texture1D SSAOKernel : register(t4);
Texture1D SSAORand : register(t5); Texture2D SSAORand : register(t5);
RWTexture2D<float4> Diffuse : register(u0); RWTexture2D<float4> Diffuse : register(u0);
RWTexture2D<float4> Specular : register(u1); RWTexture2D<float4> Specular : register(u1);
RWTexture2D<float> Ambient : register(u2); RWTexture2D<float4> Ambient : register(u2);
#endif #endif

View File

@ -30,11 +30,11 @@ Texture2D Normal : register(t1);
SamplerState S1 : register(s0); SamplerState S1 : register(s0);
cbuffer PerFrame : register(b0) cbuffer Animation : register(b0)
{ {
matrix View; float4x4 BoneAnimation[100];
float4x4 Projection; int Animated;
matrix VP; float3 Pad;
} }
cbuffer PerModel : register(b1) cbuffer PerModel : register(b1)

View File

@ -21,8 +21,8 @@ DiffSpec LightCalc(PointLight pl, float3 pos, int2 texCoord)
output.Specular * 0; output.Specular * 0;
if(d > pl.Radius) if(d > pl.Radius)
{ {
output.Diffuse = float4(0,0,0,1); output.Diffuse = float3(0,0,0);
output.Specular = float4(0,0,0,1); output.Specular = float3(0,0,0);
} }
return output; return output;
} }

View File

@ -12,13 +12,13 @@
[numthreads(16, 16, 1)] [numthreads(16, 16, 1)]
void main( uint3 DTid : SV_DispatchThreadID, uint3 GTid : SV_GroupThreadID ) void main( uint3 DTid : SV_DispatchThreadID, uint3 GTid : SV_GroupThreadID )
{ {
float2 UV = DTid / Pixels; float2 UV = DTid.xy / Pixels;
UV.x = UV.x * 2 - 1; UV.x = UV.x * 2 - 1;
UV.y = 1 - 2 * UV.y; UV.y = 1 - 2 * UV.y;
float3 ViewPos = ToVpos(DTid.xy, UV); float3 ViewPos = ToVpos(DTid.xy, UV);
DiffSpec Shaded; DiffSpec Shaded;
Shaded.Diffuse = float4(0,0,0,0); Shaded.Diffuse = float3(0,0,0);
Shaded.Specular = float4(0,0,0,0); Shaded.Specular = float3(0,0,0);
for(int i = 0; i < Lights; ++i) for(int i = 0; i < Lights; ++i)
{ {
@ -33,10 +33,10 @@ void main( uint3 DTid : SV_DispatchThreadID, uint3 GTid : SV_GroupThreadID )
Specular[DTid.xy] = float4(Shaded.Specular, 1); Specular[DTid.xy] = float4(Shaded.Specular, 1);
if((DTid.x + DTid.y) %4 == 0 ) if(DTid.x & 1 && DTid.y & 1 )
{ {
float AmbValue = GetSSAO(ViewPos, UV, DTid.xy, GTid.xy); float AmbValue = GetSSAO(ViewPos, UV, DTid.xy, GTid.xy/2);
Ambient[DTid.xy/4] = AmbValue; Ambient[DTid.xy/2] = AmbValue;
} }
} }

View File

@ -7,8 +7,7 @@ RWTexture2D<float4> Output;
[numthreads(16, 16, 1)] [numthreads(16, 16, 1)]
void main( uint3 DTid : SV_DispatchThreadID ) void main( uint3 DTid : SV_DispatchThreadID )
{ {
Output[DTid.xy] = Diffuse[DTid.xy] + Specular[DTid.xy] + Diffuse[DTid.xy] * Ambient[DTid.xy/4].w;// + float4(Ambient[DTid.xy/4].xyz,1); GLOW //Output[DTid.xy] = Diffuse[DTid.xy] + Specular[DTid.xy] + Diffuse[DTid.xy] * Ambient[DTid.xy/2].w;// + float4(Ambient[DTid.xy/4].xyz,1); GLOW
//Output[DTid.xy] = Diffuse[DTid.xy] + Diffuse[DTid.xy] * Ambient[DTid.xy/4].w;// + float4(Ambient[DTid.xy/4].xyz,1); GLOW //Output[DTid.xy] = Ambient[DTid.xy/2];
Output[DTid.xy] = Diffuse[DTid.xy] + Specular[DTid.xy];
//Output[DTid.xy] = Diffuse[DTid.xy];
} }

View File

@ -1,30 +1,33 @@
#include "Defines.hlsli" #include "Defines.hlsli"
#include "PosManipulation.hlsli" #include "PosManipulation.hlsli"
static float Radius =5; static float Radius = 100;
float GetSSAO(float3 pos, float2 uv, int2 texCoord2, uint2 rndID) float GetSSAO(float3 pos, float2 uv, int2 texCoord2, uint2 rndID)
{ {
float occlusion = 0.0f; float occlusion = 0.0f;
//create sample coordinate system //create sample coordinate system
float4 rnd = float4( SSAORand[(rndID.x + rndID.y) % SSAORand.Length.x].xyz, 0.0f ); float4 rnd = float4( SSAORand[int2(rndID.x % (SSAORand.Length.x), rndID.y % (SSAORand.Length.y))].xyz, 0.0f );
rnd = normalize(rnd); rnd = normalize(rnd);
float3 normal = NormalSpec[uv].xyz; float3 normal = NormalSpec[texCoord2].xyz;
float4 tangent = float4( normalize(rnd.xyz - (normal * dot(rnd.xyz, normal))), 0.0f ); float3 tangent = float3( normalize(rnd.xyz - (normal * dot(rnd.xyz, normal))));
float4 biTangent = float4( cross(tangent.xyz, normal), 0.0f ); float3 biTangent = float3( cross(tangent.xyz, normal));
float4x4 tbn = float4x4(tangent, biTangent, float4(normal,0), float4(pos*Radius,1)); float3x3 tbn = float3x3(tangent, biTangent, normal);
for( uint i = 0; i < SSAOKernel.Length.x; ++i ) for( uint i = 0; i < SSAOKernel.Length.x; ++i )
{ {
//int i = 0;
//take sample from localspace to viewspace //take sample from localspace to viewspace
float4 sampled = mul(tbn, float4(SSAOKernel[i].xyz,1));
float3 sampled = mul(tbn, SSAOKernel[i].xyz);
sampled = sampled * Radius + pos;
//project sample to get uv.xy //project sample to get uv.xy
float4 ProjOffset = sampled; float4 ProjOffset = float4(sampled,1);
ProjOffset = mul(Proj, ProjOffset); ProjOffset = mul(Proj, ProjOffset);
float4 offset = ProjOffset; float4 offset = ProjOffset;
float2 UV = offset; float2 UV = offset.xy;
offset /= offset.w; offset /= offset.w;
offset.xyz = offset.xyz * 0.5f + 0.5f; offset.xyz = offset.xyz * 0.5f + 0.5f;
//extra invert y axis, DX11 //extra invert y axis, DX11
@ -39,7 +42,7 @@ float GetSSAO(float3 pos, float2 uv, int2 texCoord2, uint2 rndID)
//compare to depth from sample //compare to depth from sample
float rangeCheck = (abs(pos.z - sampleDepth) < Radius) ? 1.0f : 0.0f; float rangeCheck = (abs(pos.z - sampleDepth) < Radius) ? 1.0f : 0.0f;
occlusion += (sampleDepth >= sampled.z ? 1.0f : 0.0f) * rangeCheck; occlusion += (sampleDepth <= sampled.z ? 1.0f : 0.0f) * rangeCheck;
} }
occlusion /= (float)(SSAOKernel.Length.x); occlusion /= (float)(SSAOKernel.Length.x);
occlusion = 1.0f - occlusion; occlusion = 1.0f - occlusion;

View File

@ -3,6 +3,20 @@
VertexOut main( VertexIn input ) VertexOut main( VertexIn input )
{ {
VertexOut output; VertexOut output;
/*input.pos = (
(mul(BoneAnimation[input.boneIndex.x], input.pos) * input.boneWeight.x) +
(mul(BoneAnimation[input.boneIndex.y], input.pos) * input.boneWeight.y) +
(mul(BoneAnimation[input.boneIndex.z], input.pos) * input.boneWeight.z) +
(mul(BoneAnimation[input.boneIndex.w], input.pos) * input.boneWeight.w)
* Animated) + input.pos * int(1-Animated);*/
input.pos = (
(mul(BoneAnimation[input.boneIndex.x], input.pos)/* * input.boneWeight.x*/)
* Animated) + input.pos * int(1-Animated);
//float4x4 m = matrix(float4(1,0,0,0),float4(0,1,0,0), float4(0,0,1,0), float4(0,0,0,1));
//input.pos = mul(BoneAnimation[0], float4(input.pos,1));
//input.pos = mul(m, float4(input.pos,1));
output.pos = mul(WVP, float4(input.pos,1)); output.pos = mul(WVP, float4(input.pos,1));
output.normal = mul(WV, float4(input.normal,0)).xyz; output.normal = mul(WV, float4(input.normal,0)).xyz;
output.UV = input.UV; output.UV = input.UV;

260
Code/Tester/MainTest.cpp Normal file
View File

@ -0,0 +1,260 @@
//--------------------------------------------------------------------------------------
// File: TemplateMain.cpp
//
// BTH-D3D-Template
//
// Copyright (c) Stefan Petersson 2011. All rights reserved.
//--------------------------------------------------------------------------------------
#define NOMINMAX
#include <vld.h>
#include <Windows.h>
#include "DllInterfaces\GFXAPI.h"
//--------------------------------------------------------------------------------------
// Global Variables
//--------------------------------------------------------------------------------------
HINSTANCE g_hInst = NULL;
HWND g_hWnd = NULL;
Oyster::Graphics::Model::Model* m = NULL;
Oyster::Graphics::Model::Model* m2 = NULL;
Oyster::Graphics::Model::Model* m3 = NULL;
Oyster::Math::Float4x4 V;
Oyster::Math::Float4x4 P;
//--------------------------------------------------------------------------------------
// Forward declarations
//--------------------------------------------------------------------------------------
HRESULT InitWindow( HINSTANCE hInstance, int nCmdShow );
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
HRESULT Render(float deltaTime);
HRESULT Update(float deltaTime);
HRESULT InitDirect3D();
//--------------------------------------------------------------------------------------
// Entry point to the program. Initializes everything and goes into a message processing
// loop. Idle time is used to render the scene.
//--------------------------------------------------------------------------------------
int WINAPI wWinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow )
{
BOOL b = SetDllDirectoryW(L"..\\DLL");
if( FAILED( InitWindow( hInstance, nCmdShow ) ) )
return 0;
if( FAILED( InitDirect3D() ) )
return 0;
__int64 cntsPerSec = 0;
QueryPerformanceFrequency((LARGE_INTEGER*)&cntsPerSec);
float secsPerCnt = 1.0f / (float)cntsPerSec;
__int64 prevTimeStamp = 0;
QueryPerformanceCounter((LARGE_INTEGER*)&prevTimeStamp);
std::string fps = "FPS:";
char count[100];
// Main message loop
MSG msg = {0};
float fpsCounter = 0;
while(WM_QUIT != msg.message)
{
if( PeekMessage( &msg, NULL, 0, 0, PM_REMOVE) )
{
TranslateMessage( &msg );
DispatchMessage( &msg );
}
else
{
__int64 currTimeStamp = 0;
QueryPerformanceCounter((LARGE_INTEGER*)&currTimeStamp);
float dt = (currTimeStamp - prevTimeStamp) * secsPerCnt;
//render
Update(dt);
Render(dt);
fpsCounter += dt;
if(fpsCounter>0.1f)
{
sprintf_s(count, "%f",1/dt);
SetWindowTextA(g_hWnd, (fps + count).c_str());
fpsCounter = 0;
}
prevTimeStamp = currTimeStamp;
}
}
Oyster::Graphics::API::DeleteModel(m);
Oyster::Graphics::API::DeleteModel(m2);
Oyster::Graphics::API::DeleteModel(m3);
Oyster::Graphics::API::Clean();
return (int) msg.wParam;
}
//--------------------------------------------------------------------------------------
// Register class and create window
//--------------------------------------------------------------------------------------
HRESULT InitWindow( HINSTANCE hInstance, int nCmdShow )
{
// Register class
WNDCLASSEX wcex;
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = 0;
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
wcex.lpszMenuName = NULL;
wcex.lpszClassName = L"BTH_D3D_Template";
wcex.hIconSm = 0;
if( !RegisterClassEx(&wcex) )
return E_FAIL;
// Adjust and create window
g_hInst = hInstance;
RECT rc = { 0, 0, 1280, 720 };
AdjustWindowRect( &rc, WS_OVERLAPPEDWINDOW, FALSE );
if(!(g_hWnd = CreateWindow(
L"BTH_D3D_Template",
L"BTH - Direct3D 11.0 Template",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
rc.right - rc.left,
rc.bottom - rc.top,
NULL,
NULL,
hInstance,
NULL)))
{
return E_FAIL;
}
ShowWindow( g_hWnd, nCmdShow );
return S_OK;
}
//--------------------------------------------------------------------------------------
// Create Direct3D device and swap chain
//--------------------------------------------------------------------------------------
HRESULT InitDirect3D()
{
HRESULT hr = S_OK;;
if(Oyster::Graphics::API::Init(g_hWnd,false,false, Oyster::Math::Float2( 1024, 768 )) == Oyster::Graphics::API::Fail)
{
return E_FAIL;
}
m = Oyster::Graphics::API::CreateModel(L"untitled.dan");
m2 = Oyster::Graphics::API::CreateModel(L"still.dan");
m2->WorldMatrix = Oyster::Math3D::OrientationMatrix(Oyster::Math::Float3::null,Oyster::Math::Float3(0,5,0),Oyster::Math::Float3::null);
m2->AnimationPlaying = 0;
m2->AnimationTime = 0.0f;
//m3 = Oyster::Graphics::API::CreateModel(L"box_2.dan");
//m3->WorldMatrix = Oyster::Math3D::OrientationMatrix(Oyster::Math::Float3::null,Oyster::Math::Float3(0,5,0),Oyster::Math::Float3::null);
P = Oyster::Math3D::ProjectionMatrix_Perspective(Oyster::Math::pi/2,1280.0f/720.0f,.1f,10000);
Oyster::Graphics::API::SetProjection(P);
V = Oyster::Math3D::OrientationMatrix_LookAtDirection(Oyster::Math::Float3(0,0,-1),Oyster::Math::Float3(0,1,0),Oyster::Math::Float3(0,200,500.4f));
V = V.GetInverse();
Oyster::Graphics::Definitions::Pointlight pl;
pl.Color = Oyster::Math::Float3(1,1,1);
pl.Bright = 1;
pl.Pos = Oyster::Math::Float3(0,-20.0f,30.4f);
pl.Radius = 90;
Oyster::Graphics::API::AddLight(pl);
return S_OK;
}
float angle = 0;
HRESULT Update(float deltaTime)
{
angle += Oyster::Math::pi/16 * deltaTime;
//m->WorldMatrix = Oyster::Math3D::RotationMatrix_AxisY(angle) * Oyster::Math3D::RotationMatrix_AxisX(-Oyster::Math::pi/2);
m2->WorldMatrix = Oyster::Math3D::OrientationMatrix(Oyster::Math::Float3(0,1,0)*-Oyster::Math::pi/2,Oyster::Math::Float3(0,-4,0),Oyster::Math::Float3::null);
Oyster::Math::Matrix ma = Oyster::Math::Matrix::identity;
ma *= 50;
ma.m44 = 1;
m2->WorldMatrix = m2->WorldMatrix * ma;
m2->AnimationTime += deltaTime * 0.5f;
//m3->WorldMatrix = Oyster::Math3D::OrientationMatrix(Oyster::Math::Float3(1,0,0)*-0,Oyster::Math::Float3(3,4,-1*angle),Oyster::Math::Float3::null);
return S_OK;
}
HRESULT Render(float deltaTime)
{
Oyster::Graphics::API::SetView(V);
Oyster::Graphics::API::NewFrame();
//Oyster::Graphics::API::RenderModel(*m);
Oyster::Graphics::API::RenderModel(*m2);
//Oyster::Graphics::API::RenderModel(*m3);
Oyster::Graphics::API::EndFrame();
return S_OK;
}
//--------------------------------------------------------------------------------------
// Called every time the application receives a message
//--------------------------------------------------------------------------------------
LRESULT CALLBACK WndProc( HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam )
{
PAINTSTRUCT ps;
HDC hdc;
switch (message)
{
case WM_PAINT:
hdc = BeginPaint(hWnd, &ps);
EndPaint(hWnd, &ps);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
case WM_KEYDOWN:
switch(wParam)
{
case VK_ESCAPE:
PostQuitMessage(0);
break;
//R
case 0x52:
#ifdef _DEBUG
Oyster::Graphics::API::ReloadShaders();
#endif
break;
}
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
}

255
Code/Tester/Tester.vcxproj Normal file
View File

@ -0,0 +1,255 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Debug|x64">
<Configuration>Debug</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|Win32">
<Configuration>Release</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|x64">
<Configuration>Release</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
</ItemGroup>
<PropertyGroup Label="Globals">
<ProjectGuid>{1B3BEA4C-CF75-438A-9693-60FB8444BBF3}</ProjectGuid>
<Keyword>Win32Proj</Keyword>
<RootNamespace>Tester</RootNamespace>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v110</PlatformToolset>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v110</PlatformToolset>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v110</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v110</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings">
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<LinkIncremental>true</LinkIncremental>
<IncludePath>C:\Program Files (x86)\Visual Leak Detector\include;$(IncludePath)$(VCInstallDir)include;$(VCInstallDir)atlmfc\include;</IncludePath>
<LibraryPath>C:\Program Files (x86)\Visual Leak Detector\lib\Win32;$(LibraryPath)</LibraryPath>
<OutDir>$(SolutionDir)..\Bin\Executable\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)D</TargetName>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<LinkIncremental>true</LinkIncremental>
<IncludePath>C:\Program Files (x86)\Visual Leak Detector\include;$(IncludePath)$(VCInstallDir)include;$(VCInstallDir)atlmfc\include;</IncludePath>
<OutDir>$(SolutionDir)..\Bin\Executable\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)D</TargetName>
<LibraryPath>C:\Program Files (x86)\Visual Leak Detector\lib\Win64;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<LinkIncremental>false</LinkIncremental>
<IncludePath>C:\Program Files (x86)\Visual Leak Detector\include;$(IncludePath)$(VCInstallDir)include;$(VCInstallDir)atlmfc\include;</IncludePath>
<LibraryPath>C:\Program Files (x86)\Visual Leak Detector\lib\Win32;$(LibraryPath)</LibraryPath>
<OutDir>$(SolutionDir)..\Bin\Executable\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)</TargetName>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<LinkIncremental>false</LinkIncremental>
<IncludePath>C:\Program Files (x86)\Visual Leak Detector\include;$(IncludePath)$(VCInstallDir)include;$(VCInstallDir)atlmfc\include;</IncludePath>
<OutDir>$(SolutionDir)..\Bin\Executable\</OutDir>
<IntDir>$(SolutionDir)..\Obj\$(ProjectName)\$(PlatformShortName)\$(Configuration)\</IntDir>
<TargetName>$(ProjectName)_$(PlatformShortName)</TargetName>
<LibraryPath>C:\Program Files (x86)\Visual Leak Detector\lib\Win64;$(LibraryPath)</LibraryPath>
</PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<ClCompile>
<PrecompiledHeader>
</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\OysterGraphics;..\OysterMath;..\Misc;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
<DelayLoadDLLs>OysterGraphics_$(PlatformShortName)D.dll;</DelayLoadDLLs>
<AdditionalLibraryDirectories>$(SolutionDir)..\Bin\DLL;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<AdditionalDependencies>OysterGraphics_$(PlatformShortName)D.lib;%(AdditionalDependencies)</AdditionalDependencies>
</Link>
<ProjectReference>
<LinkLibraryDependencies>
</LinkLibraryDependencies>
</ProjectReference>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<ClCompile>
<PrecompiledHeader>
</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\OysterGraphics;..\OysterMath;..\Misc;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
<DelayLoadDLLs>OysterGraphics_$(PlatformShortName)D.dll;</DelayLoadDLLs>
</Link>
<ProjectReference>
<LinkLibraryDependencies>
</LinkLibraryDependencies>
</ProjectReference>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<ClCompile>
<PrecompiledHeader>
</PrecompiledHeader>
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\OysterGraphics;..\OysterMath;..\Misc;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalDependencies>OysterGraphics_$(PlatformShortName)D.lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalLibraryDirectories>$(SolutionDir)..\Bin\DLL;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<PreventDllBinding>true</PreventDllBinding>
<DelayLoadDLLs>OysterGraphics_$(PlatformShortName)D.dll;</DelayLoadDLLs>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<PrecompiledHeader>
</PrecompiledHeader>
<Optimization>MaxSpeed</Optimization>
<Optimization>Disabled</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>false</IntrinsicFunctions>
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\OysterGraphics;..\OysterMath;..\Misc;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
<AdditionalDependencies>OysterGraphics_$(PlatformShortName).lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalLibraryDirectories>$(SolutionDir)..\Bin\DLL;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<PreventDllBinding>true</PreventDllBinding>
<DelayLoadDLLs>OysterGraphics_$(PlatformShortName).dll;</DelayLoadDLLs>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<PrecompiledHeader>
</PrecompiledHeader>
<Optimization>MaxSpeed</Optimization>
<Optimization>Disabled</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>false</IntrinsicFunctions>
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\OysterGraphics;..\OysterMath;..\Misc;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
<AdditionalDependencies>OysterGraphics_$(PlatformShortName).lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalLibraryDirectories>$(SolutionDir)..\Bin\DLL;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<PreventDllBinding>true</PreventDllBinding>
<DelayLoadDLLs>OysterGraphics_$(PlatformShortName).dll;</DelayLoadDLLs>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<PrecompiledHeader>
</PrecompiledHeader>
<Optimization>Disabled</Optimization>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>true</SDLCheck>
<AdditionalIncludeDirectories>..\OysterGraphics;..\OysterMath;..\Misc;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
<AdditionalDependencies>OysterGraphics_$(PlatformShortName).lib;%(AdditionalDependencies)</AdditionalDependencies>
<AdditionalLibraryDirectories>$(SolutionDir)..\Bin\DLL;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
<PreventDllBinding>true</PreventDllBinding>
<DelayLoadDLLs>OysterGraphics_$(PlatformShortName).dll;</DelayLoadDLLs>
</Link>
</ItemDefinitionGroup>
<ItemGroup>
<ClCompile Include="MainTest.cpp" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\Misc\Misc.vcxproj">
<Project>{2ec4dded-8f75-4c86-a10b-e1e8eb29f3ee}</Project>
</ProjectReference>
<ProjectReference Include="..\OysterGraphics\OysterGraphics.vcxproj">
<Project>{0ec83e64-230e-48ef-b08c-6ac9651b4f82}</Project>
<Private>false</Private>
<ReferenceOutputAssembly>true</ReferenceOutputAssembly>
<CopyLocalSatelliteAssemblies>false</CopyLocalSatelliteAssemblies>
<LinkLibraryDependencies>false</LinkLibraryDependencies>
<UseLibraryDependencyInputs>false</UseLibraryDependencyInputs>
</ProjectReference>
<ProjectReference Include="..\OysterMath\OysterMath.vcxproj">
<Project>{f10cbc03-9809-4cba-95d8-327c287b18ee}</Project>
</ProjectReference>
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
</Project>

View File

@ -0,0 +1,22 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<ShowAllFiles>true</ShowAllFiles>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<LocalDebuggerWorkingDirectory>$(OutDir)</LocalDebuggerWorkingDirectory>
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<LocalDebuggerWorkingDirectory>$(OutDir)</LocalDebuggerWorkingDirectory>
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<LocalDebuggerWorkingDirectory>$(OutDir)</LocalDebuggerWorkingDirectory>
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<LocalDebuggerWorkingDirectory>$(OutDir)</LocalDebuggerWorkingDirectory>
<DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
</PropertyGroup>
</Project>

View File

@ -7,7 +7,11 @@
#include <Windows.h> #include <Windows.h>
struct cPOINT :public POINT
{
cPOINT() { x=(0); y=(0); }
cPOINT(int width, int height) { x=(width); y=(height); }
};
class WindowShell class WindowShell
{ {
public: public:
@ -28,23 +32,70 @@ public:
HCURSOR cursor; //!< Optional HCURSOR cursor; //!< Optional
HBRUSH background; //!< Optional HBRUSH background; //!< Optional
WINDOW_INIT_DESC() WINDOW_INIT_DESC(
HWND _parent = 0,
HINSTANCE _hInstance = 0,
WNDPROC _windowProcCallback = 0,
const wchar_t* _windowName = L"Window",
POINT _windowSize = cPOINT(800, 600),
POINT _windowPosition = cPOINT(0,0),
UINT _windowClassStyle = (CS_HREDRAW | CS_VREDRAW | CS_OWNDC),
UINT _windowStyle = (WS_POPUPWINDOW|WS_SYSMENU|WS_CAPTION),
HICON _icon = LoadIcon(0, IDI_APPLICATION),
HCURSOR _cursor = LoadCursor(NULL, IDC_ARROW),
HBRUSH _background = (HBRUSH)GetStockObject(BLACK_BRUSH)
)
{ {
parent = 0; parent = _parent;
hInstance = NULL; hInstance = _hInstance;
windowName = L"Window"; windowName = _windowName;
windowSize.x = 800; windowSize = _windowSize;
windowSize.y = 600; windowPosition = _windowPosition;
windowPosition.x = 0; windowProcCallback = _windowProcCallback;
windowPosition.y = 0; windowClassStyle = _windowClassStyle;
windowProcCallback = NULL; windowStyle = _windowStyle;
windowClassStyle = CS_HREDRAW | CS_VREDRAW | CS_OWNDC; icon = _icon;
windowStyle = WS_POPUPWINDOW|WS_SYSMENU|WS_CAPTION; cursor = _cursor;
//windowStyle = WS_OVERLAPPEDWINDOW; background = _background;
}
WINDOW_INIT_DESC(
HWND _parent,
HINSTANCE _hInstance,
WNDPROC _windowProcCallback,
const wchar_t* _windowName,
cPOINT _windowSize,
cPOINT _windowPosition
)
{
parent = _parent;
hInstance = _hInstance;
windowName = _windowName;
windowSize = _windowSize;
windowPosition = _windowPosition;
windowProcCallback = _windowProcCallback;
windowClassStyle = (CS_HREDRAW | CS_VREDRAW | CS_OWNDC);
windowStyle = (WS_POPUPWINDOW|WS_SYSMENU|WS_CAPTION);
icon = LoadIcon(0, IDI_APPLICATION);
cursor = LoadCursor(NULL, IDC_ARROW);
background = (HBRUSH)GetStockObject(BLACK_BRUSH);
}
WINDOW_INIT_DESC(
const wchar_t* _windowName,
cPOINT _windowSize,
cPOINT _windowPosition
)
{
parent = 0;
hInstance = 0;
windowName = _windowName;
windowSize = _windowSize;
windowPosition = _windowPosition;
windowProcCallback = 0;
windowClassStyle = (CS_HREDRAW | CS_VREDRAW | CS_OWNDC);
windowStyle = (WS_POPUPWINDOW|WS_SYSMENU|WS_CAPTION);
icon = LoadIcon(0, IDI_APPLICATION); icon = LoadIcon(0, IDI_APPLICATION);
cursor = LoadCursor(NULL, IDC_ARROW); cursor = LoadCursor(NULL, IDC_ARROW);
background = (HBRUSH)GetStockObject(BLACK_BRUSH); background = (HBRUSH)GetStockObject(BLACK_BRUSH);
//background = (HBRUSH)GetStockObject(BACKGROUND_BLUE);(HBRUSH)(COLOR_WINDOW+1);
} }
}; };