Compare commits
30 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| f9936f6107 | |||
| 905af46731 | |||
| 8b0bc76a9f | |||
| fb2d49f1e0 | |||
| cc6981e35f | |||
| f9a5f60969 | |||
| b74a5aabcd | |||
| 7c88392cf3 | |||
| 20b121766a | |||
| f32b8a9b4f | |||
| ccb7adbd10 | |||
| 8e7af9ce88 | |||
| 752f8f82f9 | |||
| 1f2d0b8e76 | |||
| ec409c8177 | |||
| 82d5a5c181 | |||
| 420d39d467 | |||
| e2e2e243d4 | |||
| 5d0f9e1bb8 | |||
| d3f855c69b | |||
| 8749d1fd93 | |||
| 7205d6692c | |||
| 7b9c016082 | |||
| 235f3b57e0 | |||
| f23b929f8a | |||
| 48b9a9b264 | |||
| d7196df760 | |||
| 957458d489 | |||
| 3b24aae422 | |||
| a751531e18 |
@@ -318,6 +318,7 @@ void ClientApplication::ProcessEvents() {
|
||||
#include "options_menu.hpp"
|
||||
#include "lobby_menu.hpp"
|
||||
#include "world.hpp"
|
||||
#include "combat.hpp"
|
||||
#include "disconnected_screen.hpp"
|
||||
|
||||
void ClientApplication::ProcessSceneSignal(SceneSignal signal) {
|
||||
@@ -341,6 +342,9 @@ void ClientApplication::ProcessSceneSignal(SceneSignal signal) {
|
||||
case SceneSignal::WORLD:
|
||||
activeScene = new World(&clientIndex, &accountIndex);
|
||||
break;
|
||||
case SceneSignal::COMBAT:
|
||||
activeScene = new Combat(&clientIndex, &accountIndex);
|
||||
break;
|
||||
case SceneSignal::DISCONNECTEDSCREEN:
|
||||
activeScene = new DisconnectedScreen();
|
||||
break;
|
||||
|
||||
@@ -0,0 +1,145 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "image.hpp"
|
||||
|
||||
#include <list>
|
||||
#include <map>
|
||||
#include <string>
|
||||
|
||||
template<typename T = class Image>
|
||||
class CompositeImage {
|
||||
public:
|
||||
CompositeImage() = default;
|
||||
~CompositeImage() = default;
|
||||
|
||||
void Load(SDL_Renderer* const, std::string spriteDir, std::list<std::string> nameList);
|
||||
void SetTextures(std::map<std::string, Image>& templateImages);
|
||||
void Free();
|
||||
|
||||
void DrawTo(SDL_Renderer* const, Sint16 x, Sint16 y, double scaleX = 1.0, double scaleY = 1.0);
|
||||
|
||||
//accessors & mutators
|
||||
T* Find(std::string name);
|
||||
|
||||
bool Enable(std::string name);
|
||||
bool Disable(std::string name);
|
||||
void EnableAll();
|
||||
void DisableAll();
|
||||
|
||||
std::map<std::string, std::pair<bool, T>>* GetTemplateImages();
|
||||
|
||||
private:
|
||||
std::map<std::string, std::pair<bool, T>> imageMap;
|
||||
};
|
||||
|
||||
|
||||
template<typename T>
|
||||
void CompositeImage<T>::Load(SDL_Renderer* const renderer, std::string spriteDir, std::list<std::string> nameList) {
|
||||
for (auto& it : nameList) {
|
||||
imageMap[it].first = true;
|
||||
imageMap[it].second.Load(renderer, spriteDir + it);
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void CompositeImage<T>::SetTextures(std::map<std::string, Image>& templateImages) {
|
||||
for (auto& it : templateImages) {
|
||||
imageMap[it.first].first = true;
|
||||
imageMap[it.first].second.SetTexture(it.second.GetTexture());
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void CompositeImage<T>::Free() {
|
||||
imageMap.clear();
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void CompositeImage<T>::DrawTo(SDL_Renderer* const dest, Sint16 x, Sint16 y, double scaleX, double scaleY) {
|
||||
//draw all members, regardless of internal ordering
|
||||
for (auto& it : imageMap) {
|
||||
if (it.second.first) {
|
||||
it.second.second.DrawTo(dest, x, y, scaleX, scaleY);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//-------------------------
|
||||
//accessors & mutators
|
||||
//-------------------------
|
||||
|
||||
template<typename T>
|
||||
T* CompositeImage<T>::Find(std::string name) {
|
||||
auto it = imageMap.find(name);
|
||||
if (it == imageMap.end()) {
|
||||
return nullptr;
|
||||
}
|
||||
else {
|
||||
return &it->second.second;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
bool CompositeImage<T>::Enable(std::string name) {
|
||||
auto it = imageMap.find(name);
|
||||
if (it == imageMap.end()) {
|
||||
return false;
|
||||
}
|
||||
else {
|
||||
imageMap[name].first = true;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
bool CompositeImage<T>::Disable(std::string name) {
|
||||
auto it = imageMap.find(name);
|
||||
if (it == imageMap.end()) {
|
||||
return false;
|
||||
}
|
||||
else {
|
||||
imageMap[name].first = false;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void CompositeImage<T>::EnableAll() {
|
||||
for (auto& it : imageMap) {
|
||||
it.second.first = true;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void CompositeImage<T>::DisableAll() {
|
||||
for (auto& it : imageMap) {
|
||||
it.second.first = false;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
std::map<std::string, std::pair<bool, T>>* CompositeImage<T>::GetTemplateImages() {
|
||||
return &imageMap;
|
||||
}
|
||||
@@ -0,0 +1,94 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "barrier_manager.hpp"
|
||||
|
||||
void BarrierManager::DrawTo(SDL_Renderer* const dest, Sint16 x, Sint16 y, double scaleX, double scaleY) {
|
||||
for (auto& it : elementMap) {
|
||||
it.second.DrawTo(dest, x, y);
|
||||
}
|
||||
}
|
||||
|
||||
void BarrierManager::LoadBaseImage(SDL_Renderer* renderer, std::string fname) {
|
||||
baseImage.Load(renderer, fname);
|
||||
}
|
||||
|
||||
void BarrierManager::UnloadBaseImage() {
|
||||
baseImage.Free();
|
||||
}
|
||||
|
||||
void BarrierManager::LoadTemplateImages(SDL_Renderer* renderer, std::string spriteDir, std::list<std::string> names) {
|
||||
//sprite names are file names only
|
||||
for (auto& it : names) {
|
||||
templateImages.emplace(it, Image(renderer, spriteDir + it));
|
||||
}
|
||||
}
|
||||
|
||||
void BarrierManager::UnloadTemplateImages() {
|
||||
templateImages.clear();
|
||||
}
|
||||
|
||||
BaseBarrier* BarrierManager::Create(int index) {
|
||||
elementMap.emplace(index, BaseBarrier(baseImage, templateImages));
|
||||
return &elementMap[index];
|
||||
}
|
||||
|
||||
void BarrierManager::Unload(int i) {
|
||||
elementMap.erase(i);
|
||||
}
|
||||
|
||||
void BarrierManager::UnloadAll() {
|
||||
elementMap.clear();
|
||||
}
|
||||
|
||||
void BarrierManager::UnloadIf(std::function<bool(std::pair<const int, BaseBarrier const&>)> fn) {
|
||||
std::map<int, BaseBarrier>::iterator it = elementMap.begin();
|
||||
while (it != elementMap.end()) {
|
||||
if (fn(*it)) {
|
||||
it = elementMap.erase(it);
|
||||
}
|
||||
else {
|
||||
++it;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int BarrierManager::Size() {
|
||||
return elementMap.size();
|
||||
}
|
||||
|
||||
BaseBarrier* BarrierManager::Find(int i) {
|
||||
std::map<int, BaseBarrier>::iterator it = elementMap.find(i);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
std::map<int, BaseBarrier>* BarrierManager::GetContainer() {
|
||||
return &elementMap;
|
||||
}
|
||||
|
||||
std::map<std::string, Image>* BarrierManager::GetTemplateContainer() {
|
||||
return &templateImages;
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "base_barrier.hpp"
|
||||
|
||||
#include <list>
|
||||
#include <string>
|
||||
|
||||
class BarrierManager {
|
||||
public:
|
||||
BarrierManager() = default;
|
||||
~BarrierManager() = default;
|
||||
|
||||
void DrawTo(SDL_Renderer* const, Sint16 x, Sint16 y, double scaleX = 1.0, double scaleY = 1.0);
|
||||
|
||||
//NOTE: don't use these while you have barriers loaded
|
||||
void LoadBaseImage(SDL_Renderer* renderer, std::string fname);
|
||||
void UnloadBaseImage();
|
||||
void LoadTemplateImages(SDL_Renderer* renderer, std::string spriteDir, std::list<std::string> names);
|
||||
void UnloadTemplateImages();
|
||||
|
||||
BaseBarrier* Create(int index);
|
||||
void Unload(int i);
|
||||
void UnloadAll();
|
||||
void UnloadIf(std::function<bool(std::pair<const int, BaseBarrier const&>)> fn);
|
||||
|
||||
int Size();
|
||||
|
||||
BaseBarrier* Find(int i);
|
||||
std::map<int, BaseBarrier>* GetContainer();
|
||||
std::map<std::string, Image>* GetTemplateContainer();
|
||||
|
||||
private:
|
||||
Image baseImage;
|
||||
std::map<std::string, Image> templateImages;
|
||||
std::map<int, BaseBarrier> elementMap;
|
||||
};
|
||||
@@ -0,0 +1,105 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "base_barrier.hpp"
|
||||
|
||||
#include "config_utility.hpp"
|
||||
|
||||
#include <cstring>
|
||||
#include <sstream>
|
||||
#include <stdexcept>
|
||||
|
||||
BaseBarrier::BaseBarrier(Image& argBaseImage, std::map<std::string, Image>& templateImages) {
|
||||
baseImage.SetTexture(argBaseImage.GetTexture());
|
||||
composite.SetTextures(templateImages);
|
||||
memset(status, 0, sizeof(int) * 8);
|
||||
CorrectSprite();
|
||||
}
|
||||
|
||||
BaseBarrier::~BaseBarrier() {
|
||||
//
|
||||
}
|
||||
|
||||
void BaseBarrier::CorrectSprite() {
|
||||
//TODO: link status to sprite
|
||||
for (int i = 0; i < 8; i++) {
|
||||
//setup the name
|
||||
std::ostringstream os;
|
||||
os << "slot " << i+1;
|
||||
|
||||
switch(status[i]) {
|
||||
case 0:
|
||||
composite.Disable(os.str() + " green.png");
|
||||
composite.Disable(os.str() + " red.png");
|
||||
break;
|
||||
case 1:
|
||||
composite.Enable(os.str() + " green.png");
|
||||
composite.Disable(os.str() + " red.png");
|
||||
break;
|
||||
case 2:
|
||||
composite.Disable(os.str() + " green.png");
|
||||
composite.Enable(os.str() + " red.png");
|
||||
break;
|
||||
default: {
|
||||
std::ostringstream os;
|
||||
os << "index " << i << ", value " << status[i] << std::endl;
|
||||
throw(std::runtime_error("Unknown graphical status in barrier; " + os.str()));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void BaseBarrier::Update() {
|
||||
//
|
||||
}
|
||||
|
||||
void BaseBarrier::DrawTo(SDL_Renderer* const dest, int camX, int camY) {
|
||||
//ignore the default sprite for now
|
||||
baseImage.DrawTo(dest, origin.x - camX, origin.y - camY);
|
||||
composite.DrawTo(dest, origin.x - camX, origin.y - camY);
|
||||
}
|
||||
|
||||
int BaseBarrier::SetStatus(int k, int v) {
|
||||
if (k >= 8 || k < 0) {
|
||||
return -1;
|
||||
}
|
||||
return status[k] = v;
|
||||
}
|
||||
|
||||
int BaseBarrier::FindStatus(int k) {
|
||||
if (k >= 8 || k < 0) {
|
||||
return -1;
|
||||
}
|
||||
return status[k];
|
||||
}
|
||||
|
||||
int* BaseBarrier::SetStatusArray(int* ptr) {
|
||||
memcpy(status, ptr, sizeof(int) * 8);
|
||||
return status;
|
||||
}
|
||||
|
||||
int* BaseBarrier::GetStatusArray() {
|
||||
return status;
|
||||
}
|
||||
|
||||
CompositeImage<>* BaseBarrier::GetComposite() {
|
||||
return &composite;
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "entity.hpp"
|
||||
|
||||
#include "composite_image.hpp"
|
||||
|
||||
class BaseBarrier: public Entity {
|
||||
public:
|
||||
BaseBarrier() = default;
|
||||
BaseBarrier(Image& baseImage, std::map<std::string, Image>& templateImages);
|
||||
virtual ~BaseBarrier();
|
||||
|
||||
void CorrectSprite();
|
||||
void Update();
|
||||
void DrawTo(SDL_Renderer* const, int camX, int camY);
|
||||
|
||||
int SetStatus(int, int);
|
||||
int FindStatus(int);
|
||||
|
||||
int* SetStatusArray(int*);
|
||||
int* GetStatusArray();
|
||||
|
||||
CompositeImage<>* GetComposite();
|
||||
|
||||
protected:
|
||||
//metadata
|
||||
int status[8];
|
||||
|
||||
Image baseImage;
|
||||
CompositeImage<> composite;
|
||||
};
|
||||
@@ -50,14 +50,14 @@ BoundingBox Entity::SetBounds(BoundingBox b) {
|
||||
return bounds = b;
|
||||
}
|
||||
|
||||
Vector2 Entity::GetOrigin() {
|
||||
Vector2 Entity::GetOrigin() const {
|
||||
return origin;
|
||||
}
|
||||
|
||||
Vector2 Entity::GetMotion() {
|
||||
Vector2 Entity::GetMotion() const {
|
||||
return motion;
|
||||
}
|
||||
|
||||
BoundingBox Entity::GetBounds() {
|
||||
BoundingBox Entity::GetBounds() const {
|
||||
return bounds;
|
||||
}
|
||||
@@ -39,9 +39,9 @@ public:
|
||||
Vector2 SetMotion(Vector2 v);
|
||||
BoundingBox SetBounds(BoundingBox b);
|
||||
|
||||
Vector2 GetOrigin();
|
||||
Vector2 GetMotion();
|
||||
BoundingBox GetBounds();
|
||||
Vector2 GetOrigin() const;
|
||||
Vector2 GetMotion() const;
|
||||
BoundingBox GetBounds() const;
|
||||
|
||||
protected:
|
||||
Entity() = default;
|
||||
|
||||
@@ -33,5 +33,6 @@ enum SceneSignal {
|
||||
OPTIONSMENU,
|
||||
LOBBYMENU,
|
||||
WORLD,
|
||||
COMBAT,
|
||||
DISCONNECTEDSCREEN,
|
||||
};
|
||||
@@ -0,0 +1,77 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "combat.hpp"
|
||||
|
||||
//Public access members
|
||||
Combat::Combat(int* const argClientIndex, int* const argAccountIndex) {
|
||||
//
|
||||
}
|
||||
|
||||
Combat::~Combat() {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::RenderFrame(SDL_Renderer* renderer) {
|
||||
//
|
||||
}
|
||||
|
||||
//frame phases
|
||||
void Combat::FrameStart() {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::Update() {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::FrameEnd() {
|
||||
//
|
||||
}
|
||||
|
||||
//input events
|
||||
void Combat::QuitEvent() {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::MouseMotion(SDL_MouseMotionEvent const& event) {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::MouseButtonDown(SDL_MouseButtonEvent const& event) {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::MouseButtonUp(SDL_MouseButtonEvent const& event) {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::MouseWheel(SDL_MouseWheelEvent const& event) {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::KeyDown(SDL_KeyboardEvent const& event) {
|
||||
//
|
||||
}
|
||||
|
||||
void Combat::KeyUp(SDL_KeyboardEvent const& event) {
|
||||
//
|
||||
}
|
||||
@@ -0,0 +1,48 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "base_scene.hpp"
|
||||
|
||||
class Combat: public BaseScene {
|
||||
public:
|
||||
//Public access members
|
||||
Combat(int* const argClientIndex, int* const argAccountIndex);
|
||||
~Combat();
|
||||
|
||||
void RenderFrame(SDL_Renderer* renderer) override;
|
||||
|
||||
private:
|
||||
//frame phases
|
||||
void FrameStart() override;
|
||||
void Update() override;
|
||||
void FrameEnd() override;
|
||||
|
||||
//input events
|
||||
void QuitEvent();
|
||||
void MouseMotion(SDL_MouseMotionEvent const& event) override;
|
||||
void MouseButtonDown(SDL_MouseButtonEvent const& event) override;
|
||||
void MouseButtonUp(SDL_MouseButtonEvent const& event) override;
|
||||
void MouseWheel(SDL_MouseWheelEvent const& event) override;
|
||||
void KeyDown(SDL_KeyboardEvent const& event) override;
|
||||
void KeyUp(SDL_KeyboardEvent const& event) override;
|
||||
};
|
||||
@@ -22,6 +22,7 @@
|
||||
#include "world.hpp"
|
||||
|
||||
#include "channels.hpp"
|
||||
#include "culling_defines.hpp"
|
||||
#include "ip_operators.hpp"
|
||||
#include "fatal_error.hpp"
|
||||
|
||||
@@ -97,7 +98,28 @@ World::World(int* const argClientIndex, int* const argAccountIndex):
|
||||
SDL_RenderGetLogicalSize(GetRenderer(), &camera.width, &camera.height);
|
||||
|
||||
//debug
|
||||
//
|
||||
std::list<std::string> slotNames = {
|
||||
"slot 1 green.png",
|
||||
"slot 2 green.png",
|
||||
"slot 3 green.png",
|
||||
"slot 4 green.png",
|
||||
"slot 5 green.png",
|
||||
"slot 6 green.png",
|
||||
"slot 7 green.png",
|
||||
"slot 8 green.png",
|
||||
"slot 1 red.png",
|
||||
"slot 2 red.png",
|
||||
"slot 3 red.png",
|
||||
"slot 4 red.png",
|
||||
"slot 5 red.png",
|
||||
"slot 6 red.png",
|
||||
"slot 7 red.png",
|
||||
"slot 8 red.png"
|
||||
};
|
||||
barrierMgr.LoadBaseImage(GetRenderer(), config["dir.sprites"] + "barrier/base.png");
|
||||
barrierMgr.LoadTemplateImages(GetRenderer(), config["dir.sprites"] + "barrier/", slotNames);
|
||||
|
||||
std::cout << "Templates loaded: " << barrierMgr.GetTemplateContainer()->size() << std::endl;
|
||||
}
|
||||
|
||||
World::~World() {
|
||||
@@ -163,6 +185,42 @@ void World::Update() {
|
||||
return;
|
||||
}
|
||||
|
||||
//TODO: (0) regular query interval
|
||||
if (Clock::now() - queryTime > std::chrono::seconds(3)) {
|
||||
queryTime = Clock::now();
|
||||
//query the world state (room)
|
||||
CharacterPacket characterPacket;
|
||||
memset(&characterPacket, 0, MAX_PACKET_SIZE);
|
||||
characterPacket.type = SerialPacketType::QUERY_CHARACTER_EXISTS;
|
||||
characterPacket.roomIndex = roomIndex;
|
||||
network.SendTo(Channels::SERVER, &characterPacket);
|
||||
|
||||
CreaturePacket creaturePacket;
|
||||
creaturePacket.type = SerialPacketType::QUERY_CREATURE_EXISTS;
|
||||
creaturePacket.roomIndex = roomIndex;
|
||||
network.SendTo(Channels::SERVER, &creaturePacket);
|
||||
|
||||
BarrierPacket barrierPacket;
|
||||
barrierPacket.type = SerialPacketType::QUERY_BARRIER_EXISTS;
|
||||
barrierPacket.roomIndex = roomIndex;
|
||||
network.SendTo(Channels::SERVER, &barrierPacket);
|
||||
}
|
||||
|
||||
//cull creatures
|
||||
for (std::map<int, BaseCreature>::iterator it = creatureMap.begin(); it != creatureMap.end(); /* */) {
|
||||
if ( (localCharacter->GetOrigin() - it->second.GetOrigin()).Length() > INFLUENCE_RADIUS) {
|
||||
creatureMap.erase(it++);
|
||||
}
|
||||
else {
|
||||
it++;
|
||||
}
|
||||
}
|
||||
|
||||
//cull barriers
|
||||
barrierMgr.UnloadIf([&](std::pair<const int, BaseBarrier const&> barrierIt) -> bool {
|
||||
return (localCharacter->GetOrigin() - barrierIt.second.GetOrigin()).Length() > INFLUENCE_RADIUS;
|
||||
});
|
||||
|
||||
//get the collidable boxes
|
||||
std::list<BoundingBox> boxList = GenerateCollisionGrid(localCharacter, tileSheet.GetTileW(), tileSheet.GetTileH());
|
||||
|
||||
@@ -196,6 +254,7 @@ void World::RenderFrame(SDL_Renderer* renderer) {
|
||||
for (auto& it : creatureMap) {
|
||||
it.second.DrawTo(renderer, camera.x, camera.y);
|
||||
}
|
||||
barrierMgr.DrawTo(renderer, camera.x, camera.y);
|
||||
|
||||
//draw UI
|
||||
disconnectButton.DrawTo(renderer);
|
||||
@@ -412,6 +471,22 @@ void World::HandlePacket(SerialPacket* const argPacket) {
|
||||
hCreatureMovement(static_cast<CreaturePacket*>(argPacket));
|
||||
break;
|
||||
|
||||
//barrier management
|
||||
case SerialPacketType::BARRIER_UPDATE:
|
||||
hBarrierUpdate(static_cast<BarrierPacket*>(argPacket));
|
||||
break;
|
||||
|
||||
case SerialPacketType::BARRIER_CREATE:
|
||||
hBarrierCreate(static_cast<BarrierPacket*>(argPacket));
|
||||
break;
|
||||
case SerialPacketType::BARRIER_UNLOAD:
|
||||
hBarrierUnload(static_cast<BarrierPacket*>(argPacket));
|
||||
break;
|
||||
|
||||
case SerialPacketType::QUERY_BARRIER_EXISTS:
|
||||
hQueryBarrierExists(static_cast<BarrierPacket*>(argPacket));
|
||||
break;
|
||||
|
||||
//chat
|
||||
case SerialPacketType::TEXT_BROADCAST:
|
||||
hTextBroadcast(static_cast<TextPacket*>(argPacket));
|
||||
@@ -675,6 +750,9 @@ void World::hCharacterCreate(CharacterPacket* const argPacket) {
|
||||
if (character->GetOwner() == accountIndex) {
|
||||
localCharacter = static_cast<LocalCharacter*>(character);
|
||||
|
||||
//reset queries
|
||||
queryTime = Clock::now() - std::chrono::seconds(4); //back 4 seconds to trigger automatically
|
||||
|
||||
//focus the camera on this character's sprite
|
||||
camera.marginX = (camera.width / 2 - localCharacter->GetSprite()->GetClipW() / 2);
|
||||
camera.marginY = (camera.height/ 2 - localCharacter->GetSprite()->GetClipH() / 2);
|
||||
@@ -682,18 +760,6 @@ void World::hCharacterCreate(CharacterPacket* const argPacket) {
|
||||
//focus on this character's info
|
||||
characterIndex = argPacket->characterIndex;
|
||||
roomIndex = argPacket->roomIndex;
|
||||
|
||||
//query the world state (room)
|
||||
CharacterPacket characterPacket;
|
||||
memset(&characterPacket, 0, MAX_PACKET_SIZE);
|
||||
characterPacket.type = SerialPacketType::QUERY_CHARACTER_EXISTS;
|
||||
characterPacket.roomIndex = roomIndex;
|
||||
network.SendTo(Channels::SERVER, &characterPacket);
|
||||
|
||||
CreaturePacket creaturePacket;
|
||||
creaturePacket.type = SerialPacketType::QUERY_CREATURE_EXISTS;
|
||||
creaturePacket.roomIndex = roomIndex;
|
||||
network.SendTo(Channels::SERVER, &creaturePacket);
|
||||
}
|
||||
|
||||
//debug
|
||||
@@ -715,9 +781,10 @@ void World::hCharacterUnload(CharacterPacket* const argPacket) {
|
||||
camera.marginX = 0;
|
||||
camera.marginY = 0;
|
||||
|
||||
//clear the room
|
||||
//clear/reset the room
|
||||
roomIndex = -1;
|
||||
regionPager.UnloadAll();
|
||||
barrierMgr.UnloadAll();
|
||||
characterMap.clear();
|
||||
creatureMap.clear();
|
||||
}
|
||||
@@ -733,12 +800,12 @@ void World::hCharacterUnload(CharacterPacket* const argPacket) {
|
||||
void World::hQueryCharacterExists(CharacterPacket* const argPacket) {
|
||||
//prevent a double message about this player's character
|
||||
//TODO: why is this commented out?
|
||||
// if (argPacket->accountIndex == accountIndex) {
|
||||
// return;
|
||||
// }
|
||||
if (argPacket->accountIndex == accountIndex) {
|
||||
return;
|
||||
}
|
||||
|
||||
//ignore characters in a different room (sub-optimal)
|
||||
if (argPacket->roomIndex != roomIndex) {
|
||||
if (argPacket->roomIndex != roomIndex || (localCharacter->GetOrigin() - argPacket->origin).Length() > INFLUENCE_RADIUS) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -779,10 +846,18 @@ void World::hCharacterMovement(CharacterPacket* const argPacket) {
|
||||
//-------------------------
|
||||
|
||||
void World::hCreatureUpdate(CreaturePacket* const argPacket) {
|
||||
std::cout << "hCreatureUpdate" << std::endl;
|
||||
//TODO: (1) Authentication
|
||||
//BUGFIX: Sometimes crash on exit
|
||||
if (!localCharacter) {
|
||||
return;
|
||||
}
|
||||
|
||||
//check that this character exists
|
||||
//Cull creatures that are too far away
|
||||
if ( (localCharacter->GetOrigin() - argPacket->origin).Length() > INFLUENCE_RADIUS) {
|
||||
//ignore beyond 1000 units
|
||||
return;
|
||||
}
|
||||
|
||||
//check if this creature exists
|
||||
std::map<int, BaseCreature>::iterator creatureIt = creatureMap.find(argPacket->creatureIndex);
|
||||
if (creatureIt != creatureMap.end()) {
|
||||
//update the origin and motion, if there's a difference
|
||||
@@ -847,10 +922,12 @@ void World::hCreatureUnload(CreaturePacket* const argPacket) {
|
||||
}
|
||||
|
||||
void World::hQueryCreatureExists(CreaturePacket* const argPacket) {
|
||||
std::cout << "Creature Query" << std::endl;
|
||||
if (!localCharacter) {
|
||||
return;
|
||||
}
|
||||
|
||||
//ignore creatures in a different room (sub-optimal)
|
||||
if (argPacket->roomIndex != roomIndex) {
|
||||
if (argPacket->roomIndex != roomIndex || (localCharacter->GetOrigin() - argPacket->origin).Length() > INFLUENCE_RADIUS) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -881,6 +958,106 @@ void World::hCreatureMovement(CreaturePacket* const argPacket) {
|
||||
creatureIt->second.SetMotion(argPacket->motion);
|
||||
}
|
||||
|
||||
//-------------------------
|
||||
//barrier management
|
||||
//-------------------------
|
||||
|
||||
void World::hBarrierUpdate(BarrierPacket* const argPacket) {
|
||||
//BUGFIX: Sometimes crash on exit
|
||||
if (!localCharacter) {
|
||||
return;
|
||||
}
|
||||
|
||||
//Cull barriers that are too far away
|
||||
if ( (localCharacter->GetOrigin() - argPacket->origin).Length() > INFLUENCE_RADIUS) {
|
||||
//ignore beyond 1000 units
|
||||
return;
|
||||
}
|
||||
|
||||
//check if this barrier exists
|
||||
BaseBarrier* barrier = barrierMgr.Find(argPacket->barrierIndex);
|
||||
|
||||
if (!barrier) {
|
||||
hBarrierCreate(argPacket);
|
||||
return;
|
||||
}
|
||||
|
||||
//update the origin and motion, if there's a difference
|
||||
if (barrier->GetOrigin() != argPacket->origin) {
|
||||
barrier->SetOrigin(argPacket->origin);
|
||||
}
|
||||
barrier->SetStatusArray(argPacket->status);
|
||||
barrier->CorrectSprite();
|
||||
}
|
||||
|
||||
void World::hBarrierCreate(BarrierPacket* const argPacket) {
|
||||
//check for logic errors
|
||||
|
||||
//ignore barriers from other rooms
|
||||
if (roomIndex != argPacket->roomIndex) {
|
||||
//temporary error checking
|
||||
std::ostringstream msg;
|
||||
msg << "Barrier from the wrong room received: ";
|
||||
msg << "barrierIndex: " << argPacket->barrierIndex << ", roomIndex: " << argPacket->roomIndex;
|
||||
throw(std::runtime_error(msg.str()));
|
||||
}
|
||||
|
||||
BaseBarrier* barrier = barrierMgr.Find(argPacket->barrierIndex);
|
||||
|
||||
if (barrier) {
|
||||
std::ostringstream msg;
|
||||
msg << "Double barrier creation event; ";
|
||||
msg << "Index: " << argPacket->barrierIndex;
|
||||
throw(std::runtime_error(msg.str()));
|
||||
}
|
||||
|
||||
barrier = barrierMgr.Create(argPacket->barrierIndex);
|
||||
|
||||
//fill the barrier's info
|
||||
barrier->SetBounds(argPacket->bounds);
|
||||
barrier->SetOrigin(argPacket->origin);
|
||||
barrier->SetStatusArray(argPacket->status);
|
||||
barrier->CorrectSprite();
|
||||
|
||||
//debug
|
||||
std::cout << "Barrier Create, total: " << barrierMgr.Size() << std::endl;
|
||||
}
|
||||
|
||||
void World::hBarrierUnload(BarrierPacket* const argPacket) {
|
||||
//ignore if this barrier doesn't exist
|
||||
barrierMgr.Unload(argPacket->barrierIndex);
|
||||
|
||||
//debug
|
||||
std::cout << "Barrier Unload, total: " << barrierMgr.Size() << std::endl;
|
||||
}
|
||||
|
||||
void World::hQueryBarrierExists(BarrierPacket* const argPacket) {
|
||||
if (!localCharacter) {
|
||||
return;
|
||||
}
|
||||
|
||||
//ignore barriers in a different room (sub-optimal)
|
||||
if (argPacket->roomIndex != roomIndex || (localCharacter->GetOrigin() - argPacket->origin).Length() > INFLUENCE_RADIUS) {
|
||||
return;
|
||||
}
|
||||
|
||||
//implicitly create the element
|
||||
BaseBarrier* barrier = barrierMgr.Find(argPacket->barrierIndex);
|
||||
|
||||
if (!barrier) {
|
||||
barrier = barrierMgr.Create(argPacket->barrierIndex);
|
||||
}
|
||||
|
||||
//fill the barrier's info
|
||||
barrier->SetBounds(argPacket->bounds);
|
||||
barrier->SetOrigin(argPacket->origin);
|
||||
barrier->SetStatusArray(argPacket->status);
|
||||
barrier->CorrectSprite();
|
||||
|
||||
//debug
|
||||
std::cout << "Barrier Query, total: " << barrierMgr.Size() << std::endl;
|
||||
}
|
||||
|
||||
//-------------------------
|
||||
//chat
|
||||
//-------------------------
|
||||
@@ -902,6 +1079,11 @@ void World::hTextWhisper(TextPacket* const argPacket) {
|
||||
//-------------------------
|
||||
|
||||
void World::SendLocalCharacterMovement() {
|
||||
//BUGFIX: Sometimes crash on exit
|
||||
if (!localCharacter) {
|
||||
return;
|
||||
}
|
||||
|
||||
CharacterPacket newPacket;
|
||||
newPacket.type = SerialPacketType::CHARACTER_MOVEMENT;
|
||||
|
||||
|
||||
@@ -39,7 +39,9 @@
|
||||
#include "frame_rate.hpp"
|
||||
|
||||
//client
|
||||
#include "barrier_manager.hpp"
|
||||
#include "base_scene.hpp"
|
||||
#include "base_barrier.hpp"
|
||||
#include "base_creature.hpp"
|
||||
#include "local_character.hpp"
|
||||
|
||||
@@ -113,6 +115,12 @@ private:
|
||||
void hQueryCreatureExists(CreaturePacket* const);
|
||||
void hCreatureMovement(CreaturePacket* const);
|
||||
|
||||
//barrier management
|
||||
void hBarrierUpdate(BarrierPacket* const);
|
||||
void hBarrierCreate(BarrierPacket* const);
|
||||
void hBarrierUnload(BarrierPacket* const);
|
||||
void hQueryBarrierExists(BarrierPacket* const);
|
||||
|
||||
//chat
|
||||
//TODO: ui chat engine
|
||||
void hTextBroadcast(TextPacket* const);
|
||||
@@ -151,6 +159,7 @@ private:
|
||||
} camera;
|
||||
|
||||
//entities
|
||||
BarrierManager barrierMgr;
|
||||
std::map<int, BaseCharacter> characterMap;
|
||||
std::map<int, BaseCreature> creatureMap;
|
||||
LocalCharacter* localCharacter = nullptr;
|
||||
@@ -159,6 +168,7 @@ private:
|
||||
//TODO: (2) Heartbeat needs it's own utility
|
||||
typedef std::chrono::steady_clock Clock;
|
||||
Clock::time_point lastBeat = Clock::now();
|
||||
Clock::time_point queryTime = Clock::now() - std::chrono::seconds(4); //back 4 seconds to trigger automatically
|
||||
int attemptedBeats = 0;
|
||||
|
||||
//ugly references; I hate this
|
||||
|
||||
@@ -0,0 +1,28 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
//the bounds for the objects, mapped to the default sprites
|
||||
constexpr int BARRIER_BOUNDS_X = 0;
|
||||
constexpr int BARRIER_BOUNDS_Y = 0;
|
||||
constexpr int BARRIER_BOUNDS_WIDTH = 96;
|
||||
constexpr int BARRIER_BOUNDS_HEIGHT = 96;
|
||||
@@ -0,0 +1,39 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include <cmath>
|
||||
|
||||
//the speeds that the characters move
|
||||
constexpr double CREATURE_WALKING_SPEED = 1.0;
|
||||
constexpr double CREATURE_WALKING_MOD = 1.0/sqrt(2.0);
|
||||
constexpr double CREATURE_WALKING_NEGATIVE_MOD = 1.0 - CREATURE_WALKING_MOD;
|
||||
|
||||
//the bounds for the character objects, mapped to the default sprites
|
||||
constexpr int CREATURE_BOUNDS_X = 0;
|
||||
constexpr int CREATURE_BOUNDS_Y = 0;
|
||||
constexpr int CREATURE_BOUNDS_WIDTH = 32;
|
||||
constexpr int CREATURE_BOUNDS_HEIGHT = 32;
|
||||
|
||||
//the character's sprite format
|
||||
constexpr int CREATURE_CELLS_X = 4;
|
||||
constexpr int CREATURE_CELLS_Y = 4;
|
||||
@@ -0,0 +1,24 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
constexpr int INFLUENCE_RADIUS = 1000;
|
||||
@@ -161,7 +161,7 @@ SDL_Texture* Image::SetTexture(SDL_Texture* ptr) {
|
||||
clip.y = 0;
|
||||
if (SDL_QueryTexture(texture, nullptr, nullptr, &clip.w, &clip.h)) {
|
||||
std::ostringstream msg;
|
||||
msg << "Failed to record metadata for a newly image image";
|
||||
msg << "Failed to record metadata for a newly set image";
|
||||
msg << "; " << SDL_GetError();
|
||||
throw(std::runtime_error(msg.str()));
|
||||
}
|
||||
|
||||
@@ -0,0 +1,72 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "barrier_packet.hpp"
|
||||
|
||||
#include "serial_utility.hpp"
|
||||
|
||||
void serializeBarrier(void* buffer, BarrierPacket* packet) {
|
||||
serialCopy(&buffer, &packet->type, sizeof(SerialPacketType));
|
||||
|
||||
//identify the barrier
|
||||
serialCopy(&buffer, &packet->barrierIndex, sizeof(int));
|
||||
|
||||
//bounds
|
||||
serialCopy(&buffer, &packet->bounds.x, sizeof(int));
|
||||
serialCopy(&buffer, &packet->bounds.y, sizeof(int));
|
||||
serialCopy(&buffer, &packet->bounds.w, sizeof(int));
|
||||
serialCopy(&buffer, &packet->bounds.h, sizeof(int));
|
||||
|
||||
|
||||
//location
|
||||
serialCopy(&buffer, &packet->roomIndex, sizeof(int));
|
||||
serialCopy(&buffer, &packet->origin.x, sizeof(double));
|
||||
serialCopy(&buffer, &packet->origin.y, sizeof(double));
|
||||
serialCopy(&buffer, &packet->motion.x, sizeof(double));
|
||||
serialCopy(&buffer, &packet->motion.y, sizeof(double));
|
||||
|
||||
//graphical data
|
||||
serialCopy(&buffer, packet->status, sizeof(int) * 8);
|
||||
}
|
||||
|
||||
void deserializeBarrier(void* buffer, BarrierPacket* packet) {
|
||||
deserialCopy(&buffer, &packet->type, sizeof(SerialPacketType));
|
||||
|
||||
//identify the barrier
|
||||
deserialCopy(&buffer, &packet->barrierIndex, sizeof(int));
|
||||
|
||||
//bounds
|
||||
deserialCopy(&buffer, &packet->bounds.x, sizeof(int));
|
||||
deserialCopy(&buffer, &packet->bounds.y, sizeof(int));
|
||||
deserialCopy(&buffer, &packet->bounds.w, sizeof(int));
|
||||
deserialCopy(&buffer, &packet->bounds.h, sizeof(int));
|
||||
|
||||
|
||||
//location
|
||||
deserialCopy(&buffer, &packet->roomIndex, sizeof(int));
|
||||
deserialCopy(&buffer, &packet->origin.x, sizeof(double));
|
||||
deserialCopy(&buffer, &packet->origin.y, sizeof(double));
|
||||
deserialCopy(&buffer, &packet->motion.x, sizeof(double));
|
||||
deserialCopy(&buffer, &packet->motion.y, sizeof(double));
|
||||
|
||||
//graphical data
|
||||
deserialCopy(&buffer, packet->status, sizeof(int) * 8);
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "serial_packet_base.hpp"
|
||||
|
||||
#include "bounding_box.hpp"
|
||||
#include "vector2.hpp"
|
||||
|
||||
struct BarrierPacket : SerialPacketBase {
|
||||
//identify the barrier
|
||||
int barrierIndex;
|
||||
BoundingBox bounds;
|
||||
|
||||
//location
|
||||
int roomIndex;
|
||||
Vector2 origin;
|
||||
Vector2 motion;
|
||||
|
||||
//graphical data: 0 blank, 1 green, 2 red
|
||||
int status[8];
|
||||
};
|
||||
|
||||
void serializeBarrier(void* buffer, BarrierPacket* packet);
|
||||
void deserializeBarrier(void* buffer, BarrierPacket* packet);
|
||||
@@ -22,6 +22,7 @@
|
||||
#pragma once
|
||||
|
||||
#include "serial_packet_base.hpp"
|
||||
#include "barrier_packet.hpp"
|
||||
#include "character_packet.hpp"
|
||||
#include "client_packet.hpp"
|
||||
#include "creature_packet.hpp"
|
||||
@@ -33,7 +34,7 @@
|
||||
typedef SerialPacketBase SerialPacket;
|
||||
|
||||
//DOCS: NETWORK_VERSION is used to discern compatible servers and clients
|
||||
constexpr int NETWORK_VERSION = 20160321;
|
||||
constexpr int NETWORK_VERSION = 20160404;
|
||||
|
||||
union MaxPacket {
|
||||
CharacterPacket a;
|
||||
|
||||
@@ -142,6 +142,25 @@ enum class SerialPacketType {
|
||||
|
||||
FORMAT_END_CREATURE = 599,
|
||||
|
||||
//-------------------------
|
||||
//BarrierPacket
|
||||
// barrier index,
|
||||
// bounds,
|
||||
// roomIndex, origin, motion
|
||||
// status
|
||||
//-------------------------
|
||||
|
||||
FORMAT_COMBAT = 700,
|
||||
|
||||
BARRIER_UPDATE = 701,
|
||||
|
||||
BARRIER_CREATE = 702,
|
||||
BARRIER_UNLOAD = 703,
|
||||
|
||||
QUERY_BARRIER_EXISTS = 704,
|
||||
|
||||
FORMAT_END_COMBAT = 799,
|
||||
|
||||
//-------------------------
|
||||
//TextPacket
|
||||
// name, text
|
||||
@@ -169,5 +188,5 @@ enum class SerialPacketType {
|
||||
//not used
|
||||
//-------------------------
|
||||
|
||||
LAST = 700
|
||||
LAST = 800
|
||||
};
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
#include "serial_utility.hpp"
|
||||
|
||||
//packet types
|
||||
#include "barrier_packet.hpp"
|
||||
#include "character_packet.hpp"
|
||||
#include "client_packet.hpp"
|
||||
#include "creature_packet.hpp"
|
||||
@@ -69,6 +70,10 @@ void serializePacket(void* buffer, SerialPacketBase* packet) {
|
||||
serializeCreature(buffer, static_cast<CreaturePacket*>(packet));
|
||||
}
|
||||
|
||||
if (BOUNDS(packet->type, SerialPacketType::FORMAT_COMBAT, SerialPacketType::FORMAT_END_COMBAT)) {
|
||||
serializeBarrier(buffer, static_cast<BarrierPacket*>(packet));
|
||||
}
|
||||
|
||||
if (BOUNDS(packet->type, SerialPacketType::FORMAT_TEXT, SerialPacketType::FORMAT_END_TEXT)) {
|
||||
serializeText(buffer, static_cast<TextPacket*>(packet));
|
||||
}
|
||||
@@ -99,6 +104,10 @@ void deserializePacket(void* buffer, SerialPacketBase* packet) {
|
||||
deserializeCreature(buffer, static_cast<CreaturePacket*>(packet));
|
||||
}
|
||||
|
||||
if (BOUNDS(type, SerialPacketType::FORMAT_COMBAT, SerialPacketType::FORMAT_END_COMBAT)) {
|
||||
deserializeBarrier(buffer, static_cast<BarrierPacket*>(packet));
|
||||
}
|
||||
|
||||
if (BOUNDS(type, SerialPacketType::FORMAT_TEXT, SerialPacketType::FORMAT_END_TEXT)) {
|
||||
deserializeText(buffer, static_cast<TextPacket*>(packet));
|
||||
}
|
||||
|
||||
|
After Width: | Height: | Size: 738 B |
|
After Width: | Height: | Size: 763 B |
|
After Width: | Height: | Size: 273 B |
|
After Width: | Height: | Size: 270 B |
|
After Width: | Height: | Size: 305 B |
|
After Width: | Height: | Size: 302 B |
|
After Width: | Height: | Size: 423 B |
|
After Width: | Height: | Size: 422 B |
|
After Width: | Height: | Size: 301 B |
|
After Width: | Height: | Size: 299 B |
|
After Width: | Height: | Size: 385 B |
|
After Width: | Height: | Size: 383 B |
|
After Width: | Height: | Size: 412 B |
|
After Width: | Height: | Size: 402 B |
|
After Width: | Height: | Size: 431 B |
|
After Width: | Height: | Size: 429 B |
|
After Width: | Height: | Size: 407 B |
|
After Width: | Height: | Size: 400 B |
|
After Width: | Height: | Size: 656 B |
@@ -64,7 +64,7 @@ function doorUtility.CreateDoorPair(handle, roomOne, Xone, Yone, roomTwo, Xtwo,
|
||||
networkAPI.PumpCharacterUpdate(entity)
|
||||
|
||||
--disable the other trigger
|
||||
local triggerTwo = triggerManagerAPI.GetTrigger(roomAPI.GetTriggerMgr(roomTwo), handle)
|
||||
local triggerTwo = triggerManagerAPI.FindTrigger(roomAPI.GetTriggerMgr(roomTwo), handle)
|
||||
triggerAPI.PushExclusionEntity(triggerTwo, entity)
|
||||
end
|
||||
|
||||
@@ -77,7 +77,7 @@ function doorUtility.CreateDoorPair(handle, roomOne, Xone, Yone, roomTwo, Xtwo,
|
||||
networkAPI.PumpCharacterUpdate(entity)
|
||||
|
||||
--disable the other trigger
|
||||
local triggerOne = triggerManagerAPI.GetTrigger(roomAPI.GetTriggerMgr(roomOne), handle)
|
||||
local triggerOne = triggerManagerAPI.FindTrigger(roomAPI.GetTriggerMgr(roomOne), handle)
|
||||
triggerAPI.PushExclusionEntity(triggerOne, entity)
|
||||
end
|
||||
|
||||
|
||||
@@ -26,6 +26,12 @@
|
||||
|
||||
print("Lua script check")
|
||||
|
||||
entityAPI = require("entity")
|
||||
|
||||
for k, v in pairs(entityAPI) do
|
||||
print(k, v)
|
||||
end
|
||||
|
||||
--requirements
|
||||
roomManagerAPI = require("room_manager")
|
||||
roomAPI = require("room")
|
||||
@@ -37,6 +43,8 @@ doorUtility = require("door_utility")
|
||||
|
||||
creatureAPI = require("creature")
|
||||
creatureManagerAPI = require("creature_manager")
|
||||
barrierAPI = require("barrier")
|
||||
barrierManagerAPI = require("barrier_manager")
|
||||
|
||||
--testing creature tags
|
||||
local function bunnySquare(creature)
|
||||
@@ -54,19 +62,23 @@ local function bunnySquare(creature)
|
||||
creatureAPI.SetMotion(creature, 0, 1)
|
||||
end
|
||||
|
||||
|
||||
|
||||
--is it time to change direction?
|
||||
if os.time() - tonumber(timestamp) > 3 then
|
||||
-- print("changing directions")
|
||||
|
||||
if os.time() - tonumber(timestamp) >= 4 then
|
||||
if string.match("south", direction) then
|
||||
direction = "east"
|
||||
creatureAPI.SetMotion(creature, 1, 0)
|
||||
else
|
||||
if string.match("east", direction) then
|
||||
direction = "north"
|
||||
creatureAPI.SetMotion(creature, 0, -1)
|
||||
else
|
||||
if string.match("north", direction) then
|
||||
direction = "west"
|
||||
creatureAPI.SetMotion(creature, -1, 0)
|
||||
else --south is a default
|
||||
direction = "south"
|
||||
creatureAPI.SetMotion(creature, 0, 1)
|
||||
end
|
||||
end end end
|
||||
timestamp = tostring(os.time())
|
||||
ret = 1
|
||||
end
|
||||
@@ -76,13 +88,56 @@ local function bunnySquare(creature)
|
||||
return ret
|
||||
end
|
||||
|
||||
local function barrierTick(barrier)
|
||||
local timestamp = barrierAPI.GetTag(barrier, "timestamp")
|
||||
|
||||
--initialize the timestamp
|
||||
if string.len(timestamp) == 0 then
|
||||
timestamp = tostring(os.time())
|
||||
barrierAPI.SetTag(barrier, "timestamp", timestamp)
|
||||
end
|
||||
|
||||
--is it time to change the display?
|
||||
if os.time() - tonumber(timestamp) < 1 then
|
||||
return 0
|
||||
else
|
||||
timestamp = tostring(os.time())
|
||||
barrierAPI.SetTag(barrier, "timestamp", timestamp)
|
||||
end
|
||||
|
||||
--binary tick
|
||||
for i = 1, 8 do
|
||||
if barrierAPI.GetStatus(barrier, i) == 0 then
|
||||
barrierAPI.SetStatus(barrier, i, 1)
|
||||
return 1
|
||||
else
|
||||
barrierAPI.SetStatus(barrier, i, 0)
|
||||
end
|
||||
end
|
||||
return 0
|
||||
end
|
||||
|
||||
--test the room hooks
|
||||
roomManagerAPI.SetOnCreate(function(room, index)
|
||||
print("", "Creating room: ", roomAPI.GetName(room), index)
|
||||
|
||||
creatureManagerAPI.Create(roomAPI.GetCreatureMgr(room), "anibunny.png", bunnySquare)
|
||||
--creatureManager with SetOnCreate, SetOnUnload & create & unload
|
||||
creatureManagerAPI.SetOnCreate(roomAPI.GetCreatureMgr(room), function(creature, index)
|
||||
--
|
||||
end)
|
||||
|
||||
creatureManagerAPI.SetOnUnload(roomAPI.GetCreatureMgr(room), function(creature)
|
||||
--
|
||||
end)
|
||||
|
||||
--creatureManager with SetOnCreate, SetOnUnload & create & unload
|
||||
barrierManagerAPI.SetOnCreate(roomAPI.GetBarrierMgr(room), function(barrier)
|
||||
barrierAPI.SetScript(barrier, barrierTick)
|
||||
end)
|
||||
|
||||
roomAPI.SetOnTick(room, function(room)
|
||||
ret = 0
|
||||
--placeholders
|
||||
roomAPI.ForEachCharacter(room, function(character)
|
||||
--
|
||||
end)
|
||||
@@ -90,6 +145,20 @@ roomManagerAPI.SetOnCreate(function(room, index)
|
||||
roomAPI.ForEachCreature(room, function(creature)
|
||||
--
|
||||
end)
|
||||
|
||||
roomAPI.ForEachBarrier(room, function(creature)
|
||||
--
|
||||
end)
|
||||
|
||||
--respawn a new rabbit when needed
|
||||
if creatureManagerAPI.GetLoadedCount(roomAPI.GetCreatureMgr(room)) < 1 and
|
||||
barrierManagerAPI.GetLoadedCount(roomAPI.GetBarrierMgr(room)) < 2
|
||||
then
|
||||
--make a new creature
|
||||
creatureManagerAPI.Create(roomAPI.GetCreatureMgr(room), "anibunny.png", bunnySquare)
|
||||
ret = 1
|
||||
end
|
||||
return ret
|
||||
end)
|
||||
end)
|
||||
|
||||
@@ -106,3 +175,4 @@ roomAPI.Initialize(underworld, mapSaver.Load, mapSaver.Save, mapMaker.DebugGrass
|
||||
|
||||
--call the monstrosity
|
||||
doorUtility.CreateDoorPair("pair 1", overworld, -64, -64, underworld, 64, 64)
|
||||
|
||||
|
||||
@@ -234,7 +234,7 @@ void AccountManager::UnloadIf(std::function<bool(std::pair<const int, AccountDat
|
||||
//Define the accessors and mutators
|
||||
//-------------------------
|
||||
|
||||
AccountData* AccountManager::Get(int uid) {
|
||||
AccountData* AccountManager::Find(int uid) {
|
||||
std::map<int, AccountData>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
|
||||
@@ -42,7 +42,7 @@ public:
|
||||
void UnloadIf(std::function<bool(std::pair<const int, AccountData const&>)> fn);
|
||||
|
||||
//accessors and mutators
|
||||
AccountData* Get(int uid);
|
||||
AccountData* Find(int uid);
|
||||
int GetLoadedCount();
|
||||
int GetTotalCount();
|
||||
std::map<int, AccountData>* GetContainer();
|
||||
|
||||
@@ -102,27 +102,27 @@ static const luaL_Reg characterLib[] = {
|
||||
};
|
||||
|
||||
LUAMOD_API int openCharacterAPI(lua_State* L) {
|
||||
//get the parent table
|
||||
luaL_requiref(L, TORTUGA_ENTITY_API, openEntityAPI, false);
|
||||
|
||||
//the local table
|
||||
luaL_newlib(L, characterLib);
|
||||
|
||||
//merge the local table into the parent table
|
||||
//get the parent table
|
||||
luaL_requiref(L, TORTUGA_ENTITY_API, openEntityAPI, false);
|
||||
|
||||
//merge the parent table into the local table
|
||||
lua_pushnil(L); //first key
|
||||
while(lua_next(L, -2)) {
|
||||
//copy the key-value pair
|
||||
lua_pushvalue(L, -2);
|
||||
lua_pushvalue(L, -2);
|
||||
|
||||
//push the copy to the parent table
|
||||
//push the copy to the local table
|
||||
lua_settable(L, -6);
|
||||
|
||||
//pop the original value before continuing
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
|
||||
//remove the local table, leaving the expanded parent table
|
||||
//remove the parent table, leaving the expanded local table
|
||||
lua_pop(L, 1);
|
||||
|
||||
return 1;
|
||||
|
||||
@@ -22,7 +22,12 @@
|
||||
#include "character_data.hpp"
|
||||
|
||||
CharacterData::CharacterData(): Entity("character") {
|
||||
//EMPTY
|
||||
SetBounds({
|
||||
CHARACTER_BOUNDS_X,
|
||||
CHARACTER_BOUNDS_Y,
|
||||
CHARACTER_BOUNDS_WIDTH,
|
||||
CHARACTER_BOUNDS_HEIGHT
|
||||
});
|
||||
}
|
||||
|
||||
int CharacterData::GetOwner() {
|
||||
|
||||
@@ -294,7 +294,7 @@ void CharacterManager::UnloadIf(std::function<bool(std::pair<const int, Characte
|
||||
//Define the accessors and mutators
|
||||
//-------------------------
|
||||
|
||||
CharacterData* CharacterManager::Get(int uid) {
|
||||
CharacterData* CharacterManager::Find(int uid) {
|
||||
std::map<int, CharacterData>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
@@ -304,7 +304,7 @@ CharacterData* CharacterManager::Get(int uid) {
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
CharacterData* CharacterManager::Get(std::string handle) {
|
||||
CharacterData* CharacterManager::Find(std::string handle) {
|
||||
for (std::map<int, CharacterData>::iterator it = elementMap.begin(); it != elementMap.end(); ++it) {
|
||||
if (it->second.GetHandle() == handle) {
|
||||
return &it->second;
|
||||
|
||||
@@ -42,8 +42,8 @@ public:
|
||||
void UnloadIf(std::function<bool(std::pair<const int, CharacterData const&>)> fn);
|
||||
|
||||
//accessors and mutators
|
||||
CharacterData* Get(int uid);
|
||||
CharacterData* Get(std::string handle);
|
||||
CharacterData* Find(int uid);
|
||||
CharacterData* Find(std::string handle);
|
||||
int GetLoadedCount();
|
||||
int GetTotalCount();
|
||||
std::map<int, CharacterData>* GetContainer();
|
||||
|
||||
@@ -55,11 +55,11 @@ static int getCharacter(lua_State* L) {
|
||||
|
||||
switch(lua_type(L, 1)) {
|
||||
case LUA_TNUMBER:
|
||||
characterData = characterMgr.Get(lua_tointeger(L, 1));
|
||||
characterData = characterMgr.Find(lua_tointeger(L, 1));
|
||||
break;
|
||||
case LUA_TSTRING:
|
||||
//access characters via their handles
|
||||
characterData = characterMgr.Get(lua_tostring(L, 1));
|
||||
characterData = characterMgr.Find(lua_tostring(L, 1));
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
#config
|
||||
INCLUDES+=. .. ../creatures ../entities ../monsters ../rooms ../triggers ../../common/gameplay ../../common/map ../../common/network ../../common/network/packet_types ../../common/utilities
|
||||
INCLUDES+=. .. ../combat ../creatures ../entities ../monsters ../rooms ../triggers ../../common/gameplay ../../common/map ../../common/network ../../common/network/packet_types ../../common/utilities
|
||||
LIBS+=
|
||||
CXXFLAGS+=-std=c++11 $(addprefix -I,$(INCLUDES))
|
||||
|
||||
|
||||
@@ -86,7 +86,7 @@ void ClientManager::UnloadIf(std::function<bool(std::pair<const int, ClientData
|
||||
}
|
||||
}
|
||||
|
||||
ClientData* ClientManager::Get(int uid) {
|
||||
ClientData* ClientManager::Find(int uid) {
|
||||
std::map<int, ClientData>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
|
||||
@@ -47,7 +47,7 @@ public:
|
||||
void UnloadIf(std::function<bool(std::pair<const int, ClientData const&>)> fn);
|
||||
|
||||
//accessors & mutators
|
||||
ClientData* Get(int uid);
|
||||
ClientData* Find(int uid);
|
||||
int GetLoadedCount();
|
||||
int GetTotalCount();
|
||||
std::map<int, ClientData>* GetContainer();
|
||||
|
||||
@@ -0,0 +1,116 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "barrier_api.hpp"
|
||||
|
||||
#include "barrier_data.hpp"
|
||||
|
||||
#include "entity_api.hpp"
|
||||
|
||||
|
||||
static int setScript(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
luaL_unref(L, LUA_REGISTRYINDEX, barrier->GetScriptReference());
|
||||
barrier->SetScriptReference(luaL_ref(L, LUA_REGISTRYINDEX));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int getScript(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
lua_pushinteger(L, barrier->GetScriptReference());
|
||||
lua_gettable(L, LUA_REGISTRYINDEX);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int setTag(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
barrier->SetTag(lua_tostring(L, 2), lua_tostring(L, 3));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int getTag(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
lua_pushstring(L, barrier->GetTag(lua_tostring(L, 2)).c_str());
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int setInstance(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
barrier->SetInstanceIndex(lua_tointeger(L, 2));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int getInstance(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
lua_pushinteger(L, barrier->GetInstanceIndex());
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int setStatus(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
barrier->SetStatus(lua_tointeger(L, 2) - 1, lua_tointeger(L, 3));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int getStatus(lua_State* L) {
|
||||
BarrierData* barrier = static_cast<BarrierData*>(lua_touserdata(L, 1));
|
||||
lua_pushinteger(L, barrier->GetStatus(lua_tointeger(L, 2) - 1));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static const luaL_Reg barrierLib[] = {
|
||||
{"SetScript", setScript},
|
||||
{"GetScript", getScript},
|
||||
{"SetTag", setTag},
|
||||
{"GetTag", getTag},
|
||||
{"SetInstance", setInstance},
|
||||
{"GetInstance", getInstance},
|
||||
{"SetStatus", setStatus},
|
||||
{"GetStatus", getStatus},
|
||||
{nullptr, nullptr}
|
||||
};
|
||||
|
||||
LUAMOD_API int openBarrierAPI(lua_State* L) {
|
||||
//the local table
|
||||
luaL_newlib(L, barrierLib);
|
||||
|
||||
//get the parent table
|
||||
luaL_requiref(L, TORTUGA_ENTITY_API, openEntityAPI, false);
|
||||
|
||||
//merge the parent table into the local table
|
||||
lua_pushnil(L); //first key
|
||||
while(lua_next(L, -2)) {
|
||||
//copy the key-value pair
|
||||
lua_pushvalue(L, -2);
|
||||
lua_pushvalue(L, -2);
|
||||
|
||||
//push the copy to the local table
|
||||
lua_settable(L, -6);
|
||||
|
||||
//pop the original value before continuing
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
|
||||
//remove the parent table, leaving the expanded local table
|
||||
lua_pop(L, 1);
|
||||
|
||||
return 1;
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "lua.hpp"
|
||||
|
||||
#define TORTUGA_BARRIER_API "barrier"
|
||||
LUAMOD_API int openBarrierAPI(lua_State* L);
|
||||
@@ -0,0 +1,104 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "barrier_data.hpp"
|
||||
|
||||
#include <cstring>
|
||||
#include <sstream>
|
||||
#include <stdexcept>
|
||||
|
||||
BarrierData::BarrierData(int i):
|
||||
Entity::Entity("barrier")
|
||||
{
|
||||
instanceIndex = i;
|
||||
memset(status, 0, sizeof(int) * 8);
|
||||
}
|
||||
|
||||
BarrierData::~BarrierData() {
|
||||
//
|
||||
}
|
||||
|
||||
int BarrierData::Update(lua_State* L) {
|
||||
int ret = 0;
|
||||
|
||||
if (scriptRef != LUA_NOREF) {
|
||||
//Call the script reference
|
||||
lua_pushinteger(L, scriptRef);
|
||||
lua_gettable(L, LUA_REGISTRYINDEX);
|
||||
lua_pushlightuserdata(L, reinterpret_cast<void*>(this));
|
||||
|
||||
//check for errors
|
||||
if(lua_pcall(L, 1, 1, 0) != LUA_OK) {
|
||||
std::ostringstream msg;
|
||||
msg << "Error running barrier script: " << lua_tostring(L, -1);
|
||||
lua_pop(L, 1);
|
||||
throw(std::runtime_error(msg.str()));
|
||||
}
|
||||
|
||||
ret += lua_tonumber(L, -1);
|
||||
}
|
||||
|
||||
Entity::Update();
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
int BarrierData::SetScriptReference(int i) {
|
||||
return scriptRef = i;
|
||||
}
|
||||
|
||||
int BarrierData::GetScriptReference() {
|
||||
return scriptRef;
|
||||
}
|
||||
|
||||
std::string BarrierData::SetTag(std::string key, std::string value) {
|
||||
return tags[key] = value;
|
||||
}
|
||||
|
||||
std::string BarrierData::GetTag(std::string key) {
|
||||
return tags[key];
|
||||
}
|
||||
|
||||
int BarrierData::SetInstanceIndex(int i) {
|
||||
return instanceIndex = i;
|
||||
}
|
||||
|
||||
int BarrierData::GetInstanceIndex() const {
|
||||
return instanceIndex;
|
||||
}
|
||||
|
||||
int BarrierData::SetStatus(int k, int v) {
|
||||
if (k < 0 || k >= 8) {
|
||||
throw(std::runtime_error("Failed to set status"));
|
||||
}
|
||||
return status[k] = v;
|
||||
}
|
||||
|
||||
int BarrierData::GetStatus(int k) {
|
||||
if (k < 0 || k >= 8) {
|
||||
throw(std::runtime_error("Failed to get status"));
|
||||
}
|
||||
return status[k];
|
||||
}
|
||||
|
||||
int* BarrierData::GetStatusArray() {
|
||||
return status;
|
||||
}
|
||||
@@ -0,0 +1,59 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "entity.hpp"
|
||||
|
||||
#include "lua.hpp"
|
||||
|
||||
#include <map>
|
||||
#include <string>
|
||||
|
||||
class BarrierData: public Entity {
|
||||
public:
|
||||
BarrierData(int instanceIndex);
|
||||
~BarrierData();
|
||||
|
||||
int Update(lua_State*);
|
||||
|
||||
int SetScriptReference(int);
|
||||
int GetScriptReference();
|
||||
|
||||
std::string SetTag(std::string key, std::string value);
|
||||
std::string GetTag(std::string key);
|
||||
|
||||
int SetInstanceIndex(int i);
|
||||
int GetInstanceIndex() const;
|
||||
|
||||
int SetStatus(int k, int v);
|
||||
int GetStatus(int k);
|
||||
|
||||
int* GetStatusArray();
|
||||
|
||||
private:
|
||||
int scriptRef = LUA_NOREF;
|
||||
std::map<std::string, std::string> tags;
|
||||
|
||||
int instanceIndex;
|
||||
|
||||
int status[8];
|
||||
};
|
||||
@@ -0,0 +1,130 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "barrier_manager.hpp"
|
||||
|
||||
#include "lua_utilities.hpp"
|
||||
|
||||
BarrierManager::BarrierManager() {
|
||||
//EMPTY
|
||||
}
|
||||
|
||||
BarrierManager::~BarrierManager() {
|
||||
UnloadAll();
|
||||
}
|
||||
|
||||
//arg: a list of barriers to be updated in the clients
|
||||
void BarrierManager::Update(std::list<std::pair<const int, BarrierData*>>* barrierList, bool updateAll) {
|
||||
int ret;
|
||||
for (auto& it : elementMap) {
|
||||
ret = it.second.Update(lua);
|
||||
if (ret || updateAll) {
|
||||
barrierList->push_back(std::pair<const int, BarrierData*>(it.first, &it.second));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int BarrierManager::Create(int instanceIndex) {
|
||||
//implicitly create the new object
|
||||
elementMap.emplace( std::pair<int, BarrierData>(counter, BarrierData(instanceIndex)) );
|
||||
|
||||
runHook(lua, createRef, &elementMap.find(counter)->second, counter);
|
||||
|
||||
//TODO: do various things like saving to the database
|
||||
return counter++;
|
||||
}
|
||||
|
||||
//TODO: (1) combat load, save
|
||||
|
||||
void BarrierManager::Unload(int uid) {
|
||||
runHook(lua, unloadRef, &elementMap.find(uid)->second, uid);
|
||||
elementMap.erase(uid);
|
||||
}
|
||||
|
||||
void BarrierManager::UnloadAll() {
|
||||
for (std::map<int, BarrierData>::iterator it = elementMap.begin(); it != elementMap.end(); it++) {
|
||||
runHook(lua, unloadRef, &it->second, it->first);
|
||||
}
|
||||
elementMap.clear();
|
||||
}
|
||||
|
||||
void BarrierManager::UnloadIf(std::function<bool(std::pair<const int, BarrierData const&>)> fn) {
|
||||
std::map<int, BarrierData>::iterator it = elementMap.begin();
|
||||
while (it != elementMap.end()) {
|
||||
if (fn(*it)) {
|
||||
runHook(lua, unloadRef, &it->second, it->first);
|
||||
it = elementMap.erase(it);
|
||||
}
|
||||
else {
|
||||
++it;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
BarrierData* BarrierManager::Find(int uid) {
|
||||
std::map<int, BarrierData>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
int BarrierManager::GetLoadedCount() {
|
||||
return elementMap.size();
|
||||
}
|
||||
|
||||
std::map<int, BarrierData>* BarrierManager::GetContainer() {
|
||||
return &elementMap;
|
||||
}
|
||||
|
||||
lua_State* BarrierManager::SetLuaState(lua_State* L) {
|
||||
return lua = L;
|
||||
}
|
||||
|
||||
lua_State* BarrierManager::GetLuaState() {
|
||||
return lua;
|
||||
}
|
||||
|
||||
sqlite3* BarrierManager::SetDatabase(sqlite3* db) {
|
||||
return database = db;
|
||||
}
|
||||
|
||||
sqlite3* BarrierManager::GetDatabase() {
|
||||
return database;
|
||||
}
|
||||
|
||||
int BarrierManager::SetCreateReference(int i) {
|
||||
return createRef = i;
|
||||
}
|
||||
|
||||
int BarrierManager::SetUnloadReference(int i) {
|
||||
return unloadRef = i;
|
||||
}
|
||||
|
||||
int BarrierManager::GetCreateReference() {
|
||||
return createRef;
|
||||
}
|
||||
|
||||
int BarrierManager::GetUnloadReference() {
|
||||
return unloadRef;
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "barrier_data.hpp"
|
||||
|
||||
#include "lua.hpp"
|
||||
#include "sqlite3.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <list>
|
||||
#include <map>
|
||||
|
||||
class BarrierManager {
|
||||
public:
|
||||
BarrierManager();
|
||||
~BarrierManager();
|
||||
|
||||
//common public methods
|
||||
void Update(std::list<std::pair<const int, BarrierData*>>* barrierList, bool updateAll);
|
||||
|
||||
int Create(int instanceIndex);
|
||||
void Unload(int uid);
|
||||
|
||||
void UnloadAll();
|
||||
void UnloadIf(std::function<bool(std::pair<const int, BarrierData const&>)> fn);
|
||||
|
||||
//accessors & mutators
|
||||
BarrierData* Find(int uid);
|
||||
int GetLoadedCount();
|
||||
std::map<int, BarrierData>* GetContainer();
|
||||
|
||||
//hooks
|
||||
lua_State* SetLuaState(lua_State* L);
|
||||
lua_State* GetLuaState();
|
||||
sqlite3* SetDatabase(sqlite3* db);
|
||||
sqlite3* GetDatabase();
|
||||
|
||||
int SetCreateReference(int i);
|
||||
int SetUnloadReference(int i);
|
||||
|
||||
int GetCreateReference();
|
||||
int GetUnloadReference();
|
||||
|
||||
private:
|
||||
//members
|
||||
std::map<int, BarrierData> elementMap;
|
||||
int counter = 0;
|
||||
lua_State* lua = nullptr;
|
||||
sqlite3* database = nullptr;
|
||||
int createRef = LUA_NOREF;
|
||||
int unloadRef = LUA_NOREF;
|
||||
};
|
||||
@@ -0,0 +1,124 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "barrier_manager_api.hpp"
|
||||
|
||||
#include "barrier_manager.hpp"
|
||||
|
||||
//args: mgr, avatar, script
|
||||
static int create(lua_State* L) {
|
||||
//register the function at the top of the stack
|
||||
lua_pushinteger(L, luaL_ref(L, LUA_REGISTRYINDEX));
|
||||
|
||||
//create the actual barrier
|
||||
BarrierManager* mgr = static_cast<BarrierManager* const>(lua_touserdata(L, 1));
|
||||
int index = mgr->Create(-1);
|
||||
BarrierData* barrier = mgr->Find(index);
|
||||
lua_pushlightuserdata(L, static_cast<void*>(barrier));
|
||||
lua_pushinteger(L, index);
|
||||
return 2;
|
||||
}
|
||||
|
||||
//TOOD: overload this to take the userdata as a parameter
|
||||
static int unload(lua_State* L) {
|
||||
BarrierManager* mgr = static_cast<BarrierManager* const>(lua_touserdata(L, 1));
|
||||
mgr->Unload(lua_tointeger(L, 2));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int unloadAll(lua_State* L) {
|
||||
BarrierManager* mgr = static_cast<BarrierManager* const>(lua_touserdata(L, 1));
|
||||
mgr->UnloadAll();
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int unloadIf(lua_State* L) {
|
||||
BarrierManager* mgr = static_cast<BarrierManager* const>(lua_touserdata(L, 1));
|
||||
|
||||
//list of stuff to unload (don't invalidate iterators)
|
||||
std::list<int> unloadList;
|
||||
|
||||
//unloadIf
|
||||
for (auto it : *mgr->GetContainer()) {
|
||||
//copy the function at the top
|
||||
lua_pushvalue(L, -1);
|
||||
|
||||
//index & object as function parameters
|
||||
lua_pushinteger(L, it.first);
|
||||
lua_pushlightuserdata(L, &it.second);
|
||||
|
||||
//call
|
||||
lua_pcall(L, 2, 1, 0);
|
||||
|
||||
//unload-ish
|
||||
if (lua_toboolean(L, -1)) {
|
||||
unloadList.push_back(it.first);
|
||||
}
|
||||
}
|
||||
|
||||
//actually unload
|
||||
for (auto& it : unloadList) {
|
||||
mgr->Unload(it);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int find(lua_State* L) {
|
||||
BarrierManager* mgr = static_cast<BarrierManager* const>(lua_touserdata(L, 1));
|
||||
BarrierData* barrier = mgr->Find(lua_tointeger(L, 2));
|
||||
lua_pushlightuserdata(L, static_cast<void*>(barrier));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int getLoadedCount(lua_State* L) {
|
||||
BarrierManager* mgr = static_cast<BarrierManager* const>(lua_touserdata(L, 1));
|
||||
lua_pushinteger(L, mgr->GetLoadedCount());
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int setOnCreate(lua_State* L) {
|
||||
BarrierManager* mgr = static_cast<BarrierManager*>(lua_touserdata(L, 1));
|
||||
mgr->SetCreateReference(luaL_ref(L, LUA_REGISTRYINDEX));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int setOnUnload(lua_State* L) {
|
||||
BarrierManager* mgr = static_cast<BarrierManager*>(lua_touserdata(L, 1));
|
||||
mgr->SetUnloadReference(luaL_ref(L, LUA_REGISTRYINDEX));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const luaL_Reg barrierManagerLib[] = {
|
||||
{"Create", create},
|
||||
{"Unload", unload},
|
||||
{"UnloadAll", unloadAll},
|
||||
{"UnloadIf", unloadIf},
|
||||
{"Find", find},
|
||||
{"GetLoadedCount", getLoadedCount},
|
||||
{"SetOnCreate", setOnCreate},
|
||||
{"SetOnUnload", setOnUnload},
|
||||
{nullptr, nullptr}
|
||||
};
|
||||
|
||||
LUAMOD_API int openBarrierManagerAPI(lua_State* L) {
|
||||
luaL_newlib(L, barrierManagerLib);
|
||||
return 1;
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "lua.hpp"
|
||||
|
||||
#define TORTUGA_BARRIER_MANAGER_API "barrier_manager"
|
||||
LUAMOD_API int openBarrierManagerAPI(lua_State* L);
|
||||
@@ -0,0 +1,51 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "combat_instance.hpp"
|
||||
|
||||
CombatInstance::CombatInstance() {
|
||||
//
|
||||
}
|
||||
|
||||
CombatInstance::~CombatInstance() {
|
||||
//
|
||||
}
|
||||
|
||||
void CombatInstance::Update() {
|
||||
//
|
||||
}
|
||||
|
||||
//accessors and mutators
|
||||
void CombatInstance::PushCharacter(CharacterData* const characterData) {
|
||||
//
|
||||
}
|
||||
|
||||
void CombatInstance::PopCharacter(CharacterData* const characterData) {
|
||||
//
|
||||
}
|
||||
|
||||
void CombatInstance::PushCreature(CreatureData* const creatureData) {
|
||||
//
|
||||
}
|
||||
|
||||
void CombatInstance::PopCreature(CreatureData* const creatureData) {
|
||||
//
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "character_data.hpp"
|
||||
#include "creature_data.hpp"
|
||||
|
||||
class CombatInstance {
|
||||
public:
|
||||
CombatInstance();
|
||||
~CombatInstance();
|
||||
|
||||
void Update();
|
||||
|
||||
//accessors and mutators
|
||||
void PushCharacter(CharacterData* const characterData);
|
||||
void PopCharacter(CharacterData* const characterData);
|
||||
|
||||
void PushCreature(CreatureData* const creatureData);
|
||||
void PopCreature(CreatureData* const creatureData);
|
||||
|
||||
private:
|
||||
std::array<CharacterData*, 8> characterArray;
|
||||
std::array<CreatureData*, 8> creatureArray;
|
||||
};
|
||||
@@ -0,0 +1,101 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "combat_instance_manager.hpp"
|
||||
|
||||
CombatInstanceManager::CombatInstanceManager() {
|
||||
//EMPTY
|
||||
}
|
||||
|
||||
CombatInstanceManager::~CombatInstanceManager() {
|
||||
UnloadAll();
|
||||
}
|
||||
|
||||
//arg: a list of combats to be updated in the clients
|
||||
void CombatInstanceManager::Update() {
|
||||
for (auto& it : elementMap) {
|
||||
it.second.Update();
|
||||
}
|
||||
}
|
||||
|
||||
int CombatInstanceManager::Create() {
|
||||
//implicitly create the new object
|
||||
elementMap.emplace( std::pair<int, CombatInstance>(counter, CombatInstance()) );
|
||||
|
||||
//TODO: do various things like saving to the database
|
||||
return counter++;
|
||||
}
|
||||
|
||||
//TODO: (1) combat load, save
|
||||
|
||||
void CombatInstanceManager::Unload(int uid) {
|
||||
elementMap.erase(uid);
|
||||
}
|
||||
|
||||
void CombatInstanceManager::UnloadAll() {
|
||||
elementMap.clear();
|
||||
}
|
||||
|
||||
void CombatInstanceManager::UnloadIf(std::function<bool(std::pair<const int, CombatInstance const&>)> fn) {
|
||||
std::map<int, CombatInstance>::iterator it = elementMap.begin();
|
||||
while (it != elementMap.end()) {
|
||||
if (fn(*it)) {
|
||||
it = elementMap.erase(it);
|
||||
}
|
||||
else {
|
||||
++it;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
CombatInstance* CombatInstanceManager::Find(int uid) {
|
||||
std::map<int, CombatInstance>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
int CombatInstanceManager::GetLoadedCount() {
|
||||
return elementMap.size();
|
||||
}
|
||||
|
||||
std::map<int, CombatInstance>* CombatInstanceManager::GetContainer() {
|
||||
return &elementMap;
|
||||
}
|
||||
|
||||
lua_State* CombatInstanceManager::SetLuaState(lua_State* L) {
|
||||
return lua = L;
|
||||
}
|
||||
|
||||
lua_State* CombatInstanceManager::GetLuaState() {
|
||||
return lua;
|
||||
}
|
||||
|
||||
sqlite3* CombatInstanceManager::SetDatabase(sqlite3* db) {
|
||||
return database = db;
|
||||
}
|
||||
|
||||
sqlite3* CombatInstanceManager::GetDatabase() {
|
||||
return database;
|
||||
}
|
||||
@@ -0,0 +1,63 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "combat_instance.hpp"
|
||||
|
||||
#include "lua.hpp"
|
||||
#include "sqlite3.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <map>
|
||||
|
||||
class CombatInstanceManager {
|
||||
public:
|
||||
CombatInstanceManager();
|
||||
~CombatInstanceManager();
|
||||
|
||||
//common public methods
|
||||
void Update();
|
||||
|
||||
int Create();
|
||||
void Unload(int uid);
|
||||
|
||||
void UnloadAll();
|
||||
void UnloadIf(std::function<bool(std::pair<const int, CombatInstance const&>)> fn);
|
||||
|
||||
//accessors & mutators
|
||||
CombatInstance* Find(int uid);
|
||||
int GetLoadedCount();
|
||||
std::map<int, CombatInstance>* GetContainer();
|
||||
|
||||
//hooks
|
||||
lua_State* SetLuaState(lua_State* L);
|
||||
lua_State* GetLuaState();
|
||||
sqlite3* SetDatabase(sqlite3* db);
|
||||
sqlite3* GetDatabase();
|
||||
|
||||
private:
|
||||
//members
|
||||
std::map<int, CombatInstance> elementMap;
|
||||
int counter = 0;
|
||||
lua_State* lua = nullptr;
|
||||
sqlite3* database = nullptr;
|
||||
};
|
||||
@@ -0,0 +1,32 @@
|
||||
#config
|
||||
INCLUDES+=. .. ../characters ../creatures ../entities ../../common/gameplay ../../common/utilities
|
||||
LIBS+=
|
||||
CXXFLAGS+=-std=c++11 $(addprefix -I,$(INCLUDES))
|
||||
|
||||
#source
|
||||
CXXSRC=$(wildcard *.cpp)
|
||||
|
||||
#objects
|
||||
OBJDIR=obj
|
||||
OBJ+=$(addprefix $(OBJDIR)/,$(CXXSRC:.cpp=.o))
|
||||
|
||||
#output
|
||||
OUTDIR=..
|
||||
OUT=$(addprefix $(OUTDIR)/,server.a)
|
||||
|
||||
#targets
|
||||
all: $(OBJ) $(OUT)
|
||||
ar -crs $(OUT) $(OBJ)
|
||||
|
||||
$(OBJ): | $(OBJDIR)
|
||||
|
||||
$(OUT): | $(OUTDIR)
|
||||
|
||||
$(OBJDIR):
|
||||
mkdir $(OBJDIR)
|
||||
|
||||
$(OUTDIR):
|
||||
mkdir $(OUTDIR)
|
||||
|
||||
$(OBJDIR)/%.o: %.cpp
|
||||
$(CXX) $(CXXFLAGS) -c -o $@ $<
|
||||
@@ -76,27 +76,27 @@ static const luaL_Reg creatureLib[] = {
|
||||
};
|
||||
|
||||
LUAMOD_API int openCreatureAPI(lua_State* L) {
|
||||
//get the parent table
|
||||
luaL_requiref(L, TORTUGA_ENTITY_API, openEntityAPI, false);
|
||||
|
||||
//the local table
|
||||
luaL_newlib(L, creatureLib);
|
||||
|
||||
//merge the local table into the parent table
|
||||
//get the parent table
|
||||
luaL_requiref(L, TORTUGA_ENTITY_API, openEntityAPI, false);
|
||||
|
||||
//merge the parent table into the local table
|
||||
lua_pushnil(L); //first key
|
||||
while(lua_next(L, -2)) {
|
||||
//copy the key-value pair
|
||||
lua_pushvalue(L, -2);
|
||||
lua_pushvalue(L, -2);
|
||||
|
||||
//push the copy to the parent table
|
||||
//push the copy to the local table
|
||||
lua_settable(L, -6);
|
||||
|
||||
//pop the original value before continuing
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
|
||||
//remove the local table, leaving the expanded parent table
|
||||
//remove the parent table, leaving the expanded local table
|
||||
lua_pop(L, 1);
|
||||
|
||||
return 1;
|
||||
|
||||
@@ -29,7 +29,12 @@ CreatureData::CreatureData(std::string _avatar, int _scriptRef):
|
||||
avatar(_avatar),
|
||||
scriptRef(_scriptRef)
|
||||
{
|
||||
//EMPTY
|
||||
SetBounds({
|
||||
CREATURE_BOUNDS_X,
|
||||
CREATURE_BOUNDS_Y,
|
||||
CREATURE_BOUNDS_WIDTH,
|
||||
CREATURE_BOUNDS_HEIGHT
|
||||
});
|
||||
}
|
||||
|
||||
int CreatureData::Update(lua_State* L) {
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "creature_defines.hpp"
|
||||
#include "entity.hpp"
|
||||
|
||||
#include "lua.hpp"
|
||||
|
||||
@@ -21,6 +21,8 @@
|
||||
*/
|
||||
#include "creature_manager.hpp"
|
||||
|
||||
#include "lua_utilities.hpp"
|
||||
|
||||
CreatureManager::CreatureManager() {
|
||||
//EMPTY
|
||||
}
|
||||
@@ -30,11 +32,11 @@ CreatureManager::~CreatureManager() {
|
||||
}
|
||||
|
||||
//arg: a list of creatures to be updated in the clients
|
||||
void CreatureManager::Update(std::list<std::pair<const int, CreatureData*>>* creatureList) {
|
||||
void CreatureManager::Update(std::list<std::pair<const int, CreatureData*>>* creatureList, bool updateAll) {
|
||||
int ret;
|
||||
for (auto& it : elementMap) {
|
||||
ret = it.second.Update(lua);
|
||||
if (ret) {
|
||||
if (ret || updateAll) {
|
||||
creatureList->push_back(std::pair<const int, CreatureData*>(it.first, &it.second));
|
||||
}
|
||||
}
|
||||
@@ -44,6 +46,8 @@ int CreatureManager::Create(std::string avatar, int scriptRef) {
|
||||
//implicitly create the new object
|
||||
elementMap.emplace( std::pair<int, CreatureData>(counter, CreatureData(avatar, scriptRef)) );
|
||||
|
||||
runHook(lua, createRef, &elementMap.find(counter)->second, counter);
|
||||
|
||||
//TODO: do various things like saving to the database
|
||||
return counter++;
|
||||
}
|
||||
@@ -51,10 +55,14 @@ int CreatureManager::Create(std::string avatar, int scriptRef) {
|
||||
//TODO: (1) creature load, save
|
||||
|
||||
void CreatureManager::Unload(int uid) {
|
||||
runHook(lua, unloadRef, &elementMap.find(uid)->second, uid);
|
||||
elementMap.erase(uid);
|
||||
}
|
||||
|
||||
void CreatureManager::UnloadAll() {
|
||||
for (std::map<int, CreatureData>::iterator it = elementMap.begin(); it != elementMap.end(); it++) {
|
||||
runHook(lua, unloadRef, &it->second, it->first);
|
||||
}
|
||||
elementMap.clear();
|
||||
}
|
||||
|
||||
@@ -62,6 +70,7 @@ void CreatureManager::UnloadIf(std::function<bool(std::pair<const int, CreatureD
|
||||
std::map<int, CreatureData>::iterator it = elementMap.begin();
|
||||
while (it != elementMap.end()) {
|
||||
if (fn(*it)) {
|
||||
runHook(lua, unloadRef, &it->second, it->first);
|
||||
it = elementMap.erase(it);
|
||||
}
|
||||
else {
|
||||
@@ -70,7 +79,7 @@ void CreatureManager::UnloadIf(std::function<bool(std::pair<const int, CreatureD
|
||||
}
|
||||
}
|
||||
|
||||
CreatureData* CreatureManager::Get(int uid) {
|
||||
CreatureData* CreatureManager::Find(int uid) {
|
||||
std::map<int, CreatureData>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
@@ -103,3 +112,19 @@ sqlite3* CreatureManager::SetDatabase(sqlite3* db) {
|
||||
sqlite3* CreatureManager::GetDatabase() {
|
||||
return database;
|
||||
}
|
||||
|
||||
int CreatureManager::SetCreateReference(int i) {
|
||||
return createRef = i;
|
||||
}
|
||||
|
||||
int CreatureManager::SetUnloadReference(int i) {
|
||||
return unloadRef = i;
|
||||
}
|
||||
|
||||
int CreatureManager::GetCreateReference() {
|
||||
return createRef;
|
||||
}
|
||||
|
||||
int CreatureManager::GetUnloadReference() {
|
||||
return unloadRef;
|
||||
}
|
||||
|
||||
@@ -37,7 +37,7 @@ public:
|
||||
~CreatureManager();
|
||||
|
||||
//common public methods
|
||||
void Update(std::list<std::pair<const int, CreatureData*>>* creatureList);
|
||||
void Update(std::list<std::pair<const int, CreatureData*>>* creatureList, bool updateAll);
|
||||
|
||||
int Create(std::string avatar, int scriptRef);
|
||||
void Unload(int uid);
|
||||
@@ -46,7 +46,7 @@ public:
|
||||
void UnloadIf(std::function<bool(std::pair<const int, CreatureData const&>)> fn);
|
||||
|
||||
//accessors & mutators
|
||||
CreatureData* Get(int uid);
|
||||
CreatureData* Find(int uid);
|
||||
int GetLoadedCount();
|
||||
std::map<int, CreatureData>* GetContainer();
|
||||
|
||||
@@ -56,10 +56,18 @@ public:
|
||||
sqlite3* SetDatabase(sqlite3* db);
|
||||
sqlite3* GetDatabase();
|
||||
|
||||
int SetCreateReference(int i);
|
||||
int SetUnloadReference(int i);
|
||||
|
||||
int GetCreateReference();
|
||||
int GetUnloadReference();
|
||||
|
||||
private:
|
||||
//members
|
||||
std::map<int, CreatureData> elementMap;
|
||||
int counter = 0;
|
||||
lua_State* lua = nullptr;
|
||||
sqlite3* database = nullptr;
|
||||
int createRef = LUA_NOREF;
|
||||
int unloadRef = LUA_NOREF;
|
||||
};
|
||||
|
||||
@@ -31,7 +31,7 @@ static int create(lua_State* L) {
|
||||
//create the actual creature
|
||||
CreatureManager* mgr = static_cast<CreatureManager* const>(lua_touserdata(L, 1));
|
||||
int index = mgr->Create(lua_tostring(L, 2), lua_tointeger(L, 3)); //3 should be the unique reference within LUA_REGISTRYINDEX
|
||||
CreatureData* creature = mgr->Get(index);
|
||||
CreatureData* creature = mgr->Find(index);
|
||||
lua_pushlightuserdata(L, static_cast<void*>(creature));
|
||||
lua_pushinteger(L, index);
|
||||
return 2;
|
||||
@@ -52,13 +52,38 @@ static int unloadAll(lua_State* L) {
|
||||
|
||||
static int unloadIf(lua_State* L) {
|
||||
CreatureManager* mgr = static_cast<CreatureManager* const>(lua_touserdata(L, 1));
|
||||
//TODO: unloadIf
|
||||
|
||||
//list of stuff to unload (don't invalidate iterators)
|
||||
std::list<int> unloadList;
|
||||
|
||||
//unloadIf
|
||||
for (auto it : *mgr->GetContainer()) {
|
||||
//copy the function at the top
|
||||
lua_pushvalue(L, -1);
|
||||
|
||||
//index & object as function parameters
|
||||
lua_pushinteger(L, it.first);
|
||||
lua_pushlightuserdata(L, &it.second);
|
||||
|
||||
//call
|
||||
lua_pcall(L, 2, 1, 0);
|
||||
|
||||
//unload-ish
|
||||
if (lua_toboolean(L, -1)) {
|
||||
unloadList.push_back(it.first);
|
||||
}
|
||||
}
|
||||
|
||||
//actually unload
|
||||
for (auto& it : unloadList) {
|
||||
mgr->Unload(it);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int get(lua_State* L) {
|
||||
static int find(lua_State* L) {
|
||||
CreatureManager* mgr = static_cast<CreatureManager* const>(lua_touserdata(L, 1));
|
||||
CreatureData* creature = mgr->Get(lua_tointeger(L, 2));
|
||||
CreatureData* creature = mgr->Find(lua_tointeger(L, 2));
|
||||
lua_pushlightuserdata(L, static_cast<void*>(creature));
|
||||
return 1;
|
||||
}
|
||||
@@ -69,13 +94,27 @@ static int getLoadedCount(lua_State* L) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int setOnCreate(lua_State* L) {
|
||||
CreatureManager* mgr = static_cast<CreatureManager*>(lua_touserdata(L, 1));
|
||||
mgr->SetCreateReference(luaL_ref(L, LUA_REGISTRYINDEX));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int setOnUnload(lua_State* L) {
|
||||
CreatureManager* mgr = static_cast<CreatureManager*>(lua_touserdata(L, 1));
|
||||
mgr->SetUnloadReference(luaL_ref(L, LUA_REGISTRYINDEX));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const luaL_Reg creatureManagerLib[] = {
|
||||
{"Create", create},
|
||||
{"Unload", unload},
|
||||
{"UnloadAll", unloadAll},
|
||||
// {"UnloadIf", unloadIf},
|
||||
{"Get", get},
|
||||
{"UnloadIf", unloadIf},
|
||||
{"Find", find},
|
||||
{"GetLoadedCount", getLoadedCount},
|
||||
{"SetOnCreate", setOnCreate},
|
||||
{"SetOnUnload", setOnUnload},
|
||||
{nullptr, nullptr}
|
||||
};
|
||||
|
||||
|
||||
@@ -37,6 +37,8 @@
|
||||
#include "lua.hpp"
|
||||
|
||||
#include "entity_api.hpp"
|
||||
#include "barrier_api.hpp"
|
||||
#include "barrier_manager_api.hpp"
|
||||
#include "character_api.hpp"
|
||||
#include "character_manager_api.hpp"
|
||||
#include "region_api.hpp"
|
||||
@@ -68,6 +70,8 @@ static const luaL_Reg loadedlibs[] = {
|
||||
//these libs are preloaded and must be required before used
|
||||
static const luaL_Reg preloadedlibs[] = {
|
||||
{TORTUGA_ENTITY_API, openEntityAPI}, //required by derived classes
|
||||
{TORTUGA_BARRIER_API, openBarrierAPI},
|
||||
{TORTUGA_BARRIER_MANAGER_API, openBarrierManagerAPI},
|
||||
{TORTUGA_CHARACTER_API, openCharacterAPI},
|
||||
{TORTUGA_CHARACTER_MANAGER_API, openCharacterManagerAPI},
|
||||
{TORTUGA_CREATURE_API, openCreatureAPI},
|
||||
|
||||
@@ -0,0 +1,47 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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 "lua_utilities.hpp"
|
||||
|
||||
#include <stdexcept>
|
||||
#include <string>
|
||||
|
||||
//this is for functions passed to SetOnCreate & SetOnUnload
|
||||
int runHook(lua_State* L, int scriptRef, void* userdata, int index) {
|
||||
//get the hook
|
||||
lua_rawgeti(L, LUA_REGISTRYINDEX, scriptRef);
|
||||
|
||||
if (lua_isnil(L, -1)) {
|
||||
lua_pop(L, 1);
|
||||
return -1;
|
||||
}
|
||||
|
||||
//push args
|
||||
lua_pushlightuserdata(L, userdata);
|
||||
lua_pushinteger(L, index);
|
||||
|
||||
//call the function, 2 arg, 0 return
|
||||
if (lua_pcall(L, 2, 0, 0) != LUA_OK) {
|
||||
throw(std::runtime_error(std::string() + "Lua error: " + lua_tostring(L, -1) ));
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
/* Copyright: (c) Kayne Ruse 2013-2016
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "lua.hpp"
|
||||
|
||||
int runHook(lua_State* L, int scriptRef, void* userdata, int index);
|
||||
@@ -1,5 +1,5 @@
|
||||
#include directories
|
||||
INCLUDES+=. accounts characters clients creatures entities rooms triggers ../common/debugging ../common/gameplay ../common/map ../common/network ../common/network/packet_types ../common/utilities
|
||||
INCLUDES+=. accounts characters clients combat creatures entities rooms triggers ../common/debugging ../common/gameplay ../common/map ../common/network ../common/network/packet_types ../common/utilities
|
||||
|
||||
#libraries
|
||||
#the order of the $(LIBS) is important, at least for MinGW
|
||||
@@ -32,6 +32,7 @@ all: $(OBJ) $(OUT)
|
||||
$(MAKE) -C accounts
|
||||
$(MAKE) -C characters
|
||||
$(MAKE) -C clients
|
||||
$(MAKE) -C combat
|
||||
$(MAKE) -C creatures
|
||||
$(MAKE) -C entities
|
||||
$(MAKE) -C rooms
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
#config
|
||||
INCLUDES+=. .. ../characters ../creatures ../entities ../monsters ../triggers ../../common/gameplay ../../common/map ../../common/network ../../common/network/packet_types ../../common/utilities
|
||||
INCLUDES+=. .. ../characters ../combat ../creatures ../entities ../monsters ../triggers ../../common/gameplay ../../common/map ../../common/network ../../common/network/packet_types ../../common/utilities
|
||||
LIBS+=
|
||||
CXXFLAGS+=-std=c++11 $(addprefix -I,$(INCLUDES))
|
||||
|
||||
|
||||
@@ -50,6 +50,12 @@ static int getTilesetName(lua_State* L) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int getBarrierMgr(lua_State* L) {
|
||||
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
|
||||
lua_pushlightuserdata(L, reinterpret_cast<void*>(room->GetBarrierMgr()) );
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int getCreatureMgr(lua_State* L) {
|
||||
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
|
||||
lua_pushlightuserdata(L, reinterpret_cast<void*>(room->GetCreatureMgr()) );
|
||||
@@ -103,6 +109,24 @@ static int forEachCreature(lua_State* L) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int forEachBarrier(lua_State* L) {
|
||||
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
|
||||
BarrierManager* barrierMgr = room->GetBarrierMgr();
|
||||
//pass each barrier to the given function
|
||||
for (auto& it : *barrierMgr->GetContainer()) {
|
||||
lua_pushvalue(L, -1);
|
||||
lua_pushlightuserdata(L, static_cast<void*>(&it.second));
|
||||
//call each iteration, throwing an exception if something happened
|
||||
if (lua_pcall(L, 1, 0, 0) != LUA_OK) {
|
||||
std::ostringstream os;
|
||||
os << "Lua error: ";
|
||||
os << lua_tostring(L, -1);
|
||||
throw(std::runtime_error(os.str()));
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int setOnTick(lua_State* L) {
|
||||
RoomData* room = reinterpret_cast<RoomData*>(lua_touserdata(L, 1));
|
||||
luaL_unref(L, LUA_REGISTRYINDEX, room->GetTickReference());
|
||||
@@ -116,6 +140,19 @@ static int getOnTick(lua_State* L) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
//TODO: autogen docs
|
||||
static int setTag(lua_State* L) {
|
||||
RoomData* room = static_cast<RoomData*>(lua_touserdata(L, 1));
|
||||
room->SetTag(lua_tostring(L, 2), lua_tostring(L, 3));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int getTag(lua_State* L) {
|
||||
RoomData* room = static_cast<RoomData*>(lua_touserdata(L, 1));
|
||||
lua_pushstring(L, room->GetTag(lua_tostring(L, 2)).c_str());
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int initialize(lua_State* L) {
|
||||
RoomData* room = static_cast<RoomData*>(lua_touserdata(L, 1));
|
||||
|
||||
@@ -135,16 +172,21 @@ static const luaL_Reg roomLib[] = {
|
||||
{"SetTileset", setTilesetName},
|
||||
{"GetTileset", getTilesetName},
|
||||
|
||||
{"GetBarrierMgr", getBarrierMgr},
|
||||
{"GetCreatureMgr",getCreatureMgr},
|
||||
{"GetPager",getPager},
|
||||
{"GetTriggerMgr",getTriggerMgr},
|
||||
|
||||
{"ForEachCharacter", forEachCharacter},
|
||||
{"ForEachCreature", forEachCreature},
|
||||
{"ForEachBarrier", forEachBarrier},
|
||||
|
||||
{"SetOnTick", setOnTick},
|
||||
{"GetOnTick", getOnTick},
|
||||
|
||||
{"SetTag", setTag},
|
||||
{"GetTag", getTag},
|
||||
|
||||
{"Initialize", initialize},
|
||||
{nullptr, nullptr}
|
||||
};
|
||||
|
||||
@@ -21,6 +21,8 @@
|
||||
*/
|
||||
#include "room_data.hpp"
|
||||
|
||||
#include "barrier_defines.hpp"
|
||||
#include "culling_defines.hpp"
|
||||
#include "serial_packet.hpp"
|
||||
#include "server_utilities.hpp"
|
||||
|
||||
@@ -34,86 +36,106 @@ void RoomData::RunFrame() {
|
||||
//get the hook
|
||||
lua_rawgeti(lua, LUA_REGISTRYINDEX, tickRef);
|
||||
|
||||
//returning 1 means pump all
|
||||
bool updateAll = false;
|
||||
if (!lua_isnil(lua, -1)) {
|
||||
//call the tick function, with this as a parameter
|
||||
lua_pushlightuserdata(lua, this);
|
||||
if (lua_pcall(lua, 1, 0, 0) != LUA_OK) {
|
||||
if (lua_pcall(lua, 1, 1, 0) != LUA_OK) {
|
||||
throw(std::runtime_error(std::string() + "Lua error: " + lua_tostring(lua, -1) ));
|
||||
}
|
||||
|
||||
//pump creatures & barriers
|
||||
if (lua_tonumber(lua, -1)) {
|
||||
updateAll = true;
|
||||
}
|
||||
|
||||
lua_pop(lua, 1);
|
||||
}
|
||||
else {
|
||||
lua_pop(lua, 1);
|
||||
}
|
||||
|
||||
//lists of non-character entities that need updating client-side
|
||||
std::list<std::pair<const int, CreatureData*>> creatureList;
|
||||
std::list<std::pair<const int, BarrierData*>> barrierList;
|
||||
|
||||
//update the entities in the room
|
||||
for (auto& it : characterList) {
|
||||
it->Update();
|
||||
}
|
||||
creatureMgr.Update(&creatureList, updateAll);
|
||||
barrierMgr.Update(&barrierList, updateAll);
|
||||
|
||||
//build a list of characters for use with the triggers
|
||||
//build a list of entities for use with the triggers
|
||||
std::stack<Entity*> entityStack;
|
||||
for (auto& it : characterList) {
|
||||
entityStack.push(it);
|
||||
}
|
||||
|
||||
//Compare the triggers to the entities, using their real hitboxes
|
||||
//NOTE: this stack solution should prevent problems when modifying the various lists
|
||||
while(entityStack.size()) {
|
||||
//get the entity & hitbox
|
||||
Entity* entity = entityStack.top();
|
||||
BoundingBox entityBox = entity->GetBounds() + entity->GetOrigin();
|
||||
triggerMgr.Compare(entityStack);
|
||||
|
||||
//get the trigger pair & hitbox
|
||||
for (auto& triggerPair : *triggerMgr.GetContainer()) {
|
||||
BoundingBox triggerBox = triggerPair.second.GetBoundingBox() + triggerPair.second.GetOrigin();
|
||||
//Creature/character collisions, O(m*n)
|
||||
for (auto characterIt : characterList) {
|
||||
BoundingBox characterBox = characterIt->GetBounds() + characterIt->GetOrigin();
|
||||
|
||||
//find all collisions
|
||||
if (entityBox.CheckOverlap(triggerBox)) {
|
||||
//skip members of the exclusion list
|
||||
if (std::any_of(triggerPair.second.GetExclusionList()->begin(), triggerPair.second.GetExclusionList()->end(), [entity](Entity* ptr) -> bool {
|
||||
return entity == ptr;
|
||||
})) {
|
||||
continue;
|
||||
}
|
||||
std::list<int> creatureUnloadList;
|
||||
|
||||
//run the trigger script
|
||||
lua_rawgeti(lua, LUA_REGISTRYINDEX, triggerPair.second.GetScriptReference());
|
||||
lua_pushlightuserdata(lua, entity);
|
||||
for (auto creatureIt : *creatureMgr.GetContainer()) {
|
||||
BoundingBox creatureBox = creatureIt.second.GetBounds() + creatureIt.second.GetOrigin();
|
||||
|
||||
if (lua_pcall(lua, 1, 0, 0) != LUA_OK) {
|
||||
//error
|
||||
throw(std::runtime_error(std::string() + "Lua error: " + lua_tostring(lua, -1) ));
|
||||
}
|
||||
|
||||
//push to the exclusion list
|
||||
triggerPair.second.GetExclusionList()->push_back(entity);
|
||||
}
|
||||
else {
|
||||
//remove members of the exclusion list
|
||||
//NOTE: characters in different rooms won't be removed, but that shouldn't be a problem
|
||||
triggerPair.second.GetExclusionList()->remove_if([entity](Entity* ptr) -> bool {
|
||||
return entity == ptr;
|
||||
if (characterBox.CheckOverlap(creatureBox)) {
|
||||
int barrierIndex = barrierMgr.Create(-1);
|
||||
BarrierData* barrierData = barrierMgr.Find(barrierIndex);
|
||||
barrierData->SetRoomIndex(roomIndex);
|
||||
barrierData->SetOrigin({
|
||||
(CREATURE_BOUNDS_WIDTH - BARRIER_BOUNDS_WIDTH) / 2 + creatureBox.x,
|
||||
(CREATURE_BOUNDS_HEIGHT - BARRIER_BOUNDS_HEIGHT) / 2 + creatureBox.y,
|
||||
});
|
||||
|
||||
BarrierPacket barrierPacket;
|
||||
barrierPacket.type = SerialPacketType::BARRIER_CREATE;
|
||||
copyBarrierToPacket(&barrierPacket, barrierData, barrierIndex);
|
||||
|
||||
pumpPacketProximity(reinterpret_cast<SerialPacket*>(&barrierPacket), roomIndex, characterIt->GetOrigin(), INFLUENCE_RADIUS);
|
||||
|
||||
//delete this creature
|
||||
creatureUnloadList.push_back(creatureIt.first);
|
||||
}
|
||||
}
|
||||
|
||||
//next
|
||||
entityStack.pop();
|
||||
//actually unload these creatures
|
||||
for (auto& it : creatureUnloadList) {
|
||||
CreatureData* creatureData = creatureMgr.Find(it);
|
||||
|
||||
CreaturePacket creaturePacket;
|
||||
creaturePacket.type = SerialPacketType::CREATURE_UNLOAD;
|
||||
copyCreatureToPacket(&creaturePacket, creatureData, it);
|
||||
|
||||
pumpPacketProximity(reinterpret_cast<SerialPacket*>(&creaturePacket), roomIndex, creatureData->GetOrigin(), INFLUENCE_RADIUS);
|
||||
|
||||
creatureMgr.Unload(it);
|
||||
}
|
||||
}
|
||||
|
||||
//a list of creatures that need to be updated client-side
|
||||
std::list< std::pair<const int, CreatureData*>> creatureList;
|
||||
creatureMgr.Update(&creatureList);
|
||||
|
||||
//send the updates
|
||||
//send the creature updates
|
||||
for (auto& it : creatureList) {
|
||||
CreaturePacket packet;
|
||||
copyCreatureToPacket(&packet, it.second, it.first);
|
||||
packet.type = SerialPacketType::CREATURE_UPDATE;
|
||||
pumpPacketProximity(reinterpret_cast<SerialPacket*>(&packet), roomIndex, it.second->GetOrigin(), 320);
|
||||
packet.roomIndex = roomIndex;
|
||||
pumpPacketProximity(reinterpret_cast<SerialPacket*>(&packet), roomIndex, it.second->GetOrigin(), INFLUENCE_RADIUS);
|
||||
}
|
||||
|
||||
//TODO: creature/character collisions
|
||||
//send the barrier updates
|
||||
for (auto& it : barrierList) {
|
||||
BarrierPacket packet;
|
||||
copyBarrierToPacket(&packet, it.second, it.first);
|
||||
packet.type = SerialPacketType::BARRIER_UPDATE;
|
||||
packet.roomIndex = roomIndex;
|
||||
pumpPacketProximity(reinterpret_cast<SerialPacket*>(&packet), roomIndex, it.second->GetOrigin(), INFLUENCE_RADIUS);
|
||||
}
|
||||
}
|
||||
|
||||
std::string RoomData::SetName(std::string s) {
|
||||
@@ -140,6 +162,10 @@ int RoomData::GetRoomIndex() {
|
||||
return roomIndex;
|
||||
}
|
||||
|
||||
BarrierManager* RoomData::GetBarrierMgr() {
|
||||
return &barrierMgr;
|
||||
}
|
||||
|
||||
std::list<CharacterData*>* RoomData::GetCharacterList() {
|
||||
return &characterList;
|
||||
}
|
||||
@@ -158,6 +184,7 @@ TriggerManager* RoomData::GetTriggerMgr() {
|
||||
|
||||
lua_State* RoomData::SetLuaState(lua_State* L) {
|
||||
lua = L;
|
||||
barrierMgr.SetLuaState(lua);
|
||||
creatureMgr.SetLuaState(lua);
|
||||
pager.SetLuaState(lua);
|
||||
triggerMgr.SetLuaState(lua);
|
||||
@@ -169,6 +196,7 @@ lua_State* RoomData::GetLuaState() {
|
||||
}
|
||||
|
||||
sqlite3* RoomData::SetDatabase(sqlite3* db) {
|
||||
//TODO: (1) set database here
|
||||
database = db;
|
||||
return database;
|
||||
}
|
||||
@@ -183,4 +211,12 @@ int RoomData::SetTickReference(int i) {
|
||||
|
||||
int RoomData::GetTickReference() {
|
||||
return tickRef;
|
||||
}
|
||||
|
||||
std::string RoomData::SetTag(std::string key, std::string value) {
|
||||
return tags[key] = value;
|
||||
}
|
||||
|
||||
std::string RoomData::GetTag(std::string key) {
|
||||
return tags[key];
|
||||
}
|
||||
@@ -21,7 +21,9 @@
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "barrier_manager.hpp"
|
||||
#include "character_data.hpp"
|
||||
#include "combat_instance_manager.hpp"
|
||||
#include "creature_manager.hpp"
|
||||
#include "region_pager_lua.hpp"
|
||||
#include "trigger_manager.hpp"
|
||||
@@ -51,6 +53,7 @@ public:
|
||||
int SetRoomIndex(int i);
|
||||
int GetRoomIndex();
|
||||
|
||||
BarrierManager* GetBarrierMgr();
|
||||
std::list<CharacterData*>* GetCharacterList();
|
||||
CreatureManager* GetCreatureMgr();
|
||||
RegionPagerLua* GetPager();
|
||||
@@ -67,6 +70,9 @@ public:
|
||||
int GetTickReference();
|
||||
//TODO: other triggers like player entry & exit, etc.
|
||||
|
||||
std::string SetTag(std::string key, std::string value);
|
||||
std::string GetTag(std::string key);
|
||||
|
||||
private:
|
||||
//metadata
|
||||
std::string roomName;
|
||||
@@ -74,7 +80,9 @@ private:
|
||||
|
||||
//members
|
||||
int roomIndex = 0;
|
||||
BarrierManager barrierMgr;
|
||||
std::list<CharacterData*> characterList;
|
||||
CombatInstanceManager CombatInstanceMgr;
|
||||
CreatureManager creatureMgr;
|
||||
RegionPagerLua pager;
|
||||
TriggerManager triggerMgr;
|
||||
@@ -85,4 +93,5 @@ private:
|
||||
|
||||
//hooks
|
||||
int tickRef = LUA_NOREF;
|
||||
std::map<std::string, std::string> tags;
|
||||
};
|
||||
|
||||
@@ -116,7 +116,7 @@ void RoomManager::PushCharacter(CharacterData* character) {
|
||||
throw(std::runtime_error("Failed to push a null character to a room"));
|
||||
}
|
||||
|
||||
RoomData* room = Get(character->GetRoomIndex());
|
||||
RoomData* room = Find(character->GetRoomIndex());
|
||||
|
||||
if (!room) {
|
||||
throw(std::runtime_error("Failed to push an character to a non-existant room"));
|
||||
@@ -131,7 +131,7 @@ void RoomManager::PopCharacter(CharacterData const* character) {
|
||||
throw(std::runtime_error("Failed to pop a null character to a room"));
|
||||
}
|
||||
|
||||
RoomData* room = Get(character->GetRoomIndex());
|
||||
RoomData* room = Find(character->GetRoomIndex());
|
||||
|
||||
if (!room) {
|
||||
throw(std::runtime_error("Failed to pop an character to a non-existant room"));
|
||||
@@ -143,7 +143,7 @@ void RoomManager::PopCharacter(CharacterData const* character) {
|
||||
}
|
||||
|
||||
//TODO: rename these functions from Get to Find
|
||||
RoomData* RoomManager::Get(int uid) {
|
||||
RoomData* RoomManager::Find(int uid) {
|
||||
std::map<int, RoomData>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
@@ -153,7 +153,7 @@ RoomData* RoomManager::Get(int uid) {
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
RoomData* RoomManager::Get(std::string name) {
|
||||
RoomData* RoomManager::Find(std::string name) {
|
||||
for (std::map<int, RoomData>::iterator it = elementMap.begin(); it != elementMap.end(); ++it) {
|
||||
if (it->second.GetName() == name) {
|
||||
return &it->second;
|
||||
|
||||
@@ -43,8 +43,8 @@ public:
|
||||
void PopCharacter(CharacterData const* character);
|
||||
|
||||
//accessors and mutators
|
||||
RoomData* Get(int uid);
|
||||
RoomData* Get(std::string name);
|
||||
RoomData* Find(int uid);
|
||||
RoomData* Find(std::string name);
|
||||
int GetLoadedCount();
|
||||
std::map<int, RoomData>* GetContainer();
|
||||
|
||||
|
||||
@@ -27,7 +27,7 @@ int createRoom(lua_State* L) {
|
||||
//create & get the room
|
||||
RoomManager& roomMgr = RoomManager::GetSingleton();
|
||||
int uid = roomMgr.Create(lua_tostring(L, 1), lua_tostring(L, 2));
|
||||
RoomData* room = roomMgr.Get(uid);
|
||||
RoomData* room = roomMgr.Find(uid);
|
||||
|
||||
//TODO: initialization parameters here?
|
||||
|
||||
@@ -70,7 +70,7 @@ int unloadRoom(lua_State* L) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int getRoom(lua_State* L) {
|
||||
int findRoom(lua_State* L) {
|
||||
//integer vs name for getRoom()
|
||||
RoomManager& roomMgr = RoomManager::GetSingleton();
|
||||
RoomData* room = nullptr;
|
||||
@@ -78,11 +78,11 @@ int getRoom(lua_State* L) {
|
||||
switch(lua_type(L, 1)) {
|
||||
case LUA_TNUMBER:
|
||||
//number
|
||||
room = roomMgr.Get(lua_tointeger(L, 1));
|
||||
room = roomMgr.Find(lua_tointeger(L, 1));
|
||||
break;
|
||||
case LUA_TSTRING:
|
||||
//name
|
||||
room = roomMgr.Get(lua_tostring(L, 1));
|
||||
room = roomMgr.Find(lua_tostring(L, 1));
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -113,7 +113,7 @@ static int setOnUnload(lua_State* L) {
|
||||
static const luaL_Reg roomManagerLib[] = {
|
||||
{"CreateRoom", createRoom},
|
||||
{"UnloadRoom", unloadRoom},
|
||||
{"GetRoom", getRoom},
|
||||
{"FindRoom", findRoom},
|
||||
{"SetOnCreate", setOnCreate},
|
||||
{"SetOnUnload", setOnUnload},
|
||||
{nullptr, nullptr}
|
||||
|
||||
@@ -302,11 +302,17 @@ void ServerApplication::HandlePacket(SerialPacket* const argPacket) {
|
||||
hCharacterMovement(static_cast<CharacterPacket*>(argPacket));
|
||||
break;
|
||||
|
||||
//TODO: (1) merge character, creature & barrier queries & updates together?
|
||||
//creature management
|
||||
case SerialPacketType::QUERY_CREATURE_EXISTS:
|
||||
hQueryCreatureExists(static_cast<CreaturePacket*>(argPacket));
|
||||
break;
|
||||
|
||||
//barrier management
|
||||
case SerialPacketType::QUERY_BARRIER_EXISTS:
|
||||
hQueryBarrierExists(static_cast<BarrierPacket*>(argPacket));
|
||||
break;
|
||||
|
||||
//chat
|
||||
case SerialPacketType::TEXT_BROADCAST:
|
||||
hTextBroadcast(static_cast<TextPacket*>(argPacket));
|
||||
@@ -376,7 +382,7 @@ void ServerApplication::hJoinRequest(ClientPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hLoginRequest(ClientPacket* const argPacket) {
|
||||
//get the client data
|
||||
ClientData* clientData = clientMgr.Get(argPacket->clientIndex);
|
||||
ClientData* clientData = clientMgr.Find(argPacket->clientIndex);
|
||||
|
||||
if (clientData == nullptr || clientData->GetAddress() != argPacket->srcAddress) {
|
||||
std::cerr << "Falsified client index detected: " << argPacket->clientIndex << std::endl;
|
||||
@@ -421,12 +427,12 @@ void ServerApplication::hLoginRequest(ClientPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hLogoutRequest(ClientPacket* const argPacket) {
|
||||
//get the account and client data
|
||||
AccountData* accountData = accountMgr.Get(argPacket->accountIndex);
|
||||
AccountData* accountData = accountMgr.Find(argPacket->accountIndex);
|
||||
if (!accountData) {
|
||||
return;
|
||||
}
|
||||
|
||||
ClientData* clientData = clientMgr.Get(accountData->GetClientIndex());
|
||||
ClientData* clientData = clientMgr.Find(accountData->GetClientIndex());
|
||||
if (!clientData) {
|
||||
std::ostringstream msg;
|
||||
msg << "No client found for an account: " << accountData->GetUsername();
|
||||
@@ -455,7 +461,7 @@ void ServerApplication::hLogoutRequest(ClientPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hDisconnectRequest(ClientPacket* const argPacket) {
|
||||
//get the client data
|
||||
ClientData* clientData = clientMgr.Get(argPacket->clientIndex);
|
||||
ClientData* clientData = clientMgr.Find(argPacket->clientIndex);
|
||||
if (!clientData) {
|
||||
return;
|
||||
}
|
||||
@@ -490,11 +496,11 @@ void ServerApplication::hAdminDisconnectForced(ClientPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hAdminShutdownRequest(ClientPacket* const argPacket) {
|
||||
//get the account and client data
|
||||
AccountData* accountData = accountMgr.Get(argPacket->accountIndex);
|
||||
AccountData* accountData = accountMgr.Find(argPacket->accountIndex);
|
||||
if (!accountData) {
|
||||
return;
|
||||
}
|
||||
ClientData* clientData = clientMgr.Get(accountData->GetClientIndex());
|
||||
ClientData* clientData = clientMgr.Find(accountData->GetClientIndex());
|
||||
if (!clientData) {
|
||||
std::ostringstream msg;
|
||||
msg << "No client found for an account: " << accountData->GetUsername();
|
||||
@@ -545,7 +551,7 @@ void ServerApplication::hAdminShutdownRequest(ClientPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hRegionRequest(RegionPacket* const argPacket) {
|
||||
//get the region object, send a rejection on error
|
||||
RoomData* room = roomMgr.Get(argPacket->roomIndex);
|
||||
RoomData* room = roomMgr.Find(argPacket->roomIndex);
|
||||
if (!room) {
|
||||
//build the error message
|
||||
std::ostringstream msg;
|
||||
@@ -618,7 +624,7 @@ void ServerApplication::hCharacterCreate(CharacterPacket* const argPacket) {
|
||||
}
|
||||
|
||||
//push to the rooms
|
||||
CharacterData* characterData = characterMgr.Get(characterIndex);
|
||||
CharacterData* characterData = characterMgr.Find(characterIndex);
|
||||
roomMgr.PushCharacter(characterData);
|
||||
|
||||
//pump this character to all clients
|
||||
@@ -630,11 +636,11 @@ void ServerApplication::hCharacterCreate(CharacterPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hCharacterDelete(CharacterPacket* const argPacket) {
|
||||
//get the user's data
|
||||
AccountData* accountData = accountMgr.Get(argPacket->accountIndex);
|
||||
AccountData* accountData = accountMgr.Find(argPacket->accountIndex);
|
||||
if (!accountData) {
|
||||
return;
|
||||
}
|
||||
ClientData* clientData = clientMgr.Get(accountData->GetClientIndex());
|
||||
ClientData* clientData = clientMgr.Find(accountData->GetClientIndex());
|
||||
if (!clientData) {
|
||||
return;
|
||||
}
|
||||
@@ -663,7 +669,7 @@ void ServerApplication::hCharacterDelete(CharacterPacket* const argPacket) {
|
||||
}
|
||||
|
||||
//pop from the rooms
|
||||
CharacterData* characterData = characterMgr.Get(characterIndex);
|
||||
CharacterData* characterData = characterMgr.Find(characterIndex);
|
||||
roomMgr.PopCharacter(characterData);
|
||||
|
||||
//pump character unload
|
||||
@@ -700,7 +706,7 @@ void ServerApplication::hCharacterLoad(CharacterPacket* const argPacket) {
|
||||
}
|
||||
|
||||
//push to the rooms
|
||||
CharacterData* characterData = characterMgr.Get(characterIndex);
|
||||
CharacterData* characterData = characterMgr.Find(characterIndex);
|
||||
roomMgr.PushCharacter(characterData);
|
||||
|
||||
//pump this character to all clients
|
||||
@@ -712,17 +718,17 @@ void ServerApplication::hCharacterLoad(CharacterPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hCharacterUnload(CharacterPacket* const argPacket) {
|
||||
//get the entries
|
||||
CharacterData* characterData = characterMgr.Get(argPacket->characterIndex);
|
||||
CharacterData* characterData = characterMgr.Find(argPacket->characterIndex);
|
||||
if (!characterData) {
|
||||
return;
|
||||
}
|
||||
|
||||
AccountData* accountData = accountMgr.Get(characterData->GetOwner());
|
||||
AccountData* accountData = accountMgr.Find(characterData->GetOwner());
|
||||
if (!accountData) {
|
||||
return;
|
||||
}
|
||||
|
||||
ClientData* clientData = clientMgr.Get(accountData->GetClientIndex());
|
||||
ClientData* clientData = clientMgr.Find(accountData->GetClientIndex());
|
||||
if (!clientData) {
|
||||
return;
|
||||
}
|
||||
@@ -748,20 +754,20 @@ void ServerApplication::hCharacterUnload(CharacterPacket* const argPacket) {
|
||||
|
||||
void ServerApplication::hCharacterMovement(CharacterPacket* const argPacket) {
|
||||
//get the specified objects
|
||||
AccountData* accountData = accountMgr.Get(argPacket->accountIndex);
|
||||
AccountData* accountData = accountMgr.Find(argPacket->accountIndex);
|
||||
|
||||
if (!accountData) {
|
||||
throw(std::runtime_error("Failed to move a character, missing account"));
|
||||
}
|
||||
|
||||
CharacterData* characterData = characterMgr.Get(argPacket->characterIndex);
|
||||
CharacterData* characterData = characterMgr.Find(argPacket->characterIndex);
|
||||
|
||||
if (!characterData) {
|
||||
throw(std::runtime_error("Failed to move a character, missing character"));
|
||||
}
|
||||
|
||||
//get this account's client
|
||||
ClientData* clientData = clientMgr.Get(accountData->GetClientIndex());
|
||||
ClientData* clientData = clientMgr.Find(accountData->GetClientIndex());
|
||||
|
||||
//check for fraud
|
||||
if (clientData->GetAddress() != argPacket->srcAddress) {
|
||||
@@ -809,9 +815,9 @@ void ServerApplication::hQueryCreatureExists(CreaturePacket* const argPacket) {
|
||||
//respond with all creature data
|
||||
CreaturePacket newPacket;
|
||||
|
||||
CreatureManager* creatureMgr = roomMgr.Get(argPacket->roomIndex)->GetCreatureMgr();
|
||||
CreatureManager* creatureMgr = roomMgr.Find(argPacket->roomIndex)->GetCreatureMgr();
|
||||
|
||||
//TODO: move this into the room class
|
||||
//TODO: (0) move this into the room class?
|
||||
for (auto& it : *(creatureMgr->GetContainer()) ) {
|
||||
copyCreatureToPacket(&newPacket, &(it.second), it.first);
|
||||
newPacket.type = SerialPacketType::QUERY_CREATURE_EXISTS;
|
||||
@@ -820,6 +826,27 @@ void ServerApplication::hQueryCreatureExists(CreaturePacket* const argPacket) {
|
||||
}
|
||||
}
|
||||
|
||||
//-------------------------
|
||||
//barrier management
|
||||
//-------------------------
|
||||
|
||||
//TODO: On barrier create, etc.
|
||||
|
||||
void ServerApplication::hQueryBarrierExists(BarrierPacket* const argPacket) {
|
||||
//respond with all barrier data
|
||||
BarrierPacket newPacket;
|
||||
|
||||
BarrierManager* barrierMgr = roomMgr.Find(argPacket->roomIndex)->GetBarrierMgr();
|
||||
|
||||
//TODO: (0) move this into the room class?
|
||||
for (auto& it : *(barrierMgr->GetContainer()) ) {
|
||||
copyBarrierToPacket(&newPacket, &(it.second), it.first);
|
||||
newPacket.type = SerialPacketType::QUERY_BARRIER_EXISTS;
|
||||
newPacket.roomIndex = argPacket->roomIndex;
|
||||
network.SendTo(argPacket->srcAddress, static_cast<SerialPacket*>(&newPacket));
|
||||
}
|
||||
}
|
||||
|
||||
//-------------------------
|
||||
//chat
|
||||
//-------------------------
|
||||
|
||||
@@ -100,6 +100,9 @@ private:
|
||||
//creature management
|
||||
void hQueryCreatureExists(CreaturePacket* const);
|
||||
|
||||
//barrier management
|
||||
void hQueryBarrierExists(BarrierPacket* const);
|
||||
|
||||
//chat
|
||||
void hTextBroadcast(TextPacket* const);
|
||||
void hTextSpeech(TextPacket* const);
|
||||
|
||||
@@ -130,7 +130,7 @@ void pumpPacket(SerialPacket* const argPacket) {
|
||||
|
||||
void pumpPacketProximity(SerialPacket* const argPacket, int roomIndex, Vector2 position, int distance) {
|
||||
//send this packet to all characters within a certain distance of a point in a room
|
||||
RoomData* roomData = RoomManager::GetSingleton().Get(roomIndex);
|
||||
RoomData* roomData = RoomManager::GetSingleton().Find(roomIndex);
|
||||
|
||||
if (!roomData) {
|
||||
throw(std::runtime_error("Failed to pump to a non-existant room"));
|
||||
@@ -141,15 +141,15 @@ void pumpPacketProximity(SerialPacket* const argPacket, int roomIndex, Vector2 p
|
||||
|
||||
for (auto& characterIt : *roomData->GetCharacterList()) {
|
||||
if (distance == -1 || (characterIt->GetOrigin() - position).Length() <= distance) {
|
||||
accountData = AccountManager::GetSingleton().Get(characterIt->GetOwner());
|
||||
clientData = ClientManager::GetSingleton().Get(accountData->GetClientIndex());
|
||||
accountData = AccountManager::GetSingleton().Find(characterIt->GetOwner());
|
||||
clientData = ClientManager::GetSingleton().Find(accountData->GetClientIndex());
|
||||
UDPNetworkUtility::GetSingleton().SendTo(clientData->GetAddress(), argPacket);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void copyCharacterToPacket(CharacterPacket* const packet, int characterIndex) {
|
||||
CharacterData* characterData = CharacterManager::GetSingleton().Get(characterIndex);
|
||||
CharacterData* characterData = CharacterManager::GetSingleton().Find(characterIndex);
|
||||
if (!characterData) {
|
||||
throw(std::runtime_error("Failed to copy a character to a packet"));
|
||||
}
|
||||
@@ -177,9 +177,19 @@ void copyCreatureToPacket(CreaturePacket* const packet, CreatureData* const crea
|
||||
packet->bounds = creatureData->GetBounds();
|
||||
}
|
||||
|
||||
void copyBarrierToPacket(BarrierPacket* const packet, BarrierData* const barrierData, int barrierIndex) {
|
||||
packet->barrierIndex = barrierIndex;
|
||||
packet->roomIndex = barrierData->GetRoomIndex();
|
||||
packet->origin = barrierData->GetOrigin();
|
||||
packet->motion = barrierData->GetMotion();
|
||||
packet->bounds = barrierData->GetBounds();
|
||||
|
||||
memcpy(packet->status, barrierData->GetStatusArray(), sizeof(int) * 8);
|
||||
}
|
||||
|
||||
void pumpAndChangeRooms(int characterIndex, int newRoomIndex) {
|
||||
//get the character object
|
||||
CharacterData* character = CharacterManager::GetSingleton().Get(characterIndex);
|
||||
CharacterData* character = CharacterManager::GetSingleton().Find(characterIndex);
|
||||
|
||||
//pass ownwards
|
||||
pumpAndChangeRooms(character, newRoomIndex, characterIndex);
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "barrier_data.hpp"
|
||||
#include "character_data.hpp"
|
||||
#include "creature_data.hpp"
|
||||
#include "serial_packet.hpp"
|
||||
@@ -38,7 +39,9 @@ void copyCharacterToPacket(CharacterPacket* const packet, CharacterData* const c
|
||||
|
||||
void copyCreatureToPacket(CreaturePacket* const packet, CreatureData* const creatureData, int creatureIndex);
|
||||
|
||||
void copyBarrierToPacket(BarrierPacket* const packet, BarrierData* const barrierData, int barrierIndex);
|
||||
|
||||
void pumpAndChangeRooms(int characterIndex, int newRoomIndex);
|
||||
void pumpAndChangeRooms(CharacterData* const characterData, int newRoomIndex, int characterIndex);
|
||||
|
||||
double distance(Vector2 lhs, Vector2 rhs);
|
||||
double distance(Vector2 lhs, Vector2 rhs);
|
||||
@@ -29,6 +29,53 @@ TriggerManager::~TriggerManager() {
|
||||
UnloadAll();
|
||||
}
|
||||
|
||||
//Compare the triggers to the entities, using their real hitboxes
|
||||
void TriggerManager::Compare(std::stack<Entity*> entityStack) {
|
||||
//NOTE: this stack solution should prevent problems when modifying the various lists
|
||||
while(entityStack.size()) {
|
||||
//get the entity & hitbox
|
||||
Entity* entity = entityStack.top();
|
||||
BoundingBox entityBox = entity->GetBounds() + entity->GetOrigin();
|
||||
|
||||
//get the trigger pair & hitbox
|
||||
for (auto& triggerPair : elementMap) {
|
||||
BoundingBox triggerBox = triggerPair.second.GetBoundingBox() + triggerPair.second.GetOrigin();
|
||||
|
||||
//find all collisions
|
||||
if (entityBox.CheckOverlap(triggerBox)) {
|
||||
//skip members of the exclusion list
|
||||
if (std::any_of(triggerPair.second.GetExclusionList()->begin(), triggerPair.second.GetExclusionList()->end(), [entity](Entity* ptr) -> bool {
|
||||
return entity == ptr;
|
||||
})) {
|
||||
continue;
|
||||
}
|
||||
|
||||
//run the trigger script
|
||||
lua_rawgeti(lua, LUA_REGISTRYINDEX, triggerPair.second.GetScriptReference());
|
||||
lua_pushlightuserdata(lua, entity);
|
||||
|
||||
if (lua_pcall(lua, 1, 0, 0) != LUA_OK) {
|
||||
//error
|
||||
throw(std::runtime_error(std::string() + "Lua error: " + lua_tostring(lua, -1) ));
|
||||
}
|
||||
|
||||
//push to the exclusion list
|
||||
triggerPair.second.GetExclusionList()->push_back(entity);
|
||||
}
|
||||
else {
|
||||
//remove members of the exclusion list
|
||||
//NOTE: characters in different rooms won't be removed, but that shouldn't be a problem
|
||||
triggerPair.second.GetExclusionList()->remove_if([entity](Entity* ptr) -> bool {
|
||||
return entity == ptr;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
//next
|
||||
entityStack.pop();
|
||||
}
|
||||
}
|
||||
|
||||
int TriggerManager::Create(std::string handle) {
|
||||
//implicitly creates the element
|
||||
TriggerData& triggerData = elementMap[counter];
|
||||
@@ -59,7 +106,7 @@ void TriggerManager::UnloadIf(std::function<bool(std::pair<const int, TriggerDat
|
||||
}
|
||||
}
|
||||
|
||||
TriggerData* TriggerManager::Get(int uid) {
|
||||
TriggerData* TriggerManager::Find(int uid) {
|
||||
std::map<int, TriggerData>::iterator it = elementMap.find(uid);
|
||||
|
||||
if (it == elementMap.end()) {
|
||||
@@ -69,7 +116,7 @@ TriggerData* TriggerManager::Get(int uid) {
|
||||
return &it->second;
|
||||
}
|
||||
|
||||
TriggerData* TriggerManager::Get(std::string handle) {
|
||||
TriggerData* TriggerManager::Find(std::string handle) {
|
||||
for (std::map<int, TriggerData>::iterator it = elementMap.begin(); it != elementMap.end(); ++it) {
|
||||
if (it->second.GetHandle() == handle) {
|
||||
return &it->second;
|
||||
|
||||
@@ -29,6 +29,7 @@
|
||||
|
||||
#include <functional>
|
||||
#include <map>
|
||||
#include <stack>
|
||||
#include <string>
|
||||
|
||||
class TriggerManager {
|
||||
@@ -36,6 +37,8 @@ public:
|
||||
TriggerManager();
|
||||
~TriggerManager();
|
||||
|
||||
void Compare(std::stack<Entity*> entityStack);
|
||||
|
||||
//common public methods
|
||||
int Create(std::string handle); //TODO: return the Trigger itself?
|
||||
void Unload(int uid);
|
||||
@@ -44,8 +47,8 @@ public:
|
||||
void UnloadIf(std::function<bool(std::pair<const int, TriggerData const&>)> fn);
|
||||
|
||||
//accessors & mutators
|
||||
TriggerData* Get(int uid);
|
||||
TriggerData* Get(std::string handle);
|
||||
TriggerData* Find(int uid);
|
||||
TriggerData* Find(std::string handle);
|
||||
int GetLoadedCount();
|
||||
std::map<int, TriggerData>* GetContainer();
|
||||
|
||||
|
||||
@@ -31,7 +31,7 @@ static int create(lua_State* L) {
|
||||
|
||||
//create the trigger
|
||||
int index = mgr->Create(lua_tostring(L, 2));
|
||||
TriggerData* triggerData = mgr->Get(index);
|
||||
TriggerData* triggerData = mgr->Find(index);
|
||||
|
||||
//origin
|
||||
if (lua_gettop(L) >= 4) {
|
||||
@@ -101,16 +101,16 @@ static int unload(lua_State* L) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int getTrigger(lua_State* L) {
|
||||
static int findTrigger(lua_State* L) {
|
||||
TriggerManager* mgr = static_cast<TriggerManager*>(lua_touserdata(L, 1));
|
||||
TriggerData* triggerData = nullptr;
|
||||
|
||||
switch(lua_type(L, 2)) {
|
||||
case LUA_TNUMBER:
|
||||
triggerData = mgr->Get(lua_tointeger(L, 2));
|
||||
triggerData = mgr->Find(lua_tointeger(L, 2));
|
||||
break;
|
||||
case LUA_TSTRING:
|
||||
triggerData = mgr->Get(lua_tostring(L, 2));
|
||||
triggerData = mgr->Find(lua_tostring(L, 2));
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -137,7 +137,7 @@ static int getLoadedCount(lua_State* L) {
|
||||
static const luaL_Reg triggerManagerLib[] = {
|
||||
{"Create",create},
|
||||
{"Unload",unload},
|
||||
{"GetTrigger",getTrigger},
|
||||
{"FindTrigger",findTrigger},
|
||||
{"GetCount",getLoadedCount},
|
||||
{nullptr, nullptr}
|
||||
};
|
||||
|
||||