Compare commits

..

27 Commits

Author SHA1 Message Date
Kayne Ruse 29a09cf71f Discarding: pointers to object to push/pop was a bad idea 2015-01-02 07:18:21 +11:00
Kayne Ruse e4d7ece99c Merge branch 'bugfix-lambda' into multiple-rooms
Conflicts:
	server/server_methods.cpp
2015-01-02 07:10:29 +11:00
Kayne Ruse eb897c81e8 Tentative solution for bug #38 2015-01-02 07:09:04 +11:00
Kayne Ruse b2452fb6fe Committing incomplete work; need to fix an urgent bug 2015-01-02 06:57:20 +11:00
Kayne Ruse 4579f9f388 Don't code while drunk; it never ends well 2015-01-01 12:53:32 +11:00
Kayne Ruse b4b7c0d877 Pop & Push don't work like they should 2015-01-01 03:37:13 +11:00
Kayne Ruse ebd8e54725 Added PushEntity() & PopEntity() to RoomManager
Calling them from server_character_methods.cpp.
2015-01-01 02:51:04 +11:00
Kayne Ruse 963aca218a Comment tweaks 2015-01-01 01:29:48 +11:00
Kayne Ruse 8b8ef088d9 HOTFIX: Incorrect error code checked 2014-12-31 06:10:03 +11:00
Kayne Ruse 6704944105 Updated the map system & APIs 2014-12-31 06:01:03 +11:00
Kayne Ruse 8e50be24d4 Updated room system and room API, more to come
There's a lot of verbosity in the scripts, so it might be beneficial to
redice that at some point.
2014-12-31 04:52:10 +11:00
Kayne Ruse f9c19a630d Added trigger reference to WaypointData, unused
WaypointData also inherits from Entity now, so I could alias Entity's API
for it too. I've also made a number of comment tweaks.
2014-12-31 03:34:06 +11:00
Kayne Ruse 78c04718e0 Removed ManagerInterface, it was a bad idea 2014-12-31 03:05:19 +11:00
Kayne Ruse bb592b2436 Added the waypoint system to the modules
Also fleshed out entity_api.cpp, but that's just filler.
2014-12-30 04:37:56 +11:00
Kayne Ruse f3fb5017b3 Added waypoint API placeholder files 2014-12-30 02:45:35 +11:00
Kayne Ruse 3a9fdd511b Replaced door system with waypoint system 2014-12-30 02:38:25 +11:00
Kayne Ruse 57c6f45c21 Added API placeholder files 2014-12-30 02:19:19 +11:00
Kayne Ruse 8d204dc3c4 Merge branch 'master' into develop
Also saved todo.txt
2014-12-30 01:21:11 +11:00
Kayne Ruse 9413adcf4a Forgot the copyright in the README files 2014-12-30 01:10:43 +11:00
Kayne Ruse 99af76c5b5 Merge branch 'develop'
Conflicts:
	todo.txt
2014-12-27 23:44:54 +11:00
Kayne Ruse cc6458daa7 Merge branch 'high-water-mark' into develop
Thank fuck that's over.
2014-12-27 23:34:51 +11:00
Kayne Ruse 8708cfbee0 I give up, I'm just using the stop-dead system for now. 2014-12-27 23:16:48 +11:00
Kayne Ruse b67e85e87b Moved some messy code from InWorld::Update() to utility methods 2014-12-27 21:00:00 +11:00
Kayne Ruse 33c3143de9 Added unary negative to Vector2
This is the only fragment I'm bothering to salvage from the collisions
branch.
2014-12-27 20:31:09 +11:00
Kayne Ruse 5deb6a9d8e Merge branch 'develop' 2014-11-23 04:12:51 +11:00
Kayne Ruse 3192524922 Merge commit '0f13956'
* also eliminated ./todo.txt
2014-11-07 00:17:31 +11:00
Kayne Ruse 2a7a2889c6 Merge branch 'unix-compat' 2014-10-19 05:50:13 +11:00
64 changed files with 1146 additions and 419 deletions
+1 -1
View File
@@ -26,7 +26,7 @@ The most recent stable build for Windows can be found [here](https://dl.dropboxu
The current version of Tortuga is released under the [zlib license](http://en.wikipedia.org/wiki/Zlib_License). The current version of Tortuga is released under the [zlib license](http://en.wikipedia.org/wiki/Zlib_License).
Copyright (c) 2013, 2014 Kayne Ruse Copyright (c) 2013-2015 Kayne Ruse
This software is provided 'as-is', without any express or implied warranty. In no event will the authors be held liable for any damages arising from the use of this software. This software is provided 'as-is', without any express or implied warranty. In no event will the authors be held liable for any damages arising from the use of this software.
+7 -51
View File
@@ -21,59 +21,15 @@
*/ */
#include "local_character.hpp" #include "local_character.hpp"
bool LocalCharacter::ProcessCollisions(std::list<BoundingBox>& boxList) { #include <iostream>
if (CheckCollisionSimple(boxList, origin + motion)) {
Vector2 velocity;
velocity.x = CorrectVelocityX(boxList, motion.x);
velocity.y = CorrectVelocityY(boxList, motion.y);
origin += velocity;
return true;
}
else {
origin += motion;
return false;
}
}
bool LocalCharacter::CheckCollisionSimple(std::list<BoundingBox>& boxList, Vector2 newPos) { bool LocalCharacter::ProcessCollisionGrid(std::list<BoundingBox> boxList) {
for (auto& it : boxList) { for(auto& box : boxList) {
if (it.CheckOverlap(bounds + newPos)) { if (box.CheckOverlap(origin + bounds)) {
origin -= motion;
motion = {0, 0};
return true; return true;
} }
} }
return false; return false;
} }
double LocalCharacter::CorrectVelocityX(std::list<BoundingBox>& boxList, double velocityX) {
double ret = velocityX;
for (auto& it : boxList) {
if (it.CheckOverlap(bounds + origin + Vector2(velocityX, 0) )) {
if (velocityX > 0) {
ret = std::min(ret, it.x - (origin.x + bounds.x + bounds.w -1));
ret = std::min(ret, 0.0);
}
else if (velocityX < 0) {
ret = std::max(ret, (it.x + it.w) - (origin.x + bounds.x));
ret = std::max(ret, 0.0);
}
}
}
return ret;
}
double LocalCharacter::CorrectVelocityY(std::list<BoundingBox>& boxList, double velocityY) {
double ret = velocityY;
for (auto& it : boxList) {
if (it.CheckOverlap(bounds + origin + Vector2(0, velocityY) )) {
if (velocityY > 0) {
ret = std::min(ret, it.y - (origin.y + bounds.y + bounds.h -1));
ret = std::min(ret, 0.0);
}
else if (velocityY < 0) {
ret = std::max(ret, (it.y + it.h) - (origin.y + bounds.y));
ret = std::max(ret, 0.0);
}
}
}
return ret;
}
+3 -5
View File
@@ -33,12 +33,10 @@ public:
LocalCharacter() = default; LocalCharacter() = default;
virtual ~LocalCharacter() = default; virtual ~LocalCharacter() = default;
bool ProcessCollisions(std::list<BoundingBox>& boxList); bool ProcessCollisionGrid(std::list<BoundingBox>);
protected: private:
bool CheckCollisionSimple(std::list<BoundingBox>& boxList, Vector2 newPos); //NOTE: NO MEMBERS
double CorrectVelocityX(std::list<BoundingBox>& boxList, double velocityX);
double CorrectVelocityY(std::list<BoundingBox>& boxList, double velocityY);
}; };
#endif #endif
+75 -49
View File
@@ -134,27 +134,12 @@ void InWorld::Update() {
//free the buffer //free the buffer
delete reinterpret_cast<char*>(packetBuffer); delete reinterpret_cast<char*>(packetBuffer);
//check the connection (heartbeat) //heartbeat system
if (Clock::now() - lastBeat > std::chrono::seconds(3)) { CheckHeartBeat();
if (attemptedBeats > 2) {
//escape to the disconnect screen
SendDisconnectRequest();
SetNextScene(SceneList::DISCONNECTEDSCREEN);
ConfigUtility::GetSingleton()["client.disconnectMessage"] = "Error: Lost connection to the server";
}
else {
ServerPacket newPacket;
newPacket.type = SerialPacketType::PING;
network.SendTo(Channels::SERVER, &newPacket);
attemptedBeats++;
lastBeat = Clock::now();
}
}
//update all entities //update all entities
for (auto& it : characterMap) { for (auto& it : characterMap) {
// it.second.Update(); it.second.Update();
} }
for (auto& it : monsterMap) { for (auto& it : monsterMap) {
it.second.Update(); it.second.Update();
@@ -168,35 +153,14 @@ void InWorld::Update() {
return; return;
} }
//prepare for collisions //get the collidable boxes
BoundingBox wallBounds = {0, 0, tileSheet.GetTileW(), tileSheet.GetTileH()}; std::list<BoundingBox> boxList = GenerateCollisionGrid(localCharacter, tileSheet.GetTileW(), tileSheet.GetTileH());
std::list<BoundingBox> boxList;
//NOTE: for loops were too dense to work with, so I've just used while loops
//NOTE: this code is complex, and can be replaced with hard-coded relative positions, at the cost of variable-sized sprites/bounding boxes
//outer loop
wallBounds.x = snapToBase((double)wallBounds.w, localCharacter->GetOrigin().x) - wallBounds.w;
while(wallBounds.x < (localCharacter->GetOrigin() + localCharacter->GetBounds()).x + localCharacter->GetBounds().w) {
//inner loop
wallBounds.y = snapToBase((double)wallBounds.h, localCharacter->GetOrigin().y) - wallBounds.h;
while(wallBounds.y < (localCharacter->GetOrigin() + localCharacter->GetBounds()).y + localCharacter->GetBounds().h) {
//check to see if this tile is solid
if (regionPager.GetSolid(wallBounds.x / wallBounds.w, wallBounds.y / wallBounds.h)) {
//push onto the box set
boxList.push_front(wallBounds);
}
//increment
wallBounds.y += wallBounds.h;
}
//increment
wallBounds.x += wallBounds.w;
}
//process the collisions //process the collisions
localCharacter->ProcessCollisions(boxList); if (localCharacter->ProcessCollisionGrid(boxList)) {
localCharacter->CorrectSprite();
SendLocalCharacterMotion();
}
//update the camera //update the camera
camera.x = localCharacter->GetOrigin().x - camera.marginX; camera.x = localCharacter->GetOrigin().x - camera.marginX;
@@ -499,6 +463,26 @@ void InWorld::HandleDisconnectForced(ClientPacket* const argPacket) {
ConfigUtility::GetSingleton()["client.disconnectMessage"] = "You have been forcibly disconnected by the server"; ConfigUtility::GetSingleton()["client.disconnectMessage"] = "You have been forcibly disconnected by the server";
} }
void InWorld::CheckHeartBeat() {
//check the connection (heartbeat)
if (Clock::now() - lastBeat > std::chrono::seconds(3)) {
if (attemptedBeats > 2) {
//escape to the disconnect screen
SendDisconnectRequest();
SetNextScene(SceneList::DISCONNECTEDSCREEN);
ConfigUtility::GetSingleton()["client.disconnectMessage"] = "Error: Lost connection to the server";
}
else {
ServerPacket newPacket;
newPacket.type = SerialPacketType::PING;
network.SendTo(Channels::SERVER, &newPacket);
attemptedBeats++;
lastBeat = Clock::now();
}
}
}
//------------------------- //-------------------------
//map management //map management
//------------------------- //-------------------------
@@ -517,7 +501,9 @@ void InWorld::SendRegionRequest(int roomIndex, int x, int y) {
void InWorld::HandleRegionContent(RegionPacket* const argPacket) { void InWorld::HandleRegionContent(RegionPacket* const argPacket) {
//replace existing regions //replace existing regions
regionPager.UnloadRegion(argPacket->x, argPacket->y); regionPager.UnloadIf([&](Region const& region) -> bool {
return region.GetX() == argPacket->x && region.GetY() == argPacket->y;
});
regionPager.PushRegion(argPacket->region); regionPager.PushRegion(argPacket->region);
//clean up after the serial code //clean up after the serial code
@@ -556,9 +542,9 @@ void InWorld::UpdateMap() {
//entity management //entity management
//------------------------- //-------------------------
//NOTE: preexisting characters will result in query responses //DOCS: preexisting characters will result in query responses
//NOTE: new characters will result in create messages //DOCS: new characters will result in create messages
//NOTE: this client's character will exist in both (skipped) //DOCS: this client's character will exist in both (skipped)
void InWorld::HandleCharacterCreate(CharacterPacket* const argPacket) { void InWorld::HandleCharacterCreate(CharacterPacket* const argPacket) {
//prevent double message //prevent double message
@@ -691,6 +677,11 @@ void InWorld::HandleCharacterSetRoom(CharacterPacket* const argPacket) {
} }
void InWorld::HandleCharacterSetOrigin(CharacterPacket* const argPacket) { void InWorld::HandleCharacterSetOrigin(CharacterPacket* const argPacket) {
//TODO: Authentication
if (argPacket->characterIndex == characterIndex) {
return;
}
//check that this character exists //check that this character exists
std::map<int, BaseCharacter>::iterator characterIt = characterMap.find(argPacket->characterIndex); std::map<int, BaseCharacter>::iterator characterIt = characterMap.find(argPacket->characterIndex);
if (characterIt != characterMap.end()) { if (characterIt != characterMap.end()) {
@@ -702,6 +693,11 @@ void InWorld::HandleCharacterSetOrigin(CharacterPacket* const argPacket) {
} }
void InWorld::HandleCharacterSetMotion(CharacterPacket* const argPacket) { void InWorld::HandleCharacterSetMotion(CharacterPacket* const argPacket) {
//TODO: Authentication
if (argPacket->characterIndex == characterIndex) {
return;
}
//check that this character exists //check that this character exists
std::map<int, BaseCharacter>::iterator characterIt = characterMap.find(argPacket->characterIndex); std::map<int, BaseCharacter>::iterator characterIt = characterMap.find(argPacket->characterIndex);
if (characterIt != characterMap.end()) { if (characterIt != characterMap.end()) {
@@ -728,4 +724,34 @@ void InWorld::SendLocalCharacterMotion() {
newPacket.motion = localCharacter->GetMotion(); newPacket.motion = localCharacter->GetMotion();
network.SendTo(Channels::SERVER, &newPacket); network.SendTo(Channels::SERVER, &newPacket);
}
std::list<BoundingBox> InWorld::GenerateCollisionGrid(Entity* ptr, int tileWidth, int tileHeight) {
//prepare for collisions
BoundingBox wallBounds = {0, 0, tileWidth, tileHeight};
std::list<BoundingBox> boxList;
//NOTE: for loops were too dense to work with, so I've just used while loops
//outer loop
wallBounds.x = snapToBase((double)wallBounds.w, ptr->GetOrigin().x);
while(wallBounds.x < (ptr->GetOrigin() + ptr->GetBounds()).x + ptr->GetBounds().w) {
//inner loop
wallBounds.y = snapToBase((double)wallBounds.h, ptr->GetOrigin().y);
while(wallBounds.y < (ptr->GetOrigin() + ptr->GetBounds()).y + ptr->GetBounds().h) {
//check to see if this tile is solid
if (regionPager.GetSolid(wallBounds.x / wallBounds.w, wallBounds.y / wallBounds.h)) {
//push onto the box set
boxList.push_front(wallBounds);
}
//increment
wallBounds.y += wallBounds.h;
}
//increment
wallBounds.x += wallBounds.w;
}
return std::move(boxList);
} }
+3
View File
@@ -85,6 +85,8 @@ protected:
void HandleDisconnectResponse(ClientPacket* const); void HandleDisconnectResponse(ClientPacket* const);
void HandleDisconnectForced(ClientPacket* const); void HandleDisconnectForced(ClientPacket* const);
void CheckHeartBeat();
//map management //map management
void SendRegionRequest(int roomIndex, int x, int y); void SendRegionRequest(int roomIndex, int x, int y);
void HandleRegionContent(RegionPacket* const); void HandleRegionContent(RegionPacket* const);
@@ -100,6 +102,7 @@ protected:
//player movement //player movement
void SendLocalCharacterMotion(); void SendLocalCharacterMotion();
std::list<BoundingBox> GenerateCollisionGrid(Entity*, int tileWidth, int tileHeight);
//indexes //indexes
int& clientIndex; int& clientIndex;
+1 -21
View File
@@ -26,31 +26,11 @@
#include "region_pager_api.hpp" #include "region_pager_api.hpp"
#include "tile_sheet_api.hpp" #include "tile_sheet_api.hpp"
//macros
#include "region.hpp"
//useful "globals" //useful "globals"
static int getRegionWidth(lua_State* L) { //...
lua_pushinteger(L, REGION_WIDTH);
return 1;
}
static int getRegionHeight(lua_State* L) {
lua_pushinteger(L, REGION_HEIGHT);
return 1;
}
static int getRegionDepth(lua_State* L) {
lua_pushinteger(L, REGION_DEPTH);
return 1;
}
//This mimics linit.c to create a nested collection of all map modules. //This mimics linit.c to create a nested collection of all map modules.
static const luaL_Reg funcs[] = { static const luaL_Reg funcs[] = {
//synonyms
{"GetRegionWidth", getRegionWidth},
{"GetRegionHeight", getRegionHeight},
{"GetRegionDepth", getRegionDepth},
{nullptr, nullptr} {nullptr, nullptr}
}; };
+13 -1
View File
@@ -21,9 +21,9 @@
*/ */
#include "region.hpp" #include "region.hpp"
#include <stdexcept>
#include <cmath> #include <cmath>
#include <cstring> #include <cstring>
#include <stdexcept>
int snapToBase(int base, int x) { int snapToBase(int base, int x) {
return floor((double)x / base) * base; return floor((double)x / base) * base;
@@ -55,4 +55,16 @@ bool Region::SetSolid(int x, int y, bool b) {
bool Region::GetSolid(int x, int y) { bool Region::GetSolid(int x, int y) {
return solid[x * REGION_WIDTH + y]; return solid[x * REGION_WIDTH + y];
}
int Region::GetX() const {
return x;
}
int Region::GetY() const {
return y;
}
std::bitset<REGION_WIDTH*REGION_HEIGHT>* Region::GetSolidBitset() {
return &solid;
} }
+3 -3
View File
@@ -48,10 +48,10 @@ public:
bool GetSolid(int x, int y); bool GetSolid(int x, int y);
//accessors //accessors
int GetX() const { return x; } int GetX() const;
int GetY() const { return y; } int GetY() const;
std::bitset<REGION_WIDTH*REGION_HEIGHT>* GetSolidBitset() { return &solid; } std::bitset<REGION_WIDTH*REGION_HEIGHT>* GetSolidBitset();
private: private:
const int x; const int x;
const int y; const int y;
+2
View File
@@ -85,6 +85,8 @@ static const luaL_Reg regionLib[] = {
{"GetSolid",getSolid}, {"GetSolid",getSolid},
{"GetX",getX}, {"GetX",getX},
{"GetY",getY}, {"GetY",getY},
//the global macros
{"GetWidth",getWidth}, {"GetWidth",getWidth},
{"GetHeight",getHeight}, {"GetHeight",getHeight},
{"GetDepth",getDepth}, {"GetDepth",getDepth},
+26 -1
View File
@@ -84,7 +84,22 @@ static int createRegion(lua_State* L) {
static int unloadRegion(lua_State* L) { static int unloadRegion(lua_State* L) {
RegionPagerLua* pager = reinterpret_cast<RegionPagerLua*>(lua_touserdata(L, 1)); RegionPagerLua* pager = reinterpret_cast<RegionPagerLua*>(lua_touserdata(L, 1));
pager->UnloadRegion(lua_tointeger(L, 2), lua_tointeger(L, 3));
//two argument types: coords & the region itself
switch(lua_type(L, 2)) {
case LUA_TNUMBER:
pager->UnloadIf([&](Region const& region) -> bool {
int x = lua_tointeger(L, 2);
int y = lua_tointeger(L, 3);
return region.GetX() == x && region.GetY() == y;
});
break;
case LUA_TLIGHTUSERDATA:
pager->UnloadIf([&](Region const& region) -> bool {
return (&region) == lua_touserdata(L, 2);
});
break;
}
return 0; return 0;
} }
@@ -116,6 +131,13 @@ static int setOnUnload(lua_State* L) {
return 0; return 0;
} }
//debugging
static int containerSize(lua_State* L) {
RegionPagerLua* pager = static_cast<RegionPagerLua*>(lua_touserdata(L, 1));
lua_pushinteger(L, pager->GetContainer()->size());
return 1;
}
static const luaL_Reg regionPagerLib[] = { static const luaL_Reg regionPagerLib[] = {
//curry //curry
{"SetTile", setTile}, {"SetTile", setTile},
@@ -136,6 +158,9 @@ static const luaL_Reg regionPagerLib[] = {
{"SetOnCreate",setOnCreate}, {"SetOnCreate",setOnCreate},
{"SetOnUnload",setOnUnload}, {"SetOnUnload",setOnUnload},
//debugging
{"ContainerSize", containerSize},
//sentinel //sentinel
{nullptr, nullptr} {nullptr, nullptr}
}; };
+10 -4
View File
@@ -24,6 +24,10 @@
#include <stdexcept> #include <stdexcept>
#include <algorithm> #include <algorithm>
RegionPagerBase::~RegionPagerBase() {
UnloadAll();
};
Region::type_t RegionPagerBase::SetTile(int x, int y, int z, Region::type_t v) { Region::type_t RegionPagerBase::SetTile(int x, int y, int z, Region::type_t v) {
Region* ptr = GetRegion(x, y); Region* ptr = GetRegion(x, y);
return ptr->SetTile(x - ptr->GetX(), y - ptr->GetY(), z, v); return ptr->SetTile(x - ptr->GetX(), y - ptr->GetY(), z, v);
@@ -88,12 +92,14 @@ Region* RegionPagerBase::CreateRegion(int x, int y) {
return &regionList.front(); return &regionList.front();
} }
void RegionPagerBase::UnloadRegion(int x, int y) { void RegionPagerBase::UnloadIf(std::function<bool(Region const&)> fn) {
regionList.remove_if([x, y](Region& region) -> bool { regionList.remove_if(fn);
return region.GetX() == x && region.GetY() == y;
});
} }
void RegionPagerBase::UnloadAll() { void RegionPagerBase::UnloadAll() {
regionList.clear(); regionList.clear();
}
std::list<Region>* RegionPagerBase::GetContainer() {
return &regionList;
} }
+4 -3
View File
@@ -24,12 +24,13 @@
#include "region.hpp" #include "region.hpp"
#include <functional>
#include <list> #include <list>
class RegionPagerBase { class RegionPagerBase {
public: public:
RegionPagerBase() = default; RegionPagerBase() = default;
virtual ~RegionPagerBase() { UnloadAll(); }; virtual ~RegionPagerBase();
//tile manipulation //tile manipulation
virtual Region::type_t SetTile(int x, int y, int z, Region::type_t v); virtual Region::type_t SetTile(int x, int y, int z, Region::type_t v);
@@ -47,12 +48,12 @@ public:
virtual Region* LoadRegion(int x, int y); virtual Region* LoadRegion(int x, int y);
virtual Region* SaveRegion(int x, int y); virtual Region* SaveRegion(int x, int y);
virtual Region* CreateRegion(int x, int y); virtual Region* CreateRegion(int x, int y);
virtual void UnloadRegion(int x, int y);
virtual void UnloadIf(std::function<bool(Region const&)> fn);
virtual void UnloadAll(); virtual void UnloadAll();
//accessors & mutators //accessors & mutators
std::list<Region>* GetContainer() { return &regionList; } std::list<Region>* GetContainer();
protected: protected:
std::list<Region> regionList; std::list<Region> regionList;
}; };
+10 -3
View File
@@ -23,6 +23,9 @@
#include <stdexcept> #include <stdexcept>
//DOCS: Load, Save and Create fail unless the lua function has been set
//DOCS: UnloadIf and UnloadAll will still continue without the function set
RegionPagerLua::~RegionPagerLua() { RegionPagerLua::~RegionPagerLua() {
//unload all regions //unload all regions
UnloadAll(); UnloadAll();
@@ -130,23 +133,25 @@ Region* RegionPagerLua::CreateRegion(int x, int y) {
} }
//no return //no return
void RegionPagerLua::UnloadRegion(int x, int y) { void RegionPagerLua::UnloadIf(std::function<bool(Region const&)> fn) {
//get the pager's function from the registry //get the pager's function from the registry
lua_rawgeti(lua, LUA_REGISTRYINDEX, unloadRef); lua_rawgeti(lua, LUA_REGISTRYINDEX, unloadRef);
//check if this function is available //check if this function is available
if (lua_isnil(lua, -1)) { if (lua_isnil(lua, -1)) {
lua_pop(lua, 1); lua_pop(lua, 1);
//remove the regions anyway
regionList.remove_if(fn);
return; return;
} }
//run each region through this lambda //run each region through this lambda
regionList.remove_if([&](Region& region) -> bool { regionList.remove_if([&](Region& region) -> bool {
if (region.GetX() == x && region.GetY() == y) { if (fn(region)) {
//push a copy of the function onto the stack with the region //push a copy of the function onto the stack with the region
lua_pushvalue(lua, -1); lua_pushvalue(lua, -1);
lua_pushlightuserdata(lua, &region); lua_pushlightuserdata(lua, static_cast<void*>(&region));
//call the function, 1 arg, 0 return //call the function, 1 arg, 0 return
if (lua_pcall(lua, 1, 0, 0) != LUA_OK) { if (lua_pcall(lua, 1, 0, 0) != LUA_OK) {
@@ -171,6 +176,8 @@ void RegionPagerLua::UnloadAll() {
//check if this function is available //check if this function is available
if (lua_isnil(lua, -1)) { if (lua_isnil(lua, -1)) {
lua_pop(lua, 1); lua_pop(lua, 1);
//remove the regions anyway
regionList.clear();
return; return;
} }
+2 -1
View File
@@ -30,6 +30,7 @@
#include "lua.hpp" #include "lua.hpp"
#endif #endif
#include <functional>
#include <string> #include <string>
class RegionPagerLua : public RegionPagerBase { class RegionPagerLua : public RegionPagerBase {
@@ -41,8 +42,8 @@ public:
Region* LoadRegion(int x, int y) override; Region* LoadRegion(int x, int y) override;
Region* SaveRegion(int x, int y) override; Region* SaveRegion(int x, int y) override;
Region* CreateRegion(int x, int y) override; Region* CreateRegion(int x, int y) override;
void UnloadRegion(int x, int y) override;
void UnloadIf(std::function<bool(Region const&)> fn) override;
void UnloadAll() override; void UnloadAll() override;
//accessors & mutators //accessors & mutators
+1 -1
View File
@@ -26,7 +26,7 @@
#include <stdexcept> #include <stdexcept>
//NOTE: memset() is used before sending a packet to remove old data; you don't want to send sensitive data over the network //DOCS: memset() is used before sending a packet to remove old data; you don't want to send sensitive data over the network
//NOTE: don't confuse SerialPacketBase with UDPpacket //NOTE: don't confuse SerialPacketBase with UDPpacket
void UDPNetworkUtility::Open(int port) { void UDPNetworkUtility::Open(int port) {
+1 -1
View File
@@ -2,7 +2,7 @@ Future versions (to be determined) may be released under a modified version of t
The current version of Tortuga is released under the zlib license. The current version of Tortuga is released under the zlib license.
Copyright (c) 2013, 2014 Kayne Ruse Copyright (c) 2013-2015 Kayne Ruse
This software is provided 'as-is', without any express or implied warranty. In no event will the authors be held liable for any damages arising from the use of this software. This software is provided 'as-is', without any express or implied warranty. In no event will the authors be held liable for any damages arising from the use of this software.
+8
View File
@@ -36,4 +36,12 @@ function mapMaker.debugIsland(region)
end end
end end
function mapMaker.dirtLand(region)
for i = 1, mapSystem.Region.GetWidth(region) do
for j = 1, mapSystem.Region.GetHeight(region) do
mapSystem.Region.SetTile(region, i, j, 1, mapMaker.dirt)
end
end
end
return mapMaker return mapMaker
+2
View File
@@ -1,9 +1,11 @@
local mapSaver = {} local mapSaver = {}
function mapSaver.Load(region) function mapSaver.Load(region)
--empty --empty
print("map_saver.lua:mapSaver.Load(region)")
end end
function mapSaver.Save(region) function mapSaver.Save(region)
--empty --empty
print("map_saver.lua:mapSaver.Save(region)")
end end
--TODO: create a flexible saving & loading system --TODO: create a flexible saving & loading system
return mapSaver return mapSaver
+56 -17
View File
@@ -1,32 +1,71 @@
print("Lua script check") print("Lua script check")
mapSystem = require "map_system"
mapMaker = require "map_maker" mapMaker = require "map_maker"
mapSaver = require "map_saver" mapSaver = require "map_saver"
roomSystem = require "room_system" roomSystem = require "room_system"
waypointSystem = require "waypoint_system"
local function dumpTable(t) local function dumpTable(t)
print(t) print(t)
for k, v in pairs(t) do for k, v in pairs(t) do
print("",k, v) print("",k,v)
end end
end end
--create the overworld, set it's generator, loader & saver
--[[
local t = {
"overworld.bmp", --tileset name
mapSaver.load, --load function
mapSaver.save, --save function
mapMaker.debugIsland, --create function
mapSaver.save --unload function
}]]
dumpTable(roomSystem)
dumpTable(roomSystem.RoomManager)
dumpTable(roomSystem.Room)
--NOTE: room 0 is the first that the client asks for, therefore it must exist --NOTE: room 0 is the first that the client asks for, therefore it must exist
local overworld, uid = roomSystem.RoomManager.CreateRoom("overworld") local overworld, uid = roomSystem.RoomManager.CreateRoom("overworld", "overworld.bmp")
roomSystem.Room.Initialize(overworld, "overworld.bmp", mapSaver.Load, mapSaver.Save, mapMaker.debugIsland, mapSaver.Save)
--NOTE: This is horrible; room initialization is important
mapSystem.RegionPager.SetOnLoad(roomSystem.Room.GetPager(overworld), mapSaver.Load)
mapSystem.RegionPager.SetOnSave(roomSystem.Room.GetPager(overworld), mapSaver.Save)
mapSystem.RegionPager.SetOnCreate(roomSystem.Room.GetPager(overworld), mapMaker.debugIsland)
mapSystem.RegionPager.SetOnUnload(roomSystem.Room.GetPager(overworld), mapSaver.Save)
--Dirt Land
local dirtLand = roomSystem.RoomManager.CreateRoom("dirt land", "overworld.bmp")
roomSystem.Room.Initialize(dirtLand, mapSaver.Load, mapSaver.Save, mapMaker.dirtLand, mapSaver.Save)
print("Finished the lua script") print("Finished the lua script")
--[[
debugging test
Ideal output:
-------------------------
pager: userdata: [memory location]
Size 0: 0
[debug output from load]
Size 1: 1
[debug output from save]
Size 2: 0
[debug output from load]
Size 3: 1
[debug output from save]
Size 4: 0
-------------------------
--]-]
print("-------------------------")
local pager = roomSystem.Room.GetPager(overworld)
print("pager:", pager)
print("Size 0:", mapSystem.RegionPager.ContainerSize(pager))
local regionFoo = mapSystem.RegionPager.GetRegion(pager, 0, 0)
print("Size 1:", mapSystem.RegionPager.ContainerSize(pager))
mapSystem.RegionPager.UnloadRegion(pager, regionFoo)
print("Size 2:", mapSystem.RegionPager.ContainerSize(pager))
local regionFoo = mapSystem.RegionPager.GetRegion(pager, 0, 0)
print("Size 3:", mapSystem.RegionPager.ContainerSize(pager))
mapSystem.RegionPager.UnloadRegion(pager, 0, 0)
print("Size 4:", mapSystem.RegionPager.ContainerSize(pager))
print("-------------------------")
--]]
+1 -2
View File
@@ -200,7 +200,7 @@ void AccountManager::UnloadAll() {
elementMap.clear(); elementMap.clear();
} }
void AccountManager::UnloadIf(std::function<bool(std::pair<const int, AccountData>)> fn) { void AccountManager::UnloadIf(std::function<bool(std::pair<const int, AccountData const&>)> fn) {
//replicate std::remove_if, using custom code //replicate std::remove_if, using custom code
std::map<int, AccountData>::iterator it = elementMap.begin(); std::map<int, AccountData>::iterator it = elementMap.begin();
while (it != elementMap.end()) { while (it != elementMap.end()) {
@@ -219,7 +219,6 @@ void AccountManager::UnloadIf(std::function<bool(std::pair<const int, AccountDat
//------------------------- //-------------------------
AccountData* AccountManager::Get(int uid) { AccountData* AccountManager::Get(int uid) {
//TODO: could this load an account first?
std::map<int, AccountData>::iterator it = elementMap.find(uid); std::map<int, AccountData>::iterator it = elementMap.find(uid);
if (it == elementMap.end()) { if (it == elementMap.end()) {
+14 -16
View File
@@ -24,7 +24,6 @@
#include "account_data.hpp" #include "account_data.hpp"
#include "singleton.hpp" #include "singleton.hpp"
#include "manager_interface.hpp"
#if defined(__MINGW32__) #if defined(__MINGW32__)
#include "sqlite3/sqlite3.h" #include "sqlite3/sqlite3.h"
@@ -35,26 +34,23 @@
#include <functional> #include <functional>
#include <map> #include <map>
class AccountManager: class AccountManager: public Singleton<AccountManager> {
public Singleton<AccountManager>,
public ManagerInterface<AccountData, std::string, int>
{
public: public:
//common public methods //common public methods
int Create(std::string username, int clientIndex) override; int Create(std::string username, int clientIndex);
int Load(std::string username, int clientIndex) override; int Load(std::string username, int clientIndex);
int Save(int uid) override; int Save(int uid);
void Unload(int uid) override; void Unload(int uid);
void Delete(int uid) override; void Delete(int uid);
void UnloadAll() override; void UnloadAll();
void UnloadIf(std::function<bool(std::pair<const int, AccountData>)> fn) override; void UnloadIf(std::function<bool(std::pair<const int, AccountData const&>)> fn);
//accessors and mutators //accessors and mutators
AccountData* Get(int uid) override; AccountData* Get(int uid);
int GetLoadedCount() override; int GetLoadedCount();
int GetTotalCount() override; int GetTotalCount();
std::map<int, AccountData>* GetContainer() override; std::map<int, AccountData>* GetContainer();
sqlite3* SetDatabase(sqlite3* db); sqlite3* SetDatabase(sqlite3* db);
sqlite3* GetDatabase(); sqlite3* GetDatabase();
@@ -65,6 +61,8 @@ private:
AccountManager() = default; AccountManager() = default;
~AccountManager() = default; ~AccountManager() = default;
//members
std::map<int, AccountData> elementMap;
sqlite3* database = nullptr; sqlite3* database = nullptr;
}; };
+33
View File
@@ -0,0 +1,33 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#include "character_api.hpp"
#include "character_data.hpp"
static const luaL_Reg characterLib[] = {
{nullptr, nullptr}
};
LUAMOD_API int openCharacterAPI(lua_State* L) {
luaL_newlib(L, characterLib);
return 1;
}
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef CHARACTERAPI_HPP_
#define CHARACTERAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_CHARACTER_API "character"
LUAMOD_API int openCharacterAPI(lua_State* L);
#endif
+24
View File
@@ -30,9 +30,33 @@
#include <string> #include <string>
#include <cmath> #include <cmath>
#include <iostream>
class CharacterData: public Entity { class CharacterData: public Entity {
public: public:
CharacterData() = default; CharacterData() = default;
CharacterData(CharacterData const& rhs) {
std::cerr << "Character copy detected" << std::endl;
owner = rhs.owner;
handle = rhs.handle;
avatar = rhs.avatar;
//entity stuff
roomIndex = rhs.roomIndex;
origin = rhs.origin;
motion = rhs.motion;
}
CharacterData(CharacterData&& rhs) {
std::cerr << "Character move detected" << std::endl;
owner = rhs.owner;
handle = rhs.handle;
avatar = rhs.avatar;
//entity stuff
roomIndex = rhs.roomIndex;
origin = rhs.origin;
motion = rhs.motion;
}
~CharacterData() = default; ~CharacterData() = default;
//accessors and mutators //accessors and mutators
+2 -2
View File
@@ -229,7 +229,7 @@ void CharacterManager::UnloadAll() {
elementMap.clear(); elementMap.clear();
} }
void CharacterManager::UnloadIf(std::function<bool(std::pair<const int, CharacterData>)> fn) { void CharacterManager::UnloadIf(std::function<bool(std::pair<const int, CharacterData const&>)> fn) {
std::map<int, CharacterData>::iterator it = elementMap.begin(); std::map<int, CharacterData>::iterator it = elementMap.begin();
while (it != elementMap.end()) { while (it != elementMap.end()) {
if (fn(*it)) { if (fn(*it)) {
@@ -253,7 +253,7 @@ CharacterData* CharacterManager::Get(int uid) {
return nullptr; return nullptr;
} }
return &it->second; return &(it->second);
} }
int CharacterManager::GetLoadedCount() { int CharacterManager::GetLoadedCount() {
+14 -16
View File
@@ -24,7 +24,6 @@
#include "character_data.hpp" #include "character_data.hpp"
#include "singleton.hpp" #include "singleton.hpp"
#include "manager_interface.hpp"
#if defined(__MINGW32__) #if defined(__MINGW32__)
#include "sqlite3/sqlite3.h" #include "sqlite3/sqlite3.h"
@@ -35,26 +34,23 @@
#include <functional> #include <functional>
#include <map> #include <map>
class CharacterManager: class CharacterManager: public Singleton<CharacterManager> {
public Singleton<CharacterManager>,
public ManagerInterface<CharacterData, int, std::string, std::string>
{
public: public:
//common public methods //common public methods
int Create(int owner, std::string handle, std::string avatar) override; int Create(int owner, std::string handle, std::string avatar);
int Load(int owner, std::string handle, std::string avatar) override; int Load(int owner, std::string handle, std::string avatar);
int Save(int uid) override; int Save(int uid);
void Unload(int uid) override; void Unload(int uid);
void Delete(int uid) override; void Delete(int uid);
void UnloadAll() override; void UnloadAll();
void UnloadIf(std::function<bool(std::pair<const int, CharacterData>)> fn) override; void UnloadIf(std::function<bool(std::pair<const int, CharacterData const&>)> fn);
//accessors and mutators //accessors and mutators
CharacterData* Get(int uid) override; CharacterData* Get(int uid);
int GetLoadedCount() override; int GetLoadedCount();
int GetTotalCount() override; int GetTotalCount();
std::map<int, CharacterData>* GetContainer() override; std::map<int, CharacterData>* GetContainer();
sqlite3* SetDatabase(sqlite3* db); sqlite3* SetDatabase(sqlite3* db);
sqlite3* GetDatabase(); sqlite3* GetDatabase();
@@ -65,6 +61,8 @@ private:
CharacterManager() = default; CharacterManager() = default;
~CharacterManager() = default; ~CharacterManager() = default;
//members
std::map<int, CharacterData> elementMap;
sqlite3* database = nullptr; sqlite3* database = nullptr;
}; };
@@ -0,0 +1,33 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#include "character_manager_api.hpp"
#include "character_manager.hpp"
static const luaL_Reg characterManagerLib[] = {
{nullptr, nullptr}
};
LUAMOD_API int openCharacterManagerAPI(lua_State* L) {
luaL_newlib(L, characterManagerLib);
return 1;
}
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef CHARACTERMANAGERAPI_HPP_
#define CHARACTERMANAGERAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_CHARACTER_MANAGER_API "character_manager"
LUAMOD_API int openCharacterManagerAPI(lua_State* L);
#endif
+1 -2
View File
@@ -73,12 +73,11 @@ void ClientManager::UnloadAll() {
elementMap.clear(); elementMap.clear();
} }
void ClientManager::UnloadIf(std::function<bool(std::pair<const int, ClientData>)> fn) { void ClientManager::UnloadIf(std::function<bool(std::pair<const int, ClientData const&>)> fn) {
std::map<int, ClientData>::iterator it = elementMap.begin(); std::map<int, ClientData>::iterator it = elementMap.begin();
while (it != elementMap.end()) { while (it != elementMap.end()) {
if (fn(*it)) { if (fn(*it)) {
it = elementMap.erase(it); it = elementMap.erase(it);
//TODO: ? disconnect, unload characters, notify other clients
} }
else { else {
++it; ++it;
+12 -18
View File
@@ -23,35 +23,32 @@
#define CLIENTMANAGER_HPP_ #define CLIENTMANAGER_HPP_
#include "client_data.hpp" #include "client_data.hpp"
#include "manager_interface.hpp"
#include "server_packet.hpp" #include "server_packet.hpp"
#include "singleton.hpp" #include "singleton.hpp"
#include "SDL/SDL_net.h" #include "SDL/SDL_net.h"
#include <functional> #include <functional>
#include <map>
class ClientManager: class ClientManager: public Singleton<ClientManager> {
public Singleton<ClientManager>,
public ManagerInterface<ClientData, IPaddress>
{
public: public:
//methods //methods
int CheckConnections(); int CheckConnections();
void HandlePong(ServerPacket* const argPacket); void HandlePong(ServerPacket* const argPacket);
//common public methods //common public methods
int Create(IPaddress) override; int Create(IPaddress);
void Unload(int uid) override; void Unload(int uid);
void UnloadAll() override; void UnloadAll();
void UnloadIf(std::function<bool(std::pair<const int, ClientData>)> fn) override; void UnloadIf(std::function<bool(std::pair<const int, ClientData const&>)> fn);
//accessors & mutators //accessors & mutators
ClientData* Get(int uid) override; ClientData* Get(int uid);
int GetLoadedCount() override; int GetLoadedCount();
int GetTotalCount() override; int GetTotalCount();
std::map<int, ClientData>* GetContainer() override; std::map<int, ClientData>* GetContainer();
private: private:
friend Singleton<ClientManager>; friend Singleton<ClientManager>;
@@ -59,11 +56,8 @@ private:
ClientManager() = default; ClientManager() = default;
~ClientManager() = default; ~ClientManager() = default;
//EMPTY //members
int Load(IPaddress) override { return -1; } std::map<int, ClientData> elementMap;
int Save(int uid) override { return -1; }
void Delete(int uid) override { return; }
int counter = 0; int counter = 0;
}; };
+1 -1
View File
@@ -38,7 +38,7 @@ public:
protected: protected:
Entity() = default; Entity() = default;
~Entity() = default; virtual ~Entity() = default;
int roomIndex = -1; int roomIndex = -1;
Vector2 origin; Vector2 origin;
+77
View File
@@ -0,0 +1,77 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#include "entity_api.hpp"
#include "entity.hpp"
static int setRoomIndex(lua_State* L) {
Entity* entity = static_cast<Entity*>(lua_touserdata(L, 1));
entity->SetRoomIndex(lua_tointeger(L, 2));
return 0;
}
static int setOrigin(lua_State* L) {
Entity* entity = static_cast<Entity*>(lua_touserdata(L, 1));
entity->SetOrigin({lua_tonumber(L, 2), lua_tonumber(L, 3)});
return 0;
}
static int setMotion(lua_State* L) {
Entity* entity = static_cast<Entity*>(lua_touserdata(L, 1));
entity->SetMotion({lua_tonumber(L, 2), lua_tonumber(L, 3)});
return 0;
}
static int getRoomIndex(lua_State* L) {
Entity* entity = static_cast<Entity*>(lua_touserdata(L, 1));
lua_pushinteger(L, entity->GetRoomIndex());
return 1;
}
static int getOrigin(lua_State* L) {
Entity* entity = static_cast<Entity*>(lua_touserdata(L, 1));
lua_pushnumber(L, entity->GetOrigin().x);
lua_pushnumber(L, entity->GetOrigin().y);
return 2;
}
static int getMotion(lua_State* L) {
Entity* entity = static_cast<Entity*>(lua_touserdata(L, 1));
lua_pushnumber(L, entity->GetOrigin().x);
lua_pushnumber(L, entity->GetOrigin().y);
return 2;
}
static const luaL_Reg entityLib[] = {
{"SetRoomIndex", setRoomIndex},
{"SetOrigin", setOrigin},
{"SetMotion", setMotion},
{"GetRoomIndex", getRoomIndex},
{"GetOrigin", getOrigin},
{"GetMotion", getMotion},
{nullptr, nullptr}
};
LUAMOD_API int openEntityAPI(lua_State* L) {
luaL_newlib(L, entityLib);
return 1;
}
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef ENTITYAPI_HPP_
#define ENTITYAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_ENTITY_API "entity"
LUAMOD_API int openEntityAPI(lua_State* L);
#endif
+2
View File
@@ -42,6 +42,7 @@
#include "map_system_api.hpp" #include "map_system_api.hpp"
#include "room_system_api.hpp" #include "room_system_api.hpp"
#include "waypoint_system_api.hpp"
//these libs are loaded by lua.c and are readily available to any Lua program //these libs are loaded by lua.c and are readily available to any Lua program
static const luaL_Reg loadedlibs[] = { static const luaL_Reg loadedlibs[] = {
@@ -64,6 +65,7 @@ static const luaL_Reg loadedlibs[] = {
static const luaL_Reg preloadedlibs[] = { static const luaL_Reg preloadedlibs[] = {
{TORTUGA_MAP_SYSTEM_API, openMapSystemAPI}, {TORTUGA_MAP_SYSTEM_API, openMapSystemAPI},
{TORTUGA_ROOM_SYSTEM_API, openRoomSystemAPI}, {TORTUGA_ROOM_SYSTEM_API, openRoomSystemAPI},
{TORTUGA_WAYPOINT_SYSTEM_API, openWaypointSystemAPI},
{NULL, NULL} {NULL, NULL}
}; };
+3 -3
View File
@@ -26,10 +26,10 @@
#include "character_manager.hpp" #include "character_manager.hpp"
#include "client_manager.hpp" #include "client_manager.hpp"
#include "config_utility.hpp" #include "config_utility.hpp"
#include "door_manager.hpp"
#include "monster_manager.hpp" #include "monster_manager.hpp"
#include "room_manager.hpp" #include "room_manager.hpp"
#include "udp_network_utility.hpp" #include "udp_network_utility.hpp"
#include "waypoint_manager.hpp"
#include <stdexcept> #include <stdexcept>
#include <iostream> #include <iostream>
@@ -43,10 +43,10 @@ int main(int argc, char* argv[]) {
CharacterManager::CreateSingleton(); CharacterManager::CreateSingleton();
ClientManager::CreateSingleton(); ClientManager::CreateSingleton();
ConfigUtility::CreateSingleton(); ConfigUtility::CreateSingleton();
DoorManager::CreateSingleton();
MonsterManager::CreateSingleton(); MonsterManager::CreateSingleton();
RoomManager::CreateSingleton(); RoomManager::CreateSingleton();
UDPNetworkUtility::CreateSingleton(); UDPNetworkUtility::CreateSingleton();
WaypointManager::CreateSingleton();
//call the server's routines //call the server's routines
ServerApplication::CreateSingleton(); ServerApplication::CreateSingleton();
@@ -63,10 +63,10 @@ int main(int argc, char* argv[]) {
CharacterManager::DeleteSingleton(); CharacterManager::DeleteSingleton();
ClientManager::DeleteSingleton(); ClientManager::DeleteSingleton();
ConfigUtility::DeleteSingleton(); ConfigUtility::DeleteSingleton();
DoorManager::DeleteSingleton();
MonsterManager::DeleteSingleton(); MonsterManager::DeleteSingleton();
RoomManager::DeleteSingleton(); RoomManager::DeleteSingleton();
UDPNetworkUtility::DeleteSingleton(); UDPNetworkUtility::DeleteSingleton();
WaypointManager::DeleteSingleton();
} }
catch(exception& e) { catch(exception& e) {
cerr << "Fatal exception thrown: " << e.what() << endl; cerr << "Fatal exception thrown: " << e.what() << endl;
+2 -2
View File
@@ -1,5 +1,5 @@
#include directories #include directories
INCLUDES+=. accounts characters clients doors entities monsters rooms server_utilities ../common/debugging ../common/gameplay ../common/map ../common/network ../common/network/packet_types ../common/utilities INCLUDES+=. accounts characters clients entities monsters rooms server_utilities waypoints ../common/debugging ../common/gameplay ../common/map ../common/network ../common/network/packet_types ../common/utilities
#libraries #libraries
#the order of the $(LIBS) is important, at least for MinGW #the order of the $(LIBS) is important, at least for MinGW
@@ -28,11 +28,11 @@ all: $(OBJ) $(OUT)
$(MAKE) -C accounts $(MAKE) -C accounts
$(MAKE) -C characters $(MAKE) -C characters
$(MAKE) -C clients $(MAKE) -C clients
$(MAKE) -C doors
$(MAKE) -C entities $(MAKE) -C entities
$(MAKE) -C monsters $(MAKE) -C monsters
$(MAKE) -C rooms $(MAKE) -C rooms
$(MAKE) -C server_utilities $(MAKE) -C server_utilities
$(MAKE) -C waypoints
$(CXX) $(CXXFLAGS) -o $(OUT) $(OBJ) $(LIBS) $(CXX) $(CXXFLAGS) -o $(OUT) $(OBJ) $(LIBS)
$(OBJ): | $(OBJDIR) $(OBJ): | $(OBJDIR)
+33
View File
@@ -0,0 +1,33 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#include "monster_api.hpp"
#include "monster_data.hpp"
static const luaL_Reg monsterLib[] = {
{nullptr, nullptr}
};
LUAMOD_API int openMonsterAPI(lua_State* L) {
luaL_newlib(L, monsterLib);
return 1;
}
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef MONSTERAPI_HPP_
#define MONSTERAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_MONSTER_API "monster"
LUAMOD_API int openMonsterAPI(lua_State* L);
#endif
+1 -1
View File
@@ -45,7 +45,7 @@ void MonsterManager::UnloadAll() {
//TODO //TODO
} }
void MonsterManager::UnloadIf(std::function<bool(std::pair<const int, MonsterData>)> fn) { void MonsterManager::UnloadIf(std::function<bool(std::pair<const int, MonsterData const&>)> fn) {
//TODO //TODO
} }
+15 -16
View File
@@ -22,7 +22,6 @@
#ifndef MONSTERMANAGER_HPP_ #ifndef MONSTERMANAGER_HPP_
#define MONSTERMANAGER_HPP_ #define MONSTERMANAGER_HPP_
#include "manager_interface.hpp"
#include "monster_data.hpp" #include "monster_data.hpp"
#include "singleton.hpp" #include "singleton.hpp"
@@ -35,28 +34,26 @@
#endif #endif
#include <functional> #include <functional>
#include <map>
#include <string> #include <string>
class MonsterManager: class MonsterManager: public Singleton<MonsterManager> {
public Singleton<MonsterManager>,
public ManagerInterface<MonsterData, std::string>
{
public: public:
//common public methods //common public methods
int Create(std::string) override; int Create(std::string);
int Load(std::string) override; int Load(std::string);
int Save(int uid) override; int Save(int uid);
void Unload(int uid) override; void Unload(int uid);
void Delete(int uid) override; void Delete(int uid);
void UnloadAll() override; void UnloadAll();
void UnloadIf(std::function<bool(std::pair<const int, MonsterData>)> fn) override; void UnloadIf(std::function<bool(std::pair<const int, MonsterData const&>)> fn);
//accessors & mutators //accessors & mutators
MonsterData* Get(int uid) override; MonsterData* Get(int uid);
int GetLoadedCount() override; int GetLoadedCount();
int GetTotalCount() override; int GetTotalCount();
std::map<int, MonsterData>* GetContainer() override; std::map<int, MonsterData>* GetContainer();
//hooks //hooks
sqlite3* SetDatabase(sqlite3* db); sqlite3* SetDatabase(sqlite3* db);
@@ -70,6 +67,8 @@ private:
MonsterManager() = default; MonsterManager() = default;
~MonsterManager() = default; ~MonsterManager() = default;
//members
std::map<int, MonsterData> elementMap;
sqlite3* database = nullptr; sqlite3* database = nullptr;
lua_State* lua = nullptr; lua_State* lua = nullptr;
}; };
+33
View File
@@ -0,0 +1,33 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#include "monster_manager_api.hpp"
#include "monster_manager.hpp"
static const luaL_Reg monsterManagerLib[] = {
{nullptr, nullptr}
};
LUAMOD_API int openMonsterManagerAPI(lua_State* L) {
luaL_newlib(L, monsterManagerLib);
return 1;
}
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef MONSTERMANAGERAPI_HPP_
#define MONSTERMANAGERAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_MONSTER_MANAGER_API "monster_manager"
LUAMOD_API int openMonsterManagerAPI(lua_State* L);
#endif
+6 -7
View File
@@ -25,25 +25,25 @@
static int setRoomName(lua_State* L) { static int setRoomName(lua_State* L) {
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1)); RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
room->SetRoomName(lua_tostring(L, 2)); room->SetName(lua_tostring(L, 2));
return 0; return 0;
} }
static int getRoomName(lua_State* L) { static int getRoomName(lua_State* L) {
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1)); RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
lua_pushstring(L, room->GetRoomName().c_str()); lua_pushstring(L, room->GetName().c_str());
return 1; return 1;
} }
static int setTilesetName(lua_State* L) { static int setTilesetName(lua_State* L) {
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1)); RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
room->SetTilesetName(lua_tostring(L, 2)); room->SetTileset(lua_tostring(L, 2));
return 0; return 0;
} }
static int getTilesetName(lua_State* L) { static int getTilesetName(lua_State* L) {
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1)); RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
lua_pushstring(L, room->GetTilesetName().c_str()); lua_pushstring(L, room->GetTileset().c_str());
return 1; return 1;
} }
@@ -56,7 +56,6 @@ static int getPager(lua_State* L) {
static int initialize(lua_State* L) { static int initialize(lua_State* L) {
//set the members of the given room //set the members of the given room
RoomData* room = static_cast<RoomData*>(lua_touserdata(L, 1)); RoomData* room = static_cast<RoomData*>(lua_touserdata(L, 1));
room->SetRoomName(lua_tostring(L, 2));
//set the refs of these parameters (backwards, since it pops from the top of the stack) //set the refs of these parameters (backwards, since it pops from the top of the stack)
room->GetPager()->SetUnloadReference(luaL_ref(L, LUA_REGISTRYINDEX)); room->GetPager()->SetUnloadReference(luaL_ref(L, LUA_REGISTRYINDEX));
@@ -70,8 +69,8 @@ static int initialize(lua_State* L) {
static const luaL_Reg roomLib[] = { static const luaL_Reg roomLib[] = {
{"GetPager",getPager}, {"GetPager",getPager},
{"SetRoomName", setRoomName}, {"SetName", setRoomName},
{"GetRoomName", getRoomName}, {"GetName", getRoomName},
{"SetTileset", setTilesetName}, {"SetTileset", setTilesetName},
{"GetTileset", getTilesetName}, {"GetTileset", getTilesetName},
{"Initialize", initialize}, {"Initialize", initialize},
+4 -4
View File
@@ -21,19 +21,19 @@
*/ */
#include "room_data.hpp" #include "room_data.hpp"
std::string RoomData::SetRoomName(std::string s) { std::string RoomData::SetName(std::string s) {
return roomName = s; return roomName = s;
} }
std::string RoomData::GetRoomName() { std::string RoomData::GetName() {
return roomName; return roomName;
} }
std::string RoomData::SetTilesetName(std::string s) { std::string RoomData::SetTileset(std::string s) {
return tilesetName = s; return tilesetName = s;
} }
std::string RoomData::GetTilesetName() { std::string RoomData::GetTileset() {
return tilesetName; return tilesetName;
} }
+6 -4
View File
@@ -40,15 +40,17 @@ public:
~RoomData() = default; ~RoomData() = default;
//accessors and mutators //accessors and mutators
std::string SetRoomName(std::string s); std::string SetName(std::string);
std::string GetRoomName(); std::string GetName();
std::string SetTilesetName(std::string s); std::string SetTileset(std::string);
std::string GetTilesetName(); std::string GetTileset();
RegionPagerLua* GetPager(); RegionPagerLua* GetPager();
std::list<Entity*>* GetEntityList(); std::list<Entity*>* GetEntityList();
//TODO: triggers for unload, save, per-second, player enter, player exit, etc.
private: private:
friend class RoomManager; friend class RoomManager;
+62 -13
View File
@@ -24,37 +24,73 @@
#include "room_api.hpp" #include "room_api.hpp"
#include <stdexcept> #include <stdexcept>
#include <sstream>
//debug
#include <iostream>
//------------------------- //-------------------------
//public access methods //public access methods
//------------------------- //-------------------------
int RoomManager::Create(std::string roomName) { int RoomManager::Create(std::string roomName, std::string tileset) {
//create the room //create the room
RoomData* newRoom = &elementMap[counter]; //implicitly constructs the element RoomData* newRoom = &elementMap[counter]; //implicitly constructs the element
newRoom->SetRoomName(roomName); newRoom->SetName(roomName);
newRoom->SetTileset(tileset);
newRoom->pager.SetLuaState(lua); newRoom->pager.SetLuaState(lua);
//finish the routine //finish the routine
return counter++; return counter++;
} }
void RoomManager::Unload(int uid) { void RoomManager::PushEntity(Entity const* entity) {
//find the room if (!entity) {
std::map<int, RoomData>::iterator it = elementMap.find(uid); throw(std::runtime_error("Failed to push null entity"));
if (it == elementMap.end()) {
return;
} }
//free the memory std::map<int, RoomData>::iterator it = elementMap.find(entity->GetRoomIndex());
elementMap.erase(uid);
if (it == elementMap.end()) {
std::ostringstream msg;
// msg << "Failed to push entity; Room index not found: " << entity->GetRoomIndex() << std::endl;
throw(std::runtime_error(msg.str()));
}
it->second.entityList.push_back(const_cast<Entity*>(entity));
std::cout << "\troom[" << it->first << "].entityList.size(): " << it->second.entityList.size() << std::endl;
std::cout << "\tEntity: " << int(entity) << "," << int(it->second.entityList.front()) << std::endl;
}
void RoomManager::PopEntity(Entity const* entity) {
if (!entity) {
throw(std::runtime_error("Failed to pop null entity"));
}
std::map<int, RoomData>::iterator it = elementMap.find(entity->GetRoomIndex());
if (it == elementMap.end()) {
std::ostringstream msg;
msg << "Failed to pop entity; Room index not found: " << entity->GetRoomIndex() << std::endl;
throw(std::runtime_error(msg.str()));
}
it->second.entityList.remove_if([entity](Entity* ptr) -> bool {
bool b = (entity == ptr);
std::cout << "\tmatch(" << int(ptr) << "," << int(entity) << "): " << b << std::endl;
return b;
});
std::cout << "\troom[" << it->first << "].entityList.size(): " << it->second.entityList.size() << std::endl;
} }
void RoomManager::UnloadAll() { void RoomManager::UnloadAll() {
elementMap.clear(); elementMap.clear();
} }
void RoomManager::UnloadIf(std::function<bool(std::pair<const int,RoomData>)> fn) { void RoomManager::UnloadIf(std::function<bool(std::pair<const int, RoomData const&>)> fn) {
std::map<int, RoomData>::iterator it = elementMap.begin(); std::map<int, RoomData>::iterator it = elementMap.begin();
while (it != elementMap.end()) { while (it != elementMap.end()) {
if (fn(*it)) { if (fn(*it)) {
@@ -76,14 +112,27 @@ RoomData* RoomManager::Get(int uid) {
return &it->second; return &it->second;
} }
int RoomManager::GetLoadedCount() { RoomData* RoomManager::Get(std::string name) {
return elementMap.size(); for (std::map<int, RoomData>::iterator it = elementMap.begin(); it != elementMap.end(); ++it) {
if (it->second.GetName() == name) {
return &it->second;
}
}
return nullptr;
} }
int RoomManager::GetTotalCount() { int RoomManager::GetLoadedCount() {
return elementMap.size(); return elementMap.size();
} }
std::map<int, RoomData>* RoomManager::GetContainer() { std::map<int, RoomData>* RoomManager::GetContainer() {
return &elementMap; return &elementMap;
} }
lua_State* RoomManager::SetLuaState(lua_State* L) {
return lua = L;
}
lua_State* RoomManager::GetLuaState() {
return lua;
}
+19 -19
View File
@@ -22,9 +22,9 @@
#ifndef ROOMMANAGER_HPP_ #ifndef ROOMMANAGER_HPP_
#define ROOMMANAGER_HPP_ #define ROOMMANAGER_HPP_
#include "entity.hpp"
#include "room_data.hpp" #include "room_data.hpp"
#include "singleton.hpp" #include "singleton.hpp"
#include "manager_interface.hpp"
#if defined(__MINGW32__) #if defined(__MINGW32__)
#include "lua/lua.hpp" #include "lua/lua.hpp"
@@ -32,27 +32,29 @@
#include "lua.hpp" #include "lua.hpp"
#endif #endif
class RoomManager: #include <functional>
public Singleton<RoomManager>, #include <map>
public ManagerInterface<RoomData, std::string>
{ class RoomManager: public Singleton<RoomManager> {
public: public:
//common public methods //common public methods
int Create(std::string) override; int Create(std::string name, std::string tileset);
void Unload(int uid) override;
void UnloadAll() override; void PushEntity(Entity const* entity);
void UnloadIf(std::function<bool(std::pair<const int,RoomData>)> fn) override; void PopEntity(Entity const* entity);
void UnloadAll();
void UnloadIf(std::function<bool(std::pair<const int, RoomData const&>)> fn);
//accessors and mutators //accessors and mutators
RoomData* Get(int uid) override; RoomData* Get(int uid);
int GetLoadedCount() override; RoomData* Get(std::string name);
int GetTotalCount() override; int GetLoadedCount();
std::map<int, RoomData>* GetContainer() override; std::map<int, RoomData>* GetContainer();
//hooks //hooks
lua_State* SetLuaState(lua_State* L) { return lua = L; } lua_State* SetLuaState(lua_State* L);
lua_State* GetLuaState() { return lua; } lua_State* GetLuaState();
private: private:
friend Singleton<RoomManager>; friend Singleton<RoomManager>;
@@ -60,10 +62,8 @@ private:
RoomManager() = default; RoomManager() = default;
~RoomManager() = default; ~RoomManager() = default;
int Load(std::string) override { return -1; } //members
int Save(int uid) override { return -1; } std::map<int, RoomData> elementMap;
void Delete(int uid) override { }
lua_State* lua = nullptr; lua_State* lua = nullptr;
int counter = 0; int counter = 0;
}; };
+42 -6
View File
@@ -24,31 +24,67 @@
#include "room_manager.hpp" #include "room_manager.hpp"
int createRoom(lua_State* L) { int createRoom(lua_State* L) {
//create & get the room //create & get the room
RoomManager& roomMgr = RoomManager::GetSingleton(); RoomManager& roomMgr = RoomManager::GetSingleton();
int uid = roomMgr.Create(lua_tostring(L, 1)); int uid = roomMgr.Create(lua_tostring(L, 1), lua_tostring(L, 2));
RoomData* room = roomMgr.Get(uid); RoomData* room = roomMgr.Get(uid);
//TODO: initialization parameters here?
//return room, uid //return room, uid
lua_pushlightuserdata(L, static_cast<void*>(room)); lua_pushlightuserdata(L, static_cast<void*>(room));
lua_pushinteger(L, uid); lua_pushinteger(L, uid); //for debugging, mostly
return 2; return 2;
} }
int unloadRoom(lua_State* L) { int unloadRoom(lua_State* L) {
//TODO: check authorization for room deletion
RoomManager& roomMgr = RoomManager::GetSingleton(); RoomManager& roomMgr = RoomManager::GetSingleton();
roomMgr.Unload(lua_tointeger(L, 1));
switch(lua_type(L, 1)) {
case LUA_TNUMBER: {
//number
int uid = lua_tointeger(L, 1);
roomMgr.UnloadIf([uid](std::pair<int, RoomData> it){
return it.first == uid;
});
}
break;
case LUA_TSTRING: {
//name
std::string name = lua_tostring(L, 1);
roomMgr.UnloadIf([name](std::pair<int, RoomData> it){
return it.second.GetName() == name;
});
}
break;
case LUA_TLIGHTUSERDATA: {
//the room itself
std::string name = static_cast<RoomData*>(lua_touserdata(L, 1))->GetName();
roomMgr.UnloadIf([name](std::pair<int, RoomData> it){
return it.second.GetName() == name;
});
}
break;
}
return 0; return 0;
} }
int getRoom(lua_State* L) { int getRoom(lua_State* L) {
//TODO: integer vs name for getRoom() //TODO: integer vs name for getRoom()
RoomManager& roomMgr = RoomManager::GetSingleton(); RoomManager& roomMgr = RoomManager::GetSingleton();
RoomData* room = nullptr;
RoomData* room = roomMgr.Get(lua_tointeger(L, 1)); switch(lua_type(L, 1)) {
case LUA_TNUMBER:
//number
room = roomMgr.Get(lua_tointeger(L, 1));
break;
case LUA_TSTRING:
//name
room = roomMgr.Get(lua_tostring(L, 1));
break;
}
if (room) { if (room) {
lua_pushlightuserdata(L, static_cast<void*>(room)); lua_pushlightuserdata(L, static_cast<void*>(room));
+2 -2
View File
@@ -26,9 +26,9 @@
#include "account_manager.hpp" #include "account_manager.hpp"
#include "character_manager.hpp" #include "character_manager.hpp"
#include "client_manager.hpp" #include "client_manager.hpp"
#include "door_manager.hpp"
#include "monster_manager.hpp" #include "monster_manager.hpp"
#include "room_manager.hpp" #include "room_manager.hpp"
#include "waypoint_manager.hpp"
//utilities //utilities
#include "config_utility.hpp" #include "config_utility.hpp"
@@ -123,9 +123,9 @@ private:
AccountManager& accountMgr = AccountManager::GetSingleton(); AccountManager& accountMgr = AccountManager::GetSingleton();
CharacterManager& characterMgr = CharacterManager::GetSingleton(); CharacterManager& characterMgr = CharacterManager::GetSingleton();
ClientManager& clientMgr = ClientManager::GetSingleton(); ClientManager& clientMgr = ClientManager::GetSingleton();
DoorManager& doorMgr = DoorManager::GetSingleton();
MonsterManager& monsterMgr = MonsterManager::GetSingleton(); MonsterManager& monsterMgr = MonsterManager::GetSingleton();
RoomManager& roomMgr = RoomManager::GetSingleton(); RoomManager& roomMgr = RoomManager::GetSingleton();
WaypointManager& waypointMgr = WaypointManager::GetSingleton();
ConfigUtility& config = ConfigUtility::GetSingleton(); ConfigUtility& config = ConfigUtility::GetSingleton();
UDPNetworkUtility& network = UDPNetworkUtility::GetSingleton(); UDPNetworkUtility& network = UDPNetworkUtility::GetSingleton();
+17 -2
View File
@@ -45,6 +45,9 @@ void ServerApplication::HandleCharacterCreate(CharacterPacket* const argPacket)
return; return;
} }
//push this character to the rooms
// roomMgr.PushEntity(static_cast<Entity*>(characterMgr.Get(characterIndex)));
//pump this character to all clients //pump this character to all clients
CharacterPacket newPacket; CharacterPacket newPacket;
CopyCharacterToPacket(&newPacket, characterIndex); CopyCharacterToPacket(&newPacket, characterIndex);
@@ -87,6 +90,7 @@ void ServerApplication::HandleCharacterDelete(CharacterPacket* const argPacket)
} }
//delete the character //delete the character
// roomMgr.PopEntity(static_cast<Entity*>(characterMgr.Get(characterIndex)));
characterMgr.Delete(characterIndex); characterMgr.Delete(characterIndex);
//pump character delete //pump character delete
@@ -105,7 +109,7 @@ void ServerApplication::HandleCharacterLoad(CharacterPacket* const argPacket) {
if (characterIndex == -1) { if (characterIndex == -1) {
msg << "Character already loaded: "; msg << "Character already loaded: ";
} }
if (characterIndex == -1) { if (characterIndex == -2) {
msg << "Character name is taken: "; msg << "Character name is taken: ";
} }
msg << argPacket->handle; msg << argPacket->handle;
@@ -119,6 +123,10 @@ void ServerApplication::HandleCharacterLoad(CharacterPacket* const argPacket) {
return; return;
} }
//push this character to the rooms
std::cout << "pushing index " << characterIndex << std::endl;
roomMgr.PushEntity(static_cast<Entity*>(characterMgr.Get(characterIndex)));
//pump this character to all clients //pump this character to all clients
CharacterPacket newPacket; CharacterPacket newPacket;
CopyCharacterToPacket(&newPacket, characterIndex); CopyCharacterToPacket(&newPacket, characterIndex);
@@ -150,6 +158,8 @@ void ServerApplication::HandleCharacterUnload(CharacterPacket* const argPacket)
} }
//unload the character //unload the character
std::cout << "poping index " << argPacket->characterIndex << std::endl;
roomMgr.PopEntity(static_cast<Entity*>(characterData));
characterMgr.Unload(argPacket->characterIndex); characterMgr.Unload(argPacket->characterIndex);
//pump character delete //pump character delete
@@ -190,12 +200,17 @@ void ServerApplication::HandleCharacterSetRoom(CharacterPacket* const argPacket)
return; return;
} }
//pop from the rooms
roomMgr.PopEntity(static_cast<Entity*>(characterData));
//set the character's room, zero it's origin, zero it's motion //set the character's room, zero it's origin, zero it's motion
//TODO: Set the origin here
characterData->SetRoomIndex(argPacket->roomIndex); characterData->SetRoomIndex(argPacket->roomIndex);
characterData->SetOrigin({0, 0}); characterData->SetOrigin({0, 0});
characterData->SetMotion({0, 0}); characterData->SetMotion({0, 0});
//push to the rooms
roomMgr.PushEntity(static_cast<Entity*>(characterData));
//update the clients //update the clients
CharacterPacket newPacket; CharacterPacket newPacket;
CopyCharacterToPacket(&newPacket, argPacket->characterIndex); CopyCharacterToPacket(&newPacket, argPacket->characterIndex);
+3 -2
View File
@@ -78,7 +78,7 @@ void ServerApplication::Init(int argc, char* argv[]) {
std::cout << "Initialized lua" << std::endl; std::cout << "Initialized lua" << std::endl;
//prepend config["dir.scripts"] to the module path //append config["dir.scripts"] to the module path
if (config["dir.scripts"].size() > 0) { if (config["dir.scripts"].size() > 0) {
//get the original path //get the original path
lua_getglobal(luaState, "package"); lua_getglobal(luaState, "package");
@@ -105,6 +105,7 @@ void ServerApplication::Init(int argc, char* argv[]) {
characterMgr.SetDatabase(database); characterMgr.SetDatabase(database);
roomMgr.SetLuaState(luaState); roomMgr.SetLuaState(luaState);
waypointMgr.SetLuaState(luaState);
std::cout << "Internal managers initialized" << std::endl; std::cout << "Internal managers initialized" << std::endl;
@@ -201,9 +202,9 @@ void ServerApplication::Quit() {
accountMgr.UnloadAll(); accountMgr.UnloadAll();
characterMgr.UnloadAll(); characterMgr.UnloadAll();
clientMgr.UnloadAll(); clientMgr.UnloadAll();
doorMgr.UnloadAll();
monsterMgr.UnloadAll(); monsterMgr.UnloadAll();
roomMgr.UnloadAll(); roomMgr.UnloadAll();
waypointMgr.UnloadAll();
//APIs //APIs
lua_close(luaState); lua_close(luaState);
+8 -3
View File
@@ -97,7 +97,7 @@ void ServerApplication::HandleShutdownRequest(ClientPacket* const argPacket) {
//------------------------- //-------------------------
void ServerApplication::FullClientUnload(int index) { void ServerApplication::FullClientUnload(int index) {
clientMgr.UnloadIf([&](std::pair<const int, ClientData> client) -> bool { clientMgr.UnloadIf([&](std::pair<const int, ClientData const&> client) -> bool {
//skip the wrong clients //skip the wrong clients
if (client.first != index) { if (client.first != index) {
return false; return false;
@@ -120,7 +120,7 @@ void ServerApplication::FullClientUnload(int index) {
} }
void ServerApplication::FullAccountUnload(int index) { void ServerApplication::FullAccountUnload(int index) {
accountMgr.UnloadIf([&](std::pair<const int, AccountData> account) -> bool { accountMgr.UnloadIf([&](std::pair<const int, AccountData const&> account) -> bool {
//skip the wrong accounts //skip the wrong accounts
if (account.first != index) { if (account.first != index) {
return false; return false;
@@ -143,12 +143,17 @@ void ServerApplication::FullAccountUnload(int index) {
} }
void ServerApplication::FullCharacterUnload(int index) { void ServerApplication::FullCharacterUnload(int index) {
characterMgr.UnloadIf([&](std::pair<const int, CharacterData> character) -> bool { //BUG: #38 UnloadIf() lambas are taking COPIES of data structures, rather than the structures themselves
characterMgr.UnloadIf([&](std::pair<const int, CharacterData const&> character) -> bool {
//skip the wrong characters //skip the wrong characters
if (character.first != index) { if (character.first != index) {
return false; return false;
} }
//pop from the rooms
std::cout << "popping index " << index << std::endl;
roomMgr.PopEntity(reinterpret_cast<Entity const*>(&character.second));
//pump character unload //pump character unload
CharacterPacket newPacket; CharacterPacket newPacket;
newPacket.type = SerialPacketType::CHARACTER_DELETE; newPacket.type = SerialPacketType::CHARACTER_DELETE;
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#include "waypoint_api.hpp"
#include "waypoint_data.hpp"
//TODO: Can I alias the entity API for this?
static const luaL_Reg waypointLib[] = {
{nullptr, nullptr}
};
LUAMOD_API int openWaypointAPI(lua_State* L) {
luaL_newlib(L, waypointLib);
return 1;
}
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef WAYPOINTAPI_HPP_
#define WAYPOINTAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_WAYPOINT_API "waypoint"
LUAMOD_API int openWaypointAPI(lua_State* L);
#endif
@@ -19,20 +19,12 @@
* 3. This notice may not be removed or altered from any source * 3. This notice may not be removed or altered from any source
* distribution. * distribution.
*/ */
#include "door_data.hpp" #include "waypoint_data.hpp"
std::string DoorData::SetRoomName(std::string s) { int WaypointData::SetTriggerReference(int i) {
return roomName = s; return triggerRef = i;
} }
Vector2 DoorData::SetDestPosition(Vector2 v) { int WaypointData::GetTriggerReference() {
return destPosition = v; return triggerRef;
} }
std::string DoorData::GetRoomName() {
return roomName;
}
Vector2 DoorData::GetDestPosition() {
return destPosition;
}
@@ -19,31 +19,31 @@
* 3. This notice may not be removed or altered from any source * 3. This notice may not be removed or altered from any source
* distribution. * distribution.
*/ */
#ifndef DOORDATA_HPP_ #ifndef WAYPOINTDATA_HPP_
#define DOORDATA_HPP_ #define WAYPOINTDATA_HPP_
#include "entity.hpp" #include "entity.hpp"
#include "vector2.hpp"
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#include <string> #include <string>
class DoorData: public Entity { class WaypointData: public Entity {
public: public:
DoorData() = default; WaypointData() = default;
~DoorData() = default; ~WaypointData() = default;
//accessors & mutators int SetTriggerReference(int i);
std::string SetRoomName(std::string); int GetTriggerReference();
Vector2 SetDestPosition(Vector2);
std::string GetRoomName();
Vector2 GetDestPosition();
private: private:
friend class DoorManager; friend class WaypointManager;
std::string roomName; int triggerRef = LUA_NOREF;
Vector2 destPosition;
}; };
#endif #endif
@@ -19,48 +19,48 @@
* 3. This notice may not be removed or altered from any source * 3. This notice may not be removed or altered from any source
* distribution. * distribution.
*/ */
#include "door_manager.hpp" #include "waypoint_manager.hpp"
int DoorManager::Create(std::string, Vector2) { int WaypointManager::Create() {
//TODO //TODO
} }
int DoorManager::Load(std::string, Vector2) { int WaypointManager::Load() {
//TODO //TODO
} }
int DoorManager::Save(int uid) { int WaypointManager::Save(int uid) {
//TODO //TODO
} }
void DoorManager::Unload(int uid) { void WaypointManager::Unload(int uid) {
//TODO //TODO
} }
void DoorManager::Delete(int uid) { void WaypointManager::Delete(int uid) {
//TODO //TODO
} }
void DoorManager::UnloadAll() { void WaypointManager::UnloadAll() {
//TODO //TODO
} }
void DoorManager::UnloadIf(std::function<bool(std::pair<const int, DoorData>)> fn) { void WaypointManager::UnloadIf(std::function<bool(std::pair<const int, WaypointData const&>)> fn) {
//TODO //TODO
} }
DoorData* DoorManager::Get(int uid) { WaypointData* WaypointManager::Get(int uid) {
//TODO //TODO
} }
int DoorManager::GetLoadedCount() { int WaypointManager::GetLoadedCount() {
//TODO //TODO
} }
int DoorManager::GetTotalCount() { int WaypointManager::GetTotalCount() {
//TODO //TODO
} }
std::map<int, DoorData>* DoorManager::GetContainer() { std::map<int, WaypointData>* WaypointManager::GetContainer() {
//TODO //TODO
} }
@@ -19,43 +19,56 @@
* 3. This notice may not be removed or altered from any source * 3. This notice may not be removed or altered from any source
* distribution. * distribution.
*/ */
#ifndef DOORMANAGER_HPP_ #ifndef WAYPOINTMANAGER_HPP_
#define DOORMANAGER_HPP_ #define WAYPOINTMANAGER_HPP_
#include "door_data.hpp" #include "waypoint_data.hpp"
#include "manager_interface.hpp"
#include "singleton.hpp" #include "singleton.hpp"
#include "vector2.hpp" #include "vector2.hpp"
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#include <functional> #include <functional>
#include <map>
#include <string> #include <string>
class DoorManager: //TODO: should waypoints be managed on a per-room basis?
public Singleton<DoorManager>, class WaypointManager: public Singleton<WaypointManager> {
public ManagerInterface<DoorData, std::string, Vector2>
{
public: public:
//common public methods //common public methods
int Create(std::string, Vector2) override; int Create();
int Load(std::string, Vector2) override; int Load();
int Save(int uid) override; int Save(int uid);
void Unload(int uid) override; void Unload(int uid);
void Delete(int uid) override; void Delete(int uid);
void UnloadAll() override; void UnloadAll();
void UnloadIf(std::function<bool(std::pair<const int, DoorData>)> fn) override; void UnloadIf(std::function<bool(std::pair<const int, WaypointData const&>)> fn);
//accessors & mutators //accessors & mutators
DoorData* Get(int uid) override; WaypointData* Get(int uid);
int GetLoadedCount() override; int GetLoadedCount();
int GetTotalCount() override; int GetTotalCount();
std::map<int, DoorData>* GetContainer() override; std::map<int, WaypointData>* GetContainer();
//hooks
lua_State* SetLuaState(lua_State* L) { return lua = L; }
lua_State* GetLuaState() { return lua; }
private: private:
friend Singleton<DoorManager>; friend Singleton<WaypointManager>;
DoorManager() = default; WaypointManager() = default;
~DoorManager() = default; ~WaypointManager() = default;
//members
std::map<int, WaypointData> elementMap;
lua_State* lua = nullptr;
int counter = 0;
}; };
#endif #endif
+33
View File
@@ -0,0 +1,33 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#include "waypoint_manager_api.hpp"
#include "waypoint_manager.hpp"
static const luaL_Reg waypointManagerLib[] = {
{nullptr, nullptr}
};
LUAMOD_API int openWaypointManagerAPI(lua_State* L) {
luaL_newlib(L, waypointManagerLib);
return 1;
}
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef WAYPOINTMANAGERAPI_HPP_
#define WAYPOINTMANAGERAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_WAYPOINT_MANAGER_API "waypoint_manager"
LUAMOD_API int openWaypointManagerAPI(lua_State* L);
#endif
@@ -19,37 +19,37 @@
* 3. This notice may not be removed or altered from any source * 3. This notice may not be removed or altered from any source
* distribution. * distribution.
*/ */
#ifndef MANAGERINTERFACE_HPP_ #include "waypoint_system_api.hpp"
#define MANAGERINTERFACE_HPP_
#include <functional> //all waypoint API headers
#include <map> #include "waypoint_api.hpp"
#include "waypoint_manager_api.hpp"
template<typename T, typename... Arguments> //useful "globals"
class ManagerInterface { //...
public:
//common public methods
virtual int Create(Arguments... parameters) = 0;
virtual int Load(Arguments... parameters) = 0;
virtual int Save(int uid) = 0;
virtual void Unload(int uid) = 0;
virtual void Delete(int uid) = 0;
virtual void UnloadAll() = 0; //This mimics linit.c to create a nested collection of all waypoint modules.
virtual void UnloadIf(std::function<bool(std::pair<const int, T>)> fn) = 0; static const luaL_Reg funcs[] = {
{nullptr, nullptr}
//accessors & mutators
virtual T* Get(int uid) = 0;
virtual int GetLoadedCount() = 0;
virtual int GetTotalCount() = 0; //can be an alias of GetLoadedCount()
virtual std::map<int, T>* GetContainer() = 0;
protected:
ManagerInterface() = default;
~ManagerInterface() = default;
//members
std::map<int, T> elementMap;
}; };
#endif static const luaL_Reg libs[] = {
{"Waypoint", openWaypointAPI},
{"WaypointManager", openWaypointManagerAPI},
{nullptr, nullptr}
};
int openWaypointSystemAPI(lua_State* L) {
//create the table
luaL_newlibtable(L, libs);
//push the "global" functions
luaL_setfuncs(L, funcs, 0);
//push the substable
for (const luaL_Reg* lib = libs; lib->func; lib++) {
lib->func(L);
lua_setfield(L, -2, lib->name);
}
return 1;
}
+34
View File
@@ -0,0 +1,34 @@
/* Copyright: (c) Kayne Ruse 2013-2015
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
*
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
*
* 3. This notice may not be removed or altered from any source
* distribution.
*/
#ifndef WAYPOINTSYSTEMAPI_HPP_
#define WAYPOINTSYSTEMAPI_HPP_
#if defined(__MINGW32__)
#include "lua/lua.hpp"
#else
#include "lua.hpp"
#endif
#define TORTUGA_WAYPOINT_SYSTEM_API "waypoint_system"
LUAMOD_API int openWaypointSystemAPI(lua_State* L);
#endif
+12 -24
View File
@@ -1,31 +1,19 @@
TODO: Account system needs salts & hashes for security TODO: In need of script APIs (list)
TODO: Character system might need an API * Characters
TODO: Door system needs an API * Monsters
TODO: monster system needs an API * Waypoints
TODO: rewrite the main body of the server TODO: Account passwords (list)
TODO: I need a better way to handle the statistics * backbone account server OR
* social network login OR
* ...
* salts & hashes
TODO: Waypoints, with positions and trigger zones (collision areas) for doors, monster spawns, etc.
TODO: Fix shoddy movement TODO: Fix shoddy movement
TODO: Handle statistics server-side
TODO: Periodic mass server saves TODO: Periodic mass server saves
TODO: join vs login TODO: Remove the big "Shut Down" button (currently broken...)
TODO: Remove the big "Shut Down" button
TODO: Make a way for the server owner to control the server directly TODO: Make a way for the server owner to control the server directly
TODO: The TileSheet class should implement the surface itself TODO: The TileSheet class should implement the surface itself
TODO: Passwords/Authentication
TODO: Time delay for requesting region packets TODO: Time delay for requesting region packets
TODO: A proper logging system TODO: A proper logging system
-------------------------
The entities might need an API, which interfaces with all entity types (characters, monsters, doors, etc.)
The Entity base class handles position (including room) and motion, so something generic like this could be used (or aliased by other APIs)
entity:
-------------------------
Lobby:
JOIN_REQUEST -> JOIN_RESPONSE, JOIN_REJECTION
LOGIN_REQUEST -> LOGIN_RESPONSE, LOGIN_REJECTION