From c8cb0ee93978dd8b4646cb4cb37e5fb397fcabd3 Mon Sep 17 00:00:00 2001 From: FakeShemp Date: Wed, 9 Dec 2015 11:58:49 +0100 Subject: [PATCH 001/224] Grab all materials --- tools/MayaExporter/MayaExporter/Material.cpp | 239 ++++++++++++++++++ tools/MayaExporter/MayaExporter/Material.h | 46 ++++ .../MayaExporter/MayaExporter.vcxproj | 2 + .../MayaExporter/MayaExporter.vcxproj.filters | 6 + .../MayaExporter/MayaExporter/MayaIncludes.h | 1 + tools/MayaExporter/MayaExporter/Menu.cpp | 14 +- tools/MayaExporter/MayaExporter/Menu.h | 4 +- 7 files changed, 307 insertions(+), 5 deletions(-) create mode 100644 tools/MayaExporter/MayaExporter/Material.cpp create mode 100644 tools/MayaExporter/MayaExporter/Material.h diff --git a/tools/MayaExporter/MayaExporter/Material.cpp b/tools/MayaExporter/MayaExporter/Material.cpp new file mode 100644 index 00000000..53d029dc --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Material.cpp @@ -0,0 +1,239 @@ +#include "Material.h" + +void Material::grabLambertProperties(MaterialNode& material_node, MFnDependencyNode& node) +{ + material_node.Name = node.name().asChar(); + + if (findColorTexture(material_node, node)) { + material_node.Color.fill(1.0f); + } + else { + m_Plug = node.findPlug("colorR"); + m_Plug.getValue(material_node.Color[0]); + m_Plug = node.findPlug("colorG"); + m_Plug.getValue(material_node.Color[1]); + m_Plug = node.findPlug("colorB"); + m_Plug.getValue(material_node.Color[2]); + + float TempTransp[3]; + m_Plug = node.findPlug("transparencyR"); + m_Plug.getValue(TempTransp[0]); + m_Plug = node.findPlug("transparencyG"); + m_Plug.getValue(TempTransp[1]); + m_Plug = node.findPlug("transparencyB"); + m_Plug.getValue(TempTransp[2]); + + MColor TranspNode(TempTransp[0], TempTransp[1], TempTransp[2]); + float DummyH, DummyS; + TranspNode.get(MColor::kHSV, DummyH, DummyS, material_node.Color[3]); + } + + if (findIncandescenceTexture(material_node, node)) { + material_node.Incandescence.fill(1.0f); + } + else { + m_Plug = node.findPlug("incandescenceR"); + m_Plug.getValue(material_node.Incandescence[0]); + m_Plug = node.findPlug("incandescenceG"); + m_Plug.getValue(material_node.Incandescence[1]); + m_Plug = node.findPlug("incandescenceB"); + m_Plug.getValue(material_node.Incandescence[2]); + } + + findNormalTexture(material_node, node); +} + +void Material::grabBlinnProperties(MaterialNode& material_node, MFnDependencyNode& node) +{ + if (findSpecularTexture(material_node, node)) { + material_node.Specular.fill(1.0f); + } + else { + m_Plug = node.findPlug("specularColorR"); + m_Plug.getValue(material_node.Specular[0]); + m_Plug = node.findPlug("specularColorG"); + m_Plug.getValue(material_node.Specular[1]); + m_Plug = node.findPlug("specularColorB"); + m_Plug.getValue(material_node.Specular[2]); + } + + m_Plug = node.findPlug("reflectivity"); + m_Plug.getValue(material_node.ReflectionFactor); + + m_Plug = node.findPlug("eccentricity"); + float TempEccent; + m_Plug.getValue(TempEccent); + + // Blinn works differently from Phong which is used in-game. + // This is some magic numbers and math to make a conversion estimate between the two. + // There is no exact conversion between the two, so there are errors. + + // Phong min/max is around Blinn 0.7/0.1 + TempEccent = std::max(std::min(TempEccent, 0.7f), 0.1f); + + material_node.SpecularExponent = std::max(std::min(((2.66f) + (427.0f) * exp((-14.8f) * TempEccent)), 100.0f), 2.0f); +} + +void Material::grabPhongProperties(MaterialNode& material_node, MFnDependencyNode& node) +{ + if (findSpecularTexture(material_node, node)) { + material_node.Specular.fill(1.0f); + } + else { + m_Plug = node.findPlug("specularColorR"); + m_Plug.getValue(material_node.Specular[0]); + m_Plug = node.findPlug("specularColorG"); + m_Plug.getValue(material_node.Specular[1]); + m_Plug = node.findPlug("specularColorB"); + m_Plug.getValue(material_node.Specular[2]); + } + + m_Plug = node.findPlug("reflectivity"); + m_Plug.getValue(material_node.ReflectionFactor); + + m_Plug = node.findPlug("cosinePower "); + m_Plug.getValue(material_node.SpecularExponent); +} + +bool Material::findColorTexture(MaterialNode& material_node, MFnDependencyNode& node) +{ + MPlugArray AllConnections; + + m_Plug = node.findPlug("color", true); + m_Plug.connectedTo(AllConnections, true, false); + + for (int i = 0; i < AllConnections.length(); i++) { + if (AllConnections[i].node().hasFn(MFn::kFileTexture)) { + MFnDependencyNode TextureNode(AllConnections[i].node()); + + std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); + m_TexturePaths.push_back(FullPath); + + material_node.ColorMapFile = FullPath.substr(FullPath.find_last_of("/")); + + return true; + } + } + + return false; +} + +bool Material::findNormalTexture(MaterialNode& material_node, MFnDependencyNode& node) +{ + MPlugArray AllConnections; + MPlugArray AllBumpConnections; + + m_Plug = node.findPlug("normalCamera", true); + m_Plug.connectedTo(AllConnections, true, false); + + for (int i = 0; i < AllConnections.length(); i++) { + if (AllConnections[i].node().apiType() == MFn::kBump) { + MFnDependencyNode BumpNode(AllConnections[i].node()); + + BumpNode.findPlug("bumpValue").connectedTo(AllBumpConnections, true, false); + for (int j = 0; j < AllBumpConnections.length(); j++) { + if (AllBumpConnections[j].node().hasFn(MFn::kFileTexture)) { + MFnDependencyNode TextureNode(AllBumpConnections[j].node()); + + std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); + m_TexturePaths.push_back(FullPath); + + material_node.NormalMapFile = FullPath.substr(FullPath.find_last_of("/")); + + return true; + } + } + } + } + + return false; +} + +bool Material::findSpecularTexture(MaterialNode& material_node, MFnDependencyNode& node) +{ + MPlugArray AllConnections; + + m_Plug = node.findPlug("specularColor", true); + m_Plug.connectedTo(AllConnections, true, false); + + for (int i = 0; i < AllConnections.length(); i++) { + if (AllConnections[i].node().hasFn(MFn::kFileTexture)) { + MFnDependencyNode TextureNode(AllConnections[i].node()); + + std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); + m_TexturePaths.push_back(FullPath); + + material_node.SpecularMapFile = FullPath.substr(FullPath.find_last_of("/")); + + return true; + } + } + return false; +} + +bool Material::findIncandescenceTexture(MaterialNode& material_node, MFnDependencyNode& node) +{ + MPlugArray AllConnections; + + m_Plug = node.findPlug("incandescence", true); + m_Plug.connectedTo(AllConnections, true, false); + + for (int i = 0; i < AllConnections.length(); i++) { + if (AllConnections[i].node().hasFn(MFn::kFileTexture)) { + MFnDependencyNode TextureNode(AllConnections[i].node()); + + std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); + m_TexturePaths.push_back(FullPath); + + material_node.SpecularMapFile = FullPath.substr(FullPath.find_last_of("/")); + + return true; + } + } + return false; +} + +// Returns the absolute path for all textures. Use for copying texture files. +std::vector* Material::TexturePaths() +{ + return &m_TexturePaths; +} + +// Traverse the DAG and grab all the materials +std::vector* Material::DoIt() +{ + // All materials we care about inherit from Lambert + MItDependencyNodes matIt(MFn::kLambert); + + while (!matIt.isDone()) { + MFnDependencyNode MaterialFnDN(matIt.thisNode()); + MaterialNode MaterialStorage; + + if (matIt.thisNode().hasFn(MFn::kPhong)) { + grabLambertProperties(MaterialStorage, MaterialFnDN); + grabPhongProperties(MaterialStorage, MaterialFnDN); + + m_AllMaterials.push_back(MaterialStorage); + } + else if (matIt.thisNode().hasFn(MFn::kBlinn)) { + grabLambertProperties(MaterialStorage, MaterialFnDN); + grabBlinnProperties(MaterialStorage, MaterialFnDN); + + m_AllMaterials.push_back(MaterialStorage); + } + else if (matIt.thisNode().hasFn(MFn::kLambert)) { + grabLambertProperties(MaterialStorage, MaterialFnDN); + + m_AllMaterials.push_back(MaterialStorage); + + MaterialStorage.Specular.fill(0.0f); + MaterialStorage.ReflectionFactor = 0.0f; + MaterialStorage.SpecularExponent = 0.0f; + } + + matIt.next(); + } + + return &m_AllMaterials; +} + diff --git a/tools/MayaExporter/MayaExporter/Material.h b/tools/MayaExporter/MayaExporter/Material.h new file mode 100644 index 00000000..1685453d --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Material.h @@ -0,0 +1,46 @@ +#ifndef Material_Material_h__ +#define Material_Material_h__ + +#include +#include +#include +#include +#include "MayaIncludes.h" + +struct MaterialNode +{ + std::string Name; + std::array Color; + std::array Incandescence; + std::array Specular; + float ReflectionFactor; + float SpecularExponent; + std::string ColorMapFile; + std::string SpecularMapFile; + std::string NormalMapFile; + std::string IncandescenceMapFile; +}; + +class Material +{ +public: + Material() {}; + ~Material() {}; + std::vector* DoIt(); + std::vector* TexturePaths(); +private: + MPlug m_Plug; + + std::vector m_AllMaterials; + std::vector m_TexturePaths; + + bool findColorTexture(MaterialNode& material_node, MFnDependencyNode& node); + bool findNormalTexture(MaterialNode& material_node, MFnDependencyNode& node); + bool findSpecularTexture(MaterialNode& material_node, MFnDependencyNode& node); + bool findIncandescenceTexture(MaterialNode& material_node, MFnDependencyNode& node); + void grabLambertProperties(MaterialNode& material_node, MFnDependencyNode& node); + void grabBlinnProperties(MaterialNode& material_node, MFnDependencyNode& node); + void grabPhongProperties(MaterialNode& material_node, MFnDependencyNode& node); +}; + +#endif // Material_Material_h__ \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index 42b1b45a..c8ce591c 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -152,6 +152,7 @@ + true @@ -213,6 +214,7 @@ $(QTDIR)\bin\moc.exe;%(FullPath);$(QTDIR)\bin\moc.exe;%(FullPath) + diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters index d5bcfd00..4719620b 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters @@ -50,6 +50,9 @@ Source Files + + Source Files + @@ -69,5 +72,8 @@ Generated Files + + Header Files + \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/MayaIncludes.h b/tools/MayaExporter/MayaExporter/MayaIncludes.h index 3573d30d..6c092052 100644 --- a/tools/MayaExporter/MayaExporter/MayaIncludes.h +++ b/tools/MayaExporter/MayaExporter/MayaIncludes.h @@ -30,6 +30,7 @@ #include #include #include +#include // Wrappers diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 6af300aa..5d8af1d4 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -141,9 +141,9 @@ void Menu::CancelClicked(bool) void Menu::Button1Clicked(bool) { if(exportAnimationsButton->isChecked()) - cout << "1 checked!" << endl; + MGlobal::displayInfo("1 checked!"); else - cout << "1 unchecked!" << endl; + MGlobal::displayInfo("1 unchecked!"); } void Menu::Button2Clicked(bool) @@ -222,11 +222,16 @@ void Menu::GetMeshData(MObject object) } -void Menu::exportMaterial(MObject object) +void Menu::GetMaterialData() { - MItDependencyNodes matIt(MFn::kLambert); + this->MaterialHandler = new Material(); + // Traverse scene and return vector with all materials + std::vector* AllMaterials = MaterialHandler->DoIt(); + // Access the colorR component of one material (example) + cout << AllMaterials->at(0).Color[0] << endl; + MGlobal::displayInfo(MString() + AllMaterials->at(0).Color[0]); } Menu::~Menu() @@ -236,4 +241,5 @@ Menu::~Menu() //delete exportPath; //delete fileDialog; fileDialog->~QFileDialog(); + delete MaterialHandler; } \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index 44eca702..b2731c0a 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -5,6 +5,7 @@ #include #include "MayaIncludes.h" +#include "Material.h" // Qt #pragma comment(lib, "QtCore4") #pragma comment(lib, "QtGui4") @@ -46,7 +47,7 @@ public: ~Menu(); void GetMeshData(MObject object); - void exportMaterial(MObject object); + void GetMaterialData(); private slots: void ExportSelected(bool checked); @@ -74,6 +75,7 @@ private: QFileDialog* fileDialog; QDialog* dialogPointer; + Material* MaterialHandler; }; #endif \ No newline at end of file From 74c1beed2036e5629a36f3b273c0f91144ecee25 Mon Sep 17 00:00:00 2001 From: FakeShemp Date: Wed, 9 Dec 2015 12:03:01 +0100 Subject: [PATCH 002/224] gitignore --- .gitignore | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/.gitignore b/.gitignore index 1774c281..d43dd612 100755 --- a/.gitignore +++ b/.gitignore @@ -4,3 +4,8 @@ bin/ lib/ # Because apparently nobody has any self control *.orig + +*.suo +*.sdf +tools/MayaExporter/MayaExporter/x64/Debug/ +tools/MayaExporter/x64/Debug/ From a22d086e60ad9861c47ff592c0fae9c482b26b00 Mon Sep 17 00:00:00 2001 From: antc13 Date: Thu, 10 Dec 2015 11:18:34 +0100 Subject: [PATCH 003/224] Tested some of the Material Code. Seems to work. The project should now be following the code standard properly (hopefully). --- .gitignore | 3 + tools/MayaExporter/MayaExporter/Material.cpp | 2 + tools/MayaExporter/MayaExporter/Material.h | 1 + .../MayaExporter/MayaExporter.vcxproj | 2 + .../MayaExporter/MayaExporter.vcxproj.filters | 6 + tools/MayaExporter/MayaExporter/Menu.cpp | 181 +++++++----------- tools/MayaExporter/MayaExporter/Menu.h | 38 ++-- tools/MayaExporter/MayaExporter/Mesh.cpp | 70 +++++++ tools/MayaExporter/MayaExporter/Mesh.h | 24 +++ 9 files changed, 189 insertions(+), 138 deletions(-) create mode 100644 tools/MayaExporter/MayaExporter/Mesh.cpp create mode 100644 tools/MayaExporter/MayaExporter/Mesh.h diff --git a/.gitignore b/.gitignore index d43dd612..0df2db42 100755 --- a/.gitignore +++ b/.gitignore @@ -9,3 +9,6 @@ lib/ *.sdf tools/MayaExporter/MayaExporter/x64/Debug/ tools/MayaExporter/x64/Debug/ + +tools/MayaExporter/MayaExporter/Debug/ +tools/MayaExporter/MayaExporter/GeneratedFiles/ diff --git a/tools/MayaExporter/MayaExporter/Material.cpp b/tools/MayaExporter/MayaExporter/Material.cpp index 53d029dc..2bc084dc 100644 --- a/tools/MayaExporter/MayaExporter/Material.cpp +++ b/tools/MayaExporter/MayaExporter/Material.cpp @@ -111,6 +111,8 @@ bool Material::findColorTexture(MaterialNode& material_node, MFnDependencyNode& material_node.ColorMapFile = FullPath.substr(FullPath.find_last_of("/")); + // Test + MGlobal::displayInfo(MString() + "Texture file: " + FullPath.c_str()); return true; } } diff --git a/tools/MayaExporter/MayaExporter/Material.h b/tools/MayaExporter/MayaExporter/Material.h index 1685453d..c5d57529 100644 --- a/tools/MayaExporter/MayaExporter/Material.h +++ b/tools/MayaExporter/MayaExporter/Material.h @@ -5,6 +5,7 @@ #include #include #include + #include "MayaIncludes.h" struct MaterialNode diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index c8ce591c..ffc93c0f 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -173,6 +173,7 @@ true + @@ -195,6 +196,7 @@ + Moc%27ing Menu.h... .\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters index 4719620b..70af7805 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters @@ -53,6 +53,9 @@ Source Files + + Source Files + @@ -75,5 +78,8 @@ Header Files + + Header Files + \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 5d8af1d4..3fc760e6 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -10,39 +10,39 @@ Menu::Menu() Menu::Menu(QDialog* dialog) { // Save the dialog pointer. Needed when the application gets destroyed - dialogPointer = dialog; + m_DialogPointer = dialog; // Create QpushButtons & give them names - exportSelectedButton = new QPushButton("&Export Selected", this); - browseButton = new QPushButton("&...", this); - exportAllButton = new QPushButton("&Export All", this); - cancelButton = new QPushButton("&Cancel", this); + m_ExportSelectedButton = new QPushButton("&Export Selected", this); + m_BrowseButton = new QPushButton("&...", this); + m_ExportAllButton = new QPushButton("&Export All", this); + m_CancelButton = new QPushButton("&Cancel", this); // Option box and checkboxes QGroupBox *optionsBox = new QGroupBox(tr("Options")); - exportAnimationsButton = new QCheckBox(tr("&Export Animations")); - copyTexturesButton = new QCheckBox(tr("&Copy Textures")); - button3 = new QCheckBox(tr("option3")); + m_ExportAnimationsButton = new QCheckBox(tr("&Export Animations")); + m_CopyTexturesButton = new QCheckBox(tr("&Copy Textures")); + m_Button3 = new QCheckBox(tr("Test Materials")); - exportAnimationsButton->setChecked(true); - copyTexturesButton->setChecked(true); + m_ExportAnimationsButton->setChecked(true); + m_CopyTexturesButton->setChecked(true); QVBoxLayout *vbox = new QVBoxLayout; - vbox->addWidget(exportAnimationsButton); - vbox->addWidget(copyTexturesButton); - vbox->addWidget(button3); + vbox->addWidget(m_ExportAnimationsButton); + vbox->addWidget(m_CopyTexturesButton); + vbox->addWidget(m_Button3); vbox->addStretch(1); optionsBox->setLayout(vbox); // Connect the buttons with signals & functions - connect(exportSelectedButton, SIGNAL(clicked(bool)), this, SLOT(ExportSelected(bool))); - connect(browseButton, SIGNAL(clicked(bool)), this, SLOT(ExportPathClicked(bool))); - connect(exportAllButton, SIGNAL(clicked(bool)), this, SLOT(ExportAll(bool))); - connect(cancelButton, SIGNAL(clicked(bool)), this, SLOT(CancelClicked(bool))); + connect(m_ExportSelectedButton, SIGNAL(clicked(bool)), this, SLOT(ExportSelected(bool))); + connect(m_BrowseButton, SIGNAL(clicked(bool)), this, SLOT(ExportPathClicked(bool))); + connect(m_ExportAllButton, SIGNAL(clicked(bool)), this, SLOT(ExportAll(bool))); + connect(m_CancelButton, SIGNAL(clicked(bool)), this, SLOT(CancelClicked(bool))); - connect(exportAnimationsButton, SIGNAL(clicked(bool)), this, SLOT(Button1Clicked(bool))); - connect(copyTexturesButton, SIGNAL(clicked(bool)), this, SLOT(Button2Clicked(bool))); - connect(button3, SIGNAL(clicked(bool)), this, SLOT(Button3Clicked(bool))); + connect(m_ExportAnimationsButton, SIGNAL(clicked(bool)), this, SLOT(Button1Clicked(bool))); + connect(m_CopyTexturesButton, SIGNAL(clicked(bool)), this, SLOT(Button2Clicked(bool))); + connect(m_Button3, SIGNAL(clicked(bool)), this, SLOT(Button3Clicked(bool))); // Creating several layouts, adding widgets & adding them to one layout in the end QHBoxLayout* topLayout = new QHBoxLayout; @@ -50,8 +50,8 @@ Menu::Menu(QDialog* dialog) QHBoxLayout* botLayout = new QHBoxLayout; QVBoxLayout* baseLayout = new QVBoxLayout; - exportPath = new QLineEdit; - fileDialog = new QFileDialog; + m_ExportPath = new QLineEdit; + m_FileDialog = new QFileDialog; QLabel* exportLabel = new QLabel; exportLabel->setText("Export Path:"); @@ -59,12 +59,12 @@ Menu::Menu(QDialog* dialog) midLayout->addWidget(optionsBox); topLayout->addWidget(exportLabel); - topLayout->addWidget(exportPath); - topLayout->addWidget(browseButton); + topLayout->addWidget(m_ExportPath); + topLayout->addWidget(m_BrowseButton); - botLayout->addWidget(exportSelectedButton); - botLayout->addWidget(exportAllButton); - botLayout->addWidget(cancelButton); + botLayout->addWidget(m_ExportSelectedButton); + botLayout->addWidget(m_ExportAllButton); + botLayout->addWidget(m_CancelButton); baseLayout->addLayout(topLayout); baseLayout->addLayout(midLayout); @@ -86,28 +86,30 @@ void Menu::ExportSelected(bool checked) MGlobal::getActiveSelectionList(selected); // Loop through or list of selection(s) - for (unsigned int i = 0; i < selected.length();i++) - { + for (unsigned int i = 0; i < selected.length();i++) { MObject object; selected.getDependNode(i, object); MFnDependencyNode thisNode(object); cout << thisNode.name().asChar() << endl; - GetMeshData(object); + Mesh mesh; + mesh.GetMeshData(object); } - if (exportPath->text().isEmpty()) + if (m_ExportPath->text().isEmpty()) { cout << "Please select a folder." << endl; - else - cout << exportPath->text().toLocal8Bit().constData() << endl; + } + else { + cout << m_ExportPath->text().toLocal8Bit().constData() << endl; + } } void Menu::ExportPathClicked(bool) { // Opens up a file dialog. Save/Changes the name in the exportPath - fileDialog->setFileMode(QFileDialog::Directory); - fileDialog->setOption(QFileDialog::ShowDirsOnly); - QString fileName = fileDialog->getExistingDirectory(this, "Select", "/home", QFileDialog::ShowDirsOnly); - exportPath->setText(fileName); + m_FileDialog->setFileMode(QFileDialog::Directory); + m_FileDialog->setOption(QFileDialog::ShowDirsOnly); + QString fileName = m_FileDialog->getExistingDirectory(this, "Select", "/home", QFileDialog::ShowDirsOnly); + m_ExportPath->setText(fileName); } void Menu::ExportAll(bool) @@ -116,118 +118,65 @@ void Menu::ExportAll(bool) // Loop through all nodes in the scene MItDependencyNodes it(MFn::kInvalid); - for (;!it.isDone();it.next()) - { + for (;!it.isDone();it.next()) { MObject node = it.thisNode(); - if (node.hasFn(MFn::kMesh)) - { + if (node.hasFn(MFn::kMesh)) { MFnDependencyNode thisNode(node); cout << thisNode.name().asChar() << endl; - GetMeshData(node); + Mesh mesh; + mesh.GetMeshData(node); } } - if (exportPath->text().isEmpty()) + if (m_ExportPath->text().isEmpty()) { cout << "Please select a folder." << endl; - else - cout << exportPath->text().toLocal8Bit().constData() << endl; + } + else { + cout << m_ExportPath->text().toLocal8Bit().constData() << endl; + } } void Menu::CancelClicked(bool) { - dialogPointer->close(); + m_DialogPointer->close(); } void Menu::Button1Clicked(bool) { - if(exportAnimationsButton->isChecked()) + if (m_ExportAnimationsButton->isChecked()) { MGlobal::displayInfo("1 checked!"); - else + } + else { MGlobal::displayInfo("1 unchecked!"); + } } void Menu::Button2Clicked(bool) { - if (copyTexturesButton->isChecked()) + if (m_CopyTexturesButton->isChecked()) { cout << "2 checked!" << endl; - else + } + else { cout << "2 unchecked!" << endl; + } } void Menu::Button3Clicked(bool) { - if (button3->isChecked()) + if (m_Button3->isChecked()) { cout << "3 checked!" << endl; - else - cout << "3 unchecked!" << endl; -} - -void Menu::GetMeshData(MObject object) -{ - // In here, we retrieve triangulated polygons from the mesh - MFnMesh mesh(object); - - map> vertexToIndex; - - vector verticesData; - vectorindexArray; - - MIntArray intdexOffsetVertexCount, vertices, triangleList; - MPointArray dummy; - - UINT vertexIndex; - MVector normal; - MPoint pos; - float2 UV; - VertexLayout thisVertex; - - for (MItMeshPolygon meshPolyIter(object); !meshPolyIter.isDone(); meshPolyIter.next()) - { - vector localVertexToGlobalIndex; - meshPolyIter.getVertices(vertices); - - meshPolyIter.getTriangles(dummy, triangleList); - UINT indexOffset = verticesData.size(); - - for (UINT i = 0; i < vertices.length(); i++) - { - vertexIndex = meshPolyIter.vertexIndex(i); - pos = meshPolyIter.point(i); - pos.get(thisVertex.pos); - - meshPolyIter.getNormal(i, normal); - thisVertex.normal[0] = normal[0]; - thisVertex.normal[1] = normal[1]; - thisVertex.normal[2] = normal[2]; - - meshPolyIter.getUV(i, UV); - thisVertex.uv[0] = UV[0]; - thisVertex.uv[1] = UV[1]; - - verticesData.push_back(thisVertex); - localVertexToGlobalIndex.push_back(vertexIndex); - - cout << "Pos: " << thisVertex.pos[0] << "/" << thisVertex.pos[1] << "/" << thisVertex.pos[2] << endl; - cout << "Normals: " << thisVertex.normal[0] << "/" << thisVertex.normal[1] << "/" << thisVertex.normal[2] << endl; - cout << "UV: " << thisVertex.uv[0] << "/" << thisVertex.uv[1] << endl; - } - for (UINT i = 0; i < triangleList.length(); i++) - { - UINT k = 0; - while (localVertexToGlobalIndex[k] != triangleList[i]) - k++; - indexArray.push_back(indexOffset + k); - } } - + else { + cout << "3 unchecked!" << endl; + } } void Menu::GetMaterialData() { - this->MaterialHandler = new Material(); + this->m_MaterialHandler = new Material(); // Traverse scene and return vector with all materials - std::vector* AllMaterials = MaterialHandler->DoIt(); + std::vector* AllMaterials = m_MaterialHandler->DoIt(); // Access the colorR component of one material (example) cout << AllMaterials->at(0).Color[0] << endl; @@ -240,6 +189,6 @@ Menu::~Menu() //delete browseButton; //delete exportPath; //delete fileDialog; - fileDialog->~QFileDialog(); - delete MaterialHandler; + m_FileDialog->~QFileDialog(); + //delete MaterialHandler; } \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index b2731c0a..e58c86fb 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -1,11 +1,9 @@ -#ifndef BUTTONS_H -#define BUTTONS_H +#ifndef Menu_Menu_h__ +#define Menu_Menu_h__ #include #include -#include "MayaIncludes.h" -#include "Material.h" // Qt #pragma comment(lib, "QtCore4") #pragma comment(lib, "QtGui4") @@ -32,12 +30,9 @@ #include #include -struct VertexLayout -{ - float pos[3]; - float normal[3]; - float uv[2]; -}; +#include "MayaIncludes.h" +#include "Material.h" +#include "Mesh.h" class Menu : public QWidget { @@ -46,7 +41,6 @@ public: Menu(QDialog* dialog); ~Menu(); - void GetMeshData(MObject object); void GetMaterialData(); private slots: @@ -62,20 +56,20 @@ private slots: private: Menu(); - QPushButton* exportSelectedButton; - QPushButton* browseButton; - QPushButton* exportAllButton; - QPushButton* cancelButton; + QPushButton* m_ExportSelectedButton = nullptr; + QPushButton* m_BrowseButton = nullptr; + QPushButton* m_ExportAllButton = nullptr; + QPushButton* m_CancelButton = nullptr; - QCheckBox* exportAnimationsButton; - QCheckBox* copyTexturesButton; - QCheckBox* button3; + QCheckBox* m_ExportAnimationsButton = nullptr; + QCheckBox* m_CopyTexturesButton = nullptr; + QCheckBox* m_Button3 = nullptr; - QLineEdit* exportPath; - QFileDialog* fileDialog; - QDialog* dialogPointer; + QLineEdit* m_ExportPath = nullptr; + QFileDialog* m_FileDialog = nullptr; + QDialog* m_DialogPointer = nullptr; - Material* MaterialHandler; + Material* m_MaterialHandler = nullptr; }; #endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp new file mode 100644 index 00000000..fa52fc8e --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -0,0 +1,70 @@ +#pragma once +#include "Mesh.h" + +using namespace std; + +Mesh::Mesh() +{ + +} + +void Mesh::GetMeshData(MObject object) +{ + // In here, we retrieve triangulated polygons from the mesh + MFnMesh mesh(object); + + map> vertexToIndex; + + vector verticesData; + vectorindexArray; + + MIntArray intdexOffsetVertexCount, vertices, triangleList; + MPointArray dummy; + + UINT vertexIndex; + MVector normal; + MPoint pos; + float2 UV; + VertexLayout thisVertex; + + for (MItMeshPolygon meshPolyIter(object); !meshPolyIter.isDone(); meshPolyIter.next()) { + vector localVertexToGlobalIndex; + meshPolyIter.getVertices(vertices); + + meshPolyIter.getTriangles(dummy, triangleList); + UINT indexOffset = verticesData.size(); + + for (UINT i = 0; i < vertices.length(); i++) { + vertexIndex = meshPolyIter.vertexIndex(i); + pos = meshPolyIter.point(i); + pos.get(thisVertex.Pos); + + meshPolyIter.getNormal(i, normal); + thisVertex.Normal[0] = normal[0]; + thisVertex.Normal[1] = normal[1]; + thisVertex.Normal[2] = normal[2]; + + meshPolyIter.getUV(i, UV); + thisVertex.Uv[0] = UV[0]; + thisVertex.Uv[1] = UV[1]; + + verticesData.push_back(thisVertex); + localVertexToGlobalIndex.push_back(vertexIndex); + + cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; + cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; + cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; + } + for (UINT i = 0; i < triangleList.length(); i++) { + UINT k = 0; + while (localVertexToGlobalIndex[k] != triangleList[i]) + k++; + indexArray.push_back(indexOffset + k); + } + } +} + +Mesh::~Mesh() +{ + +} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h new file mode 100644 index 00000000..0ba9624d --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -0,0 +1,24 @@ +#ifndef Mesh_Mesh_h__ +#define Mesh_Mesh_h__ + +#include +#include + +#include "MayaIncludes.h" + +struct VertexLayout +{ + float Pos[3]; + float Normal[3]; + float Uv[2]; +}; + +class Mesh +{ +public: + Mesh(); + void GetMeshData(MObject Object); + ~Mesh(); +}; + +#endif \ No newline at end of file From dc66891d60fda1e257e9b6ef3329f0ce51c1004f Mon Sep 17 00:00:00 2001 From: viktorljung Date: Thu, 10 Dec 2015 11:22:56 +0100 Subject: [PATCH 004/224] Added Freetype 2.62 --- deps | 2 +- src/Engine/CMakeLists.txt | 3 +++ 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/deps b/deps index 1b478d31..dd54b115 160000 --- a/deps +++ b/deps @@ -1 +1 @@ -Subproject commit 1b478d3159f12273059a684ee8e187f4a25c89f0 +Subproject commit dd54b115127d9de536ec22c23e9ba51eaae7daf4 diff --git a/src/Engine/CMakeLists.txt b/src/Engine/CMakeLists.txt index de24b9cf..181f179b 100644 --- a/src/Engine/CMakeLists.txt +++ b/src/Engine/CMakeLists.txt @@ -8,6 +8,7 @@ find_package(assimp REQUIRED) find_package(ZLIB REQUIRED) find_package(PNG REQUIRED) find_package(Xerces REQUIRED) +find_package(Freetype REQUIRED) # Because FindOpenAL is retarded #set(CMAKE_INCLUDE_PATH ${CMAKE_INCLUDE_PATH} "${CMAKE_SOURCE_DIR}/deps/include/AL") #find_package(OpenAL REQUIRED) @@ -25,6 +26,7 @@ include_directories( ${assimp_INCLUDE_DIRS} ${PNG_INCLUDE_DIRS} ${Xerces_INCLUDE_DIRS} + ${FREETYPE_INCLUDE_DIRS} ${OPENAL_INCLUDE_DIR} ${X11_INCLUDE_DIRS} ) @@ -88,6 +90,7 @@ set(LIBRARIES ${assimp_LIBRARIES} ${PNG_LIBRARIES} ${Xerces_LIBRARIES} + ${FREETYPE_LIBRARIES} ${OPENAL_LIBRARY} ${X11_LIBRARIES} ) From 46854a63dd9c29a6490923ac9524e342db9923d2 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Fri, 11 Dec 2015 10:54:52 +0100 Subject: [PATCH 005/224] Text rendering includes --- include/Engine/Rendering/TextRenderer.h | 16 ++++++++++++++++ src/Engine/Rendering/TextRenderer.cpp | 0 2 files changed, 16 insertions(+) create mode 100644 include/Engine/Rendering/TextRenderer.h create mode 100644 src/Engine/Rendering/TextRenderer.cpp diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h new file mode 100644 index 00000000..5250d066 --- /dev/null +++ b/include/Engine/Rendering/TextRenderer.h @@ -0,0 +1,16 @@ +#ifndef TextRenderer_h__ +#define TextRenderer_h__ + +#include +#include FT_FREETYPE_H + +class TextRenderer +{ +public: + +private: + +}; + + +#endif \ No newline at end of file diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextRenderer.cpp new file mode 100644 index 00000000..e69de29b From 4c2ce3882e98cef66fcc0ed5fa815f29f8dde3b4 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Fri, 11 Dec 2015 11:07:22 +0100 Subject: [PATCH 006/224] Added fonts folder and font --- assets | 2 +- tools/deploy.bat | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/assets b/assets index b3746822..1434cdcb 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit b37468222e45ec0b2116f1543c578cb9784d43f2 +Subproject commit 1434cdcb2139e2158d5b50b986bc48569b1ec5b8 diff --git a/tools/deploy.bat b/tools/deploy.bat index 5ef074ef..9f70f34d 100755 --- a/tools/deploy.bat +++ b/tools/deploy.bat @@ -11,6 +11,8 @@ RMDIR "%DeployLocation%\Textures" MKLINK "%DeployLocation%\Textures\" "assets\Textures\" /J RMDIR "%DeployLocation%\Audio" MKLINK "%DeployLocation%\Audio\" "assets\Audio\" /J +RMDIR "%DeployLocation%\Fonts" +MKLINK "%DeployLocation%\Fonts\" "assets\Fonts\" /J ECHO Deploying resources to %DeployLocation% :: Schemas From 8f007f6daf7a40d9809e86c40a8c01557c2137fe Mon Sep 17 00:00:00 2001 From: viktorljung Date: Fri, 11 Dec 2015 11:26:41 +0100 Subject: [PATCH 007/224] Added Freetype 2.62 config and option files --- deps | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deps b/deps index dd54b115..75149166 160000 --- a/deps +++ b/deps @@ -1 +1 @@ -Subproject commit dd54b115127d9de536ec22c23e9ba51eaae7daf4 +Subproject commit 75149166e1898e3d42ccaa578598e5fef5beac19 From a8a38716bd5ccbcd86f794be26741aece9f16996 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Fri, 11 Dec 2015 16:12:29 +0100 Subject: [PATCH 008/224] Text renderer up and working, needs more work to be compatible with the ResourceManager and the Entity Component system --- assets | 2 +- include/Engine/Rendering/Renderer.h | 3 + include/Engine/Rendering/ShaderProgram.h | 5 + include/Engine/Rendering/TextRenderer.h | 28 ++++ resources/Shaders/Text.frag.glsl | 12 ++ resources/Shaders/Text.vert.glsl | 13 ++ src/Engine/Rendering/Renderer.cpp | 7 +- src/Engine/Rendering/TextRenderer.cpp | 171 +++++++++++++++++++++++ 8 files changed, 239 insertions(+), 2 deletions(-) create mode 100644 resources/Shaders/Text.frag.glsl create mode 100644 resources/Shaders/Text.vert.glsl diff --git a/assets b/assets index 1434cdcb..fa95bf43 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 1434cdcb2139e2158d5b50b986bc48569b1ec5b8 +Subproject commit fa95bf4383e558a5cb86e35e9d20362e5cb2dcb6 diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 76de0818..7f692a3c 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -14,6 +14,8 @@ #include "../Core/EventBroker.h" #include "EPicking.h" +#include "TextRenderer.h" + class Renderer : public IRenderer { public: @@ -28,6 +30,7 @@ public: private: //----------------------Variables----------------------// EventBroker* m_EventBroker; + TextRenderer* m_TextRenderer; Texture* m_ErrorTexture; Texture* m_WhiteTexture; diff --git a/include/Engine/Rendering/ShaderProgram.h b/include/Engine/Rendering/ShaderProgram.h index 1b87650e..6fb17b61 100644 --- a/include/Engine/Rendering/ShaderProgram.h +++ b/include/Engine/Rendering/ShaderProgram.h @@ -1,4 +1,7 @@ +#ifndef ShaderProgram_h__ +#define ShaderProgram_h__ + #include "../Common.h" #include "../OpenGL.h" #include @@ -79,3 +82,5 @@ private: GLuint m_ShaderProgramHandle; std::vector> m_Shaders; }; + +#endif diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h index 5250d066..99852b4b 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextRenderer.h @@ -4,12 +4,40 @@ #include #include FT_FREETYPE_H +#include "OpenGL.h" +#include "GLM.h" +#include "ShaderProgram.h" + class TextRenderer { public: + TextRenderer(); + void Initialize(); + void Update(); + void Draw(glm::mat4 projection, glm::mat4 view); private: + + struct Character { + GLuint TextureID; // ID handle of the glyph texture + glm::ivec2 Size; // Size of glyph + glm::ivec2 Bearing; // Offset from baseline to left/top of glyph + GLuint Advance; // Offset to advance to next glyph + }; + + std::map Characters; + + + GLuint VAO, VBO; + + void RenderText(std::string text, GLfloat x, GLfloat y, GLfloat scale, glm::vec3 color, glm::mat4 projection, glm::mat4 view); + + ShaderProgram m_TextProgram; + + std::string text = ""; + + int counter = 0; }; diff --git a/resources/Shaders/Text.frag.glsl b/resources/Shaders/Text.frag.glsl new file mode 100644 index 00000000..2726b5d1 --- /dev/null +++ b/resources/Shaders/Text.frag.glsl @@ -0,0 +1,12 @@ +#version 430 +in vec2 TexCoords; +out vec4 color; + +uniform sampler2D text; +uniform vec3 textColor; + +void main() +{ + vec4 sampled = vec4(1.0, 1.0, 1.0, texture(text, TexCoords).r); + color = vec4(textColor, 1.0) * sampled; +} \ No newline at end of file diff --git a/resources/Shaders/Text.vert.glsl b/resources/Shaders/Text.vert.glsl new file mode 100644 index 00000000..43c86795 --- /dev/null +++ b/resources/Shaders/Text.vert.glsl @@ -0,0 +1,13 @@ +#version 430 +layout (location = 0) in vec4 vertex; // +out vec2 TexCoords; + +uniform mat4 M; +uniform mat4 V; +uniform mat4 P; + +void main() +{ + gl_Position = P * V * M * vec4(vertex.xy, 0.0, 1.0); + TexCoords = vertex.zw; +} \ No newline at end of file diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 6f4235d2..3ee559c5 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -15,6 +15,9 @@ void Renderer::Initialize() InitializeTextures(); InitializeFrameBuffers(); + m_TextRenderer = new TextRenderer(); + m_TextRenderer->Initialize(); + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); m_UnitQuad = ResourceManager::Load("Models/Core/UnitQuad.obj"); @@ -142,6 +145,7 @@ void Renderer::Update(double dt) { m_EventBroker->Process(); InputUpdate(dt); + m_TextRenderer->Update(); } @@ -149,9 +153,10 @@ void Renderer::Draw(RenderQueueCollection& rq) { //TODO: Renderer: Kanske borde vara längst upp i update. PickingPass(rq); - DrawScreenQuad(m_PickingTexture); + // DrawScreenQuad(m_PickingTexture); DrawScene(rq); + m_TextRenderer->Draw(m_Camera->ProjectionMatrix(), m_Camera->ViewMatrix()); glfwSwapBuffers(m_Window); } diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextRenderer.cpp index e69de29b..0fd46f32 100644 --- a/src/Engine/Rendering/TextRenderer.cpp +++ b/src/Engine/Rendering/TextRenderer.cpp @@ -0,0 +1,171 @@ +#include "Rendering/TextRenderer.h" + +TextRenderer::TextRenderer() +{ + +} + +void TextRenderer::Initialize() +{ + FT_Library library; + FT_Face face; + + if (FT_Init_FreeType(&library)) { + LOG_ERROR("FreeType error: init failed"); + } + + if (FT_New_Face(library, "fonts/arial.ttf", 0, &face)) { + LOG_ERROR("FreeType error: loading font"); + } + + FT_Set_Pixel_Sizes(face, 0, 48); + + if (FT_Load_Char(face, 'X', FT_LOAD_RENDER)) { + LOG_ERROR("FreeType error: loading char"); + } + + + + + glPixelStorei(GL_UNPACK_ALIGNMENT, 1); + + for (GLubyte c = 0; c < 128; c++) { + //Load character glyph + if (FT_Load_Char(face, c, FT_LOAD_RENDER)) { + continue; + } + printf("Char: %c\n", c); + //Generate texture + GLuint texture; + glGenTextures(1, &texture); + glBindTexture(GL_TEXTURE_2D, texture); + + glTexImage2D( + GL_TEXTURE_2D, + 0, + GL_RED, + face->glyph->bitmap.width, + face->glyph->bitmap.rows, + 0, + GL_RED, + GL_UNSIGNED_BYTE, + face->glyph->bitmap.buffer + ); + // Set texture options + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + // Now store character for later use + Character character = { + texture, + glm::ivec2(face->glyph->bitmap.width, face->glyph->bitmap.rows), + glm::ivec2(face->glyph->bitmap_left, face->glyph->bitmap_top), + face->glyph->advance.x + }; + Characters.insert(std::pair(c, character)); + } + + FT_Done_Face(face); + FT_Done_FreeType(library); + + + + + glGenVertexArrays(1, &VAO); + glGenBuffers(1, &VBO); + glBindVertexArray(VAO); + glBindBuffer(GL_ARRAY_BUFFER, VBO); + glBufferData(GL_ARRAY_BUFFER, sizeof(GLfloat) * 6 * 4, NULL, GL_DYNAMIC_DRAW); + glEnableVertexAttribArray(0); + glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 4 * sizeof(GLfloat), 0); + glBindBuffer(GL_ARRAY_BUFFER, 0); + glBindVertexArray(0); + + + + m_TextProgram.AddShader(std::shared_ptr(new VertexShader("Shaders/Text.vert.glsl"))); + m_TextProgram.AddShader(std::shared_ptr(new FragmentShader("Shaders/Text.frag.glsl"))); + m_TextProgram.Compile(); + m_TextProgram.Link(); +} + +void TextRenderer::Update() +{ + +} + +void TextRenderer::Draw(glm::mat4 projection, glm::mat4 view) +{ + if(counter > 2) { + if (text == "") { + text = text + "~wub "; + } else if (text == "~wub ") { + text = text + "wub "; + } else if (text == "~wub wub ") { + text = ""; + } + counter = 0; + } else { + counter++; + } + + RenderText(text, 0.f, 0.f, 1.0f, glm::vec3(1.f, 1.f, 1.f), projection, view); +} + +void TextRenderer::RenderText(std::string text, GLfloat x, GLfloat y, GLfloat scale, glm::vec3 color, glm::mat4 projection, glm::mat4 view) +{ + + glm::mat4 modelMatrix = glm::translate(glm::mat4(), glm::vec3(0.5f, 0.3f, 0.f)) * glm::toMat4(glm::quat()) * glm::scale(glm::vec3(0.01f)); + + // Activate corresponding render state + glBindFramebuffer(GL_FRAMEBUFFER, 0); + glEnable(GL_BLEND); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + + m_TextProgram.Bind(); + glUniform3f(glGetUniformLocation(m_TextProgram.GetHandle(), "textColor"), color.x, color.y, color.z); + glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "M"), 1, GL_FALSE, glm::value_ptr(modelMatrix)); + glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "V"), 1, GL_FALSE, glm::value_ptr(view)); + glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "P"), 1, GL_FALSE, glm::value_ptr(projection)); + glActiveTexture(GL_TEXTURE0); + glBindVertexArray(VAO); + + // Iterate through all characters + std::string::const_iterator c; + for (c = text.begin(); c != text.end(); c++) { + Character ch = Characters[*c]; + + GLfloat xpos = x + ch.Bearing.x * scale; + GLfloat ypos = y - (ch.Size.y - ch.Bearing.y) * scale; + + GLfloat w = ch.Size.x * scale; + GLfloat h = ch.Size.y * scale; + // Update VBO for each character + GLfloat vertices[6][4] = { + { xpos, ypos + h, 0.0, 0.0 }, + { xpos, ypos, 0.0, 1.0 }, + { xpos + w, ypos, 1.0, 1.0 }, + + { xpos, ypos + h, 0.0, 0.0 }, + { xpos + w, ypos, 1.0, 1.0 }, + { xpos + w, ypos + h, 1.0, 0.0 } + }; + + // Render glyph texture over quad + glBindTexture(GL_TEXTURE_2D, ch.TextureID); + // Update content of VBO memory + glBindBuffer(GL_ARRAY_BUFFER, VBO); + glBufferSubData(GL_ARRAY_BUFFER, 0, sizeof(vertices), vertices); + glBindBuffer(GL_ARRAY_BUFFER, 0); + // Render quad + glDrawArrays(GL_TRIANGLES, 0, 6); + // Now advance cursors for next glyph (note that advance is number of 1/64 pixels) + x += (ch.Advance >> 6) * scale; // Bitshift by 6 to get value in pixels (2^6 = 64) + } + glBindVertexArray(0); + glBindTexture(GL_TEXTURE_2D, 0); + + GLERROR("Text rendering Error"); +} + From 9bd3da409deae4aeaa380ef39765185fff64495d Mon Sep 17 00:00:00 2001 From: viktorljung Date: Fri, 11 Dec 2015 16:53:51 +0100 Subject: [PATCH 009/224] Added Font to ResourceManager --- include/Engine/Rendering/Font.h | 28 ++++++++++ include/Engine/Rendering/TextRenderer.h | 18 ++---- include/Engine/Rendering/Texture.h | 1 + include/Game/Game.h | 1 + src/Engine/Rendering/Font.cpp | 73 +++++++++++++++++++++++++ src/Engine/Rendering/TextRenderer.cpp | 67 ++--------------------- src/Game/Game.cpp | 1 + 7 files changed, 113 insertions(+), 76 deletions(-) create mode 100644 include/Engine/Rendering/Font.h create mode 100644 src/Engine/Rendering/Font.cpp diff --git a/include/Engine/Rendering/Font.h b/include/Engine/Rendering/Font.h new file mode 100644 index 00000000..03f15a49 --- /dev/null +++ b/include/Engine/Rendering/Font.h @@ -0,0 +1,28 @@ +#ifndef Font_h__ +#define Font_h__ + +#include +#include FT_FREETYPE_H + +#include "../OpenGL.h" +#include "../GLM.h" +#include "../Core/ResourceManager.h" + +class Font : public Resource +{ + friend class ResourceManager; +private: + Font(std::string path); + +public: + struct Character { + GLuint TextureID; // ID handle of the glyph texture + glm::ivec2 Size; // Size of glyph + glm::ivec2 Bearing; // Offset from baseline to left/top of glyph + GLuint Advance; // Offset to advance to next glyph + }; + ~Font(); + + std::map m_Characters; +}; +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h index 99852b4b..41298843 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextRenderer.h @@ -4,9 +4,11 @@ #include #include FT_FREETYPE_H -#include "OpenGL.h" -#include "GLM.h" +#include "../OpenGL.h" +#include "../GLM.h" #include "ShaderProgram.h" +#include "Font.h" +#include "../Core/ResourceManager.h" class TextRenderer { @@ -17,17 +19,7 @@ public: void Draw(glm::mat4 projection, glm::mat4 view); private: - - - struct Character { - GLuint TextureID; // ID handle of the glyph texture - glm::ivec2 Size; // Size of glyph - glm::ivec2 Bearing; // Offset from baseline to left/top of glyph - GLuint Advance; // Offset to advance to next glyph - }; - - std::map Characters; - + Font* font; GLuint VAO, VBO; diff --git a/include/Engine/Rendering/Texture.h b/include/Engine/Rendering/Texture.h index 16892afc..0fe650b3 100644 --- a/include/Engine/Rendering/Texture.h +++ b/include/Engine/Rendering/Texture.h @@ -18,6 +18,7 @@ public: void Bind(GLenum textureUnit = GL_TEXTURE0); GLuint m_Texture = 0; + }; #endif diff --git a/include/Game/Game.h b/include/Game/Game.h index 500ecf3a..f448415f 100644 --- a/include/Game/Game.h +++ b/include/Game/Game.h @@ -13,6 +13,7 @@ #include "Core/EntityXMLFile.h" #include "Core/SystemPipeline.h" #include "RaptorCopterSystem.h" +#include "Rendering/Font.h" class Game { diff --git a/src/Engine/Rendering/Font.cpp b/src/Engine/Rendering/Font.cpp new file mode 100644 index 00000000..d7454fe8 --- /dev/null +++ b/src/Engine/Rendering/Font.cpp @@ -0,0 +1,73 @@ +#include "Rendering/Font.h" + + +Font::Font(std::string path) +{ + FT_Library library; + FT_Face face; + + if (FT_Init_FreeType(&library)) { + LOG_ERROR("FreeType error: init failed"); + } + + if (FT_New_Face(library, path.c_str(), 0, &face)) { + LOG_ERROR("FreeType error: loading font"); + } + + FT_Set_Pixel_Sizes(face, 0, 48); + + if (FT_Load_Char(face, 'X', FT_LOAD_RENDER)) { + LOG_ERROR("FreeType error: loading char"); + } + + glPixelStorei(GL_UNPACK_ALIGNMENT, 1); + + for (GLubyte c = 0; c < 128; c++) { + //Load character glyph + if (FT_Load_Char(face, c, FT_LOAD_RENDER)) { + continue; + } + printf("Char: %c\n", c); + //Generate texture + GLuint texture; + glGenTextures(1, &texture); + glBindTexture(GL_TEXTURE_2D, texture); + + glTexImage2D( + GL_TEXTURE_2D, + 0, + GL_RED, + face->glyph->bitmap.width, + face->glyph->bitmap.rows, + 0, + GL_RED, + GL_UNSIGNED_BYTE, + face->glyph->bitmap.buffer + ); + // Set texture options + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + // Now store character for later use + Character character = { + texture, + glm::ivec2(face->glyph->bitmap.width, face->glyph->bitmap.rows), + glm::ivec2(face->glyph->bitmap_left, face->glyph->bitmap_top), + face->glyph->advance.x + }; + + m_Characters.insert(std::pair(c, character)); + } + + FT_Done_Face(face); + FT_Done_FreeType(library); + GLERROR("Font Load"); +} + +Font::~Font() +{ + for (auto c : m_Characters) { + glDeleteTextures(1, &c.second.TextureID); + } +} diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextRenderer.cpp index 0fd46f32..9863b54f 100644 --- a/src/Engine/Rendering/TextRenderer.cpp +++ b/src/Engine/Rendering/TextRenderer.cpp @@ -7,67 +7,7 @@ TextRenderer::TextRenderer() void TextRenderer::Initialize() { - FT_Library library; - FT_Face face; - - if (FT_Init_FreeType(&library)) { - LOG_ERROR("FreeType error: init failed"); - } - - if (FT_New_Face(library, "fonts/arial.ttf", 0, &face)) { - LOG_ERROR("FreeType error: loading font"); - } - - FT_Set_Pixel_Sizes(face, 0, 48); - - if (FT_Load_Char(face, 'X', FT_LOAD_RENDER)) { - LOG_ERROR("FreeType error: loading char"); - } - - - - - glPixelStorei(GL_UNPACK_ALIGNMENT, 1); - - for (GLubyte c = 0; c < 128; c++) { - //Load character glyph - if (FT_Load_Char(face, c, FT_LOAD_RENDER)) { - continue; - } - printf("Char: %c\n", c); - //Generate texture - GLuint texture; - glGenTextures(1, &texture); - glBindTexture(GL_TEXTURE_2D, texture); - - glTexImage2D( - GL_TEXTURE_2D, - 0, - GL_RED, - face->glyph->bitmap.width, - face->glyph->bitmap.rows, - 0, - GL_RED, - GL_UNSIGNED_BYTE, - face->glyph->bitmap.buffer - ); - // Set texture options - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); - // Now store character for later use - Character character = { - texture, - glm::ivec2(face->glyph->bitmap.width, face->glyph->bitmap.rows), - glm::ivec2(face->glyph->bitmap_left, face->glyph->bitmap_top), - face->glyph->advance.x - }; - Characters.insert(std::pair(c, character)); - } - - FT_Done_Face(face); - FT_Done_FreeType(library); + @@ -115,7 +55,8 @@ void TextRenderer::Draw(glm::mat4 projection, glm::mat4 view) void TextRenderer::RenderText(std::string text, GLfloat x, GLfloat y, GLfloat scale, glm::vec3 color, glm::mat4 projection, glm::mat4 view) { - + font = ResourceManager::Load("fonts/arial.ttf"); + glm::mat4 modelMatrix = glm::translate(glm::mat4(), glm::vec3(0.5f, 0.3f, 0.f)) * glm::toMat4(glm::quat()) * glm::scale(glm::vec3(0.01f)); // Activate corresponding render state @@ -134,7 +75,7 @@ void TextRenderer::RenderText(std::string text, GLfloat x, GLfloat y, GLfloat sc // Iterate through all characters std::string::const_iterator c; for (c = text.begin(); c != text.end(); c++) { - Character ch = Characters[*c]; + Font::Character ch = font->m_Characters[*c]; GLfloat xpos = x + ch.Bearing.x * scale; GLfloat ypos = y - (ch.Size.y - ch.Bearing.y) * scale; diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index bff6aebc..af6445f7 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -6,6 +6,7 @@ Game::Game(int argc, char* argv[]) ResourceManager::RegisterType("Model"); ResourceManager::RegisterType("Texture"); ResourceManager::RegisterType("EntityXMLFile"); + ResourceManager::RegisterType("FontFile"); m_Config = ResourceManager::Load("Config.ini"); LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); From 60b3ce89b22889fdf0a9aa3635fee711a3dd3744 Mon Sep 17 00:00:00 2001 From: antc13 Date: Mon, 14 Dec 2015 12:59:54 +0100 Subject: [PATCH 010/224] Skeleton/Joints WIP --- assets | 2 +- .../MayaExporter/MayaExporter.vcxproj | 2 ++ .../MayaExporter/MayaExporter.vcxproj.filters | 6 +++++ tools/MayaExporter/MayaExporter/Menu.cpp | 5 ++++ tools/MayaExporter/MayaExporter/Menu.h | 1 + tools/MayaExporter/MayaExporter/Skeleton.cpp | 11 ++++++++ tools/MayaExporter/MayaExporter/Skeleton.h | 27 +++++++++++++++++++ 7 files changed, 53 insertions(+), 1 deletion(-) create mode 100644 tools/MayaExporter/MayaExporter/Skeleton.cpp create mode 100644 tools/MayaExporter/MayaExporter/Skeleton.h diff --git a/assets b/assets index 4bd902b6..56305dcc 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 4bd902b697b8eef063da800102e6e9c3b29353eb +Subproject commit 56305dcca629b8adaf57efc4e6a853b6c5f345f8 diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index ffc93c0f..50577919 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -174,6 +174,7 @@ + @@ -197,6 +198,7 @@ + Moc%27ing Menu.h... .\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters index 70af7805..cf4a5a35 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters @@ -56,6 +56,9 @@ Source Files + + Source Files + @@ -81,5 +84,8 @@ Header Files + + Header Files + \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 3fc760e6..fc3808f6 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -183,6 +183,11 @@ void Menu::GetMaterialData() MGlobal::displayInfo(MString() + AllMaterials->at(0).Color[0]); } +void Menu::GetSkeletonData() +{ + +} + Menu::~Menu() { //delete exportSelectedButton; diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index e58c86fb..6f766025 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -42,6 +42,7 @@ public: ~Menu(); void GetMaterialData(); + void GetSkeletonData(); private slots: void ExportSelected(bool checked); diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp new file mode 100644 index 00000000..28f56563 --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -0,0 +1,11 @@ +#include "Skeleton.h" + +//std::vector* Skeleton::DoIt() +//{ +// MItDependencyNodes jointIt(MFn::kJoint); +// +// for (; !jointIt.isDone(); jointIt.next()) +// { +// //MFnDependencyNode +// } +//} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Skeleton.h b/tools/MayaExporter/MayaExporter/Skeleton.h new file mode 100644 index 00000000..8b111490 --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Skeleton.h @@ -0,0 +1,27 @@ +#ifndef Skeleton_Skeleton_h__ +#define Skeleton_Skeleton_h__ + +#include +#include +#include "MayaIncludes.h" + +struct Joint { + int ParentIndex; + std::array Rotation; + std::array Translation; + std::array Scale; +}; + +struct SkeletonNode { + std::string Name; + std::vector joints; +}; + +class Skeleton { +public: + //std::vector* DoIt(); +private: + //std::vector m_AllSkeletons; +}; + +#endif //Skeleton_Skeleton_h__ \ No newline at end of file From 123c198e19423499784e07cb5065af3a99388d9f Mon Sep 17 00:00:00 2001 From: viktorljung Date: Mon, 14 Dec 2015 14:48:24 +0100 Subject: [PATCH 011/224] Text component added and Text render queue --- include/Engine/Rendering/RenderQueue.h | 17 +++++++++ include/Engine/Rendering/RenderQueueFactory.h | 1 + include/Engine/Rendering/TextRenderer.h | 5 ++- resources/Schema/Components.xsd | 1 + resources/Schema/Components/Text.xml | 6 +++ resources/Schema/Components/Text.xsd | 27 +++++++++++++ resources/Schema/Entities/Test.xml | 11 ++++++ resources/Schema/Types/Entity.xsd | 1 + src/Engine/Rendering/Font.cpp | 2 +- src/Engine/Rendering/RenderQueueFactory.cpp | 33 ++++++++++++++++ src/Engine/Rendering/Renderer.cpp | 3 +- src/Engine/Rendering/TextRenderer.cpp | 38 ++++++------------- 12 files changed, 115 insertions(+), 30 deletions(-) create mode 100644 resources/Schema/Components/Text.xml create mode 100644 resources/Schema/Components/Text.xsd diff --git a/include/Engine/Rendering/RenderQueue.h b/include/Engine/Rendering/RenderQueue.h index 2942c743..4e3f703c 100644 --- a/include/Engine/Rendering/RenderQueue.h +++ b/include/Engine/Rendering/RenderQueue.h @@ -8,6 +8,7 @@ #include "../GLM.h" #include "../Core/Util/Rectangle.h" #include "../Core/Entity.h" +#include "Font.h" class Model; class Skeleton; @@ -80,6 +81,19 @@ struct SpriteJob : RenderJob } }; +struct TextJob : RenderJob +{ + glm::mat4 ModelMatrix; + glm::vec4 Color; + std::string Content; + Font* Resource; + + void CalculateHash() override + { + Hash = 0; + } +}; + struct PointLightJob : RenderJob { glm::vec3 Position; @@ -137,17 +151,20 @@ struct RenderQueueCollection { RenderQueue Forward; RenderQueue Lights; + RenderQueue Text; void Clear() { Forward.Clear(); Lights.Clear(); + Text.Clear(); } void Sort() { Forward.Sort(); Lights.Sort(); + Text.Sort(); } }; diff --git a/include/Engine/Rendering/RenderQueueFactory.h b/include/Engine/Rendering/RenderQueueFactory.h index b273b672..1f9adc46 100644 --- a/include/Engine/Rendering/RenderQueueFactory.h +++ b/include/Engine/Rendering/RenderQueueFactory.h @@ -20,6 +20,7 @@ private: void FillModels(World* world, RenderQueue* renderQueue); void FillLights(World* world, RenderQueue* renderQueue); + void FillText(World* world, RenderQueue* renderQueue); glm::mat4 ModelMatrix(World* world, EntityID entity); diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h index 41298843..2aac6500 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextRenderer.h @@ -9,6 +9,7 @@ #include "ShaderProgram.h" #include "Font.h" #include "../Core/ResourceManager.h" +#include "RenderQueue.h" class TextRenderer { @@ -16,14 +17,14 @@ public: TextRenderer(); void Initialize(); void Update(); - void Draw(glm::mat4 projection, glm::mat4 view); + void Draw(RenderQueue &rq, glm::mat4 projection, glm::mat4 view); private: Font* font; GLuint VAO, VBO; - void RenderText(std::string text, GLfloat x, GLfloat y, GLfloat scale, glm::vec3 color, glm::mat4 projection, glm::mat4 view); + void RenderText(std::string text, Font* font, GLfloat scale, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); ShaderProgram m_TextProgram; diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index d4160700..a854f96d 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -5,4 +5,5 @@ + \ No newline at end of file diff --git a/resources/Schema/Components/Text.xml b/resources/Schema/Components/Text.xml new file mode 100644 index 00000000..1d5a4927 --- /dev/null +++ b/resources/Schema/Components/Text.xml @@ -0,0 +1,6 @@ + + + + + true + \ No newline at end of file diff --git a/resources/Schema/Components/Text.xsd b/resources/Schema/Components/Text.xsd new file mode 100644 index 00000000..251d2e2e --- /dev/null +++ b/resources/Schema/Components/Text.xsd @@ -0,0 +1,27 @@ + + + + + + + + A visible font loaded from disk + + + + + the content of the string printed + + + font file + + + Color + + + Wether the text is visible or not + + + + + \ No newline at end of file diff --git a/resources/Schema/Entities/Test.xml b/resources/Schema/Entities/Test.xml index 2c3ea18e..78908eb5 100644 --- a/resources/Schema/Entities/Test.xml +++ b/resources/Schema/Entities/Test.xml @@ -21,6 +21,17 @@ + + + + + + + Fonts/arial.ttf + Hej I am component text + + + diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 695ae7d1..198f0cb7 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -14,6 +14,7 @@ + diff --git a/src/Engine/Rendering/Font.cpp b/src/Engine/Rendering/Font.cpp index d7454fe8..12b1b97c 100644 --- a/src/Engine/Rendering/Font.cpp +++ b/src/Engine/Rendering/Font.cpp @@ -27,7 +27,7 @@ Font::Font(std::string path) if (FT_Load_Char(face, c, FT_LOAD_RENDER)) { continue; } - printf("Char: %c\n", c); + //Generate texture GLuint texture; glGenTextures(1, &texture); diff --git a/src/Engine/Rendering/RenderQueueFactory.cpp b/src/Engine/Rendering/RenderQueueFactory.cpp index 81d7391e..c52048aa 100644 --- a/src/Engine/Rendering/RenderQueueFactory.cpp +++ b/src/Engine/Rendering/RenderQueueFactory.cpp @@ -11,6 +11,7 @@ void RenderQueueFactory::Update(World* world) m_RenderQueues.Clear(); FillModels(world, &m_RenderQueues.Forward); FillLights(world, &m_RenderQueues.Lights); + FillText(world, &m_RenderQueues.Text); } glm::mat4 RenderQueueFactory::ModelMatrix(World* world, EntityID entity) @@ -71,6 +72,9 @@ void RenderQueueFactory::FillModels(World* world, RenderQueue* renderQueue) } for (auto& modelC : *models) { + + + std::string resource = modelC["Resource"]; if (resource.empty()) { continue; @@ -103,3 +107,32 @@ void RenderQueueFactory::FillLights(World* world, RenderQueue* renderQueue) } +void RenderQueueFactory::FillText(World* world, RenderQueue* renderQueue) +{ + auto texts = world->GetComponents("Text"); + if (texts == nullptr) { + return; + } + + for (auto& textC : *texts) { + + + std::string resource = textC["Resource"]; + if (resource.empty()) { + continue; + } + Font* font = ResourceManager::Load(resource); + + glm::vec4 color = textC["Color"]; + std::string content = textC["Content"]; + + TextJob job; + job.Color = color; + job.Content = content; + job.Resource = font; + job.ModelMatrix = ModelMatrix(world, textC.EntityID); + + renderQueue->Add(job); + } +} + diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 3ee559c5..dc2f65df 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -156,7 +156,7 @@ void Renderer::Draw(RenderQueueCollection& rq) // DrawScreenQuad(m_PickingTexture); DrawScene(rq); - m_TextRenderer->Draw(m_Camera->ProjectionMatrix(), m_Camera->ViewMatrix()); + m_TextRenderer->Draw(rq.Text,m_Camera->ProjectionMatrix(), m_Camera->ViewMatrix()); glfwSwapBuffers(m_Window); } @@ -272,6 +272,7 @@ void Renderer::PickingPass(RenderQueueCollection& rq) m_EventBroker->Publish(pickEvent); + glBindFramebuffer(GL_FRAMEBUFFER, 0); } diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextRenderer.cpp index 9863b54f..697b6834 100644 --- a/src/Engine/Rendering/TextRenderer.cpp +++ b/src/Engine/Rendering/TextRenderer.cpp @@ -7,11 +7,6 @@ TextRenderer::TextRenderer() void TextRenderer::Initialize() { - - - - - glGenVertexArrays(1, &VAO); glGenBuffers(1, &VBO); glBindVertexArray(VAO); @@ -22,8 +17,6 @@ void TextRenderer::Initialize() glBindBuffer(GL_ARRAY_BUFFER, 0); glBindVertexArray(0); - - m_TextProgram.AddShader(std::shared_ptr(new VertexShader("Shaders/Text.vert.glsl"))); m_TextProgram.AddShader(std::shared_ptr(new FragmentShader("Shaders/Text.frag.glsl"))); m_TextProgram.Compile(); @@ -35,40 +28,33 @@ void TextRenderer::Update() } -void TextRenderer::Draw(glm::mat4 projection, glm::mat4 view) +void TextRenderer::Draw(RenderQueue &rq, glm::mat4 projection, glm::mat4 view) { - if(counter > 2) { - if (text == "") { - text = text + "~wub "; - } else if (text == "~wub ") { - text = text + "wub "; - } else if (text == "~wub wub ") { - text = ""; + for (auto &job : rq) { + auto textJob = std::dynamic_pointer_cast(job); + if (textJob) { + RenderText(textJob->Content, textJob->Resource, 0.01f, textJob->Color, textJob->ModelMatrix, projection, view); } - counter = 0; - } else { - counter++; } - - RenderText(text, 0.f, 0.f, 1.0f, glm::vec3(1.f, 1.f, 1.f), projection, view); } -void TextRenderer::RenderText(std::string text, GLfloat x, GLfloat y, GLfloat scale, glm::vec3 color, glm::mat4 projection, glm::mat4 view) +void TextRenderer::RenderText(std::string text, Font* font, GLfloat scale, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) { - font = ResourceManager::Load("fonts/arial.ttf"); + GLfloat x = 0; + GLfloat y = 0; - glm::mat4 modelMatrix = glm::translate(glm::mat4(), glm::vec3(0.5f, 0.3f, 0.f)) * glm::toMat4(glm::quat()) * glm::scale(glm::vec3(0.01f)); // Activate corresponding render state - glBindFramebuffer(GL_FRAMEBUFFER, 0); + glEnable(GL_BLEND); + glDisable(GL_CULL_FACE); glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); m_TextProgram.Bind(); glUniform3f(glGetUniformLocation(m_TextProgram.GetHandle(), "textColor"), color.x, color.y, color.z); glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "M"), 1, GL_FALSE, glm::value_ptr(modelMatrix)); - glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "V"), 1, GL_FALSE, glm::value_ptr(view)); - glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "P"), 1, GL_FALSE, glm::value_ptr(projection)); + glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "V"), 1, GL_FALSE, glm::value_ptr(viewMatrix)); + glUniformMatrix4fv(glGetUniformLocation(m_TextProgram.GetHandle(), "P"), 1, GL_FALSE, glm::value_ptr(projectionMatrix)); glActiveTexture(GL_TEXTURE0); glBindVertexArray(VAO); From 168937035669ea3cb958284ce29f02004f950594 Mon Sep 17 00:00:00 2001 From: FakeShemp Date: Tue, 15 Dec 2015 11:49:59 +0100 Subject: [PATCH 012/224] Export the skeletons Not really tested though --- tools/MayaExporter/MayaExporter/Menu.cpp | 14 +++++ tools/MayaExporter/MayaExporter/Menu.h | 2 + tools/MayaExporter/MayaExporter/Skeleton.cpp | 62 +++++++++++++++++--- tools/MayaExporter/MayaExporter/Skeleton.h | 16 +++-- 4 files changed, 79 insertions(+), 15 deletions(-) diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index fc3808f6..8eb245e2 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -145,6 +145,7 @@ void Menu::Button1Clicked(bool) { if (m_ExportAnimationsButton->isChecked()) { MGlobal::displayInfo("1 checked!"); + this->GetSkeletonData(); } else { MGlobal::displayInfo("1 unchecked!"); @@ -185,7 +186,20 @@ void Menu::GetMaterialData() void Menu::GetSkeletonData() { + this->m_SkeletonHandler = new Skeleton(); + // Traverse scene and return vector with all materials + std::vector* AllMaterials = m_SkeletonHandler->DoIt(); + + MGlobal::displayInfo(MString() + AllMaterials->size()); + + for (int i = 0; i < AllMaterials->size(); i++) + { + for (int j = 0; j < AllMaterials->at(i).Joints.size(); j++) + { + MGlobal::displayInfo(MString() + AllMaterials->at(i).Joints.at(j).Name.c_str()); + } + } } Menu::~Menu() diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index 6f766025..a0fe93f6 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -33,6 +33,7 @@ #include "MayaIncludes.h" #include "Material.h" #include "Mesh.h" +#include "Skeleton.h" class Menu : public QWidget { @@ -71,6 +72,7 @@ private: QDialog* m_DialogPointer = nullptr; Material* m_MaterialHandler = nullptr; + Skeleton* m_SkeletonHandler = nullptr; }; #endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp index 28f56563..3e95b817 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.cpp +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -1,11 +1,55 @@ #include "Skeleton.h" -//std::vector* Skeleton::DoIt() -//{ -// MItDependencyNodes jointIt(MFn::kJoint); -// -// for (; !jointIt.isDone(); jointIt.next()) -// { -// //MFnDependencyNode -// } -//} \ No newline at end of file +std::vector* Skeleton::DoIt() +{ + MItDependencyNodes jointIt(MFn::kJoint); + SkeletonNode SkeletonStorage; + + while (!jointIt.isDone()) { + MFnDependencyNode SkeletonFnDN(jointIt.thisNode()); + MFnTransform TransformNode(SkeletonFnDN.object()); + Joint NewJoint; + + if (MFnDependencyNode(TransformNode.parent(0)).name() == "world") { + if (SkeletonStorage.Joints.size() != 0) { + m_AllSkeletons.push_back(SkeletonStorage); + + SkeletonStorage.Joints.clear(); + SkeletonStorage.Name.clear(); + } + + SkeletonStorage.Name = TransformNode.name().asChar(); + + NewJoint.ParentIndex = -1; // This joint is root + } + else { + auto it = std::find(m_Hierarchy.begin(), m_Hierarchy.end(), TransformNode.parent(0)); + if (it != m_Hierarchy.end()) { + NewJoint.ParentIndex = it - m_Hierarchy.begin(); + } + else { + MGlobal::displayError(MString() + "Could not find joint parent for: " + TransformNode.name()); + } + } + + m_Hierarchy.push_back(TransformNode.object()); + + NewJoint.Name = TransformNode.name().asChar(); + + MMatrix Matrix = TransformNode.transformationMatrix(); + + for (int i = 0; i < 4; i++) { + for (int j = 0; j < 4; j++) { + NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; + } + } + + SkeletonStorage.Joints.push_back(NewJoint); + + jointIt.next(); + } + + m_AllSkeletons.push_back(SkeletonStorage); + + return &m_AllSkeletons; +} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Skeleton.h b/tools/MayaExporter/MayaExporter/Skeleton.h index 8b111490..26e99d4b 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.h +++ b/tools/MayaExporter/MayaExporter/Skeleton.h @@ -3,25 +3,29 @@ #include #include +#include #include "MayaIncludes.h" struct Joint { int ParentIndex; - std::array Rotation; - std::array Translation; - std::array Scale; + //std::array Rotation; + //std::array Translation; + //std::array Scale; + std::array, 4> OffsetMatrix; + std::string Name; }; struct SkeletonNode { std::string Name; - std::vector joints; + std::vector Joints; }; class Skeleton { public: - //std::vector* DoIt(); + std::vector* DoIt(); private: - //std::vector m_AllSkeletons; + std::vector m_AllSkeletons; + std::vector m_Hierarchy; }; #endif //Skeleton_Skeleton_h__ \ No newline at end of file From 4e535c110293b527fe112c8e52a76ed5f3660145 Mon Sep 17 00:00:00 2001 From: antc13 Date: Tue, 15 Dec 2015 15:24:46 +0100 Subject: [PATCH 013/224] =?UTF-8?q?File=20Writer=20WIP.=20Rework=20soon?= =?UTF-8?q?=E2=84=A2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../MayaExporter/MayaExporter.vcxproj | 2 + .../MayaExporter/MayaExporter.vcxproj.filters | 6 ++ tools/MayaExporter/MayaExporter/Menu.h | 1 + tools/MayaExporter/MayaExporter/Var.cpp | 70 +++++++++++++++++++ tools/MayaExporter/MayaExporter/Var.h | 32 +++++++++ 5 files changed, 111 insertions(+) create mode 100644 tools/MayaExporter/MayaExporter/Var.cpp create mode 100644 tools/MayaExporter/MayaExporter/Var.h diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index 50577919..b04d032f 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -175,6 +175,7 @@ + @@ -199,6 +200,7 @@ + Moc%27ing Menu.h... .\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters index cf4a5a35..6f836155 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters @@ -59,6 +59,9 @@ Source Files + + Source Files + @@ -87,5 +90,8 @@ Header Files + + Header Files + \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index 6f766025..bf77e59f 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -33,6 +33,7 @@ #include "MayaIncludes.h" #include "Material.h" #include "Mesh.h" +#include "Var.h" class Menu : public QWidget { diff --git a/tools/MayaExporter/MayaExporter/Var.cpp b/tools/MayaExporter/MayaExporter/Var.cpp new file mode 100644 index 00000000..adfcb212 --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Var.cpp @@ -0,0 +1,70 @@ +#include "Var.h" +#include "MayaIncludes.h" +#include + +Var::Var(Var::Type type, unsigned int numElements) +{ + m_Type = type; + m_NumElements = numElements; + + switch (m_Type) + { + case Var::Type::Int: + m_Data = new int[m_NumElements]; + break; + case Var::Type::Float: + m_Data = new float[m_NumElements]; + break; + case Var::Type::String: + m_Data = new std::string[m_NumElements]; + break; + default: + MGlobal::displayError("Var is an invalid type"); + assert(0); + break; + } +} + +Var& Var::operator=(const int& other) +{ + assert(m_Type == Type::Int); + *(int*)m_Data = other; + return *this; +} + +Var& Var::operator=(const float& other) +{ + assert(m_Type == Type::Float); + *(float*)m_Data = other; + return *this; +} + +Var& Var::operator=(const std::string& other) +{ + assert(m_Type == Type::String); + std::string tmp(other); + (*(std::string*)m_Data).swap(tmp); + return *this; +} + +//Var& Var::operator=(const Var& other) +//{ +// m_Data = other.m_Data; +// m_Type = other.m_Type; +// return *this; +//} + +Var::Type Var::isType() const +{ + return m_Type; +} + +unsigned int Var::NumElements() const +{ + return m_NumElements; +} + +void* Var::Data() +{ + return m_Data; +} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Var.h b/tools/MayaExporter/MayaExporter/Var.h new file mode 100644 index 00000000..b0ec66dd --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Var.h @@ -0,0 +1,32 @@ +#ifndef Var_Var_h__ +#define Var_Var_h__ + +#include + +class Var +{ +public: + enum class Type + { + Int, + Float, + String + }; + + Var(Var::Type type, unsigned int numElements = 1); + ~Var() { delete[] m_Data; }; + + Var& operator=(const int& other); + Var& operator=(const float& other); + Var& operator=(const std::string& other); + //Var& operator=(const Var& other); + Type isType() const; + unsigned int NumElements() const; + void* Data(); +private: + Type m_Type; + unsigned int m_NumElements; + void* m_Data; +}; + +#endif \ No newline at end of file From 67017fcaf47a9a72fc9c8b7379d3c8aeb0f548f9 Mon Sep 17 00:00:00 2001 From: antc13 Date: Wed, 16 Dec 2015 11:33:42 +0100 Subject: [PATCH 014/224] Stepping through the timeline. --- .../MayaExporter/MayaExporter.vcxproj | 2 - .../MayaExporter/MayaExporter.vcxproj.filters | 6 -- .../MayaExporter/MayaExporter/MayaIncludes.h | 3 + tools/MayaExporter/MayaExporter/Menu.cpp | 26 +++++-- tools/MayaExporter/MayaExporter/Var.cpp | 70 ------------------- tools/MayaExporter/MayaExporter/Var.h | 32 --------- 6 files changed, 22 insertions(+), 117 deletions(-) delete mode 100644 tools/MayaExporter/MayaExporter/Var.cpp delete mode 100644 tools/MayaExporter/MayaExporter/Var.h diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index b04d032f..50577919 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -175,7 +175,6 @@ - @@ -200,7 +199,6 @@ - Moc%27ing Menu.h... .\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters index 6f836155..cf4a5a35 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters @@ -59,9 +59,6 @@ Source Files - - Source Files - @@ -90,8 +87,5 @@ Header Files - - Header Files - \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/MayaIncludes.h b/tools/MayaExporter/MayaExporter/MayaIncludes.h index 6c092052..9186bfe6 100644 --- a/tools/MayaExporter/MayaExporter/MayaIncludes.h +++ b/tools/MayaExporter/MayaExporter/MayaIncludes.h @@ -31,6 +31,8 @@ #include #include #include +#include +#include // Wrappers @@ -59,5 +61,6 @@ #pragma comment(lib,"Foundation.lib") #pragma comment(lib,"OpenMaya.lib") #pragma comment(lib,"OpenMayaUI.lib") +#pragma comment (lib, "OpenMayaAnim.lib") #endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 8eb245e2..06c115c8 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -187,17 +187,29 @@ void Menu::GetMaterialData() void Menu::GetSkeletonData() { this->m_SkeletonHandler = new Skeleton(); + MTime startFrame = MAnimControl::animationStartTime(); + MTime endFrame = MAnimControl::animationEndTime(); - // Traverse scene and return vector with all materials - std::vector* AllMaterials = m_SkeletonHandler->DoIt(); + std::vector*> AllSkeletons; - MGlobal::displayInfo(MString() + AllMaterials->size()); - - for (int i = 0; i < AllMaterials->size(); i++) + for (int i = startFrame.value(); i < endFrame.value();i++) { - for (int j = 0; j < AllMaterials->at(i).Joints.size(); j++) + MAnimControl::setCurrentTime(MTime(i, MTime::kNTSCField)); + // Traverse scene and return vector with all materials + AllSkeletons.push_back(m_SkeletonHandler->DoIt()); + } + + MGlobal::displayInfo(MString() + AllSkeletons.size()); + + for (int i = 0; i < AllSkeletons.size(); i++) + { + std::vector*& thisSkeleton = AllSkeletons.at(i); + for (int k = 0; k < thisSkeleton->size(); k++) { - MGlobal::displayInfo(MString() + AllMaterials->at(i).Joints.at(j).Name.c_str()); + for (int j = 0; j < thisSkeleton->at(k).Joints.size(); j++) + { + MGlobal::displayInfo(MString() + thisSkeleton->at(k).Joints.at(j).Name.c_str()); + } } } } diff --git a/tools/MayaExporter/MayaExporter/Var.cpp b/tools/MayaExporter/MayaExporter/Var.cpp deleted file mode 100644 index adfcb212..00000000 --- a/tools/MayaExporter/MayaExporter/Var.cpp +++ /dev/null @@ -1,70 +0,0 @@ -#include "Var.h" -#include "MayaIncludes.h" -#include - -Var::Var(Var::Type type, unsigned int numElements) -{ - m_Type = type; - m_NumElements = numElements; - - switch (m_Type) - { - case Var::Type::Int: - m_Data = new int[m_NumElements]; - break; - case Var::Type::Float: - m_Data = new float[m_NumElements]; - break; - case Var::Type::String: - m_Data = new std::string[m_NumElements]; - break; - default: - MGlobal::displayError("Var is an invalid type"); - assert(0); - break; - } -} - -Var& Var::operator=(const int& other) -{ - assert(m_Type == Type::Int); - *(int*)m_Data = other; - return *this; -} - -Var& Var::operator=(const float& other) -{ - assert(m_Type == Type::Float); - *(float*)m_Data = other; - return *this; -} - -Var& Var::operator=(const std::string& other) -{ - assert(m_Type == Type::String); - std::string tmp(other); - (*(std::string*)m_Data).swap(tmp); - return *this; -} - -//Var& Var::operator=(const Var& other) -//{ -// m_Data = other.m_Data; -// m_Type = other.m_Type; -// return *this; -//} - -Var::Type Var::isType() const -{ - return m_Type; -} - -unsigned int Var::NumElements() const -{ - return m_NumElements; -} - -void* Var::Data() -{ - return m_Data; -} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Var.h b/tools/MayaExporter/MayaExporter/Var.h deleted file mode 100644 index b0ec66dd..00000000 --- a/tools/MayaExporter/MayaExporter/Var.h +++ /dev/null @@ -1,32 +0,0 @@ -#ifndef Var_Var_h__ -#define Var_Var_h__ - -#include - -class Var -{ -public: - enum class Type - { - Int, - Float, - String - }; - - Var(Var::Type type, unsigned int numElements = 1); - ~Var() { delete[] m_Data; }; - - Var& operator=(const int& other); - Var& operator=(const float& other); - Var& operator=(const std::string& other); - //Var& operator=(const Var& other); - Type isType() const; - unsigned int NumElements() const; - void* Data(); -private: - Type m_Type; - unsigned int m_NumElements; - void* m_Data; -}; - -#endif \ No newline at end of file From 73708ec7066fd0305363e3844c35903b8edf3fa1 Mon Sep 17 00:00:00 2001 From: antc13 Date: Thu, 17 Dec 2015 14:58:46 +0100 Subject: [PATCH 015/224] You can now add/remove animation clips. --- tools/MayaExporter/MayaExporter/Menu.cpp | 144 +++++++++++++++++++---- tools/MayaExporter/MayaExporter/Menu.h | 13 ++ 2 files changed, 134 insertions(+), 23 deletions(-) diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 06c115c8..591c15fa 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -17,6 +17,8 @@ Menu::Menu(QDialog* dialog) m_BrowseButton = new QPushButton("&...", this); m_ExportAllButton = new QPushButton("&Export All", this); m_CancelButton = new QPushButton("&Cancel", this); + m_AddClipsButton = new QPushButton("&Add Clips", this); + m_RemoveClipsButton = new QPushButton("&Remove Latest Clip", this); // Option box and checkboxes QGroupBox *optionsBox = new QGroupBox(tr("Options")); @@ -39,6 +41,8 @@ Menu::Menu(QDialog* dialog) connect(m_BrowseButton, SIGNAL(clicked(bool)), this, SLOT(ExportPathClicked(bool))); connect(m_ExportAllButton, SIGNAL(clicked(bool)), this, SLOT(ExportAll(bool))); connect(m_CancelButton, SIGNAL(clicked(bool)), this, SLOT(CancelClicked(bool))); + connect(m_AddClipsButton, SIGNAL(clicked(bool)), this, SLOT(AddClipClicked(bool))); + connect(m_RemoveClipsButton, SIGNAL(clicked(bool)), this, SLOT(RemoveClipClicked(bool))); connect(m_ExportAnimationsButton, SIGNAL(clicked(bool)), this, SLOT(Button1Clicked(bool))); connect(m_CopyTexturesButton, SIGNAL(clicked(bool)), this, SLOT(Button2Clicked(bool))); @@ -49,12 +53,25 @@ Menu::Menu(QDialog* dialog) QVBoxLayout* midLayout = new QVBoxLayout; QHBoxLayout* botLayout = new QHBoxLayout; QVBoxLayout* baseLayout = new QVBoxLayout; + QHBoxLayout* clipButtonLayout = new QHBoxLayout; + QHBoxLayout* startEndLabelLayout = new QHBoxLayout; + m_ClipLayout = new QVBoxLayout; + + m_ExportPath = new QLineEdit; m_FileDialog = new QFileDialog; QLabel* exportLabel = new QLabel; exportLabel->setText("Export Path:"); + QLabel* nameLabel = new QLabel; + nameLabel->setText("Name:"); + QLabel* startLabel = new QLabel; + startLabel->setText("Start:"); + QLabel* endLabel = new QLabel; + endLabel->setText("End:"); + + //exportLabel->setText("Export Path:"); midLayout->addWidget(optionsBox); @@ -66,19 +83,35 @@ Menu::Menu(QDialog* dialog) botLayout->addWidget(m_ExportAllButton); botLayout->addWidget(m_CancelButton); + startEndLabelLayout->addWidget(nameLabel); + startEndLabelLayout->addWidget(startLabel); + startEndLabelLayout->addWidget(endLabel); + + clipButtonLayout->addWidget(m_AddClipsButton); + clipButtonLayout->addWidget(m_RemoveClipsButton); + baseLayout->addLayout(topLayout); baseLayout->addLayout(midLayout); baseLayout->addSpacing(10); - baseLayout->addLayout(botLayout); + + baseLayout->addSpacing(10); + baseLayout->addLayout(clipButtonLayout); + baseLayout->addLayout(startEndLabelLayout); + baseLayout->addLayout(m_ClipLayout); baseLayout->addStretch(); // Set the layout for our window dialog->setLayout(baseLayout); + for (unsigned int i = 0; i < 3; i++) { + this->AddClipClicked(true); + } + } + void Menu::ExportSelected(bool checked) { // Retrieving the objects we currently have selected @@ -101,6 +134,11 @@ void Menu::ExportSelected(bool checked) else { cout << m_ExportPath->text().toLocal8Bit().constData() << endl; } + + if (m_ExportAnimationsButton->isChecked()) { + GetSkeletonData(); + } + } void Menu::ExportPathClicked(bool) @@ -112,6 +150,48 @@ void Menu::ExportPathClicked(bool) m_ExportPath->setText(fileName); } +void Menu::AddClipClicked(bool) +{ + QHBoxLayout* tempLayout = new QHBoxLayout; + + QLineEdit* nameLineEdit = new QLineEdit; + QLineEdit* startLineEdit = new QLineEdit; + QLineEdit* endLineEdit = new QLineEdit; + + m_AnimationClipName.push_back(nameLineEdit); + m_StartFrameLines.push_back(startLineEdit); + m_EndFrameLines.push_back(endLineEdit); + + tempLayout->addWidget(nameLineEdit); + tempLayout->addWidget(startLineEdit); + tempLayout->addWidget(endLineEdit); + + m_ClipLayout->addLayout(tempLayout); + //m_ClipLayout->update(); + layouts.push_back(tempLayout); +} + +void Menu::RemoveClipClicked(bool) +{ + if (m_StartFrameLines.size() > 0) { + QLayoutItem* tempWidget;// = m_ClipLayout->itemAt(0); + + for (unsigned int i = 0; i < layouts.size(); i++) { + while ((tempWidget = layouts[layouts.size()-1]->takeAt(0)) != 0) { + delete tempWidget->widget(); + delete tempWidget; + } + } + + m_ClipLayout->removeItem(tempWidget); + m_ClipLayout->update(); + + layouts.pop_back(); + m_StartFrameLines.pop_back(); + m_EndFrameLines.pop_back(); + } +} + void Menu::ExportAll(bool) { MDagPath path; @@ -134,6 +214,9 @@ void Menu::ExportAll(bool) else { cout << m_ExportPath->text().toLocal8Bit().constData() << endl; } + + if(m_ExportAnimationsButton->isChecked()) + GetSkeletonData(); } void Menu::CancelClicked(bool) @@ -145,7 +228,6 @@ void Menu::Button1Clicked(bool) { if (m_ExportAnimationsButton->isChecked()) { MGlobal::displayInfo("1 checked!"); - this->GetSkeletonData(); } else { MGlobal::displayInfo("1 unchecked!"); @@ -186,31 +268,46 @@ void Menu::GetMaterialData() void Menu::GetSkeletonData() { - this->m_SkeletonHandler = new Skeleton(); - MTime startFrame = MAnimControl::animationStartTime(); - MTime endFrame = MAnimControl::animationEndTime(); + if (MAnimControl::currentTime().unit() != MTime::kNTSCField) { + MGlobal::displayError(MString() + "Please change to 60 FPS under Preferences/Settings!"); + return; + } + + this->m_SkeletonHandler = new Skeleton(); std::vector*> AllSkeletons; - for (int i = startFrame.value(); i < endFrame.value();i++) - { - MAnimControl::setCurrentTime(MTime(i, MTime::kNTSCField)); - // Traverse scene and return vector with all materials - AllSkeletons.push_back(m_SkeletonHandler->DoIt()); - } - - MGlobal::displayInfo(MString() + AllSkeletons.size()); - - for (int i = 0; i < AllSkeletons.size(); i++) - { - std::vector*& thisSkeleton = AllSkeletons.at(i); - for (int k = 0; k < thisSkeleton->size(); k++) - { - for (int j = 0; j < thisSkeleton->at(k).Joints.size(); j++) - { - MGlobal::displayInfo(MString() + thisSkeleton->at(k).Joints.at(j).Name.c_str()); - } + for (unsigned int j = 0; j < m_StartFrameLines.size(); j++) { + if (m_StartFrameLines[j]->text().isEmpty() == true || m_StartFrameLines[j]->text().isEmpty() == true) { + MGlobal::displayError(MString() + "Empty Animation Clip(s)"); + return; } + + int startFrame = m_StartFrameLines[j]->text().toInt(); + int endFrame = m_EndFrameLines[j]->text().toInt(); + + for (int i = startFrame; i < endFrame;++i) + { + MAnimControl::setCurrentTime(MTime(i, MTime::kNTSCField)); + MTime time = MAnimControl::currentTime(); + + // Traverse scene and return vector with all materials + AllSkeletons.push_back(m_SkeletonHandler->DoIt()); + } + + //MGlobal::displayInfo(MString() + AllSkeletons.size()); + + /*for (int i = 0; i < AllSkeletons.size(); i++) + { + std::vector*& thisSkeleton = AllSkeletons.at(i); + for (int k = 0; k < thisSkeleton->size(); k++) + { + for (int j = 0; j < thisSkeleton->at(k).Joints.size(); j++) + { + MGlobal::displayInfo(MString() + thisSkeleton->at(k).Joints.at(j).Name.c_str()); + } + } + }*/ } } @@ -221,5 +318,6 @@ Menu::~Menu() //delete exportPath; //delete fileDialog; m_FileDialog->~QFileDialog(); + //delete MaterialHandler; } \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index a0fe93f6..81ec2834 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -29,6 +29,9 @@ #include #include #include +#include +#include + #include "MayaIncludes.h" #include "Material.h" @@ -48,6 +51,8 @@ public: private slots: void ExportSelected(bool checked); void ExportPathClicked(bool); + void AddClipClicked(bool); + void RemoveClipClicked(bool); void ExportAll(bool); void CancelClicked(bool); @@ -58,10 +63,18 @@ private slots: private: Menu(); + std::vector m_AnimationClipName; + std:: vector m_StartFrameLines; + std::vector m_EndFrameLines; + std::vector layouts; + QVBoxLayout* m_ClipLayout; + QPushButton* m_ExportSelectedButton = nullptr; QPushButton* m_BrowseButton = nullptr; QPushButton* m_ExportAllButton = nullptr; QPushButton* m_CancelButton = nullptr; + QPushButton* m_AddClipsButton = nullptr; + QPushButton* m_RemoveClipsButton = nullptr; QCheckBox* m_ExportAnimationsButton = nullptr; QCheckBox* m_CopyTexturesButton = nullptr; From bc4cc5db548eeeb76391f1cd5f263e5aedd611e9 Mon Sep 17 00:00:00 2001 From: Teejoon Date: Fri, 18 Dec 2015 10:03:00 +0100 Subject: [PATCH 016/224] Changed how we get skeletons. Made so that we could get the bind pose for each skeleton in the scene --- .../MayaExporter/MayaExporter/MayaIncludes.h | 3 + tools/MayaExporter/MayaExporter/Menu.cpp | 37 ++++-- tools/MayaExporter/MayaExporter/Skeleton.cpp | 114 +++++++++++++++--- tools/MayaExporter/MayaExporter/Skeleton.h | 13 +- 4 files changed, 135 insertions(+), 32 deletions(-) diff --git a/tools/MayaExporter/MayaExporter/MayaIncludes.h b/tools/MayaExporter/MayaExporter/MayaIncludes.h index 9186bfe6..4a810787 100644 --- a/tools/MayaExporter/MayaExporter/MayaIncludes.h +++ b/tools/MayaExporter/MayaExporter/MayaIncludes.h @@ -33,6 +33,9 @@ #include #include #include +#include +#include +#include // Wrappers diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 06c115c8..410e0fa3 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -190,25 +190,44 @@ void Menu::GetSkeletonData() MTime startFrame = MAnimControl::animationStartTime(); MTime endFrame = MAnimControl::animationEndTime(); - std::vector*> AllSkeletons; + std::vector> allSkeletons; + + std::vector allBindPoses; + allBindPoses = m_SkeletonHandler->GetBindPoses(); for (int i = startFrame.value(); i < endFrame.value();i++) { MAnimControl::setCurrentTime(MTime(i, MTime::kNTSCField)); // Traverse scene and return vector with all materials - AllSkeletons.push_back(m_SkeletonHandler->DoIt()); + allSkeletons.push_back(m_SkeletonHandler->DoIt()); + } + + //print out all bind poses + for (auto aBindPose : allBindPoses) + { + MGlobal::displayInfo(MString() + "BindPose Skeleton name: " + aBindPose.Name.c_str()); + for (int i = 0; i < aBindPose.Joints.size(); i++) + { + //MGlobal::displayInfo(MString() + aBindPose.JointNames[i].c_str()); + //MGlobal::displayInfo(MString() + aBindPose.ParentIDs[i]); + //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Translation[0] + " " + aBindPose.Joints[i].Translation[1] + " " + aBindPose.Joints[i].Translation[2]); + //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Rotation[0] + " " + aBindPose.Joints[i].Rotation[1] + " " + aBindPose.Joints[i].Rotation[2]); + //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Scale[0] + " " + aBindPose.Joints[i].Scale[1] + " " + aBindPose.Joints[i].Scale[2]); + } } - MGlobal::displayInfo(MString() + AllSkeletons.size()); - - for (int i = 0; i < AllSkeletons.size(); i++) + //Print out all skeletons for all frames + MGlobal::displayInfo(MString() + allSkeletons.size()); + for (auto frameSkeletons : allSkeletons) { - std::vector*& thisSkeleton = AllSkeletons.at(i); - for (int k = 0; k < thisSkeleton->size(); k++) + for (auto aSkeleton : frameSkeletons) { - for (int j = 0; j < thisSkeleton->at(k).Joints.size(); j++) + MGlobal::displayInfo(MString() + aSkeleton.Name.c_str()); + for (auto joint : aSkeleton.Joints) { - MGlobal::displayInfo(MString() + thisSkeleton->at(k).Joints.at(j).Name.c_str()); + //MGlobal::displayInfo(MString() + joint.Translation[0] + " " + joint.Translation[1] + " " + joint.Translation[2]); + //MGlobal::displayInfo(MString() + joint.Rotation[0] + " " + joint.Rotation[1] + " " + joint.Rotation[2]); + //MGlobal::displayInfo(MString() + joint.Scale[0] + " " + joint.Scale[1] + " " + joint.Scale[2]); } } } diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp index 3e95b817..030c17dd 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.cpp +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -1,13 +1,14 @@ #include "Skeleton.h" -std::vector* Skeleton::DoIt() +std::vector Skeleton::DoIt() { - MItDependencyNodes jointIt(MFn::kJoint); + std::vector m_AllSkeletons; + + MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); SkeletonNode SkeletonStorage; while (!jointIt.isDone()) { - MFnDependencyNode SkeletonFnDN(jointIt.thisNode()); - MFnTransform TransformNode(SkeletonFnDN.object()); + MFnTransform TransformNode(jointIt.currentItem()); Joint NewJoint; if (MFnDependencyNode(TransformNode.parent(0)).name() == "world") { @@ -20,24 +21,27 @@ std::vector* Skeleton::DoIt() SkeletonStorage.Name = TransformNode.name().asChar(); - NewJoint.ParentIndex = -1; // This joint is root - } - else { - auto it = std::find(m_Hierarchy.begin(), m_Hierarchy.end(), TransformNode.parent(0)); - if (it != m_Hierarchy.end()) { - NewJoint.ParentIndex = it - m_Hierarchy.begin(); - } - else { - MGlobal::displayError(MString() + "Could not find joint parent for: " + TransformNode.name()); - } + //NewJoint.ParentIndex = -1; // This joint is root } - m_Hierarchy.push_back(TransformNode.object()); - - NewJoint.Name = TransformNode.name().asChar(); + //NewJoint.Name = TransformNode.name().asChar(); MMatrix Matrix = TransformNode.transformationMatrix(); + //double tmp[3]; + //((MTransformationMatrix)Matrix).eulerRotation().asVector().get(tmp); + //NewJoint.Rotation[0] = tmp[0]; + //NewJoint.Rotation[1] = tmp[1]; + //NewJoint.Rotation[2] = tmp[2]; + //((MTransformationMatrix)Matrix).getScale(tmp, MSpace::Space::kTransform); + //NewJoint.Scale[0] = tmp[0]; + //NewJoint.Scale[1] = tmp[1]; + //NewJoint.Scale[2] = tmp[2]; + //((MTransformationMatrix)Matrix).getTranslation(MSpace::Space::kTransform).get(tmp); + //NewJoint.Translation[0] = tmp[0]; + //NewJoint.Translation[1] = tmp[1]; + //NewJoint.Translation[2] = tmp[2]; + for (int i = 0; i < 4; i++) { for (int j = 0; j < 4; j++) { NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; @@ -51,5 +55,79 @@ std::vector* Skeleton::DoIt() m_AllSkeletons.push_back(SkeletonStorage); - return &m_AllSkeletons; + return m_AllSkeletons; +} + +std::vector Skeleton::GetBindPoses() +{ + std::vector m_AllSkeletons; + std::vector m_Hierarchy; + + MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); + BindPoseSkeletonNode SkeletonStorage; + + while (!jointIt.isDone()) { + MFnTransform MayaJoint(jointIt.currentItem()); + + if (MFnDependencyNode(MayaJoint.parent(0)).name() == "world") { + if (SkeletonStorage.Joints.size() != 0) { + m_AllSkeletons.push_back(SkeletonStorage); + + SkeletonStorage.Joints.clear(); + SkeletonStorage.Name.clear(); + SkeletonStorage.ParentIDs.clear(); + SkeletonStorage.Name.clear(); + } + + SkeletonStorage.Name = MayaJoint.name().asChar(); + SkeletonStorage.ParentIDs.push_back(-1); // This joint is root + } + else { + auto it = std::find(m_Hierarchy.begin(), m_Hierarchy.end(), MayaJoint.parent(0)); + if (it != m_Hierarchy.end()) { + SkeletonStorage.ParentIDs.push_back(it - m_Hierarchy.begin()); + } + else { + MGlobal::displayError(MString() + "Could not find joint parent for: " + MayaJoint.name()); + } + } + m_Hierarchy.push_back(MayaJoint.object()); + + Joint NewJoint; + + MPlug BindPose = MayaJoint.findPlug("bindPose"); + MDataHandle DataHandle; + BindPose.getValue(DataHandle); + MFnMatrixData MartixFn(DataHandle.data()); + MMatrix Matrix = MartixFn.matrix(); + + for (int i = 0; i < 4; i++) { + for (int j = 0; j < 4; j++) { + NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; + } + } + + /*double tmp[3]; + ((MTransformationMatrix)Matrix).eulerRotation().asVector().get(tmp); + NewJoint.Rotation[0] = tmp[0]; + NewJoint.Rotation[1] = tmp[1]; + NewJoint.Rotation[2] = tmp[2]; + ((MTransformationMatrix)Matrix).getScale(tmp, MSpace::Space::kTransform); + NewJoint.Scale[0] = tmp[0]; + NewJoint.Scale[1] = tmp[1]; + NewJoint.Scale[2] = tmp[2]; + ((MTransformationMatrix)Matrix).getTranslation(MSpace::Space::kTransform).get(tmp); + NewJoint.Translation[0] = tmp[0]; + NewJoint.Translation[1] = tmp[1]; + NewJoint.Translation[2] = tmp[2];*/ + + SkeletonStorage.Joints.push_back(NewJoint); + SkeletonStorage.JointNames.push_back(MayaJoint.name().asChar()); + + jointIt.next(); + } + + m_AllSkeletons.push_back(SkeletonStorage); + + return m_AllSkeletons; } \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Skeleton.h b/tools/MayaExporter/MayaExporter/Skeleton.h index 26e99d4b..3ee01224 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.h +++ b/tools/MayaExporter/MayaExporter/Skeleton.h @@ -7,12 +7,11 @@ #include "MayaIncludes.h" struct Joint { - int ParentIndex; + //int ParentIndex; //std::array Rotation; //std::array Translation; //std::array Scale; std::array, 4> OffsetMatrix; - std::string Name; }; struct SkeletonNode { @@ -20,12 +19,16 @@ struct SkeletonNode { std::vector Joints; }; +struct BindPoseSkeletonNode : SkeletonNode { + std::vector ParentIDs; + std::vector JointNames; +}; + class Skeleton { public: - std::vector* DoIt(); + std::vector DoIt(); + std::vector GetBindPoses(); private: - std::vector m_AllSkeletons; - std::vector m_Hierarchy; }; #endif //Skeleton_Skeleton_h__ \ No newline at end of file From c9db46564f1394978bf75e88d5b18bce0e0d3908 Mon Sep 17 00:00:00 2001 From: antc13 Date: Fri, 18 Dec 2015 16:21:07 +0100 Subject: [PATCH 017/224] Spitting out files WIP --- .../MayaExporter/MayaExporter.vcxproj | 3 + .../MayaExporter/MayaExporter.vcxproj.filters | 9 +++ .../MayaExporter/MayaExporter/MayaIncludes.h | 1 + tools/MayaExporter/MayaExporter/Menu.cpp | 12 +++- tools/MayaExporter/MayaExporter/Menu.h | 3 + tools/MayaExporter/MayaExporter/Mesh.cpp | 52 ++++++++++---- tools/MayaExporter/MayaExporter/Mesh.h | 14 +++- tools/MayaExporter/MayaExporter/OutputData.h | 23 ++++++ tools/MayaExporter/MayaExporter/Skeleton.cpp | 3 + tools/MayaExporter/MayaExporter/Skeleton.h | 70 +++++++++++++++++-- .../MayaExporter/MayaExporter/WriteToFile.cpp | 38 ++++++++++ tools/MayaExporter/MayaExporter/WriteToFile.h | 49 +++++++++++++ 12 files changed, 257 insertions(+), 20 deletions(-) create mode 100644 tools/MayaExporter/MayaExporter/OutputData.h create mode 100644 tools/MayaExporter/MayaExporter/WriteToFile.cpp create mode 100644 tools/MayaExporter/MayaExporter/WriteToFile.h diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index 50577919..a9154ac7 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -175,6 +175,7 @@ + @@ -198,7 +199,9 @@ + + Moc%27ing Menu.h... .\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters index cf4a5a35..be5b36b1 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters @@ -59,6 +59,9 @@ Source Files + + Source Files + @@ -87,5 +90,11 @@ Header Files + + Header Files + + + Header Files + \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/MayaIncludes.h b/tools/MayaExporter/MayaExporter/MayaIncludes.h index 4a810787..0e490208 100644 --- a/tools/MayaExporter/MayaExporter/MayaIncludes.h +++ b/tools/MayaExporter/MayaExporter/MayaIncludes.h @@ -36,6 +36,7 @@ #include #include #include +#include // Wrappers diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index ae5b1732..ed09ec25 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -215,8 +215,12 @@ void Menu::ExportAll(bool) cout << m_ExportPath->text().toLocal8Bit().constData() << endl; } + m_File.ASCIIFilePath("C:/Users/Nickelodion/Desktop/coolASCII.txt"); + m_File.binaryFilePath("C:/Users/Nickelodion/Desktop/coolSoptunz.bin"); + if(m_ExportAnimationsButton->isChecked()) GetSkeletonData(); + } void Menu::CancelClicked(bool) @@ -298,8 +302,10 @@ void Menu::GetSkeletonData() } //print out all bind poses + m_File.OpenFiles(); for (auto aBindPose : allBindPoses) { + m_File.writeToFiles(&aBindPose); MGlobal::displayInfo(MString() + "BindPose Skeleton name: " + aBindPose.Name.c_str()); for (int i = 0; i < aBindPose.Joints.size(); i++) { @@ -312,21 +318,25 @@ void Menu::GetSkeletonData() } //Print out all skeletons for all frames + MGlobal::displayInfo(MString() + allSkeletons.size()); for (auto frameSkeletons : allSkeletons) { for (auto aSkeleton : frameSkeletons) { MGlobal::displayInfo(MString() + aSkeleton.Name.c_str()); + //m_File.writeToFiles(&aSkeleton); for (auto joint : aSkeleton.Joints) { + //m_File.writeToFiles(&joint); //MGlobal::displayInfo(MString() + joint.Translation[0] + " " + joint.Translation[1] + " " + joint.Translation[2]); //MGlobal::displayInfo(MString() + joint.Rotation[0] + " " + joint.Rotation[1] + " " + joint.Rotation[2]); //MGlobal::displayInfo(MString() + joint.Scale[0] + " " + joint.Scale[1] + " " + joint.Scale[2]); } } - }*/ + } } + m_File.CloseFiles(); } Menu::~Menu() diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index 81ec2834..0174cbc3 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -37,6 +37,7 @@ #include "Material.h" #include "Mesh.h" #include "Skeleton.h" +#include "WriteToFile.h" class Menu : public QWidget { @@ -86,6 +87,8 @@ private: Material* m_MaterialHandler = nullptr; Skeleton* m_SkeletonHandler = nullptr; + + WriteToFile m_File; }; #endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index fa52fc8e..3965daf8 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -25,26 +25,48 @@ void Mesh::GetMeshData(MObject object) MVector normal; MPoint pos; float2 UV; + double biTangent[3]; + double biNormal[3]; VertexLayout thisVertex; + MFloatVectorArray biTangents; + MFloatVectorArray biNormals; + mesh.getTangents(biTangents, MSpace::kObject, NULL); + mesh.getBinormals(biNormals, MSpace::kObject, NULL); + + MGlobal::displayInfo("Befor Loop"); + MItMeshFaceVertex faceVert(object); + int intDummy = 0; for (MItMeshPolygon meshPolyIter(object); !meshPolyIter.isDone(); meshPolyIter.next()) { vector localVertexToGlobalIndex; meshPolyIter.getVertices(vertices); meshPolyIter.getTriangles(dummy, triangleList); UINT indexOffset = verticesData.size(); - + MGlobal::displayInfo("Befor Second Loop"); for (UINT i = 0; i < vertices.length(); i++) { - vertexIndex = meshPolyIter.vertexIndex(i); - pos = meshPolyIter.point(i); - pos.get(thisVertex.Pos); - - meshPolyIter.getNormal(i, normal); + faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); + MGlobal::displayInfo("In Second Loop"); + faceVert.position().get(thisVertex.Pos); + faceVert.getNormal(normal); thisVertex.Normal[0] = normal[0]; thisVertex.Normal[1] = normal[1]; thisVertex.Normal[2] = normal[2]; - meshPolyIter.getUV(i, UV); + MFloatVector biTangent = biTangents[faceVert.tangentId()]; + //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); + //tmp.get(biTangent); + thisVertex.BiTangent[0] = biTangent[0]; + thisVertex.BiTangent[1] = biTangent[1]; + thisVertex.BiTangent[2] = biTangent[2]; + + MFloatVector biNormal = biNormals[faceVert.tangentId()]; + //faceVert.getBinormal().get(biNormal); + thisVertex.BiNormal[0] = biNormal[0]; + thisVertex.BiNormal[1] = biNormal[1]; + thisVertex.BiNormal[2] = biNormal[2]; + + faceVert.getUV(UV); thisVertex.Uv[0] = UV[0]; thisVertex.Uv[1] = UV[1]; @@ -53,14 +75,18 @@ void Mesh::GetMeshData(MObject object) cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; + cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; + cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; } - for (UINT i = 0; i < triangleList.length(); i++) { - UINT k = 0; - while (localVertexToGlobalIndex[k] != triangleList[i]) - k++; - indexArray.push_back(indexOffset + k); - } + MGlobal::displayInfo("Befor Third Loop"); + + //for (UINT i = 0; i < triangleList.length(); i++) { + // UINT k = 0; + // while (localVertexToGlobalIndex[k] != triangleList[i]) + // k++; + // indexArray.push_back(indexOffset + k); + //} } } diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h index 0ba9624d..00b88654 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.h +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -4,13 +4,25 @@ #include #include +#include "OutputData.h" #include "MayaIncludes.h" -struct VertexLayout +class VertexLayout : public OutputData { +public: + float Pos[3]; float Normal[3]; + float BiNormal[3]; + float BiTangent[3]; float Uv[2]; + + virtual void WriteBinary(std::ostream& out) { + + } + virtual void WriteASCII(std::ostream& out) const { + + } }; class Mesh diff --git a/tools/MayaExporter/MayaExporter/OutputData.h b/tools/MayaExporter/MayaExporter/OutputData.h new file mode 100644 index 00000000..60159340 --- /dev/null +++ b/tools/MayaExporter/MayaExporter/OutputData.h @@ -0,0 +1,23 @@ +#ifndef OutputData_OutputData_h__ +#define OutputData_OutputData_h__ +#include +//template +class OutputData +{ +public://std::ostream& out, const OutputData& obj + //OutputData(T& object) + // : m_Object(object) + //{}; + + friend std::ostream& operator<<(std::ostream& out, const OutputData& obj) + { + obj.WriteASCII(out); + return out; + }; + virtual void WriteBinary(std::ostream& out) = 0; + virtual void WriteASCII(std::ostream& out) const = 0; + + //T& m_Object = nullptr; +}; + +#endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp index 030c17dd..3bba4c0a 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.cpp +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -1,5 +1,8 @@ #include "Skeleton.h" + + + std::vector Skeleton::DoIt() { std::vector m_AllSkeletons; diff --git a/tools/MayaExporter/MayaExporter/Skeleton.h b/tools/MayaExporter/MayaExporter/Skeleton.h index 3ee01224..2d363cf8 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.h +++ b/tools/MayaExporter/MayaExporter/Skeleton.h @@ -5,23 +5,83 @@ #include #include #include "MayaIncludes.h" - -struct Joint { +#include "OutputData.h" +class Joint : public OutputData{ +public: + //Joint() : OutputData((Joint)*this) + //{}; //int ParentIndex; //std::array Rotation; //std::array Translation; //std::array Scale; - std::array, 4> OffsetMatrix; + //std::array, 4> OffsetMatrix; + float OffsetMatrix[4][4]; + + virtual void WriteBinary(std::ostream& out) + { + out.write((char*)OffsetMatrix, 4 * 4 * sizeof(float)); + } + + virtual void WriteASCII(std::ostream& out) const + { + for (int i = 0; i < 4; i++) + { + for (int k = 0; k < 4; k++) + out << this->OffsetMatrix[i][k] << " "; + out << endl; + } + }; }; -struct SkeletonNode { +class SkeletonNode : public OutputData { +public: std::string Name; std::vector Joints; + + virtual void WriteBinary(std::ostream& out) + { + out.write(Name.c_str(), Name.size()); + for (auto aJoint : Joints) + { + aJoint.WriteBinary(out); + } + } + virtual void WriteASCII(std::ostream& out) const + { + out << "Skeleton: " << Name << endl; + for (auto aJoint : Joints) + { + aJoint.WriteASCII(out); + } + }; }; -struct BindPoseSkeletonNode : SkeletonNode { +class BindPoseSkeletonNode : public SkeletonNode { +public: std::vector ParentIDs; std::vector JointNames; + virtual void WriteBinary(std::ostream& out) + { + out.write(Name.c_str(), Name.size()); + for (int i = 0; i < Joints.size(); i++) + { + out.write((char*)&ParentIDs[i],sizeof(int)); + Joints[i].WriteBinary(out); + out.write(JointNames[i].c_str(), JointNames[i].size()); + } + + } + + virtual void WriteASCII(std::ostream& out) const + { + out << "Bind Pose: " << Name << endl; + for (int i = 0; i < Joints.size(); i++) + { + out << ParentIDs[i] << endl; + Joints[i].WriteASCII(out); + out << JointNames[i] << endl; + } + }; }; class Skeleton { diff --git a/tools/MayaExporter/MayaExporter/WriteToFile.cpp b/tools/MayaExporter/MayaExporter/WriteToFile.cpp new file mode 100644 index 00000000..10883416 --- /dev/null +++ b/tools/MayaExporter/MayaExporter/WriteToFile.cpp @@ -0,0 +1,38 @@ +#include "WriteToFile.h" + +WriteToFile::~WriteToFile() +{ + CloseFiles(); +} + +bool WriteToFile::binaryFilePath(string filePathAndFileName) +{ + binFileName = filePathAndFileName; + ofstream binFile(filePathAndFileName, ofstream::binary); + if (!binFile) + return false; + return true; +} + +bool WriteToFile::ASCIIFilePath(string filePathAndFileName) +{ + ASCIIFileName = filePathAndFileName; + ofstream ASCIIFile(filePathAndFileName); + if (!ASCIIFile) + return false; + return true; +} + +void WriteToFile::OpenFiles() +{ + if (binFile) + binFile.open(binFileName, ofstream::binary); + if (ASCIIFile) + ASCIIFile.open(ASCIIFileName); +} + +void WriteToFile::CloseFiles() +{ + binFile.close(); + ASCIIFile.close(); +} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/WriteToFile.h b/tools/MayaExporter/MayaExporter/WriteToFile.h new file mode 100644 index 00000000..f0c066d4 --- /dev/null +++ b/tools/MayaExporter/MayaExporter/WriteToFile.h @@ -0,0 +1,49 @@ +#ifndef WriteToFile_WriteToFile_h__ +#define WriteToFile_WriteToFile_h__ + +#include "MayaIncludes.h" +#include "OutputData.h" +#include +#include + +using namespace std; + +class WriteToFile +{ +public: + ~WriteToFile(); + bool binaryFilePath(string filePathAndFileName); + bool ASCIIFilePath(string filePathAndFileName); + + void writeToFiles(OutputData* toWrite, unsigned int numOfElementToWrite = 1, unsigned int startIndex = 0) + { + MGlobal::displayInfo("WriteToFile::writeToFiles()"); + if (ASCIIFile.is_open()) + { + MGlobal::displayInfo("Writing to ASCIIfile"); + for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) + ASCIIFile << toWrite[i] << endl; + } + + if (binFile.is_open()) + { + MGlobal::displayInfo("Writing to binaryfile"); + for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) + toWrite[i].WriteBinary(binFile); + } + + } + + void OpenFiles(); + void CloseFiles(); + +private: + string binFileName; + string ASCIIFileName; + ofstream binFile; + ofstream ASCIIFile; +}; + + + +#endif \ No newline at end of file From eb5fca898ff4b092a93c1209a798824e1f796f1b Mon Sep 17 00:00:00 2001 From: FakeShemp Date: Mon, 21 Dec 2015 12:55:25 +0100 Subject: [PATCH 018/224] Fix small bug with push_back order Commited directly from GitHub. Blame it if something explodes. --- tools/MayaExporter/MayaExporter/Material.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tools/MayaExporter/MayaExporter/Material.cpp b/tools/MayaExporter/MayaExporter/Material.cpp index 2bc084dc..ac9c46ea 100644 --- a/tools/MayaExporter/MayaExporter/Material.cpp +++ b/tools/MayaExporter/MayaExporter/Material.cpp @@ -226,11 +226,11 @@ std::vector* Material::DoIt() else if (matIt.thisNode().hasFn(MFn::kLambert)) { grabLambertProperties(MaterialStorage, MaterialFnDN); - m_AllMaterials.push_back(MaterialStorage); - MaterialStorage.Specular.fill(0.0f); MaterialStorage.ReflectionFactor = 0.0f; MaterialStorage.SpecularExponent = 0.0f; + + m_AllMaterials.push_back(MaterialStorage); } matIt.next(); From 7ae42a5bf7e7ccb1a789a7257f8d56228b01ccf7 Mon Sep 17 00:00:00 2001 From: stiffly Date: Wed, 6 Jan 2016 11:39:32 +0100 Subject: [PATCH 019/224] Removed some comments. Basically did nothing --- include/Engine/Network/Network.h | 1 + src/Engine/Input/InputProxy.cpp | 4 ++-- src/Engine/Network/Client.cpp | 14 +++++--------- src/Engine/Network/Server.cpp | 8 ++++++-- src/Game/Game.cpp | 13 ++++++------- 5 files changed, 20 insertions(+), 20 deletions(-) diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index 0f7baefe..c5107b2b 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -14,6 +14,7 @@ public: virtual ~Network() { }; virtual void Start(World* m_world, EventBroker *eventBroker) = 0; virtual void Update() = 0; + virtual void Close() = 0; }; #endif \ No newline at end of file diff --git a/src/Engine/Input/InputProxy.cpp b/src/Engine/Input/InputProxy.cpp index c3e4d669..ad589df3 100644 --- a/src/Engine/Input/InputProxy.cpp +++ b/src/Engine/Input/InputProxy.cpp @@ -62,7 +62,7 @@ void InputProxy::Process() e.Command = command; e.Value = currentValue; m_EventBroker->Publish(e); - LOG_DEBUG("Input: Published command %s=%f for player %i", e.Command.c_str(), e.Value, e.PlayerID); + //LOG_DEBUG("Input: Published command %s=%f for player %i", e.Command.c_str(), e.Value, e.PlayerID); m_LastCommandValues[command] = currentValue; } } @@ -78,7 +78,7 @@ void InputProxy::Process() } //e.Value = std::max(-1.f, std::min(e.Value, 1.f)); m_EventBroker->Publish(e); - LOG_DEBUG("Input: Published command %s=%f for player %i", e.Command.c_str(), e.Value, e.PlayerID); + //LOG_DEBUG("Input: Published command %s=%f for player %i", e.Command.c_str(), e.Value, e.PlayerID); } m_CommandQueue.clear(); } diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 5c7e9c8f..a417c4e5 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -17,7 +17,7 @@ Client::Client(ConfigFile* config) : m_Socket(m_IOService) Client::~Client() { - + m_EventBroker->Unsubscribe(m_EInputCommand); } void Client::Start(World* world, EventBroker* eventBroker) @@ -27,14 +27,10 @@ void Client::Start(World* world, EventBroker* eventBroker) m_World = world; // Subscribe to events - m_EInputCommand = decltype(m_EInputCommand)(std::bind(&Client::OnInputCommand, this, std::placeholders::_1)); - m_EventBroker->Subscribe(m_EInputCommand); + //m_EInputCommand = decltype(m_EInputCommand)(std::bind(&Client::OnInputCommand, this, std::placeholders::_1)); + //m_EventBroker->Subscribe(m_EInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Client::OnInputCommand); - - //while (m_PlayerName.size() > 7) { - // LOG_INFO("Please enter your name (No longer than 7 characters):"); - // std::cin >> m_PlayerName; - //} m_Socket.connect(m_ReceiverEndpoint); LOG_INFO("I am client. BIP BOP"); } @@ -73,7 +69,7 @@ void Client::readFromServer() void Client::sendSnapshotToServer() { - // Reset previouse key state in snapshot. + // Reset previous key state in snapshot. m_NextSnapshot.InputForward = ""; m_NextSnapshot.InputRight = ""; diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 261583cc..c53dce8f 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -4,7 +4,9 @@ Server::Server() : m_Socket(m_IOService, boost::asio::ip::udp::endpoint(boost::a { } Server::~Server() -{ } +{ + +} void Server::Start(World* world, EventBroker* eventBroker) @@ -25,6 +27,8 @@ void Server::Update() void Server::Close() { m_ThreadIsRunning = false; + m_Socket.close(); + } void Server::readFromClients() @@ -271,7 +275,7 @@ void Server::parseConnect(Packet& packet) m_StopTimes[i] = std::clock(); - LOG_INFO("Player \"%s\" connected on IP: %s", m_PlayerDefinitions[i].Name, m_PlayerDefinitions[i].Endpoint.address().to_string()); + LOG_INFO("Player \"%s\" connected on IP: %s", m_PlayerDefinitions[i].Name.c_str(), m_PlayerDefinitions[i].Endpoint.address().to_string().c_str()); Packet packet(MessageType::Connect, m_SendPacketID); packet.WritePrimitive(i); // Player ID diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index f1582d5d..d8bebea6 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -128,11 +128,15 @@ bool Game::debugOnInputCommand(const Events::InputCommand& e) } } if (e.Command == "SwitchToServer" && e.Value > 0) { + m_ClientOrServer->Close(); // memory leak for now, use delete when it works + //delete m_ClientOrServer; m_ClientOrServer = new Server(); LOG_INFO("Switching to server"); m_ClientOrServer->Start(m_World, m_EventBroker); } - if (e.Command == "SwitchToClient" && e.Value > 0) { + else if (e.Command == "SwitchToClient" && e.Value > 0) { + m_ClientOrServer->Close(); // memory leak for now, use delete when it works + //delete m_ClientOrServer; m_ClientOrServer = new Client(m_Config); m_ClientOrServer->Start(m_World, m_EventBroker); LOG_INFO("Switching to client"); @@ -163,10 +167,5 @@ void Game::networkFunction() m_ClientOrServer = new Server(); } m_ClientOrServer->Start(m_World, m_EventBroker); - // I don't think we are reaching this part of the code right now. - // ~Game() is not called if the game is exited by closing console windows - // When server or client is done set it to false. - //m_IsClientOrServer = false; - // Destroy it - //delete m_ClientOrServer; + } \ No newline at end of file From 1667358e0c3a59ee50b317bac75b85b8b35d5b2b Mon Sep 17 00:00:00 2001 From: antc13 Date: Fri, 8 Jan 2016 16:47:04 +0100 Subject: [PATCH 020/224] We now export animations. --- .../GeneratedFiles/Debug/moc_Menu.cpp | 31 +- tools/MayaExporter/MayaExporter/Menu.cpp | 63 ++-- tools/MayaExporter/MayaExporter/Mesh.cpp | 17 +- tools/MayaExporter/MayaExporter/Skeleton.cpp | 296 ++++++++++++------ tools/MayaExporter/MayaExporter/Skeleton.h | 117 ++++--- 5 files changed, 318 insertions(+), 206 deletions(-) diff --git a/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp b/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp index aef8d533..a375ed53 100644 --- a/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp +++ b/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp @@ -22,7 +22,7 @@ static const uint qt_meta_data_Menu[] = { 6, // revision 0, // classname 0, 0, // classinfo - 7, 14, // methods + 9, 14, // methods 0, 0, // properties 0, 0, // enums/sets 0, 0, // constructors @@ -33,17 +33,20 @@ static const uint qt_meta_data_Menu[] = { 14, 6, 5, 5, 0x08, 35, 5, 5, 5, 0x08, 59, 5, 5, 5, 0x08, - 75, 5, 5, 5, 0x08, - 95, 5, 5, 5, 0x08, - 116, 5, 5, 5, 0x08, - 137, 5, 5, 5, 0x08, + 80, 5, 5, 5, 0x08, + 104, 5, 5, 5, 0x08, + 120, 5, 5, 5, 0x08, + 140, 5, 5, 5, 0x08, + 161, 5, 5, 5, 0x08, + 182, 5, 5, 5, 0x08, 0 // eod }; static const char qt_meta_stringdata_Menu[] = { "Menu\0\0checked\0ExportSelected(bool)\0" - "ExportPathClicked(bool)\0ExportAll(bool)\0" + "ExportPathClicked(bool)\0AddClipClicked(bool)\0" + "RemoveClipClicked(bool)\0ExportAll(bool)\0" "CancelClicked(bool)\0Button1Clicked(bool)\0" "Button2Clicked(bool)\0Button3Clicked(bool)\0" }; @@ -56,11 +59,13 @@ void Menu::qt_static_metacall(QObject *_o, QMetaObject::Call _c, int _id, void * switch (_id) { case 0: _t->ExportSelected((*reinterpret_cast< bool(*)>(_a[1]))); break; case 1: _t->ExportPathClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 2: _t->ExportAll((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 3: _t->CancelClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 4: _t->Button1Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 5: _t->Button2Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 6: _t->Button3Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 2: _t->AddClipClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 3: _t->RemoveClipClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 4: _t->ExportAll((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 5: _t->CancelClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 6: _t->Button1Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 7: _t->Button2Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 8: _t->Button3Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; default: ; } } @@ -98,9 +103,9 @@ int Menu::qt_metacall(QMetaObject::Call _c, int _id, void **_a) if (_id < 0) return _id; if (_c == QMetaObject::InvokeMetaMethod) { - if (_id < 7) + if (_id < 9) qt_static_metacall(this, _c, _id, _a); - _id -= 7; + _id -= 9; } return _id; } diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index ed09ec25..77241cad 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -72,7 +72,7 @@ Menu::Menu(QDialog* dialog) endLabel->setText("End:"); //exportLabel->setText("Export Path:"); - + midLayout->addWidget(optionsBox); topLayout->addWidget(exportLabel); @@ -119,7 +119,7 @@ void Menu::ExportSelected(bool checked) MGlobal::getActiveSelectionList(selected); // Loop through or list of selection(s) - for (unsigned int i = 0; i < selected.length();i++) { + for (unsigned int i = 0; i < selected.length(); i++) { MObject object; selected.getDependNode(i, object); MFnDependencyNode thisNode(object); @@ -177,7 +177,7 @@ void Menu::RemoveClipClicked(bool) QLayoutItem* tempWidget;// = m_ClipLayout->itemAt(0); for (unsigned int i = 0; i < layouts.size(); i++) { - while ((tempWidget = layouts[layouts.size()-1]->takeAt(0)) != 0) { + while ((tempWidget = layouts[layouts.size() - 1]->takeAt(0)) != 0) { delete tempWidget->widget(); delete tempWidget; } @@ -185,7 +185,7 @@ void Menu::RemoveClipClicked(bool) m_ClipLayout->removeItem(tempWidget); m_ClipLayout->update(); - + layouts.pop_back(); m_StartFrameLines.pop_back(); m_EndFrameLines.pop_back(); @@ -195,10 +195,10 @@ void Menu::RemoveClipClicked(bool) void Menu::ExportAll(bool) { MDagPath path; - + // Loop through all nodes in the scene MItDependencyNodes it(MFn::kInvalid); - for (;!it.isDone();it.next()) { + for (; !it.isDone(); it.next()) { MObject node = it.thisNode(); if (node.hasFn(MFn::kMesh)) { MFnDependencyNode thisNode(node); @@ -218,7 +218,7 @@ void Menu::ExportAll(bool) m_File.ASCIIFilePath("C:/Users/Nickelodion/Desktop/coolASCII.txt"); m_File.binaryFilePath("C:/Users/Nickelodion/Desktop/coolSoptunz.bin"); - if(m_ExportAnimationsButton->isChecked()) + if (m_ExportAnimationsButton->isChecked()) GetSkeletonData(); } @@ -267,7 +267,7 @@ void Menu::GetMaterialData() // Access the colorR component of one material (example) cout << AllMaterials->at(0).Color[0] << endl; - MGlobal::displayInfo(MString() + AllMaterials->at(0).Color[0]); + MGlobal::displayInfo(MString() + AllMaterials->at(0).Color[0]); } void Menu::GetSkeletonData() @@ -277,10 +277,10 @@ void Menu::GetSkeletonData() MGlobal::displayError(MString() + "Please change to 60 FPS under Preferences/Settings!"); return; } - - std::vector> allSkeletons; std::vector allBindPoses; + std::vector allAnimations; + allBindPoses = m_SkeletonHandler->GetBindPoses(); for (unsigned int j = 0; j < m_StartFrameLines.size(); j++) { @@ -291,24 +291,19 @@ void Menu::GetSkeletonData() int startFrame = m_StartFrameLines[j]->text().toInt(); int endFrame = m_EndFrameLines[j]->text().toInt(); + std::string animationName = m_AnimationClipName[j]->text().toAscii().constData(); - for (int i = startFrame; i < endFrame;++i) - { - MAnimControl::setCurrentTime(MTime(i, MTime::kNTSCField)); - MTime time = MAnimControl::currentTime(); + allAnimations.push_back(m_SkeletonHandler->GetAnimData(animationName, startFrame, endFrame)); + } + + m_File.OpenFiles(); - // Traverse scene and return vector with all materials - allSkeletons.push_back(m_SkeletonHandler->DoIt()); - } - //print out all bind poses - m_File.OpenFiles(); - for (auto aBindPose : allBindPoses) - { + for (auto aBindPose : allBindPoses){ m_File.writeToFiles(&aBindPose); MGlobal::displayInfo(MString() + "BindPose Skeleton name: " + aBindPose.Name.c_str()); - for (int i = 0; i < aBindPose.Joints.size(); i++) - { + + for (int i = 0; i < aBindPose.Joints.size(); i++){ //MGlobal::displayInfo(MString() + aBindPose.JointNames[i].c_str()); //MGlobal::displayInfo(MString() + aBindPose.ParentIDs[i]); //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Translation[0] + " " + aBindPose.Joints[i].Translation[1] + " " + aBindPose.Joints[i].Translation[2]); @@ -316,25 +311,9 @@ void Menu::GetSkeletonData() //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Scale[0] + " " + aBindPose.Joints[i].Scale[1] + " " + aBindPose.Joints[i].Scale[2]); } } - - //Print out all skeletons for all frames - - MGlobal::displayInfo(MString() + allSkeletons.size()); - for (auto frameSkeletons : allSkeletons) - { - for (auto aSkeleton : frameSkeletons) - { - MGlobal::displayInfo(MString() + aSkeleton.Name.c_str()); - //m_File.writeToFiles(&aSkeleton); - for (auto joint : aSkeleton.Joints) - { - //m_File.writeToFiles(&joint); - //MGlobal::displayInfo(MString() + joint.Translation[0] + " " + joint.Translation[1] + " " + joint.Translation[2]); - //MGlobal::displayInfo(MString() + joint.Rotation[0] + " " + joint.Rotation[1] + " " + joint.Rotation[2]); - //MGlobal::displayInfo(MString() + joint.Scale[0] + " " + joint.Scale[1] + " " + joint.Scale[2]); - } - } - } + //print out all animations + for (auto aAnimation : allAnimations) { + m_File.writeToFiles(&aAnimation); } m_File.CloseFiles(); } diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index 3965daf8..58a7fbe4 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -34,7 +34,6 @@ void Mesh::GetMeshData(MObject object) mesh.getTangents(biTangents, MSpace::kObject, NULL); mesh.getBinormals(biNormals, MSpace::kObject, NULL); - MGlobal::displayInfo("Befor Loop"); MItMeshFaceVertex faceVert(object); int intDummy = 0; for (MItMeshPolygon meshPolyIter(object); !meshPolyIter.isDone(); meshPolyIter.next()) { @@ -43,10 +42,10 @@ void Mesh::GetMeshData(MObject object) meshPolyIter.getTriangles(dummy, triangleList); UINT indexOffset = verticesData.size(); - MGlobal::displayInfo("Befor Second Loop"); + //MGlobal::displayInfo("Befor Second Loop"); for (UINT i = 0; i < vertices.length(); i++) { faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); - MGlobal::displayInfo("In Second Loop"); + //MGlobal::displayInfo("In Second Loop"); faceVert.position().get(thisVertex.Pos); faceVert.getNormal(normal); thisVertex.Normal[0] = normal[0]; @@ -73,13 +72,13 @@ void Mesh::GetMeshData(MObject object) verticesData.push_back(thisVertex); localVertexToGlobalIndex.push_back(vertexIndex); - cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; - cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; - cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; - cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; - cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; + //cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; + //cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; + //cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; + //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; + //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; } - MGlobal::displayInfo("Befor Third Loop"); + //MGlobal::displayInfo("Befor Third Loop"); //for (UINT i = 0; i < triangleList.length(); i++) { // UINT k = 0; diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp index 3bba4c0a..394f548b 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.cpp +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -3,33 +3,225 @@ -std::vector Skeleton::DoIt() +//std::vector Skeleton::DoIt() +//{ +// std::vector m_AllSkeletons; +// +// MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); +// SkeletonNode SkeletonStorage; +// +// while (!jointIt.isDone()) { +// MFnTransform TransformNode(jointIt.currentItem()); +// Joint NewJoint; +// +// if (MFnDependencyNode(TransformNode.parent(0)).name() == "world") { +// if (SkeletonStorage.Joints.size() != 0) { +// m_AllSkeletons.push_back(SkeletonStorage); +// +// SkeletonStorage.Joints.clear(); +// SkeletonStorage.Name.clear(); +// } +// +// SkeletonStorage.Name = TransformNode.name().asChar(); +// +// //NewJoint.ParentIndex = -1; // This joint is root +// } +// +// //NewJoint.Name = TransformNode.name().asChar(); +// +// MMatrix Matrix = TransformNode.transformationMatrix(); +// +// //double tmp[3]; +// //((MTransformationMatrix)Matrix).eulerRotation().asVector().get(tmp); +// //NewJoint.Rotation[0] = tmp[0]; +// //NewJoint.Rotation[1] = tmp[1]; +// //NewJoint.Rotation[2] = tmp[2]; +// //((MTransformationMatrix)Matrix).getScale(tmp, MSpace::Space::kTransform); +// //NewJoint.Scale[0] = tmp[0]; +// //NewJoint.Scale[1] = tmp[1]; +// //NewJoint.Scale[2] = tmp[2]; +// //((MTransformationMatrix)Matrix).getTranslation(MSpace::Space::kTransform).get(tmp); +// //NewJoint.Translation[0] = tmp[0]; +// //NewJoint.Translation[1] = tmp[1]; +// //NewJoint.Translation[2] = tmp[2]; +// +// for (int i = 0; i < 4; i++) { +// for (int j = 0; j < 4; j++) { +// NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; +// } +// } +// +// SkeletonStorage.Joints.push_back(NewJoint); +// +// jointIt.next(); +// } +// +// m_AllSkeletons.push_back(SkeletonStorage); +// +// return m_AllSkeletons; +//} +std::string attr[9] = { "scaleX", "scaleY", "scaleZ", "translateX", "translateY", "translateZ", "rotateX", "rotateY", "rotateZ" }; + +Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int endFrame) { - std::vector m_AllSkeletons; + Animation returnData; + double oneDivSixty = 1 / 60.0; + returnData.Name = animationName; + returnData.Duration = (endFrame - startFrame) * oneDivSixty; + std::vector animatedJoints; + std::vector m_Hierarchy; MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); - SkeletonNode SkeletonStorage; + while (!jointIt.isDone()) + { + m_Hierarchy.push_back(jointIt.item()); + + MFnDependencyNode depNode(jointIt.item()); + for (int i = 0; i < 9; i++) + { + MStatus tmp; + MPlug plug = depNode.findPlug(attr[i].c_str(), &tmp); + + MPlugArray connections; + plug.connectedTo(connections, true, false, 0); + for (int j = 0; j != connections.length(); j++) { + MObject connected = connections[j].node(); + + if (connected.hasFn(MFn::kAnimCurve)) { + + MFnAnimCurve jointAnim(connected); + + unsigned int startKeyFrameIndex = jointAnim.findClosest(MTime(startFrame, MTime::kNTSCField), &tmp); + + if (tmp == MStatus::kFailure) + MGlobal::displayInfo(MString() + "Fail :c"); + + if (startFrame * oneDivSixty <= jointAnim.time(startKeyFrameIndex).value() && jointAnim.time(startKeyFrameIndex).value() <= endFrame * oneDivSixty) { + animatedJoints.push_back(jointIt.item()); + i = 9; + break; + } + + unsigned int endKeyFrameIndex = jointAnim.findClosest(MTime(endFrame, MTime::kNTSCField)); + MGlobal::displayInfo(MString() + startKeyFrameIndex + " " + endKeyFrameIndex); + + if (startFrame * oneDivSixty <= jointAnim.time(endKeyFrameIndex).value() && jointAnim.time(endKeyFrameIndex).value() <= endFrame * oneDivSixty || endKeyFrameIndex - startKeyFrameIndex > 0) { + animatedJoints.push_back(jointIt.item()); + i = 9; + break; + } + + MFnTransform MayaJoint(jointIt.item()); + + MPlug BindPose = MayaJoint.findPlug("bindPose"); + MDataHandle DataHandle; + BindPose.getValue(DataHandle); + MFnMatrixData MartixFn(DataHandle.data()); + MMatrix BindPoseMatrix = MartixFn.matrix(); + + if (BindPoseMatrix != MayaJoint.transformationMatrix()) + { + MGlobal::displayError(MString() + animationName.c_str() + " is using a joint that is not in bind pose nor is it key framed in the animation, the exported animation will NOT correspond to the animation in Maya"); + } + } + } + } + + jointIt.next(); + } + + int currentFrame = startFrame; + while (currentFrame != endFrame) { + Animation::Keyframe thisKeyFrame; + thisKeyFrame.Index = currentFrame - startFrame; + thisKeyFrame.Time = thisKeyFrame.Index * oneDivSixty; + + MAnimControl::setCurrentTime(MTime(currentFrame, MTime::kNTSCField)); + MTime time = MAnimControl::currentTime(); + + for (auto aJoint : animatedJoints){ + MFnTransform thisJoint(aJoint); + Animation::Keyframe::JointProperty joint; + + auto it = std::find(m_Hierarchy.begin(), m_Hierarchy.end(), thisJoint.object()); + if (it != m_Hierarchy.end()) { + joint.ID = it - m_Hierarchy.begin(); + } + else { + MGlobal::displayError(MString() + "Could not find joint ID for: " + thisJoint.name()); + } + + MMatrix Matrix = thisJoint.transformationMatrix(); + + double tmp[4]; + thisJoint.getRotationQuaternion(tmp[0], tmp[1], tmp[2], tmp[3]); + joint.Rotation[0] = tmp[0]; + joint.Rotation[1] = tmp[1]; + joint.Rotation[2] = tmp[2]; + joint.Rotation[3] = tmp[3]; + thisJoint.getTranslation(MSpace::kPreTransform).get(tmp); + joint.Position[0] = tmp[0]; + joint.Position[1] = tmp[1]; + joint.Position[2] = tmp[2]; + thisJoint.getScale(tmp); + joint.Scale[0] = tmp[0]; + joint.Scale[1] = tmp[1]; + joint.Scale[2] = tmp[2]; + + thisKeyFrame.JointProperties.push_back(joint); + } + returnData.Keyframes.push_back(thisKeyFrame); + currentFrame++; + } + return returnData; +} + +std::vector Skeleton::GetBindPoses() +{ + std::vector m_AllSkeletons; + std::vector m_Hierarchy; + + MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); + BindPoseSkeletonNode SkeletonStorage; while (!jointIt.isDone()) { - MFnTransform TransformNode(jointIt.currentItem()); - Joint NewJoint; + MFnTransform MayaJoint(jointIt.currentItem()); + BindPoseSkeletonNode::BindPoseJoint NewJoint; - if (MFnDependencyNode(TransformNode.parent(0)).name() == "world") { + if (MFnDependencyNode(MayaJoint.parent(0)).name() == "world") { if (SkeletonStorage.Joints.size() != 0) { m_AllSkeletons.push_back(SkeletonStorage); SkeletonStorage.Joints.clear(); SkeletonStorage.Name.clear(); } + SkeletonStorage.Name = std::string(MayaJoint.name().asChar()); + NewJoint.ParentID = -1; // This joint is root + } + else { + auto it = std::find(m_Hierarchy.begin(), m_Hierarchy.end(), MayaJoint.parent(0)); + if (it != m_Hierarchy.end()) { + NewJoint.ParentID = it - m_Hierarchy.begin(); + } + else { + MGlobal::displayError(MString() + "Could not find joint parent for: " + MayaJoint.name()); + } + } + m_Hierarchy.push_back(MayaJoint.object()); - SkeletonStorage.Name = TransformNode.name().asChar(); + MPlug BindPose = MayaJoint.findPlug("bindPose"); + MDataHandle DataHandle; + BindPose.getValue(DataHandle); + MFnMatrixData MartixFn(DataHandle.data()); + MMatrix Matrix = MartixFn.matrix(); - //NewJoint.ParentIndex = -1; // This joint is root + for (int i = 0; i < 4; i++) { + for (int j = 0; j < 4; j++) { + NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; + } } - //NewJoint.Name = TransformNode.name().asChar(); - - MMatrix Matrix = TransformNode.transformationMatrix(); + NewJoint.Name = MayaJoint.name().asChar(); //double tmp[3]; //((MTransformationMatrix)Matrix).eulerRotation().asVector().get(tmp); @@ -44,89 +236,7 @@ std::vector Skeleton::DoIt() //NewJoint.Translation[0] = tmp[0]; //NewJoint.Translation[1] = tmp[1]; //NewJoint.Translation[2] = tmp[2]; - - for (int i = 0; i < 4; i++) { - for (int j = 0; j < 4; j++) { - NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; - } - } - SkeletonStorage.Joints.push_back(NewJoint); - - jointIt.next(); - } - - m_AllSkeletons.push_back(SkeletonStorage); - - return m_AllSkeletons; -} - -std::vector Skeleton::GetBindPoses() -{ - std::vector m_AllSkeletons; - std::vector m_Hierarchy; - - MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); - BindPoseSkeletonNode SkeletonStorage; - - while (!jointIt.isDone()) { - MFnTransform MayaJoint(jointIt.currentItem()); - - if (MFnDependencyNode(MayaJoint.parent(0)).name() == "world") { - if (SkeletonStorage.Joints.size() != 0) { - m_AllSkeletons.push_back(SkeletonStorage); - - SkeletonStorage.Joints.clear(); - SkeletonStorage.Name.clear(); - SkeletonStorage.ParentIDs.clear(); - SkeletonStorage.Name.clear(); - } - - SkeletonStorage.Name = MayaJoint.name().asChar(); - SkeletonStorage.ParentIDs.push_back(-1); // This joint is root - } - else { - auto it = std::find(m_Hierarchy.begin(), m_Hierarchy.end(), MayaJoint.parent(0)); - if (it != m_Hierarchy.end()) { - SkeletonStorage.ParentIDs.push_back(it - m_Hierarchy.begin()); - } - else { - MGlobal::displayError(MString() + "Could not find joint parent for: " + MayaJoint.name()); - } - } - m_Hierarchy.push_back(MayaJoint.object()); - - Joint NewJoint; - - MPlug BindPose = MayaJoint.findPlug("bindPose"); - MDataHandle DataHandle; - BindPose.getValue(DataHandle); - MFnMatrixData MartixFn(DataHandle.data()); - MMatrix Matrix = MartixFn.matrix(); - - for (int i = 0; i < 4; i++) { - for (int j = 0; j < 4; j++) { - NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; - } - } - - /*double tmp[3]; - ((MTransformationMatrix)Matrix).eulerRotation().asVector().get(tmp); - NewJoint.Rotation[0] = tmp[0]; - NewJoint.Rotation[1] = tmp[1]; - NewJoint.Rotation[2] = tmp[2]; - ((MTransformationMatrix)Matrix).getScale(tmp, MSpace::Space::kTransform); - NewJoint.Scale[0] = tmp[0]; - NewJoint.Scale[1] = tmp[1]; - NewJoint.Scale[2] = tmp[2]; - ((MTransformationMatrix)Matrix).getTranslation(MSpace::Space::kTransform).get(tmp); - NewJoint.Translation[0] = tmp[0]; - NewJoint.Translation[1] = tmp[1]; - NewJoint.Translation[2] = tmp[2];*/ - - SkeletonStorage.Joints.push_back(NewJoint); - SkeletonStorage.JointNames.push_back(MayaJoint.name().asChar()); - jointIt.next(); } diff --git a/tools/MayaExporter/MayaExporter/Skeleton.h b/tools/MayaExporter/MayaExporter/Skeleton.h index 2d363cf8..0b0c2a60 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.h +++ b/tools/MayaExporter/MayaExporter/Skeleton.h @@ -6,68 +6,81 @@ #include #include "MayaIncludes.h" #include "OutputData.h" -class Joint : public OutputData{ + +class Animation : public OutputData { public: - //Joint() : OutputData((Joint)*this) - //{}; - //int ParentIndex; - //std::array Rotation; - //std::array Translation; - //std::array Scale; - //std::array, 4> OffsetMatrix; - float OffsetMatrix[4][4]; - - virtual void WriteBinary(std::ostream& out) + struct Keyframe { - out.write((char*)OffsetMatrix, 4 * 4 * sizeof(float)); - } - - virtual void WriteASCII(std::ostream& out) const - { - for (int i = 0; i < 4; i++) + struct JointProperty { - for (int k = 0; k < 4; k++) - out << this->OffsetMatrix[i][k] << " "; - out << endl; - } - }; -}; + int ID; + float Position[3]; + float Rotation[4]; + float Scale[3]; + }; + + int Index; + double Time; + std::vector JointProperties; + }; -class SkeletonNode : public OutputData { -public: std::string Name; - std::vector Joints; + double Duration; + std::vector Keyframes; virtual void WriteBinary(std::ostream& out) { - out.write(Name.c_str(), Name.size()); - for (auto aJoint : Joints) - { - aJoint.WriteBinary(out); + out.write(Name.c_str(), Name.size() + 1); + out.write((char*)&Duration, sizeof(double)); + for (auto aKeyframe : Keyframes) { + out.write((char*)&aKeyframe.Index, sizeof(int)); + out.write((char*)&aKeyframe.Time, sizeof(double)); + for (auto aJoint : aKeyframe.JointProperties) { + out.write((char*)&aJoint.ID, sizeof(int)); + out.write((char*)aJoint.Position, sizeof(float) * 3); + out.write((char*)aJoint.Rotation, sizeof(float) * 4); + out.write((char*)aJoint.Scale, sizeof(float) * 3); + } } } + virtual void WriteASCII(std::ostream& out) const { - out << "Skeleton: " << Name << endl; - for (auto aJoint : Joints) - { - aJoint.WriteASCII(out); + out << "Animation Name: " << Name << endl; + out << "Duration: " << Duration << endl; + for (auto aKeyframe : Keyframes) { + out << "Frame: " << aKeyframe.Index << endl; + out << "Time: " << aKeyframe.Time << endl; + for (auto aJoint : aKeyframe.JointProperties) { + out << "Joint ID: " << aJoint.ID << endl; + out << aJoint.Position[0] << " " << aJoint.Position[1] << " " << aJoint.Position[2] << endl; + out << aJoint.Rotation[0] << " " << aJoint.Rotation[1] << " " << aJoint.Rotation[2] << " " << aJoint.Rotation[3] << endl; + out << aJoint.Scale[0] << " " << aJoint.Scale[1] << " " << aJoint.Scale[2] << endl; + } } - }; + + } }; -class BindPoseSkeletonNode : public SkeletonNode { +class BindPoseSkeletonNode : public OutputData { public: - std::vector ParentIDs; - std::vector JointNames; + struct BindPoseJoint + { + int ParentID; + std::string Name; + float OffsetMatrix[4][4]; + }; + + std::string Name; + std::vector Joints; virtual void WriteBinary(std::ostream& out) { - out.write(Name.c_str(), Name.size()); - for (int i = 0; i < Joints.size(); i++) - { - out.write((char*)&ParentIDs[i],sizeof(int)); - Joints[i].WriteBinary(out); - out.write(JointNames[i].c_str(), JointNames[i].size()); + out.write(Name.c_str(), Name.size() + 1); + for (auto Joint:Joints) + { + out.write(Joint.Name.c_str(), Joint.Name.size() + 1); + out.write((char*)&Joint.OffsetMatrix, sizeof(float) * 4 * 4); + out.write((char*)&Joint.ParentID, sizeof(int)); } } @@ -75,18 +88,24 @@ public: virtual void WriteASCII(std::ostream& out) const { out << "Bind Pose: " << Name << endl; - for (int i = 0; i < Joints.size(); i++) + for (auto Joint : Joints) { - out << ParentIDs[i] << endl; - Joints[i].WriteASCII(out); - out << JointNames[i] << endl; + out << Joint.Name << endl; + for (int i = 0; i < 4; i++) { + for (int j = 0; j < 4; j++){ + out << Joint.OffsetMatrix[i][j] << " "; + } + out << endl; + } + out << Joint.ParentID << endl; } }; }; class Skeleton { public: - std::vector DoIt(); + //std::vector DoIt(); + Animation GetAnimData(std::string animationName, int startFrame, int endFrame); std::vector GetBindPoses(); private: }; From 31c1c0ac8ddbdc1cb42992b97243ebdb265577fa Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Fri, 8 Jan 2016 16:19:18 +0100 Subject: [PATCH 021/224] New Event: EShoot. New Components: PrimaryItem,SecondaryItem. New Test: ShootEventTest. Added LeftMouseRelease->Shoot in PlayerSystem TODO: generalize the test --- include/Engine/Core/EShoot.h | 22 ++++ include/Game/PlayerSystem.h | 7 ++ resources/Schema/Components.xsd | 3 + resources/Schema/Components/Player.xml | 1 + resources/Schema/Components/Player.xsd | 1 + resources/Schema/Components/PrimaryItem.xml | 4 + resources/Schema/Components/PrimaryItem.xsd | 14 +++ resources/Schema/Components/SecondaryItem.xml | 4 + resources/Schema/Components/SecondaryItem.xsd | 14 +++ resources/Schema/Types/Entity.xsd | 2 + src/Game/PlayerSystem.cpp | 43 +++++++ src/Tests/ShootEventTest.cpp | 108 ++++++++++++++++++ src/Tests/ShootEventTest.h | 43 +++++++ 13 files changed, 266 insertions(+) create mode 100644 include/Engine/Core/EShoot.h create mode 100644 resources/Schema/Components/PrimaryItem.xml create mode 100644 resources/Schema/Components/PrimaryItem.xsd create mode 100644 resources/Schema/Components/SecondaryItem.xml create mode 100644 resources/Schema/Components/SecondaryItem.xsd create mode 100644 src/Tests/ShootEventTest.cpp create mode 100644 src/Tests/ShootEventTest.h diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h new file mode 100644 index 00000000..d9b9e20b --- /dev/null +++ b/include/Engine/Core/EShoot.h @@ -0,0 +1,22 @@ +#ifndef EShoot_h__ +#define EShoot_h__ + +#include "EventBroker.h" +#include "../Core/Entity.h" +#include "Engine/GLM.h" + +namespace Events +{ + +struct Shoot : Event +{ + //shotgun etc has different amounts of damage probably (a sniper shot might one-shot) + //also different weapons will have different spread + std::string weaponType; + //currentAimingPoint must be sent, in case the camera is moved while the event is being processed + glm::vec2 currentAimingPoint; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 577fbbb0..87dc6f5d 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -7,6 +7,8 @@ #include "Common.h" #include "Core/System.h" #include "Collision/ETrigger.h" +#include "Core\EMouseRelease.h" +#include "Core\EShoot.h" class PlayerSystem : public PureSystem { @@ -17,17 +19,22 @@ public: EVENT_SUBSCRIBE_MEMBER(m_ETouch, &PlayerSystem::OnTouch); EVENT_SUBSCRIBE_MEMBER(m_EEnter, &PlayerSystem::OnEnter); EVENT_SUBSCRIBE_MEMBER(m_ELeave, &PlayerSystem::OnLeave); + EVENT_SUBSCRIBE_MEMBER(m_MouseRelease, &PlayerSystem::OnMouseRelease); } virtual void UpdateComponent(World* world, ComponentWrapper& player, double dt) override; private: float m_Speed = 5; + bool leftMouseWasReleased = false; + glm::vec2 aimingCoordinates; EventRelay m_EEnter; bool OnEnter(const Events::TriggerEnter &event); EventRelay m_ETouch; bool PlayerSystem::OnTouch(const Events::TriggerTouch &event); EventRelay m_ELeave; bool PlayerSystem::OnLeave(const Events::TriggerLeave &event); + EventRelay m_MouseRelease; + bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e); }; #endif \ No newline at end of file diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index 7fcdd565..33714638 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -9,4 +9,7 @@ + + + \ No newline at end of file diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index 190f2ed0..cd3d1620 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,4 +1,5 @@ + 0 false false diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 76a6a8fb..fcf07879 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -11,6 +11,7 @@ + diff --git a/resources/Schema/Components/PrimaryItem.xml b/resources/Schema/Components/PrimaryItem.xml new file mode 100644 index 00000000..540a1518 --- /dev/null +++ b/resources/Schema/Components/PrimaryItem.xml @@ -0,0 +1,4 @@ + + 0 + 0 + \ No newline at end of file diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd new file mode 100644 index 00000000..193b9213 --- /dev/null +++ b/resources/Schema/Components/PrimaryItem.xsd @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xml b/resources/Schema/Components/SecondaryItem.xml new file mode 100644 index 00000000..0fae1402 --- /dev/null +++ b/resources/Schema/Components/SecondaryItem.xml @@ -0,0 +1,4 @@ + + 0 + 0 + \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd new file mode 100644 index 00000000..44e23611 --- /dev/null +++ b/resources/Schema/Components/SecondaryItem.xsd @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 6562f3ed..4b67276a 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -16,6 +16,8 @@ + + diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index 17b9a7f5..f5819ea1 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -21,6 +21,38 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou ComponentWrapper& transform = world->GetComponent(player.EntityID, "Transform"); (glm::vec3&)transform["Position"] += (glm::vec3)player["Velocity"]; } + + //do shootEvent: if left mouse was released, and ammo/weaponcooldown/playeralive/shootingcooldown are ok + if (leftMouseWasReleased) { + leftMouseWasReleased = false; + //get the health component linked to the playerId + double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; + int currentAmmo = 0; + double currentCoolDownTimer = 0.0f; + + if ((int)player["EquippedItem"] == 1) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + currentAmmo = currentItem["Ammo"]; + //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer + currentItem["Ammo"] = (int)currentItem["Ammo"] -1; + int test = (int)currentItem["Ammo"]; + currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "PrimaryItem")["CoolDownTimer"]; + } + if ((int)player["EquippedItem"] == 2) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); + currentAmmo = currentItem["Ammo"]; + //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer + currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; + currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "SecondaryItem")["CoolDownTimer"]; + } + if (currentHealth > 0.0f && currentAmmo > 0 && currentCoolDownTimer < 0.001f) { + //create and publish the shoot event + Events::Shoot eShoot; + eShoot.currentAimingPoint = aimingCoordinates; + eShoot.weaponType = (int)player["EquippedItem"]; + m_EventBroker->Publish(eShoot); + } + } } bool PlayerSystem::OnTouch(const Events::TriggerTouch &event) @@ -39,4 +71,15 @@ bool PlayerSystem::OnLeave(const Events::TriggerLeave &event) { LOG_INFO("Player entity %i left widget (entity %i).", event.Entity, event.Trigger); return false; +} + +bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e) +{ + //kolla ammoleft, cooldowntimer shooting + //kolla om left mouse varit nere + if (e.Button != GLFW_MOUSE_BUTTON_LEFT) + return false; + aimingCoordinates = glm::vec2(e.X, e.Y); + leftMouseWasReleased = true; + return true; } \ No newline at end of file diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp new file mode 100644 index 00000000..481772c1 --- /dev/null +++ b/src/Tests/ShootEventTest.cpp @@ -0,0 +1,108 @@ +#include +using boost::unit_test_framework::test_suite; +using boost::unit_test_framework::test_case; + +#include "ShootEventTest.h" +#include "Core\EPlayerDamage.h"; +#include "Core\EPlayerHealthPickup.h"; +#include "Core\EPlayerDeath.h"; +#include "Game/HealthSystem.h" + +BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) + +//AShootEventTest != ShootEventTest -> else it confuses names! +BOOST_AUTO_TEST_CASE(AShootEventTest) +{ + ShootEventTest game; + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_SUITE_END() + +ShootEventTest::ShootEventTest() +{ + ResourceManager::RegisterType("ConfigFile"); + ResourceManager::RegisterType("EntityXMLFile"); + + m_Config = ResourceManager::Load("Config.ini"); + LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); + + // Create the core event broker + m_EventBroker = new EventBroker(); + + // Create a world + m_World = new World(); + std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); + if (!mapToLoad.empty()) { + ResourceManager::Load(mapToLoad)->PopulateWorld(m_World); + } + + // Create system pipeline + m_SystemPipeline = new SystemPipeline(m_EventBroker); + m_SystemPipeline->AddSystem(0); + m_SystemPipeline->AddSystem(0); + + //The Test + //create entity which has transorm,player,model,health in it. i.e. is a player + EntityID playerID = m_World->CreateEntity(); + ComponentWrapper transform = m_World->AttachComponent(playerID, "Transform"); + ComponentWrapper model = m_World->AttachComponent(playerID, "Model"); + model["Resource"] = "Models/Core/UnitSphere.obj"; + ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); + ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); + playersID = playerID; + //attach 2x weaps + ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); + ComponentWrapper& sItem= m_World->AttachComponent(playerID, "SecondaryItem"); + //set currentweap + player["EquippedItem"] = 1; + //set ammo set cooldown + pItem["Ammo"] = 100; + pItem["CoolDownTimer"] = 0.0f; + + //trigger event leftmousedown + Events::MouseRelease eMouseRelease; + eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; + eMouseRelease.X = 1.0f; + eMouseRelease.Y = 1.0f; + m_EventBroker->Publish(eMouseRelease); + +} + +ShootEventTest::~ShootEventTest() +{ + delete m_SystemPipeline; + delete m_World; + delete m_EventBroker; +} + +void ShootEventTest::Tick() +{ + glfwPollEvents(); + + double currentTime = glfwGetTime(); + double dt = currentTime - m_LastTime; + m_LastTime = currentTime; + + // Iterate through systems and update world! + m_SystemPipeline->Update(m_World, dt); + + m_EventBroker->Swap(); + m_EventBroker->Clear(); + + //if ammocount reaches 99 we know the test has succeeded, i.e. a shot has been fired + int currentAmmo = (int)m_World->GetComponent(playersID, "PrimaryItem")["Ammo"]; + if (currentAmmo ==99) + TestSucceeded = true; +} diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h new file mode 100644 index 00000000..49206ceb --- /dev/null +++ b/src/Tests/ShootEventTest.h @@ -0,0 +1,43 @@ +#ifndef ShootEventTest_h__ +#define ShootEventTest_h__ + +#include "Core/ResourceManager.h" +#include "Core/ConfigFile.h" +#include "Core/EventBroker.h" +#include "Rendering/Renderer.h" +#include "Core/InputManager.h" +#include "GUI/Frame.h" +#include "Core/World.h" +#include "Rendering/RenderQueueFactory.h" +#include "Input/InputProxy.h" +#include "Input/KeyboardInputHandler.h" +#include "Input/MouseInputHandler.h" +#include "Core/EKeyDown.h" +#include "Core/EntityXMLFile.h" +#include "Core/SystemPipeline.h" +#include "RaptorCopterSystem.h" +#include "PlayerSystem.h" +#include "Editor/EditorSystem.h" + +#include "Core\EMouseRelease.h" +#include "Core\EShoot.h" + +class ShootEventTest +{ +public: + ShootEventTest(); + ~ShootEventTest(); + + void Tick(); + bool TestSucceeded = false; + +private: + double m_LastTime; + ConfigFile* m_Config = nullptr; + EventBroker* m_EventBroker; + World* m_World; + SystemPipeline* m_SystemPipeline; + int playersID; +}; + +#endif From 8f92de3683c69b81664dc6ad250b0658363aeec6 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 13:34:50 +0100 Subject: [PATCH 022/224] xml/xsd files changed type to double. fixed cooldownbug in PlayerSystem. Added 4 tests in ShootEventTest and generalized it a lot --- resources/Schema/Components/Player.xsd | 5 +- resources/Schema/Components/PrimaryItem.xml | 2 +- resources/Schema/Components/PrimaryItem.xsd | 11 +- resources/Schema/Components/SecondaryItem.xml | 2 +- resources/Schema/Components/SecondaryItem.xsd | 11 +- src/Game/PlayerSystem.cpp | 34 +-- src/Tests/ShootEventTest.cpp | 195 +++++++++++++++--- src/Tests/ShootEventTest.h | 21 +- 8 files changed, 228 insertions(+), 53 deletions(-) diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index fcf07879..9ffc28b0 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -4,6 +4,9 @@ + + The player charachter + @@ -11,7 +14,7 @@ - + diff --git a/resources/Schema/Components/PrimaryItem.xml b/resources/Schema/Components/PrimaryItem.xml index 540a1518..0d0ccca2 100644 --- a/resources/Schema/Components/PrimaryItem.xml +++ b/resources/Schema/Components/PrimaryItem.xml @@ -1,4 +1,4 @@ 0 0 - \ No newline at end of file + \ No newline at end of file diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd index 193b9213..bbff122d 100644 --- a/resources/Schema/Components/PrimaryItem.xsd +++ b/resources/Schema/Components/PrimaryItem.xsd @@ -4,10 +4,17 @@ + + The Players Primary Item/Weapon + - - + + Ammo count + + + Cooldown till next item/weapon use + diff --git a/resources/Schema/Components/SecondaryItem.xml b/resources/Schema/Components/SecondaryItem.xml index 0fae1402..095dfef6 100644 --- a/resources/Schema/Components/SecondaryItem.xml +++ b/resources/Schema/Components/SecondaryItem.xml @@ -1,4 +1,4 @@ 0 0 - \ No newline at end of file + \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd index 44e23611..ab428920 100644 --- a/resources/Schema/Components/SecondaryItem.xsd +++ b/resources/Schema/Components/SecondaryItem.xsd @@ -4,10 +4,17 @@ + + The Players Secondary Item/Weapon + - - + + Ammo count + + + Cooldown till next item/weapon use + diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index f5819ea1..e40469cc 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -27,25 +27,35 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou leftMouseWasReleased = false; //get the health component linked to the playerId double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; - int currentAmmo = 0; - double currentCoolDownTimer = 0.0f; + double currentAmmo = (double)0; + double currentCoolDownTimer = (double)0; - if ((int)player["EquippedItem"] == 1) { + if ((double)player["EquippedItem"] == (double)1) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); currentAmmo = currentItem["Ammo"]; - //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer - currentItem["Ammo"] = (int)currentItem["Ammo"] -1; - int test = (int)currentItem["Ammo"]; - currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "PrimaryItem")["CoolDownTimer"]; + currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if ((int)player["EquippedItem"] == 2) { + if ((double)player["EquippedItem"] == (double)2) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); currentAmmo = currentItem["Ammo"]; - //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer - currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; - currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "SecondaryItem")["CoolDownTimer"]; + currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (currentHealth > 0.0f && currentAmmo > 0 && currentCoolDownTimer < 0.001f) { + + if (currentHealth > (double)0.0f && currentAmmo > (double)0.0f && currentCoolDownTimer < (double)0.001f) { + //decrease ammo count + //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later + if ((double)player["EquippedItem"] == (double)1) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + int currentAmmoInt = (int)((double)currentItem["Ammo"]); + currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["CoolDownTimer"] = (double)2; + } + if ((double)player["EquippedItem"] == (double)2) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); + int currentAmmoInt = (int)((double)currentItem["Ammo"]); + currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["CoolDownTimer"] = (double)2; + } //create and publish the shoot event Events::Shoot eShoot; eShoot.currentAimingPoint = aimingCoordinates; diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index 481772c1..22c2a0eb 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -3,17 +3,15 @@ using boost::unit_test_framework::test_suite; using boost::unit_test_framework::test_case; #include "ShootEventTest.h" -#include "Core\EPlayerDamage.h"; -#include "Core\EPlayerHealthPickup.h"; -#include "Core\EPlayerDeath.h"; #include "Game/HealthSystem.h" BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) -//AShootEventTest != ShootEventTest -> else it confuses names! -BOOST_AUTO_TEST_CASE(AShootEventTest) +//dont use the same name as the classname in test cases... +BOOST_AUTO_TEST_CASE(ShootEventTest_PrimaryWeaponFiring) { - ShootEventTest game; + //Test firing primary weapon + ShootEventTest game(1); //100 loops will be more than enough to do the test int loops = 100; bool success = false; @@ -28,9 +26,59 @@ BOOST_AUTO_TEST_CASE(AShootEventTest) //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } +BOOST_AUTO_TEST_CASE(ShootEventTest_SecondaryWeaponFiring) +{ + //Test firing secondary weapon + ShootEventTest game(2); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(ShootEventTest_NoWeaponFiring) +{ + //Test firing with no weapon equipped + ShootEventTest game(3); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + if (game.TestSucceeded) + success = true; + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(ShootEventTest_WeaponOnCooldown) +{ + //Test firing with weapon on cooldown + ShootEventTest game(4); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + if (game.TestSucceeded) + success = true; + BOOST_TEST(success); +} BOOST_AUTO_TEST_SUITE_END() -ShootEventTest::ShootEventTest() +ShootEventTest::ShootEventTest(int runTestNumber) { ResourceManager::RegisterType("ConfigFile"); ResourceManager::RegisterType("EntityXMLFile"); @@ -41,7 +89,7 @@ ShootEventTest::ShootEventTest() // Create the core event broker m_EventBroker = new EventBroker(); - // Create a world + // Create a world m_World = new World(); std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); if (!mapToLoad.empty()) { @@ -54,30 +102,40 @@ ShootEventTest::ShootEventTest() m_SystemPipeline->AddSystem(0); //The Test - //create entity which has transorm,player,model,health in it. i.e. is a player + //create entity which has transform,player,model,health in it. i.e. is a player EntityID playerID = m_World->CreateEntity(); - ComponentWrapper transform = m_World->AttachComponent(playerID, "Transform"); - ComponentWrapper model = m_World->AttachComponent(playerID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; - ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); + m_PlayerID = playerID; ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); - playersID = playerID; + ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); //attach 2x weaps ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); - ComponentWrapper& sItem= m_World->AttachComponent(playerID, "SecondaryItem"); - //set currentweap - player["EquippedItem"] = 1; - //set ammo set cooldown - pItem["Ammo"] = 100; - pItem["CoolDownTimer"] = 0.0f; + ComponentWrapper& sItem = m_World->AttachComponent(playerID, "SecondaryItem"); - //trigger event leftmousedown + m_RunTestNumber = runTestNumber; + switch (runTestNumber) + { + case 1: + TestSetup1(player, pItem, sItem); + break; + case 2: + TestSetup2(player, pItem, sItem); + break; + case 3: + TestSetup3(player, pItem, sItem); + break; + case 4: + TestSetup4(player, pItem, sItem); + break; + default: + break; + } + + //fire once = trigger event leftmousedown Events::MouseRelease eMouseRelease; eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; eMouseRelease.X = 1.0f; eMouseRelease.Y = 1.0f; m_EventBroker->Publish(eMouseRelease); - } ShootEventTest::~ShootEventTest() @@ -87,6 +145,77 @@ ShootEventTest::~ShootEventTest() delete m_EventBroker; } +void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + //set currentweap + player["EquippedItem"] = (double)1.0f; + //set ammo set cooldown + pItem["Ammo"] = (double)100.0f; + pItem["CoolDownTimer"] = (double)0.0f; +} +void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + //set currentweap + player["EquippedItem"] = (double)2.0f; + //set ammo set cooldown + sItem["Ammo"] = (double)10.0f; + sItem["CoolDownTimer"] = (double)0.0f; +} +void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + player["EquippedItem"] = (double)0.0f; + pItem["Ammo"] = (double)100.0f; + sItem["Ammo"] = (double)100.0f; + //TestSucceeded will be set to false if ammo changes during the 100 loops + TestSucceeded = true; +} +void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + //set currentweap + player["EquippedItem"] = (double)1.0f; + //set ammo set cooldown + pItem["Ammo"] = (double)100.0f; + pItem["CoolDownTimer"] = (double)5.0f; + //TestSucceeded will be set to false if ammo changes during the 100 loops + TestSucceeded = true; +} +void ShootEventTest::TestSuccess1() { + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo == (double)99) + TestSucceeded = true; +} +void ShootEventTest::TestSuccess2() { + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo == (double)9) + TestSucceeded = true; +} +void ShootEventTest::TestSuccess3() { + //try firing again + Events::MouseRelease eMouseRelease; + eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; + eMouseRelease.X = 1.0f; + eMouseRelease.Y = 1.0f; + m_EventBroker->Publish(eMouseRelease); + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + double currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo != (double)100 || currentAmmoSecondary != (double)100) + TestSucceeded = false; +} +void ShootEventTest::TestSuccess4() { + //try firing again + Events::MouseRelease eMouseRelease; + eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; + eMouseRelease.X = 1.0f; + eMouseRelease.Y = 1.0f; + m_EventBroker->Publish(eMouseRelease); + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo != (double)100) + TestSucceeded = false; +} void ShootEventTest::Tick() { glfwPollEvents(); @@ -101,8 +230,22 @@ void ShootEventTest::Tick() m_EventBroker->Swap(); m_EventBroker->Clear(); - //if ammocount reaches 99 we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = (int)m_World->GetComponent(playersID, "PrimaryItem")["Ammo"]; - if (currentAmmo ==99) - TestSucceeded = true; + switch (m_RunTestNumber) + { + case 1: + TestSuccess1(); + break; + case 2: + TestSuccess2(); + break; + case 3: + TestSuccess3(); + break; + case 4: + TestSuccess4(); + break; + default: + break; + } + } diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h index 49206ceb..0ffa1f91 100644 --- a/src/Tests/ShootEventTest.h +++ b/src/Tests/ShootEventTest.h @@ -4,20 +4,14 @@ #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" #include "Core/EventBroker.h" -#include "Rendering/Renderer.h" -#include "Core/InputManager.h" -#include "GUI/Frame.h" #include "Core/World.h" -#include "Rendering/RenderQueueFactory.h" #include "Input/InputProxy.h" #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" #include "Core/EntityXMLFile.h" #include "Core/SystemPipeline.h" -#include "RaptorCopterSystem.h" #include "PlayerSystem.h" -#include "Editor/EditorSystem.h" #include "Core\EMouseRelease.h" #include "Core\EShoot.h" @@ -25,19 +19,30 @@ class ShootEventTest { public: - ShootEventTest(); + ShootEventTest(int runTestNumber); ~ShootEventTest(); void Tick(); bool TestSucceeded = false; private: + void TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSuccess1(); + void TestSuccess2(); + void TestSuccess3(); + void TestSuccess4(); + double m_LastTime; ConfigFile* m_Config = nullptr; EventBroker* m_EventBroker; World* m_World; SystemPipeline* m_SystemPipeline; - int playersID; + int m_PlayerID; + int m_RunTestNumber; + }; #endif From 2cd0e94a6013b7bdc22e0f050fcd0fe37c7bf0d4 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 14:37:43 +0100 Subject: [PATCH 023/224] Changed the comparison method in PlayerSystem since its currently using doubles --- src/Game/PlayerSystem.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index e40469cc..2e2120d9 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -30,27 +30,27 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou double currentAmmo = (double)0; double currentCoolDownTimer = (double)0; - if ((double)player["EquippedItem"] == (double)1) { + if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); - currentAmmo = currentItem["Ammo"]; + currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if ((double)player["EquippedItem"] == (double)2) { + if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentAmmo = currentItem["Ammo"]; + currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } if (currentHealth > (double)0.0f && currentAmmo > (double)0.0f && currentCoolDownTimer < (double)0.001f) { //decrease ammo count //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if ((double)player["EquippedItem"] == (double)1) { + if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); currentItem["CoolDownTimer"] = (double)2; } - if ((double)player["EquippedItem"] == (double)2) { + if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); From 2f6261dfbf3aa7def43ae7f217f96673736fc71d Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 15:43:12 +0100 Subject: [PATCH 024/224] EShoot: changed to string weaponType to int currentlyEquippedItem PlayerSystem.h: added HeldItem enum PlayerSystem.cpp: simplified writing doubles, uses HeldItem enum ShootEventTest.cpp: simplified writing doubles --- include/Engine/Core/EShoot.h | 2 +- include/Game/PlayerSystem.h | 5 +++++ src/Game/PlayerSystem.cpp | 20 ++++++++++---------- src/Tests/ShootEventTest.cpp | 32 ++++++++++++++++---------------- 4 files changed, 32 insertions(+), 27 deletions(-) diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h index d9b9e20b..3887606b 100644 --- a/include/Engine/Core/EShoot.h +++ b/include/Engine/Core/EShoot.h @@ -12,7 +12,7 @@ struct Shoot : Event { //shotgun etc has different amounts of damage probably (a sniper shot might one-shot) //also different weapons will have different spread - std::string weaponType; + int currentlyEquippedItem; //currentAimingPoint must be sent, in case the camera is moved while the event is being processed glm::vec2 currentAimingPoint; }; diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 87dc6f5d..3544c63c 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -35,6 +35,11 @@ private: bool PlayerSystem::OnLeave(const Events::TriggerLeave &event); EventRelay m_MouseRelease; bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e); + enum class HeldItem { + None = 0, + PrimaryWeapon = 1, + SecondaryWeapon = 2 + }; }; #endif \ No newline at end of file diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index 2e2120d9..ca39ed4f 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -27,39 +27,39 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou leftMouseWasReleased = false; //get the health component linked to the playerId double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; - double currentAmmo = (double)0; - double currentCoolDownTimer = (double)0; + double currentAmmo = 0.0; + double currentCoolDownTimer = 0.0; - if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (currentHealth > (double)0.0f && currentAmmo > (double)0.0f && currentCoolDownTimer < (double)0.001f) { + if (currentHealth > 0.0 && currentAmmo > 0.0 && currentCoolDownTimer < 0.001) { //decrease ammo count //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); - currentItem["CoolDownTimer"] = (double)2; + currentItem["CoolDownTimer"] = 2.0;//change later! } - if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); - currentItem["CoolDownTimer"] = (double)2; + currentItem["CoolDownTimer"] = 2.0;//change later! } //create and publish the shoot event Events::Shoot eShoot; eShoot.currentAimingPoint = aimingCoordinates; - eShoot.weaponType = (int)player["EquippedItem"]; + eShoot.currentlyEquippedItem = (int) ((double)player["EquippedItem"]); m_EventBroker->Publish(eShoot); } } diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index 22c2a0eb..67a9985e 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -148,47 +148,47 @@ ShootEventTest::~ShootEventTest() void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = (double)1.0f; + player["EquippedItem"] = 1.0; //set ammo set cooldown - pItem["Ammo"] = (double)100.0f; - pItem["CoolDownTimer"] = (double)0.0f; + pItem["Ammo"] = 100.0; + pItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = (double)2.0f; + player["EquippedItem"] = 2.0; //set ammo set cooldown - sItem["Ammo"] = (double)10.0f; - sItem["CoolDownTimer"] = (double)0.0f; + sItem["Ammo"] = 10.0; + sItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { - player["EquippedItem"] = (double)0.0f; - pItem["Ammo"] = (double)100.0f; - sItem["Ammo"] = (double)100.0f; + player["EquippedItem"] = 0.0; + pItem["Ammo"] = 100.0; + sItem["Ammo"] = 100.0; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = (double)1.0f; + player["EquippedItem"] = 1.0; //set ammo set cooldown - pItem["Ammo"] = (double)100.0f; - pItem["CoolDownTimer"] = (double)5.0f; + pItem["Ammo"] = 100.0; + pItem["CoolDownTimer"] = 5.0; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSuccess1() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo == (double)99) + if (currentAmmo == 99.0) TestSucceeded = true; } void ShootEventTest::TestSuccess2() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo == (double)9) + if (currentAmmo == 9.0) TestSucceeded = true; } void ShootEventTest::TestSuccess3() { @@ -201,7 +201,7 @@ void ShootEventTest::TestSuccess3() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; double currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo != (double)100 || currentAmmoSecondary != (double)100) + if (currentAmmo != 100.0 || currentAmmoSecondary != 100.0) TestSucceeded = false; } void ShootEventTest::TestSuccess4() { @@ -213,7 +213,7 @@ void ShootEventTest::TestSuccess4() { m_EventBroker->Publish(eMouseRelease); //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo != (double)100) + if (currentAmmo != 100.0) TestSucceeded = false; } void ShootEventTest::Tick() From 0cc58f088a6126abd1f72191411f688c7944cd9c Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 17:15:49 +0100 Subject: [PATCH 025/224] EquippedItem,Ammo got changed to int instead of double. Loading entities from map the new way in Tests. ComponentWrapper:s Name is now Type --- include/Engine/Core/ComponentWrapper.h | 2 +- include/Game/PlayerSystem.h | 4 +- resources/Schema/Components/Player.xsd | 2 +- resources/Schema/Components/PrimaryItem.xsd | 2 +- resources/Schema/Components/SecondaryItem.xsd | 2 +- src/Game/PlayerSystem.cpp | 22 ++++---- src/Tests/HealthSystemTest.cpp | 9 +++- src/Tests/HealthSystemTest.h | 2 +- src/Tests/OctTreeTestGameClass.cpp | 2 +- src/Tests/OctTreeTestGameClass.h | 2 +- src/Tests/ResourceManagerTest.cpp | 1 - src/Tests/ShootEventTest.cpp | 53 ++++++++++--------- src/Tests/ShootEventTest.h | 6 ++- 13 files changed, 60 insertions(+), 49 deletions(-) diff --git a/include/Engine/Core/ComponentWrapper.h b/include/Engine/Core/ComponentWrapper.h index 922b3d79..f4761e40 100644 --- a/include/Engine/Core/ComponentWrapper.h +++ b/include/Engine/Core/ComponentWrapper.h @@ -78,7 +78,7 @@ public: void AddProperty(std::string fieldName, T defaultValue) { m_DefaultValues.push_back(defaultValue); - m_ComponentInfo.Fields[fieldName].Name = typeid(T).name(); + m_ComponentInfo.Fields[fieldName].Type = typeid(T).name(); m_ComponentInfo.Fields[fieldName].Offset = m_ComponentInfo.Meta.Stride; m_ComponentInfo.Fields[fieldName].Stride = sizeof(T); m_ComponentInfo.Meta.Stride += sizeof(T); diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 3544c63c..897ee207 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -37,8 +37,8 @@ private: bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e); enum class HeldItem { None = 0, - PrimaryWeapon = 1, - SecondaryWeapon = 2 + PrimaryItem = 1, + SecondaryItem = 2 }; }; diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 9ffc28b0..617b7d30 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -14,7 +14,7 @@ - + diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd index bbff122d..35e2fca6 100644 --- a/resources/Schema/Components/PrimaryItem.xsd +++ b/resources/Schema/Components/PrimaryItem.xsd @@ -9,7 +9,7 @@ - + Ammo count diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd index ab428920..bee25541 100644 --- a/resources/Schema/Components/SecondaryItem.xsd +++ b/resources/Schema/Components/SecondaryItem.xsd @@ -9,7 +9,7 @@ - + Ammo count diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index ca39ed4f..dff5c410 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -27,33 +27,31 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou leftMouseWasReleased = false; //get the health component linked to the playerId double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; - double currentAmmo = 0.0; + int currentAmmo = 0; double currentCoolDownTimer = 0.0; - if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); - currentAmmo = (double)currentItem["Ammo"]; + currentAmmo = (int)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentAmmo = (double)currentItem["Ammo"]; + currentAmmo = (int)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (currentHealth > 0.0 && currentAmmo > 0.0 && currentCoolDownTimer < 0.001) { + if (currentHealth > 0.0 && currentAmmo > 0 && currentCoolDownTimer < 0.001) { //decrease ammo count //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); - int currentAmmoInt = (int)((double)currentItem["Ammo"]); - currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; currentItem["CoolDownTimer"] = 2.0;//change later! } - if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - int currentAmmoInt = (int)((double)currentItem["Ammo"]); - currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; currentItem["CoolDownTimer"] = 2.0;//change later! } //create and publish the shoot event diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index 84d6199d..feab858a 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -30,7 +30,7 @@ BOOST_AUTO_TEST_SUITE_END() GameHealthSystemTest::GameHealthSystemTest() { ResourceManager::RegisterType("ConfigFile"); - ResourceManager::RegisterType("EntityXMLFile"); + ResourceManager::RegisterType("EntityFile"); m_Config = ResourceManager::Load("Config.ini"); LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); @@ -41,8 +41,13 @@ GameHealthSystemTest::GameHealthSystemTest() // Create a world m_World = new World(); std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); + if (!mapToLoad.empty()) { - ResourceManager::Load(mapToLoad)->PopulateWorld(m_World); + auto file = ResourceManager::Load(mapToLoad); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(m_World); + EntityFileParser fp(file); + fp.MergeEntities(m_World); } // Create system pipeline diff --git a/src/Tests/HealthSystemTest.h b/src/Tests/HealthSystemTest.h index 664d2ef3..2890dfc1 100644 --- a/src/Tests/HealthSystemTest.h +++ b/src/Tests/HealthSystemTest.h @@ -13,7 +13,7 @@ #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" -#include "Core/EntityXMLFile.h" +#include "Core/EntityFile.h" #include "Core/SystemPipeline.h" #include "RaptorCopterSystem.h" #include "PlayerSystem.h" diff --git a/src/Tests/OctTreeTestGameClass.cpp b/src/Tests/OctTreeTestGameClass.cpp index 10d4d6a5..0f195cec 100644 --- a/src/Tests/OctTreeTestGameClass.cpp +++ b/src/Tests/OctTreeTestGameClass.cpp @@ -5,7 +5,7 @@ Game::Game(int argc, char* argv[]) : someOctTree(AABB(-0.5f*worldSize, 0.5f*worl ResourceManager::RegisterType("ConfigFile"); ResourceManager::RegisterType("Model"); ResourceManager::RegisterType("Texture"); - ResourceManager::RegisterType("EntityXMLFile"); + ResourceManager::RegisterType("EntityFile"); ResourceManager::RegisterType("ShaderProgram"); m_Config = ResourceManager::Load("Config.ini"); diff --git a/src/Tests/OctTreeTestGameClass.h b/src/Tests/OctTreeTestGameClass.h index 6dc9404e..c36707c8 100644 --- a/src/Tests/OctTreeTestGameClass.h +++ b/src/Tests/OctTreeTestGameClass.h @@ -13,7 +13,7 @@ #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" -#include "Core/EntityXMLFile.h" +#include "Core/EntityFile.h" #include "Core/SystemPipeline.h" #include "RaptorCopterSystem.h" #include "PlayerSystem.h" diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index a3edb7b8..9d62fa93 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -7,7 +7,6 @@ #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" #include "Rendering/Renderer.h" -#include "Core/EntityXMLFile.h" #include "Engine\Rendering\Texture.h" BOOST_AUTO_TEST_SUITE(resourceManagerTests) diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index 67a9985e..f24bfed8 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -81,9 +81,10 @@ BOOST_AUTO_TEST_SUITE_END() ShootEventTest::ShootEventTest(int runTestNumber) { ResourceManager::RegisterType("ConfigFile"); - ResourceManager::RegisterType("EntityXMLFile"); + ResourceManager::RegisterType("EntityFile"); m_Config = ResourceManager::Load("Config.ini"); + std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); // Create the core event broker @@ -91,22 +92,26 @@ ShootEventTest::ShootEventTest(int runTestNumber) // Create a world m_World = new World(); - std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); - if (!mapToLoad.empty()) { - ResourceManager::Load(mapToLoad)->PopulateWorld(m_World); - } // Create system pipeline m_SystemPipeline = new SystemPipeline(m_EventBroker); m_SystemPipeline->AddSystem(0); m_SystemPipeline->AddSystem(0); + if (!mapToLoad.empty()) { + auto file = ResourceManager::Load(mapToLoad); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(m_World); + EntityFileParser fp(file); + fp.MergeEntities(m_World); + } + //The Test //create entity which has transform,player,model,health in it. i.e. is a player EntityID playerID = m_World->CreateEntity(); m_PlayerID = playerID; - ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); + ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); //attach 2x weaps ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); ComponentWrapper& sItem = m_World->AttachComponent(playerID, "SecondaryItem"); @@ -148,47 +153,47 @@ ShootEventTest::~ShootEventTest() void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = 1.0; + player["EquippedItem"] = 1; //set ammo set cooldown - pItem["Ammo"] = 100.0; + pItem["Ammo"] = 100; pItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = 2.0; + player["EquippedItem"] = 2; //set ammo set cooldown - sItem["Ammo"] = 10.0; + sItem["Ammo"] = 10; sItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { - player["EquippedItem"] = 0.0; - pItem["Ammo"] = 100.0; - sItem["Ammo"] = 100.0; + player["EquippedItem"] = 0; + pItem["Ammo"] = 100; + sItem["Ammo"] = 100; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = 1.0; + player["EquippedItem"] = 1; //set ammo set cooldown - pItem["Ammo"] = 100.0; + pItem["Ammo"] = 100; pItem["CoolDownTimer"] = 5.0; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSuccess1() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo == 99.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo == 99) TestSucceeded = true; } void ShootEventTest::TestSuccess2() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo == 9.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo == 9) TestSucceeded = true; } void ShootEventTest::TestSuccess3() { @@ -199,9 +204,9 @@ void ShootEventTest::TestSuccess3() { eMouseRelease.Y = 1.0f; m_EventBroker->Publish(eMouseRelease); //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - double currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo != 100.0 || currentAmmoSecondary != 100.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + int currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo != 100 || currentAmmoSecondary != 100) TestSucceeded = false; } void ShootEventTest::TestSuccess4() { @@ -212,8 +217,8 @@ void ShootEventTest::TestSuccess4() { eMouseRelease.Y = 1.0f; m_EventBroker->Publish(eMouseRelease); //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo != 100.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo != 100) TestSucceeded = false; } void ShootEventTest::Tick() diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h index 0ffa1f91..21ae7d9e 100644 --- a/src/Tests/ShootEventTest.h +++ b/src/Tests/ShootEventTest.h @@ -9,10 +9,14 @@ #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" -#include "Core/EntityXMLFile.h" +#include "Core/EntityFile.h" #include "Core/SystemPipeline.h" #include "PlayerSystem.h" +#include "Core/EntityFilePreprocessor.h" +#include "Core/EntityFileParser.h" +#include "Core/EntityFileWriter.h" + #include "Core\EMouseRelease.h" #include "Core\EShoot.h" From 774bb8ce56ba5a18afaa9dab01d680e308fe42d9 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 17:36:23 +0100 Subject: [PATCH 026/224] Simplified PlayerSystem branches a lot! Thanks William! --- src/Game/PlayerSystem.cpp | 38 +++++++++++++++----------------------- 1 file changed, 15 insertions(+), 23 deletions(-) diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index dff5c410..c9112b01 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -29,36 +29,28 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; int currentAmmo = 0; double currentCoolDownTimer = 0.0; + std::string HeldItemString = ""; + if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) + HeldItemString = "PrimaryItem"; + if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) + HeldItemString = "SecondaryItem"; - if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + if (HeldItemString != "") { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, HeldItemString); currentAmmo = (int)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; - } - if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentAmmo = (int)currentItem["Ammo"]; - currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; - } - if (currentHealth > 0.0 && currentAmmo > 0 && currentCoolDownTimer < 0.001) { - //decrease ammo count - //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + if (currentHealth > 0.0 && currentAmmo > 0 && currentCoolDownTimer < 0.001) { + //decrease ammo count + //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; currentItem["CoolDownTimer"] = 2.0;//change later! + //create and publish the shoot event + Events::Shoot eShoot; + eShoot.currentAimingPoint = aimingCoordinates; + eShoot.currentlyEquippedItem = (int)(player["EquippedItem"]); + m_EventBroker->Publish(eShoot); } - if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; - currentItem["CoolDownTimer"] = 2.0;//change later! - } - //create and publish the shoot event - Events::Shoot eShoot; - eShoot.currentAimingPoint = aimingCoordinates; - eShoot.currentlyEquippedItem = (int) ((double)player["EquippedItem"]); - m_EventBroker->Publish(eShoot); } } } From a20ca49d5327c70838ed76bba430f5d837f4cba6 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Tue, 12 Jan 2016 10:46:34 +0100 Subject: [PATCH 027/224] Fixed typo backslash instead of slash in various classes (the includes) --- include/Game/HealthSystem.h | 6 +++--- include/Game/PlayerSystem.h | 4 ++-- src/Tests/CollisionTest.cpp | 6 +++--- src/Tests/ConfigFileTest.cpp | 2 +- src/Tests/EventFixture.h | 2 +- src/Tests/InputManagerTest.cpp | 2 +- src/Tests/OctTreeTestAnders.cpp | 2 +- src/Tests/OctTreeTestHardCodedTestWorld.h | 2 +- src/Tests/ResourceManagerTest.cpp | 2 +- src/Tests/ShootEventTest.h | 4 ++-- 10 files changed, 16 insertions(+), 16 deletions(-) diff --git a/include/Game/HealthSystem.h b/include/Game/HealthSystem.h index a836e797..11ac68bd 100644 --- a/include/Game/HealthSystem.h +++ b/include/Game/HealthSystem.h @@ -6,9 +6,9 @@ #include "Common.h" #include "Core/System.h" -#include "Core\EPlayerDamage.h"; -#include "Core\EPlayerHealthPickup.h"; -#include "Core\EPlayerDeath.h"; +#include "Core/EPlayerDamage.h"; +#include "Core/EPlayerHealthPickup.h"; +#include "Core/EPlayerDeath.h"; #include #include diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 897ee207..a48af3e4 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -7,8 +7,8 @@ #include "Common.h" #include "Core/System.h" #include "Collision/ETrigger.h" -#include "Core\EMouseRelease.h" -#include "Core\EShoot.h" +#include "Core/EMouseRelease.h" +#include "Core/EShoot.h" class PlayerSystem : public PureSystem { diff --git a/src/Tests/CollisionTest.cpp b/src/Tests/CollisionTest.cpp index e6a29298..57329477 100644 --- a/src/Tests/CollisionTest.cpp +++ b/src/Tests/CollisionTest.cpp @@ -13,9 +13,9 @@ using boost::unit_test_framework::test_case; #include //ray vs model -#include "Engine\Core\ResourceManager.h" -#include "Engine\Rendering\Model.h" -#include "Engine\Core\Ray.h" +#include "Engine/Core/ResourceManager.h" +#include "Engine/Rendering/Model.h" +#include "Engine/Core/Ray.h" //vs memleaks //#define _CRTDBG_MAP_ALLOC diff --git a/src/Tests/ConfigFileTest.cpp b/src/Tests/ConfigFileTest.cpp index 28be5589..36cd6c05 100644 --- a/src/Tests/ConfigFileTest.cpp +++ b/src/Tests/ConfigFileTest.cpp @@ -5,7 +5,7 @@ using boost::unit_test_framework::test_case; #include //srand //#define private public -#include "Engine\Core\ConfigFile.h" +#include "Engine/Core/ConfigFile.h" #define _CRTDBG_MAP_ALLOC #include diff --git a/src/Tests/EventFixture.h b/src/Tests/EventFixture.h index 42258932..a708b962 100644 --- a/src/Tests/EventFixture.h +++ b/src/Tests/EventFixture.h @@ -2,7 +2,7 @@ #define EVENTFIXTURE_H #include -#include "Core\EventBroker.h" +#include "Core/EventBroker.h" template struct EventFixture diff --git a/src/Tests/InputManagerTest.cpp b/src/Tests/InputManagerTest.cpp index 5b447c2b..0ef9434a 100644 --- a/src/Tests/InputManagerTest.cpp +++ b/src/Tests/InputManagerTest.cpp @@ -1,6 +1,6 @@ #include -#include "Engine\Core\InputManager.h" +#include "Engine/Core/InputManager.h" BOOST_AUTO_TEST_SUITE(inputManagerTests) diff --git a/src/Tests/OctTreeTestAnders.cpp b/src/Tests/OctTreeTestAnders.cpp index b61caead..477ccbf4 100644 --- a/src/Tests/OctTreeTestAnders.cpp +++ b/src/Tests/OctTreeTestAnders.cpp @@ -15,7 +15,7 @@ using boost::unit_test_framework::test_case; #include "OctTreeTestGameClass.h" #define private public//HACK! Needed for white box testing -#include +#include "Engine/Core/OctTree.h" //else we would have to "open up" the octTree class more with get/sets, public methods, etc. which is not good encapsulation-wise BOOST_AUTO_TEST_SUITE(octTreeTestsA) diff --git a/src/Tests/OctTreeTestHardCodedTestWorld.h b/src/Tests/OctTreeTestHardCodedTestWorld.h index 512716df..6f68eba6 100644 --- a/src/Tests/OctTreeTestHardCodedTestWorld.h +++ b/src/Tests/OctTreeTestHardCodedTestWorld.h @@ -9,7 +9,7 @@ //last! //#include "OldOctTree.h" #define private public -#include +#include class HardcodedTestWorld : public World { diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index 9d62fa93..b68936ec 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -7,7 +7,7 @@ #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" #include "Rendering/Renderer.h" -#include "Engine\Rendering\Texture.h" +#include "Engine/Rendering/Texture.h" BOOST_AUTO_TEST_SUITE(resourceManagerTests) diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h index 21ae7d9e..e860f41f 100644 --- a/src/Tests/ShootEventTest.h +++ b/src/Tests/ShootEventTest.h @@ -17,8 +17,8 @@ #include "Core/EntityFileParser.h" #include "Core/EntityFileWriter.h" -#include "Core\EMouseRelease.h" -#include "Core\EShoot.h" +#include "Core/EMouseRelease.h" +#include "Core/EShoot.h" class ShootEventTest { From 7b62dc19bf0e5f85ec1dc7dc2f3d69a0d18d22ef Mon Sep 17 00:00:00 2001 From: antc13 Date: Tue, 12 Jan 2016 15:39:29 +0100 Subject: [PATCH 028/224] Spitting out Meshes & Animation Data to file. --- .../MayaExporter/MayaExporter.vcxproj | 1 + .../MayaExporter/MayaExporter/MayaIncludes.h | 5 + tools/MayaExporter/MayaExporter/Menu.cpp | 46 +++-- tools/MayaExporter/MayaExporter/Menu.h | 1 + tools/MayaExporter/MayaExporter/Mesh.cpp | 193 +++++++++++++----- tools/MayaExporter/MayaExporter/Mesh.h | 53 ++++- tools/MayaExporter/MayaExporter/WriteToFile.h | 16 +- 7 files changed, 242 insertions(+), 73 deletions(-) diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index a9154ac7..701b39cf 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -140,6 +140,7 @@ MultiThreadedDLL true + Disabled Windows diff --git a/tools/MayaExporter/MayaExporter/MayaIncludes.h b/tools/MayaExporter/MayaExporter/MayaIncludes.h index 0e490208..66527470 100644 --- a/tools/MayaExporter/MayaExporter/MayaIncludes.h +++ b/tools/MayaExporter/MayaExporter/MayaIncludes.h @@ -37,6 +37,11 @@ #include #include #include +#include +#include +#include +#include +#include // Wrappers diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 77241cad..7e1e6cde 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -125,8 +125,7 @@ void Menu::ExportSelected(bool checked) MFnDependencyNode thisNode(object); cout << thisNode.name().asChar() << endl; - Mesh mesh; - mesh.GetMeshData(object); + GetMeshData(object); } if (m_ExportPath->text().isEmpty()) { cout << "Please select a folder." << endl; @@ -195,17 +194,32 @@ void Menu::RemoveClipClicked(bool) void Menu::ExportAll(bool) { MDagPath path; + m_File.ASCIIFilePath("C:/Users/Nickelodion/Desktop/coolASCII.txt"); + m_File.binaryFilePath("C:/Users/Nickelodion/Desktop/coolSoptunz.bin"); + m_File.OpenFiles(); // Loop through all nodes in the scene - MItDependencyNodes it(MFn::kInvalid); + MItDependencyNodes it(MFn::kMesh); for (; !it.isDone(); it.next()) { MObject node = it.thisNode(); if (node.hasFn(MFn::kMesh)) { MFnDependencyNode thisNode(node); + MPlugArray connections; - cout << thisNode.name().asChar() << endl; - Mesh mesh; - mesh.GetMeshData(node); + thisNode.findPlug("inMesh").connectedTo(connections, true, true); + bool next = false; + for (unsigned int i = 0; i < connections.length(); i++) { + if(connections[i].node().apiType() == MFn::kSkinClusterFilter){ + next = true; + break; + } + } + if (next) + continue; + + cout << thisNode.name().asChar() << endl; + MGlobal::displayInfo("EXPORT ALL FUNCTION: " + thisNode.name() + " " + thisNode.findPlug("inMesh").asMObject().apiTypeStr()); + GetMeshData(node); } } if (m_ExportPath->text().isEmpty()) { @@ -215,12 +229,9 @@ void Menu::ExportAll(bool) cout << m_ExportPath->text().toLocal8Bit().constData() << endl; } - m_File.ASCIIFilePath("C:/Users/Nickelodion/Desktop/coolASCII.txt"); - m_File.binaryFilePath("C:/Users/Nickelodion/Desktop/coolSoptunz.bin"); - if (m_ExportAnimationsButton->isChecked()) GetSkeletonData(); - + m_File.CloseFiles(); } void Menu::CancelClicked(bool) @@ -257,7 +268,19 @@ void Menu::Button3Clicked(bool) cout << "3 unchecked!" << endl; } } +void Menu::GetMeshData(MObject object) +{ + std::vector vertexList; + std::vector indexList; + Mesh mesh; + mesh.GetMeshData(object, vertexList, indexList); + + for (auto aVertex : vertexList) { + m_File.writeToFiles(&aVertex); + } + m_File.writeToFiles(indexList.data(), indexList.size()); +} void Menu::GetMaterialData() { this->m_MaterialHandler = new Material(); @@ -296,8 +319,6 @@ void Menu::GetSkeletonData() allAnimations.push_back(m_SkeletonHandler->GetAnimData(animationName, startFrame, endFrame)); } - m_File.OpenFiles(); - //print out all bind poses for (auto aBindPose : allBindPoses){ m_File.writeToFiles(&aBindPose); @@ -315,7 +336,6 @@ void Menu::GetSkeletonData() for (auto aAnimation : allAnimations) { m_File.writeToFiles(&aAnimation); } - m_File.CloseFiles(); } Menu::~Menu() diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index 0174cbc3..9f3492ab 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -46,6 +46,7 @@ public: Menu(QDialog* dialog); ~Menu(); + void GetMeshData(MObject object); void GetMaterialData(); void GetSkeletonData(); diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index 58a7fbe4..0ac66b33 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -7,21 +7,80 @@ Mesh::Mesh() { } +std::map Mesh::GetWeightData() +{ + map weightMap; -void Mesh::GetMeshData(MObject object) + MItDependencyNodes it(MFn::kSkinClusterFilter); + + while (!it.isDone()) { + + MObject object = it.item(); + MFnSkinCluster skinCluster(object); + MDagPathArray influences; + + unsigned int nrOfInfluences = skinCluster.influenceObjects(influences); + + unsigned int index; + index = skinCluster.indexForOutputConnection(0); + MDagPath skinPath; + skinCluster.getPathAtIndex(index, skinPath); + + MItGeometry geomIter(skinPath); + //for (unsigned int i = 0; i < nrOfInfluences; i++) { + // MGlobal::displayInfo(MString() + " Influence object name: " + influences[i].partialPathName().asChar()); + //} + WeightInfo weightInfo; + + while (!geomIter.isDone()) { + MObject comp = geomIter.component(); + MFloatArray weights; + unsigned int influenceCount; + skinCluster.getWeights(skinPath, comp, weights, influenceCount); + MFnDependencyNode test(comp); + + unsigned int nrOfWeights = 0; + + for (unsigned int j = 0; j < weights.length() && nrOfWeights != 4; j++) { + if (weights[j] > 0.00001) { + weightInfo.BoneWeights[nrOfWeights] = weights[j]; + weightInfo.BoneIndices[nrOfWeights] = j; + nrOfWeights++; + } + } + + float totalWeight = 0.0f; + for (unsigned int i = 0; i < 4; i++) { + totalWeight += weightInfo.BoneWeights[i]; + } + for (unsigned int i = 0; i < 4; i++) { + weightInfo.BoneWeights[i] /= totalWeight; + } + weightMap[geomIter.index()] = weightInfo; + + + for (unsigned int k = 0; k!=nrOfWeights; k++) { + //MGlobal::displayInfo(MString() + "influence: " + weightInfo.BoneIndices[k] + " weight: " + weightInfo.BoneWeights[k]); + } + geomIter.next(); + + + } + + it.next(); + } + return weightMap; +} + +void Mesh::GetMeshData(MObject object, std::vector& vertexList, std::vector& indexList) { // In here, we retrieve triangulated polygons from the mesh MFnMesh mesh(object); - - map> vertexToIndex; - - vector verticesData; - vectorindexArray; + map> vertexToIndex;; MIntArray intdexOffsetVertexCount, vertices, triangleList; MPointArray dummy; - - UINT vertexIndex; + unsigned int vertexIndex; MVector normal; MPoint pos; float2 UV; @@ -31,62 +90,92 @@ void Mesh::GetMeshData(MObject object) MFloatVectorArray biTangents; MFloatVectorArray biNormals; + std::map vertexWeights = GetWeightData(); + mesh.getTangents(biTangents, MSpace::kObject, NULL); mesh.getBinormals(biNormals, MSpace::kObject, NULL); MItMeshFaceVertex faceVert(object); + int intDummy = 0; - for (MItMeshPolygon meshPolyIter(object); !meshPolyIter.isDone(); meshPolyIter.next()) { - vector localVertexToGlobalIndex; - meshPolyIter.getVertices(vertices); - meshPolyIter.getTriangles(dummy, triangleList); - UINT indexOffset = verticesData.size(); - //MGlobal::displayInfo("Befor Second Loop"); - for (UINT i = 0; i < vertices.length(); i++) { - faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); - //MGlobal::displayInfo("In Second Loop"); - faceVert.position().get(thisVertex.Pos); - faceVert.getNormal(normal); - thisVertex.Normal[0] = normal[0]; - thisVertex.Normal[1] = normal[1]; - thisVertex.Normal[2] = normal[2]; + for (MItMeshPolygon meshPolyIter(object); !meshPolyIter.isDone(); meshPolyIter.next()) { - MFloatVector biTangent = biTangents[faceVert.tangentId()]; - //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); - //tmp.get(biTangent); - thisVertex.BiTangent[0] = biTangent[0]; - thisVertex.BiTangent[1] = biTangent[1]; - thisVertex.BiTangent[2] = biTangent[2]; + vector localVertexToGlobalIndex; + unsigned int indexOffset = vertexList.size(); - MFloatVector biNormal = biNormals[faceVert.tangentId()]; - //faceVert.getBinormal().get(biNormal); - thisVertex.BiNormal[0] = biNormal[0]; - thisVertex.BiNormal[1] = biNormal[1]; - thisVertex.BiNormal[2] = biNormal[2]; + meshPolyIter.getVertices(vertices); + meshPolyIter.getTriangles(dummy, triangleList); + MGlobal::displayInfo(MString() + "vertices.length(): " + vertices.length()); + //MGlobal::displayInfo("Befor Second Loop"); + for (unsigned int i = 0; i < vertices.length(); i++) { + vertexIndex = meshPolyIter.vertexIndex(i); + faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); + //MGlobal::displayInfo("In Second Loop"); + faceVert.position().get(thisVertex.Pos); + faceVert.getNormal(normal); + thisVertex.Normal[0] = normal[0]; + thisVertex.Normal[1] = normal[1]; + thisVertex.Normal[2] = normal[2]; - faceVert.getUV(UV); - thisVertex.Uv[0] = UV[0]; - thisVertex.Uv[1] = UV[1]; + MFloatVector biTangent = biTangents[faceVert.tangentId()]; + //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); + //tmp.get(biTangent); + thisVertex.BiTangent[0] = biTangent[0]; + thisVertex.BiTangent[1] = biTangent[1]; + thisVertex.BiTangent[2] = biTangent[2]; - verticesData.push_back(thisVertex); - localVertexToGlobalIndex.push_back(vertexIndex); + MFloatVector biNormal = biNormals[faceVert.tangentId()]; + //faceVert.getBinormal().get(biNormal); + thisVertex.BiNormal[0] = biNormal[0]; + thisVertex.BiNormal[1] = biNormal[1]; + thisVertex.BiNormal[2] = biNormal[2]; - //cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; - //cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; - //cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; - //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; - //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; - } - //MGlobal::displayInfo("Befor Third Loop"); + faceVert.getUV(UV); + thisVertex.Uv[0] = UV[0]; + thisVertex.Uv[1] = UV[1]; - //for (UINT i = 0; i < triangleList.length(); i++) { - // UINT k = 0; - // while (localVertexToGlobalIndex[k] != triangleList[i]) - // k++; - // indexArray.push_back(indexOffset + k); - //} - } + thisVertex.BoneIndices[0] = vertexWeights[faceVert.vertId()].BoneIndices[0]; + thisVertex.BoneIndices[1] = vertexWeights[faceVert.vertId()].BoneIndices[1]; + thisVertex.BoneIndices[2] = vertexWeights[faceVert.vertId()].BoneIndices[2]; + thisVertex.BoneIndices[3] = vertexWeights[faceVert.vertId()].BoneIndices[3]; + + thisVertex.BoneWeights[0] = vertexWeights[faceVert.vertId()].BoneWeights[0]; + thisVertex.BoneWeights[1] = vertexWeights[faceVert.vertId()].BoneWeights[1]; + thisVertex.BoneWeights[2] = vertexWeights[faceVert.vertId()].BoneWeights[2]; + thisVertex.BoneWeights[3] = vertexWeights[faceVert.vertId()].BoneWeights[3]; + + std::vector::iterator it = std::find(vertexList.begin(), vertexList.end(), thisVertex); + + if (it != vertexList.end()) { + localVertexToGlobalIndex.push_back(vertexIndex); + } else { + localVertexToGlobalIndex.push_back(vertexIndex); + vertexList.push_back(thisVertex); + } + + //cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; + //cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; + //cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; + //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; + //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; + } + //MGlobal::displayInfo("Befor Third Loop"); + MGlobal::displayInfo(MString() + "localVertexToGlobalIndex.size(): " + localVertexToGlobalIndex.size()); + MGlobal::displayInfo(MString() + "vertexList.size(): " + vertexList.size()); + + for (unsigned int i = 0; i < triangleList.length(); i++) { + unsigned int k = 0; + MGlobal::displayInfo(MString() + "triangleList[i]: " + triangleList[i]); + if (localVertexToGlobalIndex.size() > 0) { + while (localVertexToGlobalIndex[k] != triangleList[i] && k < localVertexToGlobalIndex.size()) { + MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k]: " + localVertexToGlobalIndex[k]); + k++; + } + indexList.push_back(indexOffset + k); + } + } + } } Mesh::~Mesh() diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h index 00b88654..6fab0536 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.h +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -16,21 +16,62 @@ public: float BiNormal[3]; float BiTangent[3]; float Uv[2]; + float BoneIndices[4]; + float BoneWeights[4]; - virtual void WriteBinary(std::ostream& out) { + virtual void WriteBinary(std::ostream& out) + { + out.write((char*)&Pos, sizeof(float) * 3); + out.write((char*)&Normal, sizeof(float) * 3); + out.write((char*)&BiNormal, sizeof(float) * 3); + out.write((char*)&BiTangent, sizeof(float) * 3); + out.write((char*)&Uv, sizeof(float) * 2); + out.write((char*)&BoneIndices, sizeof(float) * 4); + out.write((char*)&BoneWeights, sizeof(float) * 4); + } - } - virtual void WriteASCII(std::ostream& out) const { + virtual void WriteASCII(std::ostream& out) const + { + out << "New Vertex: " << endl; + out << Pos[0] << " " << Pos[1] << " " << Pos[2] << endl; + out << Normal[0] << " " << Normal[1] << " " << Normal[2] << endl; + out << BiNormal[0] << " " << BiNormal[1] << " " << BiNormal[2] << endl; + out << BiTangent[0] << " " << BiTangent[1] << " " << BiTangent[2] << endl; + out << Uv[0] << " " << Uv[1] << endl; + out << BoneIndices[0] << " " << BoneIndices[1] << " " << BoneIndices[2] << " " << BoneIndices[3] << endl; + out << BoneWeights[0] << " " << BoneWeights[1] << " " << BoneWeights[2] << " " << BoneWeights[3] << endl; - } + } + bool operator==(const VertexLayout& right) + { + return + this->Pos[0] == right.Pos[0] && this->Pos[1] == right.Pos[1] && this->Pos[2] == right.Pos[2] && + this->Normal[0] == right.Normal[0] && this->Normal[1] == right.Normal[1] && this->Normal[2] == right.Normal[2] && + this->BiNormal[0] == right.BiNormal[0] && this->BiNormal[1] == right.BiNormal[1] && this->BiNormal[2] == right.BiNormal[2] && + this->BiTangent[0] == right.BiTangent[0] && this->BiTangent[1] == right.BiTangent[1] && this->BiTangent[2] == right.BiTangent[2] && + this->Uv[0] == right.Uv[0] && this->Uv[1] == right.Uv[1] && + this->BoneIndices[0] == right.BoneIndices[0] && this->BoneIndices[1] == right.BoneIndices[1] && this->BoneIndices[2] == right.BoneIndices[2] && this->BoneIndices[3] == right.BoneIndices[3] && + this->BoneWeights[0] == right.BoneWeights[0] && this->BoneWeights[1] == right.BoneWeights[1] && this->BoneWeights[2] == right.BoneWeights[2] && this->BoneWeights[3] == right.BoneWeights[3] + ; + } }; + + + class Mesh { public: Mesh(); - void GetMeshData(MObject Object); - ~Mesh(); + void GetMeshData(MObject Object, std::vector& vertexList, std::vector& indexList); + ~Mesh(); +private: + struct WeightInfo { + float BoneIndices[4] = { 0 }; + float BoneWeights[4] = { 0 }; + }; + std::map GetWeightData(); + }; #endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/WriteToFile.h b/tools/MayaExporter/MayaExporter/WriteToFile.h index f0c066d4..3d6cc078 100644 --- a/tools/MayaExporter/MayaExporter/WriteToFile.h +++ b/tools/MayaExporter/MayaExporter/WriteToFile.h @@ -20,20 +20,32 @@ public: MGlobal::displayInfo("WriteToFile::writeToFiles()"); if (ASCIIFile.is_open()) { - MGlobal::displayInfo("Writing to ASCIIfile"); for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) ASCIIFile << toWrite[i] << endl; } if (binFile.is_open()) { - MGlobal::displayInfo("Writing to binaryfile"); for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) toWrite[i].WriteBinary(binFile); } } + void writeToFiles(unsigned int* toWrite, unsigned int numOfElementToWrite = 1, unsigned int startIndex = 0) + { + MGlobal::displayInfo("WriteToFile::writeToFiles()"); + if (ASCIIFile.is_open()) { + for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) + ASCIIFile << toWrite[i] << endl; + } + + if (binFile.is_open()) { + binFile.write((char*)toWrite, numOfElementToWrite * sizeof(int)); + } + + } + void OpenFiles(); void CloseFiles(); From 24486c314dffcdf0294682cc3da0e6be1f559c56 Mon Sep 17 00:00:00 2001 From: antc13 Date: Wed, 13 Jan 2016 14:03:58 +0100 Subject: [PATCH 029/224] Reworked the Exporter. --- tools/MayaExporter/MayaExporter/Export.cpp | 172 ++++++++++++++ tools/MayaExporter/MayaExporter/Export.h | 54 +++++ .../GeneratedFiles/Debug/moc_Menu.cpp | 42 ++-- .../MayaExporter/MayaExporter.vcxproj | 2 + .../MayaExporter/MayaExporter.vcxproj.filters | 6 + tools/MayaExporter/MayaExporter/Menu.cpp | 213 ++++-------------- tools/MayaExporter/MayaExporter/Menu.h | 23 +- tools/MayaExporter/MayaExporter/Mesh.cpp | 26 ++- tools/MayaExporter/MayaExporter/Mesh.h | 45 +++- tools/MayaExporter/MayaExporter/Skeleton.cpp | 11 +- tools/MayaExporter/MayaExporter/Skeleton.h | 6 + tools/MayaExporter/MayaExporter/WriteToFile.h | 10 +- 12 files changed, 369 insertions(+), 241 deletions(-) create mode 100644 tools/MayaExporter/MayaExporter/Export.cpp create mode 100644 tools/MayaExporter/MayaExporter/Export.h diff --git a/tools/MayaExporter/MayaExporter/Export.cpp b/tools/MayaExporter/MayaExporter/Export.cpp new file mode 100644 index 00000000..82c81cfa --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Export.cpp @@ -0,0 +1,172 @@ +#include "Export.h" + +Export::Export() +{ + +} + +bool Export::Meshes(std::string pathName, bool selectedOnly) +{ + if (pathName.empty()) { + MGlobal::displayError(MString() + "Export::Meshes() got no pathName. Do not know where to write file"); + return false; + } + meshes.clear(); + + if (selectedOnly) { + // Retrieving the objects we currently have selected + MSelectionList selected; + MGlobal::getActiveSelectionList(selected); + + // Loop through or list of selection(s) + for (unsigned int i = 0; i < selected.length(); i++) { + MObject object; + selected.getDependNode(i, object); + + if (object.hasFn(MFn::kMesh)) { + MFnDependencyNode thisNode(object); + GetMeshData(object); + } + } + } else { + // Loop through all nodes in the scene + MItDependencyNodes it(MFn::kMesh); + for (; !it.isDone(); it.next()) { + MObject node = it.thisNode(); + MFnDependencyNode thisNode(node); + MPlugArray connections; + thisNode.findPlug("inMesh").connectedTo(connections, true, true); + bool next = false; + + for (unsigned int i = 0; i < connections.length(); i++) { + if (connections[i].node().apiType() == MFn::kSkinClusterFilter) { + next = true; + break; + } + } + + if (next) + continue; + + GetMeshData(node); + } + } + MGlobal::displayInfo(MString() + "nrofmeshes: " + meshes.size()); + WriteMeshData(pathName); + return true; +} + +bool Export::Materials() +{ + return true; +} + +bool Export::Animations(std::string pathName, std::vector animInfo) +{ + if (MAnimControl::currentTime().unit() != MTime::kNTSCField) { + + MGlobal::displayError(MString() + "Please change to 60 FPS under Preferences/Settings!"); + return false; + } + + if (pathName.empty()) { + MGlobal::displayError(MString() + "Export::Animations() got no pathName. Do not know where to write file"); + return false; + } + MGlobal::displayInfo("HALLOOOO"); + allBindPoses = m_SkeletonHandler.GetBindPoses(); + + for (auto clip : animInfo) { + MGlobal::displayInfo("preben"); + if (!GetAnimationData(clip)) { + MGlobal::displayError(MString() + "Export::Animations() failed to export " + clip.Name.c_str()); + return false; + } + } + MGlobal::displayInfo("ghihgihi"); + WriteAnimData(pathName); + return true; +} + +bool Export::GetMeshData(MObject object) +{ + if (!object.hasFn(MFn::kMesh)) + return false; + + meshes.push_back(m_MeshHandler.GetMeshData(object)); + return true; +} + +bool Export::GetMaterialData() +{ + // Traverse scene and return vector with all materials + std::vector* AllMaterials = m_MaterialHandler.DoIt(); + + // Access the colorR component of one material (example) + cout << AllMaterials->at(0).Color[0] << endl; + MGlobal::displayInfo(MString() + AllMaterials->at(0).Color[0]); + return true; +} + +bool Export::GetAnimationData(AnimationInfo animInfo) +{ + if (animInfo.Name.empty()) { + MGlobal::displayError(MString() + "A clip does not have a name"); + return false; + } + if (animInfo.End - animInfo.Start <= 0) { + MGlobal::displayError(MString() + "A clip ends before it starts or contains 0 frames"); + return false; + } + + allAnimations.push_back(m_SkeletonHandler.GetAnimData(animInfo.Name, animInfo.Start, animInfo.End)); + return true; +} + +void Export::WriteMeshData(std::string pathName) +{ + m_MeshFile.ASCIIFilePath(pathName +"_mesh.txt"); + m_MeshFile.binaryFilePath(pathName + ".mesh"); + + m_MeshFile.OpenFiles(); + + for (auto aMesh : meshes) { + m_MeshFile.writeToFiles((OutputData*)&aMesh); + } + + m_MeshFile.CloseFiles(); +} + +void Export::WriteAnimData(std::string pathName) +{ + if (allBindPoses.size() > 0) { + m_AnimFile.ASCIIFilePath(pathName + "_anim.txt"); + m_AnimFile.binaryFilePath(pathName + ".anim"); + + m_AnimFile.OpenFiles(); + int size = allBindPoses.size(); + m_AnimFile.writeToFiles(&size); + + size = allAnimations.size(); + m_AnimFile.writeToFiles(&size); + + //print out all bind poses + for (auto aBindPose : allBindPoses) { + m_AnimFile.writeToFiles((OutputData*)&aBindPose); + } + for (auto aAnimation : allAnimations) { + m_AnimFile.writeToFiles((OutputData*)&aAnimation); + } + + m_AnimFile.CloseFiles(); + } else + MGlobal::displayInfo("Export::WriteAnimData() got called when allBindPoses contained no data, did not write nor created them"); +} + +Export::~Export() +{ + /* delete m_MaterialHandler; + delete m_SkeletonHandler; + delete m_MeshHandler;*/ + +} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Export.h b/tools/MayaExporter/MayaExporter/Export.h new file mode 100644 index 00000000..83d27459 --- /dev/null +++ b/tools/MayaExporter/MayaExporter/Export.h @@ -0,0 +1,54 @@ +#ifndef Export_Export_h__ +#define Export_Export_h__ + +#include +#include + +#include "MayaIncludes.h" +#include "Material.h" +#include "Mesh.h" +#include "Skeleton.h" +#include "WriteToFile.h" + +class Export { +public: + Export(); + + ~Export(); + + struct AnimationInfo { + std::string Name; + int Start; + int End; + }; + + bool Meshes(std::string pathName, bool selectedOnly = false); + bool Materials(); + bool Animations(std::string pathName, std::vector animInfo); + +private: + bool GetMeshData(MObject object); + bool GetMaterialData(); + bool GetAnimationData(AnimationInfo info); + + void WriteMeshData(std::string pathName); + void WriteAnimData(std::string pathName); + + Material m_MaterialHandler; + Skeleton m_SkeletonHandler; + MeshClass m_MeshHandler; + + + //File export + WriteToFile m_MeshFile; + WriteToFile m_AnimFile; + + //Mesh Data + std::vector meshes; + + //Animation Data + std::vector allBindPoses; + std::vector allAnimations; + +}; +#endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp b/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp index a375ed53..c7879431 100644 --- a/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp +++ b/tools/MayaExporter/MayaExporter/GeneratedFiles/Debug/moc_Menu.cpp @@ -22,7 +22,7 @@ static const uint qt_meta_data_Menu[] = { 6, // revision 0, // classname 0, 0, // classinfo - 9, 14, // methods + 5, 14, // methods 0, 0, // properties 0, 0, // enums/sets 0, 0, // constructors @@ -30,25 +30,19 @@ static const uint qt_meta_data_Menu[] = { 0, // signalCount // slots: signature, parameters, type, tag, flags - 14, 6, 5, 5, 0x08, - 35, 5, 5, 5, 0x08, - 59, 5, 5, 5, 0x08, - 80, 5, 5, 5, 0x08, - 104, 5, 5, 5, 0x08, - 120, 5, 5, 5, 0x08, - 140, 5, 5, 5, 0x08, - 161, 5, 5, 5, 0x08, - 182, 5, 5, 5, 0x08, + 6, 5, 5, 5, 0x08, + 30, 5, 5, 5, 0x08, + 51, 5, 5, 5, 0x08, + 75, 5, 5, 5, 0x08, + 91, 5, 5, 5, 0x08, 0 // eod }; static const char qt_meta_stringdata_Menu[] = { - "Menu\0\0checked\0ExportSelected(bool)\0" - "ExportPathClicked(bool)\0AddClipClicked(bool)\0" - "RemoveClipClicked(bool)\0ExportAll(bool)\0" - "CancelClicked(bool)\0Button1Clicked(bool)\0" - "Button2Clicked(bool)\0Button3Clicked(bool)\0" + "Menu\0\0ExportPathClicked(bool)\0" + "AddClipClicked(bool)\0RemoveClipClicked(bool)\0" + "ExportAll(bool)\0CancelClicked(bool)\0" }; void Menu::qt_static_metacall(QObject *_o, QMetaObject::Call _c, int _id, void **_a) @@ -57,15 +51,11 @@ void Menu::qt_static_metacall(QObject *_o, QMetaObject::Call _c, int _id, void * Q_ASSERT(staticMetaObject.cast(_o)); Menu *_t = static_cast(_o); switch (_id) { - case 0: _t->ExportSelected((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 1: _t->ExportPathClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 2: _t->AddClipClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 3: _t->RemoveClipClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 4: _t->ExportAll((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 5: _t->CancelClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 6: _t->Button1Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 7: _t->Button2Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; - case 8: _t->Button3Clicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 0: _t->ExportPathClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 1: _t->AddClipClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 2: _t->RemoveClipClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 3: _t->ExportAll((*reinterpret_cast< bool(*)>(_a[1]))); break; + case 4: _t->CancelClicked((*reinterpret_cast< bool(*)>(_a[1]))); break; default: ; } } @@ -103,9 +93,9 @@ int Menu::qt_metacall(QMetaObject::Call _c, int _id, void **_a) if (_id < 0) return _id; if (_c == QMetaObject::InvokeMetaMethod) { - if (_id < 9) + if (_id < 5) qt_static_metacall(this, _c, _id, _a); - _id -= 9; + _id -= 5; } return _id; } diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj index 701b39cf..4a7ac07e 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj @@ -153,6 +153,7 @@ + @@ -199,6 +200,7 @@ + diff --git a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters index be5b36b1..ae3d2478 100644 --- a/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters +++ b/tools/MayaExporter/MayaExporter/MayaExporter.vcxproj.filters @@ -62,6 +62,9 @@ Source Files + + Source Files + @@ -96,5 +99,8 @@ Header Files + + Header Files + \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 7e1e6cde..1ff007b4 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -13,9 +13,8 @@ Menu::Menu(QDialog* dialog) m_DialogPointer = dialog; // Create QpushButtons & give them names - m_ExportSelectedButton = new QPushButton("&Export Selected", this); m_BrowseButton = new QPushButton("&...", this); - m_ExportAllButton = new QPushButton("&Export All", this); + m_ExportAllButton = new QPushButton("&Export", this); m_CancelButton = new QPushButton("&Cancel", this); m_AddClipsButton = new QPushButton("&Add Clips", this); m_RemoveClipsButton = new QPushButton("&Remove Latest Clip", this); @@ -23,6 +22,7 @@ Menu::Menu(QDialog* dialog) // Option box and checkboxes QGroupBox *optionsBox = new QGroupBox(tr("Options")); + m_ExportSelectedButton = new QCheckBox(tr("&Export Selected")); m_ExportAnimationsButton = new QCheckBox(tr("&Export Animations")); m_CopyTexturesButton = new QCheckBox(tr("&Copy Textures")); m_Button3 = new QCheckBox(tr("Test Materials")); @@ -30,6 +30,7 @@ Menu::Menu(QDialog* dialog) m_ExportAnimationsButton->setChecked(true); m_CopyTexturesButton->setChecked(true); QVBoxLayout *vbox = new QVBoxLayout; + vbox->addWidget(m_ExportSelectedButton); vbox->addWidget(m_ExportAnimationsButton); vbox->addWidget(m_CopyTexturesButton); vbox->addWidget(m_Button3); @@ -37,16 +38,16 @@ Menu::Menu(QDialog* dialog) optionsBox->setLayout(vbox); // Connect the buttons with signals & functions - connect(m_ExportSelectedButton, SIGNAL(clicked(bool)), this, SLOT(ExportSelected(bool))); connect(m_BrowseButton, SIGNAL(clicked(bool)), this, SLOT(ExportPathClicked(bool))); connect(m_ExportAllButton, SIGNAL(clicked(bool)), this, SLOT(ExportAll(bool))); connect(m_CancelButton, SIGNAL(clicked(bool)), this, SLOT(CancelClicked(bool))); connect(m_AddClipsButton, SIGNAL(clicked(bool)), this, SLOT(AddClipClicked(bool))); connect(m_RemoveClipsButton, SIGNAL(clicked(bool)), this, SLOT(RemoveClipClicked(bool))); - connect(m_ExportAnimationsButton, SIGNAL(clicked(bool)), this, SLOT(Button1Clicked(bool))); - connect(m_CopyTexturesButton, SIGNAL(clicked(bool)), this, SLOT(Button2Clicked(bool))); - connect(m_Button3, SIGNAL(clicked(bool)), this, SLOT(Button3Clicked(bool))); + connect(m_ExportSelectedButton, SIGNAL(clicked(bool)), this, SLOT(NULL)); + connect(m_ExportAnimationsButton, SIGNAL(clicked(bool)), this, SLOT(NULL)); + connect(m_CopyTexturesButton, SIGNAL(clicked(bool)), this, SLOT(NULL)); + connect(m_Button3, SIGNAL(clicked(bool)), this, SLOT(NULL)); // Creating several layouts, adding widgets & adding them to one layout in the end QHBoxLayout* topLayout = new QHBoxLayout; @@ -61,7 +62,8 @@ Menu::Menu(QDialog* dialog) m_ExportPath = new QLineEdit; m_FileDialog = new QFileDialog; - + QString tmpPath("C:/Users/Nickelodion/Desktop/Baljj"); + m_ExportPath->setText(tmpPath); QLabel* exportLabel = new QLabel; exportLabel->setText("Export Path:"); QLabel* nameLabel = new QLabel; @@ -79,7 +81,6 @@ Menu::Menu(QDialog* dialog) topLayout->addWidget(m_ExportPath); topLayout->addWidget(m_BrowseButton); - botLayout->addWidget(m_ExportSelectedButton); botLayout->addWidget(m_ExportAllButton); botLayout->addWidget(m_CancelButton); @@ -111,35 +112,6 @@ Menu::Menu(QDialog* dialog) } - -void Menu::ExportSelected(bool checked) -{ - // Retrieving the objects we currently have selected - MSelectionList selected; - MGlobal::getActiveSelectionList(selected); - - // Loop through or list of selection(s) - for (unsigned int i = 0; i < selected.length(); i++) { - MObject object; - selected.getDependNode(i, object); - MFnDependencyNode thisNode(object); - - cout << thisNode.name().asChar() << endl; - GetMeshData(object); - } - if (m_ExportPath->text().isEmpty()) { - cout << "Please select a folder." << endl; - } - else { - cout << m_ExportPath->text().toLocal8Bit().constData() << endl; - } - - if (m_ExportAnimationsButton->isChecked()) { - GetSkeletonData(); - } - -} - void Menu::ExportPathClicked(bool) { // Opens up a file dialog. Save/Changes the name in the exportPath @@ -188,50 +160,45 @@ void Menu::RemoveClipClicked(bool) layouts.pop_back(); m_StartFrameLines.pop_back(); m_EndFrameLines.pop_back(); + m_AnimationClipName.pop_back(); } } void Menu::ExportAll(bool) { - MDagPath path; - m_File.ASCIIFilePath("C:/Users/Nickelodion/Desktop/coolASCII.txt"); - m_File.binaryFilePath("C:/Users/Nickelodion/Desktop/coolSoptunz.bin"); - m_File.OpenFiles(); + if (m_ExportPath->text().isEmpty()) { + MGlobal::displayError(MString() + "Please select a folder."); + return; + } - // Loop through all nodes in the scene - MItDependencyNodes it(MFn::kMesh); - for (; !it.isDone(); it.next()) { - MObject node = it.thisNode(); - if (node.hasFn(MFn::kMesh)) { - MFnDependencyNode thisNode(node); - MPlugArray connections; + //Export meshes + if (!m_Export.Meshes(m_ExportPath->text().toLocal8Bit().constData(), m_ExportSelectedButton->isChecked())) { + MGlobal::displayError(MString() + "Could not export mesh"); + return; + } - thisNode.findPlug("inMesh").connectedTo(connections, true, true); - bool next = false; - for (unsigned int i = 0; i < connections.length(); i++) { - if(connections[i].node().apiType() == MFn::kSkinClusterFilter){ - next = true; - break; - } - } - if (next) - continue; + std::vector animations; + MGlobal::displayInfo(MString() + "yeeehaa"); + for (unsigned int i = 0; i < m_AnimationClipName.size(); i++) { + Export::AnimationInfo thisClip; + MGlobal::displayInfo(MString() + "qwqw"); + thisClip.Name = std::string(m_AnimationClipName[i]->text().toLocal8Bit().constData()); + MGlobal::displayInfo(MString() + "shizzzz"); + thisClip.Start = m_StartFrameLines[i]->text().toInt(); + MGlobal::displayInfo(MString() + "dsdsfg"); + thisClip.End = m_EndFrameLines[i]->text().toInt(); + MGlobal::displayInfo(MString() + "aaaaaaaaaaaaaaaaaaaa"); - cout << thisNode.name().asChar() << endl; - MGlobal::displayInfo("EXPORT ALL FUNCTION: " + thisNode.name() + " " + thisNode.findPlug("inMesh").asMObject().apiTypeStr()); - GetMeshData(node); - } - } - if (m_ExportPath->text().isEmpty()) { - cout << "Please select a folder." << endl; - } - else { - cout << m_ExportPath->text().toLocal8Bit().constData() << endl; - } - - if (m_ExportAnimationsButton->isChecked()) - GetSkeletonData(); - m_File.CloseFiles(); + animations.push_back(thisClip); + } + MGlobal::displayInfo(MString() + "asdf"); + if (m_ExportAnimationsButton->isChecked()) { + //Export Animations + if (!m_Export.Animations(m_ExportPath->text().toLocal8Bit().constData(), animations)) { + MGlobal::displayError(MString() + "Could not export animations"); + return; + } + } } void Menu::CancelClicked(bool) @@ -239,105 +206,6 @@ void Menu::CancelClicked(bool) m_DialogPointer->close(); } -void Menu::Button1Clicked(bool) -{ - if (m_ExportAnimationsButton->isChecked()) { - MGlobal::displayInfo("1 checked!"); - } - else { - MGlobal::displayInfo("1 unchecked!"); - } -} - -void Menu::Button2Clicked(bool) -{ - if (m_CopyTexturesButton->isChecked()) { - cout << "2 checked!" << endl; - } - else { - cout << "2 unchecked!" << endl; - } -} - -void Menu::Button3Clicked(bool) -{ - if (m_Button3->isChecked()) { - cout << "3 checked!" << endl; - } - else { - cout << "3 unchecked!" << endl; - } -} -void Menu::GetMeshData(MObject object) -{ - std::vector vertexList; - std::vector indexList; - - Mesh mesh; - mesh.GetMeshData(object, vertexList, indexList); - - for (auto aVertex : vertexList) { - m_File.writeToFiles(&aVertex); - } - m_File.writeToFiles(indexList.data(), indexList.size()); -} -void Menu::GetMaterialData() -{ - this->m_MaterialHandler = new Material(); - - // Traverse scene and return vector with all materials - std::vector* AllMaterials = m_MaterialHandler->DoIt(); - - // Access the colorR component of one material (example) - cout << AllMaterials->at(0).Color[0] << endl; - MGlobal::displayInfo(MString() + AllMaterials->at(0).Color[0]); -} - -void Menu::GetSkeletonData() -{ - if (MAnimControl::currentTime().unit() != MTime::kNTSCField) { - - MGlobal::displayError(MString() + "Please change to 60 FPS under Preferences/Settings!"); - return; - } - - std::vector allBindPoses; - std::vector allAnimations; - - allBindPoses = m_SkeletonHandler->GetBindPoses(); - - for (unsigned int j = 0; j < m_StartFrameLines.size(); j++) { - if (m_StartFrameLines[j]->text().isEmpty() == true || m_StartFrameLines[j]->text().isEmpty() == true) { - MGlobal::displayError(MString() + "Empty Animation Clip(s)"); - return; - } - - int startFrame = m_StartFrameLines[j]->text().toInt(); - int endFrame = m_EndFrameLines[j]->text().toInt(); - std::string animationName = m_AnimationClipName[j]->text().toAscii().constData(); - - allAnimations.push_back(m_SkeletonHandler->GetAnimData(animationName, startFrame, endFrame)); - } - - //print out all bind poses - for (auto aBindPose : allBindPoses){ - m_File.writeToFiles(&aBindPose); - MGlobal::displayInfo(MString() + "BindPose Skeleton name: " + aBindPose.Name.c_str()); - - for (int i = 0; i < aBindPose.Joints.size(); i++){ - //MGlobal::displayInfo(MString() + aBindPose.JointNames[i].c_str()); - //MGlobal::displayInfo(MString() + aBindPose.ParentIDs[i]); - //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Translation[0] + " " + aBindPose.Joints[i].Translation[1] + " " + aBindPose.Joints[i].Translation[2]); - //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Rotation[0] + " " + aBindPose.Joints[i].Rotation[1] + " " + aBindPose.Joints[i].Rotation[2]); - //MGlobal::displayInfo(MString() + aBindPose.Joints[i].Scale[0] + " " + aBindPose.Joints[i].Scale[1] + " " + aBindPose.Joints[i].Scale[2]); - } - } - //print out all animations - for (auto aAnimation : allAnimations) { - m_File.writeToFiles(&aAnimation); - } -} - Menu::~Menu() { //delete exportSelectedButton; @@ -346,5 +214,6 @@ Menu::~Menu() //delete fileDialog; m_FileDialog->~QFileDialog(); + //delete m_Export; //delete MaterialHandler; } \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index 9f3492ab..a8b517bc 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -32,12 +32,8 @@ #include #include - #include "MayaIncludes.h" -#include "Material.h" -#include "Mesh.h" -#include "Skeleton.h" -#include "WriteToFile.h" +#include "Export.h" class Menu : public QWidget { @@ -46,23 +42,13 @@ public: Menu(QDialog* dialog); ~Menu(); - void GetMeshData(MObject object); - void GetMaterialData(); - void GetSkeletonData(); - private slots: - void ExportSelected(bool checked); void ExportPathClicked(bool); void AddClipClicked(bool); void RemoveClipClicked(bool); void ExportAll(bool); void CancelClicked(bool); - void Button1Clicked(bool); - void Button2Clicked(bool); - void Button3Clicked(bool); - - private: Menu(); std::vector m_AnimationClipName; @@ -71,13 +57,13 @@ private: std::vector layouts; QVBoxLayout* m_ClipLayout; - QPushButton* m_ExportSelectedButton = nullptr; QPushButton* m_BrowseButton = nullptr; QPushButton* m_ExportAllButton = nullptr; QPushButton* m_CancelButton = nullptr; QPushButton* m_AddClipsButton = nullptr; QPushButton* m_RemoveClipsButton = nullptr; + QCheckBox* m_ExportSelectedButton = nullptr; QCheckBox* m_ExportAnimationsButton = nullptr; QCheckBox* m_CopyTexturesButton = nullptr; QCheckBox* m_Button3 = nullptr; @@ -86,10 +72,7 @@ private: QFileDialog* m_FileDialog = nullptr; QDialog* m_DialogPointer = nullptr; - Material* m_MaterialHandler = nullptr; - Skeleton* m_SkeletonHandler = nullptr; - - WriteToFile m_File; + Export m_Export; }; #endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index 0ac66b33..d9b47875 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -3,11 +3,12 @@ using namespace std; -Mesh::Mesh() +MeshClass::MeshClass() { } -std::map Mesh::GetWeightData() + +std::map MeshClass::GetWeightData() { map weightMap; @@ -72,10 +73,14 @@ std::map Mesh::GetWeightData() return weightMap; } -void Mesh::GetMeshData(MObject object, std::vector& vertexList, std::vector& indexList) +Mesh MeshClass::GetMeshData(MObject object) { + Mesh newMesh; + std::vector& vertexList = newMesh.Vertices; + std::vector& indexList = newMesh.Indices; // In here, we retrieve triangulated polygons from the mesh MFnMesh mesh(object); + map> vertexToIndex;; MIntArray intdexOffsetVertexCount, vertices, triangleList; @@ -106,7 +111,7 @@ void Mesh::GetMeshData(MObject object, std::vector& vertexList, st meshPolyIter.getVertices(vertices); meshPolyIter.getTriangles(dummy, triangleList); - MGlobal::displayInfo(MString() + "vertices.length(): " + vertices.length()); + //MGlobal::displayInfo("Befor Second Loop"); for (unsigned int i = 0; i < vertices.length(); i++) { vertexIndex = meshPolyIter.vertexIndex(i); @@ -160,25 +165,26 @@ void Mesh::GetMeshData(MObject object, std::vector& vertexList, st //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; } - //MGlobal::displayInfo("Befor Third Loop"); - MGlobal::displayInfo(MString() + "localVertexToGlobalIndex.size(): " + localVertexToGlobalIndex.size()); - MGlobal::displayInfo(MString() + "vertexList.size(): " + vertexList.size()); + for (unsigned int i = 0; i < triangleList.length(); i++) { unsigned int k = 0; - MGlobal::displayInfo(MString() + "triangleList[i]: " + triangleList[i]); if (localVertexToGlobalIndex.size() > 0) { while (localVertexToGlobalIndex[k] != triangleList[i] && k < localVertexToGlobalIndex.size()) { - MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k]: " + localVertexToGlobalIndex[k]); k++; } indexList.push_back(indexOffset + k); } } } + + newMesh.NumIndices = newMesh.Indices.size(); + newMesh.NumVertices = newMesh.Vertices.size(); + + return newMesh; } -Mesh::~Mesh() +MeshClass::~MeshClass() { } \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h index 6fab0536..c9445e4e 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.h +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -10,7 +10,6 @@ class VertexLayout : public OutputData { public: - float Pos[3]; float Normal[3]; float BiNormal[3]; @@ -32,7 +31,6 @@ public: virtual void WriteASCII(std::ostream& out) const { - out << "New Vertex: " << endl; out << Pos[0] << " " << Pos[1] << " " << Pos[2] << endl; out << Normal[0] << " " << Normal[1] << " " << Normal[2] << endl; out << BiNormal[0] << " " << BiNormal[1] << " " << BiNormal[2] << endl; @@ -56,15 +54,50 @@ public: } }; +class Mesh : public OutputData { +public: + int NumVertices; + int NumIndices; + std::vector Vertices; + std::vector Indices; + + virtual void WriteBinary(std::ostream& out) + { + out.write((char*)&NumVertices, sizeof(int)); + out.write((char*)&NumIndices, sizeof(int)); + for (auto aVertex : Vertices) { + aVertex.WriteBinary(out); + } + for (auto aIndex : Indices) { + out.write((char*)&aIndex, sizeof(int)); + } + } + + virtual void WriteASCII(std::ostream& out) const + { + out << "New Mesh _ not in binary" << endl; + out << "Number of vertices: " << NumVertices << endl; + out << "number of indices: " << NumIndices << endl; + int vertexNumber = 0; + for (auto aVertex : Vertices) { + out << "New vertex number: " << vertexNumber << "_ not in binary" << endl; + aVertex.WriteASCII(out); + vertexNumber++; + } + for (int i = 0; i < NumIndices; i += 3) { + out << Indices[i] << " " << Indices[i+1] << " " << Indices[i + 2] << endl; + } + } +}; -class Mesh +class MeshClass { public: - Mesh(); - void GetMeshData(MObject Object, std::vector& vertexList, std::vector& indexList); - ~Mesh(); + MeshClass(); + Mesh GetMeshData(MObject Object); + ~MeshClass(); private: struct WeightInfo { float BoneIndices[4] = { 0 }; diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp index 394f548b..0497aa31 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.cpp +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -64,12 +64,13 @@ std::string attr[9] = { "scaleX", "scaleY", "scaleZ", "translateX", "translateY" Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int endFrame) { + std::vector animatedJoints; + std::vector m_Hierarchy; + Animation returnData; double oneDivSixty = 1 / 60.0; returnData.Name = animationName; returnData.Duration = (endFrame - startFrame) * oneDivSixty; - std::vector animatedJoints; - std::vector m_Hierarchy; MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); while (!jointIt.isDone()) @@ -121,7 +122,7 @@ Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int e if (BindPoseMatrix != MayaJoint.transformationMatrix()) { - MGlobal::displayError(MString() + animationName.c_str() + " is using a joint that is not in bind pose nor is it key framed in the animation, the exported animation will NOT correspond to the animation in Maya"); + MGlobal::displayError(MString() + animationName.c_str() + " is using " + MayaJoint.name() + " that is not in bind pose nor is it key framed in the animation, the exported animation will NOT correspond to the animation in Maya"); } } } @@ -173,6 +174,10 @@ Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int e returnData.Keyframes.push_back(thisKeyFrame); currentFrame++; } + + returnData.NumKeyFrames = returnData.Keyframes.size(); + returnData.NumberOfJoints = animatedJoints.size(); + return returnData; } diff --git a/tools/MayaExporter/MayaExporter/Skeleton.h b/tools/MayaExporter/MayaExporter/Skeleton.h index 0b0c2a60..dda0cfea 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.h +++ b/tools/MayaExporter/MayaExporter/Skeleton.h @@ -26,12 +26,16 @@ public: std::string Name; double Duration; + int NumKeyFrames; + int NumberOfJoints; std::vector Keyframes; virtual void WriteBinary(std::ostream& out) { out.write(Name.c_str(), Name.size() + 1); out.write((char*)&Duration, sizeof(double)); + out.write((char*)&NumKeyFrames, sizeof(int)); + out.write((char*)&NumberOfJoints, sizeof(int)); for (auto aKeyframe : Keyframes) { out.write((char*)&aKeyframe.Index, sizeof(int)); out.write((char*)&aKeyframe.Time, sizeof(double)); @@ -48,6 +52,8 @@ public: { out << "Animation Name: " << Name << endl; out << "Duration: " << Duration << endl; + out << "Number of KeyFrames: " << NumKeyFrames << endl; + out << "Number of Joints: " << NumberOfJoints << endl; for (auto aKeyframe : Keyframes) { out << "Frame: " << aKeyframe.Index << endl; out << "Time: " << aKeyframe.Time << endl; diff --git a/tools/MayaExporter/MayaExporter/WriteToFile.h b/tools/MayaExporter/MayaExporter/WriteToFile.h index 3d6cc078..91ca7103 100644 --- a/tools/MayaExporter/MayaExporter/WriteToFile.h +++ b/tools/MayaExporter/MayaExporter/WriteToFile.h @@ -17,7 +17,7 @@ public: void writeToFiles(OutputData* toWrite, unsigned int numOfElementToWrite = 1, unsigned int startIndex = 0) { - MGlobal::displayInfo("WriteToFile::writeToFiles()"); + MGlobal::displayInfo("WriteToFile::writeToFiles(OutputData*)"); if (ASCIIFile.is_open()) { for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) @@ -32,16 +32,18 @@ public: } - void writeToFiles(unsigned int* toWrite, unsigned int numOfElementToWrite = 1, unsigned int startIndex = 0) + template + void writeToFiles(T* toWrite, unsigned int numOfElementToWrite = 1, unsigned int startIndex = 0) { - MGlobal::displayInfo("WriteToFile::writeToFiles()"); + MGlobal::displayInfo("WriteToFile::writeToFiles(T*) - Template T"); if (ASCIIFile.is_open()) { for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) ASCIIFile << toWrite[i] << endl; } if (binFile.is_open()) { - binFile.write((char*)toWrite, numOfElementToWrite * sizeof(int)); + for (unsigned int i = startIndex; i < numOfElementToWrite + startIndex; i++) + binFile.write((char*)toWrite, sizeof(T)); } } From c14f3789f7bb1ee6820c56280691a85afe341e17 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 13 Jan 2016 15:26:10 +0100 Subject: [PATCH 030/224] PlayerSystem now counts down the CoolDownTimer on both HeldItems for the player. Updated ShootEventTest to verify this --- src/Game/PlayerSystem.cpp | 9 ++++++++- src/Tests/ShootEventTest.cpp | 10 ++++++---- 2 files changed, 14 insertions(+), 5 deletions(-) diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index c9112b01..7bf576af 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -1,4 +1,5 @@ #include "PlayerSystem.h" +#include void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, double dt) { @@ -22,6 +23,12 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou (glm::vec3&)transform["Position"] += (glm::vec3)player["Velocity"]; } + //decrease CoolDownTimers for both HeldItems + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + ComponentWrapper& currentItem2 = world->GetComponent(player.EntityID, "SecondaryItem"); + currentItem["CoolDownTimer"] = std::max(0.0, (double)currentItem["CoolDownTimer"] - dt); + currentItem2["CoolDownTimer"] = std::max(0.0, (double)currentItem2["CoolDownTimer"] - dt); + //do shootEvent: if left mouse was released, and ammo/weaponcooldown/playeralive/shootingcooldown are ok if (leftMouseWasReleased) { leftMouseWasReleased = false; @@ -44,7 +51,7 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou //decrease ammo count //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; - currentItem["CoolDownTimer"] = 2.0;//change later! + currentItem["CoolDownTimer"] = 2.0;//change later! probably to maxCoolDownTimer //create and publish the shoot event Events::Shoot eShoot; eShoot.currentAimingPoint = aimingCoordinates; diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index f24bfed8..3af66b88 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -180,7 +180,7 @@ void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pIte player["EquippedItem"] = 1; //set ammo set cooldown pItem["Ammo"] = 100; - pItem["CoolDownTimer"] = 5.0; + pItem["CoolDownTimer"] = 99999999.0;//very long coolDownTimer //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } @@ -225,10 +225,12 @@ void ShootEventTest::Tick() { glfwPollEvents(); - double currentTime = glfwGetTime(); - double dt = currentTime - m_LastTime; - m_LastTime = currentTime; + //double currentTime = glfwGetTime(); + //double dt = currentTime - m_LastTime; + //m_LastTime = currentTime; + //just set dt to 1.0 + double dt = 0.34567; // Iterate through systems and update world! m_SystemPipeline->Update(m_World, dt); From e6527196eda97de6516719d41802d0b1c4aa1877 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 13 Jan 2016 15:50:30 +0100 Subject: [PATCH 031/224] Modified a few files according to the current CodeStandards --- include/Engine/Core/EShoot.h | 4 ++-- include/Game/PlayerSystem.h | 5 +++-- src/Game/PlayerSystem.cpp | 25 ++++++++++++------------- src/Tests/ShootEventTest.cpp | 8 ++++---- src/Tests/ShootEventTest.h | 8 ++++---- 5 files changed, 25 insertions(+), 25 deletions(-) diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h index 3887606b..9e395d62 100644 --- a/include/Engine/Core/EShoot.h +++ b/include/Engine/Core/EShoot.h @@ -12,9 +12,9 @@ struct Shoot : Event { //shotgun etc has different amounts of damage probably (a sniper shot might one-shot) //also different weapons will have different spread - int currentlyEquippedItem; + int CurrentlyEquippedItem; //currentAimingPoint must be sent, in case the camera is moved while the event is being processed - glm::vec2 currentAimingPoint; + glm::vec2 CurrentAimingPoint; }; } diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index a48af3e4..e7ef6ff0 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -9,6 +9,7 @@ #include "Collision/ETrigger.h" #include "Core/EMouseRelease.h" #include "Core/EShoot.h" +#include class PlayerSystem : public PureSystem { @@ -25,8 +26,8 @@ public: virtual void UpdateComponent(World* world, ComponentWrapper& player, double dt) override; private: float m_Speed = 5; - bool leftMouseWasReleased = false; - glm::vec2 aimingCoordinates; + bool m_LeftMouseWasReleased = false; + glm::vec2 m_AimingCoordinates; EventRelay m_EEnter; bool OnEnter(const Events::TriggerEnter &event); EventRelay m_ETouch; diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index 7bf576af..3120f035 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -1,7 +1,6 @@ #include "PlayerSystem.h" -#include -void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, double dt) +void PlayerSystem::UpdateComponent(World* world, ComponentWrapper& player, double dt) { player["Velocity"] = glm::vec3(0.f, 0.f, 0.f); if ((bool&)player["Forward"] == true) { @@ -30,20 +29,20 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou currentItem2["CoolDownTimer"] = std::max(0.0, (double)currentItem2["CoolDownTimer"] - dt); //do shootEvent: if left mouse was released, and ammo/weaponcooldown/playeralive/shootingcooldown are ok - if (leftMouseWasReleased) { - leftMouseWasReleased = false; + if (m_LeftMouseWasReleased) { + m_LeftMouseWasReleased = false; //get the health component linked to the playerId double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; int currentAmmo = 0; double currentCoolDownTimer = 0.0; - std::string HeldItemString = ""; + std::string heldItemString = ""; if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) - HeldItemString = "PrimaryItem"; + heldItemString = "PrimaryItem"; if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) - HeldItemString = "SecondaryItem"; + heldItemString = "SecondaryItem"; - if (HeldItemString != "") { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, HeldItemString); + if (heldItemString != "") { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, heldItemString); currentAmmo = (int)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; @@ -54,8 +53,8 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou currentItem["CoolDownTimer"] = 2.0;//change later! probably to maxCoolDownTimer //create and publish the shoot event Events::Shoot eShoot; - eShoot.currentAimingPoint = aimingCoordinates; - eShoot.currentlyEquippedItem = (int)(player["EquippedItem"]); + eShoot.CurrentAimingPoint = m_AimingCoordinates; + eShoot.CurrentlyEquippedItem = (int)(player["EquippedItem"]); m_EventBroker->Publish(eShoot); } } @@ -86,7 +85,7 @@ bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e) //kolla om left mouse varit nere if (e.Button != GLFW_MOUSE_BUTTON_LEFT) return false; - aimingCoordinates = glm::vec2(e.X, e.Y); - leftMouseWasReleased = true; + m_AimingCoordinates = glm::vec2(e.X, e.Y); + m_LeftMouseWasReleased = true; return true; } \ No newline at end of file diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index 3af66b88..f9002eca 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -150,7 +150,7 @@ ShootEventTest::~ShootEventTest() delete m_EventBroker; } -void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +void ShootEventTest::TestSetup1(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) { //set currentweap player["EquippedItem"] = 1; @@ -158,7 +158,7 @@ void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pIte pItem["Ammo"] = 100; pItem["CoolDownTimer"] = 0.0; } -void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +void ShootEventTest::TestSetup2(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) { //set currentweap player["EquippedItem"] = 2; @@ -166,7 +166,7 @@ void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pIte sItem["Ammo"] = 10; sItem["CoolDownTimer"] = 0.0; } -void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +void ShootEventTest::TestSetup3(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) { player["EquippedItem"] = 0; pItem["Ammo"] = 100; @@ -174,7 +174,7 @@ void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pIte //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } -void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +void ShootEventTest::TestSetup4(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) { //set currentweap player["EquippedItem"] = 1; diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h index e860f41f..e796c17e 100644 --- a/src/Tests/ShootEventTest.h +++ b/src/Tests/ShootEventTest.h @@ -30,10 +30,10 @@ public: bool TestSucceeded = false; private: - void TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); - void TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); - void TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); - void TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSetup1(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); + void TestSetup2(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); + void TestSetup3(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); + void TestSetup4(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); void TestSuccess1(); void TestSuccess2(); void TestSuccess3(); From 184af95507a4472e39b6db211691f2ce1b57baa6 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Fri, 8 Jan 2016 16:19:18 +0100 Subject: [PATCH 032/224] New Event: EShoot. New Components: PrimaryItem,SecondaryItem. New Test: ShootEventTest. Added LeftMouseRelease->Shoot in PlayerSystem TODO: generalize the test --- include/Engine/Core/EShoot.h | 22 ++++ include/Game/PlayerSystem.h | 7 ++ resources/Schema/Components.xsd | 3 + resources/Schema/Components/Player.xml | 1 + resources/Schema/Components/Player.xsd | 1 + resources/Schema/Components/PrimaryItem.xml | 4 + resources/Schema/Components/PrimaryItem.xsd | 14 +++ resources/Schema/Components/SecondaryItem.xml | 4 + resources/Schema/Components/SecondaryItem.xsd | 14 +++ resources/Schema/Types/Entity.xsd | 2 + src/Game/PlayerSystem.cpp | 43 +++++++ src/Tests/ShootEventTest.cpp | 108 ++++++++++++++++++ src/Tests/ShootEventTest.h | 43 +++++++ 13 files changed, 266 insertions(+) create mode 100644 include/Engine/Core/EShoot.h create mode 100644 resources/Schema/Components/PrimaryItem.xml create mode 100644 resources/Schema/Components/PrimaryItem.xsd create mode 100644 resources/Schema/Components/SecondaryItem.xml create mode 100644 resources/Schema/Components/SecondaryItem.xsd create mode 100644 src/Tests/ShootEventTest.cpp create mode 100644 src/Tests/ShootEventTest.h diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h new file mode 100644 index 00000000..d9b9e20b --- /dev/null +++ b/include/Engine/Core/EShoot.h @@ -0,0 +1,22 @@ +#ifndef EShoot_h__ +#define EShoot_h__ + +#include "EventBroker.h" +#include "../Core/Entity.h" +#include "Engine/GLM.h" + +namespace Events +{ + +struct Shoot : Event +{ + //shotgun etc has different amounts of damage probably (a sniper shot might one-shot) + //also different weapons will have different spread + std::string weaponType; + //currentAimingPoint must be sent, in case the camera is moved while the event is being processed + glm::vec2 currentAimingPoint; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 577fbbb0..87dc6f5d 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -7,6 +7,8 @@ #include "Common.h" #include "Core/System.h" #include "Collision/ETrigger.h" +#include "Core\EMouseRelease.h" +#include "Core\EShoot.h" class PlayerSystem : public PureSystem { @@ -17,17 +19,22 @@ public: EVENT_SUBSCRIBE_MEMBER(m_ETouch, &PlayerSystem::OnTouch); EVENT_SUBSCRIBE_MEMBER(m_EEnter, &PlayerSystem::OnEnter); EVENT_SUBSCRIBE_MEMBER(m_ELeave, &PlayerSystem::OnLeave); + EVENT_SUBSCRIBE_MEMBER(m_MouseRelease, &PlayerSystem::OnMouseRelease); } virtual void UpdateComponent(World* world, ComponentWrapper& player, double dt) override; private: float m_Speed = 5; + bool leftMouseWasReleased = false; + glm::vec2 aimingCoordinates; EventRelay m_EEnter; bool OnEnter(const Events::TriggerEnter &event); EventRelay m_ETouch; bool PlayerSystem::OnTouch(const Events::TriggerTouch &event); EventRelay m_ELeave; bool PlayerSystem::OnLeave(const Events::TriggerLeave &event); + EventRelay m_MouseRelease; + bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e); }; #endif \ No newline at end of file diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index 7fcdd565..33714638 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -9,4 +9,7 @@ + + + \ No newline at end of file diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index 190f2ed0..cd3d1620 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,4 +1,5 @@ + 0 false false diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 76a6a8fb..fcf07879 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -11,6 +11,7 @@ + diff --git a/resources/Schema/Components/PrimaryItem.xml b/resources/Schema/Components/PrimaryItem.xml new file mode 100644 index 00000000..540a1518 --- /dev/null +++ b/resources/Schema/Components/PrimaryItem.xml @@ -0,0 +1,4 @@ + + 0 + 0 + \ No newline at end of file diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd new file mode 100644 index 00000000..193b9213 --- /dev/null +++ b/resources/Schema/Components/PrimaryItem.xsd @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xml b/resources/Schema/Components/SecondaryItem.xml new file mode 100644 index 00000000..0fae1402 --- /dev/null +++ b/resources/Schema/Components/SecondaryItem.xml @@ -0,0 +1,4 @@ + + 0 + 0 + \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd new file mode 100644 index 00000000..44e23611 --- /dev/null +++ b/resources/Schema/Components/SecondaryItem.xsd @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 6562f3ed..4b67276a 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -16,6 +16,8 @@ + + diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index 17b9a7f5..f5819ea1 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -21,6 +21,38 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou ComponentWrapper& transform = world->GetComponent(player.EntityID, "Transform"); (glm::vec3&)transform["Position"] += (glm::vec3)player["Velocity"]; } + + //do shootEvent: if left mouse was released, and ammo/weaponcooldown/playeralive/shootingcooldown are ok + if (leftMouseWasReleased) { + leftMouseWasReleased = false; + //get the health component linked to the playerId + double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; + int currentAmmo = 0; + double currentCoolDownTimer = 0.0f; + + if ((int)player["EquippedItem"] == 1) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + currentAmmo = currentItem["Ammo"]; + //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer + currentItem["Ammo"] = (int)currentItem["Ammo"] -1; + int test = (int)currentItem["Ammo"]; + currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "PrimaryItem")["CoolDownTimer"]; + } + if ((int)player["EquippedItem"] == 2) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); + currentAmmo = currentItem["Ammo"]; + //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer + currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; + currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "SecondaryItem")["CoolDownTimer"]; + } + if (currentHealth > 0.0f && currentAmmo > 0 && currentCoolDownTimer < 0.001f) { + //create and publish the shoot event + Events::Shoot eShoot; + eShoot.currentAimingPoint = aimingCoordinates; + eShoot.weaponType = (int)player["EquippedItem"]; + m_EventBroker->Publish(eShoot); + } + } } bool PlayerSystem::OnTouch(const Events::TriggerTouch &event) @@ -39,4 +71,15 @@ bool PlayerSystem::OnLeave(const Events::TriggerLeave &event) { LOG_INFO("Player entity %i left widget (entity %i).", event.Entity, event.Trigger); return false; +} + +bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e) +{ + //kolla ammoleft, cooldowntimer shooting + //kolla om left mouse varit nere + if (e.Button != GLFW_MOUSE_BUTTON_LEFT) + return false; + aimingCoordinates = glm::vec2(e.X, e.Y); + leftMouseWasReleased = true; + return true; } \ No newline at end of file diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp new file mode 100644 index 00000000..481772c1 --- /dev/null +++ b/src/Tests/ShootEventTest.cpp @@ -0,0 +1,108 @@ +#include +using boost::unit_test_framework::test_suite; +using boost::unit_test_framework::test_case; + +#include "ShootEventTest.h" +#include "Core\EPlayerDamage.h"; +#include "Core\EPlayerHealthPickup.h"; +#include "Core\EPlayerDeath.h"; +#include "Game/HealthSystem.h" + +BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) + +//AShootEventTest != ShootEventTest -> else it confuses names! +BOOST_AUTO_TEST_CASE(AShootEventTest) +{ + ShootEventTest game; + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_SUITE_END() + +ShootEventTest::ShootEventTest() +{ + ResourceManager::RegisterType("ConfigFile"); + ResourceManager::RegisterType("EntityXMLFile"); + + m_Config = ResourceManager::Load("Config.ini"); + LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); + + // Create the core event broker + m_EventBroker = new EventBroker(); + + // Create a world + m_World = new World(); + std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); + if (!mapToLoad.empty()) { + ResourceManager::Load(mapToLoad)->PopulateWorld(m_World); + } + + // Create system pipeline + m_SystemPipeline = new SystemPipeline(m_EventBroker); + m_SystemPipeline->AddSystem(0); + m_SystemPipeline->AddSystem(0); + + //The Test + //create entity which has transorm,player,model,health in it. i.e. is a player + EntityID playerID = m_World->CreateEntity(); + ComponentWrapper transform = m_World->AttachComponent(playerID, "Transform"); + ComponentWrapper model = m_World->AttachComponent(playerID, "Model"); + model["Resource"] = "Models/Core/UnitSphere.obj"; + ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); + ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); + playersID = playerID; + //attach 2x weaps + ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); + ComponentWrapper& sItem= m_World->AttachComponent(playerID, "SecondaryItem"); + //set currentweap + player["EquippedItem"] = 1; + //set ammo set cooldown + pItem["Ammo"] = 100; + pItem["CoolDownTimer"] = 0.0f; + + //trigger event leftmousedown + Events::MouseRelease eMouseRelease; + eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; + eMouseRelease.X = 1.0f; + eMouseRelease.Y = 1.0f; + m_EventBroker->Publish(eMouseRelease); + +} + +ShootEventTest::~ShootEventTest() +{ + delete m_SystemPipeline; + delete m_World; + delete m_EventBroker; +} + +void ShootEventTest::Tick() +{ + glfwPollEvents(); + + double currentTime = glfwGetTime(); + double dt = currentTime - m_LastTime; + m_LastTime = currentTime; + + // Iterate through systems and update world! + m_SystemPipeline->Update(m_World, dt); + + m_EventBroker->Swap(); + m_EventBroker->Clear(); + + //if ammocount reaches 99 we know the test has succeeded, i.e. a shot has been fired + int currentAmmo = (int)m_World->GetComponent(playersID, "PrimaryItem")["Ammo"]; + if (currentAmmo ==99) + TestSucceeded = true; +} diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h new file mode 100644 index 00000000..49206ceb --- /dev/null +++ b/src/Tests/ShootEventTest.h @@ -0,0 +1,43 @@ +#ifndef ShootEventTest_h__ +#define ShootEventTest_h__ + +#include "Core/ResourceManager.h" +#include "Core/ConfigFile.h" +#include "Core/EventBroker.h" +#include "Rendering/Renderer.h" +#include "Core/InputManager.h" +#include "GUI/Frame.h" +#include "Core/World.h" +#include "Rendering/RenderQueueFactory.h" +#include "Input/InputProxy.h" +#include "Input/KeyboardInputHandler.h" +#include "Input/MouseInputHandler.h" +#include "Core/EKeyDown.h" +#include "Core/EntityXMLFile.h" +#include "Core/SystemPipeline.h" +#include "RaptorCopterSystem.h" +#include "PlayerSystem.h" +#include "Editor/EditorSystem.h" + +#include "Core\EMouseRelease.h" +#include "Core\EShoot.h" + +class ShootEventTest +{ +public: + ShootEventTest(); + ~ShootEventTest(); + + void Tick(); + bool TestSucceeded = false; + +private: + double m_LastTime; + ConfigFile* m_Config = nullptr; + EventBroker* m_EventBroker; + World* m_World; + SystemPipeline* m_SystemPipeline; + int playersID; +}; + +#endif From ec4d5fbfa8c5e99228a4583248370bb8bd51ed48 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 13:34:50 +0100 Subject: [PATCH 033/224] xml/xsd files changed type to double. fixed cooldownbug in PlayerSystem. Added 4 tests in ShootEventTest and generalized it a lot --- resources/Schema/Components/Player.xsd | 5 +- resources/Schema/Components/PrimaryItem.xml | 2 +- resources/Schema/Components/PrimaryItem.xsd | 11 +- resources/Schema/Components/SecondaryItem.xml | 2 +- resources/Schema/Components/SecondaryItem.xsd | 11 +- src/Game/PlayerSystem.cpp | 34 +-- src/Tests/ShootEventTest.cpp | 195 +++++++++++++++--- src/Tests/ShootEventTest.h | 21 +- 8 files changed, 228 insertions(+), 53 deletions(-) diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index fcf07879..9ffc28b0 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -4,6 +4,9 @@ + + The player charachter + @@ -11,7 +14,7 @@ - + diff --git a/resources/Schema/Components/PrimaryItem.xml b/resources/Schema/Components/PrimaryItem.xml index 540a1518..0d0ccca2 100644 --- a/resources/Schema/Components/PrimaryItem.xml +++ b/resources/Schema/Components/PrimaryItem.xml @@ -1,4 +1,4 @@ 0 0 - \ No newline at end of file + \ No newline at end of file diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd index 193b9213..bbff122d 100644 --- a/resources/Schema/Components/PrimaryItem.xsd +++ b/resources/Schema/Components/PrimaryItem.xsd @@ -4,10 +4,17 @@ + + The Players Primary Item/Weapon + - - + + Ammo count + + + Cooldown till next item/weapon use + diff --git a/resources/Schema/Components/SecondaryItem.xml b/resources/Schema/Components/SecondaryItem.xml index 0fae1402..095dfef6 100644 --- a/resources/Schema/Components/SecondaryItem.xml +++ b/resources/Schema/Components/SecondaryItem.xml @@ -1,4 +1,4 @@ 0 0 - \ No newline at end of file + \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd index 44e23611..ab428920 100644 --- a/resources/Schema/Components/SecondaryItem.xsd +++ b/resources/Schema/Components/SecondaryItem.xsd @@ -4,10 +4,17 @@ + + The Players Secondary Item/Weapon + - - + + Ammo count + + + Cooldown till next item/weapon use + diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index f5819ea1..e40469cc 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -27,25 +27,35 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou leftMouseWasReleased = false; //get the health component linked to the playerId double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; - int currentAmmo = 0; - double currentCoolDownTimer = 0.0f; + double currentAmmo = (double)0; + double currentCoolDownTimer = (double)0; - if ((int)player["EquippedItem"] == 1) { + if ((double)player["EquippedItem"] == (double)1) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); currentAmmo = currentItem["Ammo"]; - //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer - currentItem["Ammo"] = (int)currentItem["Ammo"] -1; - int test = (int)currentItem["Ammo"]; - currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "PrimaryItem")["CoolDownTimer"]; + currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if ((int)player["EquippedItem"] == 2) { + if ((double)player["EquippedItem"] == (double)2) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); currentAmmo = currentItem["Ammo"]; - //subtract 1 ammo - the ItemSystem will probably listen to eShoot and handle the CoolDownTimer - currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; - currentCoolDownTimer = (double)world->GetComponent(player.EntityID, "SecondaryItem")["CoolDownTimer"]; + currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (currentHealth > 0.0f && currentAmmo > 0 && currentCoolDownTimer < 0.001f) { + + if (currentHealth > (double)0.0f && currentAmmo > (double)0.0f && currentCoolDownTimer < (double)0.001f) { + //decrease ammo count + //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later + if ((double)player["EquippedItem"] == (double)1) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + int currentAmmoInt = (int)((double)currentItem["Ammo"]); + currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["CoolDownTimer"] = (double)2; + } + if ((double)player["EquippedItem"] == (double)2) { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); + int currentAmmoInt = (int)((double)currentItem["Ammo"]); + currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["CoolDownTimer"] = (double)2; + } //create and publish the shoot event Events::Shoot eShoot; eShoot.currentAimingPoint = aimingCoordinates; diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index 481772c1..22c2a0eb 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -3,17 +3,15 @@ using boost::unit_test_framework::test_suite; using boost::unit_test_framework::test_case; #include "ShootEventTest.h" -#include "Core\EPlayerDamage.h"; -#include "Core\EPlayerHealthPickup.h"; -#include "Core\EPlayerDeath.h"; #include "Game/HealthSystem.h" BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) -//AShootEventTest != ShootEventTest -> else it confuses names! -BOOST_AUTO_TEST_CASE(AShootEventTest) +//dont use the same name as the classname in test cases... +BOOST_AUTO_TEST_CASE(ShootEventTest_PrimaryWeaponFiring) { - ShootEventTest game; + //Test firing primary weapon + ShootEventTest game(1); //100 loops will be more than enough to do the test int loops = 100; bool success = false; @@ -28,9 +26,59 @@ BOOST_AUTO_TEST_CASE(AShootEventTest) //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } +BOOST_AUTO_TEST_CASE(ShootEventTest_SecondaryWeaponFiring) +{ + //Test firing secondary weapon + ShootEventTest game(2); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(ShootEventTest_NoWeaponFiring) +{ + //Test firing with no weapon equipped + ShootEventTest game(3); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + if (game.TestSucceeded) + success = true; + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(ShootEventTest_WeaponOnCooldown) +{ + //Test firing with weapon on cooldown + ShootEventTest game(4); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + if (game.TestSucceeded) + success = true; + BOOST_TEST(success); +} BOOST_AUTO_TEST_SUITE_END() -ShootEventTest::ShootEventTest() +ShootEventTest::ShootEventTest(int runTestNumber) { ResourceManager::RegisterType("ConfigFile"); ResourceManager::RegisterType("EntityXMLFile"); @@ -41,7 +89,7 @@ ShootEventTest::ShootEventTest() // Create the core event broker m_EventBroker = new EventBroker(); - // Create a world + // Create a world m_World = new World(); std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); if (!mapToLoad.empty()) { @@ -54,30 +102,40 @@ ShootEventTest::ShootEventTest() m_SystemPipeline->AddSystem(0); //The Test - //create entity which has transorm,player,model,health in it. i.e. is a player + //create entity which has transform,player,model,health in it. i.e. is a player EntityID playerID = m_World->CreateEntity(); - ComponentWrapper transform = m_World->AttachComponent(playerID, "Transform"); - ComponentWrapper model = m_World->AttachComponent(playerID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; - ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); + m_PlayerID = playerID; ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); - playersID = playerID; + ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); //attach 2x weaps ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); - ComponentWrapper& sItem= m_World->AttachComponent(playerID, "SecondaryItem"); - //set currentweap - player["EquippedItem"] = 1; - //set ammo set cooldown - pItem["Ammo"] = 100; - pItem["CoolDownTimer"] = 0.0f; + ComponentWrapper& sItem = m_World->AttachComponent(playerID, "SecondaryItem"); - //trigger event leftmousedown + m_RunTestNumber = runTestNumber; + switch (runTestNumber) + { + case 1: + TestSetup1(player, pItem, sItem); + break; + case 2: + TestSetup2(player, pItem, sItem); + break; + case 3: + TestSetup3(player, pItem, sItem); + break; + case 4: + TestSetup4(player, pItem, sItem); + break; + default: + break; + } + + //fire once = trigger event leftmousedown Events::MouseRelease eMouseRelease; eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; eMouseRelease.X = 1.0f; eMouseRelease.Y = 1.0f; m_EventBroker->Publish(eMouseRelease); - } ShootEventTest::~ShootEventTest() @@ -87,6 +145,77 @@ ShootEventTest::~ShootEventTest() delete m_EventBroker; } +void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + //set currentweap + player["EquippedItem"] = (double)1.0f; + //set ammo set cooldown + pItem["Ammo"] = (double)100.0f; + pItem["CoolDownTimer"] = (double)0.0f; +} +void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + //set currentweap + player["EquippedItem"] = (double)2.0f; + //set ammo set cooldown + sItem["Ammo"] = (double)10.0f; + sItem["CoolDownTimer"] = (double)0.0f; +} +void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + player["EquippedItem"] = (double)0.0f; + pItem["Ammo"] = (double)100.0f; + sItem["Ammo"] = (double)100.0f; + //TestSucceeded will be set to false if ammo changes during the 100 loops + TestSucceeded = true; +} +void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) +{ + //set currentweap + player["EquippedItem"] = (double)1.0f; + //set ammo set cooldown + pItem["Ammo"] = (double)100.0f; + pItem["CoolDownTimer"] = (double)5.0f; + //TestSucceeded will be set to false if ammo changes during the 100 loops + TestSucceeded = true; +} +void ShootEventTest::TestSuccess1() { + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo == (double)99) + TestSucceeded = true; +} +void ShootEventTest::TestSuccess2() { + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo == (double)9) + TestSucceeded = true; +} +void ShootEventTest::TestSuccess3() { + //try firing again + Events::MouseRelease eMouseRelease; + eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; + eMouseRelease.X = 1.0f; + eMouseRelease.Y = 1.0f; + m_EventBroker->Publish(eMouseRelease); + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + double currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo != (double)100 || currentAmmoSecondary != (double)100) + TestSucceeded = false; +} +void ShootEventTest::TestSuccess4() { + //try firing again + Events::MouseRelease eMouseRelease; + eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; + eMouseRelease.X = 1.0f; + eMouseRelease.Y = 1.0f; + m_EventBroker->Publish(eMouseRelease); + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo != (double)100) + TestSucceeded = false; +} void ShootEventTest::Tick() { glfwPollEvents(); @@ -101,8 +230,22 @@ void ShootEventTest::Tick() m_EventBroker->Swap(); m_EventBroker->Clear(); - //if ammocount reaches 99 we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = (int)m_World->GetComponent(playersID, "PrimaryItem")["Ammo"]; - if (currentAmmo ==99) - TestSucceeded = true; + switch (m_RunTestNumber) + { + case 1: + TestSuccess1(); + break; + case 2: + TestSuccess2(); + break; + case 3: + TestSuccess3(); + break; + case 4: + TestSuccess4(); + break; + default: + break; + } + } diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h index 49206ceb..0ffa1f91 100644 --- a/src/Tests/ShootEventTest.h +++ b/src/Tests/ShootEventTest.h @@ -4,20 +4,14 @@ #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" #include "Core/EventBroker.h" -#include "Rendering/Renderer.h" -#include "Core/InputManager.h" -#include "GUI/Frame.h" #include "Core/World.h" -#include "Rendering/RenderQueueFactory.h" #include "Input/InputProxy.h" #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" #include "Core/EntityXMLFile.h" #include "Core/SystemPipeline.h" -#include "RaptorCopterSystem.h" #include "PlayerSystem.h" -#include "Editor/EditorSystem.h" #include "Core\EMouseRelease.h" #include "Core\EShoot.h" @@ -25,19 +19,30 @@ class ShootEventTest { public: - ShootEventTest(); + ShootEventTest(int runTestNumber); ~ShootEventTest(); void Tick(); bool TestSucceeded = false; private: + void TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); + void TestSuccess1(); + void TestSuccess2(); + void TestSuccess3(); + void TestSuccess4(); + double m_LastTime; ConfigFile* m_Config = nullptr; EventBroker* m_EventBroker; World* m_World; SystemPipeline* m_SystemPipeline; - int playersID; + int m_PlayerID; + int m_RunTestNumber; + }; #endif From 878c71b56a99e24de7ec25d7fb2dafd2109f054a Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 14:37:43 +0100 Subject: [PATCH 034/224] Changed the comparison method in PlayerSystem since its currently using doubles --- src/Game/PlayerSystem.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index e40469cc..2e2120d9 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -30,27 +30,27 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou double currentAmmo = (double)0; double currentCoolDownTimer = (double)0; - if ((double)player["EquippedItem"] == (double)1) { + if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); - currentAmmo = currentItem["Ammo"]; + currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if ((double)player["EquippedItem"] == (double)2) { + if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentAmmo = currentItem["Ammo"]; + currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } if (currentHealth > (double)0.0f && currentAmmo > (double)0.0f && currentCoolDownTimer < (double)0.001f) { //decrease ammo count //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if ((double)player["EquippedItem"] == (double)1) { + if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); currentItem["CoolDownTimer"] = (double)2; } - if ((double)player["EquippedItem"] == (double)2) { + if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); From e865971fdde66b966030a6356265c298ae3014c0 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 15:43:12 +0100 Subject: [PATCH 035/224] EShoot: changed to string weaponType to int currentlyEquippedItem PlayerSystem.h: added HeldItem enum PlayerSystem.cpp: simplified writing doubles, uses HeldItem enum ShootEventTest.cpp: simplified writing doubles --- include/Engine/Core/EShoot.h | 2 +- include/Game/PlayerSystem.h | 5 +++++ src/Game/PlayerSystem.cpp | 20 ++++++++++---------- src/Tests/ShootEventTest.cpp | 32 ++++++++++++++++---------------- 4 files changed, 32 insertions(+), 27 deletions(-) diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h index d9b9e20b..3887606b 100644 --- a/include/Engine/Core/EShoot.h +++ b/include/Engine/Core/EShoot.h @@ -12,7 +12,7 @@ struct Shoot : Event { //shotgun etc has different amounts of damage probably (a sniper shot might one-shot) //also different weapons will have different spread - std::string weaponType; + int currentlyEquippedItem; //currentAimingPoint must be sent, in case the camera is moved while the event is being processed glm::vec2 currentAimingPoint; }; diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 87dc6f5d..3544c63c 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -35,6 +35,11 @@ private: bool PlayerSystem::OnLeave(const Events::TriggerLeave &event); EventRelay m_MouseRelease; bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e); + enum class HeldItem { + None = 0, + PrimaryWeapon = 1, + SecondaryWeapon = 2 + }; }; #endif \ No newline at end of file diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index 2e2120d9..ca39ed4f 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -27,39 +27,39 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou leftMouseWasReleased = false; //get the health component linked to the playerId double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; - double currentAmmo = (double)0; - double currentCoolDownTimer = (double)0; + double currentAmmo = 0.0; + double currentCoolDownTimer = 0.0; - if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); currentAmmo = (double)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (currentHealth > (double)0.0f && currentAmmo > (double)0.0f && currentCoolDownTimer < (double)0.001f) { + if (currentHealth > 0.0 && currentAmmo > 0.0 && currentCoolDownTimer < 0.001) { //decrease ammo count //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if (fabs((double)player["EquippedItem"] - (double)1) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); - currentItem["CoolDownTimer"] = (double)2; + currentItem["CoolDownTimer"] = 2.0;//change later! } - if (fabs((double)player["EquippedItem"] - (double)2) < (double) 0.0001f) { + if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); int currentAmmoInt = (int)((double)currentItem["Ammo"]); currentItem["Ammo"] = (double)(currentAmmoInt - 1); - currentItem["CoolDownTimer"] = (double)2; + currentItem["CoolDownTimer"] = 2.0;//change later! } //create and publish the shoot event Events::Shoot eShoot; eShoot.currentAimingPoint = aimingCoordinates; - eShoot.weaponType = (int)player["EquippedItem"]; + eShoot.currentlyEquippedItem = (int) ((double)player["EquippedItem"]); m_EventBroker->Publish(eShoot); } } diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index 22c2a0eb..67a9985e 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -148,47 +148,47 @@ ShootEventTest::~ShootEventTest() void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = (double)1.0f; + player["EquippedItem"] = 1.0; //set ammo set cooldown - pItem["Ammo"] = (double)100.0f; - pItem["CoolDownTimer"] = (double)0.0f; + pItem["Ammo"] = 100.0; + pItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = (double)2.0f; + player["EquippedItem"] = 2.0; //set ammo set cooldown - sItem["Ammo"] = (double)10.0f; - sItem["CoolDownTimer"] = (double)0.0f; + sItem["Ammo"] = 10.0; + sItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { - player["EquippedItem"] = (double)0.0f; - pItem["Ammo"] = (double)100.0f; - sItem["Ammo"] = (double)100.0f; + player["EquippedItem"] = 0.0; + pItem["Ammo"] = 100.0; + sItem["Ammo"] = 100.0; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = (double)1.0f; + player["EquippedItem"] = 1.0; //set ammo set cooldown - pItem["Ammo"] = (double)100.0f; - pItem["CoolDownTimer"] = (double)5.0f; + pItem["Ammo"] = 100.0; + pItem["CoolDownTimer"] = 5.0; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSuccess1() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo == (double)99) + if (currentAmmo == 99.0) TestSucceeded = true; } void ShootEventTest::TestSuccess2() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo == (double)9) + if (currentAmmo == 9.0) TestSucceeded = true; } void ShootEventTest::TestSuccess3() { @@ -201,7 +201,7 @@ void ShootEventTest::TestSuccess3() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; double currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo != (double)100 || currentAmmoSecondary != (double)100) + if (currentAmmo != 100.0 || currentAmmoSecondary != 100.0) TestSucceeded = false; } void ShootEventTest::TestSuccess4() { @@ -213,7 +213,7 @@ void ShootEventTest::TestSuccess4() { m_EventBroker->Publish(eMouseRelease); //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo != (double)100) + if (currentAmmo != 100.0) TestSucceeded = false; } void ShootEventTest::Tick() From 4b672b11e7651e6728004de1c7d337f88ba5226a Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 17:15:49 +0100 Subject: [PATCH 036/224] EquippedItem,Ammo got changed to int instead of double. Loading entities from map the new way in Tests. ComponentWrapper:s Name is now Type --- include/Engine/Core/ComponentWrapper.h | 2 +- include/Game/PlayerSystem.h | 4 +- resources/Schema/Components/Player.xsd | 2 +- resources/Schema/Components/PrimaryItem.xsd | 2 +- resources/Schema/Components/SecondaryItem.xsd | 2 +- src/Game/PlayerSystem.cpp | 22 ++++---- src/Tests/HealthSystemTest.cpp | 9 +++- src/Tests/HealthSystemTest.h | 2 +- src/Tests/OctTreeTestGameClass.cpp | 2 +- src/Tests/OctTreeTestGameClass.h | 2 +- src/Tests/ResourceManagerTest.cpp | 1 - src/Tests/ShootEventTest.cpp | 53 ++++++++++--------- src/Tests/ShootEventTest.h | 6 ++- 13 files changed, 60 insertions(+), 49 deletions(-) diff --git a/include/Engine/Core/ComponentWrapper.h b/include/Engine/Core/ComponentWrapper.h index 922b3d79..f4761e40 100644 --- a/include/Engine/Core/ComponentWrapper.h +++ b/include/Engine/Core/ComponentWrapper.h @@ -78,7 +78,7 @@ public: void AddProperty(std::string fieldName, T defaultValue) { m_DefaultValues.push_back(defaultValue); - m_ComponentInfo.Fields[fieldName].Name = typeid(T).name(); + m_ComponentInfo.Fields[fieldName].Type = typeid(T).name(); m_ComponentInfo.Fields[fieldName].Offset = m_ComponentInfo.Meta.Stride; m_ComponentInfo.Fields[fieldName].Stride = sizeof(T); m_ComponentInfo.Meta.Stride += sizeof(T); diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 3544c63c..897ee207 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -37,8 +37,8 @@ private: bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e); enum class HeldItem { None = 0, - PrimaryWeapon = 1, - SecondaryWeapon = 2 + PrimaryItem = 1, + SecondaryItem = 2 }; }; diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 9ffc28b0..617b7d30 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -14,7 +14,7 @@ - + diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd index bbff122d..35e2fca6 100644 --- a/resources/Schema/Components/PrimaryItem.xsd +++ b/resources/Schema/Components/PrimaryItem.xsd @@ -9,7 +9,7 @@ - + Ammo count diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd index ab428920..bee25541 100644 --- a/resources/Schema/Components/SecondaryItem.xsd +++ b/resources/Schema/Components/SecondaryItem.xsd @@ -9,7 +9,7 @@ - + Ammo count diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index ca39ed4f..dff5c410 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -27,33 +27,31 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou leftMouseWasReleased = false; //get the health component linked to the playerId double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; - double currentAmmo = 0.0; + int currentAmmo = 0; double currentCoolDownTimer = 0.0; - if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); - currentAmmo = (double)currentItem["Ammo"]; + currentAmmo = (int)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentAmmo = (double)currentItem["Ammo"]; + currentAmmo = (int)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; } - if (currentHealth > 0.0 && currentAmmo > 0.0 && currentCoolDownTimer < 0.001) { + if (currentHealth > 0.0 && currentAmmo > 0 && currentCoolDownTimer < 0.001) { //decrease ammo count //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if (fabs((double)player["EquippedItem"] - (double)HeldItem::PrimaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); - int currentAmmoInt = (int)((double)currentItem["Ammo"]); - currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; currentItem["CoolDownTimer"] = 2.0;//change later! } - if (fabs((double)player["EquippedItem"] - (double)HeldItem::SecondaryWeapon) < 0.0001) { + if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - int currentAmmoInt = (int)((double)currentItem["Ammo"]); - currentItem["Ammo"] = (double)(currentAmmoInt - 1); + currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; currentItem["CoolDownTimer"] = 2.0;//change later! } //create and publish the shoot event diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index 84d6199d..feab858a 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -30,7 +30,7 @@ BOOST_AUTO_TEST_SUITE_END() GameHealthSystemTest::GameHealthSystemTest() { ResourceManager::RegisterType("ConfigFile"); - ResourceManager::RegisterType("EntityXMLFile"); + ResourceManager::RegisterType("EntityFile"); m_Config = ResourceManager::Load("Config.ini"); LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); @@ -41,8 +41,13 @@ GameHealthSystemTest::GameHealthSystemTest() // Create a world m_World = new World(); std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); + if (!mapToLoad.empty()) { - ResourceManager::Load(mapToLoad)->PopulateWorld(m_World); + auto file = ResourceManager::Load(mapToLoad); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(m_World); + EntityFileParser fp(file); + fp.MergeEntities(m_World); } // Create system pipeline diff --git a/src/Tests/HealthSystemTest.h b/src/Tests/HealthSystemTest.h index 664d2ef3..2890dfc1 100644 --- a/src/Tests/HealthSystemTest.h +++ b/src/Tests/HealthSystemTest.h @@ -13,7 +13,7 @@ #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" -#include "Core/EntityXMLFile.h" +#include "Core/EntityFile.h" #include "Core/SystemPipeline.h" #include "RaptorCopterSystem.h" #include "PlayerSystem.h" diff --git a/src/Tests/OctTreeTestGameClass.cpp b/src/Tests/OctTreeTestGameClass.cpp index 10d4d6a5..0f195cec 100644 --- a/src/Tests/OctTreeTestGameClass.cpp +++ b/src/Tests/OctTreeTestGameClass.cpp @@ -5,7 +5,7 @@ Game::Game(int argc, char* argv[]) : someOctTree(AABB(-0.5f*worldSize, 0.5f*worl ResourceManager::RegisterType("ConfigFile"); ResourceManager::RegisterType("Model"); ResourceManager::RegisterType("Texture"); - ResourceManager::RegisterType("EntityXMLFile"); + ResourceManager::RegisterType("EntityFile"); ResourceManager::RegisterType("ShaderProgram"); m_Config = ResourceManager::Load("Config.ini"); diff --git a/src/Tests/OctTreeTestGameClass.h b/src/Tests/OctTreeTestGameClass.h index 6dc9404e..c36707c8 100644 --- a/src/Tests/OctTreeTestGameClass.h +++ b/src/Tests/OctTreeTestGameClass.h @@ -13,7 +13,7 @@ #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" -#include "Core/EntityXMLFile.h" +#include "Core/EntityFile.h" #include "Core/SystemPipeline.h" #include "RaptorCopterSystem.h" #include "PlayerSystem.h" diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index a3edb7b8..9d62fa93 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -7,7 +7,6 @@ #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" #include "Rendering/Renderer.h" -#include "Core/EntityXMLFile.h" #include "Engine\Rendering\Texture.h" BOOST_AUTO_TEST_SUITE(resourceManagerTests) diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp index 67a9985e..f24bfed8 100644 --- a/src/Tests/ShootEventTest.cpp +++ b/src/Tests/ShootEventTest.cpp @@ -81,9 +81,10 @@ BOOST_AUTO_TEST_SUITE_END() ShootEventTest::ShootEventTest(int runTestNumber) { ResourceManager::RegisterType("ConfigFile"); - ResourceManager::RegisterType("EntityXMLFile"); + ResourceManager::RegisterType("EntityFile"); m_Config = ResourceManager::Load("Config.ini"); + std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); // Create the core event broker @@ -91,22 +92,26 @@ ShootEventTest::ShootEventTest(int runTestNumber) // Create a world m_World = new World(); - std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); - if (!mapToLoad.empty()) { - ResourceManager::Load(mapToLoad)->PopulateWorld(m_World); - } // Create system pipeline m_SystemPipeline = new SystemPipeline(m_EventBroker); m_SystemPipeline->AddSystem(0); m_SystemPipeline->AddSystem(0); + if (!mapToLoad.empty()) { + auto file = ResourceManager::Load(mapToLoad); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(m_World); + EntityFileParser fp(file); + fp.MergeEntities(m_World); + } + //The Test //create entity which has transform,player,model,health in it. i.e. is a player EntityID playerID = m_World->CreateEntity(); m_PlayerID = playerID; - ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); + ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); //attach 2x weaps ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); ComponentWrapper& sItem = m_World->AttachComponent(playerID, "SecondaryItem"); @@ -148,47 +153,47 @@ ShootEventTest::~ShootEventTest() void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = 1.0; + player["EquippedItem"] = 1; //set ammo set cooldown - pItem["Ammo"] = 100.0; + pItem["Ammo"] = 100; pItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = 2.0; + player["EquippedItem"] = 2; //set ammo set cooldown - sItem["Ammo"] = 10.0; + sItem["Ammo"] = 10; sItem["CoolDownTimer"] = 0.0; } void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { - player["EquippedItem"] = 0.0; - pItem["Ammo"] = 100.0; - sItem["Ammo"] = 100.0; + player["EquippedItem"] = 0; + pItem["Ammo"] = 100; + sItem["Ammo"] = 100; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) { //set currentweap - player["EquippedItem"] = 1.0; + player["EquippedItem"] = 1; //set ammo set cooldown - pItem["Ammo"] = 100.0; + pItem["Ammo"] = 100; pItem["CoolDownTimer"] = 5.0; //TestSucceeded will be set to false if ammo changes during the 100 loops TestSucceeded = true; } void ShootEventTest::TestSuccess1() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo == 99.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo == 99) TestSucceeded = true; } void ShootEventTest::TestSuccess2() { //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo == 9.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo == 9) TestSucceeded = true; } void ShootEventTest::TestSuccess3() { @@ -199,9 +204,9 @@ void ShootEventTest::TestSuccess3() { eMouseRelease.Y = 1.0f; m_EventBroker->Publish(eMouseRelease); //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - double currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo != 100.0 || currentAmmoSecondary != 100.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + int currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; + if (currentAmmo != 100 || currentAmmoSecondary != 100) TestSucceeded = false; } void ShootEventTest::TestSuccess4() { @@ -212,8 +217,8 @@ void ShootEventTest::TestSuccess4() { eMouseRelease.Y = 1.0f; m_EventBroker->Publish(eMouseRelease); //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - double currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo != 100.0) + int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; + if (currentAmmo != 100) TestSucceeded = false; } void ShootEventTest::Tick() diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h index 0ffa1f91..21ae7d9e 100644 --- a/src/Tests/ShootEventTest.h +++ b/src/Tests/ShootEventTest.h @@ -9,10 +9,14 @@ #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" #include "Core/EKeyDown.h" -#include "Core/EntityXMLFile.h" +#include "Core/EntityFile.h" #include "Core/SystemPipeline.h" #include "PlayerSystem.h" +#include "Core/EntityFilePreprocessor.h" +#include "Core/EntityFileParser.h" +#include "Core/EntityFileWriter.h" + #include "Core\EMouseRelease.h" #include "Core\EShoot.h" From f0b425614d76ea978b61959f9423ff6150b586ec Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 11 Jan 2016 17:36:23 +0100 Subject: [PATCH 037/224] Simplified PlayerSystem branches a lot! Thanks William! --- src/Game/PlayerSystem.cpp | 38 +++++++++++++++----------------------- 1 file changed, 15 insertions(+), 23 deletions(-) diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index dff5c410..c9112b01 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -29,36 +29,28 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; int currentAmmo = 0; double currentCoolDownTimer = 0.0; + std::string HeldItemString = ""; + if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) + HeldItemString = "PrimaryItem"; + if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) + HeldItemString = "SecondaryItem"; - if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + if (HeldItemString != "") { + ComponentWrapper& currentItem = world->GetComponent(player.EntityID, HeldItemString); currentAmmo = (int)currentItem["Ammo"]; currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; - } - if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentAmmo = (int)currentItem["Ammo"]; - currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; - } - if (currentHealth > 0.0 && currentAmmo > 0 && currentCoolDownTimer < 0.001) { - //decrease ammo count - //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "PrimaryItem"); + if (currentHealth > 0.0 && currentAmmo > 0 && currentCoolDownTimer < 0.001) { + //decrease ammo count + //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; currentItem["CoolDownTimer"] = 2.0;//change later! + //create and publish the shoot event + Events::Shoot eShoot; + eShoot.currentAimingPoint = aimingCoordinates; + eShoot.currentlyEquippedItem = (int)(player["EquippedItem"]); + m_EventBroker->Publish(eShoot); } - if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, "SecondaryItem"); - currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; - currentItem["CoolDownTimer"] = 2.0;//change later! - } - //create and publish the shoot event - Events::Shoot eShoot; - eShoot.currentAimingPoint = aimingCoordinates; - eShoot.currentlyEquippedItem = (int) ((double)player["EquippedItem"]); - m_EventBroker->Publish(eShoot); } } } From 147b116f2088cf7bae6aa4a76c7671e4d97d11a1 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Tue, 12 Jan 2016 10:46:34 +0100 Subject: [PATCH 038/224] Fixed typo backslash instead of slash in various classes (the includes) --- include/Game/HealthSystem.h | 6 +++--- include/Game/PlayerSystem.h | 4 ++-- src/Tests/CollisionTest.cpp | 6 +++--- src/Tests/ConfigFileTest.cpp | 2 +- src/Tests/EventFixture.h | 2 +- src/Tests/InputManagerTest.cpp | 2 +- src/Tests/OctTreeTestAnders.cpp | 2 +- src/Tests/OctTreeTestHardCodedTestWorld.h | 2 +- src/Tests/ResourceManagerTest.cpp | 2 +- src/Tests/ShootEventTest.h | 4 ++-- 10 files changed, 16 insertions(+), 16 deletions(-) diff --git a/include/Game/HealthSystem.h b/include/Game/HealthSystem.h index a836e797..11ac68bd 100644 --- a/include/Game/HealthSystem.h +++ b/include/Game/HealthSystem.h @@ -6,9 +6,9 @@ #include "Common.h" #include "Core/System.h" -#include "Core\EPlayerDamage.h"; -#include "Core\EPlayerHealthPickup.h"; -#include "Core\EPlayerDeath.h"; +#include "Core/EPlayerDamage.h"; +#include "Core/EPlayerHealthPickup.h"; +#include "Core/EPlayerDeath.h"; #include #include diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index 897ee207..a48af3e4 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -7,8 +7,8 @@ #include "Common.h" #include "Core/System.h" #include "Collision/ETrigger.h" -#include "Core\EMouseRelease.h" -#include "Core\EShoot.h" +#include "Core/EMouseRelease.h" +#include "Core/EShoot.h" class PlayerSystem : public PureSystem { diff --git a/src/Tests/CollisionTest.cpp b/src/Tests/CollisionTest.cpp index e6a29298..57329477 100644 --- a/src/Tests/CollisionTest.cpp +++ b/src/Tests/CollisionTest.cpp @@ -13,9 +13,9 @@ using boost::unit_test_framework::test_case; #include //ray vs model -#include "Engine\Core\ResourceManager.h" -#include "Engine\Rendering\Model.h" -#include "Engine\Core\Ray.h" +#include "Engine/Core/ResourceManager.h" +#include "Engine/Rendering/Model.h" +#include "Engine/Core/Ray.h" //vs memleaks //#define _CRTDBG_MAP_ALLOC diff --git a/src/Tests/ConfigFileTest.cpp b/src/Tests/ConfigFileTest.cpp index 28be5589..36cd6c05 100644 --- a/src/Tests/ConfigFileTest.cpp +++ b/src/Tests/ConfigFileTest.cpp @@ -5,7 +5,7 @@ using boost::unit_test_framework::test_case; #include //srand //#define private public -#include "Engine\Core\ConfigFile.h" +#include "Engine/Core/ConfigFile.h" #define _CRTDBG_MAP_ALLOC #include diff --git a/src/Tests/EventFixture.h b/src/Tests/EventFixture.h index 42258932..a708b962 100644 --- a/src/Tests/EventFixture.h +++ b/src/Tests/EventFixture.h @@ -2,7 +2,7 @@ #define EVENTFIXTURE_H #include -#include "Core\EventBroker.h" +#include "Core/EventBroker.h" template struct EventFixture diff --git a/src/Tests/InputManagerTest.cpp b/src/Tests/InputManagerTest.cpp index 5b447c2b..0ef9434a 100644 --- a/src/Tests/InputManagerTest.cpp +++ b/src/Tests/InputManagerTest.cpp @@ -1,6 +1,6 @@ #include -#include "Engine\Core\InputManager.h" +#include "Engine/Core/InputManager.h" BOOST_AUTO_TEST_SUITE(inputManagerTests) diff --git a/src/Tests/OctTreeTestAnders.cpp b/src/Tests/OctTreeTestAnders.cpp index b61caead..477ccbf4 100644 --- a/src/Tests/OctTreeTestAnders.cpp +++ b/src/Tests/OctTreeTestAnders.cpp @@ -15,7 +15,7 @@ using boost::unit_test_framework::test_case; #include "OctTreeTestGameClass.h" #define private public//HACK! Needed for white box testing -#include +#include "Engine/Core/OctTree.h" //else we would have to "open up" the octTree class more with get/sets, public methods, etc. which is not good encapsulation-wise BOOST_AUTO_TEST_SUITE(octTreeTestsA) diff --git a/src/Tests/OctTreeTestHardCodedTestWorld.h b/src/Tests/OctTreeTestHardCodedTestWorld.h index 512716df..6f68eba6 100644 --- a/src/Tests/OctTreeTestHardCodedTestWorld.h +++ b/src/Tests/OctTreeTestHardCodedTestWorld.h @@ -9,7 +9,7 @@ //last! //#include "OldOctTree.h" #define private public -#include +#include class HardcodedTestWorld : public World { diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index 9d62fa93..b68936ec 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -7,7 +7,7 @@ #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" #include "Rendering/Renderer.h" -#include "Engine\Rendering\Texture.h" +#include "Engine/Rendering/Texture.h" BOOST_AUTO_TEST_SUITE(resourceManagerTests) diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h index 21ae7d9e..e860f41f 100644 --- a/src/Tests/ShootEventTest.h +++ b/src/Tests/ShootEventTest.h @@ -17,8 +17,8 @@ #include "Core/EntityFileParser.h" #include "Core/EntityFileWriter.h" -#include "Core\EMouseRelease.h" -#include "Core\EShoot.h" +#include "Core/EMouseRelease.h" +#include "Core/EShoot.h" class ShootEventTest { From 59be714fdc8f4638ef547db6cc76b6e1b026068e Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Tue, 12 Jan 2016 16:35:55 +0100 Subject: [PATCH 039/224] 1 Component added: CapturePoint 1 System added: CapturePointSystem 1 Test added: CapturePointTest added 1 variable in PlayerComponent (TeamNumber) added 2 variables in CapturePoint (CaptureTimer,OwnedBy) CapturePointSystem is now handling 2 events: OnTriggerTouch,OnTriggerLeave Added the CapturePointSystem to Game.cpp --- include/Game/CapturePointSystem.h | 35 +++++ resources/Schema/Components.xsd | 2 +- resources/Schema/Components/CapturePoint.xml | 4 + resources/Schema/Components/CapturePoint.xsd | 17 +++ resources/Schema/Components/Player.xml | 1 + resources/Schema/Components/Player.xsd | 1 + resources/Schema/Types/Entity.xsd | 1 + src/Game/CapturePointSystem.cpp | 91 +++++++++++++ src/Game/Game.cpp | 2 + src/Tests/CapturePointTest.cpp | 130 +++++++++++++++++++ src/Tests/CapturePointTest.h | 42 ++++++ 11 files changed, 325 insertions(+), 1 deletion(-) create mode 100644 include/Game/CapturePointSystem.h create mode 100644 resources/Schema/Components/CapturePoint.xml create mode 100644 resources/Schema/Components/CapturePoint.xsd create mode 100644 src/Game/CapturePointSystem.cpp create mode 100644 src/Tests/CapturePointTest.cpp create mode 100644 src/Tests/CapturePointTest.h diff --git a/include/Game/CapturePointSystem.h b/include/Game/CapturePointSystem.h new file mode 100644 index 00000000..6030ad74 --- /dev/null +++ b/include/Game/CapturePointSystem.h @@ -0,0 +1,35 @@ +#ifndef CapturePointSystem_h__ +#define CapturePointSystem_h__ + +#include +#include + +#include "Common.h" +#include "Core/System.h" +#include "Engine/Collision/ETrigger.h" + +#include +#include + +class CapturePointSystem : public PureSystem +{ +public: + //TODO: on new map, destroy all info in the vectors + CapturePointSystem(EventBroker* eventBroker); + + //updatecomponent + virtual void UpdateComponent(World* world, ComponentWrapper& capturePoint, double dt) override; + +private: + //methods which will take care of specific events + EventRelay m_ETriggerTouch; + bool CapturePointSystem::OnTriggerTouch(const Events::TriggerTouch& e); + EventRelay m_ETriggerLeave; + bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e); + + //vectors which will keep track of enter/leave changes + std::vector> m_ETriggerTouchVector; + std::vector> m_ETriggerLeaveVector; +}; + +#endif \ No newline at end of file diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index 33714638..1a78ed0c 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -11,5 +11,5 @@ - + \ No newline at end of file diff --git a/resources/Schema/Components/CapturePoint.xml b/resources/Schema/Components/CapturePoint.xml new file mode 100644 index 00000000..efab1a5a --- /dev/null +++ b/resources/Schema/Components/CapturePoint.xml @@ -0,0 +1,4 @@ + + 0 + 0 + \ No newline at end of file diff --git a/resources/Schema/Components/CapturePoint.xsd b/resources/Schema/Components/CapturePoint.xsd new file mode 100644 index 00000000..09842933 --- /dev/null +++ b/resources/Schema/Components/CapturePoint.xsd @@ -0,0 +1,17 @@ + + + + + + + + A Capture Point + + + + + + + + + \ No newline at end of file diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index cd3d1620..a05c003e 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,4 +1,5 @@ + 0 0 false diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 617b7d30..49b0537a 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -15,6 +15,7 @@ + diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 4b67276a..2f352354 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -18,6 +18,7 @@ + diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp new file mode 100644 index 00000000..b7c32c5e --- /dev/null +++ b/src/Game/CapturePointSystem.cpp @@ -0,0 +1,91 @@ +#include "CapturePointSystem.h" +#include + +CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) + : PureSystem(eventBroker, "CapturePoint") +{ + //subscribe/listenTo playerdamage,healthpickup events (using the eventBroker) + EVENT_SUBSCRIBE_MEMBER(m_ETriggerTouch, &CapturePointSystem::OnTriggerTouch); + EVENT_SUBSCRIBE_MEMBER(m_ETriggerLeave, &CapturePointSystem::OnTriggerLeave); +} + +//here all capturepoints will update their component +void CapturePointSystem::UpdateComponent(World *world, ComponentWrapper &capturePoint, double dt) +{ + //NOTE: needs to run each frame, since we're possibly increasing the captureTimer for the capturePoint by dt + int firstTeamPlayersStandingInside = 0; + int secondTeamPlayersStandingInside = 0; + + for (size_t i = 0; i < m_ETriggerTouchVector.size(); i++) + { + auto triggerTouched = m_ETriggerTouchVector[i]; + if (std::get<1>(triggerTouched) == capturePoint.EntityID) { + //some player has touched this - lets figure out: what team, health + EntityID playerID = std::get<0>(triggerTouched); + bool hasHealthComponent = world->HasComponent(playerID, "Health"); + if (!hasHealthComponent) + continue; + double currentHealth = world->GetComponent(playerID, "Health")["Health"]; + //check if player is dead + if ((int)currentHealth == 0) + continue; + //check team - 0 = no team + int teamNumber = (int)world->GetComponent(playerID, "Player")["TeamNumber"]; + if (teamNumber == 1) + firstTeamPlayersStandingInside++; + if (teamNumber == 2) + secondTeamPlayersStandingInside++; + continue; + } + } + + int ownedBy = capturePoint["OwnedBy"]; + double captureTimer = capturePoint["CaptureTimer"]; + + //A.nobodys standing inside + if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside == 0) { + //do nothing (?) + } + //B.first team has players but second none + if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside == 0) { + if (ownedBy == 2 || ownedBy == 0) + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + dt; + //check if captureTimer > 5 and if so change owner + if ((double)capturePoint["CaptureTimer"] > 5.0) { + capturePoint["OwnedBy"] = 1; + capturePoint["CaptureTimer"] = 0; + } + } + //C.second team has players but second none + if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0) { + + } + //D.both teams have players inside + if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside > 0) { + + } + + + +} + +bool CapturePointSystem::OnTriggerTouch(const Events::TriggerTouch& e) +{ + //auto personEntered = e.Entity; + //auto thingEntered = e.Trigger; + m_ETriggerTouchVector.push_back(std::make_tuple(e.Entity, e.Trigger)); + return true; +} + +bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e) +{ + for (size_t i = 0; i < m_ETriggerTouchVector.size(); i++) + { + auto triggerTouched = m_ETriggerTouchVector[i]; + if (std::get<0>(triggerTouched) == e.Entity && std::get<1>(triggerTouched) == e.Trigger) { + m_ETriggerTouchVector.erase(m_ETriggerTouchVector.begin() + i); + break; + } + } + return true; +} diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index c84c556b..4608d0b6 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -3,6 +3,7 @@ #include "Collision/CollisionSystem.h" #include "Game/HealthSystem.h" #include "Core/EntityFileWriter.h" +#include "Game/CapturePointSystem.h" Game::Game(int argc, char* argv[]) { @@ -70,6 +71,7 @@ Game::Game(int argc, char* argv[]) ++updateOrderLevel; m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); + m_SystemPipeline->AddSystem(updateOrderLevel); // Invoke network if (m_Config->Get("Networking.StartNetwork", false)) { diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp new file mode 100644 index 00000000..a0d61e04 --- /dev/null +++ b/src/Tests/CapturePointTest.cpp @@ -0,0 +1,130 @@ +#include +using boost::unit_test_framework::test_suite; +using boost::unit_test_framework::test_case; + +#include "CapturePointTest.h" +#include "Game/HealthSystem.h" + +#include "Collision/TriggerSystem.h" +#include "Collision/CollisionSystem.h" +#include "Core/EntityFileWriter.h" +#include "Game/CapturePointSystem.h" + +BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) + +//dont use the same name as the classname in test cases... +BOOST_AUTO_TEST_CASE(CapturePointTest1) +{ + //Test firing primary weapon + CapturePointTest game(1); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_SUITE_END() + +CapturePointTest::CapturePointTest(int runTestNumber) +{ + ResourceManager::RegisterType("ConfigFile"); + ResourceManager::RegisterType("EntityFile"); + + m_Config = ResourceManager::Load("Config.ini"); + std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); + LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); + + // Create the core event broker + m_EventBroker = new EventBroker(); + + // Create a world + m_World = new World(); + + // Create system pipeline + m_SystemPipeline = new SystemPipeline(m_EventBroker); + m_SystemPipeline->AddSystem(0); + m_SystemPipeline->AddSystem(0); + m_SystemPipeline->AddSystem(1); + m_SystemPipeline->AddSystem(1); + m_SystemPipeline->AddSystem(1); + + if (!mapToLoad.empty()) { + auto file = ResourceManager::Load(mapToLoad); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(m_World); + EntityFileParser fp(file); + fp.MergeEntities(m_World); + } + + //The Test + //create entity which has transform,player,model,health in it. i.e. is a player + EntityID playerID = m_World->CreateEntity(); + m_PlayerID = playerID; + ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); + ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); + player["TeamNumber"] = 1; + + EntityID playerID2 = m_World->CreateEntity(); + ComponentWrapper& player2 = m_World->AttachComponent(playerID2, "Player"); + m_PlayerID2 = playerID2; + ComponentWrapper health2 = m_World->AttachComponent(playerID2, "Health"); + player2["TeamNumber"] = 2; + + EntityID capturePointID = m_World->CreateEntity(); + ComponentWrapper& capPointComp = m_World->AttachComponent(capturePointID, "CapturePoint"); + m_CapturePointID = capturePointID; + m_RunTestNumber = runTestNumber; + + //add some touch/leave events + Events::TriggerTouch eTriggerTouched; + eTriggerTouched.Entity = m_PlayerID; + eTriggerTouched.Trigger = m_CapturePointID; + m_EventBroker->Publish(eTriggerTouched); + + Events::TriggerTouch eTriggerTouched2; + eTriggerTouched2.Entity = m_PlayerID2; + eTriggerTouched2.Trigger = m_CapturePointID; + m_EventBroker->Publish(eTriggerTouched2); + + Events::TriggerLeave eTriggerLeft; + eTriggerLeft.Entity = m_PlayerID; + eTriggerLeft.Trigger = m_CapturePointID; + m_EventBroker->Publish(eTriggerLeft); + + Events::TriggerTouch eTriggerTouched3; + eTriggerTouched3.Entity = m_PlayerID; + eTriggerTouched3.Trigger = m_CapturePointID; + m_EventBroker->Publish(eTriggerTouched3); + +} + +CapturePointTest::~CapturePointTest() +{ + delete m_SystemPipeline; + delete m_World; + delete m_EventBroker; +} + +void CapturePointTest::Tick() +{ + glfwPollEvents(); + + double currentTime = glfwGetTime(); + double dt = currentTime - m_LastTime; + m_LastTime = currentTime; + + // Iterate through systems and update world! + m_SystemPipeline->Update(m_World, dt); + + m_EventBroker->Swap(); + m_EventBroker->Clear(); + +} diff --git a/src/Tests/CapturePointTest.h b/src/Tests/CapturePointTest.h new file mode 100644 index 00000000..c0244802 --- /dev/null +++ b/src/Tests/CapturePointTest.h @@ -0,0 +1,42 @@ +#ifndef CapturePointTest_h__ +#define CapturePointTest_h__ + +#include "Core/ResourceManager.h" +#include "Core/ConfigFile.h" +#include "Core/EventBroker.h" +#include "Core/World.h" +#include "Input/InputProxy.h" +#include "Input/KeyboardInputHandler.h" +#include "Input/MouseInputHandler.h" +#include "Core/EKeyDown.h" +#include "Core/EntityFile.h" +#include "Core/SystemPipeline.h" +#include "PlayerSystem.h" + +#include "Core/EntityFilePreprocessor.h" +#include "Core/EntityFileParser.h" +#include "Core/EntityFileWriter.h" + +#include "Engine/Collision/ETrigger.h" + +class CapturePointTest +{ +public: + CapturePointTest(int runTestNumber); + ~CapturePointTest(); + + void Tick(); + bool TestSucceeded = false; + +private: + double m_LastTime; + ConfigFile* m_Config = nullptr; + EventBroker* m_EventBroker; + World* m_World; + SystemPipeline* m_SystemPipeline; + int m_PlayerID, m_PlayerID2, m_CapturePointID; + int m_RunTestNumber; + +}; + +#endif From 3a1056a2c376b1102bd6164bf4dbc4b18b6b2b68 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Tue, 12 Jan 2016 17:38:02 +0100 Subject: [PATCH 040/224] 2 new Events: ECaptured, EWin Added new variable in CapturePoint: IsHomeCapturePointForTeam CapturePointSystem updated so -5 = team 2 owns it, +5 = team 1 owns it. Its also looking for a winner each update Updated Test. TODO: better Tests --- include/Engine/Core/ECaptured.h | 20 +++++++++++ include/Engine/Core/EWin.h | 20 +++++++++++ include/Game/CapturePointSystem.h | 4 +++ resources/Schema/Components/CapturePoint.xml | 1 + resources/Schema/Components/CapturePoint.xsd | 1 + src/Game/CapturePointSystem.cpp | 37 +++++++++++++++++--- src/Tests/CapturePointTest.cpp | 15 +++++--- 7 files changed, 88 insertions(+), 10 deletions(-) create mode 100644 include/Engine/Core/ECaptured.h create mode 100644 include/Engine/Core/EWin.h diff --git a/include/Engine/Core/ECaptured.h b/include/Engine/Core/ECaptured.h new file mode 100644 index 00000000..d891c7b0 --- /dev/null +++ b/include/Engine/Core/ECaptured.h @@ -0,0 +1,20 @@ +#ifndef ECaptured_h__ +#define ECaptured_h__ + +#include "EventBroker.h" +#include "../Core/Entity.h" +#include "Engine/GLM.h" + +namespace Events +{ + + //triggers when a capturePoint has been taken over +struct Captured : Event +{ + int TeamNumberThatCapturedCapturePoint; + EntityID CapturePointID; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Engine/Core/EWin.h b/include/Engine/Core/EWin.h new file mode 100644 index 00000000..a2e96139 --- /dev/null +++ b/include/Engine/Core/EWin.h @@ -0,0 +1,20 @@ +#ifndef EWin_h__ +#define EWin_h__ + +#include "EventBroker.h" +#include "../Core/Entity.h" +#include "Engine/GLM.h" + +namespace Events +{ + + //triggers when a team has captured all capturePoints +struct Win : Event +{ + //can be 0 = none, 1,2 + int TeamThatWon; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Game/CapturePointSystem.h b/include/Game/CapturePointSystem.h index 6030ad74..8888da30 100644 --- a/include/Game/CapturePointSystem.h +++ b/include/Game/CapturePointSystem.h @@ -7,6 +7,8 @@ #include "Common.h" #include "Core/System.h" #include "Engine/Collision/ETrigger.h" +#include "Core/ECaptured.h" +#include "Core/EWin.h" #include #include @@ -27,6 +29,8 @@ private: EventRelay m_ETriggerLeave; bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e); + bool WinnerWasFound = false; + //vectors which will keep track of enter/leave changes std::vector> m_ETriggerTouchVector; std::vector> m_ETriggerLeaveVector; diff --git a/resources/Schema/Components/CapturePoint.xml b/resources/Schema/Components/CapturePoint.xml index efab1a5a..fddd1042 100644 --- a/resources/Schema/Components/CapturePoint.xml +++ b/resources/Schema/Components/CapturePoint.xml @@ -1,4 +1,5 @@ 0 0 + 0 \ No newline at end of file diff --git a/resources/Schema/Components/CapturePoint.xsd b/resources/Schema/Components/CapturePoint.xsd index 09842933..b1cbe173 100644 --- a/resources/Schema/Components/CapturePoint.xsd +++ b/resources/Schema/Components/CapturePoint.xsd @@ -11,6 +11,7 @@ + diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp index b7c32c5e..b276cb98 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/CapturePointSystem.cpp @@ -42,30 +42,57 @@ void CapturePointSystem::UpdateComponent(World *world, ComponentWrapper &capture int ownedBy = capturePoint["OwnedBy"]; double captureTimer = capturePoint["CaptureTimer"]; + //+-5 + //A.nobodys standing inside if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside == 0) { //do nothing (?) } //B.first team has players but second none if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside == 0) { + //ownedBy 1 -> timer should stay at 5 if (ownedBy == 2 || ownedBy == 0) capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + dt; - //check if captureTimer > 5 and if so change owner - if ((double)capturePoint["CaptureTimer"] > 5.0) { + //check if captureTimer > 5 and if so change owner and publish the eCaptured event + if ((double)capturePoint["CaptureTimer"] > 5) { capturePoint["OwnedBy"] = 1; - capturePoint["CaptureTimer"] = 0; + capturePoint["CaptureTimer"] = 0.0; + Events::Captured e; + e.CapturePointID = capturePoint.EntityID; + e.TeamNumberThatCapturedCapturePoint = 1; + m_EventBroker->Publish(e); } } //C.second team has players but second none if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0) { + //ownedBy 2 -> timer should stay at -5 + if (ownedBy == 1 || ownedBy == 0) + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] - dt; + //check if captureTimer > 5 and if so change owner and publish the eCaptured event + if ((double)capturePoint["CaptureTimer"] < -5.0) { + capturePoint["OwnedBy"] = 2; + capturePoint["CaptureTimer"] = 0.0; + Events::Captured e; + e.CapturePointID = capturePoint.EntityID; + e.TeamNumberThatCapturedCapturePoint = 2; + m_EventBroker->Publish(e); + } } //D.both teams have players inside if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside > 0) { - + //do nothing (?) } - + //WIN: check for possible winCondition = check if the homebase is owned by the other team + if (!WinnerWasFound && (int)capturePoint["OwnedBy"] != 0 && (int)capturePoint["IsHomeCapturePointForTeamNumber"] != 0 && + (int)capturePoint["IsHomeCapturePointForTeamNumber"] != (int)capturePoint["OwnedBy"]) { + //publish Win event + Events::Win e; + e.TeamThatWon = capturePoint["OwnedBy"]; + m_EventBroker->Publish(e); + WinnerWasFound = true; + } } diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index a0d61e04..deb64a41 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -29,6 +29,7 @@ BOOST_AUTO_TEST_CASE(CapturePointTest1) loops--; } //The system will process the events, hence it will take a while before we can read anything + success = true; BOOST_TEST(success); } BOOST_AUTO_TEST_SUITE_END() @@ -79,7 +80,9 @@ CapturePointTest::CapturePointTest(int runTestNumber) player2["TeamNumber"] = 2; EntityID capturePointID = m_World->CreateEntity(); - ComponentWrapper& capPointComp = m_World->AttachComponent(capturePointID, "CapturePoint"); + ComponentWrapper& capturePoint = m_World->AttachComponent(capturePointID, "CapturePoint"); + //this capturePoint is homeBase for team 2 + capturePoint["IsHomeCapturePointForTeamNumber"] = 2; m_CapturePointID = capturePointID; m_RunTestNumber = runTestNumber; @@ -89,10 +92,10 @@ CapturePointTest::CapturePointTest(int runTestNumber) eTriggerTouched.Trigger = m_CapturePointID; m_EventBroker->Publish(eTriggerTouched); - Events::TriggerTouch eTriggerTouched2; - eTriggerTouched2.Entity = m_PlayerID2; - eTriggerTouched2.Trigger = m_CapturePointID; - m_EventBroker->Publish(eTriggerTouched2); + //Events::TriggerTouch eTriggerTouched2; + //eTriggerTouched2.Entity = m_PlayerID2; + //eTriggerTouched2.Trigger = m_CapturePointID; + //m_EventBroker->Publish(eTriggerTouched2); Events::TriggerLeave eTriggerLeft; eTriggerLeft.Entity = m_PlayerID; @@ -104,6 +107,8 @@ CapturePointTest::CapturePointTest(int runTestNumber) eTriggerTouched3.Trigger = m_CapturePointID; m_EventBroker->Publish(eTriggerTouched3); + //init glfw so dt works + glfwInit(); } CapturePointTest::~CapturePointTest() From 7a8604bf2b447bf1fdd56eb1eb0d1823b383834b Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 13 Jan 2016 11:41:01 +0100 Subject: [PATCH 041/224] CapturePointSystem now tracks and verifies if a capturePoint can be taken over. Also the time is changed faster the more players stand on the capturepoint (number*dt). Also took care of the problem when both teams have the same contested capturepoint. Added variable in the CapturePoint component: CapturePointNumber. This is needed since we cant know what capturepoint is next to be taken over otherwise. Updated the CapturePointTest according to current CapturePointSystem TODO: try to refactor code in CapturePointSystem --- include/Game/CapturePointSystem.h | 8 +- resources/Schema/Components/CapturePoint.xml | 1 + resources/Schema/Components/CapturePoint.xsd | 1 + src/Game/CapturePointSystem.cpp | 87 ++++++++++++++++---- src/Tests/CapturePointTest.cpp | 11 ++- src/Tests/CapturePointTest.h | 2 +- 6 files changed, 91 insertions(+), 19 deletions(-) diff --git a/include/Game/CapturePointSystem.h b/include/Game/CapturePointSystem.h index 8888da30..f7e600d7 100644 --- a/include/Game/CapturePointSystem.h +++ b/include/Game/CapturePointSystem.h @@ -16,7 +16,7 @@ class CapturePointSystem : public PureSystem { public: - //TODO: on new map, destroy all info in the vectors + //WARNING: on new map, destroy all info in the vectors, as well as reset all variables (just make new?) CapturePointSystem(EventBroker* eventBroker); //updatecomponent @@ -30,6 +30,12 @@ private: bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e); bool WinnerWasFound = false; + //need to track these variables for the captureSystem to work as per design! + const int m_NotACapturePoint = 999; + int m_Team1NextPossibleCapturePoint = m_NotACapturePoint; + int m_Team2NextPossibleCapturePoint = m_NotACapturePoint; + int m_Team1HomeCapturePoint = m_NotACapturePoint; + int m_Team2HomeCapturePoint = m_NotACapturePoint; //vectors which will keep track of enter/leave changes std::vector> m_ETriggerTouchVector; diff --git a/resources/Schema/Components/CapturePoint.xml b/resources/Schema/Components/CapturePoint.xml index fddd1042..b2bd53d7 100644 --- a/resources/Schema/Components/CapturePoint.xml +++ b/resources/Schema/Components/CapturePoint.xml @@ -1,4 +1,5 @@ + 0 0 0 0 diff --git a/resources/Schema/Components/CapturePoint.xsd b/resources/Schema/Components/CapturePoint.xsd index b1cbe173..3171cf28 100644 --- a/resources/Schema/Components/CapturePoint.xsd +++ b/resources/Schema/Components/CapturePoint.xsd @@ -12,6 +12,7 @@ + diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp index b276cb98..315e9729 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/CapturePointSystem.cpp @@ -10,9 +10,11 @@ CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) } //here all capturepoints will update their component +//NOTE: needs to run each frame, since we're possibly modifying the captureTimer for the capturePoints by dt void CapturePointSystem::UpdateComponent(World *world, ComponentWrapper &capturePoint, double dt) { - //NOTE: needs to run each frame, since we're possibly increasing the captureTimer for the capturePoint by dt + //for testing only: + //dt = 20.0; int firstTeamPlayersStandingInside = 0; int secondTeamPlayersStandingInside = 0; @@ -42,40 +44,93 @@ void CapturePointSystem::UpdateComponent(World *world, ComponentWrapper &capture int ownedBy = capturePoint["OwnedBy"]; double captureTimer = capturePoint["CaptureTimer"]; - //+-5 + //check what capturePoint can be taken over next + //TODO: modify this when a point has been taken over + //A. no capturepoint taken yet for at least one of the teams + //A1. at the start of the match the system is unaware of what capturePoint is the first one for each team + if (m_Team1NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 1) { + m_Team1NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; + m_Team1HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team1NextPossibleCapturePoint + } + if (m_Team2NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 2) { + m_Team2NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; + m_Team2HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team2NextPossibleCapturePoint + } + //B. at least one capturepoint has been taken over + //do nothing, its being handled inside the next code: + + //TODO: refactor code a bit //A.nobodys standing inside if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside == 0) { //do nothing (?) } - //B.first team has players but second none - if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside == 0) { - //ownedBy 1 -> timer should stay at 5 + //B.first team has players but second none, and this capturePoint is the next in line to be able to be captured + if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside == 0 + && m_Team1NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { + //ownedBy 1 -> timer should stay at 15 + //increased by numberOfPlayersInside*dt if (ownedBy == 2 || ownedBy == 0) - capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + dt; - //check if captureTimer > 5 and if so change owner and publish the eCaptured event - if ((double)capturePoint["CaptureTimer"] > 5) { + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + firstTeamPlayersStandingInside*dt; + //check if captureTimer > 15 and if so change owner and publish the eCaptured event + //TODO: graphics 25,50,75% captured events? for graphical issues + if ((double)capturePoint["CaptureTimer"] > 15.0) { + //publish Captured event capturePoint["OwnedBy"] = 1; - capturePoint["CaptureTimer"] = 0.0; Events::Captured e; e.CapturePointID = capturePoint.EntityID; e.TeamNumberThatCapturedCapturePoint = 1; m_EventBroker->Publish(e); + //modify next m_Team1NextPossibleCapturePoint + //example team1:s homepoint is at 0 and team2:s at 7. team 1 capture 3, next will be 4 + //example team1:s homepoint is at 7 and team2:s at 0. team 1 capture 3, next will be 2 + if (m_Team1HomeCapturePoint < m_Team2HomeCapturePoint) { + m_Team1NextPossibleCapturePoint++; + //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well + if (m_Team1NextPossibleCapturePoint > m_Team2NextPossibleCapturePoint) + m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint; + } + else + { + m_Team1NextPossibleCapturePoint--; + //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well + if (m_Team1NextPossibleCapturePoint < m_Team2NextPossibleCapturePoint) + m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint; + } } } - //C.second team has players but second none - if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0) { - //ownedBy 2 -> timer should stay at -5 + //C.second team has players but second none, and this capturePoint is the next in line to be able to be captured + if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0 + && m_Team2NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { + //ownedBy 2 -> timer should stay at -15 + //decreased by numberOfPlayersInside*dt if (ownedBy == 1 || ownedBy == 0) - capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] - dt; - //check if captureTimer > 5 and if so change owner and publish the eCaptured event - if ((double)capturePoint["CaptureTimer"] < -5.0) { + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] - secondTeamPlayersStandingInside*dt; + //check if captureTimer < -15 and if so change owner and publish the eCaptured event + //TODO: graphics 25,50,75% captured events? for graphical issues + if ((double)capturePoint["CaptureTimer"] < -15.0) { capturePoint["OwnedBy"] = 2; - capturePoint["CaptureTimer"] = 0.0; Events::Captured e; e.CapturePointID = capturePoint.EntityID; e.TeamNumberThatCapturedCapturePoint = 2; m_EventBroker->Publish(e); + //modify next m_Team2NextPossibleCapturePoint + //example team2:s homepoint is at 0 and team1:s at 7. team 2 capture 3, next will be 4 + //example team2:s homepoint is at 7 and team1:s at 0. team 2 capture 3, next will be 2 + if (m_Team2HomeCapturePoint < m_Team1HomeCapturePoint) + { + m_Team2NextPossibleCapturePoint++; + //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well + if (m_Team2NextPossibleCapturePoint > m_Team1NextPossibleCapturePoint) + m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint; + } + else + { + m_Team2NextPossibleCapturePoint--; + //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well + if (m_Team2NextPossibleCapturePoint < m_Team1NextPossibleCapturePoint) + m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint; + } } } diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index deb64a41..1991acc9 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -83,7 +83,16 @@ CapturePointTest::CapturePointTest(int runTestNumber) ComponentWrapper& capturePoint = m_World->AttachComponent(capturePointID, "CapturePoint"); //this capturePoint is homeBase for team 2 capturePoint["IsHomeCapturePointForTeamNumber"] = 2; + capturePoint["CapturePointNumber"] = 0; m_CapturePointID = capturePointID; + + EntityID capturePointID2 = m_World->CreateEntity(); + ComponentWrapper& capturePoint2 = m_World->AttachComponent(capturePointID2, "CapturePoint"); + //this capturePoint is homeBase for team 1 + capturePoint2["IsHomeCapturePointForTeamNumber"] = 1; + capturePoint2["CapturePointNumber"] = 1; + m_CapturePointID2 = capturePointID2; + m_RunTestNumber = runTestNumber; //add some touch/leave events @@ -104,7 +113,7 @@ CapturePointTest::CapturePointTest(int runTestNumber) Events::TriggerTouch eTriggerTouched3; eTriggerTouched3.Entity = m_PlayerID; - eTriggerTouched3.Trigger = m_CapturePointID; + eTriggerTouched3.Trigger = m_CapturePointID2; m_EventBroker->Publish(eTriggerTouched3); //init glfw so dt works diff --git a/src/Tests/CapturePointTest.h b/src/Tests/CapturePointTest.h index c0244802..1170c613 100644 --- a/src/Tests/CapturePointTest.h +++ b/src/Tests/CapturePointTest.h @@ -34,7 +34,7 @@ private: EventBroker* m_EventBroker; World* m_World; SystemPipeline* m_SystemPipeline; - int m_PlayerID, m_PlayerID2, m_CapturePointID; + int m_PlayerID, m_PlayerID2, m_CapturePointID, m_CapturePointID2; int m_RunTestNumber; }; From ed5ac2e9239eb873591a92f4f686c1f7cfe734e4 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 13 Jan 2016 14:37:56 +0100 Subject: [PATCH 042/224] 6 new tests for CapturePointSystem have been created! TODO: refactor CapturePointSystem --- src/Tests/CapturePointTest.cpp | 369 ++++++++++++++++++++++++++++++--- src/Tests/CapturePointTest.h | 16 +- 2 files changed, 354 insertions(+), 31 deletions(-) diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index 1991acc9..32570534 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -10,12 +10,11 @@ using boost::unit_test_framework::test_case; #include "Core/EntityFileWriter.h" #include "Game/CapturePointSystem.h" -BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) +BOOST_AUTO_TEST_SUITE(CapturePointTestSuite) //dont use the same name as the classname in test cases... -BOOST_AUTO_TEST_CASE(CapturePointTest1) +BOOST_AUTO_TEST_CASE(CapturePointTest1_OnePlayerOnCapturePoint) { - //Test firing primary weapon CapturePointTest game(1); //100 loops will be more than enough to do the test int loops = 100; @@ -29,7 +28,93 @@ BOOST_AUTO_TEST_CASE(CapturePointTest1) loops--; } //The system will process the events, hence it will take a while before we can read anything - success = true; + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(CapturePointTest2_TwoPlayersOnCapturePoint) +{ + CapturePointTest game(2); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(CapturePointTest3_NoPlayersOnCapturePoint) +{ + CapturePointTest game(3); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + //successCheck needs to know when were close to 100 to check if anything happened then (NumLoops) + game.NumLoops++; + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(CapturePointTest4_TwoCapturePointsBeingCaptured) +{ + CapturePointTest game(4); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(CapturePointTest5_SameCapturePointContestedAndTakenOver) +{ + CapturePointTest game(5); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(CapturePointTest6_Team1CapturedTheLastPointAndWon) +{ + CapturePointTest game(6); + //100 loops will be more than enough to do the test + int loops = 100; + bool success = false; + while (loops > 0) { + game.Tick(); + if (game.TestSucceeded) { + success = true; + break; + } + loops--; + } + //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_SUITE_END() @@ -65,8 +150,7 @@ CapturePointTest::CapturePointTest(int runTestNumber) fp.MergeEntities(m_World); } - //The Test - //create entity which has transform,player,model,health in it. i.e. is a player + //create 2 players and 3 capturepoints for testing EntityID playerID = m_World->CreateEntity(); m_PlayerID = playerID; ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); @@ -89,32 +173,42 @@ CapturePointTest::CapturePointTest(int runTestNumber) EntityID capturePointID2 = m_World->CreateEntity(); ComponentWrapper& capturePoint2 = m_World->AttachComponent(capturePointID2, "CapturePoint"); //this capturePoint is homeBase for team 1 - capturePoint2["IsHomeCapturePointForTeamNumber"] = 1; + capturePoint2["IsHomeCapturePointForTeamNumber"] = 0; capturePoint2["CapturePointNumber"] = 1; m_CapturePointID2 = capturePointID2; + EntityID capturePointID3 = m_World->CreateEntity(); + ComponentWrapper& capturePoint3 = m_World->AttachComponent(capturePointID3, "CapturePoint"); + //this capturePoint is homeBase for team 1 + capturePoint3["IsHomeCapturePointForTeamNumber"] = 1; + capturePoint3["CapturePointNumber"] = 2; + m_CapturePointID3 = capturePointID3; + m_RunTestNumber = runTestNumber; - //add some touch/leave events - Events::TriggerTouch eTriggerTouched; - eTriggerTouched.Entity = m_PlayerID; - eTriggerTouched.Trigger = m_CapturePointID; - m_EventBroker->Publish(eTriggerTouched); - - //Events::TriggerTouch eTriggerTouched2; - //eTriggerTouched2.Entity = m_PlayerID2; - //eTriggerTouched2.Trigger = m_CapturePointID; - //m_EventBroker->Publish(eTriggerTouched2); - - Events::TriggerLeave eTriggerLeft; - eTriggerLeft.Entity = m_PlayerID; - eTriggerLeft.Trigger = m_CapturePointID; - m_EventBroker->Publish(eTriggerLeft); - - Events::TriggerTouch eTriggerTouched3; - eTriggerTouched3.Entity = m_PlayerID; - eTriggerTouched3.Trigger = m_CapturePointID2; - m_EventBroker->Publish(eTriggerTouched3); + switch (runTestNumber) + { + case 1: + TestSetup1_OnePlayerOnCapturePoint(); + break; + case 2: + TestSetup2_TwoPlayersOnCapturePoint(); + break; + case 3: + TestSetup3_NoPlayersOnCapturePoint(); + break; + case 4: + TestSetup4_TwoCapturePointsBeingCaptured(); + break; + case 5: + TestSetup5_SameCapturePointContestedAndTakenOver(); + break; + case 6: + TestSetup6_Team1CapturedTheLastPointAndWon(); + break; + default: + break; + } //init glfw so dt works glfwInit(); @@ -127,13 +221,205 @@ CapturePointTest::~CapturePointTest() delete m_EventBroker; } +void CapturePointTest::TestSetup1_OnePlayerOnCapturePoint() +{ + Events::TriggerTouch touchEvent; + Events::TriggerLeave leaveEvent; + + //player touches,leaves,touches m_CapturePointID. and enters m_CapturePointID3 + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); + + leaveEvent.Entity = m_PlayerID; + leaveEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(leaveEvent); + + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); + + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID3; + m_EventBroker->Publish(touchEvent); +} +void CapturePointTest::TestSetup2_TwoPlayersOnCapturePoint() +{ + Events::TriggerTouch touchEvent; + Events::TriggerLeave leaveEvent; + + //player touches,leaves m_CapturePointID. and enters m_CapturePointID3 + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); + + leaveEvent.Entity = m_PlayerID; + leaveEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(leaveEvent); + + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID3; + m_EventBroker->Publish(touchEvent); + + //player2 touches m_CapturePointID,m_CapturePointID2 + touchEvent.Entity = m_PlayerID2; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); + + touchEvent.Entity = m_PlayerID2; + touchEvent.Trigger = m_CapturePointID2; + m_EventBroker->Publish(touchEvent); +} +void CapturePointTest::TestSetup3_NoPlayersOnCapturePoint() +{ + Events::TriggerTouch touchEvent; + Events::TriggerLeave leaveEvent; + + //player1 touches and leaves m_CapturePointID + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); + + leaveEvent.Entity = m_PlayerID; + leaveEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(leaveEvent); + + //player2 touches and leaves m_CapturePointID2 + touchEvent.Entity = m_PlayerID2; + touchEvent.Trigger = m_CapturePointID2; + m_EventBroker->Publish(touchEvent); + + leaveEvent.Entity = m_PlayerID2; + leaveEvent.Trigger = m_CapturePointID2; + m_EventBroker->Publish(leaveEvent); + +} +void CapturePointTest::TestSetup4_TwoCapturePointsBeingCaptured() +{ + Events::TriggerTouch touchEvent; + + //player1 touches m_CapturePointID3 + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID3; + m_EventBroker->Publish(touchEvent); + + //player2 touches m_CapturePointID + touchEvent.Entity = m_PlayerID2; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); +} +void CapturePointTest::TestSetup5_SameCapturePointContestedAndTakenOver() +{ + //NOTE: setup events need to trigger first then the real event will be allowed by the system later + Events::TriggerTouch touchEvent; + + //"SETUP" homebase->same capturep + //player1 touches m_CapturePointID3 + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID3; + m_EventBroker->Publish(touchEvent); + + //player2 touches m_CapturePointID + touchEvent.Entity = m_PlayerID2; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); + + //contested same, player1 touches the contested + //player1 touches m_CapturePointID2 + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID2; + m_EventBroker->Publish(touchEvent); + + //player2 does nothing + +} +void CapturePointTest::TestSetup6_Team1CapturedTheLastPointAndWon() +{ + //NOTE: setup events need to trigger first then the real event will be allowed by the system later + Events::TriggerTouch touchEvent; + + //"SETUP" team1 captures point 2,3 + //player1 touches m_CapturePointID3 + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID3; + m_EventBroker->Publish(touchEvent); + + //player1 touches m_CapturePointID2 + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID2; + m_EventBroker->Publish(touchEvent); + + //team1 captures point 1 + //player1 touches m_CapturePointID + touchEvent.Entity = m_PlayerID; + touchEvent.Trigger = m_CapturePointID; + m_EventBroker->Publish(touchEvent); + + //player2 does nothing +} +void CapturePointTest::TestSuccess1() { + //TestSetup1_OnePlayerOnCapturePoint + + //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + if (ownedByID3 == 1) + TestSucceeded = true; +} +void CapturePointTest::TestSuccess2() { + //TestSetup2_TwoPlayersOnCapturePoint + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; + if (ownedByID3 == 1 && ownedByID1 == 2) + TestSucceeded = true; +} +void CapturePointTest::TestSuccess3() { + //TestSetup3_NoPlayersOnCapturePoint + //only do this test if were at the final loopcount + //if any capturePoint changed then, its a failure else a success + if (NumLoops == 95) { + TestSucceeded = true; + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + if (ownedByID1 != 0 || ownedByID2 != 0 || ownedByID3 != 0) + TestSucceeded = false; + } +} +void CapturePointTest::TestSuccess4() { + //TestSetup4_TwoCapturePointsBeingCaptured + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + if (ownedByID1 == 2 && ownedByID3 == 1) + TestSucceeded = true; +} +void CapturePointTest::TestSuccess5() { + //TestSetup5_SameCapturePointContestedAndTakenOver + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + if (ownedByID1 == 2 && ownedByID2 == 1 && ownedByID3 == 1) + TestSucceeded = true; +} +void CapturePointTest::TestSuccess6() { + //NOTE: the actual win-event will have to be manually checked if it triggered or not + //TestSetup6_Team1CapturedTheLastPointAndWon + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + if (ownedByID1 == 1 && ownedByID2 == 1 && ownedByID3 == 1) + TestSucceeded = true; +} void CapturePointTest::Tick() { glfwPollEvents(); - double currentTime = glfwGetTime(); - double dt = currentTime - m_LastTime; - m_LastTime = currentTime; + //double currentTime = glfwGetTime(); + //double dt = currentTime - m_LastTime; + //m_LastTime = currentTime; + + //just set dt to 10.0 since we want fast testing + double dt = 10.0; // Iterate through systems and update world! m_SystemPipeline->Update(m_World, dt); @@ -141,4 +427,27 @@ void CapturePointTest::Tick() m_EventBroker->Swap(); m_EventBroker->Clear(); + switch (m_RunTestNumber) + { + case 1: + TestSuccess1(); + break; + case 2: + TestSuccess2(); + break; + case 3: + TestSuccess3(); + break; + case 4: + TestSuccess4(); + break; + case 5: + TestSuccess5(); + break; + case 6: + TestSuccess6(); + break; + default: + break; + } } diff --git a/src/Tests/CapturePointTest.h b/src/Tests/CapturePointTest.h index 1170c613..89aea389 100644 --- a/src/Tests/CapturePointTest.h +++ b/src/Tests/CapturePointTest.h @@ -27,6 +27,20 @@ public: void Tick(); bool TestSucceeded = false; + int NumLoops = 0; + + void TestSetup1_OnePlayerOnCapturePoint(); + void TestSetup2_TwoPlayersOnCapturePoint(); + void TestSetup3_NoPlayersOnCapturePoint(); + void TestSetup4_TwoCapturePointsBeingCaptured(); + void TestSetup5_SameCapturePointContestedAndTakenOver(); + void TestSetup6_Team1CapturedTheLastPointAndWon(); + void TestSuccess1(); + void TestSuccess2(); + void TestSuccess3(); + void TestSuccess4(); + void TestSuccess5(); + void TestSuccess6(); private: double m_LastTime; @@ -34,7 +48,7 @@ private: EventBroker* m_EventBroker; World* m_World; SystemPipeline* m_SystemPipeline; - int m_PlayerID, m_PlayerID2, m_CapturePointID, m_CapturePointID2; + int m_PlayerID, m_PlayerID2, m_CapturePointID, m_CapturePointID2, m_CapturePointID3; int m_RunTestNumber; }; From f47f913bf571c824fc31766ffdd7792f0f4244bc Mon Sep 17 00:00:00 2001 From: Jocke Date: Wed, 13 Jan 2016 16:09:16 +0100 Subject: [PATCH 043/224] Added logic for sending input from Client to Server. Fixed so that snapshots set their parent correctly. Will get problems if we have more components than unsigned int max size, but that was already a problem. Client now maps Entitys received from server with local Entitys by mapping their EntityIDs. --- include/Engine/Network/Client.h | 9 +++- include/Engine/Network/Server.h | 2 +- src/Engine/Network/Client.cpp | 83 +++++++++++++++++++-------------- src/Engine/Network/Server.cpp | 51 ++++---------------- 4 files changed, 65 insertions(+), 80 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index a5488210..da734810 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -3,6 +3,7 @@ #include #include +#include #include #include @@ -45,6 +46,10 @@ private: std::string m_PlayerName; int m_PlayerID = -1; + // Server Client Lookup map + // Assumes that root node for client and server is EntityID 0. + std::unordered_map m_ServerToClientMap; + // Network logic PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; SnapshotDefinitions m_NextSnapshot; @@ -56,7 +61,7 @@ private: // Private member functions void readFromServer(); - void sendSnapshotToServer(); + void sendInputEvents(); int receive(char* data, size_t length); void send(Packet& packet); void connect(); @@ -73,7 +78,7 @@ private: void identifyPacketLoss(); bool isConnected(); EntityID createPlayer(); - + bool hasMappedEntity(EntityID entityID); // Events EventBroker* m_EventBroker; EventRelay m_EInputCommand; diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 893eed0b..84d8c143 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -12,6 +12,7 @@ #include "Core/World.h" #include "Core/EventBroker.h" #include "Network/Network.h" +#include "Input/EInputCommand.h" class Server : public Network { @@ -72,7 +73,6 @@ private: void parseDisconnect(); void parseClientPing(); void parseServerPing(); - void parseSnapshot(Packet& packet); void identifyPacketLoss(); EntityID createPlayer(); }; diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index b8849ed0..3ecee0e0 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -5,6 +5,8 @@ using namespace boost::asio::ip; Client::Client(ConfigFile* config) : m_Socket(m_IOService) { + // Asumes root node is EntityID 0 + m_ServerToClientMap.insert(std::make_pair(0, 0)); // Default is local host std::string address = config->Get("Networking.Address", "127.0.0.1"); int port = config->Get("Networking.Port", 13); @@ -16,8 +18,7 @@ Client::Client(ConfigFile* config) : m_Socket(m_IOService) } Client::~Client() -{ -} +{ } void Client::Start(World* world, EventBroker* eventBroker) { @@ -55,7 +56,7 @@ void Client::readFromServer() } } -void Client::sendSnapshotToServer() +void Client::sendInputEvents() { // Reset previous key state in snapshot. m_NextSnapshot.InputForward = ""; @@ -187,9 +188,16 @@ void Client::parseSnapshot(Packet& packet) { std::string componentType = packet.ReadString(); while (packet.DataReadSize() < packet.Size()) { - EntityID entityID = packet.ReadPrimitive(); + // Components EntityID + EntityID receivedEntityID = packet.ReadPrimitive(); + // Parents EntityID + EntityID receivedParentEntityID = packet.ReadPrimitive(); ComponentInfo componentInfo = m_World->GetComponents(componentType)->ComponentInfo(); - if (m_World->ValidEntity(entityID)) { + // Check if the received EntityID is mapped to one of our local EntityIDs + if (hasMappedEntity(receivedEntityID)) { + // Get the local EntityID + EntityID entityID = m_ServerToClientMap.at(receivedEntityID); + // Check if the component exists if (m_World->HasComponent(entityID, componentType)) { // If the entity and the component exists update it updateFields(packet, componentInfo, entityID, componentType); @@ -202,11 +210,12 @@ void Client::parseSnapshot(Packet& packet) } // If the entity dosent exist nor the component } else { - //Create Entity + // Create Entity // If entity dosen't exist EntityID newEntityID = m_World->CreateEntity(); + m_ServerToClientMap.insert(std::make_pair(receivedEntityID, newEntityID)); // Check if EntityIDs are out of sync - if (newEntityID != entityID) { + if (newEntityID != receivedEntityID) { LOG_INFO("Client::parseSnapshot(Packet& packet): Newly created EntityID is not the \ same as the one sent by server (EntityIDs are out of sync)"); } @@ -215,6 +224,21 @@ void Client::parseSnapshot(Packet& packet) // Copy data to newly created component updateFields(packet, componentInfo, newEntityID, componentType); } + + // Parent Logic + // Don't need to check if receivedEntityID is mapped. (It should have been set) + if (receivedParentEntityID != std::numeric_limits::max()) { + if (hasMappedEntity(receivedParentEntityID)) { + m_World->SetParent(m_ServerToClientMap.at(receivedEntityID), m_ServerToClientMap.at(receivedParentEntityID)); + // If Parent dosen't exist create one and map receivedParentEntityID to it. + } else { + // Create the new parent and add it to map + EntityID newParentEntityID = m_World->CreateEntity(); + m_ServerToClientMap.insert(std::make_pair(receivedParentEntityID, newParentEntityID)); + // Set the newly created Entity as parent. + m_World->SetParent(m_ServerToClientMap.at(receivedEntityID), newParentEntityID); + } + } } } @@ -273,40 +297,22 @@ void Client::moveMessageHead(char*& data, size_t& length, size_t stepSize) bool Client::OnInputCommand(const Events::InputCommand & e) { - if (isConnected()) { - ComponentWrapper& player = m_World->GetComponent(m_PlayerDefinitions[m_PlayerID].EntityID, "Player"); - if (e.Command == "Forward") { - if (e.Value > 0) { - (bool&)player["Forward"] = true; - (bool&)player["Back"] = false; - } else if (e.Value < 0) { - (bool&)player["Back"] = true; - (bool&)player["Forward"] = false; - } else { - (bool&)player["Forward"] = false; - (bool&)player["Back"] = false; - } - } - if (e.Command == "Right") { - if (e.Value > 0) { - (bool&)player["Right"] = true; - (bool&)player["Left"] = false; - } else if (e.Value < 0) { - (bool&)player["Left"] = true; - (bool&)player["Right"] = false; - } else { - (bool&)player["Left"] = false; - (bool&)player["Right"] = false; - } - } - } - if (e.Command == "ConnectToServer") { // Connect for now + if (e.Command == "Forward" || e.Command == "Right") { + Packet packet(MessageType::Event, m_SendPacketID); + packet.WriteString(e.Command); + packet.WritePrimitive(e.PlayerID); + packet.WritePrimitive(e.Value); + send(packet); + LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + return true; + } else if (e.Command == "ConnectToServer") { // Connect for now connect(); + LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + return true; } return false; } - void Client::identifyPacketLoss() { // if no packets lost, difference should be equal to 1 @@ -335,3 +341,8 @@ EntityID Client::createPlayer() ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); return entityID; } + +bool Client::hasMappedEntity(EntityID entityID) +{ + return m_ServerToClientMap.find(entityID) != m_ServerToClientMap.end(); +} diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 07fed65b..e98213a5 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -76,7 +76,6 @@ void Server::parseMessageType(Packet& packet) case MessageType::Message: break; case MessageType::Snapshot: - parseSnapshot(packet); break; case MessageType::Disconnect: parseDisconnect(); @@ -149,13 +148,15 @@ void Server::sendSnapshot() std::unordered_map worldComponentPools = m_World->GetComponentPools(); for (auto& it : worldComponentPools) { Packet packet(MessageType::Snapshot, m_SendPacketID); - std::string componentType = it.first; ComponentPool* componentPool = it.second; ComponentInfo componentInfo = componentPool->ComponentInfo(); + // Component Type packet.WriteString(componentInfo.Name); - for (auto& componentWrapper : *componentPool) { + // Components EntityID packet.WritePrimitive(componentWrapper.EntityID); + // Parents EntityID + packet.WritePrimitive(m_World->GetParent(componentWrapper.EntityID)); for (auto& componentField : componentWrapper.Info.FieldsInOrder) { ComponentInfo::Field_t fieldInfo = componentInfo.Fields.at(componentField); if (fieldInfo.Type == "string") { @@ -228,29 +229,12 @@ void Server::parseEvent(Packet& packet) // If no player matches the address return. if (i >= 8) return; - - unsigned int entityId = m_PlayerDefinitions[i].EntityID; - std::string eventString = packet.ReadString(); - if ("+Forward" == eventString) { - m_World->GetComponent(entityId, "Player")["Forward"] = true; - m_World->GetComponent(entityId, "Player")["Back"] = false; - } else if ("-Forward" == eventString) { - m_World->GetComponent(entityId, "Player")["Forward"] = false; - m_World->GetComponent(entityId, "Player")["Back"] = true; - } else if ("0Forward" == eventString) { - m_World->GetComponent(entityId, "Player")["Forward"] = false; - m_World->GetComponent(entityId, "Player")["Back"] = false; - } - if ("+Right" == eventString) { - m_World->GetComponent(entityId, "Player")["Left"] = false; - m_World->GetComponent(entityId, "Player")["Right"] = true; - } else if ("-Right" == eventString) { - m_World->GetComponent(entityId, "Player")["Right"] = false; - m_World->GetComponent(entityId, "Player")["Left"] = true; - } else if ("0Right" == eventString) { - m_World->GetComponent(entityId, "Player")["Right"] = false; - m_World->GetComponent(entityId, "Player")["Left"] = false; - } + Events::InputCommand e; + e.Command = packet.ReadString(); + e.PlayerID = packet.ReadPrimitive(); + e.Value = packet.ReadPrimitive(); + m_EventBroker->Publish(e); + LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); } void Server::parseConnect(Packet& packet) @@ -319,21 +303,6 @@ void Server::parseServerPing() } } -// NOT USED -void Server::parseSnapshot(Packet& packet) -{ - // Does no logic. Returns snapshot if client request one - // The snapshot is not a real snapshot tho... - for (int i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { - m_Socket.send_to( - boost::asio::buffer("I'm sending a snapshot to you guys!"), - m_PlayerDefinitions[i].Endpoint, - 0); - } - } -} - void Server::identifyPacketLoss() { // if no packets lost, difference should be equal to 1 From 95339206846c7f9d3beef1ab48b41b38b8d827a1 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 13 Jan 2016 16:13:57 +0100 Subject: [PATCH 044/224] Fixed a few CodeStandard mistakes. Added CapturePointSystem to CMakeLists.txt since branch is no longer based on ShootEvent-branch --- include/Game/CapturePointSystem.h | 2 +- src/Game/CMakeLists.txt | 1 + src/Game/CapturePointSystem.cpp | 6 +++--- 3 files changed, 5 insertions(+), 4 deletions(-) diff --git a/include/Game/CapturePointSystem.h b/include/Game/CapturePointSystem.h index f7e600d7..c9ff0477 100644 --- a/include/Game/CapturePointSystem.h +++ b/include/Game/CapturePointSystem.h @@ -29,7 +29,7 @@ private: EventRelay m_ETriggerLeave; bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e); - bool WinnerWasFound = false; + bool m_WinnerWasFound = false; //need to track these variables for the captureSystem to work as per design! const int m_NotACapturePoint = 999; int m_Team1NextPossibleCapturePoint = m_NotACapturePoint; diff --git a/src/Game/CMakeLists.txt b/src/Game/CMakeLists.txt index 04146670..c8f63028 100644 --- a/src/Game/CMakeLists.txt +++ b/src/Game/CMakeLists.txt @@ -21,6 +21,7 @@ set(SOURCE_FILES "Game.cpp" "HealthSystem.cpp" "PlayerSystem.cpp" + "CapturePointSystem.cpp" ) set(LIBRARIES diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp index 315e9729..867ddc62 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/CapturePointSystem.cpp @@ -11,7 +11,7 @@ CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) //here all capturepoints will update their component //NOTE: needs to run each frame, since we're possibly modifying the captureTimer for the capturePoints by dt -void CapturePointSystem::UpdateComponent(World *world, ComponentWrapper &capturePoint, double dt) +void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capturePoint, double dt) { //for testing only: //dt = 20.0; @@ -140,13 +140,13 @@ void CapturePointSystem::UpdateComponent(World *world, ComponentWrapper &capture } //WIN: check for possible winCondition = check if the homebase is owned by the other team - if (!WinnerWasFound && (int)capturePoint["OwnedBy"] != 0 && (int)capturePoint["IsHomeCapturePointForTeamNumber"] != 0 && + if (!m_WinnerWasFound && (int)capturePoint["OwnedBy"] != 0 && (int)capturePoint["IsHomeCapturePointForTeamNumber"] != 0 && (int)capturePoint["IsHomeCapturePointForTeamNumber"] != (int)capturePoint["OwnedBy"]) { //publish Win event Events::Win e; e.TeamThatWon = capturePoint["OwnedBy"]; m_EventBroker->Publish(e); - WinnerWasFound = true; + m_WinnerWasFound = true; } } From b8a41b7c13b6959e60901e6b876238ca1047d63c Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 13 Jan 2016 17:07:49 +0100 Subject: [PATCH 045/224] Updated some CapturePointLogic in CapturePointSystem: reset timer on capture, being able to take back the progress the other team did on your capturepoint. TODO: refactor! --- src/Game/CapturePointSystem.cpp | 26 +++++++++++++++++--------- 1 file changed, 17 insertions(+), 9 deletions(-) diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp index 867ddc62..4e9230ef 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/CapturePointSystem.cpp @@ -13,8 +13,6 @@ CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) //NOTE: needs to run each frame, since we're possibly modifying the captureTimer for the capturePoints by dt void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capturePoint, double dt) { - //for testing only: - //dt = 20.0; int firstTeamPlayersStandingInside = 0; int secondTeamPlayersStandingInside = 0; @@ -42,10 +40,8 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture } int ownedBy = capturePoint["OwnedBy"]; - double captureTimer = capturePoint["CaptureTimer"]; //check what capturePoint can be taken over next - //TODO: modify this when a point has been taken over //A. no capturepoint taken yet for at least one of the teams //A1. at the start of the match the system is unaware of what capturePoint is the first one for each team if (m_Team1NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 1) { @@ -70,13 +66,19 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture && m_Team1NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { //ownedBy 1 -> timer should stay at 15 //increased by numberOfPlayersInside*dt - if (ownedBy == 2 || ownedBy == 0) + //if capturePoint is not owned by the team, just increase the CaptureTimer + if (ownedBy != 1) + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + firstTeamPlayersStandingInside*dt; + //if capturePoint is owned by the team, and the other team has been trying to take it, then increase the timer towards 0 + if (ownedBy == 1 && (double)capturePoint["CaptureTimer"] < 0.0) capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + firstTeamPlayersStandingInside*dt; //check if captureTimer > 15 and if so change owner and publish the eCaptured event - //TODO: graphics 25,50,75% captured events? for graphical issues + //TODO: graphics 25,50,75% captured events? for graphical displaying if ((double)capturePoint["CaptureTimer"] > 15.0) { - //publish Captured event + //capturePoint is now owned by this team, hence also reset the captureTimer so it still takes 15secs to take it back capturePoint["OwnedBy"] = 1; + capturePoint["CaptureTimer"] = 0.0; + //publish Captured event Events::Captured e; e.CapturePointID = capturePoint.EntityID; e.TeamNumberThatCapturedCapturePoint = 1; @@ -104,12 +106,18 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture && m_Team2NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { //ownedBy 2 -> timer should stay at -15 //decreased by numberOfPlayersInside*dt - if (ownedBy == 1 || ownedBy == 0) + //if capturePoint is not owned by the team, just increase the CaptureTimer + if (ownedBy != 2) + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] - secondTeamPlayersStandingInside*dt; + //if capturePoint is owned by the team, and the other team has been trying to take it, then increase the timer towards 0 + if (ownedBy == 2 && (double)capturePoint["CaptureTimer"] > 0.0) capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] - secondTeamPlayersStandingInside*dt; //check if captureTimer < -15 and if so change owner and publish the eCaptured event - //TODO: graphics 25,50,75% captured events? for graphical issues + //TODO: graphics 25,50,75% captured events? for graphical displaying if ((double)capturePoint["CaptureTimer"] < -15.0) { + //capturePoint is now owned by this team, hence also reset the captureTimer so it still takes 15secs to take it back capturePoint["OwnedBy"] = 2; + capturePoint["CaptureTimer"] = 0.0; Events::Captured e; e.CapturePointID = capturePoint.EntityID; e.TeamNumberThatCapturedCapturePoint = 2; From a060640da3eee5e2017819fbd4fa8322302645e9 Mon Sep 17 00:00:00 2001 From: Jocke Date: Wed, 13 Jan 2016 18:00:12 +0100 Subject: [PATCH 046/224] Removed unnecessary unnecessary if in Client::OnInputCommand. Change name from Server::parseEvent to Server::parseOnInputCommand --- include/Engine/Network/Client.h | 3 ++- include/Engine/Network/MessageType.h | 1 + include/Engine/Network/Server.h | 2 +- src/Engine/Network/Client.cpp | 13 ++++++------- src/Engine/Network/Server.cpp | 6 ++++-- 5 files changed, 14 insertions(+), 11 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index da734810..6b73c95c 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -81,8 +81,9 @@ private: bool hasMappedEntity(EntityID entityID); // Events EventBroker* m_EventBroker; + EventRelay m_EInputCommand; - bool OnInputCommand(const Events::InputCommand &e); + bool OnInputCommand(const Events::InputCommand& e); }; #endif diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index 8d09c7ee..68bda9b0 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -12,6 +12,7 @@ enum class MessageType Message, Snapshot, Event, + OnInputCommand }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 84d8c143..ec2560b5 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -68,7 +68,7 @@ private: void checkForTimeOuts(); void disconnect(int i); void parseMessageType(Packet& packet); - void parseEvent(Packet& packet); + void parseOnInputCommand(Packet& packet); void parseConnect(Packet& packet); void parseDisconnect(); void parseClientPing(); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 3ecee0e0..37ee35d9 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -254,7 +254,6 @@ int Client::receive(char* data, size_t length) if (error) { LOG_ERROR("receive: %s", error.message().c_str()); } - return bytesReceived; } @@ -297,18 +296,18 @@ void Client::moveMessageHead(char*& data, size_t& length, size_t stepSize) bool Client::OnInputCommand(const Events::InputCommand & e) { - if (e.Command == "Forward" || e.Command == "Right") { - Packet packet(MessageType::Event, m_SendPacketID); + if (e.Command == "ConnectToServer") { // Connect for now + connect(); + LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + return true; + } else { + Packet packet(MessageType::OnInputCommand, m_SendPacketID); packet.WriteString(e.Command); packet.WritePrimitive(e.PlayerID); packet.WritePrimitive(e.Value); send(packet); LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; - } else if (e.Command == "ConnectToServer") { // Connect for now - connect(); - LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); - return true; } return false; } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index e98213a5..6b59a31a 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -81,8 +81,10 @@ void Server::parseMessageType(Packet& packet) parseDisconnect(); break; case MessageType::Event: - parseEvent(packet); break; + case MessageType::OnInputCommand: + parseOnInputCommand(packet); + break;; default: break; } @@ -218,7 +220,7 @@ void Server::disconnect(int i) m_PlayerDefinitions[i].Name = ""; } -void Server::parseEvent(Packet& packet) +void Server::parseOnInputCommand(Packet& packet) { size_t i; for (i = 0; i < MAXCONNECTIONS; i++) { From db18a453685d5c220dfec27462d1312a0919f412 Mon Sep 17 00:00:00 2001 From: Jocke Date: Thu, 14 Jan 2016 10:16:11 +0100 Subject: [PATCH 047/224] We are now sending EPlayerDamage events. Client now listens to EPlayerDamage events and send them to Server. Server publishes EPlayerDamage events received from Client. --- include/Engine/Network/Client.h | 5 ++++- include/Engine/Network/MessageType.h | 3 ++- include/Engine/Network/Server.h | 2 ++ src/Engine/Network/Client.cpp | 14 ++++++++++++-- src/Engine/Network/Server.cpp | 26 +++++++++++++++----------- 5 files changed, 35 insertions(+), 15 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 6b73c95c..3027ad87 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -16,6 +16,7 @@ #include "Core/EventBroker.h" #include "Core/ConfigFile.h" #include "Input/EInputCommand.h" +#include "Core/EPlayerDamage.h" class Client : public Network { @@ -79,11 +80,13 @@ private: bool isConnected(); EntityID createPlayer(); bool hasMappedEntity(EntityID entityID); + // Events EventBroker* m_EventBroker; - EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); + EventRelay m_EPlayeDamage; + bool OnPlayerDamage(const Events::PlayerDamage& e); }; #endif diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index 68bda9b0..42b049e8 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -12,7 +12,8 @@ enum class MessageType Message, Snapshot, Event, - OnInputCommand + OnInputCommand, + OnPlayerDamage }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index ec2560b5..dc7b25cd 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -13,6 +13,7 @@ #include "Core/EventBroker.h" #include "Network/Network.h" #include "Input/EInputCommand.h" +#include "Core/EPlayerDamage.h" class Server : public Network { @@ -69,6 +70,7 @@ private: void disconnect(int i); void parseMessageType(Packet& packet); void parseOnInputCommand(Packet& packet); + void parseOnPlayerDamage(Packet& packet); void parseConnect(Packet& packet); void parseDisconnect(); void parseClientPing(); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 37ee35d9..c073e79a 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -298,7 +298,7 @@ bool Client::OnInputCommand(const Events::InputCommand & e) { if (e.Command == "ConnectToServer") { // Connect for now connect(); - LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } else { Packet packet(MessageType::OnInputCommand, m_SendPacketID); @@ -306,12 +306,22 @@ bool Client::OnInputCommand(const Events::InputCommand & e) packet.WritePrimitive(e.PlayerID); packet.WritePrimitive(e.Value); send(packet); - LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } return false; } +bool Client::OnPlayerDamage(const Events::PlayerDamage & e) +{ + Packet packet(MessageType::OnInputCommand, m_SendPacketID); + packet.WritePrimitive(e.DamageAmount); + packet.WritePrimitive(e.PlayerDamagedID); + packet.WriteString(e.TypeOfDamage); + send(packet); + return false; +} + void Client::identifyPacketLoss() { // if no packets lost, difference should be equal to 1 diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 6b59a31a..1a915863 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -84,7 +84,10 @@ void Server::parseMessageType(Packet& packet) break; case MessageType::OnInputCommand: parseOnInputCommand(packet); - break;; + break; + case MessageType::OnPlayerDamage: + parseOnPlayerDamage(packet); + break; default: break; } @@ -222,21 +225,22 @@ void Server::disconnect(int i) void Server::parseOnInputCommand(Packet& packet) { - size_t i; - for (i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address()) { - break; - } - } - // If no player matches the address return. - if (i >= 8) - return; Events::InputCommand e; e.Command = packet.ReadString(); e.PlayerID = packet.ReadPrimitive(); e.Value = packet.ReadPrimitive(); m_EventBroker->Publish(e); - LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + LOG_DEBUG("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); +} + +void Server::parseOnPlayerDamage(Packet & packet) +{ + Events::PlayerDamage e; + e.DamageAmount = packet.ReadPrimitive(); + e.PlayerDamagedID = packet.ReadPrimitive(); + e.TypeOfDamage = packet.ReadString(); + m_EventBroker->Publish(e); + LOG_DEBUG("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str()); } void Server::parseConnect(Packet& packet) From 5e9a3774ab100de9b85f0deeaf3dd1dfd0202254 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Thu, 14 Jan 2016 10:23:27 +0100 Subject: [PATCH 048/224] CapturePointSystem code has been refactored and some branches "optimized" --- include/Game/CapturePointSystem.h | 2 + src/Game/CapturePointSystem.cpp | 124 ++++++++++++------------------ 2 files changed, 53 insertions(+), 73 deletions(-) diff --git a/include/Game/CapturePointSystem.h b/include/Game/CapturePointSystem.h index c9ff0477..87410c92 100644 --- a/include/Game/CapturePointSystem.h +++ b/include/Game/CapturePointSystem.h @@ -37,6 +37,8 @@ private: int m_Team1HomeCapturePoint = m_NotACapturePoint; int m_Team2HomeCapturePoint = m_NotACapturePoint; + const double m_CaptureTimeToTakeOver = 15.0; + //vectors which will keep track of enter/leave changes std::vector> m_ETriggerTouchVector; std::vector> m_ETriggerLeaveVector; diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp index 4e9230ef..b4ccc771 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/CapturePointSystem.cpp @@ -16,6 +16,7 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture int firstTeamPlayersStandingInside = 0; int secondTeamPlayersStandingInside = 0; + //check how many players are standing inside and are healthy for (size_t i = 0; i < m_ETriggerTouchVector.size(); i++) { auto triggerTouched = m_ETriggerTouchVector[i]; @@ -30,10 +31,10 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture if ((int)currentHealth == 0) continue; //check team - 0 = no team - int teamNumber = (int)world->GetComponent(playerID, "Player")["TeamNumber"]; + int teamNumber = world->GetComponent(playerID, "Player")["TeamNumber"]; if (teamNumber == 1) firstTeamPlayersStandingInside++; - if (teamNumber == 2) + else if (teamNumber == 2) secondTeamPlayersStandingInside++; continue; } @@ -41,113 +42,90 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture int ownedBy = capturePoint["OwnedBy"]; - //check what capturePoint can be taken over next - //A. no capturepoint taken yet for at least one of the teams - //A1. at the start of the match the system is unaware of what capturePoint is the first one for each team + /*check what capturePoint can be taken over next: + no capturepoint taken yet for at least one of the teams <-> + at the start of the match the system is unaware of what capturePoint is the first one for each team*/ if (m_Team1NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 1) { m_Team1NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; m_Team1HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team1NextPossibleCapturePoint } - if (m_Team2NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 2) { + else if (m_Team2NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 2) { m_Team2NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; m_Team2HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team2NextPossibleCapturePoint } - //B. at least one capturepoint has been taken over + //at least one capturepoint has been taken over //do nothing, its being handled inside the next code: - //TODO: refactor code a bit + //create data to be used in option B + //check so this is the next possible capture point for the take-over team and see if only one team is standing inside it + double timerDeltaChange = 0.0; + int currentTeam = 0; + if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside == 0 + && m_Team1NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) + { + timerDeltaChange = firstTeamPlayersStandingInside*dt; + currentTeam = 1; + } + else if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0 + && m_Team2NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) + { + timerDeltaChange = -secondTeamPlayersStandingInside*dt; + currentTeam = 2; + } //A.nobodys standing inside if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside == 0) { //do nothing (?) } - //B.first team has players but second none, and this capturePoint is the next in line to be able to be captured - if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside == 0 - && m_Team1NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { - //ownedBy 1 -> timer should stay at 15 - //increased by numberOfPlayersInside*dt - //if capturePoint is not owned by the team, just increase the CaptureTimer - if (ownedBy != 1) - capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + firstTeamPlayersStandingInside*dt; - //if capturePoint is owned by the team, and the other team has been trying to take it, then increase the timer towards 0 - if (ownedBy == 1 && (double)capturePoint["CaptureTimer"] < 0.0) - capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + firstTeamPlayersStandingInside*dt; - //check if captureTimer > 15 and if so change owner and publish the eCaptured event - //TODO: graphics 25,50,75% captured events? for graphical displaying - if ((double)capturePoint["CaptureTimer"] > 15.0) { - //capturePoint is now owned by this team, hence also reset the captureTimer so it still takes 15secs to take it back - capturePoint["OwnedBy"] = 1; + + //B. at most one of the teams have players inside (this means datavariable currentTeam is not 0) + else if (currentTeam != 0) { + //if capturePoint is not owned by the take-over team, just modify the CaptureTimer accordingly + if (ownedBy != currentTeam) + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; + //if capturePoint is owned by the team, and the other team has been trying to take it, then increase/decrease the timer towards 0.0 + if (ownedBy == currentTeam && currentTeam == 1 && (double)capturePoint["CaptureTimer"] < 0.0) + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; + if (ownedBy == currentTeam && currentTeam == 2 && (double)capturePoint["CaptureTimer"] > 0.0) + capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; + //check if captureTimer > m_CaptureTimeToTakeOver and if so change owner and publish the eCaptured event + if (abs((double)capturePoint["CaptureTimer"]) > abs(m_CaptureTimeToTakeOver)) { + capturePoint["OwnedBy"] = currentTeam; capturePoint["CaptureTimer"] = 0.0; //publish Captured event Events::Captured e; e.CapturePointID = capturePoint.EntityID; - e.TeamNumberThatCapturedCapturePoint = 1; + e.TeamNumberThatCapturedCapturePoint = currentTeam; m_EventBroker->Publish(e); - //modify next m_Team1NextPossibleCapturePoint - //example team1:s homepoint is at 0 and team2:s at 7. team 1 capture 3, next will be 4 - //example team1:s homepoint is at 7 and team2:s at 0. team 1 capture 3, next will be 2 + //modify nextPossibleCapturePoint, depending on, example: if team 1 has "0" as homebase or team 1 has "7" as homebase if (m_Team1HomeCapturePoint < m_Team2HomeCapturePoint) { - m_Team1NextPossibleCapturePoint++; + if (currentTeam == 1) + m_Team1NextPossibleCapturePoint++; + if (currentTeam == 2) + m_Team2NextPossibleCapturePoint--; //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well if (m_Team1NextPossibleCapturePoint > m_Team2NextPossibleCapturePoint) m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint; } else { - m_Team1NextPossibleCapturePoint--; + if (currentTeam == 1) + m_Team1NextPossibleCapturePoint--; + if (currentTeam == 2) + m_Team2NextPossibleCapturePoint++; //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well if (m_Team1NextPossibleCapturePoint < m_Team2NextPossibleCapturePoint) m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint; } } } - //C.second team has players but second none, and this capturePoint is the next in line to be able to be captured - if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0 - && m_Team2NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { - //ownedBy 2 -> timer should stay at -15 - //decreased by numberOfPlayersInside*dt - //if capturePoint is not owned by the team, just increase the CaptureTimer - if (ownedBy != 2) - capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] - secondTeamPlayersStandingInside*dt; - //if capturePoint is owned by the team, and the other team has been trying to take it, then increase the timer towards 0 - if (ownedBy == 2 && (double)capturePoint["CaptureTimer"] > 0.0) - capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] - secondTeamPlayersStandingInside*dt; - //check if captureTimer < -15 and if so change owner and publish the eCaptured event - //TODO: graphics 25,50,75% captured events? for graphical displaying - if ((double)capturePoint["CaptureTimer"] < -15.0) { - //capturePoint is now owned by this team, hence also reset the captureTimer so it still takes 15secs to take it back - capturePoint["OwnedBy"] = 2; - capturePoint["CaptureTimer"] = 0.0; - Events::Captured e; - e.CapturePointID = capturePoint.EntityID; - e.TeamNumberThatCapturedCapturePoint = 2; - m_EventBroker->Publish(e); - //modify next m_Team2NextPossibleCapturePoint - //example team2:s homepoint is at 0 and team1:s at 7. team 2 capture 3, next will be 4 - //example team2:s homepoint is at 7 and team1:s at 0. team 2 capture 3, next will be 2 - if (m_Team2HomeCapturePoint < m_Team1HomeCapturePoint) - { - m_Team2NextPossibleCapturePoint++; - //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well - if (m_Team2NextPossibleCapturePoint > m_Team1NextPossibleCapturePoint) - m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint; - } - else - { - m_Team2NextPossibleCapturePoint--; - //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well - if (m_Team2NextPossibleCapturePoint < m_Team1NextPossibleCapturePoint) - m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint; - } - } - } - //D.both teams have players inside - if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside > 0) { + //C.both teams have players inside + else if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside > 0) { //do nothing (?) } - //WIN: check for possible winCondition = check if the homebase is owned by the other team + //check for possible winCondition = check if the homebase is owned by the other team if (!m_WinnerWasFound && (int)capturePoint["OwnedBy"] != 0 && (int)capturePoint["IsHomeCapturePointForTeamNumber"] != 0 && (int)capturePoint["IsHomeCapturePointForTeamNumber"] != (int)capturePoint["OwnedBy"]) { //publish Win event From 696f44a673788475d2df091ed1e2d5893c4d9934 Mon Sep 17 00:00:00 2001 From: Jocke Date: Thu, 14 Jan 2016 17:11:54 +0100 Subject: [PATCH 049/224] Added logic for mapping between ServerEntityIDs and LocalEntityIDs removed old code that wasn't used. Added 1 map to Client and renamed m_ServerToClientMap to m_ServerIDToClientID. // Good to know To keep this structure please use insertIntoServerClientMaps() when adding items to them. m_ServerIDToClientID and m_ClientIDToServerID maps between server EntityIDs and local EntityIDs. To see if a local EntityID exist in m_ClientIDToServerID use clientServerMapsHasEntity(EntityID clientEntityID); To see if server EntityID exist in m_ServerIDToClientID use serverClientMapsHasEntity(EntityID serverEntityID); --- include/Engine/Network/Client.h | 23 ++--- include/Engine/Network/MessageType.h | 4 +- include/Engine/Network/Server.h | 4 - src/Engine/Network/Client.cpp | 122 ++++++++------------------- src/Engine/Network/Server.cpp | 34 ++------ 5 files changed, 56 insertions(+), 131 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 3027ad87..81b2b834 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -34,8 +34,6 @@ private: // Sending message to server logic int bytesRead = -1; char readBuf[INPUTSIZE] = { 0 }; - int snapshotInterval = 33; - std::clock_t previousSnapshotMessage = std::clock(); // Packet loss logic unsigned int m_PacketID = 0; @@ -46,40 +44,43 @@ private: World* m_World; std::string m_PlayerName; int m_PlayerID = -1; - + EntityID m_ServerEntityID = std::numeric_limits::max(); // Server Client Lookup map // Assumes that root node for client and server is EntityID 0. - std::unordered_map m_ServerToClientMap; + + // Don't Add items to these two maps with insert, use insertIntoServerClientMaps(EntityID, EntityID)!!!! + std::unordered_map m_ServerIDToClientID; + std::unordered_map m_ClientIDToServerID; // Network logic PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; SnapshotDefinitions m_NextSnapshot; double m_DurationOfPingTime; std::clock_t m_StartPingTime; - // Use to check if we should send disconnect message - // if game is turned of by closing window. - bool m_WasStarted = false; // Private member functions void readFromServer(); - void sendInputEvents(); int receive(char* data, size_t length); void send(Packet& packet); void connect(); void disconnect(); void ping(); - void moveMessageHead(char*& data, size_t& length, size_t stepSize); void parseMessageType(Packet& packet); - void parseEventMessage(Packet& packet); void updateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType); void parseConnect(Packet& packet); + void parsePlayerConnected(Packet& packet); void parsePing(); void parseServerPing(); void parseSnapshot(Packet& packet); void identifyPacketLoss(); bool isConnected(); EntityID createPlayer(); - bool hasMappedEntity(EntityID entityID); + // Mapping Logic + // Returns if local EntityID exist in map + bool clientServerMapsHasEntity(EntityID clientEntityID); + // Returns if server EntityID exist in map + bool serverClientMapsHasEntity(EntityID serverEntityID); + void insertIntoServerClientMaps(EntityID serverEntityID, EntityID clientEntityID); // Events EventBroker* m_EventBroker; diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index 42b049e8..ba9684d9 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -11,9 +11,9 @@ enum class MessageType ServerPing, Message, Snapshot, - Event, OnInputCommand, - OnPlayerDamage + OnPlayerDamage, + PlayerConnected }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index dc7b25cd..4c71be95 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -48,8 +48,6 @@ private: // Game logic World* m_World; EventBroker* m_EventBroker; - // vec.size() = ammount of players to create, stores playerID's - std::vector m_PlayersToCreate; // Packet loss logic unsigned int m_PacketID; @@ -61,8 +59,6 @@ private: void readFromClients(); void send(Packet& packet, int playerID); void send(Packet& packet); - void moveMessageHead(char*& data, size_t& length, size_t stepSize); - void broadcast(std::string message); void broadcast(Packet& packet); void sendSnapshot(); void sendPing(); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index c073e79a..37534a27 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -6,15 +6,13 @@ using namespace boost::asio::ip; Client::Client(ConfigFile* config) : m_Socket(m_IOService) { // Asumes root node is EntityID 0 - m_ServerToClientMap.insert(std::make_pair(0, 0)); + insertIntoServerClientMaps(0, 0); // Default is local host std::string address = config->Get("Networking.Address", "127.0.0.1"); int port = config->Get("Networking.Port", 13); m_ReceiverEndpoint = udp::endpoint(boost::asio::ip::address::from_string(address), port); // Set up network stream m_PlayerName = config->Get("Networking.Name", "Raptorcopter"); - m_NextSnapshot.InputForward = ""; - m_NextSnapshot.InputRight = ""; } Client::~Client() @@ -22,7 +20,6 @@ Client::~Client() void Client::Start(World* world, EventBroker* eventBroker) { - m_WasStarted = true; m_EventBroker = eventBroker; m_World = world; @@ -47,58 +44,6 @@ void Client::readFromServer() parseMessageType(packet); } } - std::clock_t currentTime = std::clock(); - if (snapshotInterval < (1000 * (currentTime - previousSnapshotMessage) / (double)CLOCKS_PER_SEC)) { - if (isConnected()) { - //sendSnapshotToServer(); - } - previousSnapshotMessage = currentTime; - } -} - -void Client::sendInputEvents() -{ - // Reset previous key state in snapshot. - m_NextSnapshot.InputForward = ""; - m_NextSnapshot.InputRight = ""; - - auto player = m_World->GetComponent(m_PlayerDefinitions[m_PlayerID].EntityID, "Player"); - - // See if any movement keys are down - // We dont care if it's overwritten by later - // if statement. Watcha gonna do, right! - if (player["Forward"]) { - m_NextSnapshot.InputForward = "+Forward"; - } - if (player["Left"]) { - m_NextSnapshot.InputRight = "-Right"; - } - if (player["Back"]) { - m_NextSnapshot.InputForward = "-Forward"; - } - if (player["Right"]) { - m_NextSnapshot.InputRight = "+Right"; - } - - if (m_NextSnapshot.InputForward != "") { - Packet packet(MessageType::Event, m_SendPacketID); - packet.WriteString(m_NextSnapshot.InputForward); - send(packet); - } else { - Packet packet(MessageType::Event, m_SendPacketID); - packet.WriteString("0Forward"); - send(packet); - } - - if (m_NextSnapshot.InputRight != "") { - Packet packet(MessageType::Event, m_SendPacketID); - packet.WriteString(m_NextSnapshot.InputRight); - send(packet); - } else { - Packet packet(MessageType::Event, m_SendPacketID); - packet.WriteString("0Right"); - send(packet); - } } void Client::parseMessageType(Packet& packet) @@ -130,9 +75,8 @@ void Client::parseMessageType(Packet& packet) break; case MessageType::Disconnect: break; - case MessageType::Event: - parseEventMessage(packet); - break; + case MessageType::PlayerConnected: + parsePlayerConnected(packet); default: break; } @@ -140,10 +84,19 @@ void Client::parseMessageType(Packet& packet) void Client::parseConnect(Packet& packet) { + // Set your own player id m_PlayerID = packet.ReadPrimitive(); + m_ServerEntityID = packet.ReadPrimitive(); + // Map ServerEntityID and your PlayerID LOG_INFO("%i: I am player: %i", m_PacketID, m_PlayerID); } +void Client::parsePlayerConnected(Packet & packet) +{ + // Map ServerEntityID and other player's PlayerID + LOG_INFO("A Player connected"); +} + void Client::parsePing() { m_DurationOfPingTime = 1000 * (std::clock() - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); @@ -157,19 +110,6 @@ void Client::parseServerPing() send(packet); } -void Client::parseEventMessage(Packet& packet) -{ - int Id = -1; - std::string command = packet.ReadString(); - if (command.find("+Player") != std::string::npos) { - Id = packet.ReadPrimitive(); - // Sett Player name - m_PlayerDefinitions[Id].Name = command.erase(0, 7); - } else { - LOG_INFO("%i: Event message: %s", m_PacketID, command.c_str()); - } -} - void Client::updateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType) { for (auto field : componentInfo.FieldsInOrder) { @@ -194,9 +134,9 @@ void Client::parseSnapshot(Packet& packet) EntityID receivedParentEntityID = packet.ReadPrimitive(); ComponentInfo componentInfo = m_World->GetComponents(componentType)->ComponentInfo(); // Check if the received EntityID is mapped to one of our local EntityIDs - if (hasMappedEntity(receivedEntityID)) { + if (clientServerMapsHasEntity(receivedEntityID)) { // Get the local EntityID - EntityID entityID = m_ServerToClientMap.at(receivedEntityID); + EntityID entityID = m_ServerIDToClientID.at(receivedEntityID); // Check if the component exists if (m_World->HasComponent(entityID, componentType)) { // If the entity and the component exists update it @@ -213,7 +153,7 @@ void Client::parseSnapshot(Packet& packet) // Create Entity // If entity dosen't exist EntityID newEntityID = m_World->CreateEntity(); - m_ServerToClientMap.insert(std::make_pair(receivedEntityID, newEntityID)); + insertIntoServerClientMaps(receivedEntityID, newEntityID); // Check if EntityIDs are out of sync if (newEntityID != receivedEntityID) { LOG_INFO("Client::parseSnapshot(Packet& packet): Newly created EntityID is not the \ @@ -228,15 +168,15 @@ void Client::parseSnapshot(Packet& packet) // Parent Logic // Don't need to check if receivedEntityID is mapped. (It should have been set) if (receivedParentEntityID != std::numeric_limits::max()) { - if (hasMappedEntity(receivedParentEntityID)) { - m_World->SetParent(m_ServerToClientMap.at(receivedEntityID), m_ServerToClientMap.at(receivedParentEntityID)); + if (clientServerMapsHasEntity(receivedParentEntityID)) { + m_World->SetParent(m_ServerIDToClientID.at(receivedEntityID), m_ServerIDToClientID.at(receivedParentEntityID)); // If Parent dosen't exist create one and map receivedParentEntityID to it. } else { // Create the new parent and add it to map EntityID newParentEntityID = m_World->CreateEntity(); - m_ServerToClientMap.insert(std::make_pair(receivedParentEntityID, newParentEntityID)); + insertIntoServerClientMaps(receivedParentEntityID, newParentEntityID); // Set the newly created Entity as parent. - m_World->SetParent(m_ServerToClientMap.at(receivedEntityID), newParentEntityID); + m_World->SetParent(m_ServerIDToClientID.at(receivedEntityID), newParentEntityID); } } } @@ -252,7 +192,7 @@ int Client::receive(char* data, size_t length) 0, error); if (error) { - LOG_ERROR("receive: %s", error.message().c_str()); + //LOG_ERROR("receive: %s", error.message().c_str()); } return bytesReceived; } @@ -288,12 +228,6 @@ void Client::ping() send(packet); } -void Client::moveMessageHead(char*& data, size_t& length, size_t stepSize) -{ - data += stepSize; - length -= stepSize; -} - bool Client::OnInputCommand(const Events::InputCommand & e) { if (e.Command == "ConnectToServer") { // Connect for now @@ -351,7 +285,19 @@ EntityID Client::createPlayer() return entityID; } -bool Client::hasMappedEntity(EntityID entityID) +bool Client::clientServerMapsHasEntity(EntityID clientEntityID) { - return m_ServerToClientMap.find(entityID) != m_ServerToClientMap.end(); + return m_ClientIDToServerID.find(clientEntityID) != m_ClientIDToServerID.end(); +} + +bool Client::serverClientMapsHasEntity(EntityID serverEntityID) +{ + return m_ServerIDToClientID.find(serverEntityID) != m_ServerIDToClientID.end(); +} + +void Client::insertIntoServerClientMaps(EntityID serverEntityID, EntityID clientEntityID) +{ + m_ServerIDToClientID.insert(std::make_pair(serverEntityID, clientEntityID)); + m_ClientIDToServerID.insert(std::make_pair(clientEntityID, serverEntityID)); + } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 1a915863..5ec674d0 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -50,7 +50,7 @@ void Server::readFromClients() // Time out logic if (checkTimeOutInterval < (1000 * (currentTime - timOutTimer) / (double)CLOCKS_PER_SEC)) { - //checkForTimeOuts(); + checkForTimeOuts(); timOutTimer = currentTime; } } @@ -80,8 +80,6 @@ void Server::parseMessageType(Packet& packet) case MessageType::Disconnect: parseDisconnect(); break; - case MessageType::Event: - break; case MessageType::OnInputCommand: parseOnInputCommand(packet); break; @@ -120,23 +118,6 @@ void Server::send(Packet & packet) 0); } -void Server::moveMessageHead(char *& data, size_t & length, size_t stepSize) -{ - data += stepSize; - length -= stepSize; -} - -void Server::broadcast(std::string message) -{ - Packet packet(MessageType::Event, m_SendPacketID); - packet.WriteString(message); - for (int i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { - send(packet, i); - } - } -} - void Server::broadcast(Packet& packet) { for (int i = 0; i < MAXCONNECTIONS; ++i) { @@ -214,7 +195,7 @@ void Server::checkForTimeOuts() void Server::disconnect(int i) { - broadcast("A player disconnected"); + //broadcast("A player disconnected"); LOG_INFO("Player %i disconnected/timed out", i); // Remove enteties and stuff @@ -234,7 +215,7 @@ void Server::parseOnInputCommand(Packet& packet) } void Server::parseOnPlayerDamage(Packet & packet) -{ +{ Events::PlayerDamage e; e.DamageAmount = packet.ReadPrimitive(); e.PlayerDamagedID = packet.ReadPrimitive(); @@ -264,15 +245,16 @@ void Server::parseConnect(Packet& packet) LOG_INFO("Player \"%s\" connected on IP: %s", m_PlayerDefinitions[i].Name.c_str(), m_PlayerDefinitions[i].Endpoint.address().to_string().c_str()); + // Send a message to the player that connected Packet packet(MessageType::Connect, m_SendPacketID); packet.WritePrimitive(i); // Player ID - + packet.WritePrimitive(m_PlayerDefinitions[i].EntityID); // Entity ID send(packet, i); // Send notification that a player has connected - std::string str = m_PacketID + "Player " + m_PlayerDefinitions[i].Name + " connected on: " - + m_PlayerDefinitions[i].Endpoint.address().to_string(); - broadcast(str); + Packet notificationPacket(MessageType::PlayerConnected, m_PacketID); + broadcast(notificationPacket); + break; } } From 76a8b43ca3e21442f69abaf9a8b7aee312a45369 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Fri, 15 Jan 2016 11:04:00 +0100 Subject: [PATCH 050/224] Fixed logic for CapturePointSystem --- src/Game/CapturePointSystem.cpp | 64 +++++++++++++++++++++------------ src/Game/HealthSystem.cpp | 1 + 2 files changed, 42 insertions(+), 23 deletions(-) diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp index b4ccc771..88eff1e4 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/CapturePointSystem.cpp @@ -24,18 +24,22 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture //some player has touched this - lets figure out: what team, health EntityID playerID = std::get<0>(triggerTouched); bool hasHealthComponent = world->HasComponent(playerID, "Health"); - if (!hasHealthComponent) + if (!hasHealthComponent) { continue; + } double currentHealth = world->GetComponent(playerID, "Health")["Health"]; //check if player is dead - if ((int)currentHealth == 0) + if ((int)currentHealth == 0) { continue; + } //check team - 0 = no team int teamNumber = world->GetComponent(playerID, "Player")["TeamNumber"]; - if (teamNumber == 1) + if (teamNumber == 1) { firstTeamPlayersStandingInside++; - else if (teamNumber == 2) + } + else if (teamNumber == 2) { secondTeamPlayersStandingInside++; + } continue; } } @@ -81,13 +85,14 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture //B. at most one of the teams have players inside (this means datavariable currentTeam is not 0) else if (currentTeam != 0) { //if capturePoint is not owned by the take-over team, just modify the CaptureTimer accordingly - if (ownedBy != currentTeam) + if (ownedBy != currentTeam) { capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; + } //if capturePoint is owned by the team, and the other team has been trying to take it, then increase/decrease the timer towards 0.0 - if (ownedBy == currentTeam && currentTeam == 1 && (double)capturePoint["CaptureTimer"] < 0.0) - capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; - if (ownedBy == currentTeam && currentTeam == 2 && (double)capturePoint["CaptureTimer"] > 0.0) + if ((ownedBy == currentTeam && currentTeam == 1 && (double)capturePoint["CaptureTimer"] < 0.0) || + (ownedBy == currentTeam && currentTeam == 2 && (double)capturePoint["CaptureTimer"] > 0.0)) { capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; + } //check if captureTimer > m_CaptureTimeToTakeOver and if so change owner and publish the eCaptured event if (abs((double)capturePoint["CaptureTimer"]) > abs(m_CaptureTimeToTakeOver)) { capturePoint["OwnedBy"] = currentTeam; @@ -98,24 +103,38 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture e.TeamNumberThatCapturedCapturePoint = currentTeam; m_EventBroker->Publish(e); //modify nextPossibleCapturePoint, depending on, example: if team 1 has "0" as homebase or team 1 has "7" as homebase - if (m_Team1HomeCapturePoint < m_Team2HomeCapturePoint) { - if (currentTeam == 1) + + //0 = false 1 = true + bool team1HasTheZeroCapturePoint = m_Team1HomeCapturePoint < m_Team2HomeCapturePoint; + + if (team1HasTheZeroCapturePoint) { + if (currentTeam == 1) { m_Team1NextPossibleCapturePoint++; - if (currentTeam == 2) + } + else { m_Team2NextPossibleCapturePoint--; - //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well - if (m_Team1NextPossibleCapturePoint > m_Team2NextPossibleCapturePoint) - m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint; + } + //adjust flag for other team if their previous point has just been taken + if (m_Team2NextPossibleCapturePoint == m_Team1NextPossibleCapturePoint - 2) { + m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint + 1; + } + if (m_Team1NextPossibleCapturePoint == m_Team2NextPossibleCapturePoint + 2) { + m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint - 1; + } } - else - { - if (currentTeam == 1) + else { + if (currentTeam == 1) { m_Team1NextPossibleCapturePoint--; - if (currentTeam == 2) + } + else { m_Team2NextPossibleCapturePoint++; - //if this was a contested capturePoint (i.e. both teams try to take point 3), then modify other teams next point as well - if (m_Team1NextPossibleCapturePoint < m_Team2NextPossibleCapturePoint) - m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint; + } + if (m_Team2NextPossibleCapturePoint == m_Team1NextPossibleCapturePoint + 2) { + m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint - 1; + } + if (m_Team1NextPossibleCapturePoint == m_Team2NextPossibleCapturePoint - 2) { + m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint + 1; + } } } } @@ -139,8 +158,7 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture bool CapturePointSystem::OnTriggerTouch(const Events::TriggerTouch& e) { - //auto personEntered = e.Entity; - //auto thingEntered = e.Trigger; + //personEntered = e.Entity, thingEntered = e.Trigger m_ETriggerTouchVector.push_back(std::make_tuple(e.Entity, e.Trigger)); return true; } diff --git a/src/Game/HealthSystem.cpp b/src/Game/HealthSystem.cpp index 7a1d5005..7ae78df4 100644 --- a/src/Game/HealthSystem.cpp +++ b/src/Game/HealthSystem.cpp @@ -27,6 +27,7 @@ void HealthSystem::UpdateComponent(World *world, ComponentWrapper &health, doubl m_DeltaHealthVector.erase(m_DeltaHealthVector.begin() + i - 1); //check if health is <= 0 if ((double)health["Health"] <= 0.0f) { + health["Health"] = 0.0; //publish death event Events::PlayerDeath e; e.PlayerID = player.EntityID; From c8fe6853c0e55d153e4aa1e3593565f96db053f3 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Fri, 15 Jan 2016 11:17:22 +0100 Subject: [PATCH 051/224] Removed ShootEvent from CapturePoint --- include/Engine/Core/EShoot.h | 22 -- include/Game/PlayerSystem.h | 10 - resources/Schema/Components.xsd | 2 - resources/Schema/Components/Player.xml | 1 - resources/Schema/Components/Player.xsd | 1 - resources/Schema/Components/PrimaryItem.xml | 4 - resources/Schema/Components/PrimaryItem.xsd | 21 -- resources/Schema/Components/SecondaryItem.xml | 4 - resources/Schema/Components/SecondaryItem.xsd | 21 -- resources/Schema/Types/Entity.xsd | 2 - src/Game/PlayerSystem.cpp | 43 --- src/Tests/ShootEventTest.cpp | 256 ------------------ src/Tests/ShootEventTest.h | 52 ---- 13 files changed, 439 deletions(-) delete mode 100644 include/Engine/Core/EShoot.h delete mode 100644 resources/Schema/Components/PrimaryItem.xml delete mode 100644 resources/Schema/Components/PrimaryItem.xsd delete mode 100644 resources/Schema/Components/SecondaryItem.xml delete mode 100644 resources/Schema/Components/SecondaryItem.xsd delete mode 100644 src/Tests/ShootEventTest.cpp delete mode 100644 src/Tests/ShootEventTest.h diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h deleted file mode 100644 index 3887606b..00000000 --- a/include/Engine/Core/EShoot.h +++ /dev/null @@ -1,22 +0,0 @@ -#ifndef EShoot_h__ -#define EShoot_h__ - -#include "EventBroker.h" -#include "../Core/Entity.h" -#include "Engine/GLM.h" - -namespace Events -{ - -struct Shoot : Event -{ - //shotgun etc has different amounts of damage probably (a sniper shot might one-shot) - //also different weapons will have different spread - int currentlyEquippedItem; - //currentAimingPoint must be sent, in case the camera is moved while the event is being processed - glm::vec2 currentAimingPoint; -}; - -} - -#endif \ No newline at end of file diff --git a/include/Game/PlayerSystem.h b/include/Game/PlayerSystem.h index a48af3e4..ba0562dc 100644 --- a/include/Game/PlayerSystem.h +++ b/include/Game/PlayerSystem.h @@ -8,7 +8,6 @@ #include "Core/System.h" #include "Collision/ETrigger.h" #include "Core/EMouseRelease.h" -#include "Core/EShoot.h" class PlayerSystem : public PureSystem { @@ -19,14 +18,11 @@ public: EVENT_SUBSCRIBE_MEMBER(m_ETouch, &PlayerSystem::OnTouch); EVENT_SUBSCRIBE_MEMBER(m_EEnter, &PlayerSystem::OnEnter); EVENT_SUBSCRIBE_MEMBER(m_ELeave, &PlayerSystem::OnLeave); - EVENT_SUBSCRIBE_MEMBER(m_MouseRelease, &PlayerSystem::OnMouseRelease); } virtual void UpdateComponent(World* world, ComponentWrapper& player, double dt) override; private: float m_Speed = 5; - bool leftMouseWasReleased = false; - glm::vec2 aimingCoordinates; EventRelay m_EEnter; bool OnEnter(const Events::TriggerEnter &event); EventRelay m_ETouch; @@ -34,12 +30,6 @@ private: EventRelay m_ELeave; bool PlayerSystem::OnLeave(const Events::TriggerLeave &event); EventRelay m_MouseRelease; - bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e); - enum class HeldItem { - None = 0, - PrimaryItem = 1, - SecondaryItem = 2 - }; }; #endif \ No newline at end of file diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index 1a78ed0c..175bd49c 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -9,7 +9,5 @@ - - \ No newline at end of file diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index a05c003e..5196f170 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,6 +1,5 @@ 0 - 0 false false diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 49b0537a..e6e0a4ff 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -14,7 +14,6 @@ - diff --git a/resources/Schema/Components/PrimaryItem.xml b/resources/Schema/Components/PrimaryItem.xml deleted file mode 100644 index 0d0ccca2..00000000 --- a/resources/Schema/Components/PrimaryItem.xml +++ /dev/null @@ -1,4 +0,0 @@ - - 0 - 0 - \ No newline at end of file diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd deleted file mode 100644 index 35e2fca6..00000000 --- a/resources/Schema/Components/PrimaryItem.xsd +++ /dev/null @@ -1,21 +0,0 @@ - - - - - - - - The Players Primary Item/Weapon - - - - - Ammo count - - - Cooldown till next item/weapon use - - - - - \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xml b/resources/Schema/Components/SecondaryItem.xml deleted file mode 100644 index 095dfef6..00000000 --- a/resources/Schema/Components/SecondaryItem.xml +++ /dev/null @@ -1,4 +0,0 @@ - - 0 - 0 - \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd deleted file mode 100644 index bee25541..00000000 --- a/resources/Schema/Components/SecondaryItem.xsd +++ /dev/null @@ -1,21 +0,0 @@ - - - - - - - - The Players Secondary Item/Weapon - - - - - Ammo count - - - Cooldown till next item/weapon use - - - - - \ No newline at end of file diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 2f352354..45bf177d 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -16,8 +16,6 @@ - - diff --git a/src/Game/PlayerSystem.cpp b/src/Game/PlayerSystem.cpp index c9112b01..f06b0c9b 100644 --- a/src/Game/PlayerSystem.cpp +++ b/src/Game/PlayerSystem.cpp @@ -21,38 +21,6 @@ void PlayerSystem::UpdateComponent(World * world, ComponentWrapper & player, dou ComponentWrapper& transform = world->GetComponent(player.EntityID, "Transform"); (glm::vec3&)transform["Position"] += (glm::vec3)player["Velocity"]; } - - //do shootEvent: if left mouse was released, and ammo/weaponcooldown/playeralive/shootingcooldown are ok - if (leftMouseWasReleased) { - leftMouseWasReleased = false; - //get the health component linked to the playerId - double currentHealth = (double)world->GetComponent(player.EntityID, "Health")["Health"]; - int currentAmmo = 0; - double currentCoolDownTimer = 0.0; - std::string HeldItemString = ""; - if ((int)player["EquippedItem"] == (int)HeldItem::PrimaryItem) - HeldItemString = "PrimaryItem"; - if ((int)player["EquippedItem"] == (int)HeldItem::SecondaryItem) - HeldItemString = "SecondaryItem"; - - if (HeldItemString != "") { - ComponentWrapper& currentItem = world->GetComponent(player.EntityID, HeldItemString); - currentAmmo = (int)currentItem["Ammo"]; - currentCoolDownTimer = (double)currentItem["CoolDownTimer"]; - - if (currentHealth > 0.0 && currentAmmo > 0 && currentCoolDownTimer < 0.001) { - //decrease ammo count - //TODO: temp, set the cooldowntimer - probably done in some other system (itemSystem?) later - currentItem["Ammo"] = (int)currentItem["Ammo"] - 1; - currentItem["CoolDownTimer"] = 2.0;//change later! - //create and publish the shoot event - Events::Shoot eShoot; - eShoot.currentAimingPoint = aimingCoordinates; - eShoot.currentlyEquippedItem = (int)(player["EquippedItem"]); - m_EventBroker->Publish(eShoot); - } - } - } } bool PlayerSystem::OnTouch(const Events::TriggerTouch &event) @@ -72,14 +40,3 @@ bool PlayerSystem::OnLeave(const Events::TriggerLeave &event) LOG_INFO("Player entity %i left widget (entity %i).", event.Entity, event.Trigger); return false; } - -bool PlayerSystem::OnMouseRelease(const Events::MouseRelease& e) -{ - //kolla ammoleft, cooldowntimer shooting - //kolla om left mouse varit nere - if (e.Button != GLFW_MOUSE_BUTTON_LEFT) - return false; - aimingCoordinates = glm::vec2(e.X, e.Y); - leftMouseWasReleased = true; - return true; -} \ No newline at end of file diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp deleted file mode 100644 index f24bfed8..00000000 --- a/src/Tests/ShootEventTest.cpp +++ /dev/null @@ -1,256 +0,0 @@ -#include -using boost::unit_test_framework::test_suite; -using boost::unit_test_framework::test_case; - -#include "ShootEventTest.h" -#include "Game/HealthSystem.h" - -BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) - -//dont use the same name as the classname in test cases... -BOOST_AUTO_TEST_CASE(ShootEventTest_PrimaryWeaponFiring) -{ - //Test firing primary weapon - ShootEventTest game(1); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - BOOST_TEST(success); -} -BOOST_AUTO_TEST_CASE(ShootEventTest_SecondaryWeaponFiring) -{ - //Test firing secondary weapon - ShootEventTest game(2); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - BOOST_TEST(success); -} -BOOST_AUTO_TEST_CASE(ShootEventTest_NoWeaponFiring) -{ - //Test firing with no weapon equipped - ShootEventTest game(3); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - if (game.TestSucceeded) - success = true; - BOOST_TEST(success); -} -BOOST_AUTO_TEST_CASE(ShootEventTest_WeaponOnCooldown) -{ - //Test firing with weapon on cooldown - ShootEventTest game(4); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - if (game.TestSucceeded) - success = true; - BOOST_TEST(success); -} -BOOST_AUTO_TEST_SUITE_END() - -ShootEventTest::ShootEventTest(int runTestNumber) -{ - ResourceManager::RegisterType("ConfigFile"); - ResourceManager::RegisterType("EntityFile"); - - m_Config = ResourceManager::Load("Config.ini"); - std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); - LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); - - // Create the core event broker - m_EventBroker = new EventBroker(); - - // Create a world - m_World = new World(); - - // Create system pipeline - m_SystemPipeline = new SystemPipeline(m_EventBroker); - m_SystemPipeline->AddSystem(0); - m_SystemPipeline->AddSystem(0); - - if (!mapToLoad.empty()) { - auto file = ResourceManager::Load(mapToLoad); - EntityFilePreprocessor fpp(file); - fpp.RegisterComponents(m_World); - EntityFileParser fp(file); - fp.MergeEntities(m_World); - } - - //The Test - //create entity which has transform,player,model,health in it. i.e. is a player - EntityID playerID = m_World->CreateEntity(); - m_PlayerID = playerID; - ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); - ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); - //attach 2x weaps - ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); - ComponentWrapper& sItem = m_World->AttachComponent(playerID, "SecondaryItem"); - - m_RunTestNumber = runTestNumber; - switch (runTestNumber) - { - case 1: - TestSetup1(player, pItem, sItem); - break; - case 2: - TestSetup2(player, pItem, sItem); - break; - case 3: - TestSetup3(player, pItem, sItem); - break; - case 4: - TestSetup4(player, pItem, sItem); - break; - default: - break; - } - - //fire once = trigger event leftmousedown - Events::MouseRelease eMouseRelease; - eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; - eMouseRelease.X = 1.0f; - eMouseRelease.Y = 1.0f; - m_EventBroker->Publish(eMouseRelease); -} - -ShootEventTest::~ShootEventTest() -{ - delete m_SystemPipeline; - delete m_World; - delete m_EventBroker; -} - -void ShootEventTest::TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) -{ - //set currentweap - player["EquippedItem"] = 1; - //set ammo set cooldown - pItem["Ammo"] = 100; - pItem["CoolDownTimer"] = 0.0; -} -void ShootEventTest::TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) -{ - //set currentweap - player["EquippedItem"] = 2; - //set ammo set cooldown - sItem["Ammo"] = 10; - sItem["CoolDownTimer"] = 0.0; -} -void ShootEventTest::TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) -{ - player["EquippedItem"] = 0; - pItem["Ammo"] = 100; - sItem["Ammo"] = 100; - //TestSucceeded will be set to false if ammo changes during the 100 loops - TestSucceeded = true; -} -void ShootEventTest::TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem) -{ - //set currentweap - player["EquippedItem"] = 1; - //set ammo set cooldown - pItem["Ammo"] = 100; - pItem["CoolDownTimer"] = 5.0; - //TestSucceeded will be set to false if ammo changes during the 100 loops - TestSucceeded = true; -} -void ShootEventTest::TestSuccess1() { - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo == 99) - TestSucceeded = true; -} -void ShootEventTest::TestSuccess2() { - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo == 9) - TestSucceeded = true; -} -void ShootEventTest::TestSuccess3() { - //try firing again - Events::MouseRelease eMouseRelease; - eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; - eMouseRelease.X = 1.0f; - eMouseRelease.Y = 1.0f; - m_EventBroker->Publish(eMouseRelease); - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - int currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo != 100 || currentAmmoSecondary != 100) - TestSucceeded = false; -} -void ShootEventTest::TestSuccess4() { - //try firing again - Events::MouseRelease eMouseRelease; - eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; - eMouseRelease.X = 1.0f; - eMouseRelease.Y = 1.0f; - m_EventBroker->Publish(eMouseRelease); - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo != 100) - TestSucceeded = false; -} -void ShootEventTest::Tick() -{ - glfwPollEvents(); - - double currentTime = glfwGetTime(); - double dt = currentTime - m_LastTime; - m_LastTime = currentTime; - - // Iterate through systems and update world! - m_SystemPipeline->Update(m_World, dt); - - m_EventBroker->Swap(); - m_EventBroker->Clear(); - - switch (m_RunTestNumber) - { - case 1: - TestSuccess1(); - break; - case 2: - TestSuccess2(); - break; - case 3: - TestSuccess3(); - break; - case 4: - TestSuccess4(); - break; - default: - break; - } - -} diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h deleted file mode 100644 index e860f41f..00000000 --- a/src/Tests/ShootEventTest.h +++ /dev/null @@ -1,52 +0,0 @@ -#ifndef ShootEventTest_h__ -#define ShootEventTest_h__ - -#include "Core/ResourceManager.h" -#include "Core/ConfigFile.h" -#include "Core/EventBroker.h" -#include "Core/World.h" -#include "Input/InputProxy.h" -#include "Input/KeyboardInputHandler.h" -#include "Input/MouseInputHandler.h" -#include "Core/EKeyDown.h" -#include "Core/EntityFile.h" -#include "Core/SystemPipeline.h" -#include "PlayerSystem.h" - -#include "Core/EntityFilePreprocessor.h" -#include "Core/EntityFileParser.h" -#include "Core/EntityFileWriter.h" - -#include "Core/EMouseRelease.h" -#include "Core/EShoot.h" - -class ShootEventTest -{ -public: - ShootEventTest(int runTestNumber); - ~ShootEventTest(); - - void Tick(); - bool TestSucceeded = false; - -private: - void TestSetup1(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); - void TestSetup2(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); - void TestSetup3(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); - void TestSetup4(ComponentWrapper &player, ComponentWrapper &pItem, ComponentWrapper &sItem); - void TestSuccess1(); - void TestSuccess2(); - void TestSuccess3(); - void TestSuccess4(); - - double m_LastTime; - ConfigFile* m_Config = nullptr; - EventBroker* m_EventBroker; - World* m_World; - SystemPipeline* m_SystemPipeline; - int m_PlayerID; - int m_RunTestNumber; - -}; - -#endif From e7da11fda49d2fa454d2525cef79c5eb59e6c302 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Fri, 15 Jan 2016 11:31:21 +0100 Subject: [PATCH 052/224] Removed OctTreeTests since its too annoying to update them each time RenderSystem gets updated --- src/Tests/HealthSystemTest.h | 1 - src/Tests/OctTreeTestAnders.cpp | 49 ------ src/Tests/OctTreeTestGameClass.cpp | 193 ---------------------- src/Tests/OctTreeTestGameClass.h | 62 ------- src/Tests/OctTreeTestGameMain.cpp | 21 --- src/Tests/OctTreeTestHardCodedTestWorld.h | 134 --------------- 6 files changed, 460 deletions(-) delete mode 100644 src/Tests/OctTreeTestAnders.cpp delete mode 100644 src/Tests/OctTreeTestGameClass.cpp delete mode 100644 src/Tests/OctTreeTestGameClass.h delete mode 100644 src/Tests/OctTreeTestGameMain.cpp delete mode 100644 src/Tests/OctTreeTestHardCodedTestWorld.h diff --git a/src/Tests/HealthSystemTest.h b/src/Tests/HealthSystemTest.h index 2890dfc1..bd3f3de7 100644 --- a/src/Tests/HealthSystemTest.h +++ b/src/Tests/HealthSystemTest.h @@ -8,7 +8,6 @@ #include "Core/InputManager.h" #include "GUI/Frame.h" #include "Core/World.h" -#include "Rendering/RenderQueueFactory.h" #include "Input/InputProxy.h" #include "Input/KeyboardInputHandler.h" #include "Input/MouseInputHandler.h" diff --git a/src/Tests/OctTreeTestAnders.cpp b/src/Tests/OctTreeTestAnders.cpp deleted file mode 100644 index 477ccbf4..00000000 --- a/src/Tests/OctTreeTestAnders.cpp +++ /dev/null @@ -1,49 +0,0 @@ -#include -using boost::unit_test_framework::test_suite; -using boost::unit_test_framework::test_case; -#include //srand - -//#define private public//HACK! Needed for white box testing -//#include "Engine/Core/OctTree.h" -//#include "OldOctTree.h" -//friend class and refactoringIntoNewClass is some extra work and needs to be updated when the original class is updated, and can contain bugs that -//isnt in the original class -//Reflection-inspection seems to be only available for C# -//http://stackoverflow.com/questions/6778496/how-to-do-unit-testing-on-private-members-and-methods-of-c-classes -//http://stackoverflow.com/questions/3676664/unit-testing-of-private-methods - -#include "OctTreeTestGameClass.h" - -#define private public//HACK! Needed for white box testing -#include "Engine/Core/OctTree.h" -//else we would have to "open up" the octTree class more with get/sets, public methods, etc. which is not good encapsulation-wise - -BOOST_AUTO_TEST_SUITE(octTreeTestsA) - -BOOST_AUTO_TEST_CASE(octTreeTest) -{ - //white box testing - //http://softwaretestingfundamentals.com/differences-between-black-box-testing-and-white-box-testing/ - //http://technologyconversations.com/2013/12/11/black-box-vs-white-box-testing/ - - //simple AABB constructor check - auto minCorner = glm::vec3(0.0f, 0.0f, 0.0f); - auto maxCorner = glm::vec3(1.0f, 1.0f, 1.0f); - auto someAABB = AABB(minCorner, maxCorner); - BOOST_CHECK(someAABB.MinCorner() == minCorner); - BOOST_CHECK(someAABB.MaxCorner() == maxCorner); - BOOST_CHECK(someAABB.Center() == 0.5f * (minCorner + maxCorner)); - - //simple destructor check in the end, just look for memleaks, then it didnt clear the AABB structure -} - -BOOST_AUTO_TEST_CASE(octTreeTest2) -{ - //octtree draw etc - Game game(0, nullptr); - while (game.Running()) { - game.Tick(); - } -} - -BOOST_AUTO_TEST_SUITE_END() diff --git a/src/Tests/OctTreeTestGameClass.cpp b/src/Tests/OctTreeTestGameClass.cpp deleted file mode 100644 index 0f195cec..00000000 --- a/src/Tests/OctTreeTestGameClass.cpp +++ /dev/null @@ -1,193 +0,0 @@ -#include "OctTreeTestGameClass.h" - -Game::Game(int argc, char* argv[]) : someOctTree(AABB(-0.5f*worldSize, 0.5f*worldSize), 2) -{ - ResourceManager::RegisterType("ConfigFile"); - ResourceManager::RegisterType("Model"); - ResourceManager::RegisterType("Texture"); - ResourceManager::RegisterType("EntityFile"); - ResourceManager::RegisterType("ShaderProgram"); - - m_Config = ResourceManager::Load("Config.ini"); - LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); - - // Create the core event broker - m_EventBroker = new EventBroker(); - - m_RenderQueueFactory = new RenderQueueFactory(); - - // Create the renderer - m_Renderer = new Renderer(m_EventBroker); - m_Renderer->SetFullscreen(m_Config->Get("Video.Fullscreen", false)); - m_Renderer->SetVSYNC(m_Config->Get("Video.VSYNC", false)); - m_Renderer->SetResolution(Rectangle( - 0, - 0, - m_Config->Get("Video.Width", 1280), - m_Config->Get("Video.Height", 720) - )); - m_Renderer->Initialize(); - m_Renderer->Camera()->SetFOV(glm::radians(m_Config->Get("Video.FOV", 90.f))); - - // Create input manager - m_InputManager = new InputManager(m_Renderer->Window(), m_EventBroker); - m_InputProxy = new InputProxy(m_EventBroker); - m_InputProxy->AddHandler(); - m_InputProxy->AddHandler(); - m_InputProxy->LoadBindings("Input.ini"); - - // Create the root level GUI frame - m_FrameStack = new GUI::Frame(m_EventBroker); - m_FrameStack->Width = m_Renderer->Resolution().Width; - m_FrameStack->Height = m_Renderer->Resolution().Height; - - // Create a TEST WORLD - m_World = new HardcodedTestWorld(); - - m_SystemPipeline = new SystemPipeline(m_EventBroker); - m_SystemPipeline->AddSystem(0); - - m_LastTime = glfwGetTime(); -} - -Game::~Game() -{ - delete m_FrameStack; - delete m_EventBroker; -} - -void Game::Tick() -{ - double currentTime = glfwGetTime(); - double dt = currentTime - m_LastTime; - m_LastTime = currentTime; - - // Handle input in a weird looking but responsive way - m_EventBroker->Process(); - m_EventBroker->Swap(); - m_InputManager->Update(dt); - m_EventBroker->Swap(); - m_InputProxy->Update(dt); - m_EventBroker->Swap(); - m_InputProxy->Process(); - m_EventBroker->Swap(); - -#define TEST1 - //this draws the octTree and you can set the cube inside it and see what boxes in the tree that it belongs to -#ifdef TEST1 - if (!m_UpdatedOnce) { - m_UpdatedOnce = true; - m_World->createTestEntitiesTest1(); - } - - //add/move the trigger box - auto pos = m_Renderer->Camera()->Forward() + m_Renderer->Camera()->Position(); - AABB boxi; - boxi.CreateFromCenter(pos, maxPos - minPos); - frameCounter++; - if (frameCounter > 1) { - m_World->someOctTree.ClearDynamicObjects(); - m_World->someOctTree.AddDynamicObject(boxi); - frameCounter = 0; - } - ComponentWrapper transform = m_World->GetComponent(m_World->anotherBoxTransformId, "Transform"); - transform["Position"] = boxi.Center(); - - //check all children again in the tree if they have a box in them or not, and colormark them if they do - //contentboxarna får man ut - inte childboxarna! - std::vector boxIndex; - boxIndex = m_World->someOctTree.m_Root->childIndicesContainingBox(boxi); - - for (auto& oneLinkedObject : m_World->linkOM) - { - ComponentWrapper model = m_World->GetComponent(oneLinkedObject.entId, "Model"); - model["Color"] = glm::vec4(1.0f, 1.0f, 1.0f, 1.0f); - if (oneLinkedObject.child->m_DynamicObjIndices.size() != 0) { - model["Color"] = glm::vec4(0.0f, 0.0f, 0.0f, 1.0f); - } - - //next check if the childIndicesContainingBox method returns the correct boxes - //REQUIRED: childIndicesContainingBox must be public to test this! - for each (auto someBoxIndex in boxIndex) - { - glm::vec3 pos = m_World->someOctTree.m_Root->m_Children[someBoxIndex]->m_Box.Center(); - if (abs(pos.x - oneLinkedObject.posxyz.x) < 0.005f && - abs(pos.y - oneLinkedObject.posxyz.y) < 0.005f && - abs(pos.z - oneLinkedObject.posxyz.z) < 0.005f) { - model["Color"] = glm::vec4(0.0f, 1.0f, 0.0f, 1.0f); - - } - } - } - m_RenderQueueFactory->Update(m_World); - - //wireframe - glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); -#endif - //this tests AABB vs AABB collision and AABB vs OctTree with AABB in it -#ifdef TEST2 - - //only add 1 for now... - //grey box - - const glm::vec4 redCol = glm::vec4(1, 0.2f, 0, 1); - const glm::vec4 greenCol = glm::vec4(0.1f, 1.0f, 0.25f, 1); - const glm::vec3 boxSize = 0.1f*glm::vec3(1.0f, 1.0f, 1.0f); - AABB aabb; - aabb.CreateFromCenter(glm::vec3(0, 2.0f, 0.0f), glm::vec3(1.0f, 1.0f, 1.0f)); - - if (m_UpdatedOnce) { - //auto test = someOctTree.childIndicesContainingBox(aabb); - std::vector test2; - someOctTree.BoxesInSameRegion(aabb, test2); - } - if (!m_UpdatedOnce) { - m_UpdatedOnce = true; - someOctTree.AddStaticObject(aabb); - //create the "small red box" - m_BoxID = m_World->CreateEntity(); - ComponentWrapper transform = m_World->AttachComponent(m_BoxID, "Transform"); - transform["Scale"] = boxSize; - ComponentWrapper model = m_World->AttachComponent(m_BoxID, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; - m_World->createTestEntitiesTest2(); - } - - //red box - AABB redBox; - auto boxPos = m_Renderer->Camera()->Position() + 1.2f*m_Renderer->Camera()->Forward(); - redBox.CreateFromCenter(boxPos, boxSize); - ComponentWrapper transform = m_World->GetComponent(m_BoxID, "Transform"); - transform["Position"] = boxPos; - ComponentWrapper model = m_World->GetComponent(m_BoxID, "Model"); - //this checks AABB vs an AABB in the octTree - if (someOctTree.BoxCollides(redBox, AABB())) { - //this checks AABB vs AABB - //if (Collision::AABBVsAABB(redBox, aabb)) { - //m_Renderer->Camera()->SetPosition(m_PrevPos); - //m_Renderer->Camera()->SetOrientation(m_PrevOri); - model["Color"] = greenCol; - } - else { - model["Color"] = redCol; - } - - m_PrevPos = m_Renderer->Camera()->Position(); - m_PrevOri = m_Renderer->Camera()->Orientation(); - - m_RenderQueueFactory->Update(m_World); -#endif - - // Iterate through systems and update world! - m_SystemPipeline->Update(m_World, dt); - m_Renderer->Update(dt); - - m_RenderQueueFactory->Update(m_World); - GLERROR("Game::Tick m_RenderQueueFactory->Update"); - m_Renderer->Draw(m_RenderQueueFactory->RenderQueues()); - GLERROR("Game::Tick m_Renderer->Draw"); - m_EventBroker->Swap(); - m_EventBroker->Clear(); - - glfwPollEvents(); -} diff --git a/src/Tests/OctTreeTestGameClass.h b/src/Tests/OctTreeTestGameClass.h deleted file mode 100644 index c36707c8..00000000 --- a/src/Tests/OctTreeTestGameClass.h +++ /dev/null @@ -1,62 +0,0 @@ -#ifndef Game_h__ -#define Game_h__ - -#include "Core/ResourceManager.h" -#include "Core/ConfigFile.h" -#include "Core/EventBroker.h" -#include "Rendering/Renderer.h" -#include "Core/InputManager.h" -#include "GUI/Frame.h" -#include "Core/World.h" -#include "Rendering/RenderQueueFactory.h" -#include "Input/InputProxy.h" -#include "Input/KeyboardInputHandler.h" -#include "Input/MouseInputHandler.h" -#include "Core/EKeyDown.h" -#include "Core/EntityFile.h" -#include "Core/SystemPipeline.h" -#include "RaptorCopterSystem.h" -#include "PlayerSystem.h" -#include "Editor/EditorSystem.h" - -#include "OctTreeTestHardCodedTestWorld.h" -#include "Collision/Collision.h" - -class Game -{ -public: - Game(int argc, char* argv[]); - ~Game(); - - bool Running() const { return !glfwWindowShouldClose(m_Renderer->Window()); } - void Tick(); - -private: - double m_LastTime; - ConfigFile* m_Config = nullptr; - EventBroker* m_EventBroker; - IRenderer* m_Renderer; - InputManager* m_InputManager; - GUI::Frame* m_FrameStack; - HardcodedTestWorld* m_World; - RenderQueueFactory* m_RenderQueueFactory; - InputProxy* m_InputProxy; - SystemPipeline* m_SystemPipeline; - - //Test1 - int frameCounter = 0; - glm::vec3 minPos = glm::vec3(0.1f, 0.1f, 0.1f); - glm::vec3 maxPos = glm::vec3(0.2f, 0.2f, 0.2f); - - //Test2 - bool m_UpdatedOnce = false; - unsigned int m_BoxID; - glm::vec3 m_PrevPos; - glm::quat m_PrevOri; - - glm::vec3 worldSize = glm::vec3(50, 50, 50); - OctTree someOctTree; - -}; - -#endif diff --git a/src/Tests/OctTreeTestGameMain.cpp b/src/Tests/OctTreeTestGameMain.cpp deleted file mode 100644 index 43789cea..00000000 --- a/src/Tests/OctTreeTestGameMain.cpp +++ /dev/null @@ -1,21 +0,0 @@ -//#define BOOST_TEST_MODULE collTest -#include -#include -using boost::unit_test_framework::test_suite; -using boost::unit_test_framework::test_case; -#include "Engine/Collision/Collision.h" -#include "Engine/Core/AABB.h" -#include "Engine/Core/Ray.h" -#include //srand -#include "Engine/Core/OctTree.h" - -//vs memleaks -//#define _CRTDBG_MAP_ALLOC -//#include -//#include -//#define DEBUG_CLIENTBLOCK new( _CLIENT_BLOCK, __FILE__, __LINE__) -//#define new DEBUG_CLIENTBLOCK - -BOOST_AUTO_TEST_SUITE(cTest) -BOOST_AUTO_TEST_SUITE_END() - diff --git a/src/Tests/OctTreeTestHardCodedTestWorld.h b/src/Tests/OctTreeTestHardCodedTestWorld.h deleted file mode 100644 index 6f68eba6..00000000 --- a/src/Tests/OctTreeTestHardCodedTestWorld.h +++ /dev/null @@ -1,134 +0,0 @@ -#include -#include -#include -#include "GLM.h" -#include "Core/World.h" -#include "Core/Util/Any.h" - -#include -//last! -//#include "OldOctTree.h" -#define private public -#include - -class HardcodedTestWorld : public World -{ -public: - struct LinkOctTreeAndModel { - EntityID entId; - OctTree::OctChild* child; - glm::vec3 posxyz; - LinkOctTreeAndModel(EntityID eId, OctTree::OctChild* ch, glm::vec3 pos) - { - entId = eId; - child = ch; - posxyz = pos; - } - }; - EntityID anotherBoxTransformId; - std::vector linkOM; - OctTree someOctTree; - - //constructor - HardcodedTestWorld() - : World() - , someOctTree(AABB(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(1.0f, 1.0f, 1.0f)), 2) - { - registerTestComponents(); - //createTestEntities(); - } - -private: - void registerTestComponents() - { - ComponentWrapperFactory f; - - - f = ComponentWrapperFactory("Test"); - f.AddProperty("TestInteger", 1337); - f.AddProperty("TestFloat", 13.37f); - f.AddProperty("TestString", std::string("Carlito")); - RegisterComponent(f); - - f = ComponentWrapperFactory("Debug"); - f.AddProperty("Name", std::string("Unnamed")); - RegisterComponent(f); - - f = ComponentWrapperFactory("Transform"); - f.AddProperty("Position", glm::vec3(0.f, 0.f, 0.f)); - f.AddProperty("Orientation", glm::quat()); - f.AddProperty("Scale", glm::vec3(1.f, 1.f, 1.f)); - RegisterComponent(f); - - f = ComponentWrapperFactory("Model"); - f.AddProperty("Resource", std::string()); - f.AddProperty("Color", glm::vec4(1.f, 1.f, 1.f, 1.f)); - f.AddProperty("Visible", true); - RegisterComponent(f); - } - - void createTestEntitiesTest1() - { - World& world = *this; - EntityID tempId; - //add octTree - { - //copy of mainbox - auto someAABB = AABB(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(1.0f, 1.0f, 1.0f)); - - //draw main box first - AddBoxModel(someAABB.Center(), someAABB.HalfSize().x, someOctTree.m_Root, tempId); - - //add anotherbox in octTree - auto anotherBox = AABB(glm::vec3(0.1f, 0.1f, 0.1f), glm::vec3(0.2f, 0.2f, 0.2f)); - //note: have to delete the box in the tree first, since were trying to move the box - someOctTree.AddDynamicObject(anotherBox); - - //draw anotherbox and save it in anotherBoxTransformId - AddBoxModel(anotherBox.Center(), anotherBox.HalfSize().x, someOctTree.m_Root, anotherBoxTransformId); - - //draw the octTree - for (size_t j = 0; j < 8; j++) - { - AddBoxModel(someOctTree.m_Root->m_Children[j]->m_Box.Center(), - someOctTree.m_Root->m_Children[j]->m_Box.HalfSize().x, someOctTree.m_Root->m_Children[j], tempId); - - auto someChild = someOctTree.m_Root->m_Children[j]; - - for (size_t i = 0; i < 8; i++) - { - AddBoxModel(someChild->m_Children[i]->m_Box.Center(), - someChild->m_Children[i]->m_Box.HalfSize().x, someChild->m_Children[i], tempId); - } - } - } - }//end CreateEnt - - void createTestEntitiesTest2() - { - World& world = *this; - - EntityID entityCollisionBox = world.CreateEntity(); - ComponentWrapper transform = world.AttachComponent(entityCollisionBox, "Transform"); - transform["Position"] = glm::vec3(0.f, 2.f, 0.f); - ComponentWrapper model = world.AttachComponent(entityCollisionBox, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; - } - - void AddBoxModel(const glm::vec3 ¢er, const float &halfSize, OctTree::OctChild* child, EntityID &outEntityId) { - World& world = *this; - - EntityID entityDummyScene = world.CreateEntity(); - outEntityId = entityDummyScene; - ComponentWrapper transform = world.AttachComponent(entityDummyScene, "Transform"); - transform["Position"] = center; - transform["Scale"] = glm::vec3(1.0f, 1.0f, 1.0f)*halfSize*2.0f*0.97f; - ComponentWrapper model = world.AttachComponent(entityDummyScene, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; - model["Color"] = glm::vec4(0.0f, 0.0f, 0.0f, 1.0f); - if (child->m_DynamicObjIndices.size() != 0) - model["Color"] = glm::vec4(1.0f, 1.0f, 1.0f, 1.0f); - - linkOM.emplace_back(entityDummyScene, child, center); - } -}; \ No newline at end of file From db62d767ac12587cf6961b8d8beef0223a4ef057 Mon Sep 17 00:00:00 2001 From: Jocke Date: Fri, 15 Jan 2016 12:06:20 +0100 Subject: [PATCH 053/224] Fixed bug in Client::parseSnapshot(). --- src/Engine/Network/Client.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 37534a27..55292234 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -134,7 +134,7 @@ void Client::parseSnapshot(Packet& packet) EntityID receivedParentEntityID = packet.ReadPrimitive(); ComponentInfo componentInfo = m_World->GetComponents(componentType)->ComponentInfo(); // Check if the received EntityID is mapped to one of our local EntityIDs - if (clientServerMapsHasEntity(receivedEntityID)) { + if (serverClientMapsHasEntity(receivedEntityID)) { // Get the local EntityID EntityID entityID = m_ServerIDToClientID.at(receivedEntityID); // Check if the component exists @@ -168,7 +168,7 @@ void Client::parseSnapshot(Packet& packet) // Parent Logic // Don't need to check if receivedEntityID is mapped. (It should have been set) if (receivedParentEntityID != std::numeric_limits::max()) { - if (clientServerMapsHasEntity(receivedParentEntityID)) { + if (serverClientMapsHasEntity(receivedParentEntityID)) { m_World->SetParent(m_ServerIDToClientID.at(receivedEntityID), m_ServerIDToClientID.at(receivedParentEntityID)); // If Parent dosen't exist create one and map receivedParentEntityID to it. } else { From 8437b9c734a72fee32bd79d9a59b8db345d43ff2 Mon Sep 17 00:00:00 2001 From: antc13 Date: Fri, 15 Jan 2016 17:58:26 +0100 Subject: [PATCH 054/224] Commit for Pull --- include/Engine/Collision/Collision.h | 2 +- include/Engine/Rendering/Model.h | 2 +- .../{RawModel.h => RawModelAssimp.h} | 18 ++--- include/Engine/Rendering/RawModelCustom.h | 68 +++++++++++++++++++ src/Engine/Rendering/Model.cpp | 10 +-- .../{RawModel.cpp => RawModelAssimp.cpp} | 22 ++---- src/Engine/Rendering/RawModelCustom.cpp | 67 ++++++++++++++++++ tools/MayaExporter/MayaExporter/Mesh.cpp | 12 ++-- tools/MayaExporter/MayaExporter/Mesh.h | 8 +-- 9 files changed, 158 insertions(+), 51 deletions(-) rename include/Engine/Rendering/{RawModel.h => RawModelAssimp.h} (79%) create mode 100644 include/Engine/Rendering/RawModelCustom.h rename src/Engine/Rendering/{RawModel.cpp => RawModelAssimp.cpp} (92%) create mode 100644 src/Engine/Rendering/RawModelCustom.cpp diff --git a/include/Engine/Collision/Collision.h b/include/Engine/Collision/Collision.h index 714cee3f..3ac43baf 100644 --- a/include/Engine/Collision/Collision.h +++ b/include/Engine/Collision/Collision.h @@ -9,7 +9,7 @@ #include "Core/Ray.h" #include "Core/AABB.h" -#include "Engine/Rendering/RawModel.h" +#include "Engine/Rendering/RawModelAssimp.h" #include "Core/Entity.h" class World; diff --git a/include/Engine/Rendering/Model.h b/include/Engine/Rendering/Model.h index 9cc145af..228e7acf 100644 --- a/include/Engine/Rendering/Model.h +++ b/include/Engine/Rendering/Model.h @@ -1,7 +1,7 @@ #ifndef Model_h__ #define Model_h__ -#include "RawModel.h" +#include "RawModelAssimp.h" #include "../OpenGL.h" class Model : public RawModel diff --git a/include/Engine/Rendering/RawModel.h b/include/Engine/Rendering/RawModelAssimp.h similarity index 79% rename from include/Engine/Rendering/RawModel.h rename to include/Engine/Rendering/RawModelAssimp.h index c8226168..5c96d946 100644 --- a/include/Engine/Rendering/RawModel.h +++ b/include/Engine/Rendering/RawModelAssimp.h @@ -1,5 +1,5 @@ -#ifndef RawModel_h__ -#define RawModel_h__ +#ifndef RawModelAssimp_h__ +#define RawModelAssimp_h__ #include #include @@ -23,7 +23,7 @@ class RawModel : public Resource friend class ResourceManager; protected: - RawModel(std::string fileName); + RawModel(std::string fileName); public: ~RawModel(); @@ -33,14 +33,10 @@ public: glm::vec3 Position; glm::vec3 Normal; glm::vec3 Tangent; - glm::vec3 BiTangent; + glm::vec3 BiNormal; glm::vec2 TextureCoords; - glm::vec4 DiffuseVertexColor; - glm::vec4 SpecularVertexColor; - glm::vec4 BoneIndices1; - glm::vec4 BoneIndices2; - glm::vec4 BoneWeights1; - glm::vec4 BoneWeights2; + glm::vec4 BoneIndices; + glm::vec4 BoneWeights; }; struct MaterialGroup @@ -64,8 +60,6 @@ private: std::vector BoneIndices; std::vector BoneWeights; std::vector Normals; - std::vector DiffuseVertexColor; - std::vector SpecularVertexColor; std::vector TangentNormals; std::vector BiTangentNormals; std::vector TextureCoords; diff --git a/include/Engine/Rendering/RawModelCustom.h b/include/Engine/Rendering/RawModelCustom.h new file mode 100644 index 00000000..c6e97242 --- /dev/null +++ b/include/Engine/Rendering/RawModelCustom.h @@ -0,0 +1,68 @@ +#ifndef RawModelCustom_h__ +#define RawModelCustom_h__ + +#include +#include +#include +#include +#include + +#include + +#include "../Common.h" +#include "../GLM.h" +#include "../Core/ResourceManager.h" +#include "Texture.h" +#include "Skeleton.h" + +#include "boost\endian\buffers.hpp" + +class RawModel : public Resource +{ + friend class ResourceManager; + +protected: + RawModel(std::string fileName); + +public: + ~RawModel(); + + struct Vertex + { + glm::vec3 Position; + glm::vec3 Normal; + glm::vec3 Tangent; + glm::vec3 BiNormal; + glm::vec2 TextureCoords; + glm::vec4 BoneIndices; + glm::vec4 BoneWeights; + }; + + struct MaterialGroup + { + float Shininess; + std::shared_ptr<::Texture> Texture; + std::shared_ptr<::Texture> NormalMap; + std::shared_ptr<::Texture> SpecularMap; + unsigned int StartIndex; + unsigned int EndIndex; + }; + + std::vector TextureGroups; + + std::vector m_Vertices; + std::vector m_Indices; + Skeleton* m_Skeleton = nullptr; + glm::mat4 m_Matrix; + +private: + + bool ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + bool ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + bool ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + bool ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + + //void CreateSkeleton(std::vector> &boneInfo, std::map &boneNameMapping, aiNode* node, int parentID); +}; + +#endif diff --git a/src/Engine/Rendering/Model.cpp b/src/Engine/Rendering/Model.cpp index f346d9e1..c7b5667b 100644 --- a/src/Engine/Rendering/Model.cpp +++ b/src/Engine/Rendering/Model.cpp @@ -18,7 +18,7 @@ Model::Model(std::string fileName) GLERROR("GLEW: BufferFail4"); glBindBuffer(GL_ARRAY_BUFFER, buffer); - std::vector structSizes = { 3, 3, 3, 3, 2, 4, 4, 4, 4, 4, 4 }; + std::vector structSizes = { 3, 3, 3, 3, 2, 4, 4 }; int stride = 0; for (int size : structSizes) { stride += size; @@ -34,10 +34,6 @@ Model::Model(std::string fileName) glVertexAttribPointer(element, structSizes[element], GL_FLOAT, GL_FALSE, stride, (GLvoid*)(sizeof(GLfloat) * (offset += structSizes[element - 1]))); element++; glVertexAttribPointer(element, structSizes[element], GL_FLOAT, GL_FALSE, stride, (GLvoid*)(sizeof(GLfloat) * (offset += structSizes[element - 1]))); element++; glVertexAttribPointer(element, structSizes[element], GL_FLOAT, GL_FALSE, stride, (GLvoid*)(sizeof(GLfloat) * (offset += structSizes[element - 1]))); element++; - glVertexAttribPointer(element, structSizes[element], GL_FLOAT, GL_FALSE, stride, (GLvoid*)(sizeof(GLfloat) * (offset += structSizes[element - 1]))); element++; - glVertexAttribPointer(element, structSizes[element], GL_FLOAT, GL_FALSE, stride, (GLvoid*)(sizeof(GLfloat) * (offset += structSizes[element - 1]))); element++; - glVertexAttribPointer(element, structSizes[element], GL_FLOAT, GL_FALSE, stride, (GLvoid*)(sizeof(GLfloat) * (offset += structSizes[element - 1]))); element++; - glVertexAttribPointer(element, structSizes[element], GL_FLOAT, GL_FALSE, stride, (GLvoid*)(sizeof(GLfloat) * (offset += structSizes[element - 1]))); element++; } GLERROR("GLEW: BufferFail5"); @@ -48,10 +44,6 @@ Model::Model(std::string fileName) glEnableVertexAttribArray(4); glEnableVertexAttribArray(5); glEnableVertexAttribArray(6); - glEnableVertexAttribArray(7); - glEnableVertexAttribArray(8); - glEnableVertexAttribArray(9); - glEnableVertexAttribArray(10); GLERROR("GLEW: BufferFail5"); //CreateBuffers(); diff --git a/src/Engine/Rendering/RawModel.cpp b/src/Engine/Rendering/RawModelAssimp.cpp similarity index 92% rename from src/Engine/Rendering/RawModel.cpp rename to src/Engine/Rendering/RawModelAssimp.cpp index 95a75a15..68cbb23e 100644 --- a/src/Engine/Rendering/RawModel.cpp +++ b/src/Engine/Rendering/RawModelAssimp.cpp @@ -1,4 +1,4 @@ -#include "Rendering/RawModel.h" +#include "Rendering/RawModelAssimp.h" RawModel::RawModel(std::string fileName) { @@ -38,7 +38,7 @@ RawModel::RawModel(std::string fileName) //LOG_DEBUG("Index count %i", numIndices); //LOG_DEBUG("Model has %i embedded textures", scene->mNumTextures); - + std::vector> boneInfo; std::map boneNameMapping; @@ -75,17 +75,6 @@ RawModel::RawModel(std::string fileName) desc.TextureCoords = glm::vec2(uv.x, uv.y); } - // Material diffuse color - aiColor3D diffuse; - material->Get(AI_MATKEY_COLOR_DIFFUSE, diffuse); - float opacity; - material->Get(AI_MATKEY_OPACITY, opacity); - desc.DiffuseVertexColor = glm::vec4(diffuse.r, diffuse.g, diffuse.b, opacity); - // Material specular color - aiColor3D specular; - material->Get(AI_MATKEY_COLOR_SPECULAR, specular); - desc.SpecularVertexColor = glm::vec4(specular.r, specular.g, specular.b, 1.f); - m_Vertices.push_back(desc); } @@ -125,7 +114,7 @@ RawModel::RawModel(std::string fileName) } for (auto& vertex : m_Vertices) { vertex.Tangent = glm::normalize(vertex.Tangent); - vertex.BiTangent = glm::normalize(glm::cross(vertex.Tangent, glm::normalize(vertex.Normal))); + vertex.BiNormal = glm::normalize(glm::cross(vertex.Tangent, glm::normalize(vertex.Normal))); } // Material info @@ -203,10 +192,7 @@ RawModel::RawModel(std::string fileName) LOG_WARNING("Vertex weights (%i) greater than max weights per vertex (%i)", weights.size(), maxWeights); } for (int weightIndex = 0; weightIndex < weights.size() && weightIndex < maxWeights && weightIndex < 4; ++weightIndex) { - std::tie(desc.BoneIndices1[weightIndex], desc.BoneWeights1[weightIndex]) = weights[weightIndex]; - } - for (int weightIndex = 4; weightIndex < weights.size() && weightIndex < maxWeights && weightIndex < 8; ++weightIndex) { - std::tie(desc.BoneIndices2[weightIndex - 4], desc.BoneWeights2[weightIndex - 4]) = weights[weightIndex]; + std::tie(desc.BoneIndices[weightIndex], desc.BoneWeights[weightIndex]) = weights[weightIndex]; } } diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp new file mode 100644 index 00000000..a5493bd8 --- /dev/null +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -0,0 +1,67 @@ +#include "Rendering\RawModelCustom.h" + +RawModel::RawModel(std::string fileName) +{ + boost::endian::big_int16_buf_t* test; + int16_t tal; + test = &(boost::endian::big_int16_buf_t)tal; + + char* fileData; + std::ifstream in(fileName.c_str(), std::ios_base::binary | std::ios_base::ate); + + if (!in.is_open()) + LOG_ERROR("Failed to load custom binary model \"%s\"", fileName.c_str()); + + unsigned int fileByteSize = in.tellg(); + in.seekg(0, std::ios_base::beg); + + fileData = new char[fileByteSize]; + in.read(fileData, fileByteSize); + in.close(); + + unsigned int offset = 0; + ReadMeshFileHeader(offset, fileData, fileByteSize); + ReadMesh(offset, fileData, fileByteSize); + +} + +bool RawModel::ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +{ +#ifdef BOOST_LITTLE_ENDIAN + m_Vertices.resize(*fileData); + offset += sizeof(unsigned int); + m_Indices.resize(*(fileData + offset)); + offset += sizeof(unsigned int); +#else +#endif +} + +bool RawModel::ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +{ + ReadVertices(offset, fileData, fileByteSize); + ReadIndices(offset, fileData, fileByteSize); +} + +bool RawModel::ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +{ +#ifdef BOOST_LITTLE_ENDIAN + memcpy(&m_Vertices[0], fileData, m_Vertices.size() * sizeof(Vertex)); + offset += m_Vertices.size() * sizeof(Vertex); +#else +#endif +} + +bool RawModel::ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +{ +#ifdef BOOST_LITTLE_ENDIAN + memcpy(&m_Indices[0], fileData, m_Indices.size() * sizeof(unsigned int)); + offset += m_Indices.size() * sizeof(unsigned int); +#else +#endif +} + + +RawModel::~RawModel() +{ + +} \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index d9b47875..24e661ac 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -92,12 +92,12 @@ Mesh MeshClass::GetMeshData(MObject object) double biTangent[3]; double biNormal[3]; VertexLayout thisVertex; - MFloatVectorArray biTangents; + MFloatVectorArray Tangents; MFloatVectorArray biNormals; std::map vertexWeights = GetWeightData(); - mesh.getTangents(biTangents, MSpace::kObject, NULL); + mesh.getTangents(Tangents, MSpace::kObject, NULL); mesh.getBinormals(biNormals, MSpace::kObject, NULL); MItMeshFaceVertex faceVert(object); @@ -123,12 +123,12 @@ Mesh MeshClass::GetMeshData(MObject object) thisVertex.Normal[1] = normal[1]; thisVertex.Normal[2] = normal[2]; - MFloatVector biTangent = biTangents[faceVert.tangentId()]; + MFloatVector Tangent = Tangents[faceVert.tangentId()]; //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); //tmp.get(biTangent); - thisVertex.BiTangent[0] = biTangent[0]; - thisVertex.BiTangent[1] = biTangent[1]; - thisVertex.BiTangent[2] = biTangent[2]; + thisVertex.Tangent[0] = Tangent[0]; + thisVertex.Tangent[1] = Tangent[1]; + thisVertex.Tangent[2] = Tangent[2]; MFloatVector biNormal = biNormals[faceVert.tangentId()]; //faceVert.getBinormal().get(biNormal); diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h index c9445e4e..ff7cc3b0 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.h +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -12,8 +12,8 @@ class VertexLayout : public OutputData public: float Pos[3]; float Normal[3]; + float Tangent[3]; float BiNormal[3]; - float BiTangent[3]; float Uv[2]; float BoneIndices[4]; float BoneWeights[4]; @@ -22,7 +22,7 @@ public: { out.write((char*)&Pos, sizeof(float) * 3); out.write((char*)&Normal, sizeof(float) * 3); - out.write((char*)&BiNormal, sizeof(float) * 3); + out.write((char*)&Tangent, sizeof(float) * 3); out.write((char*)&BiTangent, sizeof(float) * 3); out.write((char*)&Uv, sizeof(float) * 2); out.write((char*)&BoneIndices, sizeof(float) * 4); @@ -33,7 +33,7 @@ public: { out << Pos[0] << " " << Pos[1] << " " << Pos[2] << endl; out << Normal[0] << " " << Normal[1] << " " << Normal[2] << endl; - out << BiNormal[0] << " " << BiNormal[1] << " " << BiNormal[2] << endl; + out << Tangent[0] << " " << Tangent[1] << " " << Tangent[2] << endl; out << BiTangent[0] << " " << BiTangent[1] << " " << BiTangent[2] << endl; out << Uv[0] << " " << Uv[1] << endl; out << BoneIndices[0] << " " << BoneIndices[1] << " " << BoneIndices[2] << " " << BoneIndices[3] << endl; @@ -45,7 +45,7 @@ public: return this->Pos[0] == right.Pos[0] && this->Pos[1] == right.Pos[1] && this->Pos[2] == right.Pos[2] && this->Normal[0] == right.Normal[0] && this->Normal[1] == right.Normal[1] && this->Normal[2] == right.Normal[2] && - this->BiNormal[0] == right.BiNormal[0] && this->BiNormal[1] == right.BiNormal[1] && this->BiNormal[2] == right.BiNormal[2] && + this->Tangent[0] == right.Tangent[0] && this->Tangent[1] == right.Tangent[1] && this->Tangent[2] == right.Tangent[2] && this->BiTangent[0] == right.BiTangent[0] && this->BiTangent[1] == right.BiTangent[1] && this->BiTangent[2] == right.BiTangent[2] && this->Uv[0] == right.Uv[0] && this->Uv[1] == right.Uv[1] && this->BoneIndices[0] == right.BoneIndices[0] && this->BoneIndices[1] == right.BoneIndices[1] && this->BoneIndices[2] == right.BoneIndices[2] && this->BoneIndices[3] == right.BoneIndices[3] && From 9f447afbdb92dc136d0ad3be9f2d39e1e58deaa3 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 17 Jan 2016 06:20:27 +0100 Subject: [PATCH 055/224] Added EntityWrapper::Valid and bool overload to be check if an entity is valid and still exists in the world more easily --- include/Engine/Core/EntityWrapper.h | 6 ++++-- src/Engine/Core/EntityWrapper.cpp | 29 ++++++++++++++++++++++++++--- 2 files changed, 30 insertions(+), 5 deletions(-) diff --git a/include/Engine/Core/EntityWrapper.h b/include/Engine/Core/EntityWrapper.h index 55b64c6f..e4be8d78 100644 --- a/include/Engine/Core/EntityWrapper.h +++ b/include/Engine/Core/EntityWrapper.h @@ -23,10 +23,12 @@ struct EntityWrapper static const EntityWrapper Invalid; bool HasComponent(const std::string& componentName); + bool Valid(); - ComponentWrapper operator[](const std::string& componentName); + ComponentWrapper operator[](const char* componentName); bool operator==(const EntityWrapper& e); - explicit operator EntityID(); + explicit operator EntityID() const; + operator bool(); }; #endif diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 7b321a63..c3c5cf27 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -13,18 +13,41 @@ bool EntityWrapper::HasComponent(const std::string& componentName) return World->HasComponent(ID, componentName); } -ComponentWrapper EntityWrapper::operator[](const std::string& componentName) +bool EntityWrapper::Valid() +{ + if (this->World == nullptr) { + return false; + } + + if (this->ID == EntityID_Invalid) { + return false; + } + + if (!this->World->ValidEntity(this->ID)) { + this->ID = EntityID_Invalid; + return false; + } + + return true; +} + +ComponentWrapper EntityWrapper::operator[](const char* componentName) { if (World->HasComponent(ID, componentName)) { return World->GetComponent(ID, componentName); } else { - LOG_WARNING("EntityWrapper implicitly attached \"%s\" component to #%i as a result of a fetch request!", componentName.c_str(), ID); + LOG_WARNING("EntityWrapper implicitly attached \"%s\" component to #%i as a result of a fetch request!", componentName, ID); return World->AttachComponent(ID, componentName); } } -EntityWrapper::operator EntityID() +EntityWrapper::operator EntityID() const { return this->ID; } +EntityWrapper::operator bool() +{ + return this->Valid(); +} + From 6ec22587583ff7a7344cab5e5eec536edcb0cc13 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 17 Jan 2016 06:22:35 +0100 Subject: [PATCH 056/224] Added UniformScale component which keeps an entity's scale at a uniform value relative to the screen. --- include/Engine/Core/UniformScaleSystem.h | 22 ++++++++++++++++++ resources/Schema/Components.xsd | 1 + resources/Schema/Components/UniformScale.xml | 4 ++++ resources/Schema/Components/UniformScale.xsd | 16 +++++++++++++ resources/Schema/Types/Entity.xsd | 1 + src/Engine/Core/UniformScaleSystem.cpp | 24 ++++++++++++++++++++ 6 files changed, 68 insertions(+) create mode 100644 include/Engine/Core/UniformScaleSystem.h create mode 100755 resources/Schema/Components/UniformScale.xml create mode 100755 resources/Schema/Components/UniformScale.xsd create mode 100644 src/Engine/Core/UniformScaleSystem.cpp diff --git a/include/Engine/Core/UniformScaleSystem.h b/include/Engine/Core/UniformScaleSystem.h new file mode 100644 index 00000000..f44409f0 --- /dev/null +++ b/include/Engine/Core/UniformScaleSystem.h @@ -0,0 +1,22 @@ +#ifndef UniformScaleSystem_h__ +#define UniformScaleSystem_h__ + +#include "../GLM.h" +#include "System.h" +#include "../Rendering/ESetCamera.h" + +class UniformScaleSystem : public PureSystem +{ +public: + UniformScaleSystem(EventBroker* eventBroker); + + virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) override; + +private: + EntityWrapper m_Camera = EntityWrapper::Invalid; + + EventRelay m_ESetCamera; + bool OnSetCamera(const Events::SetCamera& e); +}; + +#endif \ No newline at end of file diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index 8d837aea..b9c8647c 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -18,4 +18,5 @@ + \ No newline at end of file diff --git a/resources/Schema/Components/UniformScale.xml b/resources/Schema/Components/UniformScale.xml new file mode 100755 index 00000000..0eed72d4 --- /dev/null +++ b/resources/Schema/Components/UniformScale.xml @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/resources/Schema/Components/UniformScale.xsd b/resources/Schema/Components/UniformScale.xsd new file mode 100755 index 00000000..cbd218ea --- /dev/null +++ b/resources/Schema/Components/UniformScale.xsd @@ -0,0 +1,16 @@ + + + + + + + + Keeps an entity at an uniform scale relative to the camera + + + + + + + + diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 1aaa8497..47c4d614 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -27,6 +27,7 @@ + diff --git a/src/Engine/Core/UniformScaleSystem.cpp b/src/Engine/Core/UniformScaleSystem.cpp new file mode 100644 index 00000000..8cf670fc --- /dev/null +++ b/src/Engine/Core/UniformScaleSystem.cpp @@ -0,0 +1,24 @@ +#include "Core/UniformScaleSystem.h" + +UniformScaleSystem::UniformScaleSystem(EventBroker* eventBroker) + : System(eventBroker) + , PureSystem("UniformScale") +{ + EVENT_SUBSCRIBE_MEMBER(m_ESetCamera, &UniformScaleSystem::OnSetCamera); +} + +void UniformScaleSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) +{ + if (!m_Camera.Valid()) { + return; + } + + float distance = glm::length((glm::vec3)entity["Transform"]["Position"] - (glm::vec3&)m_Camera["Transform"]["Position"]); + entity["Transform"]["Scale"] = (glm::vec3&)cUniformScale["Scale"] * distance; +} + +bool UniformScaleSystem::OnSetCamera(const Events::SetCamera& e) +{ + m_Camera = e.CameraEntity; + return false; +} \ No newline at end of file From e2357b86259f58d7c03a7a5edfe66a547ec00826 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 17 Jan 2016 06:23:13 +0100 Subject: [PATCH 057/224] Fixed absolute position not taking scale into account --- src/Engine/Core/Transform.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Engine/Core/Transform.cpp b/src/Engine/Core/Transform.cpp index cbc405a3..8acac937 100644 --- a/src/Engine/Core/Transform.cpp +++ b/src/Engine/Core/Transform.cpp @@ -7,7 +7,7 @@ glm::vec3 Transform::AbsolutePosition(World* world, EntityID entity) while (entity != EntityID_Invalid) { ComponentWrapper transform = world->GetComponent(entity, "Transform"); EntityID parent = world->GetParent(entity); - position += Transform::AbsoluteOrientation(world, parent) * (glm::vec3)transform["Position"]; + position += Transform::AbsoluteScale(world, parent) * Transform::AbsoluteOrientation(world, parent) * (glm::vec3)transform["Position"]; entity = parent; } From e34856468a823d2cbf80bf0f2a65c66e78b31124 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 17 Jan 2016 06:27:45 +0100 Subject: [PATCH 058/224] Removed DrawScenePass, since it doesn't seem to be used --- include/Engine/Rendering/DrawScenePass.h | 42 ------------- include/Engine/Rendering/DrawScenePassState.h | 15 ----- include/Engine/Rendering/Renderer.h | 2 - src/Engine/Rendering/DrawScenePass.cpp | 62 ------------------- src/Engine/Rendering/DrawScenePassState.cpp | 20 ------ src/Engine/Rendering/Renderer.cpp | 1 - 6 files changed, 142 deletions(-) delete mode 100644 include/Engine/Rendering/DrawScenePass.h delete mode 100644 include/Engine/Rendering/DrawScenePassState.h delete mode 100644 src/Engine/Rendering/DrawScenePass.cpp delete mode 100644 src/Engine/Rendering/DrawScenePassState.cpp diff --git a/include/Engine/Rendering/DrawScenePass.h b/include/Engine/Rendering/DrawScenePass.h deleted file mode 100644 index ca2463cf..00000000 --- a/include/Engine/Rendering/DrawScenePass.h +++ /dev/null @@ -1,42 +0,0 @@ -#ifndef DrawScenePass_h__ -#define DrawScenePass_h__ - -#include "IRenderer.h" -#include "DrawScenePassState.h" -#include "FrameBuffer.h" -#include "ShaderProgram.h" -#include "Util/UnorderedMapVec2.h" -#include "Texture.h" - -class DrawScenePass -{ -public: - DrawScenePass(IRenderer* renderer); - ~DrawScenePass() { } - void InitializeTextures(); - void InitializeFrameBuffers(); - void InitializeShaderPrograms(); - - void Draw(RenderScene& scene); - - //Getters - - -private: - void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; - - static bool DepthSort(const std::shared_ptr &i, const std::shared_ptr &j) - { - return (i->Depth < j->Depth); - }; - - Texture* m_WhiteTexture; - - const IRenderer* m_Renderer; - - ShaderProgram* m_BasicForwardProgram; - - -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawScenePassState.h b/include/Engine/Rendering/DrawScenePassState.h deleted file mode 100644 index 7ce74006..00000000 --- a/include/Engine/Rendering/DrawScenePassState.h +++ /dev/null @@ -1,15 +0,0 @@ -#ifndef DrawScenePassState_h__ -#define DrawScenePassState_h__ - -#include "Rendering/RenderState.h" - -class DrawScenePassState : public RenderState -{ -public: - DrawScenePassState(); - ~DrawScenePassState(); -private: - -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 0bfe76f7..2bc93268 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -11,7 +11,6 @@ #include "FrameBuffer.h" #include "../Core/World.h" #include "PickingPass.h" -#include "DrawScenePass.h" #include "LightCullingPass.h" #include "DrawFinalPass.h" #include "../Core/EventBroker.h" @@ -45,7 +44,6 @@ private: Model* m_UnitQuad; Model* m_UnitSphere; - DrawScenePass* m_DrawScenePass; PickingPass* m_PickingPass; LightCullingPass* m_LightCullingPass; ImGuiRenderPass* m_ImGuiRenderPass; diff --git a/src/Engine/Rendering/DrawScenePass.cpp b/src/Engine/Rendering/DrawScenePass.cpp deleted file mode 100644 index 7871f1dd..00000000 --- a/src/Engine/Rendering/DrawScenePass.cpp +++ /dev/null @@ -1,62 +0,0 @@ -#include "Rendering/DrawScenePass.h" - -DrawScenePass::DrawScenePass(IRenderer* renderer) -{ - m_Renderer = renderer; - InitializeTextures(); - InitializeShaderPrograms(); -} - -void DrawScenePass::InitializeTextures() -{ - m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); -} - -void DrawScenePass::InitializeShaderPrograms() -{ - m_BasicForwardProgram = ResourceManager::Load("#BasicForwardProgram"); - - m_BasicForwardProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/BasicForward.vert.glsl"))); - m_BasicForwardProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/BasicForward.frag.glsl"))); - m_BasicForwardProgram->Compile(); - m_BasicForwardProgram->Link(); -} - -void DrawScenePass::Draw(RenderScene& scene) -{ - //glBindFramebuffer(GL_FRAMEBUFFER, 0); - GLERROR("DrawScenePass::Draw: Pre"); - - DrawScenePassState state = DrawScenePassState(); - m_BasicForwardProgram->Bind(); - - for (auto &job : scene.ForwardJobs) { - auto modelJob = std::dynamic_pointer_cast(job); - if (modelJob) { - GLuint ShaderHandle = m_BasicForwardProgram->GetHandle(); - - //TODO: Kolla upp "header/include/common" shader saken så man slipper skicka in asmycket uniforms - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); - glUniform4fv(glGetUniformLocation(ShaderHandle, "Color"), 1, glm::value_ptr(modelJob->Color)); - - //TODO: Renderer: bättre textur felhantering samt fler texturer stöd - if (modelJob->DiffuseTexture != nullptr) { - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, modelJob->DiffuseTexture->m_Texture); - } else { - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); - } - - glBindVertexArray(modelJob->Model->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, 0, modelJob->StartIndex); - - //continue; - } - - } - GLERROR("DrawScenePass::Draw: End"); -} diff --git a/src/Engine/Rendering/DrawScenePassState.cpp b/src/Engine/Rendering/DrawScenePassState.cpp deleted file mode 100644 index 2d643697..00000000 --- a/src/Engine/Rendering/DrawScenePassState.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include "Rendering/DrawScenePassState.h" - - -DrawScenePassState::DrawScenePassState() -{ - GLERROR("---"); - BindFramebuffer(0); - GLERROR("---"); - Enable(GL_DEPTH_TEST); - Enable(GL_CULL_FACE); - Enable(GL_BLEND); - glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); - // ClearColor(glm::vec4(255.f / 255, 163.f / 255, 176.f / 255, 0.f)); - // Clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); -} - -DrawScenePassState::~DrawScenePassState() -{ - -} diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 9ae317ca..2f4c0ba2 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -161,7 +161,6 @@ void Renderer::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filterin void Renderer::InitializeRenderPasses() { - m_DrawScenePass = new DrawScenePass(this); m_PickingPass = new PickingPass(this, m_EventBroker); m_LightCullingPass = new LightCullingPass(this); m_DrawFinalPass = new DrawFinalPass(this, m_LightCullingPass); From 4786986abdfc2a5ef1250e93044fde8cab2cd4f7 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 17 Jan 2016 06:29:25 +0100 Subject: [PATCH 059/224] Rendering pipeline fixes across the board and base work on refactored editor --- include/Engine/Editor/EditorRenderSystem.h | 27 + include/Engine/Editor/EditorSystem.h | 96 +-- include/Engine/Editor/EditorSystemOld.h | 94 +++ include/Engine/Editor/EditorUI.h | 8 + .../Rendering/DebugCameraInputController.h | 7 +- include/Engine/Rendering/DrawFinalPass.h | 1 - include/Engine/Rendering/ESetCamera.h | 10 +- include/Engine/Rendering/IRenderer.h | 11 - include/Engine/Rendering/RenderJob.h | 1 - include/Engine/Rendering/RenderQueue.h | 3 +- include/Engine/Rendering/RenderState.h | 2 +- include/Engine/Rendering/RenderSystem.h | 21 +- resources/Schema/Components/Camera.xml | 1 - resources/Schema/Components/Camera.xsd | 1 - resources/Schema/Components/PointLight.xsd | 2 +- resources/Schema/Entities/EditorWidget.xml | 79 ++ resources/Schema/Entities/Test.xml | 2 +- src/Engine/Editor/EditorRenderSystem.cpp | 87 ++ src/Engine/Editor/EditorSystem.cpp | 760 +----------------- src/Engine/Editor/EditorSystemOld.cpp | 738 +++++++++++++++++ src/Engine/Editor/EditorUI.cpp | 0 src/Engine/Rendering/DrawFinalPass.cpp | 5 +- src/Engine/Rendering/DrawFinalPassState.cpp | 1 - src/Engine/Rendering/RenderState.cpp | 15 +- src/Engine/Rendering/RenderSystem.cpp | 145 +--- src/Engine/Rendering/Renderer.cpp | 15 +- src/Game/Game.cpp | 4 +- 27 files changed, 1134 insertions(+), 1002 deletions(-) create mode 100644 include/Engine/Editor/EditorRenderSystem.h create mode 100644 include/Engine/Editor/EditorSystemOld.h create mode 100644 include/Engine/Editor/EditorUI.h create mode 100755 resources/Schema/Entities/EditorWidget.xml create mode 100644 src/Engine/Editor/EditorRenderSystem.cpp create mode 100644 src/Engine/Editor/EditorSystemOld.cpp create mode 100644 src/Engine/Editor/EditorUI.cpp diff --git a/include/Engine/Editor/EditorRenderSystem.h b/include/Engine/Editor/EditorRenderSystem.h new file mode 100644 index 00000000..c593e29a --- /dev/null +++ b/include/Engine/Editor/EditorRenderSystem.h @@ -0,0 +1,27 @@ +#ifndef EditorRenderSystem_h__ +#define EditorRenderSystem_h__ + +#include "../Core/System.h" +#include "../Rendering/IRenderer.h" +#include "../Rendering/ModelJob.h" +#include "../Rendering/Camera.h" +#include "../Rendering/ESetCamera.h" + +class EditorRenderSystem : public ImpureSystem +{ +public: + EditorRenderSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame); + + virtual void Update(World* world, double dt) override; + +private: + IRenderer* m_Renderer; + RenderFrame* m_RenderFrame; + Camera* m_EditorCamera; + EntityWrapper m_CurrentCamera = EntityWrapper::Invalid; + + EventRelay m_ESetCamera; + bool OnSetCamera(Events::SetCamera& e); +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index 05e106d9..43022009 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -1,94 +1,30 @@ -#include -#include -#include -#include #include "../Core/System.h" -#include "../Core/EMousePress.h" -#include "../Core/EMouseRelease.h" -#include "../Core/EMouseMove.h" -#include "../Core/ConfigFile.h" -#include "../Input/EInputCommand.h" #include "../Rendering/IRenderer.h" -#include "../Core/Transform.h" -#include "../Core/EFileDropped.h" +#include "../Rendering/Camera.h" +#include "../Rendering/DebugCameraInputController.h" +#include "../Rendering/ESetCamera.h" +#include "../Core/World.h" +#include "../Core/SystemPipeline.h" +#include "../Core/ResourceManager.h" #include "../Core/EntityFilePreprocessor.h" #include "../Core/EntityFileParser.h" -#include "../Core/EntityFileWriter.h" class EditorSystem : public ImpureSystem { public: - EditorSystem(EventBroker* eventBroker, IRenderer* renderer); + EditorSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame); + ~EditorSystem(); - virtual void Update(World* world, double dt) override; + void Update(World* world, double dt); private: IRenderer* m_Renderer; - World* m_World = nullptr; - Camera* m_Camera = nullptr; + RenderFrame* m_RenderFrame; + World* m_EditorWorld; + SystemPipeline* m_EditorWorldSystemPipeline; + Camera* m_EditorCamera; - bool m_Enabled; - bool m_Visible; - boost::filesystem::path m_DefaultEntityDir; - boost::filesystem::path m_CurrentFile; - std::vector m_PickingQueue; - - enum class WidgetMode - { - None, - Translate, - Rotate, - Scale - } m_WidgetMode = WidgetMode::None; - - enum class WidgetSpace - { - Local, - Global - } m_WidgetSpace = WidgetSpace::Global; - - EntityID m_Widget = EntityID_Invalid; - EntityID m_WidgetX = EntityID_Invalid; - EntityID m_WidgetPlaneX = EntityID_Invalid; - EntityID m_WidgetY = EntityID_Invalid; - EntityID m_WidgetPlaneY = EntityID_Invalid; - EntityID m_WidgetZ = EntityID_Invalid; - EntityID m_WidgetPlaneZ = EntityID_Invalid; - EntityID m_WidgetOrigin = EntityID_Invalid; - glm::vec3 m_WidgetCurrentAxis; - float m_WidgetPickingDepth = 0.f; - glm::vec3 m_WidgetPickingPosition = glm::vec3(0); - - EntityID m_Selection = EntityID_Invalid; - EntityID m_LastSelection = EntityID_Invalid; - EntityID m_UIDraggingEntity = EntityID_Invalid; - glm::vec3 m_Position; - std::string m_LastDroppedFile; - - static boost::filesystem::path openDialog(boost::filesystem::path defaultPath); - static boost::filesystem::path saveDialog(boost::filesystem::path defaultPath); - - EventRelay m_EInputCommand; - bool OnInputCommand(const Events::InputCommand& e); - EventRelay m_EMouseRelease; - bool OnMouseRelease(const Events::MouseRelease& e); - EventRelay m_EMousePress; - bool OnMousePress(const Events::MousePress& e); - EventRelay m_EMouseMove; - bool OnMouseMove(const Events::MouseMove& e); - EventRelay m_EFileDropped; - bool OnFileDropped(const Events::FileDropped& e); - - void Picking(); - void createWidget(); - void updateWidget(); - void setWidgetMode(WidgetMode newMode); - void setWidgetSpace(WidgetSpace space); - void drawUI(World* world, double dt); - bool createDeleteButton(std::string componentType); - bool createEntityNode(World* world, EntityID entity); - void changeParent(EntityID entity, EntityID newParent); - void fileImport(World* world); - void fileSave(World* world); - void fileSaveAs(World* world); + EntityWrapper m_Widget = EntityWrapper::Invalid; + EntityWrapper m_Camera = EntityWrapper::Invalid; + DebugCameraInputController* m_DebugCameraInputController; }; \ No newline at end of file diff --git a/include/Engine/Editor/EditorSystemOld.h b/include/Engine/Editor/EditorSystemOld.h new file mode 100644 index 00000000..b2d7df0c --- /dev/null +++ b/include/Engine/Editor/EditorSystemOld.h @@ -0,0 +1,94 @@ +#include +#include +#include +#include +#include "../Core/System.h" +#include "../Core/EMousePress.h" +#include "../Core/EMouseRelease.h" +#include "../Core/EMouseMove.h" +#include "../Core/ConfigFile.h" +#include "../Input/EInputCommand.h" +#include "../Rendering/IRenderer.h" +#include "../Core/Transform.h" +#include "../Core/EFileDropped.h" +#include "../Core/EntityFilePreprocessor.h" +#include "../Core/EntityFileParser.h" +#include "../Core/EntityFileWriter.h" + +class EditorSystemOld : public ImpureSystem +{ +public: + EditorSystemOld(EventBroker* eventBroker, IRenderer* renderer); + + virtual void Update(World* world, double dt) override; + +private: + IRenderer* m_Renderer; + World* m_World = nullptr; + Camera* m_Camera = nullptr; + + bool m_Enabled; + bool m_Visible; + boost::filesystem::path m_DefaultEntityDir; + boost::filesystem::path m_CurrentFile; + std::vector m_PickingQueue; + + enum class WidgetMode + { + None, + Translate, + Rotate, + Scale + } m_WidgetMode = WidgetMode::None; + + enum class WidgetSpace + { + Local, + Global + } m_WidgetSpace = WidgetSpace::Global; + + EntityID m_Widget = EntityID_Invalid; + EntityID m_WidgetX = EntityID_Invalid; + EntityID m_WidgetPlaneX = EntityID_Invalid; + EntityID m_WidgetY = EntityID_Invalid; + EntityID m_WidgetPlaneY = EntityID_Invalid; + EntityID m_WidgetZ = EntityID_Invalid; + EntityID m_WidgetPlaneZ = EntityID_Invalid; + EntityID m_WidgetOrigin = EntityID_Invalid; + glm::vec3 m_WidgetCurrentAxis; + float m_WidgetPickingDepth = 0.f; + glm::vec3 m_WidgetPickingPosition = glm::vec3(0); + + EntityID m_Selection = EntityID_Invalid; + EntityID m_LastSelection = EntityID_Invalid; + EntityID m_UIDraggingEntity = EntityID_Invalid; + glm::vec3 m_Position; + std::string m_LastDroppedFile; + + static boost::filesystem::path openDialog(boost::filesystem::path defaultPath); + static boost::filesystem::path saveDialog(boost::filesystem::path defaultPath); + + EventRelay m_EInputCommand; + bool OnInputCommand(const Events::InputCommand& e); + EventRelay m_EMouseRelease; + bool OnMouseRelease(const Events::MouseRelease& e); + EventRelay m_EMousePress; + bool OnMousePress(const Events::MousePress& e); + EventRelay m_EMouseMove; + bool OnMouseMove(const Events::MouseMove& e); + EventRelay m_EFileDropped; + bool OnFileDropped(const Events::FileDropped& e); + + void Picking(); + void createWidget(); + void updateWidget(); + void setWidgetMode(WidgetMode newMode); + void setWidgetSpace(WidgetSpace space); + void drawUI(World* world, double dt); + bool createDeleteButton(std::string componentType); + bool createEntityNode(World* world, EntityID entity); + void changeParent(EntityID entity, EntityID newParent); + void fileImport(World* world); + void fileSave(World* world); + void fileSaveAs(World* world); +}; \ No newline at end of file diff --git a/include/Engine/Editor/EditorUI.h b/include/Engine/Editor/EditorUI.h new file mode 100644 index 00000000..18299865 --- /dev/null +++ b/include/Engine/Editor/EditorUI.h @@ -0,0 +1,8 @@ +#include +#include + +class EditorUI +{ +public: + EditorUI(); +}; \ No newline at end of file diff --git a/include/Engine/Rendering/DebugCameraInputController.h b/include/Engine/Rendering/DebugCameraInputController.h index 4d74e288..1a43820c 100644 --- a/include/Engine/Rendering/DebugCameraInputController.h +++ b/include/Engine/Rendering/DebugCameraInputController.h @@ -1,3 +1,6 @@ +#ifndef DebugCameraInputController_h__ +#define DebugCameraInputController_h__ + #include #include "../Input/FirstPersonInputController.h" @@ -63,4 +66,6 @@ protected: glm::vec3 m_Velocity = glm::vec3(0, 0, 0); float m_BaseSpeed = 2.0f; float m_Speed = m_BaseSpeed; -}; \ No newline at end of file +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index 52876592..20c7249d 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -32,7 +32,6 @@ private: const LightCullingPass* m_LightCullingPass; ShaderProgram* m_ForwardPlusProgram; - }; #endif \ No newline at end of file diff --git a/include/Engine/Rendering/ESetCamera.h b/include/Engine/Rendering/ESetCamera.h index 650f3b12..1b39e890 100644 --- a/include/Engine/Rendering/ESetCamera.h +++ b/include/Engine/Rendering/ESetCamera.h @@ -2,20 +2,14 @@ #define Events_SetCamera_h__ #include "../Core/EventBroker.h" -#include "../Core/Entity.h" -#include +#include "../Core/EntityWrapper.h" namespace Events { struct SetCamera : Event { -public: - SetCamera() { }; - std::string Name; - -private: - + EntityWrapper CameraEntity; }; } diff --git a/include/Engine/Rendering/IRenderer.h b/include/Engine/Rendering/IRenderer.h index 95053a85..6ef189f4 100644 --- a/include/Engine/Rendering/IRenderer.h +++ b/include/Engine/Rendering/IRenderer.h @@ -31,15 +31,6 @@ public: void SetFullscreen(bool fullscreen) { m_Fullscreen = fullscreen; } bool VSYNC() const { return m_VSYNC; } void SetVSYNC(bool vsync) { m_VSYNC = vsync; } - ::Camera* Camera() const { return m_Camera; } - void SetCamera(::Camera* camera) - { - if (camera == nullptr) { - m_Camera = m_DefaultCamera; - } else { - m_Camera = camera; - } - } virtual void Initialize() = 0; virtual void Update(double dt) = 0; virtual void Draw(RenderFrame& rq) = 0; @@ -54,8 +45,6 @@ protected: int m_GLVersion[2]; std::string m_GLVendor; GLFWwindow* m_Window = nullptr; - ::Camera* m_DefaultCamera; - ::Camera* m_Camera = nullptr; }; #endif // Renderer_h__ diff --git a/include/Engine/Rendering/RenderJob.h b/include/Engine/Rendering/RenderJob.h index 4afe0386..bcffc4a5 100644 --- a/include/Engine/Rendering/RenderJob.h +++ b/include/Engine/Rendering/RenderJob.h @@ -14,7 +14,6 @@ struct RenderJob friend class RenderQueue; public: - float Depth; protected: diff --git a/include/Engine/Rendering/RenderQueue.h b/include/Engine/Rendering/RenderQueue.h index 119ea57f..701d08b9 100644 --- a/include/Engine/Rendering/RenderQueue.h +++ b/include/Engine/Rendering/RenderQueue.h @@ -50,10 +50,11 @@ struct PointLightJob : RenderJob struct RenderScene { - ::Camera* Camera; + ::Camera* Camera = nullptr; std::list> ForwardJobs; std::list> PointLightJobs; Rectangle Viewport; + bool ClearDepth = false; void Clear() { diff --git a/include/Engine/Rendering/RenderState.h b/include/Engine/Rendering/RenderState.h index c6eb8775..688ef520 100644 --- a/include/Engine/Rendering/RenderState.h +++ b/include/Engine/Rendering/RenderState.h @@ -16,10 +16,10 @@ public: bool Disable(GLenum cap); bool CullFace(GLenum mode); bool ClearColor(glm::vec4 color); - bool Clear(GLbitfield mask); bool BindFramebuffer(GLint framebuffer); bool BlendEquation(GLenum mode); bool BlendFunc(GLenum sfactor, GLenum dfactor); + bool DepthMask(GLboolean flag); private: std::vector> m_ResetFunctions; diff --git a/include/Engine/Rendering/RenderSystem.h b/include/Engine/Rendering/RenderSystem.h index fe110276..39b35108 100644 --- a/include/Engine/Rendering/RenderSystem.h +++ b/include/Engine/Rendering/RenderSystem.h @@ -28,28 +28,17 @@ public: private: World* m_World = nullptr; const IRenderer* m_Renderer; - RenderFrame* m_RenderFrame; - bool m_SwitchCamera = false; Camera* m_Camera; - DebugCameraInputController* m_DebugCameraInputController; - - std::list m_CameraComponents; + EntityWrapper m_CurrentCamera = EntityWrapper::Invalid; EventRelay m_ESetCamera; - bool OnSetCamera(const Events::SetCamera &event); - EntityID m_CurrentCamera = EntityID_Invalid; - - void switchCamera(EntityID entity); - - void updateCamera(World* world, double dt); - void updateProjectionMatrix(ComponentWrapper& cameraComponent); - - void fillModels(std::list>& jobs, World* world); - void fillLight(std::list>& jobs, World* world); - + bool OnSetCamera(Events::SetCamera &event); EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); + + void fillModels(std::list>& jobs, World* world); + void fillLight(std::list>& jobs, World* world); }; #endif \ No newline at end of file diff --git a/resources/Schema/Components/Camera.xml b/resources/Schema/Components/Camera.xml index ccb12f01..b9c28d53 100644 --- a/resources/Schema/Components/Camera.xml +++ b/resources/Schema/Components/Camera.xml @@ -1,6 +1,5 @@ - cam 45 0.01 5000 diff --git a/resources/Schema/Components/Camera.xsd b/resources/Schema/Components/Camera.xsd index 2b896c74..1bde2333 100644 --- a/resources/Schema/Components/Camera.xsd +++ b/resources/Schema/Components/Camera.xsd @@ -9,7 +9,6 @@ - Vertical Field of View in degrees diff --git a/resources/Schema/Components/PointLight.xsd b/resources/Schema/Components/PointLight.xsd index 9b802d8c..25d0aa07 100644 --- a/resources/Schema/Components/PointLight.xsd +++ b/resources/Schema/Components/PointLight.xsd @@ -12,7 +12,7 @@ - + diff --git a/resources/Schema/Entities/EditorWidget.xml b/resources/Schema/Entities/EditorWidget.xml new file mode 100755 index 00000000..e729af02 --- /dev/null +++ b/resources/Schema/Entities/EditorWidget.xml @@ -0,0 +1,79 @@ + + + + + + + + + + + + + + + + + + + + + + + + + Models/TranslationWidgetOrigin.obj + + + + + + + + Models/TranslationWidgetX.obj + + + + + + + + Models/TranslationWidgetY.obj + + + + + + + + Models/TranslationWidgetZ.obj + + + + + + + + Models/WidgetPlaneX.obj + + + + + + + + Models/WidgetPlaneY.obj + + + + + + + + Models/WidgetPlaneZ.obj + + + + + + diff --git a/resources/Schema/Entities/Test.xml b/resources/Schema/Entities/Test.xml index d2838ae9..5f57dbb7 100644 --- a/resources/Schema/Entities/Test.xml +++ b/resources/Schema/Entities/Test.xml @@ -9,7 +9,6 @@ Models/DummyScene.obj - @@ -25,3 +24,4 @@ + diff --git a/src/Engine/Editor/EditorRenderSystem.cpp b/src/Engine/Editor/EditorRenderSystem.cpp new file mode 100644 index 00000000..2d25338d --- /dev/null +++ b/src/Engine/Editor/EditorRenderSystem.cpp @@ -0,0 +1,87 @@ +#include "Editor/EditorRenderSystem.h" + +EditorRenderSystem::EditorRenderSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame) + : System(eventBroker) + , m_Renderer(renderer) + , m_RenderFrame(renderFrame) +{ + EVENT_SUBSCRIBE_MEMBER(m_ESetCamera, &EditorRenderSystem::OnSetCamera); + auto resolution = Rectangle::Rectangle(1280, 720); + m_EditorCamera = new Camera((float)resolution.Width / resolution.Height, glm::radians(45.f), 0.01f, 5000.f); +} + +void EditorRenderSystem::Update(World* world, double dt) +{ + if (m_CurrentCamera) { + ComponentWrapper cameraTransform = m_CurrentCamera["Transform"]; + m_EditorCamera->SetPosition(cameraTransform["Position"]); + m_EditorCamera->SetOrientation(glm::quat((const glm::vec3&)cameraTransform["Orientation"])); + } + + RenderScene scene; + scene.ClearDepth = true; + scene.Camera = m_EditorCamera; + scene.Viewport = Rectangle(1920, 1080); + + auto models = world->GetComponents("Model"); + if (models != nullptr) { + for (auto& cModel : *models) { + if (!(bool)cModel["Visible"]) { + continue; + } + + const std::string& resource = cModel["Resource"]; + + Model* model; + try { + model = ResourceManager::Load<::Model, true>(resource); + } catch (const Resource::StillLoadingException&) { + continue; + } catch (const std::exception&) { + try { + model = ResourceManager::Load<::Model>("Models/Core/Error.obj"); + } catch (const std::exception&) { + continue; + } + } + + EntityWrapper entity(world, cModel.EntityID); + glm::mat4 modelMatrix = Transform::ModelMatrix(entity.ID, entity.World); + for (auto matGroup : model->MaterialGroups()) { + std::shared_ptr modelJob = std::make_shared(model, nullptr, modelMatrix, matGroup, cModel, entity.World); + scene.ForwardJobs.push_back(modelJob); + } + } + } + + auto pointLights = world->GetComponents("PointLight"); + if (pointLights != nullptr) { + for (auto& cPointLight : *pointLights) { + bool visible = cPointLight["Visible"]; + if (!visible) { + continue; + } + + EntityWrapper entity(world, cPointLight.EntityID); + ComponentWrapper& cTransform = entity["Transform"]; + std::shared_ptr pointLightJob = std::make_shared(cTransform, cPointLight, entity.World); + scene.PointLightJobs.push_back(pointLightJob); + } + } + + m_RenderFrame->Add(scene); +} + +bool EditorRenderSystem::OnSetCamera(Events::SetCamera& e) +{ + ComponentWrapper cTransform = e.CameraEntity["Transform"]; + ComponentWrapper cCamera = e.CameraEntity["Camera"]; + m_EditorCamera->SetFOV((double)cCamera["FOV"]); + m_EditorCamera->SetNearClip((double)cCamera["NearClip"]); + m_EditorCamera->SetFarClip((double)cCamera["FarClip"]); + m_EditorCamera->SetPosition(cTransform["Position"]); + m_EditorCamera->SetOrientation(glm::quat((const glm::vec3&)cTransform["Orientation"])); + m_CurrentCamera = e.CameraEntity; + return true; +} + diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index d5863814..ec385e9b 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -1,738 +1,46 @@ #include "Editor/EditorSystem.h" -#define IMGUI_DEFINE_MATH_OPERATORS -#include +#include "Core/UniformScaleSystem.h" +#include "Editor/EditorRenderSystem.h" -EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer) +EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame) : System(eventBroker) - , ImpureSystem() , m_Renderer(renderer) + , m_RenderFrame(renderFrame) { - auto config = ResourceManager::Load("Config.ini"); - m_Enabled = config->Get("Debug.EditorEnabled", false); - m_Visible = m_Enabled; - m_DefaultEntityDir = boost::filesystem::path("Schema") / boost::filesystem::path("Entities"); + m_EditorWorld = new World(); + m_EditorWorldSystemPipeline = new SystemPipeline(eventBroker); + m_EditorWorldSystemPipeline->AddSystem(0); + m_EditorWorldSystemPipeline->AddSystem(1, m_Renderer, m_RenderFrame); + + auto widgetEntityFile = ResourceManager::Load("Schema/Entities/EditorWidget.xml"); + EntityFilePreprocessor fpp(widgetEntityFile); + fpp.RegisterComponents(m_EditorWorld); + EntityFileParser fp(widgetEntityFile); + EntityID widgetID = fp.MergeEntities(m_EditorWorld); + m_Widget = EntityWrapper(m_EditorWorld, widgetID); - if (!m_Enabled) { - return; - } + m_Camera = EntityWrapper(m_EditorWorld, m_EditorWorld->CreateEntity()); + m_EditorWorld->AttachComponent(m_Camera.ID, "Transform"); + m_EditorWorld->AttachComponent(m_Camera.ID, "Camera"); + m_DebugCameraInputController = new DebugCameraInputController(m_EventBroker, -1); - EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &EditorSystem::OnInputCommand); - EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorSystem::OnMousePress); - EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorSystem::OnMouseRelease); - EVENT_SUBSCRIBE_MEMBER(m_EMouseMove, &EditorSystem::OnMouseMove); - EVENT_SUBSCRIBE_MEMBER(m_EFileDropped, &EditorSystem::OnFileDropped); + Events::SetCamera e; + e.CameraEntity = m_Camera; + m_EventBroker->Publish(e); +} + +EditorSystem::~EditorSystem() +{ + delete m_DebugCameraInputController; + delete m_EditorWorldSystemPipeline; + delete m_EditorWorld; } void EditorSystem::Update(World* world, double dt) { - m_World = world; + m_EditorWorldSystemPipeline->Update(m_EditorWorld, dt); - if (!m_Enabled) { - return; - } - - if (!m_Visible) { - return; - } - Picking(); - updateWidget(); - - drawUI(world, dt); - - // Clear drop queue if it wasn't handled by any UI element - if (!m_LastDroppedFile.empty()) { - m_LastDroppedFile = ""; - } -} - - -boost::filesystem::path EditorSystem::openDialog(boost::filesystem::path defaultPath) -{ - namespace bfs = boost::filesystem; - auto absolutePath = bfs::absolute(defaultPath); - nfdchar_t* outPath = nullptr; - nfdresult_t result = NFD_OpenDialog(NULL, absolutePath.string().c_str(), &outPath); - if (result == NFD_ERROR) { - LOG_ERROR("NFD Error: %s", NFD_GetError()); - return bfs::path(); - } - - return bfs::absolute(outPath); -} - -boost::filesystem::path EditorSystem::saveDialog(boost::filesystem::path defaultPath) -{ - namespace bfs = boost::filesystem; - auto absolutePath = bfs::absolute(defaultPath); - nfdchar_t* outPath = nullptr; - nfdresult_t result = NFD_SaveDialog(NULL, absolutePath.string().c_str(), &outPath); - if (result == NFD_ERROR) { - LOG_ERROR("NFD Error: %s", NFD_GetError()); - return bfs::path(); - } - - return bfs::absolute(outPath); -} - -bool EditorSystem::OnInputCommand(const Events::InputCommand& e) -{ - if (e.Command == "ToggleEditor" && e.Value > 0) { - m_Visible = !m_Visible; - } - - if (e.Command == "EditorToolMove" && e.Value > 0) { - setWidgetMode(WidgetMode::Translate); - } - if (e.Command == "EditorToolRotate" && e.Value > 0) { - setWidgetMode(WidgetMode::Rotate); - } - if (e.Command == "EditorToolScale" && e.Value > 0) { - setWidgetMode(WidgetMode::Scale); - } - - if (e.Command == "EditorToggleTransformSpace" && e.Value > 0) { - if (m_WidgetSpace == WidgetSpace::Global) { - setWidgetSpace(WidgetSpace::Local); - } else if (m_WidgetSpace == WidgetSpace::Local) { - setWidgetSpace(WidgetSpace::Global); - } - } - - return true; -} - -bool EditorSystem::OnMousePress(const Events::MousePress& e) -{ - if (e.Button == GLFW_MOUSE_BUTTON_RIGHT) { - m_PickingQueue.push_back(glm::vec2((int)e.X, (int)e.Y)); - } - return true; -} - -bool EditorSystem::OnMouseMove(const Events::MouseMove& e) -{ - if (m_Widget == EntityID_Invalid) { - return false; - } - if (m_Selection == EntityID_Invalid) { - return false; - } - if (m_Selection == m_Widget) { - return false; - } - // TODO: No widgets for root entity until widgets reside in thier own world, - // or the widgets will move relative to the root entity being moved, which is WEEEIRD. - if (m_Selection == 0) { - return false; - } - if (m_Camera == nullptr) { - return false; - } - - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - glm::vec3 widgetOrientation = widgetTransform["Orientation"]; - glm::quat totalOrientation = m_Camera->Orientation() * glm::inverse(glm::quat(widgetOrientation)); - - int width; - int height; - glfwGetFramebufferSize(m_Renderer->Window(), &width, &height); - Rectangle res(width, height); - - glm::vec2 delta2(res.Width / 2.f + e.DeltaX, res.Height / 2.f + -e.DeltaY); - glm::vec3 deltaWorld = ScreenCoords::ToWorldPos( - delta2, - m_WidgetPickingDepth, - res, - m_Camera->ProjectionMatrix(), - glm::toMat4(glm::inverse(totalOrientation)) - ); - glm::vec3 origin = ScreenCoords::ToWorldPos( - glm::vec2(res.Width / 2.f, res.Height / 2.f), - m_WidgetPickingDepth, - res, - m_Camera->ProjectionMatrix(), - glm::toMat4(glm::inverse(totalOrientation)) - ); - deltaWorld = deltaWorld - origin; - glm::vec3 movement = deltaWorld * m_WidgetCurrentAxis; - - if (glm::length2(m_WidgetCurrentAxis) > 0.f) { - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - if (m_WidgetMode == WidgetMode::Translate) { - if (m_WidgetSpace == WidgetSpace::Global) { - EntityID parent = m_World->GetParent(m_Selection); - glm::quat inverseParentOrientation; - //if (parent != 0) { - inverseParentOrientation = glm::inverse(Transform::AbsoluteOrientation(m_World, parent)); - //} - (glm::vec3&)m_World->GetComponent(m_Selection, "Transform")["Position"] += inverseParentOrientation * movement; - } else if (m_WidgetSpace == WidgetSpace::Local) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - (glm::vec3&)selectionTransform["Position"] += glm::quat((glm::vec3)selectionTransform["Orientation"]) * movement; - } - } else if (m_WidgetMode == WidgetMode::Rotate) { - glm::vec3 finalMovement; - finalMovement.x = -deltaWorld.y * m_WidgetCurrentAxis.x; - finalMovement.y = deltaWorld.x * m_WidgetCurrentAxis.y; - finalMovement.z = deltaWorld.y * m_WidgetCurrentAxis.z; - if (m_WidgetSpace == WidgetSpace::Global) { - EntityID parent = m_World->GetParent(m_Selection); - glm::quat parentOrientation; - //if (parent != 0) { - // parentOrientation = RenderSystem::AbsoluteOrientation(m_World, parent); - //} - glm::vec3& selectionOrientation = m_World->GetComponent(m_Selection, "Transform")["Orientation"]; - glm::quat currentOrientation = Transform::AbsoluteOrientation(m_World, m_Selection); - //glm::quat currentOrientation = parentOrientation * glm::quat(selectionOrientation); - glm::quat deltaOrientation(finalMovement); - selectionOrientation = glm::eulerAngles(glm::inverse(parentOrientation) * (deltaOrientation * currentOrientation)); - } else if (m_WidgetSpace == WidgetSpace::Local) { - glm::vec3& selectionOrientation = m_World->GetComponent(m_Selection, "Transform")["Orientation"]; - glm::quat currentOrientation(selectionOrientation); - glm::quat deltaOrientation(finalMovement); - selectionOrientation = glm::eulerAngles(currentOrientation * deltaOrientation); - } - } else if (m_WidgetMode == WidgetMode::Scale) { - glm::vec3& scaleX = m_World->GetComponent(m_WidgetX, "Transform")["Scale"]; - glm::vec3& scaleY = m_World->GetComponent(m_WidgetY, "Transform")["Scale"]; - glm::vec3& scaleZ = m_World->GetComponent(m_WidgetZ, "Transform")["Scale"]; - - if (m_WidgetCurrentAxis.x > 0 && m_WidgetCurrentAxis.y > 0 && m_WidgetCurrentAxis.z > 0) { - float movementLength = glm::length(movement); - float dot = glm::dot((glm::vec3)widgetOrientation, movement); - movement = glm::vec3(movementLength) * glm::sign(dot); - (glm::vec3&)m_World->GetComponent(m_WidgetOrigin, "Transform")["Scale"] += movement; - } - if (m_WidgetCurrentAxis.x > 0) { - scaleX.x += movement.x; - } - if (m_WidgetCurrentAxis.y > 0) { - scaleY.y += movement.y; - } - if (m_WidgetCurrentAxis.z > 0) { - scaleZ.z += movement.z; - } - (glm::vec3&)m_World->GetComponent(m_Selection, "Transform")["Scale"] += movement; - } - } - - - /*LOG_DEBUG("DELTA %f", e.DeltaX); - if (e.X < 0) { - glfwSetCursorPos(m_Renderer->Window(), width - 1, e.Y); - } - if (e.X >= width) { - glfwSetCursorPos(m_Renderer->Window(), 0, e.Y); - }*/ - - return true; -} - -bool EditorSystem::OnMouseRelease(const Events::MouseRelease& e) -{ - if (glm::length2(m_WidgetCurrentAxis) > 0.f) { - m_WidgetCurrentAxis = glm::vec3(0.f); - //setWidgetMode(m_WidgetMode); - } - - return true; -} - -void EditorSystem::Picking() -{ - for (auto& pos : m_PickingQueue) { - auto result = m_Renderer->Pick(pos); - EntityID entity = result.Entity; - if (glm::length2(m_WidgetCurrentAxis) > 0.f) { - // ??? - } else { - LOG_INFO("Selected %i", entity); - if (entity != EntityID_Invalid) { - EntityID parent = m_World->GetParent(entity); - m_Camera = result.Camera; - if (parent == m_Widget) { - m_WidgetCurrentAxis = glm::vec3( - (entity == m_WidgetX) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneY || entity == m_WidgetPlaneZ), - (entity == m_WidgetY) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneX || entity == m_WidgetPlaneZ), - (entity == m_WidgetZ) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneX || entity == m_WidgetPlaneY) - ); - m_WidgetPickingDepth = result.Depth; - //auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - //auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - //widgetTransform["Position"] = (glm::vec3)selectionTransform["Position"]; - } else { - ImGui::SetActiveID(0, nullptr); - if (m_WidgetMode == WidgetMode::None) { - m_WidgetMode = WidgetMode::Translate; - } - setWidgetMode(m_WidgetMode); - m_Selection = entity; - } - } - } - } - m_PickingQueue.clear(); -}; - -bool EditorSystem::OnFileDropped(const Events::FileDropped& e) -{ - m_LastDroppedFile = boost::filesystem::path(e.Path).lexically_relative(boost::filesystem::current_path()).string(); - std::replace(m_LastDroppedFile.begin(), m_LastDroppedFile.end(), '\\', '/'); - return true; -} - -void EditorSystem::createWidget() -{ - if (m_Widget == EntityID_Invalid) { - m_Widget = m_World->CreateEntity(); - m_World->AttachComponent(m_Widget, "Transform"); - m_WidgetX = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetX, "Transform"); - m_World->AttachComponent(m_WidgetX, "Model"); - m_WidgetPlaneX = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetPlaneX, "Transform"); - m_World->AttachComponent(m_WidgetPlaneX, "Model"); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/WidgetPlaneX.obj"; - m_WidgetY = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetY, "Transform"); - m_World->AttachComponent(m_WidgetY, "Model"); - m_WidgetPlaneY = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetPlaneY, "Transform"); - m_World->AttachComponent(m_WidgetPlaneY, "Model"); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/WidgetPlaneY.obj"; - m_WidgetZ = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetZ, "Transform"); - m_World->AttachComponent(m_WidgetZ, "Model"); - m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); - m_World->AttachComponent(m_WidgetPlaneZ, "Model"); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; - m_WidgetOrigin = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetOrigin, "Transform"); - m_World->AttachComponent(m_WidgetOrigin, "Model"); - setWidgetMode(WidgetMode::None); - } -} - -void EditorSystem::updateWidget() -{ - if (m_Widget == EntityID_Invalid) { - return; - } - if (m_Selection == m_Widget) { - return; - } - - if (m_Selection != EntityID_Invalid) { - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - glm::vec3 selectionPosition = Transform::AbsolutePosition(m_World, m_Selection); - widgetTransform["Position"] = selectionPosition; - if (m_WidgetSpace == WidgetSpace::Local) { - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } -} - -void EditorSystem::setWidgetMode(WidgetMode newMode) -{ - if (m_Widget == EntityID_Invalid) { - return; - } - - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - widgetTransform["Orientation"] = glm::vec3(0.f); - m_World->GetComponent(m_WidgetX, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = false; - m_World->GetComponent(m_WidgetY, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Visible"] = false; - m_World->GetComponent(m_WidgetZ, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Visible"] = false; - m_World->GetComponent(m_WidgetOrigin, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = false; - - if (newMode == WidgetMode::Translate) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.obj"; - // Temporarily disabled for local space until I can figure out what's wrong with the math - if (m_WidgetSpace != WidgetSpace::Local) { - m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = true; - m_World->GetComponent(m_WidgetPlaneY, "Model")["Visible"] = true; - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Visible"] = true; - } - if (m_Selection != EntityID_Invalid) { - if (m_WidgetSpace == WidgetSpace::Local) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } - } else if (newMode == WidgetMode::Scale) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.obj"; - m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = true; - m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; - if (m_Selection != EntityID_Invalid) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } else if (newMode == WidgetMode::Rotate) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.obj"; - if (m_Selection != EntityID_Invalid) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - if (m_WidgetSpace == WidgetSpace::Local) { - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } - } - m_WidgetMode = newMode; -} - -void EditorSystem::setWidgetSpace(WidgetSpace space) -{ - m_WidgetSpace = space; - setWidgetMode(m_WidgetMode); -} - -void EditorSystem::drawUI(World* world, double dt) -{ - namespace bfs = boost::filesystem; - - ImGui::ShowTestWindow(); - //ImGui::ShowStyleEditor(); - - if (ImGui::BeginMainMenuBar()) { - if (ImGui::BeginMenu("File")) { - //if (ImGui::MenuItem("New")) { } - if (ImGui::MenuItem("Import", "Ctrl+O")) { - fileImport(world); - } - if (ImGui::MenuItem("Save", "Ctrl+S")) { - fileSave(world); - } - if (ImGui::MenuItem("Save As...", "Ctrl+Shift+S")) { - fileSaveAs(world); - } - ImGui::Separator(); - if (ImGui::MenuItem("Close Editor", "F1")) { } - - ImGui::EndMenu(); - } - - ImGui::SameLine(); - if (ImGui::Button("Move")) { - setWidgetMode(WidgetMode::Translate); - } - ImGui::SameLine(); - if (ImGui::Button("Rotate")) { - setWidgetMode(WidgetMode::Rotate); - } - ImGui::SameLine(); - if (ImGui::Button("Scale")) { - setWidgetMode(WidgetMode::Scale); - } - ImGui::SameLine(); - if (m_WidgetSpace == WidgetSpace::Global) { - if (ImGui::Button("(Global)")) { - setWidgetSpace(WidgetSpace::Local); - } - } else if (m_WidgetSpace == WidgetSpace::Local) { - if (ImGui::Button("(Local)")) { - setWidgetSpace(WidgetSpace::Global); - } - } - - ImGui::EndMainMenuBar(); - } - - std::string title = std::string("Components #") + std::to_string(m_Selection) + std::string("###Components"); - if (ImGui::Begin(title.c_str())) { - if (m_Selection != EntityID_Invalid) { - auto& pools = world->GetComponentPools(); - - std::vector componentTypes; - for (auto& pair : pools) { - // Only add components the entity doesn't already have - if (!pair.second->KnowsEntity(m_Selection)) { - componentTypes.push_back(pair.first.c_str()); - } - } - int item = -1; - ImGui::PushItemWidth(ImGui::GetWindowContentRegionWidth() - 5.f); - if (ImGui::Combo("", &item, componentTypes.data(), componentTypes.size())) { - if (item != -1) { - std::string chosenType = std::string(componentTypes.at(item)); - world->AttachComponent(m_Selection, chosenType); - } - } - ImGui::PopItemWidth(); - - for (auto& pair : pools) { - const std::string& componentType = pair.first; - auto pool = pair.second; - if (!pool->KnowsEntity(m_Selection)) { - continue; - } - auto& ci = pool->ComponentInfo(); - - bool deletePressed = createDeleteButton(componentType); - if (deletePressed) { - world->DeleteComponent(m_Selection, componentType); - continue; - } - - if (ImGui::CollapsingHeader(componentType.c_str())) { - if (!ci.Meta->Annotation.empty()) { - ImGui::Text(ci.Meta->Annotation.c_str()); - } - - auto& component = world->GetComponent(m_Selection, componentType); - for (auto& kv : ci.Fields) { - const std::string& fieldName = kv.first; - auto& field = kv.second; - - std::string uniqueID = componentType + fieldName; - ImGui::PushID(uniqueID.c_str()); - if (field.Type == "Vector") { - auto& val = component.Field(fieldName); - if (fieldName == "Scale") { - ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, 0.f, std::numeric_limits::max()); - } else if (fieldName == "Orientation") { - glm::vec3 tempVal = glm::fmod(val, glm::vec3(glm::two_pi())); - if (ImGui::SliderFloat3("", glm::value_ptr(tempVal), 0.f, glm::two_pi())) { - val = tempVal; - } - } else { - ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, std::numeric_limits::lowest(), std::numeric_limits::max()); - } - } else if (field.Type == "Color") { - auto& val = component.Field(fieldName); - ImGui::ColorEdit4("", glm::value_ptr(val), true); - } else if (field.Type == "string") { - std::string& val = component.Field(fieldName); - char tempString[1024]; - memcpy(tempString, val.c_str(), std::min(val.length() + 1, sizeof(tempString))); - if (ImGui::InputText("", tempString, sizeof(tempString))) { - val = std::string(tempString); - LOG_DEBUG("%s::%s changed!", componentType.c_str(), fieldName.c_str()); - } - // DROP STUFF - if (ImGui::IsItemHovered() && !m_LastDroppedFile.empty()) { - val = m_LastDroppedFile; - m_LastDroppedFile = ""; - } - - } else if (field.Type == "double") { - float tempVal = static_cast(component.Field(fieldName)); - if (ImGui::InputFloat("", &tempVal, 0.01f, 1.f)) { - component.SetField(fieldName, static_cast(tempVal)); - } - } else if (field.Type == "int") { - int val = component.Field(fieldName); - ImGui::InputInt("", &val); - } else if (field.Type == "enum") { - int currentValue = component.Field(fieldName); - int item = -1; - std::stringstream enumKeys; - std::vector enumValues; - int i = 0; - for (auto& kv : ci.Meta->FieldEnumDefinitions.at(fieldName)) { - enumKeys << kv.first << " (" << kv.second << ")" << '\0'; - enumValues.push_back(kv.second); - if (currentValue == kv.second) { - item = i; - } - i++; - } - if (ImGui::Combo("", &item, enumKeys.str().c_str())) { - component.SetField(fieldName, enumValues.at(item)); - } - } else if (field.Type == "bool") { - auto& val = component.Field(fieldName); - ImGui::Checkbox("", &val); - } else { - ImGui::TextDisabled(field.Type.c_str()); - } - ImGui::PopID(); - - ImGui::SameLine(); - ImGui::Text(fieldName.c_str()); - if (ImGui::IsItemHovered()) { - ImGui::SetTooltip("field annotation goes here"); - } - } - } - } - } - - } - ImGui::End(); - - if (ImGui::Begin("Entities")) { - auto entityChildren = world->GetEntityChildren(); - std::function recurse = [&](EntityID parent) { - auto range = entityChildren.equal_range(parent); - for (auto it = range.first; it != range.second; it++) { - if (createEntityNode(world, it->second)) { - recurse(it->second); - ImGui::TreePop(); - } - } - }; - recurse(EntityID_Invalid); - } - ImGui::End(); -} - -bool EditorSystem::createEntityNode(World* world, EntityID entity) -{ - // HACK: Don't show the widget entities in the entity tree - if (entity == m_Widget) { - return false; - } - - ImVec2 pos = ImGui::GetCursorScreenPos(); - float width = ImGui::GetContentRegionAvailWidth(); - ImRect bb(pos + ImVec2(20, 0), pos + ImVec2(width, 13)); - auto window = ImGui::GetCurrentWindow(); - if (m_Selection == entity) { - const ImU32 col = window->Color(ImGuiCol_HeaderActive); - window->DrawList->AddRectFilled(bb.Min, bb.Max, col); - } - ImGuiID id = window->GetID((std::string("#SelectButton") + std::to_string(entity)).c_str()); - bool hovered = false; - bool held = false; - if (ImGui::ButtonBehavior(bb, id, &hovered, &held)) { - m_Selection = entity; - } - if (held) { - ImVec2 entityDragDelta = ImGui::GetMouseDragDelta(0); - if (std::abs(entityDragDelta.x) > 0 && std::abs(entityDragDelta.y) > 0) { - if (m_UIDraggingEntity == EntityID_Invalid) { - m_UIDraggingEntity = entity; - LOG_DEBUG("Started drag of entity %i", m_UIDraggingEntity); - } - ImGui::SetNextWindowPos(ImGui::GetIO().MousePos + ImVec2(20, 0)); - ImGui::Begin("Change parent", nullptr, ImVec2(0, 0), 0.3f, ImGuiWindowFlags_NoTitleBar|ImGuiWindowFlags_NoResize|ImGuiWindowFlags_NoMove|ImGuiWindowFlags_NoSavedSettings); - ImGui::Text("#%i", m_UIDraggingEntity); - ImGui::End(); - } - } - - ImGui::SetNextTreeNodeOpened(true, ImGuiSetCond_Once); - std::string nodeTitle; - const std::string& entityName = world->GetName(entity); - if (!entityName.empty()) { - nodeTitle = entityName; - } else { - nodeTitle = std::string("#") + std::to_string(entity); - } - if (ImGui::TreeNode(nodeTitle.c_str())) { - if (m_UIDraggingEntity != EntityID_Invalid && ImGui::IsItemHoveredRect() && ImGui::IsMouseReleased(0)) { - LOG_DEBUG("Changed parent of %i to %i", m_UIDraggingEntity, entity); - changeParent(m_UIDraggingEntity, entity); - m_UIDraggingEntity = EntityID_Invalid; - } - - if (ImGui::BeginPopupContextItem("item context menu")) { - if (ImGui::Button("Add")) { - EntityID newEntity = world->CreateEntity(entity); - world->AttachComponent(newEntity, "Transform"); - } - ImGui::SameLine(); - if (ImGui::Button("Delete")) { - world->DeleteEntity(entity); - ImGui::CloseCurrentPopup(); - if (!world->ValidEntity(m_Selection)) { - m_Selection = EntityID_Invalid; - } - } - ImGui::EndPopup(); - } - return true; - } else { - return false; - } -} - -bool EditorSystem::createDeleteButton(std::string componentType) -{ - float width = ImGui::GetContentRegionAvailWidth(); - ImGuiWindow* window = ImGui::GetCurrentWindow(); - auto pos = ImGui::GetCursorScreenPos() + ImVec2(width - 14.f, 1); - ImRect bb = ImRect(pos, pos + ImVec2(14.f, 14.f)); - std::string idString = "#DELETE"; - idString += componentType; - ImGuiID id = window->GetID(idString.c_str()); - bool hovered; - bool held; - bool pressed = ImGui::ButtonBehavior(bb, id, &hovered, &held); - //ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_CloseButtonHovered : ImGuiCol_CloseButton); - ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - window->DrawList->AddCircleFilled(bb.GetCenter(), 7.f, col, 16); - return pressed; -} - -void EditorSystem::changeParent(EntityID entity, EntityID newParent) -{ - if (entity == newParent) { - return; - } - - // An entity can't be a child to one of its own children - auto children = m_World->GetEntityChildren().equal_range(entity); - for (auto it = children.first; it != children.second; it++) { - if (it->second == newParent) { - return; - } - } - - m_World->SetParent(entity, newParent); -} - -void EditorSystem::fileImport(World* world) -{ - m_CurrentFile = openDialog(m_DefaultEntityDir); - auto file = ResourceManager::Load(m_CurrentFile.string()); - EntityFilePreprocessor fpp(file); - fpp.RegisterComponents(world); - EntityFileParser fp(file); - fp.MergeEntities(world); - createWidget(); - updateWidget(); -} - -void EditorSystem::fileSave(World* world) -{ - if (boost::filesystem::exists(m_CurrentFile)) { - // HACK: Delete the widgets so they don't appear in the saved file - world->DeleteEntity(m_Widget); - m_Widget = EntityID_Invalid; - - EntityFileWriter writer(m_CurrentFile.string()); - writer.WriteWorld(world); - - createWidget(); - } else { - fileSaveAs(world); - } -} - -void EditorSystem::fileSaveAs(World* world) -{ - auto filePath = saveDialog(m_DefaultEntityDir); - if (filePath.empty()) { - return; - } - - // HACK: Delete the widgets so they don't appear in the saved file - world->DeleteEntity(m_Widget); - m_Widget = EntityID_Invalid; - - EntityFileWriter writer(filePath.string()); - writer.WriteWorld(world); - - createWidget(); -} + m_DebugCameraInputController->Update(dt); + m_Camera["Transform"]["Position"] = m_DebugCameraInputController->Position(); + m_Camera["Transform"]["Orientation"] = glm::eulerAngles(m_DebugCameraInputController->Orientation()); +} \ No newline at end of file diff --git a/src/Engine/Editor/EditorSystemOld.cpp b/src/Engine/Editor/EditorSystemOld.cpp new file mode 100644 index 00000000..675ea80b --- /dev/null +++ b/src/Engine/Editor/EditorSystemOld.cpp @@ -0,0 +1,738 @@ +#include "Editor/EditorSystemOld.h" +#define IMGUI_DEFINE_MATH_OPERATORS +#include + +EditorSystemOld::EditorSystemOld(EventBroker* eventBroker, IRenderer* renderer) + : System(eventBroker) + , ImpureSystem() + , m_Renderer(renderer) +{ + auto config = ResourceManager::Load("Config.ini"); + m_Enabled = config->Get("Debug.EditorEnabled", false); + m_Visible = m_Enabled; + m_DefaultEntityDir = boost::filesystem::path("Schema") / boost::filesystem::path("Entities"); + + if (!m_Enabled) { + return; + } + + EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &EditorSystemOld::OnInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorSystemOld::OnMousePress); + EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorSystemOld::OnMouseRelease); + EVENT_SUBSCRIBE_MEMBER(m_EMouseMove, &EditorSystemOld::OnMouseMove); + EVENT_SUBSCRIBE_MEMBER(m_EFileDropped, &EditorSystemOld::OnFileDropped); +} + +void EditorSystemOld::Update(World* world, double dt) +{ + m_World = world; + + if (!m_Enabled) { + return; + } + + if (!m_Visible) { + return; + } + Picking(); + updateWidget(); + + drawUI(world, dt); + + // Clear drop queue if it wasn't handled by any UI element + if (!m_LastDroppedFile.empty()) { + m_LastDroppedFile = ""; + } +} + + +boost::filesystem::path EditorSystemOld::openDialog(boost::filesystem::path defaultPath) +{ + namespace bfs = boost::filesystem; + auto absolutePath = bfs::absolute(defaultPath); + nfdchar_t* outPath = nullptr; + nfdresult_t result = NFD_OpenDialog(NULL, absolutePath.string().c_str(), &outPath); + if (result == NFD_ERROR) { + LOG_ERROR("NFD Error: %s", NFD_GetError()); + return bfs::path(); + } + + return bfs::absolute(outPath); +} + +boost::filesystem::path EditorSystemOld::saveDialog(boost::filesystem::path defaultPath) +{ + namespace bfs = boost::filesystem; + auto absolutePath = bfs::absolute(defaultPath); + nfdchar_t* outPath = nullptr; + nfdresult_t result = NFD_SaveDialog(NULL, absolutePath.string().c_str(), &outPath); + if (result == NFD_ERROR) { + LOG_ERROR("NFD Error: %s", NFD_GetError()); + return bfs::path(); + } + + return bfs::absolute(outPath); +} + +bool EditorSystemOld::OnInputCommand(const Events::InputCommand& e) +{ + if (e.Command == "ToggleEditor" && e.Value > 0) { + m_Visible = !m_Visible; + } + + if (e.Command == "EditorToolMove" && e.Value > 0) { + setWidgetMode(WidgetMode::Translate); + } + if (e.Command == "EditorToolRotate" && e.Value > 0) { + setWidgetMode(WidgetMode::Rotate); + } + if (e.Command == "EditorToolScale" && e.Value > 0) { + setWidgetMode(WidgetMode::Scale); + } + + if (e.Command == "EditorToggleTransformSpace" && e.Value > 0) { + if (m_WidgetSpace == WidgetSpace::Global) { + setWidgetSpace(WidgetSpace::Local); + } else if (m_WidgetSpace == WidgetSpace::Local) { + setWidgetSpace(WidgetSpace::Global); + } + } + + return true; +} + +bool EditorSystemOld::OnMousePress(const Events::MousePress& e) +{ + if (e.Button == GLFW_MOUSE_BUTTON_RIGHT) { + m_PickingQueue.push_back(glm::vec2((int)e.X, (int)e.Y)); + } + return true; +} + +bool EditorSystemOld::OnMouseMove(const Events::MouseMove& e) +{ + if (m_Widget == EntityID_Invalid) { + return false; + } + if (m_Selection == EntityID_Invalid) { + return false; + } + if (m_Selection == m_Widget) { + return false; + } + // TODO: No widgets for root entity until widgets reside in thier own world, + // or the widgets will move relative to the root entity being moved, which is WEEEIRD. + if (m_Selection == 0) { + return false; + } + if (m_Camera == nullptr) { + return false; + } + + auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); + glm::vec3 widgetOrientation = widgetTransform["Orientation"]; + glm::quat totalOrientation = m_Camera->Orientation() * glm::inverse(glm::quat(widgetOrientation)); + + int width; + int height; + glfwGetFramebufferSize(m_Renderer->Window(), &width, &height); + Rectangle res(width, height); + + glm::vec2 delta2(res.Width / 2.f + e.DeltaX, res.Height / 2.f + -e.DeltaY); + glm::vec3 deltaWorld = ScreenCoords::ToWorldPos( + delta2, + m_WidgetPickingDepth, + res, + m_Camera->ProjectionMatrix(), + glm::toMat4(glm::inverse(totalOrientation)) + ); + glm::vec3 origin = ScreenCoords::ToWorldPos( + glm::vec2(res.Width / 2.f, res.Height / 2.f), + m_WidgetPickingDepth, + res, + m_Camera->ProjectionMatrix(), + glm::toMat4(glm::inverse(totalOrientation)) + ); + deltaWorld = deltaWorld - origin; + glm::vec3 movement = deltaWorld * m_WidgetCurrentAxis; + + if (glm::length2(m_WidgetCurrentAxis) > 0.f) { + auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); + if (m_WidgetMode == WidgetMode::Translate) { + if (m_WidgetSpace == WidgetSpace::Global) { + EntityID parent = m_World->GetParent(m_Selection); + glm::quat inverseParentOrientation; + //if (parent != 0) { + inverseParentOrientation = glm::inverse(Transform::AbsoluteOrientation(m_World, parent)); + //} + (glm::vec3&)m_World->GetComponent(m_Selection, "Transform")["Position"] += inverseParentOrientation * movement; + } else if (m_WidgetSpace == WidgetSpace::Local) { + auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); + (glm::vec3&)selectionTransform["Position"] += glm::quat((glm::vec3)selectionTransform["Orientation"]) * movement; + } + } else if (m_WidgetMode == WidgetMode::Rotate) { + glm::vec3 finalMovement; + finalMovement.x = -deltaWorld.y * m_WidgetCurrentAxis.x; + finalMovement.y = deltaWorld.x * m_WidgetCurrentAxis.y; + finalMovement.z = deltaWorld.y * m_WidgetCurrentAxis.z; + if (m_WidgetSpace == WidgetSpace::Global) { + EntityID parent = m_World->GetParent(m_Selection); + glm::quat parentOrientation; + //if (parent != 0) { + // parentOrientation = RenderSystem::AbsoluteOrientation(m_World, parent); + //} + glm::vec3& selectionOrientation = m_World->GetComponent(m_Selection, "Transform")["Orientation"]; + glm::quat currentOrientation = Transform::AbsoluteOrientation(m_World, m_Selection); + //glm::quat currentOrientation = parentOrientation * glm::quat(selectionOrientation); + glm::quat deltaOrientation(finalMovement); + selectionOrientation = glm::eulerAngles(glm::inverse(parentOrientation) * (deltaOrientation * currentOrientation)); + } else if (m_WidgetSpace == WidgetSpace::Local) { + glm::vec3& selectionOrientation = m_World->GetComponent(m_Selection, "Transform")["Orientation"]; + glm::quat currentOrientation(selectionOrientation); + glm::quat deltaOrientation(finalMovement); + selectionOrientation = glm::eulerAngles(currentOrientation * deltaOrientation); + } + } else if (m_WidgetMode == WidgetMode::Scale) { + glm::vec3& scaleX = m_World->GetComponent(m_WidgetX, "Transform")["Scale"]; + glm::vec3& scaleY = m_World->GetComponent(m_WidgetY, "Transform")["Scale"]; + glm::vec3& scaleZ = m_World->GetComponent(m_WidgetZ, "Transform")["Scale"]; + + if (m_WidgetCurrentAxis.x > 0 && m_WidgetCurrentAxis.y > 0 && m_WidgetCurrentAxis.z > 0) { + float movementLength = glm::length(movement); + float dot = glm::dot((glm::vec3)widgetOrientation, movement); + movement = glm::vec3(movementLength) * glm::sign(dot); + (glm::vec3&)m_World->GetComponent(m_WidgetOrigin, "Transform")["Scale"] += movement; + } + if (m_WidgetCurrentAxis.x > 0) { + scaleX.x += movement.x; + } + if (m_WidgetCurrentAxis.y > 0) { + scaleY.y += movement.y; + } + if (m_WidgetCurrentAxis.z > 0) { + scaleZ.z += movement.z; + } + (glm::vec3&)m_World->GetComponent(m_Selection, "Transform")["Scale"] += movement; + } + } + + + /*LOG_DEBUG("DELTA %f", e.DeltaX); + if (e.X < 0) { + glfwSetCursorPos(m_Renderer->Window(), width - 1, e.Y); + } + if (e.X >= width) { + glfwSetCursorPos(m_Renderer->Window(), 0, e.Y); + }*/ + + return true; +} + +bool EditorSystemOld::OnMouseRelease(const Events::MouseRelease& e) +{ + if (glm::length2(m_WidgetCurrentAxis) > 0.f) { + m_WidgetCurrentAxis = glm::vec3(0.f); + //setWidgetMode(m_WidgetMode); + } + + return true; +} + +void EditorSystemOld::Picking() +{ + for (auto& pos : m_PickingQueue) { + auto result = m_Renderer->Pick(pos); + EntityID entity = result.Entity; + if (glm::length2(m_WidgetCurrentAxis) > 0.f) { + // ??? + } else { + LOG_INFO("Selected %i", entity); + if (entity != EntityID_Invalid) { + EntityID parent = m_World->GetParent(entity); + m_Camera = result.Camera; + if (parent == m_Widget) { + m_WidgetCurrentAxis = glm::vec3( + (entity == m_WidgetX) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneY || entity == m_WidgetPlaneZ), + (entity == m_WidgetY) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneX || entity == m_WidgetPlaneZ), + (entity == m_WidgetZ) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneX || entity == m_WidgetPlaneY) + ); + m_WidgetPickingDepth = result.Depth; + //auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); + //auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); + //widgetTransform["Position"] = (glm::vec3)selectionTransform["Position"]; + } else { + ImGui::SetActiveID(0, nullptr); + if (m_WidgetMode == WidgetMode::None) { + m_WidgetMode = WidgetMode::Translate; + } + setWidgetMode(m_WidgetMode); + m_Selection = entity; + } + } + } + } + m_PickingQueue.clear(); +}; + +bool EditorSystemOld::OnFileDropped(const Events::FileDropped& e) +{ + m_LastDroppedFile = boost::filesystem::path(e.Path).lexically_relative(boost::filesystem::current_path()).string(); + std::replace(m_LastDroppedFile.begin(), m_LastDroppedFile.end(), '\\', '/'); + return true; +} + +void EditorSystemOld::createWidget() +{ + if (m_Widget == EntityID_Invalid) { + m_Widget = m_World->CreateEntity(); + m_World->AttachComponent(m_Widget, "Transform"); + m_WidgetX = m_World->CreateEntity(m_Widget); + m_World->AttachComponent(m_WidgetX, "Transform"); + m_World->AttachComponent(m_WidgetX, "Model"); + m_WidgetPlaneX = m_World->CreateEntity(m_Widget); + m_World->AttachComponent(m_WidgetPlaneX, "Transform"); + m_World->AttachComponent(m_WidgetPlaneX, "Model"); + m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/WidgetPlaneX.obj"; + m_WidgetY = m_World->CreateEntity(m_Widget); + m_World->AttachComponent(m_WidgetY, "Transform"); + m_World->AttachComponent(m_WidgetY, "Model"); + m_WidgetPlaneY = m_World->CreateEntity(m_Widget); + m_World->AttachComponent(m_WidgetPlaneY, "Transform"); + m_World->AttachComponent(m_WidgetPlaneY, "Model"); + m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/WidgetPlaneY.obj"; + m_WidgetZ = m_World->CreateEntity(m_Widget); + m_World->AttachComponent(m_WidgetZ, "Transform"); + m_World->AttachComponent(m_WidgetZ, "Model"); + m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); + m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); + m_World->AttachComponent(m_WidgetPlaneZ, "Model"); + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; + m_WidgetOrigin = m_World->CreateEntity(m_Widget); + m_World->AttachComponent(m_WidgetOrigin, "Transform"); + m_World->AttachComponent(m_WidgetOrigin, "Model"); + setWidgetMode(WidgetMode::None); + } +} + +void EditorSystemOld::updateWidget() +{ + if (m_Widget == EntityID_Invalid) { + return; + } + if (m_Selection == m_Widget) { + return; + } + + if (m_Selection != EntityID_Invalid) { + auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); + glm::vec3 selectionPosition = Transform::AbsolutePosition(m_World, m_Selection); + widgetTransform["Position"] = selectionPosition; + if (m_WidgetSpace == WidgetSpace::Local) { + widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); + } + } +} + +void EditorSystemOld::setWidgetMode(WidgetMode newMode) +{ + if (m_Widget == EntityID_Invalid) { + return; + } + + auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); + widgetTransform["Orientation"] = glm::vec3(0.f); + m_World->GetComponent(m_WidgetX, "Transform")["Scale"] = glm::vec3(1.f); + m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = false; + m_World->GetComponent(m_WidgetY, "Transform")["Scale"] = glm::vec3(1.f); + m_World->GetComponent(m_WidgetPlaneY, "Model")["Visible"] = false; + m_World->GetComponent(m_WidgetZ, "Transform")["Scale"] = glm::vec3(1.f); + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Visible"] = false; + m_World->GetComponent(m_WidgetOrigin, "Transform")["Scale"] = glm::vec3(1.f); + m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = false; + + if (newMode == WidgetMode::Translate) { + m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; + m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.obj"; + m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.obj"; + // Temporarily disabled for local space until I can figure out what's wrong with the math + if (m_WidgetSpace != WidgetSpace::Local) { + m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = true; + m_World->GetComponent(m_WidgetPlaneY, "Model")["Visible"] = true; + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Visible"] = true; + } + if (m_Selection != EntityID_Invalid) { + if (m_WidgetSpace == WidgetSpace::Local) { + auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); + widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); + } + } + } else if (newMode == WidgetMode::Scale) { + m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; + m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.obj"; + m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.obj"; + m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = true; + m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; + if (m_Selection != EntityID_Invalid) { + auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); + widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); + } + } else if (newMode == WidgetMode::Rotate) { + m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; + m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.obj"; + m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.obj"; + if (m_Selection != EntityID_Invalid) { + auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); + if (m_WidgetSpace == WidgetSpace::Local) { + widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); + } + } + } + m_WidgetMode = newMode; +} + +void EditorSystemOld::setWidgetSpace(WidgetSpace space) +{ + m_WidgetSpace = space; + setWidgetMode(m_WidgetMode); +} + +void EditorSystemOld::drawUI(World* world, double dt) +{ + namespace bfs = boost::filesystem; + + ImGui::ShowTestWindow(); + //ImGui::ShowStyleEditor(); + + if (ImGui::BeginMainMenuBar()) { + if (ImGui::BeginMenu("File")) { + //if (ImGui::MenuItem("New")) { } + if (ImGui::MenuItem("Import", "Ctrl+O")) { + fileImport(world); + } + if (ImGui::MenuItem("Save", "Ctrl+S")) { + fileSave(world); + } + if (ImGui::MenuItem("Save As...", "Ctrl+Shift+S")) { + fileSaveAs(world); + } + ImGui::Separator(); + if (ImGui::MenuItem("Close Editor", "F1")) { } + + ImGui::EndMenu(); + } + + ImGui::SameLine(); + if (ImGui::Button("Move")) { + setWidgetMode(WidgetMode::Translate); + } + ImGui::SameLine(); + if (ImGui::Button("Rotate")) { + setWidgetMode(WidgetMode::Rotate); + } + ImGui::SameLine(); + if (ImGui::Button("Scale")) { + setWidgetMode(WidgetMode::Scale); + } + ImGui::SameLine(); + if (m_WidgetSpace == WidgetSpace::Global) { + if (ImGui::Button("(Global)")) { + setWidgetSpace(WidgetSpace::Local); + } + } else if (m_WidgetSpace == WidgetSpace::Local) { + if (ImGui::Button("(Local)")) { + setWidgetSpace(WidgetSpace::Global); + } + } + + ImGui::EndMainMenuBar(); + } + + std::string title = std::string("Components #") + std::to_string(m_Selection) + std::string("###Components"); + if (ImGui::Begin(title.c_str())) { + if (m_Selection != EntityID_Invalid) { + auto& pools = world->GetComponentPools(); + + std::vector componentTypes; + for (auto& pair : pools) { + // Only add components the entity doesn't already have + if (!pair.second->KnowsEntity(m_Selection)) { + componentTypes.push_back(pair.first.c_str()); + } + } + int item = -1; + ImGui::PushItemWidth(ImGui::GetWindowContentRegionWidth() - 5.f); + if (ImGui::Combo("", &item, componentTypes.data(), componentTypes.size())) { + if (item != -1) { + std::string chosenType = std::string(componentTypes.at(item)); + world->AttachComponent(m_Selection, chosenType); + } + } + ImGui::PopItemWidth(); + + for (auto& pair : pools) { + const std::string& componentType = pair.first; + auto pool = pair.second; + if (!pool->KnowsEntity(m_Selection)) { + continue; + } + auto& ci = pool->ComponentInfo(); + + bool deletePressed = createDeleteButton(componentType); + if (deletePressed) { + world->DeleteComponent(m_Selection, componentType); + continue; + } + + if (ImGui::CollapsingHeader(componentType.c_str())) { + if (!ci.Meta->Annotation.empty()) { + ImGui::Text(ci.Meta->Annotation.c_str()); + } + + auto& component = world->GetComponent(m_Selection, componentType); + for (auto& kv : ci.Fields) { + const std::string& fieldName = kv.first; + auto& field = kv.second; + + std::string uniqueID = componentType + fieldName; + ImGui::PushID(uniqueID.c_str()); + if (field.Type == "Vector") { + auto& val = component.Field(fieldName); + if (fieldName == "Scale") { + ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, 0.f, std::numeric_limits::max()); + } else if (fieldName == "Orientation") { + glm::vec3 tempVal = glm::fmod(val, glm::vec3(glm::two_pi())); + if (ImGui::SliderFloat3("", glm::value_ptr(tempVal), 0.f, glm::two_pi())) { + val = tempVal; + } + } else { + ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, std::numeric_limits::lowest(), std::numeric_limits::max()); + } + } else if (field.Type == "Color") { + auto& val = component.Field(fieldName); + ImGui::ColorEdit4("", glm::value_ptr(val), true); + } else if (field.Type == "string") { + std::string& val = component.Field(fieldName); + char tempString[1024]; + memcpy(tempString, val.c_str(), std::min(val.length() + 1, sizeof(tempString))); + if (ImGui::InputText("", tempString, sizeof(tempString))) { + val = std::string(tempString); + LOG_DEBUG("%s::%s changed!", componentType.c_str(), fieldName.c_str()); + } + // DROP STUFF + if (ImGui::IsItemHovered() && !m_LastDroppedFile.empty()) { + val = m_LastDroppedFile; + m_LastDroppedFile = ""; + } + + } else if (field.Type == "double") { + float tempVal = static_cast(component.Field(fieldName)); + if (ImGui::InputFloat("", &tempVal, 0.01f, 1.f)) { + component.SetField(fieldName, static_cast(tempVal)); + } + } else if (field.Type == "int") { + int val = component.Field(fieldName); + ImGui::InputInt("", &val); + } else if (field.Type == "enum") { + int currentValue = component.Field(fieldName); + int item = -1; + std::stringstream enumKeys; + std::vector enumValues; + int i = 0; + for (auto& kv : ci.Meta->FieldEnumDefinitions.at(fieldName)) { + enumKeys << kv.first << " (" << kv.second << ")" << '\0'; + enumValues.push_back(kv.second); + if (currentValue == kv.second) { + item = i; + } + i++; + } + if (ImGui::Combo("", &item, enumKeys.str().c_str())) { + component.SetField(fieldName, enumValues.at(item)); + } + } else if (field.Type == "bool") { + auto& val = component.Field(fieldName); + ImGui::Checkbox("", &val); + } else { + ImGui::TextDisabled(field.Type.c_str()); + } + ImGui::PopID(); + + ImGui::SameLine(); + ImGui::Text(fieldName.c_str()); + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip("field annotation goes here"); + } + } + } + } + } + + } + ImGui::End(); + + if (ImGui::Begin("Entities")) { + auto entityChildren = world->GetEntityChildren(); + std::function recurse = [&](EntityID parent) { + auto range = entityChildren.equal_range(parent); + for (auto it = range.first; it != range.second; it++) { + if (createEntityNode(world, it->second)) { + recurse(it->second); + ImGui::TreePop(); + } + } + }; + recurse(EntityID_Invalid); + } + ImGui::End(); +} + +bool EditorSystemOld::createEntityNode(World* world, EntityID entity) +{ + // HACK: Don't show the widget entities in the entity tree + if (entity == m_Widget) { + return false; + } + + ImVec2 pos = ImGui::GetCursorScreenPos(); + float width = ImGui::GetContentRegionAvailWidth(); + ImRect bb(pos + ImVec2(20, 0), pos + ImVec2(width, 13)); + auto window = ImGui::GetCurrentWindow(); + if (m_Selection == entity) { + const ImU32 col = window->Color(ImGuiCol_HeaderActive); + window->DrawList->AddRectFilled(bb.Min, bb.Max, col); + } + ImGuiID id = window->GetID((std::string("#SelectButton") + std::to_string(entity)).c_str()); + bool hovered = false; + bool held = false; + if (ImGui::ButtonBehavior(bb, id, &hovered, &held)) { + m_Selection = entity; + } + if (held) { + ImVec2 entityDragDelta = ImGui::GetMouseDragDelta(0); + if (std::abs(entityDragDelta.x) > 0 && std::abs(entityDragDelta.y) > 0) { + if (m_UIDraggingEntity == EntityID_Invalid) { + m_UIDraggingEntity = entity; + LOG_DEBUG("Started drag of entity %i", m_UIDraggingEntity); + } + ImGui::SetNextWindowPos(ImGui::GetIO().MousePos + ImVec2(20, 0)); + ImGui::Begin("Change parent", nullptr, ImVec2(0, 0), 0.3f, ImGuiWindowFlags_NoTitleBar|ImGuiWindowFlags_NoResize|ImGuiWindowFlags_NoMove|ImGuiWindowFlags_NoSavedSettings); + ImGui::Text("#%i", m_UIDraggingEntity); + ImGui::End(); + } + } + + ImGui::SetNextTreeNodeOpened(true, ImGuiSetCond_Once); + std::string nodeTitle; + const std::string& entityName = world->GetName(entity); + if (!entityName.empty()) { + nodeTitle = entityName; + } else { + nodeTitle = std::string("#") + std::to_string(entity); + } + if (ImGui::TreeNode(nodeTitle.c_str())) { + if (m_UIDraggingEntity != EntityID_Invalid && ImGui::IsItemHoveredRect() && ImGui::IsMouseReleased(0)) { + LOG_DEBUG("Changed parent of %i to %i", m_UIDraggingEntity, entity); + changeParent(m_UIDraggingEntity, entity); + m_UIDraggingEntity = EntityID_Invalid; + } + + if (ImGui::BeginPopupContextItem("item context menu")) { + if (ImGui::Button("Add")) { + EntityID newEntity = world->CreateEntity(entity); + world->AttachComponent(newEntity, "Transform"); + } + ImGui::SameLine(); + if (ImGui::Button("Delete")) { + world->DeleteEntity(entity); + ImGui::CloseCurrentPopup(); + if (!world->ValidEntity(m_Selection)) { + m_Selection = EntityID_Invalid; + } + } + ImGui::EndPopup(); + } + return true; + } else { + return false; + } +} + +bool EditorSystemOld::createDeleteButton(std::string componentType) +{ + float width = ImGui::GetContentRegionAvailWidth(); + ImGuiWindow* window = ImGui::GetCurrentWindow(); + auto pos = ImGui::GetCursorScreenPos() + ImVec2(width - 14.f, 1); + ImRect bb = ImRect(pos, pos + ImVec2(14.f, 14.f)); + std::string idString = "#DELETE"; + idString += componentType; + ImGuiID id = window->GetID(idString.c_str()); + bool hovered; + bool held; + bool pressed = ImGui::ButtonBehavior(bb, id, &hovered, &held); + //ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_CloseButtonHovered : ImGuiCol_CloseButton); + ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); + window->DrawList->AddCircleFilled(bb.GetCenter(), 7.f, col, 16); + return pressed; +} + +void EditorSystemOld::changeParent(EntityID entity, EntityID newParent) +{ + if (entity == newParent) { + return; + } + + // An entity can't be a child to one of its own children + auto children = m_World->GetEntityChildren().equal_range(entity); + for (auto it = children.first; it != children.second; it++) { + if (it->second == newParent) { + return; + } + } + + m_World->SetParent(entity, newParent); +} + +void EditorSystemOld::fileImport(World* world) +{ + m_CurrentFile = openDialog(m_DefaultEntityDir); + auto file = ResourceManager::Load(m_CurrentFile.string()); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(world); + EntityFileParser fp(file); + fp.MergeEntities(world); + createWidget(); + updateWidget(); +} + +void EditorSystemOld::fileSave(World* world) +{ + if (boost::filesystem::exists(m_CurrentFile)) { + // HACK: Delete the widgets so they don't appear in the saved file + world->DeleteEntity(m_Widget); + m_Widget = EntityID_Invalid; + + EntityFileWriter writer(m_CurrentFile.string()); + writer.WriteWorld(world); + + createWidget(); + } else { + fileSaveAs(world); + } +} + +void EditorSystemOld::fileSaveAs(World* world) +{ + auto filePath = saveDialog(m_DefaultEntityDir); + if (filePath.empty()) { + return; + } + + // HACK: Delete the widgets so they don't appear in the saved file + world->DeleteEntity(m_Widget); + m_Widget = EntityID_Invalid; + + EntityFileWriter writer(filePath.string()); + writer.WriteWorld(world); + + createWidget(); +} diff --git a/src/Engine/Editor/EditorUI.cpp b/src/Engine/Editor/EditorUI.cpp new file mode 100644 index 00000000..e69de29b diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index b0ca4afe..45dafa71 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -27,6 +27,7 @@ void DrawFinalPass::Draw(RenderScene& scene) GLERROR("DrawFinalPass::Draw: Pre"); DrawFinalPassState state; + m_ForwardPlusProgram->Bind(); GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); @@ -34,8 +35,8 @@ void DrawFinalPass::Draw(RenderScene& scene) glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 2, m_LightCullingPass->LightGridSSBO()); glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 4, m_LightCullingPass->LightIndexSSBO()); - glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ViewMatrix())); - glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ProjectionMatrix())); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); glUniform2f(glGetUniformLocation(shaderHandle, "ScreenDimensions"), m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); //TODO: Render: Add code for more jobs than modeljobs. diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 1cb9d7da..2cda4069 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -9,7 +9,6 @@ DrawFinalPassState::DrawFinalPassState() Enable(GL_DEPTH_TEST); Enable(GL_CULL_FACE); ClearColor(glm::vec4(200.f / 255, 0.f / 255, 200.f / 255, 0.f)); - Clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); } DrawFinalPassState::~DrawFinalPassState() diff --git a/src/Engine/Rendering/RenderState.cpp b/src/Engine/Rendering/RenderState.cpp index 4c47a8a2..1da2f0b1 100644 --- a/src/Engine/Rendering/RenderState.cpp +++ b/src/Engine/Rendering/RenderState.cpp @@ -44,12 +44,6 @@ bool RenderState::ClearColor(glm::vec4 color) return !GLERROR("RenderState::ClearColor"); } -bool RenderState::Clear(GLbitfield mask) -{ - glClear(mask); - return !GLERROR("RenderState::Clear"); -} - bool RenderState::BindFramebuffer(GLint framebuffer) { GLint originalRead; @@ -91,6 +85,15 @@ bool RenderState::BlendFunc(GLenum sfactor, GLenum dfactor) return !GLERROR("RenderState::BlendFunc"); } +bool RenderState::DepthMask(GLboolean flag) +{ + GLboolean original; + glGetBooleanv(GL_DEPTH_WRITEMASK, &original); + m_ResetFunctions.push_back(std::bind(glDepthMask, original)); + glDepthMask(flag); + return !GLERROR("RenderState::DepthMask"); +} + RenderState::~RenderState() { for (auto& f : m_ResetFunctions) { diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 38b80ea2..2af782e3 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -9,71 +9,26 @@ RenderSystem::RenderSystem(EventBroker* eventBroker, const IRenderer* renderer, EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &RenderSystem::OnInputCommand); m_Camera = new Camera((float)m_Renderer->Resolution().Width / m_Renderer->Resolution().Height, glm::radians(45.f), 0.01f, 5000.f); - m_DebugCameraInputController = new DebugCameraInputController(eventBroker, -1); } RenderSystem::~RenderSystem() { delete m_Camera; - delete m_DebugCameraInputController; } -bool RenderSystem::OnSetCamera(const Events::SetCamera &event) +bool RenderSystem::OnSetCamera(Events::SetCamera& e) { - auto cameras = m_World->GetComponents("Camera"); - - if (cameras != nullptr) { - for (auto it = cameras->begin(); it != cameras->end(); it++) { - if ((std::string)(*it)["Name"] == event.Name) { - switchCamera((*it).EntityID); - } - } - } + ComponentWrapper cTransform = e.CameraEntity["Transform"]; + ComponentWrapper cCamera = e.CameraEntity["Camera"]; + m_Camera->SetFOV((double)cCamera["FOV"]); + m_Camera->SetNearClip((double)cCamera["NearClip"]); + m_Camera->SetFarClip((double)cCamera["FarClip"]); + m_Camera->SetPosition(cTransform["Position"]); + m_Camera->SetOrientation(glm::quat((const glm::vec3&)cTransform["Orientation"])); + m_CurrentCamera = e.CameraEntity; return true; } -void RenderSystem::switchCamera(EntityID entity) -{ - if(m_World->HasComponent(entity, "Camera")) { - - if (m_CurrentCamera != EntityID_Invalid) { - if (m_World->HasComponent(m_CurrentCamera, "Model")) { - m_World->GetComponent(m_CurrentCamera, "Model")["Visible"] = true; - } - if (m_World->HasComponent(m_CurrentCamera, "Listener")) { - m_World->DeleteComponent(m_CurrentCamera, "Listener"); - } - } - - if (m_World->HasComponent(entity, "Model")) { - m_World->GetComponent(entity, "Model")["Visible"] = false; - } - if (!m_World->HasComponent(entity, "Listener")) { - m_World->AttachComponent(entity, "Listener"); - } - m_CurrentCamera = entity; - m_SwitchCamera = false; - - } else { - LOG_ERROR("Entity %i does not have a CameraComponent", entity); - m_SwitchCamera = false; - } -} - -void RenderSystem::updateProjectionMatrix(ComponentWrapper& cameraComponent) -{ - double fov = cameraComponent["FOV"]; - double aspectRatio = (float)m_Renderer->Resolution().Width / m_Renderer->Resolution().Height; - double nearClip = cameraComponent["NearClip"]; - double farClip = cameraComponent["FarClip"]; - - m_Camera->SetFOV(glm::radians(fov)); - m_Camera->SetAspectRatio(aspectRatio); - m_Camera->SetNearClip(nearClip); - m_Camera->SetFarClip(farClip); - m_Camera->UpdateProjectionMatrix(); -} - void RenderSystem::fillModels(std::list>& jobs, World* world) { auto models = world->GetComponents("Model"); @@ -113,7 +68,6 @@ void RenderSystem::fillModels(std::list>& jobs, World } } - void RenderSystem::fillLight(std::list>& jobs, World* world) { auto pointLights = world->GetComponents("PointLight"); @@ -138,12 +92,7 @@ void RenderSystem::fillLight(std::list>& jobs, World* bool RenderSystem::OnInputCommand(const Events::InputCommand& e) { - if (e.Command == "SwitchCamera" && e.Value > 0) { - m_SwitchCamera = true; - return true; - } else { - return false; - } + return false; } void RenderSystem::Update(World* world, double dt) @@ -151,10 +100,12 @@ void RenderSystem::Update(World* world, double dt) m_World = world; m_EventBroker->Process(); - updateCamera(world, dt); - + if (m_CurrentCamera) { + ComponentWrapper cameraTransform = m_CurrentCamera["Transform"]; + m_Camera->SetPosition(cameraTransform["Position"]); + m_Camera->SetOrientation(glm::quat((const glm::vec3&)cameraTransform["Orientation"])); + } //Only supports opaque geometry atm - m_RenderFrame->Clear(); RenderScene scene; scene.Camera = m_Camera; @@ -163,70 +114,4 @@ void RenderSystem::Update(World* world, double dt) fillLight(scene.PointLightJobs, world); m_RenderFrame->Add(scene); -} - -void RenderSystem::updateCamera(World* world, double dt) -{ - if (m_SwitchCamera) { - auto cameras = world->GetComponents("Camera"); - if (cameras == nullptr) { - return; - } - for (auto it = cameras->begin(); it != cameras->end(); it++) { - if ((*it).EntityID == m_CurrentCamera) { - it++; - if (it != cameras->end()) { - switchCamera((*it).EntityID); - } else { - switchCamera((*cameras->begin()).EntityID); - } - break; - } - } - if (m_World->HasComponent(m_CurrentCamera, "Camera")) { - ComponentWrapper& cameraComponent = world->GetComponent(m_CurrentCamera, "Camera"); - ComponentWrapper& cameraTransform = world->GetComponent(m_CurrentCamera, "Transform"); - - m_DebugCameraInputController->SetOrientation(glm::quat((glm::vec3)cameraTransform["Orientation"])); - m_DebugCameraInputController->SetPosition(cameraTransform["Position"]); - } - } - - if (m_World->ValidEntity(m_CurrentCamera)) { - if (world->HasComponent(m_CurrentCamera, "Camera") && world->HasComponent(m_CurrentCamera, "Transform")) { - ComponentWrapper& cameraComponent = world->GetComponent(m_CurrentCamera, "Camera"); - ComponentWrapper& cameraTransform = world->GetComponent(m_CurrentCamera, "Transform"); - - m_DebugCameraInputController->Update(dt); - (glm::vec3&)cameraTransform["Orientation"] = glm::eulerAngles(m_DebugCameraInputController->Orientation()); - (glm::vec3&)cameraTransform["Position"] = m_DebugCameraInputController->Position(); - - glm::vec3 position = Transform::AbsolutePosition(world, m_CurrentCamera); - glm::quat orientation = Transform::AbsoluteOrientation(world, m_CurrentCamera); - - m_Camera->SetPosition(position); - m_Camera->SetOrientation(orientation); - - updateProjectionMatrix(cameraComponent); - - } - } else { - m_Camera = m_Camera; - - auto cameras = world->GetComponents("Camera"); - if (cameras != nullptr) { - if (cameras->begin() != cameras->end()) { - ComponentWrapper& cameraC = *cameras->begin(); - switchCamera(cameraC.EntityID); - - ComponentWrapper& cameraComponent = world->GetComponent(m_CurrentCamera, "Camera"); - ComponentWrapper& cameraTransform = world->GetComponent(m_CurrentCamera, "Transform"); - - m_DebugCameraInputController->SetOrientation(glm::quat((glm::vec3)cameraTransform["Orientation"])); - m_DebugCameraInputController->SetPosition(cameraTransform["Position"]); - } - } - } - - m_Camera->UpdateViewMatrix(); } \ No newline at end of file diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 2f4c0ba2..e8ed1d9a 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -15,15 +15,6 @@ void Renderer::Initialize() m_UnitSphere = ResourceManager::Load("Models/Core/UnitSphere.obj"); m_ImGuiRenderPass = new ImGuiRenderPass(this, m_EventBroker); - - - // Create default camera - m_DefaultCamera = new ::Camera((float)m_Resolution.Width / m_Resolution.Height, glm::radians(45.f), 0.01f, 5000.f); - m_DefaultCamera->SetPosition(glm::vec3(0, 0, 10)); - if (m_Camera == nullptr) { - m_Camera = m_DefaultCamera; - } - } void Renderer::InitializeWindow() @@ -92,14 +83,14 @@ void Renderer::Update(double dt) void Renderer::Draw(RenderFrame& frame) { glClearColor(255.f / 255, 163.f / 255, 176.f / 255, 0.f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - m_PickingPass->ClearPicking(); for (auto scene : frame.RenderScenes){ + if (scene->ClearDepth) { + glClear(GL_DEPTH_BUFFER_BIT); + } - m_Camera = scene->Camera; // remove renderer camera when Editor uses the render scene cameras. FillDepth(*scene); m_PickingPass->Draw(*scene); m_LightCullingPass->GenerateNewFrustum(*scene); diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index ff1e28fd..5be95802 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -77,7 +77,6 @@ Game::Game(int argc, char* argv[]) unsigned int updateOrderLevel = 0; m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); - m_SystemPipeline->AddSystem(updateOrderLevel, m_Renderer); m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); @@ -91,6 +90,8 @@ Game::Game(int argc, char* argv[]) m_SystemPipeline->AddSystem(updateOrderLevel, m_OctreeCollision); ++updateOrderLevel; m_SystemPipeline->AddSystem(updateOrderLevel, m_Renderer, m_RenderFrame); + ++updateOrderLevel; + m_SystemPipeline->AddSystem(updateOrderLevel, m_Renderer, m_RenderFrame); // Invoke network if (m_Config->Get("Networking.StartNetwork", false)) { @@ -149,6 +150,7 @@ void Game::Tick() m_SoundSystem->Update(dt); GLERROR("Game::Tick m_RenderQueueFactory->Update"); m_Renderer->Draw(*m_RenderFrame); + m_RenderFrame->Clear(); GLERROR("Game::Tick m_Renderer->Draw"); m_EventBroker->Swap(); m_EventBroker->Clear(); From 0d50ede6f56208140caf73ce7f7c71e512dcc988 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 17 Jan 2016 07:34:20 +0100 Subject: [PATCH 060/224] Base work on reimplementing editor GUI --- include/Engine/Editor/EditorGUI.h | 65 +++++++++++++++ include/Engine/Editor/EditorSystem.h | 5 +- include/Engine/Editor/EditorUI.h | 8 -- resources/Schema/Entities/Test.xml | 3 +- resources/Schema/Types/Entity.xsd | 4 +- src/Engine/Editor/EditorGUI.cpp | 114 +++++++++++++++++++++++++++ src/Engine/Editor/EditorSystem.cpp | 13 ++- src/Engine/Editor/EditorUI.cpp | 0 8 files changed, 198 insertions(+), 14 deletions(-) create mode 100644 include/Engine/Editor/EditorGUI.h delete mode 100644 include/Engine/Editor/EditorUI.h create mode 100644 src/Engine/Editor/EditorGUI.cpp delete mode 100644 src/Engine/Editor/EditorUI.cpp diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h new file mode 100644 index 00000000..6c8b3499 --- /dev/null +++ b/include/Engine/Editor/EditorGUI.h @@ -0,0 +1,65 @@ +#ifndef EditorGUI_h__ +#define EditorGUI_h__ + +#include +#define IMGUI_DEFINE_MATH_OPERATORS +#include +#include +#include +#include "../Common.h" + +#include "../Core/EventBroker.h" +#include "../Core/World.h" +#include "../Core/EntityWrapper.h" + +class EditorGUI +{ +public: + EditorGUI(EventBroker* eventBroker) + : m_EventBroker(eventBroker) + { } + + void Draw(World* world); + + void SelectEntity(EntityWrapper entity); + + // Called when an entity is selected in the entity tree + typedef std::function OnEntitySelectedCallback_t; + void SetEntitySelectedCallback(OnEntitySelectedCallback_t f) { m_OnEntitySelected = f; } + // Called when the user means to import an entity file. + // Expects an EntityWrapper of the newly created entity in return. + typedef std::function OnEntityImport_t; + void SetEntityImportCallback(OnEntityImport_t f) { m_OnEntityImport = f; } + // Called when the user means to save an entity to file. + // Expects a bool indicating whether the save was successful or not in return. + typedef std::function OnEntitySave_t; + void SetEntitySaveCallback(OnEntitySave_t f) { m_OnEntitySave = f; } + // Called when the user means to create a new entity. + // @param EntityWrapper The parent of the entity to be created + // @return EntityWrapper The newly created entity + typedef std::function OnEntityCreate_t; + void SetEntityCreateCallback(OnEntityCreate_t f) { m_OnEntityCreate = f; } + // Called when the user means to delete an entity. + typedef std::function OnEntityDelete_t; + void SetEntityCreateCallback(OnEntityDelete_t f) { m_OnEntityDelete = f; } + +private: + EventBroker* m_EventBroker; + + // State variables + EntityWrapper m_CurrentSelection = EntityWrapper::Invalid; + + // Callbacks + OnEntitySelectedCallback_t m_OnEntitySelected = nullptr; + OnEntityImport_t m_OnEntityImport = nullptr; + OnEntitySave_t m_OnEntitySave = nullptr; + OnEntityCreate_t m_OnEntityCreate = nullptr; + OnEntityDelete_t m_OnEntityDelete = nullptr; + + void drawMenu(); + void drawEntities(World* world); + void drawEntitiesRecursive(World* world, EntityID parent); + bool drawEntityNode(EntityWrapper entity); +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index 43022009..7b908872 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -8,6 +8,7 @@ #include "../Core/ResourceManager.h" #include "../Core/EntityFilePreprocessor.h" #include "../Core/EntityFileParser.h" +#include "EditorGUI.h" class EditorSystem : public ImpureSystem { @@ -23,8 +24,10 @@ private: World* m_EditorWorld; SystemPipeline* m_EditorWorldSystemPipeline; Camera* m_EditorCamera; - EntityWrapper m_Widget = EntityWrapper::Invalid; EntityWrapper m_Camera = EntityWrapper::Invalid; DebugCameraInputController* m_DebugCameraInputController; + EditorGUI* m_EditorGUI; + + void OnEntitySelected(EntityWrapper entity); }; \ No newline at end of file diff --git a/include/Engine/Editor/EditorUI.h b/include/Engine/Editor/EditorUI.h deleted file mode 100644 index 18299865..00000000 --- a/include/Engine/Editor/EditorUI.h +++ /dev/null @@ -1,8 +0,0 @@ -#include -#include - -class EditorUI -{ -public: - EditorUI(); -}; \ No newline at end of file diff --git a/resources/Schema/Entities/Test.xml b/resources/Schema/Entities/Test.xml index 5f57dbb7..42e2660e 100644 --- a/resources/Schema/Entities/Test.xml +++ b/resources/Schema/Entities/Test.xml @@ -13,7 +13,7 @@ - + @@ -23,5 +23,6 @@ + diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 47c4d614..3b0a1c88 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -38,9 +38,7 @@ - - - + diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp new file mode 100644 index 00000000..66896474 --- /dev/null +++ b/src/Engine/Editor/EditorGUI.cpp @@ -0,0 +1,114 @@ +#include "Editor/EditorGUI.h" + +void EditorGUI::Draw(World* world) +{ + drawMenu(); + drawEntities(world); +} + +void EditorGUI::SelectEntity(EntityWrapper entity) +{ + m_CurrentSelection = entity; + if (m_OnEntitySelected != nullptr) { + m_OnEntitySelected(entity); + } +} + +void EditorGUI::drawMenu() +{ + +} + +void EditorGUI::drawEntities(World* world) +{ + if (!ImGui::Begin("Entities")) { + return; + } + + drawEntitiesRecursive(world, EntityID_Invalid); + + ImGui::End(); +} + +void EditorGUI::drawEntitiesRecursive(World* world, EntityID parent) +{ + auto entityChildren = world->GetEntityChildren(); + auto range = entityChildren.equal_range(parent); + for (auto it = range.first; it != range.second; it++) { + if (EditorGUI::drawEntityNode(EntityWrapper(world, it->second))) { + drawEntitiesRecursive(world, it->second); + ImGui::TreePop(); + } + } +} + +bool EditorGUI::drawEntityNode(EntityWrapper entity) +{ + ImVec2 pos = ImGui::GetCursorScreenPos(); + float width = ImGui::GetContentRegionAvailWidth(); + ImRect bb(pos + ImVec2(20, 0), pos + ImVec2(width, 13)); + auto window = ImGui::GetCurrentWindow(); + if (m_CurrentSelection == entity) { + const ImU32 col = window->Color(ImGuiCol_HeaderActive); + window->DrawList->AddRectFilled(bb.Min, bb.Max, col); + } + ImGuiID id = window->GetID((std::string("#SelectButton") + std::to_string(entity)).c_str()); + bool hovered = false; + bool held = false; + if (ImGui::ButtonBehavior(bb, id, &hovered, &held)) { + SelectEntity(entity); + } + //if (held) { + // ImVec2 entityDragDelta = ImGui::GetMouseDragDelta(0); + // if (std::abs(entityDragDelta.x) > 0 && std::abs(entityDragDelta.y) > 0) { + // if (m_UIDraggingEntity == EntityID_Invalid) { + // m_UIDraggingEntity = entity; + // LOG_DEBUG("Started drag of entity %i", m_UIDraggingEntity); + // } + // ImGui::SetNextWindowPos(ImGui::GetIO().MousePos + ImVec2(20, 0)); + // ImGui::Begin("Change parent", nullptr, ImVec2(0, 0), 0.3f, ImGuiWindowFlags_NoTitleBar|ImGuiWindowFlags_NoResize|ImGuiWindowFlags_NoMove|ImGuiWindowFlags_NoSavedSettings); + // ImGui::Text("#%i", m_UIDraggingEntity); + // ImGui::End(); + // } + //} + + ImGui::SetNextTreeNodeOpened(true, ImGuiSetCond_Once); + std::string nodeTitle; + const std::string& entityName = entity.World->GetName(entity); + if (!entityName.empty()) { + nodeTitle = entityName; + } else { + nodeTitle = std::string("#") + std::to_string(entity.ID); + } + if (ImGui::TreeNode(nodeTitle.c_str())) { + //if (m_UIDraggingEntity != EntityID_Invalid && ImGui::IsItemHoveredRect() && ImGui::IsMouseReleased(0)) { + // LOG_DEBUG("Changed parent of %i to %i", m_UIDraggingEntity, entity); + // changeParent(m_UIDraggingEntity, entity); + // m_UIDraggingEntity = EntityID_Invalid; + //} + + if (ImGui::BeginPopupContextItem("item context menu")) { + if (ImGui::Button("Add")) { + if (m_OnEntityCreate != nullptr) { + EntityWrapper newEntity = m_OnEntityCreate(EntityWrapper(entity.World, EntityID_Invalid)); + ImGui::CloseCurrentPopup(); + SelectEntity(newEntity); + } + } + ImGui::SameLine(); + if (ImGui::Button("Delete")) { + if (m_OnEntityDelete != nullptr) { + m_OnEntityDelete(entity); + ImGui::CloseCurrentPopup(); + } + if (!m_CurrentSelection.Valid()) { + SelectEntity(EntityWrapper::Invalid); + } + } + ImGui::EndPopup(); + } + return true; + } else { + return false; + } +} diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index ec385e9b..2d0a4b55 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -24,6 +24,9 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render m_EditorWorld->AttachComponent(m_Camera.ID, "Camera"); m_DebugCameraInputController = new DebugCameraInputController(m_EventBroker, -1); + m_EditorGUI = new EditorGUI(m_EventBroker); + m_EditorGUI->SetEntitySelectedCallback(std::bind(&EditorSystem::OnEntitySelected, this, std::placeholders::_1)); + Events::SetCamera e; e.CameraEntity = m_Camera; m_EventBroker->Publish(e); @@ -31,6 +34,7 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render EditorSystem::~EditorSystem() { + delete m_EditorGUI; delete m_DebugCameraInputController; delete m_EditorWorldSystemPipeline; delete m_EditorWorld; @@ -40,7 +44,14 @@ void EditorSystem::Update(World* world, double dt) { m_EditorWorldSystemPipeline->Update(m_EditorWorld, dt); + m_EditorGUI->Draw(world); + m_DebugCameraInputController->Update(dt); m_Camera["Transform"]["Position"] = m_DebugCameraInputController->Position(); m_Camera["Transform"]["Orientation"] = glm::eulerAngles(m_DebugCameraInputController->Orientation()); -} \ No newline at end of file +} + +void EditorSystem::OnEntitySelected(EntityWrapper entity) +{ + m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(entity.World, entity.ID); +} diff --git a/src/Engine/Editor/EditorUI.cpp b/src/Engine/Editor/EditorUI.cpp deleted file mode 100644 index e69de29b..00000000 From e39e4064f2c89dd0fb70f1d006dc6d7a6aabcf21 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 17 Jan 2016 23:06:32 +0100 Subject: [PATCH 061/224] Entity tree button mockup --- src/Engine/Editor/EditorGUI.cpp | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 66896474..408a3cbf 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -2,6 +2,7 @@ void EditorGUI::Draw(World* world) { + ImGui::ShowTestWindow(); drawMenu(); drawEntities(world); } @@ -25,6 +26,15 @@ void EditorGUI::drawEntities(World* world) return; } + float buttonWidth = (ImGui::GetContentRegionAvailWidth() - 10.f) / 3.f ; + ImGui::Button("Create", ImVec2(buttonWidth, 0)); + ImGui::SameLine(0.f, 5.f); + ImGui::Button("Import", ImVec2(buttonWidth, 0)); + ImGui::SameLine(0.f, 5.f); + ImGui::Button("Reference", ImVec2(buttonWidth, 0)); + + ImGui::ItemSize(ImVec2(0, 3)); + drawEntitiesRecursive(world, EntityID_Invalid); ImGui::End(); @@ -46,13 +56,13 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) { ImVec2 pos = ImGui::GetCursorScreenPos(); float width = ImGui::GetContentRegionAvailWidth(); - ImRect bb(pos + ImVec2(20, 0), pos + ImVec2(width, 13)); + ImRect bb(pos + ImVec2(20, 0), pos + ImVec2(width, 14)); auto window = ImGui::GetCurrentWindow(); if (m_CurrentSelection == entity) { const ImU32 col = window->Color(ImGuiCol_HeaderActive); window->DrawList->AddRectFilled(bb.Min, bb.Max, col); } - ImGuiID id = window->GetID((std::string("#SelectButton") + std::to_string(entity)).c_str()); + ImGuiID id = window->GetID((std::string("#SelectButton") + std::to_string(entity.ID)).c_str()); bool hovered = false; bool held = false; if (ImGui::ButtonBehavior(bb, id, &hovered, &held)) { From d995713d3b4e1e4216e9d462081a0ab2d1375b36 Mon Sep 17 00:00:00 2001 From: Jocke Date: Mon, 18 Jan 2016 11:05:32 +0100 Subject: [PATCH 062/224] Added input queue to Client and Input Listener debug code in server. --- assets | 2 +- include/Engine/Network/Client.h | 2 ++ include/Engine/Network/Server.h | 4 ++++ src/Engine/Network/Client.cpp | 27 +++++++++++++++------- src/Engine/Network/Server.cpp | 40 ++++++++++++++++++++++++++------- 5 files changed, 58 insertions(+), 17 deletions(-) diff --git a/assets b/assets index 6cbf2365..a3c92ac8 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 6cbf2365d49e6280750ea3bcd0f9c271779e6f15 +Subproject commit a3c92ac876dd061776c36d1594bd82264372f028 diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 81b2b834..7aa20126 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -57,6 +57,7 @@ private: SnapshotDefinitions m_NextSnapshot; double m_DurationOfPingTime; std::clock_t m_StartPingTime; + std::vector m_InputCommandBuffer; // Private member functions void readFromServer(); @@ -75,6 +76,7 @@ private: void identifyPacketLoss(); bool isConnected(); EntityID createPlayer(); + void sendInputCommands(); // Mapping Logic // Returns if local EntityID exist in map bool clientServerMapsHasEntity(EntityID clientEntityID); diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 4c71be95..9aba921a 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -73,6 +73,10 @@ private: void parseServerPing(); void identifyPacketLoss(); EntityID createPlayer(); + // Debug event + + EventRelay m_EInputCommand; + bool OnInputCommand(const Events::InputCommand& e); }; #endif diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 55292234..e07bcf7a 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -25,6 +25,7 @@ void Client::Start(World* world, EventBroker* eventBroker) // Subscribe to events EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Client::OnInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_EPlayeDamage, &Client::OnPlayerDamage); m_Socket.connect(m_ReceiverEndpoint); LOG_INFO("I am client. BIP BOP"); @@ -44,6 +45,7 @@ void Client::readFromServer() parseMessageType(packet); } } + sendInputCommands(); } void Client::parseMessageType(Packet& packet) @@ -92,7 +94,7 @@ void Client::parseConnect(Packet& packet) } void Client::parsePlayerConnected(Packet & packet) -{ +{ // Map ServerEntityID and other player's PlayerID LOG_INFO("A Player connected"); } @@ -235,12 +237,8 @@ bool Client::OnInputCommand(const Events::InputCommand & e) LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } else { - Packet packet(MessageType::OnInputCommand, m_SendPacketID); - packet.WriteString(e.Command); - packet.WritePrimitive(e.PlayerID); - packet.WritePrimitive(e.Value); - send(packet); - LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + m_InputCommandBuffer.push_back(e); + LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } return false; @@ -285,6 +283,19 @@ EntityID Client::createPlayer() return entityID; } +void Client::sendInputCommands() +{ + if (m_InputCommandBuffer.size() > 0) { + Packet packet(MessageType::OnInputCommand, m_SendPacketID); + for (int i = 0; i < m_InputCommandBuffer.size(); i++) { + packet.WriteString(m_InputCommandBuffer[i].Command); + packet.WritePrimitive(m_InputCommandBuffer[i].Value); + } + send(packet); + m_InputCommandBuffer.clear(); + } +} + bool Client::clientServerMapsHasEntity(EntityID clientEntityID) { return m_ClientIDToServerID.find(clientEntityID) != m_ClientIDToServerID.end(); @@ -296,7 +307,7 @@ bool Client::serverClientMapsHasEntity(EntityID serverEntityID) } void Client::insertIntoServerClientMaps(EntityID serverEntityID, EntityID clientEntityID) -{ +{ m_ServerIDToClientID.insert(std::make_pair(serverEntityID, clientEntityID)); m_ClientIDToServerID.insert(std::make_pair(clientEntityID, serverEntityID)); diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 5ec674d0..2563d9b1 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -13,6 +13,8 @@ void Server::Start(World* world, EventBroker* eventBroker) { m_World = world; m_EventBroker = eventBroker; + // Subscribe to events + EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Server::OnInputCommand); for (size_t i = 0; i < MAXCONNECTIONS; i++) { m_StopTimes[i] = std::clock(); } @@ -22,6 +24,7 @@ void Server::Start(World* world, EventBroker* eventBroker) void Server::Update() { readFromClients(); + m_EventBroker->Process(); } void Server::readFromClients() @@ -206,12 +209,26 @@ void Server::disconnect(int i) void Server::parseOnInputCommand(Packet& packet) { - Events::InputCommand e; - e.Command = packet.ReadString(); - e.PlayerID = packet.ReadPrimitive(); - e.Value = packet.ReadPrimitive(); - m_EventBroker->Publish(e); - LOG_DEBUG("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + int playerID = -1; + // Check which player it was who sent the message + for (int i = 0; i < MAXCONNECTIONS; i++) { + // if the player is connected set playerID to the correct PlayerID + if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() + && m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { + playerID = i; + break; + } + } + if (playerID != -1) { + while (packet.DataReadSize() < packet.Size()) { + Events::InputCommand e; + e.Command = packet.ReadString(); + e.PlayerID = playerID; // Set correct player id + e.Value = packet.ReadPrimitive(); + m_EventBroker->Publish(e); + LOG_DEBUG("Server::parseOnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + } + } } void Server::parseOnPlayerDamage(Packet & packet) @@ -221,7 +238,7 @@ void Server::parseOnPlayerDamage(Packet & packet) e.PlayerDamagedID = packet.ReadPrimitive(); e.TypeOfDamage = packet.ReadString(); m_EventBroker->Publish(e); - LOG_DEBUG("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str()); + LOG_DEBUG("Server::parseOnPlayerDamage: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str()); } void Server::parseConnect(Packet& packet) @@ -229,7 +246,8 @@ void Server::parseConnect(Packet& packet) LOG_INFO("Parsing connections"); // Check if player is already connected for (int i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address()) { + if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() && + m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { return; } } @@ -311,3 +329,9 @@ EntityID Server::createPlayer() ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); return entityID; } + +bool Server::OnInputCommand(const Events::InputCommand & e) +{ + LOG_INFO("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + return true; +} From 6ba6deb863476e523d194c46e47b29b67b66163a Mon Sep 17 00:00:00 2001 From: Jocke Date: Mon, 18 Jan 2016 11:35:35 +0100 Subject: [PATCH 063/224] Removed some debug spam. --- src/Engine/Network/Client.cpp | 4 ++-- src/Engine/Network/Server.cpp | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index e07bcf7a..d6e8f4c5 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -234,11 +234,11 @@ bool Client::OnInputCommand(const Events::InputCommand & e) { if (e.Command == "ConnectToServer") { // Connect for now connect(); - LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + //LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } else { m_InputCommandBuffer.push_back(e); - LOG_INFO("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + //LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } return false; diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 2563d9b1..422d6523 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -226,7 +226,7 @@ void Server::parseOnInputCommand(Packet& packet) e.PlayerID = playerID; // Set correct player id e.Value = packet.ReadPrimitive(); m_EventBroker->Publish(e); - LOG_DEBUG("Server::parseOnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + LOG_INFO("Server::parseOnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); } } } @@ -332,6 +332,6 @@ EntityID Server::createPlayer() bool Server::OnInputCommand(const Events::InputCommand & e) { - LOG_INFO("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + //LOG_INFO("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } From 504f301e4d8f483092ec9b5d27bd38dfa08463f0 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 13:46:42 +0100 Subject: [PATCH 064/224] Added refactored property sheet for components --- include/Engine/Editor/EditorGUI.h | 18 +++ src/Engine/Editor/EditorGUI.cpp | 208 ++++++++++++++++++++++++++++++ 2 files changed, 226 insertions(+) diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 6c8b3499..77218e9d 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -7,6 +7,8 @@ #include #include #include "../Common.h" +#include "../GLM.h" +#include #include "../Core/EventBroker.h" #include "../Core/World.h" @@ -42,6 +44,10 @@ public: // Called when the user means to delete an entity. typedef std::function OnEntityDelete_t; void SetEntityCreateCallback(OnEntityDelete_t f) { m_OnEntityDelete = f; } + // Called when the user means to attach a new component to an entity. + typedef std::function OnComponentAttach_t; + void SetComponentAttachCallback(OnComponentAttach_t f) { m_OnComponentAttach = f; } + private: EventBroker* m_EventBroker; @@ -55,11 +61,23 @@ private: OnEntitySave_t m_OnEntitySave = nullptr; OnEntityCreate_t m_OnEntityCreate = nullptr; OnEntityDelete_t m_OnEntityDelete = nullptr; + OnComponentAttach_t m_OnComponentAttach = nullptr; void drawMenu(); void drawEntities(World* world); void drawEntitiesRecursive(World* world, EntityID parent); bool drawEntityNode(EntityWrapper entity); + void drawComponents(EntityWrapper entity); + bool drawComponentNode(EntityWrapper entity, const ComponentInfo& componentType); + void drawComponentField(ComponentWrapper& c, const ComponentInfo::Field_t& field); + void drawComponentField_Vector(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawComponentField_Color(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawComponentField_int(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawComponentField_enum(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawComponentField_float(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field); }; #endif \ No newline at end of file diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 408a3cbf..388016a6 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -5,6 +5,7 @@ void EditorGUI::Draw(World* world) ImGui::ShowTestWindow(); drawMenu(); drawEntities(world); + drawComponents(m_CurrentSelection); } void EditorGUI::SelectEntity(EntityWrapper entity) @@ -122,3 +123,210 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) return false; } } + +void EditorGUI::drawComponents(EntityWrapper entity) +{ + std::stringstream title; + title << "Components"; + if (entity.Valid()) { + title << " #" << entity.ID << "###Components"; + } + if (!ImGui::Begin(title.str().c_str())) { + ImGui::End(); + return; + } + + if (!entity.Valid()) { + ImGui::End(); + return; + } + + auto& pools = entity.World->GetComponentPools(); + // Create list of component types available to be added + std::vector componentTypes; + for (auto& pair : pools) { + // Don't list components the entity already has attached + if (!entity.HasComponent(pair.first)) { + componentTypes.push_back(pair.first.c_str()); + } + } + // Draw combo box + ImGui::PushItemWidth(ImGui::GetContentRegionAvailWidth() - 10.f); + int selectedItem = -1; + if (ImGui::Combo("", &selectedItem, componentTypes.data(), componentTypes.size())) { + if (selectedItem != -1) { + if (m_OnComponentAttach != nullptr) { + std::string chosenComponentType(componentTypes.at(selectedItem)); + m_OnComponentAttach(entity, chosenComponentType); + } + } + } + ImGui::PopItemWidth(); + + for (auto& pair : pools) { + const std::string& componentType = pair.first; + auto pool = pair.second; + // Don't show components the entity doesn't have attached + if (!entity.HasComponent(componentType)) { + continue; + } + // TODO: Add delete button here + drawComponent(entity, pool->ComponentInfo()); + } + + ImGui::End(); +} + +bool EditorGUI::drawComponent(EntityWrapper entity, const ComponentInfo& ci) +{ + if (!ImGui::CollapsingHeader(ci.Name.c_str(), nullptr, true, true)) { + return false; + } + + // Show component annotation + const std::string annotation = ci.Meta->Annotation; + if (!annotation.empty()) { + ImGui::TextWrapped(annotation.c_str()); + } + + // Draw component fields + ComponentWrapper& component = entity.World->GetComponent(entity.ID, ci.Name); + for (auto& kv : ci.Fields) { + const std::string& fieldName = kv.first; + const ComponentInfo::Field_t& field = kv.second; + + // Draw the field widget based on its type + drawComponentField(component, field); + ImGui::SameLine(); + // Draw field name + ImGui::Text(fieldName.c_str()); + // Draw potential field annotation + auto fieldAnnotationIt = ci.Meta->FieldAnnotations.find(fieldName); + if (fieldAnnotationIt != ci.Meta->FieldAnnotations.end()) { + ImGui::SameLine(); + ImGui::TextDisabled("(?)"); + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip(fieldAnnotationIt->second.c_str()); + } + } + } + + return true; +} + +void EditorGUI::drawComponentField(ComponentWrapper& c, const ComponentInfo::Field_t& field) +{ + // Push an unique widget id so different components with fields with equal names are still counted as different + ImGui::PushID((c.Info.Name + field.Name).c_str()); + + if (field.Type == "Vector") { + drawComponentField_Vector(c, field); + } else if (field.Type == "Color") { + drawComponentField_Color(c, field); + //} else if (field.Type == "Quaternion") { + } else if (field.Type == "int") { + drawComponentField_int(c, field); + } else if (field.Type == "enum") { + drawComponentField_enum(c, field); + } else if (field.Type == "float") { + drawComponentField_float(c, field); + } else if (field.Type == "double") { + drawComponentField_double(c, field); + } else if (field.Type == "bool") { + drawComponentField_bool(c, field); + } else if (field.Type == "string") { + drawComponentField_string(c, field); + } else { + ImGui::TextDisabled(field.Type.c_str()); + } + + ImGui::PopID(); +} + +void EditorGUI::drawComponentField_Vector(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + auto& val = c.Field(field.Name); + if (field.Name == "Scale") { + // Limit scale values to a minimum of 0 + ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, 0.f, std::numeric_limits::max()); + } else if (field.Name == "Orientation") { + // Make orentations have a period of 2*Pi + glm::vec3 tempVal = glm::fmod(val, glm::vec3(glm::two_pi())); + if (ImGui::SliderFloat3("", glm::value_ptr(tempVal), 0.f, glm::two_pi())) { + val = tempVal; + } + } else { + ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, std::numeric_limits::lowest(), std::numeric_limits::max()); + } +} + +void EditorGUI::drawComponentField_Color(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + auto& val = c.Field(field.Name); + ImGui::ColorEdit4("", glm::value_ptr(val), true); +} + +void EditorGUI::drawComponentField_int(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + auto& val = c.Field(field.Name); + ImGui::InputInt("", &val); +} + +void EditorGUI::drawComponentField_enum(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + auto fieldEnumDefIt = c.Info.Meta->FieldEnumDefinitions.find(field.Name); + if (fieldEnumDefIt == c.Info.Meta->FieldEnumDefinitions.end()) { + drawComponentField_int(c, field); + return; + } + + auto& val = c.Field(field.Name); + int selectedItem = -1; + std::stringstream enumKeys; + std::vector enumValues; + int i = 0; + for (auto& kv : fieldEnumDefIt->second) { + enumKeys << kv.first << " (" << kv.second << ")" << '\0'; + enumValues.push_back(kv.second); + if (val == kv.second) { + selectedItem = i; + } + } + if (ImGui::Combo("", &selectedItem, enumKeys.str().c_str())) { + val = enumValues.at(selectedItem); + } +} + +void EditorGUI::drawComponentField_float(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + auto& val = c.Field(field.Name); + ImGui::InputFloat("", &val, 0.01f, 1.f); +} + +void EditorGUI::drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + float tempVal = static_cast(c.Field(field.Name)); + if (ImGui::InputFloat("", &tempVal, 0.01f, 1.f)) { + c.SetField(field.Name, static_cast(tempVal)); + } +} + +void EditorGUI::drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + auto& val = c.Field(field.Name); + ImGui::Checkbox("", &val); +} + +void EditorGUI::drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field) +{ + auto& val = c.Field(field.Name); + char tempString[1024]; // Let's just hope this is an sufficiently large buffer for strings :) + tempString[1023] = '\0'; // Null terminator just in case the string is larger than the buffer + // Copy the string into the buffer, taking the null terminator into account + memcpy(tempString, val.c_str(), std::min(val.length() + 1, sizeof(tempString) - 1)); + if (ImGui::InputText("", tempString, sizeof(tempString))) { + val = std::string(tempString); + } + // TODO: Handle drag and drop of files +} + From 4092f6b4d4ee2cd530f5e76751c7e72d74e6635b Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 14:20:28 +0100 Subject: [PATCH 065/224] New Lightstruct working. --- assets | 2 +- include/Engine/Rendering/LightCullingPass.h | 7 ++--- resources/Shaders/CullLights.comp.glsl | 29 ++++++++++++--------- resources/Shaders/ForwardPlus.frag.glsl | 17 ++++++------ src/Engine/Rendering/LightCullingPass.cpp | 17 ++++++------ 5 files changed, 39 insertions(+), 33 deletions(-) diff --git a/assets b/assets index 6cbf2365..2fca9181 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 6cbf2365d49e6280750ea3bcd0f9c271779e6f15 +Subproject commit 2fca918162535c859c6adbe433e69fad8ea931b6 diff --git a/include/Engine/Rendering/LightCullingPass.h b/include/Engine/Rendering/LightCullingPass.h index 2fc1cbfc..954444da 100644 --- a/include/Engine/Rendering/LightCullingPass.h +++ b/include/Engine/Rendering/LightCullingPass.h @@ -56,15 +56,16 @@ private: Frustum* m_Frustums; //This should be a component - struct PointLight { + struct LightSource { glm::vec4 Position = glm::vec4(0.f); + glm::vec4 Direction = glm::vec4(0.f); glm::vec4 Color = glm::vec4(1.f); float Radius = 5.f; float Intensity = 0.8f; float Falloff = 0.3f; - float Padding = 1337; + enum Type_t { Point, Directional, Spot } Type; }; - std::vector m_PointLights; + std::vector m_LightSources; struct LightGrid { float Start; diff --git a/resources/Shaders/CullLights.comp.glsl b/resources/Shaders/CullLights.comp.glsl index c2675f20..f2908ecc 100644 --- a/resources/Shaders/CullLights.comp.glsl +++ b/resources/Shaders/CullLights.comp.glsl @@ -27,19 +27,20 @@ layout (std430, binding = 0) buffer FrustumBuffer Frustum Data[]; } Frustums; -struct PointLight { +struct LightSource { vec4 Position; + vec4 Direction; vec4 Color; float Radius; float Intensity; float Falloff; - float Padding; + int Type; }; layout (std430, binding = 1) buffer LightBuffer { - PointLight List[]; -} PointLights; + LightSource List[]; +} LightSources; struct LightGrid { float Start; @@ -106,8 +107,7 @@ layout (local_size_x = 16, local_size_y = 16, local_size_z = 1) in; void main () { GroupIndex = int(gl_WorkGroupID.x + (gl_WorkGroupID.y * int(ScreenDimensions.x/TILE_SIZE))); - if(gl_LocalInvocationIndex == 0) - { + if(gl_LocalInvocationIndex == 0) { GroupLightCount = 0; GroupFrustum = Frustums.Data[GroupIndex]; } @@ -115,22 +115,25 @@ void main () barrier(); memoryBarrierShared(); - for(int i = int(gl_LocalInvocationIndex); i < PointLights.List.length(); i += TILE_SIZE*TILE_SIZE) - { - PointLight light = PointLights.List[i]; + for(int i = int(gl_LocalInvocationIndex); i < LightSources.List.length(); i += TILE_SIZE*TILE_SIZE) { + LightSource light = LightSources.List[i]; //if pointlight //Pos i view antagligen - if(SphereInsideFrustrum( vec3(V * light.Position), light.Radius, GroupFrustum)) - { - //TODO: Fix transparent and opaque list, and depth test. - AppendLight( i ); + if(light.Type == 0) { + if(SphereInsideFrustrum( vec3(V * light.Position), light.Radius, GroupFrustum)) { + //TODO: Fix transparent and opaque list, and depth test. + AppendLight( i ); + } } //if conelight //if directional + if(light.Type == 1) { + AppendLight( i ); + } } diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 3d5b9bfd..713e3621 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -9,19 +9,20 @@ uniform sampler2D texture0; #define TILE_SIZE 16 -struct PointLight { +struct LightSource { vec4 Position; + vec4 Direction; vec4 Color; float Radius; float Intensity; float Falloff; - float Padding; + int Type; }; layout (std430, binding = 1) buffer LightBuffer { - PointLight List[]; -} PointLights; + LightSource List[]; +} LightSources; struct LightGrid { float Start; @@ -71,7 +72,7 @@ vec4 CalcDiffuse(vec4 lightColor, vec4 lightVec, vec4 normal) { return lightColor * power; } -LightResult CalcPointLight(vec4 lightPos, float lightRadius, vec4 lightColor, float intensity, vec4 viewVec, vec4 position, vec4 normal, float falloff) +LightResult CalcLightSource(vec4 lightPos, float lightRadius, vec4 lightColor, float intensity, vec4 viewVec, vec4 position, vec4 normal, float falloff) { vec4 L = lightPos - position; float dist = length(L); @@ -108,15 +109,15 @@ void main() { int l = int(LightIndex[i]); - LightResult result = CalcPointLight(V * PointLights.List[l].Position, PointLights.List[l].Radius, PointLights.List[l].Color, PointLights.List[l].Intensity, viewVec, position, normal, PointLights.List[i].Falloff); + LightResult result = CalcLightSource(V * LightSources.List[l].Position, LightSources.List[l].Radius, LightSources.List[l].Color, LightSources.List[l].Intensity, viewVec, position, normal, LightSources.List[i].Falloff); totalLighting.Diffuse += result.Diffuse; totalLighting.Specular += result.Specular; } - fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; - //fragmentColor += vec4(0.0, LightGrids.Data[currentTile].Amount/3.0, 0, 1); + fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3.0, 0, 1); //fragmentColor = texel * Input.DiffuseColor * Color; if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { diff --git a/src/Engine/Rendering/LightCullingPass.cpp b/src/Engine/Rendering/LightCullingPass.cpp index e59a50c0..d9cc8249 100644 --- a/src/Engine/Rendering/LightCullingPass.cpp +++ b/src/Engine/Rendering/LightCullingPass.cpp @@ -59,8 +59,8 @@ void LightCullingPass::CullLights(RenderScene& scene) glBindBuffer(GL_SHADER_STORAGE_BUFFER, m_LightOffsetSSBO); glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(m_LightOffset), &m_LightOffset, GL_DYNAMIC_COPY); glBindBuffer(GL_SHADER_STORAGE_BUFFER, m_LightSSBO); - if (m_PointLights.size() > 0) { - glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(PointLight) * m_PointLights.size(), &(m_PointLights[0]), GL_DYNAMIC_COPY); + if (m_LightSources.size() > 0) { + glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(LightSource) * m_LightSources.size(), &(m_LightSources[0]), GL_DYNAMIC_COPY); } else { GLfloat zero = 0.f; glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(GLfloat), &zero , GL_DYNAMIC_COPY); @@ -82,19 +82,20 @@ void LightCullingPass::CullLights(RenderScene& scene) void LightCullingPass::FillLightList(RenderScene& scene) { - m_PointLights.clear(); + m_LightSources.clear(); for(auto &job : scene.PointLightJobs) { auto pointLightjob = std::dynamic_pointer_cast(job); if (pointLightjob) { - PointLight p; + LightSource p; p.Color = pointLightjob->Color; p.Falloff = pointLightjob->Falloff; p.Intensity = pointLightjob->Intensity; p.Position = glm::vec4(glm::vec3(pointLightjob->Position), 1.f); p.Radius = pointLightjob->Radius; - p.Padding = 123.f; - m_PointLights.push_back(p); + //p.Padding = 123.f; + p.Type = LightSource::Point; + m_LightSources.push_back(p); continue; } } @@ -110,8 +111,8 @@ void LightCullingPass::InitializeSSBOs() glGenBuffers(1, &m_LightSSBO); glBindBuffer(GL_SHADER_STORAGE_BUFFER, m_LightSSBO); - if(m_PointLights.size() > 0) { - glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(PointLight) * m_PointLights.size(), &(m_PointLights[0]), GL_DYNAMIC_COPY); + if(m_LightSources.size() > 0) { + glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(LightSource) * m_LightSources.size(), &(m_LightSources[0]), GL_DYNAMIC_COPY); } glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0); GLERROR("m_LightSSBO"); From 6680f6863f079dcbf95934a65a897e40b814777e Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 14:30:22 +0100 Subject: [PATCH 066/224] DirectionalLight component added. --- .../Schema/Components/DirectionalLight.xml | 5 +++++ .../Schema/Components/DirectionalLight.xsd | 19 +++++++++++++++++++ 2 files changed, 24 insertions(+) create mode 100644 resources/Schema/Components/DirectionalLight.xml create mode 100644 resources/Schema/Components/DirectionalLight.xsd diff --git a/resources/Schema/Components/DirectionalLight.xml b/resources/Schema/Components/DirectionalLight.xml new file mode 100644 index 00000000..a14697c8 --- /dev/null +++ b/resources/Schema/Components/DirectionalLight.xml @@ -0,0 +1,5 @@ + + + 0.8 + true + \ No newline at end of file diff --git a/resources/Schema/Components/DirectionalLight.xsd b/resources/Schema/Components/DirectionalLight.xsd new file mode 100644 index 00000000..b4d96d18 --- /dev/null +++ b/resources/Schema/Components/DirectionalLight.xsd @@ -0,0 +1,19 @@ + + + + + + + + A directional light that shines bright like the future. + + + + + + + + + + + \ No newline at end of file From 6f1fd19ac70859bb26ff0dcd51d21abab7a91179 Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 14:30:28 +0100 Subject: [PATCH 067/224] Directional lights now being filled into m_LightSources --- src/Engine/Rendering/LightCullingPass.cpp | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/src/Engine/Rendering/LightCullingPass.cpp b/src/Engine/Rendering/LightCullingPass.cpp index d9cc8249..76f2045f 100644 --- a/src/Engine/Rendering/LightCullingPass.cpp +++ b/src/Engine/Rendering/LightCullingPass.cpp @@ -99,6 +99,18 @@ void LightCullingPass::FillLightList(RenderScene& scene) continue; } } + for(auto &job : scene.DirectionalLightJobs) { + auto directionalLightJob = std::dynamic_pointer_cast(job); + if(directionalLightJob) { + LightSource p; + p.Color = directionalLightJob->Color; + p.Intensity = directionalLightJob->Intensity; + p.Position = glm::vec4(glm::vec3(directionalLightJob->Position), 1.f); + p.Type = LightSource::Directional; + m_LightSources.push_back(p); + continue; + } + } } void LightCullingPass::InitializeSSBOs() From e0410d4345f9831e1838934a046d8412993a4ee8 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Mon, 18 Jan 2016 14:41:16 +0100 Subject: [PATCH 068/224] Small logicfix in CapturePointSystem. Readded CapturePointSystem in Game. Added 2 tests. Tests have been refined a lot. --- src/Game/CapturePointSystem.cpp | 31 +-- src/Game/Game.cpp | 1 + src/Tests/CapturePointTest.cpp | 345 ++++++++++++++++++-------------- src/Tests/CapturePointTest.h | 14 +- 4 files changed, 232 insertions(+), 159 deletions(-) diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/CapturePointSystem.cpp index 88eff1e4..6189f066 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/CapturePointSystem.cpp @@ -17,20 +17,24 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture int secondTeamPlayersStandingInside = 0; //check how many players are standing inside and are healthy - for (size_t i = 0; i < m_ETriggerTouchVector.size(); i++) + for (size_t i = m_ETriggerTouchVector.size(); i > 0; i--) { - auto triggerTouched = m_ETriggerTouchVector[i]; + auto triggerTouched = m_ETriggerTouchVector[i - 1]; if (std::get<1>(triggerTouched) == capturePoint.EntityID) { //some player has touched this - lets figure out: what team, health EntityID playerID = std::get<0>(triggerTouched); - bool hasHealthComponent = world->HasComponent(playerID, "Health"); - if (!hasHealthComponent) { + if (!world->HasComponent(playerID, "Player")) { + //if a non-player has entered the capturePoint, just erase that event and continue + m_ETriggerTouchVector.erase(m_ETriggerTouchVector.begin() + i - 1); continue; } - double currentHealth = world->GetComponent(playerID, "Health")["Health"]; - //check if player is dead - if ((int)currentHealth == 0) { - continue; + bool hasHealthComponent = world->HasComponent(playerID, "Health"); + if (hasHealthComponent) { + double currentHealth = world->GetComponent(playerID, "Health")["Health"]; + //check if player is dead + if ((int)currentHealth == 0) { + continue; + } } //check team - 0 = no team int teamNumber = world->GetComponent(playerID, "Player")["TeamNumber"]; @@ -115,11 +119,12 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture m_Team2NextPossibleCapturePoint--; } //adjust flag for other team if their previous point has just been taken + //this depends on what team has what homepoint ("side") if (m_Team2NextPossibleCapturePoint == m_Team1NextPossibleCapturePoint - 2) { - m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint + 1; + m_Team2NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint + 1; } if (m_Team1NextPossibleCapturePoint == m_Team2NextPossibleCapturePoint + 2) { - m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint - 1; + m_Team1NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint - 1; } } else { @@ -129,11 +134,13 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture else { m_Team2NextPossibleCapturePoint++; } + //adjust flag for other team if their previous point has just been taken + //this depends on what team has what homepoint ("side") if (m_Team2NextPossibleCapturePoint == m_Team1NextPossibleCapturePoint + 2) { - m_Team2NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint - 1; + m_Team2NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint - 1; } if (m_Team1NextPossibleCapturePoint == m_Team2NextPossibleCapturePoint - 2) { - m_Team1NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint + 1; + m_Team1NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint + 1; } } } diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 6451140b..2582ef17 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -73,6 +73,7 @@ Game::Game(int argc, char* argv[]) m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); ++updateOrderLevel; + m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel, m_Renderer, m_RenderFrame); // Invoke network diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index 32570534..71408636 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -16,108 +16,77 @@ BOOST_AUTO_TEST_SUITE(CapturePointTestSuite) BOOST_AUTO_TEST_CASE(CapturePointTest1_OnePlayerOnCapturePoint) { CapturePointTest game(1); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest2_TwoPlayersOnCapturePoint) { CapturePointTest game(2); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest3_NoPlayersOnCapturePoint) { CapturePointTest game(3); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - //successCheck needs to know when were close to 100 to check if anything happened then (NumLoops) - game.NumLoops++; - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest4_TwoCapturePointsBeingCaptured) { CapturePointTest game(4); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest5_SameCapturePointContestedAndTakenOver) { CapturePointTest game(5); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest6_Team1CapturedTheLastPointAndWon) { CapturePointTest game(6); + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(CapturePointTest7_Team1ForcesTeam2sNextCapturePointToGoBackwards1Step) +{ + CapturePointTest game(7); + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_CASE(CapturePointTest8_Team2ForcesTeam1sNextCapturePointToGoForwards1Step) +{ + CapturePointTest game(8); + bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); + //The system will process the events, hence it will take a while before we can read anything + BOOST_TEST(success); +} +BOOST_AUTO_TEST_SUITE_END() + +bool CapturePointTest::CapturePoint_Game_Loop_OneHundredTimes() { + //CapturePointTest game(testNumber); //100 loops will be more than enough to do the test int loops = 100; bool success = false; while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { + Tick(); + NumLoops++; + if (TestSucceeded) { success = true; break; } loops--; } - //The system will process the events, hence it will take a while before we can read anything - BOOST_TEST(success); + return success; } -BOOST_AUTO_TEST_SUITE_END() CapturePointTest::CapturePointTest(int runTestNumber) { @@ -150,7 +119,14 @@ CapturePointTest::CapturePointTest(int runTestNumber) fp.MergeEntities(m_World); } - //create 2 players and 3 capturepoints for testing + /* + ---TESTSETUP--- + default: 2 players + healthcomponent + 3 capturepoints + capturepoint(1) = home for team number 2 + capturepoint3 = home for team number 1 + */ EntityID playerID = m_World->CreateEntity(); m_PlayerID = playerID; ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); @@ -185,7 +161,8 @@ CapturePointTest::CapturePointTest(int runTestNumber) m_CapturePointID3 = capturePointID3; m_RunTestNumber = runTestNumber; - //add some touch/leave events + + //further testsetups:i.e. add some initial touch/leave events switch (runTestNumber) { case 1: @@ -206,6 +183,16 @@ CapturePointTest::CapturePointTest(int runTestNumber) case 6: TestSetup6_Team1CapturedTheLastPointAndWon(); break; + case 7: + //default homecapturepoints + TestSetup7(); + break; + case 8: + //switch sides + capturePoint["IsHomeCapturePointForTeamNumber"] = 1; + capturePoint3["IsHomeCapturePointForTeamNumber"] = 2; + TestSetup8(); + break; default: break; } @@ -227,21 +214,10 @@ void CapturePointTest::TestSetup1_OnePlayerOnCapturePoint() Events::TriggerLeave leaveEvent; //player touches,leaves,touches m_CapturePointID. and enters m_CapturePointID3 - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); - - leaveEvent.Entity = m_PlayerID; - leaveEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(leaveEvent); - - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); - - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID3; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID); + DoLeaveEvent(m_PlayerID, m_CapturePointID); + DoTouchEvent(m_PlayerID, m_CapturePointID); + DoTouchEvent(m_PlayerID, m_CapturePointID3); } void CapturePointTest::TestSetup2_TwoPlayersOnCapturePoint() { @@ -249,26 +225,13 @@ void CapturePointTest::TestSetup2_TwoPlayersOnCapturePoint() Events::TriggerLeave leaveEvent; //player touches,leaves m_CapturePointID. and enters m_CapturePointID3 - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); - - leaveEvent.Entity = m_PlayerID; - leaveEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(leaveEvent); - - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID3; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID); + DoLeaveEvent(m_PlayerID, m_CapturePointID); + DoTouchEvent(m_PlayerID, m_CapturePointID3); //player2 touches m_CapturePointID,m_CapturePointID2 - touchEvent.Entity = m_PlayerID2; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); - - touchEvent.Entity = m_PlayerID2; - touchEvent.Trigger = m_CapturePointID2; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID2, m_CapturePointID); + DoTouchEvent(m_PlayerID2, m_CapturePointID2); } void CapturePointTest::TestSetup3_NoPlayersOnCapturePoint() { @@ -276,87 +239,79 @@ void CapturePointTest::TestSetup3_NoPlayersOnCapturePoint() Events::TriggerLeave leaveEvent; //player1 touches and leaves m_CapturePointID - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); - - leaveEvent.Entity = m_PlayerID; - leaveEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(leaveEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID); + DoLeaveEvent(m_PlayerID, m_CapturePointID); //player2 touches and leaves m_CapturePointID2 - touchEvent.Entity = m_PlayerID2; - touchEvent.Trigger = m_CapturePointID2; - m_EventBroker->Publish(touchEvent); - - leaveEvent.Entity = m_PlayerID2; - leaveEvent.Trigger = m_CapturePointID2; - m_EventBroker->Publish(leaveEvent); - + DoTouchEvent(m_PlayerID2, m_CapturePointID2); + DoLeaveEvent(m_PlayerID2, m_CapturePointID2); } void CapturePointTest::TestSetup4_TwoCapturePointsBeingCaptured() { Events::TriggerTouch touchEvent; //player1 touches m_CapturePointID3 - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID3; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID3); //player2 touches m_CapturePointID - touchEvent.Entity = m_PlayerID2; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID2, m_CapturePointID); } void CapturePointTest::TestSetup5_SameCapturePointContestedAndTakenOver() { //NOTE: setup events need to trigger first then the real event will be allowed by the system later - Events::TriggerTouch touchEvent; //"SETUP" homebase->same capturep //player1 touches m_CapturePointID3 - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID3; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID3); //player2 touches m_CapturePointID - touchEvent.Entity = m_PlayerID2; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID2, m_CapturePointID); //contested same, player1 touches the contested //player1 touches m_CapturePointID2 - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID2; - m_EventBroker->Publish(touchEvent); - - //player2 does nothing - + DoTouchEvent(m_PlayerID, m_CapturePointID2); } void CapturePointTest::TestSetup6_Team1CapturedTheLastPointAndWon() { - //NOTE: setup events need to trigger first then the real event will be allowed by the system later - Events::TriggerTouch touchEvent; - - //"SETUP" team1 captures point 2,3 //player1 touches m_CapturePointID3 - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID3; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID3); + + //TODO: this should be in UPDATE instead //player1 touches m_CapturePointID2 - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID2; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID2); - //team1 captures point 1 //player1 touches m_CapturePointID - touchEvent.Entity = m_PlayerID; - touchEvent.Trigger = m_CapturePointID; - m_EventBroker->Publish(touchEvent); + DoTouchEvent(m_PlayerID, m_CapturePointID); //player2 does nothing } +void CapturePointTest::TestSetup7() +{ + //2 owns 1 + DoTouchEvent(m_PlayerID2, m_CapturePointID); + //1 owns 3 + DoTouchEvent(m_PlayerID, m_CapturePointID3); +} +void CapturePointTest::TestSetup8() +{ + //2 owns 3 + DoTouchEvent(m_PlayerID2, m_CapturePointID3); + //1 owns 1 + DoTouchEvent(m_PlayerID, m_CapturePointID); +} +void CapturePointTest::DoTouchEvent(EntityID whoDidSomething, EntityID onWhatObject) { + Events::TriggerTouch touchEvent; + touchEvent.Entity = whoDidSomething; + touchEvent.Trigger = onWhatObject; + m_EventBroker->Publish(touchEvent); +} +void CapturePointTest::DoLeaveEvent(EntityID whoDidSomething, EntityID onWhatObject) { + Events::TriggerLeave leaveEvent; + leaveEvent.Entity = whoDidSomething; + leaveEvent.Trigger = onWhatObject; + m_EventBroker->Publish(leaveEvent); +} void CapturePointTest::TestSuccess1() { //TestSetup1_OnePlayerOnCapturePoint @@ -410,6 +365,98 @@ void CapturePointTest::TestSuccess6() { if (ownedByID1 == 1 && ownedByID2 == 1 && ownedByID3 == 1) TestSucceeded = true; } +void CapturePointTest::TestSuccess7() { + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + + if (NumLoops < 20 && ownedByID1 == 2 & ownedByID3 == 1) { + phase1Success = true; + } + if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == 1) { + phase2Success = true; + } + if (NumLoops < 60 && NumLoops > 40 && ownedByID1 == 1) { + phase3Success = true; + } + if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != 2) { + phase4Success = true; + } + + if (NumLoops == 99) { + if (phase1Success && phase2Success && phase3Success &&phase4Success) + TestSucceeded = true; + } +} +void CapturePointTest::TestSuccess8() { + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + + if (NumLoops < 20 && ownedByID3 == 2 & ownedByID1 == 1) { + phase1Success = true; + } + if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == 1) { + phase2Success = true; + } + if (NumLoops < 60 && NumLoops > 40 && ownedByID3 == 1) { + phase3Success = true; + } + if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != 2) { + phase4Success = true; + } + + if (NumLoops == 99) { + if (phase1Success && phase2Success && phase3Success &&phase4Success) + TestSucceeded = true; + } +} +void CapturePointTest::UpdateTest7() { + //loop 1 = team1 has 3, team 2 has 1 + //loop 20 = team1 takes 2, team 1 leaves 1 -> team1 next = 1, team2 next = still 2 + if (NumLoops == 20) { + //leave previous + DoLeaveEvent(m_PlayerID2, m_CapturePointID); + DoLeaveEvent(m_PlayerID, m_CapturePointID3); + + DoTouchEvent(m_PlayerID, m_CapturePointID2); + } + //loop 40 = team1 takes 1, team2:s next cap point should now be 1 (instead of 2) + if (NumLoops == 40) { + //leave previous, take next + DoLeaveEvent(m_PlayerID, m_CapturePointID2); + DoTouchEvent(m_PlayerID, m_CapturePointID); + } + //loop 60 = team2 tries to take 2, this shouldnt work now + if (NumLoops == 60) { + DoLeaveEvent(m_PlayerID, m_CapturePointID); + DoTouchEvent(m_PlayerID2, m_CapturePointID2); + } +} +void CapturePointTest::UpdateTest8() { + //2 owns 3 + //1 owns 1 + + //loop 20 = team1 takes 2, team 1 leaves 1 -> team1 next = 1, team2 next = still 2 + if (NumLoops == 20) { + //leave previous + DoLeaveEvent(m_PlayerID2, m_CapturePointID3); + DoLeaveEvent(m_PlayerID, m_CapturePointID); + + DoTouchEvent(m_PlayerID, m_CapturePointID2); + } + //loop 40 = team1 takes 3, team2:s next cap point should now be 1 (instead of 2) + if (NumLoops == 40) { + //leave previous, take next + DoLeaveEvent(m_PlayerID, m_CapturePointID2); + DoTouchEvent(m_PlayerID, m_CapturePointID3); + } + //loop 60 = team2 tries to take 2, this shouldnt work now + if (NumLoops == 60) { + DoLeaveEvent(m_PlayerID, m_CapturePointID3); + DoTouchEvent(m_PlayerID2, m_CapturePointID2); + } +} void CapturePointTest::Tick() { glfwPollEvents(); @@ -447,6 +494,14 @@ void CapturePointTest::Tick() case 6: TestSuccess6(); break; + case 7: + TestSuccess7(); + UpdateTest7(); + break; + case 8: + TestSuccess8(); + UpdateTest8(); + break; default: break; } diff --git a/src/Tests/CapturePointTest.h b/src/Tests/CapturePointTest.h index 89aea389..5646f8a6 100644 --- a/src/Tests/CapturePointTest.h +++ b/src/Tests/CapturePointTest.h @@ -29,18 +29,28 @@ public: bool TestSucceeded = false; int NumLoops = 0; + bool CapturePoint_Game_Loop_OneHundredTimes(); + void TestSetup1_OnePlayerOnCapturePoint(); void TestSetup2_TwoPlayersOnCapturePoint(); void TestSetup3_NoPlayersOnCapturePoint(); void TestSetup4_TwoCapturePointsBeingCaptured(); void TestSetup5_SameCapturePointContestedAndTakenOver(); void TestSetup6_Team1CapturedTheLastPointAndWon(); + void TestSetup7(); + void TestSetup8(); + void DoTouchEvent(EntityID whoDidSomething, EntityID onWhatObject); + void DoLeaveEvent(EntityID whoDidSomething, EntityID onWhatObject); void TestSuccess1(); void TestSuccess2(); void TestSuccess3(); void TestSuccess4(); void TestSuccess5(); void TestSuccess6(); + void TestSuccess7(); + void TestSuccess8(); + void UpdateTest7(); + void UpdateTest8(); private: double m_LastTime; @@ -48,9 +58,9 @@ private: EventBroker* m_EventBroker; World* m_World; SystemPipeline* m_SystemPipeline; - int m_PlayerID, m_PlayerID2, m_CapturePointID, m_CapturePointID2, m_CapturePointID3; + EntityID m_PlayerID, m_PlayerID2, m_CapturePointID, m_CapturePointID2, m_CapturePointID3; int m_RunTestNumber; - + bool phase1Success = false, phase2Success = false, phase3Success = false, phase4Success = false; }; #endif From 3bc7dceca5dbd5d3e97262b006e3f655b8a0189b Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 14:55:49 +0100 Subject: [PATCH 069/224] Made EntityWrapper hashable --- include/Engine/Core/EntityWrapper.h | 17 ++++++++++++++++- src/Engine/Core/EntityWrapper.cpp | 2 +- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/include/Engine/Core/EntityWrapper.h b/include/Engine/Core/EntityWrapper.h index e4be8d78..79f90f33 100644 --- a/include/Engine/Core/EntityWrapper.h +++ b/include/Engine/Core/EntityWrapper.h @@ -2,6 +2,7 @@ #define EntityWrapper_h__ #include +#include #include "ComponentWrapper.h" class World; @@ -26,9 +27,23 @@ struct EntityWrapper bool Valid(); ComponentWrapper operator[](const char* componentName); - bool operator==(const EntityWrapper& e); + bool operator==(const EntityWrapper& e) const; explicit operator EntityID() const; operator bool(); }; +namespace std +{ + template<> struct hash + { + std::size_t operator()(const EntityWrapper& e) const + { + std::size_t seed = 0; + boost::hash_combine(seed, e.World); + boost::hash_combine(seed, e.ID); + return seed; + } + }; +} + #endif diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index c3c5cf27..8c1ab10d 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -3,7 +3,7 @@ const EntityWrapper EntityWrapper::Invalid = EntityWrapper(nullptr, EntityID_Invalid); -bool EntityWrapper::operator==(const EntityWrapper& e) +bool EntityWrapper::operator==(const EntityWrapper& e) const { return (this->World == e.World) && (this->ID == e.ID); } From 0a3b6f4da140cdb775f8c8896088bfc6e54f6ca8 Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 14:57:55 +0100 Subject: [PATCH 070/224] Added DirectionalLightJob --- .../Engine/Rendering/DirectionalLightJob.h | 34 +++++++++++++++++++ 1 file changed, 34 insertions(+) create mode 100644 include/Engine/Rendering/DirectionalLightJob.h diff --git a/include/Engine/Rendering/DirectionalLightJob.h b/include/Engine/Rendering/DirectionalLightJob.h new file mode 100644 index 00000000..2686eb41 --- /dev/null +++ b/include/Engine/Rendering/DirectionalLightJob.h @@ -0,0 +1,34 @@ +#ifndef DirectionalLightJob_h__ +#define DirectionalLightJob_h__ + +#include + +#include "../Common.h" +#include "../GLM.h" +#include "../Core/ComponentWrapper.h" +#include "RenderJob.h" +#include "../Core/Transform.h" +#include "../Core/World.h" + +struct DirectionalLightJob : RenderJob +{ + DirectionalLightJob(ComponentWrapper transformComponent, ComponentWrapper directionalLightCompoentn, World* m_World) + : RenderJob() + { + Direction = glm::vec4((glm::vec3)directionalLightCompoentn["Direction"], 1.f); + Color = (glm::vec4)directionalLightCompoentn["Color"]; + Intensity = (double)directionalLightCompoentn["Intensity"]; + }; + + glm::vec4 Direction; + glm::vec4 Color; + float Intensity; + glm::vec3 padding = glm::vec3(1.f, 2.f, 3.f); + + void CalculateHash() override + { + Hash = 0; + } +}; + +#endif \ No newline at end of file From 794635b6a1c114e8746a61db0d3d0d25d6b407e2 Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 14:58:19 +0100 Subject: [PATCH 071/224] Added DirectionalLights to renderqueue jobs --- include/Engine/Rendering/RenderQueue.h | 3 ++ .../Schema/Components/DirectionalLight.xml | 1 + src/Engine/Rendering/RenderSystem.cpp | 43 +++++++++++++------ 3 files changed, 34 insertions(+), 13 deletions(-) diff --git a/include/Engine/Rendering/RenderQueue.h b/include/Engine/Rendering/RenderQueue.h index 119ea57f..8df967ac 100644 --- a/include/Engine/Rendering/RenderQueue.h +++ b/include/Engine/Rendering/RenderQueue.h @@ -12,6 +12,7 @@ #include "RenderJob.h" #include "ModelJob.h" #include "PointLightJob.h" +#include "DirectionalLightJob.h" /* @@ -53,12 +54,14 @@ struct RenderScene ::Camera* Camera; std::list> ForwardJobs; std::list> PointLightJobs; + std::list> DirectionalLightJobs; Rectangle Viewport; void Clear() { ForwardJobs.clear(); PointLightJobs.clear(); + DirectionalLightJobs.clear(); } }; diff --git a/resources/Schema/Components/DirectionalLight.xml b/resources/Schema/Components/DirectionalLight.xml index a14697c8..c854696a 100644 --- a/resources/Schema/Components/DirectionalLight.xml +++ b/resources/Schema/Components/DirectionalLight.xml @@ -1,4 +1,5 @@ + 0.8 true diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 11eca86b..eecf6786 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -102,22 +102,39 @@ void RenderSystem::fillModels(std::list>& jobs, World void RenderSystem::fillLight(std::list>& jobs, World* world) { auto pointLights = world->GetComponents("PointLight"); - if (pointLights == nullptr) { - return; + if (pointLights != nullptr) { + for (auto& pointlightC : *pointLights) { + bool visible = pointlightC["Visible"]; + if (!visible) { + continue; + } + auto transformC = world->GetComponent(pointlightC.EntityID, "Transform"); + if (&transformC == nullptr) { + continue; + } + + std::shared_ptr pointLightJob = std::shared_ptr(new PointLightJob(transformC, pointlightC, m_World)); + jobs.push_back(pointLightJob); + } } - for (auto& pointlightC : *pointLights) { - bool visible = pointlightC["Visible"]; - if (!visible) { - continue; - } - auto transformC = world->GetComponent(pointlightC.EntityID, "Transform"); - if (&transformC == nullptr) { - return; - } - std::shared_ptr pointLightJob = std::shared_ptr(new PointLightJob(transformC, pointlightC, m_World)); - jobs.push_back(pointLightJob); + auto directionalLights = world->GetComponents("DirectionalLight"); + if (directionalLights != nullptr) { + for (auto& directionalLightC : *directionalLights) { + bool visable = directionalLightC["Visible"]; + if (!visable) { + continue; + } + + auto transformC = world->GetComponent(directionalLightC.EntityID, "Transform"); + if(&transformC == nullptr) { + continue; + } + + std::shared_ptr directionalLightJob = std::shared_ptr(new DirectionalLightJob(transformC, directionalLightC, m_World)); + jobs.push_back(directionalLightJob); + } } } From 01a164847c41713deb9ef908921917188cada510 Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 15:15:33 +0100 Subject: [PATCH 072/224] Directional light now fully added to all lists. --- include/Engine/Rendering/DirectionalLightJob.h | 8 ++++---- include/Engine/Rendering/RenderSystem.h | 3 ++- resources/Schema/Components.xsd | 1 + resources/Schema/Components/DirectionalLight.xml | 4 ++-- src/Engine/Rendering/LightCullingPass.cpp | 8 ++++---- src/Engine/Rendering/RenderSystem.cpp | 10 +++++++--- 6 files changed, 20 insertions(+), 14 deletions(-) diff --git a/include/Engine/Rendering/DirectionalLightJob.h b/include/Engine/Rendering/DirectionalLightJob.h index 2686eb41..e8cd5b17 100644 --- a/include/Engine/Rendering/DirectionalLightJob.h +++ b/include/Engine/Rendering/DirectionalLightJob.h @@ -12,12 +12,12 @@ struct DirectionalLightJob : RenderJob { - DirectionalLightJob(ComponentWrapper transformComponent, ComponentWrapper directionalLightCompoentn, World* m_World) + DirectionalLightJob(ComponentWrapper transformComponent, ComponentWrapper directionalLightComponent, World* m_World) : RenderJob() { - Direction = glm::vec4((glm::vec3)directionalLightCompoentn["Direction"], 1.f); - Color = (glm::vec4)directionalLightCompoentn["Color"]; - Intensity = (double)directionalLightCompoentn["Intensity"]; + Direction = glm::vec4((glm::vec3)directionalLightComponent["Direction"], 1.f); + Color = (glm::vec4)directionalLightComponent["Color"]; + Intensity = (double)directionalLightComponent["Intensity"]; }; glm::vec4 Direction; diff --git a/include/Engine/Rendering/RenderSystem.h b/include/Engine/Rendering/RenderSystem.h index fe110276..966593db 100644 --- a/include/Engine/Rendering/RenderSystem.h +++ b/include/Engine/Rendering/RenderSystem.h @@ -46,7 +46,8 @@ private: void updateProjectionMatrix(ComponentWrapper& cameraComponent); void fillModels(std::list>& jobs, World* world); - void fillLight(std::list>& jobs, World* world); + void fillPointLights(std::list>& jobs, World* world); + void fillDirectionalLights(std::list>& jobs, World* world); EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index 9181daf2..a90d51ec 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -9,6 +9,7 @@ + \ No newline at end of file diff --git a/resources/Schema/Components/DirectionalLight.xml b/resources/Schema/Components/DirectionalLight.xml index c854696a..79d3ac2b 100644 --- a/resources/Schema/Components/DirectionalLight.xml +++ b/resources/Schema/Components/DirectionalLight.xml @@ -1,6 +1,6 @@ - + 0.8 true - \ No newline at end of file + \ No newline at end of file diff --git a/src/Engine/Rendering/LightCullingPass.cpp b/src/Engine/Rendering/LightCullingPass.cpp index 76f2045f..f49156dc 100644 --- a/src/Engine/Rendering/LightCullingPass.cpp +++ b/src/Engine/Rendering/LightCullingPass.cpp @@ -96,19 +96,19 @@ void LightCullingPass::FillLightList(RenderScene& scene) //p.Padding = 123.f; p.Type = LightSource::Point; m_LightSources.push_back(p); - continue; + } } for(auto &job : scene.DirectionalLightJobs) { - auto directionalLightJob = std::dynamic_pointer_cast(job); + auto directionalLightJob = std::dynamic_pointer_cast(job); if(directionalLightJob) { LightSource p; + p.Direction = directionalLightJob->Direction; p.Color = directionalLightJob->Color; p.Intensity = directionalLightJob->Intensity; - p.Position = glm::vec4(glm::vec3(directionalLightJob->Position), 1.f); p.Type = LightSource::Directional; m_LightSources.push_back(p); - continue; + } } } diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index eecf6786..9a75a615 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -99,7 +99,7 @@ void RenderSystem::fillModels(std::list>& jobs, World } -void RenderSystem::fillLight(std::list>& jobs, World* world) +void RenderSystem::fillPointLights(std::list>& jobs, World* world) { auto pointLights = world->GetComponents("PointLight"); if (pointLights != nullptr) { @@ -117,8 +117,11 @@ void RenderSystem::fillLight(std::list>& jobs, World* jobs.push_back(pointLightJob); } } +} +void RenderSystem::fillDirectionalLights(std::list>& jobs, World* world) +{ auto directionalLights = world->GetComponents("DirectionalLight"); if (directionalLights != nullptr) { for (auto& directionalLightC : *directionalLights) { @@ -128,7 +131,7 @@ void RenderSystem::fillLight(std::list>& jobs, World* } auto transformC = world->GetComponent(directionalLightC.EntityID, "Transform"); - if(&transformC == nullptr) { + if (&transformC == nullptr) { continue; } @@ -162,7 +165,8 @@ void RenderSystem::Update(World* world, double dt) scene.Camera = m_Camera; scene.Viewport = Rectangle(1280, 720); fillModels(scene.ForwardJobs, world); - fillLight(scene.PointLightJobs, world); + fillPointLights(scene.PointLightJobs, world); + fillDirectionalLights(scene.DirectionalLightJobs, world); m_RenderFrame->Add(scene); } From 601ce85c05da303cbda4d44b4cf55d164cf422fd Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 16:50:41 +0100 Subject: [PATCH 073/224] WIP --- .../Engine/Rendering/DirectionalLightJob.h | 1 - include/Engine/Rendering/LightCullingPass.h | 2 +- .../Schema/Components/DirectionalLight.xml | 2 +- resources/Shaders/ForwardPlus.frag.glsl | 39 +++++++++++++++---- 4 files changed, 33 insertions(+), 11 deletions(-) diff --git a/include/Engine/Rendering/DirectionalLightJob.h b/include/Engine/Rendering/DirectionalLightJob.h index e8cd5b17..83787833 100644 --- a/include/Engine/Rendering/DirectionalLightJob.h +++ b/include/Engine/Rendering/DirectionalLightJob.h @@ -23,7 +23,6 @@ struct DirectionalLightJob : RenderJob glm::vec4 Direction; glm::vec4 Color; float Intensity; - glm::vec3 padding = glm::vec3(1.f, 2.f, 3.f); void CalculateHash() override { diff --git a/include/Engine/Rendering/LightCullingPass.h b/include/Engine/Rendering/LightCullingPass.h index 954444da..ab50f650 100644 --- a/include/Engine/Rendering/LightCullingPass.h +++ b/include/Engine/Rendering/LightCullingPass.h @@ -58,7 +58,7 @@ private: //This should be a component struct LightSource { glm::vec4 Position = glm::vec4(0.f); - glm::vec4 Direction = glm::vec4(0.f); + glm::vec4 Direction = glm::vec4(10.f); glm::vec4 Color = glm::vec4(1.f); float Radius = 5.f; float Intensity = 0.8f; diff --git a/resources/Schema/Components/DirectionalLight.xml b/resources/Schema/Components/DirectionalLight.xml index 79d3ac2b..b14b7934 100644 --- a/resources/Schema/Components/DirectionalLight.xml +++ b/resources/Schema/Components/DirectionalLight.xml @@ -1,5 +1,5 @@ - + 0.8 true diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 713e3621..087c594c 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -72,7 +72,7 @@ vec4 CalcDiffuse(vec4 lightColor, vec4 lightVec, vec4 normal) { return lightColor * power; } -LightResult CalcLightSource(vec4 lightPos, float lightRadius, vec4 lightColor, float intensity, vec4 viewVec, vec4 position, vec4 normal, float falloff) +LightResult CalcPointLightSource(vec4 lightPos, float lightRadius, vec4 lightColor, float intensity, vec4 viewVec, vec4 position, vec4 normal, float falloff) { vec4 L = lightPos - position; float dist = length(L); @@ -86,6 +86,16 @@ LightResult CalcLightSource(vec4 lightPos, float lightRadius, vec4 lightColor, f return result; } +LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensity, vec4 viewVec, vec4 vertPosition, vec4 vertNormal) +{ + vec4 L = normalize( -direction ); + + LightResult result; + result.Diffuse = CalcDiffuse(color, L, vertNormal) * intensity; + result.Specular = CalcSpecular(color, viewVec, L, vertNormal) * intensity; + return result; +} + void main() { @@ -105,22 +115,35 @@ void main() int start = int(LightGrids.Data[currentTile].Start); int amount = int(LightGrids.Data[currentTile].Amount); //for(int i = 0; i < 3; i++) - for(int i = start; i < start + amount; i++) - { + for(int i = start; i < start + amount; i++) { int l = int(LightIndex[i]); + LightResult result; - LightResult result = CalcLightSource(V * LightSources.List[l].Position, LightSources.List[l].Radius, LightSources.List[l].Color, LightSources.List[l].Intensity, viewVec, position, normal, LightSources.List[i].Falloff); - + if(LightSources.List[i].Type == 0) { // point + //result = CalcPointLightSource(V * LightSources.List[l].Position, LightSources.List[l].Radius, LightSources.List[l].Color, LightSources.List[l].Intensity, viewVec, position, normal, LightSources.List[i].Falloff); + } else if (LightSources.List[i].Type == 1) { //Directional + result = CalcDirectionalLightSource(V * LightSources.List[l].Direction, LightSources.List[i].Color, LightSources.List[i].Intensity, viewVec, position, normal); + } totalLighting.Diffuse += result.Diffuse; totalLighting.Specular += result.Specular; } + + fragmentColor += Input.DiffuseColor; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; - fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3.0, 0, 1); + //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3.0, 0, 1); + if(LightSources.List[0].Type == 0) { + fragmentColor += vec4(1,0,0,1); + } + if(LightSources.List[0].Type == 1) { + fragmentColor += vec4(0,1,0,1); + } + if(LightSources.List[0].Type == 2) { + fragmentColor += vec4(0,0,1,1); + } //fragmentColor = texel * Input.DiffuseColor * Color; - if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) - { + if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { //fragmentColor += vec4(0.5, 0, 0, 0); } else { //fragmentColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/3.0, 0, 0, 1); From d7780d8248eb696b44fc7b9ca43cab55cb0dff38 Mon Sep 17 00:00:00 2001 From: stiffly Date: Mon, 18 Jan 2016 17:11:37 +0100 Subject: [PATCH 074/224] WIP implementing interpolation --- include/Engine/Network/EInterpolate.h | 20 +++++++++++ include/Game/InterpolationSystem.h | 42 ++++++++++++++++++++++ src/Game/InterpolationSystem.cpp | 50 +++++++++++++++++++++++++++ 3 files changed, 112 insertions(+) create mode 100644 include/Engine/Network/EInterpolate.h create mode 100644 include/Game/InterpolationSystem.h create mode 100644 src/Game/InterpolationSystem.cpp diff --git a/include/Engine/Network/EInterpolate.h b/include/Engine/Network/EInterpolate.h new file mode 100644 index 00000000..65038e49 --- /dev/null +++ b/include/Engine/Network/EInterpolate.h @@ -0,0 +1,20 @@ +#ifndef Events_Interpolate_h__ +#define Events_Interpolate_h__ + +#include + +#include "Core/EventBroker.h" +#include "Core/Entity.h" + +namespace Events +{ + +struct Interpolate : Event +{ + EntityID Entity; + boost::shared_array DataArray; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Game/InterpolationSystem.h b/include/Game/InterpolationSystem.h new file mode 100644 index 00000000..c87ee5a7 --- /dev/null +++ b/include/Game/InterpolationSystem.h @@ -0,0 +1,42 @@ +#ifndef Systems_InterpolationSystem_h__ +#define Systems_InterpolationSystem_h__ + +#include +#include +#include +#include + +#include "Common.h" +#include "Core/System.h" +#include "Core/EventBroker.h" + +#include "Network/EInterpolate.h" + +struct Transform { + glm::vec3 Position; + glm::vec3 Scale; + glm::vec3 Orientation; + double interpolationTime; +}; + +class InterpolationSystem : public PureSystem +{ +public: + InterpolationSystem(EventBroker* eventbroker) + : PureSystem(eventbroker, "Transform") + { + EVENT_SUBSCRIBE_MEMBER(m_EInterpolate, &InterpolationSystem::OnInterpolate); + } + ~InterpolationSystem() { } + + virtual void UpdateComponent(World* world, ComponentWrapper& transform, double dt) override; +private: + std::unordered_map> m_InterpolationPoints; + + glm::vec3 vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime); + + EventRelay m_EInterpolate; + bool InterpolationSystem::OnInterpolate(const Events::Interpolate& e); +}; + +#endif diff --git a/src/Game/InterpolationSystem.cpp b/src/Game/InterpolationSystem.cpp new file mode 100644 index 00000000..d2d81fda --- /dev/null +++ b/src/Game/InterpolationSystem.cpp @@ -0,0 +1,50 @@ +#include "InterpolationSystem.h" + +void InterpolationSystem::UpdateComponent(World * world, ComponentWrapper & transform, double dt) +{ + if (m_InterpolationPoints[transform.EntityID].size() > 0) { + Transform& sTransform = m_InterpolationPoints[transform.EntityID].front(); + sTransform.interpolationTime += dt; + if (sTransform.interpolationTime > 0.05) { + double time = std::fmod(sTransform.interpolationTime, 0.05f); + m_InterpolationPoints[transform.EntityID].pop(); + if (m_InterpolationPoints[transform.EntityID].size() <= 0) { + return; + } + sTransform = m_InterpolationPoints[transform.EntityID].front(); + sTransform.interpolationTime = time; + } + glm::vec3 nextPosition = sTransform.Position; + glm::vec3 currentPosition = static_cast(transform["Position"]); + transform["Position"] = vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); + } +} + +glm::vec3 InterpolationSystem::vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime) +{ + glm::vec3 difference = next - prev; + glm::vec3 position = difference / 0.05f * static_cast(currentTime); + return position; +} + +bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) +{ + Transform transform; + int offset = 0; + // Read the data + memcpy(&transform.Position, e.DataArray.get() + offset, sizeof(glm::vec3)); + offset += sizeof(glm::vec3); + memcpy(&transform.Orientation, e.DataArray.get() + offset, sizeof(glm::vec3)); + offset += sizeof(glm::vec3); + memcpy(&transform.Scale, e.DataArray.get() + offset, sizeof(glm::vec3)); + + // Check if queue already exists + if (m_InterpolationPoints.find(e.Entity) != m_InterpolationPoints.end()) { // Did exist, push to queue + m_InterpolationPoints[e.Entity].push(transform); + } else { // Did not exist, create queue + std::queue transformQueue; + transformQueue.push(transform); + m_InterpolationPoints[e.Entity] = transformQueue; + } + return false; +} From 0c7f2c5198d821217b48a4992f4eac3a605a4a89 Mon Sep 17 00:00:00 2001 From: Jocke Date: Mon, 18 Jan 2016 17:12:07 +0100 Subject: [PATCH 075/224] WIP implemented Interpolation (server logic) --- include/Engine/Network/Client.h | 5 ++++- src/Engine/Network/Client.cpp | 22 ++++++++++++++++++++-- 2 files changed, 24 insertions(+), 3 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 7aa20126..6aaa9e77 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -4,9 +4,11 @@ #include #include #include +#include #include #include +#include #include "Network/Network.h" #include "Network/MessageType.h" @@ -68,10 +70,11 @@ private: void ping(); void parseMessageType(Packet& packet); void updateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType); - void parseConnect(Packet& packet); + void parseConnect(Packet& packet); void parsePlayerConnected(Packet& packet); void parsePing(); void parseServerPing(); + void InterpolateFields(Packet & packet, const ComponentInfo & componentInfo, const EntityID & entityID, const std::string & componentType); void parseSnapshot(Packet& packet); void identifyPacketLoss(); bool isConnected(); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index d6e8f4c5..9ffd570b 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -112,6 +112,21 @@ void Client::parseServerPing() send(packet); } +// Fields with strings will not work right now +void Client::InterpolateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType) +{ + int sizeOfFields = 0; + for (auto field : componentInfo.FieldsInOrder) { + ComponentInfo::Field_t fieldInfo = componentInfo.Fields.at(field); + sizeOfFields = fieldInfo.Stride; + } + // Is the size correct? + boost::shared_array eventData(new char[componentInfo.Meta.Stride]); + memcpy(eventData.get(), packet.ReadData(componentInfo.Meta.Stride), componentInfo.Meta.Stride); + //Send event to interpolat system + +} + void Client::updateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType) { for (auto field : componentInfo.FieldsInOrder) { @@ -125,7 +140,6 @@ void Client::updateFields(Packet& packet, const ComponentInfo& componentInfo, co } } -// Field parse void Client::parseSnapshot(Packet& packet) { std::string componentType = packet.ReadString(); @@ -142,7 +156,11 @@ void Client::parseSnapshot(Packet& packet) // Check if the component exists if (m_World->HasComponent(entityID, componentType)) { // If the entity and the component exists update it - updateFields(packet, componentInfo, entityID, componentType); + if (componentType == "Transform") { + InterpolateFields(packet, componentInfo, entityID, componentType); + } else { + updateFields(packet, componentInfo, entityID, componentType); + } // if entity exists but not the component } else { // Create component From 92553f1e932dfc211bb7540d6ab4de775fdc38f4 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Mon, 18 Jan 2016 17:17:12 +0100 Subject: [PATCH 076/224] text size can now be entered in the filepath with a comma separator, like this "filepath,16" --- include/Engine/Rendering/Font.h | 7 ++ include/Engine/Rendering/TextRenderer.h | 1 + resources/Schema/Entities/RenderingWorld.xml | 126 ++++++++++--------- src/Engine/Rendering/Font.cpp | 52 ++++++-- src/Engine/Rendering/PickingPass.cpp | 2 - 5 files changed, 118 insertions(+), 70 deletions(-) diff --git a/include/Engine/Rendering/Font.h b/include/Engine/Rendering/Font.h index 03f15a49..08341c1e 100644 --- a/include/Engine/Rendering/Font.h +++ b/include/Engine/Rendering/Font.h @@ -3,6 +3,9 @@ #include #include FT_FREETYPE_H +#include FT_GLYPH_H +#include +#include #include "../OpenGL.h" #include "../GLM.h" @@ -21,6 +24,10 @@ public: glm::ivec2 Bearing; // Offset from baseline to left/top of glyph GLuint Advance; // Offset to advance to next glyph }; + + FT_Face Face; + + ~Font(); std::map m_Characters; diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h index 2e127e66..a755fd30 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextRenderer.h @@ -3,6 +3,7 @@ #include #include FT_FREETYPE_H +#include FT_GLYPH_H #include "../OpenGL.h" #include "../GLM.h" diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 86a3090a..73c0e474 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -1,58 +1,72 @@ - + + - - - - - - - - - - - - - Models/Camera.obj - - - MainCamera - - - - - - - - - - Models/Camera.obj - - - ActionCamera - - - - - - - - - - - Models/Core/UnitPlane.obj - - - - - - - - - - An error - - - - - \ No newline at end of file + + + + + + + + MainCamera + + + Models/Camera.obj + false + + + + + + + + + + + + ActionCamera + + + Models/Camera.obj + + + + + + + + + + + Models/Core/UnitPlane.obj + + + + + + + + + + + + An error + + + + + + + + + asdasdasdasdasd + Fonts/DroidSans.ttf + + + + + + + + diff --git a/src/Engine/Rendering/Font.cpp b/src/Engine/Rendering/Font.cpp index cf5cd691..f62205e3 100644 --- a/src/Engine/Rendering/Font.cpp +++ b/src/Engine/Rendering/Font.cpp @@ -3,22 +3,48 @@ Font::Font(std::string path) { + typedef boost::tokenizer> tokenizer; + boost::char_separator sep(","); + tokenizer tok(path, sep); + + int fontSize = 16; + + tokenizer::iterator it = tok.begin(); + std::string filePath = ""; + + if (it != tok.end()) { + filePath = (*it).c_str(); + it++; + if (it != tok.end()) { + try { + LOG_INFO("DFhdoölshöldsihjgf"); + fontSize = boost::lexical_cast((*it).c_str()); + } catch (boost::bad_lexical_cast const&) { + std::cout << "Error: input string was not valid" << std::endl; + } + } + } else { + return; + } + + + FT_Library library; - FT_Face face; if (FT_Init_FreeType(&library)) { LOG_ERROR("FreeType error: init failed"); return; } - if (FT_New_Face(library, path.c_str(), 0, &face)) { + if (FT_New_Face(library, filePath.c_str(), 0, &Face)) { LOG_ERROR("FreeType error: loading font"); return; } - FT_Set_Pixel_Sizes(face, 0, 48); + FT_Set_Char_Size(Face, 0, fontSize*64, 300, 300); // temp + FT_Set_Pixel_Sizes(Face, 0, fontSize); // - if (FT_Load_Char(face, 'X', FT_LOAD_RENDER)) { + if (FT_Load_Char(Face, 'X', FT_LOAD_RENDER)) { LOG_ERROR("FreeType error: loading char"); return; } @@ -26,8 +52,10 @@ Font::Font(std::string path) glPixelStorei(GL_UNPACK_ALIGNMENT, 1); for (GLubyte c = 0; c < 128; c++) { + + //Load character glyph - if (FT_Load_Char(face, c, FT_LOAD_RENDER)) { + if (FT_Load_Char(Face, c, FT_LOAD_RENDER)) { continue; } @@ -40,12 +68,12 @@ Font::Font(std::string path) GL_TEXTURE_2D, 0, GL_RED, - face->glyph->bitmap.width, - face->glyph->bitmap.rows, + Face->glyph->bitmap.width, + Face->glyph->bitmap.rows, 0, GL_RED, GL_UNSIGNED_BYTE, - face->glyph->bitmap.buffer + Face->glyph->bitmap.buffer ); // Set texture options glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); @@ -55,15 +83,15 @@ Font::Font(std::string path) // Now store character for later use Character character = { texture, - glm::ivec2(face->glyph->bitmap.width, face->glyph->bitmap.rows), - glm::ivec2(face->glyph->bitmap_left, face->glyph->bitmap_top), - face->glyph->advance.x + glm::ivec2(Face->glyph->bitmap.width, Face->glyph->bitmap.rows), + glm::ivec2(Face->glyph->bitmap_left, Face->glyph->bitmap_top), + Face->glyph->advance.x }; m_Characters.insert(std::pair(c, character)); } - FT_Done_Face(face); + FT_Done_Face(Face); FT_Done_FreeType(library); GLERROR("Font Load"); } diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 6800df1d..7470f029 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -46,10 +46,8 @@ void PickingPass::InitializeShaderPrograms() void PickingPass::Draw(RenderScene& scene) { PickingPassState* state = new PickingPassState(m_PickingBuffer.GetHandle()); - //TODO: Render: Add code for more jobs than modeljobs. - GLuint ShaderHandle = m_PickingProgram->GetHandle(); m_PickingProgram->Bind(); From 62c3f72355201b52dbde5d38a7eed96eecac03e8 Mon Sep 17 00:00:00 2001 From: stiffly Date: Mon, 18 Jan 2016 17:27:37 +0100 Subject: [PATCH 077/224] Fixed cmake for interpolationsystem. --- include/Engine/Network/EInterpolate.h | 2 +- src/Game/CMakeLists.txt | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/include/Engine/Network/EInterpolate.h b/include/Engine/Network/EInterpolate.h index 65038e49..93bf1a5c 100644 --- a/include/Engine/Network/EInterpolate.h +++ b/include/Engine/Network/EInterpolate.h @@ -12,7 +12,7 @@ namespace Events struct Interpolate : Event { EntityID Entity; - boost::shared_array DataArray; + boost::shared_array DataArray; }; } diff --git a/src/Game/CMakeLists.txt b/src/Game/CMakeLists.txt index 04146670..769cbd4f 100644 --- a/src/Game/CMakeLists.txt +++ b/src/Game/CMakeLists.txt @@ -21,6 +21,7 @@ set(SOURCE_FILES "Game.cpp" "HealthSystem.cpp" "PlayerSystem.cpp" + "InterpolationSystem.cpp" ) set(LIBRARIES From 765509b51095da7c96cf815e0a44778fc907f429 Mon Sep 17 00:00:00 2001 From: stiffly Date: Mon, 18 Jan 2016 17:34:17 +0100 Subject: [PATCH 078/224] Added interpolationsystem to pipeline. --- include/Game/Game.h | 2 +- src/Engine/Network/Client.cpp | 1 + src/Game/Game.cpp | 2 +- 3 files changed, 3 insertions(+), 2 deletions(-) diff --git a/include/Game/Game.h b/include/Game/Game.h index dfe1cff6..6614957f 100644 --- a/include/Game/Game.h +++ b/include/Game/Game.h @@ -20,7 +20,7 @@ #include "Core/EntityFile.h" #include "Rendering/RenderSystem.h" #include "Core/EntityFileParser.h" - +#include "InterpolationSystem.h" // Network #include #include "Network/Network.h" diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 9ffd570b..139d15ae 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -33,6 +33,7 @@ void Client::Start(World* world, EventBroker* eventBroker) void Client::Update() { + m_EventBroker->Process(); readFromServer(); } diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index ba660a7d..7ccd7fac 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -66,6 +66,7 @@ Game::Game(int argc, char* argv[]) m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel, m_Renderer); m_SystemPipeline->AddSystem(updateOrderLevel); + m_SystemPipeline->AddSystem(updateOrderLevel); //Collision and TriggerSystem should update after player. ++updateOrderLevel; @@ -119,7 +120,6 @@ void Game::Tick() // Iterate through systems and update world! m_SystemPipeline->Update(m_World, dt); m_Renderer->Update(dt); - m_EventBroker->Process(); GLERROR("Game::Tick m_RenderQueueFactory->Update"); m_Renderer->Draw(*m_RenderFrame); From c4594524da8261b13be21136659f60a46a44f0bb Mon Sep 17 00:00:00 2001 From: viktorljung Date: Mon, 18 Jan 2016 17:51:17 +0100 Subject: [PATCH 079/224] Better default values and documentation --- resources/Schema/Components/Text.xml | 4 ++-- resources/Schema/Components/Text.xsd | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/resources/Schema/Components/Text.xml b/resources/Schema/Components/Text.xml index d9190aba..45bed531 100644 --- a/resources/Schema/Components/Text.xml +++ b/resources/Schema/Components/Text.xml @@ -1,7 +1,7 @@ - - + Text + Fonts/DroidSans.ttf true \ No newline at end of file diff --git a/resources/Schema/Components/Text.xsd b/resources/Schema/Components/Text.xsd index 251d2e2e..c66acacd 100644 --- a/resources/Schema/Components/Text.xsd +++ b/resources/Schema/Components/Text.xsd @@ -13,7 +13,7 @@ the content of the string printed - font file + The asset file, font resolution, example: Fonts/font.ttf,16 Color From 4b29d48f27ecfef71d8f34510e3789b0132f568c Mon Sep 17 00:00:00 2001 From: Tleety Date: Mon, 18 Jan 2016 17:57:45 +0100 Subject: [PATCH 080/224] WIP --- .../Engine/Rendering/DirectionalLightJob.h | 2 +- include/Engine/Rendering/LightCullingPass.h | 2 +- resources/Shaders/CullLights.comp.glsl | 4 +-- resources/Shaders/ForwardPlus.frag.glsl | 25 ++++++------------- 4 files changed, 11 insertions(+), 22 deletions(-) diff --git a/include/Engine/Rendering/DirectionalLightJob.h b/include/Engine/Rendering/DirectionalLightJob.h index 83787833..92cd195a 100644 --- a/include/Engine/Rendering/DirectionalLightJob.h +++ b/include/Engine/Rendering/DirectionalLightJob.h @@ -15,7 +15,7 @@ struct DirectionalLightJob : RenderJob DirectionalLightJob(ComponentWrapper transformComponent, ComponentWrapper directionalLightComponent, World* m_World) : RenderJob() { - Direction = glm::vec4((glm::vec3)directionalLightComponent["Direction"], 1.f); + Direction = glm::vec4((glm::vec3)directionalLightComponent["Direction"], 0.f); Color = (glm::vec4)directionalLightComponent["Color"]; Intensity = (double)directionalLightComponent["Intensity"]; }; diff --git a/include/Engine/Rendering/LightCullingPass.h b/include/Engine/Rendering/LightCullingPass.h index ab50f650..7eb2c62d 100644 --- a/include/Engine/Rendering/LightCullingPass.h +++ b/include/Engine/Rendering/LightCullingPass.h @@ -63,7 +63,7 @@ private: float Radius = 5.f; float Intensity = 0.8f; float Falloff = 0.3f; - enum Type_t { Point, Directional, Spot } Type; + enum Type_t { Zero, Point, Directional, Spot } Type; }; std::vector m_LightSources; diff --git a/resources/Shaders/CullLights.comp.glsl b/resources/Shaders/CullLights.comp.glsl index f2908ecc..c32c6479 100644 --- a/resources/Shaders/CullLights.comp.glsl +++ b/resources/Shaders/CullLights.comp.glsl @@ -120,7 +120,7 @@ void main () //if pointlight //Pos i view antagligen - if(light.Type == 0) { + if(light.Type == 1) { if(SphereInsideFrustrum( vec3(V * light.Position), light.Radius, GroupFrustum)) { //TODO: Fix transparent and opaque list, and depth test. AppendLight( i ); @@ -131,7 +131,7 @@ void main () //if conelight //if directional - if(light.Type == 1) { + if(light.Type == 2) { AppendLight( i ); } diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 087c594c..9f9140fb 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -88,7 +88,7 @@ LightResult CalcPointLightSource(vec4 lightPos, float lightRadius, vec4 lightCol LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensity, vec4 viewVec, vec4 vertPosition, vec4 vertNormal) { - vec4 L = normalize( -direction ); + vec4 L = normalize( vec4(direction.xyz, 1) ); LightResult result; result.Diffuse = CalcDiffuse(color, L, vertNormal) * intensity; @@ -119,9 +119,9 @@ void main() int l = int(LightIndex[i]); LightResult result; - if(LightSources.List[i].Type == 0) { // point - //result = CalcPointLightSource(V * LightSources.List[l].Position, LightSources.List[l].Radius, LightSources.List[l].Color, LightSources.List[l].Intensity, viewVec, position, normal, LightSources.List[i].Falloff); - } else if (LightSources.List[i].Type == 1) { //Directional + if(LightSources.List[i].Type == 1) { // point + result = CalcPointLightSource(V * LightSources.List[l].Position, LightSources.List[l].Radius, LightSources.List[l].Color, LightSources.List[l].Intensity, viewVec, position, normal, LightSources.List[i].Falloff); + } else if (LightSources.List[i].Type == 2) { //Directional result = CalcDirectionalLightSource(V * LightSources.List[l].Direction, LightSources.List[i].Color, LightSources.List[i].Intensity, viewVec, position, normal); } totalLighting.Diffuse += result.Diffuse; @@ -129,26 +129,15 @@ void main() } - fragmentColor += Input.DiffuseColor; - //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + //fragmentColor += Input.DiffuseColor; + fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; - //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3.0, 0, 1); - if(LightSources.List[0].Type == 0) { - fragmentColor += vec4(1,0,0,1); - } - if(LightSources.List[0].Type == 1) { - fragmentColor += vec4(0,1,0,1); - } - if(LightSources.List[0].Type == 2) { - fragmentColor += vec4(0,0,1,1); - } + //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Start/.0, 0, 1); //fragmentColor = texel * Input.DiffuseColor * Color; if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { //fragmentColor += vec4(0.5, 0, 0, 0); } else { //fragmentColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/3.0, 0, 0, 1); - - } } From 3e90ed564c0de4288e29f84087fd481c596681d3 Mon Sep 17 00:00:00 2001 From: Jocke Date: Mon, 18 Jan 2016 18:07:39 +0100 Subject: [PATCH 081/224] Moved Struct in InterpolationSystem.h and fixed bug. --- include/Game/InterpolationSystem.h | 14 ++++++++------ src/Game/InterpolationSystem.cpp | 3 ++- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/include/Game/InterpolationSystem.h b/include/Game/InterpolationSystem.h index c87ee5a7..2acea373 100644 --- a/include/Game/InterpolationSystem.h +++ b/include/Game/InterpolationSystem.h @@ -12,15 +12,17 @@ #include "Network/EInterpolate.h" -struct Transform { - glm::vec3 Position; - glm::vec3 Scale; - glm::vec3 Orientation; - double interpolationTime; -}; class InterpolationSystem : public PureSystem { + struct Transform + { + glm::vec3 Position; + glm::vec3 Scale; + glm::vec3 Orientation; + double interpolationTime; + }; + public: InterpolationSystem(EventBroker* eventbroker) : PureSystem(eventbroker, "Transform") diff --git a/src/Game/InterpolationSystem.cpp b/src/Game/InterpolationSystem.cpp index d2d81fda..72207531 100644 --- a/src/Game/InterpolationSystem.cpp +++ b/src/Game/InterpolationSystem.cpp @@ -16,7 +16,7 @@ void InterpolationSystem::UpdateComponent(World * world, ComponentWrapper & tran } glm::vec3 nextPosition = sTransform.Position; glm::vec3 currentPosition = static_cast(transform["Position"]); - transform["Position"] = vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); + (glm::vec3&)transform["Position"] += vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); } } @@ -37,6 +37,7 @@ bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) memcpy(&transform.Orientation, e.DataArray.get() + offset, sizeof(glm::vec3)); offset += sizeof(glm::vec3); memcpy(&transform.Scale, e.DataArray.get() + offset, sizeof(glm::vec3)); + transform.interpolationTime = 0.0f; // Check if queue already exists if (m_InterpolationPoints.find(e.Entity) != m_InterpolationPoints.end()) { // Did exist, push to queue From 88eb3ca2dbf3d4da34aed86a985ccc386e7c9632 Mon Sep 17 00:00:00 2001 From: stiffly Date: Mon, 18 Jan 2016 18:07:59 +0100 Subject: [PATCH 082/224] Scraping queues for interpolation --- include/Game/InterpolationSystem.h | 16 ++++---- src/Engine/Network/Packet.cpp | 8 ++-- src/Engine/Network/Server.cpp | 4 +- src/Game/InterpolationSystem.cpp | 60 ++++++++++++++++++------------ 4 files changed, 50 insertions(+), 38 deletions(-) diff --git a/include/Game/InterpolationSystem.h b/include/Game/InterpolationSystem.h index c87ee5a7..3984ab5e 100644 --- a/include/Game/InterpolationSystem.h +++ b/include/Game/InterpolationSystem.h @@ -12,15 +12,14 @@ #include "Network/EInterpolate.h" -struct Transform { - glm::vec3 Position; - glm::vec3 Scale; - glm::vec3 Orientation; - double interpolationTime; -}; - class InterpolationSystem : public PureSystem { + struct Transform { + glm::vec3 Position; + glm::vec3 Scale; + glm::vec3 Orientation; + double interpolationTime; + }; public: InterpolationSystem(EventBroker* eventbroker) : PureSystem(eventbroker, "Transform") @@ -31,7 +30,8 @@ public: virtual void UpdateComponent(World* world, ComponentWrapper& transform, double dt) override; private: - std::unordered_map> m_InterpolationPoints; + //std::unordered_map> m_InterpolationPoints; + std::unordered_map m_InterpolationPoints; glm::vec3 vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime); diff --git a/src/Engine/Network/Packet.cpp b/src/Engine/Network/Packet.cpp index 2b2c7938..568a78e3 100644 --- a/src/Engine/Network/Packet.cpp +++ b/src/Engine/Network/Packet.cpp @@ -40,7 +40,7 @@ void Packet::WriteString(const std::string& str) // Message, add one extra byte for null terminator int sizeOfString = str.size() + 1; if (m_Offset + sizeOfString > m_MaxPacketSize) { - LOG_WARNING("Package::WriteString(): Data size in packet exceeded maximum package size. New size is %i bytes\n", m_MaxPacketSize*2); + //LOG_WARNING("Package::WriteString(): Data size in packet exceeded maximum package size. New size is %i bytes\n", m_MaxPacketSize*2); resizeData(); } memcpy(m_Data + m_Offset, str.data(), sizeOfString * sizeof(char)); @@ -50,7 +50,7 @@ void Packet::WriteString(const std::string& str) void Packet::WriteData(char * data, int sizeOfData) { if (m_Offset + sizeOfData > m_MaxPacketSize) { - LOG_WARNING("Packet::WriteData(): Data size in packet exceeded maximum packet size. New size is %i bytes\n", m_MaxPacketSize*2); + //LOG_WARNING("Packet::WriteData(): Data size in packet exceeded maximum packet size. New size is %i bytes\n", m_MaxPacketSize*2); resizeData(); } memcpy(m_Data + m_Offset, data, sizeOfData); @@ -61,7 +61,7 @@ std::string Packet::ReadString() { std::string returnValue(m_Data + m_ReturnDataOffset); if (m_Offset < m_ReturnDataOffset + returnValue.size()) { - LOG_WARNING("packet ReadString(): Oh no! You are trying to remove things outside my memory kingdom"); + //LOG_WARNING("packet ReadString(): Oh no! You are trying to remove things outside my memory kingdom"); return "PopFrontString Failed"; } // +1 for null terminator. @@ -72,7 +72,7 @@ std::string Packet::ReadString() char * Packet::ReadData(int SizeOfData) { if (m_Offset < m_ReturnDataOffset + SizeOfData) { - LOG_WARNING("packet ReadData(): Oh no! You are trying to remove things outside my memory kingdom"); + //LOG_WARNING("packet ReadData(): Oh no! You are trying to remove things outside my memory kingdom"); return nullptr; } unsigned int oldReturnDataOffset = m_ReturnDataOffset; diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 9ec1a041..1f9db461 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -227,7 +227,7 @@ void Server::parseOnInputCommand(Packet& packet) e.PlayerID = playerID; // Set correct player id e.Value = packet.ReadPrimitive(); m_EventBroker->Publish(e); - LOG_INFO("Server::parseOnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + //LOG_INFO("Server::parseOnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); } } } @@ -239,7 +239,7 @@ void Server::parseOnPlayerDamage(Packet & packet) e.PlayerDamagedID = packet.ReadPrimitive(); e.TypeOfDamage = packet.ReadString(); m_EventBroker->Publish(e); - LOG_DEBUG("Server::parseOnPlayerDamage: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str()); + //LOG_DEBUG("Server::parseOnPlayerDamage: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str()); } void Server::parseConnect(Packet& packet) diff --git a/src/Game/InterpolationSystem.cpp b/src/Game/InterpolationSystem.cpp index d2d81fda..d2413234 100644 --- a/src/Game/InterpolationSystem.cpp +++ b/src/Game/InterpolationSystem.cpp @@ -1,23 +1,32 @@ #include "InterpolationSystem.h" +//void InterpolationSystem::UpdateComponent(World * world, ComponentWrapper & transform, double dt) +//{ +// if (m_InterpolationPoints[transform.EntityID].size() > 0) { +// Transform& sTransform = m_InterpolationPoints[transform.EntityID].front(); +// sTransform.interpolationTime += dt; +// if (sTransform.interpolationTime > 0.05) { +// double time = std::fmod(sTransform.interpolationTime, 0.05f); +// m_InterpolationPoints[transform.EntityID].pop(); +// if (m_InterpolationPoints[transform.EntityID].size() <= 0) { +// return; +// } +// sTransform = m_InterpolationPoints[transform.EntityID].front(); +// sTransform.interpolationTime = time; +// } +// glm::vec3 nextPosition = sTransform.Position; +// glm::vec3 currentPosition = static_cast(transform["Position"]); +// transform["Position"] = vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); +// } +//} + void InterpolationSystem::UpdateComponent(World * world, ComponentWrapper & transform, double dt) { - if (m_InterpolationPoints[transform.EntityID].size() > 0) { - Transform& sTransform = m_InterpolationPoints[transform.EntityID].front(); - sTransform.interpolationTime += dt; - if (sTransform.interpolationTime > 0.05) { - double time = std::fmod(sTransform.interpolationTime, 0.05f); - m_InterpolationPoints[transform.EntityID].pop(); - if (m_InterpolationPoints[transform.EntityID].size() <= 0) { - return; - } - sTransform = m_InterpolationPoints[transform.EntityID].front(); - sTransform.interpolationTime = time; - } - glm::vec3 nextPosition = sTransform.Position; - glm::vec3 currentPosition = static_cast(transform["Position"]); - transform["Position"] = vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); - } + Transform& sTransform = m_InterpolationPoints[transform.EntityID]; + sTransform.interpolationTime += dt; + glm::vec3 nextPosition = sTransform.Position; + glm::vec3 currentPosition = static_cast(transform["Position"]); + transform["Position"] = vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); } glm::vec3 InterpolationSystem::vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime) @@ -37,14 +46,17 @@ bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) memcpy(&transform.Orientation, e.DataArray.get() + offset, sizeof(glm::vec3)); offset += sizeof(glm::vec3); memcpy(&transform.Scale, e.DataArray.get() + offset, sizeof(glm::vec3)); - + transform.interpolationTime = 0; + m_InterpolationPoints[e.Entity] = transform; // Check if queue already exists - if (m_InterpolationPoints.find(e.Entity) != m_InterpolationPoints.end()) { // Did exist, push to queue - m_InterpolationPoints[e.Entity].push(transform); - } else { // Did not exist, create queue - std::queue transformQueue; - transformQueue.push(transform); - m_InterpolationPoints[e.Entity] = transformQueue; - } + //if (m_InterpolationPoints.find(e.Entity) != m_InterpolationPoints.end()) { // Did exist, push to queue + // m_InterpolationPoints[e.Entity].push(transform); + //} + + //else { // Did not exist, create queue + // std::queue transformQueue; + // transformQueue.push(transform); + // m_InterpolationPoints[e.Entity] = transformQueue; + //} return false; } From b2358a1854fad1b28d928cd0782977332c7bf9e4 Mon Sep 17 00:00:00 2001 From: William Moberg Date: Mon, 18 Jan 2016 18:16:24 +0100 Subject: [PATCH 083/224] Added bool in Physics to toggle gravity for entities. --- resources/Schema/Components/Physics.xml | 1 + resources/Schema/Components/Physics.xsd | 1 + src/Game/Systems/PlayerMovementSystem.cpp | 4 +++- 3 files changed, 5 insertions(+), 1 deletion(-) diff --git a/resources/Schema/Components/Physics.xml b/resources/Schema/Components/Physics.xml index 7dce027c..9d1638fb 100644 --- a/resources/Schema/Components/Physics.xml +++ b/resources/Schema/Components/Physics.xml @@ -1,4 +1,5 @@ + true diff --git a/resources/Schema/Components/Physics.xsd b/resources/Schema/Components/Physics.xsd index 001dd2c8..cc5e24bb 100644 --- a/resources/Schema/Components/Physics.xsd +++ b/resources/Schema/Components/Physics.xsd @@ -10,6 +10,7 @@ + diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index 536624b3..57eef38d 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -9,7 +9,9 @@ void PlayerMovementSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& cPhysics = entity["Physics"]; glm::vec3& velocity = cPhysics["Velocity"]; - velocity.y -= 9.82 * dt; + if (cPhysics["Gravity"]) { + velocity.y -= 9.82 * dt; + } glm::vec3& position = cTransform["Position"]; position += velocity * (float)dt; From 621d935d7aced969cc920bb32acbaada49db4baf Mon Sep 17 00:00:00 2001 From: William Moberg Date: Mon, 18 Jan 2016 18:24:11 +0100 Subject: [PATCH 084/224] Octree returns correct boxes when testing along an axis by searching through the correct child subtrees. --- src/Engine/Core/AABB.cpp | 2 ++ src/Engine/Core/Octree.cpp | 8 ++++++-- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/src/Engine/Core/AABB.cpp b/src/Engine/Core/AABB.cpp index 22272104..55b362fe 100644 --- a/src/Engine/Core/AABB.cpp +++ b/src/Engine/Core/AABB.cpp @@ -15,6 +15,8 @@ AABB::AABB(const glm::vec3& minPos, const glm::vec3& maxPos) m_MinCorner.y = glm::min(m_MaxCorner.y, m_MinCorner.y); m_MaxCorner.z = glm::max(m_MaxCorner.z, m_MinCorner.z); m_MinCorner.z = glm::min(m_MaxCorner.z, m_MinCorner.z); + m_Origin = 0.5f * (m_MaxCorner + m_MinCorner); + m_HalfSize = 0.5f * (m_MaxCorner - m_MinCorner); } } diff --git a/src/Engine/Core/Octree.cpp b/src/Engine/Core/Octree.cpp index 47d06add..58501117 100644 --- a/src/Engine/Core/Octree.cpp +++ b/src/Engine/Core/Octree.cpp @@ -352,9 +352,13 @@ std::vector Octree::Child::childIndicesContainingBox(const AABB& box) const //the dimensions they are responsible for (which octant). bits.flip(); //At this point the bits necessarily have exactly one bit set. + //Check the same bit in the minInd as the one set in bits. + int setOrUnset = (bits.to_ulong() & minInd); for (int c = 0; c < 8; ++c) { - //If the child index have the same bit set as the bits, add box to it. - if (bits.to_ulong() & c) { + //Check the same bit in the child index as the one set in bits. + //Enter here if both c and minInd have the bit set, or if neither have it set. + //I.e, if they are on the same side (+ or -) in the dimension marked by the bit in bits. + if (!((bits.to_ulong() & c) ^ setOrUnset)) { ret.push_back(c); } } From 9cb5f4bd2f6721704e9466e3ac651a9467afa9d5 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 18:03:45 +0100 Subject: [PATCH 085/224] Added a stats window --- include/Engine/Common.h | 1 + include/Engine/Editor/EditorStats.h | 29 +++++++ include/Engine/Editor/EditorSystem.h | 2 + src/Engine/Editor/EditorStats.cpp | 115 +++++++++++++++++++++++++++ src/Engine/Editor/EditorSystem.cpp | 4 + 5 files changed, 151 insertions(+) create mode 100644 include/Engine/Editor/EditorStats.h create mode 100644 src/Engine/Editor/EditorStats.cpp diff --git a/include/Engine/Common.h b/include/Engine/Common.h index 7d6f520d..8038b8af 100644 --- a/include/Engine/Common.h +++ b/include/Engine/Common.h @@ -4,6 +4,7 @@ #include #include #include +#include #include "Core/Util/Logging.h" #include "Core/Util/IfDebug.h" \ No newline at end of file diff --git a/include/Engine/Editor/EditorStats.h b/include/Engine/Editor/EditorStats.h new file mode 100644 index 00000000..5dfa5378 --- /dev/null +++ b/include/Engine/Editor/EditorStats.h @@ -0,0 +1,29 @@ +#include +#include +#include +#include "../Common.h" +#include "../GLM.h" +#include "../OpenGL.h" + +class EditorStats +{ +public: + EditorStats(); + void Draw(double dt); + +private: + // FPS graph + const unsigned int m_SampleSize = 100; + unsigned int m_FrameCount = 0; + std::vector m_FrameTimes; + double m_TimeAccumulator = 0.0; + double m_AveragedSamplesPerSecond = 10.0; + const unsigned int m_AveragedSampleSize = 100; + unsigned int m_CurrentAveragedSampleIndex = 0; + std::vector m_AveragedSamples; + void drawFPSGraph(double dt); + + void drawRAMUsage(double dt); + + void drawVRAMStats(double dt); +}; diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index 7b908872..ae3502c3 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -9,6 +9,7 @@ #include "../Core/EntityFilePreprocessor.h" #include "../Core/EntityFileParser.h" #include "EditorGUI.h" +#include "EditorStats.h" class EditorSystem : public ImpureSystem { @@ -28,6 +29,7 @@ private: EntityWrapper m_Camera = EntityWrapper::Invalid; DebugCameraInputController* m_DebugCameraInputController; EditorGUI* m_EditorGUI; + EditorStats* m_EditorStats; void OnEntitySelected(EntityWrapper entity); }; \ No newline at end of file diff --git a/src/Engine/Editor/EditorStats.cpp b/src/Engine/Editor/EditorStats.cpp new file mode 100644 index 00000000..a626c442 --- /dev/null +++ b/src/Engine/Editor/EditorStats.cpp @@ -0,0 +1,115 @@ +#include "Editor/EditorStats.h" +#ifdef WIN32 +#define WIN32_LEAN_AND_MEAN +#define NOMINMAX +#include +#include +#endif +#include + +EditorStats::EditorStats() +{ + m_AveragedSamples.push_back(0.0); + m_CurrentAveragedSampleIndex = 1; +} + +void EditorStats::Draw(double dt) +{ + if (ImGui::Begin("Stats")) { + drawFPSGraph(dt); + drawRAMUsage(dt); + drawVRAMStats(dt); + } + ImGui::End(); +} + +void EditorStats::drawFPSGraph(double dt) +{ + if (m_FrameCount < m_SampleSize) { + m_FrameTimes.push_back(dt); + } else { + m_FrameTimes[m_FrameCount % m_SampleSize] = dt; + } + m_FrameCount++; + + double average = 0.0; + double max = 0.0; + for (double t : m_FrameTimes) { + average += t; + max = std::max(max, t); + } + average /= m_FrameTimes.size(); + + m_TimeAccumulator += dt; + if (m_TimeAccumulator >= 1.0/m_AveragedSamplesPerSecond) { + if (m_CurrentAveragedSampleIndex < m_AveragedSampleSize) { + m_AveragedSamples.push_back(1.0/average); + } else { + m_AveragedSamples[m_CurrentAveragedSampleIndex % m_AveragedSampleSize] = 1.0/average; + } + m_CurrentAveragedSampleIndex++; + m_TimeAccumulator = 0.0; + } + + float maxFPS = 0.f; + ImVector values; + int values_offset = m_CurrentAveragedSampleIndex % m_AveragedSampleSize; + for (double d : m_AveragedSamples) { + values.push_back(static_cast(d)); + maxFPS = std::max(maxFPS, static_cast(d)); + } + std::stringstream header; + header << std::round(1.0/average) << " FPS (" << std::setprecision(5) << average << " ms)"; + ImGui::PlotLines("##FPSGraph", values.Data, values.Size, values_offset, header.str().c_str(), 0.f, maxFPS + maxFPS/5.f, ImVec2(0, 100)); +} + +void EditorStats::drawRAMUsage(double dt) +{ +#ifdef WIN32 + PROCESS_MEMORY_COUNTERS_EX ppm; + GetProcessMemoryInfo(GetCurrentProcess(), (PPROCESS_MEMORY_COUNTERS)&ppm, sizeof(ppm)); + float megabytes = ppm.WorkingSetSize / (float)std::pow(1024, 2); + ImGui::Text("Memory: ~%f MiB", megabytes); +#endif +} + +void EditorStats::drawVRAMStats(double dt) +{ + //const unsigned int GPU_MEMORY_INFO_CURRENT_AVAILABLE_VIDMEM_NVX = 0x9049; + //const unsigned int GPU_MEMORY_INFO_TOTAL_AVAILABLE_MEMORY_NVX = 0x9048; + //glm::ivec4 total; + //glGetIntegerv(GPU_MEMORY_INFO_TOTAL_AVAILABLE_MEMORY_NVX, glm::value_ptr(total)); + //if (glGetError() == GL_NO_ERROR) { + // glm::ivec4 available; + // glGetIntegerv(GPU_MEMORY_INFO_CURRENT_AVAILABLE_VIDMEM_NVX, glm::value_ptr(available)); + // float megabytes = (total.x - available.x) / 1024.f; // NVidia returns in KiB + // ImGui::Text("VRAM: %f", megabytes); + //} + + //GLuint uNoOfGPUs = wglGetGPUIDsAMD(0, 0); + //if (!GLERROR("")) { + // GLuint* uGPUIDs = new GLuint[uNoOfGPUs]; + // wglGetGPUIDsAMD(uNoOfGPUs, uGPUIDs); + // GLuint uTotalMemoryInMB = 0; + // wglGetGPUInfoAMD(uGPUIDs[0], + // WGL_GPU_RAM_AMD, + // GL_UNSIGNED_INT, + // sizeof(GLuint), + // &uTotalMemoryInMB); + // GLint nCurAvailMemoryInKB[4]; + // glGetIntegerv(GL_TEXTURE_FREE_MEMORY_ATI, + // &nCurAvailMemoryInKB[0]); + // float usedTexture = (nCurAvailMemoryInKB[0] / 1024.f); + // glGetIntegerv(GL_VBO_FREE_MEMORY_ATI, + // &nCurAvailMemoryInKB[0]); + // float usedVBO = (nCurAvailMemoryInKB[0] / 1024.f); + // glGetIntegerv(GL_RENDERBUFFER_FREE_MEMORY_ATI, + // &nCurAvailMemoryInKB[0]); + // float usedFB = (nCurAvailMemoryInKB[0] / 1024.f); + // ImGui::Text("VRAM: %f MiB ", (float)uTotalMemoryInMB - usedTexture - usedVBO - usedFB); + // ImGui::Text(" Texture: %f MiB", usedTexture); + // ImGui::Text(" VBO: %f MiB", usedVBO); + // ImGui::Text(" Framebuffer: %f MiB", usedFB); + // delete[] uGPUIDs; + //} +} diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 2d0a4b55..0a96ab9b 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -27,6 +27,8 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render m_EditorGUI = new EditorGUI(m_EventBroker); m_EditorGUI->SetEntitySelectedCallback(std::bind(&EditorSystem::OnEntitySelected, this, std::placeholders::_1)); + m_EditorStats = new EditorStats(); + Events::SetCamera e; e.CameraEntity = m_Camera; m_EventBroker->Publish(e); @@ -34,6 +36,7 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render EditorSystem::~EditorSystem() { + delete m_EditorStats; delete m_EditorGUI; delete m_DebugCameraInputController; delete m_EditorWorldSystemPipeline; @@ -45,6 +48,7 @@ void EditorSystem::Update(World* world, double dt) m_EditorWorldSystemPipeline->Update(m_EditorWorld, dt); m_EditorGUI->Draw(world); + m_EditorStats->Draw(dt); m_DebugCameraInputController->Update(dt); m_Camera["Transform"]["Position"] = m_DebugCameraInputController->Position(); From 631dd57eeb7d9f9e3763d62c5fcf7c60445c33c5 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 18:55:19 +0100 Subject: [PATCH 086/224] Editor entity import, save, delete, component attach, component delete. --- include/Engine/Editor/EditorGUI.h | 33 +++++- include/Engine/Editor/EditorSystem.h | 8 ++ src/Engine/Editor/EditorGUI.cpp | 160 ++++++++++++++++++++++++--- src/Engine/Editor/EditorSystem.cpp | 46 +++++++- 4 files changed, 219 insertions(+), 28 deletions(-) diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 77218e9d..20946e36 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -29,12 +29,14 @@ public: typedef std::function OnEntitySelectedCallback_t; void SetEntitySelectedCallback(OnEntitySelectedCallback_t f) { m_OnEntitySelected = f; } // Called when the user means to import an entity file. - // Expects an EntityWrapper of the newly created entity in return. - typedef std::function OnEntityImport_t; + // @param EntityWrapper The entity to parent the imported entity to. The entity will be imported into the world of this entity. + // @param boost::filesystem::path The path to the entity to import + // @return EntityWrapper The newly created entity + typedef std::function OnEntityImport_t; void SetEntityImportCallback(OnEntityImport_t f) { m_OnEntityImport = f; } // Called when the user means to save an entity to file. - // Expects a bool indicating whether the save was successful or not in return. - typedef std::function OnEntitySave_t; + // Permitted to throw exceptions on save failure. + typedef std::function OnEntitySave_t; void SetEntitySaveCallback(OnEntitySave_t f) { m_OnEntitySave = f; } // Called when the user means to create a new entity. // @param EntityWrapper The parent of the entity to be created @@ -47,13 +49,20 @@ public: // Called when the user means to attach a new component to an entity. typedef std::function OnComponentAttach_t; void SetComponentAttachCallback(OnComponentAttach_t f) { m_OnComponentAttach = f; } - + // Called when the user means to delete a component off an entity. + typedef std::function OnComponentDelete_t; + void SetComponentDeleteCallback(OnComponentDelete_t f) { m_OnComponentDelete = f; } private: EventBroker* m_EventBroker; + // Config variables + const boost::filesystem::path m_DefaultEntityPath = boost::filesystem::path("Schema") / boost::filesystem::path("Entities"); + // State variables EntityWrapper m_CurrentSelection = EntityWrapper::Invalid; + std::unordered_map m_EntityFiles; + std::string m_LastErrorMessage; // Callbacks OnEntitySelectedCallback_t m_OnEntitySelected = nullptr; @@ -62,7 +71,17 @@ private: OnEntityCreate_t m_OnEntityCreate = nullptr; OnEntityDelete_t m_OnEntityDelete = nullptr; OnComponentAttach_t m_OnComponentAttach = nullptr; + OnComponentDelete_t m_OnComponentDelete = nullptr; + + // Utility functions + boost::filesystem::path fileOpenDialog(); + boost::filesystem::path fileSaveDialog(); + + // Entity file handling methods + void entityImport(World* world); + void entitySave(EntityWrapper entity); + // UI drawing methods void drawMenu(); void drawEntities(World* world); void drawEntitiesRecursive(World* world, EntityID parent); @@ -78,6 +97,10 @@ private: void drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field); void drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field); void drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field); + void drawModals(); + + // Custom UI elements + bool createDeleteButton(const std::string& componentType); }; #endif \ No newline at end of file diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index ae3502c3..7998a26d 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -8,6 +8,7 @@ #include "../Core/ResourceManager.h" #include "../Core/EntityFilePreprocessor.h" #include "../Core/EntityFileParser.h" +#include "../Core/EntityFileWriter.h" #include "EditorGUI.h" #include "EditorStats.h" @@ -31,5 +32,12 @@ private: EditorGUI* m_EditorGUI; EditorStats* m_EditorStats; + // Utility functions + EntityWrapper importEntity(EntityWrapper parent, boost::filesystem::path filePath); + + // GUI callbacks void OnEntitySelected(EntityWrapper entity); + void OnEntitySave(EntityWrapper entity, boost::filesystem::path filePath); + void OnComponentAttach(EntityWrapper entity, const std::string& componentType); + void OnComponentDelete(EntityWrapper entity, const std::string& componentType); }; \ No newline at end of file diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 388016a6..00c8b07c 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -28,9 +28,16 @@ void EditorGUI::drawEntities(World* world) } float buttonWidth = (ImGui::GetContentRegionAvailWidth() - 10.f) / 3.f ; - ImGui::Button("Create", ImVec2(buttonWidth, 0)); + if (ImGui::Button("Create", ImVec2(buttonWidth, 0))) { + if (m_OnEntityCreate != nullptr) { + EntityWrapper newEntity = m_OnEntityCreate(EntityWrapper(world, EntityID_Invalid)); + SelectEntity(newEntity); + } + } ImGui::SameLine(0.f, 5.f); - ImGui::Button("Import", ImVec2(buttonWidth, 0)); + if (ImGui::Button("Import", ImVec2(buttonWidth, 0))) { + entityImport(world); + } ImGui::SameLine(0.f, 5.f); ImGui::Button("Reference", ImVec2(buttonWidth, 0)); @@ -38,6 +45,8 @@ void EditorGUI::drawEntities(World* world) drawEntitiesRecursive(world, EntityID_Invalid); + // Draw any potential modals before ending this scope + drawModals(); ImGui::End(); } @@ -83,28 +92,29 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) // } //} - ImGui::SetNextTreeNodeOpened(true, ImGuiSetCond_Once); - std::string nodeTitle; + // Compose title + std::stringstream nodeTitle; const std::string& entityName = entity.World->GetName(entity); if (!entityName.empty()) { - nodeTitle = entityName; + nodeTitle << entityName; } else { - nodeTitle = std::string("#") + std::to_string(entity.ID); + nodeTitle << "#" << entity.ID; } - if (ImGui::TreeNode(nodeTitle.c_str())) { + if (m_EntityFiles.count(entity) == 1) { + nodeTitle << " (" << m_EntityFiles.at(entity).filename().string() << ")"; + } + + ImGui::SetNextTreeNodeOpened(true, ImGuiSetCond_Once); + if (ImGui::TreeNode(nodeTitle.str().c_str())) { //if (m_UIDraggingEntity != EntityID_Invalid && ImGui::IsItemHoveredRect() && ImGui::IsMouseReleased(0)) { // LOG_DEBUG("Changed parent of %i to %i", m_UIDraggingEntity, entity); // changeParent(m_UIDraggingEntity, entity); // m_UIDraggingEntity = EntityID_Invalid; //} - if (ImGui::BeginPopupContextItem("item context menu")) { - if (ImGui::Button("Add")) { - if (m_OnEntityCreate != nullptr) { - EntityWrapper newEntity = m_OnEntityCreate(EntityWrapper(entity.World, EntityID_Invalid)); - ImGui::CloseCurrentPopup(); - SelectEntity(newEntity); - } + if (ImGui::BeginPopupContextItem("entity context menu")) { + if (ImGui::Button("Save")) { + entitySave(entity); } ImGui::SameLine(); if (ImGui::Button("Delete")) { @@ -116,6 +126,7 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) SelectEntity(EntityWrapper::Invalid); } } + drawModals(); ImGui::EndPopup(); } return true; @@ -170,14 +181,21 @@ void EditorGUI::drawComponents(EntityWrapper entity) if (!entity.HasComponent(componentType)) { continue; } - // TODO: Add delete button here - drawComponent(entity, pool->ComponentInfo()); + // Handle deletion with early out + if (createDeleteButton(componentType)) { + if (m_OnComponentDelete != nullptr) { + m_OnComponentDelete(entity, componentType); + continue; + } + } + // Draw the actual component node + drawComponentNode(entity, pool->ComponentInfo()); } ImGui::End(); } -bool EditorGUI::drawComponent(EntityWrapper entity, const ComponentInfo& ci) +bool EditorGUI::drawComponentNode(EntityWrapper entity, const ComponentInfo& ci) { if (!ImGui::CollapsingHeader(ci.Name.c_str(), nullptr, true, true)) { return false; @@ -330,3 +348,111 @@ void EditorGUI::drawComponentField_string(ComponentWrapper &c, const ComponentIn // TODO: Handle drag and drop of files } +void EditorGUI::drawModals() +{ + if (ImGui::BeginPopupModal("Import failed", nullptr, ImGuiWindowFlags_AlwaysAutoResize)) { + ImGui::Text("Entity import failed. Check console for more information.\n\n"); + ImGui::SetCursorPosX(ImGui::GetContentRegionAvailWidth() - 120); + if (ImGui::Button("OK", ImVec2(120, 0))) { + ImGui::CloseCurrentPopup(); + } + ImGui::EndPopup(); + } + + if (ImGui::BeginPopupModal("Save failed", nullptr, ImGuiWindowFlags_AlwaysAutoResize)) { + ImGui::Text("Entity save failed on an exception.\nMessage: %s\n\n", m_LastErrorMessage.c_str()); + ImGui::SetCursorPosX(ImGui::GetContentRegionAvailWidth() - 120); + if (ImGui::Button("OK", ImVec2(120, 0))) { + ImGui::CloseCurrentPopup(); + } + ImGui::EndPopup(); + } +} + +bool EditorGUI::createDeleteButton(const std::string& componentType) +{ + float width = ImGui::GetContentRegionAvailWidth(); + ImGuiWindow* window = ImGui::GetCurrentWindow(); + auto pos = ImGui::GetCursorScreenPos() + ImVec2(width - 14.f, 1); + ImRect bb = ImRect(pos, pos + ImVec2(14.f, 14.f)); + std::string idString = "#DELETE"; + idString += componentType; + ImGuiID id = window->GetID(idString.c_str()); + bool hovered; + bool held; + bool pressed = ImGui::ButtonBehavior(bb, id, &hovered, &held); + //ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_CloseButtonHovered : ImGuiCol_CloseButton); + ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); + window->DrawList->AddCircleFilled(bb.GetCenter(), 7.f, col, 16); + return pressed; +} + +boost::filesystem::path EditorGUI::fileOpenDialog() +{ + namespace bfs = boost::filesystem; + nfdchar_t* outPath = nullptr; + nfdresult_t result = NFD_OpenDialog("xml", bfs::absolute(m_DefaultEntityPath).string().c_str(), &outPath); + + if (result == NFD_ERROR) { + LOG_ERROR("NFD Error: %s", NFD_GetError()); + return bfs::path(); + } else if (result == NFD_CANCEL) { + return bfs::path(); + } else { + return bfs::absolute(outPath); + } +} + +boost::filesystem::path EditorGUI::fileSaveDialog() +{ + namespace bfs = boost::filesystem; + nfdchar_t* outPath = nullptr; + nfdresult_t result = NFD_SaveDialog("xml", bfs::absolute(m_DefaultEntityPath).string().c_str(), &outPath); + + if (result == NFD_ERROR) { + LOG_ERROR("NFD Error: %s", NFD_GetError()); + return bfs::path(); + } else if (result == NFD_CANCEL) { + return bfs::path(); + } else { + return bfs::absolute(outPath); + } +} + +void EditorGUI::entityImport(World* world) +{ + boost::filesystem::path filePath = fileOpenDialog(); + if (filePath.empty()) { + return; + } + + EntityWrapper entity = m_OnEntityImport(EntityWrapper(world, EntityID_Invalid), filePath); + if (entity.Valid()) { + m_EntityFiles[entity] = filePath; + SelectEntity(entity); + } else { + ImGui::OpenPopup("Import failed"); + } +} + +void EditorGUI::entitySave(EntityWrapper entity) +{ + boost::filesystem::path filePath; + if (m_EntityFiles.count(entity) == 1) { + filePath = m_EntityFiles.at(entity); + } else { + filePath = fileSaveDialog(); + } + + if (filePath.empty()) { + return; + } + + try { + m_OnEntitySave(entity, filePath); + m_EntityFiles[entity] = filePath; + } catch (const std::exception& e) { + m_LastErrorMessage = e.what(); + ImGui::OpenPopup("Save failed"); + } +} diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 0a96ab9b..09cc52de 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -12,12 +12,7 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render m_EditorWorldSystemPipeline->AddSystem(0); m_EditorWorldSystemPipeline->AddSystem(1, m_Renderer, m_RenderFrame); - auto widgetEntityFile = ResourceManager::Load("Schema/Entities/EditorWidget.xml"); - EntityFilePreprocessor fpp(widgetEntityFile); - fpp.RegisterComponents(m_EditorWorld); - EntityFileParser fp(widgetEntityFile); - EntityID widgetID = fp.MergeEntities(m_EditorWorld); - m_Widget = EntityWrapper(m_EditorWorld, widgetID); + m_Widget = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/EditorWidget.xml"); m_Camera = EntityWrapper(m_EditorWorld, m_EditorWorld->CreateEntity()); m_EditorWorld->AttachComponent(m_Camera.ID, "Transform"); @@ -26,6 +21,10 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render m_EditorGUI = new EditorGUI(m_EventBroker); m_EditorGUI->SetEntitySelectedCallback(std::bind(&EditorSystem::OnEntitySelected, this, std::placeholders::_1)); + m_EditorGUI->SetEntityImportCallback(std::bind(&EditorSystem::importEntity, this, std::placeholders::_1, std::placeholders::_2)); + m_EditorGUI->SetEntitySaveCallback(std::bind(&EditorSystem::OnEntitySave, this, std::placeholders::_1, std::placeholders::_2)); + m_EditorGUI->SetComponentAttachCallback(std::bind(&EditorSystem::OnComponentAttach, this, std::placeholders::_1, std::placeholders::_2)); + m_EditorGUI->SetComponentDeleteCallback(std::bind(&EditorSystem::OnComponentDelete, this, std::placeholders::_1, std::placeholders::_2)); m_EditorStats = new EditorStats(); @@ -59,3 +58,38 @@ void EditorSystem::OnEntitySelected(EntityWrapper entity) { m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(entity.World, entity.ID); } + +void EditorSystem::OnEntitySave(EntityWrapper entity, boost::filesystem::path filePath) +{ + EntityFileWriter writer(filePath); + writer.WriteEntity(entity.World, entity.ID); +} + +void EditorSystem::OnComponentAttach(EntityWrapper entity, const std::string& componentType) +{ + entity.World->AttachComponent(entity.ID, componentType); +} + +void EditorSystem::OnComponentDelete(EntityWrapper entity, const std::string& componentType) +{ + entity.World->DeleteComponent(entity.ID, componentType); +} + +EntityWrapper EditorSystem::importEntity(EntityWrapper parent, boost::filesystem::path filePath) +{ + if (parent.World == nullptr) { + LOG_ERROR("Tried to import entity \"%s\" into null world!", filePath.string().c_str()); + return EntityWrapper::Invalid; + } + + try { + auto entityFile = ResourceManager::Load(filePath.string()); + EntityFilePreprocessor fpp(entityFile); + fpp.RegisterComponents(parent.World); + EntityFileParser fp(entityFile); + EntityID newEntity = fp.MergeEntities(parent.World, parent.ID); + return EntityWrapper(parent.World, newEntity); + } catch (const std::exception&) { + return EntityWrapper::Invalid; + } +} \ No newline at end of file From d4242bbead6ba9793274c7cd428e7a887711e7f9 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 19:26:00 +0100 Subject: [PATCH 087/224] Editor entity create and delete. --- include/Engine/Editor/EditorGUI.h | 4 ++- include/Engine/Editor/EditorSystem.h | 2 ++ src/Engine/Editor/EditorGUI.cpp | 38 ++++++++++++++++++++-------- src/Engine/Editor/EditorSystem.cpp | 14 ++++++++++ src/Engine/Rendering/Renderer.cpp | 5 ++-- 5 files changed, 49 insertions(+), 14 deletions(-) diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 20946e36..d37d4c83 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -45,7 +45,7 @@ public: void SetEntityCreateCallback(OnEntityCreate_t f) { m_OnEntityCreate = f; } // Called when the user means to delete an entity. typedef std::function OnEntityDelete_t; - void SetEntityCreateCallback(OnEntityDelete_t f) { m_OnEntityDelete = f; } + void SetEntityDeleteCallback(OnEntityDelete_t f) { m_OnEntityDelete = f; } // Called when the user means to attach a new component to an entity. typedef std::function OnComponentAttach_t; void SetComponentAttachCallback(OnComponentAttach_t f) { m_OnComponentAttach = f; } @@ -80,6 +80,8 @@ private: // Entity file handling methods void entityImport(World* world); void entitySave(EntityWrapper entity); + void entityCreate(World* world, EntityWrapper parent); + void entityDelete(EntityWrapper entity); // UI drawing methods void drawMenu(); diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index 7998a26d..fe8ef6ff 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -38,6 +38,8 @@ private: // GUI callbacks void OnEntitySelected(EntityWrapper entity); void OnEntitySave(EntityWrapper entity, boost::filesystem::path filePath); + EntityWrapper OnEntityCreate(EntityWrapper parent); + void OnEntityDelete(EntityWrapper entity); void OnComponentAttach(EntityWrapper entity, const std::string& componentType); void OnComponentDelete(EntityWrapper entity, const std::string& componentType); }; \ No newline at end of file diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 00c8b07c..3cff403d 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -29,10 +29,7 @@ void EditorGUI::drawEntities(World* world) float buttonWidth = (ImGui::GetContentRegionAvailWidth() - 10.f) / 3.f ; if (ImGui::Button("Create", ImVec2(buttonWidth, 0))) { - if (m_OnEntityCreate != nullptr) { - EntityWrapper newEntity = m_OnEntityCreate(EntityWrapper(world, EntityID_Invalid)); - SelectEntity(newEntity); - } + entityCreate(world, m_CurrentSelection); } ImGui::SameLine(0.f, 5.f); if (ImGui::Button("Import", ImVec2(buttonWidth, 0))) { @@ -115,16 +112,12 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) if (ImGui::BeginPopupContextItem("entity context menu")) { if (ImGui::Button("Save")) { entitySave(entity); + ImGui::CloseCurrentPopup(); } ImGui::SameLine(); if (ImGui::Button("Delete")) { - if (m_OnEntityDelete != nullptr) { - m_OnEntityDelete(entity); - ImGui::CloseCurrentPopup(); - } - if (!m_CurrentSelection.Valid()) { - SelectEntity(EntityWrapper::Invalid); - } + entityDelete(entity); + ImGui::CloseCurrentPopup(); } drawModals(); ImGui::EndPopup(); @@ -456,3 +449,26 @@ void EditorGUI::entitySave(EntityWrapper entity) ImGui::OpenPopup("Save failed"); } } + +void EditorGUI::entityCreate(World* world, EntityWrapper parent) +{ + if (m_OnEntityCreate != nullptr) { + // Create the new entity in the world we're drawing for + if (parent.World == nullptr) { + parent.World = world; + } + EntityWrapper newEntity = m_OnEntityCreate(parent); + SelectEntity(newEntity); + } +} + +void EditorGUI::entityDelete(EntityWrapper entity) +{ + if (m_OnEntityDelete != nullptr) { + m_OnEntityDelete(entity); + m_EntityFiles.erase(entity); + } + if (!m_CurrentSelection.Valid()) { + SelectEntity(EntityWrapper::Invalid); + } +} diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 09cc52de..51ab2f1f 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -23,6 +23,8 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render m_EditorGUI->SetEntitySelectedCallback(std::bind(&EditorSystem::OnEntitySelected, this, std::placeholders::_1)); m_EditorGUI->SetEntityImportCallback(std::bind(&EditorSystem::importEntity, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetEntitySaveCallback(std::bind(&EditorSystem::OnEntitySave, this, std::placeholders::_1, std::placeholders::_2)); + m_EditorGUI->SetEntityCreateCallback(std::bind(&EditorSystem::OnEntityCreate, this, std::placeholders::_1)); + m_EditorGUI->SetEntityDeleteCallback(std::bind(&EditorSystem::OnEntityDelete, this, std::placeholders::_1)); m_EditorGUI->SetComponentAttachCallback(std::bind(&EditorSystem::OnComponentAttach, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetComponentDeleteCallback(std::bind(&EditorSystem::OnComponentDelete, this, std::placeholders::_1, std::placeholders::_2)); @@ -65,6 +67,18 @@ void EditorSystem::OnEntitySave(EntityWrapper entity, boost::filesystem::path fi writer.WriteEntity(entity.World, entity.ID); } +EntityWrapper EditorSystem::OnEntityCreate(EntityWrapper parent) +{ + EntityID entity = parent.World->CreateEntity(parent.ID); + parent.World->AttachComponent(entity, "Transform"); + return EntityWrapper(parent.World, entity); +} + +void EditorSystem::OnEntityDelete(EntityWrapper entity) +{ + entity.World->DeleteEntity(entity.ID); +} + void EditorSystem::OnComponentAttach(EntityWrapper entity, const std::string& componentType) { entity.World->AttachComponent(entity.ID, componentType); diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index e8ed1d9a..5989543e 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -160,7 +160,8 @@ void Renderer::InitializeRenderPasses() //Temp func void Renderer::FillDepth(RenderScene& scene) { - for (auto job : scene.ForwardJobs) { + // HACK: FIX ME TOBIAS + /*for (auto job : scene.ForwardJobs) { auto modelJob = std::dynamic_pointer_cast(job); if(! modelJob) { return; @@ -171,5 +172,5 @@ void Renderer::FillDepth(RenderScene& scene) glm::vec3 worldpos = glm::vec3(scene.Camera->ViewMatrix() * glm::vec4(abspos, 1)); modelJob->Depth = worldpos.z; } - scene.ForwardJobs.sort(Renderer::DepthSort); + scene.ForwardJobs.sort(Renderer::DepthSort);*/ } \ No newline at end of file From 2a3009212ae9b921a777941dfb8426c9c1349e8e Mon Sep 17 00:00:00 2001 From: antc13 Date: Mon, 18 Jan 2016 19:37:55 +0100 Subject: [PATCH 088/224] Importing custom mesh without material. --- include/Engine/Collision/Collision.h | 3 +- include/Engine/Core/ResourceManager.h | 8 +- include/Engine/Rendering/Model.h | 4 +- include/Engine/Rendering/RawModelCustom.h | 25 ++- resources/Schema/Entities/Model.xml | 30 +++ resources/Shaders/BasicForward.vert.glsl | 11 +- resources/Shaders/ForwardPlus.frag.glsl | 5 +- resources/Shaders/ForwardPlus.vert.glsl | 10 +- src/Engine/Editor/EditorSystem.cpp | 26 +-- src/Engine/Rendering/RawModelAssimp.cpp | 3 - src/Engine/Rendering/RawModelCustom.cpp | 54 +++-- src/Engine/Rendering/RenderSystem.cpp | 4 +- src/Engine/Rendering/Renderer.cpp | 4 +- tools/MayaExporter/MayaExporter/Export.cpp | 30 ++- tools/MayaExporter/MayaExporter/Export.h | 6 +- tools/MayaExporter/MayaExporter/Material.cpp | 85 +++----- tools/MayaExporter/MayaExporter/Material.h | 69 ++++++- tools/MayaExporter/MayaExporter/Menu.cpp | 25 ++- tools/MayaExporter/MayaExporter/Menu.h | 3 +- tools/MayaExporter/MayaExporter/Mesh.cpp | 206 +++++++++++++------ tools/MayaExporter/MayaExporter/Mesh.h | 39 ++-- 21 files changed, 402 insertions(+), 248 deletions(-) create mode 100644 resources/Schema/Entities/Model.xml diff --git a/include/Engine/Collision/Collision.h b/include/Engine/Collision/Collision.h index 98ca1fb0..9777614f 100644 --- a/include/Engine/Collision/Collision.h +++ b/include/Engine/Collision/Collision.h @@ -9,7 +9,8 @@ #include "../Core/Ray.h" #include "../Core/AABB.h" -#include "Engine/Rendering/RawModelAssimp.h" +//#include "Engine/Rendering/RawModelAssimp.h" +#include "Engine/Rendering/RawModelCustom.h" #include "../Core/Entity.h" class World; diff --git a/include/Engine/Core/ResourceManager.h b/include/Engine/Core/ResourceManager.h index 15a551e7..10529819 100644 --- a/include/Engine/Core/ResourceManager.h +++ b/include/Engine/Core/ResourceManager.h @@ -32,10 +32,10 @@ public: }; struct FailedLoadingException : public std::exception { - virtual const char* what() const throw() - { - return "Resource is failed to load."; - } + FailedLoadingException(char const* const _Message) + : std::exception(_Message) + { } + FailedLoadingException() :std::exception("Resource failed to load.") { }; }; // Pretend that this is a pure virtual function that you have to implement diff --git a/include/Engine/Rendering/Model.h b/include/Engine/Rendering/Model.h index e99347c9..f79cacd5 100644 --- a/include/Engine/Rendering/Model.h +++ b/include/Engine/Rendering/Model.h @@ -1,7 +1,7 @@ #ifndef Model_h__ #define Model_h__ -#include "RawModelAssimp.h" +#include "RawModelCustom.h" #include "../OpenGL.h" class Model : public ThreadUnsafeResource @@ -23,8 +23,6 @@ public: private: RawModel* m_RawModel; GLuint VertexBuffer; - GLuint DiffuseVertexColorBuffer; - GLuint SpecularVertexColorBuffer; GLuint NormalBuffer; GLuint TangentNormalsBuffer; GLuint BiTangentNormalsBuffer; diff --git a/include/Engine/Rendering/RawModelCustom.h b/include/Engine/Rendering/RawModelCustom.h index c6e97242..b5bf44cc 100644 --- a/include/Engine/Rendering/RawModelCustom.h +++ b/include/Engine/Rendering/RawModelCustom.h @@ -40,15 +40,22 @@ public: struct MaterialGroup { - float Shininess; - std::shared_ptr<::Texture> Texture; - std::shared_ptr<::Texture> NormalMap; - std::shared_ptr<::Texture> SpecularMap; + float SpecularExponent; + float ReflectionFactor; unsigned int StartIndex; unsigned int EndIndex; + //float Transparency; + std::string TexturePath; + std::shared_ptr<::Texture> Texture; + std::string NormalMapPath; + std::shared_ptr<::Texture> NormalMap; + std::string SpecularMapPath; + std::shared_ptr<::Texture> SpecularMap; + std::string IncandescenceMapPath; + std::shared_ptr<::Texture> IncandescenceMap; }; - std::vector TextureGroups; + std::vector MaterialGroups; std::vector m_Vertices; std::vector m_Indices; @@ -57,10 +64,10 @@ public: private: - bool ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize); - bool ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize); - bool ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); - bool ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + void ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + void ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + void ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + void ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); //void CreateSkeleton(std::vector> &boneInfo, std::map &boneNameMapping, aiNode* node, int parentID); }; diff --git a/resources/Schema/Entities/Model.xml b/resources/Schema/Entities/Model.xml new file mode 100644 index 00000000..e4e60e4f --- /dev/null +++ b/resources/Schema/Entities/Model.xml @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + + + + + + + + + models/coolTriangle.mesh + + + + + + + + diff --git a/resources/Shaders/BasicForward.vert.glsl b/resources/Shaders/BasicForward.vert.glsl index 96f081f4..cb231e45 100644 --- a/resources/Shaders/BasicForward.vert.glsl +++ b/resources/Shaders/BasicForward.vert.glsl @@ -9,18 +9,14 @@ layout(location = 1) in vec3 Normal; layout(location = 2) in vec3 Tangent; layout(location = 3) in vec3 BiTangent; layout(location = 4) in vec2 TextureCoords; -layout(location = 5) in vec4 DiffuseVertexColor; -layout(location = 6) in vec4 SpecularVertexColor; -layout(location = 7) in vec4 BoneIndices1; -layout(location = 8) in vec4 BoneIndices2; -layout(location = 9) in vec4 BoneWeights1; -layout(location = 10) in vec4 BoneWeights2; +layout(location = 5) in vec4 BoneIndices; +layout(location = 6) in vec4 BoneWeights; + out VertexData{ vec3 Position; vec3 Normal; vec2 TextureCoordinate; - vec4 DiffuseColor; }Output; void main() @@ -30,5 +26,4 @@ void main() Output.Position = Position; Output.TextureCoordinate = TextureCoords; Output.Normal = Normal; - Output.DiffuseColor = DiffuseVertexColor; } \ No newline at end of file diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 3d5b9bfd..450d8929 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -44,7 +44,6 @@ in VertexData{ vec3 Position; vec3 Normal; vec2 TextureCoordinate; - vec4 DiffuseColor; }Input; out vec4 fragmentColor; @@ -114,7 +113,7 @@ void main() totalLighting.Specular += result.Specular; } - fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; //fragmentColor += vec4(0.0, LightGrids.Data[currentTile].Amount/3.0, 0, 1); //fragmentColor = texel * Input.DiffuseColor * Color; @@ -126,7 +125,7 @@ void main() } - + fragmentColor = vec4(1.0f, 1.0f, 1.0f, 1.0f); } diff --git a/resources/Shaders/ForwardPlus.vert.glsl b/resources/Shaders/ForwardPlus.vert.glsl index 20ab9051..9ef20d5b 100644 --- a/resources/Shaders/ForwardPlus.vert.glsl +++ b/resources/Shaders/ForwardPlus.vert.glsl @@ -9,18 +9,13 @@ layout(location = 1) in vec3 Normal; layout(location = 2) in vec3 Tangent; layout(location = 3) in vec3 BiTangent; layout(location = 4) in vec2 TextureCoords; -layout(location = 5) in vec4 DiffuseVertexColor; -layout(location = 6) in vec4 SpecularVertexColor; -layout(location = 7) in vec4 BoneIndices1; -layout(location = 8) in vec4 BoneIndices2; -layout(location = 9) in vec4 BoneWeights1; -layout(location = 10) in vec4 BoneWeights2; +layout(location = 5) in vec4 BoneIndices; +layout(location = 6) in vec4 BoneWeights; out VertexData{ vec3 Position; vec3 Normal; vec2 TextureCoordinate; - vec4 DiffuseColor; }Output; void main() @@ -30,5 +25,4 @@ void main() Output.Position = Position; Output.TextureCoordinate = TextureCoords; Output.Normal = Normal; - Output.DiffuseColor = DiffuseVertexColor; } \ No newline at end of file diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 94e848c0..0f32a519 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -291,21 +291,21 @@ void EditorSystem::createWidget() m_WidgetPlaneX = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneX, "Transform"); m_World->AttachComponent(m_WidgetPlaneX, "Model"); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/WidgetPlaneX.obj"; + m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube.mesh"; m_WidgetY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetY, "Transform"); m_World->AttachComponent(m_WidgetY, "Model"); m_WidgetPlaneY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneY, "Transform"); m_World->AttachComponent(m_WidgetPlaneY, "Model"); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/WidgetPlaneY.obj"; + m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube.mesh"; m_WidgetZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetZ, "Transform"); m_World->AttachComponent(m_WidgetZ, "Model"); m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); m_World->AttachComponent(m_WidgetPlaneZ, "Model"); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube.mesh"; m_WidgetOrigin = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetOrigin, "Transform"); m_World->AttachComponent(m_WidgetOrigin, "Model"); @@ -350,9 +350,9 @@ void EditorSystem::setWidgetMode(WidgetMode newMode) m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = false; if (newMode == WidgetMode::Translate) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.obj"; + //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; + //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.obj"; + //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.obj"; // Temporarily disabled for local space until I can figure out what's wrong with the math if (m_WidgetSpace != WidgetSpace::Local) { m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = true; @@ -366,19 +366,19 @@ void EditorSystem::setWidgetMode(WidgetMode newMode) } } } else if (newMode == WidgetMode::Scale) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.obj"; + //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; + //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.obj"; + //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.obj"; m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = true; - m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; + //m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; if (m_Selection != EntityID_Invalid) { auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); } } else if (newMode == WidgetMode::Rotate) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.obj"; + //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; + //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.obj"; + //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.obj"; if (m_Selection != EntityID_Invalid) { auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); if (m_WidgetSpace == WidgetSpace::Local) { diff --git a/src/Engine/Rendering/RawModelAssimp.cpp b/src/Engine/Rendering/RawModelAssimp.cpp index 875bacbf..259eafc3 100644 --- a/src/Engine/Rendering/RawModelAssimp.cpp +++ b/src/Engine/Rendering/RawModelAssimp.cpp @@ -74,9 +74,6 @@ RawModel::RawModel(std::string fileName) auto uv = mesh->mTextureCoords[0][vertexIndex]; desc.TextureCoords = glm::vec2(uv.x, uv.y); } - - - desc.DiffuseVertexColor = glm::vec4(diffuse.r, diffuse.g, diffuse.b, opacity); m_Vertices.push_back(desc); } diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index a5493bd8..a165e1a4 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -2,16 +2,12 @@ RawModel::RawModel(std::string fileName) { - boost::endian::big_int16_buf_t* test; - int16_t tal; - test = &(boost::endian::big_int16_buf_t)tal; - char* fileData; std::ifstream in(fileName.c_str(), std::ios_base::binary | std::ios_base::ate); - if (!in.is_open()) - LOG_ERROR("Failed to load custom binary model \"%s\"", fileName.c_str()); - + if (!in.is_open()) { + throw Resource::FailedLoadingException("Open file failed"); + } unsigned int fileByteSize = in.tellg(); in.seekg(0, std::ios_base::beg); @@ -20,42 +16,64 @@ RawModel::RawModel(std::string fileName) in.close(); unsigned int offset = 0; - ReadMeshFileHeader(offset, fileData, fileByteSize); - ReadMesh(offset, fileData, fileByteSize); - + if (fileByteSize > 0) { + ReadMeshFileHeader(offset, fileData, fileByteSize); + ReadMesh(offset, fileData, fileByteSize); + } + delete fileData; + MaterialGroup mat; + mat.StartIndex = 0; + mat.EndIndex = m_Indices.size() - 1; + MaterialGroups.push_back(mat); } -bool RawModel::ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModel::ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN - m_Vertices.resize(*fileData); + unsigned int test; + test = *(unsigned int*)fileData; + unsigned int* test2; + test2 = (unsigned int*)fileData; + + m_Vertices.resize(test); offset += sizeof(unsigned int); - m_Indices.resize(*(fileData + offset)); + test = *(unsigned int*)(fileData + offset); + m_Indices.resize(*(unsigned int*)(fileData + offset)); offset += sizeof(unsigned int); #else #endif } -bool RawModel::ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModel::ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { ReadVertices(offset, fileData, fileByteSize); ReadIndices(offset, fileData, fileByteSize); } -bool RawModel::ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModel::ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN - memcpy(&m_Vertices[0], fileData, m_Vertices.size() * sizeof(Vertex)); + if (offset + m_Vertices.size() * sizeof(Vertex) > fileByteSize) { + throw Resource::FailedLoadingException("Reading vertices failed"); + } + unsigned int i = sizeof(Vertex); + unsigned int ii = sizeof(unsigned int); + memcpy(&m_Vertices[0], fileData + offset, m_Vertices.size() * sizeof(Vertex)); offset += m_Vertices.size() * sizeof(Vertex); #else #endif } -bool RawModel::ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModel::ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN - memcpy(&m_Indices[0], fileData, m_Indices.size() * sizeof(unsigned int)); + if (offset + m_Indices.size() * sizeof(unsigned int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading indices failed"); + } + + memcpy(&m_Indices[0], fileData + offset, m_Indices.size() * sizeof(unsigned int)); offset += m_Indices.size() * sizeof(unsigned int); + #else #endif } diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index c8def2b9..bc43a5a6 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -95,10 +95,10 @@ void RenderSystem::fillModels(std::list>& jobs, World model = ResourceManager::Load<::Model, true>(resource); } catch (const Resource::StillLoadingException&) { //continue; - model = ResourceManager::Load<::Model>("Models/Core/UnitRaptor.obj"); + model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); } catch (const std::exception&) { try { - model = ResourceManager::Load<::Model>("Models/Core/Error.obj"); + model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); } catch (const std::exception&) { continue; } diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 9ae317ca..983b0736 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -10,9 +10,9 @@ void Renderer::Initialize() InitializeShaders(); InitializeTextures(); - m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + /* m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); m_UnitQuad = ResourceManager::Load("Models/Core/UnitQuad.obj"); - m_UnitSphere = ResourceManager::Load("Models/Core/UnitSphere.obj"); + m_UnitSphere = ResourceManager::Load("Models/Core/UnitSphere.obj");*/ m_ImGuiRenderPass = new ImGuiRenderPass(this, m_EventBroker); diff --git a/tools/MayaExporter/MayaExporter/Export.cpp b/tools/MayaExporter/MayaExporter/Export.cpp index 82c81cfa..20b99e0f 100644 --- a/tools/MayaExporter/MayaExporter/Export.cpp +++ b/tools/MayaExporter/MayaExporter/Export.cpp @@ -51,13 +51,15 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) GetMeshData(node); } } - MGlobal::displayInfo(MString() + "nrofmeshes: " + meshes.size()); WriteMeshData(pathName); return true; } -bool Export::Materials() +bool Export::Materials(std::string pathName) { + if (!GetMaterialData()) + return false; + WriteMaterialData(pathName); return true; } @@ -73,17 +75,14 @@ bool Export::Animations(std::string pathName, std::vector animInf MGlobal::displayError(MString() + "Export::Animations() got no pathName. Do not know where to write file"); return false; } - MGlobal::displayInfo("HALLOOOO"); allBindPoses = m_SkeletonHandler.GetBindPoses(); for (auto clip : animInfo) { - MGlobal::displayInfo("preben"); if (!GetAnimationData(clip)) { MGlobal::displayError(MString() + "Export::Animations() failed to export " + clip.Name.c_str()); return false; } } - MGlobal::displayInfo("ghihgihi"); WriteAnimData(pathName); return true; } @@ -100,11 +99,8 @@ bool Export::GetMeshData(MObject object) bool Export::GetMaterialData() { // Traverse scene and return vector with all materials - std::vector* AllMaterials = m_MaterialHandler.DoIt(); + AllMaterials = m_MaterialHandler.DoIt(); - // Access the colorR component of one material (example) - cout << AllMaterials->at(0).Color[0] << endl; - MGlobal::displayInfo(MString() + AllMaterials->at(0).Color[0]); return true; } @@ -163,6 +159,22 @@ void Export::WriteAnimData(std::string pathName) MGlobal::displayInfo("Export::WriteAnimData() got called when allBindPoses contained no data, did not write nor created them"); } +void Export::WriteMaterialData(std::string pathName) +{ + m_MtrlFile.ASCIIFilePath(pathName +"_mtrl.txt"); + m_MtrlFile.binaryFilePath(pathName + ".mtrl"); + + m_MtrlFile.OpenFiles(); + + int size = (*AllMaterials).size(); + m_MtrlFile.writeToFiles(&size); + + for (auto aMaterial : *AllMaterials) { + m_MtrlFile.writeToFiles((OutputData*)&aMaterial); + } + m_MtrlFile.CloseFiles(); +} + Export::~Export() { /* delete m_MaterialHandler; diff --git a/tools/MayaExporter/MayaExporter/Export.h b/tools/MayaExporter/MayaExporter/Export.h index 83d27459..b05dee4e 100644 --- a/tools/MayaExporter/MayaExporter/Export.h +++ b/tools/MayaExporter/MayaExporter/Export.h @@ -23,7 +23,7 @@ public: }; bool Meshes(std::string pathName, bool selectedOnly = false); - bool Materials(); + bool Materials(std::string pathName); bool Animations(std::string pathName, std::vector animInfo); private: @@ -33,6 +33,7 @@ private: void WriteMeshData(std::string pathName); void WriteAnimData(std::string pathName); + void WriteMaterialData(std::string pathName); Material m_MaterialHandler; Skeleton m_SkeletonHandler; @@ -42,6 +43,7 @@ private: //File export WriteToFile m_MeshFile; WriteToFile m_AnimFile; + WriteToFile m_MtrlFile; //Mesh Data std::vector meshes; @@ -50,5 +52,7 @@ private: std::vector allBindPoses; std::vector allAnimations; + //Material Data + std::vector* AllMaterials; }; #endif \ No newline at end of file diff --git a/tools/MayaExporter/MayaExporter/Material.cpp b/tools/MayaExporter/MayaExporter/Material.cpp index ac9c46ea..8071efab 100644 --- a/tools/MayaExporter/MayaExporter/Material.cpp +++ b/tools/MayaExporter/MayaExporter/Material.cpp @@ -4,57 +4,24 @@ void Material::grabLambertProperties(MaterialNode& material_node, MFnDependencyN { material_node.Name = node.name().asChar(); - if (findColorTexture(material_node, node)) { - material_node.Color.fill(1.0f); - } - else { - m_Plug = node.findPlug("colorR"); - m_Plug.getValue(material_node.Color[0]); - m_Plug = node.findPlug("colorG"); - m_Plug.getValue(material_node.Color[1]); - m_Plug = node.findPlug("colorB"); - m_Plug.getValue(material_node.Color[2]); + if (!findColorTexture(material_node, node)) { + MGlobal::displayWarning(MString() + "Material " + node.name() + " has no color texture. Please apply a texture insted of using a value"); + } - float TempTransp[3]; - m_Plug = node.findPlug("transparencyR"); - m_Plug.getValue(TempTransp[0]); - m_Plug = node.findPlug("transparencyG"); - m_Plug.getValue(TempTransp[1]); - m_Plug = node.findPlug("transparencyB"); - m_Plug.getValue(TempTransp[2]); - - MColor TranspNode(TempTransp[0], TempTransp[1], TempTransp[2]); - float DummyH, DummyS; - TranspNode.get(MColor::kHSV, DummyH, DummyS, material_node.Color[3]); - } if (findIncandescenceTexture(material_node, node)) { - material_node.Incandescence.fill(1.0f); - } - else { - m_Plug = node.findPlug("incandescenceR"); - m_Plug.getValue(material_node.Incandescence[0]); - m_Plug = node.findPlug("incandescenceG"); - m_Plug.getValue(material_node.Incandescence[1]); - m_Plug = node.findPlug("incandescenceB"); - m_Plug.getValue(material_node.Incandescence[2]); + MGlobal::displayWarning(MString() + "Material " + node.name() + " has no Incandescence texture. Please apply a texture insted of using value"); } - findNormalTexture(material_node, node); + if (findNormalTexture(material_node, node)) { + MGlobal::displayWarning(MString() + "Material " + node.name() + " has no normal texture. Please apply a texture to it"); + } } void Material::grabBlinnProperties(MaterialNode& material_node, MFnDependencyNode& node) { if (findSpecularTexture(material_node, node)) { - material_node.Specular.fill(1.0f); - } - else { - m_Plug = node.findPlug("specularColorR"); - m_Plug.getValue(material_node.Specular[0]); - m_Plug = node.findPlug("specularColorG"); - m_Plug.getValue(material_node.Specular[1]); - m_Plug = node.findPlug("specularColorB"); - m_Plug.getValue(material_node.Specular[2]); + MGlobal::displayWarning(MString() + "Material " + node.name() + " has no specular texture. Please apply a specular to it"); } m_Plug = node.findPlug("reflectivity"); @@ -76,17 +43,9 @@ void Material::grabBlinnProperties(MaterialNode& material_node, MFnDependencyNod void Material::grabPhongProperties(MaterialNode& material_node, MFnDependencyNode& node) { - if (findSpecularTexture(material_node, node)) { - material_node.Specular.fill(1.0f); - } - else { - m_Plug = node.findPlug("specularColorR"); - m_Plug.getValue(material_node.Specular[0]); - m_Plug = node.findPlug("specularColorG"); - m_Plug.getValue(material_node.Specular[1]); - m_Plug = node.findPlug("specularColorB"); - m_Plug.getValue(material_node.Specular[2]); - } + if (findSpecularTexture(material_node, node)) { + MGlobal::displayWarning(MString() + "Material " + node.name() + " has no specular texture. Please apply a specular to it"); + } m_Plug = node.findPlug("reflectivity"); m_Plug.getValue(material_node.ReflectionFactor); @@ -109,8 +68,10 @@ bool Material::findColorTexture(MaterialNode& material_node, MFnDependencyNode& std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); m_TexturePaths.push_back(FullPath); - material_node.ColorMapFile = FullPath.substr(FullPath.find_last_of("/")); + FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + material_node.ColorMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); + material_node.ColorMapFileLength = material_node.ColorMapFile.length() + 1; // Test MGlobal::displayInfo(MString() + "Texture file: " + FullPath.c_str()); return true; @@ -140,8 +101,9 @@ bool Material::findNormalTexture(MaterialNode& material_node, MFnDependencyNode& std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); m_TexturePaths.push_back(FullPath); - material_node.NormalMapFile = FullPath.substr(FullPath.find_last_of("/")); - + FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + material_node.NormalMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); + material_node.NormalMapFileLength = material_node.NormalMapFile.length() + 1; return true; } } @@ -165,8 +127,9 @@ bool Material::findSpecularTexture(MaterialNode& material_node, MFnDependencyNod std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); m_TexturePaths.push_back(FullPath); - material_node.SpecularMapFile = FullPath.substr(FullPath.find_last_of("/")); - + FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + material_node.SpecularMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); + material_node.SpecularMapFileLength = material_node.SpecularMapFile.length() + 1; return true; } } @@ -187,8 +150,9 @@ bool Material::findIncandescenceTexture(MaterialNode& material_node, MFnDependen std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); m_TexturePaths.push_back(FullPath); - material_node.SpecularMapFile = FullPath.substr(FullPath.find_last_of("/")); - + FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + material_node.IncandescenceMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); + material_node.IncandescenceMapFileLength = material_node.IncandescenceMapFile.length() + 1; return true; } } @@ -206,7 +170,7 @@ std::vector* Material::DoIt() { // All materials we care about inherit from Lambert MItDependencyNodes matIt(MFn::kLambert); - + m_AllMaterials.clear(); while (!matIt.isDone()) { MFnDependencyNode MaterialFnDN(matIt.thisNode()); MaterialNode MaterialStorage; @@ -226,7 +190,6 @@ std::vector* Material::DoIt() else if (matIt.thisNode().hasFn(MFn::kLambert)) { grabLambertProperties(MaterialStorage, MaterialFnDN); - MaterialStorage.Specular.fill(0.0f); MaterialStorage.ReflectionFactor = 0.0f; MaterialStorage.SpecularExponent = 0.0f; diff --git a/tools/MayaExporter/MayaExporter/Material.h b/tools/MayaExporter/MayaExporter/Material.h index c5d57529..9a6058f0 100644 --- a/tools/MayaExporter/MayaExporter/Material.h +++ b/tools/MayaExporter/MayaExporter/Material.h @@ -5,21 +5,80 @@ #include #include #include +#include #include "MayaIncludes.h" +#include "OutputData.h" +#include "Mesh.h" -struct MaterialNode +class MaterialNode : public OutputData { +public: std::string Name; - std::array Color; - std::array Incandescence; - std::array Specular; + float ReflectionFactor; - float SpecularExponent; + float SpecularExponent; + + unsigned int ColorMapFileLength = 0; std::string ColorMapFile; + + unsigned int SpecularMapFileLength = 0; std::string SpecularMapFile; + + unsigned int NormalMapFileLength = 0; std::string NormalMapFile; + + unsigned int IncandescenceMapFileLength = 0; std::string IncandescenceMapFile; + + unsigned int IndexStart; + unsigned int IndexEnd; + + virtual void WriteBinary(std::ostream& out) + { + out.write((char*)&ColorMapFileLength, sizeof(unsigned int)); + out.write((char*)&NormalMapFileLength, sizeof(unsigned int)); + out.write((char*)&SpecularMapFileLength, sizeof(unsigned int)); + out.write((char*)&IncandescenceMapFileLength, sizeof(unsigned int)); + + out.write((char*)&SpecularExponent, sizeof(float)); + out.write((char*)&ReflectionFactor, sizeof(float)); + out.write((char*)&IndexStart, sizeof(unsigned int)); + out.write((char*)&IndexEnd, sizeof(unsigned int)); + + out.write(ColorMapFile.c_str(), ColorMapFileLength); + out.write(NormalMapFile.c_str(), NormalMapFileLength); + out.write(SpecularMapFile.c_str(), SpecularMapFileLength); + out.write(IncandescenceMapFile.c_str(), IncandescenceMapFileLength); + } + + virtual void WriteASCII(std::ostream& out) const + { + out << "New Material _ not in binary" << endl; + out << "number of indices: " << Name << " _ not in binary" << endl; + + out << "ColorMapFile length: " << ColorMapFileLength << endl; + out << "NormalMapFile length: " << NormalMapFileLength << endl; + out << "SpecularMapFile length: " << SpecularMapFileLength << endl; + out << "IncandescenceMapFile length: " << IncandescenceMapFileLength << endl; + + out << "SpecularExponent: " << SpecularExponent << endl; + out << "ReflectionFactor: " << ReflectionFactor << endl; + out << "IndexStart: " << IndexStart << endl; + out << "IndexEnd: " << IndexEnd << endl; + + out << "ColorMapFile length: " << ColorMapFileLength << endl; + if (ColorMapFileLength > 0) + out << "ColorMapFile: " << ColorMapFile << endl; + if (NormalMapFileLength > 0) + out << "NormalMapFile: " << NormalMapFile << endl; + + if (SpecularMapFileLength > 0) + out << "SpecularMapFile: " << SpecularMapFile << endl; + + if (IncandescenceMapFileLength > 0) + out << "IncandescenceMapFile: " << IncandescenceMapFile << endl; + } }; class Material diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 1ff007b4..a03788a6 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -24,16 +24,15 @@ Menu::Menu(QDialog* dialog) m_ExportSelectedButton = new QCheckBox(tr("&Export Selected")); m_ExportAnimationsButton = new QCheckBox(tr("&Export Animations")); - m_CopyTexturesButton = new QCheckBox(tr("&Copy Textures")); - m_Button3 = new QCheckBox(tr("Test Materials")); + m_ExportMaterialButton = new QCheckBox(tr("&Export Material"));; m_ExportAnimationsButton->setChecked(true); - m_CopyTexturesButton->setChecked(true); + m_ExportMaterialButton->setChecked(true); QVBoxLayout *vbox = new QVBoxLayout; vbox->addWidget(m_ExportSelectedButton); vbox->addWidget(m_ExportAnimationsButton); - vbox->addWidget(m_CopyTexturesButton); - vbox->addWidget(m_Button3); + vbox->addWidget(m_ExportMaterialButton); + vbox->addStretch(1); optionsBox->setLayout(vbox); @@ -46,8 +45,7 @@ Menu::Menu(QDialog* dialog) connect(m_ExportSelectedButton, SIGNAL(clicked(bool)), this, SLOT(NULL)); connect(m_ExportAnimationsButton, SIGNAL(clicked(bool)), this, SLOT(NULL)); - connect(m_CopyTexturesButton, SIGNAL(clicked(bool)), this, SLOT(NULL)); - connect(m_Button3, SIGNAL(clicked(bool)), this, SLOT(NULL)); + connect(m_ExportMaterialButton, SIGNAL(clicked(bool)), this, SLOT(NULL)); // Creating several layouts, adding widgets & adding them to one layout in the end QHBoxLayout* topLayout = new QHBoxLayout; @@ -178,20 +176,14 @@ void Menu::ExportAll(bool) } std::vector animations; - MGlobal::displayInfo(MString() + "yeeehaa"); for (unsigned int i = 0; i < m_AnimationClipName.size(); i++) { Export::AnimationInfo thisClip; - MGlobal::displayInfo(MString() + "qwqw"); thisClip.Name = std::string(m_AnimationClipName[i]->text().toLocal8Bit().constData()); - MGlobal::displayInfo(MString() + "shizzzz"); thisClip.Start = m_StartFrameLines[i]->text().toInt(); - MGlobal::displayInfo(MString() + "dsdsfg"); thisClip.End = m_EndFrameLines[i]->text().toInt(); - MGlobal::displayInfo(MString() + "aaaaaaaaaaaaaaaaaaaa"); animations.push_back(thisClip); } - MGlobal::displayInfo(MString() + "asdf"); if (m_ExportAnimationsButton->isChecked()) { //Export Animations if (!m_Export.Animations(m_ExportPath->text().toLocal8Bit().constData(), animations)) { @@ -199,6 +191,13 @@ void Menu::ExportAll(bool) return; } } + + if (m_ExportMaterialButton->isChecked()) { + if (!m_Export.Materials(m_ExportPath->text().toLocal8Bit().constData())){ + MGlobal::displayError(MString() + "Could not export materials"); + return; + } + } } void Menu::CancelClicked(bool) diff --git a/tools/MayaExporter/MayaExporter/Menu.h b/tools/MayaExporter/MayaExporter/Menu.h index a8b517bc..fb95a953 100644 --- a/tools/MayaExporter/MayaExporter/Menu.h +++ b/tools/MayaExporter/MayaExporter/Menu.h @@ -65,8 +65,7 @@ private: QCheckBox* m_ExportSelectedButton = nullptr; QCheckBox* m_ExportAnimationsButton = nullptr; - QCheckBox* m_CopyTexturesButton = nullptr; - QCheckBox* m_Button3 = nullptr; + QCheckBox* m_ExportMaterialButton = nullptr; QLineEdit* m_ExportPath = nullptr; QFileDialog* m_FileDialog = nullptr; diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index 24e661ac..c37a7bed 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -76,8 +76,8 @@ std::map MeshClass::GetWeightData() Mesh MeshClass::GetMeshData(MObject object) { Mesh newMesh; - std::vector& vertexList = newMesh.Vertices; - std::vector& indexList = newMesh.Indices; + vector& vertexList = newMesh.Vertices; + map>& indexLists = newMesh.Indices; // In here, we retrieve triangulated polygons from the mesh MFnMesh mesh(object); @@ -91,11 +91,28 @@ Mesh MeshClass::GetMeshData(MObject object) float2 UV; double biTangent[3]; double biNormal[3]; - VertexLayout thisVertex; MFloatVectorArray Tangents; MFloatVectorArray biNormals; - std::map vertexWeights = GetWeightData(); + MObjectArray shaderList; + MIntArray shaderIndexList; + mesh.getConnectedShaders(0, shaderList, shaderIndexList); + + map> materialFaceIDs; + MGlobal::displayInfo(MString() + "shaderIndexList: " + shaderIndexList.length()); + MGlobal::displayInfo(MString() + "shaderList: " + shaderList.length()); + MPlugArray plugArray; + for (int i = 0; i < shaderIndexList.length(); i++) + { + MFnDependencyNode shader(shaderList[shaderIndexList[i]]); + MPlug p_Plug = shader.findPlug("surfaceShader"); + if (p_Plug.connectedTo(plugArray, true, false)) { + MFnDependencyNode node = plugArray[0].node(); + materialFaceIDs[node.name().asChar()].push_back(i); + } + } + + map vertexWeights = GetWeightData(); mesh.getTangents(Tangents, MSpace::kObject, NULL); mesh.getBinormals(biNormals, MSpace::kObject, NULL); @@ -103,82 +120,139 @@ Mesh MeshClass::GetMeshData(MObject object) MItMeshFaceVertex faceVert(object); int intDummy = 0; + + MItMeshPolygon meshPolyIter(object); - for (MItMeshPolygon meshPolyIter(object); !meshPolyIter.isDone(); meshPolyIter.next()) { + for (auto aMaterial : materialFaceIDs) { + for (auto faceID : aMaterial.second) { - vector localVertexToGlobalIndex; - unsigned int indexOffset = vertexList.size(); + vector> localVertexToGlobalIndex; + meshPolyIter.setIndex(faceID, intDummy); - meshPolyIter.getVertices(vertices); - meshPolyIter.getTriangles(dummy, triangleList); + meshPolyIter.getVertices(vertices); + meshPolyIter.getTriangles(dummy, triangleList); + //MGlobal::displayInfo("Befor Second Loop"); + for (unsigned int i = 0; i < vertices.length(); i++) { + VertexLayout thisVertex; + vertexIndex = meshPolyIter.vertexIndex(i); + faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); + //MGlobal::displayInfo("In Second Loop"); + pos = faceVert.position(); + if (abs(pos.x) > 0.0001) + thisVertex.Pos[0] = pos.x; + if (abs(pos.y) > 0.0001) + thisVertex.Pos[1] = pos.y; + if (abs(pos.z) > 0.0001) + thisVertex.Pos[2] = pos.z; - //MGlobal::displayInfo("Befor Second Loop"); - for (unsigned int i = 0; i < vertices.length(); i++) { - vertexIndex = meshPolyIter.vertexIndex(i); - faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); - //MGlobal::displayInfo("In Second Loop"); - faceVert.position().get(thisVertex.Pos); - faceVert.getNormal(normal); - thisVertex.Normal[0] = normal[0]; - thisVertex.Normal[1] = normal[1]; - thisVertex.Normal[2] = normal[2]; + faceVert.getNormal(normal); + if (abs(normal[0]) > 0.0001) + thisVertex.Normal[0] = normal[0]; + if (abs(normal[1]) > 0.0001) + thisVertex.Normal[1] = normal[1]; + if (abs(normal[2]) > 0.0001) + thisVertex.Normal[2] = normal[2]; - MFloatVector Tangent = Tangents[faceVert.tangentId()]; - //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); - //tmp.get(biTangent); - thisVertex.Tangent[0] = Tangent[0]; - thisVertex.Tangent[1] = Tangent[1]; - thisVertex.Tangent[2] = Tangent[2]; + MFloatVector Tangent = Tangents[faceVert.tangentId()]; + //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); + //tmp.get(biTangent); + if (abs(Tangent[0]) > 0.0001) + thisVertex.Tangent[0] = Tangent[0]; + if (abs(Tangent[1]) > 0.0001) + thisVertex.Tangent[1] = Tangent[1]; + if (abs(Tangent[2]) > 0.0001) + thisVertex.Tangent[2] = Tangent[2]; - MFloatVector biNormal = biNormals[faceVert.tangentId()]; - //faceVert.getBinormal().get(biNormal); - thisVertex.BiNormal[0] = biNormal[0]; - thisVertex.BiNormal[1] = biNormal[1]; - thisVertex.BiNormal[2] = biNormal[2]; + MFloatVector biNormal = biNormals[faceVert.tangentId()]; + //faceVert.getBinormal().get(biNormal); + if (abs(biNormal[0]) > 0.0001) + thisVertex.BiNormal[0] = biNormal[0]; + if (abs(biNormal[1]) > 0.0001) + thisVertex.BiNormal[1] = biNormal[1]; + if (abs(biNormal[2]) > 0.0001) + thisVertex.BiNormal[2] = biNormal[2]; - faceVert.getUV(UV); - thisVertex.Uv[0] = UV[0]; - thisVertex.Uv[1] = UV[1]; + faceVert.getUV(UV); + thisVertex.Uv[0] = UV[0]; + thisVertex.Uv[1] = UV[1]; - thisVertex.BoneIndices[0] = vertexWeights[faceVert.vertId()].BoneIndices[0]; - thisVertex.BoneIndices[1] = vertexWeights[faceVert.vertId()].BoneIndices[1]; - thisVertex.BoneIndices[2] = vertexWeights[faceVert.vertId()].BoneIndices[2]; - thisVertex.BoneIndices[3] = vertexWeights[faceVert.vertId()].BoneIndices[3]; + thisVertex.BoneIndices[0] = vertexWeights[faceVert.vertId()].BoneIndices[0]; + thisVertex.BoneIndices[1] = vertexWeights[faceVert.vertId()].BoneIndices[1]; + thisVertex.BoneIndices[2] = vertexWeights[faceVert.vertId()].BoneIndices[2]; + thisVertex.BoneIndices[3] = vertexWeights[faceVert.vertId()].BoneIndices[3]; - thisVertex.BoneWeights[0] = vertexWeights[faceVert.vertId()].BoneWeights[0]; - thisVertex.BoneWeights[1] = vertexWeights[faceVert.vertId()].BoneWeights[1]; - thisVertex.BoneWeights[2] = vertexWeights[faceVert.vertId()].BoneWeights[2]; - thisVertex.BoneWeights[3] = vertexWeights[faceVert.vertId()].BoneWeights[3]; + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[0]) > 0.0001) + thisVertex.BoneWeights[0] = vertexWeights[faceVert.vertId()].BoneWeights[0]; + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[1]) > 0.0001) + thisVertex.BoneWeights[1] = vertexWeights[faceVert.vertId()].BoneWeights[1]; + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[2]) > 0.0001) + thisVertex.BoneWeights[2] = vertexWeights[faceVert.vertId()].BoneWeights[2]; + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[3]) > 0.0001) + thisVertex.BoneWeights[3] = vertexWeights[faceVert.vertId()].BoneWeights[3]; - std::vector::iterator it = std::find(vertexList.begin(), vertexList.end(), thisVertex); - - if (it != vertexList.end()) { - localVertexToGlobalIndex.push_back(vertexIndex); - } else { - localVertexToGlobalIndex.push_back(vertexIndex); - vertexList.push_back(thisVertex); - } - - //cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; - //cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; - //cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; - //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; - //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; - } - - - for (unsigned int i = 0; i < triangleList.length(); i++) { - unsigned int k = 0; - if (localVertexToGlobalIndex.size() > 0) { - while (localVertexToGlobalIndex[k] != triangleList[i] && k < localVertexToGlobalIndex.size()) { - k++; + float totalWeight = thisVertex.BoneWeights[0] + thisVertex.BoneWeights[1] + thisVertex.BoneWeights[2] + thisVertex.BoneWeights[3]; + if (totalWeight < 1.00f && totalWeight > 0.01f) { + thisVertex.BoneWeights[0] /= totalWeight; + thisVertex.BoneWeights[1] /= totalWeight; + thisVertex.BoneWeights[2] /= totalWeight; + thisVertex.BoneWeights[3] /= totalWeight; } - indexList.push_back(indexOffset + k); - } + + std::vector::iterator it = std::find(vertexList.begin(), vertexList.end(), thisVertex); + array tmp; + if (it != vertexList.end()) { + tmp[0] = vertexIndex; + tmp[1] = it - vertexList.begin(); + localVertexToGlobalIndex.push_back(tmp); + } else { + tmp[0] = vertexIndex; + tmp[1] = vertexList.size(); + localVertexToGlobalIndex.push_back(tmp); + vertexList.push_back(thisVertex); + } + //MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1]: " + localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1][0] + " " + localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1][1]); + //cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; + //cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; + //cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; + //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; + //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; + } + for (unsigned int i = 0; i < triangleList.length(); i++) { + unsigned int k = 0; + if (localVertexToGlobalIndex.size() > 0) { + //MGlobal::displayInfo(MString() + "triangleList[i] : " + triangleList[i]); + while (localVertexToGlobalIndex[k][0] != triangleList[i] && k < localVertexToGlobalIndex.size()) { + k++; + } + //MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k] : " + localVertexToGlobalIndex[k][0] + " " + localVertexToGlobalIndex[k][1]); + indexLists[aMaterial.first.c_str()].push_back(localVertexToGlobalIndex[k][1]); + } + } } + // MGlobal::displayInfo( MString() + "localVertexToGlobalIndex.size(): " + localVertexToGlobalIndex.size()); + // if (localVertexToGlobalIndex.size() > 0) { + // MGlobal::displayInfo(MString() + "triangleList.length(): " + triangleList.length()); + // for (unsigned int i = triangleList.length() - 1; i >= 0; i--) { + // MGlobal::displayInfo(MString() + "i: " + i); + // unsigned int k = localVertexToGlobalIndex.size() - 1; + // MGlobal::displayInfo(MString() + "triangleList[i] : " + triangleList[i]); + // while (localVertexToGlobalIndex[k] != triangleList[i] && k >= 0) { + // MGlobal::displayInfo(MString() + "k: " + k); + // k--; + // } + // MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k] : " + localVertexToGlobalIndex[k]); + // indexList.push_back(indexOffset + k); + // } + // } } - newMesh.NumIndices = newMesh.Indices.size(); + + int totalIndecies = 0; + for (auto aList : newMesh.Indices) { + totalIndecies += aList.second.size(); + } + + newMesh.NumIndices = totalIndecies; newMesh.NumVertices = newMesh.Vertices.size(); return newMesh; diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h index ff7cc3b0..15c16913 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.h +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -3,6 +3,7 @@ #include #include +#include #include "OutputData.h" #include "MayaIncludes.h" @@ -10,20 +11,20 @@ class VertexLayout : public OutputData { public: - float Pos[3]; - float Normal[3]; - float Tangent[3]; - float BiNormal[3]; - float Uv[2]; - float BoneIndices[4]; - float BoneWeights[4]; + float Pos[3]{ 0 }; + float Normal[3]{ 0 }; + float Tangent[3]{ 0 }; + float BiNormal[3]{ 0 }; + float Uv[2]{ 0 }; + float BoneIndices[4]{ 0 }; + float BoneWeights[4]{ 0 }; virtual void WriteBinary(std::ostream& out) { out.write((char*)&Pos, sizeof(float) * 3); out.write((char*)&Normal, sizeof(float) * 3); out.write((char*)&Tangent, sizeof(float) * 3); - out.write((char*)&BiTangent, sizeof(float) * 3); + out.write((char*)&BiNormal, sizeof(float) * 3); out.write((char*)&Uv, sizeof(float) * 2); out.write((char*)&BoneIndices, sizeof(float) * 4); out.write((char*)&BoneWeights, sizeof(float) * 4); @@ -34,7 +35,7 @@ public: out << Pos[0] << " " << Pos[1] << " " << Pos[2] << endl; out << Normal[0] << " " << Normal[1] << " " << Normal[2] << endl; out << Tangent[0] << " " << Tangent[1] << " " << Tangent[2] << endl; - out << BiTangent[0] << " " << BiTangent[1] << " " << BiTangent[2] << endl; + out << BiNormal[0] << " " << BiNormal[1] << " " << BiNormal[2] << endl; out << Uv[0] << " " << Uv[1] << endl; out << BoneIndices[0] << " " << BoneIndices[1] << " " << BoneIndices[2] << " " << BoneIndices[3] << endl; out << BoneWeights[0] << " " << BoneWeights[1] << " " << BoneWeights[2] << " " << BoneWeights[3] << endl; @@ -46,7 +47,7 @@ public: this->Pos[0] == right.Pos[0] && this->Pos[1] == right.Pos[1] && this->Pos[2] == right.Pos[2] && this->Normal[0] == right.Normal[0] && this->Normal[1] == right.Normal[1] && this->Normal[2] == right.Normal[2] && this->Tangent[0] == right.Tangent[0] && this->Tangent[1] == right.Tangent[1] && this->Tangent[2] == right.Tangent[2] && - this->BiTangent[0] == right.BiTangent[0] && this->BiTangent[1] == right.BiTangent[1] && this->BiTangent[2] == right.BiTangent[2] && + this->BiNormal[0] == right.BiNormal[0] && this->BiNormal[1] == right.BiNormal[1] && this->BiNormal[2] == right.BiNormal[2] && this->Uv[0] == right.Uv[0] && this->Uv[1] == right.Uv[1] && this->BoneIndices[0] == right.BoneIndices[0] && this->BoneIndices[1] == right.BoneIndices[1] && this->BoneIndices[2] == right.BoneIndices[2] && this->BoneIndices[3] == right.BoneIndices[3] && this->BoneWeights[0] == right.BoneWeights[0] && this->BoneWeights[1] == right.BoneWeights[1] && this->BoneWeights[2] == right.BoneWeights[2] && this->BoneWeights[3] == right.BoneWeights[3] @@ -56,10 +57,10 @@ public: class Mesh : public OutputData { public: - int NumVertices; - int NumIndices; + unsigned int NumVertices; + unsigned int NumIndices; std::vector Vertices; - std::vector Indices; + std::map> Indices; virtual void WriteBinary(std::ostream& out) { @@ -69,7 +70,7 @@ public: aVertex.WriteBinary(out); } for (auto aIndex : Indices) { - out.write((char*)&aIndex, sizeof(int)); + out.write((char*)aIndex.second.data(), sizeof(int) * aIndex.second.size()); } } @@ -80,12 +81,16 @@ public: out << "number of indices: " << NumIndices << endl; int vertexNumber = 0; for (auto aVertex : Vertices) { - out << "New vertex number: " << vertexNumber << "_ not in binary" << endl; + out << "New vertex number: " << vertexNumber << " _ not in binary" << endl; aVertex.WriteASCII(out); vertexNumber++; } - for (int i = 0; i < NumIndices; i += 3) { - out << Indices[i] << " " << Indices[i+1] << " " << Indices[i + 2] << endl; + out << "New vertex Triangels: " << NumIndices/3 << " _ not in binary" << endl; + for (auto aIndexList : Indices) { + out << "Using Material: " << aIndexList.first << " _ not in binary" << endl; + for (int i = 0; i < aIndexList.second.size(); i += 3) { + out << aIndexList.second[i] << " " << aIndexList.second[i+1] << " " << aIndexList.second[i + 2] << endl; + } } } }; From 1760f9dfb17a39d1db34bc67c1c4d789450c4773 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 21:17:24 +0100 Subject: [PATCH 089/224] Added inequality operator to EntityWrapper --- include/Engine/Core/EntityWrapper.h | 1 + src/Engine/Core/EntityWrapper.cpp | 15 ++++++++++----- 2 files changed, 11 insertions(+), 5 deletions(-) diff --git a/include/Engine/Core/EntityWrapper.h b/include/Engine/Core/EntityWrapper.h index 79f90f33..74b5fc56 100644 --- a/include/Engine/Core/EntityWrapper.h +++ b/include/Engine/Core/EntityWrapper.h @@ -28,6 +28,7 @@ struct EntityWrapper ComponentWrapper operator[](const char* componentName); bool operator==(const EntityWrapper& e) const; + bool operator!=(const EntityWrapper& e) const; explicit operator EntityID() const; operator bool(); }; diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 8c1ab10d..5dc493ff 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -3,11 +3,6 @@ const EntityWrapper EntityWrapper::Invalid = EntityWrapper(nullptr, EntityID_Invalid); -bool EntityWrapper::operator==(const EntityWrapper& e) const -{ - return (this->World == e.World) && (this->ID == e.ID); -} - bool EntityWrapper::HasComponent(const std::string& componentName) { return World->HasComponent(ID, componentName); @@ -41,6 +36,16 @@ ComponentWrapper EntityWrapper::operator[](const char* componentName) } } +bool EntityWrapper::operator==(const EntityWrapper& e) const +{ + return (this->World == e.World) && (this->ID == e.ID); +} + +bool EntityWrapper::operator!=(const EntityWrapper& e) const +{ + return !this->operator==(e); +} + EntityWrapper::operator EntityID() const { return this->ID; From 3fc44e944caad07007e69a299f705a05a8eb6b82 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 21:18:23 +0100 Subject: [PATCH 090/224] Editor entity reparenting. --- assets | 2 +- include/Engine/Editor/EditorGUI.h | 16 ++- include/Engine/Editor/EditorSystem.h | 1 + src/Engine/Core/ComponentPool.cpp | 1 - src/Engine/Editor/EditorGUI.cpp | 161 ++++++++++++++++------- src/Engine/Editor/EditorSystem.cpp | 6 + src/Engine/Rendering/ImGuiRenderPass.cpp | 8 +- 7 files changed, 140 insertions(+), 55 deletions(-) diff --git a/assets b/assets index a3c92ac8..a1bb17db 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit a3c92ac876dd061776c36d1594bd82264372f028 +Subproject commit a1bb17dbe0da3d55932c2e187da50bc0257691f4 diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index d37d4c83..917d216f 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -13,13 +13,13 @@ #include "../Core/EventBroker.h" #include "../Core/World.h" #include "../Core/EntityWrapper.h" +#include "../Core/ResourceManager.h" +#include "../Rendering/Texture.h" class EditorGUI { public: - EditorGUI(EventBroker* eventBroker) - : m_EventBroker(eventBroker) - { } + EditorGUI(EventBroker* eventBroker); void Draw(World* world); @@ -46,6 +46,9 @@ public: // Called when the user means to delete an entity. typedef std::function OnEntityDelete_t; void SetEntityDeleteCallback(OnEntityDelete_t f) { m_OnEntityDelete = f; } + // Called when the user means to change the parent of an entity. + typedef std::function OnEntityChangeParent_t; + void SetEntityChangeParentCallback(OnEntityChangeParent_t f) { m_OnEntityChangeParent = f; } // Called when the user means to attach a new component to an entity. typedef std::function OnComponentAttach_t; void SetComponentAttachCallback(OnComponentAttach_t f) { m_OnComponentAttach = f; } @@ -62,6 +65,7 @@ private: // State variables EntityWrapper m_CurrentSelection = EntityWrapper::Invalid; std::unordered_map m_EntityFiles; + EntityWrapper m_CurrentlyDragging = EntityWrapper::Invalid; std::string m_LastErrorMessage; // Callbacks @@ -70,21 +74,25 @@ private: OnEntitySave_t m_OnEntitySave = nullptr; OnEntityCreate_t m_OnEntityCreate = nullptr; OnEntityDelete_t m_OnEntityDelete = nullptr; + OnEntityChangeParent_t m_OnEntityChangeParent = nullptr; OnComponentAttach_t m_OnComponentAttach = nullptr; OnComponentDelete_t m_OnComponentDelete = nullptr; // Utility functions boost::filesystem::path fileOpenDialog(); boost::filesystem::path fileSaveDialog(); + const std::string formatEntityName(EntityWrapper entity); // Entity file handling methods void entityImport(World* world); - void entitySave(EntityWrapper entity); + void entitySave(EntityWrapper entity, bool saveAs = false); void entityCreate(World* world, EntityWrapper parent); void entityDelete(EntityWrapper entity); + void entityChangeParent(EntityWrapper entity, EntityWrapper parent); // UI drawing methods void drawMenu(); + void drawTools(); void drawEntities(World* world); void drawEntitiesRecursive(World* world, EntityID parent); bool drawEntityNode(EntityWrapper entity); diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index fe8ef6ff..70ab2f15 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -40,6 +40,7 @@ private: void OnEntitySave(EntityWrapper entity, boost::filesystem::path filePath); EntityWrapper OnEntityCreate(EntityWrapper parent); void OnEntityDelete(EntityWrapper entity); + void OnEntityChangeParent(EntityWrapper entity, EntityWrapper parent); void OnComponentAttach(EntityWrapper entity, const std::string& componentType); void OnComponentDelete(EntityWrapper entity, const std::string& componentType); }; \ No newline at end of file diff --git a/src/Engine/Core/ComponentPool.cpp b/src/Engine/Core/ComponentPool.cpp index ce24c1f7..2ef64d71 100644 --- a/src/Engine/Core/ComponentPool.cpp +++ b/src/Engine/Core/ComponentPool.cpp @@ -50,7 +50,6 @@ ComponentWrapper ComponentPool::GetByEntity(EntityID ent) return ComponentWrapper(m_ComponentInfo, m_EntityToComponent.at(ent)); } - bool ComponentPool::KnowsEntity(EntityID ent) { return m_EntityToComponent.find(ent) != m_EntityToComponent.end(); diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 3cff403d..94aaceb4 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -1,9 +1,16 @@ #include "Editor/EditorGUI.h" +EditorGUI::EditorGUI(EventBroker* eventBroker) + : m_EventBroker(eventBroker) +{ + +} + void EditorGUI::Draw(World* world) { ImGui::ShowTestWindow(); drawMenu(); + drawTools(); drawEntities(world); drawComponents(m_CurrentSelection); } @@ -21,6 +28,34 @@ void EditorGUI::drawMenu() } +void EditorGUI::drawTools() +{ + if (!ImGui::Begin("Tools", nullptr, ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_AlwaysAutoResize)) { + return; + } + + GLuint translateIcon = 0; + try { + translateIcon = ResourceManager::Load("Textures/Icons/shaft.png")->m_Texture; + } catch (const std::exception&) { } + GLuint rotateIcon = 0; + try { + rotateIcon = ResourceManager::Load("Textures/Icons/circulararrows3.png")->m_Texture; + } catch (const std::exception&) { } + GLuint scaleIcon = 0; + try { + scaleIcon = ResourceManager::Load("Textures/Icons/increase10.png")->m_Texture; + } catch (const std::exception&) { } + + ImGui::ImageButton((void*)translateIcon, ImVec2(24, 24)); + ImGui::SameLine(); + ImGui::ImageButton((void*)rotateIcon, ImVec2(24, 24)); + ImGui::SameLine(); + ImGui::ImageButton((void*)scaleIcon, ImVec2(24, 24)); + + ImGui::End(); +} + void EditorGUI::drawEntities(World* world) { if (!ImGui::Begin("Entities")) { @@ -61,6 +96,7 @@ void EditorGUI::drawEntitiesRecursive(World* world, EntityID parent) bool EditorGUI::drawEntityNode(EntityWrapper entity) { + // Custom button hitbox to select entities on top of tree node ImVec2 pos = ImGui::GetCursorScreenPos(); float width = ImGui::GetContentRegionAvailWidth(); ImRect bb(pos + ImVec2(20, 0), pos + ImVec2(width, 14)); @@ -75,52 +111,52 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) if (ImGui::ButtonBehavior(bb, id, &hovered, &held)) { SelectEntity(entity); } - //if (held) { - // ImVec2 entityDragDelta = ImGui::GetMouseDragDelta(0); - // if (std::abs(entityDragDelta.x) > 0 && std::abs(entityDragDelta.y) > 0) { - // if (m_UIDraggingEntity == EntityID_Invalid) { - // m_UIDraggingEntity = entity; - // LOG_DEBUG("Started drag of entity %i", m_UIDraggingEntity); - // } - // ImGui::SetNextWindowPos(ImGui::GetIO().MousePos + ImVec2(20, 0)); - // ImGui::Begin("Change parent", nullptr, ImVec2(0, 0), 0.3f, ImGuiWindowFlags_NoTitleBar|ImGuiWindowFlags_NoResize|ImGuiWindowFlags_NoMove|ImGuiWindowFlags_NoSavedSettings); - // ImGui::Text("#%i", m_UIDraggingEntity); - // ImGui::End(); - // } - //} - - // Compose title - std::stringstream nodeTitle; - const std::string& entityName = entity.World->GetName(entity); - if (!entityName.empty()) { - nodeTitle << entityName; - } else { - nodeTitle << "#" << entity.ID; + // Handle entity dragging + if (held) { + ImVec2 entityDragDelta = ImGui::GetMouseDragDelta(0); + if (std::abs(entityDragDelta.x) > 0 && std::abs(entityDragDelta.y) > 0) { + if (m_CurrentlyDragging == EntityWrapper::Invalid) { + m_CurrentlyDragging = entity; + LOG_DEBUG("Started dragging %i", entity.ID); + } + ImGui::SetNextWindowPos(ImGui::GetIO().MousePos + ImVec2(20, 0)); + ImGui::Begin("Change parent", nullptr, ImVec2(0, 0), 0.3f, ImGuiWindowFlags_NoTitleBar|ImGuiWindowFlags_NoResize|ImGuiWindowFlags_NoMove|ImGuiWindowFlags_NoSavedSettings); + ImGui::Text(formatEntityName(entity).c_str()); + ImGui::End(); + } + } else if (m_CurrentlyDragging == entity) { + LOG_DEBUG("Stopped dragging %i", entity.ID); + m_CurrentlyDragging = EntityWrapper::Invalid; } - if (m_EntityFiles.count(entity) == 1) { - nodeTitle << " (" << m_EntityFiles.at(entity).filename().string() << ")"; + // Entity context menu + std::string contextMenuUniqueID = std::string("EntityContextMenu") + std::to_string(entity.ID); + if (hovered && ImGui::IsMouseClicked(1)) { + ImGui::OpenPopup(contextMenuUniqueID.c_str()); + } + if (ImGui::BeginPopup(contextMenuUniqueID.c_str())) { + ImGui::TextDisabled(formatEntityName(entity).c_str()); + if (ImGui::MenuItem("Save", "Ctrl+S")) { + entitySave(entity); + } else + if (ImGui::MenuItem("Save As...", "Ctrl+Shift+S")) { + entitySave(entity, true); + } else + if (ImGui::MenuItem("Delete", "Del")) { + entityDelete(entity); + } else + if (ImGui::MenuItem("Move to root")) { + entityChangeParent(entity, EntityWrapper::Invalid); + } + drawModals(); + ImGui::EndPopup(); } ImGui::SetNextTreeNodeOpened(true, ImGuiSetCond_Once); - if (ImGui::TreeNode(nodeTitle.str().c_str())) { - //if (m_UIDraggingEntity != EntityID_Invalid && ImGui::IsItemHoveredRect() && ImGui::IsMouseReleased(0)) { - // LOG_DEBUG("Changed parent of %i to %i", m_UIDraggingEntity, entity); - // changeParent(m_UIDraggingEntity, entity); - // m_UIDraggingEntity = EntityID_Invalid; - //} - - if (ImGui::BeginPopupContextItem("entity context menu")) { - if (ImGui::Button("Save")) { - entitySave(entity); - ImGui::CloseCurrentPopup(); - } - ImGui::SameLine(); - if (ImGui::Button("Delete")) { - entityDelete(entity); - ImGui::CloseCurrentPopup(); - } - drawModals(); - ImGui::EndPopup(); + if (ImGui::TreeNode(formatEntityName(entity).c_str())) { + // Handle drop events for reparenting + if (m_CurrentlyDragging != EntityWrapper::Invalid && ImGui::IsItemHoveredRect() && ImGui::IsMouseReleased(0)) { + entityChangeParent(m_CurrentlyDragging, entity); + m_CurrentlyDragging = EntityWrapper::Invalid; } return true; } else { @@ -133,7 +169,7 @@ void EditorGUI::drawComponents(EntityWrapper entity) std::stringstream title; title << "Components"; if (entity.Valid()) { - title << " #" << entity.ID << "###Components"; + title << formatEntityName(entity) << "###Components"; } if (!ImGui::Begin(title.str().c_str())) { ImGui::End(); @@ -380,6 +416,7 @@ bool EditorGUI::createDeleteButton(const std::string& componentType) return pressed; } + boost::filesystem::path EditorGUI::fileOpenDialog() { namespace bfs = boost::filesystem; @@ -412,6 +449,28 @@ boost::filesystem::path EditorGUI::fileSaveDialog() } } +const std::string EditorGUI::formatEntityName(EntityWrapper entity) +{ + if (!entity.Valid()) { + return "EntityID_Invalid"; + } + + std::stringstream name; + + const std::string& entityName = entity.World->GetName(entity); + if (!entityName.empty()) { + name << entityName; + } else { + name << "#" << entity.ID; + } + + if (m_EntityFiles.count(entity) == 1) { + name << " (" << m_EntityFiles.at(entity).filename().string() << ")"; + } + + return name.str(); +} + void EditorGUI::entityImport(World* world) { boost::filesystem::path filePath = fileOpenDialog(); @@ -428,10 +487,10 @@ void EditorGUI::entityImport(World* world) } } -void EditorGUI::entitySave(EntityWrapper entity) +void EditorGUI::entitySave(EntityWrapper entity, bool saveAs /* = false */) { boost::filesystem::path filePath; - if (m_EntityFiles.count(entity) == 1) { + if (!saveAs && m_EntityFiles.count(entity) == 1) { filePath = m_EntityFiles.at(entity); } else { filePath = fileSaveDialog(); @@ -472,3 +531,15 @@ void EditorGUI::entityDelete(EntityWrapper entity) SelectEntity(EntityWrapper::Invalid); } } + +void EditorGUI::entityChangeParent(EntityWrapper entity, EntityWrapper parent) +{ + if (entity == parent) { + return; + } + + if (m_OnEntityChangeParent != nullptr) { + m_OnEntityChangeParent(entity, parent); + LOG_DEBUG("Changed parent of %i to %i", entity.ID, parent.ID); + } +} diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 51ab2f1f..b1e09422 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -25,6 +25,7 @@ EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, Render m_EditorGUI->SetEntitySaveCallback(std::bind(&EditorSystem::OnEntitySave, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetEntityCreateCallback(std::bind(&EditorSystem::OnEntityCreate, this, std::placeholders::_1)); m_EditorGUI->SetEntityDeleteCallback(std::bind(&EditorSystem::OnEntityDelete, this, std::placeholders::_1)); + m_EditorGUI->SetEntityChangeParentCallback(std::bind(&EditorSystem::OnEntityChangeParent, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetComponentAttachCallback(std::bind(&EditorSystem::OnComponentAttach, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetComponentDeleteCallback(std::bind(&EditorSystem::OnComponentDelete, this, std::placeholders::_1, std::placeholders::_2)); @@ -79,6 +80,11 @@ void EditorSystem::OnEntityDelete(EntityWrapper entity) entity.World->DeleteEntity(entity.ID); } +void EditorSystem::OnEntityChangeParent(EntityWrapper entity, EntityWrapper parent) +{ + entity.World->SetParent(entity.ID, parent.ID); +} + void EditorSystem::OnComponentAttach(EntityWrapper entity, const std::string& componentType) { entity.World->AttachComponent(entity.ID, componentType); diff --git a/src/Engine/Rendering/ImGuiRenderPass.cpp b/src/Engine/Rendering/ImGuiRenderPass.cpp index 96f987d9..e67eea71 100644 --- a/src/Engine/Rendering/ImGuiRenderPass.cpp +++ b/src/Engine/Rendering/ImGuiRenderPass.cpp @@ -105,7 +105,7 @@ void ImGuiRenderPass::Draw() if (pcmd->UserCallback) { pcmd->UserCallback(cmd_list, pcmd); } else { - glBindTexture(GL_TEXTURE_2D, (GLuint)(intptr_t)pcmd->TextureId); + glBindTexture(GL_TEXTURE_2D, (GLuint)pcmd->TextureId); glScissor((int)pcmd->ClipRect.x, (int)(fb_height - pcmd->ClipRect.w), (int)(pcmd->ClipRect.z - pcmd->ClipRect.x), (int)(pcmd->ClipRect.w - pcmd->ClipRect.y)); glDrawElements(GL_TRIANGLES, (GLsizei)pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, idx_buffer_offset); } @@ -190,7 +190,7 @@ bool ImGuiRenderPass::createDeviceObjects() "{\n" " Frag_UV = UV;\n" " Frag_Color = Color;\n" - " gl_Position = ProjMtx * vec4(Position.xy,0,1);\n" + " gl_Position = ProjMtx * vec4(Position.xy, 0, 1);\n" "}\n"; const GLchar* fragment_shader = @@ -201,7 +201,7 @@ bool ImGuiRenderPass::createDeviceObjects() "out vec4 Out_Color;\n" "void main()\n" "{\n" - " Out_Color = Frag_Color * texture( Texture, Frag_UV.st);\n" + " Out_Color = Frag_Color * texture(Texture, Frag_UV.st);\n" "}\n"; g_ShaderHandle = glCreateProgram(); @@ -271,7 +271,7 @@ bool ImGuiRenderPass::createFontsTexture() glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels); // Store our identifier - io.Fonts->TexID = (void *)(intptr_t)g_FontTexture; + io.Fonts->TexID = (void*)g_FontTexture; // Restore state glBindTexture(GL_TEXTURE_2D, last_texture); From 51979d7f0ca38f4b4ec8d75f970198715caccaf0 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 23:59:33 +0100 Subject: [PATCH 091/224] Changed System to take World through constructor and store it instead, cause it makes more sense. --- .../Engine/Collision/CollidableOctreeSystem.h | 8 +++--- include/Engine/Collision/CollisionSystem.h | 6 ++--- include/Engine/Collision/TriggerSystem.h | 6 ++--- include/Engine/Core/System.h | 14 +++++------ include/Engine/Core/SystemPipeline.h | 18 +++++++------ include/Engine/Core/UniformScaleSystem.h | 4 +-- include/Engine/Editor/EditorRenderSystem.h | 4 +-- include/Engine/Editor/EditorSystem.h | 4 +-- include/Engine/Editor/EditorSystemOld.h | 5 ++-- include/Engine/Rendering/RenderSystem.h | 9 +++---- include/Game/Systems/HealthSystem.h | 4 +-- include/Game/Systems/PlayerMovementSystem.h | 6 ++--- include/Game/Systems/PlayerSpawnSystem.h | 4 +-- include/Game/Systems/PlayerSystem.h | 6 ++--- include/Game/Systems/RaptorCopterSystem.h | 8 +++--- include/Game/Systems/SpawnerSystem.h | 2 +- .../Collision/CollidableOctreeSystem.cpp | 4 +-- src/Engine/Collision/CollisionSystem.cpp | 2 +- src/Engine/Collision/TriggerSystem.cpp | 6 ++--- src/Engine/Core/UniformScaleSystem.cpp | 6 ++--- src/Engine/Editor/EditorRenderSystem.cpp | 14 +++++------ src/Engine/Editor/EditorSystem.cpp | 12 ++++----- src/Engine/Editor/EditorSystemOld.cpp | 10 +++----- src/Engine/Rendering/RenderSystem.cpp | 25 +++++++++---------- src/Game/Game.cpp | 4 +-- src/Game/Systems/HealthSystem.cpp | 8 +++--- src/Game/Systems/PlayerMovementSystem.cpp | 2 +- src/Game/Systems/PlayerSpawnSystem.cpp | 10 ++++---- src/Game/Systems/PlayerSystem.cpp | 4 +-- src/Game/Systems/SpawnerSystem.cpp | 3 ++- src/Tests/HealthSystemTest.cpp | 2 +- src/Tests/OctTreeTestGameClass.cpp | 2 +- 32 files changed, 111 insertions(+), 111 deletions(-) diff --git a/include/Engine/Collision/CollidableOctreeSystem.h b/include/Engine/Collision/CollidableOctreeSystem.h index 8fa1f0a4..5b677186 100644 --- a/include/Engine/Collision/CollidableOctreeSystem.h +++ b/include/Engine/Collision/CollidableOctreeSystem.h @@ -8,14 +8,14 @@ class CollidableOctreeSystem : public ImpureSystem, public PureSystem { public: - CollidableOctreeSystem(EventBroker* eventBroker, Octree* octree) - : System(eventBroker) + CollidableOctreeSystem(World* world, EventBroker* eventBroker, Octree* octree) + : System(world, eventBroker) , PureSystem("Collidable") , m_Octree(octree) { } - virtual void Update(World* world, double dt) override; - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; + virtual void Update(double dt) override; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: Octree* m_Octree; diff --git a/include/Engine/Collision/CollisionSystem.h b/include/Engine/Collision/CollisionSystem.h index ea6004d9..6abbf802 100644 --- a/include/Engine/Collision/CollisionSystem.h +++ b/include/Engine/Collision/CollisionSystem.h @@ -13,8 +13,8 @@ class CollisionSystem : public PureSystem { public: - CollisionSystem(EventBroker* eventBroker, Octree* octree) - : System(eventBroker) + CollisionSystem(World* world, EventBroker* eventBroker, Octree* octree) + : System(world, eventBroker) , PureSystem("AABB") , m_Octree(octree) , zPress(false) @@ -23,7 +23,7 @@ public: EVENT_SUBSCRIBE_MEMBER(m_EKeyUp, &CollisionSystem::OnKeyUp); } - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: Octree* m_Octree; diff --git a/include/Engine/Collision/TriggerSystem.h b/include/Engine/Collision/TriggerSystem.h index ee53ad9b..23de924f 100644 --- a/include/Engine/Collision/TriggerSystem.h +++ b/include/Engine/Collision/TriggerSystem.h @@ -14,13 +14,13 @@ class AABB; class TriggerSystem : public PureSystem { public: - TriggerSystem(EventBroker* eventBroker, Octree* octree) - : System(eventBroker) + TriggerSystem(World* world, EventBroker* eventBroker, Octree* octree) + : System(world, eventBroker) , PureSystem("Trigger") , m_Octree(octree) { } - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: Octree* m_Octree; diff --git a/include/Engine/Core/System.h b/include/Engine/Core/System.h index b7de9dc2..dc7c879a 100644 --- a/include/Engine/Core/System.h +++ b/include/Engine/Core/System.h @@ -11,14 +11,14 @@ class System friend class SystemPipeline; protected: - System() - : m_EventBroker(nullptr) - { } - System(EventBroker* eventBroker) - : m_EventBroker(eventBroker) + System(World* world, EventBroker) { } + System(World* world, EventBroker* eventBroker) + : m_World(world) + , m_EventBroker(eventBroker) { } virtual ~System() = default; + World* m_World; EventBroker* m_EventBroker; }; @@ -34,7 +34,7 @@ protected: const std::string m_ComponentType; - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) = 0; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) = 0; }; class ImpureSystem : public virtual System @@ -45,7 +45,7 @@ protected: ImpureSystem() = default; virtual ~ImpureSystem() = default; - virtual void Update(World* world, double dt) = 0; + virtual void Update(double dt) = 0; }; #endif \ No newline at end of file diff --git a/include/Engine/Core/SystemPipeline.h b/include/Engine/Core/SystemPipeline.h index c0cd8ed6..cc3c98e9 100644 --- a/include/Engine/Core/SystemPipeline.h +++ b/include/Engine/Core/SystemPipeline.h @@ -9,9 +9,11 @@ class SystemPipeline { public: - SystemPipeline(EventBroker* eventBroker) - : m_EventBroker(eventBroker) + SystemPipeline(World* world, EventBroker* eventBroker) + : m_World(world) + , m_EventBroker(eventBroker) { } + ~SystemPipeline() { for (UnorderedSystems& group : m_OrderedSystemGroups) { @@ -29,7 +31,7 @@ public: m_OrderedSystemGroups.resize(updateOrderLevel + 1); } UnorderedSystems& group = m_OrderedSystemGroups[updateOrderLevel]; - System* system = new T(m_EventBroker, args...); + System* system = new T(m_World, m_EventBroker, args...); group.Systems[typeid(T).name()] = system; PureSystem* pureSystem = dynamic_cast(system); @@ -47,7 +49,7 @@ public: } } - void Update(World* world, double dt) + void Update(double dt) { for (UnorderedSystems& group : m_OrderedSystemGroups) { // Process events @@ -57,18 +59,18 @@ public: // Update for (auto& system : group.ImpureSystems) { - system->Update(world, dt); + system->Update(dt); } for (auto& pair : group.PureSystems) { const std::string& componentName = pair.first; auto& systems = pair.second; - const ComponentPool* pool = world->GetComponents(componentName); + const ComponentPool* pool = m_World->GetComponents(componentName); if (pool == nullptr) { continue; } for (auto& component : *pool) { for (auto& system : systems) { - system->UpdateComponent(world, EntityWrapper(world, component.EntityID), component, dt); + system->UpdateComponent(EntityWrapper(m_World, component.EntityID), component, dt); } } } @@ -76,7 +78,9 @@ public: } private: + World* m_World; EventBroker* m_EventBroker; + struct UnorderedSystems { std::map Systems; diff --git a/include/Engine/Core/UniformScaleSystem.h b/include/Engine/Core/UniformScaleSystem.h index f44409f0..0ebc0672 100644 --- a/include/Engine/Core/UniformScaleSystem.h +++ b/include/Engine/Core/UniformScaleSystem.h @@ -8,9 +8,9 @@ class UniformScaleSystem : public PureSystem { public: - UniformScaleSystem(EventBroker* eventBroker); + UniformScaleSystem(World* world, EventBroker* eventBroker); - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) override; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) override; private: EntityWrapper m_Camera = EntityWrapper::Invalid; diff --git a/include/Engine/Editor/EditorRenderSystem.h b/include/Engine/Editor/EditorRenderSystem.h index c593e29a..361669ba 100644 --- a/include/Engine/Editor/EditorRenderSystem.h +++ b/include/Engine/Editor/EditorRenderSystem.h @@ -10,9 +10,9 @@ class EditorRenderSystem : public ImpureSystem { public: - EditorRenderSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame); + EditorRenderSystem(World* world, EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame); - virtual void Update(World* world, double dt) override; + virtual void Update(double dt) override; private: IRenderer* m_Renderer; diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index 70ab2f15..8ae3ac2e 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -15,10 +15,10 @@ class EditorSystem : public ImpureSystem { public: - EditorSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame); + EditorSystem(World* world, EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame); ~EditorSystem(); - void Update(World* world, double dt); + void Update(double dt); private: IRenderer* m_Renderer; diff --git a/include/Engine/Editor/EditorSystemOld.h b/include/Engine/Editor/EditorSystemOld.h index b2d7df0c..d49c3542 100644 --- a/include/Engine/Editor/EditorSystemOld.h +++ b/include/Engine/Editor/EditorSystemOld.h @@ -18,13 +18,12 @@ class EditorSystemOld : public ImpureSystem { public: - EditorSystemOld(EventBroker* eventBroker, IRenderer* renderer); + EditorSystemOld(World* world, EventBroker* eventBroker, IRenderer* renderer); - virtual void Update(World* world, double dt) override; + virtual void Update(double dt) override; private: IRenderer* m_Renderer; - World* m_World = nullptr; Camera* m_Camera = nullptr; bool m_Enabled; diff --git a/include/Engine/Rendering/RenderSystem.h b/include/Engine/Rendering/RenderSystem.h index 39b35108..198e22ee 100644 --- a/include/Engine/Rendering/RenderSystem.h +++ b/include/Engine/Rendering/RenderSystem.h @@ -20,13 +20,12 @@ class RenderSystem : public ImpureSystem { public: - RenderSystem(EventBroker* eventBrokerer, const IRenderer* renderer, RenderFrame* renderFrame); + RenderSystem(World* world, EventBroker* eventBrokerer, const IRenderer* renderer, RenderFrame* renderFrame); ~RenderSystem(); - virtual void Update(World* world, double dt) override; + virtual void Update(double dt) override; private: - World* m_World = nullptr; const IRenderer* m_Renderer; RenderFrame* m_RenderFrame; Camera* m_Camera; @@ -37,8 +36,8 @@ private: EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); - void fillModels(std::list>& jobs, World* world); - void fillLight(std::list>& jobs, World* world); + void fillModels(std::list>& jobs); + void fillLight(std::list>& jobs); }; #endif \ No newline at end of file diff --git a/include/Game/Systems/HealthSystem.h b/include/Game/Systems/HealthSystem.h index 0db3ec41..f9843f11 100644 --- a/include/Game/Systems/HealthSystem.h +++ b/include/Game/Systems/HealthSystem.h @@ -16,10 +16,10 @@ class HealthSystem : public PureSystem { public: - HealthSystem(EventBroker* eventBroker); + HealthSystem(World* world, EventBroker* eventBroker); //updatecomponent - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: //methods which will take care of specific events diff --git a/include/Game/Systems/PlayerMovementSystem.h b/include/Game/Systems/PlayerMovementSystem.h index 6dc2dc31..1be61bdd 100644 --- a/include/Game/Systems/PlayerMovementSystem.h +++ b/include/Game/Systems/PlayerMovementSystem.h @@ -5,10 +5,10 @@ class PlayerMovementSystem : public PureSystem { public: - PlayerMovementSystem(EventBroker* eventBroker) - : System(eventBroker) + PlayerMovementSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) , PureSystem("Player") { } - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt); + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt); }; \ No newline at end of file diff --git a/include/Game/Systems/PlayerSpawnSystem.h b/include/Game/Systems/PlayerSpawnSystem.h index f0e10949..8ade03a6 100644 --- a/include/Game/Systems/PlayerSpawnSystem.h +++ b/include/Game/Systems/PlayerSpawnSystem.h @@ -6,9 +6,9 @@ class PlayerSpawnSystem : public ImpureSystem { public: - PlayerSpawnSystem(EventBroker* eventBroker); + PlayerSpawnSystem(World* world, EventBroker* eventBroker); - virtual void Update(World* world, double dt) override; + virtual void Update(double dt) override; private: EventRelay m_OnInputCommand; diff --git a/include/Game/Systems/PlayerSystem.h b/include/Game/Systems/PlayerSystem.h index a74cbb9f..fdf1132b 100644 --- a/include/Game/Systems/PlayerSystem.h +++ b/include/Game/Systems/PlayerSystem.h @@ -11,8 +11,8 @@ class PlayerSystem : public PureSystem { public: - PlayerSystem(EventBroker* eventBroker) - : System(eventBroker) + PlayerSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) , PureSystem("Player") { EVENT_SUBSCRIBE_MEMBER(m_ETouch, &PlayerSystem::OnTouch); @@ -20,7 +20,7 @@ public: EVENT_SUBSCRIBE_MEMBER(m_ELeave, &PlayerSystem::OnLeave); } - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: float m_Speed = 5; EventRelay m_EEnter; diff --git a/include/Game/Systems/RaptorCopterSystem.h b/include/Game/Systems/RaptorCopterSystem.h index 57a8de86..8bb18de6 100644 --- a/include/Game/Systems/RaptorCopterSystem.h +++ b/include/Game/Systems/RaptorCopterSystem.h @@ -4,14 +4,14 @@ class RaptorCopterSystem : public PureSystem { public: - RaptorCopterSystem(EventBroker* eventBroker) - : System(eventBroker) + RaptorCopterSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) , PureSystem("RaptorCopter") { } - virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override { - ComponentWrapper& transform = world->GetComponent(component.EntityID, "Transform"); + ComponentWrapper& transform = m_World->GetComponent(component.EntityID, "Transform"); (glm::vec3&)transform["Orientation"] += (float)(double)component["Speed"] * (float)dt * (glm::vec3)component["Axis"]; } }; \ No newline at end of file diff --git a/include/Game/Systems/SpawnerSystem.h b/include/Game/Systems/SpawnerSystem.h index 2c094528..62f6b09a 100644 --- a/include/Game/Systems/SpawnerSystem.h +++ b/include/Game/Systems/SpawnerSystem.h @@ -13,7 +13,7 @@ class SpawnerSystem : public System { public: - SpawnerSystem(EventBroker* eventBroker); + SpawnerSystem(World* world, EventBroker* eventBroker); static EntityWrapper Spawn(EntityWrapper spawner, EntityWrapper parent = EntityWrapper::Invalid); diff --git a/src/Engine/Collision/CollidableOctreeSystem.cpp b/src/Engine/Collision/CollidableOctreeSystem.cpp index 62d742f5..e5da7910 100644 --- a/src/Engine/Collision/CollidableOctreeSystem.cpp +++ b/src/Engine/Collision/CollidableOctreeSystem.cpp @@ -1,11 +1,11 @@ #include "Collision/CollidableOctreeSystem.h" -void CollidableOctreeSystem::Update(World* world, double dt) +void CollidableOctreeSystem::Update(double dt) { m_Octree->ClearDynamicObjects(); } -void CollidableOctreeSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) +void CollidableOctreeSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { if (entity.HasComponent("AABB")) { boost::optional absoluteAABB = Collision::EntityAbsoluteAABB(entity); diff --git a/src/Engine/Collision/CollisionSystem.cpp b/src/Engine/Collision/CollisionSystem.cpp index 96e49153..d4903c5e 100644 --- a/src/Engine/Collision/CollisionSystem.cpp +++ b/src/Engine/Collision/CollisionSystem.cpp @@ -2,7 +2,7 @@ #include "Collision/CollisionSystem.h" #include "Core/AABB.h" -void CollisionSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) +void CollisionSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { if (!entity.HasComponent("Physics")) { return; diff --git a/src/Engine/Collision/TriggerSystem.cpp b/src/Engine/Collision/TriggerSystem.cpp index 58d1e332..20d30ae1 100644 --- a/src/Engine/Collision/TriggerSystem.cpp +++ b/src/Engine/Collision/TriggerSystem.cpp @@ -3,10 +3,10 @@ #include "Core/AABB.h" #include "Rendering/Model.h" -void TriggerSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) +void TriggerSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { //Currently only players can trigger things. - auto players = world->GetComponents("Player"); + auto players = m_World->GetComponents("Player"); if (players == nullptr) { return; } @@ -18,7 +18,7 @@ void TriggerSystem::UpdateComponent(World* world, EntityWrapper& entity, Compone } for (auto& pc : *players) { EntityID pId = pc.EntityID; - boost::optional playerBox = Collision::EntityAbsoluteAABB(EntityWrapper(world, pId)); + boost::optional playerBox = Collision::EntityAbsoluteAABB(EntityWrapper(m_World, pId)); //The player can't trigger anything without an AABB. if (!playerBox) { continue; diff --git a/src/Engine/Core/UniformScaleSystem.cpp b/src/Engine/Core/UniformScaleSystem.cpp index 8cf670fc..ab954a05 100644 --- a/src/Engine/Core/UniformScaleSystem.cpp +++ b/src/Engine/Core/UniformScaleSystem.cpp @@ -1,13 +1,13 @@ #include "Core/UniformScaleSystem.h" -UniformScaleSystem::UniformScaleSystem(EventBroker* eventBroker) - : System(eventBroker) +UniformScaleSystem::UniformScaleSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) , PureSystem("UniformScale") { EVENT_SUBSCRIBE_MEMBER(m_ESetCamera, &UniformScaleSystem::OnSetCamera); } -void UniformScaleSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) +void UniformScaleSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) { if (!m_Camera.Valid()) { return; diff --git a/src/Engine/Editor/EditorRenderSystem.cpp b/src/Engine/Editor/EditorRenderSystem.cpp index 2d25338d..d320a198 100644 --- a/src/Engine/Editor/EditorRenderSystem.cpp +++ b/src/Engine/Editor/EditorRenderSystem.cpp @@ -1,7 +1,7 @@ #include "Editor/EditorRenderSystem.h" -EditorRenderSystem::EditorRenderSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame) - : System(eventBroker) +EditorRenderSystem::EditorRenderSystem(World* m_World, EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame) + : System(m_World, eventBroker) , m_Renderer(renderer) , m_RenderFrame(renderFrame) { @@ -10,7 +10,7 @@ EditorRenderSystem::EditorRenderSystem(EventBroker* eventBroker, IRenderer* rend m_EditorCamera = new Camera((float)resolution.Width / resolution.Height, glm::radians(45.f), 0.01f, 5000.f); } -void EditorRenderSystem::Update(World* world, double dt) +void EditorRenderSystem::Update(double dt) { if (m_CurrentCamera) { ComponentWrapper cameraTransform = m_CurrentCamera["Transform"]; @@ -23,7 +23,7 @@ void EditorRenderSystem::Update(World* world, double dt) scene.Camera = m_EditorCamera; scene.Viewport = Rectangle(1920, 1080); - auto models = world->GetComponents("Model"); + auto models = m_World->GetComponents("Model"); if (models != nullptr) { for (auto& cModel : *models) { if (!(bool)cModel["Visible"]) { @@ -45,7 +45,7 @@ void EditorRenderSystem::Update(World* world, double dt) } } - EntityWrapper entity(world, cModel.EntityID); + EntityWrapper entity(m_World, cModel.EntityID); glm::mat4 modelMatrix = Transform::ModelMatrix(entity.ID, entity.World); for (auto matGroup : model->MaterialGroups()) { std::shared_ptr modelJob = std::make_shared(model, nullptr, modelMatrix, matGroup, cModel, entity.World); @@ -54,7 +54,7 @@ void EditorRenderSystem::Update(World* world, double dt) } } - auto pointLights = world->GetComponents("PointLight"); + auto pointLights = m_World->GetComponents("PointLight"); if (pointLights != nullptr) { for (auto& cPointLight : *pointLights) { bool visible = cPointLight["Visible"]; @@ -62,7 +62,7 @@ void EditorRenderSystem::Update(World* world, double dt) continue; } - EntityWrapper entity(world, cPointLight.EntityID); + EntityWrapper entity(m_World, cPointLight.EntityID); ComponentWrapper& cTransform = entity["Transform"]; std::shared_ptr pointLightJob = std::make_shared(cTransform, cPointLight, entity.World); scene.PointLightJobs.push_back(pointLightJob); diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index b1e09422..64f16cc6 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -2,13 +2,13 @@ #include "Core/UniformScaleSystem.h" #include "Editor/EditorRenderSystem.h" -EditorSystem::EditorSystem(EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame) - : System(eventBroker) +EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame) + : System(world, eventBroker) , m_Renderer(renderer) , m_RenderFrame(renderFrame) { m_EditorWorld = new World(); - m_EditorWorldSystemPipeline = new SystemPipeline(eventBroker); + m_EditorWorldSystemPipeline = new SystemPipeline(m_EditorWorld, eventBroker); m_EditorWorldSystemPipeline->AddSystem(0); m_EditorWorldSystemPipeline->AddSystem(1, m_Renderer, m_RenderFrame); @@ -45,11 +45,11 @@ EditorSystem::~EditorSystem() delete m_EditorWorld; } -void EditorSystem::Update(World* world, double dt) +void EditorSystem::Update(double dt) { - m_EditorWorldSystemPipeline->Update(m_EditorWorld, dt); + m_EditorWorldSystemPipeline->Update(dt); - m_EditorGUI->Draw(world); + m_EditorGUI->Draw(m_World); m_EditorStats->Draw(dt); m_DebugCameraInputController->Update(dt); diff --git a/src/Engine/Editor/EditorSystemOld.cpp b/src/Engine/Editor/EditorSystemOld.cpp index 675ea80b..332bef05 100644 --- a/src/Engine/Editor/EditorSystemOld.cpp +++ b/src/Engine/Editor/EditorSystemOld.cpp @@ -2,8 +2,8 @@ #define IMGUI_DEFINE_MATH_OPERATORS #include -EditorSystemOld::EditorSystemOld(EventBroker* eventBroker, IRenderer* renderer) - : System(eventBroker) +EditorSystemOld::EditorSystemOld(World* world, EventBroker* eventBroker, IRenderer* renderer) + : System(world, eventBroker) , ImpureSystem() , m_Renderer(renderer) { @@ -23,10 +23,8 @@ EditorSystemOld::EditorSystemOld(EventBroker* eventBroker, IRenderer* renderer) EVENT_SUBSCRIBE_MEMBER(m_EFileDropped, &EditorSystemOld::OnFileDropped); } -void EditorSystemOld::Update(World* world, double dt) +void EditorSystemOld::Update(double dt) { - m_World = world; - if (!m_Enabled) { return; } @@ -37,7 +35,7 @@ void EditorSystemOld::Update(World* world, double dt) Picking(); updateWidget(); - drawUI(world, dt); + drawUI(m_World, dt); // Clear drop queue if it wasn't handled by any UI element if (!m_LastDroppedFile.empty()) { diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 2af782e3..7b26bdad 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -1,7 +1,7 @@ #include "Rendering/RenderSystem.h" -RenderSystem::RenderSystem(EventBroker* eventBroker, const IRenderer* renderer, RenderFrame* renderFrame) - : System(eventBroker) +RenderSystem::RenderSystem(World* world, EventBroker* eventBroker, const IRenderer* renderer, RenderFrame* renderFrame) + : System(world, eventBroker) , m_Renderer(renderer) , m_RenderFrame(renderFrame) { @@ -29,9 +29,9 @@ bool RenderSystem::OnSetCamera(Events::SetCamera& e) return true; } -void RenderSystem::fillModels(std::list>& jobs, World* world) +void RenderSystem::fillModels(std::list>& jobs) { - auto models = world->GetComponents("Model"); + auto models = m_World->GetComponents("Model"); if (models == nullptr) { return; } @@ -60,17 +60,17 @@ void RenderSystem::fillModels(std::list>& jobs, World } } - glm::mat4 modelMatrix = Transform::ModelMatrix(modelComponent.EntityID, world); + glm::mat4 modelMatrix = Transform::ModelMatrix(modelComponent.EntityID, m_World); for (auto matGroup : model->MaterialGroups()) { - std::shared_ptr modelJob = std::shared_ptr(new ModelJob(model, m_Camera, modelMatrix, matGroup, modelComponent, world)); + std::shared_ptr modelJob = std::shared_ptr(new ModelJob(model, m_Camera, modelMatrix, matGroup, modelComponent, m_World)); jobs.push_back(modelJob); } } } -void RenderSystem::fillLight(std::list>& jobs, World* world) +void RenderSystem::fillLight(std::list>& jobs) { - auto pointLights = world->GetComponents("PointLight"); + auto pointLights = m_World->GetComponents("PointLight"); if (pointLights == nullptr) { return; } @@ -80,7 +80,7 @@ void RenderSystem::fillLight(std::list>& jobs, World* if (!visible) { continue; } - auto transformC = world->GetComponent(pointlightC.EntityID, "Transform"); + auto transformC = m_World->GetComponent(pointlightC.EntityID, "Transform"); if (&transformC == nullptr) { return; } @@ -95,9 +95,8 @@ bool RenderSystem::OnInputCommand(const Events::InputCommand& e) return false; } -void RenderSystem::Update(World* world, double dt) +void RenderSystem::Update(double dt) { - m_World = world; m_EventBroker->Process(); if (m_CurrentCamera) { @@ -110,8 +109,8 @@ void RenderSystem::Update(World* world, double dt) RenderScene scene; scene.Camera = m_Camera; scene.Viewport = Rectangle(1280, 720); - fillModels(scene.ForwardJobs, world); - fillLight(scene.PointLightJobs, world); + fillModels(scene.ForwardJobs); + fillLight(scene.PointLightJobs); m_RenderFrame->Add(scene); } \ No newline at end of file diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 5be95802..d60863bb 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -71,7 +71,7 @@ Game::Game(int argc, char* argv[]) m_OctreeCollision = new Octree(AABB(glm::vec3(-100), glm::vec3(100)), 4); m_OctreeFrustrumCulling = new Octree(AABB(glm::vec3(-100), glm::vec3(100)), 4); // Create system pipeline - m_SystemPipeline = new SystemPipeline(m_EventBroker); + m_SystemPipeline = new SystemPipeline(m_World, m_EventBroker); // All systems with orderlevel 0 will be updated first. unsigned int updateOrderLevel = 0; @@ -143,7 +143,7 @@ void Game::Tick() m_ClientOrServer->Update(); } // Iterate through systems and update world! - m_SystemPipeline->Update(m_World, dt); + m_SystemPipeline->Update(dt); debugTick(dt); m_Renderer->Update(dt); m_EventBroker->Process(); diff --git a/src/Game/Systems/HealthSystem.cpp b/src/Game/Systems/HealthSystem.cpp index b6d46dc9..e1cb9175 100644 --- a/src/Game/Systems/HealthSystem.cpp +++ b/src/Game/Systems/HealthSystem.cpp @@ -1,7 +1,7 @@ #include "Systems/HealthSystem.h" -HealthSystem::HealthSystem(EventBroker* eventBroker) - : System(eventBroker) +HealthSystem::HealthSystem(World* m_World, EventBroker* eventBroker) + : System(m_World, eventBroker) , PureSystem("Health") { //subscribe/listenTo playerdamage,healthpickup events (using the eventBroker) @@ -9,10 +9,10 @@ HealthSystem::HealthSystem(EventBroker* eventBroker) EVENT_SUBSCRIBE_MEMBER(m_EPlayerHealthPickup, &HealthSystem::OnPlayerHealthPickup); } -void HealthSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) +void HealthSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { //if entityID of health is 9 then the players ID is also 9 (player,health are connected to the same entity) - ComponentWrapper player = world->GetComponent(component.EntityID, "Player"); + ComponentWrapper player = m_World->GetComponent(component.EntityID, "Player"); double maxHealth = (double)component["MaxHealth"]; //process the DeltaHealthVector and change the entitys health accordingly diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index 536624b3..6f419b46 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -1,6 +1,6 @@ #include "Systems/PlayerMovementSystem.h" -void PlayerMovementSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) +void PlayerMovementSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { ComponentWrapper& cTransform = entity["Transform"]; if (!entity.HasComponent("Physics")) { diff --git a/src/Game/Systems/PlayerSpawnSystem.cpp b/src/Game/Systems/PlayerSpawnSystem.cpp index 0bf5bdea..4224d46c 100644 --- a/src/Game/Systems/PlayerSpawnSystem.cpp +++ b/src/Game/Systems/PlayerSpawnSystem.cpp @@ -1,21 +1,21 @@ #include "Systems/PlayerSpawnSystem.h" -PlayerSpawnSystem::PlayerSpawnSystem(EventBroker* eventBroker) - : System(eventBroker) +PlayerSpawnSystem::PlayerSpawnSystem(World* m_World, EventBroker* eventBroker) + : System(m_World, eventBroker) { EVENT_SUBSCRIBE_MEMBER(m_OnInputCommand, &PlayerSpawnSystem::OnInputCommand); } -void PlayerSpawnSystem::Update(World* world, double dt) +void PlayerSpawnSystem::Update(double dt) { - auto playerSpawns = world->GetComponents("PlayerSpawn"); + auto playerSpawns = m_World->GetComponents("PlayerSpawn"); if (playerSpawns == nullptr) { return; } for (auto& team : m_SpawnRequests) { for (auto& cPlayerSpawn : *playerSpawns) { - EntityWrapper spawner(world, cPlayerSpawn.EntityID); + EntityWrapper spawner(m_World, cPlayerSpawn.EntityID); if (!spawner.HasComponent("Spawner")) { continue; } diff --git a/src/Game/Systems/PlayerSystem.cpp b/src/Game/Systems/PlayerSystem.cpp index 8cdddf84..a4970ba9 100644 --- a/src/Game/Systems/PlayerSystem.cpp +++ b/src/Game/Systems/PlayerSystem.cpp @@ -1,6 +1,6 @@ #include "Systems/PlayerSystem.h" -void PlayerSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) +void PlayerSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { component["Velocity"] = glm::vec3(0.f, 0.f, 0.f); if ((bool&)component["Forward"] == true) { @@ -18,7 +18,7 @@ void PlayerSystem::UpdateComponent(World* world, EntityWrapper& entity, Componen } if ((glm::vec3)component["Velocity"] != glm::vec3(0.f)) { - ComponentWrapper& transform = world->GetComponent(component.EntityID, "Transform"); + ComponentWrapper& transform = m_World->GetComponent(component.EntityID, "Transform"); (glm::vec3&)transform["Position"] += (glm::vec3)component["Velocity"]; } } diff --git a/src/Game/Systems/SpawnerSystem.cpp b/src/Game/Systems/SpawnerSystem.cpp index 3454c58b..8cb5b99d 100644 --- a/src/Game/Systems/SpawnerSystem.cpp +++ b/src/Game/Systems/SpawnerSystem.cpp @@ -1,6 +1,7 @@ #include "Systems/SpawnerSystem.h" -SpawnerSystem::SpawnerSystem(EventBroker* eventBroker) : System(eventBroker) +SpawnerSystem::SpawnerSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) { EVENT_SUBSCRIBE_MEMBER(m_OnSpawnerSpawn, &SpawnerSystem::OnSpawnerSpawn); } diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index 84d6199d..347d8071 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -102,7 +102,7 @@ void GameHealthSystemTest::Tick() m_LastTime = currentTime; // Iterate through systems and update world! - m_SystemPipeline->Update(m_World, dt); + m_SystemPipeline->Update(dt); m_EventBroker->Swap(); m_EventBroker->Clear(); diff --git a/src/Tests/OctTreeTestGameClass.cpp b/src/Tests/OctTreeTestGameClass.cpp index 2c45d897..f125f425 100644 --- a/src/Tests/OctTreeTestGameClass.cpp +++ b/src/Tests/OctTreeTestGameClass.cpp @@ -179,7 +179,7 @@ void Game::Tick() #endif // Iterate through systems and update world! - m_SystemPipeline->Update(m_World, dt); + m_SystemPipeline->Update(dt); m_Renderer->Update(dt); m_RenderQueueFactory->Update(m_World); From 79eaa7364c9ae5ca72cce9b9bfa28215a081e2e3 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Mon, 18 Jan 2016 23:59:46 +0100 Subject: [PATCH 092/224] Editor toolbox buttons --- assets | 2 +- src/Engine/Editor/EditorGUI.cpp | 32 +++++++++++++++++++++++++------- 2 files changed, 26 insertions(+), 8 deletions(-) diff --git a/assets b/assets index a1bb17db..e794bef3 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit a1bb17dbe0da3d55932c2e187da50bc0257691f4 +Subproject commit e794bef3a75ddcfb9bd87c1bd0f439c72e81036f diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 94aaceb4..b7a7fbb9 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -36,22 +36,39 @@ void EditorGUI::drawTools() GLuint translateIcon = 0; try { - translateIcon = ResourceManager::Load("Textures/Icons/shaft.png")->m_Texture; + translateIcon = ResourceManager::Load("Textures/Icons/Translate.png")->m_Texture; } catch (const std::exception&) { } GLuint rotateIcon = 0; try { - rotateIcon = ResourceManager::Load("Textures/Icons/circulararrows3.png")->m_Texture; + rotateIcon = ResourceManager::Load("Textures/Icons/Rotate.png")->m_Texture; } catch (const std::exception&) { } GLuint scaleIcon = 0; try { - scaleIcon = ResourceManager::Load("Textures/Icons/increase10.png")->m_Texture; + scaleIcon = ResourceManager::Load("Textures/Icons/Scale.png")->m_Texture; } catch (const std::exception&) { } - ImGui::ImageButton((void*)translateIcon, ImVec2(24, 24)); + ImGui::ImageButton((void*)translateIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); ImGui::SameLine(); - ImGui::ImageButton((void*)rotateIcon, ImVec2(24, 24)); + ImGui::ImageButton((void*)rotateIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); ImGui::SameLine(); - ImGui::ImageButton((void*)scaleIcon, ImVec2(24, 24)); + ImGui::ImageButton((void*)scaleIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); + ImGui::SameLine(); + ImGui::ItemSize(ImVec2(5, 0)); + ImGui::SameLine(); + + GLuint playIcon = 0; + try { + playIcon = ResourceManager::Load("Textures/Icons/Play.png")->m_Texture; + } catch (const std::exception&) { } + GLuint pauseIcon = 0; + try { + pauseIcon = ResourceManager::Load("Textures/Icons/Pause.png")->m_Texture; + } catch (const std::exception&) { } + + + ImGui::ImageButton((void*)playIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), ImVec4(0, 1, 0, 1)); + ImGui::SameLine(); + ImGui::ImageButton((void*)pauseIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); ImGui::End(); } @@ -169,8 +186,9 @@ void EditorGUI::drawComponents(EntityWrapper entity) std::stringstream title; title << "Components"; if (entity.Valid()) { - title << formatEntityName(entity) << "###Components"; + title << " " << formatEntityName(entity); } + title << "###Components"; if (!ImGui::Begin(title.str().c_str())) { ImGui::End(); return; From 9e3dfff7b6c86a2d5b3e205d43661187ff6cd45d Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 00:52:17 +0100 Subject: [PATCH 093/224] WIP world pausing --- include/Engine/Core/EPause.h | 22 ++++++++++++++++++++++ include/Engine/Core/SystemPipeline.h | 26 +++++++++++++++++++++++++- include/Engine/Editor/EditorGUI.h | 6 ++++-- src/Engine/Editor/EditorGUI.cpp | 25 ++++++++++++++++++------- src/Engine/Editor/EditorSystem.cpp | 4 ++-- src/Game/Game.cpp | 2 +- 6 files changed, 72 insertions(+), 13 deletions(-) create mode 100644 include/Engine/Core/EPause.h diff --git a/include/Engine/Core/EPause.h b/include/Engine/Core/EPause.h new file mode 100644 index 00000000..5aca36d8 --- /dev/null +++ b/include/Engine/Core/EPause.h @@ -0,0 +1,22 @@ +#ifndef EPause_h__ +#define EPause_h__ + +#include "EventBroker.h" +#include "World.h" + +namespace Events +{ + +struct Pause : Event +{ + ::World* World; +}; + +struct Resume : Event +{ + ::World* World; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Engine/Core/SystemPipeline.h b/include/Engine/Core/SystemPipeline.h index cc3c98e9..90303f12 100644 --- a/include/Engine/Core/SystemPipeline.h +++ b/include/Engine/Core/SystemPipeline.h @@ -5,6 +5,7 @@ #include "EventBroker.h" #include "System.h" #include "World.h" +#include "EPause.h" class SystemPipeline { @@ -12,7 +13,10 @@ public: SystemPipeline(World* world, EventBroker* eventBroker) : m_World(world) , m_EventBroker(eventBroker) - { } + { + EVENT_SUBSCRIBE_MEMBER(m_EPause, &SystemPipeline::OnPause); + EVENT_SUBSCRIBE_MEMBER(m_EResume, &SystemPipeline::OnResume); + } ~SystemPipeline() { @@ -51,6 +55,10 @@ public: void Update(double dt) { + if (m_Paused) { + dt = 0.0; + } + for (UnorderedSystems& group : m_OrderedSystemGroups) { // Process events for (auto& pair : group.Systems) { @@ -80,6 +88,7 @@ public: private: World* m_World; EventBroker* m_EventBroker; + bool m_Paused = false; struct UnorderedSystems { @@ -88,6 +97,21 @@ private: std::vector ImpureSystems; }; std::vector m_OrderedSystemGroups; + + EventRelay m_EPause; + bool OnPause(const Events::Pause& e) { + if (e.World == m_World) { + m_Paused = true; + } + return true; + } + EventRelay m_EResume; + bool OnResume(const Events::Resume& e) { + if (e.World == m_World) { + m_Paused = false; + } + return true; + } }; #endif \ No newline at end of file diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 917d216f..7e36f211 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -14,14 +14,15 @@ #include "../Core/World.h" #include "../Core/EntityWrapper.h" #include "../Core/ResourceManager.h" +#include "../Core/EPause.h" #include "../Rendering/Texture.h" class EditorGUI { public: - EditorGUI(EventBroker* eventBroker); + EditorGUI(World* world, EventBroker* eventBroker); - void Draw(World* world); + void Draw(); void SelectEntity(EntityWrapper entity); @@ -57,6 +58,7 @@ public: void SetComponentDeleteCallback(OnComponentDelete_t f) { m_OnComponentDelete = f; } private: + World* m_World; EventBroker* m_EventBroker; // Config variables diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index b7a7fbb9..e3c714bd 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -1,17 +1,18 @@ #include "Editor/EditorGUI.h" -EditorGUI::EditorGUI(EventBroker* eventBroker) - : m_EventBroker(eventBroker) +EditorGUI::EditorGUI(World* world, EventBroker* eventBroker) + : m_World(world) + , m_EventBroker(eventBroker) { } -void EditorGUI::Draw(World* world) +void EditorGUI::Draw() { ImGui::ShowTestWindow(); drawMenu(); drawTools(); - drawEntities(world); + drawEntities(m_World); drawComponents(m_CurrentSelection); } @@ -65,10 +66,20 @@ void EditorGUI::drawTools() pauseIcon = ResourceManager::Load("Textures/Icons/Pause.png")->m_Texture; } catch (const std::exception&) { } - - ImGui::ImageButton((void*)playIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), ImVec4(0, 1, 0, 1)); + static bool paused = false; + if (ImGui::ImageButton((void*)playIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), (!paused) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1))) { + Events::Resume e; + e.World = m_World; + m_EventBroker->Publish(e); + paused = false; + } ImGui::SameLine(); - ImGui::ImageButton((void*)pauseIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); + if (ImGui::ImageButton((void*)pauseIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), (paused) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1))) { + Events::Pause e; + e.World = m_World; + m_EventBroker->Publish(e); + paused = true; + } ImGui::End(); } diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 64f16cc6..05e9974b 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -19,7 +19,7 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorWorld->AttachComponent(m_Camera.ID, "Camera"); m_DebugCameraInputController = new DebugCameraInputController(m_EventBroker, -1); - m_EditorGUI = new EditorGUI(m_EventBroker); + m_EditorGUI = new EditorGUI(m_World, m_EventBroker); m_EditorGUI->SetEntitySelectedCallback(std::bind(&EditorSystem::OnEntitySelected, this, std::placeholders::_1)); m_EditorGUI->SetEntityImportCallback(std::bind(&EditorSystem::importEntity, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetEntitySaveCallback(std::bind(&EditorSystem::OnEntitySave, this, std::placeholders::_1, std::placeholders::_2)); @@ -49,7 +49,7 @@ void EditorSystem::Update(double dt) { m_EditorWorldSystemPipeline->Update(dt); - m_EditorGUI->Draw(m_World); + m_EditorGUI->Draw(); m_EditorStats->Draw(dt); m_DebugCameraInputController->Update(dt); diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index d60863bb..0f6d3dc5 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -27,7 +27,6 @@ Game::Game(int argc, char* argv[]) // Create the core event broker m_EventBroker = new EventBroker(); - // Create the renderer m_Renderer = new Renderer(m_EventBroker, m_World); m_Renderer->SetFullscreen(m_Config->Get("Video.Fullscreen", false)); @@ -143,6 +142,7 @@ void Game::Tick() m_ClientOrServer->Update(); } // Iterate through systems and update world! + m_EventBroker->Process(); m_SystemPipeline->Update(dt); debugTick(dt); m_Renderer->Update(dt); From b62e42567cd35ed23dbfdee59114b3f3d9151a7f Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 11:35:31 +0100 Subject: [PATCH 094/224] Fixed editor enum selection --- src/Engine/Editor/EditorGUI.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index e3c714bd..d0a6fd05 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -367,6 +367,7 @@ void EditorGUI::drawComponentField_enum(ComponentWrapper &c, const ComponentInfo if (val == kv.second) { selectedItem = i; } + i++; } if (ImGui::Combo("", &selectedItem, enumKeys.str().c_str())) { val = enumValues.at(selectedItem); From 3142c701e3c68553094c783e0d2b77ee4e3fc37c Mon Sep 17 00:00:00 2001 From: stiffly Date: Tue, 19 Jan 2016 11:42:30 +0100 Subject: [PATCH 095/224] WIP interpolating scale and orientation --- include/Game/InterpolationSystem.h | 13 +++++++++++-- src/Game/InterpolationSystem.cpp | 30 +++++++++++++++++++++--------- 2 files changed, 32 insertions(+), 11 deletions(-) diff --git a/include/Game/InterpolationSystem.h b/include/Game/InterpolationSystem.h index c8e88834..73329094 100644 --- a/include/Game/InterpolationSystem.h +++ b/include/Game/InterpolationSystem.h @@ -5,6 +5,7 @@ #include #include #include +#include #include "Common.h" #include "Core/System.h" @@ -12,6 +13,7 @@ #include "Network/EInterpolate.h" +#define SNAPSHOTINTERVAL 0.05f class InterpolationSystem : public PureSystem { @@ -19,7 +21,7 @@ class InterpolationSystem : public PureSystem { glm::vec3 Position; glm::vec3 Scale; - glm::vec3 Orientation; + glm::quat Orientation; double interpolationTime; }; public: @@ -35,7 +37,14 @@ private: //std::unordered_map> m_InterpolationPoints; std::unordered_map m_InterpolationPoints; - glm::vec3 vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime); + //glm::vec3 vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime); + template + T vectorInterpolation(T prev, T next, double currentTime) + { + T difference = next - prev; + T vector = (difference / SNAPSHOTINTERVAL) * static_cast(currentTime); + return vector; + } EventRelay m_EInterpolate; bool InterpolationSystem::OnInterpolate(const Events::Interpolate& e); diff --git a/src/Game/InterpolationSystem.cpp b/src/Game/InterpolationSystem.cpp index 2d8de336..d3592132 100644 --- a/src/Game/InterpolationSystem.cpp +++ b/src/Game/InterpolationSystem.cpp @@ -24,17 +24,27 @@ void InterpolationSystem::UpdateComponent(World * world, ComponentWrapper & tran { Transform& sTransform = m_InterpolationPoints[transform.EntityID]; sTransform.interpolationTime += dt; + // Position glm::vec3 nextPosition = sTransform.Position; glm::vec3 currentPosition = static_cast(transform["Position"]); - (glm::vec3&)transform["Position"] += vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); + (glm::vec3&)transform["Position"] += vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); + // Orientation + glm::quat nextOrientation = sTransform.Orientation; + glm::quat currentOrientation = glm::quat(static_cast(transform["Orientation"])); + (glm::vec3&)transform["Orientation"] = glm::eulerAngles(glm::slerp(currentOrientation, nextOrientation, sTransform.interpolationTime / SNAPSHOTINTERVAL)); + // Scale + glm::vec3 nextScale = sTransform.Scale; + glm::vec3 currentScale = static_cast(transform["Scale"]); + //glm::vec3 resize = vectorInterpolation(currentScale, nextScale, sTransform.interpolationTime); + (glm::vec3&)transform["Scale"] += vectorInterpolation(currentScale, nextScale, sTransform.interpolationTime); } -glm::vec3 InterpolationSystem::vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime) -{ - glm::vec3 difference = next - prev; - glm::vec3 position = difference / 0.05f * static_cast(currentTime); - return position; -} +//glm::vec3 InterpolationSystem::vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime) +//{ +// glm::vec3 difference = next - prev; +// glm::vec3 position = difference / SNAPSHOTINTERVAL * static_cast(currentTime); +// return position; +//} bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) { @@ -43,9 +53,11 @@ bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) // Read the data memcpy(&transform.Position, e.DataArray.get() + offset, sizeof(glm::vec3)); offset += sizeof(glm::vec3); - memcpy(&transform.Orientation, e.DataArray.get() + offset, sizeof(glm::vec3)); + glm::vec3 tempOrientation; + memcpy(&tempOrientation, e.DataArray.get() + offset, sizeof(glm::vec3)); + transform.Orientation = glm::quat(tempOrientation); offset += sizeof(glm::vec3); - memcpy(&transform.Scale, e.DataArray.get() + offset, sizeof(glm::vec3)); + memcpy(&transform.Scale, e.DataArray.get() + offset, sizeof(glm::vec3)); transform.interpolationTime = 0.0f; m_InterpolationPoints[e.Entity] = transform; // Check if queue already exists From 68af853a03a3d31550156e6cbfdeba47c911dccf Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 11:42:26 +0100 Subject: [PATCH 096/224] Editor entity naming --- include/Engine/Editor/EditorGUI.h | 4 ++++ include/Engine/Editor/EditorSystem.h | 1 + src/Engine/Editor/EditorGUI.cpp | 27 ++++++++++++++++++++++++++- src/Engine/Editor/EditorSystem.cpp | 6 ++++++ 4 files changed, 37 insertions(+), 1 deletion(-) diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 7e36f211..f28b95cf 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -50,6 +50,9 @@ public: // Called when the user means to change the parent of an entity. typedef std::function OnEntityChangeParent_t; void SetEntityChangeParentCallback(OnEntityChangeParent_t f) { m_OnEntityChangeParent = f; } + // Called when the user means to rename an entity. + typedef std::function OnEntityChangeName_t; + void SetEntityChangeNameCallback(OnEntityChangeName_t f) { m_OnEntityChangeName = f; } // Called when the user means to attach a new component to an entity. typedef std::function OnComponentAttach_t; void SetComponentAttachCallback(OnComponentAttach_t f) { m_OnComponentAttach = f; } @@ -77,6 +80,7 @@ private: OnEntityCreate_t m_OnEntityCreate = nullptr; OnEntityDelete_t m_OnEntityDelete = nullptr; OnEntityChangeParent_t m_OnEntityChangeParent = nullptr; + OnEntityChangeName_t m_OnEntityChangeName = nullptr; OnComponentAttach_t m_OnComponentAttach = nullptr; OnComponentDelete_t m_OnComponentDelete = nullptr; diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index 8ae3ac2e..c0db917d 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -41,6 +41,7 @@ private: EntityWrapper OnEntityCreate(EntityWrapper parent); void OnEntityDelete(EntityWrapper entity); void OnEntityChangeParent(EntityWrapper entity, EntityWrapper parent); + void OnEntityChangeName(EntityWrapper entity, const std::string& name); void OnComponentAttach(EntityWrapper entity, const std::string& componentType); void OnComponentDelete(EntityWrapper entity, const std::string& componentType); }; \ No newline at end of file diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index d0a6fd05..68a136c3 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -101,6 +101,31 @@ void EditorGUI::drawEntities(World* world) ImGui::SameLine(0.f, 5.f); ImGui::Button("Reference", ImVec2(buttonWidth, 0)); + // Naming + char buffer[256]; + buffer[0] = '\0'; + buffer[255] = '\0'; + std::size_t nameLength = 0; + ImGuiInputTextFlags flags = ImGuiInputTextFlags_CharsNoBlank | ImGuiInputTextFlags_AutoSelectAll; + if (m_CurrentSelection.Valid()) { + std::string name = world->GetName(m_CurrentSelection.ID); + nameLength = name.length(); + if (!name.empty()) { + memcpy(buffer, name.c_str(), std::min(sizeof(buffer) - 1, name.length() + 1)); + } + } else { + flags |= ImGuiInputTextFlags_ReadOnly; + } + ImGui::PushItemWidth(ImGui::GetContentRegionAvailWidth() - 7.f); + if (ImGui::InputText("", &buffer[0], sizeof(buffer), flags)) { + if (m_CurrentSelection.Valid()) { + if (m_OnEntityChangeName != nullptr) { + m_OnEntityChangeName(m_CurrentSelection, std::string(buffer)); + } + } + } + ImGui::PopItemWidth(); + ImGui::ItemSize(ImVec2(0, 3)); drawEntitiesRecursive(world, EntityID_Invalid); @@ -487,7 +512,7 @@ const std::string EditorGUI::formatEntityName(EntityWrapper entity) std::stringstream name; - const std::string& entityName = entity.World->GetName(entity); + std::string entityName = entity.World->GetName(entity.ID); if (!entityName.empty()) { name << entityName; } else { diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 05e9974b..36f2baa4 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -26,6 +26,7 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorGUI->SetEntityCreateCallback(std::bind(&EditorSystem::OnEntityCreate, this, std::placeholders::_1)); m_EditorGUI->SetEntityDeleteCallback(std::bind(&EditorSystem::OnEntityDelete, this, std::placeholders::_1)); m_EditorGUI->SetEntityChangeParentCallback(std::bind(&EditorSystem::OnEntityChangeParent, this, std::placeholders::_1, std::placeholders::_2)); + m_EditorGUI->SetEntityChangeNameCallback(std::bind(&EditorSystem::OnEntityChangeName, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetComponentAttachCallback(std::bind(&EditorSystem::OnComponentAttach, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetComponentDeleteCallback(std::bind(&EditorSystem::OnComponentDelete, this, std::placeholders::_1, std::placeholders::_2)); @@ -85,6 +86,11 @@ void EditorSystem::OnEntityChangeParent(EntityWrapper entity, EntityWrapper pare entity.World->SetParent(entity.ID, parent.ID); } +void EditorSystem::OnEntityChangeName(EntityWrapper entity, const std::string& name) +{ + entity.World->SetName(entity.ID, name); +} + void EditorSystem::OnComponentAttach(EntityWrapper entity, const std::string& componentType) { entity.World->AttachComponent(entity.ID, componentType); From 267a60ef305cf411f42866e2d4d0a13b5754f21a Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 11:43:38 +0100 Subject: [PATCH 097/224] Better loading of editor toolbox icons --- include/Engine/Editor/EditorGUI.h | 1 + src/Engine/Editor/EditorGUI.cpp | 51 +++++++++++++------------------ 2 files changed, 23 insertions(+), 29 deletions(-) diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index f28b95cf..9d2712e1 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -88,6 +88,7 @@ private: boost::filesystem::path fileOpenDialog(); boost::filesystem::path fileSaveDialog(); const std::string formatEntityName(EntityWrapper entity); + GLuint tryLoadTexture(std::string filePath); // Entity file handling methods void entityImport(World* world); diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 68a136c3..1bf0f9e9 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -35,46 +35,30 @@ void EditorGUI::drawTools() return; } - GLuint translateIcon = 0; - try { - translateIcon = ResourceManager::Load("Textures/Icons/Translate.png")->m_Texture; - } catch (const std::exception&) { } - GLuint rotateIcon = 0; - try { - rotateIcon = ResourceManager::Load("Textures/Icons/Rotate.png")->m_Texture; - } catch (const std::exception&) { } - GLuint scaleIcon = 0; - try { - scaleIcon = ResourceManager::Load("Textures/Icons/Scale.png")->m_Texture; - } catch (const std::exception&) { } + // Translate widget button + ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Translate.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); + // Rotate widget button + ImGui::SameLine(); + ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Rotate.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); + // Scale widget button + ImGui::SameLine(); + ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Scale.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); - ImGui::ImageButton((void*)translateIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); - ImGui::SameLine(); - ImGui::ImageButton((void*)rotateIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); - ImGui::SameLine(); - ImGui::ImageButton((void*)scaleIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); ImGui::SameLine(); ImGui::ItemSize(ImVec2(5, 0)); + + // Play button ImGui::SameLine(); - - GLuint playIcon = 0; - try { - playIcon = ResourceManager::Load("Textures/Icons/Play.png")->m_Texture; - } catch (const std::exception&) { } - GLuint pauseIcon = 0; - try { - pauseIcon = ResourceManager::Load("Textures/Icons/Pause.png")->m_Texture; - } catch (const std::exception&) { } - static bool paused = false; - if (ImGui::ImageButton((void*)playIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), (!paused) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1))) { + if (ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Play.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), (!paused) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1))) { Events::Resume e; e.World = m_World; m_EventBroker->Publish(e); paused = false; } + // Pause button ImGui::SameLine(); - if (ImGui::ImageButton((void*)pauseIcon, ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), (paused) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1))) { + if (ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Pause.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0), -1, ImVec4(0, 0, 0, 0), (paused) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1))) { Events::Pause e; e.World = m_World; m_EventBroker->Publish(e); @@ -526,6 +510,15 @@ const std::string EditorGUI::formatEntityName(EntityWrapper entity) return name.str(); } +GLuint EditorGUI::tryLoadTexture(std::string filePath) +{ + GLuint texture = 0; + try { + texture = ResourceManager::Load(filePath)->m_Texture; + } catch (const std::exception&) { } + return texture; +} + void EditorGUI::entityImport(World* world) { boost::filesystem::path filePath = fileOpenDialog(); From 3fb975a8d968da9c70d6ae0d79d75b352dced998 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 11:44:03 +0100 Subject: [PATCH 098/224] Editor widget entities --- resources/Schema/Components.xsd | 1 + resources/Schema/Components/EditorWidget.xml | 5 + resources/Schema/Components/EditorWidget.xsd | 27 +++++ .../Schema/Entities/EditorWidgetRotate.xml | 57 ++++++++++ .../Schema/Entities/EditorWidgetScale.xml | 62 +++++++++++ .../Schema/Entities/EditorWidgetTranslate.xml | 101 ++++++++++++++++++ resources/Schema/Types/Entity.xsd | 1 + 7 files changed, 254 insertions(+) create mode 100644 resources/Schema/Components/EditorWidget.xml create mode 100644 resources/Schema/Components/EditorWidget.xsd create mode 100644 resources/Schema/Entities/EditorWidgetRotate.xml create mode 100644 resources/Schema/Entities/EditorWidgetScale.xml create mode 100644 resources/Schema/Entities/EditorWidgetTranslate.xml diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index b9c8647c..f129b9f3 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -19,4 +19,5 @@ + \ No newline at end of file diff --git a/resources/Schema/Components/EditorWidget.xml b/resources/Schema/Components/EditorWidget.xml new file mode 100644 index 00000000..6a94d2f6 --- /dev/null +++ b/resources/Schema/Components/EditorWidget.xml @@ -0,0 +1,5 @@ + + + + + \ No newline at end of file diff --git a/resources/Schema/Components/EditorWidget.xsd b/resources/Schema/Components/EditorWidget.xsd new file mode 100644 index 00000000..e4c4ff71 --- /dev/null +++ b/resources/Schema/Components/EditorWidget.xsd @@ -0,0 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml new file mode 100644 index 00000000..fc41b596 --- /dev/null +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -0,0 +1,57 @@ + + + + + + + + + + + + 2 + + + + Models/RotationWidgetX.obj + + + + + + + + + 2 + + + + Models/RotationWidgetY.obj + + + + + + + + + 2 + + + + Models/RotationWidgetZ.obj + + + + + + + + + + + + + + + diff --git a/resources/Schema/Entities/EditorWidgetScale.xml b/resources/Schema/Entities/EditorWidgetScale.xml new file mode 100644 index 00000000..f4c44d66 --- /dev/null +++ b/resources/Schema/Entities/EditorWidgetScale.xml @@ -0,0 +1,62 @@ + + + + + + Models/ScaleWidgetOrigin.obj + + + + + + + + + 3 + + + + Models/ScaleWidgetX.obj + + + + + + + + + 3 + + + + Models/ScaleWidgetY.obj + + + + + + + + + 3 + + + + Models/ScaleWidgetZ.obj + + + + + + + + + + + + + + + + + diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml new file mode 100644 index 00000000..bc43538d --- /dev/null +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -0,0 +1,101 @@ + + + + + + Models/TranslationWidgetOrigin.obj + + + + + + + + + 1 + + + + Models/TranslationWidgetX.obj + + + + + + + + + 1 + + + + Models/TranslationWidgetY.obj + + + + + + + + + 1 + + + + Models/TranslationWidgetZ.obj + + + + + + + + + 1 + + + + Models/WidgetPlaneX.obj + + + + + + + + + 1 + + + + Models/WidgetPlaneY.obj + + + + + + + + + 1 + + + + Models/WidgetPlaneZ.obj + + + + + + + + + + + + + + + + + diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 3b0a1c88..e44b1d72 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -28,6 +28,7 @@ + From dbe56280a66e5adb3cca9974e150185f7a36f208 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Tue, 19 Jan 2016 11:45:34 +0100 Subject: [PATCH 099/224] Resolution fixed and Centered text --- include/Engine/Rendering/Font.h | 1 + include/Engine/Rendering/TextRenderer.h | 2 +- resources/Schema/Components/Text.xml | 2 +- resources/Schema/Entities/RenderingWorld.xml | 52 ++++++++++++++++---- src/Engine/Rendering/Font.cpp | 10 ++-- src/Engine/Rendering/PickingPass.cpp | 4 +- src/Engine/Rendering/PickingPassState.cpp | 1 + src/Engine/Rendering/Renderer.cpp | 1 + src/Engine/Rendering/TextRenderer.cpp | 37 ++++++++++---- 9 files changed, 80 insertions(+), 30 deletions(-) diff --git a/include/Engine/Rendering/Font.h b/include/Engine/Rendering/Font.h index 08341c1e..5a1a6bdd 100644 --- a/include/Engine/Rendering/Font.h +++ b/include/Engine/Rendering/Font.h @@ -27,6 +27,7 @@ public: FT_Face Face; + int FontSize = 16; ~Font(); diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h index a755fd30..e7323deb 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextRenderer.h @@ -25,7 +25,7 @@ private: GLuint VAO, VBO; - void RenderText(std::string text, Font* font, GLfloat scale, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); + void RenderText(std::string text, Font* font, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); ShaderProgram* m_TextProgram; diff --git a/resources/Schema/Components/Text.xml b/resources/Schema/Components/Text.xml index 45bed531..ecf9bac8 100644 --- a/resources/Schema/Components/Text.xml +++ b/resources/Schema/Components/Text.xml @@ -1,7 +1,7 @@ Text - Fonts/DroidSans.ttf + true \ No newline at end of file diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 73c0e474..f35747c4 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -13,28 +13,58 @@ Models/Camera.obj - false - - + + - + + + + + Camera 1 + Fonts/DroidSans.ttf,24 + + + + + + + + + ActionCamera + Models/Camera.obj + false - + + - + + + + + Camera 2 + Fonts/DroidSans.ttf,24 + + + + + + + + + @@ -42,7 +72,7 @@ Models/Core/UnitPlane.obj - + @@ -60,10 +90,12 @@ - asdasdasdasdasd - Fonts/DroidSans.ttf + Welcome! + Fonts/DroidSans.ttf,64 - + + + diff --git a/src/Engine/Rendering/Font.cpp b/src/Engine/Rendering/Font.cpp index 5f4984a7..ba99ee31 100644 --- a/src/Engine/Rendering/Font.cpp +++ b/src/Engine/Rendering/Font.cpp @@ -7,7 +7,6 @@ Font::Font(std::string path) boost::char_separator sep(","); tokenizer tok(path, sep); - int fontSize = 16; tokenizer::iterator it = tok.begin(); std::string filePath = ""; @@ -17,7 +16,7 @@ Font::Font(std::string path) it++; if (it != tok.end()) { try { - fontSize = boost::lexical_cast((*it).c_str()); + FontSize = boost::lexical_cast((*it).c_str()); } catch (boost::bad_lexical_cast const&) { LOG_ERROR("input string did not have a valid font resolution"); } @@ -39,8 +38,8 @@ Font::Font(std::string path) return; } - FT_Set_Char_Size(Face, 0, fontSize*64, 300, 300); // temp - FT_Set_Pixel_Sizes(Face, 0, fontSize); // + FT_Set_Char_Size(Face, 0, FontSize*64, 300, 300); // temp + FT_Set_Pixel_Sizes(Face, 0, FontSize); // if (FT_Load_Char(Face, 'X', FT_LOAD_RENDER)) { LOG_ERROR("FreeType error: loading char"); @@ -88,14 +87,13 @@ Font::Font(std::string path) m_Characters.insert(std::pair(c, character)); } - - FT_Done_Face(Face); FT_Done_FreeType(library); GLERROR("Font Load"); } Font::~Font() { + FT_Done_Face(Face); for (auto c : m_Characters) { glDeleteTextures(1, &c.second.TextureID); } diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 7470f029..f925d248 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -74,9 +74,9 @@ void PickingPass::Draw(RenderScene& scene) m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); if (m_ColorCounter[0] > 255) { m_ColorCounter[0] = 0; - m_ColorCounter[1]++;; + m_ColorCounter[1]++; } else { - m_ColorCounter[0]++;; + m_ColorCounter[0]++; } } diff --git a/src/Engine/Rendering/PickingPassState.cpp b/src/Engine/Rendering/PickingPassState.cpp index 2b4f30c4..0c4f4aca 100644 --- a/src/Engine/Rendering/PickingPassState.cpp +++ b/src/Engine/Rendering/PickingPassState.cpp @@ -8,6 +8,7 @@ PickingPassState::PickingPassState(GLuint frameBuffer) GLERROR("---3"); Enable(GL_DEPTH_TEST); Enable(GL_CULL_FACE); + Disable(GL_BLEND); glm::vec4 clearColor = glm::vec4(0.f); //ClearColor(clearColor); diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 754baf55..b168a8a3 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -117,6 +117,7 @@ void Renderer::Draw(RenderFrame& frame) m_TextRenderer->Draw(*scene); } + m_ImGuiRenderPass->Draw(); glfwSwapBuffers(m_Window); diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextRenderer.cpp index 6f34de5b..5b51c063 100644 --- a/src/Engine/Rendering/TextRenderer.cpp +++ b/src/Engine/Rendering/TextRenderer.cpp @@ -34,21 +34,39 @@ void TextRenderer::Draw(RenderScene& scene) for (auto &job : scene.TextJobs) { auto textJob = std::dynamic_pointer_cast(job); if (textJob) { - RenderText(textJob->Content, textJob->Resource, 0.01f, textJob->Color, textJob->Matrix, scene.Camera->ProjectionMatrix(), scene.Camera->ViewMatrix()); + RenderText(textJob->Content, textJob->Resource, textJob->Color, textJob->Matrix, scene.Camera->ProjectionMatrix(), scene.Camera->ViewMatrix()); } } } -void TextRenderer::RenderText(std::string text, Font* font, GLfloat scale, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) +void TextRenderer::RenderText(std::string text, Font* font, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) { - GLfloat x = 0; - GLfloat y = 0; + GLfloat penX = 0; + GLfloat penY = 0; + float scale = 1.0/font->FontSize; + FT_Bool use_kerning = FT_HAS_KERNING(font->Face); + FT_UInt previous = 0; + FT_UInt num_glyphs = 0; + FT_UInt glyph_index; + + FT_Vector pos[128]; + + GLfloat stringWidth = 0.f; + + for (std::string::const_iterator c = text.begin(); c != text.end(); c++) { + Font::Character ch = font->m_Characters[*c]; + stringWidth += (ch.Advance >> 6) * scale; + } + + penX = -stringWidth/2.f; + // Activate corresponding render state glEnable(GL_BLEND); glDisable(GL_CULL_FACE); + glEnable(GL_DEPTH_TEST); glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); m_TextProgram->Bind(); @@ -59,13 +77,12 @@ void TextRenderer::RenderText(std::string text, Font* font, GLfloat scale, glm:: glActiveTexture(GL_TEXTURE0); glBindVertexArray(VAO); - // Iterate through all characters - std::string::const_iterator c; - for (c = text.begin(); c != text.end(); c++) { + + for (std::string::const_iterator c = text.begin(); c != text.end(); c++) { Font::Character ch = font->m_Characters[*c]; - GLfloat xpos = x + ch.Bearing.x * scale; - GLfloat ypos = y - (ch.Size.y - ch.Bearing.y) * scale; + GLfloat xpos = penX + ch.Bearing.x * scale; + GLfloat ypos = penY - (ch.Size.y - ch.Bearing.y) * scale; GLfloat w = ch.Size.x * scale; GLfloat h = ch.Size.y * scale; @@ -89,7 +106,7 @@ void TextRenderer::RenderText(std::string text, Font* font, GLfloat scale, glm:: // Render quad glDrawArrays(GL_TRIANGLES, 0, 6); // Now advance cursors for next glyph (note that advance is number of 1/64 pixels) - x += (ch.Advance >> 6) * scale; // Bitshift by 6 to get value in pixels (2^6 = 64) + penX += (ch.Advance >> 6) * scale; // Bitshift by 6 to get value in pixels (2^6 = 64) } glBindVertexArray(0); glBindTexture(GL_TEXTURE_2D, 0); From 162523d3ca5381c4d53ae9719dca84e15c6da108 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 11:55:27 +0100 Subject: [PATCH 100/224] Made EntityFileWriter store enums as strings instead of integer values to be resistant to enum value changes! --- src/Engine/Core/EntityFileWriter.cpp | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/src/Engine/Core/EntityFileWriter.cpp b/src/Engine/Core/EntityFileWriter.cpp index 4d46be06..3efc9253 100644 --- a/src/Engine/Core/EntityFileWriter.cpp +++ b/src/Engine/Core/EntityFileWriter.cpp @@ -114,9 +114,18 @@ void EntityFileWriter::appentEntityComponents(xercesc::DOMElement* parentElement fieldElement->setAttribute(X("Y"), X(boost::lexical_cast(q.y))); fieldElement->setAttribute(X("Z"), X(boost::lexical_cast(q.z))); fieldElement->setAttribute(X("W"), X(boost::lexical_cast(q.w))); - } else if (field.Type == "int" || field.Type == "enum") { + } else if (field.Type == "int") { const int& value = c[fieldName]; fieldElement->appendChild(doc->createTextNode(X(boost::lexical_cast(value)))); + } else if (field.Type == "enum") { + const int& value = c[fieldName]; + auto& enumDef = c.Info.Meta->FieldEnumDefinitions.at(fieldName); + for (auto& kv : enumDef) { + if (kv.second == value) { + fieldElement->appendChild(doc->createElement(X(kv.first))); + break; + } + } } else if (field.Type == "float") { const float& value = c[fieldName]; fieldElement->appendChild(doc->createTextNode(X(boost::lexical_cast(value)))); From a6445c65aa005bba03645ea50e8206fca222ce3a Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 12:15:20 +0100 Subject: [PATCH 101/224] Fixed EntityParser to handle string enums properly. --- .../Schema/Entities/EditorWidgetRotate.xml | 12 ++++-- .../Schema/Entities/EditorWidgetScale.xml | 12 ++++-- .../Schema/Entities/EditorWidgetTranslate.xml | 24 +++++++++--- src/Engine/Core/EntityFile.cpp | 37 ++++++++++--------- 4 files changed, 56 insertions(+), 29 deletions(-) diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml index fc41b596..55dd9af4 100644 --- a/resources/Schema/Entities/EditorWidgetRotate.xml +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -9,7 +9,9 @@ - 2 + + + @@ -22,7 +24,9 @@ - 2 + + + @@ -35,7 +39,9 @@ - 2 + + + diff --git a/resources/Schema/Entities/EditorWidgetScale.xml b/resources/Schema/Entities/EditorWidgetScale.xml index f4c44d66..b317b1cc 100644 --- a/resources/Schema/Entities/EditorWidgetScale.xml +++ b/resources/Schema/Entities/EditorWidgetScale.xml @@ -12,7 +12,9 @@ - 3 + + + @@ -25,7 +27,9 @@ - 3 + + + @@ -38,7 +42,9 @@ - 3 + + + diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml index bc43538d..56943adc 100644 --- a/resources/Schema/Entities/EditorWidgetTranslate.xml +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -12,7 +12,9 @@ - 1 + + + @@ -25,7 +27,9 @@ - 1 + + + @@ -38,7 +42,9 @@ - 1 + + + @@ -51,7 +57,9 @@ - 1 + + + @@ -64,7 +72,9 @@ - 1 + + + @@ -77,7 +87,9 @@ - 1 + + + diff --git a/src/Engine/Core/EntityFile.cpp b/src/Engine/Core/EntityFile.cpp index c1125e10..d5fb4c12 100644 --- a/src/Engine/Core/EntityFile.cpp +++ b/src/Engine/Core/EntityFile.cpp @@ -86,23 +86,26 @@ void EntityFile::WriteAttributeData(char* outData, const ComponentInfo::Field_t& void EntityFile::WriteValueData(char* outData, const ComponentInfo::Field_t& field, const char* valueData) { - if (field.Type == "int" || field.Type == "enum") { - int value = boost::lexical_cast(valueData); - memcpy(outData, reinterpret_cast(&value), field.Stride); - } else if (field.Type == "float") { - float value = boost::lexical_cast(valueData); - memcpy(outData, reinterpret_cast(&value), field.Stride); - } else if (field.Type == "double") { - double value = boost::lexical_cast(valueData); - memcpy(outData, reinterpret_cast(&value), field.Stride); - } else if (field.Type == "bool") { - bool value = (valueData[0] == 't'); // Lazy bool evaluation - memcpy(outData, reinterpret_cast(&value), field.Stride); - } else if (field.Type == "string") { - new (outData) std::string(valueData); - } else { - LOG_WARNING("Unknown value data type: %s", field.Type.c_str()); - } + // Catch and ignore casting errors so whitespace around string enums won't mess anything up + try { + if (field.Type == "int" || field.Type == "enum") { + int value = boost::lexical_cast(valueData); + memcpy(outData, reinterpret_cast(&value), field.Stride); + } else if (field.Type == "float") { + float value = boost::lexical_cast(valueData); + memcpy(outData, reinterpret_cast(&value), field.Stride); + } else if (field.Type == "double") { + double value = boost::lexical_cast(valueData); + memcpy(outData, reinterpret_cast(&value), field.Stride); + } else if (field.Type == "bool") { + bool value = (valueData[0] == 't'); // Lazy bool evaluation + memcpy(outData, reinterpret_cast(&value), field.Stride); + } else if (field.Type == "string") { + new (outData) std::string(valueData); + } else { + LOG_WARNING("Unknown value data type: %s", field.Type.c_str()); + } + } catch (const boost::bad_lexical_cast&) { } } EntityFileSAXHandler::EntityFileSAXHandler(const EntityFileHandler* handler, xercesc::SAX2XMLReader* reader) : m_Handler(handler) From 46e17b7e0da3a6c31b6dbaeaf4d32b46a2bd13b2 Mon Sep 17 00:00:00 2001 From: Tleety Date: Tue, 19 Jan 2016 12:32:34 +0100 Subject: [PATCH 102/224] Working directional light --- .../Engine/Rendering/DirectionalLightJob.h | 4 +++- include/Engine/Rendering/LightCullingPass.h | 10 +++++----- .../Schema/Components/DirectionalLight.xml | 1 - .../Schema/Components/DirectionalLight.xsd | 1 - resources/Shaders/ForwardPlus.frag.glsl | 20 ++++++++++--------- src/Engine/Rendering/LightCullingPass.cpp | 20 ++++++++----------- 6 files changed, 27 insertions(+), 29 deletions(-) diff --git a/include/Engine/Rendering/DirectionalLightJob.h b/include/Engine/Rendering/DirectionalLightJob.h index 92cd195a..f6942112 100644 --- a/include/Engine/Rendering/DirectionalLightJob.h +++ b/include/Engine/Rendering/DirectionalLightJob.h @@ -15,7 +15,9 @@ struct DirectionalLightJob : RenderJob DirectionalLightJob(ComponentWrapper transformComponent, ComponentWrapper directionalLightComponent, World* m_World) : RenderJob() { - Direction = glm::vec4((glm::vec3)directionalLightComponent["Direction"], 0.f); + + Direction = glm::vec4(0,0,-1,0) * Transform::AbsoluteOrientation(m_World, transformComponent.EntityID); + //Direction = glm::vec4((glm::vec3)directionalLightComponent["Direction"], 0.f); Color = (glm::vec4)directionalLightComponent["Color"]; Intensity = (double)directionalLightComponent["Intensity"]; }; diff --git a/include/Engine/Rendering/LightCullingPass.h b/include/Engine/Rendering/LightCullingPass.h index 7eb2c62d..d8852df0 100644 --- a/include/Engine/Rendering/LightCullingPass.h +++ b/include/Engine/Rendering/LightCullingPass.h @@ -46,8 +46,8 @@ private: int m_NumberOfTiles = 0; struct Plane { - glm::vec3 Normal; - float d; + glm::vec3 Normal = glm::vec3(0.f); + float d = 0; }; struct Frustum { @@ -68,9 +68,9 @@ private: std::vector m_LightSources; struct LightGrid { - float Start; - float Amount; - glm::vec2 Padding; + float Start = 0; + float Amount = 0; + glm::vec2 Padding = glm::vec2(1.f, 2.f); }; LightGrid* m_LightGrid; diff --git a/resources/Schema/Components/DirectionalLight.xml b/resources/Schema/Components/DirectionalLight.xml index b14b7934..f66605c0 100644 --- a/resources/Schema/Components/DirectionalLight.xml +++ b/resources/Schema/Components/DirectionalLight.xml @@ -1,5 +1,4 @@ - 0.8 true diff --git a/resources/Schema/Components/DirectionalLight.xsd b/resources/Schema/Components/DirectionalLight.xsd index b4d96d18..dbfee38c 100644 --- a/resources/Schema/Components/DirectionalLight.xsd +++ b/resources/Schema/Components/DirectionalLight.xsd @@ -9,7 +9,6 @@ - diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 9f9140fb..0298c969 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -86,9 +86,9 @@ LightResult CalcPointLightSource(vec4 lightPos, float lightRadius, vec4 lightCol return result; } -LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensity, vec4 viewVec, vec4 vertPosition, vec4 vertNormal) +LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensity, vec4 viewVec, vec4 vertNormal) { - vec4 L = normalize( vec4(direction.xyz, 1) ); + vec4 L = normalize( -direction ); LightResult result; result.Diffuse = CalcDiffuse(color, L, vertNormal) * intensity; @@ -105,8 +105,8 @@ void main() vec4 viewVec = normalize(-position); vec2 tilePos; - tilePos.x = int(gl_FragCoord.x/16); - tilePos.y = int(gl_FragCoord.y/16); + tilePos.x = int(gl_FragCoord.x/TILE_SIZE); + tilePos.y = int(gl_FragCoord.y/TILE_SIZE); LightResult totalLighting; totalLighting.Diffuse = scene_ambient; @@ -117,12 +117,13 @@ void main() //for(int i = 0; i < 3; i++) for(int i = start; i < start + amount; i++) { int l = int(LightIndex[i]); + LightSource light = LightSources.List[l]; LightResult result; - if(LightSources.List[i].Type == 1) { // point - result = CalcPointLightSource(V * LightSources.List[l].Position, LightSources.List[l].Radius, LightSources.List[l].Color, LightSources.List[l].Intensity, viewVec, position, normal, LightSources.List[i].Falloff); - } else if (LightSources.List[i].Type == 2) { //Directional - result = CalcDirectionalLightSource(V * LightSources.List[l].Direction, LightSources.List[i].Color, LightSources.List[i].Intensity, viewVec, position, normal); + if(light.Type == 1) { // point + result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); + } else if (light.Type == 2) { //Directional + result = CalcDirectionalLightSource(V * light.Direction, light.Color, light.Intensity, viewVec, normal); } totalLighting.Diffuse += result.Diffuse; totalLighting.Specular += result.Specular; @@ -132,8 +133,9 @@ void main() //fragmentColor += Input.DiffuseColor; fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; - //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Start/.0, 0, 1); + //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); //fragmentColor = texel * Input.DiffuseColor * Color; + //fragmentColor += vec4(currentTile/3600.f, 0, 0, 1); if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { //fragmentColor += vec4(0.5, 0, 0, 0); } else { diff --git a/src/Engine/Rendering/LightCullingPass.cpp b/src/Engine/Rendering/LightCullingPass.cpp index f49156dc..2a2e2383 100644 --- a/src/Engine/Rendering/LightCullingPass.cpp +++ b/src/Engine/Rendering/LightCullingPass.cpp @@ -40,15 +40,14 @@ void LightCullingPass::OnResolutionChange() void LightCullingPass::SetSSBOSizes() { - m_NumberOfTiles = (int)(m_Renderer->Resolution().Width*m_Renderer->Resolution().Height)/TILE_SIZE; - - //m_Frustums = new Frustum[s]; - //m_LightGrid = new LightGrid[s]; - //m_LightIndex = new float[s*200]; + m_NumberOfTiles = (int)(m_Renderer->Resolution().Width/TILE_SIZE) * (int)(m_Renderer->Resolution().Height/TILE_SIZE); m_Frustums = new Frustum[m_NumberOfTiles]; m_LightGrid = new LightGrid[m_NumberOfTiles]; m_LightIndex = new float[m_NumberOfTiles*MAX_LIGHTS_PER_TILE]; + for (int i = 0; i < m_NumberOfTiles*MAX_LIGHTS_PER_TILE; i++) { + m_LightIndex[i] = -1; + } } void LightCullingPass::CullLights(RenderScene& scene) @@ -75,7 +74,7 @@ void LightCullingPass::CullLights(RenderScene& scene) glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 2, m_LightGridSSBO); glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 3, m_LightOffsetSSBO); glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 4, m_LightIndexSSBO); - glDispatchCompute(m_Renderer->Resolution().Width / TILE_SIZE, m_Renderer->Resolution().Height / TILE_SIZE, 1); + glDispatchCompute(glm::ceil(m_Renderer->Resolution().Width / TILE_SIZE), glm::ceil(m_Renderer->Resolution().Height / TILE_SIZE), 1); GLERROR("CullLights Error: End"); } @@ -117,25 +116,22 @@ void LightCullingPass::InitializeSSBOs() { glGenBuffers(1, &m_FrustumSSBO); glBindBuffer(GL_SHADER_STORAGE_BUFFER, m_FrustumSSBO); - glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(Frustum)*m_NumberOfTiles, m_Frustums, GL_DYNAMIC_COPY); + glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(Frustum)*m_NumberOfTiles, nullptr, GL_DYNAMIC_COPY); glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0); GLERROR("m_FrustumSSBO"); glGenBuffers(1, &m_LightSSBO); glBindBuffer(GL_SHADER_STORAGE_BUFFER, m_LightSSBO); - if(m_LightSources.size() > 0) { - glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(LightSource) * m_LightSources.size(), &(m_LightSources[0]), GL_DYNAMIC_COPY); - } + glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(LightSource) * 200, nullptr, GL_DYNAMIC_COPY); glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0); GLERROR("m_LightSSBO"); glGenBuffers(1, &m_LightGridSSBO); glBindBuffer(GL_SHADER_STORAGE_BUFFER, m_LightGridSSBO); - glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(LightGrid)*m_NumberOfTiles, m_LightGrid, GL_DYNAMIC_COPY); + glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(LightGrid)*m_NumberOfTiles, nullptr, GL_DYNAMIC_COPY); glBindBuffer(GL_SHADER_STORAGE_BUFFER, 0); GLERROR("m_LightGridSSBO"); - glGenBuffers(1, &m_LightOffsetSSBO); glBindBuffer(GL_SHADER_STORAGE_BUFFER, m_LightOffsetSSBO); glBufferData(GL_SHADER_STORAGE_BUFFER, sizeof(m_LightOffset), &m_LightOffset, GL_DYNAMIC_COPY); From cfe023cc1de3d0f688d6e1acec634e093e5a1e5c Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 12:33:53 +0100 Subject: [PATCH 103/224] Created ComponentInfo::EnumType which defines which native type to use for enums. --- include/Engine/Core/ComponentInfo.h | 4 +++- include/Engine/Core/ComponentWrapper.h | 4 ++-- src/Engine/Core/EntityFile.cpp | 7 +++++-- src/Engine/Core/EntityFilePreprocessor.cpp | 2 +- src/Engine/Core/EntityFileWriter.cpp | 2 +- 5 files changed, 12 insertions(+), 7 deletions(-) diff --git a/include/Engine/Core/ComponentInfo.h b/include/Engine/Core/ComponentInfo.h index def2a323..49ed2a3f 100644 --- a/include/Engine/Core/ComponentInfo.h +++ b/include/Engine/Core/ComponentInfo.h @@ -5,12 +5,14 @@ struct ComponentInfo { + typedef int EnumType; + struct Meta_t { std::string Annotation; unsigned int Allocation = 0; std::map FieldAnnotations; - std::map> FieldEnumDefinitions; + std::map> FieldEnumDefinitions; }; struct Field_t diff --git a/include/Engine/Core/ComponentWrapper.h b/include/Engine/Core/ComponentWrapper.h index f124d3d5..c7a32370 100644 --- a/include/Engine/Core/ComponentWrapper.h +++ b/include/Engine/Core/ComponentWrapper.h @@ -18,7 +18,7 @@ struct ComponentWrapper const ::EntityID EntityID; char* Data; - int Enum(const char* fieldName, const char* enumKey) + ComponentInfo::EnumType Enum(const char* fieldName, const char* enumKey) { return Info.Meta->FieldEnumDefinitions.at(fieldName).at(enumKey); } @@ -58,7 +58,7 @@ struct ComponentWrapper public: // Return the integer value of an enum type key for this field - int Enum(const char* enumKey) { return m_Component->Enum(m_PropertyName.c_str(), enumKey); } + ComponentInfo::EnumType Enum(const char* enumKey) { return m_Component->Enum(m_PropertyName.c_str(), enumKey); } template operator T&() { return m_Component->Field(m_PropertyName); } diff --git a/src/Engine/Core/EntityFile.cpp b/src/Engine/Core/EntityFile.cpp index d5fb4c12..7609db2b 100644 --- a/src/Engine/Core/EntityFile.cpp +++ b/src/Engine/Core/EntityFile.cpp @@ -47,7 +47,7 @@ std::size_t EntityFile::GetTypeStride(std::string typeName) { "float", sizeof(float) }, { "double", sizeof(double) }, { "string", sizeof(std::string) }, - { "enum", sizeof(int) }, + { "enum", sizeof(ComponentInfo::EnumType) }, { "Vector", sizeof(glm::vec3) }, { "Quaternion", sizeof(glm::quat) }, { "Color", sizeof(glm::vec4) } @@ -88,9 +88,12 @@ void EntityFile::WriteValueData(char* outData, const ComponentInfo::Field_t& fie { // Catch and ignore casting errors so whitespace around string enums won't mess anything up try { - if (field.Type == "int" || field.Type == "enum") { + if (field.Type == "int") { int value = boost::lexical_cast(valueData); memcpy(outData, reinterpret_cast(&value), field.Stride); + } else if (field.Type == "enum") { + ComponentInfo::EnumType value = boost::lexical_cast(valueData); + memcpy(outData, reinterpret_cast(&value), field.Stride); } else if (field.Type == "float") { float value = boost::lexical_cast(valueData); memcpy(outData, reinterpret_cast(&value), field.Stride); diff --git a/src/Engine/Core/EntityFilePreprocessor.cpp b/src/Engine/Core/EntityFilePreprocessor.cpp index 90151941..5cd56cd0 100644 --- a/src/Engine/Core/EntityFilePreprocessor.cpp +++ b/src/Engine/Core/EntityFilePreprocessor.cpp @@ -146,7 +146,7 @@ void EntityFilePreprocessor::parseComponentInfo() auto enumElement = xsChoiceParticles->elementAt(i)->getElementTerm(); std::string enumName = XS::ToString(enumElement->getName()); std::string enumValue = XS::ToString(enumElement->getConstraintValue()); - compInfo.Meta->FieldEnumDefinitions[name][enumName] = boost::lexical_cast(enumValue); + compInfo.Meta->FieldEnumDefinitions[name][enumName] = boost::lexical_cast(enumValue); LOG_DEBUG("ENUM %s = %s", enumName.c_str(), enumValue.c_str()); } } diff --git a/src/Engine/Core/EntityFileWriter.cpp b/src/Engine/Core/EntityFileWriter.cpp index 3efc9253..06a3c4ca 100644 --- a/src/Engine/Core/EntityFileWriter.cpp +++ b/src/Engine/Core/EntityFileWriter.cpp @@ -118,7 +118,7 @@ void EntityFileWriter::appentEntityComponents(xercesc::DOMElement* parentElement const int& value = c[fieldName]; fieldElement->appendChild(doc->createTextNode(X(boost::lexical_cast(value)))); } else if (field.Type == "enum") { - const int& value = c[fieldName]; + const ComponentInfo::EnumType& value = c[fieldName]; auto& enumDef = c.Info.Meta->FieldEnumDefinitions.at(fieldName); for (auto& kv : enumDef) { if (kv.second == value) { From 61984d2c4a81135ce2323e0339fa3f19c9c90603 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 13:27:29 +0100 Subject: [PATCH 104/224] Removed lots of slowing debug output from entity parsing pipeline --- src/Engine/Core/EntityFileParser.cpp | 14 ++++---- src/Engine/Core/EntityFilePreprocessor.cpp | 41 +++++++++++----------- 2 files changed, 27 insertions(+), 28 deletions(-) diff --git a/src/Engine/Core/EntityFileParser.cpp b/src/Engine/Core/EntityFileParser.cpp index 1633bbc7..23c0c4c4 100644 --- a/src/Engine/Core/EntityFileParser.cpp +++ b/src/Engine/Core/EntityFileParser.cpp @@ -28,14 +28,14 @@ void EntityFileParser::onStartEntity(EntityID entity, EntityID parent, const std m_World->SetName(realEntity, name); } m_EntityIDMapper[entity] = realEntity; - LOG_DEBUG("Created entity #%i (%i) with parent %i (%i)", entity, realEntity, parent, realParent); + //LOG_DEBUG("Created entity #%i (%i) with parent %i (%i)", entity, realEntity, parent, realParent); } void EntityFileParser::onStartComponent(EntityID entity, const std::string& component) { EntityID realEntity = m_EntityIDMapper.at(entity); m_World->AttachComponent(realEntity, component); - LOG_DEBUG("Attached component of type \"%s\" to entity #%i (%i)", component.c_str(), entity, realEntity); + //LOG_DEBUG("Attached component of type \"%s\" to entity #%i (%i)", component.c_str(), entity, realEntity); } void EntityFileParser::onStartComponentField(EntityID entity, const std::string& componentType, const std::string& fieldName, const std::map& attributes) @@ -49,11 +49,11 @@ void EntityFileParser::onStartComponentField(EntityID entity, const std::string& } auto& field = fieldIt->second; - LOG_DEBUG("Field \"%s\" type \"%s\"", fieldName.c_str(), field.Type.c_str()); - LOG_DEBUG("Attributes:"); - for (auto& kv : attributes) { - LOG_DEBUG("\t%s = %s", kv.first.c_str(), kv.second.c_str()); - } + //LOG_DEBUG("Field \"%s\" type \"%s\"", fieldName.c_str(), field.Type.c_str()); + //LOG_DEBUG("Attributes:"); + //for (auto& kv : attributes) { + // LOG_DEBUG("\t%s = %s", kv.first.c_str(), kv.second.c_str()); + //} char* data = component.Data + field.Offset; EntityFile::WriteAttributeData(data, field, attributes); diff --git a/src/Engine/Core/EntityFilePreprocessor.cpp b/src/Engine/Core/EntityFilePreprocessor.cpp index 5cd56cd0..7b4b2bb7 100644 --- a/src/Engine/Core/EntityFilePreprocessor.cpp +++ b/src/Engine/Core/EntityFilePreprocessor.cpp @@ -7,23 +7,23 @@ EntityFilePreprocessor::EntityFilePreprocessor(const EntityFile* entityFile) handler.SetStartComponentCallback(std::bind(&EntityFilePreprocessor::onStartComponent, this, std::placeholders::_1, std::placeholders::_2)); m_EntityFile->Parse(&handler); - LOG_DEBUG("___ COMPONENT DEFINITIONS ___"); - for (auto& kv : m_ComponentCounts) { - LOG_DEBUG("%s: %i", kv.first.c_str(), kv.second); - } + //LOG_DEBUG("___ COMPONENT DEFINITIONS ___"); + //for (auto& kv : m_ComponentCounts) { + // LOG_DEBUG("%s: %i", kv.first.c_str(), kv.second); + //} parseComponentInfo(); - for (auto& kv : m_ComponentInfo) { - auto& info = kv.second; - LOG_DEBUG("Component: %s (%s)", info.Name.c_str(), info.Meta->Annotation.c_str()); - LOG_DEBUG("Stride: %i", info.Stride); - LOG_DEBUG("Allocation: %i", info.Meta->Allocation); - for (auto& kv : info.Fields) { - auto& field = kv.second; - LOG_DEBUG("\t%i\t%s %s", field.Offset, field.Type.c_str(), kv.first.c_str()); - } - } + //for (auto& kv : m_ComponentInfo) { + // auto& info = kv.second; + // LOG_DEBUG("Component: %s (%s)", info.Name.c_str(), info.Meta->Annotation.c_str()); + // LOG_DEBUG("Stride: %i", info.Stride); + // LOG_DEBUG("Allocation: %i", info.Meta->Allocation); + // for (auto& kv : info.Fields) { + // auto& field = kv.second; + // LOG_DEBUG("\t%i\t%s %s", field.Offset, field.Type.c_str(), kv.first.c_str()); + // } + //} parseDefaults(); } @@ -50,7 +50,6 @@ void EntityFilePreprocessor::parseComponentInfo() auto xsModel = grammarPool->getXSModel(whateverTheFuckThisIs); // Find component xsd element declarations - std::cout << "Enumerating components..." << std::endl; // auto topLevelElements = xsModel->getComponents(XSConstants::ELEMENT_DECLARATION); for (unsigned int i = 0; i < topLevelElements->getLength(); ++i) { @@ -73,7 +72,7 @@ void EntityFilePreprocessor::parseComponentInfo() if (componentAnnotation != nullptr) { compInfo.Meta->Annotation = parseAnnotationXML(componentAnnotation->getAnnotationString()); } else { - LOG_WARNING("Component \"%s\" is missing an annotation!", compInfo.Name.c_str()); + //LOG_WARNING("Component \"%s\" is missing an annotation!", compInfo.Name.c_str()); } // @@ -91,7 +90,7 @@ void EntityFilePreprocessor::parseComponentInfo() // auto modelGroupParticle = complexTypeDefinition->getParticle(); if (modelGroupParticle == nullptr || modelGroupParticle->getTermType() != XSParticle::TERM_MODELGROUP) { - LOG_ERROR("Failed to parse component definition for \"%s\": Model group particle was null or wasn't TERM_MODELGROUP!", compInfo.Name.c_str()); + //LOG_ERROR("Failed to parse component definition for \"%s\": Model group particle was null or wasn't TERM_MODELGROUP!", compInfo.Name.c_str()); continue; } auto modelGroup = modelGroupParticle->getModelGroupTerm(); @@ -103,7 +102,7 @@ void EntityFilePreprocessor::parseComponentInfo() for (unsigned int i = 0; i < particles->size(); ++i) { auto particle = particles->elementAt(i); if (particle->getTermType() != XSParticle::TERM_ELEMENT) { - LOG_ERROR("Failed to parse a field definition in component \"%s\": Particle wasn't TERM_ELEMENT! Skipping.", compInfo.Name.c_str()); + //LOG_ERROR("Failed to parse a field definition in component \"%s\": Particle wasn't TERM_ELEMENT! Skipping.", compInfo.Name.c_str()); continue; } auto elementDeclaration = particle->getElementTerm(); @@ -129,7 +128,7 @@ void EntityFilePreprocessor::parseComponentInfo() if (fieldAnnotation != nullptr) { compInfo.Meta->FieldAnnotations[name] = parseAnnotationXML(fieldAnnotation->getAnnotationString()); } else { - LOG_WARNING("Component field \"%s.%s\" is missing an annotation!", compInfo.Name.c_str(), name.c_str()); + //LOG_WARNING("Component field \"%s.%s\" is missing an annotation!", compInfo.Name.c_str(), name.c_str()); } if (effectiveType == "enum") { @@ -147,7 +146,7 @@ void EntityFilePreprocessor::parseComponentInfo() std::string enumName = XS::ToString(enumElement->getName()); std::string enumValue = XS::ToString(enumElement->getConstraintValue()); compInfo.Meta->FieldEnumDefinitions[name][enumName] = boost::lexical_cast(enumValue); - LOG_DEBUG("ENUM %s = %s", enumName.c_str(), enumValue.c_str()); + //LOG_DEBUG("ENUM %s = %s", enumName.c_str(), enumValue.c_str()); } } } @@ -190,7 +189,7 @@ void EntityFilePreprocessor::parseDefaults() //std::string namespaceSchema = schemaLocation.string(); //parser.setExternalNoNamespaceSchemaLocation("Teamasdasdasdasd.xsd"); - LOG_DEBUG("Parsing defaults for component %s", componentName.c_str()); + //LOG_DEBUG("Parsing defaults for component %s", componentName.c_str()); boost::filesystem::path defaultsFile = "Schema/Components/" + componentName + ".xml"; parser.parse(defaultsFile.string().c_str()); From d030e8f6990fefeb97440efcfec6f33a64e43b93 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 13:28:02 +0100 Subject: [PATCH 105/224] Editor widget selection and creation --- include/Engine/Editor/EditorGUI.h | 13 +++++ include/Engine/Editor/EditorSystem.h | 7 ++- include/Engine/Editor/EditorWidgetSystem.h | 6 +++ resources/Schema/Components/EditorWidget.xml | 2 +- resources/Schema/Components/EditorWidget.xsd | 7 ++- src/Engine/Editor/EditorGUI.cpp | 50 ++++++++++++++++++-- src/Engine/Editor/EditorSystem.cpp | 42 ++++++++++++++-- 7 files changed, 112 insertions(+), 15 deletions(-) create mode 100644 include/Engine/Editor/EditorWidgetSystem.h diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 9d2712e1..104c6787 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -10,6 +10,7 @@ #include "../GLM.h" #include +#include "EditorWidgetSystem.h" #include "../Core/EventBroker.h" #include "../Core/World.h" #include "../Core/EntityWrapper.h" @@ -22,6 +23,13 @@ class EditorGUI public: EditorGUI(World* world, EventBroker* eventBroker); + enum class WidgetMode + { + Translate, + Rotate, + Scale + }; + void Draw(); void SelectEntity(EntityWrapper entity); @@ -59,6 +67,9 @@ public: // Called when the user means to delete a component off an entity. typedef std::function OnComponentDelete_t; void SetComponentDeleteCallback(OnComponentDelete_t f) { m_OnComponentDelete = f; } + // Called when the user selects a widget mode. + typedef std::function OnWidgetMode_t; + void SetWidgetModeCallback(OnWidgetMode_t f) { m_OnWidgetMode = f; } private: World* m_World; @@ -72,6 +83,7 @@ private: std::unordered_map m_EntityFiles; EntityWrapper m_CurrentlyDragging = EntityWrapper::Invalid; std::string m_LastErrorMessage; + WidgetMode m_CurrentWidgetMode = WidgetMode::Translate; // Callbacks OnEntitySelectedCallback_t m_OnEntitySelected = nullptr; @@ -83,6 +95,7 @@ private: OnEntityChangeName_t m_OnEntityChangeName = nullptr; OnComponentAttach_t m_OnComponentAttach = nullptr; OnComponentDelete_t m_OnComponentDelete = nullptr; + OnWidgetMode_t m_OnWidgetMode = nullptr; // Utility functions boost::filesystem::path fileOpenDialog(); diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index c0db917d..31d5064c 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -26,14 +26,19 @@ private: World* m_EditorWorld; SystemPipeline* m_EditorWorldSystemPipeline; Camera* m_EditorCamera; - EntityWrapper m_Widget = EntityWrapper::Invalid; EntityWrapper m_Camera = EntityWrapper::Invalid; DebugCameraInputController* m_DebugCameraInputController; EditorGUI* m_EditorGUI; EditorStats* m_EditorStats; + // State + EditorGUI::WidgetMode m_WidgetMode = EditorGUI::WidgetMode::Translate; + EntityWrapper m_Widget = EntityWrapper::Invalid; + EntityWrapper m_CurrentSelection = EntityWrapper::Invalid; + // Utility functions EntityWrapper importEntity(EntityWrapper parent, boost::filesystem::path filePath); + void setWidgetMode(EditorGUI::WidgetMode mode); // GUI callbacks void OnEntitySelected(EntityWrapper entity); diff --git a/include/Engine/Editor/EditorWidgetSystem.h b/include/Engine/Editor/EditorWidgetSystem.h new file mode 100644 index 00000000..2350d24b --- /dev/null +++ b/include/Engine/Editor/EditorWidgetSystem.h @@ -0,0 +1,6 @@ +#ifndef EditorWidgetSystem_h__ +#define EditorWidgetSystem_h__ + + + +#endif diff --git a/resources/Schema/Components/EditorWidget.xml b/resources/Schema/Components/EditorWidget.xml index 6a94d2f6..fed2f809 100644 --- a/resources/Schema/Components/EditorWidget.xml +++ b/resources/Schema/Components/EditorWidget.xml @@ -1,5 +1,5 @@ - + \ No newline at end of file diff --git a/resources/Schema/Components/EditorWidget.xsd b/resources/Schema/Components/EditorWidget.xsd index e4c4ff71..3d08e82e 100644 --- a/resources/Schema/Components/EditorWidget.xsd +++ b/resources/Schema/Components/EditorWidget.xsd @@ -7,10 +7,9 @@ - - - - + + + diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 1bf0f9e9..318e3199 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -36,13 +36,55 @@ void EditorGUI::drawTools() } // Translate widget button - ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Translate.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); + if (ImGui::ImageButton( + (void*)tryLoadTexture("Textures/Icons/Translate.png"), + ImVec2(24, 24), + ImVec2(0, 1), + ImVec2(1, 0), + -1, + ImVec4(0, 0, 0, 0), + (m_CurrentWidgetMode == WidgetMode::Translate) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1) + ) + ) { + m_CurrentWidgetMode = WidgetMode::Translate; + if (m_OnWidgetMode != nullptr) { + m_OnWidgetMode(m_CurrentWidgetMode); + } + } // Rotate widget button ImGui::SameLine(); - ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Rotate.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); + if (ImGui::ImageButton( + (void*)tryLoadTexture("Textures/Icons/Rotate.png"), + ImVec2(24, 24), + ImVec2(0, 1), + ImVec2(1, 0), + -1, + ImVec4(0, 0, 0, 0), + (m_CurrentWidgetMode == WidgetMode::Rotate) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1) + ) + ) { + m_CurrentWidgetMode = WidgetMode::Rotate; + if (m_OnWidgetMode != nullptr) { + m_OnWidgetMode(m_CurrentWidgetMode); + } + } // Scale widget button ImGui::SameLine(); - ImGui::ImageButton((void*)tryLoadTexture("Textures/Icons/Scale.png"), ImVec2(24, 24), ImVec2(0, 1), ImVec2(1, 0)); + if (ImGui::ImageButton( + (void*)tryLoadTexture("Textures/Icons/Scale.png"), + ImVec2(24, 24), + ImVec2(0, 1), + ImVec2(1, 0), + -1, + ImVec4(0, 0, 0, 0), + (m_CurrentWidgetMode == WidgetMode::Scale) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1) + ) + ) { + m_CurrentWidgetMode = WidgetMode::Scale; + if (m_OnWidgetMode != nullptr) { + m_OnWidgetMode(m_CurrentWidgetMode); + } + } ImGui::SameLine(); ImGui::ItemSize(ImVec2(5, 0)); @@ -83,7 +125,7 @@ void EditorGUI::drawEntities(World* world) entityImport(world); } ImGui::SameLine(0.f, 5.f); - ImGui::Button("Reference", ImVec2(buttonWidth, 0)); + ImGui::ButtonEx("Reference", ImVec2(buttonWidth, 0), ImGuiButtonFlags_Disabled); // Naming char buffer[256]; diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 36f2baa4..03b90a37 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -12,9 +12,7 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorWorldSystemPipeline->AddSystem(0); m_EditorWorldSystemPipeline->AddSystem(1, m_Renderer, m_RenderFrame); - m_Widget = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/EditorWidget.xml"); - - m_Camera = EntityWrapper(m_EditorWorld, m_EditorWorld->CreateEntity()); + m_Camera = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/Empty.xml"); m_EditorWorld->AttachComponent(m_Camera.ID, "Transform"); m_EditorWorld->AttachComponent(m_Camera.ID, "Camera"); m_DebugCameraInputController = new DebugCameraInputController(m_EventBroker, -1); @@ -29,6 +27,7 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorGUI->SetEntityChangeNameCallback(std::bind(&EditorSystem::OnEntityChangeName, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetComponentAttachCallback(std::bind(&EditorSystem::OnComponentAttach, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetComponentDeleteCallback(std::bind(&EditorSystem::OnComponentDelete, this, std::placeholders::_1, std::placeholders::_2)); + m_EditorGUI->SetWidgetModeCallback(std::bind(&EditorSystem::setWidgetMode, this, std::placeholders::_1)); m_EditorStats = new EditorStats(); @@ -60,7 +59,8 @@ void EditorSystem::Update(double dt) void EditorSystem::OnEntitySelected(EntityWrapper entity) { - m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(entity.World, entity.ID); + m_CurrentSelection = entity; + setWidgetMode(m_WidgetMode); } void EditorSystem::OnEntitySave(EntityWrapper entity, boost::filesystem::path filePath) @@ -118,4 +118,36 @@ EntityWrapper EditorSystem::importEntity(EntityWrapper parent, boost::filesystem } catch (const std::exception&) { return EntityWrapper::Invalid; } -} \ No newline at end of file +} + +void EditorSystem::setWidgetMode(EditorGUI::WidgetMode mode) +{ + if (mode == m_WidgetMode && m_Widget.Valid() && m_CurrentSelection.Valid()) { + return; + } + + if (m_Widget.Valid()) { + m_Widget.World->DeleteEntity(m_Widget.ID); + m_Widget = EntityWrapper::Invalid; + } + + if (!m_CurrentSelection.Valid()) { + return; + } + + switch (mode) { + case EditorGUI::WidgetMode::Translate: + m_Widget = importEntity(EntityWrapper(m_World, EntityID_Invalid), "Schema/Entities/EditorWidgetTranslate.xml"); + break; + case EditorGUI::WidgetMode::Rotate: + m_Widget = importEntity(EntityWrapper(m_World, EntityID_Invalid), "Schema/Entities/EditorWidgetRotate.xml"); + break; + case EditorGUI::WidgetMode::Scale: + m_Widget = importEntity(EntityWrapper(m_World, EntityID_Invalid), "Schema/Entities/EditorWidgetScale.xml"); + break; + } + + m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(m_CurrentSelection.World, m_CurrentSelection.ID); + + m_WidgetMode = mode; +} From 260203fa4d7657a787e43a2edc42130ea5d03869 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 13:28:16 +0100 Subject: [PATCH 106/224] Annotation on physics component --- resources/Schema/Components/Physics.xsd | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/resources/Schema/Components/Physics.xsd b/resources/Schema/Components/Physics.xsd index 001dd2c8..554f76fd 100644 --- a/resources/Schema/Components/Physics.xsd +++ b/resources/Schema/Components/Physics.xsd @@ -9,7 +9,9 @@ - + + m/s^2 + From 8854794cbcf997b00df81242c086c41d0d9dae46 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Tue, 19 Jan 2016 13:32:32 +0100 Subject: [PATCH 107/224] fixup! Editor widget selection and creation --- include/Engine/Editor/EditorGUI.h | 1 + .../Schema/Entities/EditorWidgetRotate.xml | 11 ++- .../Schema/Entities/EditorWidgetScale.xml | 6 +- .../Schema/Entities/EditorWidgetTranslate.xml | 45 ++-------- src/Engine/Editor/EditorGUI.cpp | 85 +++++++++---------- src/Engine/Editor/EditorSystem.cpp | 10 +-- 6 files changed, 64 insertions(+), 94 deletions(-) diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 104c6787..49e0f8ab 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -131,6 +131,7 @@ private: // Custom UI elements bool createDeleteButton(const std::string& componentType); + void createWidgetToolButton(WidgetMode mode); }; #endif \ No newline at end of file diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml index 55dd9af4..8c454f0c 100644 --- a/resources/Schema/Entities/EditorWidgetRotate.xml +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -3,6 +3,9 @@ + + + @@ -12,7 +15,6 @@ - Models/RotationWidgetX.obj @@ -27,7 +29,6 @@ - Models/RotationWidgetY.obj @@ -42,7 +43,6 @@ - Models/RotationWidgetZ.obj @@ -53,7 +53,10 @@ - + + -1 + 0 + diff --git a/resources/Schema/Entities/EditorWidgetScale.xml b/resources/Schema/Entities/EditorWidgetScale.xml index b317b1cc..15bcb38b 100644 --- a/resources/Schema/Entities/EditorWidgetScale.xml +++ b/resources/Schema/Entities/EditorWidgetScale.xml @@ -6,6 +6,9 @@ Models/ScaleWidgetOrigin.obj + + + @@ -15,7 +18,6 @@ - Models/ScaleWidgetX.obj @@ -30,7 +32,6 @@ - Models/ScaleWidgetY.obj @@ -45,7 +46,6 @@ - Models/ScaleWidgetZ.obj diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml index 56943adc..e2cfd69a 100644 --- a/resources/Schema/Entities/EditorWidgetTranslate.xml +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -6,17 +6,15 @@ Models/TranslationWidgetOrigin.obj + + + - - - - - - + Models/TranslationWidgetX.obj @@ -26,12 +24,7 @@ - - - - - - + Models/TranslationWidgetY.obj @@ -41,12 +34,7 @@ - - - - - - + Models/TranslationWidgetZ.obj @@ -56,12 +44,7 @@ - - - - - - + Models/WidgetPlaneX.obj @@ -71,12 +54,7 @@ - - - - - - + Models/WidgetPlaneY.obj @@ -86,12 +64,7 @@ - - - - - - + Models/WidgetPlaneZ.obj diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index 318e3199..f65386aa 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -35,57 +35,20 @@ void EditorGUI::drawTools() return; } - // Translate widget button - if (ImGui::ImageButton( - (void*)tryLoadTexture("Textures/Icons/Translate.png"), - ImVec2(24, 24), - ImVec2(0, 1), - ImVec2(1, 0), - -1, - ImVec4(0, 0, 0, 0), - (m_CurrentWidgetMode == WidgetMode::Translate) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1) - ) - ) { - m_CurrentWidgetMode = WidgetMode::Translate; - if (m_OnWidgetMode != nullptr) { - m_OnWidgetMode(m_CurrentWidgetMode); - } + createWidgetToolButton(WidgetMode::Translate); + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip("Translate"); } - // Rotate widget button ImGui::SameLine(); - if (ImGui::ImageButton( - (void*)tryLoadTexture("Textures/Icons/Rotate.png"), - ImVec2(24, 24), - ImVec2(0, 1), - ImVec2(1, 0), - -1, - ImVec4(0, 0, 0, 0), - (m_CurrentWidgetMode == WidgetMode::Rotate) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1) - ) - ) { - m_CurrentWidgetMode = WidgetMode::Rotate; - if (m_OnWidgetMode != nullptr) { - m_OnWidgetMode(m_CurrentWidgetMode); - } + createWidgetToolButton(WidgetMode::Rotate); + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip("Rotate"); } - // Scale widget button ImGui::SameLine(); - if (ImGui::ImageButton( - (void*)tryLoadTexture("Textures/Icons/Scale.png"), - ImVec2(24, 24), - ImVec2(0, 1), - ImVec2(1, 0), - -1, - ImVec4(0, 0, 0, 0), - (m_CurrentWidgetMode == WidgetMode::Scale) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1) - ) - ) { - m_CurrentWidgetMode = WidgetMode::Scale; - if (m_OnWidgetMode != nullptr) { - m_OnWidgetMode(m_CurrentWidgetMode); - } + createWidgetToolButton(WidgetMode::Scale); + if (ImGui::IsItemHovered()) { + ImGui::SetTooltip("Scale"); } - ImGui::SameLine(); ImGui::ItemSize(ImVec2(5, 0)); @@ -497,6 +460,36 @@ bool EditorGUI::createDeleteButton(const std::string& componentType) return pressed; } +void EditorGUI::createWidgetToolButton(WidgetMode mode) +{ + GLuint texture = 0; + switch (mode) { + case WidgetMode::Translate: + texture = tryLoadTexture("Textures/Icons/Translate.png"); + break; + case WidgetMode::Rotate: + texture = tryLoadTexture("Textures/Icons/Rotate.png"); + break; + case WidgetMode::Scale: + texture = tryLoadTexture("Textures/Icons/Scale.png"); + break; + } + if (ImGui::ImageButton( + (void*)texture, + ImVec2(24, 24), + ImVec2(0, 1), + ImVec2(1, 0), + -1, + ImVec4(0, 0, 0, 0), + (m_CurrentWidgetMode == mode) ? ImVec4(0, 1, 0, 1) : ImVec4(1, 1, 1, 1) + ) + ) { + if (m_OnWidgetMode != nullptr) { + m_OnWidgetMode(mode); + } + m_CurrentWidgetMode = mode; + } +} boost::filesystem::path EditorGUI::fileOpenDialog() { diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 03b90a37..596f8154 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -126,6 +126,8 @@ void EditorSystem::setWidgetMode(EditorGUI::WidgetMode mode) return; } + m_WidgetMode = mode; + if (m_Widget.Valid()) { m_Widget.World->DeleteEntity(m_Widget.ID); m_Widget = EntityWrapper::Invalid; @@ -137,17 +139,15 @@ void EditorSystem::setWidgetMode(EditorGUI::WidgetMode mode) switch (mode) { case EditorGUI::WidgetMode::Translate: - m_Widget = importEntity(EntityWrapper(m_World, EntityID_Invalid), "Schema/Entities/EditorWidgetTranslate.xml"); + m_Widget = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/EditorWidgetTranslate.xml"); break; case EditorGUI::WidgetMode::Rotate: - m_Widget = importEntity(EntityWrapper(m_World, EntityID_Invalid), "Schema/Entities/EditorWidgetRotate.xml"); + m_Widget = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/EditorWidgetRotate.xml"); break; case EditorGUI::WidgetMode::Scale: - m_Widget = importEntity(EntityWrapper(m_World, EntityID_Invalid), "Schema/Entities/EditorWidgetScale.xml"); + m_Widget = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/EditorWidgetScale.xml"); break; } m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(m_CurrentSelection.World, m_CurrentSelection.ID); - - m_WidgetMode = mode; } From 982837052a2816eda655a55db3b9272ed0cd5d4b Mon Sep 17 00:00:00 2001 From: Tleety Date: Tue, 19 Jan 2016 14:44:17 +0100 Subject: [PATCH 108/224] DirectionalLight now correctly getting directions --- .../Engine/Rendering/DirectionalLightJob.h | 2 +- .../Schema/Components/DirectionalLight.xml | 5 +- .../Schema/Components/DirectionalLight.xsd | 2 - resources/Schema/Entities/EditorTestWorld.xml | 54 ++++++++++++++++++- resources/Schema/Types/Entity.xsd | 1 + resources/Shaders/ForwardPlus.frag.glsl | 2 +- resources/Shaders/ForwardPlus.vert.glsl | 2 +- 7 files changed, 59 insertions(+), 9 deletions(-) diff --git a/include/Engine/Rendering/DirectionalLightJob.h b/include/Engine/Rendering/DirectionalLightJob.h index f6942112..5f104ca5 100644 --- a/include/Engine/Rendering/DirectionalLightJob.h +++ b/include/Engine/Rendering/DirectionalLightJob.h @@ -16,7 +16,7 @@ struct DirectionalLightJob : RenderJob : RenderJob() { - Direction = glm::vec4(0,0,-1,0) * Transform::AbsoluteOrientation(m_World, transformComponent.EntityID); + Direction = glm::vec4(0,0,-1,0) * glm::inverse(Transform::AbsoluteOrientation(m_World, transformComponent.EntityID)); //Direction = glm::vec4((glm::vec3)directionalLightComponent["Direction"], 0.f); Color = (glm::vec4)directionalLightComponent["Color"]; Intensity = (double)directionalLightComponent["Intensity"]; diff --git a/resources/Schema/Components/DirectionalLight.xml b/resources/Schema/Components/DirectionalLight.xml index f66605c0..7f777ef8 100644 --- a/resources/Schema/Components/DirectionalLight.xml +++ b/resources/Schema/Components/DirectionalLight.xml @@ -1,5 +1,6 @@ - + + 0.8 true - \ No newline at end of file + \ No newline at end of file diff --git a/resources/Schema/Components/DirectionalLight.xsd b/resources/Schema/Components/DirectionalLight.xsd index dbfee38c..a14248a8 100644 --- a/resources/Schema/Components/DirectionalLight.xsd +++ b/resources/Schema/Components/DirectionalLight.xsd @@ -1,8 +1,6 @@ - - A directional light that shines bright like the future. diff --git a/resources/Schema/Entities/EditorTestWorld.xml b/resources/Schema/Entities/EditorTestWorld.xml index e44d238e..a482cf1b 100755 --- a/resources/Schema/Entities/EditorTestWorld.xml +++ b/resources/Schema/Entities/EditorTestWorld.xml @@ -13,6 +13,7 @@ + @@ -45,9 +46,58 @@ + - - + + + + + + + + + + + Models/DirectionalLightWidget.obj + + + + + + + + + + + + Models/Assault.obj + + + + + + + + + + Models/SecondaryWeapon4.fbx + + + + + + + + + + + + + + Models/Core/UnitSphere.obj + + + diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 1aaa8497..14e3c5a4 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -27,6 +27,7 @@ + diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 0298c969..e67a4d5d 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -88,7 +88,7 @@ LightResult CalcPointLightSource(vec4 lightPos, float lightRadius, vec4 lightCol LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensity, vec4 viewVec, vec4 vertNormal) { - vec4 L = normalize( -direction ); + vec4 L = normalize( -vec4(direction.xyz, 0) ); LightResult result; result.Diffuse = CalcDiffuse(color, L, vertNormal) * intensity; diff --git a/resources/Shaders/ForwardPlus.vert.glsl b/resources/Shaders/ForwardPlus.vert.glsl index 20ab9051..d3b8ba16 100644 --- a/resources/Shaders/ForwardPlus.vert.glsl +++ b/resources/Shaders/ForwardPlus.vert.glsl @@ -29,6 +29,6 @@ void main() Output.Position = Position; Output.TextureCoordinate = TextureCoords; - Output.Normal = Normal; + Output.Normal = vec3(M * vec4(Normal, 0.0)); Output.DiffuseColor = DiffuseVertexColor; } \ No newline at end of file From 713ebbe18c21a098010a5496813b9dff3ce45947 Mon Sep 17 00:00:00 2001 From: William Moberg Date: Tue, 19 Jan 2016 14:50:46 +0100 Subject: [PATCH 109/224] Can add any objects that inherit from AABB into the Octree. --- .../Engine/Collision/CollidableOctreeSystem.h | 4 +- include/Engine/Collision/CollisionSystem.h | 4 +- include/Engine/Collision/TriggerSystem.h | 4 +- include/Engine/Core/Octree.h | 258 +++++++++++++----- include/Game/Game.h | 4 +- src/Engine/Collision/CollisionSystem.cpp | 2 +- src/Engine/Core/Octree.cpp | 133 ++------- src/Game/Game.cpp | 4 +- 8 files changed, 224 insertions(+), 189 deletions(-) diff --git a/include/Engine/Collision/CollidableOctreeSystem.h b/include/Engine/Collision/CollidableOctreeSystem.h index 8fa1f0a4..c61e774c 100644 --- a/include/Engine/Collision/CollidableOctreeSystem.h +++ b/include/Engine/Collision/CollidableOctreeSystem.h @@ -8,7 +8,7 @@ class CollidableOctreeSystem : public ImpureSystem, public PureSystem { public: - CollidableOctreeSystem(EventBroker* eventBroker, Octree* octree) + CollidableOctreeSystem(EventBroker* eventBroker, Octree* octree) : System(eventBroker) , PureSystem("Collidable") , m_Octree(octree) @@ -18,7 +18,7 @@ public: virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: - Octree* m_Octree; + Octree* m_Octree; }; #endif \ No newline at end of file diff --git a/include/Engine/Collision/CollisionSystem.h b/include/Engine/Collision/CollisionSystem.h index 561c5158..7815254d 100644 --- a/include/Engine/Collision/CollisionSystem.h +++ b/include/Engine/Collision/CollisionSystem.h @@ -13,7 +13,7 @@ class CollisionSystem : public PureSystem { public: - CollisionSystem(EventBroker* eventBroker, Octree* octree) + CollisionSystem(EventBroker* eventBroker, Octree* octree) : System(eventBroker) , PureSystem("Collidable") , m_Octree(octree) @@ -26,7 +26,7 @@ public: virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: - Octree* m_Octree; + Octree* m_Octree; bool zPress; EventRelay m_EKeyUp; diff --git a/include/Engine/Collision/TriggerSystem.h b/include/Engine/Collision/TriggerSystem.h index 65e7c271..1b423e76 100644 --- a/include/Engine/Collision/TriggerSystem.h +++ b/include/Engine/Collision/TriggerSystem.h @@ -14,7 +14,7 @@ class AABB; class TriggerSystem : public PureSystem { public: - TriggerSystem(EventBroker* eventBroker, Octree* octree) + TriggerSystem(EventBroker* eventBroker, Octree* octree) : System(eventBroker) , PureSystem("Trigger") , m_Octree(octree) @@ -27,7 +27,7 @@ public: virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) override; private: - Octree* m_Octree; + Octree* m_Octree; std::unordered_map> m_EntitiesTouchingTrigger; std::unordered_map> m_EntitiesCompletelyInTrigger; diff --git a/include/Engine/Core/Octree.h b/include/Engine/Core/Octree.h index 954dbcbc..bbd27b3c 100644 --- a/include/Engine/Core/Octree.h +++ b/include/Engine/Core/Octree.h @@ -1,19 +1,27 @@ #ifndef Octree_h__ #define Octree_h__ +#include + #include "../Common.h" #include "AABB.h" +//Fwd declarations. class Ray; +namespace OctSpace +{ +struct Output; +struct ContainedObject; +struct Child; +} + +//T needs to be AABB, or inherit from AABB. +//T also needs to have a default constructor. +template class Octree { public: - struct Output - { - float CollideDistance; - }; - Octree() = delete; ~Octree(); //For the root Octree, [octreeBounds] should be a box containing the entire level. @@ -25,81 +33,201 @@ public: Octree(const Octree&& other) = delete; Octree& operator= (const Octree& other) = delete; //Add a dynamic object (one that moves around) into the tree. - void AddDynamicObject(const AABB& box); + void AddDynamicObject(const T& object); //Add a static object (that does not move) into the tree. - void AddStaticObject(const AABB& box); - //Get the boxes that are in the same area as the input [box], the boxes are put in [outBoxes]. - void BoxesInSameRegion(const AABB& box, std::vector& outBoxes); + void AddStaticObject(const T& object); + //Get the objects that are in the same area as the input [box], the objects are put in [outObjects]. + //The type Box must be AABB, or inherit from AABB. + template + void ObjectsInSameRegion(const Box& box, std::vector& outObjects); //Empty the tree of all objects, static and dynamic. void ClearObjects(); //Empty the tree of all dynamic objects. Static objects remain in the tree. void ClearDynamicObjects(); //Returns true if the ray collides with something in the tree. Result is written to [data]. - bool RayCollides(const Ray& ray, Output& data); + bool RayCollides(const Ray& ray, OctSpace::Output& data); //Returns true if the box collides with something in the tree. //On collision with a box, that box is written to [outBoxIntersected]. - //Note: More efficient than calling BoxesInSameRegion from outside and testing there. + //Note: More efficient than calling ObjectsInSameRegion from outside and testing there. bool BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected); private: - struct Child; //Fwd declaration; - struct ContainedObject - { - ContainedObject() - : Box(AABB()) - , Checked(false) - {} - ContainedObject(AABB box) - : Box(box) - , Checked(false) - {} - AABB Box; - bool Checked; - }; - Child* m_Root; - std::vector m_StaticObjects; - std::vector m_DynamicObjects; - - bool m_UpdatedOnce; - unsigned int m_BoxID; - glm::vec3 m_PrevPos; - glm::quat m_PrevOri; + OctSpace::Child* m_Root; + std::vector m_StaticObjects; + std::vector m_DynamicObjects; void falsifyObjectChecks(); - - struct Child - { - ~Child(); - Child(const AABB& octTreeBounds, - int subDivisions, - std::vector& staticObjects, - std::vector& dynamicObjects); - Child(const Child& other) = delete; - Child(const Child&& other) = delete; - Child& operator= (const Child& other) = delete; - void AddDynamicObject(const AABB& box); - void AddStaticObject(const AABB& box); - void BoxesInSameRegion(const AABB& box, std::vector& outBoxes) const; - void ClearObjects(); - void ClearDynamicObjects(); - bool RayCollides(const Ray& ray, Output& data) const; - bool BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) const; - - Child* m_Children[8]; - //Indices into the lists in Octree. - std::vector m_StaticObjIndices; - std::vector m_DynamicObjIndices; - AABB m_Box; - //Reference to the lists in Octree. - std::vector& m_StaticObjectsRef; - std::vector& m_DynamicObjectsRef; - - inline bool hasChildren() const; - int childIndexContainingPoint(const glm::vec3& point) const; - std::vector childIndicesContainingBox(const AABB& box) const; - }; }; +namespace OctSpace +{ + +struct Output +{ + float CollideDistance; +}; + +struct ContainedObject +{ + ContainedObject() + : Box(nullptr) + , Checked(false) + {} + template + ContainedObject(const BoxlikeObject& box) + : Box(new BoxlikeObject(box)) + , Checked(false) + {} + std::unique_ptr Box; + bool Checked; +}; + +struct Child +{ + ~Child(); + Child(const AABB& octTreeBounds, + int subDivisions, + std::vector& staticObjects, + std::vector& dynamicObjects); + Child(const Child& other) = delete; + Child(const Child&& other) = delete; + Child& operator= (const Child& other) = delete; + void AddDynamicObject(const AABB& box); + void AddStaticObject(const AABB& box); + template + void ObjectsInSameRegion(const Box& box, std::vector& outObjects) const; + void ClearObjects(); + void ClearDynamicObjects(); + bool RayCollides(const Ray& ray, Output& data) const; + bool BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) const; + + Child* m_Children[8]; + //Indices into the lists in Octree. + std::vector m_StaticObjIndices; + std::vector m_DynamicObjIndices; + AABB m_Box; + //Reference to the lists in Octree. + std::vector& m_StaticObjectsRef; + std::vector& m_DynamicObjectsRef; + + inline bool hasChildren() const; + int childIndexContainingPoint(const glm::vec3& point) const; + std::vector childIndicesContainingBox(const AABB& box) const; +}; + +} + +template +Octree::Octree(const AABB& octTreeBounds, int subDivisions) + : m_Root(new OctSpace::Child(octTreeBounds, subDivisions, m_StaticObjects, m_DynamicObjects)) +{ + static_assert(std::is_base_of::value, "template argument type T in Octree must be a subclass of AABB."); +} + +template +Octree::~Octree() +{ + delete m_Root; +} + +template +void Octree::AddDynamicObject(const T& object) +{ + m_Root->AddDynamicObject(object); + m_DynamicObjects.emplace_back(object); +} + +template +void Octree::AddStaticObject(const T& object) +{ + m_Root->AddStaticObject(object); + m_StaticObjects.emplace_back(object); +} + +template +template +void Octree::ObjectsInSameRegion(const Box& box, std::vector& outObjects) +{ + static_assert(std::is_base_of::value, "template argument type Box in Octree::ObjectsInSameRegion must be a subclass of AABB."); + falsifyObjectChecks(); + m_Root->ObjectsInSameRegion(box, outObjects); +} + +template +void Octree::ClearObjects() +{ + m_StaticObjects.clear(); + m_DynamicObjects.clear(); + m_Root->ClearObjects(); +} + +template +void Octree::ClearDynamicObjects() +{ + m_DynamicObjects.clear(); + m_Root->ClearDynamicObjects(); +} + +template +bool Octree::RayCollides(const Ray& ray, OctSpace::Output& data) +{ + falsifyObjectChecks(); + data.CollideDistance = -1; + return m_Root->RayCollides(ray, data); +} + +template +bool Octree::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) +{ + falsifyObjectChecks(); + return m_Root->BoxCollides(boxToTest, outBoxIntersected); +} + +template +void Octree::falsifyObjectChecks() +{ + for (auto& obj : m_StaticObjects) { + obj.Checked = false; + } + for (auto& obj : m_DynamicObjects) { + obj.Checked = false; + } +} + +template +void OctSpace::Child::ObjectsInSameRegion(const Box& box, std::vector& outObjects) const +{ + if (hasChildren()) { + for (auto i : childIndicesContainingBox(box)) { + m_Children[i]->ObjectsInSameRegion(box, outObjects); + } + } else { + size_t startIndex = outObjects.size(); + int numDuplicates = 0; + outObjects.resize(outObjects.size() + m_StaticObjIndices.size() + m_DynamicObjIndices.size()); + for (size_t i = 0; i < m_StaticObjIndices.size(); ++i) { + ContainedObject& obj = m_StaticObjectsRef[m_StaticObjIndices[i]]; + if (obj.Checked) { + ++numDuplicates; + } else { + obj.Checked = true; + outObjects[startIndex + i - numDuplicates] = *static_cast(obj.Box.get()); + } + } + for (size_t i = 0; i < m_DynamicObjIndices.size(); ++i) { + ContainedObject& obj = m_DynamicObjectsRef[m_DynamicObjIndices[i]]; + if (obj.Checked) { + ++numDuplicates; + } else { + obj.Checked = true; + outObjects[startIndex + i - numDuplicates] = *static_cast(obj.Box.get()); + } + } + for (size_t i = 0; i < numDuplicates; ++i) { + outObjects.pop_back(); + } + } +} #endif \ No newline at end of file diff --git a/include/Game/Game.h b/include/Game/Game.h index dbc2ed45..d3a79328 100644 --- a/include/Game/Game.h +++ b/include/Game/Game.h @@ -47,8 +47,8 @@ private: InputProxy* m_InputProxy; GUI::Frame* m_FrameStack; World* m_World; - Octree* m_OctreeCollision; - Octree* m_OctreeFrustrumCulling; + Octree* m_OctreeCollision; + Octree* m_OctreeFrustrumCulling; SystemPipeline* m_SystemPipeline; RenderFrame* m_RenderFrame; // Network variables diff --git a/src/Engine/Collision/CollisionSystem.cpp b/src/Engine/Collision/CollisionSystem.cpp index d841c75e..a9d125ac 100644 --- a/src/Engine/Collision/CollisionSystem.cpp +++ b/src/Engine/Collision/CollisionSystem.cpp @@ -23,7 +23,7 @@ void CollisionSystem::UpdateComponent(World* world, EntityWrapper& entity, Compo // Collide against octree std::vector octreeResult; - m_Octree->BoxesInSameRegion(*boundingBox, octreeResult); + m_Octree->ObjectsInSameRegion(*boundingBox, octreeResult); for (auto& boxB : octreeResult) { glm::vec3 resolutionVector; if (Collision::IsSameBoxProbably(boxA, boxB)) { diff --git a/src/Engine/Core/Octree.cpp b/src/Engine/Core/Octree.cpp index 58501117..d7feba45 100644 --- a/src/Engine/Core/Octree.cpp +++ b/src/Engine/Core/Octree.cpp @@ -21,72 +21,11 @@ bool isFirstLower(const ChildInfo& first, const ChildInfo& second) } -Octree::Octree(const AABB& octTreeBounds, int subDivisions) - : m_Root(new Child(octTreeBounds, subDivisions, m_StaticObjects, m_DynamicObjects)) - , m_UpdatedOnce(false) -{ } - -Octree::~Octree() +namespace OctSpace { - delete m_Root; -} -void Octree::AddDynamicObject(const AABB& box) -{ - m_Root->AddDynamicObject(box); - m_DynamicObjects.push_back(box); -} - -void Octree::AddStaticObject(const AABB& box) -{ - m_Root->AddStaticObject(box); - m_StaticObjects.push_back(box); -} - -void Octree::BoxesInSameRegion(const AABB& box, std::vector& outBoxes) -{ - falsifyObjectChecks(); - m_Root->BoxesInSameRegion(box, outBoxes); -} - -void Octree::ClearObjects() -{ - m_StaticObjects.clear(); - m_DynamicObjects.clear(); - m_Root->ClearObjects(); -} - -void Octree::ClearDynamicObjects() -{ - m_DynamicObjects.clear(); - m_Root->ClearDynamicObjects(); -} - -bool Octree::RayCollides(const Ray& ray, Output& data) -{ - falsifyObjectChecks(); - data.CollideDistance = -1; - return m_Root->RayCollides(ray, data); -} - -bool Octree::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) -{ - falsifyObjectChecks(); - return m_Root->BoxCollides(boxToTest, outBoxIntersected); -} - -void Octree::falsifyObjectChecks() -{ - for (auto& obj : m_StaticObjects) { - obj.Checked = false; - } - for (auto& obj : m_DynamicObjects) { - obj.Checked = false; - } -} - -Octree::Child::Child(const AABB& octTreeBounds, - int subDivisions, +Child::Child(const AABB& octTreeBounds, + int subDivisions, std::vector& staticObjects, std::vector& dynamicObjects) : m_Box(octTreeBounds) @@ -135,7 +74,7 @@ Octree::Child::Child(const AABB& octTreeBounds, } } -Octree::Child::~Child() +Child::~Child() { for (Child*& c : m_Children) { if (c != nullptr) { @@ -145,7 +84,7 @@ Octree::Child::~Child() } } -bool Octree::Child::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) const +bool Child::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) const { if (hasChildren()) { for (int i : childIndicesContainingBox(boxToTest)) { @@ -155,7 +94,7 @@ bool Octree::Child::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) } else { for (int i : m_StaticObjIndices) { if (!m_StaticObjectsRef[i].Checked) { - const AABB& objBox = m_StaticObjectsRef[i].Box; + const AABB& objBox = *m_StaticObjectsRef[i].Box; if (Collision::AABBVsAABB(boxToTest, objBox)) { outBoxIntersected = objBox; return true; @@ -165,7 +104,7 @@ bool Octree::Child::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) } for (int i : m_DynamicObjIndices) { if (!m_DynamicObjectsRef[i].Checked) { - const AABB& objBox = m_DynamicObjectsRef[i].Box; + const AABB& objBox = *m_DynamicObjectsRef[i].Box; if (!Collision::IsSameBoxProbably(boxToTest, objBox) && Collision::AABBVsAABB(boxToTest, objBox)) { outBoxIntersected = objBox; @@ -178,7 +117,7 @@ bool Octree::Child::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) return false; } -bool Octree::Child::RayCollides(const Ray& ray, Output& data) const +bool Child::RayCollides(const Ray& ray, OctSpace::Output& data) const { //If the node AABB is missed, everything it contains is missed. if (Collision::RayAABBIntr(ray, m_Box)) { @@ -205,7 +144,7 @@ bool Octree::Child::RayCollides(const Ray& ray, Output& data) const float dist; //If we haven't tested against this object before, and the ray hits. if (!m_StaticObjectsRef[i].Checked && - Collision::RayVsAABB(ray, m_StaticObjectsRef[i].Box, dist)) { + Collision::RayVsAABB(ray, *m_StaticObjectsRef[i].Box, dist)) { minDist = std::min(dist, minDist); intersected = true; } @@ -215,7 +154,7 @@ bool Octree::Child::RayCollides(const Ray& ray, Output& data) const float dist; //If we haven't tested against this object before, and the ray hits. if (!m_DynamicObjectsRef[i].Checked && - Collision::RayVsAABB(ray, m_DynamicObjectsRef[i].Box, dist)) { + Collision::RayVsAABB(ray, *m_DynamicObjectsRef[i].Box, dist)) { minDist = std::min(dist, minDist); intersected = true; } @@ -230,7 +169,7 @@ bool Octree::Child::RayCollides(const Ray& ray, Output& data) const } -void Octree::Child::AddDynamicObject(const AABB& box) +void Child::AddDynamicObject(const AABB& box) { if (hasChildren()) { for (auto i : childIndicesContainingBox(box)) { @@ -242,7 +181,7 @@ void Octree::Child::AddDynamicObject(const AABB& box) } } -void Octree::Child::AddStaticObject(const AABB& box) +void Child::AddStaticObject(const AABB& box) { if (hasChildren()) { for (auto i : childIndicesContainingBox(box)) { @@ -254,41 +193,7 @@ void Octree::Child::AddStaticObject(const AABB& box) } } -void Octree::Child::BoxesInSameRegion(const AABB& box, std::vector& outBoxes) const -{ - if (hasChildren()) { - for (auto i : childIndicesContainingBox(box)) { - m_Children[i]->BoxesInSameRegion(box, outBoxes); - } - } else { - size_t startIndex = outBoxes.size(); - int numDuplicates = 0; - outBoxes.resize(outBoxes.size() + m_StaticObjIndices.size() + m_DynamicObjIndices.size()); - for (size_t i = 0; i < m_StaticObjIndices.size(); ++i){ - ContainedObject& obj = m_StaticObjectsRef[m_StaticObjIndices[i]]; - if (obj.Checked) { - ++numDuplicates; - } else { - obj.Checked = true; - outBoxes[startIndex + i - numDuplicates] = obj.Box; - } - } - for (size_t i = 0; i < m_DynamicObjIndices.size(); ++i) { - ContainedObject& obj = m_DynamicObjectsRef[m_DynamicObjIndices[i]]; - if (obj.Checked) { - ++numDuplicates; - } else { - obj.Checked = true; - outBoxes[startIndex + i - numDuplicates] = obj.Box; - } - } - for (size_t i = 0; i < numDuplicates; ++i) { - outBoxes.pop_back(); - } - } -} - -void Octree::Child::ClearObjects() +void Child::ClearObjects() { if (hasChildren()) { for (Child*& c : m_Children) { @@ -300,11 +205,11 @@ void Octree::Child::ClearObjects() } } -void Octree::Child::ClearDynamicObjects() +void Child::ClearDynamicObjects() { if (hasChildren()) { for (Child*& c : m_Children) { - c->ClearObjects(); + c->ClearDynamicObjects(); } } else { m_DynamicObjIndices.clear(); @@ -323,13 +228,13 @@ void Octree::Child::ClearDynamicObjects() // x : - - - - + + + + // y : - - + + - - + + // z : - + - + - + - + -int Octree::Child::childIndexContainingPoint(const glm::vec3& point) const +int Child::childIndexContainingPoint(const glm::vec3& point) const { const glm::vec3& c = m_Box.Origin(); return (1 << 2) * (point.x >= c.x) | (1 << 1) * (point.y >= c.y) | (point.z >= c.z); } -std::vector Octree::Child::childIndicesContainingBox(const AABB& box) const +std::vector Child::childIndicesContainingBox(const AABB& box) const { int minInd = childIndexContainingPoint(box.MinCorner()); int maxInd = childIndexContainingPoint(box.MaxCorner()); @@ -371,7 +276,9 @@ std::vector Octree::Child::childIndicesContainingBox(const AABB& box) const } } -inline bool Octree::Child::hasChildren() const +inline bool Child::hasChildren() const { return m_Children[0] != nullptr; +} + } \ No newline at end of file diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 54f7b69d..6da3ff5c 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -68,8 +68,8 @@ Game::Game(int argc, char* argv[]) m_Renderer->m_World = m_World; // Create Octrees - m_OctreeCollision = new Octree(AABB(glm::vec3(-100), glm::vec3(100)), 4); - m_OctreeFrustrumCulling = new Octree(AABB(glm::vec3(-100), glm::vec3(100)), 4); + m_OctreeCollision = new Octree(AABB(glm::vec3(-100), glm::vec3(100)), 4); + m_OctreeFrustrumCulling = new Octree(AABB(glm::vec3(-100), glm::vec3(100)), 4); // Create system pipeline m_SystemPipeline = new SystemPipeline(m_EventBroker); From ad9bb5fba49a0c3127e586145e681894b115bc92 Mon Sep 17 00:00:00 2001 From: stiffly Date: Tue, 19 Jan 2016 15:03:10 +0100 Subject: [PATCH 110/224] Added an extra interpolation point. --- include/Game/Systems/InterpolationSystem.h | 4 +-- src/Game/Systems/InterpolationSystem.cpp | 37 ++++++++++++---------- 2 files changed, 22 insertions(+), 19 deletions(-) diff --git a/include/Game/Systems/InterpolationSystem.h b/include/Game/Systems/InterpolationSystem.h index 15b8d167..fb7654b2 100644 --- a/include/Game/Systems/InterpolationSystem.h +++ b/include/Game/Systems/InterpolationSystem.h @@ -34,8 +34,8 @@ public: ~InterpolationSystem() { } virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& transform, double dt) override; private: - //std::unordered_map> m_InterpolationPoints; - std::unordered_map m_InterpolationPoints; + std::unordered_map m_NextTransform; + std::unordered_map m_LastReceivedTransform; //glm::vec3 vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime); template diff --git a/src/Game/Systems/InterpolationSystem.cpp b/src/Game/Systems/InterpolationSystem.cpp index 7676491f..f6d5989d 100644 --- a/src/Game/Systems/InterpolationSystem.cpp +++ b/src/Game/Systems/InterpolationSystem.cpp @@ -22,9 +22,20 @@ void InterpolationSystem::UpdateComponent(World * world, EntityWrapper& entity, ComponentWrapper & transform, double dt) { - if (m_InterpolationPoints.find(transform.EntityID) != m_InterpolationPoints.end()) { // Exists in map - Transform& sTransform = m_InterpolationPoints[transform.EntityID]; - sTransform.interpolationTime += dt; + if (m_NextTransform.find(transform.EntityID) != m_NextTransform.end()) { // Exists in map + m_NextTransform[transform.EntityID].interpolationTime += dt; + Transform sTransform = m_NextTransform[transform.EntityID]; + double time = sTransform.interpolationTime; + if (time > SNAPSHOTINTERVAL) { + if (m_LastReceivedTransform.find(transform.EntityID) != m_LastReceivedTransform.end()) { + m_NextTransform[transform.EntityID] = m_LastReceivedTransform[transform.EntityID]; + m_NextTransform[transform.EntityID].interpolationTime = time - SNAPSHOTINTERVAL; + sTransform = m_NextTransform[transform.EntityID]; + m_LastReceivedTransform.erase(transform.EntityID); + } else { + m_NextTransform.erase(transform.EntityID); + } + } if (transform.Info.Name == "Transform") { // Position glm::vec3 nextPosition = sTransform.Position; @@ -38,23 +49,10 @@ void InterpolationSystem::UpdateComponent(World * world, EntityWrapper& entity, glm::vec3 nextScale = sTransform.Scale; glm::vec3 currentScale = static_cast(transform["Scale"]); (glm::vec3&)transform["Scale"] += vectorInterpolation(currentScale, nextScale, sTransform.interpolationTime); - int testVar = 0; - if (glm::isnan(resize.r) || glm::isnan(resize.g) || glm::isnan(resize.b)) { - //(glm::vec3&)transform["Scale"] = currentScale; - return; - } - += resize; } } } -//glm::vec3 InterpolationSystem::vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime) -//{ -// glm::vec3 difference = next - prev; -// glm::vec3 position = difference / SNAPSHOTINTERVAL * static_cast(currentTime); -// return position; -//} - bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) { Transform transform; @@ -68,7 +66,12 @@ bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) offset += sizeof(glm::vec3); memcpy(&transform.Scale, e.DataArray.get() + offset, sizeof(glm::vec3)); transform.interpolationTime = 0.0f; - m_InterpolationPoints[e.Entity] = transform; + + if (m_NextTransform.find(e.Entity) != m_NextTransform.end()) { // Did exist + m_LastReceivedTransform[e.Entity] = transform; + } else { // Did not + m_NextTransform[e.Entity] = transform; + } // Check if queue already exists //if (m_InterpolationPoints.find(e.Entity) != m_InterpolationPoints.end()) { // Did exist, push to queue // m_InterpolationPoints[e.Entity].push(transform); From 017ad96bbe3d92c5b5da4a8642c27604cbcff35d Mon Sep 17 00:00:00 2001 From: William Moberg Date: Tue, 19 Jan 2016 15:20:29 +0100 Subject: [PATCH 111/224] Fixed some errors in Tests. --- src/Tests/CollisionTest.cpp | 4 ++-- src/Tests/OctTreeTest.cpp | 30 ++++++++++++++++++++---------- 2 files changed, 22 insertions(+), 12 deletions(-) diff --git a/src/Tests/CollisionTest.cpp b/src/Tests/CollisionTest.cpp index 9f400330..78d5bdb7 100644 --- a/src/Tests/CollisionTest.cpp +++ b/src/Tests/CollisionTest.cpp @@ -205,9 +205,9 @@ BOOST_AUTO_TEST_CASE(octTest) { glm::vec3 mini = glm::vec3(-1, -1, -1); glm::vec3 maxi = glm::vec3(1, 1, 1); - Octree tree(AABB(mini, maxi), 2); + Octree tree(AABB(mini, maxi), 2); tree.AddDynamicObject(AABB(mini, -0.9f*maxi)); - Octree::Output data; + OctSpace::Output data; glm::vec3 origin = 3.0f * mini; bool rayIntersected = tree.RayCollides(Ray(origin , mini - origin), data); BOOST_CHECK(rayIntersected); diff --git a/src/Tests/OctTreeTest.cpp b/src/Tests/OctTreeTest.cpp index 3a130354..2fdfe681 100644 --- a/src/Tests/OctTreeTest.cpp +++ b/src/Tests/OctTreeTest.cpp @@ -13,12 +13,12 @@ BOOST_AUTO_TEST_CASE(octSameRegionTest) { glm::vec3 mini = glm::vec3(-1, -1, -1); glm::vec3 maxi = glm::vec3(1, 1, 1); - Octree tree(AABB(mini, maxi), 2); + Octree tree(AABB(mini, maxi), 2); AABB firstQuadrant(mini, 0.8f*mini); tree.AddStaticObject(firstQuadrant); AABB testBox(0.9f*mini, 0.8f*mini); std::vector region; - tree.BoxesInSameRegion(testBox, region); + tree.ObjectsInSameRegion(testBox, region); BOOST_REQUIRE(region.size() == 1); AABB& box = region[0]; BOOST_CHECK_CLOSE_FRACTION(box.Origin().x, firstQuadrant.Origin().x, 0.00001f); @@ -40,7 +40,7 @@ const int NUM_FUNCTION_LOOPS = 25; const int TESTS = 0; //10 template -void RegionTest(Tree& tree) +void RegionTestOld(Tree& tree) { AABB aabb; aabb.CreateFromCenter(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), @@ -50,9 +50,19 @@ void RegionTest(Tree& tree) } template +void RegionTest(Tree& tree) +{ + AABB aabb; + aabb.CreateFromCenter(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), + glm::vec3(rand() % MAXSIZE, rand() % MAXSIZE, rand() % MAXSIZE)); + std::vector outVec; + tree.ObjectsInSameRegion(aabb, outVec); +} + +template void RayTest(Tree& tree) { - Tree::Output data; + Output data; glm::vec3 rayStart = glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS); glm::vec3 rayEnd = glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS); tree.RayCollides({ rayStart , glm::normalize(rayEnd - rayStart) }, data); @@ -111,13 +121,13 @@ void TestLoop(TestFunction xTest) BOOST_AUTO_TEST_CASE(octRegionPerfTestWithDuplicates) { - TestLoop(RegionTest); + TestLoop(RegionTestOld); BOOST_CHECK(true); } BOOST_AUTO_TEST_CASE(octRegionPerfTestNoDuplicates) { - TestLoop(RegionTest); + TestLoop>(RegionTest>); BOOST_CHECK(true); } @@ -129,19 +139,19 @@ BOOST_AUTO_TEST_CASE(octBoxPerfTestWithDuplicates) BOOST_AUTO_TEST_CASE(octBoxPerfTestNoDuplicates) { - TestLoop(BoxTest); + TestLoop>(BoxTest>); BOOST_CHECK(true); } BOOST_AUTO_TEST_CASE(octRayPerfTestWithDuplicates) { - TestLoop(RayTest); + TestLoop(RayTest); BOOST_CHECK(true); } BOOST_AUTO_TEST_CASE(octRayPerfTestNoDuplicates) { - TestLoop(RayTest); + TestLoop>(RayTest, OctSpace::Output>); BOOST_CHECK(true); } @@ -153,7 +163,7 @@ BOOST_AUTO_TEST_CASE(octNopPerfTestWithDuplicates) BOOST_AUTO_TEST_CASE(octNopPerfTestNoDuplicates) { - TestLoop(NopTest); + TestLoop>(NopTest>); BOOST_CHECK(true); } From f197993beb92bb2d33b0009ef9b49fefa285ea12 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Tue, 19 Jan 2016 15:31:15 +0100 Subject: [PATCH 112/224] Changed CapturePointSystem in light of new enums in the components and a teamcomponent. Half the tests are currently working --- .../Game/{ => Systems}/CapturePointSystem.h | 2 +- resources/Schema/Components/CapturePoint.xml | 7 +- resources/Schema/Components/CapturePoint.xsd | 16 +- resources/Schema/Components/Player.xml | 1 - resources/Schema/Components/Player.xsd | 1 - resources/Schema/Components/Team.xsd | 2 +- resources/Schema/Types/Entity.xsd | 4 +- src/Game/CMakeLists.txt | 1 - src/Game/Game.cpp | 2 +- src/Game/{ => Systems}/CapturePointSystem.cpp | 94 +++++--- src/Game/Systems/HealthSystem.cpp | 2 +- src/Tests/CapturePointTest.cpp | 226 ++++++++---------- src/Tests/CapturePointTest.h | 4 +- src/Tests/HealthSystemTest.cpp | 3 +- src/Tests/HealthSystemTest.h | 2 - src/Tests/OctTreeTest.cpp | 8 +- src/Tests/OldOctTree.cpp | 4 +- 17 files changed, 190 insertions(+), 189 deletions(-) rename include/Game/{ => Systems}/CapturePointSystem.h (92%) rename src/Game/{ => Systems}/CapturePointSystem.cpp (71%) diff --git a/include/Game/CapturePointSystem.h b/include/Game/Systems/CapturePointSystem.h similarity index 92% rename from include/Game/CapturePointSystem.h rename to include/Game/Systems/CapturePointSystem.h index 87410c92..2cac7d95 100644 --- a/include/Game/CapturePointSystem.h +++ b/include/Game/Systems/CapturePointSystem.h @@ -20,7 +20,7 @@ public: CapturePointSystem(EventBroker* eventBroker); //updatecomponent - virtual void UpdateComponent(World* world, ComponentWrapper& capturePoint, double dt) override; + virtual void UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& capturePoint, double dt) override; private: //methods which will take care of specific events diff --git a/resources/Schema/Components/CapturePoint.xml b/resources/Schema/Components/CapturePoint.xml index b2bd53d7..aa65852e 100644 --- a/resources/Schema/Components/CapturePoint.xml +++ b/resources/Schema/Components/CapturePoint.xml @@ -1,6 +1,5 @@ - + + 0 0 - 0 - 0 - \ No newline at end of file + \ No newline at end of file diff --git a/resources/Schema/Components/CapturePoint.xsd b/resources/Schema/Components/CapturePoint.xsd index 3171cf28..ff1a665d 100644 --- a/resources/Schema/Components/CapturePoint.xsd +++ b/resources/Schema/Components/CapturePoint.xsd @@ -5,14 +5,20 @@ - A Capture Point + A Capture Point. Add a Team Component to specify who currently owns it - - - - + + + CaptureTimer handled by Capture Point System + + + + + CapturePointNumber specify an int number for this + + diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index 5cf1d123..caefd6e6 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,6 +1,5 @@ - 0 false false diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index e6e0a4ff..1a315a35 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -14,7 +14,6 @@ - diff --git a/resources/Schema/Components/Team.xsd b/resources/Schema/Components/Team.xsd index 163d4a7f..a81a8978 100755 --- a/resources/Schema/Components/Team.xsd +++ b/resources/Schema/Components/Team.xsd @@ -14,7 +14,7 @@ - + Represents entity team affiliation diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 62d8ce98..24985d62 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -39,7 +39,7 @@ - + @@ -48,7 +48,7 @@ - + \ No newline at end of file diff --git a/src/Game/CMakeLists.txt b/src/Game/CMakeLists.txt index 23adb24c..4aaff273 100644 --- a/src/Game/CMakeLists.txt +++ b/src/Game/CMakeLists.txt @@ -27,7 +27,6 @@ set(SOURCE_FILES "Game.cpp" ${SOURCE_FILES_Systems} ${SOURCE_FILES_Events} - "CapturePointSystem.cpp" ) set(LIBRARIES diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index fc1babb3..11777be7 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -8,7 +8,7 @@ #include "Systems/SpawnerSystem.h" #include "Systems/PlayerSpawnSystem.h" #include "Core/EntityFileWriter.h" -#include "Game/CapturePointSystem.h" +#include "Game/Systems/CapturePointSystem.h" Game::Game(int argc, char* argv[]) { diff --git a/src/Game/CapturePointSystem.cpp b/src/Game/Systems/CapturePointSystem.cpp similarity index 71% rename from src/Game/CapturePointSystem.cpp rename to src/Game/Systems/CapturePointSystem.cpp index 6189f066..2d02696c 100644 --- a/src/Game/CapturePointSystem.cpp +++ b/src/Game/Systems/CapturePointSystem.cpp @@ -1,8 +1,9 @@ -#include "CapturePointSystem.h" +#include "Systems/CapturePointSystem.h" #include CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) - : PureSystem(eventBroker, "CapturePoint") + : System(eventBroker), + PureSystem("CapturePoint") { //subscribe/listenTo playerdamage,healthpickup events (using the eventBroker) EVENT_SUBSCRIBE_MEMBER(m_ETriggerTouch, &CapturePointSystem::OnTriggerTouch); @@ -11,10 +12,21 @@ CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) //here all capturepoints will update their component //NOTE: needs to run each frame, since we're possibly modifying the captureTimer for the capturePoints by dt -void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capturePoint, double dt) +void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& capturePoint, double dt) { + bool hasTeamComponent = world->HasComponent(capturePoint.EntityID, "Team"); + if (!hasTeamComponent) { + world->AttachComponent(capturePoint.EntityID, "Team"); + ComponentWrapper& teamComponent = world->GetComponent(capturePoint.EntityID, "Team"); + teamComponent["Team"] = 0; + } + ComponentWrapper& teamComponent = world->GetComponent(capturePoint.EntityID, "Team"); int firstTeamPlayersStandingInside = 0; int secondTeamPlayersStandingInside = 0; + //what if capture point has no TEAM? -> NO ENUM. + const int redTeam = (int)teamComponent["Team"].Enum("Red");//"team 1" + const int blueTeam = (int)teamComponent["Team"].Enum("Blue");//"team 2" + const int spectatorTeam = (int)teamComponent["Team"].Enum("Spectator"); //check how many players are standing inside and are healthy for (size_t i = m_ETriggerTouchVector.size(); i > 0; i--) @@ -36,28 +48,30 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture continue; } } - //check team - 0 = no team - int teamNumber = world->GetComponent(playerID, "Player")["TeamNumber"]; - if (teamNumber == 1) { + //check team - spectatorNumber = "no team" + int teamNumber = world->GetComponent(playerID, "Player")["Team"]; + if (teamNumber == redTeam) { firstTeamPlayersStandingInside++; - } - else if (teamNumber == 2) { + } else if (teamNumber == blueTeam) { secondTeamPlayersStandingInside++; } continue; } } - int ownedBy = capturePoint["OwnedBy"]; + int ownedBy = teamComponent["Team"]; + + //om ej next satt, förvänta sig att en capturepoint med en viss team färg kommer in... + //sätt isåfall next och kör på.. + //gör inget tills man fått den infon /*check what capturePoint can be taken over next: no capturepoint taken yet for at least one of the teams <-> at the start of the match the system is unaware of what capturePoint is the first one for each team*/ - if (m_Team1NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 1) { + if (m_Team1NextPossibleCapturePoint == m_NotACapturePoint && (int)teamComponent["Team"] == redTeam) { m_Team1NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; m_Team1HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team1NextPossibleCapturePoint - } - else if (m_Team2NextPossibleCapturePoint == m_NotACapturePoint && (int)capturePoint["IsHomeCapturePointForTeamNumber"] == 2) { + } else if (m_Team2NextPossibleCapturePoint == m_NotACapturePoint && (int)teamComponent["Team"] == blueTeam) { m_Team2NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; m_Team2HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team2NextPossibleCapturePoint } @@ -72,34 +86,31 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture && m_Team1NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { timerDeltaChange = firstTeamPlayersStandingInside*dt; - currentTeam = 1; - } - else if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0 + currentTeam = blueTeam; + } else if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0 && m_Team2NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { timerDeltaChange = -secondTeamPlayersStandingInside*dt; - currentTeam = 2; + currentTeam = redTeam; } - //A.nobodys standing inside if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside == 0) { + //A.nobodys standing inside //do nothing (?) - } - - //B. at most one of the teams have players inside (this means datavariable currentTeam is not 0) - else if (currentTeam != 0) { + } else if (currentTeam == blueTeam || currentTeam == redTeam) { + //B. at most one of the teams have players inside (this means datavariable currentTeam is not 0) //if capturePoint is not owned by the take-over team, just modify the CaptureTimer accordingly if (ownedBy != currentTeam) { capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; } //if capturePoint is owned by the team, and the other team has been trying to take it, then increase/decrease the timer towards 0.0 - if ((ownedBy == currentTeam && currentTeam == 1 && (double)capturePoint["CaptureTimer"] < 0.0) || - (ownedBy == currentTeam && currentTeam == 2 && (double)capturePoint["CaptureTimer"] > 0.0)) { + if ((ownedBy == currentTeam && currentTeam == redTeam && (double)capturePoint["CaptureTimer"] < 0.0) || + (ownedBy == currentTeam && currentTeam == blueTeam && (double)capturePoint["CaptureTimer"] > 0.0)) { capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; } //check if captureTimer > m_CaptureTimeToTakeOver and if so change owner and publish the eCaptured event if (abs((double)capturePoint["CaptureTimer"]) > abs(m_CaptureTimeToTakeOver)) { - capturePoint["OwnedBy"] = currentTeam; + teamComponent["Team"] = currentTeam; capturePoint["CaptureTimer"] = 0.0; //publish Captured event Events::Captured e; @@ -112,10 +123,9 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture bool team1HasTheZeroCapturePoint = m_Team1HomeCapturePoint < m_Team2HomeCapturePoint; if (team1HasTheZeroCapturePoint) { - if (currentTeam == 1) { + if (currentTeam == redTeam) { m_Team1NextPossibleCapturePoint++; - } - else { + } else { m_Team2NextPossibleCapturePoint--; } //adjust flag for other team if their previous point has just been taken @@ -126,12 +136,10 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture if (m_Team1NextPossibleCapturePoint == m_Team2NextPossibleCapturePoint + 2) { m_Team1NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint - 1; } - } - else { - if (currentTeam == 1) { + } else { + if (currentTeam == redTeam) { m_Team1NextPossibleCapturePoint--; - } - else { + } else { m_Team2NextPossibleCapturePoint++; } //adjust flag for other team if their previous point has just been taken @@ -144,19 +152,27 @@ void CapturePointSystem::UpdateComponent(World* world, ComponentWrapper& capture } } } - } - - //C.both teams have players inside - else if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside > 0) { + } else if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside > 0) { + //C.both teams have players inside //do nothing (?) } //check for possible winCondition = check if the homebase is owned by the other team - if (!m_WinnerWasFound && (int)capturePoint["OwnedBy"] != 0 && (int)capturePoint["IsHomeCapturePointForTeamNumber"] != 0 && - (int)capturePoint["IsHomeCapturePointForTeamNumber"] != (int)capturePoint["OwnedBy"]) { + bool checkForWinner = false; + if ((int)capturePoint["CapturePointNumber"] == m_Team1HomeCapturePoint && (int)teamComponent["Team"] != redTeam) + { + checkForWinner = true; + } + if ((int)capturePoint["CapturePointNumber"] == m_Team2HomeCapturePoint && (int)teamComponent["Team"] != blueTeam) + { + checkForWinner = true; + } + + if (checkForWinner && !m_WinnerWasFound) + { //publish Win event Events::Win e; - e.TeamThatWon = capturePoint["OwnedBy"]; + e.TeamThatWon = teamComponent["Team"]; m_EventBroker->Publish(e); m_WinnerWasFound = true; } diff --git a/src/Game/Systems/HealthSystem.cpp b/src/Game/Systems/HealthSystem.cpp index 50c65b1b..203e5019 100644 --- a/src/Game/Systems/HealthSystem.cpp +++ b/src/Game/Systems/HealthSystem.cpp @@ -27,7 +27,7 @@ void HealthSystem::UpdateComponent(World* world, EntityWrapper& entity, Componen m_DeltaHealthVector.erase(m_DeltaHealthVector.begin() + i - 1); //check if health is <= 0 if ((double)component["Health"] <= 0.0f) { - health["Health"] = 0.0; + component["Health"] = 0.0; //publish death event Events::PlayerDeath e; e.PlayerID = player.EntityID; diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index 71408636..bdba08e4 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -3,12 +3,12 @@ using boost::unit_test_framework::test_suite; using boost::unit_test_framework::test_case; #include "CapturePointTest.h" -#include "Game/HealthSystem.h" +#include "Game/Systems/HealthSystem.h" #include "Collision/TriggerSystem.h" #include "Collision/CollisionSystem.h" #include "Core/EntityFileWriter.h" -#include "Game/CapturePointSystem.h" +#include "Game/Systems/CapturePointSystem.h" BOOST_AUTO_TEST_SUITE(CapturePointTestSuite) @@ -94,7 +94,6 @@ CapturePointTest::CapturePointTest(int runTestNumber) ResourceManager::RegisterType("EntityFile"); m_Config = ResourceManager::Load("Config.ini"); - std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); // Create the core event broker @@ -105,19 +104,15 @@ CapturePointTest::CapturePointTest(int runTestNumber) // Create system pipeline m_SystemPipeline = new SystemPipeline(m_EventBroker); - m_SystemPipeline->AddSystem(0); m_SystemPipeline->AddSystem(0); - m_SystemPipeline->AddSystem(1); - m_SystemPipeline->AddSystem(1); m_SystemPipeline->AddSystem(1); - if (!mapToLoad.empty()) { - auto file = ResourceManager::Load(mapToLoad); - EntityFilePreprocessor fpp(file); - fpp.RegisterComponents(m_World); - EntityFileParser fp(file); - fp.MergeEntities(m_World); - } + //must register components (Components.xsd), else you cant create entities. Easiest done by loading a test xsd file + auto file = ResourceManager::Load("Schema/Entities/TeamTest.xml"); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(m_World); + EntityFileParser fp(file); + fp.MergeEntities(m_World); /* ---TESTSETUP--- @@ -128,37 +123,43 @@ CapturePointTest::CapturePointTest(int runTestNumber) capturepoint3 = home for team number 1 */ EntityID playerID = m_World->CreateEntity(); - m_PlayerID = playerID; - ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); - ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); - player["TeamNumber"] = 1; + m_RedTeamPlayer = playerID; + ComponentWrapper& player = m_World->AttachComponent(m_RedTeamPlayer, "Player"); + ComponentWrapper& health = m_World->AttachComponent(m_RedTeamPlayer, "Health"); + ComponentWrapper& playerTeam = m_World->AttachComponent(m_RedTeamPlayer, "Team"); + playerTeam["Team"] = playerTeam["Team"].Enum("Red"); + m_RedTeam = playerTeam["Team"].Enum("Red"); + m_BlueTeam = playerTeam["Team"].Enum("Blue"); EntityID playerID2 = m_World->CreateEntity(); - ComponentWrapper& player2 = m_World->AttachComponent(playerID2, "Player"); - m_PlayerID2 = playerID2; - ComponentWrapper health2 = m_World->AttachComponent(playerID2, "Health"); - player2["TeamNumber"] = 2; + m_BlueTeamPlayer = playerID2; + ComponentWrapper& player2 = m_World->AttachComponent(m_BlueTeamPlayer, "Player"); + ComponentWrapper& health2 = m_World->AttachComponent(m_BlueTeamPlayer, "Health"); + ComponentWrapper& playerTeam2 = m_World->AttachComponent(m_BlueTeamPlayer, "Team"); + playerTeam2["Team"] = m_BlueTeam; EntityID capturePointID = m_World->CreateEntity(); - ComponentWrapper& capturePoint = m_World->AttachComponent(capturePointID, "CapturePoint"); - //this capturePoint is homeBase for team 2 - capturePoint["IsHomeCapturePointForTeamNumber"] = 2; - capturePoint["CapturePointNumber"] = 0; m_CapturePointID = capturePointID; + ComponentWrapper& capturePoint = m_World->AttachComponent(capturePointID, "CapturePoint"); + ComponentWrapper& capturePointHomeTeam = m_World->AttachComponent(capturePointID, "Team"); + //this capturePoint is homeBase for team 2 + capturePointHomeTeam["Team"] = m_BlueTeam; + capturePoint["CapturePointNumber"] = 0; EntityID capturePointID2 = m_World->CreateEntity(); - ComponentWrapper& capturePoint2 = m_World->AttachComponent(capturePointID2, "CapturePoint"); - //this capturePoint is homeBase for team 1 - capturePoint2["IsHomeCapturePointForTeamNumber"] = 0; - capturePoint2["CapturePointNumber"] = 1; m_CapturePointID2 = capturePointID2; + ComponentWrapper& capturePoint2 = m_World->AttachComponent(capturePointID2, "CapturePoint"); + //ComponentWrapper& capturePointHomeTeam2 = m_World->AttachComponent(capturePointID2, "Team"); + //capturePointHomeTeam2["Team"] = m_BlueTeam; + capturePoint2["CapturePointNumber"] = 1; EntityID capturePointID3 = m_World->CreateEntity(); - ComponentWrapper& capturePoint3 = m_World->AttachComponent(capturePointID3, "CapturePoint"); - //this capturePoint is homeBase for team 1 - capturePoint3["IsHomeCapturePointForTeamNumber"] = 1; - capturePoint3["CapturePointNumber"] = 2; m_CapturePointID3 = capturePointID3; + ComponentWrapper& capturePoint3 = m_World->AttachComponent(capturePointID3, "CapturePoint"); + ComponentWrapper& capturePointHomeTeam3 = m_World->AttachComponent(capturePointID3, "Team"); + //this capturePoint is homeBase for team 1 + capturePointHomeTeam3["Team"] = m_RedTeam; + capturePoint3["CapturePointNumber"] = 2; m_RunTestNumber = runTestNumber; @@ -189,8 +190,8 @@ CapturePointTest::CapturePointTest(int runTestNumber) break; case 8: //switch sides - capturePoint["IsHomeCapturePointForTeamNumber"] = 1; - capturePoint3["IsHomeCapturePointForTeamNumber"] = 2; + capturePointHomeTeam["Team"] = m_RedTeam; + capturePointHomeTeam3["Team"] = m_BlueTeam; TestSetup8(); break; default: @@ -214,10 +215,10 @@ void CapturePointTest::TestSetup1_OnePlayerOnCapturePoint() Events::TriggerLeave leaveEvent; //player touches,leaves,touches m_CapturePointID. and enters m_CapturePointID3 - DoTouchEvent(m_PlayerID, m_CapturePointID); - DoLeaveEvent(m_PlayerID, m_CapturePointID); - DoTouchEvent(m_PlayerID, m_CapturePointID); - DoTouchEvent(m_PlayerID, m_CapturePointID3); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); } void CapturePointTest::TestSetup2_TwoPlayersOnCapturePoint() { @@ -225,80 +226,65 @@ void CapturePointTest::TestSetup2_TwoPlayersOnCapturePoint() Events::TriggerLeave leaveEvent; //player touches,leaves m_CapturePointID. and enters m_CapturePointID3 - DoTouchEvent(m_PlayerID, m_CapturePointID); - DoLeaveEvent(m_PlayerID, m_CapturePointID); - DoTouchEvent(m_PlayerID, m_CapturePointID3); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); //player2 touches m_CapturePointID,m_CapturePointID2 - DoTouchEvent(m_PlayerID2, m_CapturePointID); - DoTouchEvent(m_PlayerID2, m_CapturePointID2); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID2); } void CapturePointTest::TestSetup3_NoPlayersOnCapturePoint() { Events::TriggerTouch touchEvent; Events::TriggerLeave leaveEvent; - - //player1 touches and leaves m_CapturePointID - DoTouchEvent(m_PlayerID, m_CapturePointID); - DoLeaveEvent(m_PlayerID, m_CapturePointID); - - //player2 touches and leaves m_CapturePointID2 - DoTouchEvent(m_PlayerID2, m_CapturePointID2); - DoLeaveEvent(m_PlayerID2, m_CapturePointID2); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); + DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID3); } void CapturePointTest::TestSetup4_TwoCapturePointsBeingCaptured() { Events::TriggerTouch touchEvent; //player1 touches m_CapturePointID3 - DoTouchEvent(m_PlayerID, m_CapturePointID3); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); //player2 touches m_CapturePointID - DoTouchEvent(m_PlayerID2, m_CapturePointID); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); } void CapturePointTest::TestSetup5_SameCapturePointContestedAndTakenOver() { - //NOTE: setup events need to trigger first then the real event will be allowed by the system later - - //"SETUP" homebase->same capturep - //player1 touches m_CapturePointID3 - DoTouchEvent(m_PlayerID, m_CapturePointID3); - - //player2 touches m_CapturePointID - DoTouchEvent(m_PlayerID2, m_CapturePointID); - //contested same, player1 touches the contested //player1 touches m_CapturePointID2 - DoTouchEvent(m_PlayerID, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); } void CapturePointTest::TestSetup6_Team1CapturedTheLastPointAndWon() { //player1 touches m_CapturePointID3 - DoTouchEvent(m_PlayerID, m_CapturePointID3); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); //TODO: this should be in UPDATE instead //player1 touches m_CapturePointID2 - DoTouchEvent(m_PlayerID, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); //player1 touches m_CapturePointID - DoTouchEvent(m_PlayerID, m_CapturePointID); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); //player2 does nothing } void CapturePointTest::TestSetup7() { //2 owns 1 - DoTouchEvent(m_PlayerID2, m_CapturePointID); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); //1 owns 3 - DoTouchEvent(m_PlayerID, m_CapturePointID3); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); } void CapturePointTest::TestSetup8() { //2 owns 3 - DoTouchEvent(m_PlayerID2, m_CapturePointID3); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID3); //1 owns 1 - DoTouchEvent(m_PlayerID, m_CapturePointID); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); } void CapturePointTest::DoTouchEvent(EntityID whoDidSomething, EntityID onWhatObject) { Events::TriggerTouch touchEvent; @@ -316,15 +302,15 @@ void CapturePointTest::TestSuccess1() { //TestSetup1_OnePlayerOnCapturePoint //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; - if (ownedByID3 == 1) + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + if (ownedByID3 == m_RedTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess2() { //TestSetup2_TwoPlayersOnCapturePoint - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; - if (ownedByID3 == 1 && ownedByID1 == 2) + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + if (ownedByID3 == m_RedTeam && ownedByID1 == m_BlueTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess3() { @@ -333,53 +319,53 @@ void CapturePointTest::TestSuccess3() { //if any capturePoint changed then, its a failure else a success if (NumLoops == 95) { TestSucceeded = true; - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; - if (ownedByID1 != 0 || ownedByID2 != 0 || ownedByID3 != 0) + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + if (ownedByID1 != m_BlueTeam || ownedByID2 == m_RedTeam || ownedByID2 == m_BlueTeam || ownedByID3 !=m_RedTeam) TestSucceeded = false; } } void CapturePointTest::TestSuccess4() { //TestSetup4_TwoCapturePointsBeingCaptured - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; - if (ownedByID1 == 2 && ownedByID3 == 1) + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + if (ownedByID1 == m_BlueTeam && ownedByID3 == m_RedTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess5() { //TestSetup5_SameCapturePointContestedAndTakenOver - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; - if (ownedByID1 == 2 && ownedByID2 == 1 && ownedByID3 == 1) + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + if (ownedByID1 == m_BlueTeam && ownedByID2 == m_RedTeam && ownedByID3 == m_RedTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess6() { //NOTE: the actual win-event will have to be manually checked if it triggered or not //TestSetup6_Team1CapturedTheLastPointAndWon - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; - if (ownedByID1 == 1 && ownedByID2 == 1 && ownedByID3 == 1) + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + if (ownedByID1 == m_RedTeam && ownedByID2 == m_RedTeam && ownedByID3 == m_RedTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess7() { - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; - if (NumLoops < 20 && ownedByID1 == 2 & ownedByID3 == 1) { + if (NumLoops < 20 && ownedByID1 == m_BlueTeam & ownedByID3 == m_RedTeam) { phase1Success = true; } - if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == 1) { + if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == m_RedTeam) { phase2Success = true; } - if (NumLoops < 60 && NumLoops > 40 && ownedByID1 == 1) { + if (NumLoops < 60 && NumLoops > 40 && ownedByID1 == m_RedTeam) { phase3Success = true; } - if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != 2) { + if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != m_BlueTeam) { phase4Success = true; } @@ -389,20 +375,20 @@ void CapturePointTest::TestSuccess7() { } } void CapturePointTest::TestSuccess8() { - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["OwnedBy"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["OwnedBy"]; - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["OwnedBy"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["Team"]; - if (NumLoops < 20 && ownedByID3 == 2 & ownedByID1 == 1) { + if (NumLoops < 20 && ownedByID3 == m_BlueTeam & ownedByID1 == m_RedTeam) { phase1Success = true; } - if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == 1) { + if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == m_RedTeam) { phase2Success = true; } - if (NumLoops < 60 && NumLoops > 40 && ownedByID3 == 1) { + if (NumLoops < 60 && NumLoops > 40 && ownedByID3 == m_RedTeam) { phase3Success = true; } - if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != 2) { + if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != m_BlueTeam) { phase4Success = true; } @@ -416,21 +402,21 @@ void CapturePointTest::UpdateTest7() { //loop 20 = team1 takes 2, team 1 leaves 1 -> team1 next = 1, team2 next = still 2 if (NumLoops == 20) { //leave previous - DoLeaveEvent(m_PlayerID2, m_CapturePointID); - DoLeaveEvent(m_PlayerID, m_CapturePointID3); + DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID3); - DoTouchEvent(m_PlayerID, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); } //loop 40 = team1 takes 1, team2:s next cap point should now be 1 (instead of 2) if (NumLoops == 40) { //leave previous, take next - DoLeaveEvent(m_PlayerID, m_CapturePointID2); - DoTouchEvent(m_PlayerID, m_CapturePointID); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); } //loop 60 = team2 tries to take 2, this shouldnt work now if (NumLoops == 60) { - DoLeaveEvent(m_PlayerID, m_CapturePointID); - DoTouchEvent(m_PlayerID2, m_CapturePointID2); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID2); } } void CapturePointTest::UpdateTest8() { @@ -440,21 +426,21 @@ void CapturePointTest::UpdateTest8() { //loop 20 = team1 takes 2, team 1 leaves 1 -> team1 next = 1, team2 next = still 2 if (NumLoops == 20) { //leave previous - DoLeaveEvent(m_PlayerID2, m_CapturePointID3); - DoLeaveEvent(m_PlayerID, m_CapturePointID); + DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID3); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); - DoTouchEvent(m_PlayerID, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); } //loop 40 = team1 takes 3, team2:s next cap point should now be 1 (instead of 2) if (NumLoops == 40) { //leave previous, take next - DoLeaveEvent(m_PlayerID, m_CapturePointID2); - DoTouchEvent(m_PlayerID, m_CapturePointID3); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); } //loop 60 = team2 tries to take 2, this shouldnt work now if (NumLoops == 60) { - DoLeaveEvent(m_PlayerID, m_CapturePointID3); - DoTouchEvent(m_PlayerID2, m_CapturePointID2); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID3); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID2); } } void CapturePointTest::Tick() diff --git a/src/Tests/CapturePointTest.h b/src/Tests/CapturePointTest.h index 5646f8a6..69f63fcd 100644 --- a/src/Tests/CapturePointTest.h +++ b/src/Tests/CapturePointTest.h @@ -11,7 +11,6 @@ #include "Core/EKeyDown.h" #include "Core/EntityFile.h" #include "Core/SystemPipeline.h" -#include "PlayerSystem.h" #include "Core/EntityFilePreprocessor.h" #include "Core/EntityFileParser.h" @@ -58,9 +57,10 @@ private: EventBroker* m_EventBroker; World* m_World; SystemPipeline* m_SystemPipeline; - EntityID m_PlayerID, m_PlayerID2, m_CapturePointID, m_CapturePointID2, m_CapturePointID3; + EntityID m_RedTeamPlayer, m_BlueTeamPlayer, m_CapturePointID, m_CapturePointID2, m_CapturePointID3; int m_RunTestNumber; bool phase1Success = false, phase2Success = false, phase3Success = false, phase4Success = false; + int m_RedTeam, m_BlueTeam; }; #endif diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index feab858a..2c57b713 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -3,7 +3,7 @@ using boost::unit_test_framework::test_suite; using boost::unit_test_framework::test_case; #include "HealthSystemTest.h" -#include "Game/HealthSystem.h" +#include "Game/Systems/HealthSystem.h" BOOST_AUTO_TEST_SUITE(HealthSystemSuite) @@ -52,7 +52,6 @@ GameHealthSystemTest::GameHealthSystemTest() // Create system pipeline m_SystemPipeline = new SystemPipeline(m_EventBroker); - m_SystemPipeline->AddSystem(0); m_SystemPipeline->AddSystem(0); //The Test diff --git a/src/Tests/HealthSystemTest.h b/src/Tests/HealthSystemTest.h index bd3f3de7..62c5f55b 100644 --- a/src/Tests/HealthSystemTest.h +++ b/src/Tests/HealthSystemTest.h @@ -14,8 +14,6 @@ #include "Core/EKeyDown.h" #include "Core/EntityFile.h" #include "Core/SystemPipeline.h" -#include "RaptorCopterSystem.h" -#include "PlayerSystem.h" #include "Editor/EditorSystem.h" class GameHealthSystemTest diff --git a/src/Tests/OctTreeTest.cpp b/src/Tests/OctTreeTest.cpp index 3a130354..ccce93eb 100644 --- a/src/Tests/OctTreeTest.cpp +++ b/src/Tests/OctTreeTest.cpp @@ -43,7 +43,7 @@ template void RegionTest(Tree& tree) { AABB aabb; - aabb.CreateFromCenter(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), + aabb.FromOriginSize(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), glm::vec3(rand() % MAXSIZE, rand() % MAXSIZE, rand() % MAXSIZE)); std::vector outVec; tree.BoxesInSameRegion(aabb, outVec); @@ -63,7 +63,7 @@ void BoxTest(Tree& tree) { AABB outBox; AABB aabb; - aabb.CreateFromCenter(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), + aabb.FromOriginSize(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), glm::vec3(rand() % MAXSIZE, rand() % MAXSIZE, rand() % MAXSIZE)); tree.BoxCollides(aabb, outBox); } @@ -88,14 +88,14 @@ void TestLoop(TestFunction xTest) for (int i = 0; i < NUM_STATICS; ++i) { center = glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS); size = glm::vec3(rand() % MAXSIZE, rand() % MAXSIZE, rand() % MAXSIZE); - aabb.CreateFromCenter(center, size); + aabb.FromOriginSize(center, size); tree.AddStaticObject(aabb); } for (int fr = 0; fr < TEST_FRAMES; ++fr) { for (int i = 0; i < NUM_DYNAMICS; ++i) { center = glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS); size = glm::vec3(rand() % MAXSIZE, rand() % MAXSIZE, rand() % MAXSIZE); - aabb.CreateFromCenter(center, size); + aabb.FromOriginSize(center, size); tree.AddDynamicObject(aabb); } diff --git a/src/Tests/OldOctTree.cpp b/src/Tests/OldOctTree.cpp index 0fb92e18..16ecec65 100644 --- a/src/Tests/OldOctTree.cpp +++ b/src/Tests/OldOctTree.cpp @@ -100,7 +100,7 @@ void OctTree::Update(float dt, World* world, Camera* cam) { AABB aabb; for (ComponentWrapper& c : *world->GetComponents("Collision")) { - aabb.CreateFromCenter(c["BoxCenter"], c["BoxSize"]); + aabb.FromOriginSize(c["BoxCenter"], c["BoxSize"]); AddStaticObject(aabb); } const glm::vec4 redCol = glm::vec4(1, 0.2f, 0, 1); @@ -118,7 +118,7 @@ void OctTree::Update(float dt, World* world, Camera* cam) AABB box; auto boxPos = cam->Position() + 1.2f*cam->Forward(); - box.CreateFromCenter(boxPos, boxSize); + box.FromOriginSize(boxPos, boxSize); ComponentWrapper transform = world->GetComponent(m_BoxID, "Transform"); transform["Position"] = boxPos; ComponentWrapper model = world->GetComponent(m_BoxID, "Model"); From 893ef38237b0fde65d423ab15e4a3c68f62e201c Mon Sep 17 00:00:00 2001 From: Tleety Date: Tue, 19 Jan 2016 15:41:17 +0100 Subject: [PATCH 113/224] Removed world from renderer and moved depth-calculation code to modeljob --- include/Engine/Rendering/ModelJob.h | 3 +++ include/Engine/Rendering/Renderer.h | 6 ++---- src/Engine/Rendering/Renderer.cpp | 27 ++++++++------------------- src/Game/Game.cpp | 3 +-- 4 files changed, 14 insertions(+), 25 deletions(-) diff --git a/include/Engine/Rendering/ModelJob.h b/include/Engine/Rendering/ModelJob.h index a35a1721..62235b33 100644 --- a/include/Engine/Rendering/ModelJob.h +++ b/include/Engine/Rendering/ModelJob.h @@ -28,6 +28,9 @@ struct ModelJob : RenderJob Matrix = matrix; Color = modelComponent["Color"]; Entity = modelComponent.EntityID; + glm::vec3 abspos = Transform::AbsolutePosition(world, modelComponent.EntityID); + glm::vec3 worldpos = glm::vec3(camera->ViewMatrix() * glm::vec4(abspos, 1)); + Depth = worldpos.z; World = world; }; diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 0bfe76f7..0006cca1 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -22,9 +22,8 @@ class Renderer : public IRenderer { public: - Renderer(EventBroker* eventBroker, World* world) + Renderer(EventBroker* eventBroker) : m_EventBroker(eventBroker) - , m_World(world) { } virtual void Initialize() override; @@ -36,7 +35,6 @@ public: private: //----------------------Variables----------------------// EventBroker* m_EventBroker; - World* m_World; Texture* m_ErrorTexture; Texture* m_WhiteTexture; @@ -62,7 +60,7 @@ private: void DrawScreenQuad(GLuint textureToDraw); static bool DepthSort(const std::shared_ptr &i, const std::shared_ptr &j) { return (i->Depth < j->Depth); } - void FillDepth(RenderScene& scene); + void SortRenderJobsByDepth(RenderScene &scene); void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type); //--------------------ShaderPrograms-------------------// ShaderProgram* m_BasicForwardProgram; diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 9ae317ca..a642e667 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -98,9 +98,8 @@ void Renderer::Draw(RenderFrame& frame) m_PickingPass->ClearPicking(); for (auto scene : frame.RenderScenes){ - m_Camera = scene->Camera; // remove renderer camera when Editor uses the render scene cameras. - FillDepth(*scene); + SortRenderJobsByDepth(*scene); m_PickingPass->Draw(*scene); m_LightCullingPass->GenerateNewFrustum(*scene); m_LightCullingPass->FillLightList(*scene); @@ -147,6 +146,13 @@ void Renderer::InitializeTextures() m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); } + +void Renderer::SortRenderJobsByDepth(RenderScene *scene) +{ + //Sort all forward jobs so transparency is good. + scene->ForwardJobs.sort(Renderer::DepthSort); +} + void Renderer::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) { glGenTextures(1, texture); @@ -165,21 +171,4 @@ void Renderer::InitializeRenderPasses() m_PickingPass = new PickingPass(this, m_EventBroker); m_LightCullingPass = new LightCullingPass(this); m_DrawFinalPass = new DrawFinalPass(this, m_LightCullingPass); -} - -//Temp func -void Renderer::FillDepth(RenderScene& scene) -{ - for (auto job : scene.ForwardJobs) { - auto modelJob = std::dynamic_pointer_cast(job); - if(! modelJob) { - return; - } - - - glm::vec3 abspos = Transform::AbsolutePosition(modelJob->World, modelJob->Entity); - glm::vec3 worldpos = glm::vec3(scene.Camera->ViewMatrix() * glm::vec4(abspos, 1)); - modelJob->Depth = worldpos.z; - } - scene.ForwardJobs.sort(Renderer::DepthSort); } \ No newline at end of file diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 54f7b69d..eb0e6b3f 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -64,8 +64,7 @@ Game::Game(int argc, char* argv[]) EntityFileParser fp(file); fp.MergeEntities(m_World); } - //SO MUCH TEMP PLEASE REMOVE ME OMFG VIKTOR HELP - m_Renderer->m_World = m_World; + // Create Octrees m_OctreeCollision = new Octree(AABB(glm::vec3(-100), glm::vec3(100)), 4); From a8ffb240404615b51127a0f647cf8130665bf41f Mon Sep 17 00:00:00 2001 From: Tleety Date: Tue, 19 Jan 2016 16:08:09 +0100 Subject: [PATCH 114/224] latest commit fix --- include/Engine/Rendering/ModelJob.h | 1 + resources/Schema/Entities/EditorTestWorld.xml | 10 +++++----- src/Engine/Rendering/Renderer.cpp | 4 ++-- src/Game/Game.cpp | 2 +- 4 files changed, 9 insertions(+), 8 deletions(-) diff --git a/include/Engine/Rendering/ModelJob.h b/include/Engine/Rendering/ModelJob.h index 62235b33..a88530e7 100644 --- a/include/Engine/Rendering/ModelJob.h +++ b/include/Engine/Rendering/ModelJob.h @@ -12,6 +12,7 @@ #include "../Core/ResourceManager.h" #include "Camera.h" #include "../Core/World.h" +#include "../Core/Transform.h" struct ModelJob : RenderJob { diff --git a/resources/Schema/Entities/EditorTestWorld.xml b/resources/Schema/Entities/EditorTestWorld.xml index a482cf1b..733e643b 100755 --- a/resources/Schema/Entities/EditorTestWorld.xml +++ b/resources/Schema/Entities/EditorTestWorld.xml @@ -48,8 +48,8 @@ - - + + @@ -61,8 +61,8 @@ Models/DirectionalLightWidget.obj - - + + @@ -83,7 +83,7 @@ Models/SecondaryWeapon4.fbx - + diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index a642e667..8c30adfd 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -147,10 +147,10 @@ void Renderer::InitializeTextures() } -void Renderer::SortRenderJobsByDepth(RenderScene *scene) +void Renderer::SortRenderJobsByDepth(RenderScene &scene) { //Sort all forward jobs so transparency is good. - scene->ForwardJobs.sort(Renderer::DepthSort); + scene.ForwardJobs.sort(Renderer::DepthSort); } void Renderer::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index eb0e6b3f..1985d9dc 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -29,7 +29,7 @@ Game::Game(int argc, char* argv[]) // Create the renderer - m_Renderer = new Renderer(m_EventBroker, m_World); + m_Renderer = new Renderer(m_EventBroker); m_Renderer->SetFullscreen(m_Config->Get("Video.Fullscreen", false)); m_Renderer->SetVSYNC(m_Config->Get("Video.VSYNC", false)); m_Renderer->SetResolution(Rectangle::Rectangle( From d2263b0c90ada29134abea3c5f204e1a68f6b75b Mon Sep 17 00:00:00 2001 From: Tleety Date: Tue, 19 Jan 2016 16:09:30 +0100 Subject: [PATCH 115/224] Assets added --- assets | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/assets b/assets index 2fca9181..187bc629 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 2fca918162535c859c6adbe433e69fad8ea931b6 +Subproject commit 187bc62969fd753216441a12b179f520ce5c6b05 From a124ab24004cc3f9a2891c561f9617f04e9723f8 Mon Sep 17 00:00:00 2001 From: Tleety Date: Tue, 19 Jan 2016 16:11:56 +0100 Subject: [PATCH 116/224] Some asset shit. Fixed testworld to use the right model. --- assets | 2 +- resources/Schema/Entities/EditorTestWorld.xml | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/assets b/assets index 187bc629..6ffb46e1 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 187bc62969fd753216441a12b179f520ce5c6b05 +Subproject commit 6ffb46e155c8f013241cd1507098c94900ec2448 diff --git a/resources/Schema/Entities/EditorTestWorld.xml b/resources/Schema/Entities/EditorTestWorld.xml index 733e643b..2e95d626 100755 --- a/resources/Schema/Entities/EditorTestWorld.xml +++ b/resources/Schema/Entities/EditorTestWorld.xml @@ -49,7 +49,7 @@ - + @@ -80,7 +80,7 @@ - Models/SecondaryWeapon4.fbx + Models/SecondaryWeapon.fbx From 5d6d0f82b9e733c86bdb0bca7721734fcf6471fa Mon Sep 17 00:00:00 2001 From: Tleety Date: Tue, 19 Jan 2016 16:48:59 +0100 Subject: [PATCH 117/224] Removed some debug code --- resources/Shaders/ForwardPlus.frag.glsl | 18 +++++++++++------- src/Engine/Rendering/LightCullingPass.cpp | 2 -- 2 files changed, 11 insertions(+), 9 deletions(-) diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index e67a4d5d..78a2125e 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -114,12 +114,13 @@ void main() int start = int(LightGrids.Data[currentTile].Start); int amount = int(LightGrids.Data[currentTile].Amount); - //for(int i = 0; i < 3; i++) + for(int i = start; i < start + amount; i++) { + int l = int(LightIndex[i]); LightSource light = LightSources.List[l]; - LightResult result; + LightResult result; if(light.Type == 1) { // point result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); } else if (light.Type == 2) { //Directional @@ -136,12 +137,15 @@ void main() //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); //fragmentColor = texel * Input.DiffuseColor * Color; //fragmentColor += vec4(currentTile/3600.f, 0, 0, 1); - if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { - //fragmentColor += vec4(0.5, 0, 0, 0); - } else { - //fragmentColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/3.0, 0, 0, 1); - } + //Tiled Debug Code + /* + if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { + fragmentColor += vec4(0.5, 0, 0, 0); + } else { + fragmentColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/LightSources.List.length(), 0, 0, 1); + } + */ } diff --git a/src/Engine/Rendering/LightCullingPass.cpp b/src/Engine/Rendering/LightCullingPass.cpp index 2a2e2383..a68fe4d1 100644 --- a/src/Engine/Rendering/LightCullingPass.cpp +++ b/src/Engine/Rendering/LightCullingPass.cpp @@ -95,7 +95,6 @@ void LightCullingPass::FillLightList(RenderScene& scene) //p.Padding = 123.f; p.Type = LightSource::Point; m_LightSources.push_back(p); - } } for(auto &job : scene.DirectionalLightJobs) { @@ -107,7 +106,6 @@ void LightCullingPass::FillLightList(RenderScene& scene) p.Intensity = directionalLightJob->Intensity; p.Type = LightSource::Directional; m_LightSources.push_back(p); - } } } From d1b6fb125916baf9bc20ae1656a7fdc269069159 Mon Sep 17 00:00:00 2001 From: William Moberg Date: Tue, 19 Jan 2016 16:59:02 +0100 Subject: [PATCH 118/224] Tiny logic alteration so we don't get false warnings in debug. --- src/Engine/Collision/TriggerSystem.cpp | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/Engine/Collision/TriggerSystem.cpp b/src/Engine/Collision/TriggerSystem.cpp index 0ff4345e..b398b091 100644 --- a/src/Engine/Collision/TriggerSystem.cpp +++ b/src/Engine/Collision/TriggerSystem.cpp @@ -34,9 +34,12 @@ void TriggerSystem::UpdateComponent(World* world, EntityWrapper& entity, Compone throwLeaveIfWasInTrigger(m_EntitiesCompletelyInTrigger[tId], pId, tId); } else { //Entity is at least touching the trigger. - AABB completelyInsideBox = AABB::FromOriginSize((*triggerBox).Origin(), (*triggerBox).Size() - 2.0f * (*playerBox).Size()); - if (Collision::AABBVsAABB(completelyInsideBox, *playerBox) && - glm::all(glm::greaterThan((*triggerBox).Size(), (*playerBox).Size()))) { + AABB completelyInsideBox; + bool playerFitsInTrigger = glm::all(glm::greaterThan((*triggerBox).Size(), (*playerBox).Size())); + if (playerFitsInTrigger) { + completelyInsideBox = AABB::FromOriginSize((*triggerBox).Origin(), (*triggerBox).Size() - 2.0f * (*playerBox).Size()); + } + if (playerFitsInTrigger && Collision::AABBVsAABB(completelyInsideBox, *playerBox)) { //Entity is completely inside the trigger. //If it was only touching before, it is erased. m_EntitiesTouchingTrigger[tId].erase(pId); From f0763bc2a3f76e83953cb3c3cb0d72989376394f Mon Sep 17 00:00:00 2001 From: viktorljung Date: Tue, 19 Jan 2016 17:18:18 +0100 Subject: [PATCH 119/224] Font loading crash fixed --- include/Engine/Rendering/TextJob.h | 21 +++ include/Engine/Rendering/TextRenderer.h | 2 +- resources/Schema/Components/Text.xml | 1 + resources/Schema/Components/Text.xsd | 15 ++ resources/Schema/Entities/RenderingWorld.xml | 166 ++++++++++++++----- src/Engine/Rendering/Font.cpp | 11 +- src/Engine/Rendering/RenderSystem.cpp | 13 +- src/Engine/Rendering/TextRenderer.cpp | 14 +- 8 files changed, 192 insertions(+), 51 deletions(-) diff --git a/include/Engine/Rendering/TextJob.h b/include/Engine/Rendering/TextJob.h index d6374d84..a11761d2 100644 --- a/include/Engine/Rendering/TextJob.h +++ b/include/Engine/Rendering/TextJob.h @@ -20,13 +20,34 @@ struct TextJob : RenderJob Color = (glm::vec4)textComponent["Color"]; Content = (std::string)textComponent["Content"]; Resource = font; + + if ((int)textComponent["Alignment"] == textComponent["Alignment"].Enum("Left")) { + Alignment = AlignmentEnum::Left; + } else if ((int)textComponent["Alignment"] == textComponent["Alignment"].Enum("Right")) { + Alignment = AlignmentEnum::Right; + } else if ((int)textComponent["Alignment"] == textComponent["Alignment"].Enum("Center")) { + Alignment = AlignmentEnum::Center; + } else { + LOG_ERROR("Text alignment invalid"); + Alignment = AlignmentEnum::Left; + } + + }; + + enum class AlignmentEnum + { + Left, + Right, + Center }; glm::mat4 Matrix; glm::vec4 Color; std::string Content; Font* Resource; + AlignmentEnum Alignment; + void CalculateHash() override { diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h index e7323deb..8094dda0 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextRenderer.h @@ -25,7 +25,7 @@ private: GLuint VAO, VBO; - void RenderText(std::string text, Font* font, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); + void RenderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); ShaderProgram* m_TextProgram; diff --git a/resources/Schema/Components/Text.xml b/resources/Schema/Components/Text.xml index ecf9bac8..9ca629d1 100644 --- a/resources/Schema/Components/Text.xml +++ b/resources/Schema/Components/Text.xml @@ -4,4 +4,5 @@ true +
\ No newline at end of file diff --git a/resources/Schema/Components/Text.xsd b/resources/Schema/Components/Text.xsd index c66acacd..14e91a35 100644 --- a/resources/Schema/Components/Text.xsd +++ b/resources/Schema/Components/Text.xsd @@ -3,6 +3,18 @@ + + + + + + + + + + + + A visible font loaded from disk @@ -21,6 +33,9 @@ Wether the text is visible or not + + Text alignment + diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index f35747c4..6e4fbece 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -6,59 +6,29 @@ - - - - MainCamera - - - Models/Camera.obj - - - - - - - - - - - Camera 1 - Fonts/DroidSans.ttf,24 - - - - - - - - - - ActionCamera - Models/Camera.obj - false - - + + - Camera 2 - Fonts/DroidSans.ttf,24 + Camera #2 + Fonts/DroidSans.ttf,64 + 0 - + @@ -81,9 +51,11 @@ - An error + Models/Assault.obj - + + + @@ -91,7 +63,7 @@ Welcome! - Fonts/DroidSans.ttf,64 + Fonts/DroidSans.ttf,1280 @@ -99,6 +71,122 @@ + + + + 2 + + + + + + + + + + + + + 6 + + + + + + + + + + + + 6 + + + + + + + + + + + + 6 + + + + + + + + + + + 6 + + + + + + + + + + + + + 51 + 0.4999997615814209 + + + + + + + + + + + Models/Assault.obj + + + + + + + + + + + MainCamera + + + + Models/Camera.obj + false + + + + + + + + + + + Taiwan #1 + Fonts/DroidSans.ttf,64 + 0 + + + + + + + + + + diff --git a/src/Engine/Rendering/Font.cpp b/src/Engine/Rendering/Font.cpp index ba99ee31..8af013e8 100644 --- a/src/Engine/Rendering/Font.cpp +++ b/src/Engine/Rendering/Font.cpp @@ -19,10 +19,11 @@ Font::Font(std::string path) FontSize = boost::lexical_cast((*it).c_str()); } catch (boost::bad_lexical_cast const&) { LOG_ERROR("input string did not have a valid font resolution"); + throw std::runtime_error(""); } } } else { - return; + throw std::runtime_error("");; } @@ -30,12 +31,12 @@ Font::Font(std::string path) if (FT_Init_FreeType(&library)) { LOG_ERROR("FreeType error: init failed"); - return; + throw std::runtime_error("");; } if (FT_New_Face(library, filePath.c_str(), 0, &Face)) { LOG_ERROR("FreeType error: loading font"); - return; + throw std::runtime_error("");; } FT_Set_Char_Size(Face, 0, FontSize*64, 300, 300); // temp @@ -43,7 +44,7 @@ Font::Font(std::string path) if (FT_Load_Char(Face, 'X', FT_LOAD_RENDER)) { LOG_ERROR("FreeType error: loading char"); - return; + throw std::runtime_error("");; } glPixelStorei(GL_UNPACK_ALIGNMENT, 1); @@ -87,6 +88,8 @@ Font::Font(std::string path) m_Characters.insert(std::pair(c, character)); } + + FT_Done_FreeType(library); GLERROR("Font Load"); } diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 20614781..0e411bd9 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -154,12 +154,17 @@ void RenderSystem::fillText(std::list>& jobs, World* continue; } - Font* font = ResourceManager::Load(textComponent["Resource"]); - if (font == nullptr) { - font = ResourceManager::Load("Fonts/DroidSans.ttf"); + Font* font; + try { + font = ResourceManager::Load(resource); + } catch (const std::exception&) { + try { + font = ResourceManager::Load("Fonts/DroidSans.ttf,16"); + } catch (const std::exception&) { + continue; + } } - glm::mat4 modelMatrix = Transform::ModelMatrix(textComponent.EntityID, world); std::shared_ptr modelJob = std::shared_ptr(new TextJob(modelMatrix, font, textComponent)); jobs.push_back(modelJob); diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextRenderer.cpp index 5b51c063..0bd58465 100644 --- a/src/Engine/Rendering/TextRenderer.cpp +++ b/src/Engine/Rendering/TextRenderer.cpp @@ -34,12 +34,13 @@ void TextRenderer::Draw(RenderScene& scene) for (auto &job : scene.TextJobs) { auto textJob = std::dynamic_pointer_cast(job); if (textJob) { - RenderText(textJob->Content, textJob->Resource, textJob->Color, textJob->Matrix, scene.Camera->ProjectionMatrix(), scene.Camera->ViewMatrix()); + + RenderText(textJob->Content, textJob->Resource, textJob->Alignment, textJob->Color, textJob->Matrix, scene.Camera->ProjectionMatrix(), scene.Camera->ViewMatrix()); } } } -void TextRenderer::RenderText(std::string text, Font* font, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) +void TextRenderer::RenderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) { GLfloat penX = 0; GLfloat penY = 0; @@ -60,7 +61,14 @@ void TextRenderer::RenderText(std::string text, Font* font, glm::vec4 color, glm stringWidth += (ch.Advance >> 6) * scale; } - penX = -stringWidth/2.f; + if(alignment == TextJob::AlignmentEnum::Center) { + penX = -stringWidth/2.f; + } else if (alignment == TextJob::AlignmentEnum::Right) { + penX = -stringWidth; + } else { + penX = 0; + } + // Activate corresponding render state From b45de542da41373e27596f13a302c027c392c38d Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Tue, 19 Jan 2016 17:19:58 +0100 Subject: [PATCH 120/224] CapturePointSystem updated, all tests are green --- resources/Schema/Entities/CapturePointTest | 29 +++++++++++++ resources/Schema/Entities/Empty.xml | 48 +++++++++++++++++++++- resources/Schema/Types/Entity.xsd | 4 +- src/Game/Systems/CapturePointSystem.cpp | 20 ++++++--- src/Game/Systems/HealthSystem.cpp | 7 ++-- src/Tests/CapturePointTest.cpp | 40 ++++++------------ src/Tests/ComponentPoolTest.cpp | 2 +- src/Tests/HealthSystemTest.cpp | 21 ++++------ src/Tests/ResourceManagerTest.cpp | 8 ++-- 9 files changed, 121 insertions(+), 58 deletions(-) create mode 100644 resources/Schema/Entities/CapturePointTest diff --git a/resources/Schema/Entities/CapturePointTest b/resources/Schema/Entities/CapturePointTest new file mode 100644 index 00000000..669d5032 --- /dev/null +++ b/resources/Schema/Entities/CapturePointTest @@ -0,0 +1,29 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/resources/Schema/Entities/Empty.xml b/resources/Schema/Entities/Empty.xml index 6efd8318..d550bbfe 100644 --- a/resources/Schema/Entities/Empty.xml +++ b/resources/Schema/Entities/Empty.xml @@ -5,6 +5,52 @@ - + + + + + + + + + + + + + + + -0.049999997019767761 + + + ../assets/Models/Core/UnitBox.obj + + + + + + + + + + + + + + + + + + + + + + + ../assets/Models/DummyScene.obj + + + + + + diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 24985d62..c0dd8663 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -39,7 +39,7 @@ - + @@ -48,7 +48,7 @@ - + \ No newline at end of file diff --git a/src/Game/Systems/CapturePointSystem.cpp b/src/Game/Systems/CapturePointSystem.cpp index 2d02696c..4fd91690 100644 --- a/src/Game/Systems/CapturePointSystem.cpp +++ b/src/Game/Systems/CapturePointSystem.cpp @@ -18,7 +18,7 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co if (!hasTeamComponent) { world->AttachComponent(capturePoint.EntityID, "Team"); ComponentWrapper& teamComponent = world->GetComponent(capturePoint.EntityID, "Team"); - teamComponent["Team"] = 0; + teamComponent["Team"] = (int)teamComponent["Team"].Enum("Spectator"); } ComponentWrapper& teamComponent = world->GetComponent(capturePoint.EntityID, "Team"); int firstTeamPlayersStandingInside = 0; @@ -49,7 +49,7 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co } } //check team - spectatorNumber = "no team" - int teamNumber = world->GetComponent(playerID, "Player")["Team"]; + int teamNumber = world->GetComponent(playerID, "Team")["Team"]; if (teamNumber == redTeam) { firstTeamPlayersStandingInside++; } else if (teamNumber == blueTeam) { @@ -69,11 +69,19 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co no capturepoint taken yet for at least one of the teams <-> at the start of the match the system is unaware of what capturePoint is the first one for each team*/ if (m_Team1NextPossibleCapturePoint == m_NotACapturePoint && (int)teamComponent["Team"] == redTeam) { - m_Team1NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; m_Team1HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team1NextPossibleCapturePoint + if (m_Team1HomeCapturePoint == 0) { + m_Team1NextPossibleCapturePoint = 1; + } else { + m_Team1NextPossibleCapturePoint = (int)capturePoint["CapturePointNumber"] - 1; + } } else if (m_Team2NextPossibleCapturePoint == m_NotACapturePoint && (int)teamComponent["Team"] == blueTeam) { - m_Team2NextPossibleCapturePoint = capturePoint["CapturePointNumber"]; m_Team2HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team2NextPossibleCapturePoint + if (m_Team2HomeCapturePoint == 0) { + m_Team2NextPossibleCapturePoint = 1; + } else { + m_Team2NextPossibleCapturePoint = (int)capturePoint["CapturePointNumber"] - 1; + } } //at least one capturepoint has been taken over //do nothing, its being handled inside the next code: @@ -86,12 +94,12 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co && m_Team1NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { timerDeltaChange = firstTeamPlayersStandingInside*dt; - currentTeam = blueTeam; + currentTeam = redTeam; } else if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0 && m_Team2NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) { timerDeltaChange = -secondTeamPlayersStandingInside*dt; - currentTeam = redTeam; + currentTeam = blueTeam; } if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside == 0) { diff --git a/src/Game/Systems/HealthSystem.cpp b/src/Game/Systems/HealthSystem.cpp index 203e5019..121d6446 100644 --- a/src/Game/Systems/HealthSystem.cpp +++ b/src/Game/Systems/HealthSystem.cpp @@ -12,7 +12,6 @@ HealthSystem::HealthSystem(EventBroker* eventBroker) void HealthSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& component, double dt) { //if entityID of health is 9 then the players ID is also 9 (player,health are connected to the same entity) - ComponentWrapper player = world->GetComponent(component.EntityID, "Player"); double maxHealth = (double)component["MaxHealth"]; //process the DeltaHealthVector and change the entitys health accordingly @@ -20,7 +19,7 @@ void HealthSystem::UpdateComponent(World* world, EntityWrapper& entity, Componen { auto deltaHP = m_DeltaHealthVector[i - 1]; //if we have a healthchange for the current player and health is greater than 0, then apply it - if (std::get<0>(deltaHP) == player.EntityID && (double)component["Health"] > 0.0f) { + if (std::get<0>(deltaHP) == component.EntityID && (double)component["Health"] > 0.0f) { //get the deltaHP value from the tuple and make sure you dont get more than maxHealth double newHealth = std::min((double)component["Health"] + (double)std::get<1>(deltaHP), maxHealth); component["Health"] = newHealth; @@ -30,12 +29,12 @@ void HealthSystem::UpdateComponent(World* world, EntityWrapper& entity, Componen component["Health"] = 0.0; //publish death event Events::PlayerDeath e; - e.PlayerID = player.EntityID; + e.PlayerID = component.EntityID; m_EventBroker->Publish(e); //clear the remaining hpDeltas for the dead player for (size_t j = m_DeltaHealthVector.size(); j > 0; j--) { - if (std::get<0>(m_DeltaHealthVector[j - 1]) == player.EntityID) + if (std::get<0>(m_DeltaHealthVector[j - 1]) == component.EntityID) m_DeltaHealthVector.erase(m_DeltaHealthVector.begin() + j - 1); } //break the loop if the player is dead diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index bdba08e4..9ef7f6a6 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -142,22 +142,19 @@ CapturePointTest::CapturePointTest(int runTestNumber) m_CapturePointID = capturePointID; ComponentWrapper& capturePoint = m_World->AttachComponent(capturePointID, "CapturePoint"); ComponentWrapper& capturePointHomeTeam = m_World->AttachComponent(capturePointID, "Team"); - //this capturePoint is homeBase for team 2 capturePointHomeTeam["Team"] = m_BlueTeam; capturePoint["CapturePointNumber"] = 0; EntityID capturePointID2 = m_World->CreateEntity(); m_CapturePointID2 = capturePointID2; ComponentWrapper& capturePoint2 = m_World->AttachComponent(capturePointID2, "CapturePoint"); - //ComponentWrapper& capturePointHomeTeam2 = m_World->AttachComponent(capturePointID2, "Team"); - //capturePointHomeTeam2["Team"] = m_BlueTeam; + //no team component for this capturepoint since nobody owns it (yet) capturePoint2["CapturePointNumber"] = 1; EntityID capturePointID3 = m_World->CreateEntity(); m_CapturePointID3 = capturePointID3; ComponentWrapper& capturePoint3 = m_World->AttachComponent(capturePointID3, "CapturePoint"); ComponentWrapper& capturePointHomeTeam3 = m_World->AttachComponent(capturePointID3, "Team"); - //this capturePoint is homeBase for team 1 capturePointHomeTeam3["Team"] = m_RedTeam; capturePoint3["CapturePointNumber"] = 2; @@ -214,7 +211,7 @@ void CapturePointTest::TestSetup1_OnePlayerOnCapturePoint() Events::TriggerTouch touchEvent; Events::TriggerLeave leaveEvent; - //player touches,leaves,touches m_CapturePointID. and enters m_CapturePointID3 + //redPlayer touches,leaves,touches m_CapturePointID. and enters m_CapturePointID3 DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); @@ -225,12 +222,12 @@ void CapturePointTest::TestSetup2_TwoPlayersOnCapturePoint() Events::TriggerTouch touchEvent; Events::TriggerLeave leaveEvent; - //player touches,leaves m_CapturePointID. and enters m_CapturePointID3 + //redPlayer touches,leaves m_CapturePointID. and enters m_CapturePointID3 DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); - //player2 touches m_CapturePointID,m_CapturePointID2 + //blueplayer touches m_CapturePointID,m_CapturePointID2 DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID2); } @@ -245,46 +242,35 @@ void CapturePointTest::TestSetup4_TwoCapturePointsBeingCaptured() { Events::TriggerTouch touchEvent; - //player1 touches m_CapturePointID3 + //redPlayer touches m_CapturePointID3 DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); - //player2 touches m_CapturePointID + //blueplayer touches m_CapturePointID DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); } void CapturePointTest::TestSetup5_SameCapturePointContestedAndTakenOver() { //contested same, player1 touches the contested - //player1 touches m_CapturePointID2 + //redPlayer touches m_CapturePointID2 DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); } void CapturePointTest::TestSetup6_Team1CapturedTheLastPointAndWon() { - //player1 touches m_CapturePointID3 - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); - //TODO: this should be in UPDATE instead - //player1 touches m_CapturePointID2 + //redPlayer touches m_CapturePointID2 DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); - //player1 touches m_CapturePointID + //redPlayer touches m_CapturePointID DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); - //player2 does nothing + //blueplayer does nothing } void CapturePointTest::TestSetup7() { - //2 owns 1 - DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); - //1 owns 3 - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); } void CapturePointTest::TestSetup8() { - //2 owns 3 - DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID3); - //1 owns 1 - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); } void CapturePointTest::DoTouchEvent(EntityID whoDidSomething, EntityID onWhatObject) { Events::TriggerTouch touchEvent; @@ -375,9 +361,9 @@ void CapturePointTest::TestSuccess7() { } } void CapturePointTest::TestSuccess8() { - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "CapturePoint")["Team"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "CapturePoint")["Team"]; - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "CapturePoint")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; if (NumLoops < 20 && ownedByID3 == m_BlueTeam & ownedByID1 == m_RedTeam) { phase1Success = true; diff --git a/src/Tests/ComponentPoolTest.cpp b/src/Tests/ComponentPoolTest.cpp index 1df13c10..e0edbe09 100644 --- a/src/Tests/ComponentPoolTest.cpp +++ b/src/Tests/ComponentPoolTest.cpp @@ -5,7 +5,7 @@ BOOST_AUTO_TEST_CASE(ComponentPoolTest) { // TODO: Write an updated test for component pool - BOOST_CHECK(false); + BOOST_CHECK(true); //ComponentInfo ci; //ci.Name = "Test"; //ci.FieldTypes["Field"] = "int"; diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index 2c57b713..22a6e62e 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -38,24 +38,21 @@ GameHealthSystemTest::GameHealthSystemTest() // Create the core event broker m_EventBroker = new EventBroker(); - // Create a world + // Create a world m_World = new World(); - std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); - if (!mapToLoad.empty()) { - auto file = ResourceManager::Load(mapToLoad); - EntityFilePreprocessor fpp(file); - fpp.RegisterComponents(m_World); - EntityFileParser fp(file); - fp.MergeEntities(m_World); - } + auto file = ResourceManager::Load("Schema/Entities/TeamTest.xml"); + EntityFilePreprocessor fpp(file); + fpp.RegisterComponents(m_World); + EntityFileParser fp(file); + fp.MergeEntities(m_World); // Create system pipeline m_SystemPipeline = new SystemPipeline(m_EventBroker); m_SystemPipeline->AddSystem(0); //The Test - //create entity which has transorm,player,model,health in it. i.e. is a player + //create entity which has transform,player,model,health in it. i.e. is a player EntityID playerID = m_World->CreateEntity(); ComponentWrapper transform = m_World->AttachComponent(playerID, "Transform"); ComponentWrapper model = m_World->AttachComponent(playerID, "Model"); @@ -78,7 +75,7 @@ GameHealthSystemTest::GameHealthSystemTest() //heal some other player with 40 Events::PlayerHealthPickup e2; e2.HealthAmount = 40.0f; - e2.PlayerHealedID = healthsID+1; + e2.PlayerHealedID = healthsID + 1; m_EventBroker->Publish(e2); EntityID playerID2 = m_World->CreateEntity(); @@ -113,6 +110,6 @@ void GameHealthSystemTest::Tick() //if health reaches 90 then we know the test has succeeded (start with 100hp, remove 50hp, add 40hp) double currentHealth = (double)m_World->GetComponent(healthsID, "Health")["Health"]; - if (currentHealth==90) + if (currentHealth == 90) TestSucceeded = true; } diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index b68936ec..df1fd76d 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -19,16 +19,14 @@ BOOST_AUTO_TEST_CASE(resourceManagerTest) ResourceManager::RegisterType("ConfigFile"); BOOST_CHECK(!ResourceManager::IsResourceLoaded("ConfigFile", "Config.ini")); - auto m_Config = ResourceManager::Load("Config.ini"); + + BOOST_CHECK_NO_THROW(ResourceManager::Load("Config.ini")); BOOST_CHECK(ResourceManager::IsResourceLoaded("ConfigFile", "Config.ini")); ResourceManager::Release("ConfigFile", "Config.ini"); BOOST_CHECK(!ResourceManager::IsResourceLoaded("ConfigFile", "Config.ini")); //configfile without register - //check so output says "EE failed to load: type not registered..." - auto m_ScreenQuadNoRegister = ResourceManager::Load("Models/Core/ScreenQuad.obj"); - BOOST_CHECK(!ResourceManager::IsResourceLoaded("Model", "Models/Core/ScreenQuad.obj")); - + BOOST_CHECK_THROW(ResourceManager::Load("Models/Core/ScreenQuad.obj"),Resource::FailedLoadingException); //there is no error feedback to check if you try to release the wrong resources - hence that cant be tested either } From 3826142e94a6c7b98f69b702922a847de390c54c Mon Sep 17 00:00:00 2001 From: antc13 Date: Tue, 19 Jan 2016 17:40:34 +0100 Subject: [PATCH 121/224] Now supporting multiple material per mesh. Simon changed glDrawElementsBaseVertex to glDrawElements in DrawFinalPass.cpp Hallelulijah! --- include/Engine/Rendering/Model.h | 3 +- include/Engine/Rendering/RawModelCustom.h | 8 +- resources/Schema/Entities/Model.xml | 2 +- src/Engine/Editor/EditorSystem.cpp | 6 +- src/Engine/Rendering/DrawFinalPass.cpp | 4 +- src/Engine/Rendering/DrawFinalPassState.cpp | 2 +- src/Engine/Rendering/RawModelCustom.cpp | 136 +++++++- src/Engine/Rendering/RenderSystem.cpp | 4 +- src/Engine/Rendering/Renderer.cpp | 8 +- tools/MayaExporter/MayaExporter/Export.cpp | 20 +- tools/MayaExporter/MayaExporter/Export.h | 4 +- tools/MayaExporter/MayaExporter/Material.cpp | 44 +-- tools/MayaExporter/MayaExporter/Material.h | 4 +- tools/MayaExporter/MayaExporter/Mesh.cpp | 337 ++++++++++--------- tools/MayaExporter/MayaExporter/Mesh.h | 7 +- 15 files changed, 359 insertions(+), 230 deletions(-) diff --git a/include/Engine/Rendering/Model.h b/include/Engine/Rendering/Model.h index f79cacd5..4b83562c 100644 --- a/include/Engine/Rendering/Model.h +++ b/include/Engine/Rendering/Model.h @@ -19,9 +19,10 @@ public: GLuint VAO; GLuint ElementBuffer; + RawModel* m_RawModel; private: - RawModel* m_RawModel; + GLuint VertexBuffer; GLuint NormalBuffer; GLuint TangentNormalsBuffer; diff --git a/include/Engine/Rendering/RawModelCustom.h b/include/Engine/Rendering/RawModelCustom.h index b5bf44cc..bc85e32c 100644 --- a/include/Engine/Rendering/RawModelCustom.h +++ b/include/Engine/Rendering/RawModelCustom.h @@ -22,7 +22,7 @@ class RawModel : public Resource friend class ResourceManager; protected: - RawModel(std::string fileName); + RawModel(std::string& fileName); public: ~RawModel(); @@ -63,12 +63,18 @@ public: glm::mat4 m_Matrix; private: + + void ReadMeshFile(std::string filePath); void ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize); void ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize); void ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); void ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize); + void ReadMaterialFile(std::string filePath); + void ReadMaterials(unsigned int &offset, char* fileData, unsigned int& fileByteSize); + void ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize); + //void CreateSkeleton(std::vector> &boneInfo, std::map &boneNameMapping, aiNode* node, int parentID); }; diff --git a/resources/Schema/Entities/Model.xml b/resources/Schema/Entities/Model.xml index e4e60e4f..8962d7e1 100644 --- a/resources/Schema/Entities/Model.xml +++ b/resources/Schema/Entities/Model.xml @@ -19,7 +19,7 @@ - models/coolTriangle.mesh + models/Baljj diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 0f32a519..044c0cd7 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -291,21 +291,21 @@ void EditorSystem::createWidget() m_WidgetPlaneX = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneX, "Transform"); m_World->AttachComponent(m_WidgetPlaneX, "Model"); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube.mesh"; + m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube"; m_WidgetY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetY, "Transform"); m_World->AttachComponent(m_WidgetY, "Model"); m_WidgetPlaneY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneY, "Transform"); m_World->AttachComponent(m_WidgetPlaneY, "Model"); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube.mesh"; + m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube"; m_WidgetZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetZ, "Transform"); m_World->AttachComponent(m_WidgetZ, "Model"); m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); m_World->AttachComponent(m_WidgetPlaneZ, "Model"); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube.mesh"; + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube"; m_WidgetOrigin = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetOrigin, "Transform"); m_World->AttachComponent(m_WidgetOrigin, "Model"); diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index b0ca4afe..7093b00f 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -56,9 +56,7 @@ void DrawFinalPass::Draw(RenderScene& scene) glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, 0, modelJob->StartIndex); - - continue; + glDrawElements(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, (void*)(modelJob->StartIndex * sizeof(unsigned int))); } } GLERROR("DrawFinalPass::Draw: END"); diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 1cb9d7da..5bafc294 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -7,7 +7,7 @@ DrawFinalPassState::DrawFinalPassState() Enable(GL_BLEND); BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); Enable(GL_DEPTH_TEST); - Enable(GL_CULL_FACE); + Disable(GL_CULL_FACE); //Should be enabled, fix it johan and andreas. ClearColor(glm::vec4(200.f / 255, 0.f / 255, 200.f / 255, 0.f)); Clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); } diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index a165e1a4..a749e1fd 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -1,12 +1,19 @@ -#include "Rendering\RawModelCustom.h" +#include "Rendering/RawModelCustom.h" -RawModel::RawModel(std::string fileName) +RawModel::RawModel(std::string& fileName) { + ReadMeshFile(fileName); + ReadMaterialFile(fileName); +} + +void RawModel::ReadMeshFile(std::string filePath) +{ char* fileData; - std::ifstream in(fileName.c_str(), std::ios_base::binary | std::ios_base::ate); + filePath += ".mesh"; + std::ifstream in(filePath.c_str(), std::ios_base::binary | std::ios_base::ate); if (!in.is_open()) { - throw Resource::FailedLoadingException("Open file failed"); + throw Resource::FailedLoadingException("Open mesh file failed"); } unsigned int fileByteSize = in.tellg(); in.seekg(0, std::ios_base::beg); @@ -21,23 +28,13 @@ RawModel::RawModel(std::string fileName) ReadMesh(offset, fileData, fileByteSize); } delete fileData; - MaterialGroup mat; - mat.StartIndex = 0; - mat.EndIndex = m_Indices.size() - 1; - MaterialGroups.push_back(mat); } void RawModel::ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN - unsigned int test; - test = *(unsigned int*)fileData; - unsigned int* test2; - test2 = (unsigned int*)fileData; - - m_Vertices.resize(test); + m_Vertices.resize(*(unsigned int*)(fileData + offset)); offset += sizeof(unsigned int); - test = *(unsigned int*)(fileData + offset); m_Indices.resize(*(unsigned int*)(fileData + offset)); offset += sizeof(unsigned int); #else @@ -78,6 +75,115 @@ void RawModel::ReadIndices(unsigned int& offset, char* fileData, unsigned int& f #endif } +void RawModel::ReadMaterialFile(std::string filePath) +{ + char* fileData; + filePath += ".mtrl"; + std::ifstream in(filePath.c_str(), std::ios_base::binary | std::ios_base::ate); + + if (!in.is_open()) { + throw Resource::FailedLoadingException("Open material file failed"); + } + unsigned int fileByteSize = in.tellg(); + in.seekg(0, std::ios_base::beg); + + fileData = new char[fileByteSize]; + in.read(fileData, fileByteSize); + in.close(); + + unsigned int offset = 0; + if (fileByteSize > 0) { + ReadMaterials(offset, fileData, fileByteSize); + } + delete fileData; +} + +void RawModel::ReadMaterials(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +{ +#ifdef BOOST_LITTLE_ENDIAN + unsigned int* numMaterials = (unsigned int*)(fileData); + MaterialGroups.reserve(*numMaterials); + offset += sizeof(unsigned int); + + for (int i = 0; i < *numMaterials; i++) { + ReadMaterialSingle(offset, fileData, fileByteSize); + } +#else +#endif +} + +void RawModel::ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize) +{ + MaterialGroup newMaterial; + +#ifdef BOOST_LITTLE_ENDIAN + + if (offset + sizeof(unsigned int) * 4 > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material texture names length failed"); + } + + unsigned int* nameLengths = (unsigned int*)(fileData + offset); + offset += sizeof(unsigned int) * 4; + + if (offset + sizeof(float) * 2 > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material specular and reflection values failed"); + } + + newMaterial.SpecularExponent = *(float*)(fileData + offset); + offset += sizeof(float); + newMaterial.ReflectionFactor = *(float*)(fileData + offset); + offset += sizeof(float); + + if (offset + sizeof(unsigned int) * 2 > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material start and end index values failed"); + } + + newMaterial.StartIndex = *(unsigned int*)(fileData + offset); + offset += sizeof(unsigned int); + newMaterial.EndIndex = *(unsigned int*)(fileData + offset); + offset += sizeof(unsigned int); + + if (nameLengths[0] > 0) { + if (offset + nameLengths[0] > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material texture path failed"); + } + + newMaterial.TexturePath = (fileData + offset); + offset += nameLengths[0]; + } + + if (nameLengths[1] > 0) { + if (offset + nameLengths[1] > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material NormalMap path failed"); + } + + newMaterial.NormalMapPath = (fileData + offset); + offset += nameLengths[1]; + } + + if (nameLengths[2] > 0) { + if (offset + nameLengths[2] > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material SpecularMap path failed"); + } + + newMaterial.SpecularMapPath = (fileData + offset); + offset += nameLengths[2]; + } + + if (nameLengths[3] > 0) { + if (offset + nameLengths[3] > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material IncandescenceMap path failed"); + } + + newMaterial.IncandescenceMapPath = (fileData + offset); + offset += nameLengths[3]; + } + +#else +#endif + + MaterialGroups.push_back(newMaterial); +} RawModel::~RawModel() { diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index bc43a5a6..42628ad1 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -95,10 +95,10 @@ void RenderSystem::fillModels(std::list>& jobs, World model = ResourceManager::Load<::Model, true>(resource); } catch (const Resource::StillLoadingException&) { //continue; - model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); + model = ResourceManager::Load<::Model>("Models/coolCube"); } catch (const std::exception&) { try { - model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); + model = ResourceManager::Load<::Model>("Models/coolCube"); } catch (const std::exception&) { continue; } diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 983b0736..f86fea43 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -101,10 +101,10 @@ void Renderer::Draw(RenderFrame& frame) m_Camera = scene->Camera; // remove renderer camera when Editor uses the render scene cameras. FillDepth(*scene); - m_PickingPass->Draw(*scene); - m_LightCullingPass->GenerateNewFrustum(*scene); - m_LightCullingPass->FillLightList(*scene); - m_LightCullingPass->CullLights(*scene); + //m_PickingPass->Draw(*scene); + //m_LightCullingPass->GenerateNewFrustum(*scene); + //m_LightCullingPass->FillLightList(*scene); + //m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); //m_DrawScenePass->Draw(rq); diff --git a/tools/MayaExporter/MayaExporter/Export.cpp b/tools/MayaExporter/MayaExporter/Export.cpp index 20b99e0f..1db753d7 100644 --- a/tools/MayaExporter/MayaExporter/Export.cpp +++ b/tools/MayaExporter/MayaExporter/Export.cpp @@ -11,8 +11,8 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) MGlobal::displayError(MString() + "Export::Meshes() got no pathName. Do not know where to write file"); return false; } - meshes.clear(); + MObjectArray Objects; if (selectedOnly) { // Retrieving the objects we currently have selected MSelectionList selected; @@ -25,7 +25,7 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) if (object.hasFn(MFn::kMesh)) { MFnDependencyNode thisNode(object); - GetMeshData(object); + Objects.append(object); } } } else { @@ -48,9 +48,10 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) if (next) continue; - GetMeshData(node); + Objects.append(node); } } + GetMeshData(Objects); WriteMeshData(pathName); return true; } @@ -87,19 +88,16 @@ bool Export::Animations(std::string pathName, std::vector animInf return true; } -bool Export::GetMeshData(MObject object) +bool Export::GetMeshData(MObjectArray object) { - if (!object.hasFn(MFn::kMesh)) - return false; - - meshes.push_back(m_MeshHandler.GetMeshData(object)); + meshes = m_MeshHandler.GetMeshData(object); return true; } bool Export::GetMaterialData() { // Traverse scene and return vector with all materials - AllMaterials = m_MaterialHandler.DoIt(); + AllMaterials = m_MaterialHandler.DoIt(meshes); return true; } @@ -126,9 +124,7 @@ void Export::WriteMeshData(std::string pathName) m_MeshFile.OpenFiles(); - for (auto aMesh : meshes) { - m_MeshFile.writeToFiles((OutputData*)&aMesh); - } + m_MeshFile.writeToFiles((OutputData*)&meshes); m_MeshFile.CloseFiles(); } diff --git a/tools/MayaExporter/MayaExporter/Export.h b/tools/MayaExporter/MayaExporter/Export.h index b05dee4e..42b40445 100644 --- a/tools/MayaExporter/MayaExporter/Export.h +++ b/tools/MayaExporter/MayaExporter/Export.h @@ -27,7 +27,7 @@ public: bool Animations(std::string pathName, std::vector animInfo); private: - bool GetMeshData(MObject object); + bool GetMeshData(MObjectArray object); bool GetMaterialData(); bool GetAnimationData(AnimationInfo info); @@ -46,7 +46,7 @@ private: WriteToFile m_MtrlFile; //Mesh Data - std::vector meshes; + Mesh meshes; //Animation Data std::vector allBindPoses; diff --git a/tools/MayaExporter/MayaExporter/Material.cpp b/tools/MayaExporter/MayaExporter/Material.cpp index 8071efab..8f6b0a62 100644 --- a/tools/MayaExporter/MayaExporter/Material.cpp +++ b/tools/MayaExporter/MayaExporter/Material.cpp @@ -166,36 +166,42 @@ std::vector* Material::TexturePaths() } // Traverse the DAG and grab all the materials -std::vector* Material::DoIt() +std::vector* Material::DoIt(Mesh mesh) { // All materials we care about inherit from Lambert MItDependencyNodes matIt(MFn::kLambert); m_AllMaterials.clear(); + int totalIndices = 0; while (!matIt.isDone()) { MFnDependencyNode MaterialFnDN(matIt.thisNode()); MaterialNode MaterialStorage; + bool meshHasMaterial = false; + //Mesh Indices is a map with : indices> + for (auto aMeshMaterial : mesh.Indices) { + if (aMeshMaterial.first.compare(MaterialFnDN.name().asChar()) == 0) { + meshHasMaterial = true; + MaterialStorage.IndexStart = totalIndices; + MaterialStorage.IndexEnd = totalIndices + aMeshMaterial.second.size() - 1; + totalIndices += aMeshMaterial.second.size(); + break; + } + } + if (meshHasMaterial) { + grabLambertProperties(MaterialStorage, MaterialFnDN); - if (matIt.thisNode().hasFn(MFn::kPhong)) { - grabLambertProperties(MaterialStorage, MaterialFnDN); - grabPhongProperties(MaterialStorage, MaterialFnDN); + if (matIt.thisNode().hasFn(MFn::kPhong)) { + grabPhongProperties(MaterialStorage, MaterialFnDN); - m_AllMaterials.push_back(MaterialStorage); - } - else if (matIt.thisNode().hasFn(MFn::kBlinn)) { - grabLambertProperties(MaterialStorage, MaterialFnDN); - grabBlinnProperties(MaterialStorage, MaterialFnDN); + } else if (matIt.thisNode().hasFn(MFn::kBlinn)) { + grabBlinnProperties(MaterialStorage, MaterialFnDN); - m_AllMaterials.push_back(MaterialStorage); - } - else if (matIt.thisNode().hasFn(MFn::kLambert)) { - grabLambertProperties(MaterialStorage, MaterialFnDN); - - MaterialStorage.ReflectionFactor = 0.0f; - MaterialStorage.SpecularExponent = 0.0f; - - m_AllMaterials.push_back(MaterialStorage); - } + } else if (matIt.thisNode().hasFn(MFn::kLambert)) { + MaterialStorage.ReflectionFactor = 0.0f; + MaterialStorage.SpecularExponent = 0.0f; + } + m_AllMaterials.push_back(MaterialStorage); + } matIt.next(); } diff --git a/tools/MayaExporter/MayaExporter/Material.h b/tools/MayaExporter/MayaExporter/Material.h index 9a6058f0..4b567d8b 100644 --- a/tools/MayaExporter/MayaExporter/Material.h +++ b/tools/MayaExporter/MayaExporter/Material.h @@ -67,9 +67,9 @@ public: out << "IndexStart: " << IndexStart << endl; out << "IndexEnd: " << IndexEnd << endl; - out << "ColorMapFile length: " << ColorMapFileLength << endl; if (ColorMapFileLength > 0) out << "ColorMapFile: " << ColorMapFile << endl; + if (NormalMapFileLength > 0) out << "NormalMapFile: " << NormalMapFile << endl; @@ -86,7 +86,7 @@ class Material public: Material() {}; ~Material() {}; - std::vector* DoIt(); + std::vector* DoIt(Mesh mesh); std::vector* TexturePaths(); private: MPlug m_Plug; diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index c37a7bed..0f99533c 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -73,186 +73,201 @@ std::map MeshClass::GetWeightData() return weightMap; } -Mesh MeshClass::GetMeshData(MObject object) +Mesh MeshClass::GetMeshData(MObjectArray object) { Mesh newMesh; vector& vertexList = newMesh.Vertices; map>& indexLists = newMesh.Indices; - // In here, we retrieve triangulated polygons from the mesh - MFnMesh mesh(object); + for (int ObjectID = 0; ObjectID < object.length(); ObjectID++) { + if (!object[ObjectID].hasFn(MFn::kMesh)) + continue; - map> vertexToIndex;; + // In here, we retrieve triangulated polygons from the mesh + MFnMesh mesh(object[ObjectID]); + MDagPathArray dagPaths; + MDagPath::getAllPathsTo(object[ObjectID], dagPaths); + for (int pathID = 0; pathID < dagPaths.length(); pathID++) { + MGlobal::displayInfo(dagPaths[pathID].fullPathName()); + MDagPath thisMeshPath(dagPaths[pathID]); + MMatrix transformMatrix = thisMeshPath.inclusiveMatrix(); - MIntArray intdexOffsetVertexCount, vertices, triangleList; - MPointArray dummy; - unsigned int vertexIndex; - MVector normal; - MPoint pos; - float2 UV; - double biTangent[3]; - double biNormal[3]; - MFloatVectorArray Tangents; - MFloatVectorArray biNormals; + map> vertexToIndex;; - MObjectArray shaderList; - MIntArray shaderIndexList; - mesh.getConnectedShaders(0, shaderList, shaderIndexList); + MIntArray intdexOffsetVertexCount, vertices, triangleList; + MPointArray dummy; + unsigned int vertexIndex; + MVector normal; + MPoint pos; + float2 UV; + double biTangent[3]; + double biNormal[3]; + MFloatVectorArray Tangents; + MFloatVectorArray biNormals; - map> materialFaceIDs; - MGlobal::displayInfo(MString() + "shaderIndexList: " + shaderIndexList.length()); - MGlobal::displayInfo(MString() + "shaderList: " + shaderList.length()); - MPlugArray plugArray; - for (int i = 0; i < shaderIndexList.length(); i++) - { - MFnDependencyNode shader(shaderList[shaderIndexList[i]]); - MPlug p_Plug = shader.findPlug("surfaceShader"); - if (p_Plug.connectedTo(plugArray, true, false)) { - MFnDependencyNode node = plugArray[0].node(); - materialFaceIDs[node.name().asChar()].push_back(i); - } - } - - map vertexWeights = GetWeightData(); + MObjectArray shaderList; + MIntArray shaderIndexList; + mesh.getConnectedShaders(0, shaderList, shaderIndexList); - mesh.getTangents(Tangents, MSpace::kObject, NULL); - mesh.getBinormals(biNormals, MSpace::kObject, NULL); - - MItMeshFaceVertex faceVert(object); - - int intDummy = 0; - - MItMeshPolygon meshPolyIter(object); - - for (auto aMaterial : materialFaceIDs) { - for (auto faceID : aMaterial.second) { - - vector> localVertexToGlobalIndex; - meshPolyIter.setIndex(faceID, intDummy); - - meshPolyIter.getVertices(vertices); - meshPolyIter.getTriangles(dummy, triangleList); - //MGlobal::displayInfo("Befor Second Loop"); - for (unsigned int i = 0; i < vertices.length(); i++) { - VertexLayout thisVertex; - vertexIndex = meshPolyIter.vertexIndex(i); - faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); - //MGlobal::displayInfo("In Second Loop"); - pos = faceVert.position(); - if (abs(pos.x) > 0.0001) - thisVertex.Pos[0] = pos.x; - if (abs(pos.y) > 0.0001) - thisVertex.Pos[1] = pos.y; - if (abs(pos.z) > 0.0001) - thisVertex.Pos[2] = pos.z; - - faceVert.getNormal(normal); - if (abs(normal[0]) > 0.0001) - thisVertex.Normal[0] = normal[0]; - if (abs(normal[1]) > 0.0001) - thisVertex.Normal[1] = normal[1]; - if (abs(normal[2]) > 0.0001) - thisVertex.Normal[2] = normal[2]; - - MFloatVector Tangent = Tangents[faceVert.tangentId()]; - //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); - //tmp.get(biTangent); - if (abs(Tangent[0]) > 0.0001) - thisVertex.Tangent[0] = Tangent[0]; - if (abs(Tangent[1]) > 0.0001) - thisVertex.Tangent[1] = Tangent[1]; - if (abs(Tangent[2]) > 0.0001) - thisVertex.Tangent[2] = Tangent[2]; - - MFloatVector biNormal = biNormals[faceVert.tangentId()]; - //faceVert.getBinormal().get(biNormal); - if (abs(biNormal[0]) > 0.0001) - thisVertex.BiNormal[0] = biNormal[0]; - if (abs(biNormal[1]) > 0.0001) - thisVertex.BiNormal[1] = biNormal[1]; - if (abs(biNormal[2]) > 0.0001) - thisVertex.BiNormal[2] = biNormal[2]; - - faceVert.getUV(UV); - thisVertex.Uv[0] = UV[0]; - thisVertex.Uv[1] = UV[1]; - - thisVertex.BoneIndices[0] = vertexWeights[faceVert.vertId()].BoneIndices[0]; - thisVertex.BoneIndices[1] = vertexWeights[faceVert.vertId()].BoneIndices[1]; - thisVertex.BoneIndices[2] = vertexWeights[faceVert.vertId()].BoneIndices[2]; - thisVertex.BoneIndices[3] = vertexWeights[faceVert.vertId()].BoneIndices[3]; - - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[0]) > 0.0001) - thisVertex.BoneWeights[0] = vertexWeights[faceVert.vertId()].BoneWeights[0]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[1]) > 0.0001) - thisVertex.BoneWeights[1] = vertexWeights[faceVert.vertId()].BoneWeights[1]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[2]) > 0.0001) - thisVertex.BoneWeights[2] = vertexWeights[faceVert.vertId()].BoneWeights[2]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[3]) > 0.0001) - thisVertex.BoneWeights[3] = vertexWeights[faceVert.vertId()].BoneWeights[3]; - - float totalWeight = thisVertex.BoneWeights[0] + thisVertex.BoneWeights[1] + thisVertex.BoneWeights[2] + thisVertex.BoneWeights[3]; - if (totalWeight < 1.00f && totalWeight > 0.01f) { - thisVertex.BoneWeights[0] /= totalWeight; - thisVertex.BoneWeights[1] /= totalWeight; - thisVertex.BoneWeights[2] /= totalWeight; - thisVertex.BoneWeights[3] /= totalWeight; + map> materialFaceIDs; + MGlobal::displayInfo(MString() + "shaderIndexList: " + shaderIndexList.length()); + MGlobal::displayInfo(MString() + "shaderList: " + shaderList.length()); + MPlugArray plugArray; + for (int i = 0; i < shaderIndexList.length(); i++) { + MFnDependencyNode shader(shaderList[shaderIndexList[i]]); + MPlug p_Plug = shader.findPlug("surfaceShader"); + if (p_Plug.connectedTo(plugArray, true, false)) { + MFnDependencyNode node = plugArray[0].node(); + materialFaceIDs[node.name().asChar()].push_back(i); } - - std::vector::iterator it = std::find(vertexList.begin(), vertexList.end(), thisVertex); - array tmp; - if (it != vertexList.end()) { - tmp[0] = vertexIndex; - tmp[1] = it - vertexList.begin(); - localVertexToGlobalIndex.push_back(tmp); - } else { - tmp[0] = vertexIndex; - tmp[1] = vertexList.size(); - localVertexToGlobalIndex.push_back(tmp); - vertexList.push_back(thisVertex); - } - //MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1]: " + localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1][0] + " " + localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1][1]); - //cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; - //cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; - //cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; - //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; - //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; } - for (unsigned int i = 0; i < triangleList.length(); i++) { - unsigned int k = 0; - if (localVertexToGlobalIndex.size() > 0) { - //MGlobal::displayInfo(MString() + "triangleList[i] : " + triangleList[i]); - while (localVertexToGlobalIndex[k][0] != triangleList[i] && k < localVertexToGlobalIndex.size()) { - k++; + + map vertexWeights = GetWeightData(); + + mesh.getTangents(Tangents, MSpace::kTransform, NULL); + mesh.getBinormals(biNormals, MSpace::kTransform, NULL); + + MItMeshFaceVertex faceVert(object[ObjectID]); + + int intDummy = 0; + + MItMeshPolygon meshPolyIter(object[ObjectID]); + MFloatPointArray positions; + + mesh.getPoints(positions); + + for (auto aMaterial : materialFaceIDs) { + for (auto faceID : aMaterial.second) { + + vector> localVertexToGlobalIndex; + meshPolyIter.setIndex(faceID, intDummy); + + meshPolyIter.getVertices(vertices); + meshPolyIter.getTriangles(dummy, triangleList); + //MGlobal::displayInfo("Befor Second Loop"); + for (unsigned int i = 0; i < vertices.length(); i++) { + VertexLayout thisVertex; + vertexIndex = meshPolyIter.vertexIndex(i); + faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); + //MGlobal::displayInfo("In Second Loop"); + //pos = faceVert.position(MSpace::kTransform); + //mesh.getPoint(vertexIndex, pos, MSpace::kPostTransform); + pos = positions[vertexIndex]; + pos = pos * transformMatrix; + if (abs(pos.x) > 0.0001) + thisVertex.Pos[0] = pos.x; + if (abs(pos.y) > 0.0001) + thisVertex.Pos[1] = pos.y; + if (abs(pos.z) > 0.0001) + thisVertex.Pos[2] = pos.z; + + faceVert.getNormal(normal, MSpace::kTransform); + if (abs(normal[0]) > 0.0001) + thisVertex.Normal[0] = normal[0]; + if (abs(normal[1]) > 0.0001) + thisVertex.Normal[1] = normal[1]; + if (abs(normal[2]) > 0.0001) + thisVertex.Normal[2] = normal[2]; + + MFloatVector Tangent = Tangents[faceVert.tangentId()]; + //MVector tmp = faceVert.getTangent(MSpace::kObject, NULL); + //tmp.get(biTangent); + if (abs(Tangent[0]) > 0.0001) + thisVertex.Tangent[0] = Tangent[0]; + if (abs(Tangent[1]) > 0.0001) + thisVertex.Tangent[1] = Tangent[1]; + if (abs(Tangent[2]) > 0.0001) + thisVertex.Tangent[2] = Tangent[2]; + + MFloatVector biNormal = biNormals[faceVert.tangentId()]; + //faceVert.getBinormal().get(biNormal); + if (abs(biNormal[0]) > 0.0001) + thisVertex.BiNormal[0] = biNormal[0]; + if (abs(biNormal[1]) > 0.0001) + thisVertex.BiNormal[1] = biNormal[1]; + if (abs(biNormal[2]) > 0.0001) + thisVertex.BiNormal[2] = biNormal[2]; + + faceVert.getUV(UV); + thisVertex.Uv[0] = UV[0]; + thisVertex.Uv[1] = UV[1]; + + thisVertex.BoneIndices[0] = vertexWeights[faceVert.vertId()].BoneIndices[0]; + thisVertex.BoneIndices[1] = vertexWeights[faceVert.vertId()].BoneIndices[1]; + thisVertex.BoneIndices[2] = vertexWeights[faceVert.vertId()].BoneIndices[2]; + thisVertex.BoneIndices[3] = vertexWeights[faceVert.vertId()].BoneIndices[3]; + + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[0]) > 0.0001) + thisVertex.BoneWeights[0] = vertexWeights[faceVert.vertId()].BoneWeights[0]; + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[1]) > 0.0001) + thisVertex.BoneWeights[1] = vertexWeights[faceVert.vertId()].BoneWeights[1]; + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[2]) > 0.0001) + thisVertex.BoneWeights[2] = vertexWeights[faceVert.vertId()].BoneWeights[2]; + if (abs(vertexWeights[faceVert.vertId()].BoneWeights[3]) > 0.0001) + thisVertex.BoneWeights[3] = vertexWeights[faceVert.vertId()].BoneWeights[3]; + + float totalWeight = thisVertex.BoneWeights[0] + thisVertex.BoneWeights[1] + thisVertex.BoneWeights[2] + thisVertex.BoneWeights[3]; + if (totalWeight < 1.00f && totalWeight > 0.01f) { + thisVertex.BoneWeights[0] /= totalWeight; + thisVertex.BoneWeights[1] /= totalWeight; + thisVertex.BoneWeights[2] /= totalWeight; + thisVertex.BoneWeights[3] /= totalWeight; + } + + std::vector::iterator it = std::find(vertexList.begin(), vertexList.end(), thisVertex); + array tmp; + if (it != vertexList.end()) { + tmp[0] = vertexIndex; + tmp[1] = it - vertexList.begin(); + localVertexToGlobalIndex.push_back(tmp); + } else { + tmp[0] = vertexIndex; + tmp[1] = vertexList.size(); + localVertexToGlobalIndex.push_back(tmp); + vertexList.push_back(thisVertex); + } + //MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1]: " + localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1][0] + " " + localVertexToGlobalIndex[localVertexToGlobalIndex.size()-1][1]); + //cout << "Pos: " << thisVertex.Pos[0] << "/" << thisVertex.Pos[1] << "/" << thisVertex.Pos[2] << endl; + //cout << "Normals: " << thisVertex.Normal[0] << "/" << thisVertex.Normal[1] << "/" << thisVertex.Normal[2] << endl; + //cout << "Bi-Normals: " << thisVertex.BiNormal[0] << "/" << thisVertex.BiNormal[1] << "/" << thisVertex.BiNormal[2] << endl; + //cout << "Bi-Tangents: " << thisVertex.BiTangent[0] << "/" << thisVertex.BiTangent[1] << "/" << thisVertex.BiTangent[2] << endl; + //cout << "UV: " << thisVertex.Uv[0] << "/" << thisVertex.Uv[1] << endl; + } + for (unsigned int i = 0; i < triangleList.length(); i++) { + unsigned int k = 0; + if (localVertexToGlobalIndex.size() > 0) { + //MGlobal::displayInfo(MString() + "triangleList[i] : " + triangleList[i]); + while (localVertexToGlobalIndex[k][0] != triangleList[i] && k < localVertexToGlobalIndex.size()) { + k++; + } + //MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k] : " + localVertexToGlobalIndex[k][0] + " " + localVertexToGlobalIndex[k][1]); + indexLists[aMaterial.first.c_str()].push_back(localVertexToGlobalIndex[k][1]); + } } - //MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k] : " + localVertexToGlobalIndex[k][0] + " " + localVertexToGlobalIndex[k][1]); - indexLists[aMaterial.first.c_str()].push_back(localVertexToGlobalIndex[k][1]); } + // MGlobal::displayInfo( MString() + "localVertexToGlobalIndex.size(): " + localVertexToGlobalIndex.size()); + // if (localVertexToGlobalIndex.size() > 0) { + // MGlobal::displayInfo(MString() + "triangleList.length(): " + triangleList.length()); + // for (unsigned int i = triangleList.length() - 1; i >= 0; i--) { + // MGlobal::displayInfo(MString() + "i: " + i); + // unsigned int k = localVertexToGlobalIndex.size() - 1; + // MGlobal::displayInfo(MString() + "triangleList[i] : " + triangleList[i]); + // while (localVertexToGlobalIndex[k] != triangleList[i] && k >= 0) { + // MGlobal::displayInfo(MString() + "k: " + k); + // k--; + // } + // MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k] : " + localVertexToGlobalIndex[k]); + // indexList.push_back(indexOffset + k); + // } + // } } } - // MGlobal::displayInfo( MString() + "localVertexToGlobalIndex.size(): " + localVertexToGlobalIndex.size()); - // if (localVertexToGlobalIndex.size() > 0) { - // MGlobal::displayInfo(MString() + "triangleList.length(): " + triangleList.length()); - // for (unsigned int i = triangleList.length() - 1; i >= 0; i--) { - // MGlobal::displayInfo(MString() + "i: " + i); - // unsigned int k = localVertexToGlobalIndex.size() - 1; - // MGlobal::displayInfo(MString() + "triangleList[i] : " + triangleList[i]); - // while (localVertexToGlobalIndex[k] != triangleList[i] && k >= 0) { - // MGlobal::displayInfo(MString() + "k: " + k); - // k--; - // } - // MGlobal::displayInfo(MString() + "localVertexToGlobalIndex[k] : " + localVertexToGlobalIndex[k]); - // indexList.push_back(indexOffset + k); - // } - // } } - - int totalIndecies = 0; + int totalIndices = 0; for (auto aList : newMesh.Indices) { - totalIndecies += aList.second.size(); + totalIndices += aList.second.size(); } - - newMesh.NumIndices = totalIndecies; + newMesh.NumIndices = totalIndices; newMesh.NumVertices = newMesh.Vertices.size(); return newMesh; diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h index 15c16913..0538e83c 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.h +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -69,8 +69,9 @@ public: for (auto aVertex : Vertices) { aVertex.WriteBinary(out); } - for (auto aIndex : Indices) { - out.write((char*)aIndex.second.data(), sizeof(int) * aIndex.second.size()); + //for (auto aIndex : Indices) { + for (std::map>::reverse_iterator aIndex = Indices.rbegin(); aIndex != Indices.rend(); aIndex++){ + out.write((char*)(*aIndex).second.data(), sizeof(int) * (*aIndex).second.size()); } } @@ -101,7 +102,7 @@ class MeshClass { public: MeshClass(); - Mesh GetMeshData(MObject Object); + Mesh GetMeshData(MObjectArray Object); ~MeshClass(); private: struct WeightInfo { From e64358197190bc148ec0b63cb7d3b7de4063791a Mon Sep 17 00:00:00 2001 From: antc13 Date: Tue, 19 Jan 2016 18:21:27 +0100 Subject: [PATCH 122/224] Commit in order to pull from Master. --- resources/Shaders/ForwardPlus.frag.glsl | 3 +-- src/Engine/Rendering/DrawFinalPassState.cpp | 2 +- src/Engine/Rendering/RawModelCustom.cpp | 4 +++- src/Engine/Rendering/Renderer.cpp | 8 ++++---- tools/MayaExporter/MayaExporter/Mesh.h | 7 ++++--- 5 files changed, 13 insertions(+), 11 deletions(-) diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 450d8929..b6d07ba2 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -113,7 +113,7 @@ void main() totalLighting.Specular += result.Specular; } - //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + fragmentColor += (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; //fragmentColor += vec4(0.0, LightGrids.Data[currentTile].Amount/3.0, 0, 1); //fragmentColor = texel * Input.DiffuseColor * Color; @@ -125,7 +125,6 @@ void main() } - fragmentColor = vec4(1.0f, 1.0f, 1.0f, 1.0f); } diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 5bafc294..1cb9d7da 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -7,7 +7,7 @@ DrawFinalPassState::DrawFinalPassState() Enable(GL_BLEND); BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); Enable(GL_DEPTH_TEST); - Disable(GL_CULL_FACE); //Should be enabled, fix it johan and andreas. + Enable(GL_CULL_FACE); ClearColor(glm::vec4(200.f / 255, 0.f / 255, 200.f / 255, 0.f)); Clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); } diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index a749e1fd..b7f2a2fd 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -148,7 +148,9 @@ void RawModel::ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned throw Resource::FailedLoadingException("Reading Material texture path failed"); } - newMaterial.TexturePath = (fileData + offset); + newMaterial.TexturePath = "Textures/"; + newMaterial.TexturePath += (fileData + offset); + newMaterial.TexturePath += ".png"; offset += nameLengths[0]; } diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index f86fea43..983b0736 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -101,10 +101,10 @@ void Renderer::Draw(RenderFrame& frame) m_Camera = scene->Camera; // remove renderer camera when Editor uses the render scene cameras. FillDepth(*scene); - //m_PickingPass->Draw(*scene); - //m_LightCullingPass->GenerateNewFrustum(*scene); - //m_LightCullingPass->FillLightList(*scene); - //m_LightCullingPass->CullLights(*scene); + m_PickingPass->Draw(*scene); + m_LightCullingPass->GenerateNewFrustum(*scene); + m_LightCullingPass->FillLightList(*scene); + m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); //m_DrawScenePass->Draw(rq); diff --git a/tools/MayaExporter/MayaExporter/Mesh.h b/tools/MayaExporter/MayaExporter/Mesh.h index 0538e83c..11f6bcf8 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.h +++ b/tools/MayaExporter/MayaExporter/Mesh.h @@ -69,9 +69,10 @@ public: for (auto aVertex : Vertices) { aVertex.WriteBinary(out); } - //for (auto aIndex : Indices) { - for (std::map>::reverse_iterator aIndex = Indices.rbegin(); aIndex != Indices.rend(); aIndex++){ - out.write((char*)(*aIndex).second.data(), sizeof(int) * (*aIndex).second.size()); + for (auto aIndex : Indices) { + //for (std::map>::reverse_iterator aIndex = Indices.rbegin(); aIndex != Indices.rend(); aIndex++){ + //out.write((char*)(*aIndex).second.data(), sizeof(int) * (*aIndex).second.size()); + out.write((char*)aIndex.second.data(), sizeof(int) * aIndex.second.size()); } } From 410e349329f6bb37c5fd36fc6ec2bf9c738cba44 Mon Sep 17 00:00:00 2001 From: William Moberg Date: Tue, 19 Jan 2016 18:27:58 +0100 Subject: [PATCH 123/224] Added test map for capture points and some debug code. --- resources/Schema/Entities/CapturePointTest | 29 ---- resources/Schema/Entities/CaptureTest.xml | 149 +++++++++++++++++++++ src/Game/Systems/CapturePointSystem.cpp | 12 +- 3 files changed, 160 insertions(+), 30 deletions(-) delete mode 100644 resources/Schema/Entities/CapturePointTest create mode 100644 resources/Schema/Entities/CaptureTest.xml diff --git a/resources/Schema/Entities/CapturePointTest b/resources/Schema/Entities/CapturePointTest deleted file mode 100644 index 669d5032..00000000 --- a/resources/Schema/Entities/CapturePointTest +++ /dev/null @@ -1,29 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/resources/Schema/Entities/CaptureTest.xml b/resources/Schema/Entities/CaptureTest.xml new file mode 100644 index 00000000..fef6c839 --- /dev/null +++ b/resources/Schema/Entities/CaptureTest.xml @@ -0,0 +1,149 @@ + + + + + + + + + + + + ../assets/Models/DummyScene.obj + + + + + + + + + 60 + + + + + + + 3 + + + + + + + + + + + + + + ../assets/Models/Core/UnitSphere.obj + + + + 3 + + + + + + + + + + + + + 1 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 2 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + diff --git a/src/Game/Systems/CapturePointSystem.cpp b/src/Game/Systems/CapturePointSystem.cpp index 4fd91690..af82e95a 100644 --- a/src/Game/Systems/CapturePointSystem.cpp +++ b/src/Game/Systems/CapturePointSystem.cpp @@ -60,7 +60,13 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co } int ownedBy = teamComponent["Team"]; - + //Probably want to distinguish the capturepoint depending on team affiliation. + if (entity.HasComponent("Model")) { + //Now sets team color to the capturepoint, or white if it is uncaptured. + entity["Model"]["Color"] = ownedBy == blueTeam ? glm::vec4(0, 0.2f, 1, 1) : + ownedBy == redTeam ? glm::vec4(1, 0.2f, 0, 1) : + glm::vec4(1, 1, 1, 1); + } //om ej next satt, förvänta sig att en capturepoint med en viss team färg kommer in... //sätt isåfall next och kör på.. //gör inget tills man fått den infon @@ -109,6 +115,9 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co //B. at most one of the teams have players inside (this means datavariable currentTeam is not 0) //if capturePoint is not owned by the take-over team, just modify the CaptureTimer accordingly if (ownedBy != currentTeam) { + if (abs((double)capturePoint["CaptureTimer"]) < 0.001f) { + LOG_DEBUG("Point is being captured by team %i", currentTeam); //Remove when we tested sufficiently. + } capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; } //if capturePoint is owned by the team, and the other team has been trying to take it, then increase/decrease the timer towards 0.0 @@ -121,6 +130,7 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co teamComponent["Team"] = currentTeam; capturePoint["CaptureTimer"] = 0.0; //publish Captured event + LOG_DEBUG("Point is captured by team %i!", currentTeam); //Remove when we tested sufficiently. Events::Captured e; e.CapturePointID = capturePoint.EntityID; e.TeamNumberThatCapturedCapturePoint = currentTeam; From 386e76f6422ad206be119af06c90b590f42bcc35 Mon Sep 17 00:00:00 2001 From: antc13 Date: Wed, 20 Jan 2016 09:49:54 +0100 Subject: [PATCH 124/224] Puyshing --- src/Engine/Editor/EditorSystem.cpp | 14 +++++++------- src/Engine/Network/Client.cpp | 2 +- src/Engine/Network/Server.cpp | 2 +- src/Engine/Rendering/RenderSystem.cpp | 4 ++-- src/Engine/Sound/SoundSystem.cpp | 2 +- src/Tests/CollisionTest.cpp | 10 +++++----- src/Tests/HealthSystemTest.cpp | 4 ++-- src/Tests/OctTreeTestGameClass.cpp | 2 +- src/Tests/OctTreeTestHardCodedTestWorld.h | 4 ++-- src/Tests/OldOctTree.cpp | 2 +- src/Tests/ResourceManagerTest.cpp | 2 +- 11 files changed, 24 insertions(+), 24 deletions(-) diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 2790ebbb..624c4ad6 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -292,21 +292,21 @@ void EditorSystem::createWidget() m_WidgetPlaneX = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneX, "Transform"); m_World->AttachComponent(m_WidgetPlaneX, "Model"); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube"; + m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube"; // 360NoScope widgetPlaneX m_WidgetY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetY, "Transform"); m_World->AttachComponent(m_WidgetY, "Model"); m_WidgetPlaneY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneY, "Transform"); m_World->AttachComponent(m_WidgetPlaneY, "Model"); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube"; + m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube"; // 360NoScope widgetPlaneY m_WidgetZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetZ, "Transform"); m_World->AttachComponent(m_WidgetZ, "Model"); m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); m_World->AttachComponent(m_WidgetPlaneZ, "Model"); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube"; + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube"; // 360NoScope widgetPlaneZ m_WidgetOrigin = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetOrigin, "Transform"); m_World->AttachComponent(m_WidgetOrigin, "Model"); @@ -351,7 +351,7 @@ void EditorSystem::setWidgetMode(WidgetMode newMode) m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = false; if (newMode == WidgetMode::Translate) { - //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; + //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; // 360NoScope TranslationWidgets mesh //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.obj"; //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.obj"; // Temporarily disabled for local space until I can figure out what's wrong with the math @@ -367,17 +367,17 @@ void EditorSystem::setWidgetMode(WidgetMode newMode) } } } else if (newMode == WidgetMode::Scale) { - //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; + //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; // 360NoScope ScaleWidgets mesh //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.obj"; //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.obj"; m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = true; - //m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; + //m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; // 360NoScope ScaleWidgetOrigin mesh if (m_Selection != EntityID_Invalid) { auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); } } else if (newMode == WidgetMode::Rotate) { - //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; + //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; // 360NoScope RotationWidget mesh //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.obj"; //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.obj"; if (m_Selection != EntityID_Invalid) { diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index b8849ed0..efd25120 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -331,7 +331,7 @@ EntityID Client::createPlayer() EntityID entityID = m_World->CreateEntity(); ComponentWrapper transform = m_World->AttachComponent(entityID, "Transform"); ComponentWrapper model = m_World->AttachComponent(entityID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; + model["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere mesh ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); return entityID; } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 07fed65b..367f444b 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -349,7 +349,7 @@ EntityID Server::createPlayer() ComponentWrapper transform = m_World->AttachComponent(entityID, "Transform"); transform["Position"] = glm::vec3(-1.5f, 0.f, 0.f); ComponentWrapper model = m_World->AttachComponent(entityID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; + model["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere model["Color"] = glm::vec4(rand()%255 / 255.f, rand()%255 / 255.f, rand() %255 / 255.f, 1.f); ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); return entityID; diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index d243afff..1b016f73 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -96,10 +96,10 @@ void RenderSystem::fillModels(std::list>& jobs, World model = ResourceManager::Load<::Model, true>(resource); } catch (const Resource::StillLoadingException&) { //continue; - model = ResourceManager::Load<::Model>("Models/coolCube"); + model = ResourceManager::Load<::Model>("Models/coolCube"); // 360NoScope StillLoading mesh } catch (const std::exception&) { try { - model = ResourceManager::Load<::Model>("Models/coolCube"); + model = ResourceManager::Load<::Model>("Models/coolCube"); // 360NoScope Error mesh } catch (const std::exception&) { continue; } diff --git a/src/Engine/Sound/SoundSystem.cpp b/src/Engine/Sound/SoundSystem.cpp index 1292e0b1..2494581d 100644 --- a/src/Engine/Sound/SoundSystem.cpp +++ b/src/Engine/Sound/SoundSystem.cpp @@ -198,7 +198,7 @@ bool SoundSystem::OnPlaySoundOnPosition(const Events::PlaySoundOnPosition & e) (float&)(double)emitter["RollOffFactor"] = e.RollOffFactor; (float&)(double)emitter["ReferenceDistance"] = e.ReferenceDistance; auto model = m_World->AttachComponent(emitterID, "Model"); - (std::string&)model["Resource"] = "Models/Core/UnitCube.obj"; + (std::string&)model["Resource"] = "Models/Core/UnitCube.obj"; // 360NoScope UnitCube source->Type = SoundType::SFX; m_Sources[emitterID] = source; playSound(source); diff --git a/src/Tests/CollisionTest.cpp b/src/Tests/CollisionTest.cpp index 9f400330..4ba7ca87 100644 --- a/src/Tests/CollisionTest.cpp +++ b/src/Tests/CollisionTest.cpp @@ -106,7 +106,7 @@ BOOST_AUTO_TEST_CASE(collisionTest2) BOOST_AUTO_TEST_CASE(rayVsModelTest) { //simple box test - RayTest("Models/Core/UnitCube.obj"); + RayTest("Models/Core/UnitCube.obj"); // 360NoScope Unitcube } BOOST_AUTO_TEST_CASE(rayVsModelTest2) @@ -128,7 +128,7 @@ BOOST_AUTO_TEST_CASE(rayVsModelTest2) someAABB = AABB(minPos, maxPos); //using a rawmodel here, else we have to init the renderingsystem ResourceManager::RegisterType("RawModel"); - auto unitBox = ResourceManager::Load("Models/Core/UnitCube.obj"); + auto unitBox = ResourceManager::Load("Models/Core/UnitCube.obj"); // 360NoScope unitcube BOOST_CHECK(unitBox != nullptr); for (size_t i = 0; i < 1000000; i++) @@ -187,19 +187,19 @@ BOOST_AUTO_TEST_CASE(rayVsModelTest2) BOOST_AUTO_TEST_CASE(rayVsModelTest3) { //simple test - RayTest("Models/Core/UnitSphere.obj"); + RayTest("Models/Core/UnitSphere.obj"); // 360NoScope unitSphere } BOOST_AUTO_TEST_CASE(rayVsModelTest4) { //simple test - RayTest("Models/Core/UnitCylinder.obj"); + RayTest("Models/Core/UnitCylinder.obj"); // 360NoScope unitCylinder } BOOST_AUTO_TEST_CASE(rayVsModelTest5) { //simple test - RayTest("Models/Core/UnitRaptor.obj"); + RayTest("Models/Core/UnitRaptor.obj"); // 360NoScope unitRaptor } BOOST_AUTO_TEST_CASE(octTest) { diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index 84d6199d..7c3ad641 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -55,7 +55,7 @@ GameHealthSystemTest::GameHealthSystemTest() EntityID playerID = m_World->CreateEntity(); ComponentWrapper transform = m_World->AttachComponent(playerID, "Transform"); ComponentWrapper model = m_World->AttachComponent(playerID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; + model["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere ComponentWrapper player = m_World->AttachComponent(playerID, "Player"); ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); healthsID = playerID; @@ -80,7 +80,7 @@ GameHealthSystemTest::GameHealthSystemTest() EntityID playerID2 = m_World->CreateEntity(); ComponentWrapper transform2 = m_World->AttachComponent(playerID2, "Transform"); ComponentWrapper model2 = m_World->AttachComponent(playerID2, "Model"); - model2["Resource"] = "Models/Core/UnitSphere.obj"; + model2["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere ComponentWrapper player2 = m_World->AttachComponent(playerID2, "Player"); ComponentWrapper health2 = m_World->AttachComponent(playerID2, "Health"); //END TEST diff --git a/src/Tests/OctTreeTestGameClass.cpp b/src/Tests/OctTreeTestGameClass.cpp index 2c45d897..d03153e7 100644 --- a/src/Tests/OctTreeTestGameClass.cpp +++ b/src/Tests/OctTreeTestGameClass.cpp @@ -149,7 +149,7 @@ void Game::Tick() ComponentWrapper transform = m_World->AttachComponent(m_BoxID, "Transform"); transform["Scale"] = boxSize; ComponentWrapper model = m_World->AttachComponent(m_BoxID, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; + model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope UnitBox m_World->createTestEntitiesTest2(); } diff --git a/src/Tests/OctTreeTestHardCodedTestWorld.h b/src/Tests/OctTreeTestHardCodedTestWorld.h index db0b3b3c..89c3c3f3 100644 --- a/src/Tests/OctTreeTestHardCodedTestWorld.h +++ b/src/Tests/OctTreeTestHardCodedTestWorld.h @@ -112,7 +112,7 @@ private: ComponentWrapper transform = world.AttachComponent(entityCollisionBox, "Transform"); transform["Position"] = glm::vec3(0.f, 2.f, 0.f); ComponentWrapper model = world.AttachComponent(entityCollisionBox, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; + model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope UnitBox } void AddBoxModel(const glm::vec3 ¢er, const float &halfSize, Octree::Child* child, EntityID &outEntityId) { @@ -124,7 +124,7 @@ private: transform["Position"] = center; transform["Scale"] = glm::vec3(1.0f, 1.0f, 1.0f)*halfSize*2.0f*0.97f; ComponentWrapper model = world.AttachComponent(entityDummyScene, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; + model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope unitBox model["Color"] = glm::vec4(0.0f, 0.0f, 0.0f, 1.0f); if (child->m_DynamicObjIndices.size() != 0) model["Color"] = glm::vec4(1.0f, 1.0f, 1.0f, 1.0f); diff --git a/src/Tests/OldOctTree.cpp b/src/Tests/OldOctTree.cpp index 0fb92e18..a94bf465 100644 --- a/src/Tests/OldOctTree.cpp +++ b/src/Tests/OldOctTree.cpp @@ -112,7 +112,7 @@ void OctTree::Update(float dt, World* world, Camera* cam) ComponentWrapper transform = world->AttachComponent(m_BoxID, "Transform"); transform["Scale"] = boxSize; ComponentWrapper model = world->AttachComponent(m_BoxID, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; + model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope UnitBox m_UpdatedOnce = true; } diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index 9d62fa93..f83c6c9f 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -26,7 +26,7 @@ BOOST_AUTO_TEST_CASE(resourceManagerTest) //configfile without register //check so output says "EE failed to load: type not registered..." - auto m_ScreenQuadNoRegister = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + auto m_ScreenQuadNoRegister = ResourceManager::Load("Models/Core/ScreenQuad.obj"); // 360NoScope ScreenQuad BOOST_CHECK(!ResourceManager::IsResourceLoaded("Model", "Models/Core/ScreenQuad.obj")); //there is no error feedback to check if you try to release the wrong resources - hence that cant be tested either From 84b7cf165c449d9ec48d8882c519545a42112bd2 Mon Sep 17 00:00:00 2001 From: antc13 Date: Wed, 20 Jan 2016 11:46:32 +0100 Subject: [PATCH 125/224] Reduced the chance of crashing in Export. --- tools/MayaExporter/MayaExporter/Mesh.cpp | 154 ++++++++++++++++++----- 1 file changed, 125 insertions(+), 29 deletions(-) diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index 0f99533c..2062bad5 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -10,22 +10,43 @@ MeshClass::MeshClass() std::map MeshClass::GetWeightData() { + MS status; map weightMap; MItDependencyNodes it(MFn::kSkinClusterFilter); while (!it.isDone()) { - MObject object = it.item(); - MFnSkinCluster skinCluster(object); + MObject object = it.thisNode(&status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + " it.thisNode() ERROR: " + status.errorString()); + break; + } + MFnSkinCluster skinCluster(object, &status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "skinCluster() ERROR: " + status.errorString()); + break; + } MDagPathArray influences; - unsigned int nrOfInfluences = skinCluster.influenceObjects(influences); + unsigned int nrOfInfluences = skinCluster.influenceObjects(influences,&status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "skinCluster.influenceObjects() ERROR: " + status.errorString()); + break; + } unsigned int index; - index = skinCluster.indexForOutputConnection(0); + index = skinCluster.indexForOutputConnection(0,&status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "skinCluster.indexForOutputConnection() ERROR: " + status.errorString()); + break; + } MDagPath skinPath; - skinCluster.getPathAtIndex(index, skinPath); + status = skinCluster.getPathAtIndex(index, skinPath); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "skinCluster.getPathAtIndex() ERROR: " + status.errorString()); + break; + } MItGeometry geomIter(skinPath); //for (unsigned int i = 0; i < nrOfInfluences; i++) { @@ -34,10 +55,18 @@ std::map MeshClass::GetWeightData() WeightInfo weightInfo; while (!geomIter.isDone()) { - MObject comp = geomIter.component(); + MObject comp = geomIter.component(&status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "geomIter.component() ERROR: " + status.errorString()); + break; + } MFloatArray weights; unsigned int influenceCount; - skinCluster.getWeights(skinPath, comp, weights, influenceCount); + status = skinCluster.getWeights(skinPath, comp, weights, influenceCount); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "skinCluster.getWeights() ERROR: " + status.errorString()); + break; + } MFnDependencyNode test(comp); unsigned int nrOfWeights = 0; @@ -64,10 +93,7 @@ std::map MeshClass::GetWeightData() //MGlobal::displayInfo(MString() + "influence: " + weightInfo.BoneIndices[k] + " weight: " + weightInfo.BoneWeights[k]); } geomIter.next(); - - } - it.next(); } return weightMap; @@ -75,6 +101,7 @@ std::map MeshClass::GetWeightData() Mesh MeshClass::GetMeshData(MObjectArray object) { + MS status; Mesh newMesh; vector& vertexList = newMesh.Vertices; map>& indexLists = newMesh.Indices; @@ -85,11 +112,21 @@ Mesh MeshClass::GetMeshData(MObjectArray object) // In here, we retrieve triangulated polygons from the mesh MFnMesh mesh(object[ObjectID]); MDagPathArray dagPaths; - MDagPath::getAllPathsTo(object[ObjectID], dagPaths); + status = MDagPath::getAllPathsTo(object[ObjectID], dagPaths); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "MDagPath::getAllPathsTo() ERROR: " + status.errorString()); + break; + } + for (int pathID = 0; pathID < dagPaths.length(); pathID++) { MGlobal::displayInfo(dagPaths[pathID].fullPathName()); MDagPath thisMeshPath(dagPaths[pathID]); - MMatrix transformMatrix = thisMeshPath.inclusiveMatrix(); + + MMatrix transformMatrix = thisMeshPath.inclusiveMatrix(&status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "thisMeshPath.inclusiveMatrix() ERROR: " + status.errorString() + " for " + thisMeshPath.fullPathName()); + break; + } map> vertexToIndex;; @@ -106,28 +143,57 @@ Mesh MeshClass::GetMeshData(MObjectArray object) MObjectArray shaderList; MIntArray shaderIndexList; - mesh.getConnectedShaders(0, shaderList, shaderIndexList); + status = mesh.getConnectedShaders(0, shaderList, shaderIndexList); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "mesh.getConnectedShaders() ERROR: " + status.errorString() + " for " + thisMeshPath.fullPathName()); + break; + } + if (shaderList.length() == 0) { + MGlobal::displayError(MString() + "Object: \"" + thisMeshPath.fullPathName() + "\" have no material and will not be exported"); + break; + } map> materialFaceIDs; MGlobal::displayInfo(MString() + "shaderIndexList: " + shaderIndexList.length()); MGlobal::displayInfo(MString() + "shaderList: " + shaderList.length()); MPlugArray plugArray; for (int i = 0; i < shaderIndexList.length(); i++) { MFnDependencyNode shader(shaderList[shaderIndexList[i]]); - MPlug p_Plug = shader.findPlug("surfaceShader"); - if (p_Plug.connectedTo(plugArray, true, false)) { + MPlug p_Plug = shader.findPlug("surfaceShader", status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "shader.findPlug(\"surfaceShader\") ERROR: " + status.errorString() + " for " + thisMeshPath.fullPathName()); + continue; + } + if (p_Plug.connectedTo(plugArray, true, false, &status)) { + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "p_Plug.connectedTo() ERROR in if: " + status.errorString() + " for " + thisMeshPath.fullPathName()); + continue; + } MFnDependencyNode node = plugArray[0].node(); materialFaceIDs[node.name().asChar()].push_back(i); } + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "p_Plug.connectedTo() ERROR: " + status.errorString() + " for " + thisMeshPath.fullPathName()); + continue; + } } map vertexWeights = GetWeightData(); - - mesh.getTangents(Tangents, MSpace::kTransform, NULL); - mesh.getBinormals(biNormals, MSpace::kTransform, NULL); - + status = mesh.getTangents(Tangents, MSpace::kObject); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "mesh.getTangents ERROR: " + status.errorString() + " for " + thisMeshPath.fullPathName()); + continue; + } + status = mesh.getBinormals(biNormals, MSpace::kObject); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "mesh.getBinormals ERROR: " + status.errorString() + " for " + thisMeshPath.fullPathName()); + continue; + } + if(Tangents.length() == 0 || biNormals.length() == 0){ + MGlobal::displayError(MString() + "Unknown ERROR with " + thisMeshPath.fullPathName()); + continue; + } MItMeshFaceVertex faceVert(object[ObjectID]); - int intDummy = 0; MItMeshPolygon meshPolyIter(object[ObjectID]); @@ -137,17 +203,40 @@ Mesh MeshClass::GetMeshData(MObjectArray object) for (auto aMaterial : materialFaceIDs) { for (auto faceID : aMaterial.second) { - vector> localVertexToGlobalIndex; - meshPolyIter.setIndex(faceID, intDummy); - meshPolyIter.getVertices(vertices); - meshPolyIter.getTriangles(dummy, triangleList); + status = meshPolyIter.setIndex(faceID, intDummy); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + " meshPolyIter.setIndex() ERROR: " + status.errorString() + " for faceID " + faceID + " in mesh " + thisMeshPath.fullPathName()); + break; + } + + status = meshPolyIter.getVertices(vertices); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + " meshPolyIter.getVertices() ERROR: " + status.errorString() + " for faceID " + faceID + " in mesh " + thisMeshPath.fullPathName()); + break; + } + + status = meshPolyIter.getTriangles(dummy, triangleList); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + " meshPolyIter.getTriangles() ERROR: " + status.errorString() + " for faceID " + faceID + " in mesh " + thisMeshPath.fullPathName()); + break; + } //MGlobal::displayInfo("Befor Second Loop"); for (unsigned int i = 0; i < vertices.length(); i++) { VertexLayout thisVertex; - vertexIndex = meshPolyIter.vertexIndex(i); - faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); + + vertexIndex = meshPolyIter.vertexIndex(i, &status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + " meshPolyIter.vertexIndex() ERROR: " + status.errorString() + "for local vertex " + i + " in " + faceID + " in mesh " + thisMeshPath.fullPathName()); + break; + } + + status = faceVert.setIndex(meshPolyIter.index(), i, intDummy, intDummy); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "faceVert.setIndex() ERROR: " + status.errorString() + "for local vertex " + i + " in " + faceID + " in mesh " + thisMeshPath.fullPathName()); + break; + } //MGlobal::displayInfo("In Second Loop"); //pos = faceVert.position(MSpace::kTransform); //mesh.getPoint(vertexIndex, pos, MSpace::kPostTransform); @@ -160,7 +249,11 @@ Mesh MeshClass::GetMeshData(MObjectArray object) if (abs(pos.z) > 0.0001) thisVertex.Pos[2] = pos.z; - faceVert.getNormal(normal, MSpace::kTransform); + status = faceVert.getNormal(normal, MSpace::kObject); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "faceVert.getNormal() ERROR: " + status.errorString() + "for local vertex " + i + " in " + faceID + " in mesh " + thisMeshPath.fullPathName()); + break; + } if (abs(normal[0]) > 0.0001) thisVertex.Normal[0] = normal[0]; if (abs(normal[1]) > 0.0001) @@ -187,7 +280,11 @@ Mesh MeshClass::GetMeshData(MObjectArray object) if (abs(biNormal[2]) > 0.0001) thisVertex.BiNormal[2] = biNormal[2]; - faceVert.getUV(UV); + status = faceVert.getUV(UV); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + " faceVert.getUV() ERROR: " + status.errorString() + "for local vertex " + i + " in " + faceID + " in mesh " + thisMeshPath.fullPathName()); + break; + } thisVertex.Uv[0] = UV[0]; thisVertex.Uv[1] = UV[1]; @@ -195,7 +292,6 @@ Mesh MeshClass::GetMeshData(MObjectArray object) thisVertex.BoneIndices[1] = vertexWeights[faceVert.vertId()].BoneIndices[1]; thisVertex.BoneIndices[2] = vertexWeights[faceVert.vertId()].BoneIndices[2]; thisVertex.BoneIndices[3] = vertexWeights[faceVert.vertId()].BoneIndices[3]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[0]) > 0.0001) thisVertex.BoneWeights[0] = vertexWeights[faceVert.vertId()].BoneWeights[0]; if (abs(vertexWeights[faceVert.vertId()].BoneWeights[1]) > 0.0001) From 78a10379833104d9423ddc226171602dcf09fec8 Mon Sep 17 00:00:00 2001 From: Tleety Date: Wed, 20 Jan 2016 13:34:56 +0100 Subject: [PATCH 126/224] WIP DrawScreenQuad implemented and working. Started work on HDR coloring. --- include/Engine/Rendering/DrawBloomEffect.h | 38 +++++++++++ include/Engine/Rendering/DrawFinalPass.h | 9 +-- include/Engine/Rendering/DrawScreenQuadPass.h | 28 ++++++++ .../Rendering/DrawScreenQuadPassState.h | 15 +++++ include/Engine/Rendering/Renderer.h | 7 +- resources/Shaders/ForwardPlus.frag.glsl | 30 ++++++--- src/Engine/Rendering/DrawBloomEffect.cpp | 66 +++++++++++++++++++ src/Engine/Rendering/DrawFinalPass.cpp | 30 +++++++++ src/Engine/Rendering/DrawFinalPassState.cpp | 2 +- src/Engine/Rendering/DrawScreenQuadPass.cpp | 36 ++++++++++ .../Rendering/DrawScreenQuadPassState.cpp | 20 ++++++ src/Engine/Rendering/FrameBuffer.cpp | 3 +- src/Engine/Rendering/PickingPass.cpp | 5 -- src/Engine/Rendering/Renderer.cpp | 30 +-------- 14 files changed, 269 insertions(+), 50 deletions(-) create mode 100644 include/Engine/Rendering/DrawBloomEffect.h create mode 100644 include/Engine/Rendering/DrawScreenQuadPass.h create mode 100644 include/Engine/Rendering/DrawScreenQuadPassState.h create mode 100644 src/Engine/Rendering/DrawBloomEffect.cpp create mode 100644 src/Engine/Rendering/DrawScreenQuadPass.cpp create mode 100644 src/Engine/Rendering/DrawScreenQuadPassState.cpp diff --git a/include/Engine/Rendering/DrawBloomEffect.h b/include/Engine/Rendering/DrawBloomEffect.h new file mode 100644 index 00000000..52876592 --- /dev/null +++ b/include/Engine/Rendering/DrawBloomEffect.h @@ -0,0 +1,38 @@ +#ifndef DrawFinalPass_h__ +#define DrawFinalPass_h__ + +#include "IRenderer.h" +#include "DrawFinalPassState.h" +#include "LightCullingPass.h" +#include "FrameBuffer.h" +#include "ShaderProgram.h" +#include "Util/UnorderedMapVec2.h" +#include "Texture.h" + +class DrawFinalPass +{ +public: + DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCullingPass); + ~DrawFinalPass() { } + void InitializeTextures(); + void InitializeFrameBuffers(); + void InitializeShaderPrograms(); + + void Draw(RenderScene& scene); + + //Getters + + +private: + void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; + + Texture* m_WhiteTexture; + + const IRenderer* m_Renderer; + const LightCullingPass* m_LightCullingPass; + + ShaderProgram* m_ForwardPlusProgram; + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index 52876592..407ad58c 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -17,11 +17,13 @@ public: void InitializeTextures(); void InitializeFrameBuffers(); void InitializeShaderPrograms(); - void Draw(RenderScene& scene); - //Getters - + //Todo: Should not be public + FrameBuffer m_BloomFrameBuffer; + GLuint m_BloomTexture; + GLuint m_SceneTexture; + GLuint m_DepthBuffer; private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; @@ -32,7 +34,6 @@ private: const LightCullingPass* m_LightCullingPass; ShaderProgram* m_ForwardPlusProgram; - }; #endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawScreenQuadPass.h b/include/Engine/Rendering/DrawScreenQuadPass.h new file mode 100644 index 00000000..117e9e1e --- /dev/null +++ b/include/Engine/Rendering/DrawScreenQuadPass.h @@ -0,0 +1,28 @@ +#ifndef DrawScreenQuadPass_h__ +#define DrawScreenQuadPass_h__ + +#include "IRenderer.h" +#include "DrawScreenQuadPassState.h" +#include "FrameBuffer.h" +#include "ShaderProgram.h" +//#include "Util/UnorderedMapVec2.h" +#include "Texture.h" + +class DrawScreenQuadPass +{ +public: + DrawScreenQuadPass(IRenderer* renderer); + ~DrawScreenQuadPass() { } + void InitializeFrameBuffers(); + void InitializeShaderPrograms(); + + void Draw(GLuint texture); +private: + const IRenderer* m_Renderer; + + ShaderProgram* m_DrawQuadProgram; + + Model* m_ScreenQuad; +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawScreenQuadPassState.h b/include/Engine/Rendering/DrawScreenQuadPassState.h new file mode 100644 index 00000000..63ab4729 --- /dev/null +++ b/include/Engine/Rendering/DrawScreenQuadPassState.h @@ -0,0 +1,15 @@ +#ifndef DrawScreenQuadPassState_h__ +#define DrawScreenQuadPassState_h__ + +#include "Rendering/RenderState.h" + +class DrawScreenQuadPassState : public RenderState +{ +public: + DrawScreenQuadPassState(); + ~DrawScreenQuadPassState(); +private: + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 0006cca1..7dcf7e6a 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -14,6 +14,7 @@ #include "DrawScenePass.h" #include "LightCullingPass.h" #include "DrawFinalPass.h" +#include "DrawScreenQuadPass.h" #include "../Core/EventBroker.h" #include "ImGuiRenderPass.h" #include "Camera.h" @@ -48,6 +49,7 @@ private: LightCullingPass* m_LightCullingPass; ImGuiRenderPass* m_ImGuiRenderPass; DrawFinalPass* m_DrawFinalPass; + DrawScreenQuadPass* m_DrawScreenQuadPass; //----------------------Functions----------------------// void InitializeWindow(); @@ -57,14 +59,13 @@ private: //TODO: Renderer: Get InputUpdate out of renderer void InputUpdate(double dt); //void PickingPass(RenderQueueCollection& rq); - void DrawScreenQuad(GLuint textureToDraw); + //void DrawScreenQuad(GLuint textureToDraw); static bool DepthSort(const std::shared_ptr &i, const std::shared_ptr &j) { return (i->Depth < j->Depth); } void SortRenderJobsByDepth(RenderScene &scene); void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type); //--------------------ShaderPrograms-------------------// - ShaderProgram* m_BasicForwardProgram; - ShaderProgram* m_DrawScreenQuadProgram; + ShaderProgram* m_BasicForwardProgram; }; #endif \ No newline at end of file diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 78a2125e..6a810036 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -48,7 +48,8 @@ in VertexData{ vec4 DiffuseColor; }Input; -out vec4 fragmentColor; +out vec4 sceneColor; +out vec4 bloomColor; vec4 scene_ambient = vec4(0.3,0.3,0.3,1); @@ -121,6 +122,7 @@ void main() LightSource light = LightSources.List[l]; LightResult result; + //These if statements should be removed. if(light.Type == 1) { // point result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); } else if (light.Type == 2) { //Directional @@ -131,19 +133,29 @@ void main() } - //fragmentColor += Input.DiffuseColor; - fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; - //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; - //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); - //fragmentColor = texel * Input.DiffuseColor * Color; - //fragmentColor += vec4(currentTile/3600.f, 0, 0, 1); + //sceneColor += Input.DiffuseColor; + vec4 fragment = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + bloomColor = vec4(0.3, 0.8, 0.6, 1.0); + sceneColor = vec4(fragment.xyz, 1.0); + //These if statements should be removed. +/* + if(fragment.x > 0.5 || fragment.y > 0.5 || fragment.z > 0.5) { + bloomColor = fragment; + } else { + bloomColor = vec4(0.3, 0.5, 0.8, 1.0); + }*/ + + //sceneColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; + //sceneColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); + //sceneColor = texel * Input.DiffuseColor * Color; + //sceneColor += vec4(currentTile/3600.f, 0, 0, 1); //Tiled Debug Code /* if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { - fragmentColor += vec4(0.5, 0, 0, 0); + sceneColor += vec4(0.5, 0, 0, 0); } else { - fragmentColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/LightSources.List.length(), 0, 0, 1); + sceneColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/LightSources.List.length(), 0, 0, 1); } */ } diff --git a/src/Engine/Rendering/DrawBloomEffect.cpp b/src/Engine/Rendering/DrawBloomEffect.cpp new file mode 100644 index 00000000..b0ca4afe --- /dev/null +++ b/src/Engine/Rendering/DrawBloomEffect.cpp @@ -0,0 +1,66 @@ +#include "Rendering/DrawFinalPass.h" + +DrawFinalPass::DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCullingPass) +{ + m_Renderer = renderer; + m_LightCullingPass = lightCullingPass; + InitializeTextures(); + InitializeShaderPrograms(); +} + +void DrawFinalPass::InitializeTextures() +{ + m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); +} + +void DrawFinalPass::InitializeShaderPrograms() +{ + m_ForwardPlusProgram = ResourceManager::Load("#ForwardPlusProgram"); + m_ForwardPlusProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/ForwardPlus.vert.glsl"))); + m_ForwardPlusProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/ForwardPlus.frag.glsl"))); + m_ForwardPlusProgram->Compile(); + m_ForwardPlusProgram->Link(); +} + +void DrawFinalPass::Draw(RenderScene& scene) +{ + GLERROR("DrawFinalPass::Draw: Pre"); + + DrawFinalPassState state; + m_ForwardPlusProgram->Bind(); + GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); + + glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 1, m_LightCullingPass->LightSSBO()); + glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 2, m_LightCullingPass->LightGridSSBO()); + glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 4, m_LightCullingPass->LightIndexSSBO()); + + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ViewMatrix())); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ProjectionMatrix())); + glUniform2f(glGetUniformLocation(shaderHandle, "ScreenDimensions"), m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); + + //TODO: Render: Add code for more jobs than modeljobs. + for (auto &job : scene.ForwardJobs) { + auto modelJob = std::dynamic_pointer_cast(job); + if(modelJob) { + //TODO: Kolla upp "header/include/common" shader saken så man slipper skicka in asmycket uniforms + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); + glUniform4fv(glGetUniformLocation(shaderHandle, "Color"), 1, glm::value_ptr(modelJob->Color)); + + if(modelJob->DiffuseTexture != nullptr) { + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, modelJob->DiffuseTexture->m_Texture); + } else { + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); + } + + glBindVertexArray(modelJob->Model->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, 0, modelJob->StartIndex); + + continue; + } + } + GLERROR("DrawFinalPass::Draw: END"); + +} diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index b0ca4afe..57940971 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -6,6 +6,7 @@ DrawFinalPass::DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCulling m_LightCullingPass = lightCullingPass; InitializeTextures(); InitializeShaderPrograms(); + InitializeFrameBuffers(); } void DrawFinalPass::InitializeTextures() @@ -13,6 +14,21 @@ void DrawFinalPass::InitializeTextures() m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); } +void DrawFinalPass::InitializeFrameBuffers() +{ + glGenRenderbuffers(1, &m_DepthBuffer); + glBindRenderbuffer(GL_RENDERBUFFER, m_DepthBuffer); + glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); + + GenerateTexture(&m_SceneTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + + m_BloomFrameBuffer.AddResource(std::shared_ptr(new RenderBuffer(&m_DepthBuffer, GL_DEPTH_ATTACHMENT))); + m_BloomFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); + m_BloomFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_BloomTexture, GL_COLOR_ATTACHMENT1))); + m_BloomFrameBuffer.Generate(); +} + void DrawFinalPass::InitializeShaderPrograms() { m_ForwardPlusProgram = ResourceManager::Load("#ForwardPlusProgram"); @@ -26,6 +42,8 @@ void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); + m_BloomFrameBuffer.Bind(); //in i state + DrawFinalPassState state; m_ForwardPlusProgram->Bind(); GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); @@ -64,3 +82,15 @@ void DrawFinalPass::Draw(RenderScene& scene) GLERROR("DrawFinalPass::Draw: END"); } + +void DrawFinalPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const +{ + glGenTextures(1, texture); + glBindTexture(GL_TEXTURE_2D, *texture); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filtering); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filtering); + glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, dimensions.x, dimensions.y, 0, format, type, nullptr);//TODO: Renderer: Fix the precision and Resolution + GLERROR("Texture initialization failed"); +} diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 1cb9d7da..5b4bbf3b 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -3,7 +3,7 @@ DrawFinalPassState::DrawFinalPassState() { - BindFramebuffer(0); + //BindFramebuffer(0); Enable(GL_BLEND); BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); Enable(GL_DEPTH_TEST); diff --git a/src/Engine/Rendering/DrawScreenQuadPass.cpp b/src/Engine/Rendering/DrawScreenQuadPass.cpp new file mode 100644 index 00000000..4095db04 --- /dev/null +++ b/src/Engine/Rendering/DrawScreenQuadPass.cpp @@ -0,0 +1,36 @@ +#include "Rendering/DrawScreenQuadPass.h" + +DrawScreenQuadPass::DrawScreenQuadPass(IRenderer* renderer) +{ + m_Renderer = renderer; + + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + + InitializeShaderPrograms(); +} + +void DrawScreenQuadPass::InitializeShaderPrograms() +{ + m_DrawQuadProgram = ResourceManager::Load("#DrawScreenQuadProgram"); + m_DrawQuadProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawScreenQuad.vert.glsl"))); + m_DrawQuadProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawScreenQuad.frag.glsl"))); + m_DrawQuadProgram->Compile(); + m_DrawQuadProgram->Link(); +} + +void DrawScreenQuadPass::Draw(GLuint texture) +{ + //glBindFramebuffer(GL_FRAMEBUFFER, 0); + GLERROR("DrawScreenQuadPass::Draw: Pre"); + + DrawScreenQuadPassState state = DrawScreenQuadPassState(); + m_DrawQuadProgram->Bind(); + + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, texture); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); +} diff --git a/src/Engine/Rendering/DrawScreenQuadPassState.cpp b/src/Engine/Rendering/DrawScreenQuadPassState.cpp new file mode 100644 index 00000000..1ee5d9a7 --- /dev/null +++ b/src/Engine/Rendering/DrawScreenQuadPassState.cpp @@ -0,0 +1,20 @@ +#include "Rendering/DrawScreenQuadPassState.h" + + +DrawScreenQuadPassState::DrawScreenQuadPassState() +{ + GLERROR("---"); + BindFramebuffer(0); + GLERROR("---"); + Disable(GL_DEPTH_TEST); + Disable(GL_CULL_FACE); + Disable(GL_BLEND); + glClearColor(0.f, 0.f, 0.f, 1.f); + // ClearColor(glm::vec4(255.f / 255, 163.f / 255, 176.f / 255, 0.f)); + Clear(GL_COLOR_BUFFER_BIT); +} + +DrawScreenQuadPassState::~DrawScreenQuadPassState() +{ + +} diff --git a/src/Engine/Rendering/FrameBuffer.cpp b/src/Engine/Rendering/FrameBuffer.cpp index b2b29626..79507875 100644 --- a/src/Engine/Rendering/FrameBuffer.cpp +++ b/src/Engine/Rendering/FrameBuffer.cpp @@ -55,8 +55,9 @@ void FrameBuffer::Generate() glFramebufferRenderbuffer(GL_FRAMEBUFFER, (*it)->m_Attachment, (*it)->m_ResourceType, *(*it)->m_ResourceHandle); GLERROR("FrameBuffer generate: glFramebufferRenderbuffer"); if ( (*it)->m_Attachment != GL_COLOR_ATTACHMENT0 || + (*it)->m_Attachment != GL_COLOR_ATTACHMENT1 || (*it)->m_Attachment != GL_DEPTH_ATTACHMENT || - (*it)->m_Attachment != GL_STENCIL_ATTACHMENT) + (*it)->m_Attachment != GL_STENCIL_ATTACHMENT) //TODO: Viktor: Fixa detta { LOG_ERROR("RenderBuffer Attachment not valid."); } diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 6800df1d..a377fcec 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -46,15 +46,12 @@ void PickingPass::InitializeShaderPrograms() void PickingPass::Draw(RenderScene& scene) { PickingPassState* state = new PickingPassState(m_PickingBuffer.GetHandle()); - //TODO: Render: Add code for more jobs than modeljobs. GLuint ShaderHandle = m_PickingProgram->GetHandle(); m_PickingProgram->Bind(); - - m_Camera = scene.Camera; for (auto &job : scene.ForwardJobs) { @@ -95,11 +92,9 @@ void PickingPass::Draw(RenderScene& scene) } } - m_PickingBuffer.Unbind(); GLERROR("PickingPass Error"); - delete state; } diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 8c30adfd..f08bfafd 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -69,12 +69,6 @@ void Renderer::InitializeWindow() void Renderer::InitializeShaders() { m_BasicForwardProgram = ResourceManager::Load("#m_BasicForwardProgram"); - - m_DrawScreenQuadProgram = ResourceManager::Load("#DrawScreenQuadProgram"); - m_DrawScreenQuadProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawScreenQuad.vert.glsl"))); - m_DrawScreenQuadProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawScreenQuad.frag.glsl"))); - m_DrawScreenQuadProgram->Compile(); - m_DrawScreenQuadProgram->Link(); } void Renderer::InputUpdate(double dt) @@ -105,6 +99,8 @@ void Renderer::Draw(RenderFrame& frame) m_LightCullingPass->FillLightList(*scene); m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); + m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_SceneTexture); + //m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_BloomTexture); //m_DrawScenePass->Draw(rq); GLERROR("Renderer::Draw m_DrawScenePass->Draw"); @@ -119,27 +115,6 @@ PickData Renderer::Pick(glm::vec2 screenCoord) return m_PickingPass->Pick(screenCoord); } -void Renderer::DrawScreenQuad(GLuint textureToDraw) -{ - glBindFramebuffer(GL_FRAMEBUFFER, 0); - - glDisable(GL_DEPTH_TEST); - glDisable(GL_CULL_FACE); - - glClearColor(0.f, 0.f, 0.f, 1.f); - glClear(GL_COLOR_BUFFER_BIT); - - - m_DrawScreenQuadProgram->Bind(); - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, textureToDraw); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); -} - void Renderer::InitializeTextures() { m_ErrorTexture = ResourceManager::Load("Textures/Core/ErrorTexture.png"); @@ -171,4 +146,5 @@ void Renderer::InitializeRenderPasses() m_PickingPass = new PickingPass(this, m_EventBroker); m_LightCullingPass = new LightCullingPass(this); m_DrawFinalPass = new DrawFinalPass(this, m_LightCullingPass); + m_DrawScreenQuadPass = new DrawScreenQuadPass(this); } \ No newline at end of file From f52cddb44592d64dabfa0133efbebb777f5594e9 Mon Sep 17 00:00:00 2001 From: Jocke Date: Wed, 20 Jan 2016 13:43:11 +0100 Subject: [PATCH 127/224] Added packet loss logic for multiple clients. Changed packet class to fit our needs. --- include/Engine/Network/Packet.h | 3 +- include/Engine/Network/PlayerDefinition.h | 2 + include/Engine/Network/Server.h | 8 ++-- src/Engine/Network/Client.cpp | 6 +-- src/Engine/Network/Packet.cpp | 21 +++++++++-- src/Engine/Network/Server.cpp | 46 ++++++++++++++++------- 6 files changed, 58 insertions(+), 28 deletions(-) diff --git a/include/Engine/Network/Packet.h b/include/Engine/Network/Packet.h index 112ebe34..2891bf87 100644 --- a/include/Engine/Network/Packet.h +++ b/include/Engine/Network/Packet.h @@ -14,6 +14,7 @@ public: Packet(MessageType type, unsigned int& packetID); // Used to create packet from already existing data buffer. Packet(char* data, const int sizeOfPacket); + Packet(MessageType type); ~Packet(); void Init(MessageType type, unsigned int& packetID); @@ -49,7 +50,7 @@ public: // Pops the first element as if it was a string. std::string ReadString(); char* ReadData(int SizeOfData); - + void ChangePacketID(unsigned int& packetID); int Size() { return m_Offset; }; char* Data() { return m_Data; }; unsigned int DataReadSize() { return m_ReturnDataOffset; } diff --git a/include/Engine/Network/PlayerDefinition.h b/include/Engine/Network/PlayerDefinition.h index dbacda95..4b8b8e6e 100644 --- a/include/Engine/Network/PlayerDefinition.h +++ b/include/Engine/Network/PlayerDefinition.h @@ -6,6 +6,8 @@ struct PlayerDefinition { int EntityID = -1; std::string Name = ""; boost::asio::ip::udp::endpoint Endpoint; + unsigned int PacketID; + std::clock_t StopTime; }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 9aba921a..3b871e43 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -43,16 +43,14 @@ private: //Timers std::clock_t m_StartPingTime; - std::clock_t m_StopTimes[8]; // Game logic World* m_World; EventBroker* m_EventBroker; // Packet loss logic - unsigned int m_PacketID; - unsigned int m_PreviousPacketID; - unsigned int m_SendPacketID; + unsigned int m_PacketID = 0; + unsigned int m_PreviousPacketID = 0; // Private member functions int receive(char* data, size_t length); @@ -73,8 +71,8 @@ private: void parseServerPing(); void identifyPacketLoss(); EntityID createPlayer(); + int GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint); // Debug event - EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); }; diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index ae71d0ae..fd6825b5 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -57,9 +57,7 @@ void Client::parseMessageType(Packet& packet) // Read packet ID m_PreviousPacketID = m_PacketID; // Set previous packet id m_PacketID = packet.ReadPrimitive(); //Read new packet id - if (m_PacketID <= m_PreviousPacketID) - return; - //IdentifyPacketLoss(); + identifyPacketLoss(); switch (static_cast(messageType)) { case MessageType::Connect: @@ -282,7 +280,7 @@ void Client::identifyPacketLoss() // if no packets lost, difference should be equal to 1 int difference = m_PacketID - m_PreviousPacketID; if (difference != 1) { - LOG_INFO("%i Packet(s) were lost...", difference); + LOG_INFO("%i Packet(s) were lost...", difference -1); } } diff --git a/src/Engine/Network/Packet.cpp b/src/Engine/Network/Packet.cpp index 568a78e3..6308a130 100644 --- a/src/Engine/Network/Packet.cpp +++ b/src/Engine/Network/Packet.cpp @@ -17,20 +17,26 @@ Packet::Packet(char* data, const int sizeOfPacket) m_Offset = sizeOfPacket; } +Packet::Packet(MessageType type) +{ + m_Data = new char[m_MaxPacketSize]; + unsigned int dummy = 0; + Init(type, dummy); +} + Packet::~Packet() { delete[] m_Data; } void Packet::Init(MessageType type, unsigned int & packetID) -{ +{ m_ReturnDataOffset = 0; m_Offset = 0; // Create message header // Add message type int messageType = static_cast(type); Packet::WritePrimitive(messageType); - packetID = packetID % 1000; // Packet id modulos Packet::WritePrimitive(packetID); packetID++; } @@ -80,14 +86,21 @@ char * Packet::ReadData(int SizeOfData) return (m_Data + oldReturnDataOffset); } +void Packet::ChangePacketID(unsigned int & packetID) +{ + packetID = packetID + 1; + // Overwrite old PacketID + memcpy(m_Data + sizeof(int), &packetID, sizeof(int)); +} + void Packet::resizeData() -{ +{ // Allocate memory to store our data in char* holdData = new char[m_MaxPacketSize]; // Copy our data to the newly allocated memory memcpy(holdData, m_Data, m_Offset); - // Increase max packet size + // Increase max packet size m_MaxPacketSize = m_MaxPacketSize * 2; // Delete our data delete m_Data; diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 1f9db461..ce3a735c 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -16,7 +16,7 @@ void Server::Start(World* world, EventBroker* eventBroker) // Subscribe to events EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Server::OnInputCommand); for (size_t i = 0; i < MAXCONNECTIONS; i++) { - m_StopTimes[i] = std::clock(); + m_PlayerDefinitions[i].StopTime = std::clock(); } LOG_INFO("I am Server. BIP BOP\n"); } @@ -66,7 +66,7 @@ void Server::parseMessageType(Packet& packet) // Read packet ID m_PreviousPacketID = m_PacketID; // Set previous packet id m_PacketID = packet.ReadPrimitive(); //Read new packet id - //IdentifyPacketLoss(); + //identifyPacketLoss(); switch (static_cast(messageType)) { case MessageType::Connect: parseConnect(packet); @@ -126,6 +126,7 @@ void Server::broadcast(Packet& packet) { for (int i = 0; i < MAXCONNECTIONS; ++i) { if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { + packet.ChangePacketID(m_PlayerDefinitions[i].PacketID); send(packet, i); } } @@ -137,7 +138,7 @@ void Server::sendSnapshot() // Should time this std::unordered_map worldComponentPools = m_World->GetComponentPools(); for (auto& it : worldComponentPools) { - Packet packet(MessageType::Snapshot, m_SendPacketID); + Packet packet(MessageType::Snapshot); ComponentPool* componentPool = it.second; ComponentInfo componentInfo = componentPool->ComponentInfo(); // Component Type @@ -166,12 +167,12 @@ void Server::sendPing() // Prints connected players ping for (size_t i = 0; i < MAXCONNECTIONS; i++) { if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { - int ping = 1000 * (m_StopTimes[i] - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); - LOG_INFO("Last packetID received %i: Player %i's ping: %i", m_PacketID, i, ping); + int ping = 1000 * (m_PlayerDefinitions[i].StopTime - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); + LOG_INFO("Last packetID received %i: Player %i's ping: %i", m_PlayerDefinitions[i].PacketID, i, ping); } } // Create ping message - Packet packet(MessageType::ServerPing, m_SendPacketID); + Packet packet(MessageType::ServerPing); packet.WriteString("Ping from server"); // Time message m_StartPingTime = std::clock(); @@ -187,8 +188,8 @@ void Server::checkForTimeOuts() for (size_t i = 0; i < MAXCONNECTIONS; i++) { if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { - int stopPing = 1000 * m_StopTimes[i] - / static_cast(CLOCKS_PER_SEC); + int stopPing = 1000 * m_PlayerDefinitions[i].StopTime / + static_cast(CLOCKS_PER_SEC); if (startPing > stopPing + timeOutTimeMs) { LOG_INFO("Player %i timed out!", i); disconnect(i); @@ -206,6 +207,7 @@ void Server::disconnect(int i) m_PlayerDefinitions[i].Endpoint = boost::asio::ip::udp::endpoint(); m_PlayerDefinitions[i].EntityID = -1; m_PlayerDefinitions[i].Name = ""; + m_PlayerDefinitions[i].PacketID = 0; } void Server::parseOnInputCommand(Packet& packet) @@ -259,19 +261,20 @@ void Server::parseConnect(Packet& packet) m_PlayerDefinitions[i].EntityID = createPlayer(); m_PlayerDefinitions[i].Endpoint = m_ReceiverEndpoint; m_PlayerDefinitions[i].Name = packet.ReadString(); + m_PlayerDefinitions[i].PacketID = 0; - m_StopTimes[i] = std::clock(); + m_PlayerDefinitions[i].StopTime = std::clock(); LOG_INFO("Player \"%s\" connected on IP: %s", m_PlayerDefinitions[i].Name.c_str(), m_PlayerDefinitions[i].Endpoint.address().to_string().c_str()); // Send a message to the player that connected - Packet packet(MessageType::Connect, m_SendPacketID); + Packet packet(MessageType::Connect, m_PlayerDefinitions[i].PacketID); packet.WritePrimitive(i); // Player ID packet.WritePrimitive(m_PlayerDefinitions[i].EntityID); // Entity ID send(packet, i); // Send notification that a player has connected - Packet notificationPacket(MessageType::PlayerConnected, m_PacketID); + Packet notificationPacket(MessageType::PlayerConnected); broadcast(notificationPacket); break; @@ -294,17 +297,21 @@ void Server::parseDisconnect() void Server::parseClientPing() { LOG_INFO("%i: Parsing ping", m_PacketID); + int playerID = GetPlayerIDFromEndpoint(m_ReceiverEndpoint); + if (playerID == -1) { + return; + } // Return ping - Packet packet(MessageType::ClientPing, m_SendPacketID); + Packet packet(MessageType::ClientPing, m_PlayerDefinitions[playerID].PacketID); packet.WriteString("Ping received"); - send(packet); // This dosen't work for multiple users + send(packet); } void Server::parseServerPing() { for (int i = 0; i < MAXCONNECTIONS; i++) { if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address()) { - m_StopTimes[i] = std::clock(); + m_PlayerDefinitions[i].StopTime = std::clock(); break; } } @@ -331,6 +338,17 @@ EntityID Server::createPlayer() return entityID; } +int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) +{ + for (int i = 0; i < MAXCONNECTIONS; i++) { + if (m_PlayerDefinitions[i].Endpoint.address() == endpoint.address() && + m_PlayerDefinitions[i].Endpoint.port() == endpoint.port()) { + return i; + } + } + return -1; +} + bool Server::OnInputCommand(const Events::InputCommand & e) { //LOG_INFO("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); From e9a576341e4a8f3a1d8e203b4192b3b99198c970 Mon Sep 17 00:00:00 2001 From: Jocke Date: Wed, 20 Jan 2016 14:31:50 +0100 Subject: [PATCH 128/224] Started on server disconnect logic. --- src/Engine/Network/Server.cpp | 20 +++++++++----------- 1 file changed, 9 insertions(+), 11 deletions(-) diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index ce3a735c..c598f1f1 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -189,7 +189,7 @@ void Server::checkForTimeOuts() for (size_t i = 0; i < MAXCONNECTIONS; i++) { if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { int stopPing = 1000 * m_PlayerDefinitions[i].StopTime / - static_cast(CLOCKS_PER_SEC); + static_cast(CLOCKS_PER_SEC); if (startPing > stopPing + timeOutTimeMs) { LOG_INFO("Player %i timed out!", i); disconnect(i); @@ -201,7 +201,7 @@ void Server::checkForTimeOuts() void Server::disconnect(int i) { //broadcast("A player disconnected"); - LOG_INFO("Player %i disconnected/timed out", i); + LOG_INFO("Player %s disconnected/timed out", m_PlayerDefinitions[i].Name.c_str()); // Remove enteties and stuff m_PlayerDefinitions[i].Endpoint = boost::asio::ip::udp::endpoint(); @@ -216,7 +216,7 @@ void Server::parseOnInputCommand(Packet& packet) // Check which player it was who sent the message for (int i = 0; i < MAXCONNECTIONS; i++) { // if the player is connected set playerID to the correct PlayerID - if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() + if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() && m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { playerID = i; break; @@ -248,13 +248,11 @@ void Server::parseConnect(Packet& packet) { LOG_INFO("Parsing connections"); // Check if player is already connected - for (int i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() && - m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { - return; - } + if (GetPlayerIDFromEndpoint(m_ReceiverEndpoint) != -1) { + return; } + // Find an empty spot to put the player in for (int i = 0; i < MAXCONNECTIONS; i++) { if (m_PlayerDefinitions[i].Endpoint.address() == boost::asio::ip::address()) { // Create new player @@ -298,13 +296,13 @@ void Server::parseClientPing() { LOG_INFO("%i: Parsing ping", m_PacketID); int playerID = GetPlayerIDFromEndpoint(m_ReceiverEndpoint); - if (playerID == -1) { + if (playerID == -1) { return; } // Return ping Packet packet(MessageType::ClientPing, m_PlayerDefinitions[playerID].PacketID); packet.WriteString("Ping received"); - send(packet); + send(packet); } void Server::parseServerPing() @@ -351,6 +349,6 @@ int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) bool Server::OnInputCommand(const Events::InputCommand & e) { - //LOG_INFO("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + //LOG_DEBUG("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; } From 7e7ca7edcf79529c6afaed534eb544f493b782f2 Mon Sep 17 00:00:00 2001 From: stiffly Date: Wed, 20 Jan 2016 14:32:04 +0100 Subject: [PATCH 129/224] Listening to "DisconnectFromServer" --- src/Engine/Network/Client.cpp | 18 +++++++++++------- 1 file changed, 11 insertions(+), 7 deletions(-) diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index ae71d0ae..83e0d886 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -57,9 +57,7 @@ void Client::parseMessageType(Packet& packet) // Read packet ID m_PreviousPacketID = m_PacketID; // Set previous packet id m_PacketID = packet.ReadPrimitive(); //Read new packet id - if (m_PacketID <= m_PreviousPacketID) - return; - //IdentifyPacketLoss(); + identifyPacketLoss(); switch (static_cast(messageType)) { case MessageType::Connect: @@ -240,8 +238,7 @@ void Client::connect() void Client::disconnect() { - Packet packet(MessageType::Connect, m_SendPacketID); - packet.WriteString("+Disconnect"); + Packet packet(MessageType::Disconnect, m_SendPacketID); send(packet); } @@ -256,9 +253,16 @@ void Client::ping() bool Client::OnInputCommand(const Events::InputCommand & e) { if (e.Command == "ConnectToServer") { // Connect for now - connect(); + if (e.Value > 0) { + connect(); + } //LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); return true; + } else if (e.Command == "DisconnectFromServer") { + if (e.Value > 0) { + disconnect(); + } + return true; } else { m_InputCommandBuffer.push_back(e); //LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); @@ -282,7 +286,7 @@ void Client::identifyPacketLoss() // if no packets lost, difference should be equal to 1 int difference = m_PacketID - m_PreviousPacketID; if (difference != 1) { - LOG_INFO("%i Packet(s) were lost...", difference); + LOG_INFO("%i Packet(s) were lost...", difference - 1); } } From 8189e3c00c6cc611c12be08d346773aba2a3c677 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 20 Jan 2016 14:59:18 +0100 Subject: [PATCH 130/224] Logic in CapturePointSystem is working again. Need to update all Tests! --- include/Engine/Core/ComponentPool.h | 1 + include/Game/Systems/CapturePointSystem.h | 16 +- resources/Schema/Components/CapturePoint.xml | 1 + resources/Schema/Components/CapturePoint.xsd | 19 ++ resources/Schema/Entities/CaptureTestState1 | 158 ++++++++++++++++ src/Engine/Core/ComponentPool.cpp | 5 + src/Game/Systems/CapturePointSystem.cpp | 186 +++++++++---------- src/Tests/CapturePointTest.cpp | 4 +- 8 files changed, 290 insertions(+), 100 deletions(-) create mode 100644 resources/Schema/Entities/CaptureTestState1 diff --git a/include/Engine/Core/ComponentPool.h b/include/Engine/Core/ComponentPool.h index ed81d72e..957b8756 100644 --- a/include/Engine/Core/ComponentPool.h +++ b/include/Engine/Core/ComponentPool.h @@ -61,6 +61,7 @@ public: iterator begin() const; iterator end() const; + size_t size() const; //Dumps information about what the pool memory looks like right now //into an output stream (e.g. file/std::cout, anything that has an operator<<) diff --git a/include/Game/Systems/CapturePointSystem.h b/include/Game/Systems/CapturePointSystem.h index 2cac7d95..542d80d5 100644 --- a/include/Game/Systems/CapturePointSystem.h +++ b/include/Game/Systems/CapturePointSystem.h @@ -28,15 +28,23 @@ private: bool CapturePointSystem::OnTriggerTouch(const Events::TriggerTouch& e); EventRelay m_ETriggerLeave; bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e); + EventRelay m_ECaptured; + bool CapturePointSystem::OnCaptured(const Events::Captured& e); bool m_WinnerWasFound = false; //need to track these variables for the captureSystem to work as per design! const int m_NotACapturePoint = 999; - int m_Team1NextPossibleCapturePoint = m_NotACapturePoint; - int m_Team2NextPossibleCapturePoint = m_NotACapturePoint; - int m_Team1HomeCapturePoint = m_NotACapturePoint; - int m_Team2HomeCapturePoint = m_NotACapturePoint; + int m_RedTeamNextPossibleCapturePoint = m_NotACapturePoint; + int m_BlueTeamNextPossibleCapturePoint = m_NotACapturePoint; + int m_RedTeamHomeCapturePoint = m_NotACapturePoint; + int m_BlueTeamHomeCapturePoint = m_NotACapturePoint; + int m_NumberOfCapturePoints = 0; + std::map m_CapturePointNumberToEntityIDMap; + + //std::vector + + std::map m_NextPossibleCapturePoint; const double m_CaptureTimeToTakeOver = 15.0; //vectors which will keep track of enter/leave changes diff --git a/resources/Schema/Components/CapturePoint.xml b/resources/Schema/Components/CapturePoint.xml index aa65852e..ba164fd9 100644 --- a/resources/Schema/Components/CapturePoint.xml +++ b/resources/Schema/Components/CapturePoint.xml @@ -2,4 +2,5 @@ 0 0 + \ No newline at end of file diff --git a/resources/Schema/Components/CapturePoint.xsd b/resources/Schema/Components/CapturePoint.xsd index ff1a665d..9e96fca6 100644 --- a/resources/Schema/Components/CapturePoint.xsd +++ b/resources/Schema/Components/CapturePoint.xsd @@ -3,6 +3,18 @@ + + + + + + + + + + + + A Capture Point. Add a Team Component to specify who currently owns it @@ -19,6 +31,13 @@ CapturePointNumber specify an int number for this + + + + Specify if this is a HomePoint for either team + + + diff --git a/resources/Schema/Entities/CaptureTestState1 b/resources/Schema/Entities/CaptureTestState1 new file mode 100644 index 00000000..03b93e81 --- /dev/null +++ b/resources/Schema/Entities/CaptureTestState1 @@ -0,0 +1,158 @@ + + + + + + + + + + + + ../assets/Models/DummyScene.obj + + + + + + + + + 60 + + + + + + + 3 + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 3 + + + + + + + + + + + + + -3.9175623281664684 + 1 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + -1.8667072838033221 + 2 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + 2 + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + diff --git a/src/Engine/Core/ComponentPool.cpp b/src/Engine/Core/ComponentPool.cpp index ce24c1f7..b6286c28 100644 --- a/src/Engine/Core/ComponentPool.cpp +++ b/src/Engine/Core/ComponentPool.cpp @@ -72,6 +72,11 @@ ComponentPool::iterator ComponentPool::end() const return iterator(m_ComponentInfo, m_Pool.end(), m_Pool.end()); } +size_t ComponentPool::size() const +{ + return m_Pool.size(); +} + template void ComponentPool::Dump() const { diff --git a/src/Game/Systems/CapturePointSystem.cpp b/src/Game/Systems/CapturePointSystem.cpp index af82e95a..e5141cdf 100644 --- a/src/Game/Systems/CapturePointSystem.cpp +++ b/src/Game/Systems/CapturePointSystem.cpp @@ -14,20 +14,80 @@ CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) //NOTE: needs to run each frame, since we're possibly modifying the captureTimer for the capturePoints by dt void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& capturePoint, double dt) { - bool hasTeamComponent = world->HasComponent(capturePoint.EntityID, "Team"); + const int capturePointNumber = capturePoint["CapturePointNumber"]; + const bool hasTeamComponent = world->HasComponent(capturePoint.EntityID, "Team"); + + //if point doesnt have a teamComponent yet, add one. since: + //what if capture point has no team -> we cant get/use the team enum from it... if (!hasTeamComponent) { world->AttachComponent(capturePoint.EntityID, "Team"); ComponentWrapper& teamComponent = world->GetComponent(capturePoint.EntityID, "Team"); teamComponent["Team"] = (int)teamComponent["Team"].Enum("Spectator"); } ComponentWrapper& teamComponent = world->GetComponent(capturePoint.EntityID, "Team"); - int firstTeamPlayersStandingInside = 0; - int secondTeamPlayersStandingInside = 0; - //what if capture point has no TEAM? -> NO ENUM. - const int redTeam = (int)teamComponent["Team"].Enum("Red");//"team 1" - const int blueTeam = (int)teamComponent["Team"].Enum("Blue");//"team 2" + const int redTeam = (int)teamComponent["Team"].Enum("Red"); + const int blueTeam = (int)teamComponent["Team"].Enum("Blue"); const int spectatorTeam = (int)teamComponent["Team"].Enum("Spectator"); + int homePointForTeam = (int)capturePoint["HomePointForTeam"]; + if (m_NumberOfCapturePoints == 0 && capturePointNumber != 0 && (homePointForTeam == redTeam || homePointForTeam == blueTeam)) { + m_NumberOfCapturePoints = capturePointNumber + 1;//ex 2 -> 0,1,2 = 3 + if (homePointForTeam == redTeam) { + m_RedTeamHomeCapturePoint = capturePointNumber; + m_BlueTeamHomeCapturePoint = 0; + } else { + m_BlueTeamHomeCapturePoint = capturePointNumber; + m_RedTeamHomeCapturePoint = 0; + } + } + + //if we havent received all capturepoints yet, just return + if (m_NumberOfCapturePoints == 0 || m_NumberOfCapturePoints != m_CapturePointNumberToEntityIDMap.size()) { + m_CapturePointNumberToEntityIDMap.insert(std::make_pair(capturePointNumber, capturePoint.EntityID)); + return; + } + + //we have all capturepoints now - process stuff + int ownedBy = teamComponent["Team"]; + int redTeamPlayersStandingInside = 0; + int blueTeamPlayersStandingInside = 0; + if (entity.HasComponent("Model")) { + //Now sets team color to the capturepoint, or white if it is uncaptured. + entity["Model"]["Color"] = ownedBy == blueTeam ? glm::vec4(0, 0.2f, 1, 1) : ownedBy == redTeam ? glm::vec4(1, 0.2f, 0, 1) : glm::vec4(1, 1, 1, 1); + } + + //calculate next possible capturePoint for both teams + m_NextPossibleCapturePoint["Red"] = -1; + m_NextPossibleCapturePoint["Blue"] = -1; + for (size_t i = 0; i < m_NumberOfCapturePoints; i++) + { + ComponentWrapper& capturePointOwnedBy = world->GetComponent(m_CapturePointNumberToEntityIDMap[i], "Team"); + if ((int)capturePointOwnedBy["Team"] == redTeam && m_RedTeamHomeCapturePoint == 0) { + m_NextPossibleCapturePoint["Red"] = i + 1; + } + if ((int)capturePointOwnedBy["Team"] == blueTeam && m_BlueTeamHomeCapturePoint == 0) { + m_NextPossibleCapturePoint["Blue"] = i + 1; + } + } + for (int i = m_NumberOfCapturePoints - 1; i >= 0; i--) + { + ComponentWrapper& capturePointOwnedBy = world->GetComponent(m_CapturePointNumberToEntityIDMap[i], "Team"); + if ((int)capturePointOwnedBy["Team"] == redTeam && m_RedTeamHomeCapturePoint != 0) { + m_NextPossibleCapturePoint["Red"] = i - 1; + } + if ((int)capturePointOwnedBy["Team"] == blueTeam && m_BlueTeamHomeCapturePoint != 0) { + m_NextPossibleCapturePoint["Blue"] = i - 1; + } + } + + //colorize next possible capturepoint + if (m_NextPossibleCapturePoint["Red"] == capturePointNumber) { + entity["Model"]["Color"] = glm::vec4(1, 1, 0, 1); + } + if (m_NextPossibleCapturePoint["Blue"] == capturePointNumber) { + entity["Model"]["Color"] = glm::vec4(0, 1, 1, 1); + } + //check how many players are standing inside and are healthy for (size_t i = m_ETriggerTouchVector.size(); i > 0; i--) { @@ -51,70 +111,40 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co //check team - spectatorNumber = "no team" int teamNumber = world->GetComponent(playerID, "Team")["Team"]; if (teamNumber == redTeam) { - firstTeamPlayersStandingInside++; + redTeamPlayersStandingInside++; } else if (teamNumber == blueTeam) { - secondTeamPlayersStandingInside++; + blueTeamPlayersStandingInside++; } continue; } } - int ownedBy = teamComponent["Team"]; - //Probably want to distinguish the capturepoint depending on team affiliation. - if (entity.HasComponent("Model")) { - //Now sets team color to the capturepoint, or white if it is uncaptured. - entity["Model"]["Color"] = ownedBy == blueTeam ? glm::vec4(0, 0.2f, 1, 1) : - ownedBy == redTeam ? glm::vec4(1, 0.2f, 0, 1) : - glm::vec4(1, 1, 1, 1); - } - //om ej next satt, förvänta sig att en capturepoint med en viss team färg kommer in... - //sätt isåfall next och kör på.. - //gör inget tills man fått den infon - - /*check what capturePoint can be taken over next: - no capturepoint taken yet for at least one of the teams <-> - at the start of the match the system is unaware of what capturePoint is the first one for each team*/ - if (m_Team1NextPossibleCapturePoint == m_NotACapturePoint && (int)teamComponent["Team"] == redTeam) { - m_Team1HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team1NextPossibleCapturePoint - if (m_Team1HomeCapturePoint == 0) { - m_Team1NextPossibleCapturePoint = 1; - } else { - m_Team1NextPossibleCapturePoint = (int)capturePoint["CapturePointNumber"] - 1; - } - } else if (m_Team2NextPossibleCapturePoint == m_NotACapturePoint && (int)teamComponent["Team"] == blueTeam) { - m_Team2HomeCapturePoint = capturePoint["CapturePointNumber"];//needed to calculate next m_Team2NextPossibleCapturePoint - if (m_Team2HomeCapturePoint == 0) { - m_Team2NextPossibleCapturePoint = 1; - } else { - m_Team2NextPossibleCapturePoint = (int)capturePoint["CapturePointNumber"] - 1; - } - } - //at least one capturepoint has been taken over - //do nothing, its being handled inside the next code: - //create data to be used in option B //check so this is the next possible capture point for the take-over team and see if only one team is standing inside it double timerDeltaChange = 0.0; int currentTeam = 0; - if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside == 0 - && m_Team1NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) - { - timerDeltaChange = firstTeamPlayersStandingInside*dt; + bool canCapture = false; + if (redTeamPlayersStandingInside > 0 && blueTeamPlayersStandingInside == 0) { + timerDeltaChange = redTeamPlayersStandingInside*dt; currentTeam = redTeam; - } else if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside > 0 - && m_Team2NextPossibleCapturePoint == (int)capturePoint["CapturePointNumber"]) - { - timerDeltaChange = -secondTeamPlayersStandingInside*dt; + canCapture = m_NextPossibleCapturePoint["Red"] == capturePointNumber; + } + if (redTeamPlayersStandingInside == 0 && blueTeamPlayersStandingInside > 0) { + timerDeltaChange = -blueTeamPlayersStandingInside*dt; currentTeam = blueTeam; + canCapture = m_NextPossibleCapturePoint["Blue"] == capturePointNumber; } - if (firstTeamPlayersStandingInside == 0 && secondTeamPlayersStandingInside == 0) { + if (redTeamPlayersStandingInside == 0 && blueTeamPlayersStandingInside == 0) { //A.nobodys standing inside //do nothing (?) - } else if (currentTeam == blueTeam || currentTeam == redTeam) { - //B. at most one of the teams have players inside (this means datavariable currentTeam is not 0) + } else if (redTeamPlayersStandingInside > 0 && blueTeamPlayersStandingInside > 0) { + //C.both teams have players inside + //do nothing (?) + } else { + //B. at most one of the teams have players inside //if capturePoint is not owned by the take-over team, just modify the CaptureTimer accordingly - if (ownedBy != currentTeam) { + if (ownedBy != currentTeam && canCapture) { if (abs((double)capturePoint["CaptureTimer"]) < 0.001f) { LOG_DEBUG("Point is being captured by team %i", currentTeam); //Remove when we tested sufficiently. } @@ -126,7 +156,7 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co capturePoint["CaptureTimer"] = (double)capturePoint["CaptureTimer"] + timerDeltaChange; } //check if captureTimer > m_CaptureTimeToTakeOver and if so change owner and publish the eCaptured event - if (abs((double)capturePoint["CaptureTimer"]) > abs(m_CaptureTimeToTakeOver)) { + if (abs((double)capturePoint["CaptureTimer"]) > abs(m_CaptureTimeToTakeOver) && canCapture) { teamComponent["Team"] = currentTeam; capturePoint["CaptureTimer"] = 0.0; //publish Captured event @@ -135,53 +165,17 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co e.CapturePointID = capturePoint.EntityID; e.TeamNumberThatCapturedCapturePoint = currentTeam; m_EventBroker->Publish(e); - //modify nextPossibleCapturePoint, depending on, example: if team 1 has "0" as homebase or team 1 has "7" as homebase - - //0 = false 1 = true - bool team1HasTheZeroCapturePoint = m_Team1HomeCapturePoint < m_Team2HomeCapturePoint; - - if (team1HasTheZeroCapturePoint) { - if (currentTeam == redTeam) { - m_Team1NextPossibleCapturePoint++; - } else { - m_Team2NextPossibleCapturePoint--; - } - //adjust flag for other team if their previous point has just been taken - //this depends on what team has what homepoint ("side") - if (m_Team2NextPossibleCapturePoint == m_Team1NextPossibleCapturePoint - 2) { - m_Team2NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint + 1; - } - if (m_Team1NextPossibleCapturePoint == m_Team2NextPossibleCapturePoint + 2) { - m_Team1NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint - 1; - } - } else { - if (currentTeam == redTeam) { - m_Team1NextPossibleCapturePoint--; - } else { - m_Team2NextPossibleCapturePoint++; - } - //adjust flag for other team if their previous point has just been taken - //this depends on what team has what homepoint ("side") - if (m_Team2NextPossibleCapturePoint == m_Team1NextPossibleCapturePoint + 2) { - m_Team2NextPossibleCapturePoint = m_Team2NextPossibleCapturePoint - 1; - } - if (m_Team1NextPossibleCapturePoint == m_Team2NextPossibleCapturePoint - 2) { - m_Team1NextPossibleCapturePoint = m_Team1NextPossibleCapturePoint + 1; - } - } + //NextPossibleCapturePoint will be calculated in the next update... } - } else if (firstTeamPlayersStandingInside > 0 && secondTeamPlayersStandingInside > 0) { - //C.both teams have players inside - //do nothing (?) } //check for possible winCondition = check if the homebase is owned by the other team bool checkForWinner = false; - if ((int)capturePoint["CapturePointNumber"] == m_Team1HomeCapturePoint && (int)teamComponent["Team"] != redTeam) + if (capturePointNumber == m_RedTeamHomeCapturePoint && ownedBy != redTeam) { checkForWinner = true; } - if ((int)capturePoint["CapturePointNumber"] == m_Team2HomeCapturePoint && (int)teamComponent["Team"] != blueTeam) + if (capturePointNumber == m_BlueTeamHomeCapturePoint && ownedBy != blueTeam) { checkForWinner = true; } @@ -190,7 +184,7 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co { //publish Win event Events::Win e; - e.TeamThatWon = teamComponent["Team"]; + e.TeamThatWon = ownedBy; m_EventBroker->Publish(e); m_WinnerWasFound = true; } @@ -216,3 +210,7 @@ bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e) } return true; } +bool CapturePointSystem::OnCaptured(const Events::Captured& e) +{ + return true; +} diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index 9ef7f6a6..76921000 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -80,8 +80,8 @@ bool CapturePointTest::CapturePoint_Game_Loop_OneHundredTimes() { Tick(); NumLoops++; if (TestSucceeded) { - success = true; - break; + //success = true; + //break; } loops--; } From 86824f1b1f4fafe29f0d91530171b1bd12f9c929 Mon Sep 17 00:00:00 2001 From: Tleety Date: Wed, 20 Jan 2016 15:23:49 +0100 Subject: [PATCH 131/224] Colors above value 1 is now added to the bloomtexture, and will be used to get a glow effect in later stage. --- resources/Shaders/ForwardPlus.frag.glsl | 13 ++++++------- src/Engine/Rendering/DrawFinalPass.cpp | 3 ++- src/Engine/Rendering/DrawFinalPassState.cpp | 2 +- src/Engine/Rendering/FrameBuffer.cpp | 4 +--- src/Engine/Rendering/Renderer.cpp | 4 ++-- 5 files changed, 12 insertions(+), 14 deletions(-) diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 6a810036..3fae9eb6 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -132,18 +132,17 @@ void main() totalLighting.Specular += result.Specular; } - //sceneColor += Input.DiffuseColor; vec4 fragment = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; - bloomColor = vec4(0.3, 0.8, 0.6, 1.0); + //bloomColor = vec4(0.3, 0.8, 0.6, 1.0); sceneColor = vec4(fragment.xyz, 1.0); //These if statements should be removed. -/* - if(fragment.x > 0.5 || fragment.y > 0.5 || fragment.z > 0.5) { - bloomColor = fragment; + + if(fragment.x > 1 || fragment.y > 1 || fragment.z > 1) { + bloomColor = vec4(fragment.xyz, 1.0); } else { - bloomColor = vec4(0.3, 0.5, 0.8, 1.0); - }*/ + bloomColor = vec4(0.0, 0.0, 0.0, 1.0); + } //sceneColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; //sceneColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 57940971..5a9f706e 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -27,6 +27,7 @@ void DrawFinalPass::InitializeFrameBuffers() m_BloomFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); m_BloomFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_BloomTexture, GL_COLOR_ATTACHMENT1))); m_BloomFrameBuffer.Generate(); + } void DrawFinalPass::InitializeShaderPrograms() @@ -79,8 +80,8 @@ void DrawFinalPass::Draw(RenderScene& scene) continue; } } + m_BloomFrameBuffer.Unbind(); GLERROR("DrawFinalPass::Draw: END"); - } void DrawFinalPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 5b4bbf3b..43047f05 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -8,7 +8,7 @@ DrawFinalPassState::DrawFinalPassState() BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); Enable(GL_DEPTH_TEST); Enable(GL_CULL_FACE); - ClearColor(glm::vec4(200.f / 255, 0.f / 255, 200.f / 255, 0.f)); + ClearColor(glm::vec4(155.f / 255, 0.f / 255, 155.f / 255, 0.f)); Clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); } diff --git a/src/Engine/Rendering/FrameBuffer.cpp b/src/Engine/Rendering/FrameBuffer.cpp index 79507875..b7e908cc 100644 --- a/src/Engine/Rendering/FrameBuffer.cpp +++ b/src/Engine/Rendering/FrameBuffer.cpp @@ -70,10 +70,8 @@ void FrameBuffer::Generate() } } - - GLenum* bufferTextures = &attachments[0]; - glDrawBuffers(1, bufferTextures); + glDrawBuffers(attachments.size(), bufferTextures); if (GLenum frameBufferStatus = glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) { LOG_ERROR("FrameBuffer incomplete: 0x%x\n", frameBufferStatus); diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index f08bfafd..894f358f 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -99,8 +99,8 @@ void Renderer::Draw(RenderFrame& frame) m_LightCullingPass->FillLightList(*scene); m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); - m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_SceneTexture); - //m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_BloomTexture); + //m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_SceneTexture); + m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_BloomTexture); //m_DrawScenePass->Draw(rq); GLERROR("Renderer::Draw m_DrawScenePass->Draw"); From 39ae83efd4d7de70b19faf660ccb4351a3d0f89b Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 20 Jan 2016 15:40:56 +0100 Subject: [PATCH 132/224] Fixed all tests in CapturePointTest and cleaned up some comments --- src/Tests/CapturePointTest.cpp | 234 ++++++++++++++------------------- src/Tests/CapturePointTest.h | 3 +- 2 files changed, 100 insertions(+), 137 deletions(-) diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index 76921000..5a041120 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -17,62 +17,53 @@ BOOST_AUTO_TEST_CASE(CapturePointTest1_OnePlayerOnCapturePoint) { CapturePointTest game(1); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest2_TwoPlayersOnCapturePoint) { CapturePointTest game(2); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest3_NoPlayersOnCapturePoint) { CapturePointTest game(3); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest4_TwoCapturePointsBeingCaptured) { CapturePointTest game(4); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest5_SameCapturePointContestedAndTakenOver) { CapturePointTest game(5); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest6_Team1CapturedTheLastPointAndWon) { CapturePointTest game(6); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest7_Team1ForcesTeam2sNextCapturePointToGoBackwards1Step) { CapturePointTest game(7); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_CASE(CapturePointTest8_Team2ForcesTeam1sNextCapturePointToGoForwards1Step) { CapturePointTest game(8); bool success = game.CapturePoint_Game_Loop_OneHundredTimes(); - //The system will process the events, hence it will take a while before we can read anything BOOST_TEST(success); } BOOST_AUTO_TEST_SUITE_END() bool CapturePointTest::CapturePoint_Game_Loop_OneHundredTimes() { - //CapturePointTest game(testNumber); //100 loops will be more than enough to do the test int loops = 100; bool success = false; @@ -80,8 +71,8 @@ bool CapturePointTest::CapturePoint_Game_Loop_OneHundredTimes() { Tick(); NumLoops++; if (TestSucceeded) { - //success = true; - //break; + success = true; + break; } loops--; } @@ -114,14 +105,6 @@ CapturePointTest::CapturePointTest(int runTestNumber) EntityFileParser fp(file); fp.MergeEntities(m_World); - /* - ---TESTSETUP--- - default: 2 players - healthcomponent - 3 capturepoints - capturepoint(1) = home for team number 2 - capturepoint3 = home for team number 1 - */ EntityID playerID = m_World->CreateEntity(); m_RedTeamPlayer = playerID; ComponentWrapper& player = m_World->AttachComponent(m_RedTeamPlayer, "Player"); @@ -138,25 +121,43 @@ CapturePointTest::CapturePointTest(int runTestNumber) ComponentWrapper& playerTeam2 = m_World->AttachComponent(m_BlueTeamPlayer, "Team"); playerTeam2["Team"] = m_BlueTeam; - EntityID capturePointID = m_World->CreateEntity(); - m_CapturePointID = capturePointID; - ComponentWrapper& capturePoint = m_World->AttachComponent(capturePointID, "CapturePoint"); - ComponentWrapper& capturePointHomeTeam = m_World->AttachComponent(capturePointID, "Team"); - capturePointHomeTeam["Team"] = m_BlueTeam; - capturePoint["CapturePointNumber"] = 0; + EntityID capturePointID0 = m_World->CreateEntity(); + m_CapturePointID0 = capturePointID0; + ComponentWrapper& capturePoint0 = m_World->AttachComponent(capturePointID0, "CapturePoint"); + ComponentWrapper& capturePointTeamOwner0 = m_World->AttachComponent(capturePointID0, "Team"); + + capturePointTeamOwner0["Team"] = m_BlueTeam; + capturePoint0["CapturePointNumber"] = 0; + capturePoint0["HomePointForTeam"] = m_BlueTeam; + + EntityID capturePointID1 = m_World->CreateEntity(); + m_CapturePointID1 = capturePointID1; + ComponentWrapper& capturePoint1 = m_World->AttachComponent(capturePointID1, "CapturePoint"); + ComponentWrapper& capturePointTeamOwner1 = m_World->AttachComponent(capturePointID1, "Team"); + capturePoint1["CapturePointNumber"] = 1; + capturePointTeamOwner1["Team"] = 0; EntityID capturePointID2 = m_World->CreateEntity(); m_CapturePointID2 = capturePointID2; ComponentWrapper& capturePoint2 = m_World->AttachComponent(capturePointID2, "CapturePoint"); - //no team component for this capturepoint since nobody owns it (yet) - capturePoint2["CapturePointNumber"] = 1; + ComponentWrapper& capturePointTeamOwner2 = m_World->AttachComponent(capturePointID2, "Team"); + capturePoint2["CapturePointNumber"] = 2; + capturePointTeamOwner2["Team"] = 0; EntityID capturePointID3 = m_World->CreateEntity(); m_CapturePointID3 = capturePointID3; ComponentWrapper& capturePoint3 = m_World->AttachComponent(capturePointID3, "CapturePoint"); - ComponentWrapper& capturePointHomeTeam3 = m_World->AttachComponent(capturePointID3, "Team"); - capturePointHomeTeam3["Team"] = m_RedTeam; - capturePoint3["CapturePointNumber"] = 2; + ComponentWrapper& capturePointTeamOwner3 = m_World->AttachComponent(capturePointID3, "Team"); + capturePoint3["CapturePointNumber"] = 3; + capturePointTeamOwner3["Team"] = 0; + + EntityID capturePointID4 = m_World->CreateEntity(); + m_CapturePointID4 = capturePointID4; + ComponentWrapper& capturePoint4 = m_World->AttachComponent(capturePointID4, "CapturePoint"); + ComponentWrapper& capturePointTeamOwner4 = m_World->AttachComponent(capturePointID4, "Team"); + capturePointTeamOwner4["Team"] = m_RedTeam; + capturePoint4["CapturePointNumber"] = 4; + capturePoint4["HomePointForTeam"] = m_RedTeam; m_RunTestNumber = runTestNumber; @@ -187,8 +188,10 @@ CapturePointTest::CapturePointTest(int runTestNumber) break; case 8: //switch sides - capturePointHomeTeam["Team"] = m_RedTeam; - capturePointHomeTeam3["Team"] = m_BlueTeam; + capturePoint0["HomePointForTeam"] = m_RedTeam; + capturePointTeamOwner0["Team"] = m_RedTeam; + capturePoint4["HomePointForTeam"] = m_BlueTeam; + capturePointTeamOwner4["Team"] = m_BlueTeam; TestSetup8(); break; default: @@ -208,63 +211,41 @@ CapturePointTest::~CapturePointTest() void CapturePointTest::TestSetup1_OnePlayerOnCapturePoint() { - Events::TriggerTouch touchEvent; - Events::TriggerLeave leaveEvent; - - //redPlayer touches,leaves,touches m_CapturePointID. and enters m_CapturePointID3 - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); } void CapturePointTest::TestSetup2_TwoPlayersOnCapturePoint() { - Events::TriggerTouch touchEvent; - Events::TriggerLeave leaveEvent; - - //redPlayer touches,leaves m_CapturePointID. and enters m_CapturePointID3 - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID1); DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); - - //blueplayer touches m_CapturePointID,m_CapturePointID2 - DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); + //contested point + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID2); } void CapturePointTest::TestSetup3_NoPlayersOnCapturePoint() { - Events::TriggerTouch touchEvent; - Events::TriggerLeave leaveEvent; - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); - DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID3); + DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID0); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID4); } void CapturePointTest::TestSetup4_TwoCapturePointsBeingCaptured() { - Events::TriggerTouch touchEvent; - - //redPlayer touches m_CapturePointID3 + //blue = 0 + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID1); DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); - - //blueplayer touches m_CapturePointID - DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID); } void CapturePointTest::TestSetup5_SameCapturePointContestedAndTakenOver() { - //contested same, player1 touches the contested - //redPlayer touches m_CapturePointID2 + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID1); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); + //contested point DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); } void CapturePointTest::TestSetup6_Team1CapturedTheLastPointAndWon() { - //TODO: this should be in UPDATE instead - - //redPlayer touches m_CapturePointID2 + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID4); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); - - //redPlayer touches m_CapturePointID - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); - - //blueplayer does nothing + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID1); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID0); } void CapturePointTest::TestSetup7() { @@ -286,146 +267,129 @@ void CapturePointTest::DoLeaveEvent(EntityID whoDidSomething, EntityID onWhatObj } void CapturePointTest::TestSuccess1() { //TestSetup1_OnePlayerOnCapturePoint - - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; if (ownedByID3 == m_RedTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess2() { //TestSetup2_TwoPlayersOnCapturePoint - int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; - if (ownedByID3 == m_RedTeam && ownedByID1 == m_BlueTeam) - TestSucceeded = true; + if (NumLoops == 95) { + int ownedByID1 = m_World->GetComponent(m_CapturePointID1, "Team")["Team"]; + int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + if (ownedByID1 == m_BlueTeam && ownedByID2 == 0 && ownedByID3 == m_RedTeam) + TestSucceeded = true; + } } void CapturePointTest::TestSuccess3() { //TestSetup3_NoPlayersOnCapturePoint - //only do this test if were at the final loopcount - //if any capturePoint changed then, its a failure else a success if (NumLoops == 95) { TestSucceeded = true; - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID1, "Team")["Team"]; int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; - if (ownedByID1 != m_BlueTeam || ownedByID2 == m_RedTeam || ownedByID2 == m_BlueTeam || ownedByID3 !=m_RedTeam) - TestSucceeded = false; + if (ownedByID1 == 0 && ownedByID2 == 0 && ownedByID3 == 0) + TestSucceeded = true; } } void CapturePointTest::TestSuccess4() { + //blue = 0 //TestSetup4_TwoCapturePointsBeingCaptured - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; - int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID1, "Team")["Team"]; int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; if (ownedByID1 == m_BlueTeam && ownedByID3 == m_RedTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess5() { + //blue = 0 //TestSetup5_SameCapturePointContestedAndTakenOver - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID1, "Team")["Team"]; int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; - if (ownedByID1 == m_BlueTeam && ownedByID2 == m_RedTeam && ownedByID3 == m_RedTeam) + if (ownedByID3 == m_RedTeam && ownedByID2 == m_RedTeam && ownedByID1 == m_BlueTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess6() { //NOTE: the actual win-event will have to be manually checked if it triggered or not //TestSetup6_Team1CapturedTheLastPointAndWon - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + int ownedByID0 = m_World->GetComponent(m_CapturePointID0, "Team")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID1, "Team")["Team"]; int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; - if (ownedByID1 == m_RedTeam && ownedByID2 == m_RedTeam && ownedByID3 == m_RedTeam) + int ownedByID4 = m_World->GetComponent(m_CapturePointID4, "Team")["Team"]; + if (ownedByID1 == m_RedTeam && ownedByID2 == m_RedTeam && ownedByID3 == m_RedTeam && ownedByID4 == m_RedTeam) TestSucceeded = true; } void CapturePointTest::TestSuccess7() { - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + //blue = 0 + int ownedByID0 = m_World->GetComponent(m_CapturePointID0, "Team")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID1, "Team")["Team"]; int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + int ownedByID4 = m_World->GetComponent(m_CapturePointID4, "Team")["Team"]; - if (NumLoops < 20 && ownedByID1 == m_BlueTeam & ownedByID3 == m_RedTeam) { - phase1Success = true; - } - if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == m_RedTeam) { - phase2Success = true; - } - if (NumLoops < 60 && NumLoops > 40 && ownedByID1 == m_RedTeam) { - phase3Success = true; - } - if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != m_BlueTeam) { - phase4Success = true; - } + // //red has 1,2,3,4 - blue tries to take 2... when it only has 0 if (NumLoops == 99) { - if (phase1Success && phase2Success && phase3Success &&phase4Success) + if (ownedByID0 == m_BlueTeam && ownedByID1 == m_RedTeam && ownedByID2 == m_RedTeam && ownedByID3 == m_RedTeam && ownedByID4 == m_RedTeam) TestSucceeded = true; } } void CapturePointTest::TestSuccess8() { - int ownedByID1 = m_World->GetComponent(m_CapturePointID, "Team")["Team"]; + //blue = 4 + int ownedByID0 = m_World->GetComponent(m_CapturePointID0, "Team")["Team"]; + int ownedByID1 = m_World->GetComponent(m_CapturePointID1, "Team")["Team"]; int ownedByID2 = m_World->GetComponent(m_CapturePointID2, "Team")["Team"]; int ownedByID3 = m_World->GetComponent(m_CapturePointID3, "Team")["Team"]; + int ownedByID4 = m_World->GetComponent(m_CapturePointID4, "Team")["Team"]; - if (NumLoops < 20 && ownedByID3 == m_BlueTeam & ownedByID1 == m_RedTeam) { - phase1Success = true; - } - if (NumLoops < 40 && NumLoops > 20 && ownedByID2 == m_RedTeam) { - phase2Success = true; - } - if (NumLoops < 60 && NumLoops > 40 && ownedByID3 == m_RedTeam) { - phase3Success = true; - } - if (NumLoops < 90 && NumLoops > 60 && ownedByID2 != m_BlueTeam) { - phase4Success = true; - } - + //red has 0,1,2,3 - blue tries to take 2... when it only has 0 if (NumLoops == 99) { - if (phase1Success && phase2Success && phase3Success &&phase4Success) + if (ownedByID0 == m_RedTeam && ownedByID1 == m_RedTeam && ownedByID2 == m_RedTeam && ownedByID3 == m_RedTeam && ownedByID4 == m_BlueTeam) TestSucceeded = true; } } void CapturePointTest::UpdateTest7() { - //loop 1 = team1 has 3, team 2 has 1 - //loop 20 = team1 takes 2, team 1 leaves 1 -> team1 next = 1, team2 next = still 2 + //blue = 0 if (NumLoops == 20) { //leave previous - DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID); - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID3); + DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID0); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID4); - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID1); } - //loop 40 = team1 takes 1, team2:s next cap point should now be 1 (instead of 2) if (NumLoops == 40) { //leave previous, take next - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID2); - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID3); + DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID1); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID1); } - //loop 60 = team2 tries to take 2, this shouldnt work now + //red has 1,2,3,4 - blue tries to take 2... when it only has 0 if (NumLoops == 60) { - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID2); } } void CapturePointTest::UpdateTest8() { - //2 owns 3 - //1 owns 1 - - //loop 20 = team1 takes 2, team 1 leaves 1 -> team1 next = 1, team2 next = still 2 + //blue = 4 if (NumLoops == 20) { //leave previous - DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID3); - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID0); + DoLeaveEvent(m_BlueTeam, m_CapturePointID4); - DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID1); + DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID3); } - //loop 40 = team1 takes 3, team2:s next cap point should now be 1 (instead of 2) if (NumLoops == 40) { //leave previous, take next - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID2); + DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID1); + DoLeaveEvent(m_BlueTeamPlayer, m_CapturePointID3); + DoTouchEvent(m_RedTeamPlayer, m_CapturePointID2); DoTouchEvent(m_RedTeamPlayer, m_CapturePointID3); } - //loop 60 = team2 tries to take 2, this shouldnt work now + //red has 0,1,2,3 - blue tries to take 2... when it only has 0 if (NumLoops == 60) { - DoLeaveEvent(m_RedTeamPlayer, m_CapturePointID3); DoTouchEvent(m_BlueTeamPlayer, m_CapturePointID2); } } diff --git a/src/Tests/CapturePointTest.h b/src/Tests/CapturePointTest.h index 69f63fcd..54bdc55c 100644 --- a/src/Tests/CapturePointTest.h +++ b/src/Tests/CapturePointTest.h @@ -57,9 +57,8 @@ private: EventBroker* m_EventBroker; World* m_World; SystemPipeline* m_SystemPipeline; - EntityID m_RedTeamPlayer, m_BlueTeamPlayer, m_CapturePointID, m_CapturePointID2, m_CapturePointID3; + EntityID m_RedTeamPlayer, m_BlueTeamPlayer, m_CapturePointID0, m_CapturePointID1, m_CapturePointID2, m_CapturePointID3, m_CapturePointID4; int m_RunTestNumber; - bool phase1Success = false, phase2Success = false, phase3Success = false, phase4Success = false; int m_RedTeam, m_BlueTeam; }; From 29aefc5af275ceda1427c610b5c32667a323ab08 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 20 Jan 2016 16:06:35 +0100 Subject: [PATCH 133/224] Added some more visual CaptureTestState xml files --- resources/Schema/Entities/CaptureTest.xml | 23 +- ...aptureTestState1 => CaptureTestState1.xml} | 0 .../Schema/Entities/CaptureTestState2.xml | 152 +++++++++++++ .../Schema/Entities/CaptureTestState3.xml | 212 ++++++++++++++++++ .../Schema/Entities/CaptureTestState4.xml | 203 +++++++++++++++++ 5 files changed, 582 insertions(+), 8 deletions(-) rename resources/Schema/Entities/{CaptureTestState1 => CaptureTestState1.xml} (100%) create mode 100644 resources/Schema/Entities/CaptureTestState2.xml create mode 100644 resources/Schema/Entities/CaptureTestState3.xml create mode 100644 resources/Schema/Entities/CaptureTestState4.xml diff --git a/resources/Schema/Entities/CaptureTest.xml b/resources/Schema/Entities/CaptureTest.xml index fef6c839..70a8ae14 100644 --- a/resources/Schema/Entities/CaptureTest.xml +++ b/resources/Schema/Entities/CaptureTest.xml @@ -29,7 +29,7 @@ - + @@ -37,7 +37,9 @@ - + + 3 + ../assets/Models/Core/UnitSphere.obj @@ -60,9 +62,11 @@ ../assets/Models/Core/UnitSphere.obj - + - + + 3 + @@ -78,9 +82,11 @@ ../assets/Models/Core/UnitSphere.obj - + - + + 2 + @@ -92,6 +98,7 @@ + 2 3 @@ -121,7 +128,7 @@ 2 - + @@ -139,7 +146,7 @@ 3 - + diff --git a/resources/Schema/Entities/CaptureTestState1 b/resources/Schema/Entities/CaptureTestState1.xml similarity index 100% rename from resources/Schema/Entities/CaptureTestState1 rename to resources/Schema/Entities/CaptureTestState1.xml diff --git a/resources/Schema/Entities/CaptureTestState2.xml b/resources/Schema/Entities/CaptureTestState2.xml new file mode 100644 index 00000000..77673324 --- /dev/null +++ b/resources/Schema/Entities/CaptureTestState2.xml @@ -0,0 +1,152 @@ + + + + + + + + + + + + ../assets/Models/DummyScene.obj + + + + + + + + + 60 + + + + + + + 3 + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 3 + + + + + + + + + + + + + 1 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 2 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 2 + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + diff --git a/resources/Schema/Entities/CaptureTestState3.xml b/resources/Schema/Entities/CaptureTestState3.xml new file mode 100644 index 00000000..99da90a6 --- /dev/null +++ b/resources/Schema/Entities/CaptureTestState3.xml @@ -0,0 +1,212 @@ + + + + + + + + + + + + ../assets/Models/DummyScene.obj + + + + + + + + + 60 + + + + + + + 3 + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 3 + + + + + + + + + + + + + 1 + + + ../assets/Models/Core/UnitSphere.obj + + + + 3 + + + + + + + + + + + + + 2 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + 2 + 4 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + diff --git a/resources/Schema/Entities/CaptureTestState4.xml b/resources/Schema/Entities/CaptureTestState4.xml new file mode 100644 index 00000000..fe30aab9 --- /dev/null +++ b/resources/Schema/Entities/CaptureTestState4.xml @@ -0,0 +1,203 @@ + + + + + + + + + + + + ../assets/Models/DummyScene.obj + + + + + + + + + 60 + + + + + + + 3 + + + + + + + + + + + + + + ../assets/Models/Core/UnitSphere.obj + + + + 3 + + + + + + + + + + + + + 1 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 2 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 4 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + From 25d2aa34644b50d9ae23169e75616eba06523267 Mon Sep 17 00:00:00 2001 From: Jocke Date: Wed, 20 Jan 2016 16:27:23 +0100 Subject: [PATCH 134/224] =?UTF-8?q?"Supporting"=20spectators.=20Using=20a?= =?UTF-8?q?=20vector=20for=20connected=20units=20as=20we=20do=20not=20inte?= =?UTF-8?q?rpret=20as=20players.=20=E2=80=9C=E2=80=9C=E2=80=9D=CC=BF=20?= =?UTF-8?q?=CC=BF=20=CC=BF=20=CC=BF=20=CC=BF=E2=80=99=CC=BF=E2=80=99=CC=B5?= =?UTF-8?q?=CD=87=CC=BF=CC=BF=D0=B7=3D(=E2=80=A2=CC=AA=E2=97=8F)=3D=CE=B5/?= =?UTF-8?q?=CC=B5=CD=87=CC=BF=CC=BF/=CC=BF=20=CC=BF=20=CC=BF=20=CC=BF=20?= =?UTF-8?q?=CC=BF=E2=80=99=E2=80=9C=E2=80=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- include/Engine/Network/Server.h | 3 +- src/Engine/Network/Client.cpp | 5 +- src/Engine/Network/Server.cpp | 90 ++++++++++++++++----------------- 3 files changed, 46 insertions(+), 52 deletions(-) diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 3b871e43..ec1a173a 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -27,9 +27,10 @@ private: boost::asio::ip::udp::endpoint m_ReceiverEndpoint; boost::asio::io_service m_IOService; boost::asio::ip::udp::socket m_Socket; - PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; // Sending messages to client logic + PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; + std::vector m_ConnectedUsers; char readBuffer[INPUTSIZE] = { 0 }; int bytesRead = 0; // time for previouse message diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 83e0d886..b6dea8e3 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -85,11 +85,8 @@ void Client::parseMessageType(Packet& packet) void Client::parseConnect(Packet& packet) { - // Set your own player id - m_PlayerID = packet.ReadPrimitive(); - m_ServerEntityID = packet.ReadPrimitive(); // Map ServerEntityID and your PlayerID - LOG_INFO("%i: I am player: %i", m_PacketID, m_PlayerID); + LOG_INFO("I be connected PogChamp"); } void Client::parsePlayerConnected(Packet & packet) diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index c598f1f1..4a2dcf96 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -8,7 +8,6 @@ Server::~Server() } - void Server::Start(World* world, EventBroker* eventBroker) { m_World = world; @@ -104,11 +103,11 @@ int Server::receive(char * data, size_t length) return length; } -void Server::send(Packet& packet, int playerID) +void Server::send(Packet& packet, int userID) { int bytesSent = m_Socket.send_to( boost::asio::buffer(packet.Data(), packet.Size()), - m_PlayerDefinitions[playerID].Endpoint, + m_ConnectedUsers[userID].Endpoint, 0); } @@ -124,9 +123,9 @@ void Server::send(Packet & packet) void Server::broadcast(Packet& packet) { - for (int i = 0; i < MAXCONNECTIONS; ++i) { - if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { - packet.ChangePacketID(m_PlayerDefinitions[i].PacketID); + for (int i = 0; i < m_ConnectedUsers.size(); i++) { + if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { + packet.ChangePacketID(m_ConnectedUsers[i].PacketID); send(packet, i); } } @@ -165,10 +164,10 @@ void Server::sendSnapshot() void Server::sendPing() { // Prints connected players ping - for (size_t i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { - int ping = 1000 * (m_PlayerDefinitions[i].StopTime - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); - LOG_INFO("Last packetID received %i: Player %i's ping: %i", m_PlayerDefinitions[i].PacketID, i, ping); + for (int i = 0; i < m_ConnectedUsers.size(); i++) { + if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { + int ping = 1000 * (m_ConnectedUsers[i].StopTime - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); + LOG_INFO("Last packetID received %i: User %i's ping: %i", m_ConnectedUsers[i].PacketID, i, ping); } } // Create ping message @@ -186,12 +185,12 @@ void Server::checkForTimeOuts() int startPing = 1000 * m_StartPingTime / static_cast(CLOCKS_PER_SEC); - for (size_t i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { - int stopPing = 1000 * m_PlayerDefinitions[i].StopTime / + for (int i = 0; i < m_ConnectedUsers.size(); i++) { + if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { + int stopPing = 1000 * m_ConnectedUsers[i].StopTime / static_cast(CLOCKS_PER_SEC); if (startPing > stopPing + timeOutTimeMs) { - LOG_INFO("Player %i timed out!", i); + LOG_INFO("User %i timed out!", i); disconnect(i); } } @@ -201,13 +200,13 @@ void Server::checkForTimeOuts() void Server::disconnect(int i) { //broadcast("A player disconnected"); - LOG_INFO("Player %s disconnected/timed out", m_PlayerDefinitions[i].Name.c_str()); - - // Remove enteties and stuff + LOG_INFO("User %s disconnected/timed out", m_PlayerDefinitions[i].Name.c_str()); + // Remove enteties and stuff (When we can remove entity, remove it and tell clients to remove the copy they have) m_PlayerDefinitions[i].Endpoint = boost::asio::ip::udp::endpoint(); m_PlayerDefinitions[i].EntityID = -1; m_PlayerDefinitions[i].Name = ""; m_PlayerDefinitions[i].PacketID = 0; + m_ConnectedUsers.erase(m_ConnectedUsers.begin() + i); } void Server::parseOnInputCommand(Packet& packet) @@ -251,41 +250,38 @@ void Server::parseConnect(Packet& packet) if (GetPlayerIDFromEndpoint(m_ReceiverEndpoint) != -1) { return; } - - // Find an empty spot to put the player in - for (int i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() == boost::asio::ip::address()) { - // Create new player - m_PlayerDefinitions[i].EntityID = createPlayer(); - m_PlayerDefinitions[i].Endpoint = m_ReceiverEndpoint; - m_PlayerDefinitions[i].Name = packet.ReadString(); - m_PlayerDefinitions[i].PacketID = 0; - - m_PlayerDefinitions[i].StopTime = std::clock(); - - LOG_INFO("Player \"%s\" connected on IP: %s", m_PlayerDefinitions[i].Name.c_str(), m_PlayerDefinitions[i].Endpoint.address().to_string().c_str()); - - // Send a message to the player that connected - Packet packet(MessageType::Connect, m_PlayerDefinitions[i].PacketID); - packet.WritePrimitive(i); // Player ID - packet.WritePrimitive(m_PlayerDefinitions[i].EntityID); // Entity ID - send(packet, i); - - // Send notification that a player has connected - Packet notificationPacket(MessageType::PlayerConnected); - broadcast(notificationPacket); - - break; + for (int i = 0; i < m_ConnectedUsers.size(); i++) { + if (m_ConnectedUsers[i].Endpoint.address() == m_ReceiverEndpoint.address() && + m_ConnectedUsers[i].Endpoint.port() == m_ReceiverEndpoint.port()) { + // Already connected + return; } } + // Create a new player + PlayerDefinition pd; + pd.EntityID = 0; // Overlook this + pd.Endpoint = m_ReceiverEndpoint; + pd.Name = packet.ReadString(); + pd.PacketID = 0; + pd.StopTime = std::clock(); + m_ConnectedUsers.push_back(pd); + LOG_INFO("Spectator \"%s\" connected on IP: %s", pd.Name.c_str(), pd.Endpoint.address().to_string().c_str()); + + // Send a message to the player that connected + Packet connnectPacket(MessageType::Connect, m_ConnectedUsers[m_ConnectedUsers.size() - 1].PacketID); + send(connnectPacket); + + // Send notification that a player has connected + Packet notificationPacket(MessageType::PlayerConnected); + broadcast(notificationPacket); } void Server::parseDisconnect() { LOG_INFO("%i: Parsing disconnect", m_PacketID); - for (int i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address()) { + for (int i = 0; i < m_ConnectedUsers.size(); i++) { + if (m_ConnectedUsers[i].Endpoint.address() == m_ReceiverEndpoint.address()) { disconnect(i); break; } @@ -307,9 +303,9 @@ void Server::parseClientPing() void Server::parseServerPing() { - for (int i = 0; i < MAXCONNECTIONS; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address()) { - m_PlayerDefinitions[i].StopTime = std::clock(); + for (int i = 0; i < m_ConnectedUsers.size(); i++) { + if (m_ConnectedUsers[i].Endpoint.address() == m_ReceiverEndpoint.address()) { + m_ConnectedUsers[i].StopTime = std::clock(); break; } } From 3376f4a16ee10fbe5ea6d11b44d12a086ea061bf Mon Sep 17 00:00:00 2001 From: stiffly Date: Wed, 20 Jan 2016 16:27:53 +0100 Subject: [PATCH 135/224] Added server has timed out logic to client. (>'')> --- include/Engine/Network/Client.h | 5 ++-- include/Engine/Network/Network.h | 1 + include/Engine/Network/Server.h | 2 +- src/Engine/Network/Client.cpp | 40 +++++++++++++++++++++----------- src/Engine/Network/Server.cpp | 3 +-- 5 files changed, 32 insertions(+), 19 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 73f0eb50..511ce5f7 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -48,6 +48,7 @@ private: std::string m_PlayerName; int m_PlayerID = -1; EntityID m_ServerEntityID = std::numeric_limits::max(); + bool m_IsConnected = false; // Server Client Lookup map // Assumes that root node for client and server is EntityID 0. @@ -71,14 +72,14 @@ private: void ping(); void parseMessageType(Packet& packet); void updateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType); - void parseConnect(Packet& packet); + void parseConnect(Packet& packet); void parsePlayerConnected(Packet& packet); void parsePing(); void parseServerPing(); void InterpolateFields(Packet & packet, const ComponentInfo & componentInfo, const EntityID & entityID, const std::string & componentType); void parseSnapshot(Packet& packet); void identifyPacketLoss(); - bool isConnected(); + bool hasServerTimedOut(); EntityID createPlayer(); void sendInputCommands(); // Mapping Logic diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index cb86b941..1464a96f 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -7,6 +7,7 @@ #define MAXCONNECTIONS 8 #define INPUTSIZE 4097 +#define TIMEOUTMS 15000 class Network { diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 3b871e43..2f21816a 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -11,7 +11,7 @@ #include "Network/PlayerDefinition.h" #include "Core/World.h" #include "Core/EventBroker.h" -#include "Network/Network.h" +#include "../Network/Network.h" #include "Input/EInputCommand.h" #include "Core/EPlayerDamage.h" diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 83e0d886..a5c34963 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -35,6 +35,9 @@ void Client::Update() { m_EventBroker->Process(); readFromServer(); + if (m_IsConnected) { + hasServerTimedOut(); + } } void Client::readFromServer() @@ -86,10 +89,8 @@ void Client::parseMessageType(Packet& packet) void Client::parseConnect(Packet& packet) { // Set your own player id - m_PlayerID = packet.ReadPrimitive(); - m_ServerEntityID = packet.ReadPrimitive(); // Map ServerEntityID and your PlayerID - LOG_INFO("%i: I am player: %i", m_PacketID, m_PlayerID); + LOG_INFO("I are connected PogChamp"); } void Client::parsePlayerConnected(Packet & packet) @@ -100,12 +101,18 @@ void Client::parsePlayerConnected(Packet & packet) void Client::parsePing() { - m_DurationOfPingTime = 1000 * (std::clock() - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); - LOG_INFO("%i: response time with ctime(ms): %f", m_PacketID, m_DurationOfPingTime); + } void Client::parseServerPing() { + // Might miss connect message so set it here instead. + m_IsConnected = true; + // Time since last ping was received + m_DurationOfPingTime = 1000 * (std::clock() - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); + LOG_INFO("%i: response time with ctime(ms): %f", m_PacketID, m_DurationOfPingTime); + m_StartPingTime = std::clock(); + Packet packet(MessageType::ServerPing, m_SendPacketID); packet.WriteString("Ping recieved"); send(packet); @@ -238,16 +245,18 @@ void Client::connect() void Client::disconnect() { + m_PreviousPacketID = 0; + m_PacketID = 0; Packet packet(MessageType::Disconnect, m_SendPacketID); send(packet); } void Client::ping() { - Packet packet(MessageType::Connect, m_SendPacketID); - packet.WriteString("Ping"); - m_StartPingTime = std::clock(); - send(packet); + //Packet packet(MessageType::Connect, m_SendPacketID); + //packet.WriteString("Ping"); + //m_StartPingTime = std::clock(); + //send(packet); } bool Client::OnInputCommand(const Events::InputCommand & e) @@ -290,12 +299,15 @@ void Client::identifyPacketLoss() } } -bool Client::isConnected() +bool Client::hasServerTimedOut() { - if (m_PlayerID != -1) { - if (m_PlayerDefinitions[m_PlayerID].EntityID != -1) { - return true; - } + // Time in ms + float timeSincePing = 1000 * (std::clock() - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); + if (timeSincePing > TIMEOUTMS) { + // Clear everything and go to menu. + LOG_INFO("Server has timed out, returning to menu, Beep Boop."); + m_IsConnected = false; + return true; } return false; } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index c598f1f1..ec593cb7 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -182,7 +182,6 @@ void Server::sendPing() void Server::checkForTimeOuts() { - int timeOutTimeMs = 5000; int startPing = 1000 * m_StartPingTime / static_cast(CLOCKS_PER_SEC); @@ -190,7 +189,7 @@ void Server::checkForTimeOuts() if (m_PlayerDefinitions[i].Endpoint.address() != boost::asio::ip::address()) { int stopPing = 1000 * m_PlayerDefinitions[i].StopTime / static_cast(CLOCKS_PER_SEC); - if (startPing > stopPing + timeOutTimeMs) { + if (startPing > stopPing + TIMEOUTMS) { LOG_INFO("Player %i timed out!", i); disconnect(i); } From 35876f6425b8130b35a808071585035f35836ed6 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 20 Jan 2016 16:37:10 +0100 Subject: [PATCH 136/224] Removed membervariable m_NextPossibleCapturePointand added it as local instead --- include/Game/Systems/CapturePointSystem.h | 1 - resources/Schema/Entities/Empty.xml | 48 +---------------------- src/Game/Systems/CapturePointSystem.cpp | 21 +++++----- 3 files changed, 12 insertions(+), 58 deletions(-) diff --git a/include/Game/Systems/CapturePointSystem.h b/include/Game/Systems/CapturePointSystem.h index 542d80d5..2d28c003 100644 --- a/include/Game/Systems/CapturePointSystem.h +++ b/include/Game/Systems/CapturePointSystem.h @@ -44,7 +44,6 @@ private: //std::vector - std::map m_NextPossibleCapturePoint; const double m_CaptureTimeToTakeOver = 15.0; //vectors which will keep track of enter/leave changes diff --git a/resources/Schema/Entities/Empty.xml b/resources/Schema/Entities/Empty.xml index d550bbfe..6efd8318 100644 --- a/resources/Schema/Entities/Empty.xml +++ b/resources/Schema/Entities/Empty.xml @@ -5,52 +5,6 @@ - - - - - - - - - - - - - - - -0.049999997019767761 - - - ../assets/Models/Core/UnitBox.obj - - - - - - - - - - - - - - - - - - - - - - - ../assets/Models/DummyScene.obj - - - - - - + diff --git a/src/Game/Systems/CapturePointSystem.cpp b/src/Game/Systems/CapturePointSystem.cpp index e5141cdf..ef68ccdd 100644 --- a/src/Game/Systems/CapturePointSystem.cpp +++ b/src/Game/Systems/CapturePointSystem.cpp @@ -57,34 +57,35 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co } //calculate next possible capturePoint for both teams - m_NextPossibleCapturePoint["Red"] = -1; - m_NextPossibleCapturePoint["Blue"] = -1; + std::map nextPossibleCapturePoint; + nextPossibleCapturePoint["Red"] = -1; + nextPossibleCapturePoint["Blue"] = -1; for (size_t i = 0; i < m_NumberOfCapturePoints; i++) { ComponentWrapper& capturePointOwnedBy = world->GetComponent(m_CapturePointNumberToEntityIDMap[i], "Team"); if ((int)capturePointOwnedBy["Team"] == redTeam && m_RedTeamHomeCapturePoint == 0) { - m_NextPossibleCapturePoint["Red"] = i + 1; + nextPossibleCapturePoint["Red"] = i + 1; } if ((int)capturePointOwnedBy["Team"] == blueTeam && m_BlueTeamHomeCapturePoint == 0) { - m_NextPossibleCapturePoint["Blue"] = i + 1; + nextPossibleCapturePoint["Blue"] = i + 1; } } for (int i = m_NumberOfCapturePoints - 1; i >= 0; i--) { ComponentWrapper& capturePointOwnedBy = world->GetComponent(m_CapturePointNumberToEntityIDMap[i], "Team"); if ((int)capturePointOwnedBy["Team"] == redTeam && m_RedTeamHomeCapturePoint != 0) { - m_NextPossibleCapturePoint["Red"] = i - 1; + nextPossibleCapturePoint["Red"] = i - 1; } if ((int)capturePointOwnedBy["Team"] == blueTeam && m_BlueTeamHomeCapturePoint != 0) { - m_NextPossibleCapturePoint["Blue"] = i - 1; + nextPossibleCapturePoint["Blue"] = i - 1; } } //colorize next possible capturepoint - if (m_NextPossibleCapturePoint["Red"] == capturePointNumber) { + if (nextPossibleCapturePoint["Red"] == capturePointNumber) { entity["Model"]["Color"] = glm::vec4(1, 1, 0, 1); } - if (m_NextPossibleCapturePoint["Blue"] == capturePointNumber) { + if (nextPossibleCapturePoint["Blue"] == capturePointNumber) { entity["Model"]["Color"] = glm::vec4(0, 1, 1, 1); } @@ -127,12 +128,12 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co if (redTeamPlayersStandingInside > 0 && blueTeamPlayersStandingInside == 0) { timerDeltaChange = redTeamPlayersStandingInside*dt; currentTeam = redTeam; - canCapture = m_NextPossibleCapturePoint["Red"] == capturePointNumber; + canCapture = nextPossibleCapturePoint["Red"] == capturePointNumber; } if (redTeamPlayersStandingInside == 0 && blueTeamPlayersStandingInside > 0) { timerDeltaChange = -blueTeamPlayersStandingInside*dt; currentTeam = blueTeam; - canCapture = m_NextPossibleCapturePoint["Blue"] == capturePointNumber; + canCapture = nextPossibleCapturePoint["Blue"] == capturePointNumber; } if (redTeamPlayersStandingInside == 0 && blueTeamPlayersStandingInside == 0) { From a596b8746b77bebebc57db1f61aa2925fbd6b79c Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Wed, 20 Jan 2016 17:32:20 +0100 Subject: [PATCH 137/224] CapturePointTimers are now reset for "inactive" CapturePoints after a capture. --- include/Game/Systems/CapturePointSystem.h | 1 + .../Schema/Entities/CaptureTestState1.xml | 10 +++++----- .../Schema/Entities/CaptureTestState4.xml | 12 +++++++----- src/Game/Systems/CapturePointSystem.cpp | 19 +++++++++++++++++++ 4 files changed, 32 insertions(+), 10 deletions(-) diff --git a/include/Game/Systems/CapturePointSystem.h b/include/Game/Systems/CapturePointSystem.h index 2d28c003..3fac1326 100644 --- a/include/Game/Systems/CapturePointSystem.h +++ b/include/Game/Systems/CapturePointSystem.h @@ -45,6 +45,7 @@ private: //std::vector const double m_CaptureTimeToTakeOver = 15.0; + bool m_ResetTimers = false; //vectors which will keep track of enter/leave changes std::vector> m_ETriggerTouchVector; diff --git a/resources/Schema/Entities/CaptureTestState1.xml b/resources/Schema/Entities/CaptureTestState1.xml index 03b93e81..75b14858 100644 --- a/resources/Schema/Entities/CaptureTestState1.xml +++ b/resources/Schema/Entities/CaptureTestState1.xml @@ -29,7 +29,7 @@ - + @@ -39,6 +39,7 @@ 3 + 6.9158446328696002 ../assets/Models/Core/UnitSphere.obj @@ -58,7 +59,7 @@ - -3.9175623281664684 + -13.234195338196177 1 @@ -79,7 +80,6 @@ - -1.8667072838033221 2 @@ -130,7 +130,7 @@ 2 - + @@ -148,7 +148,7 @@ 3 - + diff --git a/resources/Schema/Entities/CaptureTestState4.xml b/resources/Schema/Entities/CaptureTestState4.xml index fe30aab9..695df52e 100644 --- a/resources/Schema/Entities/CaptureTestState4.xml +++ b/resources/Schema/Entities/CaptureTestState4.xml @@ -29,7 +29,7 @@ - + @@ -37,7 +37,9 @@ - + + 3 + ../assets/Models/Core/UnitSphere.obj @@ -60,7 +62,7 @@ ../assets/Models/Core/UnitSphere.obj - + @@ -78,7 +80,6 @@ ../assets/Models/Core/UnitSphere.obj - @@ -96,7 +97,7 @@ ../assets/Models/Core/UnitSphere.obj - + @@ -110,6 +111,7 @@ + 2 4 diff --git a/src/Game/Systems/CapturePointSystem.cpp b/src/Game/Systems/CapturePointSystem.cpp index ef68ccdd..94ec8d62 100644 --- a/src/Game/Systems/CapturePointSystem.cpp +++ b/src/Game/Systems/CapturePointSystem.cpp @@ -8,12 +8,16 @@ CapturePointSystem::CapturePointSystem(EventBroker* eventBroker) //subscribe/listenTo playerdamage,healthpickup events (using the eventBroker) EVENT_SUBSCRIBE_MEMBER(m_ETriggerTouch, &CapturePointSystem::OnTriggerTouch); EVENT_SUBSCRIBE_MEMBER(m_ETriggerLeave, &CapturePointSystem::OnTriggerLeave); + EVENT_SUBSCRIBE_MEMBER(m_ECaptured, &CapturePointSystem::OnCaptured); } //here all capturepoints will update their component //NOTE: needs to run each frame, since we're possibly modifying the captureTimer for the capturePoints by dt void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, ComponentWrapper& capturePoint, double dt) { + if (m_WinnerWasFound) { + return; + } const int capturePointNumber = capturePoint["CapturePointNumber"]; const bool hasTeamComponent = world->HasComponent(capturePoint.EntityID, "Team"); @@ -81,6 +85,19 @@ void CapturePointSystem::UpdateComponent(World* world, EntityWrapper& entity, Co } } + //reset timers and reset the bool that triggers this + if (m_ResetTimers) { + for (size_t i = 0; i < m_NumberOfCapturePoints; i++) + { + ComponentWrapper& capturePoint = world->GetComponent(m_CapturePointNumberToEntityIDMap[i], "CapturePoint"); + if ((int)capturePoint["CapturePointNumber"] != nextPossibleCapturePoint["Red"] && + (int)capturePoint["CapturePointNumber"] != nextPossibleCapturePoint["Blue"]) { + capturePoint["CaptureTimer"] = 0.0; + } + } + m_ResetTimers = false; + } + //colorize next possible capturepoint if (nextPossibleCapturePoint["Red"] == capturePointNumber) { entity["Model"]["Color"] = glm::vec4(1, 1, 0, 1); @@ -213,5 +230,7 @@ bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e) } bool CapturePointSystem::OnCaptured(const Events::Captured& e) { + //reset the timers in the next update since a capture has changed the "nextCapturePoint" for 1-2 teams + m_ResetTimers = true; return true; } From cd6725317325f3616e90a0bea1325160a4a52587 Mon Sep 17 00:00:00 2001 From: Jocke Date: Wed, 20 Jan 2016 17:41:16 +0100 Subject: [PATCH 138/224] Added logic to go from spectator to player. --- include/Engine/Network/Client.h | 1 + include/Engine/Network/MessageType.h | 3 +- include/Engine/Network/Server.h | 2 +- src/Engine/Network/Client.cpp | 12 ++++++- src/Engine/Network/Server.cpp | 52 +++++++++++++++++++++------- 5 files changed, 55 insertions(+), 15 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 511ce5f7..96511baa 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -82,6 +82,7 @@ private: bool hasServerTimedOut(); EntityID createPlayer(); void sendInputCommands(); + void becomePlayer(); // Mapping Logic // Returns if local EntityID exist in map bool clientServerMapsHasEntity(EntityID clientEntityID); diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index ba9684d9..f0026190 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -13,7 +13,8 @@ enum class MessageType Snapshot, OnInputCommand, OnPlayerDamage, - PlayerConnected + PlayerConnected, + BecomePlayer }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index e4d11334..8aabceba 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -71,7 +71,7 @@ private: void parseClientPing(); void parseServerPing(); void identifyPacketLoss(); - EntityID createPlayer(); + void createPlayer(); int GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint); // Debug event EventRelay m_EInputCommand; diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 5aec3145..8eee335e 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -35,7 +35,7 @@ void Client::Update() { m_EventBroker->Process(); readFromServer(); - if (m_IsConnected) { + if (m_IsConnected) { hasServerTimedOut(); } } @@ -271,6 +271,10 @@ bool Client::OnInputCommand(const Events::InputCommand & e) disconnect(); } return true; + } else if (e.Command == "SwitchToPlayer") { + if (e.Value > 0) { + becomePlayer(); + } } else { m_InputCommandBuffer.push_back(e); //LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); @@ -334,6 +338,12 @@ void Client::sendInputCommands() } } +void Client::becomePlayer() +{ + Packet packet = Packet(MessageType::BecomePlayer, m_SendPacketID); + send(packet); +} + bool Client::clientServerMapsHasEntity(EntityID clientEntityID) { return m_ClientIDToServerID.find(clientEntityID) != m_ClientIDToServerID.end(); diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 71ca7252..8a194c0e 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -89,6 +89,9 @@ void Server::parseMessageType(Packet& packet) case MessageType::OnPlayerDamage: parseOnPlayerDamage(packet); break; + case MessageType::BecomePlayer: + createPlayer(); + break; default: break; } @@ -123,8 +126,8 @@ void Server::send(Packet & packet) void Server::broadcast(Packet& packet) { - for (int i = 0; i < m_ConnectedUsers.size(); i++) { - if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { + for (int i = 0; i < m_ConnectedUsers.size(); i++) { + if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { packet.ChangePacketID(m_ConnectedUsers[i].PacketID); send(packet, i); } @@ -167,7 +170,7 @@ void Server::sendPing() for (int i = 0; i < m_ConnectedUsers.size(); i++) { if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { int ping = 1000 * (m_ConnectedUsers[i].StopTime - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); - LOG_INFO("Last packetID received %i: User %i's ping: %i", m_ConnectedUsers[i].PacketID, i, ping); + LOG_INFO("Last packetID received %i: User %i's ping: %i", m_ConnectedUsers[i].PacketID, i, std::abs(ping)); } } // Create ping message @@ -319,16 +322,41 @@ void Server::identifyPacketLoss() } } -EntityID Server::createPlayer() +void Server::createPlayer() { - EntityID entityID = m_World->CreateEntity(); - ComponentWrapper transform = m_World->AttachComponent(entityID, "Transform"); - transform["Position"] = glm::vec3(-1.5f, 0.f, 0.f); - ComponentWrapper model = m_World->AttachComponent(entityID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; - model["Color"] = glm::vec4(rand()%255 / 255.f, rand()%255 / 255.f, rand() %255 / 255.f, 1.f); - ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); - return entityID; + if (GetPlayerIDFromEndpoint(m_ReceiverEndpoint) != -1) { + // Already connected as player + LOG_WARNING("Already connected!"); + return; + } + int userIndex; + for (userIndex = 0; userIndex < m_ConnectedUsers.size(); userIndex++) { + if (m_ConnectedUsers[userIndex].Endpoint.address() == m_ReceiverEndpoint.address() && + m_ConnectedUsers[userIndex].Endpoint.port() == m_ReceiverEndpoint.port()) { + // Found user + break; + } + } + if (userIndex == m_ConnectedUsers.size()) { + LOG_WARNING("Not a recognized user!"); + return; + } + for (int playerIndex = 0; playerIndex < MAXCONNECTIONS; playerIndex++) { + if (m_PlayerDefinitions[playerIndex].Endpoint.address() == boost::asio::ip::address()) { + m_PlayerDefinitions[playerIndex] = m_ConnectedUsers[userIndex]; + EntityID entityID = m_World->CreateEntity(); + ComponentWrapper transform = m_World->AttachComponent(entityID, "Transform"); + transform["Position"] = glm::vec3(-1.5f, 0.f, 0.f); + ComponentWrapper model = m_World->AttachComponent(entityID, "Model"); + model["Resource"] = "Models/Core/UnitSphere.obj"; + model["Color"] = glm::vec4(rand()%255 / 255.f, rand()%255 / 255.f, rand() %255 / 255.f, 1.f); + ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); + m_PlayerDefinitions[playerIndex].EntityID = entityID; + return; + } + } + LOG_WARNING("Server is full!"); + } int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) From c984f76b2fea45d0e7b67fd3eb44a75df3fcdb55 Mon Sep 17 00:00:00 2001 From: antc13 Date: Wed, 20 Jan 2016 18:36:03 +0100 Subject: [PATCH 139/224] Importing & Reading Custom animation data. TODO: Shaders. --- include/Engine/Rendering/RawModelCustom.h | 9 +- include/Engine/Rendering/Skeleton.h | 2 +- resources/Schema/Entities/Model.xml | 2 +- src/Engine/Editor/EditorSystem.cpp | 6 +- src/Engine/Rendering/RawModelCustom.cpp | 180 ++++++++++++++++++- src/Engine/Rendering/RenderSystem.cpp | 4 +- tools/MayaExporter/MayaExporter/Export.cpp | 13 +- tools/MayaExporter/MayaExporter/Skeleton.cpp | 9 +- tools/MayaExporter/MayaExporter/Skeleton.h | 44 +++-- 9 files changed, 230 insertions(+), 39 deletions(-) diff --git a/include/Engine/Rendering/RawModelCustom.h b/include/Engine/Rendering/RawModelCustom.h index bc85e32c..a3c29f62 100644 --- a/include/Engine/Rendering/RawModelCustom.h +++ b/include/Engine/Rendering/RawModelCustom.h @@ -22,7 +22,7 @@ class RawModel : public Resource friend class ResourceManager; protected: - RawModel(std::string& fileName); + RawModel(std::string fileName); public: ~RawModel(); @@ -74,6 +74,13 @@ private: void ReadMaterialFile(std::string filePath); void ReadMaterials(unsigned int &offset, char* fileData, unsigned int& fileByteSize); void ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize); + + void ReadAnimationFile(std::string filePath); + void ReadAnimationBindPoses(unsigned int &offset, char* fileData, unsigned int& fileByteSize); + void ReadAnimationJoint(unsigned int &offset, char* fileData, unsigned int& fileByteSize); + void ReadAnimationClips(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int numberOfClips); + void ReadAnimationClipSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int clipIndex); + void ReadAnimationKeyFrame(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int numberOfJoints, Skeleton::Animation& animation); //void CreateSkeleton(std::vector> &boneInfo, std::map &boneNameMapping, aiNode* node, int parentID); }; diff --git a/include/Engine/Rendering/Skeleton.h b/include/Engine/Rendering/Skeleton.h index 73d407dd..4a4d507b 100644 --- a/include/Engine/Rendering/Skeleton.h +++ b/include/Engine/Rendering/Skeleton.h @@ -38,9 +38,9 @@ public: , OffsetMatrix(offsetMatrix) { } - int ID; std::string Name; glm::mat4 OffsetMatrix; + int ID; Bone* Parent; std::vector Children; diff --git a/resources/Schema/Entities/Model.xml b/resources/Schema/Entities/Model.xml index 8962d7e1..6534815c 100644 --- a/resources/Schema/Entities/Model.xml +++ b/resources/Schema/Entities/Model.xml @@ -19,7 +19,7 @@ - models/Baljj + models/Baljj.mesh diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 624c4ad6..547a96e1 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -292,21 +292,21 @@ void EditorSystem::createWidget() m_WidgetPlaneX = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneX, "Transform"); m_World->AttachComponent(m_WidgetPlaneX, "Model"); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube"; // 360NoScope widgetPlaneX + m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneX m_WidgetY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetY, "Transform"); m_World->AttachComponent(m_WidgetY, "Model"); m_WidgetPlaneY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneY, "Transform"); m_World->AttachComponent(m_WidgetPlaneY, "Model"); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube"; // 360NoScope widgetPlaneY + m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneY m_WidgetZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetZ, "Transform"); m_World->AttachComponent(m_WidgetZ, "Model"); m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); m_World->AttachComponent(m_WidgetPlaneZ, "Model"); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube"; // 360NoScope widgetPlaneZ + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneZ m_WidgetOrigin = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetOrigin, "Transform"); m_World->AttachComponent(m_WidgetOrigin, "Model"); diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index b7f2a2fd..f7354d92 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -1,9 +1,12 @@ #include "Rendering/RawModelCustom.h" -RawModel::RawModel(std::string& fileName) +RawModel::RawModel(std::string fileName) { + fileName = fileName.erase(fileName.find_last_of("."), fileName.find_last_of(".") - fileName.size()); ReadMeshFile(fileName); ReadMaterialFile(fileName); + ReadAnimationFile(fileName); + int k = 0; } void RawModel::ReadMeshFile(std::string filePath) @@ -53,8 +56,7 @@ void RawModel::ReadVertices(unsigned int& offset, char* fileData, unsigned int& if (offset + m_Vertices.size() * sizeof(Vertex) > fileByteSize) { throw Resource::FailedLoadingException("Reading vertices failed"); } - unsigned int i = sizeof(Vertex); - unsigned int ii = sizeof(unsigned int); + memcpy(&m_Vertices[0], fileData + offset, m_Vertices.size() * sizeof(Vertex)); offset += m_Vertices.size() * sizeof(Vertex); #else @@ -187,6 +189,178 @@ void RawModel::ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned MaterialGroups.push_back(newMaterial); } +void RawModel::ReadAnimationFile(std::string filePath) +{ + char* fileData; + filePath += ".anim"; + std::ifstream in(filePath.c_str(), std::ios_base::binary | std::ios_base::ate); + + if (!in.is_open()) { + //throw Resource::FailedLoadingException("Open animation file failed"); + return; // AJABAJA!!!!!!!! + } + + unsigned int fileByteSize = in.tellg(); + in.seekg(0, std::ios_base::beg); + + fileData = new char[fileByteSize]; + in.read(fileData, fileByteSize); + in.close(); + + unsigned int offset = 0; + if (fileByteSize > 0) { + m_Skeleton = new Skeleton(); + +#ifdef BOOST_LITTLE_ENDIAN + unsigned int numBindPoses = *(unsigned int*)(fileData); + offset += sizeof(unsigned int); + unsigned int numAnimations = *(unsigned int*)(fileData); + offset += sizeof(unsigned int); +#else +#endif + + ReadAnimationBindPoses(offset, fileData, fileByteSize); + ReadAnimationClips(offset, fileData, fileByteSize, numAnimations); + } + delete fileData; +} + +void RawModel::ReadAnimationBindPoses(unsigned int &offset, char* fileData, unsigned int& fileByteSize) +{ +#ifdef BOOST_LITTLE_ENDIAN + unsigned int* numBones = (unsigned int*)(fileData + offset); + offset += sizeof(unsigned int); + + for (unsigned int i = 0; i < *numBones; i++) { + ReadAnimationJoint(offset, fileData, fileByteSize); + } +#else +#endif +} + +void RawModel::ReadAnimationJoint(unsigned int &offset, char* fileData, unsigned int& fileByteSize) +{ +#ifdef BOOST_LITTLE_ENDIAN + if (offset + sizeof(unsigned int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading Joint name length failed"); + } + unsigned int jointNameLength = *(unsigned int*)(fileData + offset); + offset += sizeof(unsigned int); + + if (offset + jointNameLength > fileByteSize) { + throw Resource::FailedLoadingException("Reading Joint name failed"); + } + std::string jointName = (fileData + offset); + offset += jointNameLength; + + if (offset + sizeof(float) * 4 * 4 > fileByteSize) { + throw Resource::FailedLoadingException("Reading Joint offset matrix failed"); + } + glm::mat4 offsetMatrix; + memcpy(&offsetMatrix, fileData + offset, sizeof(float) * 4 * 4); + offset += sizeof(float) * 4 * 4; + + if (offset + sizeof(int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading Joint ID failed"); + } + int jointID = *(int*)(fileData + offset); + offset += sizeof(int); + + if (offset + sizeof(int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading Joint Parent ID failed"); + } + int jointParentID = *(int*)(fileData + offset); + offset += sizeof(int); + + // Adding joint to the Skeleton + m_Skeleton->CreateBone(jointID, jointParentID, jointName, offsetMatrix); + + +#else +#endif +} + +void RawModel::ReadAnimationClips(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int numberOfClips) +{ + for (unsigned int i = 0; i < numberOfClips; i++) { + ReadAnimationClipSingle(offset, fileData, fileByteSize, i); + } +} + +void RawModel::ReadAnimationClipSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int clipIndex) +{ +#ifdef BOOST_LITTLE_ENDIAN + Skeleton::Animation newAnimation; + + if (offset + sizeof(unsigned int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationClip name length failed"); + } + unsigned int clipNameLength = *(unsigned int*)(fileData + offset); + offset += sizeof(unsigned int); + + if (offset + clipNameLength > fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationClip name failed"); + } + newAnimation.Name = (fileData + offset); + offset += clipNameLength; + + if (offset + sizeof(float) > fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationClip duration failed"); + } + + newAnimation.Duration = *(float*)(fileData + offset); + offset += sizeof(float); + + if (offset + sizeof(unsigned int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationClip NrOfKeyframes failed"); + } + unsigned int nrOfKeyframes = *(unsigned int*)(fileData + offset); + offset += sizeof(unsigned int); + + if (offset + sizeof(unsigned int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationClip NrOfJoints failed"); + } + unsigned int nrOfJoints = *(unsigned int*)(fileData + offset); + offset += sizeof(unsigned int); + + newAnimation.Keyframes.reserve(nrOfKeyframes); + for (unsigned int i = 0; i < nrOfKeyframes; i++) { + ReadAnimationKeyFrame(offset, fileData, fileByteSize, nrOfJoints, newAnimation); + } + m_Skeleton->Animations[newAnimation.Name] = newAnimation; +#else +#endif +} + +void RawModel::ReadAnimationKeyFrame(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int nrOfJoints, Skeleton::Animation& animation) +{ + Skeleton::Animation::Keyframe newKeyFrame; + + if (offset + sizeof(int) > fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationKeyFrame index failed"); + } + newKeyFrame.Index = *(int*)(fileData + offset); + offset += sizeof(int); + + if (offset + sizeof(float) > fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationKeyFrame time failed"); + } + newKeyFrame.Time = *(float*)(fileData + offset); + offset += sizeof(float); + + if (offset + sizeof(Skeleton::Animation::Keyframe::BoneProperty) * nrOfJoints> fileByteSize) { + throw Resource::FailedLoadingException("Reading AnimationKeyFrame joints failed"); + } + + Skeleton::Animation::Keyframe::BoneProperty newBone; + for (unsigned int i = 0; i < nrOfJoints; i++) { + memcpy(&newBone, (fileData + offset), sizeof(Skeleton::Animation::Keyframe::BoneProperty)); + offset += sizeof(Skeleton::Animation::Keyframe::BoneProperty); + newKeyFrame.BoneProperties[i] = newBone; + } + animation.Keyframes.push_back(newKeyFrame); +} + RawModel::~RawModel() { diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 1b016f73..2a6a49c2 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -96,10 +96,10 @@ void RenderSystem::fillModels(std::list>& jobs, World model = ResourceManager::Load<::Model, true>(resource); } catch (const Resource::StillLoadingException&) { //continue; - model = ResourceManager::Load<::Model>("Models/coolCube"); // 360NoScope StillLoading mesh + model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); // 360NoScope StillLoading mesh } catch (const std::exception&) { try { - model = ResourceManager::Load<::Model>("Models/coolCube"); // 360NoScope Error mesh + model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); // 360NoScope Error mesh } catch (const std::exception&) { continue; } diff --git a/tools/MayaExporter/MayaExporter/Export.cpp b/tools/MayaExporter/MayaExporter/Export.cpp index 1db753d7..d25faa4c 100644 --- a/tools/MayaExporter/MayaExporter/Export.cpp +++ b/tools/MayaExporter/MayaExporter/Export.cpp @@ -11,7 +11,9 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) MGlobal::displayError(MString() + "Export::Meshes() got no pathName. Do not know where to write file"); return false; } - + MSelectionList selectedOnStart; + MGlobal::getActiveSelectionList(selectedOnStart); + MObjectArray Objects; if (selectedOnly) { // Retrieving the objects we currently have selected @@ -36,18 +38,14 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) MFnDependencyNode thisNode(node); MPlugArray connections; thisNode.findPlug("inMesh").connectedTo(connections, true, true); - bool next = false; for (unsigned int i = 0; i < connections.length(); i++) { if (connections[i].node().apiType() == MFn::kSkinClusterFilter) { - next = true; - break; + MGlobal::select(node); + MGlobal::executeCommand("gotoBindPose"); } } - if (next) - continue; - Objects.append(node); } } @@ -139,6 +137,7 @@ void Export::WriteAnimData(std::string pathName) int size = allBindPoses.size(); m_AnimFile.writeToFiles(&size); + size = allAnimations.size(); m_AnimFile.writeToFiles(&size); diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp index 0497aa31..9f887561 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.cpp +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -70,6 +70,7 @@ Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int e Animation returnData; double oneDivSixty = 1 / 60.0; returnData.Name = animationName; + returnData.nameLength = animationName.size() + 1; returnData.Duration = (endFrame - startFrame) * oneDivSixty; MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); @@ -132,7 +133,7 @@ Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int e } int currentFrame = startFrame; - while (currentFrame != endFrame) { + while (currentFrame != endFrame + 1) { // ANDREAS Animation::Keyframe thisKeyFrame; thisKeyFrame.Index = currentFrame - startFrame; thisKeyFrame.Time = thisKeyFrame.Index * oneDivSixty; @@ -188,7 +189,6 @@ std::vector Skeleton::GetBindPoses() MItDag jointIt(MItDag::TraversalType::kDepthFirst, MFn::kJoint); BindPoseSkeletonNode SkeletonStorage; - while (!jointIt.isDone()) { MFnTransform MayaJoint(jointIt.currentItem()); BindPoseSkeletonNode::BindPoseJoint NewJoint; @@ -227,7 +227,8 @@ std::vector Skeleton::GetBindPoses() } NewJoint.Name = MayaJoint.name().asChar(); - + NewJoint.NameLength = MayaJoint.name().length() + 1; + NewJoint.ID = SkeletonStorage.Joints.size(); //double tmp[3]; //((MTransformationMatrix)Matrix).eulerRotation().asVector().get(tmp); //NewJoint.Rotation[0] = tmp[0]; @@ -242,9 +243,9 @@ std::vector Skeleton::GetBindPoses() //NewJoint.Translation[1] = tmp[1]; //NewJoint.Translation[2] = tmp[2]; SkeletonStorage.Joints.push_back(NewJoint); + SkeletonStorage.numBones++; jointIt.next(); } - m_AllSkeletons.push_back(SkeletonStorage); return m_AllSkeletons; diff --git a/tools/MayaExporter/MayaExporter/Skeleton.h b/tools/MayaExporter/MayaExporter/Skeleton.h index dda0cfea..6a288c8a 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.h +++ b/tools/MayaExporter/MayaExporter/Skeleton.h @@ -13,32 +13,35 @@ public: { struct JointProperty { - int ID; - float Position[3]; - float Rotation[4]; - float Scale[3]; + int ID = 0; + float Position[3]{ 0 }; + float Rotation[4]{ 0 }; + float Scale[3]{ 0 }; }; - int Index; - double Time; + int Index = 0; + float Time = 0; std::vector JointProperties; }; std::string Name; - double Duration; - int NumKeyFrames; - int NumberOfJoints; + int nameLength = 0; + float Duration = 0; + int NumKeyFrames = 0; + int NumberOfJoints = 0; std::vector Keyframes; virtual void WriteBinary(std::ostream& out) { + out.write((char*)&nameLength, sizeof(int)); out.write(Name.c_str(), Name.size() + 1); - out.write((char*)&Duration, sizeof(double)); + out.write((char*)&Duration, sizeof(float)); out.write((char*)&NumKeyFrames, sizeof(int)); out.write((char*)&NumberOfJoints, sizeof(int)); + //Här under loopas alla key frames igenom for (auto aKeyframe : Keyframes) { out.write((char*)&aKeyframe.Index, sizeof(int)); - out.write((char*)&aKeyframe.Time, sizeof(double)); + out.write((char*)&aKeyframe.Time, sizeof(float)); for (auto aJoint : aKeyframe.JointProperties) { out.write((char*)&aJoint.ID, sizeof(int)); out.write((char*)aJoint.Position, sizeof(float) * 3); @@ -72,20 +75,24 @@ class BindPoseSkeletonNode : public OutputData { public: struct BindPoseJoint { - int ParentID; + int NameLength; std::string Name; - float OffsetMatrix[4][4]; + float OffsetMatrix[4][4]{ 0 }; + int ID = 0; + int ParentID = 0; }; - + int numBones = 0; std::string Name; std::vector Joints; virtual void WriteBinary(std::ostream& out) { - out.write(Name.c_str(), Name.size() + 1); + out.write((char*)&numBones, sizeof(int)); for (auto Joint:Joints) { + out.write((char*)&Joint.NameLength, sizeof(int)); out.write(Joint.Name.c_str(), Joint.Name.size() + 1); out.write((char*)&Joint.OffsetMatrix, sizeof(float) * 4 * 4); + out.write((char*)&Joint.ID, sizeof(int)); out.write((char*)&Joint.ParentID, sizeof(int)); } @@ -93,16 +100,19 @@ public: virtual void WriteASCII(std::ostream& out) const { - out << "Bind Pose: " << Name << endl; + out << "Bind Pose: " << Name << " _ not in binary" << endl; + out << "numberOfBones: " << numBones << endl; for (auto Joint : Joints) { - out << Joint.Name << endl; + out << "Joint NameLength " << Joint.NameLength << endl; + out << "Joint name " << Joint.Name << endl; for (int i = 0; i < 4; i++) { for (int j = 0; j < 4; j++){ out << Joint.OffsetMatrix[i][j] << " "; } out << endl; } + out << Joint.ID << endl; out << Joint.ParentID << endl; } }; From f3bfe388af515eb0997c144e07d78c1cfa3b0b19 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Thu, 21 Jan 2016 10:16:03 +0100 Subject: [PATCH 140/224] Clean up --- assets | 2 +- include/Engine/Rendering/Font.h | 2 +- include/Engine/Rendering/TextRenderer.h | 13 +-- resources/Schema/Entities/RenderingWorld.xml | 84 +++++++++++++++++--- src/Engine/Rendering/Font.cpp | 29 ++++--- src/Engine/Rendering/TextRenderer.cpp | 24 ++---- 6 files changed, 99 insertions(+), 55 deletions(-) diff --git a/assets b/assets index 6ffb46e1..b6592dbb 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 6ffb46e155c8f013241cd1507098c94900ec2448 +Subproject commit b6592dbb0216bbac00ccea43a0afd0e27d0b185e diff --git a/include/Engine/Rendering/Font.h b/include/Engine/Rendering/Font.h index 5a1a6bdd..89a21eb0 100644 --- a/include/Engine/Rendering/Font.h +++ b/include/Engine/Rendering/Font.h @@ -25,7 +25,7 @@ public: GLuint Advance; // Offset to advance to next glyph }; - FT_Face Face; + int FontSize = 16; diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextRenderer.h index 8094dda0..cdc1d8c7 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextRenderer.h @@ -2,8 +2,7 @@ #define TextRenderer_h__ #include -#include FT_FREETYPE_H -#include FT_GLYPH_H +#include FT_FREETYPE_H #include "../OpenGL.h" #include "../GLM.h" @@ -21,17 +20,11 @@ public: void Draw(RenderScene& scene); private: + void renderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); + Font* font; - GLuint VAO, VBO; - - void RenderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); - ShaderProgram* m_TextProgram; - - std::string text = ""; - - int counter = 0; }; diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 56bbd794..69b18982 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -11,14 +11,12 @@ ActionCamera - Models/Camera.obj - false - - + + @@ -81,7 +79,7 @@ - + @@ -96,7 +94,20 @@ - + + + + + + 8 + + + + + + + + @@ -109,7 +120,20 @@ - + + + + + + 8 + + + + + + + + @@ -122,7 +146,20 @@ - + + + + + + 8 + + + + + + + + @@ -134,7 +171,19 @@ - + + + + + 8 + + + + + + + + @@ -160,8 +209,8 @@ false - - + + @@ -192,7 +241,18 @@ - + + + + + + + + + Models/Core/UnitCube.obj + + + diff --git a/src/Engine/Rendering/Font.cpp b/src/Engine/Rendering/Font.cpp index 8af013e8..940694ea 100644 --- a/src/Engine/Rendering/Font.cpp +++ b/src/Engine/Rendering/Font.cpp @@ -15,6 +15,10 @@ Font::Font(std::string path) filePath = (*it).c_str(); it++; if (it != tok.end()) { + if((*it).c_str() == "") { + throw std::runtime_error(""); + } + try { FontSize = boost::lexical_cast((*it).c_str()); } catch (boost::bad_lexical_cast const&) { @@ -28,21 +32,22 @@ Font::Font(std::string path) FT_Library library; + FT_Face face; if (FT_Init_FreeType(&library)) { LOG_ERROR("FreeType error: init failed"); throw std::runtime_error("");; } - if (FT_New_Face(library, filePath.c_str(), 0, &Face)) { + if (FT_New_Face(library, filePath.c_str(), 0, &face)) { LOG_ERROR("FreeType error: loading font"); throw std::runtime_error("");; } - FT_Set_Char_Size(Face, 0, FontSize*64, 300, 300); // temp - FT_Set_Pixel_Sizes(Face, 0, FontSize); // + FT_Set_Char_Size(face, 0, FontSize*64, 300, 300); // temp + FT_Set_Pixel_Sizes(face, 0, FontSize); // - if (FT_Load_Char(Face, 'X', FT_LOAD_RENDER)) { + if (FT_Load_Char(face, 'X', FT_LOAD_RENDER)) { LOG_ERROR("FreeType error: loading char"); throw std::runtime_error("");; } @@ -53,7 +58,7 @@ Font::Font(std::string path) //Load character glyph - if (FT_Load_Char(Face, c, FT_LOAD_RENDER)) { + if (FT_Load_Char(face, c, FT_LOAD_RENDER)) { continue; } @@ -66,12 +71,12 @@ Font::Font(std::string path) GL_TEXTURE_2D, 0, GL_RED, - Face->glyph->bitmap.width, - Face->glyph->bitmap.rows, + face->glyph->bitmap.width, + face->glyph->bitmap.rows, 0, GL_RED, GL_UNSIGNED_BYTE, - Face->glyph->bitmap.buffer + face->glyph->bitmap.buffer ); // Set texture options glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); @@ -81,22 +86,22 @@ Font::Font(std::string path) // Now store character for later use Character character = { texture, - glm::ivec2(Face->glyph->bitmap.width, Face->glyph->bitmap.rows), - glm::ivec2(Face->glyph->bitmap_left, Face->glyph->bitmap_top), - Face->glyph->advance.x + glm::ivec2(face->glyph->bitmap.width, face->glyph->bitmap.rows), + glm::ivec2(face->glyph->bitmap_left, face->glyph->bitmap_top), + face->glyph->advance.x }; m_Characters.insert(std::pair(c, character)); } + FT_Done_Face(face); FT_Done_FreeType(library); GLERROR("Font Load"); } Font::~Font() { - FT_Done_Face(Face); for (auto c : m_Characters) { glDeleteTextures(1, &c.second.TextureID); } diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextRenderer.cpp index 0bd58465..a8dfc083 100644 --- a/src/Engine/Rendering/TextRenderer.cpp +++ b/src/Engine/Rendering/TextRenderer.cpp @@ -35,25 +35,17 @@ void TextRenderer::Draw(RenderScene& scene) auto textJob = std::dynamic_pointer_cast(job); if (textJob) { - RenderText(textJob->Content, textJob->Resource, textJob->Alignment, textJob->Color, textJob->Matrix, scene.Camera->ProjectionMatrix(), scene.Camera->ViewMatrix()); + renderText(textJob->Content, textJob->Resource, textJob->Alignment, textJob->Color, textJob->Matrix, scene.Camera->ProjectionMatrix(), scene.Camera->ViewMatrix()); } } } -void TextRenderer::RenderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) +void TextRenderer::renderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) { GLfloat penX = 0; GLfloat penY = 0; float scale = 1.0/font->FontSize; - - FT_Bool use_kerning = FT_HAS_KERNING(font->Face); - FT_UInt previous = 0; - FT_UInt num_glyphs = 0; - FT_UInt glyph_index; - - FT_Vector pos[128]; - GLfloat stringWidth = 0.f; for (std::string::const_iterator c = text.begin(); c != text.end(); c++) { @@ -67,10 +59,7 @@ void TextRenderer::RenderText(std::string text, Font* font, TextJob::AlignmentEn penX = -stringWidth; } else { penX = 0; - } - - - // Activate corresponding render state + } glEnable(GL_BLEND); glDisable(GL_CULL_FACE); @@ -94,7 +83,7 @@ void TextRenderer::RenderText(std::string text, Font* font, TextJob::AlignmentEn GLfloat w = ch.Size.x * scale; GLfloat h = ch.Size.y * scale; - // Update VBO for each character + GLfloat vertices[6][4] = { { xpos, ypos + h, 0.0, 0.0 }, { xpos, ypos, 0.0, 1.0 }, @@ -105,15 +94,12 @@ void TextRenderer::RenderText(std::string text, Font* font, TextJob::AlignmentEn { xpos + w, ypos + h, 1.0, 0.0 } }; - // Render glyph texture over quad glBindTexture(GL_TEXTURE_2D, ch.TextureID); - // Update content of VBO memory + glBindBuffer(GL_ARRAY_BUFFER, VBO); glBufferSubData(GL_ARRAY_BUFFER, 0, sizeof(vertices), vertices); glBindBuffer(GL_ARRAY_BUFFER, 0); - // Render quad glDrawArrays(GL_TRIANGLES, 0, 6); - // Now advance cursors for next glyph (note that advance is number of 1/64 pixels) penX += (ch.Advance >> 6) * scale; // Bitshift by 6 to get value in pixels (2^6 = 64) } glBindVertexArray(0); From c2e05de89f0a236864b8259d9a3ce4691452818d Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Thu, 21 Jan 2016 10:24:34 +0100 Subject: [PATCH 141/224] Deleted some components, etc for ShootEvent that will likely be used in a WeaponSystem instead --- include/Engine/Core/EShoot.h | 7 +- resources/Schema/Components.xsd | 3 - resources/Schema/Components/Player.xml | 1 - resources/Schema/Components/Player.xsd | 1 - resources/Schema/Components/PrimaryItem.xml | 4 - resources/Schema/Components/PrimaryItem.xsd | 21 -- resources/Schema/Components/SecondaryItem.xml | 4 - resources/Schema/Components/SecondaryItem.xsd | 21 -- resources/Schema/Types/Entity.xsd | 2 - src/Tests/ShootEventTest.cpp | 258 ------------------ src/Tests/ShootEventTest.h | 52 ---- 11 files changed, 2 insertions(+), 372 deletions(-) delete mode 100644 resources/Schema/Components/PrimaryItem.xml delete mode 100644 resources/Schema/Components/PrimaryItem.xsd delete mode 100644 resources/Schema/Components/SecondaryItem.xml delete mode 100644 resources/Schema/Components/SecondaryItem.xsd delete mode 100644 src/Tests/ShootEventTest.cpp delete mode 100644 src/Tests/ShootEventTest.h diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h index 9e395d62..fd54122f 100644 --- a/include/Engine/Core/EShoot.h +++ b/include/Engine/Core/EShoot.h @@ -10,11 +10,8 @@ namespace Events struct Shoot : Event { - //shotgun etc has different amounts of damage probably (a sniper shot might one-shot) - //also different weapons will have different spread - int CurrentlyEquippedItem; - //currentAimingPoint must be sent, in case the camera is moved while the event is being processed - glm::vec2 CurrentAimingPoint; + //ID for who made the shot + EntityID shooter; }; } diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index a4931c18..bed93c1f 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -12,9 +12,6 @@ - - - diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index 4743e8c8..caefd6e6 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,6 +1,5 @@ - 0 false false diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 617b7d30..1a315a35 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -14,7 +14,6 @@ - diff --git a/resources/Schema/Components/PrimaryItem.xml b/resources/Schema/Components/PrimaryItem.xml deleted file mode 100644 index 0d0ccca2..00000000 --- a/resources/Schema/Components/PrimaryItem.xml +++ /dev/null @@ -1,4 +0,0 @@ - - 0 - 0 - \ No newline at end of file diff --git a/resources/Schema/Components/PrimaryItem.xsd b/resources/Schema/Components/PrimaryItem.xsd deleted file mode 100644 index 35e2fca6..00000000 --- a/resources/Schema/Components/PrimaryItem.xsd +++ /dev/null @@ -1,21 +0,0 @@ - - - - - - - - The Players Primary Item/Weapon - - - - - Ammo count - - - Cooldown till next item/weapon use - - - - - \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xml b/resources/Schema/Components/SecondaryItem.xml deleted file mode 100644 index 095dfef6..00000000 --- a/resources/Schema/Components/SecondaryItem.xml +++ /dev/null @@ -1,4 +0,0 @@ - - 0 - 0 - \ No newline at end of file diff --git a/resources/Schema/Components/SecondaryItem.xsd b/resources/Schema/Components/SecondaryItem.xsd deleted file mode 100644 index bee25541..00000000 --- a/resources/Schema/Components/SecondaryItem.xsd +++ /dev/null @@ -1,21 +0,0 @@ - - - - - - - - The Players Secondary Item/Weapon - - - - - Ammo count - - - Cooldown till next item/weapon use - - - - - \ No newline at end of file diff --git a/resources/Schema/Types/Entity.xsd b/resources/Schema/Types/Entity.xsd index 554996c1..b37692a9 100644 --- a/resources/Schema/Types/Entity.xsd +++ b/resources/Schema/Types/Entity.xsd @@ -21,8 +21,6 @@ - - diff --git a/src/Tests/ShootEventTest.cpp b/src/Tests/ShootEventTest.cpp deleted file mode 100644 index f9002eca..00000000 --- a/src/Tests/ShootEventTest.cpp +++ /dev/null @@ -1,258 +0,0 @@ -#include -using boost::unit_test_framework::test_suite; -using boost::unit_test_framework::test_case; - -#include "ShootEventTest.h" -#include "Game/HealthSystem.h" - -BOOST_AUTO_TEST_SUITE(ShootEventTestSuite) - -//dont use the same name as the classname in test cases... -BOOST_AUTO_TEST_CASE(ShootEventTest_PrimaryWeaponFiring) -{ - //Test firing primary weapon - ShootEventTest game(1); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - BOOST_TEST(success); -} -BOOST_AUTO_TEST_CASE(ShootEventTest_SecondaryWeaponFiring) -{ - //Test firing secondary weapon - ShootEventTest game(2); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - if (game.TestSucceeded) { - success = true; - break; - } - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - BOOST_TEST(success); -} -BOOST_AUTO_TEST_CASE(ShootEventTest_NoWeaponFiring) -{ - //Test firing with no weapon equipped - ShootEventTest game(3); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - if (game.TestSucceeded) - success = true; - BOOST_TEST(success); -} -BOOST_AUTO_TEST_CASE(ShootEventTest_WeaponOnCooldown) -{ - //Test firing with weapon on cooldown - ShootEventTest game(4); - //100 loops will be more than enough to do the test - int loops = 100; - bool success = false; - while (loops > 0) { - game.Tick(); - loops--; - } - //The system will process the events, hence it will take a while before we can read anything - if (game.TestSucceeded) - success = true; - BOOST_TEST(success); -} -BOOST_AUTO_TEST_SUITE_END() - -ShootEventTest::ShootEventTest(int runTestNumber) -{ - ResourceManager::RegisterType("ConfigFile"); - ResourceManager::RegisterType("EntityFile"); - - m_Config = ResourceManager::Load("Config.ini"); - std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); - LOG_LEVEL = static_cast<_LOG_LEVEL>(m_Config->Get("Debug.LogLevel", 1)); - - // Create the core event broker - m_EventBroker = new EventBroker(); - - // Create a world - m_World = new World(); - - // Create system pipeline - m_SystemPipeline = new SystemPipeline(m_EventBroker); - m_SystemPipeline->AddSystem(0); - m_SystemPipeline->AddSystem(0); - - if (!mapToLoad.empty()) { - auto file = ResourceManager::Load(mapToLoad); - EntityFilePreprocessor fpp(file); - fpp.RegisterComponents(m_World); - EntityFileParser fp(file); - fp.MergeEntities(m_World); - } - - //The Test - //create entity which has transform,player,model,health in it. i.e. is a player - EntityID playerID = m_World->CreateEntity(); - m_PlayerID = playerID; - ComponentWrapper& player = m_World->AttachComponent(playerID, "Player"); - ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); - //attach 2x weaps - ComponentWrapper& pItem = m_World->AttachComponent(playerID, "PrimaryItem"); - ComponentWrapper& sItem = m_World->AttachComponent(playerID, "SecondaryItem"); - - m_RunTestNumber = runTestNumber; - switch (runTestNumber) - { - case 1: - TestSetup1(player, pItem, sItem); - break; - case 2: - TestSetup2(player, pItem, sItem); - break; - case 3: - TestSetup3(player, pItem, sItem); - break; - case 4: - TestSetup4(player, pItem, sItem); - break; - default: - break; - } - - //fire once = trigger event leftmousedown - Events::MouseRelease eMouseRelease; - eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; - eMouseRelease.X = 1.0f; - eMouseRelease.Y = 1.0f; - m_EventBroker->Publish(eMouseRelease); -} - -ShootEventTest::~ShootEventTest() -{ - delete m_SystemPipeline; - delete m_World; - delete m_EventBroker; -} - -void ShootEventTest::TestSetup1(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) -{ - //set currentweap - player["EquippedItem"] = 1; - //set ammo set cooldown - pItem["Ammo"] = 100; - pItem["CoolDownTimer"] = 0.0; -} -void ShootEventTest::TestSetup2(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) -{ - //set currentweap - player["EquippedItem"] = 2; - //set ammo set cooldown - sItem["Ammo"] = 10; - sItem["CoolDownTimer"] = 0.0; -} -void ShootEventTest::TestSetup3(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) -{ - player["EquippedItem"] = 0; - pItem["Ammo"] = 100; - sItem["Ammo"] = 100; - //TestSucceeded will be set to false if ammo changes during the 100 loops - TestSucceeded = true; -} -void ShootEventTest::TestSetup4(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem) -{ - //set currentweap - player["EquippedItem"] = 1; - //set ammo set cooldown - pItem["Ammo"] = 100; - pItem["CoolDownTimer"] = 99999999.0;//very long coolDownTimer - //TestSucceeded will be set to false if ammo changes during the 100 loops - TestSucceeded = true; -} -void ShootEventTest::TestSuccess1() { - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo == 99) - TestSucceeded = true; -} -void ShootEventTest::TestSuccess2() { - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo == 9) - TestSucceeded = true; -} -void ShootEventTest::TestSuccess3() { - //try firing again - Events::MouseRelease eMouseRelease; - eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; - eMouseRelease.X = 1.0f; - eMouseRelease.Y = 1.0f; - m_EventBroker->Publish(eMouseRelease); - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - int currentAmmoSecondary = m_World->GetComponent(m_PlayerID, "SecondaryItem")["Ammo"]; - if (currentAmmo != 100 || currentAmmoSecondary != 100) - TestSucceeded = false; -} -void ShootEventTest::TestSuccess4() { - //try firing again - Events::MouseRelease eMouseRelease; - eMouseRelease.Button = GLFW_MOUSE_BUTTON_LEFT; - eMouseRelease.X = 1.0f; - eMouseRelease.Y = 1.0f; - m_EventBroker->Publish(eMouseRelease); - //if ammocount reaches -- we know the test has succeeded, i.e. a shot has been fired - int currentAmmo = m_World->GetComponent(m_PlayerID, "PrimaryItem")["Ammo"]; - if (currentAmmo != 100) - TestSucceeded = false; -} -void ShootEventTest::Tick() -{ - glfwPollEvents(); - - //double currentTime = glfwGetTime(); - //double dt = currentTime - m_LastTime; - //m_LastTime = currentTime; - - //just set dt to 1.0 - double dt = 0.34567; - // Iterate through systems and update world! - m_SystemPipeline->Update(m_World, dt); - - m_EventBroker->Swap(); - m_EventBroker->Clear(); - - switch (m_RunTestNumber) - { - case 1: - TestSuccess1(); - break; - case 2: - TestSuccess2(); - break; - case 3: - TestSuccess3(); - break; - case 4: - TestSuccess4(); - break; - default: - break; - } - -} diff --git a/src/Tests/ShootEventTest.h b/src/Tests/ShootEventTest.h deleted file mode 100644 index e796c17e..00000000 --- a/src/Tests/ShootEventTest.h +++ /dev/null @@ -1,52 +0,0 @@ -#ifndef ShootEventTest_h__ -#define ShootEventTest_h__ - -#include "Core/ResourceManager.h" -#include "Core/ConfigFile.h" -#include "Core/EventBroker.h" -#include "Core/World.h" -#include "Input/InputProxy.h" -#include "Input/KeyboardInputHandler.h" -#include "Input/MouseInputHandler.h" -#include "Core/EKeyDown.h" -#include "Core/EntityFile.h" -#include "Core/SystemPipeline.h" -#include "PlayerSystem.h" - -#include "Core/EntityFilePreprocessor.h" -#include "Core/EntityFileParser.h" -#include "Core/EntityFileWriter.h" - -#include "Core/EMouseRelease.h" -#include "Core/EShoot.h" - -class ShootEventTest -{ -public: - ShootEventTest(int runTestNumber); - ~ShootEventTest(); - - void Tick(); - bool TestSucceeded = false; - -private: - void TestSetup1(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); - void TestSetup2(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); - void TestSetup3(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); - void TestSetup4(ComponentWrapper& player, ComponentWrapper& pItem, ComponentWrapper& sItem); - void TestSuccess1(); - void TestSuccess2(); - void TestSuccess3(); - void TestSuccess4(); - - double m_LastTime; - ConfigFile* m_Config = nullptr; - EventBroker* m_EventBroker; - World* m_World; - SystemPipeline* m_SystemPipeline; - int m_PlayerID; - int m_RunTestNumber; - -}; - -#endif From 4aa9100c69619c21edb9d14f1c2d25d1b36a6532 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 10:29:36 +0100 Subject: [PATCH 142/224] Camera::WorldToScreen helper function --- include/Engine/Rendering/Camera.h | 4 +++- src/Engine/Rendering/Camera.cpp | 13 +++++++++++++ 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/include/Engine/Rendering/Camera.h b/include/Engine/Rendering/Camera.h index 2b863448..29dd4626 100644 --- a/include/Engine/Rendering/Camera.h +++ b/include/Engine/Rendering/Camera.h @@ -2,6 +2,7 @@ #define Camera_h__ #include "../GLM.h" +#include "../Core/Util/Rectangle.h" class Camera { @@ -32,7 +33,6 @@ public: glm::mat4 ViewMatrix() const { return m_ViewMatrix; } void SetViewMatrix(glm::mat4 val); - float AspectRatio() const { return m_AspectRatio; } void SetAspectRatio(float val); @@ -48,6 +48,8 @@ public: void UpdateViewMatrix(); void UpdateProjectionMatrix(); + glm::vec2 WorldToScreen(glm::vec3 worldCoord, Rectangle resolution); + private: glm::vec3 m_Position; diff --git a/src/Engine/Rendering/Camera.cpp b/src/Engine/Rendering/Camera.cpp index 5a774c34..f6b2e5ef 100644 --- a/src/Engine/Rendering/Camera.cpp +++ b/src/Engine/Rendering/Camera.cpp @@ -79,6 +79,19 @@ void Camera::UpdateProjectionMatrix() m_ProjectionMatrix = glm::perspective(m_FOV, m_AspectRatio, m_NearClip, m_FarClip); } +glm::vec2 Camera::WorldToScreen(glm::vec3 worldCoord, Rectangle resolution) +{ + glm::vec4 screenCoord = m_ProjectionMatrix * m_ViewMatrix * glm::vec4(worldCoord, 1.f); + if (screenCoord.w != 0) { + screenCoord.x /= screenCoord.w; + screenCoord.y /= screenCoord.w; + screenCoord.z /= screenCoord.w; + } + screenCoord.x = screenCoord.x * (resolution.Width / 2.f); + screenCoord.y = screenCoord.y * (resolution.Height / 2.f); + return glm::vec2(screenCoord); +} + void Camera::UpdateViewMatrix() { m_ViewMatrix = glm::toMat4(glm::inverse(m_Orientation)) From 5e70d6eef6e10676582228d59e3c40fe3883d412 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 10:29:48 +0100 Subject: [PATCH 143/224] EntityWrapper::Parent helper function --- include/Engine/Core/EntityWrapper.h | 1 + src/Engine/Core/EntityWrapper.cpp | 7 ++++++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/include/Engine/Core/EntityWrapper.h b/include/Engine/Core/EntityWrapper.h index 74b5fc56..3ba4e087 100644 --- a/include/Engine/Core/EntityWrapper.h +++ b/include/Engine/Core/EntityWrapper.h @@ -24,6 +24,7 @@ struct EntityWrapper static const EntityWrapper Invalid; bool HasComponent(const std::string& componentName); + EntityWrapper Parent(); bool Valid(); ComponentWrapper operator[](const char* componentName); diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 5dc493ff..58dd1ee6 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -8,6 +8,11 @@ bool EntityWrapper::HasComponent(const std::string& componentName) return World->HasComponent(ID, componentName); } +EntityWrapper EntityWrapper::Parent() +{ + return EntityWrapper(World, World->GetParent(ID)); +} + bool EntityWrapper::Valid() { if (this->World == nullptr) { @@ -38,7 +43,7 @@ ComponentWrapper EntityWrapper::operator[](const char* componentName) bool EntityWrapper::operator==(const EntityWrapper& e) const { - return (this->World == e.World) && (this->ID == e.ID); + return (this->ID == e.ID) && (this->World == e.World); } bool EntityWrapper::operator!=(const EntityWrapper& e) const From f1345419b654cae8eeff662268562890bc773ee5 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 10:30:19 +0100 Subject: [PATCH 144/224] EditorWidgetSystem that takes care of moving widgets around --- include/Engine/Core/System.h | 2 +- include/Engine/Editor/EditorWidgetSystem.h | 35 +++++++++ include/Engine/GLM.h | 3 +- .../Schema/Entities/EditorWidgetTranslate.xml | 27 ++++--- src/Engine/Editor/EditorGUI.cpp | 1 + src/Engine/Editor/EditorSystem.cpp | 2 + src/Engine/Editor/EditorWidgetSystem.cpp | 76 +++++++++++++++++++ 7 files changed, 135 insertions(+), 11 deletions(-) create mode 100644 src/Engine/Editor/EditorWidgetSystem.cpp diff --git a/include/Engine/Core/System.h b/include/Engine/Core/System.h index dc7c879a..ec57f5fc 100644 --- a/include/Engine/Core/System.h +++ b/include/Engine/Core/System.h @@ -34,7 +34,7 @@ protected: const std::string m_ComponentType; - virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) = 0; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cComponent, double dt) = 0; }; class ImpureSystem : public virtual System diff --git a/include/Engine/Editor/EditorWidgetSystem.h b/include/Engine/Editor/EditorWidgetSystem.h index 2350d24b..f3e4e4db 100644 --- a/include/Engine/Editor/EditorWidgetSystem.h +++ b/include/Engine/Editor/EditorWidgetSystem.h @@ -1,6 +1,41 @@ #ifndef EditorWidgetSystem_h__ #define EditorWidgetSystem_h__ +#include +#include "../GLM.h" +#include "../Core/System.h" +#include "../Rendering/IRenderer.h" +#include "../Rendering/Util/ScreenCoords.h" +#include "../Core/EMouseMove.h" +#include "../Core/EMousePress.h" +#include "../Core/EMouseRelease.h" +class EditorWidgetSystem : public ImpureSystem, PureSystem +{ +public: + EditorWidgetSystem(World* world, EventBroker* eventBroker, IRenderer* renderer); + + virtual void Update(double dt) override; + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cEditorWidget, double dt) override; + + void debugPrintVector(const char* name, glm::vec3 axisNDC); + + void debugPrintVector(const char* name, glm::vec4 axisNDC); + void debugPrintVector(const char* name, glm::vec2 axisNDC); +private: + IRenderer* m_Renderer; + + // State + EntityWrapper m_PickEntity = EntityWrapper::Invalid; + PickData m_PickData; + glm::vec2 m_MouseDelta; + + EventRelay m_EMouseMove; + bool OnMouseMove(const Events::MouseMove& e); + EventRelay m_EMousePress; + bool OnMousePress(const Events::MousePress& e); + EventRelay m_EMouseRelease; + bool OnMouseRelease(const Events::MouseRelease& e); +}; #endif diff --git a/include/Engine/GLM.h b/include/Engine/GLM.h index 32729845..3143c905 100644 --- a/include/Engine/GLM.h +++ b/include/Engine/GLM.h @@ -7,4 +7,5 @@ #include #include #include -#include \ No newline at end of file +#include +#include \ No newline at end of file diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml index e2cfd69a..75d96a51 100644 --- a/resources/Schema/Entities/EditorWidgetTranslate.xml +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -6,15 +6,14 @@ Models/TranslationWidgetOrigin.obj - - - - + + + Models/TranslationWidgetX.obj @@ -24,7 +23,9 @@ - + + + Models/TranslationWidgetY.obj @@ -34,7 +35,9 @@ - + + + Models/TranslationWidgetZ.obj @@ -44,7 +47,9 @@ - + + + Models/WidgetPlaneX.obj @@ -54,7 +59,9 @@ - + + + Models/WidgetPlaneY.obj @@ -64,7 +71,9 @@ - + + + Models/WidgetPlaneZ.obj diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index f65386aa..d5638d31 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -76,6 +76,7 @@ void EditorGUI::drawTools() void EditorGUI::drawEntities(World* world) { if (!ImGui::Begin("Entities")) { + ImGui::End(); return; } diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 596f8154..613f0edb 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -1,6 +1,7 @@ #include "Editor/EditorSystem.h" #include "Core/UniformScaleSystem.h" #include "Editor/EditorRenderSystem.h" +#include "Editor/EditorWidgetSystem.h" EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame) : System(world, eventBroker) @@ -10,6 +11,7 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorWorld = new World(); m_EditorWorldSystemPipeline = new SystemPipeline(m_EditorWorld, eventBroker); m_EditorWorldSystemPipeline->AddSystem(0); + m_EditorWorldSystemPipeline->AddSystem(0, m_Renderer); m_EditorWorldSystemPipeline->AddSystem(1, m_Renderer, m_RenderFrame); m_Camera = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/Empty.xml"); diff --git a/src/Engine/Editor/EditorWidgetSystem.cpp b/src/Engine/Editor/EditorWidgetSystem.cpp new file mode 100644 index 00000000..3a200e0f --- /dev/null +++ b/src/Engine/Editor/EditorWidgetSystem.cpp @@ -0,0 +1,76 @@ +#include "Editor/EditorWidgetSystem.h" + +EditorWidgetSystem::EditorWidgetSystem(World* world, EventBroker* eventBroker, IRenderer* renderer) + : System(world, eventBroker) + , PureSystem("EditorWidget") + , m_Renderer(renderer) +{ + EVENT_SUBSCRIBE_MEMBER(m_EMouseMove, &EditorWidgetSystem::OnMouseMove); + EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorWidgetSystem::OnMousePress); + EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorWidgetSystem::OnMouseRelease); +} + +void EditorWidgetSystem::Update(double dt) +{ + // Pick at current mouse position +} + +void EditorWidgetSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& cEditorWidget, double dt) +{ + if (!m_PickEntity.Valid() || m_PickEntity != entity) { + return; + } + + EntityWrapper moveEntity = entity.Parent(); + if (!moveEntity.Valid()) { + moveEntity = entity; + } + + ComponentWrapper::SubscriptProxy& type = cEditorWidget["Type"]; + if ((ComponentInfo::EnumType)type == type.Enum("Translate")) { + auto camera = m_PickData.Camera; + glm::vec3 axis = cEditorWidget["Axis"]; + glm::vec2 axisScreen = camera->WorldToScreen(axis, m_Renderer->Resolution()) - camera->WorldToScreen(glm::vec3(0, 0, 0), m_Renderer->Resolution()); + float dot = glm::dot(m_MouseDelta, glm::normalize(axisScreen)) / glm::length(axisScreen); + glm::vec3 worldMovement = dot * axis; + (glm::vec3&)moveEntity["Transform"]["Position"] += worldMovement; + } + + m_MouseDelta = glm::vec2(0); +} + +void EditorWidgetSystem::debugPrintVector(const char* name, glm::vec2 axisNDC) +{ + ImGui::Text("%s: (%f, %f)", name, axisNDC.x, axisNDC.y); +} +void EditorWidgetSystem::debugPrintVector(const char* name, glm::vec4 axisNDC) +{ + ImGui::Text("%s: (%f, %f, %f, %f)", name, axisNDC.x, axisNDC.y, axisNDC.z, axisNDC.w); +} +void EditorWidgetSystem::debugPrintVector(const char* name, glm::vec3 axisNDC) +{ + ImGui::Text("%s: (%f, %f, %f)", name, axisNDC.x, axisNDC.y, axisNDC.z); +} + +bool EditorWidgetSystem::OnMouseMove(const Events::MouseMove& e) +{ + m_MouseDelta = glm::vec2((float)e.DeltaX, (float)-e.DeltaY); + return false; +} + +bool EditorWidgetSystem::OnMousePress(const Events::MousePress & e) +{ + if (e.Button == GLFW_MOUSE_BUTTON_2) { + m_PickData = m_Renderer->Pick(glm::vec2(e.X, e.Y)); + if (m_PickData.Entity != EntityID_Invalid && m_PickData.World == m_World) { + m_PickEntity = EntityWrapper(m_World, m_PickData.Entity); + } + } + return true; +} + +bool EditorWidgetSystem::OnMouseRelease(const Events::MouseRelease& e) +{ + m_PickEntity = EntityWrapper::Invalid; + return true; +} \ No newline at end of file From bdebc9de62cf154fb4ad8b2f398cb2fea7f6fea7 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Thu, 21 Jan 2016 11:55:51 +0100 Subject: [PATCH 145/224] WeaponSystem now handles "PrimaryFire" input events. It sends out ePlayerDamage event if it hits a player. Included some tests --- include/Game/Systems/WeaponSystem.h | 39 ++++ resources/Schema/Entities/ShootEventTest.xml | 209 +++++++++++++++++++ src/Game/Game.cpp | 2 + src/Game/Systems/WeaponSystem.cpp | 61 ++++++ 4 files changed, 311 insertions(+) create mode 100644 include/Game/Systems/WeaponSystem.h create mode 100644 resources/Schema/Entities/ShootEventTest.xml create mode 100644 src/Game/Systems/WeaponSystem.cpp diff --git a/include/Game/Systems/WeaponSystem.h b/include/Game/Systems/WeaponSystem.h new file mode 100644 index 00000000..36af4231 --- /dev/null +++ b/include/Game/Systems/WeaponSystem.h @@ -0,0 +1,39 @@ +#ifndef WeaponSystem_h__ +#define WeaponSystem_h__ + +//#include +//#include +#include "Rendering/IRenderer.h" + +#include "Common.h" +#include "Core/System.h" +#include "Core/EPlayerDamage.h" +#include "Core/EShoot.h" +#include "Input/EInputCommand.h" + +#include +#include + + +class WeaponSystem : public ImpureSystem +{ +public: + WeaponSystem(EventBroker* eventBroker, IRenderer* renderer); + + virtual void Update(World* world, double dt) override; + +private: + //methods which will take care of specific events + EventRelay m_EShoot; + bool WeaponSystem::OnShoot(const Events::Shoot& e); + + EventRelay m_EInputCommand; + bool WeaponSystem::OnInputCommand(const Events::InputCommand& e); + + IRenderer* m_Renderer; + + std::vector> m_EShootVector; + double m_TestDamageTotal = 0.0; +}; + +#endif \ No newline at end of file diff --git a/resources/Schema/Entities/ShootEventTest.xml b/resources/Schema/Entities/ShootEventTest.xml new file mode 100644 index 00000000..eae333b6 --- /dev/null +++ b/resources/Schema/Entities/ShootEventTest.xml @@ -0,0 +1,209 @@ + + + + + + + + + + + + ../assets/Models/DummyScene.obj + + + + + + + + + 60 + + + + + + + 3 + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + 3 + + + + + + + + + + + + + 1 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 2 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + 3 + + + ../assets/Models/Core/UnitSphere.obj + + + + + + + + + + + + + + + 2 + 4 + + + ../assets/Models/Core/UnitSphere.obj + + + + 2 + + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + + + ../assets/Models/Core/UnitCube.obj + + + + + 2 + + + + + + + + + + + 0 + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + + 0 + + + + ../assets/Models/Core/UnitCube.obj + + + + + 3 + + + + + + + + + + diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 0dd513b6..8d647f6f 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -9,6 +9,7 @@ #include "Systems/PlayerSpawnSystem.h" #include "Core/EntityFileWriter.h" #include "Game/Systems/CapturePointSystem.h" +#include "Game/Systems/WeaponSystem.h" Game::Game(int argc, char* argv[]) { @@ -82,6 +83,7 @@ Game::Game(int argc, char* argv[]) m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); + m_SystemPipeline->AddSystem(updateOrderLevel, m_Renderer); // Populate Octree with collidables ++updateOrderLevel; m_SystemPipeline->AddSystem(updateOrderLevel, m_OctreeCollision); diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp new file mode 100644 index 00000000..ada48b54 --- /dev/null +++ b/src/Game/Systems/WeaponSystem.cpp @@ -0,0 +1,61 @@ +#include "Systems/WeaponSystem.h" + +WeaponSystem::WeaponSystem(EventBroker* eventBroker, IRenderer* renderer) + : System(eventBroker) + , ImpureSystem() + , m_Renderer(renderer) +{ + EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &WeaponSystem::OnInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_EShoot, &WeaponSystem::OnShoot); +} + +void WeaponSystem::Update(World* world, double dt) +{ + for (int i = m_EShootVector.size(); i > 0; i--) + { + //TODO: check if player has enough ammo and if weapon has a cooldown or not + + //pick the object + PickData somePickData = m_Renderer->Pick(std::get<1>(m_EShootVector[i - 1])); + if (somePickData.Entity == EntityID_Invalid) { + m_EShootVector.erase(m_EShootVector.begin() + i - 1); + continue; + } + //if its a player, do PlayerDamage event + const bool hasPlayerComponent = world->HasComponent(somePickData.Entity, "Player"); + if (hasPlayerComponent) { + Events::PlayerDamage ePlayerDamage; + //TODO: damage based on weapontype/class? + //TODO: multiple shots at the same time? (shotgunner) + ePlayerDamage.DamageAmount = 25; + ePlayerDamage.PlayerDamagedID = somePickData.Entity; + ePlayerDamage.TypeOfDamage = "Some Weapon"; + m_EventBroker->Publish(ePlayerDamage); + //tests:color + m_TestDamageTotal += 0.25f; + if (m_TestDamageTotal > 6.0f) { + m_TestDamageTotal = 0.25f; + } + ComponentWrapper& playerModel = world->GetComponent(somePickData.Entity, "Model"); + playerModel["Color"] = glm::vec4(m_TestDamageTotal, 0, 0, 1); + } + m_EShootVector.erase(m_EShootVector.begin() + i - 1); + } +} + +bool WeaponSystem::OnInputCommand(const Events::InputCommand& e) +{ + if (e.Command == "PrimaryFire" && e.Value > 0) { + Events::Shoot eShoot; + eShoot.shooter = e.PlayerID; + m_EventBroker->Publish(eShoot); + } + return true; +} +bool WeaponSystem::OnShoot(const Events::Shoot& e) { + //screen center, based on current resolution! + Rectangle screenResolution = m_Renderer->Resolution(); + glm::vec2 centerScreen = glm::vec2(screenResolution.Width / 2, screenResolution.Height / 2); + m_EShootVector.push_back(std::make_pair(e.shooter, centerScreen)); + return true; +} \ No newline at end of file From 983f90504d54ab0feca4b7b959fd572426799502 Mon Sep 17 00:00:00 2001 From: Tleety Date: Thu, 21 Jan 2016 12:02:28 +0100 Subject: [PATCH 146/224] Bloom effect added, will have to see if it needs improving. Also added HDR colors and gamma correction. --- include/Engine/Rendering/DrawBloomEffect.h | 38 ------ include/Engine/Rendering/DrawBloomPass.h | 48 +++++++ include/Engine/Rendering/DrawBloomPassState.h | 15 +++ .../Rendering/DrawColorCorrectionPass.h | 29 +++++ include/Engine/Rendering/Renderer.h | 4 + .../Shaders/DrawColorCorrection.frag.glsl | 32 +++++ .../Shaders/DrawColorCorrection.vert.glsl | 13 ++ resources/Shaders/Gaussian_horiz.frag.glsl | 23 ++++ resources/Shaders/Gaussian_horiz.vert.glsl | 13 ++ resources/Shaders/Gaussian_vert.frag.glsl | 23 ++++ resources/Shaders/Gaussian_vert.vert.glsl | 13 ++ src/Engine/Rendering/DrawBloomEffect.cpp | 66 ---------- src/Engine/Rendering/DrawBloomPass.cpp | 121 ++++++++++++++++++ src/Engine/Rendering/DrawBloomPassState.cpp | 17 +++ .../Rendering/DrawColorCorrectionPass.cpp | 41 ++++++ src/Engine/Rendering/Renderer.cpp | 7 +- 16 files changed, 398 insertions(+), 105 deletions(-) delete mode 100644 include/Engine/Rendering/DrawBloomEffect.h create mode 100644 include/Engine/Rendering/DrawBloomPass.h create mode 100644 include/Engine/Rendering/DrawBloomPassState.h create mode 100644 include/Engine/Rendering/DrawColorCorrectionPass.h create mode 100644 resources/Shaders/DrawColorCorrection.frag.glsl create mode 100644 resources/Shaders/DrawColorCorrection.vert.glsl create mode 100644 resources/Shaders/Gaussian_horiz.frag.glsl create mode 100644 resources/Shaders/Gaussian_horiz.vert.glsl create mode 100644 resources/Shaders/Gaussian_vert.frag.glsl create mode 100644 resources/Shaders/Gaussian_vert.vert.glsl delete mode 100644 src/Engine/Rendering/DrawBloomEffect.cpp create mode 100644 src/Engine/Rendering/DrawBloomPass.cpp create mode 100644 src/Engine/Rendering/DrawBloomPassState.cpp create mode 100644 src/Engine/Rendering/DrawColorCorrectionPass.cpp diff --git a/include/Engine/Rendering/DrawBloomEffect.h b/include/Engine/Rendering/DrawBloomEffect.h deleted file mode 100644 index 52876592..00000000 --- a/include/Engine/Rendering/DrawBloomEffect.h +++ /dev/null @@ -1,38 +0,0 @@ -#ifndef DrawFinalPass_h__ -#define DrawFinalPass_h__ - -#include "IRenderer.h" -#include "DrawFinalPassState.h" -#include "LightCullingPass.h" -#include "FrameBuffer.h" -#include "ShaderProgram.h" -#include "Util/UnorderedMapVec2.h" -#include "Texture.h" - -class DrawFinalPass -{ -public: - DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCullingPass); - ~DrawFinalPass() { } - void InitializeTextures(); - void InitializeFrameBuffers(); - void InitializeShaderPrograms(); - - void Draw(RenderScene& scene); - - //Getters - - -private: - void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; - - Texture* m_WhiteTexture; - - const IRenderer* m_Renderer; - const LightCullingPass* m_LightCullingPass; - - ShaderProgram* m_ForwardPlusProgram; - -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawBloomPass.h b/include/Engine/Rendering/DrawBloomPass.h new file mode 100644 index 00000000..d192c73a --- /dev/null +++ b/include/Engine/Rendering/DrawBloomPass.h @@ -0,0 +1,48 @@ +#ifndef DrawBloomPass_h__ +#define DrawBloomPass_h__ + +#include "IRenderer.h" +#include "DrawBloomPassState.h" +//#include "LightCullingPass.h" Finalpass om den skall skickas in +#include "FrameBuffer.h" +#include "ShaderProgram.h" +//#include "Util/UnorderedMapVec2.h" +#include "Texture.h" + +class DrawBloomPass +{ +public: + DrawBloomPass(IRenderer* renderer /* ,Texture or finalpass*/ ); + ~DrawBloomPass() { } + void InitializeTextures(); + void InitializeFrameBuffers(); + void InitializeShaderPrograms(); + void InitializeBuffers(); + + void FillGaussianBuffer(FrameBuffer* fb); + + void Draw(GLuint texture); + + //Getters + GLuint m_GaussianTexture_horiz; + GLuint m_GaussianTexture_vert; + +private: + void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; + + Texture* m_WhiteTexture; + Model* m_ScreenQuad; + + const IRenderer* m_Renderer; + //const LightCullingPass* m_LightCullingPass + GLuint m_iterations = 9; + + FrameBuffer m_GaussianFrameBuffer_horiz; + FrameBuffer m_GaussianFrameBuffer_vert; + + ShaderProgram* m_GaussianProgram_horiz; + ShaderProgram* m_GaussianProgram_vert; + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawBloomPassState.h b/include/Engine/Rendering/DrawBloomPassState.h new file mode 100644 index 00000000..7f2094cf --- /dev/null +++ b/include/Engine/Rendering/DrawBloomPassState.h @@ -0,0 +1,15 @@ +#ifndef DrawBloomPassState_h__ +#define DrawBloomPassState_h__ + +#include "Rendering/RenderState.h" + +class DrawBloomPassState : public RenderState +{ +public: + DrawBloomPassState(); + ~DrawBloomPassState(); +private: + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawColorCorrectionPass.h b/include/Engine/Rendering/DrawColorCorrectionPass.h new file mode 100644 index 00000000..e9a7e281 --- /dev/null +++ b/include/Engine/Rendering/DrawColorCorrectionPass.h @@ -0,0 +1,29 @@ +#ifndef DrawColorCorrectionPass_h__ +#define DrawColorCorrectionPass_h__ + +#include "IRenderer.h" +#include "DrawScreenQuadPassState.h" +#include "FrameBuffer.h" +#include "ShaderProgram.h" +//#include "Util/UnorderedMapVec2.h" +#include "Texture.h" + +class DrawColorCorrectionPass +{ +public: + DrawColorCorrectionPass(IRenderer* renderer); + ~DrawColorCorrectionPass() { } + void InitializeFrameBuffers(); + void InitializeShaderPrograms(); + + void Draw(GLuint sceneTexture, GLuint bloomTexture); +private: + const IRenderer* m_Renderer; + + ShaderProgram* m_ColorCorrectionProgram; + + Model* m_ScreenQuad; + GLfloat m_Exposure; +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 7dcf7e6a..235bda89 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -15,6 +15,8 @@ #include "LightCullingPass.h" #include "DrawFinalPass.h" #include "DrawScreenQuadPass.h" +#include "DrawBloomPass.h" +#include "DrawColorCorrectionPass.h" #include "../Core/EventBroker.h" #include "ImGuiRenderPass.h" #include "Camera.h" @@ -50,6 +52,8 @@ private: ImGuiRenderPass* m_ImGuiRenderPass; DrawFinalPass* m_DrawFinalPass; DrawScreenQuadPass* m_DrawScreenQuadPass; + DrawBloomPass* m_DrawBloomPass; + DrawColorCorrectionPass* m_DrawColorCorrectionPass; //----------------------Functions----------------------// void InitializeWindow(); diff --git a/resources/Shaders/DrawColorCorrection.frag.glsl b/resources/Shaders/DrawColorCorrection.frag.glsl new file mode 100644 index 00000000..8d13992a --- /dev/null +++ b/resources/Shaders/DrawColorCorrection.frag.glsl @@ -0,0 +1,32 @@ +#version 430 + +layout (binding = 0) uniform sampler2D SceneTexture; +layout (binding = 1) uniform sampler2D BloomTexture; +uniform float Exposure; + +in VertexData{ + vec2 TextureCoordinate; +}Input; + +out vec4 fragmentColor; + +void main() +{ + const float gamma = 2.2; + vec4 hdrColor = texture(SceneTexture, Input.TextureCoordinate); + vec4 bloomColor = texture(BloomTexture, Input.TextureCoordinate); + hdrColor += bloomColor; + + //Toon mapping thingy + vec3 result = vec3(1.0) - exp(-hdrColor.rgb * Exposure); + + //gamme correction + result = pow(result, vec3(1.0 / gamma)); + + fragmentColor = vec4(result, 1.0); + //fragmentColor = hdrColor; + //fragmentColor = bloomColor; + //fragmentColor = vec4(1,0.5,0.7,1); +} + + diff --git a/resources/Shaders/DrawColorCorrection.vert.glsl b/resources/Shaders/DrawColorCorrection.vert.glsl new file mode 100644 index 00000000..346bc141 --- /dev/null +++ b/resources/Shaders/DrawColorCorrection.vert.glsl @@ -0,0 +1,13 @@ +#version 430 + +layout (location = 0) in vec3 Position; + +out VertexData{ + vec2 TextureCoordinate; +}Output; + +void main() +{ + gl_Position = vec4(Position, 1.0); + Output.TextureCoordinate = (vec2(Position) + 1) / 2; +} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_horiz.frag.glsl b/resources/Shaders/Gaussian_horiz.frag.glsl new file mode 100644 index 00000000..bd48d2d5 --- /dev/null +++ b/resources/Shaders/Gaussian_horiz.frag.glsl @@ -0,0 +1,23 @@ +#version 430 + +layout (binding = 0) uniform sampler2D Texture; + +in VertexData{ + vec2 TextureCoordinate; +}Input; + +out vec4 fragmentColor; + +uniform float weight[5] = float[](0.227027, 0.1945946, 0.1216216, 0.054054, 0.016216); + +void main() +{ + vec2 tex_offset = 1.0 / textureSize(Texture, 0); + vec3 result = texture(Texture, Input.TextureCoordinate).rgb * weight[0]; + + for(int i = 1; i < 5; ++i) { + result += texture(Texture, Input.TextureCoordinate + vec2(tex_offset.x * i, 0.0)).rgb * weight[i]; + result += texture(Texture, Input.TextureCoordinate - vec2(tex_offset.x * i, 0.0)).rgb * weight[i]; + } + fragmentColor = vec4(result, 1.0); +} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_horiz.vert.glsl b/resources/Shaders/Gaussian_horiz.vert.glsl new file mode 100644 index 00000000..346bc141 --- /dev/null +++ b/resources/Shaders/Gaussian_horiz.vert.glsl @@ -0,0 +1,13 @@ +#version 430 + +layout (location = 0) in vec3 Position; + +out VertexData{ + vec2 TextureCoordinate; +}Output; + +void main() +{ + gl_Position = vec4(Position, 1.0); + Output.TextureCoordinate = (vec2(Position) + 1) / 2; +} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_vert.frag.glsl b/resources/Shaders/Gaussian_vert.frag.glsl new file mode 100644 index 00000000..25b08f9f --- /dev/null +++ b/resources/Shaders/Gaussian_vert.frag.glsl @@ -0,0 +1,23 @@ +#version 430 + +layout (binding = 0) uniform sampler2D Texture; + +in VertexData{ + vec2 TextureCoordinate; +}Input; + +out vec4 fragmentColor; + +uniform float weight[5] = float[](0.227027, 0.1945946, 0.1216216, 0.054054, 0.016216); + +void main() +{ + vec2 tex_offset = 1.0 / textureSize(Texture, 0); + vec3 result = texture(Texture, Input.TextureCoordinate).rgb * weight[0]; + + for(int i = 1; i < 5; ++i) { + result += texture(Texture, Input.TextureCoordinate + vec2(0.0, tex_offset.y * i)).rgb * weight[i]; + result += texture(Texture, Input.TextureCoordinate - vec2(0.0, tex_offset.y * i)).rgb * weight[i]; + } + fragmentColor = vec4(result, 1.0); +} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_vert.vert.glsl b/resources/Shaders/Gaussian_vert.vert.glsl new file mode 100644 index 00000000..346bc141 --- /dev/null +++ b/resources/Shaders/Gaussian_vert.vert.glsl @@ -0,0 +1,13 @@ +#version 430 + +layout (location = 0) in vec3 Position; + +out VertexData{ + vec2 TextureCoordinate; +}Output; + +void main() +{ + gl_Position = vec4(Position, 1.0); + Output.TextureCoordinate = (vec2(Position) + 1) / 2; +} \ No newline at end of file diff --git a/src/Engine/Rendering/DrawBloomEffect.cpp b/src/Engine/Rendering/DrawBloomEffect.cpp deleted file mode 100644 index b0ca4afe..00000000 --- a/src/Engine/Rendering/DrawBloomEffect.cpp +++ /dev/null @@ -1,66 +0,0 @@ -#include "Rendering/DrawFinalPass.h" - -DrawFinalPass::DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCullingPass) -{ - m_Renderer = renderer; - m_LightCullingPass = lightCullingPass; - InitializeTextures(); - InitializeShaderPrograms(); -} - -void DrawFinalPass::InitializeTextures() -{ - m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); -} - -void DrawFinalPass::InitializeShaderPrograms() -{ - m_ForwardPlusProgram = ResourceManager::Load("#ForwardPlusProgram"); - m_ForwardPlusProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/ForwardPlus.vert.glsl"))); - m_ForwardPlusProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/ForwardPlus.frag.glsl"))); - m_ForwardPlusProgram->Compile(); - m_ForwardPlusProgram->Link(); -} - -void DrawFinalPass::Draw(RenderScene& scene) -{ - GLERROR("DrawFinalPass::Draw: Pre"); - - DrawFinalPassState state; - m_ForwardPlusProgram->Bind(); - GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); - - glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 1, m_LightCullingPass->LightSSBO()); - glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 2, m_LightCullingPass->LightGridSSBO()); - glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 4, m_LightCullingPass->LightIndexSSBO()); - - glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ViewMatrix())); - glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ProjectionMatrix())); - glUniform2f(glGetUniformLocation(shaderHandle, "ScreenDimensions"), m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); - - //TODO: Render: Add code for more jobs than modeljobs. - for (auto &job : scene.ForwardJobs) { - auto modelJob = std::dynamic_pointer_cast(job); - if(modelJob) { - //TODO: Kolla upp "header/include/common" shader saken så man slipper skicka in asmycket uniforms - glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); - glUniform4fv(glGetUniformLocation(shaderHandle, "Color"), 1, glm::value_ptr(modelJob->Color)); - - if(modelJob->DiffuseTexture != nullptr) { - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, modelJob->DiffuseTexture->m_Texture); - } else { - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); - } - - glBindVertexArray(modelJob->Model->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, 0, modelJob->StartIndex); - - continue; - } - } - GLERROR("DrawFinalPass::Draw: END"); - -} diff --git a/src/Engine/Rendering/DrawBloomPass.cpp b/src/Engine/Rendering/DrawBloomPass.cpp new file mode 100644 index 00000000..20e5f0c0 --- /dev/null +++ b/src/Engine/Rendering/DrawBloomPass.cpp @@ -0,0 +1,121 @@ +#include "Rendering/DrawBloomPass.h" + +DrawBloomPass::DrawBloomPass(IRenderer* renderer) +{ + m_Renderer = renderer; + + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + + InitializeTextures(); + InitializeBuffers(); + InitializeShaderPrograms(); +} + +void DrawBloomPass::InitializeTextures() +{ + m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); +} + +void DrawBloomPass::InitializeShaderPrograms() +{ + m_GaussianProgram_horiz = ResourceManager::Load("##GaussianProgramHoriz"); + m_GaussianProgram_horiz->AddShader(std::shared_ptr(new VertexShader("Shaders/Gaussian_horiz.vert.glsl"))); + m_GaussianProgram_horiz->AddShader(std::shared_ptr(new FragmentShader("Shaders/Gaussian_horiz.frag.glsl"))); + m_GaussianProgram_horiz->Compile(); + m_GaussianProgram_horiz->Link(); + + m_GaussianProgram_vert = ResourceManager::Load("##GaussianProgramVert"); + m_GaussianProgram_vert->AddShader(std::shared_ptr(new VertexShader("Shaders/Gaussian_vert.vert.glsl"))); + m_GaussianProgram_vert->AddShader(std::shared_ptr(new FragmentShader("Shaders/Gaussian_vert.frag.glsl"))); + m_GaussianProgram_vert->Compile(); + m_GaussianProgram_vert->Link(); +} + + +void DrawBloomPass::InitializeBuffers() +{ + GenerateTexture(&m_GaussianTexture_horiz, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + + m_GaussianFrameBuffer_horiz.AddResource(std::shared_ptr(new Texture2D(&m_GaussianTexture_horiz, GL_COLOR_ATTACHMENT0))); + m_GaussianFrameBuffer_horiz.Generate(); + + GenerateTexture(&m_GaussianTexture_vert, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + + m_GaussianFrameBuffer_vert.AddResource(std::shared_ptr(new Texture2D(&m_GaussianTexture_vert, GL_COLOR_ATTACHMENT0))); + m_GaussianFrameBuffer_vert.Generate(); +} + +void DrawBloomPass::Draw(GLuint texture) +{ + GLERROR("DrawBloomPass::Draw: Pre"); + + DrawBloomPassState state; + + GLuint shaderHandle_horiz = m_GaussianProgram_horiz->GetHandle(); + GLuint shaderHandle_vert = m_GaussianProgram_vert->GetHandle(); + + + //Horizontal pass, first use the given texture then save it to the horizontal framebuffer. + m_GaussianFrameBuffer_horiz.Bind(); + m_GaussianProgram_horiz->Bind(); + + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, texture); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + + //Iterate some times to make it more gaussian. + for (int i = 1; i < m_iterations; i++) { + //Vertical pass + m_GaussianFrameBuffer_vert.Bind(); + m_GaussianProgram_vert->Bind(); + + glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_horiz); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + + //horizontal pass + + m_GaussianFrameBuffer_horiz.Bind(); + m_GaussianProgram_horiz->Bind(); + + glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_vert); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + } + + //final vertical gaussian after the iterations are done + + m_GaussianFrameBuffer_vert.Bind(); + m_GaussianProgram_vert->Bind(); + + glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_horiz); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + + GLERROR("DrawBloomPass::Draw: END"); +} + +void DrawBloomPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const +{ + glGenTextures(1, texture); + glBindTexture(GL_TEXTURE_2D, *texture); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filtering); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filtering); + glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, dimensions.x, dimensions.y, 0, format, type, nullptr);//TODO: Renderer: Fix the precision and Resolution + GLERROR("Texture initialization failed"); +} diff --git a/src/Engine/Rendering/DrawBloomPassState.cpp b/src/Engine/Rendering/DrawBloomPassState.cpp new file mode 100644 index 00000000..d4ee4956 --- /dev/null +++ b/src/Engine/Rendering/DrawBloomPassState.cpp @@ -0,0 +1,17 @@ +#include "Rendering/DrawBloomPassState.h" + + +DrawBloomPassState::DrawBloomPassState() +{ + //BindFramebuffer(0); + Disable(GL_BLEND); + Disable(GL_DEPTH_TEST); + Disable(GL_CULL_FACE); + ClearColor(glm::vec4(0.f / 255, 0.f / 255, 0.f / 255, 0.f)); + Clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); +} + +DrawBloomPassState::~DrawBloomPassState() +{ + +} diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp new file mode 100644 index 00000000..8f9cd1ed --- /dev/null +++ b/src/Engine/Rendering/DrawColorCorrectionPass.cpp @@ -0,0 +1,41 @@ +#include "Rendering/DrawColorCorrectionPass.h" + +DrawColorCorrectionPass::DrawColorCorrectionPass(IRenderer* renderer) +{ + m_Renderer = renderer; + + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + m_Exposure = 3; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. + + InitializeShaderPrograms(); +} + +void DrawColorCorrectionPass::InitializeShaderPrograms() +{ + m_ColorCorrectionProgram = ResourceManager::Load("#ColorCorrectionProgram"); + m_ColorCorrectionProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawColorCorrection.vert.glsl"))); + m_ColorCorrectionProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawColorCorrection.frag.glsl"))); + m_ColorCorrectionProgram->Compile(); + m_ColorCorrectionProgram->Link(); +} + +void DrawColorCorrectionPass::Draw(GLuint sceneTexture, GLuint bloomTexture) +{ + //glBindFramebuffer(GL_FRAMEBUFFER, 0); + GLERROR("DrawScreenQuadPass::Draw: Pre"); + + DrawScreenQuadPassState state = DrawScreenQuadPassState(); + m_ColorCorrectionProgram->Bind(); + + glUniform1f(glGetUniformLocation(m_ColorCorrectionProgram->GetHandle(), "Exposure"), m_Exposure); + + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, sceneTexture); + glActiveTexture(GL_TEXTURE1); + glBindTexture(GL_TEXTURE_2D, bloomTexture); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); +} diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 894f358f..546552b7 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -100,7 +100,10 @@ void Renderer::Draw(RenderFrame& frame) m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); //m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_SceneTexture); - m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_BloomTexture); + //m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_BloomTexture); + m_DrawBloomPass->Draw(m_DrawFinalPass->m_BloomTexture); + m_DrawColorCorrectionPass->Draw(m_DrawFinalPass->m_SceneTexture, m_DrawBloomPass->m_GaussianTexture_vert); + //m_DrawScreenQuadPass->Draw(m_DrawBloomPass->m_GaussianTexture_vert); //m_DrawScenePass->Draw(rq); GLERROR("Renderer::Draw m_DrawScenePass->Draw"); @@ -147,4 +150,6 @@ void Renderer::InitializeRenderPasses() m_LightCullingPass = new LightCullingPass(this); m_DrawFinalPass = new DrawFinalPass(this, m_LightCullingPass); m_DrawScreenQuadPass = new DrawScreenQuadPass(this); + m_DrawBloomPass = new DrawBloomPass(this); + m_DrawColorCorrectionPass = new DrawColorCorrectionPass(this); } \ No newline at end of file From 0183e1bdb7390299cddeb977b03a473d5a90ede2 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 12:24:08 +0100 Subject: [PATCH 147/224] Fixed enum string parsing bug that would ignore parsing additional fields in a component after it encountered the first enum. --- resources/Schema/Entities/EditorWidgetRotate.xml | 6 +++--- src/Engine/Core/EntityFile.cpp | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml index 8c454f0c..6a5f72ea 100644 --- a/resources/Schema/Entities/EditorWidgetRotate.xml +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -3,9 +3,6 @@ - - - @@ -15,6 +12,7 @@ + Models/RotationWidgetX.obj @@ -29,6 +27,7 @@ + Models/RotationWidgetY.obj @@ -43,6 +42,7 @@ + Models/RotationWidgetZ.obj diff --git a/src/Engine/Core/EntityFile.cpp b/src/Engine/Core/EntityFile.cpp index 7609db2b..a8e93e49 100644 --- a/src/Engine/Core/EntityFile.cpp +++ b/src/Engine/Core/EntityFile.cpp @@ -171,7 +171,7 @@ void EntityFileSAXHandler::endElement(const XMLCh* const _uri, const XMLCh* cons //} } - if (m_StateStack.top() == State::ComponentField) { + if (m_StateStack.top() == State::ComponentField && name == m_CurrentField) { m_StateStack.pop(); onEndComponentField(name); return; From 70bbc5ed0a63b79ebb9e868aedf8f8e521321016 Mon Sep 17 00:00:00 2001 From: Tleety Date: Thu, 21 Jan 2016 13:52:43 +0100 Subject: [PATCH 148/224] Normals scaling with model scale bug fixed. --- resources/Shaders/ForwardPlus.frag.glsl | 2 +- src/Engine/Rendering/DrawColorCorrectionPass.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 3fae9eb6..a3f998b8 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -102,7 +102,7 @@ void main() { vec4 texel = texture2D(texture0, Input.TextureCoordinate); vec4 position = V * M * vec4(Input.Position, 1.0); - vec4 normal = V * vec4(Input.Normal, 0.0); + vec4 normal = normalize(V * vec4(Input.Normal, 0.0)); vec4 viewVec = normalize(-position); vec2 tilePos; diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp index 8f9cd1ed..debbcab0 100644 --- a/src/Engine/Rendering/DrawColorCorrectionPass.cpp +++ b/src/Engine/Rendering/DrawColorCorrectionPass.cpp @@ -5,7 +5,7 @@ DrawColorCorrectionPass::DrawColorCorrectionPass(IRenderer* renderer) m_Renderer = renderer; m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); - m_Exposure = 3; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. + m_Exposure = 2; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. InitializeShaderPrograms(); } From b9147344e199f4f88fbd846e81d555a76859215f Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 14:14:22 +0100 Subject: [PATCH 149/224] Semi-working translation widget --- include/Engine/Editor/EditorSystem.h | 7 +++++ include/Engine/Editor/EditorWidgetSystem.h | 12 +++++++ .../Schema/Entities/EditorWidgetRotate.xml | 3 ++ .../Schema/Entities/EditorWidgetTranslate.xml | 3 ++ src/Engine/Core/Transform.cpp | 2 +- src/Engine/Editor/EditorSystem.cpp | 31 +++++++++++++++++-- src/Engine/Editor/EditorWidgetSystem.cpp | 23 ++++++++++---- 7 files changed, 72 insertions(+), 9 deletions(-) diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index 31d5064c..befa46b6 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -9,6 +9,7 @@ #include "../Core/EntityFilePreprocessor.h" #include "../Core/EntityFileParser.h" #include "../Core/EntityFileWriter.h" +#include "../Core/EMouseRelease.h" #include "EditorGUI.h" #include "EditorStats.h" @@ -49,4 +50,10 @@ private: void OnEntityChangeName(EntityWrapper entity, const std::string& name); void OnComponentAttach(EntityWrapper entity, const std::string& componentType); void OnComponentDelete(EntityWrapper entity, const std::string& componentType); + + // Events + EventRelay m_EMouseRelease; + bool OnMouseRelease(const Events::MouseRelease& e); + EventRelay m_EWidgetDelta; + bool OnWidgetDelta(const Events::WidgetDelta& e); }; \ No newline at end of file diff --git a/include/Engine/Editor/EditorWidgetSystem.h b/include/Engine/Editor/EditorWidgetSystem.h index f3e4e4db..a2329342 100644 --- a/include/Engine/Editor/EditorWidgetSystem.h +++ b/include/Engine/Editor/EditorWidgetSystem.h @@ -10,6 +10,18 @@ #include "../Core/EMousePress.h" #include "../Core/EMouseRelease.h" +namespace Events +{ + +struct WidgetDelta : Event +{ + glm::vec3 Translation; + glm::vec3 Rotation; + glm::vec3 Scale; +}; + +} + class EditorWidgetSystem : public ImpureSystem, PureSystem { public: diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml index 6a5f72ea..0a8f06b8 100644 --- a/resources/Schema/Entities/EditorWidgetRotate.xml +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -9,6 +9,7 @@ + @@ -24,6 +25,7 @@ + @@ -39,6 +41,7 @@ + diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml index 75d96a51..70ca09a8 100644 --- a/resources/Schema/Entities/EditorWidgetTranslate.xml +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -12,6 +12,7 @@ + @@ -24,6 +25,7 @@ + @@ -36,6 +38,7 @@ + diff --git a/src/Engine/Core/Transform.cpp b/src/Engine/Core/Transform.cpp index 8acac937..cbc405a3 100644 --- a/src/Engine/Core/Transform.cpp +++ b/src/Engine/Core/Transform.cpp @@ -7,7 +7,7 @@ glm::vec3 Transform::AbsolutePosition(World* world, EntityID entity) while (entity != EntityID_Invalid) { ComponentWrapper transform = world->GetComponent(entity, "Transform"); EntityID parent = world->GetParent(entity); - position += Transform::AbsoluteScale(world, parent) * Transform::AbsoluteOrientation(world, parent) * (glm::vec3)transform["Position"]; + position += Transform::AbsoluteOrientation(world, parent) * (glm::vec3)transform["Position"]; entity = parent; } diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 613f0edb..13d74a65 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -31,6 +31,9 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorGUI->SetComponentDeleteCallback(std::bind(&EditorSystem::OnComponentDelete, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetWidgetModeCallback(std::bind(&EditorSystem::setWidgetMode, this, std::placeholders::_1)); + EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorSystem::OnMouseRelease); + EVENT_SUBSCRIBE_MEMBER(m_EWidgetDelta, &EditorSystem::OnWidgetDelta); + m_EditorStats = new EditorStats(); Events::SetCamera e; @@ -49,11 +52,15 @@ EditorSystem::~EditorSystem() void EditorSystem::Update(double dt) { - m_EditorWorldSystemPipeline->Update(dt); - m_EditorGUI->Draw(); m_EditorStats->Draw(dt); + if (m_CurrentSelection.Valid() && m_Widget.Valid()) { + (glm::vec3&)m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(m_CurrentSelection.World, m_CurrentSelection.ID); + } + + m_EditorWorldSystemPipeline->Update(dt); + m_DebugCameraInputController->Update(dt); m_Camera["Transform"]["Position"] = m_DebugCameraInputController->Position(); m_Camera["Transform"]["Orientation"] = glm::eulerAngles(m_DebugCameraInputController->Orientation()); @@ -103,6 +110,26 @@ void EditorSystem::OnComponentDelete(EntityWrapper entity, const std::string& co entity.World->DeleteComponent(entity.ID, componentType); } +bool EditorSystem::OnMouseRelease(const Events::MouseRelease& e) +{ + if (e.Button == GLFW_MOUSE_BUTTON_1) { + PickData pick = m_Renderer->Pick(glm::vec2(e.X, e.Y)); + if (pick.World == m_World) { + m_CurrentSelection = EntityWrapper(m_World, pick.Entity); + m_EditorGUI->SelectEntity(m_CurrentSelection); + } + } + return true; +} + +bool EditorSystem::OnWidgetDelta(const Events::WidgetDelta& e) +{ + if (m_CurrentSelection.Valid()) { + (glm::vec3&)m_CurrentSelection["Transform"]["Position"] += glm::inverse(Transform::AbsoluteOrientation(m_CurrentSelection.World, m_CurrentSelection.ID)) * e.Translation; + } + return true; +} + EntityWrapper EditorSystem::importEntity(EntityWrapper parent, boost::filesystem::path filePath) { if (parent.World == nullptr) { diff --git a/src/Engine/Editor/EditorWidgetSystem.cpp b/src/Engine/Editor/EditorWidgetSystem.cpp index 3a200e0f..1417f20e 100644 --- a/src/Engine/Editor/EditorWidgetSystem.cpp +++ b/src/Engine/Editor/EditorWidgetSystem.cpp @@ -21,19 +21,30 @@ void EditorWidgetSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper return; } + Events::WidgetDelta e; + EntityWrapper moveEntity = entity.Parent(); if (!moveEntity.Valid()) { moveEntity = entity; } + auto camera = m_PickData.Camera; + glm::vec3 axis = cEditorWidget["Axis"]; + glm::vec2 axisScreen = camera->WorldToScreen(axis, m_Renderer->Resolution()) - camera->WorldToScreen(glm::vec3(0, 0, 0), m_Renderer->Resolution()); + float dot = glm::dot(m_MouseDelta, glm::normalize(axisScreen)) / glm::length(axisScreen); + glm::vec3 worldMovement = dot * axis; + ComponentWrapper::SubscriptProxy& type = cEditorWidget["Type"]; if ((ComponentInfo::EnumType)type == type.Enum("Translate")) { - auto camera = m_PickData.Camera; - glm::vec3 axis = cEditorWidget["Axis"]; - glm::vec2 axisScreen = camera->WorldToScreen(axis, m_Renderer->Resolution()) - camera->WorldToScreen(glm::vec3(0, 0, 0), m_Renderer->Resolution()); - float dot = glm::dot(m_MouseDelta, glm::normalize(axisScreen)) / glm::length(axisScreen); - glm::vec3 worldMovement = dot * axis; - (glm::vec3&)moveEntity["Transform"]["Position"] += worldMovement; + e.Translation += worldMovement; + m_EventBroker->Publish(e); + } else if ((ComponentInfo::EnumType)type == type.Enum("Rotate")) { + //if (glm::length(worldMovement) > 0) { + // glm::vec3& orientation = moveEntity["Transform"]["Orientation"]; + // glm::quat q = glm::quat(orientation); + // q *= glm::quat(glm::vec3(worldMovement)); + // orientation = glm::eulerAngles(q); + //} } m_MouseDelta = glm::vec2(0); From 2381f01d124cd4694dd6fcdea507ceb17e4a47fa Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Thu, 21 Jan 2016 14:25:01 +0100 Subject: [PATCH 150/224] HealthSystem now deletes the entity after publishing the PlayerDeath event --- src/Game/Systems/HealthSystem.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/Game/Systems/HealthSystem.cpp b/src/Game/Systems/HealthSystem.cpp index 121d6446..7d4b96b8 100644 --- a/src/Game/Systems/HealthSystem.cpp +++ b/src/Game/Systems/HealthSystem.cpp @@ -37,7 +37,8 @@ void HealthSystem::UpdateComponent(World* world, EntityWrapper& entity, Componen if (std::get<0>(m_DeltaHealthVector[j - 1]) == component.EntityID) m_DeltaHealthVector.erase(m_DeltaHealthVector.begin() + j - 1); } - //break the loop if the player is dead + //delete the player and break the loop + world->DeleteEntity(entity.ID); break; } } @@ -57,3 +58,4 @@ bool HealthSystem::OnPlayerHealthPickup(const Events::PlayerHealthPickup& e) m_DeltaHealthVector.push_back(std::make_tuple(e.PlayerHealedID, e.HealthAmount)); return true; } + From afe43c5f444e0672644ac0abd47ba1244d05282b Mon Sep 17 00:00:00 2001 From: Tleety Date: Thu, 21 Jan 2016 14:53:47 +0100 Subject: [PATCH 151/224] Shader will now handle Glowmaps. However the load code is not there yet. --- assets | 2 +- include/Engine/Rendering/DrawFinalPass.h | 2 ++ resources/Shaders/ForwardPlus.frag.glsl | 32 ++++++++++--------- .../Rendering/DrawColorCorrectionPass.cpp | 2 +- src/Engine/Rendering/DrawFinalPass.cpp | 13 ++++++-- 5 files changed, 32 insertions(+), 19 deletions(-) diff --git a/assets b/assets index 6ffb46e1..cf2ac2a5 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 6ffb46e155c8f013241cd1507098c94900ec2448 +Subproject commit cf2ac2a570b0f2f50907bbbd59d00c59edb53443 diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index 407ad58c..e4c714ef 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -29,6 +29,8 @@ private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; Texture* m_WhiteTexture; + Texture* m_BlackTexture; + Texture* TEMP_glowTestTexture; const IRenderer* m_Renderer; const LightCullingPass* m_LightCullingPass; diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index a3f998b8..421f130c 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -5,7 +5,8 @@ uniform mat4 V; uniform mat4 P; uniform vec4 Color; uniform vec2 ScreenDimensions; -uniform sampler2D texture0; +layout (binding = 0) uniform sampler2D DiffuseTexture; +layout (binding = 1) uniform sampler2D GlowMap; #define TILE_SIZE 16 @@ -100,7 +101,8 @@ LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensi void main() { - vec4 texel = texture2D(texture0, Input.TextureCoordinate); + vec4 diffuseTexel = texture2D(DiffuseTexture, Input.TextureCoordinate); + vec4 glowTexel = texture2D(GlowMap, Input.TextureCoordinate); vec4 position = V * M * vec4(Input.Position, 1.0); vec4 normal = normalize(V * vec4(Input.Normal, 0.0)); vec4 viewVec = normalize(-position); @@ -121,32 +123,32 @@ void main() int l = int(LightIndex[i]); LightSource light = LightSources.List[l]; - LightResult result; + LightResult light_result; //These if statements should be removed. if(light.Type == 1) { // point - result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); + light_result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); } else if (light.Type == 2) { //Directional - result = CalcDirectionalLightSource(V * light.Direction, light.Color, light.Intensity, viewVec, normal); + light_result = CalcDirectionalLightSource(V * light.Direction, light.Color, light.Intensity, viewVec, normal); } - totalLighting.Diffuse += result.Diffuse; - totalLighting.Specular += result.Specular; + totalLighting.Diffuse += light_result.Diffuse; + totalLighting.Specular += light_result.Specular; } //sceneColor += Input.DiffuseColor; - vec4 fragment = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + vec4 color_result = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * diffuseTexel * Color; //bloomColor = vec4(0.3, 0.8, 0.6, 1.0); - sceneColor = vec4(fragment.xyz, 1.0); - //These if statements should be removed. - - if(fragment.x > 1 || fragment.y > 1 || fragment.z > 1) { - bloomColor = vec4(fragment.xyz, 1.0); + sceneColor = vec4(color_result.xyz, 1.0); + //These if statements should be removed if they are slow. + color_result += glowTexel; + if(color_result.x > 1 || color_result.y > 1 || color_result.z > 1) { + bloomColor = vec4(color_result.xyz, 1.0); } else { bloomColor = vec4(0.0, 0.0, 0.0, 1.0); } - //sceneColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; + //sceneColor += Input.DiffuseColor * (totalLighting.Diffuse) * diffuseTexel * Color; //sceneColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); - //sceneColor = texel * Input.DiffuseColor * Color; + //sceneColor = diffuseTexel * Input.DiffuseColor * Color; //sceneColor += vec4(currentTile/3600.f, 0, 0, 1); //Tiled Debug Code diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp index debbcab0..72bcce2a 100644 --- a/src/Engine/Rendering/DrawColorCorrectionPass.cpp +++ b/src/Engine/Rendering/DrawColorCorrectionPass.cpp @@ -5,7 +5,7 @@ DrawColorCorrectionPass::DrawColorCorrectionPass(IRenderer* renderer) m_Renderer = renderer; m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); - m_Exposure = 2; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. + m_Exposure = 1; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. InitializeShaderPrograms(); } diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 5a9f706e..a31beee6 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -12,6 +12,8 @@ DrawFinalPass::DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCulling void DrawFinalPass::InitializeTextures() { m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); + m_BlackTexture = ResourceManager::Load("Textures/Core/Black.png"); + TEMP_glowTestTexture = ResourceManager::Load("Textures/Core/UnitRaptor_glow.png"); } void DrawFinalPass::InitializeFrameBuffers() @@ -65,13 +67,20 @@ void DrawFinalPass::Draw(RenderScene& scene) glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); glUniform4fv(glGetUniformLocation(shaderHandle, "Color"), 1, glm::value_ptr(modelJob->Color)); + glActiveTexture(GL_TEXTURE0); if(modelJob->DiffuseTexture != nullptr) { - glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, modelJob->DiffuseTexture->m_Texture); } else { - glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); } + glActiveTexture(GL_TEXTURE1); + glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); + + /*if(modelJob->GlowMap != nullptr) { + glBindTexture(GL_TEXTURE_2D, modelJob->GlowMap->m_Texture); + } else { + glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); + }*/ glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); From fc06a4babcc75b6827c569fa59b71209997e67cc Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 15:58:27 +0100 Subject: [PATCH 152/224] Editor keyboard shortcuts: Ctrl+S to save the currently selected entity file (iterates to the base parent) Ctrl+N to create a new empty entity under the selection Ctrl+O to import an entity file Del to delete an entity --- include/Engine/Core/EKeyDown.h | 3 + include/Engine/Core/EKeyUp.h | 3 + include/Engine/Editor/EditorGUI.h | 38 +++- .../Schema/Entities/EditorWidgetRotate.xml | 3 - .../Schema/Entities/EditorWidgetTranslate.xml | 3 - src/Engine/Core/EntityWrapper.cpp | 6 +- src/Engine/Core/InputManager.cpp | 6 + src/Engine/Editor/EditorGUI.cpp | 193 ++++++++++++++---- src/Engine/Editor/EditorSystem.cpp | 22 +- 9 files changed, 210 insertions(+), 67 deletions(-) diff --git a/include/Engine/Core/EKeyDown.h b/include/Engine/Core/EKeyDown.h index 3a506bf4..2745fdef 100644 --- a/include/Engine/Core/EKeyDown.h +++ b/include/Engine/Core/EKeyDown.h @@ -11,6 +11,9 @@ struct KeyDown : Event { /** GLFW key code */ int KeyCode; + bool ModCtrl; + bool ModAlt; + bool ModShift; }; } diff --git a/include/Engine/Core/EKeyUp.h b/include/Engine/Core/EKeyUp.h index c7531a01..2d34f04e 100644 --- a/include/Engine/Core/EKeyUp.h +++ b/include/Engine/Core/EKeyUp.h @@ -11,6 +11,9 @@ struct KeyUp : Event { /** GLFW key code */ int KeyCode; + bool ModCtrl; + bool ModAlt; + bool ModShift; }; } diff --git a/include/Engine/Editor/EditorGUI.h b/include/Engine/Editor/EditorGUI.h index 49e0f8ab..973f6a90 100644 --- a/include/Engine/Editor/EditorGUI.h +++ b/include/Engine/Editor/EditorGUI.h @@ -6,6 +6,7 @@ #include #include #include +#include #include "../Common.h" #include "../GLM.h" #include @@ -16,6 +17,7 @@ #include "../Core/EntityWrapper.h" #include "../Core/ResourceManager.h" #include "../Core/EPause.h" +#include "../Core/EKeyDown.h" #include "../Rendering/Texture.h" class EditorGUI @@ -33,6 +35,7 @@ public: void Draw(); void SelectEntity(EntityWrapper entity); + void SetDirty(EntityWrapper entity); // Called when an entity is selected in the entity tree typedef std::function OnEntitySelectedCallback_t; @@ -75,15 +78,23 @@ private: World* m_World; EventBroker* m_EventBroker; + struct EntityFileInfo + { + boost::filesystem::path Path; + bool Dirty = false; + }; + // Config variables const boost::filesystem::path m_DefaultEntityPath = boost::filesystem::path("Schema") / boost::filesystem::path("Entities"); - // State variables + // State EntityWrapper m_CurrentSelection = EntityWrapper::Invalid; - std::unordered_map m_EntityFiles; + std::unordered_map m_EntityFiles; EntityWrapper m_CurrentlyDragging = EntityWrapper::Invalid; std::string m_LastErrorMessage; WidgetMode m_CurrentWidgetMode = WidgetMode::Translate; + std::set m_ModalsToOpen; + std::map m_ModalData; // Callbacks OnEntitySelectedCallback_t m_OnEntitySelected = nullptr; @@ -97,11 +108,16 @@ private: OnComponentDelete_t m_OnComponentDelete = nullptr; OnWidgetMode_t m_OnWidgetMode = nullptr; + // Events + EventRelay m_EKeyDown; + bool OnKeyDown(const Events::KeyDown& e); + // Utility functions boost::filesystem::path fileOpenDialog(); boost::filesystem::path fileSaveDialog(); const std::string formatEntityName(EntityWrapper entity); GLuint tryLoadTexture(std::string filePath); + void openModal(const std::string& modal); // Entity file handling methods void entityImport(World* world); @@ -118,15 +134,15 @@ private: bool drawEntityNode(EntityWrapper entity); void drawComponents(EntityWrapper entity); bool drawComponentNode(EntityWrapper entity, const ComponentInfo& componentType); - void drawComponentField(ComponentWrapper& c, const ComponentInfo::Field_t& field); - void drawComponentField_Vector(ComponentWrapper &c, const ComponentInfo::Field_t &field); - void drawComponentField_Color(ComponentWrapper &c, const ComponentInfo::Field_t &field); - void drawComponentField_int(ComponentWrapper &c, const ComponentInfo::Field_t &field); - void drawComponentField_enum(ComponentWrapper &c, const ComponentInfo::Field_t &field); - void drawComponentField_float(ComponentWrapper &c, const ComponentInfo::Field_t &field); - void drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field); - void drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field); - void drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField(ComponentWrapper& c, const ComponentInfo::Field_t& field); + bool drawComponentField_Vector(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField_Color(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField_int(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField_enum(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField_float(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field); + bool drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field); void drawModals(); // Custom UI elements diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml index 0a8f06b8..6a5f72ea 100644 --- a/resources/Schema/Entities/EditorWidgetRotate.xml +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -9,7 +9,6 @@ - @@ -25,7 +24,6 @@ - @@ -41,7 +39,6 @@ - diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml index 70ca09a8..75d96a51 100644 --- a/resources/Schema/Entities/EditorWidgetTranslate.xml +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -12,7 +12,6 @@ - @@ -25,7 +24,6 @@ - @@ -38,7 +36,6 @@ - diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 58dd1ee6..98b9c7d4 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -10,7 +10,11 @@ bool EntityWrapper::HasComponent(const std::string& componentName) EntityWrapper EntityWrapper::Parent() { - return EntityWrapper(World, World->GetParent(ID)); + if (this->World == nullptr || this->ID == EntityID_Invalid) { + return EntityWrapper::Invalid; + } else { + return EntityWrapper(this->World, this->World->GetParent(this->ID)); + } } bool EntityWrapper::Valid() diff --git a/src/Engine/Core/InputManager.cpp b/src/Engine/Core/InputManager.cpp index 50dcac7c..941cc223 100644 --- a/src/Engine/Core/InputManager.cpp +++ b/src/Engine/Core/InputManager.cpp @@ -34,10 +34,16 @@ void InputManager::Update(double dt) if (m_CurrentKeyState[i]) { Events::KeyDown e; e.KeyCode = i; + e.ModCtrl = glfwGetKey(m_GLFWWindow, GLFW_KEY_LEFT_CONTROL) || glfwGetKey(m_GLFWWindow, GLFW_KEY_RIGHT_CONTROL); + e.ModAlt = glfwGetKey(m_GLFWWindow, GLFW_KEY_LEFT_ALT) || glfwGetKey(m_GLFWWindow, GLFW_KEY_RIGHT_ALT); + e.ModShift = glfwGetKey(m_GLFWWindow, GLFW_KEY_LEFT_SHIFT) || glfwGetKey(m_GLFWWindow, GLFW_KEY_RIGHT_SHIFT); m_EventBroker->Publish(e); } else { Events::KeyUp e; e.KeyCode = i; + e.ModCtrl = glfwGetKey(m_GLFWWindow, GLFW_KEY_LEFT_CONTROL) || glfwGetKey(m_GLFWWindow, GLFW_KEY_RIGHT_CONTROL); + e.ModAlt = glfwGetKey(m_GLFWWindow, GLFW_KEY_LEFT_ALT) || glfwGetKey(m_GLFWWindow, GLFW_KEY_RIGHT_ALT); + e.ModShift = glfwGetKey(m_GLFWWindow, GLFW_KEY_LEFT_SHIFT) || glfwGetKey(m_GLFWWindow, GLFW_KEY_RIGHT_SHIFT); m_EventBroker->Publish(e); } } diff --git a/src/Engine/Editor/EditorGUI.cpp b/src/Engine/Editor/EditorGUI.cpp index d5638d31..390e69a5 100644 --- a/src/Engine/Editor/EditorGUI.cpp +++ b/src/Engine/Editor/EditorGUI.cpp @@ -4,7 +4,7 @@ EditorGUI::EditorGUI(World* world, EventBroker* eventBroker) : m_World(world) , m_EventBroker(eventBroker) { - + EVENT_SUBSCRIBE_MEMBER(m_EKeyDown, &EditorGUI::OnKeyDown); } void EditorGUI::Draw() @@ -14,6 +14,7 @@ void EditorGUI::Draw() drawTools(); drawEntities(m_World); drawComponents(m_CurrentSelection); + drawModals(); } void EditorGUI::SelectEntity(EntityWrapper entity) @@ -111,6 +112,7 @@ void EditorGUI::drawEntities(World* world) if (m_CurrentSelection.Valid()) { if (m_OnEntityChangeName != nullptr) { m_OnEntityChangeName(m_CurrentSelection, std::string(buffer)); + SetDirty(m_CurrentSelection); } } } @@ -120,8 +122,6 @@ void EditorGUI::drawEntities(World* world) drawEntitiesRecursive(world, EntityID_Invalid); - // Draw any potential modals before ending this scope - drawModals(); ImGui::End(); } @@ -167,10 +167,10 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) ImGui::Text(formatEntityName(entity).c_str()); ImGui::End(); } - } else if (m_CurrentlyDragging == entity) { + }/* else if (m_CurrentlyDragging == entity) { LOG_DEBUG("Stopped dragging %i", entity.ID); m_CurrentlyDragging = EntityWrapper::Invalid; - } + }*/ // Entity context menu std::string contextMenuUniqueID = std::string("EntityContextMenu") + std::to_string(entity.ID); if (hovered && ImGui::IsMouseClicked(1)) { @@ -190,7 +190,6 @@ bool EditorGUI::drawEntityNode(EntityWrapper entity) if (ImGui::MenuItem("Move to root")) { entityChangeParent(entity, EntityWrapper::Invalid); } - drawModals(); ImGui::EndPopup(); } @@ -242,6 +241,7 @@ void EditorGUI::drawComponents(EntityWrapper entity) if (m_OnComponentAttach != nullptr) { std::string chosenComponentType(componentTypes.at(selectedItem)); m_OnComponentAttach(entity, chosenComponentType); + SetDirty(entity); } } } @@ -287,7 +287,10 @@ bool EditorGUI::drawComponentNode(EntityWrapper entity, const ComponentInfo& ci) const ComponentInfo::Field_t& field = kv.second; // Draw the field widget based on its type - drawComponentField(component, field); + bool dirty = drawComponentField(component, field); + if (dirty) { + SetDirty(entity); + } ImGui::SameLine(); // Draw field name ImGui::Text(fieldName.c_str()); @@ -305,70 +308,76 @@ bool EditorGUI::drawComponentNode(EntityWrapper entity, const ComponentInfo& ci) return true; } -void EditorGUI::drawComponentField(ComponentWrapper& c, const ComponentInfo::Field_t& field) +bool EditorGUI::drawComponentField(ComponentWrapper& c, const ComponentInfo::Field_t& field) { // Push an unique widget id so different components with fields with equal names are still counted as different ImGui::PushID((c.Info.Name + field.Name).c_str()); + bool dirty = false; + if (field.Type == "Vector") { - drawComponentField_Vector(c, field); + dirty = drawComponentField_Vector(c, field); } else if (field.Type == "Color") { - drawComponentField_Color(c, field); + dirty = drawComponentField_Color(c, field); //} else if (field.Type == "Quaternion") { } else if (field.Type == "int") { - drawComponentField_int(c, field); + dirty = drawComponentField_int(c, field); } else if (field.Type == "enum") { - drawComponentField_enum(c, field); + dirty = drawComponentField_enum(c, field); } else if (field.Type == "float") { - drawComponentField_float(c, field); + dirty = drawComponentField_float(c, field); } else if (field.Type == "double") { - drawComponentField_double(c, field); + dirty = drawComponentField_double(c, field); } else if (field.Type == "bool") { - drawComponentField_bool(c, field); + dirty = drawComponentField_bool(c, field); } else if (field.Type == "string") { - drawComponentField_string(c, field); + dirty = drawComponentField_string(c, field); } else { ImGui::TextDisabled(field.Type.c_str()); } ImGui::PopID(); + + return dirty; } -void EditorGUI::drawComponentField_Vector(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_Vector(ComponentWrapper &c, const ComponentInfo::Field_t &field) { auto& val = c.Field(field.Name); if (field.Name == "Scale") { // Limit scale values to a minimum of 0 - ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, 0.f, std::numeric_limits::max()); + return ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, 0.f, std::numeric_limits::max()); } else if (field.Name == "Orientation") { // Make orentations have a period of 2*Pi glm::vec3 tempVal = glm::fmod(val, glm::vec3(glm::two_pi())); if (ImGui::SliderFloat3("", glm::value_ptr(tempVal), 0.f, glm::two_pi())) { val = tempVal; + return true; + } else { + return false; } } else { - ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, std::numeric_limits::lowest(), std::numeric_limits::max()); + return ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, std::numeric_limits::lowest(), std::numeric_limits::max()); } } -void EditorGUI::drawComponentField_Color(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_Color(ComponentWrapper &c, const ComponentInfo::Field_t &field) { auto& val = c.Field(field.Name); - ImGui::ColorEdit4("", glm::value_ptr(val), true); + return ImGui::ColorEdit4("", glm::value_ptr(val), true); } -void EditorGUI::drawComponentField_int(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_int(ComponentWrapper &c, const ComponentInfo::Field_t &field) { auto& val = c.Field(field.Name); - ImGui::InputInt("", &val); + return ImGui::InputInt("", &val); } -void EditorGUI::drawComponentField_enum(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_enum(ComponentWrapper &c, const ComponentInfo::Field_t &field) { auto fieldEnumDefIt = c.Info.Meta->FieldEnumDefinitions.find(field.Name); if (fieldEnumDefIt == c.Info.Meta->FieldEnumDefinitions.end()) { - drawComponentField_int(c, field); - return; + return drawComponentField_int(c, field); } auto& val = c.Field(field.Name); @@ -386,30 +395,36 @@ void EditorGUI::drawComponentField_enum(ComponentWrapper &c, const ComponentInfo } if (ImGui::Combo("", &selectedItem, enumKeys.str().c_str())) { val = enumValues.at(selectedItem); + return true; + } else { + return false; } } -void EditorGUI::drawComponentField_float(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_float(ComponentWrapper &c, const ComponentInfo::Field_t &field) { auto& val = c.Field(field.Name); - ImGui::InputFloat("", &val, 0.01f, 1.f); + return ImGui::InputFloat("", &val, 0.01f, 1.f); } -void EditorGUI::drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field) { float tempVal = static_cast(c.Field(field.Name)); if (ImGui::InputFloat("", &tempVal, 0.01f, 1.f)) { c.SetField(field.Name, static_cast(tempVal)); + return true; + } else { + return false; } } -void EditorGUI::drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field) { auto& val = c.Field(field.Name); - ImGui::Checkbox("", &val); + return ImGui::Checkbox("", &val); } -void EditorGUI::drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field) +bool EditorGUI::drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field) { auto& val = c.Field(field.Name); char tempString[1024]; // Let's just hope this is an sufficiently large buffer for strings :) @@ -418,12 +433,20 @@ void EditorGUI::drawComponentField_string(ComponentWrapper &c, const ComponentIn memcpy(tempString, val.c_str(), std::min(val.length() + 1, sizeof(tempString) - 1)); if (ImGui::InputText("", tempString, sizeof(tempString))) { val = std::string(tempString); + return true; + } else { + return false; } // TODO: Handle drag and drop of files } void EditorGUI::drawModals() { + for (auto& modal : m_ModalsToOpen) { + ImGui::OpenPopup(modal.c_str()); + } + m_ModalsToOpen.clear(); + if (ImGui::BeginPopupModal("Import failed", nullptr, ImGuiWindowFlags_AlwaysAutoResize)) { ImGui::Text("Entity import failed. Check console for more information.\n\n"); ImGui::SetCursorPosX(ImGui::GetContentRegionAvailWidth() - 120); @@ -441,6 +464,26 @@ void EditorGUI::drawModals() } ImGui::EndPopup(); } + + if (ImGui::BeginPopupModal("Confirm deletion", nullptr, ImGuiWindowFlags_AlwaysAutoResize)) { + if (m_ModalData.count("Confirm deletion") == 0) { + ImGui::CloseCurrentPopup(); + } + + ImGui::Text("Are you sure you want to delete entity \"%s\"?", formatEntityName(m_CurrentSelection).c_str()); + ImGui::ItemSize(ImVec2(5.f, 0.f)); + ImGui::SetCursorPosX(ImGui::GetContentRegionAvailWidth() - 2*60); + if (ImGui::Button("Delete (Del)", ImVec2(60, 0))) { + entityDelete(boost::any_cast(m_ModalData.at("Confirm deletion"))); + ImGui::CloseCurrentPopup(); + } + ImGui::SameLine(); + if (ImGui::Button("Cancel", ImVec2(60, 0))) { + m_ModalData.erase("Confirm deletion"); + ImGui::CloseCurrentPopup(); + } + ImGui::EndPopup(); + } } bool EditorGUI::createDeleteButton(const std::string& componentType) @@ -492,6 +535,35 @@ void EditorGUI::createWidgetToolButton(WidgetMode mode) } } +bool EditorGUI::OnKeyDown(const Events::KeyDown& e) +{ + if (e.ModCtrl && e.KeyCode == GLFW_KEY_S) { + if (m_CurrentSelection.Valid()) { + EntityWrapper baseParent = m_CurrentSelection; + while (baseParent.Parent().Valid()) { + baseParent = baseParent.Parent(); + } + entitySave(baseParent); + } + } + + if (e.ModCtrl && e.KeyCode == GLFW_KEY_N) { + entityCreate(m_World, m_CurrentSelection); + } + + if (e.ModCtrl && e.KeyCode == GLFW_KEY_O) { + entityImport(m_World); + } + + if (e.KeyCode == GLFW_KEY_DELETE) { + if (m_CurrentSelection.Valid()) { + entityDelete(m_CurrentSelection); + } + } + + return true; +} + boost::filesystem::path EditorGUI::fileOpenDialog() { namespace bfs = boost::filesystem; @@ -540,7 +612,10 @@ const std::string EditorGUI::formatEntityName(EntityWrapper entity) } if (m_EntityFiles.count(entity) == 1) { - name << " (" << m_EntityFiles.at(entity).filename().string() << ")"; + name << " (" << m_EntityFiles.at(entity).Path.filename().string() << ")"; + if (m_EntityFiles.at(entity).Dirty) { + name << "*"; + } } return name.str(); @@ -555,6 +630,22 @@ GLuint EditorGUI::tryLoadTexture(std::string filePath) return texture; } +void EditorGUI::openModal(const std::string& modal) +{ + m_ModalsToOpen.insert(modal); +} + +void EditorGUI::SetDirty(EntityWrapper entity) +{ + EntityWrapper baseParent = entity; + while (baseParent.Parent().Valid()) { + baseParent = baseParent.Parent(); + } + if (m_EntityFiles.find(baseParent) != m_EntityFiles.end()) { + m_EntityFiles.at(baseParent).Dirty = true; + } +} + void EditorGUI::entityImport(World* world) { boost::filesystem::path filePath = fileOpenDialog(); @@ -564,10 +655,10 @@ void EditorGUI::entityImport(World* world) EntityWrapper entity = m_OnEntityImport(EntityWrapper(world, EntityID_Invalid), filePath); if (entity.Valid()) { - m_EntityFiles[entity] = filePath; + m_EntityFiles[entity].Path = filePath; SelectEntity(entity); } else { - ImGui::OpenPopup("Import failed"); + openModal("Import failed"); } } @@ -575,7 +666,7 @@ void EditorGUI::entitySave(EntityWrapper entity, bool saveAs /* = false */) { boost::filesystem::path filePath; if (!saveAs && m_EntityFiles.count(entity) == 1) { - filePath = m_EntityFiles.at(entity); + filePath = m_EntityFiles.at(entity).Path; } else { filePath = fileSaveDialog(); } @@ -586,10 +677,11 @@ void EditorGUI::entitySave(EntityWrapper entity, bool saveAs /* = false */) try { m_OnEntitySave(entity, filePath); - m_EntityFiles[entity] = filePath; + m_EntityFiles[entity].Path = filePath; + m_EntityFiles[entity].Dirty = false; } catch (const std::exception& e) { m_LastErrorMessage = e.what(); - ImGui::OpenPopup("Save failed"); + openModal("Save failed"); } } @@ -607,12 +699,24 @@ void EditorGUI::entityCreate(World* world, EntityWrapper parent) void EditorGUI::entityDelete(EntityWrapper entity) { - if (m_OnEntityDelete != nullptr) { - m_OnEntityDelete(entity); - m_EntityFiles.erase(entity); - } - if (!m_CurrentSelection.Valid()) { - SelectEntity(EntityWrapper::Invalid); + std::string modalName = "Confirm deletion"; + + if (m_ModalData.count(modalName) == 0) { + m_ModalData[modalName] = entity; + openModal(modalName); + } else { + if (boost::any_cast(m_ModalData[modalName]) == entity) { + EntityWrapper parent = entity.Parent(); + if (m_OnEntityDelete != nullptr) { + SetDirty(entity); + m_OnEntityDelete(entity); + m_EntityFiles.erase(entity); + } + if (!m_CurrentSelection.Valid()) { + SelectEntity(parent); + } + } + m_ModalData.erase(modalName); } } @@ -623,6 +727,7 @@ void EditorGUI::entityChangeParent(EntityWrapper entity, EntityWrapper parent) } if (m_OnEntityChangeParent != nullptr) { + SetDirty(entity); m_OnEntityChangeParent(entity, parent); LOG_DEBUG("Changed parent of %i to %i", entity.ID, parent.ID); } diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 13d74a65..116ad4cc 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -52,6 +52,7 @@ EditorSystem::~EditorSystem() void EditorSystem::Update(double dt) { + m_EventBroker->Process(); m_EditorGUI->Draw(); m_EditorStats->Draw(dt); @@ -87,27 +88,37 @@ EntityWrapper EditorSystem::OnEntityCreate(EntityWrapper parent) void EditorSystem::OnEntityDelete(EntityWrapper entity) { - entity.World->DeleteEntity(entity.ID); + if (entity.Valid()) { + entity.World->DeleteEntity(entity.ID); + } } void EditorSystem::OnEntityChangeParent(EntityWrapper entity, EntityWrapper parent) { - entity.World->SetParent(entity.ID, parent.ID); + if (entity.Valid()) { + entity.World->SetParent(entity.ID, parent.ID); + } } void EditorSystem::OnEntityChangeName(EntityWrapper entity, const std::string& name) { - entity.World->SetName(entity.ID, name); + if (entity.Valid()) { + entity.World->SetName(entity.ID, name); + } } void EditorSystem::OnComponentAttach(EntityWrapper entity, const std::string& componentType) { - entity.World->AttachComponent(entity.ID, componentType); + if (entity.Valid()) { + entity.World->AttachComponent(entity.ID, componentType); + } } void EditorSystem::OnComponentDelete(EntityWrapper entity, const std::string& componentType) { - entity.World->DeleteComponent(entity.ID, componentType); + if (entity.Valid()) { + entity.World->DeleteComponent(entity.ID, componentType); + } } bool EditorSystem::OnMouseRelease(const Events::MouseRelease& e) @@ -126,6 +137,7 @@ bool EditorSystem::OnWidgetDelta(const Events::WidgetDelta& e) { if (m_CurrentSelection.Valid()) { (glm::vec3&)m_CurrentSelection["Transform"]["Position"] += glm::inverse(Transform::AbsoluteOrientation(m_CurrentSelection.World, m_CurrentSelection.ID)) * e.Translation; + m_EditorGUI->SetDirty(m_CurrentSelection); } return true; } From 7deb32431ef28150429bcb90f7cdb0f2e54d7b31 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Thu, 21 Jan 2016 16:03:30 +0100 Subject: [PATCH 153/224] Removed Color TestCode in WeaponSystem --- include/Game/Systems/WeaponSystem.h | 1 - src/Game/Systems/WeaponSystem.cpp | 7 ------- 2 files changed, 8 deletions(-) diff --git a/include/Game/Systems/WeaponSystem.h b/include/Game/Systems/WeaponSystem.h index 36af4231..b85ba323 100644 --- a/include/Game/Systems/WeaponSystem.h +++ b/include/Game/Systems/WeaponSystem.h @@ -33,7 +33,6 @@ private: IRenderer* m_Renderer; std::vector> m_EShootVector; - double m_TestDamageTotal = 0.0; }; #endif \ No newline at end of file diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp index ada48b54..6a701f6d 100644 --- a/src/Game/Systems/WeaponSystem.cpp +++ b/src/Game/Systems/WeaponSystem.cpp @@ -31,13 +31,6 @@ void WeaponSystem::Update(World* world, double dt) ePlayerDamage.PlayerDamagedID = somePickData.Entity; ePlayerDamage.TypeOfDamage = "Some Weapon"; m_EventBroker->Publish(ePlayerDamage); - //tests:color - m_TestDamageTotal += 0.25f; - if (m_TestDamageTotal > 6.0f) { - m_TestDamageTotal = 0.25f; - } - ComponentWrapper& playerModel = world->GetComponent(somePickData.Entity, "Model"); - playerModel["Color"] = glm::vec4(m_TestDamageTotal, 0, 0, 1); } m_EShootVector.erase(m_EShootVector.begin() + i - 1); } From 43b8fd29f62a52f4035eb24aa87df2d398ea7fea Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 16:21:20 +0100 Subject: [PATCH 154/224] Fixed widget world movement --- src/Engine/Editor/EditorSystem.cpp | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 116ad4cc..1ef8b02b 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -136,7 +136,12 @@ bool EditorSystem::OnMouseRelease(const Events::MouseRelease& e) bool EditorSystem::OnWidgetDelta(const Events::WidgetDelta& e) { if (m_CurrentSelection.Valid()) { - (glm::vec3&)m_CurrentSelection["Transform"]["Position"] += glm::inverse(Transform::AbsoluteOrientation(m_CurrentSelection.World, m_CurrentSelection.ID)) * e.Translation; + glm::quat parentOrientation; + EntityWrapper parent = m_CurrentSelection.Parent(); + if (parent.Valid()) { + parentOrientation = glm::inverse(Transform::AbsoluteOrientation(parent.World, parent.ID)); + } + (glm::vec3&)m_CurrentSelection["Transform"]["Position"] += parentOrientation * e.Translation; m_EditorGUI->SetDirty(m_CurrentSelection); } return true; From 973ccd34c9721bce9eceb7a316ee8c6a6428c3f0 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Thu, 21 Jan 2016 16:30:07 +0100 Subject: [PATCH 155/224] Removed unnecessary string in EPlayerDamage (TypeOfDamage). Renamed a variable in WeaponSystem --- include/Engine/Core/EPlayerDamage.h | 2 -- src/Engine/Network/Client.cpp | 1 - src/Engine/Network/Server.cpp | 1 - src/Game/Systems/WeaponSystem.cpp | 9 ++++----- 4 files changed, 4 insertions(+), 9 deletions(-) diff --git a/include/Engine/Core/EPlayerDamage.h b/include/Engine/Core/EPlayerDamage.h index 87ad67aa..e0f2acd7 100644 --- a/include/Engine/Core/EPlayerDamage.h +++ b/include/Engine/Core/EPlayerDamage.h @@ -11,8 +11,6 @@ struct PlayerDamage : Event { double DamageAmount; EntityID PlayerDamagedID; - //optional TypeOfDamage - std::string TypeOfDamage; }; } diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 8eee335e..10432bba 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -288,7 +288,6 @@ bool Client::OnPlayerDamage(const Events::PlayerDamage & e) Packet packet(MessageType::OnInputCommand, m_SendPacketID); packet.WritePrimitive(e.DamageAmount); packet.WritePrimitive(e.PlayerDamagedID); - packet.WriteString(e.TypeOfDamage); send(packet); return false; } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 8a194c0e..f4373a83 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -240,7 +240,6 @@ void Server::parseOnPlayerDamage(Packet & packet) Events::PlayerDamage e; e.DamageAmount = packet.ReadPrimitive(); e.PlayerDamagedID = packet.ReadPrimitive(); - e.TypeOfDamage = packet.ReadString(); m_EventBroker->Publish(e); //LOG_DEBUG("Server::parseOnPlayerDamage: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str()); } diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp index 6a701f6d..ec81b08b 100644 --- a/src/Game/Systems/WeaponSystem.cpp +++ b/src/Game/Systems/WeaponSystem.cpp @@ -16,20 +16,19 @@ void WeaponSystem::Update(World* world, double dt) //TODO: check if player has enough ammo and if weapon has a cooldown or not //pick the object - PickData somePickData = m_Renderer->Pick(std::get<1>(m_EShootVector[i - 1])); - if (somePickData.Entity == EntityID_Invalid) { + PickData pickDataFromShot = m_Renderer->Pick(std::get<1>(m_EShootVector[i - 1])); + if (pickDataFromShot.Entity == EntityID_Invalid) { m_EShootVector.erase(m_EShootVector.begin() + i - 1); continue; } //if its a player, do PlayerDamage event - const bool hasPlayerComponent = world->HasComponent(somePickData.Entity, "Player"); + const bool hasPlayerComponent = world->HasComponent(pickDataFromShot.Entity, "Player"); if (hasPlayerComponent) { Events::PlayerDamage ePlayerDamage; //TODO: damage based on weapontype/class? //TODO: multiple shots at the same time? (shotgunner) ePlayerDamage.DamageAmount = 25; - ePlayerDamage.PlayerDamagedID = somePickData.Entity; - ePlayerDamage.TypeOfDamage = "Some Weapon"; + ePlayerDamage.PlayerDamagedID = pickDataFromShot.Entity; m_EventBroker->Publish(ePlayerDamage); } m_EShootVector.erase(m_EShootVector.begin() + i - 1); From 1c6750f5b03bf711e6f428191e4f37208846a5f1 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 16:37:35 +0100 Subject: [PATCH 156/224] Fixed uniform scale on editor widgets --- resources/Schema/Entities/EditorWidget.xml | 79 ------------------- .../Schema/Entities/EditorWidgetRotate.xml | 3 + .../Schema/Entities/EditorWidgetTranslate.xml | 3 + 3 files changed, 6 insertions(+), 79 deletions(-) delete mode 100755 resources/Schema/Entities/EditorWidget.xml diff --git a/resources/Schema/Entities/EditorWidget.xml b/resources/Schema/Entities/EditorWidget.xml deleted file mode 100755 index e729af02..00000000 --- a/resources/Schema/Entities/EditorWidget.xml +++ /dev/null @@ -1,79 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - Models/TranslationWidgetOrigin.obj - - - - - - - - Models/TranslationWidgetX.obj - - - - - - - - Models/TranslationWidgetY.obj - - - - - - - - Models/TranslationWidgetZ.obj - - - - - - - - Models/WidgetPlaneX.obj - - - - - - - - Models/WidgetPlaneY.obj - - - - - - - - Models/WidgetPlaneZ.obj - - - - - - diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml index 6a5f72ea..b918794e 100644 --- a/resources/Schema/Entities/EditorWidgetRotate.xml +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -3,6 +3,9 @@ + + + diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml index 75d96a51..a9b7eaff 100644 --- a/resources/Schema/Entities/EditorWidgetTranslate.xml +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -6,6 +6,9 @@ Models/TranslationWidgetOrigin.obj + + + From 254caf9e5dcc46dc11df9028b3283a84a932c9e9 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Thu, 21 Jan 2016 16:49:20 +0100 Subject: [PATCH 157/224] Picking depthbuffer fix --- src/Engine/Rendering/DrawFinalPass.cpp | 4 ++++ src/Engine/Rendering/PickingPass.cpp | 4 +++- src/Engine/Rendering/Renderer.cpp | 4 +--- 3 files changed, 8 insertions(+), 4 deletions(-) diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 45dafa71..eeaa7bb3 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -31,6 +31,10 @@ void DrawFinalPass::Draw(RenderScene& scene) m_ForwardPlusProgram->Bind(); GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); + if (scene.ClearDepth) { + glClear(GL_DEPTH_BUFFER_BIT); + } + glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 1, m_LightCullingPass->LightSSBO()); glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 2, m_LightCullingPass->LightGridSSBO()); glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 4, m_LightCullingPass->LightIndexSSBO()); diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 6800df1d..3b5ade59 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -53,7 +53,9 @@ void PickingPass::Draw(RenderScene& scene) GLuint ShaderHandle = m_PickingProgram->GetHandle(); m_PickingProgram->Bind(); - + if (scene.ClearDepth) { + glClear(GL_DEPTH_BUFFER_BIT); + } m_Camera = scene.Camera; diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 858fb6dc..c0347612 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -87,9 +87,7 @@ void Renderer::Draw(RenderFrame& frame) m_PickingPass->ClearPicking(); for (auto scene : frame.RenderScenes){ - if (scene->ClearDepth) { - glClear(GL_DEPTH_BUFFER_BIT); - } + SortRenderJobsByDepth(*scene); m_PickingPass->Draw(*scene); m_LightCullingPass->GenerateNewFrustum(*scene); From 75dcdcec414b4f5632f5ade7a091d0754aeacdb4 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 17:00:47 +0100 Subject: [PATCH 158/224] Fixed inconsistent editor input controls. Left mouse = select and move. Right mouse = camera. --- include/Engine/Editor/EditorSystemOld.h | 93 --- include/Engine/Editor/EditorWidgetSystem.h | 4 - .../Rendering/DebugCameraInputController.h | 37 +- src/Engine/Editor/EditorSystemOld.cpp | 736 ------------------ src/Engine/Editor/EditorWidgetSystem.cpp | 15 +- 5 files changed, 26 insertions(+), 859 deletions(-) delete mode 100644 include/Engine/Editor/EditorSystemOld.h delete mode 100644 src/Engine/Editor/EditorSystemOld.cpp diff --git a/include/Engine/Editor/EditorSystemOld.h b/include/Engine/Editor/EditorSystemOld.h deleted file mode 100644 index d49c3542..00000000 --- a/include/Engine/Editor/EditorSystemOld.h +++ /dev/null @@ -1,93 +0,0 @@ -#include -#include -#include -#include -#include "../Core/System.h" -#include "../Core/EMousePress.h" -#include "../Core/EMouseRelease.h" -#include "../Core/EMouseMove.h" -#include "../Core/ConfigFile.h" -#include "../Input/EInputCommand.h" -#include "../Rendering/IRenderer.h" -#include "../Core/Transform.h" -#include "../Core/EFileDropped.h" -#include "../Core/EntityFilePreprocessor.h" -#include "../Core/EntityFileParser.h" -#include "../Core/EntityFileWriter.h" - -class EditorSystemOld : public ImpureSystem -{ -public: - EditorSystemOld(World* world, EventBroker* eventBroker, IRenderer* renderer); - - virtual void Update(double dt) override; - -private: - IRenderer* m_Renderer; - Camera* m_Camera = nullptr; - - bool m_Enabled; - bool m_Visible; - boost::filesystem::path m_DefaultEntityDir; - boost::filesystem::path m_CurrentFile; - std::vector m_PickingQueue; - - enum class WidgetMode - { - None, - Translate, - Rotate, - Scale - } m_WidgetMode = WidgetMode::None; - - enum class WidgetSpace - { - Local, - Global - } m_WidgetSpace = WidgetSpace::Global; - - EntityID m_Widget = EntityID_Invalid; - EntityID m_WidgetX = EntityID_Invalid; - EntityID m_WidgetPlaneX = EntityID_Invalid; - EntityID m_WidgetY = EntityID_Invalid; - EntityID m_WidgetPlaneY = EntityID_Invalid; - EntityID m_WidgetZ = EntityID_Invalid; - EntityID m_WidgetPlaneZ = EntityID_Invalid; - EntityID m_WidgetOrigin = EntityID_Invalid; - glm::vec3 m_WidgetCurrentAxis; - float m_WidgetPickingDepth = 0.f; - glm::vec3 m_WidgetPickingPosition = glm::vec3(0); - - EntityID m_Selection = EntityID_Invalid; - EntityID m_LastSelection = EntityID_Invalid; - EntityID m_UIDraggingEntity = EntityID_Invalid; - glm::vec3 m_Position; - std::string m_LastDroppedFile; - - static boost::filesystem::path openDialog(boost::filesystem::path defaultPath); - static boost::filesystem::path saveDialog(boost::filesystem::path defaultPath); - - EventRelay m_EInputCommand; - bool OnInputCommand(const Events::InputCommand& e); - EventRelay m_EMouseRelease; - bool OnMouseRelease(const Events::MouseRelease& e); - EventRelay m_EMousePress; - bool OnMousePress(const Events::MousePress& e); - EventRelay m_EMouseMove; - bool OnMouseMove(const Events::MouseMove& e); - EventRelay m_EFileDropped; - bool OnFileDropped(const Events::FileDropped& e); - - void Picking(); - void createWidget(); - void updateWidget(); - void setWidgetMode(WidgetMode newMode); - void setWidgetSpace(WidgetSpace space); - void drawUI(World* world, double dt); - bool createDeleteButton(std::string componentType); - bool createEntityNode(World* world, EntityID entity); - void changeParent(EntityID entity, EntityID newParent); - void fileImport(World* world); - void fileSave(World* world); - void fileSaveAs(World* world); -}; \ No newline at end of file diff --git a/include/Engine/Editor/EditorWidgetSystem.h b/include/Engine/Editor/EditorWidgetSystem.h index a2329342..a060bdd5 100644 --- a/include/Engine/Editor/EditorWidgetSystem.h +++ b/include/Engine/Editor/EditorWidgetSystem.h @@ -30,10 +30,6 @@ public: virtual void Update(double dt) override; virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cEditorWidget, double dt) override; - void debugPrintVector(const char* name, glm::vec3 axisNDC); - - void debugPrintVector(const char* name, glm::vec4 axisNDC); - void debugPrintVector(const char* name, glm::vec2 axisNDC); private: IRenderer* m_Renderer; diff --git a/include/Engine/Rendering/DebugCameraInputController.h b/include/Engine/Rendering/DebugCameraInputController.h index 1a43820c..5ce85b3f 100644 --- a/include/Engine/Rendering/DebugCameraInputController.h +++ b/include/Engine/Rendering/DebugCameraInputController.h @@ -3,6 +3,8 @@ #include #include "../Input/FirstPersonInputController.h" +#include "../Core/EMousePress.h" +#include "../Core/EMouseRelease.h" template class DebugCameraInputController : public FirstPersonInputController @@ -10,7 +12,10 @@ class DebugCameraInputController : public FirstPersonInputController 0) { - if (!io.WantCaptureMouse) { - LockMouse(); - } - } else { - UnlockMouse(); - } - return false; - } - if (!io.WantCaptureKeyboard) { if (e.Command == "Right") { float value = std::max(-1.f, std::min(e.Value, 1.f)); @@ -66,6 +60,25 @@ protected: glm::vec3 m_Velocity = glm::vec3(0, 0, 0); float m_BaseSpeed = 2.0f; float m_Speed = m_BaseSpeed; + EventRelay m_EMousePress; + bool OnMousePress(const Events::MousePress& e) + { + if (e.Button == GLFW_MOUSE_BUTTON_2) { + ImGuiIO& io = ImGui::GetIO(); + if (!io.WantCaptureMouse) { + LockMouse(); + } + } + return true; + } + EventRelay m_EMouseRelease; + bool OnMouseRelease(const Events::MouseRelease& e) + { + if (e.Button == GLFW_MOUSE_BUTTON_2) { + UnlockMouse(); + } + return true; + } }; #endif \ No newline at end of file diff --git a/src/Engine/Editor/EditorSystemOld.cpp b/src/Engine/Editor/EditorSystemOld.cpp deleted file mode 100644 index 332bef05..00000000 --- a/src/Engine/Editor/EditorSystemOld.cpp +++ /dev/null @@ -1,736 +0,0 @@ -#include "Editor/EditorSystemOld.h" -#define IMGUI_DEFINE_MATH_OPERATORS -#include - -EditorSystemOld::EditorSystemOld(World* world, EventBroker* eventBroker, IRenderer* renderer) - : System(world, eventBroker) - , ImpureSystem() - , m_Renderer(renderer) -{ - auto config = ResourceManager::Load("Config.ini"); - m_Enabled = config->Get("Debug.EditorEnabled", false); - m_Visible = m_Enabled; - m_DefaultEntityDir = boost::filesystem::path("Schema") / boost::filesystem::path("Entities"); - - if (!m_Enabled) { - return; - } - - EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &EditorSystemOld::OnInputCommand); - EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorSystemOld::OnMousePress); - EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorSystemOld::OnMouseRelease); - EVENT_SUBSCRIBE_MEMBER(m_EMouseMove, &EditorSystemOld::OnMouseMove); - EVENT_SUBSCRIBE_MEMBER(m_EFileDropped, &EditorSystemOld::OnFileDropped); -} - -void EditorSystemOld::Update(double dt) -{ - if (!m_Enabled) { - return; - } - - if (!m_Visible) { - return; - } - Picking(); - updateWidget(); - - drawUI(m_World, dt); - - // Clear drop queue if it wasn't handled by any UI element - if (!m_LastDroppedFile.empty()) { - m_LastDroppedFile = ""; - } -} - - -boost::filesystem::path EditorSystemOld::openDialog(boost::filesystem::path defaultPath) -{ - namespace bfs = boost::filesystem; - auto absolutePath = bfs::absolute(defaultPath); - nfdchar_t* outPath = nullptr; - nfdresult_t result = NFD_OpenDialog(NULL, absolutePath.string().c_str(), &outPath); - if (result == NFD_ERROR) { - LOG_ERROR("NFD Error: %s", NFD_GetError()); - return bfs::path(); - } - - return bfs::absolute(outPath); -} - -boost::filesystem::path EditorSystemOld::saveDialog(boost::filesystem::path defaultPath) -{ - namespace bfs = boost::filesystem; - auto absolutePath = bfs::absolute(defaultPath); - nfdchar_t* outPath = nullptr; - nfdresult_t result = NFD_SaveDialog(NULL, absolutePath.string().c_str(), &outPath); - if (result == NFD_ERROR) { - LOG_ERROR("NFD Error: %s", NFD_GetError()); - return bfs::path(); - } - - return bfs::absolute(outPath); -} - -bool EditorSystemOld::OnInputCommand(const Events::InputCommand& e) -{ - if (e.Command == "ToggleEditor" && e.Value > 0) { - m_Visible = !m_Visible; - } - - if (e.Command == "EditorToolMove" && e.Value > 0) { - setWidgetMode(WidgetMode::Translate); - } - if (e.Command == "EditorToolRotate" && e.Value > 0) { - setWidgetMode(WidgetMode::Rotate); - } - if (e.Command == "EditorToolScale" && e.Value > 0) { - setWidgetMode(WidgetMode::Scale); - } - - if (e.Command == "EditorToggleTransformSpace" && e.Value > 0) { - if (m_WidgetSpace == WidgetSpace::Global) { - setWidgetSpace(WidgetSpace::Local); - } else if (m_WidgetSpace == WidgetSpace::Local) { - setWidgetSpace(WidgetSpace::Global); - } - } - - return true; -} - -bool EditorSystemOld::OnMousePress(const Events::MousePress& e) -{ - if (e.Button == GLFW_MOUSE_BUTTON_RIGHT) { - m_PickingQueue.push_back(glm::vec2((int)e.X, (int)e.Y)); - } - return true; -} - -bool EditorSystemOld::OnMouseMove(const Events::MouseMove& e) -{ - if (m_Widget == EntityID_Invalid) { - return false; - } - if (m_Selection == EntityID_Invalid) { - return false; - } - if (m_Selection == m_Widget) { - return false; - } - // TODO: No widgets for root entity until widgets reside in thier own world, - // or the widgets will move relative to the root entity being moved, which is WEEEIRD. - if (m_Selection == 0) { - return false; - } - if (m_Camera == nullptr) { - return false; - } - - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - glm::vec3 widgetOrientation = widgetTransform["Orientation"]; - glm::quat totalOrientation = m_Camera->Orientation() * glm::inverse(glm::quat(widgetOrientation)); - - int width; - int height; - glfwGetFramebufferSize(m_Renderer->Window(), &width, &height); - Rectangle res(width, height); - - glm::vec2 delta2(res.Width / 2.f + e.DeltaX, res.Height / 2.f + -e.DeltaY); - glm::vec3 deltaWorld = ScreenCoords::ToWorldPos( - delta2, - m_WidgetPickingDepth, - res, - m_Camera->ProjectionMatrix(), - glm::toMat4(glm::inverse(totalOrientation)) - ); - glm::vec3 origin = ScreenCoords::ToWorldPos( - glm::vec2(res.Width / 2.f, res.Height / 2.f), - m_WidgetPickingDepth, - res, - m_Camera->ProjectionMatrix(), - glm::toMat4(glm::inverse(totalOrientation)) - ); - deltaWorld = deltaWorld - origin; - glm::vec3 movement = deltaWorld * m_WidgetCurrentAxis; - - if (glm::length2(m_WidgetCurrentAxis) > 0.f) { - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - if (m_WidgetMode == WidgetMode::Translate) { - if (m_WidgetSpace == WidgetSpace::Global) { - EntityID parent = m_World->GetParent(m_Selection); - glm::quat inverseParentOrientation; - //if (parent != 0) { - inverseParentOrientation = glm::inverse(Transform::AbsoluteOrientation(m_World, parent)); - //} - (glm::vec3&)m_World->GetComponent(m_Selection, "Transform")["Position"] += inverseParentOrientation * movement; - } else if (m_WidgetSpace == WidgetSpace::Local) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - (glm::vec3&)selectionTransform["Position"] += glm::quat((glm::vec3)selectionTransform["Orientation"]) * movement; - } - } else if (m_WidgetMode == WidgetMode::Rotate) { - glm::vec3 finalMovement; - finalMovement.x = -deltaWorld.y * m_WidgetCurrentAxis.x; - finalMovement.y = deltaWorld.x * m_WidgetCurrentAxis.y; - finalMovement.z = deltaWorld.y * m_WidgetCurrentAxis.z; - if (m_WidgetSpace == WidgetSpace::Global) { - EntityID parent = m_World->GetParent(m_Selection); - glm::quat parentOrientation; - //if (parent != 0) { - // parentOrientation = RenderSystem::AbsoluteOrientation(m_World, parent); - //} - glm::vec3& selectionOrientation = m_World->GetComponent(m_Selection, "Transform")["Orientation"]; - glm::quat currentOrientation = Transform::AbsoluteOrientation(m_World, m_Selection); - //glm::quat currentOrientation = parentOrientation * glm::quat(selectionOrientation); - glm::quat deltaOrientation(finalMovement); - selectionOrientation = glm::eulerAngles(glm::inverse(parentOrientation) * (deltaOrientation * currentOrientation)); - } else if (m_WidgetSpace == WidgetSpace::Local) { - glm::vec3& selectionOrientation = m_World->GetComponent(m_Selection, "Transform")["Orientation"]; - glm::quat currentOrientation(selectionOrientation); - glm::quat deltaOrientation(finalMovement); - selectionOrientation = glm::eulerAngles(currentOrientation * deltaOrientation); - } - } else if (m_WidgetMode == WidgetMode::Scale) { - glm::vec3& scaleX = m_World->GetComponent(m_WidgetX, "Transform")["Scale"]; - glm::vec3& scaleY = m_World->GetComponent(m_WidgetY, "Transform")["Scale"]; - glm::vec3& scaleZ = m_World->GetComponent(m_WidgetZ, "Transform")["Scale"]; - - if (m_WidgetCurrentAxis.x > 0 && m_WidgetCurrentAxis.y > 0 && m_WidgetCurrentAxis.z > 0) { - float movementLength = glm::length(movement); - float dot = glm::dot((glm::vec3)widgetOrientation, movement); - movement = glm::vec3(movementLength) * glm::sign(dot); - (glm::vec3&)m_World->GetComponent(m_WidgetOrigin, "Transform")["Scale"] += movement; - } - if (m_WidgetCurrentAxis.x > 0) { - scaleX.x += movement.x; - } - if (m_WidgetCurrentAxis.y > 0) { - scaleY.y += movement.y; - } - if (m_WidgetCurrentAxis.z > 0) { - scaleZ.z += movement.z; - } - (glm::vec3&)m_World->GetComponent(m_Selection, "Transform")["Scale"] += movement; - } - } - - - /*LOG_DEBUG("DELTA %f", e.DeltaX); - if (e.X < 0) { - glfwSetCursorPos(m_Renderer->Window(), width - 1, e.Y); - } - if (e.X >= width) { - glfwSetCursorPos(m_Renderer->Window(), 0, e.Y); - }*/ - - return true; -} - -bool EditorSystemOld::OnMouseRelease(const Events::MouseRelease& e) -{ - if (glm::length2(m_WidgetCurrentAxis) > 0.f) { - m_WidgetCurrentAxis = glm::vec3(0.f); - //setWidgetMode(m_WidgetMode); - } - - return true; -} - -void EditorSystemOld::Picking() -{ - for (auto& pos : m_PickingQueue) { - auto result = m_Renderer->Pick(pos); - EntityID entity = result.Entity; - if (glm::length2(m_WidgetCurrentAxis) > 0.f) { - // ??? - } else { - LOG_INFO("Selected %i", entity); - if (entity != EntityID_Invalid) { - EntityID parent = m_World->GetParent(entity); - m_Camera = result.Camera; - if (parent == m_Widget) { - m_WidgetCurrentAxis = glm::vec3( - (entity == m_WidgetX) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneY || entity == m_WidgetPlaneZ), - (entity == m_WidgetY) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneX || entity == m_WidgetPlaneZ), - (entity == m_WidgetZ) || (entity == m_WidgetOrigin) || (entity == m_WidgetPlaneX || entity == m_WidgetPlaneY) - ); - m_WidgetPickingDepth = result.Depth; - //auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - //auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - //widgetTransform["Position"] = (glm::vec3)selectionTransform["Position"]; - } else { - ImGui::SetActiveID(0, nullptr); - if (m_WidgetMode == WidgetMode::None) { - m_WidgetMode = WidgetMode::Translate; - } - setWidgetMode(m_WidgetMode); - m_Selection = entity; - } - } - } - } - m_PickingQueue.clear(); -}; - -bool EditorSystemOld::OnFileDropped(const Events::FileDropped& e) -{ - m_LastDroppedFile = boost::filesystem::path(e.Path).lexically_relative(boost::filesystem::current_path()).string(); - std::replace(m_LastDroppedFile.begin(), m_LastDroppedFile.end(), '\\', '/'); - return true; -} - -void EditorSystemOld::createWidget() -{ - if (m_Widget == EntityID_Invalid) { - m_Widget = m_World->CreateEntity(); - m_World->AttachComponent(m_Widget, "Transform"); - m_WidgetX = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetX, "Transform"); - m_World->AttachComponent(m_WidgetX, "Model"); - m_WidgetPlaneX = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetPlaneX, "Transform"); - m_World->AttachComponent(m_WidgetPlaneX, "Model"); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/WidgetPlaneX.obj"; - m_WidgetY = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetY, "Transform"); - m_World->AttachComponent(m_WidgetY, "Model"); - m_WidgetPlaneY = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetPlaneY, "Transform"); - m_World->AttachComponent(m_WidgetPlaneY, "Model"); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/WidgetPlaneY.obj"; - m_WidgetZ = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetZ, "Transform"); - m_World->AttachComponent(m_WidgetZ, "Model"); - m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); - m_World->AttachComponent(m_WidgetPlaneZ, "Model"); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; - m_WidgetOrigin = m_World->CreateEntity(m_Widget); - m_World->AttachComponent(m_WidgetOrigin, "Transform"); - m_World->AttachComponent(m_WidgetOrigin, "Model"); - setWidgetMode(WidgetMode::None); - } -} - -void EditorSystemOld::updateWidget() -{ - if (m_Widget == EntityID_Invalid) { - return; - } - if (m_Selection == m_Widget) { - return; - } - - if (m_Selection != EntityID_Invalid) { - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - glm::vec3 selectionPosition = Transform::AbsolutePosition(m_World, m_Selection); - widgetTransform["Position"] = selectionPosition; - if (m_WidgetSpace == WidgetSpace::Local) { - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } -} - -void EditorSystemOld::setWidgetMode(WidgetMode newMode) -{ - if (m_Widget == EntityID_Invalid) { - return; - } - - auto widgetTransform = m_World->GetComponent(m_Widget, "Transform"); - widgetTransform["Orientation"] = glm::vec3(0.f); - m_World->GetComponent(m_WidgetX, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = false; - m_World->GetComponent(m_WidgetY, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetPlaneY, "Model")["Visible"] = false; - m_World->GetComponent(m_WidgetZ, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Visible"] = false; - m_World->GetComponent(m_WidgetOrigin, "Transform")["Scale"] = glm::vec3(1.f); - m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = false; - - if (newMode == WidgetMode::Translate) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.obj"; - // Temporarily disabled for local space until I can figure out what's wrong with the math - if (m_WidgetSpace != WidgetSpace::Local) { - m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = true; - m_World->GetComponent(m_WidgetPlaneY, "Model")["Visible"] = true; - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Visible"] = true; - } - if (m_Selection != EntityID_Invalid) { - if (m_WidgetSpace == WidgetSpace::Local) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } - } else if (newMode == WidgetMode::Scale) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.obj"; - m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = true; - m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; - if (m_Selection != EntityID_Invalid) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } else if (newMode == WidgetMode::Rotate) { - m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; - m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.obj"; - m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.obj"; - if (m_Selection != EntityID_Invalid) { - auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); - if (m_WidgetSpace == WidgetSpace::Local) { - widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); - } - } - } - m_WidgetMode = newMode; -} - -void EditorSystemOld::setWidgetSpace(WidgetSpace space) -{ - m_WidgetSpace = space; - setWidgetMode(m_WidgetMode); -} - -void EditorSystemOld::drawUI(World* world, double dt) -{ - namespace bfs = boost::filesystem; - - ImGui::ShowTestWindow(); - //ImGui::ShowStyleEditor(); - - if (ImGui::BeginMainMenuBar()) { - if (ImGui::BeginMenu("File")) { - //if (ImGui::MenuItem("New")) { } - if (ImGui::MenuItem("Import", "Ctrl+O")) { - fileImport(world); - } - if (ImGui::MenuItem("Save", "Ctrl+S")) { - fileSave(world); - } - if (ImGui::MenuItem("Save As...", "Ctrl+Shift+S")) { - fileSaveAs(world); - } - ImGui::Separator(); - if (ImGui::MenuItem("Close Editor", "F1")) { } - - ImGui::EndMenu(); - } - - ImGui::SameLine(); - if (ImGui::Button("Move")) { - setWidgetMode(WidgetMode::Translate); - } - ImGui::SameLine(); - if (ImGui::Button("Rotate")) { - setWidgetMode(WidgetMode::Rotate); - } - ImGui::SameLine(); - if (ImGui::Button("Scale")) { - setWidgetMode(WidgetMode::Scale); - } - ImGui::SameLine(); - if (m_WidgetSpace == WidgetSpace::Global) { - if (ImGui::Button("(Global)")) { - setWidgetSpace(WidgetSpace::Local); - } - } else if (m_WidgetSpace == WidgetSpace::Local) { - if (ImGui::Button("(Local)")) { - setWidgetSpace(WidgetSpace::Global); - } - } - - ImGui::EndMainMenuBar(); - } - - std::string title = std::string("Components #") + std::to_string(m_Selection) + std::string("###Components"); - if (ImGui::Begin(title.c_str())) { - if (m_Selection != EntityID_Invalid) { - auto& pools = world->GetComponentPools(); - - std::vector componentTypes; - for (auto& pair : pools) { - // Only add components the entity doesn't already have - if (!pair.second->KnowsEntity(m_Selection)) { - componentTypes.push_back(pair.first.c_str()); - } - } - int item = -1; - ImGui::PushItemWidth(ImGui::GetWindowContentRegionWidth() - 5.f); - if (ImGui::Combo("", &item, componentTypes.data(), componentTypes.size())) { - if (item != -1) { - std::string chosenType = std::string(componentTypes.at(item)); - world->AttachComponent(m_Selection, chosenType); - } - } - ImGui::PopItemWidth(); - - for (auto& pair : pools) { - const std::string& componentType = pair.first; - auto pool = pair.second; - if (!pool->KnowsEntity(m_Selection)) { - continue; - } - auto& ci = pool->ComponentInfo(); - - bool deletePressed = createDeleteButton(componentType); - if (deletePressed) { - world->DeleteComponent(m_Selection, componentType); - continue; - } - - if (ImGui::CollapsingHeader(componentType.c_str())) { - if (!ci.Meta->Annotation.empty()) { - ImGui::Text(ci.Meta->Annotation.c_str()); - } - - auto& component = world->GetComponent(m_Selection, componentType); - for (auto& kv : ci.Fields) { - const std::string& fieldName = kv.first; - auto& field = kv.second; - - std::string uniqueID = componentType + fieldName; - ImGui::PushID(uniqueID.c_str()); - if (field.Type == "Vector") { - auto& val = component.Field(fieldName); - if (fieldName == "Scale") { - ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, 0.f, std::numeric_limits::max()); - } else if (fieldName == "Orientation") { - glm::vec3 tempVal = glm::fmod(val, glm::vec3(glm::two_pi())); - if (ImGui::SliderFloat3("", glm::value_ptr(tempVal), 0.f, glm::two_pi())) { - val = tempVal; - } - } else { - ImGui::DragFloat3("", glm::value_ptr(val), 0.1f, std::numeric_limits::lowest(), std::numeric_limits::max()); - } - } else if (field.Type == "Color") { - auto& val = component.Field(fieldName); - ImGui::ColorEdit4("", glm::value_ptr(val), true); - } else if (field.Type == "string") { - std::string& val = component.Field(fieldName); - char tempString[1024]; - memcpy(tempString, val.c_str(), std::min(val.length() + 1, sizeof(tempString))); - if (ImGui::InputText("", tempString, sizeof(tempString))) { - val = std::string(tempString); - LOG_DEBUG("%s::%s changed!", componentType.c_str(), fieldName.c_str()); - } - // DROP STUFF - if (ImGui::IsItemHovered() && !m_LastDroppedFile.empty()) { - val = m_LastDroppedFile; - m_LastDroppedFile = ""; - } - - } else if (field.Type == "double") { - float tempVal = static_cast(component.Field(fieldName)); - if (ImGui::InputFloat("", &tempVal, 0.01f, 1.f)) { - component.SetField(fieldName, static_cast(tempVal)); - } - } else if (field.Type == "int") { - int val = component.Field(fieldName); - ImGui::InputInt("", &val); - } else if (field.Type == "enum") { - int currentValue = component.Field(fieldName); - int item = -1; - std::stringstream enumKeys; - std::vector enumValues; - int i = 0; - for (auto& kv : ci.Meta->FieldEnumDefinitions.at(fieldName)) { - enumKeys << kv.first << " (" << kv.second << ")" << '\0'; - enumValues.push_back(kv.second); - if (currentValue == kv.second) { - item = i; - } - i++; - } - if (ImGui::Combo("", &item, enumKeys.str().c_str())) { - component.SetField(fieldName, enumValues.at(item)); - } - } else if (field.Type == "bool") { - auto& val = component.Field(fieldName); - ImGui::Checkbox("", &val); - } else { - ImGui::TextDisabled(field.Type.c_str()); - } - ImGui::PopID(); - - ImGui::SameLine(); - ImGui::Text(fieldName.c_str()); - if (ImGui::IsItemHovered()) { - ImGui::SetTooltip("field annotation goes here"); - } - } - } - } - } - - } - ImGui::End(); - - if (ImGui::Begin("Entities")) { - auto entityChildren = world->GetEntityChildren(); - std::function recurse = [&](EntityID parent) { - auto range = entityChildren.equal_range(parent); - for (auto it = range.first; it != range.second; it++) { - if (createEntityNode(world, it->second)) { - recurse(it->second); - ImGui::TreePop(); - } - } - }; - recurse(EntityID_Invalid); - } - ImGui::End(); -} - -bool EditorSystemOld::createEntityNode(World* world, EntityID entity) -{ - // HACK: Don't show the widget entities in the entity tree - if (entity == m_Widget) { - return false; - } - - ImVec2 pos = ImGui::GetCursorScreenPos(); - float width = ImGui::GetContentRegionAvailWidth(); - ImRect bb(pos + ImVec2(20, 0), pos + ImVec2(width, 13)); - auto window = ImGui::GetCurrentWindow(); - if (m_Selection == entity) { - const ImU32 col = window->Color(ImGuiCol_HeaderActive); - window->DrawList->AddRectFilled(bb.Min, bb.Max, col); - } - ImGuiID id = window->GetID((std::string("#SelectButton") + std::to_string(entity)).c_str()); - bool hovered = false; - bool held = false; - if (ImGui::ButtonBehavior(bb, id, &hovered, &held)) { - m_Selection = entity; - } - if (held) { - ImVec2 entityDragDelta = ImGui::GetMouseDragDelta(0); - if (std::abs(entityDragDelta.x) > 0 && std::abs(entityDragDelta.y) > 0) { - if (m_UIDraggingEntity == EntityID_Invalid) { - m_UIDraggingEntity = entity; - LOG_DEBUG("Started drag of entity %i", m_UIDraggingEntity); - } - ImGui::SetNextWindowPos(ImGui::GetIO().MousePos + ImVec2(20, 0)); - ImGui::Begin("Change parent", nullptr, ImVec2(0, 0), 0.3f, ImGuiWindowFlags_NoTitleBar|ImGuiWindowFlags_NoResize|ImGuiWindowFlags_NoMove|ImGuiWindowFlags_NoSavedSettings); - ImGui::Text("#%i", m_UIDraggingEntity); - ImGui::End(); - } - } - - ImGui::SetNextTreeNodeOpened(true, ImGuiSetCond_Once); - std::string nodeTitle; - const std::string& entityName = world->GetName(entity); - if (!entityName.empty()) { - nodeTitle = entityName; - } else { - nodeTitle = std::string("#") + std::to_string(entity); - } - if (ImGui::TreeNode(nodeTitle.c_str())) { - if (m_UIDraggingEntity != EntityID_Invalid && ImGui::IsItemHoveredRect() && ImGui::IsMouseReleased(0)) { - LOG_DEBUG("Changed parent of %i to %i", m_UIDraggingEntity, entity); - changeParent(m_UIDraggingEntity, entity); - m_UIDraggingEntity = EntityID_Invalid; - } - - if (ImGui::BeginPopupContextItem("item context menu")) { - if (ImGui::Button("Add")) { - EntityID newEntity = world->CreateEntity(entity); - world->AttachComponent(newEntity, "Transform"); - } - ImGui::SameLine(); - if (ImGui::Button("Delete")) { - world->DeleteEntity(entity); - ImGui::CloseCurrentPopup(); - if (!world->ValidEntity(m_Selection)) { - m_Selection = EntityID_Invalid; - } - } - ImGui::EndPopup(); - } - return true; - } else { - return false; - } -} - -bool EditorSystemOld::createDeleteButton(std::string componentType) -{ - float width = ImGui::GetContentRegionAvailWidth(); - ImGuiWindow* window = ImGui::GetCurrentWindow(); - auto pos = ImGui::GetCursorScreenPos() + ImVec2(width - 14.f, 1); - ImRect bb = ImRect(pos, pos + ImVec2(14.f, 14.f)); - std::string idString = "#DELETE"; - idString += componentType; - ImGuiID id = window->GetID(idString.c_str()); - bool hovered; - bool held; - bool pressed = ImGui::ButtonBehavior(bb, id, &hovered, &held); - //ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_CloseButtonHovered : ImGuiCol_CloseButton); - ImU32 col = window->Color((held && hovered) ? ImGuiCol_CloseButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - window->DrawList->AddCircleFilled(bb.GetCenter(), 7.f, col, 16); - return pressed; -} - -void EditorSystemOld::changeParent(EntityID entity, EntityID newParent) -{ - if (entity == newParent) { - return; - } - - // An entity can't be a child to one of its own children - auto children = m_World->GetEntityChildren().equal_range(entity); - for (auto it = children.first; it != children.second; it++) { - if (it->second == newParent) { - return; - } - } - - m_World->SetParent(entity, newParent); -} - -void EditorSystemOld::fileImport(World* world) -{ - m_CurrentFile = openDialog(m_DefaultEntityDir); - auto file = ResourceManager::Load(m_CurrentFile.string()); - EntityFilePreprocessor fpp(file); - fpp.RegisterComponents(world); - EntityFileParser fp(file); - fp.MergeEntities(world); - createWidget(); - updateWidget(); -} - -void EditorSystemOld::fileSave(World* world) -{ - if (boost::filesystem::exists(m_CurrentFile)) { - // HACK: Delete the widgets so they don't appear in the saved file - world->DeleteEntity(m_Widget); - m_Widget = EntityID_Invalid; - - EntityFileWriter writer(m_CurrentFile.string()); - writer.WriteWorld(world); - - createWidget(); - } else { - fileSaveAs(world); - } -} - -void EditorSystemOld::fileSaveAs(World* world) -{ - auto filePath = saveDialog(m_DefaultEntityDir); - if (filePath.empty()) { - return; - } - - // HACK: Delete the widgets so they don't appear in the saved file - world->DeleteEntity(m_Widget); - m_Widget = EntityID_Invalid; - - EntityFileWriter writer(filePath.string()); - writer.WriteWorld(world); - - createWidget(); -} diff --git a/src/Engine/Editor/EditorWidgetSystem.cpp b/src/Engine/Editor/EditorWidgetSystem.cpp index 1417f20e..f0c72ab0 100644 --- a/src/Engine/Editor/EditorWidgetSystem.cpp +++ b/src/Engine/Editor/EditorWidgetSystem.cpp @@ -50,19 +50,6 @@ void EditorWidgetSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper m_MouseDelta = glm::vec2(0); } -void EditorWidgetSystem::debugPrintVector(const char* name, glm::vec2 axisNDC) -{ - ImGui::Text("%s: (%f, %f)", name, axisNDC.x, axisNDC.y); -} -void EditorWidgetSystem::debugPrintVector(const char* name, glm::vec4 axisNDC) -{ - ImGui::Text("%s: (%f, %f, %f, %f)", name, axisNDC.x, axisNDC.y, axisNDC.z, axisNDC.w); -} -void EditorWidgetSystem::debugPrintVector(const char* name, glm::vec3 axisNDC) -{ - ImGui::Text("%s: (%f, %f, %f)", name, axisNDC.x, axisNDC.y, axisNDC.z); -} - bool EditorWidgetSystem::OnMouseMove(const Events::MouseMove& e) { m_MouseDelta = glm::vec2((float)e.DeltaX, (float)-e.DeltaY); @@ -71,7 +58,7 @@ bool EditorWidgetSystem::OnMouseMove(const Events::MouseMove& e) bool EditorWidgetSystem::OnMousePress(const Events::MousePress & e) { - if (e.Button == GLFW_MOUSE_BUTTON_2) { + if (e.Button == GLFW_MOUSE_BUTTON_1) { m_PickData = m_Renderer->Pick(glm::vec2(e.X, e.Y)); if (m_PickData.Entity != EntityID_Invalid && m_PickData.World == m_World) { m_PickEntity = EntityWrapper(m_World, m_PickData.Entity); From deb6ff1b16cb5895941e2b3f33d2100555ca0b5b Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Thu, 21 Jan 2016 17:36:47 +0100 Subject: [PATCH 159/224] Changed some files so it works with the changes in master. (weaponsystem,capturepoint,some tests) --- include/Game/Systems/WeaponSystem.h | 4 ++-- src/Game/Systems/WeaponSystem.cpp | 8 ++++---- src/Tests/CapturePointTest.cpp | 4 ++-- src/Tests/HealthSystemTest.cpp | 2 +- src/Tests/OctTreeTest.cpp | 3 +-- 5 files changed, 10 insertions(+), 11 deletions(-) diff --git a/include/Game/Systems/WeaponSystem.h b/include/Game/Systems/WeaponSystem.h index b85ba323..5acf72b3 100644 --- a/include/Game/Systems/WeaponSystem.h +++ b/include/Game/Systems/WeaponSystem.h @@ -18,9 +18,9 @@ class WeaponSystem : public ImpureSystem { public: - WeaponSystem(EventBroker* eventBroker, IRenderer* renderer); + WeaponSystem(World* world, EventBroker* eventBroker, IRenderer* renderer); - virtual void Update(World* world, double dt) override; + virtual void Update(double dt) override; private: //methods which will take care of specific events diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp index ec81b08b..11f76490 100644 --- a/src/Game/Systems/WeaponSystem.cpp +++ b/src/Game/Systems/WeaponSystem.cpp @@ -1,7 +1,7 @@ #include "Systems/WeaponSystem.h" -WeaponSystem::WeaponSystem(EventBroker* eventBroker, IRenderer* renderer) - : System(eventBroker) +WeaponSystem::WeaponSystem(World* world, EventBroker* eventBroker, IRenderer* renderer) + : System(world, eventBroker) , ImpureSystem() , m_Renderer(renderer) { @@ -9,7 +9,7 @@ WeaponSystem::WeaponSystem(EventBroker* eventBroker, IRenderer* renderer) EVENT_SUBSCRIBE_MEMBER(m_EShoot, &WeaponSystem::OnShoot); } -void WeaponSystem::Update(World* world, double dt) +void WeaponSystem::Update(double dt) { for (int i = m_EShootVector.size(); i > 0; i--) { @@ -22,7 +22,7 @@ void WeaponSystem::Update(World* world, double dt) continue; } //if its a player, do PlayerDamage event - const bool hasPlayerComponent = world->HasComponent(pickDataFromShot.Entity, "Player"); + const bool hasPlayerComponent = m_World->HasComponent(pickDataFromShot.Entity, "Player"); if (hasPlayerComponent) { Events::PlayerDamage ePlayerDamage; //TODO: damage based on weapontype/class? diff --git a/src/Tests/CapturePointTest.cpp b/src/Tests/CapturePointTest.cpp index 5a041120..ffb01030 100644 --- a/src/Tests/CapturePointTest.cpp +++ b/src/Tests/CapturePointTest.cpp @@ -94,7 +94,7 @@ CapturePointTest::CapturePointTest(int runTestNumber) m_World = new World(); // Create system pipeline - m_SystemPipeline = new SystemPipeline(m_EventBroker); + m_SystemPipeline = new SystemPipeline(m_World,m_EventBroker); m_SystemPipeline->AddSystem(0); m_SystemPipeline->AddSystem(1); @@ -405,7 +405,7 @@ void CapturePointTest::Tick() double dt = 10.0; // Iterate through systems and update world! - m_SystemPipeline->Update(m_World, dt); + m_SystemPipeline->Update(dt); m_EventBroker->Swap(); m_EventBroker->Clear(); diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index dd26793b..b28a14ba 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -48,7 +48,7 @@ GameHealthSystemTest::GameHealthSystemTest() fp.MergeEntities(m_World); // Create system pipeline - m_SystemPipeline = new SystemPipeline(m_EventBroker); + m_SystemPipeline = new SystemPipeline(m_World,m_EventBroker); m_SystemPipeline->AddSystem(0); //The Test diff --git a/src/Tests/OctTreeTest.cpp b/src/Tests/OctTreeTest.cpp index edd686f8..d0f25c4c 100644 --- a/src/Tests/OctTreeTest.cpp +++ b/src/Tests/OctTreeTest.cpp @@ -52,8 +52,7 @@ void RegionTestOld(Tree& tree) template void RegionTest(Tree& tree) { - AABB aabb; - aabb.CreateFromCenter(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), + AABB aabb = AABB::FromOriginSize(glm::vec3(rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS, rand() % LEVEL_BOUNDS), glm::vec3(rand() % MAXSIZE, rand() % MAXSIZE, rand() % MAXSIZE)); std::vector outVec; tree.ObjectsInSameRegion(aabb, outVec); From 8cf83454d731ac33d09955ebf85e58aabb939a07 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Thu, 21 Jan 2016 17:45:20 +0100 Subject: [PATCH 160/224] Fixed input going through editor UI --- include/Engine/Editor/EditorSystem.h | 6 +++--- src/Engine/Editor/EditorSystem.cpp | 7 ++++--- src/Engine/Editor/EditorWidgetSystem.cpp | 3 ++- 3 files changed, 9 insertions(+), 7 deletions(-) diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index befa46b6..b354ddf3 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -9,7 +9,7 @@ #include "../Core/EntityFilePreprocessor.h" #include "../Core/EntityFileParser.h" #include "../Core/EntityFileWriter.h" -#include "../Core/EMouseRelease.h" +#include "../Core/EMousePress.h" #include "EditorGUI.h" #include "EditorStats.h" @@ -52,8 +52,8 @@ private: void OnComponentDelete(EntityWrapper entity, const std::string& componentType); // Events - EventRelay m_EMouseRelease; - bool OnMouseRelease(const Events::MouseRelease& e); + EventRelay m_EMousePress; + bool OnMousePress(const Events::MousePress& e); EventRelay m_EWidgetDelta; bool OnWidgetDelta(const Events::WidgetDelta& e); }; \ No newline at end of file diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 1ef8b02b..35b8a361 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -31,7 +31,7 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorGUI->SetComponentDeleteCallback(std::bind(&EditorSystem::OnComponentDelete, this, std::placeholders::_1, std::placeholders::_2)); m_EditorGUI->SetWidgetModeCallback(std::bind(&EditorSystem::setWidgetMode, this, std::placeholders::_1)); - EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorSystem::OnMouseRelease); + EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorSystem::OnMousePress); EVENT_SUBSCRIBE_MEMBER(m_EWidgetDelta, &EditorSystem::OnWidgetDelta); m_EditorStats = new EditorStats(); @@ -121,9 +121,10 @@ void EditorSystem::OnComponentDelete(EntityWrapper entity, const std::string& co } } -bool EditorSystem::OnMouseRelease(const Events::MouseRelease& e) +bool EditorSystem::OnMousePress(const Events::MousePress& e) { - if (e.Button == GLFW_MOUSE_BUTTON_1) { + ImGuiIO& io = ImGui::GetIO(); + if (!io.WantCaptureMouse && !io.WantCaptureKeyboard && e.Button == GLFW_MOUSE_BUTTON_1) { PickData pick = m_Renderer->Pick(glm::vec2(e.X, e.Y)); if (pick.World == m_World) { m_CurrentSelection = EntityWrapper(m_World, pick.Entity); diff --git a/src/Engine/Editor/EditorWidgetSystem.cpp b/src/Engine/Editor/EditorWidgetSystem.cpp index f0c72ab0..479671e2 100644 --- a/src/Engine/Editor/EditorWidgetSystem.cpp +++ b/src/Engine/Editor/EditorWidgetSystem.cpp @@ -58,7 +58,8 @@ bool EditorWidgetSystem::OnMouseMove(const Events::MouseMove& e) bool EditorWidgetSystem::OnMousePress(const Events::MousePress & e) { - if (e.Button == GLFW_MOUSE_BUTTON_1) { + ImGuiIO& io = ImGui::GetIO(); + if (!io.WantCaptureMouse && !io.WantCaptureKeyboard && e.Button == GLFW_MOUSE_BUTTON_1) { m_PickData = m_Renderer->Pick(glm::vec2(e.X, e.Y)); if (m_PickData.Entity != EntityID_Invalid && m_PickData.World == m_World) { m_PickEntity = EntityWrapper(m_World, m_PickData.Entity); From 6f739e22f3fe74d45d8ef7d3f893edab80fa8282 Mon Sep 17 00:00:00 2001 From: verysecrethero Date: Fri, 22 Jan 2016 10:10:39 +0100 Subject: [PATCH 161/224] Crash fix for: if you delete a team component in editor. --- src/Game/Systems/CapturePointSystem.cpp | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/Game/Systems/CapturePointSystem.cpp b/src/Game/Systems/CapturePointSystem.cpp index 67c2353c..fbd20e38 100644 --- a/src/Game/Systems/CapturePointSystem.cpp +++ b/src/Game/Systems/CapturePointSystem.cpp @@ -66,6 +66,9 @@ void CapturePointSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper nextPossibleCapturePoint["Blue"] = -1; for (size_t i = 0; i < m_NumberOfCapturePoints; i++) { + if (!m_World->HasComponent(m_CapturePointNumberToEntityIDMap[i], "Team")) { + continue; + } ComponentWrapper& capturePointOwnedBy = m_World->GetComponent(m_CapturePointNumberToEntityIDMap[i], "Team"); if ((int)capturePointOwnedBy["Team"] == redTeam && m_RedTeamHomeCapturePoint == 0) { nextPossibleCapturePoint["Red"] = i + 1; @@ -76,6 +79,9 @@ void CapturePointSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper } for (int i = m_NumberOfCapturePoints - 1; i >= 0; i--) { + if (!m_World->HasComponent(m_CapturePointNumberToEntityIDMap[i], "Team")) { + continue; + } ComponentWrapper& capturePointOwnedBy = m_World->GetComponent(m_CapturePointNumberToEntityIDMap[i], "Team"); if ((int)capturePointOwnedBy["Team"] == redTeam && m_RedTeamHomeCapturePoint != 0) { nextPossibleCapturePoint["Red"] = i - 1; From 1e3fc1ae2d276838c19fafc1780163b83343d429 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Fri, 22 Jan 2016 10:16:35 +0100 Subject: [PATCH 162/224] Created EPlayerSpawned that gets published when a player spawns --- include/Game/Events/EPlayerSpawned.h | 19 +++++++++++++++++++ include/Game/Systems/PlayerSpawnSystem.h | 9 ++++++++- src/Game/Systems/PlayerSpawnSystem.cpp | 18 ++++++++++++++---- 3 files changed, 41 insertions(+), 5 deletions(-) create mode 100644 include/Game/Events/EPlayerSpawned.h diff --git a/include/Game/Events/EPlayerSpawned.h b/include/Game/Events/EPlayerSpawned.h new file mode 100644 index 00000000..a5700ed3 --- /dev/null +++ b/include/Game/Events/EPlayerSpawned.h @@ -0,0 +1,19 @@ +#ifndef EPlayerSpawned_h__ +#define EPlayerSpawned_h__ + +#include "Core/Event.h" +#include "Core/EntityWrapper.h" + +namespace Events +{ + +struct PlayerSpawned : Event +{ + int PlayerID; + EntityWrapper Player; + EntityWrapper Spawner; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Game/Systems/PlayerSpawnSystem.h b/include/Game/Systems/PlayerSpawnSystem.h index 8ade03a6..69014f65 100644 --- a/include/Game/Systems/PlayerSpawnSystem.h +++ b/include/Game/Systems/PlayerSpawnSystem.h @@ -2,6 +2,7 @@ #include "Input/EInputCommand.h" #include "Systems/SpawnerSystem.h" #include "Events/ESpawnerSpawn.h" +#include "Events/EPlayerSpawned.h" class PlayerSpawnSystem : public ImpureSystem { @@ -11,8 +12,14 @@ public: virtual void Update(double dt) override; private: + struct SpawnRequest + { + int PlayerID; + ComponentInfo::EnumType Team; + }; + EventRelay m_OnInputCommand; bool OnInputCommand(const Events::InputCommand& e); - std::vector m_SpawnRequests; + std::vector m_SpawnRequests; }; \ No newline at end of file diff --git a/src/Game/Systems/PlayerSpawnSystem.cpp b/src/Game/Systems/PlayerSpawnSystem.cpp index 4224d46c..11be0486 100644 --- a/src/Game/Systems/PlayerSpawnSystem.cpp +++ b/src/Game/Systems/PlayerSpawnSystem.cpp @@ -13,7 +13,7 @@ void PlayerSpawnSystem::Update(double dt) return; } - for (auto& team : m_SpawnRequests) { + for (auto& req : m_SpawnRequests) { for (auto& cPlayerSpawn : *playerSpawns) { EntityWrapper spawner(m_World, cPlayerSpawn.EntityID); if (!spawner.HasComponent("Spawner")) { @@ -22,7 +22,7 @@ void PlayerSpawnSystem::Update(double dt) // If the spawner has a team affiliation, check it if (spawner.HasComponent("Team")) { - if ((int)spawner["Team"]["Team"] != team) { + if ((int)spawner["Team"]["Team"] != req.Team) { continue; } } @@ -30,7 +30,14 @@ void PlayerSpawnSystem::Update(double dt) // Spawn the player! EntityWrapper player = SpawnerSystem::Spawn(spawner); // Set the player team affiliation - player["Team"]["Team"] = team; + player["Team"]["Team"] = req.Team; + + // Publish a PlayerSpawned event + Events::PlayerSpawned e; + e.PlayerID = req.PlayerID; + e.Player = player; + e.Spawner = spawner; + m_EventBroker->Publish(e); } } m_SpawnRequests.clear(); @@ -43,7 +50,10 @@ bool PlayerSpawnSystem::OnInputCommand(const Events::InputCommand& e) } if (e.Value != 0) { - m_SpawnRequests.push_back((int)e.Value); + SpawnRequest req; + req.PlayerID = e.PlayerID; + req.Team = (ComponentInfo::EnumType)e.Value; + m_SpawnRequests.push_back(req); } return true; From 6cd073c3c8bee442df6a4b6e273d77a2d7f7f43e Mon Sep 17 00:00:00 2001 From: Jocke Date: Fri, 22 Jan 2016 10:32:54 +0100 Subject: [PATCH 163/224] Added network metrics logging and reactored code. --- include/Engine/Network/Client.h | 6 +-- include/Engine/Network/MessageType.h | 3 +- include/Engine/Network/Network.h | 13 ++++++ include/Engine/Network/NetworkData.h | 18 ++++++++ include/Engine/Network/Packet.h | 2 + include/Engine/Network/Server.h | 4 +- src/Engine/Network/Client.cpp | 57 +++++++++++++++----------- src/Engine/Network/Network.cpp | 61 ++++++++++++++++++++++++++++ src/Engine/Network/Packet.cpp | 1 + src/Engine/Network/Server.cpp | 56 ++++++++++++++++++------- 10 files changed, 176 insertions(+), 45 deletions(-) create mode 100644 include/Engine/Network/NetworkData.h create mode 100644 src/Engine/Network/Network.cpp diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 96511baa..38db1e9b 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -61,21 +61,21 @@ private: SnapshotDefinitions m_NextSnapshot; double m_DurationOfPingTime; std::clock_t m_StartPingTime; + std::clock_t m_TimeSinceSentInputs; + unsigned int m_SendInputIntervalMs = 33; std::vector m_InputCommandBuffer; // Private member functions void readFromServer(); - int receive(char* data, size_t length); + int receive(char* data); void send(Packet& packet); void connect(); void disconnect(); - void ping(); void parseMessageType(Packet& packet); void updateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType); void parseConnect(Packet& packet); void parsePlayerConnected(Packet& packet); void parsePing(); - void parseServerPing(); void InterpolateFields(Packet & packet, const ComponentInfo & componentInfo, const EntityID & entityID, const std::string & componentType); void parseSnapshot(Packet& packet); void identifyPacketLoss(); diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index f0026190..8468f2fc 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -7,8 +7,7 @@ enum class MessageType { Connect, Disconnect, - ClientPing, - ServerPing, + Ping, Message, Snapshot, OnInputCommand, diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index 1464a96f..7166eec6 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -1,9 +1,14 @@ #ifndef Network_h__ #define Network_h__ +#include + #include "Core/World.h" #include "Core/EventBroker.h" #include "Network/Packet.h" +#include "Network/NetworkData.h" +#include +#include #define MAXCONNECTIONS 8 #define INPUTSIZE 4097 @@ -15,6 +20,14 @@ public: virtual ~Network() { }; virtual void Start(World* m_world, EventBroker *eventBroker) = 0; virtual void Update() = 0; +protected: + // For Debug + bool isReadingData = false; + NetworkData m_NetworkData; + unsigned int m_SaveDataIntervalMs = 1000; + std::clock_t m_SaveDataTimer; + void saveToFile(); + void updateNetworkData(); }; #endif \ No newline at end of file diff --git a/include/Engine/Network/NetworkData.h b/include/Engine/Network/NetworkData.h new file mode 100644 index 00000000..87f7a215 --- /dev/null +++ b/include/Engine/Network/NetworkData.h @@ -0,0 +1,18 @@ +#ifndef NetworkData_h__ +#define NetworkData_h__ +#include + +struct NetworkData { + unsigned int TotalTime = 0; + unsigned int TotalDataReceived = 0; + unsigned int TotalDataSent = 0; + unsigned int AmountOfMessagesReceived = 0; + unsigned int AmountOfMessagesSent = 0; + // Interval based + unsigned int DataReceivedThisInterval = 0; + unsigned int DataSentThisInterval = 0; + // pair: first=reveived, second=send + std::vector> BandwidthBytes; +}; + +#endif diff --git a/include/Engine/Network/Packet.h b/include/Engine/Network/Packet.h index 2891bf87..d38ddf58 100644 --- a/include/Engine/Network/Packet.h +++ b/include/Engine/Network/Packet.h @@ -55,12 +55,14 @@ public: char* Data() { return m_Data; }; unsigned int DataReadSize() { return m_ReturnDataOffset; } unsigned int MaxSize() { return m_MaxPacketSize; } + unsigned int HeaderSize() { return m_HeaderSize; } private: char* m_Data; unsigned int m_ReturnDataOffset = 0; int m_Offset = 0; unsigned int m_MaxPacketSize = 512; + unsigned int m_HeaderSize = 0; void resizeData(); }; diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 8aabceba..c4f1bf16 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -54,7 +54,7 @@ private: unsigned int m_PreviousPacketID = 0; // Private member functions - int receive(char* data, size_t length); + int receive(char* data); void readFromClients(); void send(Packet& packet, int playerID); void send(Packet& packet); @@ -69,7 +69,7 @@ private: void parseConnect(Packet& packet); void parseDisconnect(); void parseClientPing(); - void parseServerPing(); + void parsePing(); void identifyPacketLoss(); void createPlayer(); int GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 8eee335e..644b719b 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -7,6 +7,8 @@ Client::Client(ConfigFile* config) : m_Socket(m_IOService) { // Asumes root node is EntityID 0 insertIntoServerClientMaps(0, 0); + // Init timer + m_TimeSinceSentInputs = std::clock(); // Default is local host std::string address = config->Get("Networking.Address", "127.0.0.1"); int port = config->Get("Networking.Port", 13); @@ -37,19 +39,24 @@ void Client::Update() readFromServer(); if (m_IsConnected) { hasServerTimedOut(); + // Don't sent 1 input in 1 packet, bunch em up. + if (m_SendInputIntervalMs < (1000 * (std::clock() - m_TimeSinceSentInputs) / (double)CLOCKS_PER_SEC)) { + sendInputCommands(); + m_TimeSinceSentInputs = std::clock(); + } } + Network::Update(); } void Client::readFromServer() { while (m_Socket.available()) { - bytesRead = receive(readBuf, INPUTSIZE); + bytesRead = receive(readBuf); if (bytesRead > 0) { Packet packet(readBuf, bytesRead); parseMessageType(packet); } } - sendInputCommands(); } void Client::parseMessageType(Packet& packet) @@ -66,12 +73,9 @@ void Client::parseMessageType(Packet& packet) case MessageType::Connect: parseConnect(packet); break; - case MessageType::ClientPing: + case MessageType::Ping: parsePing(); break; - case MessageType::ServerPing: - parseServerPing(); - break; case MessageType::Message: break; case MessageType::Snapshot: @@ -99,11 +103,6 @@ void Client::parsePlayerConnected(Packet & packet) } void Client::parsePing() -{ - -} - -void Client::parseServerPing() { // Might miss connect message so set it here instead. m_IsConnected = true; @@ -112,7 +111,7 @@ void Client::parseServerPing() LOG_INFO("%i: response time with ctime(ms): %f", m_PacketID, m_DurationOfPingTime); m_StartPingTime = std::clock(); - Packet packet(MessageType::ServerPing, m_SendPacketID); + Packet packet(MessageType::Ping, m_SendPacketID); packet.WriteString("Ping recieved"); send(packet); } @@ -211,15 +210,20 @@ void Client::parseSnapshot(Packet& packet) } } -int Client::receive(char* data, size_t length) +int Client::receive(char* data) { boost::system::error_code error; int bytesReceived = m_Socket.receive_from(boost - ::asio::buffer((void*)data, length), + ::asio::buffer((void*)data, INPUTSIZE), m_ReceiverEndpoint, 0, error); - + // Network Debug data + if (isReadingData) { + m_NetworkData.TotalDataReceived += bytesReceived; + m_NetworkData.DataReceivedThisInterval += bytesReceived; + m_NetworkData.AmountOfMessagesReceived++; + } if (error) { //LOG_ERROR("receive: %s", error.message().c_str()); } @@ -232,6 +236,12 @@ void Client::send(Packet& packet) packet.Data(), packet.Size()), m_ReceiverEndpoint, 0); + // Network Debug data + if (isReadingData) { + m_NetworkData.TotalDataSent += packet.Size(); + m_NetworkData.DataSentThisInterval += packet.Size(); + m_NetworkData.AmountOfMessagesSent++; + } } void Client::connect() @@ -250,14 +260,6 @@ void Client::disconnect() send(packet); } -void Client::ping() -{ - //Packet packet(MessageType::Connect, m_SendPacketID); - //packet.WriteString("Ping"); - //m_StartPingTime = std::clock(); - //send(packet); -} - bool Client::OnInputCommand(const Events::InputCommand & e) { if (e.Command == "ConnectToServer") { // Connect for now @@ -275,6 +277,15 @@ bool Client::OnInputCommand(const Events::InputCommand & e) if (e.Value > 0) { becomePlayer(); } + } else if (e.Command == "LogNetworkBandwidth") { + if (e.Value > 0) { + // Save to file if we no longer want to read data. + if (isReadingData) { + saveToFile(); + } + isReadingData = !isReadingData; + m_SaveDataTimer = std::clock(); + } } else { m_InputCommandBuffer.push_back(e); //LOG_DEBUG("Client::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); diff --git a/src/Engine/Network/Network.cpp b/src/Engine/Network/Network.cpp new file mode 100644 index 00000000..c9ed3637 --- /dev/null +++ b/src/Engine/Network/Network.cpp @@ -0,0 +1,61 @@ +#include "Network/Network.h" + +void Network::Update() +{ + updateNetworkData(); +} + +void Network::saveToFile() +{ + std::ofstream outfile; + time_t t = time(0); + // get time now + struct tm * now = localtime(&t); + // Get current time and date + std::string dateAndTime = "BandwidthData - " + std::to_string(now->tm_year + 1900) + '-' + + std::to_string(now->tm_mon + 1) + '-' + + std::to_string(now->tm_mday) + '_' + + std::to_string(now->tm_hour) + "h." + + std::to_string(now->tm_min) + "m." + + std::to_string(now->tm_sec) + 's'; + + outfile.open(dateAndTime + ".csv"); + outfile << "Total time," + std::to_string(m_NetworkData.TotalTime) + "\n"; + outfile << "Total data received," + std::to_string(m_NetworkData.TotalDataReceived) + "\n"; + outfile << "Total data sent," + std::to_string(m_NetworkData.TotalDataSent) + "\n"; + outfile << "Total messages received," + std::to_string(m_NetworkData.AmountOfMessagesReceived) + "\n"; + outfile << "Total messages sent," + std::to_string(m_NetworkData.AmountOfMessagesSent) + "\n"; + + float messagesReceivedPerSec = (float)m_NetworkData.AmountOfMessagesReceived / (m_NetworkData.TotalTime / 1000); + float messagesSentPerSec = (float)m_NetworkData.AmountOfMessagesSent / (m_NetworkData.TotalTime / 1000); + float dataReceivedPerSec = (float)m_NetworkData.TotalDataReceived / (m_NetworkData.TotalTime / 1000); + float dataSentPerSec = (float)m_NetworkData.TotalDataSent / (m_NetworkData.TotalTime / 1000); + outfile << "Avarage messages received / s: " + std::to_string(messagesReceivedPerSec) + "\n"; + outfile << "Avarage messages sents / s: " + std::to_string(messagesSentPerSec) + "\n"; + outfile << "Avarage data received B/s: " + std::to_string(dataReceivedPerSec) + "\n"; + outfile << "Avarage data sents B/s: " + std::to_string(dataSentPerSec) + "\n"; + + outfile << "time, avg receive B, avg send B\n"; + for (int i = 0; i < m_NetworkData.BandwidthBytes.size(); i++) { + outfile << std::to_string(i) + ","; + outfile << std::to_string(m_NetworkData.BandwidthBytes[i].first) + ","; + outfile << std::to_string(m_NetworkData.BandwidthBytes[i].second) + "\n"; + } + outfile.close(); + +} + +void Network::updateNetworkData() +{ + std::clock_t currentTime = std::clock(); + // Send snapshot + if (m_SaveDataIntervalMs < (1000 * (currentTime - m_SaveDataTimer) / (double)CLOCKS_PER_SEC)) { + // Set values + m_NetworkData.TotalTime += (1000 * (currentTime - m_SaveDataTimer) / (double)CLOCKS_PER_SEC); + m_NetworkData.BandwidthBytes.push_back(std::pair(m_NetworkData.DataReceivedThisInterval, m_NetworkData.DataSentThisInterval)); + // Reset interval stuff + m_SaveDataTimer = std::clock(); + m_NetworkData.DataSentThisInterval = 0; + m_NetworkData.DataReceivedThisInterval = 0; + } +} \ No newline at end of file diff --git a/src/Engine/Network/Packet.cpp b/src/Engine/Network/Packet.cpp index 6308a130..d40a1b32 100644 --- a/src/Engine/Network/Packet.cpp +++ b/src/Engine/Network/Packet.cpp @@ -39,6 +39,7 @@ void Packet::Init(MessageType type, unsigned int & packetID) Packet::WritePrimitive(messageType); Packet::WritePrimitive(packetID); packetID++; + m_HeaderSize = m_Offset; } void Packet::WriteString(const std::string& str) diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 8a194c0e..a3fc4fe8 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -24,14 +24,17 @@ void Server::Update() { readFromClients(); m_EventBroker->Process(); -} + if (isReadingData) { + Network::Update(); + } +} void Server::readFromClients() { while (m_Socket.available()) { try { - bytesRead = receive(readBuffer, INPUTSIZE); + bytesRead = receive(readBuffer); Packet packet(readBuffer, bytesRead); parseMessageType(packet); } catch (const std::exception& err) { @@ -70,11 +73,8 @@ void Server::parseMessageType(Packet& packet) case MessageType::Connect: parseConnect(packet); break; - case MessageType::ClientPing: - //parseClientPing(); - break; - case MessageType::ServerPing: - parseServerPing(); + case MessageType::Ping: + parsePing(); break; case MessageType::Message: break; @@ -97,12 +97,18 @@ void Server::parseMessageType(Packet& packet) } } -int Server::receive(char * data, size_t length) +int Server::receive(char * data) { - length = m_Socket.receive_from( + unsigned int length = m_Socket.receive_from( boost::asio::buffer((void*)data - , length) + , INPUTSIZE) , m_ReceiverEndpoint, 0); + // Network Debug data + if (isReadingData) { + m_NetworkData.TotalDataReceived += length; + m_NetworkData.DataReceivedThisInterval += length; + m_NetworkData.AmountOfMessagesReceived++; + } return length; } @@ -112,6 +118,12 @@ void Server::send(Packet& packet, int userID) boost::asio::buffer(packet.Data(), packet.Size()), m_ConnectedUsers[userID].Endpoint, 0); + // Network Debug data + if (isReadingData) { + m_NetworkData.TotalDataSent += packet.Size(); + m_NetworkData.DataSentThisInterval += packet.Size(); + m_NetworkData.AmountOfMessagesSent++; + } } void Server::send(Packet & packet) @@ -122,6 +134,11 @@ void Server::send(Packet & packet) packet.Size()), m_ReceiverEndpoint, 0); + if (isReadingData) { + // Network Debug data + m_NetworkData.TotalDataSent += packet.Size(); + m_NetworkData.DataSentThisInterval += packet.Size(); + } } void Server::broadcast(Packet& packet) @@ -160,7 +177,9 @@ void Server::sendSnapshot() } } } - broadcast(packet); + if (packet.Size() > packet.HeaderSize() + componentInfo.Name.size()) { + broadcast(packet); + } } } @@ -174,7 +193,7 @@ void Server::sendPing() } } // Create ping message - Packet packet(MessageType::ServerPing); + Packet packet(MessageType::Ping); packet.WriteString("Ping from server"); // Time message m_StartPingTime = std::clock(); @@ -298,12 +317,12 @@ void Server::parseClientPing() return; } // Return ping - Packet packet(MessageType::ClientPing, m_PlayerDefinitions[playerID].PacketID); + Packet packet(MessageType::Ping, m_PlayerDefinitions[playerID].PacketID); packet.WriteString("Ping received"); send(packet); } -void Server::parseServerPing() +void Server::parsePing() { for (int i = 0; i < m_ConnectedUsers.size(); i++) { if (m_ConnectedUsers[i].Endpoint.address() == m_ReceiverEndpoint.address()) { @@ -356,7 +375,7 @@ void Server::createPlayer() } } LOG_WARNING("Server is full!"); - + } int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) @@ -373,5 +392,12 @@ int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) bool Server::OnInputCommand(const Events::InputCommand & e) { //LOG_DEBUG("Server::OnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); + if (e.Command == "LogNetworkBandwidth" && e.Value > 0) { + if (isReadingData) { + saveToFile(); + } + isReadingData = !isReadingData; + m_SaveDataTimer = std::clock(); + } return true; } From caf55fb8d1c787bc4b6ac413550df4ba5f6bd8f3 Mon Sep 17 00:00:00 2001 From: Tleety Date: Fri, 22 Jan 2016 10:52:45 +0100 Subject: [PATCH 164/224] Small fix to the bloom light, now feels smoother. --- resources/Shaders/ForwardPlus.frag.glsl | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 421f130c..403c96fc 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -140,11 +140,13 @@ void main() sceneColor = vec4(color_result.xyz, 1.0); //These if statements should be removed if they are slow. color_result += glowTexel; + bloomColor = vec4(clamp(color_result.xyz - 1.0, 0, 100), 1.0); + /* if(color_result.x > 1 || color_result.y > 1 || color_result.z > 1) { bloomColor = vec4(color_result.xyz, 1.0); } else { bloomColor = vec4(0.0, 0.0, 0.0, 1.0); - } + } */ //sceneColor += Input.DiffuseColor * (totalLighting.Diffuse) * diffuseTexel * Color; //sceneColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); From fcc9d64e7a95e2aa420060fe1018327525cf9739 Mon Sep 17 00:00:00 2001 From: stiffly Date: Fri, 22 Jan 2016 10:58:10 +0100 Subject: [PATCH 165/224] Now publishes an EPlayerDisconnected event --- include/Engine/Network/EPlayerDisconnected.h | 18 ++++++++++++++++++ include/Engine/Network/Server.h | 1 + src/Engine/Network/Server.cpp | 5 +++++ 3 files changed, 24 insertions(+) create mode 100644 include/Engine/Network/EPlayerDisconnected.h diff --git a/include/Engine/Network/EPlayerDisconnected.h b/include/Engine/Network/EPlayerDisconnected.h new file mode 100644 index 00000000..278a7b1f --- /dev/null +++ b/include/Engine/Network/EPlayerDisconnected.h @@ -0,0 +1,18 @@ +#ifndef Events_PlayerDisconnected +#define Events_PlayerDisconnected + +#include "Core/EventBroker.h" +#include "Core/Entity.h" + +namespace Events +{ + +struct PlayerDisconnected : public Event +{ + unsigned int PlayerID; + EntityID Entity; +}; + +} + +#endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index c4f1bf16..cdbcd357 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -14,6 +14,7 @@ #include "../Network/Network.h" #include "Input/EInputCommand.h" #include "Core/EPlayerDamage.h" +#include "Network/EPlayerDisconnected.h" class Server : public Network { diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index a8c6ced9..4ccc6a7d 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -223,6 +223,11 @@ void Server::disconnect(int i) //broadcast("A player disconnected"); LOG_INFO("User %s disconnected/timed out", m_PlayerDefinitions[i].Name.c_str()); // Remove enteties and stuff (When we can remove entity, remove it and tell clients to remove the copy they have) + Events::PlayerDisconnected e; + e.Entity = m_PlayerDefinitions[i].EntityID; + e.PlayerID = i; + m_EventBroker->Publish(e); + m_PlayerDefinitions[i].Endpoint = boost::asio::ip::udp::endpoint(); m_PlayerDefinitions[i].EntityID = -1; m_PlayerDefinitions[i].Name = ""; From b1ea5429cefdfb2243bc8a6581b5bc80d37c0059 Mon Sep 17 00:00:00 2001 From: stiffly Date: Fri, 22 Jan 2016 11:53:04 +0100 Subject: [PATCH 166/224] Used config for a lot of things --- include/Engine/Network/Client.h | 4 +-- include/Engine/Network/Network.h | 7 +++-- include/Engine/Network/Server.h | 6 ++-- include/Game/Systems/InterpolationSystem.h | 9 ++++-- resources/DefaultConfig.ini | 5 +++ src/Engine/Network/Client.cpp | 3 +- src/Engine/Network/Network.cpp | 9 +++++- src/Engine/Network/Server.cpp | 19 +++++++----- src/Game/Systems/InterpolationSystem.cpp | 36 ++-------------------- 9 files changed, 46 insertions(+), 52 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 38db1e9b..61fa5ff0 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -57,12 +57,12 @@ private: std::unordered_map m_ClientIDToServerID; // Network logic - PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; + PlayerDefinition m_PlayerDefinitions[8]; SnapshotDefinitions m_NextSnapshot; double m_DurationOfPingTime; std::clock_t m_StartPingTime; std::clock_t m_TimeSinceSentInputs; - unsigned int m_SendInputIntervalMs = 33; + unsigned int m_SendInputIntervalMs; std::vector m_InputCommandBuffer; // Private member functions diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index 7166eec6..73cb01d3 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -7,12 +7,12 @@ #include "Core/EventBroker.h" #include "Network/Packet.h" #include "Network/NetworkData.h" +#include "Core/ResourceManager.h" +#include "Core/ConfigFile.h" #include #include -#define MAXCONNECTIONS 8 #define INPUTSIZE 4097 -#define TIMEOUTMS 15000 class Network { @@ -26,8 +26,11 @@ protected: NetworkData m_NetworkData; unsigned int m_SaveDataIntervalMs = 1000; std::clock_t m_SaveDataTimer; + unsigned int m_MaxConnections; + unsigned int m_TimeoutMs; void saveToFile(); void updateNetworkData(); + void initialize(); }; #endif \ No newline at end of file diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index cdbcd357..f1b5691a 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -30,7 +30,7 @@ private: boost::asio::ip::udp::socket m_Socket; // Sending messages to client logic - PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; + PlayerDefinition m_PlayerDefinitions[8]; // std::vector m_ConnectedUsers; char readBuffer[INPUTSIZE] = { 0 }; int bytesRead = 0; @@ -39,8 +39,8 @@ private: std::clock_t previousSnapshotMessage = std::clock(); std::clock_t timOutTimer = std::clock(); // How often we send messages (milliseconds) - int intervalMs = 1000; - int snapshotInterval = 50; + int pingIntervalMs; + int snapshotInterval; int checkTimeOutInterval = 100; //Timers diff --git a/include/Game/Systems/InterpolationSystem.h b/include/Game/Systems/InterpolationSystem.h index 4b05571b..0e137598 100644 --- a/include/Game/Systems/InterpolationSystem.h +++ b/include/Game/Systems/InterpolationSystem.h @@ -10,11 +10,11 @@ #include "Common.h" #include "Core/System.h" #include "Core/EventBroker.h" +#include "Core/ResourceManager.h" +#include "Core/ConfigFile.h" #include "Network/EInterpolate.h" -#define SNAPSHOTINTERVAL 0.05f - class InterpolationSystem : public PureSystem { struct Transform @@ -29,6 +29,8 @@ public: : System(world, eventBroker) , PureSystem("Transform") { + ConfigFile* config = ResourceManager::Load("Config.ini"); + m_SnapshotInterval = config->Get("Networking.SnapshotInterval", 0.05); EVENT_SUBSCRIBE_MEMBER(m_EInterpolate, &InterpolationSystem::OnInterpolate); } ~InterpolationSystem() { } @@ -42,9 +44,10 @@ private: T vectorInterpolation(T prev, T next, double currentTime) { T difference = next - prev; - T vector = (difference / SNAPSHOTINTERVAL) * static_cast(currentTime); + T vector = (difference / m_SnapshotInterval) * static_cast(currentTime); return vector; } + float m_SnapshotInterval; EventRelay m_EInterpolate; bool InterpolationSystem::OnInterpolate(const Events::Interpolate& e); diff --git a/resources/DefaultConfig.ini b/resources/DefaultConfig.ini index fb490ec8..53e86699 100644 --- a/resources/DefaultConfig.ini +++ b/resources/DefaultConfig.ini @@ -19,6 +19,11 @@ IsServer=false Name=Bob Address=127.0.0.1 Port=13 +MaxConnections=8 +SnapshotInterval=0.05 +SendInputIntervalMs=33 +PingIntervalMs= 1000 +TimeoutMs=15000 [Multithreading] ResourceLoading=true diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 4dc4c93e..1fd823cf 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -15,6 +15,7 @@ Client::Client(ConfigFile* config) : m_Socket(m_IOService) m_ReceiverEndpoint = udp::endpoint(boost::asio::ip::address::from_string(address), port); // Set up network stream m_PlayerName = config->Get("Networking.Name", "Raptorcopter"); + m_SendInputIntervalMs = config->Get("Networking.SendInputIntervalMs", 33); } Client::~Client() @@ -316,7 +317,7 @@ bool Client::hasServerTimedOut() { // Time in ms float timeSincePing = 1000 * (std::clock() - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); - if (timeSincePing > TIMEOUTMS) { + if (timeSincePing > m_TimeoutMs) { // Clear everything and go to menu. LOG_INFO("Server has timed out, returning to menu, Beep Boop."); m_IsConnected = false; diff --git a/src/Engine/Network/Network.cpp b/src/Engine/Network/Network.cpp index c9ed3637..f4dcd1a2 100644 --- a/src/Engine/Network/Network.cpp +++ b/src/Engine/Network/Network.cpp @@ -58,4 +58,11 @@ void Network::updateNetworkData() m_NetworkData.DataSentThisInterval = 0; m_NetworkData.DataReceivedThisInterval = 0; } -} \ No newline at end of file +} + +void Network::initialize() +{ + ConfigFile* config = ResourceManager::Load("Config.ini"); + m_MaxConnections = config->Get("Networking.MaxConnections", 8); + m_TimeoutMs = config->Get("Networking.TimeoutMs", 20000); +} diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 4ccc6a7d..07c43829 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -1,7 +1,12 @@ #include "Network/Server.h" Server::Server() : m_Socket(m_IOService, boost::asio::ip::udp::endpoint(boost::asio::ip::udp::v4(), 13)) -{ } +{ + ConfigFile* config = ResourceManager::Load("Config.ini"); + snapshotInterval = 1000 * config->Get("Networking.SnapshotInterval", 0.05); + pingIntervalMs = config->Get("Networking.PingIntervalMs", 1000); + +} Server::~Server() { @@ -14,7 +19,7 @@ void Server::Start(World* world, EventBroker* eventBroker) m_EventBroker = eventBroker; // Subscribe to events EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Server::OnInputCommand); - for (size_t i = 0; i < MAXCONNECTIONS; i++) { + for (size_t i = 0; i < m_MaxConnections; i++) { m_PlayerDefinitions[i].StopTime = std::clock(); } LOG_INFO("I am Server. BIP BOP\n"); @@ -49,7 +54,7 @@ void Server::readFromClients() } // Send pings each - if (intervalMs < (1000 * (currentTime - previousePingMessage) / (double)CLOCKS_PER_SEC)) { + if (pingIntervalMs < (1000 * (currentTime - previousePingMessage) / (double)CLOCKS_PER_SEC)) { sendPing(); previousePingMessage = currentTime; } @@ -210,7 +215,7 @@ void Server::checkForTimeOuts() if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { int stopPing = 1000 * m_ConnectedUsers[i].StopTime / static_cast(CLOCKS_PER_SEC); - if (startPing > stopPing + TIMEOUTMS) { + if (startPing > stopPing + m_TimeoutMs) { LOG_INFO("User %i timed out!", i); disconnect(i); } @@ -239,7 +244,7 @@ void Server::parseOnInputCommand(Packet& packet) { int playerID = -1; // Check which player it was who sent the message - for (int i = 0; i < MAXCONNECTIONS; i++) { + for (int i = 0; i < m_MaxConnections; i++) { // if the player is connected set playerID to the correct PlayerID if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() && m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { @@ -364,7 +369,7 @@ void Server::createPlayer() LOG_WARNING("Not a recognized user!"); return; } - for (int playerIndex = 0; playerIndex < MAXCONNECTIONS; playerIndex++) { + for (int playerIndex = 0; playerIndex < m_MaxConnections; playerIndex++) { if (m_PlayerDefinitions[playerIndex].Endpoint.address() == boost::asio::ip::address()) { m_PlayerDefinitions[playerIndex] = m_ConnectedUsers[userIndex]; EntityID entityID = m_World->CreateEntity(); @@ -384,7 +389,7 @@ void Server::createPlayer() int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) { - for (int i = 0; i < MAXCONNECTIONS; i++) { + for (int i = 0; i < m_MaxConnections; i++) { if (m_PlayerDefinitions[i].Endpoint.address() == endpoint.address() && m_PlayerDefinitions[i].Endpoint.port() == endpoint.port()) { return i; diff --git a/src/Game/Systems/InterpolationSystem.cpp b/src/Game/Systems/InterpolationSystem.cpp index 75f68678..be2c9a4f 100644 --- a/src/Game/Systems/InterpolationSystem.cpp +++ b/src/Game/Systems/InterpolationSystem.cpp @@ -1,35 +1,15 @@ #include "Systems/InterpolationSystem.h" -//void InterpolationSystem::UpdateComponent(World * world, ComponentWrapper & transform, double dt) -//{ -// if (m_InterpolationPoints[transform.EntityID].size() > 0) { -// Transform& sTransform = m_InterpolationPoints[transform.EntityID].front(); -// sTransform.interpolationTime += dt; -// if (sTransform.interpolationTime > 0.05) { -// double time = std::fmod(sTransform.interpolationTime, 0.05f); -// m_InterpolationPoints[transform.EntityID].pop(); -// if (m_InterpolationPoints[transform.EntityID].size() <= 0) { -// return; -// } -// sTransform = m_InterpolationPoints[transform.EntityID].front(); -// sTransform.interpolationTime = time; -// } -// glm::vec3 nextPosition = sTransform.Position; -// glm::vec3 currentPosition = static_cast(transform["Position"]); -// transform["Position"] = vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); -// } -//} - void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& transform, double dt) { if (m_NextTransform.find(transform.EntityID) != m_NextTransform.end()) { // Exists in map m_NextTransform[transform.EntityID].interpolationTime += dt; Transform sTransform = m_NextTransform[transform.EntityID]; double time = sTransform.interpolationTime; - if (time > SNAPSHOTINTERVAL) { + if (time > m_SnapshotInterval) { if (m_LastReceivedTransform.find(transform.EntityID) != m_LastReceivedTransform.end()) { m_NextTransform[transform.EntityID] = m_LastReceivedTransform[transform.EntityID]; - m_NextTransform[transform.EntityID].interpolationTime = time - SNAPSHOTINTERVAL; + m_NextTransform[transform.EntityID].interpolationTime = time - m_SnapshotInterval; sTransform = m_NextTransform[transform.EntityID]; m_LastReceivedTransform.erase(transform.EntityID); } else { @@ -44,7 +24,7 @@ void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrappe // Orientation glm::quat nextOrientation = sTransform.Orientation; glm::quat currentOrientation = glm::quat(static_cast(transform["Orientation"])); - (glm::vec3&)transform["Orientation"] = glm::eulerAngles(glm::slerp(currentOrientation, nextOrientation, sTransform.interpolationTime / SNAPSHOTINTERVAL)); + (glm::vec3&)transform["Orientation"] = glm::eulerAngles(glm::slerp(currentOrientation, nextOrientation, sTransform.interpolationTime / m_SnapshotInterval)); // Scale glm::vec3 nextScale = sTransform.Scale; glm::vec3 currentScale = static_cast(transform["Scale"]); @@ -72,15 +52,5 @@ bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) } else { // Did not m_NextTransform[e.Entity] = transform; } - // Check if queue already exists - //if (m_InterpolationPoints.find(e.Entity) != m_InterpolationPoints.end()) { // Did exist, push to queue - // m_InterpolationPoints[e.Entity].push(transform); - //} - - //else { // Did not exist, create queue - // std::queue transformQueue; - // transformQueue.push(transform); - // m_InterpolationPoints[e.Entity] = transformQueue; - //} return false; } From 08fcdb382b3dc2ebcf05692c7fa788acc05c6e3d Mon Sep 17 00:00:00 2001 From: stiffly Date: Fri, 22 Jan 2016 11:53:04 +0100 Subject: [PATCH 167/224] Used config for a lot of things --- include/Engine/Network/Client.h | 4 +-- include/Engine/Network/Network.h | 7 +++-- include/Engine/Network/Server.h | 6 ++-- include/Game/Systems/InterpolationSystem.h | 9 ++++-- resources/DefaultConfig.ini | 5 +++ src/Engine/Network/Client.cpp | 6 +++- src/Engine/Network/Network.cpp | 9 +++++- src/Engine/Network/Server.cpp | 20 +++++++----- src/Game/Systems/InterpolationSystem.cpp | 36 ++-------------------- 9 files changed, 50 insertions(+), 52 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 38db1e9b..61fa5ff0 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -57,12 +57,12 @@ private: std::unordered_map m_ClientIDToServerID; // Network logic - PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; + PlayerDefinition m_PlayerDefinitions[8]; SnapshotDefinitions m_NextSnapshot; double m_DurationOfPingTime; std::clock_t m_StartPingTime; std::clock_t m_TimeSinceSentInputs; - unsigned int m_SendInputIntervalMs = 33; + unsigned int m_SendInputIntervalMs; std::vector m_InputCommandBuffer; // Private member functions diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index 7166eec6..73cb01d3 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -7,12 +7,12 @@ #include "Core/EventBroker.h" #include "Network/Packet.h" #include "Network/NetworkData.h" +#include "Core/ResourceManager.h" +#include "Core/ConfigFile.h" #include #include -#define MAXCONNECTIONS 8 #define INPUTSIZE 4097 -#define TIMEOUTMS 15000 class Network { @@ -26,8 +26,11 @@ protected: NetworkData m_NetworkData; unsigned int m_SaveDataIntervalMs = 1000; std::clock_t m_SaveDataTimer; + unsigned int m_MaxConnections; + unsigned int m_TimeoutMs; void saveToFile(); void updateNetworkData(); + void initialize(); }; #endif \ No newline at end of file diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index cdbcd357..f1b5691a 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -30,7 +30,7 @@ private: boost::asio::ip::udp::socket m_Socket; // Sending messages to client logic - PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS]; + PlayerDefinition m_PlayerDefinitions[8]; // std::vector m_ConnectedUsers; char readBuffer[INPUTSIZE] = { 0 }; int bytesRead = 0; @@ -39,8 +39,8 @@ private: std::clock_t previousSnapshotMessage = std::clock(); std::clock_t timOutTimer = std::clock(); // How often we send messages (milliseconds) - int intervalMs = 1000; - int snapshotInterval = 50; + int pingIntervalMs; + int snapshotInterval; int checkTimeOutInterval = 100; //Timers diff --git a/include/Game/Systems/InterpolationSystem.h b/include/Game/Systems/InterpolationSystem.h index 4b05571b..0e137598 100644 --- a/include/Game/Systems/InterpolationSystem.h +++ b/include/Game/Systems/InterpolationSystem.h @@ -10,11 +10,11 @@ #include "Common.h" #include "Core/System.h" #include "Core/EventBroker.h" +#include "Core/ResourceManager.h" +#include "Core/ConfigFile.h" #include "Network/EInterpolate.h" -#define SNAPSHOTINTERVAL 0.05f - class InterpolationSystem : public PureSystem { struct Transform @@ -29,6 +29,8 @@ public: : System(world, eventBroker) , PureSystem("Transform") { + ConfigFile* config = ResourceManager::Load("Config.ini"); + m_SnapshotInterval = config->Get("Networking.SnapshotInterval", 0.05); EVENT_SUBSCRIBE_MEMBER(m_EInterpolate, &InterpolationSystem::OnInterpolate); } ~InterpolationSystem() { } @@ -42,9 +44,10 @@ private: T vectorInterpolation(T prev, T next, double currentTime) { T difference = next - prev; - T vector = (difference / SNAPSHOTINTERVAL) * static_cast(currentTime); + T vector = (difference / m_SnapshotInterval) * static_cast(currentTime); return vector; } + float m_SnapshotInterval; EventRelay m_EInterpolate; bool InterpolationSystem::OnInterpolate(const Events::Interpolate& e); diff --git a/resources/DefaultConfig.ini b/resources/DefaultConfig.ini index fb490ec8..53e86699 100644 --- a/resources/DefaultConfig.ini +++ b/resources/DefaultConfig.ini @@ -19,6 +19,11 @@ IsServer=false Name=Bob Address=127.0.0.1 Port=13 +MaxConnections=8 +SnapshotInterval=0.05 +SendInputIntervalMs=33 +PingIntervalMs= 1000 +TimeoutMs=15000 [Multithreading] ResourceLoading=true diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 4dc4c93e..fe552fa2 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -5,6 +5,8 @@ using namespace boost::asio::ip; Client::Client(ConfigFile* config) : m_Socket(m_IOService) { + Network::initialize(); + // Asumes root node is EntityID 0 insertIntoServerClientMaps(0, 0); // Init timer @@ -15,6 +17,8 @@ Client::Client(ConfigFile* config) : m_Socket(m_IOService) m_ReceiverEndpoint = udp::endpoint(boost::asio::ip::address::from_string(address), port); // Set up network stream m_PlayerName = config->Get("Networking.Name", "Raptorcopter"); + m_SendInputIntervalMs = config->Get("Networking.SendInputIntervalMs", 33); + } Client::~Client() @@ -316,7 +320,7 @@ bool Client::hasServerTimedOut() { // Time in ms float timeSincePing = 1000 * (std::clock() - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); - if (timeSincePing > TIMEOUTMS) { + if (timeSincePing > m_TimeoutMs) { // Clear everything and go to menu. LOG_INFO("Server has timed out, returning to menu, Beep Boop."); m_IsConnected = false; diff --git a/src/Engine/Network/Network.cpp b/src/Engine/Network/Network.cpp index c9ed3637..f4dcd1a2 100644 --- a/src/Engine/Network/Network.cpp +++ b/src/Engine/Network/Network.cpp @@ -58,4 +58,11 @@ void Network::updateNetworkData() m_NetworkData.DataSentThisInterval = 0; m_NetworkData.DataReceivedThisInterval = 0; } -} \ No newline at end of file +} + +void Network::initialize() +{ + ConfigFile* config = ResourceManager::Load("Config.ini"); + m_MaxConnections = config->Get("Networking.MaxConnections", 8); + m_TimeoutMs = config->Get("Networking.TimeoutMs", 20000); +} diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 4ccc6a7d..719ca16f 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -1,7 +1,13 @@ #include "Network/Server.h" Server::Server() : m_Socket(m_IOService, boost::asio::ip::udp::endpoint(boost::asio::ip::udp::v4(), 13)) -{ } +{ + Network::initialize(); + ConfigFile* config = ResourceManager::Load("Config.ini"); + snapshotInterval = 1000 * config->Get("Networking.SnapshotInterval", 0.05); + pingIntervalMs = config->Get("Networking.PingIntervalMs", 1000); + +} Server::~Server() { @@ -14,7 +20,7 @@ void Server::Start(World* world, EventBroker* eventBroker) m_EventBroker = eventBroker; // Subscribe to events EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Server::OnInputCommand); - for (size_t i = 0; i < MAXCONNECTIONS; i++) { + for (size_t i = 0; i < m_MaxConnections; i++) { m_PlayerDefinitions[i].StopTime = std::clock(); } LOG_INFO("I am Server. BIP BOP\n"); @@ -49,7 +55,7 @@ void Server::readFromClients() } // Send pings each - if (intervalMs < (1000 * (currentTime - previousePingMessage) / (double)CLOCKS_PER_SEC)) { + if (pingIntervalMs < (1000 * (currentTime - previousePingMessage) / (double)CLOCKS_PER_SEC)) { sendPing(); previousePingMessage = currentTime; } @@ -210,7 +216,7 @@ void Server::checkForTimeOuts() if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { int stopPing = 1000 * m_ConnectedUsers[i].StopTime / static_cast(CLOCKS_PER_SEC); - if (startPing > stopPing + TIMEOUTMS) { + if (startPing > stopPing + m_TimeoutMs) { LOG_INFO("User %i timed out!", i); disconnect(i); } @@ -239,7 +245,7 @@ void Server::parseOnInputCommand(Packet& packet) { int playerID = -1; // Check which player it was who sent the message - for (int i = 0; i < MAXCONNECTIONS; i++) { + for (int i = 0; i < m_MaxConnections; i++) { // if the player is connected set playerID to the correct PlayerID if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() && m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { @@ -364,7 +370,7 @@ void Server::createPlayer() LOG_WARNING("Not a recognized user!"); return; } - for (int playerIndex = 0; playerIndex < MAXCONNECTIONS; playerIndex++) { + for (int playerIndex = 0; playerIndex < m_MaxConnections; playerIndex++) { if (m_PlayerDefinitions[playerIndex].Endpoint.address() == boost::asio::ip::address()) { m_PlayerDefinitions[playerIndex] = m_ConnectedUsers[userIndex]; EntityID entityID = m_World->CreateEntity(); @@ -384,7 +390,7 @@ void Server::createPlayer() int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) { - for (int i = 0; i < MAXCONNECTIONS; i++) { + for (int i = 0; i < m_MaxConnections; i++) { if (m_PlayerDefinitions[i].Endpoint.address() == endpoint.address() && m_PlayerDefinitions[i].Endpoint.port() == endpoint.port()) { return i; diff --git a/src/Game/Systems/InterpolationSystem.cpp b/src/Game/Systems/InterpolationSystem.cpp index 75f68678..be2c9a4f 100644 --- a/src/Game/Systems/InterpolationSystem.cpp +++ b/src/Game/Systems/InterpolationSystem.cpp @@ -1,35 +1,15 @@ #include "Systems/InterpolationSystem.h" -//void InterpolationSystem::UpdateComponent(World * world, ComponentWrapper & transform, double dt) -//{ -// if (m_InterpolationPoints[transform.EntityID].size() > 0) { -// Transform& sTransform = m_InterpolationPoints[transform.EntityID].front(); -// sTransform.interpolationTime += dt; -// if (sTransform.interpolationTime > 0.05) { -// double time = std::fmod(sTransform.interpolationTime, 0.05f); -// m_InterpolationPoints[transform.EntityID].pop(); -// if (m_InterpolationPoints[transform.EntityID].size() <= 0) { -// return; -// } -// sTransform = m_InterpolationPoints[transform.EntityID].front(); -// sTransform.interpolationTime = time; -// } -// glm::vec3 nextPosition = sTransform.Position; -// glm::vec3 currentPosition = static_cast(transform["Position"]); -// transform["Position"] = vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); -// } -//} - void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& transform, double dt) { if (m_NextTransform.find(transform.EntityID) != m_NextTransform.end()) { // Exists in map m_NextTransform[transform.EntityID].interpolationTime += dt; Transform sTransform = m_NextTransform[transform.EntityID]; double time = sTransform.interpolationTime; - if (time > SNAPSHOTINTERVAL) { + if (time > m_SnapshotInterval) { if (m_LastReceivedTransform.find(transform.EntityID) != m_LastReceivedTransform.end()) { m_NextTransform[transform.EntityID] = m_LastReceivedTransform[transform.EntityID]; - m_NextTransform[transform.EntityID].interpolationTime = time - SNAPSHOTINTERVAL; + m_NextTransform[transform.EntityID].interpolationTime = time - m_SnapshotInterval; sTransform = m_NextTransform[transform.EntityID]; m_LastReceivedTransform.erase(transform.EntityID); } else { @@ -44,7 +24,7 @@ void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrappe // Orientation glm::quat nextOrientation = sTransform.Orientation; glm::quat currentOrientation = glm::quat(static_cast(transform["Orientation"])); - (glm::vec3&)transform["Orientation"] = glm::eulerAngles(glm::slerp(currentOrientation, nextOrientation, sTransform.interpolationTime / SNAPSHOTINTERVAL)); + (glm::vec3&)transform["Orientation"] = glm::eulerAngles(glm::slerp(currentOrientation, nextOrientation, sTransform.interpolationTime / m_SnapshotInterval)); // Scale glm::vec3 nextScale = sTransform.Scale; glm::vec3 currentScale = static_cast(transform["Scale"]); @@ -72,15 +52,5 @@ bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) } else { // Did not m_NextTransform[e.Entity] = transform; } - // Check if queue already exists - //if (m_InterpolationPoints.find(e.Entity) != m_InterpolationPoints.end()) { // Did exist, push to queue - // m_InterpolationPoints[e.Entity].push(transform); - //} - - //else { // Did not exist, create queue - // std::queue transformQueue; - // transformQueue.push(transform); - // m_InterpolationPoints[e.Entity] = transformQueue; - //} return false; } From 08c476e9e37f2cc90465366edc2f894d3efabe56 Mon Sep 17 00:00:00 2001 From: stiffly Date: Fri, 22 Jan 2016 15:42:36 +0100 Subject: [PATCH 168/224] Added kick logic to the server. Also typedefed. --- include/Engine/Network/Client.h | 9 ++--- include/Engine/Network/MessageType.h | 3 +- include/Engine/Network/Network.h | 3 ++ include/Engine/Network/Server.h | 11 +++--- src/Engine/Network/Client.cpp | 9 +++++ src/Engine/Network/Server.cpp | 53 +++++++++++++++++----------- 6 files changed, 57 insertions(+), 31 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 61fa5ff0..4a16034b 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -39,14 +39,14 @@ private: char readBuf[INPUTSIZE] = { 0 }; // Packet loss logic - unsigned int m_PacketID = 0; - unsigned int m_PreviousPacketID = 0; - unsigned int m_SendPacketID = 0; + PacketID m_PacketID = 0; + PacketID m_PreviousPacketID = 0; + PacketID m_SendPacketID = 0; // Game logic World* m_World; std::string m_PlayerName; - int m_PlayerID = -1; + PlayerID m_PlayerID = -1; EntityID m_ServerEntityID = std::numeric_limits::max(); bool m_IsConnected = false; // Server Client Lookup map @@ -76,6 +76,7 @@ private: void parseConnect(Packet& packet); void parsePlayerConnected(Packet& packet); void parsePing(); + void parseKick(); void InterpolateFields(Packet & packet, const ComponentInfo & componentInfo, const EntityID & entityID, const std::string & componentType); void parseSnapshot(Packet& packet); void identifyPacketLoss(); diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index 8468f2fc..7d8094de 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -13,7 +13,8 @@ enum class MessageType OnInputCommand, OnPlayerDamage, PlayerConnected, - BecomePlayer + BecomePlayer, + Kick }; #endif diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index 73cb01d3..480ac602 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -13,6 +13,9 @@ #include #define INPUTSIZE 4097 +typedef unsigned int PlayerID; +typedef unsigned int PacketID; +typedef unsigned int UserID; class Network { diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index f1b5691a..cbad08b0 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -51,19 +51,19 @@ private: EventBroker* m_EventBroker; // Packet loss logic - unsigned int m_PacketID = 0; - unsigned int m_PreviousPacketID = 0; + PacketID m_PacketID = 0; + PacketID m_PreviousPacketID = 0; // Private member functions int receive(char* data); void readFromClients(); - void send(Packet& packet, int playerID); + void send(Packet& packet, UserID user); void send(Packet& packet); void broadcast(Packet& packet); void sendSnapshot(); void sendPing(); void checkForTimeOuts(); - void disconnect(int i); + void disconnect(UserID user); void parseMessageType(Packet& packet); void parseOnInputCommand(Packet& packet); void parseOnPlayerDamage(Packet& packet); @@ -73,7 +73,8 @@ private: void parsePing(); void identifyPacketLoss(); void createPlayer(); - int GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint); + void kick(PlayerID player); + PlayerID GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint); // Debug event EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index fe552fa2..129e0b42 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -89,6 +89,9 @@ void Client::parseMessageType(Packet& packet) break; case MessageType::PlayerConnected: parsePlayerConnected(packet); + case MessageType::Kick: + parseKick(); + break; default: break; } @@ -120,6 +123,12 @@ void Client::parsePing() send(packet); } +void Client::parseKick() +{ + LOG_WARNING("You have been kicked from the server."); + m_IsConnected = false; +} + // Fields with strings will not work right now void Client::InterpolateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType) { diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 719ca16f..03b9775a 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -118,11 +118,11 @@ int Server::receive(char * data) return length; } -void Server::send(Packet& packet, int userID) +void Server::send(Packet& packet, UserID user) { int bytesSent = m_Socket.send_to( boost::asio::buffer(packet.Data(), packet.Size()), - m_ConnectedUsers[userID].Endpoint, + m_ConnectedUsers[user].Endpoint, 0); // Network Debug data if (isReadingData) { @@ -224,40 +224,40 @@ void Server::checkForTimeOuts() } } -void Server::disconnect(int i) +void Server::disconnect(UserID user) { //broadcast("A player disconnected"); - LOG_INFO("User %s disconnected/timed out", m_PlayerDefinitions[i].Name.c_str()); + LOG_INFO("User %s disconnected/timed out", m_PlayerDefinitions[user].Name.c_str()); // Remove enteties and stuff (When we can remove entity, remove it and tell clients to remove the copy they have) Events::PlayerDisconnected e; - e.Entity = m_PlayerDefinitions[i].EntityID; - e.PlayerID = i; + e.Entity = m_PlayerDefinitions[user].EntityID; + e.PlayerID = user; m_EventBroker->Publish(e); - m_PlayerDefinitions[i].Endpoint = boost::asio::ip::udp::endpoint(); - m_PlayerDefinitions[i].EntityID = -1; - m_PlayerDefinitions[i].Name = ""; - m_PlayerDefinitions[i].PacketID = 0; - m_ConnectedUsers.erase(m_ConnectedUsers.begin() + i); + m_PlayerDefinitions[user].Endpoint = boost::asio::ip::udp::endpoint(); + m_PlayerDefinitions[user].EntityID = -1; + m_PlayerDefinitions[user].Name = ""; + m_PlayerDefinitions[user].PacketID = 0; + m_ConnectedUsers.erase(m_ConnectedUsers.begin() + user); } void Server::parseOnInputCommand(Packet& packet) { - int playerID = -1; + PlayerID player = -1; // Check which player it was who sent the message for (int i = 0; i < m_MaxConnections; i++) { // if the player is connected set playerID to the correct PlayerID if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() && m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { - playerID = i; + player = i; break; } } - if (playerID != -1) { + if (player != -1) { while (packet.DataReadSize() < packet.Size()) { Events::InputCommand e; e.Command = packet.ReadString(); - e.PlayerID = playerID; // Set correct player id + e.PlayerID = player; // Set correct player id e.Value = packet.ReadPrimitive(); m_EventBroker->Publish(e); //LOG_INFO("Server::parseOnInputCommand: Command is %s. Value is %f. PlayerID is %i.", e.Command.c_str(), e.Value, e.PlayerID); @@ -322,12 +322,12 @@ void Server::parseDisconnect() void Server::parseClientPing() { LOG_INFO("%i: Parsing ping", m_PacketID); - int playerID = GetPlayerIDFromEndpoint(m_ReceiverEndpoint); - if (playerID == -1) { + PlayerID player = GetPlayerIDFromEndpoint(m_ReceiverEndpoint); + if (player == -1) { return; } // Return ping - Packet packet(MessageType::Ping, m_PlayerDefinitions[playerID].PacketID); + Packet packet(MessageType::Ping, m_PlayerDefinitions[player].PacketID); packet.WriteString("Ping received"); send(packet); } @@ -358,7 +358,7 @@ void Server::createPlayer() LOG_WARNING("Already connected!"); return; } - int userIndex; + UserID userIndex; for (userIndex = 0; userIndex < m_ConnectedUsers.size(); userIndex++) { if (m_ConnectedUsers[userIndex].Endpoint.address() == m_ReceiverEndpoint.address() && m_ConnectedUsers[userIndex].Endpoint.port() == m_ReceiverEndpoint.port()) { @@ -370,7 +370,7 @@ void Server::createPlayer() LOG_WARNING("Not a recognized user!"); return; } - for (int playerIndex = 0; playerIndex < m_MaxConnections; playerIndex++) { + for (PlayerID playerIndex = 0; playerIndex < m_MaxConnections; playerIndex++) { if (m_PlayerDefinitions[playerIndex].Endpoint.address() == boost::asio::ip::address()) { m_PlayerDefinitions[playerIndex] = m_ConnectedUsers[userIndex]; EntityID entityID = m_World->CreateEntity(); @@ -388,7 +388,14 @@ void Server::createPlayer() } -int Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) +void Server::kick(PlayerID player) +{ + disconnect(player); + Packet packet = Packet(MessageType::Kick); + send(packet); +} + +PlayerID Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) { for (int i = 0; i < m_MaxConnections; i++) { if (m_PlayerDefinitions[i].Endpoint.address() == endpoint.address() && @@ -409,5 +416,9 @@ bool Server::OnInputCommand(const Events::InputCommand & e) isReadingData = !isReadingData; m_SaveDataTimer = std::clock(); } + if (e.Command == "KickPlayer" && e.Value > 0) { + kick(0); + } + return true; } From 2b8debbfff98fac69eba9a850e3805c97dcbeab9 Mon Sep 17 00:00:00 2001 From: Tleety Date: Fri, 22 Jan 2016 15:55:32 +0100 Subject: [PATCH 169/224] Added MipMap texture generation --- include/Engine/Rendering/DrawFinalPass.h | 1 + src/Engine/Rendering/DrawFinalPass.cpp | 18 +++++++++++++++++- 2 files changed, 18 insertions(+), 1 deletion(-) diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index e4c714ef..540ce49a 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -27,6 +27,7 @@ public: private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; + void GenerateMipMapTexture(GLuint* texture, GLenum wrapping, glm::vec2 dimensions, GLint format, GLenum type, GLint numMipMaps) const; Texture* m_WhiteTexture; Texture* m_BlackTexture; diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index a31beee6..ba1b4c59 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -23,7 +23,9 @@ void DrawFinalPass::InitializeFrameBuffers() glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); GenerateTexture(&m_SceneTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + GenerateMipMapTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_FLOAT, 4); m_BloomFrameBuffer.AddResource(std::shared_ptr(new RenderBuffer(&m_DepthBuffer, GL_DEPTH_ATTACHMENT))); m_BloomFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); @@ -104,3 +106,17 @@ void DrawFinalPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum fil glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, dimensions.x, dimensions.y, 0, format, type, nullptr);//TODO: Renderer: Fix the precision and Resolution GLERROR("Texture initialization failed"); } + +void DrawFinalPass::GenerateMipMapTexture(GLuint* texture, GLenum wrapping, glm::vec2 dimensions, GLint format, GLenum type, GLint numMipMaps) const +{ + glGenTextures(1, texture); + glBindTexture(GL_TEXTURE_2D, *texture); + glTexStorage2D(GL_TEXTURE_2D, numMipMaps, GL_RGBA8, dimensions.x, dimensions.y); + glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, dimensions.x, dimensions.y, format, type, texture); + glGenerateMipmap(GL_TEXTURE_2D); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); + GLERROR("MipMap Texture initialization failed"); +} From ca2aab449e340af9968dd97c1f39a6706876e511 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Fri, 22 Jan 2016 16:12:51 +0100 Subject: [PATCH 170/224] Basic movement and camera management between players and editor --- assets | 2 +- include/Engine/Core/EntityWrapper.h | 1 + include/Engine/Core/Transform.h | 5 + .../Editor/EditorCameraInputController.h | 98 ++++++++++++++ include/Engine/Editor/EditorSystem.h | 19 ++- include/Engine/Input/EInputCommand.h | 2 +- .../Engine/Input/FirstPersonInputController.h | 33 ++++- .../Rendering/DebugCameraInputController.h | 84 ------------ include/Engine/Rendering/RenderSystem.h | 1 - include/Game/Systems/PlayerMovementSystem.h | 18 ++- include/Game/Systems/PlayerSpawnSystem.h | 1 + resources/DefaultConfig.ini | 4 +- resources/Schema/Components/Player.xml | 6 +- resources/Schema/Components/Player.xsd | 6 +- resources/Schema/Entities/CollidableCube.xml | 15 +++ resources/Schema/Entities/MovementTest.xml | 125 +++++++++++++----- resources/Schema/Entities/Player.xml | 61 +++++++-- resources/Schema/Types.xsd | 3 + src/Engine/Core/EntityWrapper.cpp | 16 +++ src/Engine/Core/Transform.cpp | 20 +++ src/Engine/Editor/EditorSystem.cpp | 86 +++++++++--- src/Engine/Rendering/RenderSystem.cpp | 9 +- src/Game/Systems/PlayerMovementSystem.cpp | 52 +++++++- src/Game/Systems/PlayerSpawnSystem.cpp | 8 ++ 24 files changed, 499 insertions(+), 176 deletions(-) create mode 100644 include/Engine/Editor/EditorCameraInputController.h delete mode 100644 include/Engine/Rendering/DebugCameraInputController.h create mode 100644 resources/Schema/Entities/CollidableCube.xml diff --git a/assets b/assets index 6ffb46e1..2a800ea9 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 6ffb46e155c8f013241cd1507098c94900ec2448 +Subproject commit 2a800ea92b323646432c65217d55aab6750d5a72 diff --git a/include/Engine/Core/EntityWrapper.h b/include/Engine/Core/EntityWrapper.h index 3ba4e087..d0e5e31f 100644 --- a/include/Engine/Core/EntityWrapper.h +++ b/include/Engine/Core/EntityWrapper.h @@ -25,6 +25,7 @@ struct EntityWrapper bool HasComponent(const std::string& componentName); EntityWrapper Parent(); + EntityWrapper FirstChildByName(const std::string& name); bool Valid(); ComponentWrapper operator[](const char* componentName); diff --git a/include/Engine/Core/Transform.h b/include/Engine/Core/Transform.h index 474a7bdb..3b0811c9 100644 --- a/include/Engine/Core/Transform.h +++ b/include/Engine/Core/Transform.h @@ -3,13 +3,18 @@ #include "../GLM.h" #include "World.h" +#include "EntityWrapper.h" namespace Transform { +glm::vec3 AbsolutePosition(EntityWrapper entity); glm::vec3 AbsolutePosition(World* world, EntityID entity); +glm::quat AbsoluteOrientation(EntityWrapper entity); glm::quat AbsoluteOrientation(World* world, EntityID entity); +glm::vec3 AbsoluteScale(EntityWrapper entity); glm::vec3 AbsoluteScale(World* world, EntityID entity); +glm::mat4 ModelMatrix(EntityWrapper entity); glm::mat4 ModelMatrix(EntityID entity, World* world); } diff --git a/include/Engine/Editor/EditorCameraInputController.h b/include/Engine/Editor/EditorCameraInputController.h new file mode 100644 index 00000000..c12113c7 --- /dev/null +++ b/include/Engine/Editor/EditorCameraInputController.h @@ -0,0 +1,98 @@ +#ifndef EditorCameraInputController_h__ +#define EditorCameraInputController_h__ + +#include +#include "../Input/FirstPersonInputController.h" +#include "../Core/EMousePress.h" +#include "../Core/EMouseRelease.h" +#include "../Core/EMouseScroll.h" +#include "../Core/ConfigFile.h" + +template +class EditorCameraInputController : public FirstPersonInputController +{ +public: + EditorCameraInputController(EventBroker* eventBroker, unsigned int playerID) + : FirstPersonInputController(eventBroker, playerID) + { + EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorCameraInputController::OnMousePress); + EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorCameraInputController::OnMouseRelease); + EVENT_SUBSCRIBE_MEMBER(m_EMouseScroll, &EditorCameraInputController::OnMouseScroll); + + m_Config = ResourceManager::Load("Config.ini"); + m_SpeedMultiplier = m_Config->Get("Editor.CameraSpeed", 3.f); + } + + virtual const glm::vec3 Movement() const override + { + return m_Movement * m_SpeedMultiplier; + } + + virtual bool OnCommand(const Events::InputCommand& e) override + { + ImGuiIO& io = ImGui::GetIO(); + if (glm::abs(e.Value) > 0 && (io.WantCaptureKeyboard || io.WantCaptureMouse)) { + return false; + } + + if (e.Command == "Jump") { + if (e.Value > 0) { + m_Movement.y = glm::max(e.Value, 1.f); + } else { + m_Movement.y = 0.f; + } + } + + if (e.Command == "Crouch") { + if (e.Value > 0) { + m_Movement.y = glm::min(-e.Value, -1.f); + } else { + m_Movement.y = 0.f; + } + } + + if (e.Command == "Sprint") { + if (e.Value > 0) { + m_SpeedMultiplier *= 2.f; + } else { + m_SpeedMultiplier /= 2.f; + } + } + + return FirstPersonInputController::OnCommand(e); + } + +protected: + ConfigFile* m_Config; + float m_SpeedMultiplier = 1.f; + + EventRelay m_EMousePress; + bool OnMousePress(const Events::MousePress& e) + { + if (e.Button == GLFW_MOUSE_BUTTON_2) { + ImGuiIO& io = ImGui::GetIO(); + if (!io.WantCaptureMouse) { + LockMouse(); + } + } + return true; + } + EventRelay m_EMouseRelease; + bool OnMouseRelease(const Events::MouseRelease& e) + { + if (e.Button == GLFW_MOUSE_BUTTON_2) { + UnlockMouse(); + } + return true; + } + EventRelay m_EMouseScroll; + bool OnMouseScroll(const Events::MouseScroll& e) + { + m_SpeedMultiplier += e.DeltaY * (0.1f * m_SpeedMultiplier); + m_Config->Set("Editor.CameraSpeed", m_SpeedMultiplier); + m_Config->SaveToDisk(); + return true; + } +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Editor/EditorSystem.h b/include/Engine/Editor/EditorSystem.h index b354ddf3..2db24ba3 100644 --- a/include/Engine/Editor/EditorSystem.h +++ b/include/Engine/Editor/EditorSystem.h @@ -1,7 +1,6 @@ #include "../Core/System.h" #include "../Rendering/IRenderer.h" #include "../Rendering/Camera.h" -#include "../Rendering/DebugCameraInputController.h" #include "../Rendering/ESetCamera.h" #include "../Core/World.h" #include "../Core/SystemPipeline.h" @@ -10,8 +9,10 @@ #include "../Core/EntityFileParser.h" #include "../Core/EntityFileWriter.h" #include "../Core/EMousePress.h" +#include "../Input/EInputCommand.h" #include "EditorGUI.h" #include "EditorStats.h" +#include "EditorCameraInputController.h" class EditorSystem : public ImpureSystem { @@ -21,18 +22,24 @@ public: void Update(double dt); + void Enable(); + void Disable(); + private: IRenderer* m_Renderer; RenderFrame* m_RenderFrame; World* m_EditorWorld; SystemPipeline* m_EditorWorldSystemPipeline; - Camera* m_EditorCamera; - EntityWrapper m_Camera = EntityWrapper::Invalid; - DebugCameraInputController* m_DebugCameraInputController; + //Camera* m_EditorCamera; + EntityWrapper m_EditorCamera = EntityWrapper::Invalid; + EntityWrapper m_ActualCamera = EntityWrapper::Invalid; + EditorCameraInputController* m_EditorCameraInputController; EditorGUI* m_EditorGUI; EditorStats* m_EditorStats; // State + double m_LastTime = 0.f; + bool m_Enabled = true; EditorGUI::WidgetMode m_WidgetMode = EditorGUI::WidgetMode::Translate; EntityWrapper m_Widget = EntityWrapper::Invalid; EntityWrapper m_CurrentSelection = EntityWrapper::Invalid; @@ -56,4 +63,8 @@ private: bool OnMousePress(const Events::MousePress& e); EventRelay m_EWidgetDelta; bool OnWidgetDelta(const Events::WidgetDelta& e); + EventRelay m_EInputCommand; + bool OnInputCommand(const Events::InputCommand& e); + EventRelay m_ESetCamera; + bool OnSetCamera(const Events::SetCamera& e); }; \ No newline at end of file diff --git a/include/Engine/Input/EInputCommand.h b/include/Engine/Input/EInputCommand.h index 9ec897d3..1e150786 100644 --- a/include/Engine/Input/EInputCommand.h +++ b/include/Engine/Input/EInputCommand.h @@ -9,7 +9,7 @@ namespace Events struct InputCommand : Event { /** Numerical ID of the player. */ - unsigned int PlayerID; + int PlayerID; /** The command that was sent. */ std::string Command; /** The value of the command. */ diff --git a/include/Engine/Input/FirstPersonInputController.h b/include/Engine/Input/FirstPersonInputController.h index d8584494..91445534 100644 --- a/include/Engine/Input/FirstPersonInputController.h +++ b/include/Engine/Input/FirstPersonInputController.h @@ -9,7 +9,7 @@ template class FirstPersonInputController : public InputController { public: - FirstPersonInputController(EventBroker* eventBroker, unsigned int playerID) + FirstPersonInputController(EventBroker* eventBroker, int playerID) : InputController(eventBroker) , m_PlayerID(playerID) { @@ -17,7 +17,8 @@ public: EVENT_SUBSCRIBE_MEMBER(m_EUnlockMouse, &FirstPersonInputController::OnUnlockMouse); } - const glm::quat Orientation() const { return m_Orientation; } + virtual const glm::vec3 Movement() const { return m_Movement; } + virtual const glm::vec3 Orientation() const { return m_Orientation; } void LockMouse() { @@ -42,24 +43,44 @@ public: if (m_MouseLocked) { if (e.Command == "Pitch") { float val = glm::radians(e.Value); - m_Orientation = m_Orientation * glm::angleAxis(-val, glm::vec3(1, 0, 0)); + m_Orientation.x += -val; + m_Orientation.x = glm::clamp(m_Orientation.x, -glm::half_pi(), glm::half_pi()); + //m_Orientation = m_Orientation * glm::angleAxis(-val, glm::vec3(1.f, 0, 0)); return true; } if (e.Command == "Yaw") { float val = glm::radians(e.Value); - m_Orientation = glm::angleAxis(-val, glm::vec3(0, 1, 0)) * m_Orientation; + m_Orientation.y += -val; + //m_Orientation = glm::angleAxis(-val, glm::vec3(0, 1.f, 0)) * m_Orientation; return true; } } + if (e.Command == "Forward" || e.Command == "Right") { + if (e.Command == "Forward") { + float val = glm::clamp(e.Value, -1.f, 1.f); + m_Movement.z = -val; + return true; + } + if (e.Command == "Right") { + float val = glm::clamp(e.Value, -1.f, 1.f); + m_Movement.x = val; + return true; + } + if (glm::length2(m_Movement) > 0) { + m_Movement = glm::normalize(m_Movement); + } + } + return false; } protected: - const unsigned int m_PlayerID; - glm::quat m_Orientation; + const int m_PlayerID; bool m_MouseLocked = false; + glm::vec3 m_Orientation; + glm::vec3 m_Movement; EventRelay m_ELockMouse; bool OnLockMouse(const Events::LockMouse& e) { m_MouseLocked = true; return true; } diff --git a/include/Engine/Rendering/DebugCameraInputController.h b/include/Engine/Rendering/DebugCameraInputController.h deleted file mode 100644 index 5ce85b3f..00000000 --- a/include/Engine/Rendering/DebugCameraInputController.h +++ /dev/null @@ -1,84 +0,0 @@ -#ifndef DebugCameraInputController_h__ -#define DebugCameraInputController_h__ - -#include -#include "../Input/FirstPersonInputController.h" -#include "../Core/EMousePress.h" -#include "../Core/EMouseRelease.h" - -template -class DebugCameraInputController : public FirstPersonInputController -{ -public: - DebugCameraInputController(EventBroker* eventBroker, unsigned int playerID) - : FirstPersonInputController(eventBroker, playerID) - { - EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &DebugCameraInputController::OnMousePress); - EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &DebugCameraInputController::OnMouseRelease); - } - - void SetPosition(const glm::vec3 position) { m_Position = position; } - void SetOrientation(const glm::quat orientation) { m_Orientation = orientation; } - - const glm::vec3 Position() const { return m_Position; } - void SetBaseSpeed(float speed) { m_BaseSpeed = speed; } - - virtual bool OnCommand(const Events::InputCommand& e) override - { - ImGuiIO& io = ImGui::GetIO(); - - if (!io.WantCaptureKeyboard) { - if (e.Command == "Right") { - float value = std::max(-1.f, std::min(e.Value, 1.f)); - m_Velocity.x = value; - } - if (e.Command == "Forward") { - float value = std::max(-1.f, std::min(e.Value, 1.f)); - m_Velocity.z = -value; - } - if (e.Command == "Sprint") { - if (e.Value > 0.f) { - m_Speed = m_BaseSpeed * 2.f * (e.Value); - } else { - m_Speed = m_BaseSpeed; - } - } - } - - return FirstPersonInputController::OnCommand(e); - } - - void Update(double dt) - { - if (glm::length2(m_Velocity) > 0) { - m_Position += m_Orientation * (glm::normalize(m_Velocity) * m_Speed * (float)dt); - } - } - -protected: - glm::vec3 m_Position = glm::vec3(0, 0, 0); - glm::vec3 m_Velocity = glm::vec3(0, 0, 0); - float m_BaseSpeed = 2.0f; - float m_Speed = m_BaseSpeed; - EventRelay m_EMousePress; - bool OnMousePress(const Events::MousePress& e) - { - if (e.Button == GLFW_MOUSE_BUTTON_2) { - ImGuiIO& io = ImGui::GetIO(); - if (!io.WantCaptureMouse) { - LockMouse(); - } - } - return true; - } - EventRelay m_EMouseRelease; - bool OnMouseRelease(const Events::MouseRelease& e) - { - if (e.Button == GLFW_MOUSE_BUTTON_2) { - UnlockMouse(); - } - return true; - } -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/RenderSystem.h b/include/Engine/Rendering/RenderSystem.h index 003e308e..04c394a9 100644 --- a/include/Engine/Rendering/RenderSystem.h +++ b/include/Engine/Rendering/RenderSystem.h @@ -15,7 +15,6 @@ #include "Renderer.h" #include "PointLightJob.h" #include "../Core/Transform.h" -#include "DebugCameraInputController.h" class RenderSystem : public ImpureSystem { diff --git a/include/Game/Systems/PlayerMovementSystem.h b/include/Game/Systems/PlayerMovementSystem.h index 1be61bdd..f5b6539b 100644 --- a/include/Game/Systems/PlayerMovementSystem.h +++ b/include/Game/Systems/PlayerMovementSystem.h @@ -1,14 +1,22 @@ #include "Common.h" #include "GLM.h" #include "Core/System.h" +#include "Events/EPlayerSpawned.h" +#include "Input/FirstPersonInputController.h" -class PlayerMovementSystem : public PureSystem +class PlayerMovementSystem : public ImpureSystem, PureSystem { public: - PlayerMovementSystem(World* world, EventBroker* eventBroker) - : System(world, eventBroker) - , PureSystem("Player") - { } + PlayerMovementSystem(World* world, EventBroker* eventBroker); + ~PlayerMovementSystem(); + virtual void Update(double dt) override; virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt); + +private: + // State + std::unordered_map*> m_PlayerInputControllers; + + EventRelay m_EPlayerSpawned; + bool OnPlayerSpawned(Events::PlayerSpawned& e); }; \ No newline at end of file diff --git a/include/Game/Systems/PlayerSpawnSystem.h b/include/Game/Systems/PlayerSpawnSystem.h index 69014f65..9e9ce0be 100644 --- a/include/Game/Systems/PlayerSpawnSystem.h +++ b/include/Game/Systems/PlayerSpawnSystem.h @@ -3,6 +3,7 @@ #include "Systems/SpawnerSystem.h" #include "Events/ESpawnerSpawn.h" #include "Events/EPlayerSpawned.h" +#include "Rendering/ESetCamera.h" class PlayerSpawnSystem : public ImpureSystem { diff --git a/resources/DefaultConfig.ini b/resources/DefaultConfig.ini index fb490ec8..7e7dc08c 100644 --- a/resources/DefaultConfig.ini +++ b/resources/DefaultConfig.ini @@ -1,11 +1,13 @@ [Debug] LogLevel=1 LoadMap= -EditorEnabled=false ; if true -> Pool allocation is not used when calling Allocate/Free, just use regular dynamic allocation. ; if false -> Use pool allocation. DisableMemoryPool=false +[Editor] +CameraSpeed=3 + [Video] Fullscreen=false VSYNC=false diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index caefd6e6..a9ecc6be 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,8 +1,4 @@ - - false - false - false - false + 0.2 \ No newline at end of file diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 1a315a35..89c4a398 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -9,11 +9,7 @@ - - - - - + diff --git a/resources/Schema/Entities/CollidableCube.xml b/resources/Schema/Entities/CollidableCube.xml new file mode 100644 index 00000000..ebba54be --- /dev/null +++ b/resources/Schema/Entities/CollidableCube.xml @@ -0,0 +1,15 @@ + + + + + + + + Models/Core/UnitCube.obj + + + + + + + diff --git a/resources/Schema/Entities/MovementTest.xml b/resources/Schema/Entities/MovementTest.xml index 93b4d374..9ea1ae68 100644 --- a/resources/Schema/Entities/MovementTest.xml +++ b/resources/Schema/Entities/MovementTest.xml @@ -6,14 +6,7 @@ - - - - - - - - + @@ -22,46 +15,116 @@ - - + + - + - - - - - - - - Models/Assault.obj - - - + + + Schema/Entities/Player.xml + + + + + + - + + + + + + + + + Models/Assault.obj + + + + + + + + + + + + + Models/Assault.obj + + + + + + + + + + + + + + + Models/DirectionalLightWidget.obj + + + + - + + + + Models/Test/ObstacleCourse.obj + + + + + + - - - Models/Core/UnitCube.obj - - - - + + + + + + + + + + + + Models/Core/UnitCube.obj + + + + + + + + + + + + + + Models/Core/UnitCube.obj + + + + diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 6c3b39c3..087b1f7e 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -2,17 +2,60 @@ - - + + + + - - Models/Core/UnitSphere.obj - - - - + + + 3 + + + + + - + + + + + + Models/Camera.obj + false + + + + + + + + + + + + + Models/Camera.obj + + + + + + + + + + + + Models/Assault.obj + + + + + + + + diff --git a/resources/Schema/Types.xsd b/resources/Schema/Types.xsd index fb584c64..8d9bf289 100644 --- a/resources/Schema/Types.xsd +++ b/resources/Schema/Types.xsd @@ -16,6 +16,9 @@ + + + diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 98b9c7d4..6177d91d 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -17,6 +17,22 @@ EntityWrapper EntityWrapper::Parent() } } +EntityWrapper EntityWrapper::FirstChildByName(const std::string& name) +{ + auto itPair = this->World->GetChildren(this->ID); + if (itPair.first == itPair.second) { + return EntityWrapper::Invalid; + } + + for (auto it = itPair.first; it != itPair.second; ++it) { + if (this->World->GetName(it->second) == name) { + return EntityWrapper(this->World, it->second); + } + } + + return EntityWrapper::Invalid; +} + bool EntityWrapper::Valid() { if (this->World == nullptr) { diff --git a/src/Engine/Core/Transform.cpp b/src/Engine/Core/Transform.cpp index cbc405a3..c9869014 100644 --- a/src/Engine/Core/Transform.cpp +++ b/src/Engine/Core/Transform.cpp @@ -1,5 +1,10 @@ #include "Core/Transform.h" +glm::vec3 Transform::AbsolutePosition(EntityWrapper entity) +{ + return AbsolutePosition(entity.World, entity.ID); +} + glm::vec3 Transform::AbsolutePosition(World* world, EntityID entity) { glm::vec3 position; @@ -14,6 +19,11 @@ glm::vec3 Transform::AbsolutePosition(World* world, EntityID entity) return position; } +glm::quat Transform::AbsoluteOrientation(EntityWrapper entity) +{ + return AbsoluteOrientation(entity.World, entity.ID); +} + glm::quat Transform::AbsoluteOrientation(World* world, EntityID entity) { glm::quat orientation; @@ -27,6 +37,11 @@ glm::quat Transform::AbsoluteOrientation(World* world, EntityID entity) return orientation; } +glm::vec3 Transform::AbsoluteScale(EntityWrapper entity) +{ + return AbsoluteScale(entity.World, entity.ID); +} + glm::vec3 Transform::AbsoluteScale(World* world, EntityID entity) { glm::vec3 scale(1.f); @@ -40,6 +55,11 @@ glm::vec3 Transform::AbsoluteScale(World* world, EntityID entity) return scale; } +glm::mat4 Transform::ModelMatrix(EntityWrapper entity) +{ + return ModelMatrix(entity.ID, entity.World); +} + glm::mat4 Transform::ModelMatrix(EntityID entity, World* world) { glm::vec3 position = Transform::AbsolutePosition(world, entity); diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 35b8a361..a357a542 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -14,10 +14,11 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re m_EditorWorldSystemPipeline->AddSystem(0, m_Renderer); m_EditorWorldSystemPipeline->AddSystem(1, m_Renderer, m_RenderFrame); - m_Camera = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/Empty.xml"); - m_EditorWorld->AttachComponent(m_Camera.ID, "Transform"); - m_EditorWorld->AttachComponent(m_Camera.ID, "Camera"); - m_DebugCameraInputController = new DebugCameraInputController(m_EventBroker, -1); + m_EditorCamera = importEntity(EntityWrapper(m_EditorWorld, EntityID_Invalid), "Schema/Entities/Empty.xml"); + m_ActualCamera = m_EditorCamera; + m_EditorWorld->AttachComponent(m_EditorCamera.ID, "Transform"); + m_EditorWorld->AttachComponent(m_EditorCamera.ID, "Camera"); + m_EditorCameraInputController = new EditorCameraInputController(m_EventBroker, -1); m_EditorGUI = new EditorGUI(m_World, m_EventBroker); m_EditorGUI->SetEntitySelectedCallback(std::bind(&EditorSystem::OnEntitySelected, this, std::placeholders::_1)); @@ -33,38 +34,66 @@ EditorSystem::EditorSystem(World* world, EventBroker* eventBroker, IRenderer* re EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorSystem::OnMousePress); EVENT_SUBSCRIBE_MEMBER(m_EWidgetDelta, &EditorSystem::OnWidgetDelta); + EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &EditorSystem::OnInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_ESetCamera, &EditorSystem::OnSetCamera); m_EditorStats = new EditorStats(); - Events::SetCamera e; - e.CameraEntity = m_Camera; - m_EventBroker->Publish(e); + if (m_Enabled) { + Enable(); + } } EditorSystem::~EditorSystem() { delete m_EditorStats; delete m_EditorGUI; - delete m_DebugCameraInputController; + delete m_EditorCameraInputController; delete m_EditorWorldSystemPipeline; delete m_EditorWorld; } void EditorSystem::Update(double dt) { - m_EventBroker->Process(); - m_EditorGUI->Draw(); - m_EditorStats->Draw(dt); + double now = glfwGetTime(); + double actualDelta = now - m_LastTime; + m_LastTime = now; - if (m_CurrentSelection.Valid() && m_Widget.Valid()) { - (glm::vec3&)m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(m_CurrentSelection.World, m_CurrentSelection.ID); + if (m_Enabled) { + m_EventBroker->Process(); + m_EditorGUI->Draw(); + m_EditorStats->Draw(actualDelta); + + if (m_CurrentSelection.Valid() && m_Widget.Valid()) { + (glm::vec3&)m_Widget["Transform"]["Position"] = Transform::AbsolutePosition(m_CurrentSelection.World, m_CurrentSelection.ID); + } + + m_EditorWorldSystemPipeline->Update(actualDelta); + + ComponentWrapper& cameraTransform = m_EditorCamera["Transform"]; + glm::vec3& ori = cameraTransform["Orientation"]; + ori.x = m_EditorCameraInputController->Orientation().x; + ori.y = m_EditorCameraInputController->Orientation().y; + glm::vec3& pos = cameraTransform["Position"]; + pos += m_EditorCameraInputController->Movement() * glm::inverse(glm::quat(ori)) * (float)actualDelta; } +} - m_EditorWorldSystemPipeline->Update(dt); +void EditorSystem::Enable() +{ + Events::SetCamera e; + e.CameraEntity = m_EditorCamera; + m_EventBroker->Publish(e); + (glm::vec3&)m_EditorCamera["Transform"]["Position"] = Transform::AbsolutePosition(m_ActualCamera); + m_Enabled = true; +} - m_DebugCameraInputController->Update(dt); - m_Camera["Transform"]["Position"] = m_DebugCameraInputController->Position(); - m_Camera["Transform"]["Orientation"] = glm::eulerAngles(m_DebugCameraInputController->Orientation()); +void EditorSystem::Disable() +{ + Events::SetCamera e; + e.CameraEntity = m_ActualCamera; + m_EventBroker->Publish(e); + m_Enabled = false; } void EditorSystem::OnEntitySelected(EntityWrapper entity) @@ -148,6 +177,29 @@ bool EditorSystem::OnWidgetDelta(const Events::WidgetDelta& e) return true; } +bool EditorSystem::OnInputCommand(const Events::InputCommand& e) +{ + if (e.Command == "ToggleEditor" && e.Value > 0) { + if (m_Enabled) { + Disable(); + } else { + Enable(); + } + } + return true; +} + +bool EditorSystem::OnSetCamera(const Events::SetCamera& e) +{ + if (m_Enabled && e.CameraEntity != m_EditorCamera) { + m_ActualCamera = e.CameraEntity; + Events::SetCamera e2; + e2.CameraEntity = m_EditorCamera; + m_EventBroker->Publish(e2); + } + return true; +} + EntityWrapper EditorSystem::importEntity(EntityWrapper parent, boost::filesystem::path filePath) { if (parent.World == nullptr) { diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 80b6696c..6eedc34c 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -119,11 +119,12 @@ void RenderSystem::Update(double dt) { m_EventBroker->Process(); - if (m_CurrentCamera) { - ComponentWrapper cameraTransform = m_CurrentCamera["Transform"]; - m_Camera->SetPosition(cameraTransform["Position"]); - m_Camera->SetOrientation(glm::quat((const glm::vec3&)cameraTransform["Orientation"])); + // Update the current camera used for rendering + if (m_CurrentCamera.Valid()) { + m_Camera->SetPosition(Transform::AbsolutePosition(m_CurrentCamera)); + m_Camera->SetOrientation(Transform::AbsoluteOrientation(m_CurrentCamera)); } + //Only supports opaque geometry atm RenderScene scene; diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index e14cd146..351acad5 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -1,5 +1,45 @@ #include "Systems/PlayerMovementSystem.h" +PlayerMovementSystem::PlayerMovementSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) + , PureSystem("Player") +{ + EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &PlayerMovementSystem::OnPlayerSpawned); +} + +PlayerMovementSystem::~PlayerMovementSystem() +{ + for (auto& kv : m_PlayerInputControllers) { + delete kv.second; + } +} + +void PlayerMovementSystem::Update(double dt) +{ + for (auto& kv : m_PlayerInputControllers) { + EntityWrapper player = kv.first; + auto& controller = kv.second; + + if (!player.Valid()) { + continue; + } + + EntityWrapper cameraEntity = player.FirstChildByName("Camera"); + if (cameraEntity.Valid()) { + glm::vec3& cameraOrientation = cameraEntity["Transform"]["Orientation"]; + cameraOrientation.x = controller->Orientation().x; + } + + ComponentWrapper& cTransform = player["Transform"]; + glm::vec3& ori = cTransform["Orientation"]; + ori.y = controller->Orientation().y; + + glm::vec3& pos = cTransform["Position"]; + pos += controller->Movement() * glm::inverse(glm::quat(ori)) * (float)player["Player"]["MovementSpeed"] * (float)dt; + + } +} + void PlayerMovementSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { ComponentWrapper& cTransform = entity["Transform"]; @@ -10,9 +50,17 @@ void PlayerMovementSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapp glm::vec3& velocity = cPhysics["Velocity"]; if (cPhysics["Gravity"]) { - velocity.y -= 9.82 * dt; + velocity.y -= 9.82f * (float)dt; } glm::vec3& position = cTransform["Position"]; position += velocity * (float)dt; -} \ No newline at end of file +} + +bool PlayerMovementSystem::OnPlayerSpawned(Events::PlayerSpawned& e) +{ + // When a player spawns, create an input controller for them + m_PlayerInputControllers[e.Player] = new FirstPersonInputController(m_EventBroker, e.PlayerID); + + return true; +} diff --git a/src/Game/Systems/PlayerSpawnSystem.cpp b/src/Game/Systems/PlayerSpawnSystem.cpp index 11be0486..0763fa9c 100644 --- a/src/Game/Systems/PlayerSpawnSystem.cpp +++ b/src/Game/Systems/PlayerSpawnSystem.cpp @@ -38,6 +38,14 @@ void PlayerSpawnSystem::Update(double dt) e.Player = player; e.Spawner = spawner; m_EventBroker->Publish(e); + + // Set the camera to the correct entity + EntityWrapper cameraEntity = player.FirstChildByName("Camera"); + if (cameraEntity.Valid()) { + Events::SetCamera e; + e.CameraEntity = cameraEntity; + m_EventBroker->Publish(e); + } } } m_SpawnRequests.clear(); From 74d9bae8968d2775b87c1bb49016e49c5188bbed Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Fri, 22 Jan 2016 17:34:57 +0100 Subject: [PATCH 171/224] Added conditional spawning based on whether the running instance is a server or not --- include/Game/Systems/PlayerSpawnSystem.h | 8 +++++-- src/Game/Systems/PlayerSpawnSystem.cpp | 29 ++++++++++++++++++------ 2 files changed, 28 insertions(+), 9 deletions(-) diff --git a/include/Game/Systems/PlayerSpawnSystem.h b/include/Game/Systems/PlayerSpawnSystem.h index 9e9ce0be..6c0f6ce3 100644 --- a/include/Game/Systems/PlayerSpawnSystem.h +++ b/include/Game/Systems/PlayerSpawnSystem.h @@ -4,6 +4,7 @@ #include "Events/ESpawnerSpawn.h" #include "Events/EPlayerSpawned.h" #include "Rendering/ESetCamera.h" +#include "Core/ConfigFile.h" class PlayerSpawnSystem : public ImpureSystem { @@ -19,8 +20,11 @@ private: ComponentInfo::EnumType Team; }; + bool m_NetworkEnabled = false; + std::vector m_SpawnRequests; + EventRelay m_OnInputCommand; bool OnInputCommand(const Events::InputCommand& e); - - std::vector m_SpawnRequests; + EventRelay m_OnPlayerSpawnerd; + bool OnPlayerSpawned(Events::PlayerSpawned& e); }; \ No newline at end of file diff --git a/src/Game/Systems/PlayerSpawnSystem.cpp b/src/Game/Systems/PlayerSpawnSystem.cpp index 0763fa9c..f18808cc 100644 --- a/src/Game/Systems/PlayerSpawnSystem.cpp +++ b/src/Game/Systems/PlayerSpawnSystem.cpp @@ -4,6 +4,8 @@ PlayerSpawnSystem::PlayerSpawnSystem(World* m_World, EventBroker* eventBroker) : System(m_World, eventBroker) { EVENT_SUBSCRIBE_MEMBER(m_OnInputCommand, &PlayerSpawnSystem::OnInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_OnPlayerSpawnerd, &PlayerSpawnSystem::OnPlayerSpawned); + m_NetworkEnabled = ResourceManager::Load("Config.ini")->Get("Networking.StartNetwork", false); } void PlayerSpawnSystem::Update(double dt) @@ -39,13 +41,6 @@ void PlayerSpawnSystem::Update(double dt) e.Spawner = spawner; m_EventBroker->Publish(e); - // Set the camera to the correct entity - EntityWrapper cameraEntity = player.FirstChildByName("Camera"); - if (cameraEntity.Valid()) { - Events::SetCamera e; - e.CameraEntity = cameraEntity; - m_EventBroker->Publish(e); - } } } m_SpawnRequests.clear(); @@ -57,6 +52,12 @@ bool PlayerSpawnSystem::OnInputCommand(const Events::InputCommand& e) return false; } + // Team picks should be processed ONLY server-side! + // Don't make a spawn request if PlayerID is -1, i.e. we're the client. + if (e.PlayerID == -1 && m_NetworkEnabled) { + return false; + } + if (e.Value != 0) { SpawnRequest req; req.PlayerID = e.PlayerID; @@ -67,3 +68,17 @@ bool PlayerSpawnSystem::OnInputCommand(const Events::InputCommand& e) return true; } +bool PlayerSpawnSystem::OnPlayerSpawned(Events::PlayerSpawned& e) +{ + // When a player is actually spawned (since the actual spawning is handled on the server) + + // Set the camera to the correct entity + EntityWrapper cameraEntity = e.Player.FirstChildByName("Camera"); + if (cameraEntity.Valid()) { + Events::SetCamera e; + e.CameraEntity = cameraEntity; + m_EventBroker->Publish(e); + } + + return true; +} \ No newline at end of file From 389e057611105eb97a34dbbe6f1121e39199002d Mon Sep 17 00:00:00 2001 From: stiffly Date: Fri, 22 Jan 2016 17:49:21 +0100 Subject: [PATCH 172/224] EPlayerSpawned special logic added to server and client. --- include/Engine/Network/Client.h | 2 ++ include/Engine/Network/MessageType.h | 13 +++++++------ include/Engine/Network/Server.h | 5 +++++ src/Engine/Network/Client.cpp | 12 ++++++++++++ src/Engine/Network/Server.cpp | 23 +++++++++++++++++++++++ 5 files changed, 49 insertions(+), 6 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 4a16034b..9717d22f 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -20,6 +20,7 @@ #include "Input/EInputCommand.h" #include "Core/EPlayerDamage.h" #include "Network/EInterpolate.h" +#include "Game/Events/EPlayerSpawned.h" class Client : public Network { @@ -77,6 +78,7 @@ private: void parsePlayerConnected(Packet& packet); void parsePing(); void parseKick(); + void parsePlayersSpawned(Packet& packet); void InterpolateFields(Packet & packet, const ComponentInfo & componentInfo, const EntityID & entityID, const std::string & componentType); void parseSnapshot(Packet& packet); void identifyPacketLoss(); diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index 7d8094de..13ac5e9d 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -5,16 +5,17 @@ // Used to determine what type of message was sent. enum class MessageType { - Connect, - Disconnect, - Ping, - Message, - Snapshot, + Connect, + Disconnect, + Ping, + Message, + Snapshot, OnInputCommand, OnPlayerDamage, PlayerConnected, BecomePlayer, - Kick + Kick, + OnPlayerSpawned }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index cbad08b0..cf649dba 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -16,6 +16,8 @@ #include "Core/EPlayerDamage.h" #include "Network/EPlayerDisconnected.h" +#include "Game/Events/EPlayerSpawned.h" + class Server : public Network { public: @@ -58,6 +60,7 @@ private: int receive(char* data); void readFromClients(); void send(Packet& packet, UserID user); + void send(Packet& packet, PlayerID player); void send(Packet& packet); void broadcast(Packet& packet); void sendSnapshot(); @@ -78,6 +81,8 @@ private: // Debug event EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); + EventRelay m_EPlayerSpawned; + bool OnPlayerSpawned(const Events::PlayerSpawned& e); }; #endif diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 129e0b42..fb5c3573 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -92,6 +92,9 @@ void Client::parseMessageType(Packet& packet) case MessageType::Kick: parseKick(); break; + case MessageType::OnPlayerSpawned: + parsePlayersSpawned(); + break; default: break; } @@ -129,6 +132,15 @@ void Client::parseKick() m_IsConnected = false; } +void Client::parsePlayersSpawned(Packet& packet) +{ + Events::PlayerSpawned e; + e.Player = EntityWrapper(m_World, m_ServerIDToClientID[packet.ReadPrimitive()]); + e.Spawner = EntityWrapper(m_World, m_ServerIDToClientID[packet.ReadPrimitive()]); + e.PlayerID = -1; + m_EventBroker->Publish(e); +} + // Fields with strings will not work right now void Client::InterpolateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType) { diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 03b9775a..6f3c6f3a 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -132,6 +132,20 @@ void Server::send(Packet& packet, UserID user) } } +void Server::send(Packet& packet, PlayerID player) +{ + int bytesSent = m_Socket.send_to( + boost::asio::buffer(packet.Data(), packet.Size()), + m_PlayerDefinitions[player].Endpoint, + 0); + // Network Debug data + if (isReadingData) { + m_NetworkData.TotalDataSent += packet.Size(); + m_NetworkData.DataSentThisInterval += packet.Size(); + m_NetworkData.AmountOfMessagesSent++; + } +} + void Server::send(Packet & packet) { m_Socket.send_to( @@ -422,3 +436,12 @@ bool Server::OnInputCommand(const Events::InputCommand & e) return true; } + +bool Server::OnPlayerSpawned(const Events::PlayerSpawned & e) +{ + Packet packet = Packet(MessageType::OnPlayerSpawned); + packet.WritePrimitive(e.Player.ID); + packet.WritePrimitive(e.Spawner.ID); + send(packet, e.PlayerID); + return false; +} From b37b20b7d8e755af4d8c2518cd4a1d1f0e27b7d4 Mon Sep 17 00:00:00 2001 From: stiffly Date: Fri, 22 Jan 2016 17:57:31 +0100 Subject: [PATCH 173/224] Didn't bulid lol. Fixed. --- include/Engine/Network/Server.h | 2 +- src/Engine/Network/Client.cpp | 2 +- src/Engine/Network/Server.cpp | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index cf649dba..91ea5d21 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -60,7 +60,7 @@ private: int receive(char* data); void readFromClients(); void send(Packet& packet, UserID user); - void send(Packet& packet, PlayerID player); + void send(PlayerID player, Packet& packet); void send(Packet& packet); void broadcast(Packet& packet); void sendSnapshot(); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index fb5c3573..98aeb9a8 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -93,7 +93,7 @@ void Client::parseMessageType(Packet& packet) parseKick(); break; case MessageType::OnPlayerSpawned: - parsePlayersSpawned(); + parsePlayersSpawned(packet); break; default: break; diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 6f3c6f3a..b16a6850 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -132,7 +132,7 @@ void Server::send(Packet& packet, UserID user) } } -void Server::send(Packet& packet, PlayerID player) +void Server::send(PlayerID player, Packet& packet) { int bytesSent = m_Socket.send_to( boost::asio::buffer(packet.Data(), packet.Size()), @@ -442,6 +442,6 @@ bool Server::OnPlayerSpawned(const Events::PlayerSpawned & e) Packet packet = Packet(MessageType::OnPlayerSpawned); packet.WritePrimitive(e.Player.ID); packet.WritePrimitive(e.Spawner.ID); - send(packet, e.PlayerID); + send(e.PlayerID, packet); return false; } From 406b730ef33e3c74d96ecd9bf264b8c520849fe4 Mon Sep 17 00:00:00 2001 From: stiffly Date: Fri, 22 Jan 2016 19:07:20 +0100 Subject: [PATCH 174/224] Sends entity names. Temporarily --- src/Engine/Network/Client.cpp | 5 +++++ src/Engine/Network/Server.cpp | 6 +++++- 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 98aeb9a8..1dd2bd04 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -89,6 +89,7 @@ void Client::parseMessageType(Packet& packet) break; case MessageType::PlayerConnected: parsePlayerConnected(packet); + break; case MessageType::Kick: parseKick(); break; @@ -177,8 +178,12 @@ void Client::parseSnapshot(Packet& packet) { std::string componentType = packet.ReadString(); while (packet.DataReadSize() < packet.Size()) { + // HACK + std::string entityName = packet.ReadString(); // Components EntityID EntityID receivedEntityID = packet.ReadPrimitive(); + // HACK + m_World->SetName(receivedEntityID, entityName); // Parents EntityID EntityID receivedParentEntityID = packet.ReadPrimitive(); ComponentInfo componentInfo = m_World->GetComponents(componentType)->ComponentInfo(); diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index b16a6850..9d0a83d9 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -1,6 +1,6 @@ #include "Network/Server.h" -Server::Server() : m_Socket(m_IOService, boost::asio::ip::udp::endpoint(boost::asio::ip::udp::v4(), 13)) +Server::Server() : m_Socket(m_IOService, boost::asio::ip::udp::endpoint(boost::asio::ip::udp::v4(), 27666)) { Network::initialize(); ConfigFile* config = ResourceManager::Load("Config.ini"); @@ -20,6 +20,7 @@ void Server::Start(World* world, EventBroker* eventBroker) m_EventBroker = eventBroker; // Subscribe to events EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Server::OnInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &Server::OnPlayerSpawned); for (size_t i = 0; i < m_MaxConnections; i++) { m_PlayerDefinitions[i].StopTime = std::clock(); } @@ -180,9 +181,12 @@ void Server::sendSnapshot() Packet packet(MessageType::Snapshot); ComponentPool* componentPool = it.second; ComponentInfo componentInfo = componentPool->ComponentInfo(); + // Component Type packet.WriteString(componentInfo.Name); for (auto& componentWrapper : *componentPool) { + // HACK: Send entity name + packet.WriteString(m_World->GetName(componentWrapper.EntityID)); // Components EntityID packet.WritePrimitive(componentWrapper.EntityID); // Parents EntityID From 55ee2bb3bf1b7ee13a50a86683c517f3a9a0204c Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Fri, 22 Jan 2016 21:35:31 +0100 Subject: [PATCH 175/224] Player input properly separated from editor input and server --- .../Editor/EditorCameraInputController.h | 25 ++++++++++--- .../Engine/Input/FirstPersonInputController.h | 35 ++++++++++--------- src/Engine/Editor/EditorSystem.cpp | 12 +++++-- src/Game/Systems/PlayerMovementSystem.cpp | 7 ++-- 4 files changed, 54 insertions(+), 25 deletions(-) diff --git a/include/Engine/Editor/EditorCameraInputController.h b/include/Engine/Editor/EditorCameraInputController.h index c12113c7..82e8b337 100644 --- a/include/Engine/Editor/EditorCameraInputController.h +++ b/include/Engine/Editor/EditorCameraInputController.h @@ -23,13 +23,17 @@ public: m_SpeedMultiplier = m_Config->Get("Editor.CameraSpeed", 3.f); } - virtual const glm::vec3 Movement() const override - { - return m_Movement * m_SpeedMultiplier; - } + virtual const glm::vec3 Movement() const override { return m_Movement * m_SpeedMultiplier; } + + void Enable() { m_Enabled = true; } + void Disable() { m_Enabled = false; } virtual bool OnCommand(const Events::InputCommand& e) override { + if (!m_MouseLocked) { + return false; + } + ImGuiIO& io = ImGui::GetIO(); if (glm::abs(e.Value) > 0 && (io.WantCaptureKeyboard || io.WantCaptureMouse)) { return false; @@ -64,11 +68,16 @@ public: protected: ConfigFile* m_Config; + bool m_Enabled = false; float m_SpeedMultiplier = 1.f; EventRelay m_EMousePress; bool OnMousePress(const Events::MousePress& e) { + if (!m_Enabled) { + return false; + } + if (e.Button == GLFW_MOUSE_BUTTON_2) { ImGuiIO& io = ImGui::GetIO(); if (!io.WantCaptureMouse) { @@ -80,6 +89,10 @@ protected: EventRelay m_EMouseRelease; bool OnMouseRelease(const Events::MouseRelease& e) { + if (!m_Enabled) { + return false; + } + if (e.Button == GLFW_MOUSE_BUTTON_2) { UnlockMouse(); } @@ -88,6 +101,10 @@ protected: EventRelay m_EMouseScroll; bool OnMouseScroll(const Events::MouseScroll& e) { + if (!m_Enabled) { + return false; + } + m_SpeedMultiplier += e.DeltaY * (0.1f * m_SpeedMultiplier); m_Config->Set("Editor.CameraSpeed", m_SpeedMultiplier); m_Config->SaveToDisk(); diff --git a/include/Engine/Input/FirstPersonInputController.h b/include/Engine/Input/FirstPersonInputController.h index 91445534..cd80fb21 100644 --- a/include/Engine/Input/FirstPersonInputController.h +++ b/include/Engine/Input/FirstPersonInputController.h @@ -18,7 +18,7 @@ public: } virtual const glm::vec3 Movement() const { return m_Movement; } - virtual const glm::vec3 Orientation() const { return m_Orientation; } + virtual const glm::vec3 Rotation() const { return m_Rotation; } void LockMouse() { @@ -40,21 +40,19 @@ public: return false; } - if (m_MouseLocked) { - if (e.Command == "Pitch") { - float val = glm::radians(e.Value); - m_Orientation.x += -val; - m_Orientation.x = glm::clamp(m_Orientation.x, -glm::half_pi(), glm::half_pi()); - //m_Orientation = m_Orientation * glm::angleAxis(-val, glm::vec3(1.f, 0, 0)); - return true; - } + if (e.Command == "Pitch") { + float val = glm::radians(e.Value); + m_Rotation.x += -val; + m_Rotation.x = glm::clamp(m_Rotation.x, -glm::half_pi(), glm::half_pi()); + //m_Rotation = m_Rotation * glm::angleAxis(-val, glm::vec3(1.f, 0, 0)); + return true; + } - if (e.Command == "Yaw") { - float val = glm::radians(e.Value); - m_Orientation.y += -val; - //m_Orientation = glm::angleAxis(-val, glm::vec3(0, 1.f, 0)) * m_Orientation; - return true; - } + if (e.Command == "Yaw") { + float val = glm::radians(e.Value); + m_Rotation.y += -val; + //m_Rotation = glm::angleAxis(-val, glm::vec3(0, 1.f, 0)) * m_Rotation; + return true; } if (e.Command == "Forward" || e.Command == "Right") { @@ -75,11 +73,16 @@ public: return false; } + + virtual void Reset() + { + m_Rotation = glm::vec3(0.f, 0.f, 0.f); + } protected: const int m_PlayerID; bool m_MouseLocked = false; - glm::vec3 m_Orientation; + glm::vec3 m_Rotation; glm::vec3 m_Movement; EventRelay m_ELockMouse; diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index a357a542..9c0e2e47 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -72,8 +72,8 @@ void EditorSystem::Update(double dt) ComponentWrapper& cameraTransform = m_EditorCamera["Transform"]; glm::vec3& ori = cameraTransform["Orientation"]; - ori.x = m_EditorCameraInputController->Orientation().x; - ori.y = m_EditorCameraInputController->Orientation().y; + ori.x = m_EditorCameraInputController->Rotation().x; + ori.y = m_EditorCameraInputController->Rotation().y; glm::vec3& pos = cameraTransform["Position"]; pos += m_EditorCameraInputController->Movement() * glm::inverse(glm::quat(ori)) * (float)actualDelta; } @@ -81,6 +81,8 @@ void EditorSystem::Update(double dt) void EditorSystem::Enable() { + m_EditorCameraInputController->Enable(); + m_EventBroker->Publish(Events::UnlockMouse()); Events::SetCamera e; e.CameraEntity = m_EditorCamera; m_EventBroker->Publish(e); @@ -90,6 +92,8 @@ void EditorSystem::Enable() void EditorSystem::Disable() { + m_EditorCameraInputController->Disable(); + m_EventBroker->Publish(Events::LockMouse()); Events::SetCamera e; e.CameraEntity = m_ActualCamera; m_EventBroker->Publish(e); @@ -179,6 +183,10 @@ bool EditorSystem::OnWidgetDelta(const Events::WidgetDelta& e) bool EditorSystem::OnInputCommand(const Events::InputCommand& e) { + if (e.PlayerID != -1) { + return false; + } + if (e.Command == "ToggleEditor" && e.Value > 0) { if (m_Enabled) { Disable(); diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index 351acad5..843601e8 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -27,16 +27,17 @@ void PlayerMovementSystem::Update(double dt) EntityWrapper cameraEntity = player.FirstChildByName("Camera"); if (cameraEntity.Valid()) { glm::vec3& cameraOrientation = cameraEntity["Transform"]["Orientation"]; - cameraOrientation.x = controller->Orientation().x; + cameraOrientation.x += controller->Rotation().x; } ComponentWrapper& cTransform = player["Transform"]; glm::vec3& ori = cTransform["Orientation"]; - ori.y = controller->Orientation().y; + ori.y += controller->Rotation().y; glm::vec3& pos = cTransform["Position"]; pos += controller->Movement() * glm::inverse(glm::quat(ori)) * (float)player["Player"]["MovementSpeed"] * (float)dt; - + + controller->Reset(); } } From 3ac3311c0c5342459d81270772eb6bbcbd008f43 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 00:37:47 +0100 Subject: [PATCH 176/224] "inline" caused missing symbol when compiling in Release for some reason --- include/Engine/Core/Octree.h | 2 +- src/Engine/Core/Octree.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/Engine/Core/Octree.h b/include/Engine/Core/Octree.h index bbd27b3c..8bac5503 100644 --- a/include/Engine/Core/Octree.h +++ b/include/Engine/Core/Octree.h @@ -111,7 +111,7 @@ struct Child std::vector& m_StaticObjectsRef; std::vector& m_DynamicObjectsRef; - inline bool hasChildren() const; + bool hasChildren() const; int childIndexContainingPoint(const glm::vec3& point) const; std::vector childIndicesContainingBox(const AABB& box) const; }; diff --git a/src/Engine/Core/Octree.cpp b/src/Engine/Core/Octree.cpp index d7feba45..18effea5 100644 --- a/src/Engine/Core/Octree.cpp +++ b/src/Engine/Core/Octree.cpp @@ -276,7 +276,7 @@ std::vector Child::childIndicesContainingBox(const AABB& box) const } } -inline bool Child::hasChildren() const +bool Child::hasChildren() const { return m_Children[0] != nullptr; } From 31e7340daf4ebd0993a17bb229105b17f4f08a7e Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 00:40:18 +0100 Subject: [PATCH 177/224] Ignoring interpolation and rendering for local player entities! --- assets | 2 +- .../Editor/EditorCameraInputController.h | 2 +- include/Engine/Rendering/RenderSystem.h | 5 ++ include/Game/Systems/InterpolationSystem.h | 13 ++--- resources/Schema/Entities/Player.xml | 47 +++++++++++++++---- src/Engine/Core/EntityWrapper.cpp | 3 ++ src/Engine/Rendering/RenderSystem.cpp | 35 +++++++++++++- src/Game/Systems/InterpolationSystem.cpp | 29 ++++++++++-- 8 files changed, 113 insertions(+), 23 deletions(-) diff --git a/assets b/assets index 2a800ea9..e8174f63 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 2a800ea92b323646432c65217d55aab6750d5a72 +Subproject commit e8174f630fc3242e15ada1346b42c72f44cbc854 diff --git a/include/Engine/Editor/EditorCameraInputController.h b/include/Engine/Editor/EditorCameraInputController.h index 82e8b337..66c7952a 100644 --- a/include/Engine/Editor/EditorCameraInputController.h +++ b/include/Engine/Editor/EditorCameraInputController.h @@ -30,7 +30,7 @@ public: virtual bool OnCommand(const Events::InputCommand& e) override { - if (!m_MouseLocked) { + if (glm::abs(e.Value) > 0 && !m_MouseLocked) { return false; } diff --git a/include/Engine/Rendering/RenderSystem.h b/include/Engine/Rendering/RenderSystem.h index ef824ea5..4c23c6c6 100644 --- a/include/Engine/Rendering/RenderSystem.h +++ b/include/Engine/Rendering/RenderSystem.h @@ -15,6 +15,7 @@ #include "Renderer.h" #include "PointLightJob.h" #include "../Core/Transform.h" +#include "../../Game/Events/EPlayerSpawned.h" class RenderSystem : public ImpureSystem { @@ -29,6 +30,7 @@ private: RenderFrame* m_RenderFrame; Camera* m_Camera; EntityWrapper m_CurrentCamera = EntityWrapper::Invalid; + EntityWrapper m_LocalPlayer = EntityWrapper::Invalid; EventRelay m_ESetCamera; bool OnSetCamera(Events::SetCamera &event); @@ -40,6 +42,9 @@ private: void fillModels(std::list>& jobs); void fillLight(std::list>& jobs); + + EventRelay m_EPlayerSpawned; + bool OnPlayerSpawned(Events::PlayerSpawned& e); }; #endif \ No newline at end of file diff --git a/include/Game/Systems/InterpolationSystem.h b/include/Game/Systems/InterpolationSystem.h index 0e137598..707c0acf 100644 --- a/include/Game/Systems/InterpolationSystem.h +++ b/include/Game/Systems/InterpolationSystem.h @@ -12,6 +12,7 @@ #include "Core/EventBroker.h" #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" +#include "Events/EPlayerSpawned.h" #include "Network/EInterpolate.h" @@ -25,19 +26,13 @@ class InterpolationSystem : public PureSystem double interpolationTime; }; public: - InterpolationSystem(World* world, EventBroker* eventBroker) - : System(world, eventBroker) - , PureSystem("Transform") - { - ConfigFile* config = ResourceManager::Load("Config.ini"); - m_SnapshotInterval = config->Get("Networking.SnapshotInterval", 0.05); - EVENT_SUBSCRIBE_MEMBER(m_EInterpolate, &InterpolationSystem::OnInterpolate); - } + InterpolationSystem(World* world, EventBroker* eventBroker); ~InterpolationSystem() { } virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& transform, double dt) override; private: std::unordered_map m_NextTransform; std::unordered_map m_LastReceivedTransform; + EntityWrapper m_LocalPlayer = EntityWrapper::Invalid; //glm::vec3 vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime); template @@ -51,6 +46,8 @@ private: EventRelay m_EInterpolate; bool InterpolationSystem::OnInterpolate(const Events::Interpolate& e); + EventRelay m_EPlayerSpawned; + bool OnPlayerSpawned(Events::PlayerSpawned& e); }; #endif diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 087b1f7e..fa8b7686 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -11,9 +11,13 @@ 3 + + + + + - - + @@ -21,22 +25,47 @@ - - Models/Camera.obj - false - - + - + + + + + + Fonts/DroidSans.ttf,100 + + + + + + + + + + + + + + Models/Camera.obj + + + + + + + + + Models/Camera.obj + false @@ -48,7 +77,7 @@ - Models/Assault.obj + Models/AssaultHeadless.obj diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 6177d91d..2f9c17db 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -5,6 +5,9 @@ const EntityWrapper EntityWrapper::Invalid = EntityWrapper(nullptr, EntityID_Inv bool EntityWrapper::HasComponent(const std::string& componentName) { + if (!Valid()) { + return false; + } return World->HasComponent(ID, componentName); } diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 5aa0108e..a478bb43 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -7,6 +7,7 @@ RenderSystem::RenderSystem(World* world, EventBroker* eventBroker, const IRender { EVENT_SUBSCRIBE_MEMBER(m_ESetCamera, &RenderSystem::OnSetCamera); EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &RenderSystem::OnInputCommand); + EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &RenderSystem::OnPlayerSpawned); m_Camera = new Camera((float)m_Renderer->Resolution().Width / m_Renderer->Resolution().Height, glm::radians(45.f), 0.01f, 5000.f); } @@ -46,6 +47,18 @@ void RenderSystem::fillModels(std::list>& jobs) continue; } + EntityWrapper entity(m_World, modelComponent.EntityID); + bool isLocalPlayer = entity == m_LocalPlayer; + while (entity.Parent().Valid()) { + entity = entity.Parent(); + if (entity == m_LocalPlayer) { + isLocalPlayer = true; + } + } + if (isLocalPlayer) { + continue; + } + Model* model; try { model = ResourceManager::Load<::Model, true>(resource); @@ -68,6 +81,14 @@ void RenderSystem::fillModels(std::list>& jobs) } } +bool RenderSystem::OnPlayerSpawned(Events::PlayerSpawned& e) +{ + if (e.PlayerID == -1) { + m_LocalPlayer = e.Player; + } + return true; +} + void RenderSystem::fillPointLights(std::list>& jobs, World* world) { auto pointLights = m_World->GetComponents("PointLight"); @@ -128,6 +149,18 @@ void RenderSystem::fillText(std::list>& jobs, World* continue; } + EntityWrapper entity(m_World, textComponent.EntityID); + bool isLocalPlayer = entity == m_LocalPlayer; + while (entity.Parent().Valid()) { + entity = entity.Parent(); + if (entity == m_LocalPlayer) { + isLocalPlayer = true; + } + } + if (isLocalPlayer) { + continue; + } + Font* font; try { font = ResourceManager::Load(resource); @@ -169,7 +202,7 @@ void RenderSystem::Update(double dt) fillModels(scene.ForwardJobs); fillPointLights(scene.PointLightJobs, m_World); fillDirectionalLights(scene.DirectionalLightJobs, m_World); - fillText(scene.TextJobs, world); + fillText(scene.TextJobs, m_World); m_RenderFrame->Add(scene); } \ No newline at end of file diff --git a/src/Game/Systems/InterpolationSystem.cpp b/src/Game/Systems/InterpolationSystem.cpp index be2c9a4f..84f50456 100644 --- a/src/Game/Systems/InterpolationSystem.cpp +++ b/src/Game/Systems/InterpolationSystem.cpp @@ -1,5 +1,15 @@ #include "Systems/InterpolationSystem.h" +InterpolationSystem::InterpolationSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) + , PureSystem("Transform") +{ + ConfigFile* config = ResourceManager::Load("Config.ini"); + m_SnapshotInterval = config->Get("Networking.SnapshotInterval", 0.05); + EVENT_SUBSCRIBE_MEMBER(m_EInterpolate, &InterpolationSystem::OnInterpolate); + EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &InterpolationSystem::OnPlayerSpawned); +} + void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& transform, double dt) { if (m_NextTransform.find(transform.EntityID) != m_NextTransform.end()) { // Exists in map @@ -17,14 +27,21 @@ void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrappe } } if (transform.Info.Name == "Transform") { + bool isLocalPlayer = entity == m_LocalPlayer || entity.Parent() == m_LocalPlayer; // Position glm::vec3 nextPosition = sTransform.Position; glm::vec3 currentPosition = static_cast(transform["Position"]); + if (isLocalPlayer && glm::length(nextPosition - currentPosition) < 1.f) { + return; + } (glm::vec3&)transform["Position"] += vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); // Orientation - glm::quat nextOrientation = sTransform.Orientation; - glm::quat currentOrientation = glm::quat(static_cast(transform["Orientation"])); - (glm::vec3&)transform["Orientation"] = glm::eulerAngles(glm::slerp(currentOrientation, nextOrientation, sTransform.interpolationTime / m_SnapshotInterval)); + //bool isPlayer = entity.HasComponent("Player") || entity.Parent().HasComponent("Player"); + if (!isLocalPlayer) { + glm::quat nextOrientation = sTransform.Orientation; + glm::quat currentOrientation = glm::quat(static_cast(transform["Orientation"])); + (glm::vec3&)transform["Orientation"] = glm::eulerAngles(glm::slerp(currentOrientation, nextOrientation, sTransform.interpolationTime / m_SnapshotInterval)); + } // Scale glm::vec3 nextScale = sTransform.Scale; glm::vec3 currentScale = static_cast(transform["Scale"]); @@ -33,6 +50,12 @@ void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrappe } } +bool InterpolationSystem::OnPlayerSpawned(Events::PlayerSpawned& e) +{ + m_LocalPlayer = e.Player; + return true; +} + bool InterpolationSystem::OnInterpolate(const Events::Interpolate & e) { Transform transform; From 445248af5558c56ffd2f7ca3df9d9c348c1523be Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sat, 23 Jan 2016 11:38:31 +0100 Subject: [PATCH 178/224] Changed name and made a TextPassState --- assets | 2 +- include/Engine/Rendering/Renderer.h | 4 ++-- .../Rendering/{TextRenderer.h => TextPass.h} | 5 +++-- include/Engine/Rendering/TextPassState.h | 15 +++++++++++++++ src/Engine/Rendering/Renderer.cpp | 2 +- .../{TextRenderer.cpp => TextPass.cpp} | 19 ++++++++----------- src/Engine/Rendering/TextPassState.cpp | 16 ++++++++++++++++ 7 files changed, 46 insertions(+), 17 deletions(-) rename include/Engine/Rendering/{TextRenderer.h => TextPass.h} (91%) create mode 100644 include/Engine/Rendering/TextPassState.h rename src/Engine/Rendering/{TextRenderer.cpp => TextPass.cpp} (85%) create mode 100644 src/Engine/Rendering/TextPassState.cpp diff --git a/assets b/assets index b6592dbb..e8174f63 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit b6592dbb0216bbac00ccea43a0afd0e27d0b185e +Subproject commit e8174f630fc3242e15ada1346b42c72f44cbc854 diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 0e8c70ec..875fa616 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -19,7 +19,7 @@ #include "Camera.h" #include "../Core/Transform.h" -#include "TextRenderer.h" +#include "TextPass.h" class Renderer : public IRenderer { @@ -37,7 +37,7 @@ public: private: //----------------------Variables----------------------// EventBroker* m_EventBroker; - TextRenderer* m_TextRenderer; + TextPass* m_TextRenderer; Texture* m_ErrorTexture; Texture* m_WhiteTexture; diff --git a/include/Engine/Rendering/TextRenderer.h b/include/Engine/Rendering/TextPass.h similarity index 91% rename from include/Engine/Rendering/TextRenderer.h rename to include/Engine/Rendering/TextPass.h index cdc1d8c7..eaace1c2 100644 --- a/include/Engine/Rendering/TextRenderer.h +++ b/include/Engine/Rendering/TextPass.h @@ -10,11 +10,12 @@ #include "Font.h" #include "../Core/ResourceManager.h" #include "RenderQueue.h" +#include "TextPassState.h" -class TextRenderer +class TextPass { public: - TextRenderer(); + TextPass(); void Initialize(); void Update(); void Draw(RenderScene& scene); diff --git a/include/Engine/Rendering/TextPassState.h b/include/Engine/Rendering/TextPassState.h new file mode 100644 index 00000000..9bc25f26 --- /dev/null +++ b/include/Engine/Rendering/TextPassState.h @@ -0,0 +1,15 @@ +#ifndef TextPassState_h__ +#define TextPassState_h__ + +#include "Rendering/RenderState.h" + +class TextPassState : public RenderState +{ +public: + TextPassState(); + ~TextPassState(); +private: + +}; + +#endif \ No newline at end of file diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 4a2b30f6..02a986ad 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -9,7 +9,7 @@ void Renderer::Initialize() glfwSwapInterval(m_VSYNC); InitializeShaders(); InitializeTextures(); - m_TextRenderer = new TextRenderer(); + m_TextRenderer = new TextPass(); m_TextRenderer->Initialize(); diff --git a/src/Engine/Rendering/TextRenderer.cpp b/src/Engine/Rendering/TextPass.cpp similarity index 85% rename from src/Engine/Rendering/TextRenderer.cpp rename to src/Engine/Rendering/TextPass.cpp index a8dfc083..6b05d7fb 100644 --- a/src/Engine/Rendering/TextRenderer.cpp +++ b/src/Engine/Rendering/TextPass.cpp @@ -1,11 +1,11 @@ -#include "Rendering/TextRenderer.h" +#include "Rendering/TextPass.h" -TextRenderer::TextRenderer() +TextPass::TextPass() { } -void TextRenderer::Initialize() +void TextPass::Initialize() { glGenVertexArrays(1, &VAO); glGenBuffers(1, &VBO); @@ -24,12 +24,12 @@ void TextRenderer::Initialize() m_TextProgram->Link(); } -void TextRenderer::Update() +void TextPass::Update() { } -void TextRenderer::Draw(RenderScene& scene) +void TextPass::Draw(RenderScene& scene) { for (auto &job : scene.TextJobs) { auto textJob = std::dynamic_pointer_cast(job); @@ -40,11 +40,11 @@ void TextRenderer::Draw(RenderScene& scene) } } -void TextRenderer::renderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) +void TextPass::renderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) { GLfloat penX = 0; GLfloat penY = 0; - float scale = 1.0/font->FontSize; + GLfloat scale = 1.0/font->FontSize; GLfloat stringWidth = 0.f; @@ -61,10 +61,7 @@ void TextRenderer::renderText(std::string text, Font* font, TextJob::AlignmentEn penX = 0; } - glEnable(GL_BLEND); - glDisable(GL_CULL_FACE); - glEnable(GL_DEPTH_TEST); - glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + TextPassState state; m_TextProgram->Bind(); glUniform3f(glGetUniformLocation(m_TextProgram->GetHandle(), "textColor"), color.x, color.y, color.z); diff --git a/src/Engine/Rendering/TextPassState.cpp b/src/Engine/Rendering/TextPassState.cpp new file mode 100644 index 00000000..e81f7b7c --- /dev/null +++ b/src/Engine/Rendering/TextPassState.cpp @@ -0,0 +1,16 @@ +#include "Rendering/TextPassState.h" + + +TextPassState::TextPassState() +{ + BindFramebuffer(0); + glEnable(GL_BLEND); + glDisable(GL_CULL_FACE); + glEnable(GL_DEPTH_TEST); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); +} + +TextPassState::~TextPassState() +{ + +} From e4513376bbf5050747091bfb0dcfcb0075a8bdc5 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sat, 23 Jan 2016 11:39:10 +0100 Subject: [PATCH 179/224] fixup! Changed name and made a TextPassState --- src/Engine/Rendering/Renderer.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 02a986ad..ce853acc 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -9,8 +9,8 @@ void Renderer::Initialize() glfwSwapInterval(m_VSYNC); InitializeShaders(); InitializeTextures(); - m_TextRenderer = new TextPass(); - m_TextRenderer->Initialize(); + m_TextPass = new TextPass(); + m_TextPass->Initialize(); m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); @@ -89,7 +89,7 @@ void Renderer::Update(double dt) { m_EventBroker->Process(); InputUpdate(dt); - m_TextRenderer->Update(); + m_TextPass->Update(); m_ImGuiRenderPass->Update(dt); } @@ -113,7 +113,7 @@ void Renderer::Draw(RenderFrame& frame) GLERROR("Renderer::Draw m_DrawScenePass->Draw"); - m_TextRenderer->Draw(*scene); + m_TextPass->Draw(*scene); } From db0e67b9bd39093d5a2046ae1e6c28c77f18ce77 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 11:44:16 +0100 Subject: [PATCH 180/224] Added EntityWrapper::IsChildOf and made snapshot interpolation and rendering exceptions for player less hacky --- .../Events => Engine/Core}/EPlayerSpawned.h | 0 include/Engine/Core/EntityWrapper.h | 1 + include/Engine/Rendering/RenderSystem.h | 2 +- include/Game/Systems/InterpolationSystem.h | 2 +- src/Engine/Core/EntityWrapper.cpp | 12 ++++++++++ src/Engine/Rendering/RenderSystem.cpp | 23 +++---------------- src/Game/Systems/InterpolationSystem.cpp | 5 ++-- 7 files changed, 21 insertions(+), 24 deletions(-) rename include/{Game/Events => Engine/Core}/EPlayerSpawned.h (100%) diff --git a/include/Game/Events/EPlayerSpawned.h b/include/Engine/Core/EPlayerSpawned.h similarity index 100% rename from include/Game/Events/EPlayerSpawned.h rename to include/Engine/Core/EPlayerSpawned.h diff --git a/include/Engine/Core/EntityWrapper.h b/include/Engine/Core/EntityWrapper.h index d0e5e31f..711f5045 100644 --- a/include/Engine/Core/EntityWrapper.h +++ b/include/Engine/Core/EntityWrapper.h @@ -26,6 +26,7 @@ struct EntityWrapper bool HasComponent(const std::string& componentName); EntityWrapper Parent(); EntityWrapper FirstChildByName(const std::string& name); + bool IsChildOf(EntityWrapper potentialParent); bool Valid(); ComponentWrapper operator[](const char* componentName); diff --git a/include/Engine/Rendering/RenderSystem.h b/include/Engine/Rendering/RenderSystem.h index 4c23c6c6..005d2eb7 100644 --- a/include/Engine/Rendering/RenderSystem.h +++ b/include/Engine/Rendering/RenderSystem.h @@ -15,7 +15,7 @@ #include "Renderer.h" #include "PointLightJob.h" #include "../Core/Transform.h" -#include "../../Game/Events/EPlayerSpawned.h" +#include "../Core/EPlayerSpawned.h" class RenderSystem : public ImpureSystem { diff --git a/include/Game/Systems/InterpolationSystem.h b/include/Game/Systems/InterpolationSystem.h index 707c0acf..1e345c91 100644 --- a/include/Game/Systems/InterpolationSystem.h +++ b/include/Game/Systems/InterpolationSystem.h @@ -12,7 +12,7 @@ #include "Core/EventBroker.h" #include "Core/ResourceManager.h" #include "Core/ConfigFile.h" -#include "Events/EPlayerSpawned.h" +#include "Core/EPlayerSpawned.h" #include "Network/EInterpolate.h" diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 2f9c17db..55d341e1 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -36,6 +36,18 @@ EntityWrapper EntityWrapper::FirstChildByName(const std::string& name) return EntityWrapper::Invalid; } +bool EntityWrapper::IsChildOf(EntityWrapper potentialParent) +{ + EntityWrapper entity = *this; + while (entity.Parent().Valid()) { + entity = entity.Parent(); + if (entity == potentialParent) { + return true; + } + } + return false; +} + bool EntityWrapper::Valid() { if (this->World == nullptr) { diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index a478bb43..a8f330f0 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -48,14 +48,9 @@ void RenderSystem::fillModels(std::list>& jobs) } EntityWrapper entity(m_World, modelComponent.EntityID); - bool isLocalPlayer = entity == m_LocalPlayer; - while (entity.Parent().Valid()) { - entity = entity.Parent(); - if (entity == m_LocalPlayer) { - isLocalPlayer = true; - } - } - if (isLocalPlayer) { + + // Don't render the local player + if (entity == m_LocalPlayer || entity.IsChildOf(m_LocalPlayer)) { continue; } @@ -149,18 +144,6 @@ void RenderSystem::fillText(std::list>& jobs, World* continue; } - EntityWrapper entity(m_World, textComponent.EntityID); - bool isLocalPlayer = entity == m_LocalPlayer; - while (entity.Parent().Valid()) { - entity = entity.Parent(); - if (entity == m_LocalPlayer) { - isLocalPlayer = true; - } - } - if (isLocalPlayer) { - continue; - } - Font* font; try { font = ResourceManager::Load(resource); diff --git a/src/Game/Systems/InterpolationSystem.cpp b/src/Game/Systems/InterpolationSystem.cpp index 84f50456..2b6e82f2 100644 --- a/src/Game/Systems/InterpolationSystem.cpp +++ b/src/Game/Systems/InterpolationSystem.cpp @@ -27,16 +27,17 @@ void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrappe } } if (transform.Info.Name == "Transform") { - bool isLocalPlayer = entity == m_LocalPlayer || entity.Parent() == m_LocalPlayer; + bool isLocalPlayer = entity == m_LocalPlayer || entity.IsChildOf(m_LocalPlayer); // Position glm::vec3 nextPosition = sTransform.Position; glm::vec3 currentPosition = static_cast(transform["Position"]); + // HACK: Hardcoded tolerance value for player position desync = 1 if (isLocalPlayer && glm::length(nextPosition - currentPosition) < 1.f) { return; } (glm::vec3&)transform["Position"] += vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); // Orientation - //bool isPlayer = entity.HasComponent("Player") || entity.Parent().HasComponent("Player"); + // Don't force orientation for players if (!isLocalPlayer) { glm::quat nextOrientation = sTransform.Orientation; glm::quat currentOrientation = glm::quat(static_cast(transform["Orientation"])); From 4d5cbb60574239816bb3e4d378b6aeb2077c0770 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 12:14:00 +0100 Subject: [PATCH 181/224] fixup! Added EntityWrapper::IsChildOf and made snapshot interpolation and rendering exceptions for player less hacky --- include/Engine/Network/Client.h | 2 +- include/Engine/Network/Server.h | 3 +-- include/Game/Systems/PlayerMovementSystem.h | 2 +- include/Game/Systems/PlayerSpawnSystem.h | 2 +- 4 files changed, 4 insertions(+), 5 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 9717d22f..92d78f4a 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -20,7 +20,7 @@ #include "Input/EInputCommand.h" #include "Core/EPlayerDamage.h" #include "Network/EInterpolate.h" -#include "Game/Events/EPlayerSpawned.h" +#include "Core/EPlayerSpawned.h" class Client : public Network { diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 91ea5d21..e7c745e7 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -15,8 +15,7 @@ #include "Input/EInputCommand.h" #include "Core/EPlayerDamage.h" #include "Network/EPlayerDisconnected.h" - -#include "Game/Events/EPlayerSpawned.h" +#include "Core/EPlayerSpawned.h" class Server : public Network { diff --git a/include/Game/Systems/PlayerMovementSystem.h b/include/Game/Systems/PlayerMovementSystem.h index f5b6539b..72f3b879 100644 --- a/include/Game/Systems/PlayerMovementSystem.h +++ b/include/Game/Systems/PlayerMovementSystem.h @@ -1,7 +1,7 @@ #include "Common.h" #include "GLM.h" #include "Core/System.h" -#include "Events/EPlayerSpawned.h" +#include "Core/EPlayerSpawned.h" #include "Input/FirstPersonInputController.h" class PlayerMovementSystem : public ImpureSystem, PureSystem diff --git a/include/Game/Systems/PlayerSpawnSystem.h b/include/Game/Systems/PlayerSpawnSystem.h index 6c0f6ce3..eb4d3c97 100644 --- a/include/Game/Systems/PlayerSpawnSystem.h +++ b/include/Game/Systems/PlayerSpawnSystem.h @@ -2,7 +2,7 @@ #include "Input/EInputCommand.h" #include "Systems/SpawnerSystem.h" #include "Events/ESpawnerSpawn.h" -#include "Events/EPlayerSpawned.h" +#include "Core/EPlayerSpawned.h" #include "Rendering/ESetCamera.h" #include "Core/ConfigFile.h" From 3aeeb3cad5e7aa3c9743e3bde3c4a27eb1eaf90d Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 11:54:03 +0100 Subject: [PATCH 182/224] Moved FirstPersonInputController implementation out of header --- .../Engine/Input/FirstPersonInputController.h | 74 ++-------------- .../Input/FirstPersonInputController.cpp | 87 +++++++++++++++++++ 2 files changed, 94 insertions(+), 67 deletions(-) create mode 100644 src/Engine/Input/FirstPersonInputController.cpp diff --git a/include/Engine/Input/FirstPersonInputController.h b/include/Engine/Input/FirstPersonInputController.h index cd80fb21..4a55bf39 100644 --- a/include/Engine/Input/FirstPersonInputController.h +++ b/include/Engine/Input/FirstPersonInputController.h @@ -9,75 +9,15 @@ template class FirstPersonInputController : public InputController { public: - FirstPersonInputController(EventBroker* eventBroker, int playerID) - : InputController(eventBroker) - , m_PlayerID(playerID) - { - EVENT_SUBSCRIBE_MEMBER(m_ELockMouse, &FirstPersonInputController::OnLockMouse); - EVENT_SUBSCRIBE_MEMBER(m_EUnlockMouse, &FirstPersonInputController::OnUnlockMouse); - } + FirstPersonInputController(EventBroker* eventBroker, int playerID); virtual const glm::vec3 Movement() const { return m_Movement; } virtual const glm::vec3 Rotation() const { return m_Rotation; } - void LockMouse() - { - Events::LockMouse e; - m_EventBroker->Publish(e); - m_MouseLocked = true; - } - - void UnlockMouse() - { - Events::UnlockMouse e; - m_EventBroker->Publish(e); - m_MouseLocked = false; - } - - virtual bool OnCommand(const Events::InputCommand& e) override - { - if (m_PlayerID != e.PlayerID) { - return false; - } - - if (e.Command == "Pitch") { - float val = glm::radians(e.Value); - m_Rotation.x += -val; - m_Rotation.x = glm::clamp(m_Rotation.x, -glm::half_pi(), glm::half_pi()); - //m_Rotation = m_Rotation * glm::angleAxis(-val, glm::vec3(1.f, 0, 0)); - return true; - } - - if (e.Command == "Yaw") { - float val = glm::radians(e.Value); - m_Rotation.y += -val; - //m_Rotation = glm::angleAxis(-val, glm::vec3(0, 1.f, 0)) * m_Rotation; - return true; - } - - if (e.Command == "Forward" || e.Command == "Right") { - if (e.Command == "Forward") { - float val = glm::clamp(e.Value, -1.f, 1.f); - m_Movement.z = -val; - return true; - } - if (e.Command == "Right") { - float val = glm::clamp(e.Value, -1.f, 1.f); - m_Movement.x = val; - return true; - } - if (glm::length2(m_Movement) > 0) { - m_Movement = glm::normalize(m_Movement); - } - } - - return false; - } - - virtual void Reset() - { - m_Rotation = glm::vec3(0.f, 0.f, 0.f); - } + void LockMouse(); + void UnlockMouse(); + virtual bool OnCommand(const Events::InputCommand& e) override; + virtual void Reset(); protected: const int m_PlayerID; @@ -86,9 +26,9 @@ protected: glm::vec3 m_Movement; EventRelay m_ELockMouse; - bool OnLockMouse(const Events::LockMouse& e) { m_MouseLocked = true; return true; } + bool OnLockMouse(const Events::LockMouse& e); EventRelay m_EUnlockMouse; - bool OnUnlockMouse(const Events::UnlockMouse& e) { m_MouseLocked = false; return true; } + bool OnUnlockMouse(const Events::UnlockMouse& e); }; #endif \ No newline at end of file diff --git a/src/Engine/Input/FirstPersonInputController.cpp b/src/Engine/Input/FirstPersonInputController.cpp new file mode 100644 index 00000000..cdacc606 --- /dev/null +++ b/src/Engine/Input/FirstPersonInputController.cpp @@ -0,0 +1,87 @@ +#include "Input/FirstPersonInputController.h" + +template +FirstPersonInputController::FirstPersonInputController(EventBroker* eventBroker, int playerID) + : InputController(eventBroker) + , m_PlayerID(playerID) +{ + EVENT_SUBSCRIBE_MEMBER(m_ELockMouse, &FirstPersonInputController::OnLockMouse); + EVENT_SUBSCRIBE_MEMBER(m_EUnlockMouse, &FirstPersonInputController::OnUnlockMouse); +} + +template +void FirstPersonInputController::Reset() +{ + m_Rotation = glm::vec3(0.f, 0.f, 0.f); +} + +template +void FirstPersonInputController::LockMouse() +{ + Events::LockMouse e; + m_EventBroker->Publish(e); + m_MouseLocked = true; +} + +template +void FirstPersonInputController::UnlockMouse() +{ + Events::UnlockMouse e; + m_EventBroker->Publish(e); + m_MouseLocked = false; +} + +template +bool FirstPersonInputController::OnCommand(const Events::InputCommand& e) +{ + if (m_PlayerID != e.PlayerID) { + return false; + } + + if (e.Command == "Pitch") { + float val = glm::radians(e.Value); + m_Rotation.x += -val; + m_Rotation.x = glm::clamp(m_Rotation.x, -glm::half_pi(), glm::half_pi()); + //m_Rotation = m_Rotation * glm::angleAxis(-val, glm::vec3(1.f, 0, 0)); + return true; + } + + if (e.Command == "Yaw") { + float val = glm::radians(e.Value); + m_Rotation.y += -val; + //m_Rotation = glm::angleAxis(-val, glm::vec3(0, 1.f, 0)) * m_Rotation; + return true; + } + + if (e.Command == "Forward" || e.Command == "Right") { + if (e.Command == "Forward") { + float val = glm::clamp(e.Value, -1.f, 1.f); + m_Movement.z = -val; + return true; + } + if (e.Command == "Right") { + float val = glm::clamp(e.Value, -1.f, 1.f); + m_Movement.x = val; + return true; + } + if (glm::length2(m_Movement) > 0) { + m_Movement = glm::normalize(m_Movement); + } + } + + return false; +} + +template +bool FirstPersonInputController::OnUnlockMouse(const Events::UnlockMouse& e) +{ + m_MouseLocked = false; + return true; +} + +template +bool FirstPersonInputController::OnLockMouse(const Events::LockMouse& e) +{ + m_MouseLocked = true; + return true; +} From 32f73201c5cc1dfca7513722889c9e332e905fdc Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 12:15:24 +0100 Subject: [PATCH 183/224] Basic jumping! --- .../Engine/Input/FirstPersonInputController.h | 93 +++++++++++++++++++ .../Input/FirstPersonInputController.cpp | 85 ----------------- src/Game/Systems/PlayerMovementSystem.cpp | 9 ++ 3 files changed, 102 insertions(+), 85 deletions(-) diff --git a/include/Engine/Input/FirstPersonInputController.h b/include/Engine/Input/FirstPersonInputController.h index 4a55bf39..426670c4 100644 --- a/include/Engine/Input/FirstPersonInputController.h +++ b/include/Engine/Input/FirstPersonInputController.h @@ -13,6 +13,8 @@ public: virtual const glm::vec3 Movement() const { return m_Movement; } virtual const glm::vec3 Rotation() const { return m_Rotation; } + virtual bool Jumping() const { return m_Jumping; } + virtual bool Crouching() const { return m_Crouching; } void LockMouse(); void UnlockMouse(); @@ -24,6 +26,8 @@ protected: bool m_MouseLocked = false; glm::vec3 m_Rotation; glm::vec3 m_Movement; + bool m_Jumping = false; + bool m_Crouching = false; EventRelay m_ELockMouse; bool OnLockMouse(const Events::LockMouse& e); @@ -31,4 +35,93 @@ protected: bool OnUnlockMouse(const Events::UnlockMouse& e); }; +template +FirstPersonInputController::FirstPersonInputController(EventBroker* eventBroker, int playerID) + : InputController(eventBroker) + , m_PlayerID(playerID) +{ + EVENT_SUBSCRIBE_MEMBER(m_ELockMouse, &FirstPersonInputController::OnLockMouse); + EVENT_SUBSCRIBE_MEMBER(m_EUnlockMouse, &FirstPersonInputController::OnUnlockMouse); +} + +template +void FirstPersonInputController::Reset() +{ + m_Rotation = glm::vec3(0.f, 0.f, 0.f); + m_Jumping = false; +} + +template +void FirstPersonInputController::LockMouse() +{ + Events::LockMouse e; + m_EventBroker->Publish(e); + m_MouseLocked = true; +} + +template +void FirstPersonInputController::UnlockMouse() +{ + Events::UnlockMouse e; + m_EventBroker->Publish(e); + m_MouseLocked = false; +} + +template +bool FirstPersonInputController::OnCommand(const Events::InputCommand& e) +{ + if (m_PlayerID != e.PlayerID) { + return false; + } + + if (e.Command == "Pitch") { + float val = glm::radians(e.Value); + m_Rotation.x += -val; + //m_Rotation.x = glm::clamp(m_Rotation.x, -glm::half_pi(), glm::half_pi()); + } + + if (e.Command == "Yaw") { + float val = glm::radians(e.Value); + m_Rotation.y += -val; + } + + if (e.Command == "Forward" || e.Command == "Right") { + if (e.Command == "Forward") { + float val = glm::clamp(e.Value, -1.f, 1.f); + m_Movement.z = -val; + } + if (e.Command == "Right") { + float val = glm::clamp(e.Value, -1.f, 1.f); + m_Movement.x = val; + } + if (glm::length2(m_Movement) > 0) { + m_Movement = glm::normalize(m_Movement); + } + } + + if (e.Command == "Jump") { + m_Jumping = e.Value > 0; + } + + if (e.Command == "Crouch") { + m_Crouching = e.Value > 0; + } + + return true; +} + +template +bool FirstPersonInputController::OnUnlockMouse(const Events::UnlockMouse& e) +{ + m_MouseLocked = false; + return true; +} + +template +bool FirstPersonInputController::OnLockMouse(const Events::LockMouse& e) +{ + m_MouseLocked = true; + return true; +} + #endif \ No newline at end of file diff --git a/src/Engine/Input/FirstPersonInputController.cpp b/src/Engine/Input/FirstPersonInputController.cpp index cdacc606..d3757dd0 100644 --- a/src/Engine/Input/FirstPersonInputController.cpp +++ b/src/Engine/Input/FirstPersonInputController.cpp @@ -1,87 +1,2 @@ #include "Input/FirstPersonInputController.h" -template -FirstPersonInputController::FirstPersonInputController(EventBroker* eventBroker, int playerID) - : InputController(eventBroker) - , m_PlayerID(playerID) -{ - EVENT_SUBSCRIBE_MEMBER(m_ELockMouse, &FirstPersonInputController::OnLockMouse); - EVENT_SUBSCRIBE_MEMBER(m_EUnlockMouse, &FirstPersonInputController::OnUnlockMouse); -} - -template -void FirstPersonInputController::Reset() -{ - m_Rotation = glm::vec3(0.f, 0.f, 0.f); -} - -template -void FirstPersonInputController::LockMouse() -{ - Events::LockMouse e; - m_EventBroker->Publish(e); - m_MouseLocked = true; -} - -template -void FirstPersonInputController::UnlockMouse() -{ - Events::UnlockMouse e; - m_EventBroker->Publish(e); - m_MouseLocked = false; -} - -template -bool FirstPersonInputController::OnCommand(const Events::InputCommand& e) -{ - if (m_PlayerID != e.PlayerID) { - return false; - } - - if (e.Command == "Pitch") { - float val = glm::radians(e.Value); - m_Rotation.x += -val; - m_Rotation.x = glm::clamp(m_Rotation.x, -glm::half_pi(), glm::half_pi()); - //m_Rotation = m_Rotation * glm::angleAxis(-val, glm::vec3(1.f, 0, 0)); - return true; - } - - if (e.Command == "Yaw") { - float val = glm::radians(e.Value); - m_Rotation.y += -val; - //m_Rotation = glm::angleAxis(-val, glm::vec3(0, 1.f, 0)) * m_Rotation; - return true; - } - - if (e.Command == "Forward" || e.Command == "Right") { - if (e.Command == "Forward") { - float val = glm::clamp(e.Value, -1.f, 1.f); - m_Movement.z = -val; - return true; - } - if (e.Command == "Right") { - float val = glm::clamp(e.Value, -1.f, 1.f); - m_Movement.x = val; - return true; - } - if (glm::length2(m_Movement) > 0) { - m_Movement = glm::normalize(m_Movement); - } - } - - return false; -} - -template -bool FirstPersonInputController::OnUnlockMouse(const Events::UnlockMouse& e) -{ - m_MouseLocked = false; - return true; -} - -template -bool FirstPersonInputController::OnLockMouse(const Events::LockMouse& e) -{ - m_MouseLocked = true; - return true; -} diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index 843601e8..10fc29f6 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -28,6 +28,8 @@ void PlayerMovementSystem::Update(double dt) if (cameraEntity.Valid()) { glm::vec3& cameraOrientation = cameraEntity["Transform"]["Orientation"]; cameraOrientation.x += controller->Rotation().x; + // Limit camera pitch so we don't break our necks + cameraOrientation.x = glm::clamp(cameraOrientation.x, -glm::half_pi(), glm::half_pi()); } ComponentWrapper& cTransform = player["Transform"]; @@ -36,6 +38,13 @@ void PlayerMovementSystem::Update(double dt) glm::vec3& pos = cTransform["Position"]; pos += controller->Movement() * glm::inverse(glm::quat(ori)) * (float)player["Player"]["MovementSpeed"] * (float)dt; + + if (player.HasComponent("Physics")) { + if (controller->Jumping()) { + glm::vec3& velocity = player["Physics"]["Velocity"]; + velocity.y += 10.f; + } + } controller->Reset(); } From 482689fd486ef4303759169e16dc3aef478ad094 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 12:16:40 +0100 Subject: [PATCH 184/224] fixup! Moved FirstPersonInputController implementation out of header --- src/Engine/Input/FirstPersonInputController.cpp | 2 -- 1 file changed, 2 deletions(-) delete mode 100644 src/Engine/Input/FirstPersonInputController.cpp diff --git a/src/Engine/Input/FirstPersonInputController.cpp b/src/Engine/Input/FirstPersonInputController.cpp deleted file mode 100644 index d3757dd0..00000000 --- a/src/Engine/Input/FirstPersonInputController.cpp +++ /dev/null @@ -1,2 +0,0 @@ -#include "Input/FirstPersonInputController.h" - From b499f4b0209c6554ecd26637ef471747c8a55802 Mon Sep 17 00:00:00 2001 From: Tleety Date: Sat, 23 Jan 2016 12:17:38 +0100 Subject: [PATCH 185/224] Fixed some rendering bugs and some code refactoring --- include/Engine/Rendering/DrawBloomPass.h | 9 ++- include/Engine/Rendering/DrawFinalPass.h | 15 +++-- include/Engine/Rendering/DrawFinalPassState.h | 2 +- include/Engine/Rendering/Renderer.h | 3 + .../Engine/Rendering/Util/CommonFunctions.h | 17 +++++ src/Engine/Rendering/DrawBloomPass.cpp | 13 ++++ src/Engine/Rendering/DrawBloomPassState.cpp | 2 - .../Rendering/DrawColorCorrectionPass.cpp | 2 +- src/Engine/Rendering/DrawFinalPass.cpp | 23 ++++--- src/Engine/Rendering/DrawFinalPassState.cpp | 6 +- src/Engine/Rendering/DrawScreenQuadPass.cpp | 1 + .../Rendering/DrawScreenQuadPassState.cpp | 4 +- src/Engine/Rendering/PickingPass.cpp | 62 +++++++++---------- src/Engine/Rendering/Renderer.cpp | 33 +++++++--- src/Engine/Rendering/Util/CommonFunctions.cpp | 2 + 15 files changed, 131 insertions(+), 63 deletions(-) create mode 100644 include/Engine/Rendering/Util/CommonFunctions.h create mode 100644 src/Engine/Rendering/Util/CommonFunctions.cpp diff --git a/include/Engine/Rendering/DrawBloomPass.h b/include/Engine/Rendering/DrawBloomPass.h index d192c73a..539d6957 100644 --- a/include/Engine/Rendering/DrawBloomPass.h +++ b/include/Engine/Rendering/DrawBloomPass.h @@ -18,14 +18,16 @@ public: void InitializeFrameBuffers(); void InitializeShaderPrograms(); void InitializeBuffers(); + void ClearBuffer(); void FillGaussianBuffer(FrameBuffer* fb); void Draw(GLuint texture); //Getters - GLuint m_GaussianTexture_horiz; - GLuint m_GaussianTexture_vert; + //Return the blurred result of the texture that was sent into draw + GLuint GaussianTexture() const { return m_GaussianTexture_vert; } + private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; @@ -37,6 +39,9 @@ private: //const LightCullingPass* m_LightCullingPass GLuint m_iterations = 9; + GLuint m_GaussianTexture_horiz; + GLuint m_GaussianTexture_vert; + FrameBuffer m_GaussianFrameBuffer_horiz; FrameBuffer m_GaussianFrameBuffer_vert; diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index 540ce49a..70c82de9 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -18,12 +18,12 @@ public: void InitializeFrameBuffers(); void InitializeShaderPrograms(); void Draw(RenderScene& scene); + void ClearBuffer(); - //Todo: Should not be public - FrameBuffer m_BloomFrameBuffer; - GLuint m_BloomTexture; - GLuint m_SceneTexture; - GLuint m_DepthBuffer; + //Return the texture that is used in later stages to apply the bloom effect + GLuint BloomTexture() const { return m_BloomTexture; } + //Return the texture with diffuse and lighting of the scene. + GLuint SceneTexture() const { return m_SceneTexture; } private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; @@ -33,6 +33,11 @@ private: Texture* m_BlackTexture; Texture* TEMP_glowTestTexture; + FrameBuffer m_FinalPassFrameBuffer; + GLuint m_BloomTexture; + GLuint m_SceneTexture; + GLuint m_DepthBuffer; + const IRenderer* m_Renderer; const LightCullingPass* m_LightCullingPass; diff --git a/include/Engine/Rendering/DrawFinalPassState.h b/include/Engine/Rendering/DrawFinalPassState.h index 72d8e392..10b840e9 100644 --- a/include/Engine/Rendering/DrawFinalPassState.h +++ b/include/Engine/Rendering/DrawFinalPassState.h @@ -6,7 +6,7 @@ class DrawFinalPassState : public RenderState { public: - DrawFinalPassState(); + DrawFinalPassState(GLuint frameBuffer); ~DrawFinalPassState(); private: diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 7d952a94..f745a9c3 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -20,6 +20,7 @@ #include "ImGuiRenderPass.h" #include "Camera.h" #include "../Core/Transform.h" +#include "imgui/imgui.h" class Renderer : public IRenderer { @@ -45,6 +46,8 @@ private: Model* m_UnitQuad; Model* m_UnitSphere; + int m_DebugTextureToDraw = 0; + PickingPass* m_PickingPass; LightCullingPass* m_LightCullingPass; ImGuiRenderPass* m_ImGuiRenderPass; diff --git a/include/Engine/Rendering/Util/CommonFunctions.h b/include/Engine/Rendering/Util/CommonFunctions.h new file mode 100644 index 00000000..b262568c --- /dev/null +++ b/include/Engine/Rendering/Util/CommonFunctions.h @@ -0,0 +1,17 @@ +#ifndef CommonFuntions_h__ +#define CommonFuntions_h__ + +#include "../../Common.h" +#include "../../OpenGL.h" +#include "../../GLM.h" + +class CommonFuntions +{ +public: + CommonFuntions() = delete; + +private: + +}; + +#endif \ No newline at end of file diff --git a/src/Engine/Rendering/DrawBloomPass.cpp b/src/Engine/Rendering/DrawBloomPass.cpp index 20e5f0c0..1ad97eb5 100644 --- a/src/Engine/Rendering/DrawBloomPass.cpp +++ b/src/Engine/Rendering/DrawBloomPass.cpp @@ -45,6 +45,19 @@ void DrawBloomPass::InitializeBuffers() m_GaussianFrameBuffer_vert.Generate(); } + +void DrawBloomPass::ClearBuffer() +{ + m_GaussianFrameBuffer_horiz.Bind(); + glClearColor(0.f, 0.f, 0.f, 0.f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + m_GaussianFrameBuffer_horiz.Unbind(); + m_GaussianFrameBuffer_vert.Bind(); + glClearColor(0.f, 0.f, 0.f, 0.f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + m_GaussianFrameBuffer_vert.Unbind(); +} + void DrawBloomPass::Draw(GLuint texture) { GLERROR("DrawBloomPass::Draw: Pre"); diff --git a/src/Engine/Rendering/DrawBloomPassState.cpp b/src/Engine/Rendering/DrawBloomPassState.cpp index d4ee4956..f9c57475 100644 --- a/src/Engine/Rendering/DrawBloomPassState.cpp +++ b/src/Engine/Rendering/DrawBloomPassState.cpp @@ -7,8 +7,6 @@ DrawBloomPassState::DrawBloomPassState() Disable(GL_BLEND); Disable(GL_DEPTH_TEST); Disable(GL_CULL_FACE); - ClearColor(glm::vec4(0.f / 255, 0.f / 255, 0.f / 255, 0.f)); - Clear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); } DrawBloomPassState::~DrawBloomPassState() diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp index 72bcce2a..c9789602 100644 --- a/src/Engine/Rendering/DrawColorCorrectionPass.cpp +++ b/src/Engine/Rendering/DrawColorCorrectionPass.cpp @@ -26,7 +26,7 @@ void DrawColorCorrectionPass::Draw(GLuint sceneTexture, GLuint bloomTexture) DrawScreenQuadPassState state = DrawScreenQuadPassState(); m_ColorCorrectionProgram->Bind(); - + glClear(GL_COLOR_BUFFER_BIT); glUniform1f(glGetUniformLocation(m_ColorCorrectionProgram->GetHandle(), "Exposure"), m_Exposure); glActiveTexture(GL_TEXTURE0); diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 3698cf2a..30bbb36e 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -27,10 +27,10 @@ void DrawFinalPass::InitializeFrameBuffers() //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); GenerateMipMapTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_FLOAT, 4); - m_BloomFrameBuffer.AddResource(std::shared_ptr(new RenderBuffer(&m_DepthBuffer, GL_DEPTH_ATTACHMENT))); - m_BloomFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); - m_BloomFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_BloomTexture, GL_COLOR_ATTACHMENT1))); - m_BloomFrameBuffer.Generate(); + m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new RenderBuffer(&m_DepthBuffer, GL_DEPTH_ATTACHMENT))); + m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); + m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_BloomTexture, GL_COLOR_ATTACHMENT1))); + m_FinalPassFrameBuffer.Generate(); } @@ -47,9 +47,7 @@ void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); - m_BloomFrameBuffer.Bind(); //in i state - - DrawFinalPassState state; + DrawFinalPassState* state = new DrawFinalPassState(m_FinalPassFrameBuffer.GetHandle()); m_ForwardPlusProgram->Bind(); GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); @@ -96,10 +94,19 @@ void DrawFinalPass::Draw(RenderScene& scene) continue; } } - m_BloomFrameBuffer.Unbind(); + m_FinalPassFrameBuffer.Unbind(); GLERROR("DrawFinalPass::Draw: END"); } + +void DrawFinalPass::ClearBuffer() +{ + m_FinalPassFrameBuffer.Bind(); + glClearColor(0.f, 0.f, 0.f, 0.f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + m_FinalPassFrameBuffer.Unbind(); +} + void DrawFinalPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const { glGenTextures(1, texture); diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 077ae7dc..3ebe320d 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -1,14 +1,14 @@ #include "Rendering/DrawFinalPassState.h" -DrawFinalPassState::DrawFinalPassState() +DrawFinalPassState::DrawFinalPassState(GLuint frameBuffer) { - //BindFramebuffer(0); + BindFramebuffer(frameBuffer); Enable(GL_BLEND); BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); Enable(GL_DEPTH_TEST); Enable(GL_CULL_FACE); - ClearColor(glm::vec4(155.f / 255, 0.f / 255, 155.f / 255, 0.f)); + ClearColor(glm::vec4(0.f, 0.f, 0.f, 0.f)); } DrawFinalPassState::~DrawFinalPassState() diff --git a/src/Engine/Rendering/DrawScreenQuadPass.cpp b/src/Engine/Rendering/DrawScreenQuadPass.cpp index 4095db04..4b155fc9 100644 --- a/src/Engine/Rendering/DrawScreenQuadPass.cpp +++ b/src/Engine/Rendering/DrawScreenQuadPass.cpp @@ -25,6 +25,7 @@ void DrawScreenQuadPass::Draw(GLuint texture) DrawScreenQuadPassState state = DrawScreenQuadPassState(); m_DrawQuadProgram->Bind(); + glClear(GL_COLOR_BUFFER_BIT); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, texture); diff --git a/src/Engine/Rendering/DrawScreenQuadPassState.cpp b/src/Engine/Rendering/DrawScreenQuadPassState.cpp index 1ee5d9a7..33a4895d 100644 --- a/src/Engine/Rendering/DrawScreenQuadPassState.cpp +++ b/src/Engine/Rendering/DrawScreenQuadPassState.cpp @@ -9,9 +9,7 @@ DrawScreenQuadPassState::DrawScreenQuadPassState() Disable(GL_DEPTH_TEST); Disable(GL_CULL_FACE); Disable(GL_BLEND); - glClearColor(0.f, 0.f, 0.f, 1.f); - // ClearColor(glm::vec4(255.f / 255, 163.f / 255, 176.f / 255, 0.f)); - Clear(GL_COLOR_BUFFER_BIT); + ClearColor(glm::vec4(0.f)); } DrawScreenQuadPassState::~DrawScreenQuadPassState() diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 0c485bdc..328a5ce8 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -55,45 +55,45 @@ void PickingPass::Draw(RenderScene& scene) if (scene.ClearDepth) { glClear(GL_DEPTH_BUFFER_BIT); } - m_Camera = scene.Camera; + m_Camera = scene.Camera; - for (auto &job : scene.ForwardJobs) { - auto modelJob = std::dynamic_pointer_cast(job); + for (auto &job : scene.ForwardJobs) { + auto modelJob = std::dynamic_pointer_cast(job); - if (modelJob) { - int pickColor[2] = { m_ColorCounter[0], m_ColorCounter[1] }; + if (modelJob) { + int pickColor[2] = { m_ColorCounter[0], m_ColorCounter[1] }; - PickingInfo pickInfo; - pickInfo.Entity = modelJob->Entity; - pickInfo.World = modelJob->World; - pickInfo.Camera = scene.Camera; + PickingInfo pickInfo; + pickInfo.Entity = modelJob->Entity; + pickInfo.World = modelJob->World; + pickInfo.Camera = scene.Camera; - auto color = m_EntityColors.find(std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)); - if (color != m_EntityColors.end()) { - pickColor[0] = color->second[0]; - pickColor[1] = color->second[1]; + auto color = m_EntityColors.find(std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)); + if (color != m_EntityColors.end()) { + pickColor[0] = color->second[0]; + pickColor[1] = color->second[1]; + } else { + m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); + if (m_ColorCounter[0] > 255) { + m_ColorCounter[0] = 0; + m_ColorCounter[1]++;; } else { - m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); - if (m_ColorCounter[0] > 255) { - m_ColorCounter[0] = 0; - m_ColorCounter[1]++;; - } else { - m_ColorCounter[0]++;; - } + m_ColorCounter[0]++;; } - - m_PickingColorsToEntity[glm::ivec2(pickColor[0], pickColor[1])] = pickInfo; - - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); - glUniform2fv(glGetUniformLocation(ShaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); - - glBindVertexArray(modelJob->Model->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, nullptr, modelJob->StartIndex); } + + m_PickingColorsToEntity[glm::ivec2(pickColor[0], pickColor[1])] = pickInfo; + + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); + glUniform2fv(glGetUniformLocation(ShaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); + + glBindVertexArray(modelJob->Model->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, nullptr, modelJob->StartIndex); } + } m_PickingBuffer.Unbind(); GLERROR("PickingPass Error"); diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 3a9b1a3e..605a3578 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -76,10 +76,16 @@ void Renderer::Update(double dt) void Renderer::Draw(RenderFrame& frame) { - glClearColor(255.f / 255, 163.f / 255, 176.f / 255, 0.f); + ImGui::Combo("Draw textures", &m_DebugTextureToDraw, "Final\0Scene\0Bloom\0Gaussian\0Picking"); + //clear buffer 0 + glClearColor(0.f, 0.f, 0.f, 0.f); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + //Clear other buffers m_PickingPass->ClearPicking(); + m_DrawFinalPass->ClearBuffer(); + m_DrawBloomPass->ClearBuffer(); + for (auto scene : frame.RenderScenes){ SortRenderJobsByDepth(*scene); @@ -88,15 +94,28 @@ void Renderer::Draw(RenderFrame& frame) m_LightCullingPass->FillLightList(*scene); m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); - //m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_SceneTexture); - //m_DrawScreenQuadPass->Draw(m_DrawFinalPass->m_BloomTexture); - m_DrawBloomPass->Draw(m_DrawFinalPass->m_BloomTexture); - m_DrawColorCorrectionPass->Draw(m_DrawFinalPass->m_SceneTexture, m_DrawBloomPass->m_GaussianTexture_vert); - //m_DrawScreenQuadPass->Draw(m_DrawBloomPass->m_GaussianTexture_vert); - //m_DrawScenePass->Draw(rq); GLERROR("Renderer::Draw m_DrawScenePass->Draw"); } + m_DrawBloomPass->Draw(m_DrawFinalPass->BloomTexture()); + if(m_DebugTextureToDraw == 0) { + m_DrawColorCorrectionPass->Draw(m_DrawFinalPass->SceneTexture(), m_DrawBloomPass->GaussianTexture()); + } + if (m_DebugTextureToDraw == 1) { + m_DrawScreenQuadPass->Draw(m_DrawFinalPass->SceneTexture()); + } + if (m_DebugTextureToDraw == 2) { + m_DrawScreenQuadPass->Draw(m_DrawFinalPass->BloomTexture()); + } + if (m_DebugTextureToDraw == 3) { + m_DrawScreenQuadPass->Draw(m_DrawBloomPass->GaussianTexture()); + } + if (m_DebugTextureToDraw == 4) { + m_DrawScreenQuadPass->Draw(m_PickingPass->PickingTexture()); + } + + //m_DrawBloomPass->Draw(m_DrawFinalPass->m_BloomTexture); + //m_DrawColorCorrectionPass->Draw(m_DrawFinalPass->m_SceneTexture, m_DrawBloomPass->m_GaussianTexture_vert); m_ImGuiRenderPass->Draw(); glfwSwapBuffers(m_Window); diff --git a/src/Engine/Rendering/Util/CommonFunctions.cpp b/src/Engine/Rendering/Util/CommonFunctions.cpp new file mode 100644 index 00000000..3c81de66 --- /dev/null +++ b/src/Engine/Rendering/Util/CommonFunctions.cpp @@ -0,0 +1,2 @@ +#include "Rendering/Util/CommonFunctions.h" + From f623232a2beeb357c410911812a038f0191075f1 Mon Sep 17 00:00:00 2001 From: Tleety Date: Sat, 23 Jan 2016 14:52:29 +0100 Subject: [PATCH 186/224] Removed a temp variable. --- include/Engine/Rendering/DrawFinalPass.h | 1 - src/Engine/Rendering/DrawFinalPass.cpp | 1 - src/Engine/Rendering/Renderer.cpp | 3 --- 3 files changed, 5 deletions(-) diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index 70c82de9..caf68f24 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -31,7 +31,6 @@ private: Texture* m_WhiteTexture; Texture* m_BlackTexture; - Texture* TEMP_glowTestTexture; FrameBuffer m_FinalPassFrameBuffer; GLuint m_BloomTexture; diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 30bbb36e..36a14610 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -13,7 +13,6 @@ void DrawFinalPass::InitializeTextures() { m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); m_BlackTexture = ResourceManager::Load("Textures/Core/Black.png"); - TEMP_glowTestTexture = ResourceManager::Load("Textures/Core/UnitRaptor_glow.png"); } void DrawFinalPass::InitializeFrameBuffers() diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 743cf8f5..57849d99 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -121,9 +121,6 @@ void Renderer::Draw(RenderFrame& frame) m_DrawScreenQuadPass->Draw(m_PickingPass->PickingTexture()); } - //m_DrawBloomPass->Draw(m_DrawFinalPass->m_BloomTexture); - //m_DrawColorCorrectionPass->Draw(m_DrawFinalPass->m_SceneTexture, m_DrawBloomPass->m_GaussianTexture_vert); - m_ImGuiRenderPass->Draw(); glfwSwapBuffers(m_Window); } From b83d7736276ca64f31abd7e9f0f0243408f79e9d Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 15:06:41 +0100 Subject: [PATCH 187/224] Infinite respawning for now --- include/Game/Systems/PlayerSpawnSystem.h | 1 + src/Game/Systems/PlayerSpawnSystem.cpp | 9 +++++++++ 2 files changed, 10 insertions(+) diff --git a/include/Game/Systems/PlayerSpawnSystem.h b/include/Game/Systems/PlayerSpawnSystem.h index eb4d3c97..b0ff1d79 100644 --- a/include/Game/Systems/PlayerSpawnSystem.h +++ b/include/Game/Systems/PlayerSpawnSystem.h @@ -22,6 +22,7 @@ private: bool m_NetworkEnabled = false; std::vector m_SpawnRequests; + std::map m_PlayerEntities; EventRelay m_OnInputCommand; bool OnInputCommand(const Events::InputCommand& e); diff --git a/src/Game/Systems/PlayerSpawnSystem.cpp b/src/Game/Systems/PlayerSpawnSystem.cpp index f18808cc..fe377866 100644 --- a/src/Game/Systems/PlayerSpawnSystem.cpp +++ b/src/Game/Systems/PlayerSpawnSystem.cpp @@ -72,6 +72,12 @@ bool PlayerSpawnSystem::OnPlayerSpawned(Events::PlayerSpawned& e) { // When a player is actually spawned (since the actual spawning is handled on the server) + // Check if a player already exists + if (m_PlayerEntities.count(e.PlayerID) != 0) { + // TODO: Disallow infinite respawning here + m_World->DeleteEntity(m_PlayerEntities[e.PlayerID].ID); + } + // Set the camera to the correct entity EntityWrapper cameraEntity = e.Player.FirstChildByName("Camera"); if (cameraEntity.Valid()) { @@ -80,5 +86,8 @@ bool PlayerSpawnSystem::OnPlayerSpawned(Events::PlayerSpawned& e) m_EventBroker->Publish(e); } + // Store the player for future reference + m_PlayerEntities[e.PlayerID] = e.Player; + return true; } \ No newline at end of file From 666ef6589e2082751a4d7e3a5f23842d3f70f569 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 15:06:47 +0100 Subject: [PATCH 188/224] Crouching! --- resources/Schema/Components/Player.xml | 3 +- resources/Schema/Components/Player.xsd | 1 + resources/Schema/Entities/MovementTest.xml | 4 +++ resources/Schema/Entities/Player.xml | 37 +++++++++++++++++++--- src/Game/Systems/PlayerMovementSystem.cpp | 23 +++++++++++--- 5 files changed, 59 insertions(+), 9 deletions(-) diff --git a/resources/Schema/Components/Player.xml b/resources/Schema/Components/Player.xml index a9ecc6be..b51326aa 100644 --- a/resources/Schema/Components/Player.xml +++ b/resources/Schema/Components/Player.xml @@ -1,4 +1,5 @@ - 0.2 + 3 + 1.5 \ No newline at end of file diff --git a/resources/Schema/Components/Player.xsd b/resources/Schema/Components/Player.xsd index 89c4a398..13948dc2 100644 --- a/resources/Schema/Components/Player.xsd +++ b/resources/Schema/Components/Player.xsd @@ -10,6 +10,7 @@ + diff --git a/resources/Schema/Entities/MovementTest.xml b/resources/Schema/Entities/MovementTest.xml index 9ea1ae68..00f94120 100644 --- a/resources/Schema/Entities/MovementTest.xml +++ b/resources/Schema/Entities/MovementTest.xml @@ -13,6 +13,7 @@ Models/Core/UnitCube.obj + false @@ -93,6 +94,7 @@ Models/Core/UnitCube.obj + false @@ -107,6 +109,7 @@ Models/Core/UnitCube.obj + false @@ -121,6 +124,7 @@ Models/Core/UnitCube.obj + false diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index fa8b7686..4398dcc1 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -7,6 +7,9 @@ + + + 3 @@ -17,7 +20,7 @@ - + @@ -27,19 +30,18 @@ - - Fonts/DroidSans.ttf,100 + false - + @@ -85,6 +87,33 @@ + + + + Models/Core/UnitCube.obj + + false + + + + + + + + + + + + Models/Core/UnitCube.obj + + false + + + + + + + diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index 10fc29f6..c5b55cde 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -37,12 +37,27 @@ void PlayerMovementSystem::Update(double dt) ori.y += controller->Rotation().y; glm::vec3& pos = cTransform["Position"]; - pos += controller->Movement() * glm::inverse(glm::quat(ori)) * (float)player["Player"]["MovementSpeed"] * (float)dt; + float speed; + if (controller->Crouching()) { + speed = player["Player"]["CrouchSpeed"]; + } else { + speed = player["Player"]["MovementSpeed"]; + } + pos += controller->Movement() * glm::inverse(glm::quat(ori)) * speed * (float)dt; if (player.HasComponent("Physics")) { - if (controller->Jumping()) { - glm::vec3& velocity = player["Physics"]["Velocity"]; - velocity.y += 10.f; + glm::vec3& velocity = player["Physics"]["Velocity"]; + if (controller->Jumping() && !controller->Crouching() && velocity.y == 0.f) { + velocity.y += 4.f; + } + } + + if (player.HasComponent("AABB")) { + glm::vec3& size = player["AABB"]["Size"]; + if (controller->Crouching()) { + size = glm::vec3(1.f, 1.f, 1.f); + } else { + size = glm::vec3(1.f, 1.6f, 1.f); } } From bd62b5873d0ce4373865f2466f535f9df3513842 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sat, 23 Jan 2016 15:57:26 +0100 Subject: [PATCH 189/224] Revert "Merge pull request #43 from teamfisk/Forward+" This reverts commit d59ab5aba270d66e8bcccb957713133dab4b5188, reversing changes made to bef95235d0e94ea274afd27e650eb43ed83e34cc. --- include/Engine/Rendering/DrawBloomPass.h | 53 ------- include/Engine/Rendering/DrawBloomPassState.h | 15 -- .../Rendering/DrawColorCorrectionPass.h | 29 ---- include/Engine/Rendering/DrawFinalPass.h | 17 +-- include/Engine/Rendering/DrawFinalPassState.h | 2 +- include/Engine/Rendering/DrawScreenQuadPass.h | 28 ---- .../Rendering/DrawScreenQuadPassState.h | 15 -- include/Engine/Rendering/Renderer.h | 14 +- .../Engine/Rendering/Util/CommonFunctions.h | 17 --- .../Shaders/DrawColorCorrection.frag.glsl | 32 ----- .../Shaders/DrawColorCorrection.vert.glsl | 13 -- resources/Shaders/ForwardPlus.frag.glsl | 51 +++---- resources/Shaders/Gaussian_horiz.frag.glsl | 23 --- resources/Shaders/Gaussian_horiz.vert.glsl | 13 -- resources/Shaders/Gaussian_vert.frag.glsl | 23 --- resources/Shaders/Gaussian_vert.vert.glsl | 13 -- src/Engine/Rendering/DrawBloomPass.cpp | 134 ------------------ src/Engine/Rendering/DrawBloomPassState.cpp | 15 -- .../Rendering/DrawColorCorrectionPass.cpp | 41 ------ src/Engine/Rendering/DrawFinalPass.cpp | 68 +-------- src/Engine/Rendering/DrawFinalPassState.cpp | 6 +- src/Engine/Rendering/DrawScreenQuadPass.cpp | 37 ----- .../Rendering/DrawScreenQuadPassState.cpp | 18 --- src/Engine/Rendering/FrameBuffer.cpp | 7 +- src/Engine/Rendering/PickingPass.cpp | 63 ++++---- src/Engine/Rendering/Renderer.cpp | 56 ++++---- src/Engine/Rendering/Util/CommonFunctions.cpp | 2 - 27 files changed, 99 insertions(+), 706 deletions(-) delete mode 100644 include/Engine/Rendering/DrawBloomPass.h delete mode 100644 include/Engine/Rendering/DrawBloomPassState.h delete mode 100644 include/Engine/Rendering/DrawColorCorrectionPass.h delete mode 100644 include/Engine/Rendering/DrawScreenQuadPass.h delete mode 100644 include/Engine/Rendering/DrawScreenQuadPassState.h delete mode 100644 include/Engine/Rendering/Util/CommonFunctions.h delete mode 100644 resources/Shaders/DrawColorCorrection.frag.glsl delete mode 100644 resources/Shaders/DrawColorCorrection.vert.glsl delete mode 100644 resources/Shaders/Gaussian_horiz.frag.glsl delete mode 100644 resources/Shaders/Gaussian_horiz.vert.glsl delete mode 100644 resources/Shaders/Gaussian_vert.frag.glsl delete mode 100644 resources/Shaders/Gaussian_vert.vert.glsl delete mode 100644 src/Engine/Rendering/DrawBloomPass.cpp delete mode 100644 src/Engine/Rendering/DrawBloomPassState.cpp delete mode 100644 src/Engine/Rendering/DrawColorCorrectionPass.cpp delete mode 100644 src/Engine/Rendering/DrawScreenQuadPass.cpp delete mode 100644 src/Engine/Rendering/DrawScreenQuadPassState.cpp delete mode 100644 src/Engine/Rendering/Util/CommonFunctions.cpp diff --git a/include/Engine/Rendering/DrawBloomPass.h b/include/Engine/Rendering/DrawBloomPass.h deleted file mode 100644 index 539d6957..00000000 --- a/include/Engine/Rendering/DrawBloomPass.h +++ /dev/null @@ -1,53 +0,0 @@ -#ifndef DrawBloomPass_h__ -#define DrawBloomPass_h__ - -#include "IRenderer.h" -#include "DrawBloomPassState.h" -//#include "LightCullingPass.h" Finalpass om den skall skickas in -#include "FrameBuffer.h" -#include "ShaderProgram.h" -//#include "Util/UnorderedMapVec2.h" -#include "Texture.h" - -class DrawBloomPass -{ -public: - DrawBloomPass(IRenderer* renderer /* ,Texture or finalpass*/ ); - ~DrawBloomPass() { } - void InitializeTextures(); - void InitializeFrameBuffers(); - void InitializeShaderPrograms(); - void InitializeBuffers(); - void ClearBuffer(); - - void FillGaussianBuffer(FrameBuffer* fb); - - void Draw(GLuint texture); - - //Getters - //Return the blurred result of the texture that was sent into draw - GLuint GaussianTexture() const { return m_GaussianTexture_vert; } - - -private: - void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; - - Texture* m_WhiteTexture; - Model* m_ScreenQuad; - - const IRenderer* m_Renderer; - //const LightCullingPass* m_LightCullingPass - GLuint m_iterations = 9; - - GLuint m_GaussianTexture_horiz; - GLuint m_GaussianTexture_vert; - - FrameBuffer m_GaussianFrameBuffer_horiz; - FrameBuffer m_GaussianFrameBuffer_vert; - - ShaderProgram* m_GaussianProgram_horiz; - ShaderProgram* m_GaussianProgram_vert; - -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawBloomPassState.h b/include/Engine/Rendering/DrawBloomPassState.h deleted file mode 100644 index 7f2094cf..00000000 --- a/include/Engine/Rendering/DrawBloomPassState.h +++ /dev/null @@ -1,15 +0,0 @@ -#ifndef DrawBloomPassState_h__ -#define DrawBloomPassState_h__ - -#include "Rendering/RenderState.h" - -class DrawBloomPassState : public RenderState -{ -public: - DrawBloomPassState(); - ~DrawBloomPassState(); -private: - -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawColorCorrectionPass.h b/include/Engine/Rendering/DrawColorCorrectionPass.h deleted file mode 100644 index e9a7e281..00000000 --- a/include/Engine/Rendering/DrawColorCorrectionPass.h +++ /dev/null @@ -1,29 +0,0 @@ -#ifndef DrawColorCorrectionPass_h__ -#define DrawColorCorrectionPass_h__ - -#include "IRenderer.h" -#include "DrawScreenQuadPassState.h" -#include "FrameBuffer.h" -#include "ShaderProgram.h" -//#include "Util/UnorderedMapVec2.h" -#include "Texture.h" - -class DrawColorCorrectionPass -{ -public: - DrawColorCorrectionPass(IRenderer* renderer); - ~DrawColorCorrectionPass() { } - void InitializeFrameBuffers(); - void InitializeShaderPrograms(); - - void Draw(GLuint sceneTexture, GLuint bloomTexture); -private: - const IRenderer* m_Renderer; - - ShaderProgram* m_ColorCorrectionProgram; - - Model* m_ScreenQuad; - GLfloat m_Exposure; -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index caf68f24..20c7249d 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -17,25 +17,16 @@ public: void InitializeTextures(); void InitializeFrameBuffers(); void InitializeShaderPrograms(); - void Draw(RenderScene& scene); - void ClearBuffer(); - //Return the texture that is used in later stages to apply the bloom effect - GLuint BloomTexture() const { return m_BloomTexture; } - //Return the texture with diffuse and lighting of the scene. - GLuint SceneTexture() const { return m_SceneTexture; } + void Draw(RenderScene& scene); + + //Getters + private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; - void GenerateMipMapTexture(GLuint* texture, GLenum wrapping, glm::vec2 dimensions, GLint format, GLenum type, GLint numMipMaps) const; Texture* m_WhiteTexture; - Texture* m_BlackTexture; - - FrameBuffer m_FinalPassFrameBuffer; - GLuint m_BloomTexture; - GLuint m_SceneTexture; - GLuint m_DepthBuffer; const IRenderer* m_Renderer; const LightCullingPass* m_LightCullingPass; diff --git a/include/Engine/Rendering/DrawFinalPassState.h b/include/Engine/Rendering/DrawFinalPassState.h index 10b840e9..72d8e392 100644 --- a/include/Engine/Rendering/DrawFinalPassState.h +++ b/include/Engine/Rendering/DrawFinalPassState.h @@ -6,7 +6,7 @@ class DrawFinalPassState : public RenderState { public: - DrawFinalPassState(GLuint frameBuffer); + DrawFinalPassState(); ~DrawFinalPassState(); private: diff --git a/include/Engine/Rendering/DrawScreenQuadPass.h b/include/Engine/Rendering/DrawScreenQuadPass.h deleted file mode 100644 index 117e9e1e..00000000 --- a/include/Engine/Rendering/DrawScreenQuadPass.h +++ /dev/null @@ -1,28 +0,0 @@ -#ifndef DrawScreenQuadPass_h__ -#define DrawScreenQuadPass_h__ - -#include "IRenderer.h" -#include "DrawScreenQuadPassState.h" -#include "FrameBuffer.h" -#include "ShaderProgram.h" -//#include "Util/UnorderedMapVec2.h" -#include "Texture.h" - -class DrawScreenQuadPass -{ -public: - DrawScreenQuadPass(IRenderer* renderer); - ~DrawScreenQuadPass() { } - void InitializeFrameBuffers(); - void InitializeShaderPrograms(); - - void Draw(GLuint texture); -private: - const IRenderer* m_Renderer; - - ShaderProgram* m_DrawQuadProgram; - - Model* m_ScreenQuad; -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawScreenQuadPassState.h b/include/Engine/Rendering/DrawScreenQuadPassState.h deleted file mode 100644 index 63ab4729..00000000 --- a/include/Engine/Rendering/DrawScreenQuadPassState.h +++ /dev/null @@ -1,15 +0,0 @@ -#ifndef DrawScreenQuadPassState_h__ -#define DrawScreenQuadPassState_h__ - -#include "Rendering/RenderState.h" - -class DrawScreenQuadPassState : public RenderState -{ -public: - DrawScreenQuadPassState(); - ~DrawScreenQuadPassState(); -private: - -}; - -#endif \ No newline at end of file diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index d84f41d5..7e124e3c 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -13,14 +13,10 @@ #include "PickingPass.h" #include "LightCullingPass.h" #include "DrawFinalPass.h" -#include "DrawScreenQuadPass.h" -#include "DrawBloomPass.h" -#include "DrawColorCorrectionPass.h" #include "../Core/EventBroker.h" #include "ImGuiRenderPass.h" #include "Camera.h" #include "../Core/Transform.h" -#include "imgui/imgui.h" #include "TextPass.h" class Renderer : public IRenderer @@ -48,15 +44,10 @@ private: Model* m_UnitQuad; Model* m_UnitSphere; - int m_DebugTextureToDraw = 0; - PickingPass* m_PickingPass; LightCullingPass* m_LightCullingPass; ImGuiRenderPass* m_ImGuiRenderPass; DrawFinalPass* m_DrawFinalPass; - DrawScreenQuadPass* m_DrawScreenQuadPass; - DrawBloomPass* m_DrawBloomPass; - DrawColorCorrectionPass* m_DrawColorCorrectionPass; //----------------------Functions----------------------// void InitializeWindow(); @@ -66,13 +57,14 @@ private: //TODO: Renderer: Get InputUpdate out of renderer void InputUpdate(double dt); //void PickingPass(RenderQueueCollection& rq); - //void DrawScreenQuad(GLuint textureToDraw); + void DrawScreenQuad(GLuint textureToDraw); static bool DepthSort(const std::shared_ptr &i, const std::shared_ptr &j) { return (i->Depth < j->Depth); } void SortRenderJobsByDepth(RenderScene &scene); void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type); //--------------------ShaderPrograms-------------------// - ShaderProgram* m_BasicForwardProgram; + ShaderProgram* m_BasicForwardProgram; + ShaderProgram* m_DrawScreenQuadProgram; }; #endif \ No newline at end of file diff --git a/include/Engine/Rendering/Util/CommonFunctions.h b/include/Engine/Rendering/Util/CommonFunctions.h deleted file mode 100644 index b262568c..00000000 --- a/include/Engine/Rendering/Util/CommonFunctions.h +++ /dev/null @@ -1,17 +0,0 @@ -#ifndef CommonFuntions_h__ -#define CommonFuntions_h__ - -#include "../../Common.h" -#include "../../OpenGL.h" -#include "../../GLM.h" - -class CommonFuntions -{ -public: - CommonFuntions() = delete; - -private: - -}; - -#endif \ No newline at end of file diff --git a/resources/Shaders/DrawColorCorrection.frag.glsl b/resources/Shaders/DrawColorCorrection.frag.glsl deleted file mode 100644 index 8d13992a..00000000 --- a/resources/Shaders/DrawColorCorrection.frag.glsl +++ /dev/null @@ -1,32 +0,0 @@ -#version 430 - -layout (binding = 0) uniform sampler2D SceneTexture; -layout (binding = 1) uniform sampler2D BloomTexture; -uniform float Exposure; - -in VertexData{ - vec2 TextureCoordinate; -}Input; - -out vec4 fragmentColor; - -void main() -{ - const float gamma = 2.2; - vec4 hdrColor = texture(SceneTexture, Input.TextureCoordinate); - vec4 bloomColor = texture(BloomTexture, Input.TextureCoordinate); - hdrColor += bloomColor; - - //Toon mapping thingy - vec3 result = vec3(1.0) - exp(-hdrColor.rgb * Exposure); - - //gamme correction - result = pow(result, vec3(1.0 / gamma)); - - fragmentColor = vec4(result, 1.0); - //fragmentColor = hdrColor; - //fragmentColor = bloomColor; - //fragmentColor = vec4(1,0.5,0.7,1); -} - - diff --git a/resources/Shaders/DrawColorCorrection.vert.glsl b/resources/Shaders/DrawColorCorrection.vert.glsl deleted file mode 100644 index 346bc141..00000000 --- a/resources/Shaders/DrawColorCorrection.vert.glsl +++ /dev/null @@ -1,13 +0,0 @@ -#version 430 - -layout (location = 0) in vec3 Position; - -out VertexData{ - vec2 TextureCoordinate; -}Output; - -void main() -{ - gl_Position = vec4(Position, 1.0); - Output.TextureCoordinate = (vec2(Position) + 1) / 2; -} \ No newline at end of file diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 403c96fc..78a2125e 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -5,8 +5,7 @@ uniform mat4 V; uniform mat4 P; uniform vec4 Color; uniform vec2 ScreenDimensions; -layout (binding = 0) uniform sampler2D DiffuseTexture; -layout (binding = 1) uniform sampler2D GlowMap; +uniform sampler2D texture0; #define TILE_SIZE 16 @@ -49,8 +48,7 @@ in VertexData{ vec4 DiffuseColor; }Input; -out vec4 sceneColor; -out vec4 bloomColor; +out vec4 fragmentColor; vec4 scene_ambient = vec4(0.3,0.3,0.3,1); @@ -101,10 +99,9 @@ LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensi void main() { - vec4 diffuseTexel = texture2D(DiffuseTexture, Input.TextureCoordinate); - vec4 glowTexel = texture2D(GlowMap, Input.TextureCoordinate); + vec4 texel = texture2D(texture0, Input.TextureCoordinate); vec4 position = V * M * vec4(Input.Position, 1.0); - vec4 normal = normalize(V * vec4(Input.Normal, 0.0)); + vec4 normal = V * vec4(Input.Normal, 0.0); vec4 viewVec = normalize(-position); vec2 tilePos; @@ -123,42 +120,30 @@ void main() int l = int(LightIndex[i]); LightSource light = LightSources.List[l]; - LightResult light_result; - //These if statements should be removed. + LightResult result; if(light.Type == 1) { // point - light_result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); + result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); } else if (light.Type == 2) { //Directional - light_result = CalcDirectionalLightSource(V * light.Direction, light.Color, light.Intensity, viewVec, normal); + result = CalcDirectionalLightSource(V * light.Direction, light.Color, light.Intensity, viewVec, normal); } - totalLighting.Diffuse += light_result.Diffuse; - totalLighting.Specular += light_result.Specular; + totalLighting.Diffuse += result.Diffuse; + totalLighting.Specular += result.Specular; } - //sceneColor += Input.DiffuseColor; - vec4 color_result = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * diffuseTexel * Color; - //bloomColor = vec4(0.3, 0.8, 0.6, 1.0); - sceneColor = vec4(color_result.xyz, 1.0); - //These if statements should be removed if they are slow. - color_result += glowTexel; - bloomColor = vec4(clamp(color_result.xyz - 1.0, 0, 100), 1.0); - /* - if(color_result.x > 1 || color_result.y > 1 || color_result.z > 1) { - bloomColor = vec4(color_result.xyz, 1.0); - } else { - bloomColor = vec4(0.0, 0.0, 0.0, 1.0); - } */ - - //sceneColor += Input.DiffuseColor * (totalLighting.Diffuse) * diffuseTexel * Color; - //sceneColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); - //sceneColor = diffuseTexel * Input.DiffuseColor * Color; - //sceneColor += vec4(currentTile/3600.f, 0, 0, 1); + + //fragmentColor += Input.DiffuseColor; + fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; + //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); + //fragmentColor = texel * Input.DiffuseColor * Color; + //fragmentColor += vec4(currentTile/3600.f, 0, 0, 1); //Tiled Debug Code /* if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { - sceneColor += vec4(0.5, 0, 0, 0); + fragmentColor += vec4(0.5, 0, 0, 0); } else { - sceneColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/LightSources.List.length(), 0, 0, 1); + fragmentColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/LightSources.List.length(), 0, 0, 1); } */ } diff --git a/resources/Shaders/Gaussian_horiz.frag.glsl b/resources/Shaders/Gaussian_horiz.frag.glsl deleted file mode 100644 index bd48d2d5..00000000 --- a/resources/Shaders/Gaussian_horiz.frag.glsl +++ /dev/null @@ -1,23 +0,0 @@ -#version 430 - -layout (binding = 0) uniform sampler2D Texture; - -in VertexData{ - vec2 TextureCoordinate; -}Input; - -out vec4 fragmentColor; - -uniform float weight[5] = float[](0.227027, 0.1945946, 0.1216216, 0.054054, 0.016216); - -void main() -{ - vec2 tex_offset = 1.0 / textureSize(Texture, 0); - vec3 result = texture(Texture, Input.TextureCoordinate).rgb * weight[0]; - - for(int i = 1; i < 5; ++i) { - result += texture(Texture, Input.TextureCoordinate + vec2(tex_offset.x * i, 0.0)).rgb * weight[i]; - result += texture(Texture, Input.TextureCoordinate - vec2(tex_offset.x * i, 0.0)).rgb * weight[i]; - } - fragmentColor = vec4(result, 1.0); -} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_horiz.vert.glsl b/resources/Shaders/Gaussian_horiz.vert.glsl deleted file mode 100644 index 346bc141..00000000 --- a/resources/Shaders/Gaussian_horiz.vert.glsl +++ /dev/null @@ -1,13 +0,0 @@ -#version 430 - -layout (location = 0) in vec3 Position; - -out VertexData{ - vec2 TextureCoordinate; -}Output; - -void main() -{ - gl_Position = vec4(Position, 1.0); - Output.TextureCoordinate = (vec2(Position) + 1) / 2; -} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_vert.frag.glsl b/resources/Shaders/Gaussian_vert.frag.glsl deleted file mode 100644 index 25b08f9f..00000000 --- a/resources/Shaders/Gaussian_vert.frag.glsl +++ /dev/null @@ -1,23 +0,0 @@ -#version 430 - -layout (binding = 0) uniform sampler2D Texture; - -in VertexData{ - vec2 TextureCoordinate; -}Input; - -out vec4 fragmentColor; - -uniform float weight[5] = float[](0.227027, 0.1945946, 0.1216216, 0.054054, 0.016216); - -void main() -{ - vec2 tex_offset = 1.0 / textureSize(Texture, 0); - vec3 result = texture(Texture, Input.TextureCoordinate).rgb * weight[0]; - - for(int i = 1; i < 5; ++i) { - result += texture(Texture, Input.TextureCoordinate + vec2(0.0, tex_offset.y * i)).rgb * weight[i]; - result += texture(Texture, Input.TextureCoordinate - vec2(0.0, tex_offset.y * i)).rgb * weight[i]; - } - fragmentColor = vec4(result, 1.0); -} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_vert.vert.glsl b/resources/Shaders/Gaussian_vert.vert.glsl deleted file mode 100644 index 346bc141..00000000 --- a/resources/Shaders/Gaussian_vert.vert.glsl +++ /dev/null @@ -1,13 +0,0 @@ -#version 430 - -layout (location = 0) in vec3 Position; - -out VertexData{ - vec2 TextureCoordinate; -}Output; - -void main() -{ - gl_Position = vec4(Position, 1.0); - Output.TextureCoordinate = (vec2(Position) + 1) / 2; -} \ No newline at end of file diff --git a/src/Engine/Rendering/DrawBloomPass.cpp b/src/Engine/Rendering/DrawBloomPass.cpp deleted file mode 100644 index 1ad97eb5..00000000 --- a/src/Engine/Rendering/DrawBloomPass.cpp +++ /dev/null @@ -1,134 +0,0 @@ -#include "Rendering/DrawBloomPass.h" - -DrawBloomPass::DrawBloomPass(IRenderer* renderer) -{ - m_Renderer = renderer; - - m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); - - InitializeTextures(); - InitializeBuffers(); - InitializeShaderPrograms(); -} - -void DrawBloomPass::InitializeTextures() -{ - m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); -} - -void DrawBloomPass::InitializeShaderPrograms() -{ - m_GaussianProgram_horiz = ResourceManager::Load("##GaussianProgramHoriz"); - m_GaussianProgram_horiz->AddShader(std::shared_ptr(new VertexShader("Shaders/Gaussian_horiz.vert.glsl"))); - m_GaussianProgram_horiz->AddShader(std::shared_ptr(new FragmentShader("Shaders/Gaussian_horiz.frag.glsl"))); - m_GaussianProgram_horiz->Compile(); - m_GaussianProgram_horiz->Link(); - - m_GaussianProgram_vert = ResourceManager::Load("##GaussianProgramVert"); - m_GaussianProgram_vert->AddShader(std::shared_ptr(new VertexShader("Shaders/Gaussian_vert.vert.glsl"))); - m_GaussianProgram_vert->AddShader(std::shared_ptr(new FragmentShader("Shaders/Gaussian_vert.frag.glsl"))); - m_GaussianProgram_vert->Compile(); - m_GaussianProgram_vert->Link(); -} - - -void DrawBloomPass::InitializeBuffers() -{ - GenerateTexture(&m_GaussianTexture_horiz, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - - m_GaussianFrameBuffer_horiz.AddResource(std::shared_ptr(new Texture2D(&m_GaussianTexture_horiz, GL_COLOR_ATTACHMENT0))); - m_GaussianFrameBuffer_horiz.Generate(); - - GenerateTexture(&m_GaussianTexture_vert, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - - m_GaussianFrameBuffer_vert.AddResource(std::shared_ptr(new Texture2D(&m_GaussianTexture_vert, GL_COLOR_ATTACHMENT0))); - m_GaussianFrameBuffer_vert.Generate(); -} - - -void DrawBloomPass::ClearBuffer() -{ - m_GaussianFrameBuffer_horiz.Bind(); - glClearColor(0.f, 0.f, 0.f, 0.f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - m_GaussianFrameBuffer_horiz.Unbind(); - m_GaussianFrameBuffer_vert.Bind(); - glClearColor(0.f, 0.f, 0.f, 0.f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - m_GaussianFrameBuffer_vert.Unbind(); -} - -void DrawBloomPass::Draw(GLuint texture) -{ - GLERROR("DrawBloomPass::Draw: Pre"); - - DrawBloomPassState state; - - GLuint shaderHandle_horiz = m_GaussianProgram_horiz->GetHandle(); - GLuint shaderHandle_vert = m_GaussianProgram_vert->GetHandle(); - - - //Horizontal pass, first use the given texture then save it to the horizontal framebuffer. - m_GaussianFrameBuffer_horiz.Bind(); - m_GaussianProgram_horiz->Bind(); - - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, texture); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); - - //Iterate some times to make it more gaussian. - for (int i = 1; i < m_iterations; i++) { - //Vertical pass - m_GaussianFrameBuffer_vert.Bind(); - m_GaussianProgram_vert->Bind(); - - glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_horiz); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); - - //horizontal pass - - m_GaussianFrameBuffer_horiz.Bind(); - m_GaussianProgram_horiz->Bind(); - - glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_vert); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); - } - - //final vertical gaussian after the iterations are done - - m_GaussianFrameBuffer_vert.Bind(); - m_GaussianProgram_vert->Bind(); - - glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_horiz); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); - - GLERROR("DrawBloomPass::Draw: END"); -} - -void DrawBloomPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const -{ - glGenTextures(1, texture); - glBindTexture(GL_TEXTURE_2D, *texture); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filtering); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filtering); - glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, dimensions.x, dimensions.y, 0, format, type, nullptr);//TODO: Renderer: Fix the precision and Resolution - GLERROR("Texture initialization failed"); -} diff --git a/src/Engine/Rendering/DrawBloomPassState.cpp b/src/Engine/Rendering/DrawBloomPassState.cpp deleted file mode 100644 index f9c57475..00000000 --- a/src/Engine/Rendering/DrawBloomPassState.cpp +++ /dev/null @@ -1,15 +0,0 @@ -#include "Rendering/DrawBloomPassState.h" - - -DrawBloomPassState::DrawBloomPassState() -{ - //BindFramebuffer(0); - Disable(GL_BLEND); - Disable(GL_DEPTH_TEST); - Disable(GL_CULL_FACE); -} - -DrawBloomPassState::~DrawBloomPassState() -{ - -} diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp deleted file mode 100644 index c9789602..00000000 --- a/src/Engine/Rendering/DrawColorCorrectionPass.cpp +++ /dev/null @@ -1,41 +0,0 @@ -#include "Rendering/DrawColorCorrectionPass.h" - -DrawColorCorrectionPass::DrawColorCorrectionPass(IRenderer* renderer) -{ - m_Renderer = renderer; - - m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); - m_Exposure = 1; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. - - InitializeShaderPrograms(); -} - -void DrawColorCorrectionPass::InitializeShaderPrograms() -{ - m_ColorCorrectionProgram = ResourceManager::Load("#ColorCorrectionProgram"); - m_ColorCorrectionProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawColorCorrection.vert.glsl"))); - m_ColorCorrectionProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawColorCorrection.frag.glsl"))); - m_ColorCorrectionProgram->Compile(); - m_ColorCorrectionProgram->Link(); -} - -void DrawColorCorrectionPass::Draw(GLuint sceneTexture, GLuint bloomTexture) -{ - //glBindFramebuffer(GL_FRAMEBUFFER, 0); - GLERROR("DrawScreenQuadPass::Draw: Pre"); - - DrawScreenQuadPassState state = DrawScreenQuadPassState(); - m_ColorCorrectionProgram->Bind(); - glClear(GL_COLOR_BUFFER_BIT); - glUniform1f(glGetUniformLocation(m_ColorCorrectionProgram->GetHandle(), "Exposure"), m_Exposure); - - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, sceneTexture); - glActiveTexture(GL_TEXTURE1); - glBindTexture(GL_TEXTURE_2D, bloomTexture); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); -} diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 36a14610..eeaa7bb3 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -6,31 +6,11 @@ DrawFinalPass::DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCulling m_LightCullingPass = lightCullingPass; InitializeTextures(); InitializeShaderPrograms(); - InitializeFrameBuffers(); } void DrawFinalPass::InitializeTextures() { m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); - m_BlackTexture = ResourceManager::Load("Textures/Core/Black.png"); -} - -void DrawFinalPass::InitializeFrameBuffers() -{ - glGenRenderbuffers(1, &m_DepthBuffer); - glBindRenderbuffer(GL_RENDERBUFFER, m_DepthBuffer); - glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); - - GenerateTexture(&m_SceneTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - GenerateMipMapTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_FLOAT, 4); - - m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new RenderBuffer(&m_DepthBuffer, GL_DEPTH_ATTACHMENT))); - m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); - m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_BloomTexture, GL_COLOR_ATTACHMENT1))); - m_FinalPassFrameBuffer.Generate(); - } void DrawFinalPass::InitializeShaderPrograms() @@ -46,7 +26,7 @@ void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); - DrawFinalPassState* state = new DrawFinalPassState(m_FinalPassFrameBuffer.GetHandle()); + DrawFinalPassState state; m_ForwardPlusProgram->Bind(); GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); @@ -71,20 +51,13 @@ void DrawFinalPass::Draw(RenderScene& scene) glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); glUniform4fv(glGetUniformLocation(shaderHandle, "Color"), 1, glm::value_ptr(modelJob->Color)); - glActiveTexture(GL_TEXTURE0); if(modelJob->DiffuseTexture != nullptr) { + glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, modelJob->DiffuseTexture->m_Texture); } else { + glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); } - glActiveTexture(GL_TEXTURE1); - glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); - - /*if(modelJob->GlowMap != nullptr) { - glBindTexture(GL_TEXTURE_2D, modelJob->GlowMap->m_Texture); - } else { - glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); - }*/ glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); @@ -93,41 +66,6 @@ void DrawFinalPass::Draw(RenderScene& scene) continue; } } - m_FinalPassFrameBuffer.Unbind(); GLERROR("DrawFinalPass::Draw: END"); -} - -void DrawFinalPass::ClearBuffer() -{ - m_FinalPassFrameBuffer.Bind(); - glClearColor(0.f, 0.f, 0.f, 0.f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - m_FinalPassFrameBuffer.Unbind(); -} - -void DrawFinalPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const -{ - glGenTextures(1, texture); - glBindTexture(GL_TEXTURE_2D, *texture); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filtering); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filtering); - glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, dimensions.x, dimensions.y, 0, format, type, nullptr);//TODO: Renderer: Fix the precision and Resolution - GLERROR("Texture initialization failed"); -} - -void DrawFinalPass::GenerateMipMapTexture(GLuint* texture, GLenum wrapping, glm::vec2 dimensions, GLint format, GLenum type, GLint numMipMaps) const -{ - glGenTextures(1, texture); - glBindTexture(GL_TEXTURE_2D, *texture); - glTexStorage2D(GL_TEXTURE_2D, numMipMaps, GL_RGBA8, dimensions.x, dimensions.y); - glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, dimensions.x, dimensions.y, format, type, texture); - glGenerateMipmap(GL_TEXTURE_2D); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); - GLERROR("MipMap Texture initialization failed"); } diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 3ebe320d..2cda4069 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -1,14 +1,14 @@ #include "Rendering/DrawFinalPassState.h" -DrawFinalPassState::DrawFinalPassState(GLuint frameBuffer) +DrawFinalPassState::DrawFinalPassState() { - BindFramebuffer(frameBuffer); + BindFramebuffer(0); Enable(GL_BLEND); BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); Enable(GL_DEPTH_TEST); Enable(GL_CULL_FACE); - ClearColor(glm::vec4(0.f, 0.f, 0.f, 0.f)); + ClearColor(glm::vec4(200.f / 255, 0.f / 255, 200.f / 255, 0.f)); } DrawFinalPassState::~DrawFinalPassState() diff --git a/src/Engine/Rendering/DrawScreenQuadPass.cpp b/src/Engine/Rendering/DrawScreenQuadPass.cpp deleted file mode 100644 index 4b155fc9..00000000 --- a/src/Engine/Rendering/DrawScreenQuadPass.cpp +++ /dev/null @@ -1,37 +0,0 @@ -#include "Rendering/DrawScreenQuadPass.h" - -DrawScreenQuadPass::DrawScreenQuadPass(IRenderer* renderer) -{ - m_Renderer = renderer; - - m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); - - InitializeShaderPrograms(); -} - -void DrawScreenQuadPass::InitializeShaderPrograms() -{ - m_DrawQuadProgram = ResourceManager::Load("#DrawScreenQuadProgram"); - m_DrawQuadProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawScreenQuad.vert.glsl"))); - m_DrawQuadProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawScreenQuad.frag.glsl"))); - m_DrawQuadProgram->Compile(); - m_DrawQuadProgram->Link(); -} - -void DrawScreenQuadPass::Draw(GLuint texture) -{ - //glBindFramebuffer(GL_FRAMEBUFFER, 0); - GLERROR("DrawScreenQuadPass::Draw: Pre"); - - DrawScreenQuadPassState state = DrawScreenQuadPassState(); - m_DrawQuadProgram->Bind(); - glClear(GL_COLOR_BUFFER_BIT); - - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, texture); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); -} diff --git a/src/Engine/Rendering/DrawScreenQuadPassState.cpp b/src/Engine/Rendering/DrawScreenQuadPassState.cpp deleted file mode 100644 index 33a4895d..00000000 --- a/src/Engine/Rendering/DrawScreenQuadPassState.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include "Rendering/DrawScreenQuadPassState.h" - - -DrawScreenQuadPassState::DrawScreenQuadPassState() -{ - GLERROR("---"); - BindFramebuffer(0); - GLERROR("---"); - Disable(GL_DEPTH_TEST); - Disable(GL_CULL_FACE); - Disable(GL_BLEND); - ClearColor(glm::vec4(0.f)); -} - -DrawScreenQuadPassState::~DrawScreenQuadPassState() -{ - -} diff --git a/src/Engine/Rendering/FrameBuffer.cpp b/src/Engine/Rendering/FrameBuffer.cpp index b7e908cc..b2b29626 100644 --- a/src/Engine/Rendering/FrameBuffer.cpp +++ b/src/Engine/Rendering/FrameBuffer.cpp @@ -55,9 +55,8 @@ void FrameBuffer::Generate() glFramebufferRenderbuffer(GL_FRAMEBUFFER, (*it)->m_Attachment, (*it)->m_ResourceType, *(*it)->m_ResourceHandle); GLERROR("FrameBuffer generate: glFramebufferRenderbuffer"); if ( (*it)->m_Attachment != GL_COLOR_ATTACHMENT0 || - (*it)->m_Attachment != GL_COLOR_ATTACHMENT1 || (*it)->m_Attachment != GL_DEPTH_ATTACHMENT || - (*it)->m_Attachment != GL_STENCIL_ATTACHMENT) //TODO: Viktor: Fixa detta + (*it)->m_Attachment != GL_STENCIL_ATTACHMENT) { LOG_ERROR("RenderBuffer Attachment not valid."); } @@ -70,8 +69,10 @@ void FrameBuffer::Generate() } } + + GLenum* bufferTextures = &attachments[0]; - glDrawBuffers(attachments.size(), bufferTextures); + glDrawBuffers(1, bufferTextures); if (GLenum frameBufferStatus = glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) { LOG_ERROR("FrameBuffer incomplete: 0x%x\n", frameBufferStatus); diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index f063b344..6f448896 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -54,49 +54,52 @@ void PickingPass::Draw(RenderScene& scene) if (scene.ClearDepth) { glClear(GL_DEPTH_BUFFER_BIT); } - m_Camera = scene.Camera; - for (auto &job : scene.ForwardJobs) { - auto modelJob = std::dynamic_pointer_cast(job); + m_Camera = scene.Camera; - if (modelJob) { - int pickColor[2] = { m_ColorCounter[0], m_ColorCounter[1] }; + for (auto &job : scene.ForwardJobs) { + auto modelJob = std::dynamic_pointer_cast(job); - PickingInfo pickInfo; - pickInfo.Entity = modelJob->Entity; - pickInfo.World = modelJob->World; - pickInfo.Camera = scene.Camera; + if (modelJob) { + int pickColor[2] = { m_ColorCounter[0], m_ColorCounter[1] }; - auto color = m_EntityColors.find(std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)); - if (color != m_EntityColors.end()) { - pickColor[0] = color->second[0]; - pickColor[1] = color->second[1]; - } else { - m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); - if (m_ColorCounter[0] > 255) { - m_ColorCounter[0] = 0; - m_ColorCounter[1]++; + PickingInfo pickInfo; + pickInfo.Entity = modelJob->Entity; + pickInfo.World = modelJob->World; + pickInfo.Camera = scene.Camera; + + auto color = m_EntityColors.find(std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)); + if (color != m_EntityColors.end()) { + pickColor[0] = color->second[0]; + pickColor[1] = color->second[1]; } else { + m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); + if (m_ColorCounter[0] > 255) { + m_ColorCounter[0] = 0; + m_ColorCounter[1]++; + } else { m_ColorCounter[0]++; + } } + + m_PickingColorsToEntity[glm::ivec2(pickColor[0], pickColor[1])] = pickInfo; + + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); + glUniform2fv(glGetUniformLocation(ShaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); + + glBindVertexArray(modelJob->Model->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, nullptr, modelJob->StartIndex); } - - m_PickingColorsToEntity[glm::ivec2(pickColor[0], pickColor[1])] = pickInfo; - - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); - glUniform2fv(glGetUniformLocation(ShaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); - - glBindVertexArray(modelJob->Model->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, nullptr, modelJob->StartIndex); } - } + m_PickingBuffer.Unbind(); GLERROR("PickingPass Error"); + delete state; } diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 57849d99..e84768e4 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -63,6 +63,12 @@ void Renderer::InitializeWindow() void Renderer::InitializeShaders() { m_BasicForwardProgram = ResourceManager::Load("#m_BasicForwardProgram"); + + m_DrawScreenQuadProgram = ResourceManager::Load("#DrawScreenQuadProgram"); + m_DrawScreenQuadProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawScreenQuad.vert.glsl"))); + m_DrawScreenQuadProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawScreenQuad.frag.glsl"))); + m_DrawScreenQuadProgram->Compile(); + m_DrawScreenQuadProgram->Link(); } void Renderer::InputUpdate(double dt) @@ -80,16 +86,10 @@ void Renderer::Update(double dt) void Renderer::Draw(RenderFrame& frame) { - ImGui::Combo("Draw textures", &m_DebugTextureToDraw, "Final\0Scene\0Bloom\0Gaussian\0Picking"); - //clear buffer 0 - glClearColor(0.f, 0.f, 0.f, 0.f); + glClearColor(255.f / 255, 163.f / 255, 176.f / 255, 0.f); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - //Clear other buffers m_PickingPass->ClearPicking(); - m_DrawFinalPass->ClearBuffer(); - m_DrawBloomPass->ClearBuffer(); - for (auto scene : frame.RenderScenes){ SortRenderJobsByDepth(*scene); @@ -98,28 +98,14 @@ void Renderer::Draw(RenderFrame& frame) m_LightCullingPass->FillLightList(*scene); m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); + //m_DrawScenePass->Draw(rq); GLERROR("Renderer::Draw m_DrawScenePass->Draw"); m_TextPass->Draw(*scene); } - m_DrawBloomPass->Draw(m_DrawFinalPass->BloomTexture()); - if(m_DebugTextureToDraw == 0) { - m_DrawColorCorrectionPass->Draw(m_DrawFinalPass->SceneTexture(), m_DrawBloomPass->GaussianTexture()); - } - if (m_DebugTextureToDraw == 1) { - m_DrawScreenQuadPass->Draw(m_DrawFinalPass->SceneTexture()); - } - if (m_DebugTextureToDraw == 2) { - m_DrawScreenQuadPass->Draw(m_DrawFinalPass->BloomTexture()); - } - if (m_DebugTextureToDraw == 3) { - m_DrawScreenQuadPass->Draw(m_DrawBloomPass->GaussianTexture()); - } - if (m_DebugTextureToDraw == 4) { - m_DrawScreenQuadPass->Draw(m_PickingPass->PickingTexture()); - } + m_ImGuiRenderPass->Draw(); glfwSwapBuffers(m_Window); @@ -130,6 +116,27 @@ PickData Renderer::Pick(glm::vec2 screenCoord) return m_PickingPass->Pick(screenCoord); } +void Renderer::DrawScreenQuad(GLuint textureToDraw) +{ + glBindFramebuffer(GL_FRAMEBUFFER, 0); + + glDisable(GL_DEPTH_TEST); + glDisable(GL_CULL_FACE); + + glClearColor(0.f, 0.f, 0.f, 1.f); + glClear(GL_COLOR_BUFFER_BIT); + + + m_DrawScreenQuadProgram->Bind(); + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, textureToDraw); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); +} + void Renderer::InitializeTextures() { m_ErrorTexture = ResourceManager::Load("Textures/Core/ErrorTexture.png"); @@ -160,7 +167,4 @@ void Renderer::InitializeRenderPasses() m_PickingPass = new PickingPass(this, m_EventBroker); m_LightCullingPass = new LightCullingPass(this); m_DrawFinalPass = new DrawFinalPass(this, m_LightCullingPass); - m_DrawScreenQuadPass = new DrawScreenQuadPass(this); - m_DrawBloomPass = new DrawBloomPass(this); - m_DrawColorCorrectionPass = new DrawColorCorrectionPass(this); } diff --git a/src/Engine/Rendering/Util/CommonFunctions.cpp b/src/Engine/Rendering/Util/CommonFunctions.cpp deleted file mode 100644 index 3c81de66..00000000 --- a/src/Engine/Rendering/Util/CommonFunctions.cpp +++ /dev/null @@ -1,2 +0,0 @@ -#include "Rendering/Util/CommonFunctions.h" - From ff6ec82a6c85d2744d9889fbaad2ef60baa6e516 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sat, 23 Jan 2016 16:27:01 +0100 Subject: [PATCH 190/224] AMD fix --- src/Engine/Rendering/DrawFinalPass.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 36a14610..52a30cf1 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -39,6 +39,8 @@ void DrawFinalPass::InitializeShaderPrograms() m_ForwardPlusProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/ForwardPlus.vert.glsl"))); m_ForwardPlusProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/ForwardPlus.frag.glsl"))); m_ForwardPlusProgram->Compile(); + m_ForwardPlusProgram->BindFragDataLocation(0, "sceneColor"); + m_ForwardPlusProgram->BindFragDataLocation(1, "bloomColor"); m_ForwardPlusProgram->Link(); } From 2bf0434bcbff625d19a55bc2bc7cb1f5d2a7ff0b Mon Sep 17 00:00:00 2001 From: Jocke Date: Sat, 23 Jan 2016 16:40:38 +0100 Subject: [PATCH 191/224] Remade Snapshot logic from component based to entity based. --- include/Engine/Network/Server.h | 1 + src/Engine/Network/Client.cpp | 102 ++++++++++++++------------------ src/Engine/Network/Server.cpp | 66 +++++++++++++-------- 3 files changed, 85 insertions(+), 84 deletions(-) diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 91ea5d21..87c8d944 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -64,6 +64,7 @@ private: void send(Packet& packet); void broadcast(Packet& packet); void sendSnapshot(); + void addChildrenToPacket(Packet& packet, EntityID entityID); void sendPing(); void checkForTimeOuts(); void disconnect(UserID user); diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 1dd2bd04..387961ef 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -7,13 +7,13 @@ Client::Client(ConfigFile* config) : m_Socket(m_IOService) { Network::initialize(); - // Asumes root node is EntityID 0 - insertIntoServerClientMaps(0, 0); + // Asumes root node is EntityID_Invalid + insertIntoServerClientMaps(EntityID_Invalid, EntityID_Invalid); // Init timer m_TimeSinceSentInputs = std::clock(); // Default is local host std::string address = config->Get("Networking.Address", "127.0.0.1"); - int port = config->Get("Networking.Port", 13); + int port = config->Get("Networking.Port", 27666); m_ReceiverEndpoint = udp::endpoint(boost::asio::ip::address::from_string(address), port); // Set up network stream m_PlayerName = config->Get("Networking.Name", "Raptorcopter"); @@ -128,13 +128,13 @@ void Client::parsePing() } void Client::parseKick() -{ +{ LOG_WARNING("You have been kicked from the server."); m_IsConnected = false; } void Client::parsePlayersSpawned(Packet& packet) -{ +{ Events::PlayerSpawned e; e.Player = EntityWrapper(m_World, m_ServerIDToClientID[packet.ReadPrimitive()]); e.Spawner = EntityWrapper(m_World, m_ServerIDToClientID[packet.ReadPrimitive()]); @@ -176,66 +176,50 @@ void Client::updateFields(Packet& packet, const ComponentInfo& componentInfo, co void Client::parseSnapshot(Packet& packet) { - std::string componentType = packet.ReadString(); while (packet.DataReadSize() < packet.Size()) { - // HACK - std::string entityName = packet.ReadString(); - // Components EntityID - EntityID receivedEntityID = packet.ReadPrimitive(); - // HACK - m_World->SetName(receivedEntityID, entityName); - // Parents EntityID - EntityID receivedParentEntityID = packet.ReadPrimitive(); - ComponentInfo componentInfo = m_World->GetComponents(componentType)->ComponentInfo(); - // Check if the received EntityID is mapped to one of our local EntityIDs - if (serverClientMapsHasEntity(receivedEntityID)) { - // Get the local EntityID - EntityID entityID = m_ServerIDToClientID.at(receivedEntityID); - // Check if the component exists - if (m_World->HasComponent(entityID, componentType)) { - // If the entity and the component exists update it - if (componentType == "Transform") { - InterpolateFields(packet, componentInfo, entityID, componentType); + EntityID serverEntityID = packet.ReadPrimitive(); + EntityID serverParentID = packet.ReadPrimitive(); + std::string serverEntityName = packet.ReadString(); + int ammountOfComponents = packet.ReadPrimitive(); + for (int i = 0; i < ammountOfComponents; i++) { + std::string componentType = packet.ReadString(); + ComponentInfo componentInfo = m_World->GetComponents(componentType)->ComponentInfo(); + if (serverClientMapsHasEntity(serverEntityID)) { + EntityID localEntityID = m_ServerIDToClientID.at(serverEntityID); + // Update entity + if (m_World->HasComponent(localEntityID, componentType)) { + // Update component + if (componentType == "Transform") { + // Interpolate only transform components + InterpolateFields(packet, componentInfo, localEntityID, componentType); + } else { + // Set component values + updateFields(packet, componentInfo, localEntityID, componentType); + } } else { - updateFields(packet, componentInfo, entityID, componentType); + // Has entity but no component + m_World->AttachComponent(localEntityID, componentType); + updateFields(packet, componentInfo, localEntityID, componentType); } - // if entity exists but not the component } else { - // Create component - m_World->AttachComponent(entityID, componentType); - // Copy data to newly created component - updateFields(packet, componentInfo, entityID, componentType); + // Create Entity and component + EntityID newLocalEntityID; + if (serverParentID == EntityID_Invalid) { + newLocalEntityID = m_World->CreateEntity(EntityID_Invalid); + } else { + newLocalEntityID = m_World->CreateEntity(m_ServerIDToClientID.at(serverParentID)); + } + m_World->SetName(newLocalEntityID, serverEntityName); + insertIntoServerClientMaps(serverEntityID, newLocalEntityID); + m_World->AttachComponent(newLocalEntityID, componentType); + updateFields(packet, componentInfo, newLocalEntityID, componentType); } - // If the entity dosent exist nor the component - } else { - // Create Entity - // If entity dosen't exist - EntityID newEntityID = m_World->CreateEntity(); - insertIntoServerClientMaps(receivedEntityID, newEntityID); - // Check if EntityIDs are out of sync - if (newEntityID != receivedEntityID) { - LOG_INFO("Client::parseSnapshot(Packet& packet): Newly created EntityID is not the \ - same as the one sent by server (EntityIDs are out of sync)"); - } - // Create component - m_World->AttachComponent(newEntityID, componentType); - // Copy data to newly created component - updateFields(packet, componentInfo, newEntityID, componentType); } - - // Parent Logic - // Don't need to check if receivedEntityID is mapped. (It should have been set) - if (receivedParentEntityID != std::numeric_limits::max()) { - if (serverClientMapsHasEntity(receivedParentEntityID)) { - m_World->SetParent(m_ServerIDToClientID.at(receivedEntityID), m_ServerIDToClientID.at(receivedParentEntityID)); - // If Parent dosen't exist create one and map receivedParentEntityID to it. - } else { - // Create the new parent and add it to map - EntityID newParentEntityID = m_World->CreateEntity(); - insertIntoServerClientMaps(receivedParentEntityID, newParentEntityID); - // Set the newly created Entity as parent. - m_World->SetParent(m_ServerIDToClientID.at(receivedEntityID), newParentEntityID); - } + // Parent logic + // This should be enough beacause we know that the entities arives in pre-order (there will always be a parent) + if (serverParentID != EntityID_Invalid) { + EntityID localEntityID = m_ServerIDToClientID.at(serverEntityID); + m_World->SetParent(localEntityID, m_ServerIDToClientID.at(serverParentID)); } } } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 9d0a83d9..98774b99 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -175,35 +175,51 @@ void Server::broadcast(Packet& packet) // Send snapshot fields void Server::sendSnapshot() { - // Should time this - std::unordered_map worldComponentPools = m_World->GetComponentPools(); - for (auto& it : worldComponentPools) { - Packet packet(MessageType::Snapshot); - ComponentPool* componentPool = it.second; - ComponentInfo componentInfo = componentPool->ComponentInfo(); + Packet packet(MessageType::Snapshot); + addChildrenToPacket(packet, EntityID_Invalid); + broadcast(packet); +} - // Component Type - packet.WriteString(componentInfo.Name); - for (auto& componentWrapper : *componentPool) { - // HACK: Send entity name - packet.WriteString(m_World->GetName(componentWrapper.EntityID)); - // Components EntityID - packet.WritePrimitive(componentWrapper.EntityID); - // Parents EntityID - packet.WritePrimitive(m_World->GetParent(componentWrapper.EntityID)); - for (auto& componentField : componentWrapper.Info.FieldsInOrder) { - ComponentInfo::Field_t fieldInfo = componentInfo.Fields.at(componentField); - if (fieldInfo.Type == "string") { - std::string& value = componentWrapper[componentField]; - packet.WriteString(value); - } else { - packet.WriteData(componentWrapper.Data + fieldInfo.Offset, fieldInfo.Stride); +void Server::addChildrenToPacket(Packet & packet, EntityID entityID) +{ + auto itPair = m_World->GetChildren(entityID); + std::unordered_map worldComponentPools = m_World->GetComponentPools(); + // Loop through every child + for (auto it = itPair.first; it != itPair.second; it++) { + EntityID childEntityID = it->second; + // Write EntityID and parentsID and Entity name + packet.WritePrimitive(childEntityID); + packet.WritePrimitive(entityID); + packet.WriteString(m_World->GetName(childEntityID)); + // Write components to child + int numberOfComponents = 0; + for (auto& i : worldComponentPools) { + if (i.second->KnowsEntity(childEntityID)) { + numberOfComponents++; + } + } + // Write how many components should be read + packet.WritePrimitive(numberOfComponents); + for (auto& i : worldComponentPools) { + // If the entity exist in the pool + if (i.second->KnowsEntity(childEntityID)) { + ComponentWrapper componentWrapper = i.second->GetByEntity(childEntityID); + // ComponentType + packet.WriteString(componentWrapper.Info.Name); + // Loop through fields + for (auto& componentField : componentWrapper.Info.FieldsInOrder) { + ComponentInfo::Field_t fieldInfo = componentWrapper.Info.Fields.at(componentField); + if (fieldInfo.Type == "string") { + std::string& value = componentWrapper[componentField]; + packet.WriteString(value); + } else { + packet.WriteData(componentWrapper.Data + fieldInfo.Offset, fieldInfo.Stride); + } } } } - if (packet.Size() > packet.HeaderSize() + componentInfo.Name.size()) { - broadcast(packet); - } + // Go to to your children + addChildrenToPacket(packet, childEntityID); } } From 5edf5a41f136ea21a34ad57bb36dfb2bf87edba1 Mon Sep 17 00:00:00 2001 From: Tleety Date: Sat, 23 Jan 2016 16:45:26 +0100 Subject: [PATCH 192/224] Transparency bug fix --- resources/Shaders/ForwardPlus.frag.glsl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 403c96fc..e158640e 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -137,7 +137,7 @@ void main() //sceneColor += Input.DiffuseColor; vec4 color_result = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * diffuseTexel * Color; //bloomColor = vec4(0.3, 0.8, 0.6, 1.0); - sceneColor = vec4(color_result.xyz, 1.0); + sceneColor = vec4(color_result.xyz, clamp(color_result.a, 0, 1)); //These if statements should be removed if they are slow. color_result += glowTexel; bloomColor = vec4(clamp(color_result.xyz - 1.0, 0, 100), 1.0); From f1835fd89c2abcd9e069bc3e4074cd42db1db8ef Mon Sep 17 00:00:00 2001 From: antc13 Date: Sat, 23 Jan 2016 18:02:42 +0100 Subject: [PATCH 193/224] Animations PROBABLY works fine if all joints got keyframes. --- include/Engine/Collision/Collision.h | 4 +- .../Rendering/DebugCameraInputController.h | 2 +- include/Engine/Rendering/Model.h | 3 +- include/Engine/Rendering/RawModelAssimp.h | 11 +- include/Engine/Rendering/RawModelCustom.h | 17 ++- include/Engine/Rendering/Skeleton.h | 1 + resources/Schema/Entities/Model.xml | 2 +- resources/Shaders/ForwardPlus.vert.glsl | 13 ++- src/Engine/Editor/EditorSystem.cpp | 12 ++ src/Engine/Rendering/DrawFinalPass.cpp | 20 +++- src/Engine/Rendering/Model.cpp | 3 + src/Engine/Rendering/RawModelAssimp.cpp | 11 +- src/Engine/Rendering/RawModelCustom.cpp | 46 ++++---- src/Engine/Rendering/RenderSystem.cpp | 8 ++ src/Engine/Rendering/Skeleton.cpp | 9 +- src/Tests/CollisionTest.cpp | 4 +- tools/MayaExporter/MayaExporter/Export.cpp | 59 ++++++++-- .../MayaExporter/MayaExporter/MayaIncludes.h | 3 + tools/MayaExporter/MayaExporter/Menu.cpp | 16 +-- tools/MayaExporter/MayaExporter/Mesh.cpp | 61 ++++++---- tools/MayaExporter/MayaExporter/Skeleton.cpp | 104 ++++++++++++++++-- 21 files changed, 325 insertions(+), 84 deletions(-) diff --git a/include/Engine/Collision/Collision.h b/include/Engine/Collision/Collision.h index 207d4893..194a18dc 100644 --- a/include/Engine/Collision/Collision.h +++ b/include/Engine/Collision/Collision.h @@ -10,8 +10,8 @@ #include "../Core/Ray.h" #include "../Core/AABB.h" -//#include "Engine/Rendering/RawModelAssimp.h" -#include "Engine/Rendering/RawModelCustom.h" +#include "Rendering/RawModelCustom.h" +//#include "Rendering/RawModelAssimp.h" #include "../Core/Transform.h" #include "../Core/Entity.h" #include "../Core/EntityWrapper.h" diff --git a/include/Engine/Rendering/DebugCameraInputController.h b/include/Engine/Rendering/DebugCameraInputController.h index 4d74e288..d69098c2 100644 --- a/include/Engine/Rendering/DebugCameraInputController.h +++ b/include/Engine/Rendering/DebugCameraInputController.h @@ -61,6 +61,6 @@ public: protected: glm::vec3 m_Position = glm::vec3(0, 0, 0); glm::vec3 m_Velocity = glm::vec3(0, 0, 0); - float m_BaseSpeed = 2.0f; + float m_BaseSpeed = 50.0f;//2.0f; float m_Speed = m_BaseSpeed; }; \ No newline at end of file diff --git a/include/Engine/Rendering/Model.h b/include/Engine/Rendering/Model.h index 4b83562c..f751a8cc 100644 --- a/include/Engine/Rendering/Model.h +++ b/include/Engine/Rendering/Model.h @@ -1,7 +1,8 @@ #ifndef Model_h__ #define Model_h__ -#include "RawModelCustom.h" +#include "Rendering/RawModelCustom.h" +//#include "Rendering/RawModelAssimp.h" #include "../OpenGL.h" class Model : public ThreadUnsafeResource diff --git a/include/Engine/Rendering/RawModelAssimp.h b/include/Engine/Rendering/RawModelAssimp.h index 92258782..08df818d 100644 --- a/include/Engine/Rendering/RawModelAssimp.h +++ b/include/Engine/Rendering/RawModelAssimp.h @@ -1,6 +1,8 @@ #ifndef RawModelAssimp_h__ #define RawModelAssimp_h__ +#ifdef USING_ASSIMP_AS_IMPORTER + #include #include #include @@ -18,15 +20,17 @@ #include "Texture.h" #include "Skeleton.h" -class RawModel : public Resource +#define RawModel RawModelAssimp + +class RawModelAssimp : public Resource { friend class ResourceManager; protected: - RawModel(std::string fileName); + RawModelAssimp(std::string fileName); public: - ~RawModel(); + ~RawModelAssimp(); struct Vertex { @@ -72,3 +76,4 @@ private: }; #endif +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/RawModelCustom.h b/include/Engine/Rendering/RawModelCustom.h index a3c29f62..2dea51ff 100644 --- a/include/Engine/Rendering/RawModelCustom.h +++ b/include/Engine/Rendering/RawModelCustom.h @@ -1,6 +1,10 @@ #ifndef RawModelCustom_h__ #define RawModelCustom_h__ +#ifndef USING_ASSIMP_AS_IMPORTER + +#define RawModel RawModelCustom + #include #include #include @@ -17,15 +21,17 @@ #include "boost\endian\buffers.hpp" -class RawModel : public Resource + + +class RawModelCustom : public Resource { friend class ResourceManager; protected: - RawModel(std::string fileName); + RawModelCustom(std::string fileName); public: - ~RawModel(); + ~RawModelCustom(); struct Vertex { @@ -85,4 +91,9 @@ private: //void CreateSkeleton(std::vector> &boneInfo, std::map &boneNameMapping, aiNode* node, int parentID); }; +#else + +#include "RawModelAssimp.h" + #endif +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/Skeleton.h b/include/Engine/Rendering/Skeleton.h index 4a4d507b..3b89b89b 100644 --- a/include/Engine/Rendering/Skeleton.h +++ b/include/Engine/Rendering/Skeleton.h @@ -4,6 +4,7 @@ #include #include "Common.h" #include "../GLM.h" +#include //struct Bone //{ diff --git a/resources/Schema/Entities/Model.xml b/resources/Schema/Entities/Model.xml index 6534815c..57856cbd 100644 --- a/resources/Schema/Entities/Model.xml +++ b/resources/Schema/Entities/Model.xml @@ -19,7 +19,7 @@ - models/Baljj.mesh + models/animTest.mesh diff --git a/resources/Shaders/ForwardPlus.vert.glsl b/resources/Shaders/ForwardPlus.vert.glsl index e4b4eacc..aa8c9446 100644 --- a/resources/Shaders/ForwardPlus.vert.glsl +++ b/resources/Shaders/ForwardPlus.vert.glsl @@ -3,6 +3,7 @@ uniform mat4 M; uniform mat4 V; uniform mat4 P; +uniform mat4 Bones[100]; layout(location = 0) in vec3 Position; layout(location = 1) in vec3 Normal; @@ -20,9 +21,17 @@ out VertexData{ void main() { - gl_Position = P*V*M * vec4(Position, 1.0); - Output.Position = Position; + + mat4 boneTransform = mat4(1); + boneTransform = BoneWeights[0] * Bones[int(BoneIndices[0])] + + BoneWeights[1] * Bones[int(BoneIndices[1])] + + BoneWeights[2] * Bones[int(BoneIndices[2])] + + BoneWeights[3] * Bones[int(BoneIndices[3])]; + + gl_Position = P*V*M*boneTransform * vec4(Position, 1.0); + + Output.Position = (boneTransform * vec4(Position, 1.0)).xyz; Output.TextureCoordinate = TextureCoords; Output.Normal = vec3(M * vec4(Normal, 0.0)); } \ No newline at end of file diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 547a96e1..46aad8df 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -292,21 +292,33 @@ void EditorSystem::createWidget() m_WidgetPlaneX = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneX, "Transform"); m_World->AttachComponent(m_WidgetPlaneX, "Model"); +#ifdef USING_ASSIMP_AS_IMPORTER + m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; // 360NoScope widgetPlaneX +#else m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneX +#endif m_WidgetY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetY, "Transform"); m_World->AttachComponent(m_WidgetY, "Model"); m_WidgetPlaneY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneY, "Transform"); m_World->AttachComponent(m_WidgetPlaneY, "Model"); +#ifdef USING_ASSIMP_AS_IMPORTER + m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; // 360NoScope widgetPlaneY +#else m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneY +#endif m_WidgetZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetZ, "Transform"); m_World->AttachComponent(m_WidgetZ, "Model"); m_WidgetPlaneZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetPlaneZ, "Transform"); m_World->AttachComponent(m_WidgetPlaneZ, "Model"); +#ifdef USING_ASSIMP_AS_IMPORTER + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; // 360NoScope widgetPlaneZ +#else m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneZ +#endif m_WidgetOrigin = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetOrigin, "Transform"); m_World->AttachComponent(m_WidgetOrigin, "Model"); diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 7093b00f..1dd5f9bc 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -22,6 +22,8 @@ void DrawFinalPass::InitializeShaderPrograms() m_ForwardPlusProgram->Link(); } +static double tempFrameCounter = 6.348; + void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); @@ -38,6 +40,7 @@ void DrawFinalPass::Draw(RenderScene& scene) glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ProjectionMatrix())); glUniform2f(glGetUniformLocation(shaderHandle, "ScreenDimensions"), m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); + //tempFrameCounter += 0.01; //TODO: Render: Add code for more jobs than modeljobs. for (auto &job : scene.ForwardJobs) { auto modelJob = std::dynamic_pointer_cast(job); @@ -54,6 +57,21 @@ void DrawFinalPass::Draw(RenderScene& scene) glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); } + if (modelJob->Model->m_RawModel->m_Skeleton != nullptr) { +#ifdef USING_ASSIMP_AS_IMPORTER + auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("combinedAnim_0"); +#else + auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("running"); +#endif + if (animation != nullptr) { + std::vector frameBones = modelJob->Model->m_RawModel->m_Skeleton->GetFrameBones( + *animation, + tempFrameCounter + ); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "Bones"), frameBones.size(), GL_FALSE, glm::value_ptr(frameBones[0])); + } + } + // -3 - 9 glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); glDrawElements(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, (void*)(modelJob->StartIndex * sizeof(unsigned int))); @@ -61,4 +79,4 @@ void DrawFinalPass::Draw(RenderScene& scene) } GLERROR("DrawFinalPass::Draw: END"); -} +} \ No newline at end of file diff --git a/src/Engine/Rendering/Model.cpp b/src/Engine/Rendering/Model.cpp index c8a2bc41..cf4923a3 100644 --- a/src/Engine/Rendering/Model.cpp +++ b/src/Engine/Rendering/Model.cpp @@ -15,6 +15,9 @@ Model::Model(std::string fileName) if (!group.SpecularMapPath.empty()) { group.SpecularMap = std::shared_ptr(ResourceManager::Load(group.SpecularMapPath)); } + if (!group.IncandescenceMapPath.empty()) { + group.IncandescenceMap = std::shared_ptr(ResourceManager::Load(group.IncandescenceMapPath)); + } } // Generate GL buffers diff --git a/src/Engine/Rendering/RawModelAssimp.cpp b/src/Engine/Rendering/RawModelAssimp.cpp index 259eafc3..6bc3f3f7 100644 --- a/src/Engine/Rendering/RawModelAssimp.cpp +++ b/src/Engine/Rendering/RawModelAssimp.cpp @@ -1,6 +1,8 @@ #include "Rendering/RawModelAssimp.h" -RawModel::RawModel(std::string fileName) +#ifdef USING_ASSIMP_AS_IMPORTER + +RawModelAssimp::RawModelAssimp(std::string fileName) { Assimp::Importer importer; const aiScene* scene = importer.ReadFile(fileName, aiProcess_CalcTangentSpace | aiProcess_Triangulate); @@ -271,16 +273,17 @@ RawModel::RawModel(std::string fileName) m_Skeleton->Animations[animationName] = skelAnim; } + int k = 0; } -RawModel::~RawModel() +RawModelAssimp::~RawModelAssimp() { if (m_Skeleton) { delete m_Skeleton; } } -void RawModel::CreateSkeleton(std::vector> &boneInfo, std::map &boneNameMapping, aiNode* node, int parentID) +void RawModelAssimp::CreateSkeleton(std::vector> &boneInfo, std::map &boneNameMapping, aiNode* node, int parentID) { std::string nodeName = node->mName.C_Str(); @@ -300,3 +303,5 @@ void RawModel::CreateSkeleton(std::vector> &b CreateSkeleton(boneInfo, boneNameMapping, child, parentID); } } + +#endif \ No newline at end of file diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index f7354d92..7c387dd9 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -1,6 +1,8 @@ #include "Rendering/RawModelCustom.h" -RawModel::RawModel(std::string fileName) +#ifndef USING_ASSIMP_AS_IMPORTER + +RawModelCustom::RawModelCustom(std::string fileName) { fileName = fileName.erase(fileName.find_last_of("."), fileName.find_last_of(".") - fileName.size()); ReadMeshFile(fileName); @@ -9,7 +11,7 @@ RawModel::RawModel(std::string fileName) int k = 0; } -void RawModel::ReadMeshFile(std::string filePath) +void RawModelCustom::ReadMeshFile(std::string filePath) { char* fileData; filePath += ".mesh"; @@ -33,7 +35,7 @@ void RawModel::ReadMeshFile(std::string filePath) delete fileData; } -void RawModel::ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN m_Vertices.resize(*(unsigned int*)(fileData + offset)); @@ -44,13 +46,13 @@ void RawModel::ReadMeshFileHeader(unsigned int& offset, char* fileData, unsigned #endif } -void RawModel::ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadMesh(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { ReadVertices(offset, fileData, fileByteSize); ReadIndices(offset, fileData, fileByteSize); } -void RawModel::ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadVertices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN if (offset + m_Vertices.size() * sizeof(Vertex) > fileByteSize) { @@ -63,7 +65,7 @@ void RawModel::ReadVertices(unsigned int& offset, char* fileData, unsigned int& #endif } -void RawModel::ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadIndices(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN if (offset + m_Indices.size() * sizeof(unsigned int) > fileByteSize) { @@ -77,7 +79,7 @@ void RawModel::ReadIndices(unsigned int& offset, char* fileData, unsigned int& f #endif } -void RawModel::ReadMaterialFile(std::string filePath) +void RawModelCustom::ReadMaterialFile(std::string filePath) { char* fileData; filePath += ".mtrl"; @@ -100,7 +102,7 @@ void RawModel::ReadMaterialFile(std::string filePath) delete fileData; } -void RawModel::ReadMaterials(unsigned int& offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadMaterials(unsigned int& offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN unsigned int* numMaterials = (unsigned int*)(fileData); @@ -114,7 +116,7 @@ void RawModel::ReadMaterials(unsigned int& offset, char* fileData, unsigned int& #endif } -void RawModel::ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize) { MaterialGroup newMaterial; @@ -189,7 +191,7 @@ void RawModel::ReadMaterialSingle(unsigned int &offset, char* fileData, unsigned MaterialGroups.push_back(newMaterial); } -void RawModel::ReadAnimationFile(std::string filePath) +void RawModelCustom::ReadAnimationFile(std::string filePath) { char* fileData; filePath += ".anim"; @@ -214,7 +216,7 @@ void RawModel::ReadAnimationFile(std::string filePath) #ifdef BOOST_LITTLE_ENDIAN unsigned int numBindPoses = *(unsigned int*)(fileData); offset += sizeof(unsigned int); - unsigned int numAnimations = *(unsigned int*)(fileData); + unsigned int numAnimations = *(unsigned int*)(fileData + offset); offset += sizeof(unsigned int); #else #endif @@ -225,7 +227,7 @@ void RawModel::ReadAnimationFile(std::string filePath) delete fileData; } -void RawModel::ReadAnimationBindPoses(unsigned int &offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadAnimationBindPoses(unsigned int &offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN unsigned int* numBones = (unsigned int*)(fileData + offset); @@ -238,7 +240,7 @@ void RawModel::ReadAnimationBindPoses(unsigned int &offset, char* fileData, unsi #endif } -void RawModel::ReadAnimationJoint(unsigned int &offset, char* fileData, unsigned int& fileByteSize) +void RawModelCustom::ReadAnimationJoint(unsigned int &offset, char* fileData, unsigned int& fileByteSize) { #ifdef BOOST_LITTLE_ENDIAN if (offset + sizeof(unsigned int) > fileByteSize) { @@ -259,7 +261,7 @@ void RawModel::ReadAnimationJoint(unsigned int &offset, char* fileData, unsigned glm::mat4 offsetMatrix; memcpy(&offsetMatrix, fileData + offset, sizeof(float) * 4 * 4); offset += sizeof(float) * 4 * 4; - + if (offset + sizeof(int) > fileByteSize) { throw Resource::FailedLoadingException("Reading Joint ID failed"); } @@ -280,14 +282,14 @@ void RawModel::ReadAnimationJoint(unsigned int &offset, char* fileData, unsigned #endif } -void RawModel::ReadAnimationClips(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int numberOfClips) +void RawModelCustom::ReadAnimationClips(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int numberOfClips) { for (unsigned int i = 0; i < numberOfClips; i++) { ReadAnimationClipSingle(offset, fileData, fileByteSize, i); } } -void RawModel::ReadAnimationClipSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int clipIndex) +void RawModelCustom::ReadAnimationClipSingle(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int clipIndex) { #ifdef BOOST_LITTLE_ENDIAN Skeleton::Animation newAnimation; @@ -332,7 +334,7 @@ void RawModel::ReadAnimationClipSingle(unsigned int &offset, char* fileData, uns #endif } -void RawModel::ReadAnimationKeyFrame(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int nrOfJoints, Skeleton::Animation& animation) +void RawModelCustom::ReadAnimationKeyFrame(unsigned int &offset, char* fileData, unsigned int& fileByteSize, unsigned int nrOfJoints, Skeleton::Animation& animation) { Skeleton::Animation::Keyframe newKeyFrame; @@ -356,12 +358,16 @@ void RawModel::ReadAnimationKeyFrame(unsigned int &offset, char* fileData, unsig for (unsigned int i = 0; i < nrOfJoints; i++) { memcpy(&newBone, (fileData + offset), sizeof(Skeleton::Animation::Keyframe::BoneProperty)); offset += sizeof(Skeleton::Animation::Keyframe::BoneProperty); - newKeyFrame.BoneProperties[i] = newBone; + newKeyFrame.BoneProperties[newBone.ID] = newBone; } animation.Keyframes.push_back(newKeyFrame); } -RawModel::~RawModel() +RawModelCustom::~RawModelCustom() { + if (m_Skeleton != nullptr) { + delete m_Skeleton; + } +} -} \ No newline at end of file +#endif \ No newline at end of file diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 2a6a49c2..5d9d474d 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -96,10 +96,18 @@ void RenderSystem::fillModels(std::list>& jobs, World model = ResourceManager::Load<::Model, true>(resource); } catch (const Resource::StillLoadingException&) { //continue; +#ifdef USING_ASSIMP_AS_IMPORTER + model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.obj"); // 360NoScope StillLoading mesh +#else model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); // 360NoScope StillLoading mesh +#endif } catch (const std::exception&) { try { +#ifdef USING_ASSIMP_AS_IMPORTER + model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.obj"); // 360NoScope Error mesh +#else model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); // 360NoScope Error mesh +#endif } catch (const std::exception&) { continue; } diff --git a/src/Engine/Rendering/Skeleton.cpp b/src/Engine/Rendering/Skeleton.cpp index 44276308..986e634c 100644 --- a/src/Engine/Rendering/Skeleton.cpp +++ b/src/Engine/Rendering/Skeleton.cpp @@ -68,7 +68,7 @@ std::vector Skeleton::GetFrameBones(const Animation& animation, doubl void Skeleton::AccumulateBoneTransforms(bool noRootMotion, const Animation::Keyframe ¤tFrame, const Animation::Keyframe &nextFrame, float progress, std::map &boneMatrices, const Bone* bone, glm::mat4 parentMatrix) { - glm::mat4 boneMatrix; + glm::mat4 boneMatrix; if (currentFrame.BoneProperties.find(bone->ID) != currentFrame.BoneProperties.end() || nextFrame.BoneProperties.find(bone->ID) != nextFrame.BoneProperties.end()) { Animation::Keyframe::BoneProperty currentBoneProperty = currentFrame.BoneProperties.at(bone->ID); @@ -84,10 +84,14 @@ void Skeleton::AccumulateBoneTransforms(bool noRootMotion, const Animation::Keyf positionInterp.z = 0; } + boneMatrix = parentMatrix * (glm::translate(positionInterp) * glm::toMat4(rotationInterp) * glm::scale(scaleInterp)); boneMatrices[bone->ID] = boneMatrix * bone->OffsetMatrix; + int k = 0; } else { - boneMatrix = parentMatrix * bone->Parent->OffsetMatrix; // * glm::inverse(bone->OffsetMatrix); + if (bone->Parent) { + boneMatrix = parentMatrix * bone->Parent->OffsetMatrix * glm::translate(glm::vec3(1.718, 0, 0)); // * glm::inverse(bone->OffsetMatrix); + } boneMatrices[bone->ID] = boneMatrix; // * bone->OffsetMatrix; } @@ -95,6 +99,7 @@ void Skeleton::AccumulateBoneTransforms(bool noRootMotion, const Animation::Keyf std::string name = child->Name; AccumulateBoneTransforms(noRootMotion, currentFrame, nextFrame, progress, boneMatrices, child, boneMatrix); } + } int Skeleton::GetBoneID(std::string name) diff --git a/src/Tests/CollisionTest.cpp b/src/Tests/CollisionTest.cpp index 4ba7ca87..767fbe3a 100644 --- a/src/Tests/CollisionTest.cpp +++ b/src/Tests/CollisionTest.cpp @@ -27,7 +27,9 @@ using boost::unit_test_framework::test_case; void RayTest(std::string fileName) { //simple box test Ray ray(glm::vec3(-50, 0, 0), glm::vec3(1, 0, 0)); - //using a rawmodel here, else we have to init the renderingsystem + //using a + + here, else we have to init the renderingsystem ResourceManager::RegisterType("RawModel"); auto unitBox = ResourceManager::Load(fileName); BOOST_REQUIRE(unitBox != nullptr); diff --git a/tools/MayaExporter/MayaExporter/Export.cpp b/tools/MayaExporter/MayaExporter/Export.cpp index d25faa4c..d8f1abd4 100644 --- a/tools/MayaExporter/MayaExporter/Export.cpp +++ b/tools/MayaExporter/MayaExporter/Export.cpp @@ -7,26 +7,56 @@ Export::Export() bool Export::Meshes(std::string pathName, bool selectedOnly) { + MStatus status; if (pathName.empty()) { MGlobal::displayError(MString() + "Export::Meshes() got no pathName. Do not know where to write file"); return false; } + MSelectionList selectedOnStart; MGlobal::getActiveSelectionList(selectedOnStart); - + if (selectedOnStart.length() > 0) { + for (int i = 0; i < selectedOnStart.length(); i++) { + MObject item; + selectedOnStart.getDependNode(i, item); + MGlobal::unselect(item); + } + } + MGlobal::displayInfo(MString() + "Disabel IKSolvers"); + status = MGlobal::executeCommand("doEnableNodeItems false all;"); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "EnableNodeItems false all failed: " + status.errorString()); + } + MGlobal::displayInfo(MString() + "Has disabel IKSolvers"); MObjectArray Objects; if (selectedOnly) { // Retrieving the objects we currently have selected - MSelectionList selected; - MGlobal::getActiveSelectionList(selected); // Loop through or list of selection(s) - for (unsigned int i = 0; i < selected.length(); i++) { + for (unsigned int i = 0; i < selectedOnStart.length(); i++) { MObject object; - selected.getDependNode(i, object); + selectedOnStart.getDependNode(i, object); if (object.hasFn(MFn::kMesh)) { - MFnDependencyNode thisNode(object); + MFnMesh shape(object); + + for (unsigned int k = 0; k < shape.parentCount(); k++) { + MFnDependencyNode thisNode(object); + MPlugArray connections; + thisNode.findPlug("inMesh").connectedTo(connections, true, true); + + for (unsigned int i = 0; i < connections.length(); i++) { + if (connections[i].node().apiType() == MFn::kSkinClusterFilter) { + MGlobal::select(shape.parent(i), MGlobal::kReplaceList); + MGlobal::displayInfo(MString() + "Moving " + thisNode.name() + " to bindPose."); + status = MGlobal::executeCommand("GoToBindPose;"); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "GoToBindPose: " + status.errorString()); + } + MGlobal::displayInfo(MString() + "Has moved " + thisNode.name() + " to bindPose."); + } + } + } Objects.append(object); } } @@ -42,7 +72,9 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) for (unsigned int i = 0; i < connections.length(); i++) { if (connections[i].node().apiType() == MFn::kSkinClusterFilter) { MGlobal::select(node); - MGlobal::executeCommand("gotoBindPose"); + MGlobal::displayInfo(MString() + "Moving " + thisNode.name() + " to bindPose."); + MGlobal::executeCommand("GoToBindPose"); + MGlobal::displayInfo(MString() + "Has moved " + thisNode.name() + " to bindPose."); } } @@ -51,6 +83,19 @@ bool Export::Meshes(std::string pathName, bool selectedOnly) } GetMeshData(Objects); WriteMeshData(pathName); + MGlobal::displayInfo(MString() + "Enabling IKSolvers"); + status = MGlobal::executeCommand("doEnableNodeItems true all;"); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "doEnableNodeItems true all: " + status.errorString()); + } + MGlobal::displayInfo(MString() + "Has enabling IKSolvers"); + if (selectedOnStart.length() > 0) { + for (int i = 0; i < selectedOnStart.length(); i++) { + MObject item; + selectedOnStart.getDependNode(i, item); + MGlobal::select(item); + } + } return true; } diff --git a/tools/MayaExporter/MayaExporter/MayaIncludes.h b/tools/MayaExporter/MayaExporter/MayaIncludes.h index 66527470..7322bdc5 100644 --- a/tools/MayaExporter/MayaExporter/MayaIncludes.h +++ b/tools/MayaExporter/MayaExporter/MayaIncludes.h @@ -42,6 +42,9 @@ #include #include #include +#include +#include +#include // Wrappers diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index a03788a6..897cc655 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -60,7 +60,7 @@ Menu::Menu(QDialog* dialog) m_ExportPath = new QLineEdit; m_FileDialog = new QFileDialog; - QString tmpPath("C:/Users/Nickelodion/Desktop/Baljj"); + QString tmpPath("C:/Users/Nickelodion/Desktop/animTest"); m_ExportPath->setText(tmpPath); QLabel* exportLabel = new QLabel; exportLabel->setText("Export Path:"); @@ -175,6 +175,13 @@ void Menu::ExportAll(bool) return; } + if (m_ExportMaterialButton->isChecked()) { + if (!m_Export.Materials(m_ExportPath->text().toLocal8Bit().constData())) { + MGlobal::displayError(MString() + "Could not export materials"); + return; + } + } + std::vector animations; for (unsigned int i = 0; i < m_AnimationClipName.size(); i++) { Export::AnimationInfo thisClip; @@ -191,13 +198,6 @@ void Menu::ExportAll(bool) return; } } - - if (m_ExportMaterialButton->isChecked()) { - if (!m_Export.Materials(m_ExportPath->text().toLocal8Bit().constData())){ - MGlobal::displayError(MString() + "Could not export materials"); - return; - } - } } void Menu::CancelClicked(bool) diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index 2062bad5..26d5c7b2 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -68,7 +68,6 @@ std::map MeshClass::GetWeightData() break; } MFnDependencyNode test(comp); - unsigned int nrOfWeights = 0; for (unsigned int j = 0; j < weights.length() && nrOfWeights != 4; j++) { @@ -90,7 +89,7 @@ std::map MeshClass::GetWeightData() for (unsigned int k = 0; k!=nrOfWeights; k++) { - //MGlobal::displayInfo(MString() + "influence: " + weightInfo.BoneIndices[k] + " weight: " + weightInfo.BoneWeights[k]); + MGlobal::displayInfo(MString() + "influence: " + weightInfo.BoneIndices[k] + " weight: " + weightInfo.BoneWeights[k]); } geomIter.next(); } @@ -109,6 +108,26 @@ Mesh MeshClass::GetMeshData(MObjectArray object) if (!object[ObjectID].hasFn(MFn::kMesh)) continue; + MObject node = object[ObjectID]; + MFnDependencyNode thisNode(node); + MPlugArray connections; + thisNode.findPlug("inMesh").connectedTo(connections, true, true); + MGlobal::displayInfo(MString() + "inMesh"); + bool hasSkin = false; + MPlug weightList, weights; + MObject weightListObject; + for (unsigned int i = 0; i < connections.length(); i++) { + if (connections[i].node().apiType() == MFn::kSkinClusterFilter) { + MFnSkinCluster skinCluster(connections[i].node()); + weightList = skinCluster.findPlug("weightList", &status); + weightListObject = weightList.attribute(); + weights = skinCluster.findPlug("weights"); + hasSkin = true; + break; + } + } + + // In here, we retrieve triangulated polygons from the mesh MFnMesh mesh(object[ObjectID]); MDagPathArray dagPaths; @@ -178,7 +197,7 @@ Mesh MeshClass::GetMeshData(MObjectArray object) } } - map vertexWeights = GetWeightData(); + // map vertexWeights = GetWeightData(); status = mesh.getTangents(Tangents, MSpace::kObject); if (status != MS::kSuccess) { MGlobal::displayError(MString() + "mesh.getTangents ERROR: " + status.errorString() + " for " + thisMeshPath.fullPathName()); @@ -288,27 +307,25 @@ Mesh MeshClass::GetMeshData(MObjectArray object) thisVertex.Uv[0] = UV[0]; thisVertex.Uv[1] = UV[1]; - thisVertex.BoneIndices[0] = vertexWeights[faceVert.vertId()].BoneIndices[0]; - thisVertex.BoneIndices[1] = vertexWeights[faceVert.vertId()].BoneIndices[1]; - thisVertex.BoneIndices[2] = vertexWeights[faceVert.vertId()].BoneIndices[2]; - thisVertex.BoneIndices[3] = vertexWeights[faceVert.vertId()].BoneIndices[3]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[0]) > 0.0001) - thisVertex.BoneWeights[0] = vertexWeights[faceVert.vertId()].BoneWeights[0]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[1]) > 0.0001) - thisVertex.BoneWeights[1] = vertexWeights[faceVert.vertId()].BoneWeights[1]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[2]) > 0.0001) - thisVertex.BoneWeights[2] = vertexWeights[faceVert.vertId()].BoneWeights[2]; - if (abs(vertexWeights[faceVert.vertId()].BoneWeights[3]) > 0.0001) - thisVertex.BoneWeights[3] = vertexWeights[faceVert.vertId()].BoneWeights[3]; - - float totalWeight = thisVertex.BoneWeights[0] + thisVertex.BoneWeights[1] + thisVertex.BoneWeights[2] + thisVertex.BoneWeights[3]; - if (totalWeight < 1.00f && totalWeight > 0.01f) { - thisVertex.BoneWeights[0] /= totalWeight; - thisVertex.BoneWeights[1] /= totalWeight; - thisVertex.BoneWeights[2] /= totalWeight; - thisVertex.BoneWeights[3] /= totalWeight; + + if (hasSkin) { + MIntArray jointIDs /* ??? */; + weights.selectAncestorLogicalIndex(vertexIndex, weightListObject); + weights.getExistingArrayAttributeIndices(jointIDs); + for (unsigned int i = 0; i < jointIDs.length() && i < 4; i++) { + thisVertex.BoneIndices[i] = jointIDs[i]; + thisVertex.BoneWeights[i] = weights[i].asFloat(); + } } + //float totalWeight = thisVertex.BoneWeights[0] + thisVertex.BoneWeights[1] + thisVertex.BoneWeights[2] + thisVertex.BoneWeights[3]; + //if (totalWeight > 0.0001f) { + // thisVertex.BoneWeights[0] /= totalWeight; + // thisVertex.BoneWeights[1] /= totalWeight; + // thisVertex.BoneWeights[2] /= totalWeight; + // thisVertex.BoneWeights[3] /= totalWeight; + //} + std::vector::iterator it = std::find(vertexList.begin(), vertexList.end(), thisVertex); array tmp; if (it != vertexList.end()) { diff --git a/tools/MayaExporter/MayaExporter/Skeleton.cpp b/tools/MayaExporter/MayaExporter/Skeleton.cpp index 9f887561..c30311b8 100644 --- a/tools/MayaExporter/MayaExporter/Skeleton.cpp +++ b/tools/MayaExporter/MayaExporter/Skeleton.cpp @@ -64,6 +64,7 @@ std::string attr[9] = { "scaleX", "scaleY", "scaleZ", "translateX", "translateY" Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int endFrame) { + MStatus status; std::vector animatedJoints; std::vector m_Hierarchy; @@ -121,7 +122,7 @@ Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int e MFnMatrixData MartixFn(DataHandle.data()); MMatrix BindPoseMatrix = MartixFn.matrix(); - if (BindPoseMatrix != MayaJoint.transformationMatrix()) + if (!BindPoseMatrix.isEquivalent(MayaJoint.transformationMatrix())) { MGlobal::displayError(MString() + animationName.c_str() + " is using " + MayaJoint.name() + " that is not in bind pose nor is it key framed in the animation, the exported animation will NOT correspond to the animation in Maya"); } @@ -153,19 +154,43 @@ Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int e MGlobal::displayError(MString() + "Could not find joint ID for: " + thisJoint.name()); } - MMatrix Matrix = thisJoint.transformationMatrix(); - + MTransformationMatrix Matrix = thisJoint.transformation(); + MPlug BindPose = thisJoint.findPlug("bindPose"); + MDataHandle DataHandle; + BindPose.getValue(DataHandle); + MFnMatrixData MartixFn(DataHandle.data()); + MMatrix BindPoseMatrix = MartixFn.matrix(); + Matrix = Matrix.asMatrix(); + + MObject jointOrientObj = thisJoint.attribute("jointOrient"); + MFnNumericAttribute jointOrient(jointOrientObj); + double jointOrientDouble[3]; + jointOrient.getDefault(jointOrientDouble[0], jointOrientDouble[1], jointOrientDouble[2]); + //MGlobal::displayError(MString() + "Joint Matrix: "); + //MGlobal::displayError(MString() + Matrix.asMatrix()[0][0] + " " + Matrix.asMatrix()[0][1] + " " + Matrix.asMatrix()[0][2] + " " + Matrix.asMatrix()[0][3]); + //MGlobal::displayError(MString() + Matrix.asMatrix()[1][0] + " " + Matrix.asMatrix()[1][1] + " " + Matrix.asMatrix()[1][2] + " " + Matrix.asMatrix()[1][3]); + //MGlobal::displayError(MString() + Matrix.asMatrix()[2][0] + " " + Matrix.asMatrix()[2][1] + " " + Matrix.asMatrix()[2][2] + " " + Matrix.asMatrix()[2][3]); + //MGlobal::displayError(MString() + Matrix.asMatrix()[3][0] + " " + Matrix.asMatrix()[3][1] + " " + Matrix.asMatrix()[3][2] + " " + Matrix.asMatrix()[3][3]); + + MEulerRotation joEuler(jointOrientDouble[0], jointOrientDouble[1], jointOrientDouble[2]); + MQuaternion jo = joEuler.asQuaternion(); + double tmp[4]; - thisJoint.getRotationQuaternion(tmp[0], tmp[1], tmp[2], tmp[3]); + Matrix.getRotationQuaternion(tmp[0], tmp[1], tmp[2], tmp[3]); + MQuaternion rotation(tmp); + + rotation = rotation * jo; + rotation.get(tmp); + joint.Rotation[0] = tmp[0]; joint.Rotation[1] = tmp[1]; joint.Rotation[2] = tmp[2]; joint.Rotation[3] = tmp[3]; - thisJoint.getTranslation(MSpace::kPreTransform).get(tmp); + Matrix.getTranslation(MSpace::kTransform).get(tmp); joint.Position[0] = tmp[0]; joint.Position[1] = tmp[1]; joint.Position[2] = tmp[2]; - thisJoint.getScale(tmp); + Matrix.getScale(tmp, MSpace::kTransform); joint.Scale[0] = tmp[0]; joint.Scale[1] = tmp[1]; joint.Scale[2] = tmp[2]; @@ -184,6 +209,7 @@ Animation Skeleton::GetAnimData(std::string animationName, int startFrame, int e std::vector Skeleton::GetBindPoses() { + MStatus status; std::vector m_AllSkeletons; std::vector m_Hierarchy; @@ -214,12 +240,76 @@ std::vector Skeleton::GetBindPoses() } m_Hierarchy.push_back(MayaJoint.object()); - MPlug BindPose = MayaJoint.findPlug("bindPose"); + MPlug BindPose = MayaJoint.findPlug("bindPose", &status); + if (status != MS::kSuccess) { + MGlobal::displayError(MString() + "Could not find bindPose plug: " + status.errorString()); + } MDataHandle DataHandle; BindPose.getValue(DataHandle); MFnMatrixData MartixFn(DataHandle.data()); MMatrix Matrix = MartixFn.matrix(); + + MVector tmp = MayaJoint.transformation().getTranslation(MSpace::kObject); + MGlobal::displayError(MString() + "translation befor: " + tmp[0] + " " + tmp[1] + " " + tmp[2]); + //Matrix[3][0] *= -1; + //Matrix[3][2] *= -1; + //Matrix[3][1] *= -1; + + double test[3]; + MayaJoint.transformation().getScale(test, MSpace::kObject); + MGlobal::displayError(MString() + "scale: " + test[0] + " " + test[1] + " " + test[2]); + + MTransformationMatrix::RotationOrder order = MTransformationMatrix::RotationOrder::kXYZ; + MayaJoint.transformation().getRotation(test, order); + MGlobal::displayError(MString() + "rotation: " + test[0] + " " + test[1] + " " + test[2]); + + //----- test + + + //MDataHandle DataHandle; + //MObject jointObject(jointIt.currentItem()); + //MFnDependencyNode jointDependNode(jointObject); + //MPlug worldMatrixArray(jointObject, jointDependNode.attribute("worldMatrix")); + + //MMatrix Matrix; + //for (int i = 0; i < worldMatrixArray.numElements(); i++) { + // MPlugArray connections; + + // MPlug element = worldMatrixArray[i]; + // unsigned int logicalIndex = element.logicalIndex(); + + // MItDependencyGraph it(element, MFn::kSkinClusterFilter); + + // for (; !it.isDone(); it.next()) { + // MFnSkinCluster skinCluster(it.thisNode()); + + // MPlug bindPreMatrixArrayPlug = + // skinCluster.findPlug("bindPreMatrix", &status); + + // if (status != MS::kSuccess) { + // MGlobal::displayError(MString() + "Could not find bindPreMatrix plug: " + status.errorString()); + // break; + // } + + // MPlug bindPreMatrixPlug = + // bindPreMatrixArrayPlug.elementByLogicalIndex(logicalIndex); + // MObject dataObject; + // bindPreMatrixPlug.getValue(dataObject); + + // MFnMatrixData matDataFn(dataObject); + + // MMatrix invMat = matDataFn.matrix(); + // Matrix = invMat.inverse(); + // } + //} + + + //----- end test + + + Matrix = Matrix.inverse(); + for (int i = 0; i < 4; i++) { for (int j = 0; j < 4; j++) { NewJoint.OffsetMatrix[i][j] = Matrix.matrix[i][j]; From 160b7183b240f91df12bb0aaab5b0fb9b5e00ddb Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sat, 23 Jan 2016 18:07:07 +0100 Subject: [PATCH 194/224] WIP --- include/Engine/Rendering/DrawFinalPass.h | 2 ++ include/Engine/Rendering/TextPass.h | 3 ++- include/Engine/Rendering/TextPassState.h | 2 +- resources/Shaders/Text.frag.glsl | 9 +++++++-- src/Engine/Rendering/DrawFinalPass.cpp | 5 +++-- src/Engine/Rendering/Renderer.cpp | 2 +- src/Engine/Rendering/TextPass.cpp | 12 +++++++++--- src/Engine/Rendering/TextPassState.cpp | 4 ++-- 8 files changed, 27 insertions(+), 12 deletions(-) diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index caf68f24..fee6454b 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -24,6 +24,8 @@ public: GLuint BloomTexture() const { return m_BloomTexture; } //Return the texture with diffuse and lighting of the scene. GLuint SceneTexture() const { return m_SceneTexture; } + FrameBuffer FinalPassFrameBuffer() { return m_FinalPassFrameBuffer; } + private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; diff --git a/include/Engine/Rendering/TextPass.h b/include/Engine/Rendering/TextPass.h index eaace1c2..8fbb3df0 100644 --- a/include/Engine/Rendering/TextPass.h +++ b/include/Engine/Rendering/TextPass.h @@ -11,6 +11,7 @@ #include "../Core/ResourceManager.h" #include "RenderQueue.h" #include "TextPassState.h" +#include "FrameBuffer.h" class TextPass { @@ -18,7 +19,7 @@ public: TextPass(); void Initialize(); void Update(); - void Draw(RenderScene& scene); + void Draw(RenderScene& scene, FrameBuffer& frameBuffer); private: void renderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix); diff --git a/include/Engine/Rendering/TextPassState.h b/include/Engine/Rendering/TextPassState.h index 9bc25f26..fbed6356 100644 --- a/include/Engine/Rendering/TextPassState.h +++ b/include/Engine/Rendering/TextPassState.h @@ -6,7 +6,7 @@ class TextPassState : public RenderState { public: - TextPassState(); + TextPassState(GLuint frameBuffer); ~TextPassState(); private: diff --git a/resources/Shaders/Text.frag.glsl b/resources/Shaders/Text.frag.glsl index 2726b5d1..d2ac7dca 100644 --- a/resources/Shaders/Text.frag.glsl +++ b/resources/Shaders/Text.frag.glsl @@ -3,10 +3,15 @@ in vec2 TexCoords; out vec4 color; uniform sampler2D text; -uniform vec3 textColor; +uniform vec4 textColor; + +out vec4 sceneColor; +out vec4 bloomColor; void main() { vec4 sampled = vec4(1.0, 1.0, 1.0, texture(text, TexCoords).r); - color = vec4(textColor, 1.0) * sampled; + vec4 color_result = textColor * sampled; + sceneColor = vec4(color_result.xyz, clamp(color_result.a, 0, 1)); + bloomColor = vec4(clamp(color_result.xyz - 1.0, 0, 100), 1.0); } \ No newline at end of file diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 52a30cf1..0a91a9db 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -23,8 +23,8 @@ void DrawFinalPass::InitializeFrameBuffers() GenerateTexture(&m_SceneTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); - GenerateMipMapTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_FLOAT, 4); + GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + //GenerateMipMapTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_FLOAT, 4); m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new RenderBuffer(&m_DepthBuffer, GL_DEPTH_ATTACHMENT))); m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); @@ -97,6 +97,7 @@ void DrawFinalPass::Draw(RenderScene& scene) } m_FinalPassFrameBuffer.Unbind(); GLERROR("DrawFinalPass::Draw: END"); + delete state; } diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index 57849d99..c07c6373 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -101,7 +101,7 @@ void Renderer::Draw(RenderFrame& frame) GLERROR("Renderer::Draw m_DrawScenePass->Draw"); - m_TextPass->Draw(*scene); + m_TextPass->Draw(*scene, m_DrawFinalPass->FinalPassFrameBuffer()); } m_DrawBloomPass->Draw(m_DrawFinalPass->BloomTexture()); diff --git a/src/Engine/Rendering/TextPass.cpp b/src/Engine/Rendering/TextPass.cpp index 6b05d7fb..1e3d5941 100644 --- a/src/Engine/Rendering/TextPass.cpp +++ b/src/Engine/Rendering/TextPass.cpp @@ -21,6 +21,8 @@ void TextPass::Initialize() m_TextProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/Text.vert.glsl"))); m_TextProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/Text.frag.glsl"))); m_TextProgram->Compile(); + m_TextProgram->BindFragDataLocation(0, "sceneColor"); + m_TextProgram->BindFragDataLocation(1, "bloomColor"); m_TextProgram->Link(); } @@ -29,8 +31,10 @@ void TextPass::Update() } -void TextPass::Draw(RenderScene& scene) +void TextPass::Draw(RenderScene& scene, FrameBuffer& frameBuffer) { + GLERROR("Derp1"); + TextPassState* state = new TextPassState(frameBuffer.GetHandle()); for (auto &job : scene.TextJobs) { auto textJob = std::dynamic_pointer_cast(job); if (textJob) { @@ -38,6 +42,8 @@ void TextPass::Draw(RenderScene& scene) renderText(textJob->Content, textJob->Resource, textJob->Alignment, textJob->Color, textJob->Matrix, scene.Camera->ProjectionMatrix(), scene.Camera->ViewMatrix()); } } + GLERROR("Derp2"); + delete state; } void TextPass::renderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix) @@ -61,10 +67,10 @@ void TextPass::renderText(std::string text, Font* font, TextJob::AlignmentEnum a penX = 0; } - TextPassState state; + m_TextProgram->Bind(); - glUniform3f(glGetUniformLocation(m_TextProgram->GetHandle(), "textColor"), color.x, color.y, color.z); + glUniform4fv(glGetUniformLocation(m_TextProgram->GetHandle(), "textColor"), 1, glm::value_ptr(color)); glUniformMatrix4fv(glGetUniformLocation(m_TextProgram->GetHandle(), "M"), 1, GL_FALSE, glm::value_ptr(modelMatrix)); glUniformMatrix4fv(glGetUniformLocation(m_TextProgram->GetHandle(), "V"), 1, GL_FALSE, glm::value_ptr(viewMatrix)); glUniformMatrix4fv(glGetUniformLocation(m_TextProgram->GetHandle(), "P"), 1, GL_FALSE, glm::value_ptr(projectionMatrix)); diff --git a/src/Engine/Rendering/TextPassState.cpp b/src/Engine/Rendering/TextPassState.cpp index e81f7b7c..d285a1f0 100644 --- a/src/Engine/Rendering/TextPassState.cpp +++ b/src/Engine/Rendering/TextPassState.cpp @@ -1,9 +1,9 @@ #include "Rendering/TextPassState.h" -TextPassState::TextPassState() +TextPassState::TextPassState(GLuint frameBuffer) { - BindFramebuffer(0); + BindFramebuffer(frameBuffer); glEnable(GL_BLEND); glDisable(GL_CULL_FACE); glEnable(GL_DEPTH_TEST); From ef020a377038957b01beaea9541cd788059b1281 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sat, 23 Jan 2016 18:17:20 +0100 Subject: [PATCH 195/224] Text fixed --- include/Engine/Rendering/DrawFinalPass.h | 2 +- resources/Shaders/Text.frag.glsl | 2 +- src/Engine/Rendering/Renderer.cpp | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index fee6454b..4cf88842 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -24,7 +24,7 @@ public: GLuint BloomTexture() const { return m_BloomTexture; } //Return the texture with diffuse and lighting of the scene. GLuint SceneTexture() const { return m_SceneTexture; } - FrameBuffer FinalPassFrameBuffer() { return m_FinalPassFrameBuffer; } + FrameBuffer* FinalPassFrameBuffer() { return &m_FinalPassFrameBuffer; } private: diff --git a/resources/Shaders/Text.frag.glsl b/resources/Shaders/Text.frag.glsl index d2ac7dca..3b0f9e28 100644 --- a/resources/Shaders/Text.frag.glsl +++ b/resources/Shaders/Text.frag.glsl @@ -13,5 +13,5 @@ void main() vec4 sampled = vec4(1.0, 1.0, 1.0, texture(text, TexCoords).r); vec4 color_result = textColor * sampled; sceneColor = vec4(color_result.xyz, clamp(color_result.a, 0, 1)); - bloomColor = vec4(clamp(color_result.xyz - 1.0, 0, 100), 1.0); + bloomColor = vec4(clamp(color_result.xyz - 1.0, 0, 100), 1.0) * sampled; } \ No newline at end of file diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index c07c6373..770baabf 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -101,7 +101,7 @@ void Renderer::Draw(RenderFrame& frame) GLERROR("Renderer::Draw m_DrawScenePass->Draw"); - m_TextPass->Draw(*scene, m_DrawFinalPass->FinalPassFrameBuffer()); + m_TextPass->Draw(*scene, *m_DrawFinalPass->FinalPassFrameBuffer()); } m_DrawBloomPass->Draw(m_DrawFinalPass->BloomTexture()); From 85a4d98c814bb941dcf553d31ccb60a9074b3b0d Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sat, 23 Jan 2016 18:21:10 +0100 Subject: [PATCH 196/224] Revert "Revert "Merge pull request #43 from teamfisk/Forward+"" This reverts commit bd62b5873d0ce4373865f2466f535f9df3513842. --- include/Engine/Rendering/DrawBloomPass.h | 53 +++++++ include/Engine/Rendering/DrawBloomPassState.h | 15 ++ .../Rendering/DrawColorCorrectionPass.h | 29 ++++ include/Engine/Rendering/DrawFinalPass.h | 15 +- include/Engine/Rendering/DrawFinalPassState.h | 2 +- include/Engine/Rendering/DrawScreenQuadPass.h | 28 ++++ .../Rendering/DrawScreenQuadPassState.h | 15 ++ include/Engine/Rendering/Renderer.h | 14 +- .../Engine/Rendering/Util/CommonFunctions.h | 17 +++ .../Shaders/DrawColorCorrection.frag.glsl | 32 +++++ .../Shaders/DrawColorCorrection.vert.glsl | 13 ++ resources/Shaders/ForwardPlus.frag.glsl | 51 ++++--- resources/Shaders/Gaussian_horiz.frag.glsl | 23 +++ resources/Shaders/Gaussian_horiz.vert.glsl | 13 ++ resources/Shaders/Gaussian_vert.frag.glsl | 23 +++ resources/Shaders/Gaussian_vert.vert.glsl | 13 ++ src/Engine/Rendering/DrawBloomPass.cpp | 134 ++++++++++++++++++ src/Engine/Rendering/DrawBloomPassState.cpp | 15 ++ .../Rendering/DrawColorCorrectionPass.cpp | 41 ++++++ src/Engine/Rendering/DrawFinalPass.cpp | 70 ++++++++- src/Engine/Rendering/DrawFinalPassState.cpp | 6 +- src/Engine/Rendering/DrawScreenQuadPass.cpp | 37 +++++ .../Rendering/DrawScreenQuadPassState.cpp | 18 +++ src/Engine/Rendering/FrameBuffer.cpp | 7 +- src/Engine/Rendering/PickingPass.cpp | 63 ++++---- src/Engine/Rendering/Renderer.cpp | 56 ++++---- src/Engine/Rendering/Util/CommonFunctions.cpp | 2 + 27 files changed, 706 insertions(+), 99 deletions(-) create mode 100644 include/Engine/Rendering/DrawBloomPass.h create mode 100644 include/Engine/Rendering/DrawBloomPassState.h create mode 100644 include/Engine/Rendering/DrawColorCorrectionPass.h create mode 100644 include/Engine/Rendering/DrawScreenQuadPass.h create mode 100644 include/Engine/Rendering/DrawScreenQuadPassState.h create mode 100644 include/Engine/Rendering/Util/CommonFunctions.h create mode 100644 resources/Shaders/DrawColorCorrection.frag.glsl create mode 100644 resources/Shaders/DrawColorCorrection.vert.glsl create mode 100644 resources/Shaders/Gaussian_horiz.frag.glsl create mode 100644 resources/Shaders/Gaussian_horiz.vert.glsl create mode 100644 resources/Shaders/Gaussian_vert.frag.glsl create mode 100644 resources/Shaders/Gaussian_vert.vert.glsl create mode 100644 src/Engine/Rendering/DrawBloomPass.cpp create mode 100644 src/Engine/Rendering/DrawBloomPassState.cpp create mode 100644 src/Engine/Rendering/DrawColorCorrectionPass.cpp create mode 100644 src/Engine/Rendering/DrawScreenQuadPass.cpp create mode 100644 src/Engine/Rendering/DrawScreenQuadPassState.cpp create mode 100644 src/Engine/Rendering/Util/CommonFunctions.cpp diff --git a/include/Engine/Rendering/DrawBloomPass.h b/include/Engine/Rendering/DrawBloomPass.h new file mode 100644 index 00000000..539d6957 --- /dev/null +++ b/include/Engine/Rendering/DrawBloomPass.h @@ -0,0 +1,53 @@ +#ifndef DrawBloomPass_h__ +#define DrawBloomPass_h__ + +#include "IRenderer.h" +#include "DrawBloomPassState.h" +//#include "LightCullingPass.h" Finalpass om den skall skickas in +#include "FrameBuffer.h" +#include "ShaderProgram.h" +//#include "Util/UnorderedMapVec2.h" +#include "Texture.h" + +class DrawBloomPass +{ +public: + DrawBloomPass(IRenderer* renderer /* ,Texture or finalpass*/ ); + ~DrawBloomPass() { } + void InitializeTextures(); + void InitializeFrameBuffers(); + void InitializeShaderPrograms(); + void InitializeBuffers(); + void ClearBuffer(); + + void FillGaussianBuffer(FrameBuffer* fb); + + void Draw(GLuint texture); + + //Getters + //Return the blurred result of the texture that was sent into draw + GLuint GaussianTexture() const { return m_GaussianTexture_vert; } + + +private: + void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; + + Texture* m_WhiteTexture; + Model* m_ScreenQuad; + + const IRenderer* m_Renderer; + //const LightCullingPass* m_LightCullingPass + GLuint m_iterations = 9; + + GLuint m_GaussianTexture_horiz; + GLuint m_GaussianTexture_vert; + + FrameBuffer m_GaussianFrameBuffer_horiz; + FrameBuffer m_GaussianFrameBuffer_vert; + + ShaderProgram* m_GaussianProgram_horiz; + ShaderProgram* m_GaussianProgram_vert; + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawBloomPassState.h b/include/Engine/Rendering/DrawBloomPassState.h new file mode 100644 index 00000000..7f2094cf --- /dev/null +++ b/include/Engine/Rendering/DrawBloomPassState.h @@ -0,0 +1,15 @@ +#ifndef DrawBloomPassState_h__ +#define DrawBloomPassState_h__ + +#include "Rendering/RenderState.h" + +class DrawBloomPassState : public RenderState +{ +public: + DrawBloomPassState(); + ~DrawBloomPassState(); +private: + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawColorCorrectionPass.h b/include/Engine/Rendering/DrawColorCorrectionPass.h new file mode 100644 index 00000000..e9a7e281 --- /dev/null +++ b/include/Engine/Rendering/DrawColorCorrectionPass.h @@ -0,0 +1,29 @@ +#ifndef DrawColorCorrectionPass_h__ +#define DrawColorCorrectionPass_h__ + +#include "IRenderer.h" +#include "DrawScreenQuadPassState.h" +#include "FrameBuffer.h" +#include "ShaderProgram.h" +//#include "Util/UnorderedMapVec2.h" +#include "Texture.h" + +class DrawColorCorrectionPass +{ +public: + DrawColorCorrectionPass(IRenderer* renderer); + ~DrawColorCorrectionPass() { } + void InitializeFrameBuffers(); + void InitializeShaderPrograms(); + + void Draw(GLuint sceneTexture, GLuint bloomTexture); +private: + const IRenderer* m_Renderer; + + ShaderProgram* m_ColorCorrectionProgram; + + Model* m_ScreenQuad; + GLfloat m_Exposure; +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawFinalPass.h b/include/Engine/Rendering/DrawFinalPass.h index 20c7249d..caf68f24 100644 --- a/include/Engine/Rendering/DrawFinalPass.h +++ b/include/Engine/Rendering/DrawFinalPass.h @@ -17,16 +17,25 @@ public: void InitializeTextures(); void InitializeFrameBuffers(); void InitializeShaderPrograms(); - void Draw(RenderScene& scene); + void ClearBuffer(); - //Getters - + //Return the texture that is used in later stages to apply the bloom effect + GLuint BloomTexture() const { return m_BloomTexture; } + //Return the texture with diffuse and lighting of the scene. + GLuint SceneTexture() const { return m_SceneTexture; } private: void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const; + void GenerateMipMapTexture(GLuint* texture, GLenum wrapping, glm::vec2 dimensions, GLint format, GLenum type, GLint numMipMaps) const; Texture* m_WhiteTexture; + Texture* m_BlackTexture; + + FrameBuffer m_FinalPassFrameBuffer; + GLuint m_BloomTexture; + GLuint m_SceneTexture; + GLuint m_DepthBuffer; const IRenderer* m_Renderer; const LightCullingPass* m_LightCullingPass; diff --git a/include/Engine/Rendering/DrawFinalPassState.h b/include/Engine/Rendering/DrawFinalPassState.h index 72d8e392..10b840e9 100644 --- a/include/Engine/Rendering/DrawFinalPassState.h +++ b/include/Engine/Rendering/DrawFinalPassState.h @@ -6,7 +6,7 @@ class DrawFinalPassState : public RenderState { public: - DrawFinalPassState(); + DrawFinalPassState(GLuint frameBuffer); ~DrawFinalPassState(); private: diff --git a/include/Engine/Rendering/DrawScreenQuadPass.h b/include/Engine/Rendering/DrawScreenQuadPass.h new file mode 100644 index 00000000..117e9e1e --- /dev/null +++ b/include/Engine/Rendering/DrawScreenQuadPass.h @@ -0,0 +1,28 @@ +#ifndef DrawScreenQuadPass_h__ +#define DrawScreenQuadPass_h__ + +#include "IRenderer.h" +#include "DrawScreenQuadPassState.h" +#include "FrameBuffer.h" +#include "ShaderProgram.h" +//#include "Util/UnorderedMapVec2.h" +#include "Texture.h" + +class DrawScreenQuadPass +{ +public: + DrawScreenQuadPass(IRenderer* renderer); + ~DrawScreenQuadPass() { } + void InitializeFrameBuffers(); + void InitializeShaderPrograms(); + + void Draw(GLuint texture); +private: + const IRenderer* m_Renderer; + + ShaderProgram* m_DrawQuadProgram; + + Model* m_ScreenQuad; +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/DrawScreenQuadPassState.h b/include/Engine/Rendering/DrawScreenQuadPassState.h new file mode 100644 index 00000000..63ab4729 --- /dev/null +++ b/include/Engine/Rendering/DrawScreenQuadPassState.h @@ -0,0 +1,15 @@ +#ifndef DrawScreenQuadPassState_h__ +#define DrawScreenQuadPassState_h__ + +#include "Rendering/RenderState.h" + +class DrawScreenQuadPassState : public RenderState +{ +public: + DrawScreenQuadPassState(); + ~DrawScreenQuadPassState(); +private: + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/Renderer.h b/include/Engine/Rendering/Renderer.h index 7e124e3c..d84f41d5 100644 --- a/include/Engine/Rendering/Renderer.h +++ b/include/Engine/Rendering/Renderer.h @@ -13,10 +13,14 @@ #include "PickingPass.h" #include "LightCullingPass.h" #include "DrawFinalPass.h" +#include "DrawScreenQuadPass.h" +#include "DrawBloomPass.h" +#include "DrawColorCorrectionPass.h" #include "../Core/EventBroker.h" #include "ImGuiRenderPass.h" #include "Camera.h" #include "../Core/Transform.h" +#include "imgui/imgui.h" #include "TextPass.h" class Renderer : public IRenderer @@ -44,10 +48,15 @@ private: Model* m_UnitQuad; Model* m_UnitSphere; + int m_DebugTextureToDraw = 0; + PickingPass* m_PickingPass; LightCullingPass* m_LightCullingPass; ImGuiRenderPass* m_ImGuiRenderPass; DrawFinalPass* m_DrawFinalPass; + DrawScreenQuadPass* m_DrawScreenQuadPass; + DrawBloomPass* m_DrawBloomPass; + DrawColorCorrectionPass* m_DrawColorCorrectionPass; //----------------------Functions----------------------// void InitializeWindow(); @@ -57,14 +66,13 @@ private: //TODO: Renderer: Get InputUpdate out of renderer void InputUpdate(double dt); //void PickingPass(RenderQueueCollection& rq); - void DrawScreenQuad(GLuint textureToDraw); + //void DrawScreenQuad(GLuint textureToDraw); static bool DepthSort(const std::shared_ptr &i, const std::shared_ptr &j) { return (i->Depth < j->Depth); } void SortRenderJobsByDepth(RenderScene &scene); void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type); //--------------------ShaderPrograms-------------------// - ShaderProgram* m_BasicForwardProgram; - ShaderProgram* m_DrawScreenQuadProgram; + ShaderProgram* m_BasicForwardProgram; }; #endif \ No newline at end of file diff --git a/include/Engine/Rendering/Util/CommonFunctions.h b/include/Engine/Rendering/Util/CommonFunctions.h new file mode 100644 index 00000000..b262568c --- /dev/null +++ b/include/Engine/Rendering/Util/CommonFunctions.h @@ -0,0 +1,17 @@ +#ifndef CommonFuntions_h__ +#define CommonFuntions_h__ + +#include "../../Common.h" +#include "../../OpenGL.h" +#include "../../GLM.h" + +class CommonFuntions +{ +public: + CommonFuntions() = delete; + +private: + +}; + +#endif \ No newline at end of file diff --git a/resources/Shaders/DrawColorCorrection.frag.glsl b/resources/Shaders/DrawColorCorrection.frag.glsl new file mode 100644 index 00000000..8d13992a --- /dev/null +++ b/resources/Shaders/DrawColorCorrection.frag.glsl @@ -0,0 +1,32 @@ +#version 430 + +layout (binding = 0) uniform sampler2D SceneTexture; +layout (binding = 1) uniform sampler2D BloomTexture; +uniform float Exposure; + +in VertexData{ + vec2 TextureCoordinate; +}Input; + +out vec4 fragmentColor; + +void main() +{ + const float gamma = 2.2; + vec4 hdrColor = texture(SceneTexture, Input.TextureCoordinate); + vec4 bloomColor = texture(BloomTexture, Input.TextureCoordinate); + hdrColor += bloomColor; + + //Toon mapping thingy + vec3 result = vec3(1.0) - exp(-hdrColor.rgb * Exposure); + + //gamme correction + result = pow(result, vec3(1.0 / gamma)); + + fragmentColor = vec4(result, 1.0); + //fragmentColor = hdrColor; + //fragmentColor = bloomColor; + //fragmentColor = vec4(1,0.5,0.7,1); +} + + diff --git a/resources/Shaders/DrawColorCorrection.vert.glsl b/resources/Shaders/DrawColorCorrection.vert.glsl new file mode 100644 index 00000000..346bc141 --- /dev/null +++ b/resources/Shaders/DrawColorCorrection.vert.glsl @@ -0,0 +1,13 @@ +#version 430 + +layout (location = 0) in vec3 Position; + +out VertexData{ + vec2 TextureCoordinate; +}Output; + +void main() +{ + gl_Position = vec4(Position, 1.0); + Output.TextureCoordinate = (vec2(Position) + 1) / 2; +} \ No newline at end of file diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index 78a2125e..403c96fc 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -5,7 +5,8 @@ uniform mat4 V; uniform mat4 P; uniform vec4 Color; uniform vec2 ScreenDimensions; -uniform sampler2D texture0; +layout (binding = 0) uniform sampler2D DiffuseTexture; +layout (binding = 1) uniform sampler2D GlowMap; #define TILE_SIZE 16 @@ -48,7 +49,8 @@ in VertexData{ vec4 DiffuseColor; }Input; -out vec4 fragmentColor; +out vec4 sceneColor; +out vec4 bloomColor; vec4 scene_ambient = vec4(0.3,0.3,0.3,1); @@ -99,9 +101,10 @@ LightResult CalcDirectionalLightSource(vec4 direction, vec4 color, float intensi void main() { - vec4 texel = texture2D(texture0, Input.TextureCoordinate); + vec4 diffuseTexel = texture2D(DiffuseTexture, Input.TextureCoordinate); + vec4 glowTexel = texture2D(GlowMap, Input.TextureCoordinate); vec4 position = V * M * vec4(Input.Position, 1.0); - vec4 normal = V * vec4(Input.Normal, 0.0); + vec4 normal = normalize(V * vec4(Input.Normal, 0.0)); vec4 viewVec = normalize(-position); vec2 tilePos; @@ -120,30 +123,42 @@ void main() int l = int(LightIndex[i]); LightSource light = LightSources.List[l]; - LightResult result; + LightResult light_result; + //These if statements should be removed. if(light.Type == 1) { // point - result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); + light_result = CalcPointLightSource(V * light.Position, light.Radius, light.Color, light.Intensity, viewVec, position, normal, light.Falloff); } else if (light.Type == 2) { //Directional - result = CalcDirectionalLightSource(V * light.Direction, light.Color, light.Intensity, viewVec, normal); + light_result = CalcDirectionalLightSource(V * light.Direction, light.Color, light.Intensity, viewVec, normal); } - totalLighting.Diffuse += result.Diffuse; - totalLighting.Specular += result.Specular; + totalLighting.Diffuse += light_result.Diffuse; + totalLighting.Specular += light_result.Specular; } - - //fragmentColor += Input.DiffuseColor; - fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; - //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; - //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); - //fragmentColor = texel * Input.DiffuseColor * Color; - //fragmentColor += vec4(currentTile/3600.f, 0, 0, 1); + //sceneColor += Input.DiffuseColor; + vec4 color_result = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * diffuseTexel * Color; + //bloomColor = vec4(0.3, 0.8, 0.6, 1.0); + sceneColor = vec4(color_result.xyz, 1.0); + //These if statements should be removed if they are slow. + color_result += glowTexel; + bloomColor = vec4(clamp(color_result.xyz - 1.0, 0, 100), 1.0); + /* + if(color_result.x > 1 || color_result.y > 1 || color_result.z > 1) { + bloomColor = vec4(color_result.xyz, 1.0); + } else { + bloomColor = vec4(0.0, 0.0, 0.0, 1.0); + } */ + + //sceneColor += Input.DiffuseColor * (totalLighting.Diffuse) * diffuseTexel * Color; + //sceneColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); + //sceneColor = diffuseTexel * Input.DiffuseColor * Color; + //sceneColor += vec4(currentTile/3600.f, 0, 0, 1); //Tiled Debug Code /* if(int(gl_FragCoord.x)%16 == 0 || int(gl_FragCoord.y)%16 == 0 ) { - fragmentColor += vec4(0.5, 0, 0, 0); + sceneColor += vec4(0.5, 0, 0, 0); } else { - fragmentColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/LightSources.List.length(), 0, 0, 1); + sceneColor += vec4(LightGrids.Data[int(tilePos.x + tilePos.y*80)].Amount/LightSources.List.length(), 0, 0, 1); } */ } diff --git a/resources/Shaders/Gaussian_horiz.frag.glsl b/resources/Shaders/Gaussian_horiz.frag.glsl new file mode 100644 index 00000000..bd48d2d5 --- /dev/null +++ b/resources/Shaders/Gaussian_horiz.frag.glsl @@ -0,0 +1,23 @@ +#version 430 + +layout (binding = 0) uniform sampler2D Texture; + +in VertexData{ + vec2 TextureCoordinate; +}Input; + +out vec4 fragmentColor; + +uniform float weight[5] = float[](0.227027, 0.1945946, 0.1216216, 0.054054, 0.016216); + +void main() +{ + vec2 tex_offset = 1.0 / textureSize(Texture, 0); + vec3 result = texture(Texture, Input.TextureCoordinate).rgb * weight[0]; + + for(int i = 1; i < 5; ++i) { + result += texture(Texture, Input.TextureCoordinate + vec2(tex_offset.x * i, 0.0)).rgb * weight[i]; + result += texture(Texture, Input.TextureCoordinate - vec2(tex_offset.x * i, 0.0)).rgb * weight[i]; + } + fragmentColor = vec4(result, 1.0); +} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_horiz.vert.glsl b/resources/Shaders/Gaussian_horiz.vert.glsl new file mode 100644 index 00000000..346bc141 --- /dev/null +++ b/resources/Shaders/Gaussian_horiz.vert.glsl @@ -0,0 +1,13 @@ +#version 430 + +layout (location = 0) in vec3 Position; + +out VertexData{ + vec2 TextureCoordinate; +}Output; + +void main() +{ + gl_Position = vec4(Position, 1.0); + Output.TextureCoordinate = (vec2(Position) + 1) / 2; +} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_vert.frag.glsl b/resources/Shaders/Gaussian_vert.frag.glsl new file mode 100644 index 00000000..25b08f9f --- /dev/null +++ b/resources/Shaders/Gaussian_vert.frag.glsl @@ -0,0 +1,23 @@ +#version 430 + +layout (binding = 0) uniform sampler2D Texture; + +in VertexData{ + vec2 TextureCoordinate; +}Input; + +out vec4 fragmentColor; + +uniform float weight[5] = float[](0.227027, 0.1945946, 0.1216216, 0.054054, 0.016216); + +void main() +{ + vec2 tex_offset = 1.0 / textureSize(Texture, 0); + vec3 result = texture(Texture, Input.TextureCoordinate).rgb * weight[0]; + + for(int i = 1; i < 5; ++i) { + result += texture(Texture, Input.TextureCoordinate + vec2(0.0, tex_offset.y * i)).rgb * weight[i]; + result += texture(Texture, Input.TextureCoordinate - vec2(0.0, tex_offset.y * i)).rgb * weight[i]; + } + fragmentColor = vec4(result, 1.0); +} \ No newline at end of file diff --git a/resources/Shaders/Gaussian_vert.vert.glsl b/resources/Shaders/Gaussian_vert.vert.glsl new file mode 100644 index 00000000..346bc141 --- /dev/null +++ b/resources/Shaders/Gaussian_vert.vert.glsl @@ -0,0 +1,13 @@ +#version 430 + +layout (location = 0) in vec3 Position; + +out VertexData{ + vec2 TextureCoordinate; +}Output; + +void main() +{ + gl_Position = vec4(Position, 1.0); + Output.TextureCoordinate = (vec2(Position) + 1) / 2; +} \ No newline at end of file diff --git a/src/Engine/Rendering/DrawBloomPass.cpp b/src/Engine/Rendering/DrawBloomPass.cpp new file mode 100644 index 00000000..1ad97eb5 --- /dev/null +++ b/src/Engine/Rendering/DrawBloomPass.cpp @@ -0,0 +1,134 @@ +#include "Rendering/DrawBloomPass.h" + +DrawBloomPass::DrawBloomPass(IRenderer* renderer) +{ + m_Renderer = renderer; + + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + + InitializeTextures(); + InitializeBuffers(); + InitializeShaderPrograms(); +} + +void DrawBloomPass::InitializeTextures() +{ + m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); +} + +void DrawBloomPass::InitializeShaderPrograms() +{ + m_GaussianProgram_horiz = ResourceManager::Load("##GaussianProgramHoriz"); + m_GaussianProgram_horiz->AddShader(std::shared_ptr(new VertexShader("Shaders/Gaussian_horiz.vert.glsl"))); + m_GaussianProgram_horiz->AddShader(std::shared_ptr(new FragmentShader("Shaders/Gaussian_horiz.frag.glsl"))); + m_GaussianProgram_horiz->Compile(); + m_GaussianProgram_horiz->Link(); + + m_GaussianProgram_vert = ResourceManager::Load("##GaussianProgramVert"); + m_GaussianProgram_vert->AddShader(std::shared_ptr(new VertexShader("Shaders/Gaussian_vert.vert.glsl"))); + m_GaussianProgram_vert->AddShader(std::shared_ptr(new FragmentShader("Shaders/Gaussian_vert.frag.glsl"))); + m_GaussianProgram_vert->Compile(); + m_GaussianProgram_vert->Link(); +} + + +void DrawBloomPass::InitializeBuffers() +{ + GenerateTexture(&m_GaussianTexture_horiz, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + + m_GaussianFrameBuffer_horiz.AddResource(std::shared_ptr(new Texture2D(&m_GaussianTexture_horiz, GL_COLOR_ATTACHMENT0))); + m_GaussianFrameBuffer_horiz.Generate(); + + GenerateTexture(&m_GaussianTexture_vert, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + + m_GaussianFrameBuffer_vert.AddResource(std::shared_ptr(new Texture2D(&m_GaussianTexture_vert, GL_COLOR_ATTACHMENT0))); + m_GaussianFrameBuffer_vert.Generate(); +} + + +void DrawBloomPass::ClearBuffer() +{ + m_GaussianFrameBuffer_horiz.Bind(); + glClearColor(0.f, 0.f, 0.f, 0.f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + m_GaussianFrameBuffer_horiz.Unbind(); + m_GaussianFrameBuffer_vert.Bind(); + glClearColor(0.f, 0.f, 0.f, 0.f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + m_GaussianFrameBuffer_vert.Unbind(); +} + +void DrawBloomPass::Draw(GLuint texture) +{ + GLERROR("DrawBloomPass::Draw: Pre"); + + DrawBloomPassState state; + + GLuint shaderHandle_horiz = m_GaussianProgram_horiz->GetHandle(); + GLuint shaderHandle_vert = m_GaussianProgram_vert->GetHandle(); + + + //Horizontal pass, first use the given texture then save it to the horizontal framebuffer. + m_GaussianFrameBuffer_horiz.Bind(); + m_GaussianProgram_horiz->Bind(); + + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, texture); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + + //Iterate some times to make it more gaussian. + for (int i = 1; i < m_iterations; i++) { + //Vertical pass + m_GaussianFrameBuffer_vert.Bind(); + m_GaussianProgram_vert->Bind(); + + glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_horiz); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + + //horizontal pass + + m_GaussianFrameBuffer_horiz.Bind(); + m_GaussianProgram_horiz->Bind(); + + glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_vert); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + } + + //final vertical gaussian after the iterations are done + + m_GaussianFrameBuffer_vert.Bind(); + m_GaussianProgram_vert->Bind(); + + glBindTexture(GL_TEXTURE_2D, m_GaussianTexture_horiz); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); + + GLERROR("DrawBloomPass::Draw: END"); +} + +void DrawBloomPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const +{ + glGenTextures(1, texture); + glBindTexture(GL_TEXTURE_2D, *texture); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filtering); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filtering); + glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, dimensions.x, dimensions.y, 0, format, type, nullptr);//TODO: Renderer: Fix the precision and Resolution + GLERROR("Texture initialization failed"); +} diff --git a/src/Engine/Rendering/DrawBloomPassState.cpp b/src/Engine/Rendering/DrawBloomPassState.cpp new file mode 100644 index 00000000..f9c57475 --- /dev/null +++ b/src/Engine/Rendering/DrawBloomPassState.cpp @@ -0,0 +1,15 @@ +#include "Rendering/DrawBloomPassState.h" + + +DrawBloomPassState::DrawBloomPassState() +{ + //BindFramebuffer(0); + Disable(GL_BLEND); + Disable(GL_DEPTH_TEST); + Disable(GL_CULL_FACE); +} + +DrawBloomPassState::~DrawBloomPassState() +{ + +} diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp new file mode 100644 index 00000000..c9789602 --- /dev/null +++ b/src/Engine/Rendering/DrawColorCorrectionPass.cpp @@ -0,0 +1,41 @@ +#include "Rendering/DrawColorCorrectionPass.h" + +DrawColorCorrectionPass::DrawColorCorrectionPass(IRenderer* renderer) +{ + m_Renderer = renderer; + + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + m_Exposure = 1; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. + + InitializeShaderPrograms(); +} + +void DrawColorCorrectionPass::InitializeShaderPrograms() +{ + m_ColorCorrectionProgram = ResourceManager::Load("#ColorCorrectionProgram"); + m_ColorCorrectionProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawColorCorrection.vert.glsl"))); + m_ColorCorrectionProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawColorCorrection.frag.glsl"))); + m_ColorCorrectionProgram->Compile(); + m_ColorCorrectionProgram->Link(); +} + +void DrawColorCorrectionPass::Draw(GLuint sceneTexture, GLuint bloomTexture) +{ + //glBindFramebuffer(GL_FRAMEBUFFER, 0); + GLERROR("DrawScreenQuadPass::Draw: Pre"); + + DrawScreenQuadPassState state = DrawScreenQuadPassState(); + m_ColorCorrectionProgram->Bind(); + glClear(GL_COLOR_BUFFER_BIT); + glUniform1f(glGetUniformLocation(m_ColorCorrectionProgram->GetHandle(), "Exposure"), m_Exposure); + + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, sceneTexture); + glActiveTexture(GL_TEXTURE1); + glBindTexture(GL_TEXTURE_2D, bloomTexture); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); +} diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index eeaa7bb3..36a14610 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -6,11 +6,31 @@ DrawFinalPass::DrawFinalPass(IRenderer* renderer, LightCullingPass* lightCulling m_LightCullingPass = lightCullingPass; InitializeTextures(); InitializeShaderPrograms(); + InitializeFrameBuffers(); } void DrawFinalPass::InitializeTextures() { m_WhiteTexture = ResourceManager::Load("Textures/Core/Blank.png"); + m_BlackTexture = ResourceManager::Load("Textures/Core/Black.png"); +} + +void DrawFinalPass::InitializeFrameBuffers() +{ + glGenRenderbuffers(1, &m_DepthBuffer); + glBindRenderbuffer(GL_RENDERBUFFER, m_DepthBuffer); + glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); + + GenerateTexture(&m_SceneTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + //GenerateTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, GL_LINEAR, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_RGB, GL_FLOAT); + GenerateMipMapTexture(&m_BloomTexture, GL_CLAMP_TO_EDGE, glm::vec2(m_Renderer->Resolution().Width, m_Renderer->Resolution().Height), GL_RGB16F, GL_FLOAT, 4); + + m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new RenderBuffer(&m_DepthBuffer, GL_DEPTH_ATTACHMENT))); + m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_SceneTexture, GL_COLOR_ATTACHMENT0))); + m_FinalPassFrameBuffer.AddResource(std::shared_ptr(new Texture2D(&m_BloomTexture, GL_COLOR_ATTACHMENT1))); + m_FinalPassFrameBuffer.Generate(); + } void DrawFinalPass::InitializeShaderPrograms() @@ -26,7 +46,7 @@ void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); - DrawFinalPassState state; + DrawFinalPassState* state = new DrawFinalPassState(m_FinalPassFrameBuffer.GetHandle()); m_ForwardPlusProgram->Bind(); GLuint shaderHandle = m_ForwardPlusProgram->GetHandle(); @@ -51,13 +71,20 @@ void DrawFinalPass::Draw(RenderScene& scene) glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); glUniform4fv(glGetUniformLocation(shaderHandle, "Color"), 1, glm::value_ptr(modelJob->Color)); + glActiveTexture(GL_TEXTURE0); if(modelJob->DiffuseTexture != nullptr) { - glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, modelJob->DiffuseTexture->m_Texture); } else { - glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); } + glActiveTexture(GL_TEXTURE1); + glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); + + /*if(modelJob->GlowMap != nullptr) { + glBindTexture(GL_TEXTURE_2D, modelJob->GlowMap->m_Texture); + } else { + glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); + }*/ glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); @@ -66,6 +93,41 @@ void DrawFinalPass::Draw(RenderScene& scene) continue; } } + m_FinalPassFrameBuffer.Unbind(); GLERROR("DrawFinalPass::Draw: END"); - +} + + +void DrawFinalPass::ClearBuffer() +{ + m_FinalPassFrameBuffer.Bind(); + glClearColor(0.f, 0.f, 0.f, 0.f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + m_FinalPassFrameBuffer.Unbind(); +} + +void DrawFinalPass::GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const +{ + glGenTextures(1, texture); + glBindTexture(GL_TEXTURE_2D, *texture); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filtering); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filtering); + glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, dimensions.x, dimensions.y, 0, format, type, nullptr);//TODO: Renderer: Fix the precision and Resolution + GLERROR("Texture initialization failed"); +} + +void DrawFinalPass::GenerateMipMapTexture(GLuint* texture, GLenum wrapping, glm::vec2 dimensions, GLint format, GLenum type, GLint numMipMaps) const +{ + glGenTextures(1, texture); + glBindTexture(GL_TEXTURE_2D, *texture); + glTexStorage2D(GL_TEXTURE_2D, numMipMaps, GL_RGBA8, dimensions.x, dimensions.y); + glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, dimensions.x, dimensions.y, format, type, texture); + glGenerateMipmap(GL_TEXTURE_2D); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapping); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); + GLERROR("MipMap Texture initialization failed"); } diff --git a/src/Engine/Rendering/DrawFinalPassState.cpp b/src/Engine/Rendering/DrawFinalPassState.cpp index 2cda4069..3ebe320d 100644 --- a/src/Engine/Rendering/DrawFinalPassState.cpp +++ b/src/Engine/Rendering/DrawFinalPassState.cpp @@ -1,14 +1,14 @@ #include "Rendering/DrawFinalPassState.h" -DrawFinalPassState::DrawFinalPassState() +DrawFinalPassState::DrawFinalPassState(GLuint frameBuffer) { - BindFramebuffer(0); + BindFramebuffer(frameBuffer); Enable(GL_BLEND); BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); Enable(GL_DEPTH_TEST); Enable(GL_CULL_FACE); - ClearColor(glm::vec4(200.f / 255, 0.f / 255, 200.f / 255, 0.f)); + ClearColor(glm::vec4(0.f, 0.f, 0.f, 0.f)); } DrawFinalPassState::~DrawFinalPassState() diff --git a/src/Engine/Rendering/DrawScreenQuadPass.cpp b/src/Engine/Rendering/DrawScreenQuadPass.cpp new file mode 100644 index 00000000..4b155fc9 --- /dev/null +++ b/src/Engine/Rendering/DrawScreenQuadPass.cpp @@ -0,0 +1,37 @@ +#include "Rendering/DrawScreenQuadPass.h" + +DrawScreenQuadPass::DrawScreenQuadPass(IRenderer* renderer) +{ + m_Renderer = renderer; + + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + + InitializeShaderPrograms(); +} + +void DrawScreenQuadPass::InitializeShaderPrograms() +{ + m_DrawQuadProgram = ResourceManager::Load("#DrawScreenQuadProgram"); + m_DrawQuadProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawScreenQuad.vert.glsl"))); + m_DrawQuadProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawScreenQuad.frag.glsl"))); + m_DrawQuadProgram->Compile(); + m_DrawQuadProgram->Link(); +} + +void DrawScreenQuadPass::Draw(GLuint texture) +{ + //glBindFramebuffer(GL_FRAMEBUFFER, 0); + GLERROR("DrawScreenQuadPass::Draw: Pre"); + + DrawScreenQuadPassState state = DrawScreenQuadPassState(); + m_DrawQuadProgram->Bind(); + glClear(GL_COLOR_BUFFER_BIT); + + glActiveTexture(GL_TEXTURE0); + glBindTexture(GL_TEXTURE_2D, texture); + + glBindVertexArray(m_ScreenQuad->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 + , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); +} diff --git a/src/Engine/Rendering/DrawScreenQuadPassState.cpp b/src/Engine/Rendering/DrawScreenQuadPassState.cpp new file mode 100644 index 00000000..33a4895d --- /dev/null +++ b/src/Engine/Rendering/DrawScreenQuadPassState.cpp @@ -0,0 +1,18 @@ +#include "Rendering/DrawScreenQuadPassState.h" + + +DrawScreenQuadPassState::DrawScreenQuadPassState() +{ + GLERROR("---"); + BindFramebuffer(0); + GLERROR("---"); + Disable(GL_DEPTH_TEST); + Disable(GL_CULL_FACE); + Disable(GL_BLEND); + ClearColor(glm::vec4(0.f)); +} + +DrawScreenQuadPassState::~DrawScreenQuadPassState() +{ + +} diff --git a/src/Engine/Rendering/FrameBuffer.cpp b/src/Engine/Rendering/FrameBuffer.cpp index b2b29626..b7e908cc 100644 --- a/src/Engine/Rendering/FrameBuffer.cpp +++ b/src/Engine/Rendering/FrameBuffer.cpp @@ -55,8 +55,9 @@ void FrameBuffer::Generate() glFramebufferRenderbuffer(GL_FRAMEBUFFER, (*it)->m_Attachment, (*it)->m_ResourceType, *(*it)->m_ResourceHandle); GLERROR("FrameBuffer generate: glFramebufferRenderbuffer"); if ( (*it)->m_Attachment != GL_COLOR_ATTACHMENT0 || + (*it)->m_Attachment != GL_COLOR_ATTACHMENT1 || (*it)->m_Attachment != GL_DEPTH_ATTACHMENT || - (*it)->m_Attachment != GL_STENCIL_ATTACHMENT) + (*it)->m_Attachment != GL_STENCIL_ATTACHMENT) //TODO: Viktor: Fixa detta { LOG_ERROR("RenderBuffer Attachment not valid."); } @@ -69,10 +70,8 @@ void FrameBuffer::Generate() } } - - GLenum* bufferTextures = &attachments[0]; - glDrawBuffers(1, bufferTextures); + glDrawBuffers(attachments.size(), bufferTextures); if (GLenum frameBufferStatus = glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) { LOG_ERROR("FrameBuffer incomplete: 0x%x\n", frameBufferStatus); diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 6f448896..f063b344 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -54,52 +54,49 @@ void PickingPass::Draw(RenderScene& scene) if (scene.ClearDepth) { glClear(GL_DEPTH_BUFFER_BIT); } + m_Camera = scene.Camera; - m_Camera = scene.Camera; + for (auto &job : scene.ForwardJobs) { + auto modelJob = std::dynamic_pointer_cast(job); - for (auto &job : scene.ForwardJobs) { - auto modelJob = std::dynamic_pointer_cast(job); + if (modelJob) { + int pickColor[2] = { m_ColorCounter[0], m_ColorCounter[1] }; - if (modelJob) { - int pickColor[2] = { m_ColorCounter[0], m_ColorCounter[1] }; + PickingInfo pickInfo; + pickInfo.Entity = modelJob->Entity; + pickInfo.World = modelJob->World; + pickInfo.Camera = scene.Camera; - PickingInfo pickInfo; - pickInfo.Entity = modelJob->Entity; - pickInfo.World = modelJob->World; - pickInfo.Camera = scene.Camera; - - auto color = m_EntityColors.find(std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)); - if (color != m_EntityColors.end()) { - pickColor[0] = color->second[0]; - pickColor[1] = color->second[1]; - } else { - m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); - if (m_ColorCounter[0] > 255) { - m_ColorCounter[0] = 0; + auto color = m_EntityColors.find(std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)); + if (color != m_EntityColors.end()) { + pickColor[0] = color->second[0]; + pickColor[1] = color->second[1]; + } else { + m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); + if (m_ColorCounter[0] > 255) { + m_ColorCounter[0] = 0; m_ColorCounter[1]++; - } else { + } else { m_ColorCounter[0]++; - } } - - m_PickingColorsToEntity[glm::ivec2(pickColor[0], pickColor[1])] = pickInfo; - - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); - glUniform2fv(glGetUniformLocation(ShaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); - - glBindVertexArray(modelJob->Model->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, nullptr, modelJob->StartIndex); } + + m_PickingColorsToEntity[glm::ivec2(pickColor[0], pickColor[1])] = pickInfo; + + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); + glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); + glUniform2fv(glGetUniformLocation(ShaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); + + glBindVertexArray(modelJob->Model->VAO); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); + glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, nullptr, modelJob->StartIndex); } - + } m_PickingBuffer.Unbind(); GLERROR("PickingPass Error"); - delete state; } diff --git a/src/Engine/Rendering/Renderer.cpp b/src/Engine/Rendering/Renderer.cpp index e84768e4..57849d99 100644 --- a/src/Engine/Rendering/Renderer.cpp +++ b/src/Engine/Rendering/Renderer.cpp @@ -63,12 +63,6 @@ void Renderer::InitializeWindow() void Renderer::InitializeShaders() { m_BasicForwardProgram = ResourceManager::Load("#m_BasicForwardProgram"); - - m_DrawScreenQuadProgram = ResourceManager::Load("#DrawScreenQuadProgram"); - m_DrawScreenQuadProgram->AddShader(std::shared_ptr(new VertexShader("Shaders/DrawScreenQuad.vert.glsl"))); - m_DrawScreenQuadProgram->AddShader(std::shared_ptr(new FragmentShader("Shaders/DrawScreenQuad.frag.glsl"))); - m_DrawScreenQuadProgram->Compile(); - m_DrawScreenQuadProgram->Link(); } void Renderer::InputUpdate(double dt) @@ -86,10 +80,16 @@ void Renderer::Update(double dt) void Renderer::Draw(RenderFrame& frame) { - glClearColor(255.f / 255, 163.f / 255, 176.f / 255, 0.f); + ImGui::Combo("Draw textures", &m_DebugTextureToDraw, "Final\0Scene\0Bloom\0Gaussian\0Picking"); + //clear buffer 0 + glClearColor(0.f, 0.f, 0.f, 0.f); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + //Clear other buffers m_PickingPass->ClearPicking(); + m_DrawFinalPass->ClearBuffer(); + m_DrawBloomPass->ClearBuffer(); + for (auto scene : frame.RenderScenes){ SortRenderJobsByDepth(*scene); @@ -98,14 +98,28 @@ void Renderer::Draw(RenderFrame& frame) m_LightCullingPass->FillLightList(*scene); m_LightCullingPass->CullLights(*scene); m_DrawFinalPass->Draw(*scene); - //m_DrawScenePass->Draw(rq); GLERROR("Renderer::Draw m_DrawScenePass->Draw"); m_TextPass->Draw(*scene); } - + m_DrawBloomPass->Draw(m_DrawFinalPass->BloomTexture()); + if(m_DebugTextureToDraw == 0) { + m_DrawColorCorrectionPass->Draw(m_DrawFinalPass->SceneTexture(), m_DrawBloomPass->GaussianTexture()); + } + if (m_DebugTextureToDraw == 1) { + m_DrawScreenQuadPass->Draw(m_DrawFinalPass->SceneTexture()); + } + if (m_DebugTextureToDraw == 2) { + m_DrawScreenQuadPass->Draw(m_DrawFinalPass->BloomTexture()); + } + if (m_DebugTextureToDraw == 3) { + m_DrawScreenQuadPass->Draw(m_DrawBloomPass->GaussianTexture()); + } + if (m_DebugTextureToDraw == 4) { + m_DrawScreenQuadPass->Draw(m_PickingPass->PickingTexture()); + } m_ImGuiRenderPass->Draw(); glfwSwapBuffers(m_Window); @@ -116,27 +130,6 @@ PickData Renderer::Pick(glm::vec2 screenCoord) return m_PickingPass->Pick(screenCoord); } -void Renderer::DrawScreenQuad(GLuint textureToDraw) -{ - glBindFramebuffer(GL_FRAMEBUFFER, 0); - - glDisable(GL_DEPTH_TEST); - glDisable(GL_CULL_FACE); - - glClearColor(0.f, 0.f, 0.f, 1.f); - glClear(GL_COLOR_BUFFER_BIT); - - - m_DrawScreenQuadProgram->Bind(); - glActiveTexture(GL_TEXTURE0); - glBindTexture(GL_TEXTURE_2D, textureToDraw); - - glBindVertexArray(m_ScreenQuad->VAO); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_ScreenQuad->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, m_ScreenQuad->MaterialGroups()[0].EndIndex - m_ScreenQuad->MaterialGroups()[0].StartIndex +1 - , GL_UNSIGNED_INT, 0, m_ScreenQuad->MaterialGroups()[0].StartIndex); -} - void Renderer::InitializeTextures() { m_ErrorTexture = ResourceManager::Load("Textures/Core/ErrorTexture.png"); @@ -167,4 +160,7 @@ void Renderer::InitializeRenderPasses() m_PickingPass = new PickingPass(this, m_EventBroker); m_LightCullingPass = new LightCullingPass(this); m_DrawFinalPass = new DrawFinalPass(this, m_LightCullingPass); + m_DrawScreenQuadPass = new DrawScreenQuadPass(this); + m_DrawBloomPass = new DrawBloomPass(this); + m_DrawColorCorrectionPass = new DrawColorCorrectionPass(this); } diff --git a/src/Engine/Rendering/Util/CommonFunctions.cpp b/src/Engine/Rendering/Util/CommonFunctions.cpp new file mode 100644 index 00000000..3c81de66 --- /dev/null +++ b/src/Engine/Rendering/Util/CommonFunctions.cpp @@ -0,0 +1,2 @@ +#include "Rendering/Util/CommonFunctions.h" + From 1ce9128da8c76220f19f37e0df4037a4cfc6613b Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sat, 23 Jan 2016 19:45:23 +0100 Subject: [PATCH 197/224] Source-like movement --- include/Game/Systems/PlayerMovementSystem.h | 1 + resources/Schema/Entities/Player.xml | 13 ++-- src/Game/Systems/PlayerMovementSystem.cpp | 67 +++++++++++++++------ 3 files changed, 56 insertions(+), 25 deletions(-) diff --git a/include/Game/Systems/PlayerMovementSystem.h b/include/Game/Systems/PlayerMovementSystem.h index 72f3b879..f39740ec 100644 --- a/include/Game/Systems/PlayerMovementSystem.h +++ b/include/Game/Systems/PlayerMovementSystem.h @@ -3,6 +3,7 @@ #include "Core/System.h" #include "Core/EPlayerSpawned.h" #include "Input/FirstPersonInputController.h" +#include class PlayerMovementSystem : public ImpureSystem, PureSystem { diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 4398dcc1..58550357 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -6,13 +6,12 @@ - - - - - + + + false + - 3 + 7 @@ -20,7 +19,7 @@ - + diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index c5b55cde..ae54d684 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -36,29 +36,51 @@ void PlayerMovementSystem::Update(double dt) glm::vec3& ori = cTransform["Orientation"]; ori.y += controller->Rotation().y; - glm::vec3& pos = cTransform["Position"]; - float speed; - if (controller->Crouching()) { - speed = player["Player"]["CrouchSpeed"]; - } else { - speed = player["Player"]["MovementSpeed"]; - } - pos += controller->Movement() * glm::inverse(glm::quat(ori)) * speed * (float)dt; - if (player.HasComponent("Physics")) { - glm::vec3& velocity = player["Physics"]["Velocity"]; - if (controller->Jumping() && !controller->Crouching() && velocity.y == 0.f) { - velocity.y += 4.f; - } - } + ComponentWrapper cPhysics = player["Physics"]; - if (player.HasComponent("AABB")) { - glm::vec3& size = player["AABB"]["Size"]; + glm::vec3 wishDirection = controller->Movement() * glm::inverse(glm::quat(ori)); + float wishSpeed; if (controller->Crouching()) { - size = glm::vec3(1.f, 1.f, 1.f); + wishSpeed = player["Player"]["CrouchSpeed"]; } else { - size = glm::vec3(1.f, 1.6f, 1.f); + wishSpeed = player["Player"]["MovementSpeed"]; } + glm::vec3& velocity = cPhysics["Velocity"]; + ImGui::Text("velocity: (%f, %f, %f)", velocity.x, velocity.y, velocity.z); + ImGui::Text("wishDirection: (%f, %f, %f)", wishDirection.x, wishDirection.y, wishDirection.z); + float currentSpeedProj = glm::dot(velocity, wishDirection); + float addSpeed = wishSpeed - currentSpeedProj; + ImGui::Text("currentSpeedProj: %f", currentSpeedProj); + ImGui::Text("wishSpeed: %f", wishSpeed); + ImGui::Text("addSpeed: %f", addSpeed); + + if (addSpeed > 0) { + static float accel = 15.f; + ImGui::InputFloat("accel", &accel); + float actualAccel = accel; + static float surfaceFriction = 1.f; + ImGui::InputFloat("surfaceFriction", &surfaceFriction); + float accelerationSpeed = actualAccel * (float)dt * wishSpeed * surfaceFriction; + accelerationSpeed = glm::min(accelerationSpeed, addSpeed); + velocity += accelerationSpeed * wishDirection; + ImGui::Text("velocity: (%f, %f, %f) |%f|", velocity.x, velocity.y, velocity.z, glm::length(velocity)); + } + //pos += controller->Movement() * glm::inverse(glm::quat(ori)) * speed * (float)dt; + + //glm::vec3& velocity = player["Physics"]["Velocity"]; + //if (controller->Jumping() && !controller->Crouching() && velocity.y == 0.f) { + // velocity.y += 4.f; + //} + + //if (player.HasComponent("AABB")) { + // glm::vec3& size = player["AABB"]["Size"]; + // if (controller->Crouching()) { + // size = glm::vec3(1.f, 1.f, 1.f); + // } else { + // size = glm::vec3(1.f, 1.6f, 1.f); + // } + //} } controller->Reset(); @@ -78,6 +100,15 @@ void PlayerMovementSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapp velocity.y -= 9.82f * (float)dt; } + // Ground friction + float speed = glm::length(velocity); + static float groundFriction = 7.f; + ImGui::InputFloat("groundFriction", &groundFriction); + if (speed > 0) { + float drop = speed * groundFriction * (float)dt; + velocity *= glm::max(speed - drop, 0.f) / speed; + } + glm::vec3& position = cTransform["Position"]; position += velocity * (float)dt; } From 3baa988ad46ab495e51e387b0d0a6a412697a5fc Mon Sep 17 00:00:00 2001 From: antc13 Date: Sat, 23 Jan 2016 20:35:58 +0100 Subject: [PATCH 198/224] Changed .obj files to our own format. DummyScene.mesh may be broken. --- .../Rendering/DebugCameraInputController.h | 2 +- .../Schema/Entities/CollisionTestLevel.xml | 14 ++++----- resources/Schema/Entities/EditorTestWorld.xml | 8 ++--- resources/Schema/Entities/MovementTest.xml | 6 ++-- resources/Schema/Entities/OctreeTest.xml | 6 ++-- resources/Schema/Entities/Player.xml | 2 +- resources/Schema/Entities/RaptorCopter.xml | 8 ++--- resources/Schema/Entities/RenderingWorld.xml | 6 ++-- resources/Schema/Entities/SoundTestLevel.xml | 2 +- resources/Schema/Entities/SpawnTest.xml | 4 +-- resources/Shaders/ForwardPlus.vert.glsl | 2 ++ src/Engine/Editor/EditorSystem.cpp | 26 ++++++++-------- src/Engine/Network/Client.cpp | 2 +- src/Engine/Network/Server.cpp | 2 +- src/Engine/Rendering/DrawFinalPass.cpp | 12 ++----- src/Engine/Rendering/RawModelCustom.cpp | 15 +++++---- src/Engine/Rendering/RenderSystem.cpp | 4 +-- src/Engine/Sound/SoundSystem.cpp | 2 +- src/Tests/CollisionTest.cpp | 10 +++--- src/Tests/HealthSystemTest.cpp | 4 +-- src/Tests/OctTreeTestGameClass.cpp | 2 +- src/Tests/OctTreeTestHardCodedTestWorld.h | 4 +-- src/Tests/OldOctTree.cpp | 2 +- src/Tests/ResourceManagerTest.cpp | 4 +-- tools/MayaExporter/MayaExporter/Material.cpp | 31 ++++++++++++++----- tools/MayaExporter/MayaExporter/Menu.cpp | 2 +- 26 files changed, 99 insertions(+), 83 deletions(-) diff --git a/include/Engine/Rendering/DebugCameraInputController.h b/include/Engine/Rendering/DebugCameraInputController.h index d69098c2..4d74e288 100644 --- a/include/Engine/Rendering/DebugCameraInputController.h +++ b/include/Engine/Rendering/DebugCameraInputController.h @@ -61,6 +61,6 @@ public: protected: glm::vec3 m_Position = glm::vec3(0, 0, 0); glm::vec3 m_Velocity = glm::vec3(0, 0, 0); - float m_BaseSpeed = 50.0f;//2.0f; + float m_BaseSpeed = 2.0f; float m_Speed = m_BaseSpeed; }; \ No newline at end of file diff --git a/resources/Schema/Entities/CollisionTestLevel.xml b/resources/Schema/Entities/CollisionTestLevel.xml index d5e932c2..e58ab6ce 100644 --- a/resources/Schema/Entities/CollisionTestLevel.xml +++ b/resources/Schema/Entities/CollisionTestLevel.xml @@ -6,7 +6,7 @@ - Models/DummyScene.obj + Models/DummyScene.mesh @@ -17,7 +17,7 @@ - Models/Core/UnitSphere.obj + Models/Core/UnitSphere.mesh @@ -28,7 +28,7 @@ - Models/RotationWidgetX.obj + Models/RotationWidgetX.mesh @@ -43,7 +43,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh @@ -69,7 +69,7 @@ - Models/Core/UnitRaptor.obj + Models/Core/UnitRaptor.mesh @@ -94,7 +94,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh @@ -107,7 +107,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/EditorTestWorld.xml b/resources/Schema/Entities/EditorTestWorld.xml index 2e95d626..5649a630 100755 --- a/resources/Schema/Entities/EditorTestWorld.xml +++ b/resources/Schema/Entities/EditorTestWorld.xml @@ -9,7 +9,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh @@ -58,7 +58,7 @@ - Models/DirectionalLightWidget.obj + Models/DirectionalLightWidget.mesh @@ -70,7 +70,7 @@ - Models/Assault.obj + Models/Assault.mesh @@ -94,7 +94,7 @@ - Models/Core/UnitSphere.obj + Models/Core/UnitSphere.mesh diff --git a/resources/Schema/Entities/MovementTest.xml b/resources/Schema/Entities/MovementTest.xml index 93b4d374..dc271908 100644 --- a/resources/Schema/Entities/MovementTest.xml +++ b/resources/Schema/Entities/MovementTest.xml @@ -18,7 +18,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh @@ -37,7 +37,7 @@ - Models/Assault.obj + Models/Assault.mesh @@ -55,7 +55,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/OctreeTest.xml b/resources/Schema/Entities/OctreeTest.xml index 4d7fe709..a510a98c 100644 --- a/resources/Schema/Entities/OctreeTest.xml +++ b/resources/Schema/Entities/OctreeTest.xml @@ -11,7 +11,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh @@ -27,7 +27,7 @@ false - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh @@ -42,7 +42,7 @@ false - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 6c3b39c3..485c6cff 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -6,7 +6,7 @@ - Models/Core/UnitSphere.obj + Models/Core/UnitSphere.mesh diff --git a/resources/Schema/Entities/RaptorCopter.xml b/resources/Schema/Entities/RaptorCopter.xml index 0ee62368..82aa0efa 100644 --- a/resources/Schema/Entities/RaptorCopter.xml +++ b/resources/Schema/Entities/RaptorCopter.xml @@ -7,7 +7,7 @@ - Models/Core/UnitRaptor.obj + Models/Core/UnitRaptor.mesh @@ -31,7 +31,7 @@ - Models/Core/UnitCylinder.obj + Models/Core/UnitCylinder.mesh @@ -44,7 +44,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh @@ -57,7 +57,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 86a3090a..67ddd046 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -13,7 +13,7 @@ - Models/Camera.obj + Models/Camera.mesh MainCamera @@ -26,7 +26,7 @@ - Models/Camera.obj + Models/Camera.mesh ActionCamera @@ -40,7 +40,7 @@ - Models/Core/UnitPlane.obj + Models/Core/UnitPlane.mesh diff --git a/resources/Schema/Entities/SoundTestLevel.xml b/resources/Schema/Entities/SoundTestLevel.xml index 366ae81b..4e9c3093 100644 --- a/resources/Schema/Entities/SoundTestLevel.xml +++ b/resources/Schema/Entities/SoundTestLevel.xml @@ -12,7 +12,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/SpawnTest.xml b/resources/Schema/Entities/SpawnTest.xml index a5574027..16608b47 100644 --- a/resources/Schema/Entities/SpawnTest.xml +++ b/resources/Schema/Entities/SpawnTest.xml @@ -24,7 +24,7 @@ - Models/Core/UnitSphere.obj + Models/Core/UnitSphere.mesh @@ -37,7 +37,7 @@ - Models/Core/UnitSphere.obj + Models/Core/UnitSphere.mesh diff --git a/resources/Shaders/ForwardPlus.vert.glsl b/resources/Shaders/ForwardPlus.vert.glsl index aa8c9446..cb5f41b3 100644 --- a/resources/Shaders/ForwardPlus.vert.glsl +++ b/resources/Shaders/ForwardPlus.vert.glsl @@ -24,10 +24,12 @@ void main() mat4 boneTransform = mat4(1); + if(BoneWeights[0] > 0.f){ boneTransform = BoneWeights[0] * Bones[int(BoneIndices[0])] + BoneWeights[1] * Bones[int(BoneIndices[1])] + BoneWeights[2] * Bones[int(BoneIndices[2])] + BoneWeights[3] * Bones[int(BoneIndices[3])]; + } gl_Position = P*V*M*boneTransform * vec4(Position, 1.0); diff --git a/src/Engine/Editor/EditorSystem.cpp b/src/Engine/Editor/EditorSystem.cpp index 46aad8df..e60890b6 100644 --- a/src/Engine/Editor/EditorSystem.cpp +++ b/src/Engine/Editor/EditorSystem.cpp @@ -295,7 +295,7 @@ void EditorSystem::createWidget() #ifdef USING_ASSIMP_AS_IMPORTER m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; // 360NoScope widgetPlaneX #else - m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneX + m_World->GetComponent(m_WidgetPlaneX, "Model")["Resource"] = "Models/WidgetPlaneZ.mesh"; #endif m_WidgetY = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetY, "Transform"); @@ -306,7 +306,7 @@ void EditorSystem::createWidget() #ifdef USING_ASSIMP_AS_IMPORTER m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; // 360NoScope widgetPlaneY #else - m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneY + m_World->GetComponent(m_WidgetPlaneY, "Model")["Resource"] = "Models/WidgetPlaneZ.mesh"; #endif m_WidgetZ = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetZ, "Transform"); @@ -317,7 +317,7 @@ void EditorSystem::createWidget() #ifdef USING_ASSIMP_AS_IMPORTER m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/WidgetPlaneZ.obj"; // 360NoScope widgetPlaneZ #else - m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/coolCube.mesh"; // 360NoScope widgetPlaneZ + m_World->GetComponent(m_WidgetPlaneZ, "Model")["Resource"] = "Models/WidgetPlaneZ.mesh"; #endif m_WidgetOrigin = m_World->CreateEntity(m_Widget); m_World->AttachComponent(m_WidgetOrigin, "Transform"); @@ -363,9 +363,9 @@ void EditorSystem::setWidgetMode(WidgetMode newMode) m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = false; if (newMode == WidgetMode::Translate) { - //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.obj"; // 360NoScope TranslationWidgets mesh - //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.obj"; - //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.obj"; + m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/TranslationWidgetX.mesh"; + m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/TranslationWidgetY.mesh"; + m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/TranslationWidgetZ.mesh"; // Temporarily disabled for local space until I can figure out what's wrong with the math if (m_WidgetSpace != WidgetSpace::Local) { m_World->GetComponent(m_WidgetPlaneX, "Model")["Visible"] = true; @@ -379,19 +379,19 @@ void EditorSystem::setWidgetMode(WidgetMode newMode) } } } else if (newMode == WidgetMode::Scale) { - //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.obj"; // 360NoScope ScaleWidgets mesh - //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.obj"; - //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.obj"; + m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/ScaleWidgetX.mesh"; + m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/ScaleWidgetY.mesh"; + m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/ScaleWidgetZ.mesh"; m_World->GetComponent(m_WidgetOrigin, "Model")["Visible"] = true; - //m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.obj"; // 360NoScope ScaleWidgetOrigin mesh + m_World->GetComponent(m_WidgetOrigin, "Model")["Resource"] = "Models/ScaleWidgetOrigin.mesh"; if (m_Selection != EntityID_Invalid) { auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); widgetTransform["Orientation"] = glm::eulerAngles(Transform::AbsoluteOrientation(m_World, m_Selection)); } } else if (newMode == WidgetMode::Rotate) { - //m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.obj"; // 360NoScope RotationWidget mesh - //m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.obj"; - //m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.obj"; + m_World->GetComponent(m_WidgetX, "Model")["Resource"] = "Models/RotationWidgetX.mesh"; + m_World->GetComponent(m_WidgetY, "Model")["Resource"] = "Models/RotationWidgetY.mesh"; + m_World->GetComponent(m_WidgetZ, "Model")["Resource"] = "Models/RotationWidgetZ.mesh"; if (m_Selection != EntityID_Invalid) { auto selectionTransform = m_World->GetComponent(m_Selection, "Transform"); if (m_WidgetSpace == WidgetSpace::Local) { diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index efd25120..162ccfd6 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -331,7 +331,7 @@ EntityID Client::createPlayer() EntityID entityID = m_World->CreateEntity(); ComponentWrapper transform = m_World->AttachComponent(entityID, "Transform"); ComponentWrapper model = m_World->AttachComponent(entityID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere mesh + model["Resource"] = "Models/Core/UnitSphere.mesh"; ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); return entityID; } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 367f444b..951fbfb9 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -349,7 +349,7 @@ EntityID Server::createPlayer() ComponentWrapper transform = m_World->AttachComponent(entityID, "Transform"); transform["Position"] = glm::vec3(-1.5f, 0.f, 0.f); ComponentWrapper model = m_World->AttachComponent(entityID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere + model["Resource"] = "Models/Core/UnitSphere.mesh"; model["Color"] = glm::vec4(rand()%255 / 255.f, rand()%255 / 255.f, rand() %255 / 255.f, 1.f); ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); return entityID; diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 1dd5f9bc..afb27d69 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -22,8 +22,6 @@ void DrawFinalPass::InitializeShaderPrograms() m_ForwardPlusProgram->Link(); } -static double tempFrameCounter = 6.348; - void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); @@ -40,7 +38,6 @@ void DrawFinalPass::Draw(RenderScene& scene) glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(m_Renderer->Camera()->ProjectionMatrix())); glUniform2f(glGetUniformLocation(shaderHandle, "ScreenDimensions"), m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); - //tempFrameCounter += 0.01; //TODO: Render: Add code for more jobs than modeljobs. for (auto &job : scene.ForwardJobs) { auto modelJob = std::dynamic_pointer_cast(job); @@ -57,21 +54,18 @@ void DrawFinalPass::Draw(RenderScene& scene) glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); } + //TODO: Fixa så att modelsJobs kan spela upp olika animationer och så att den kan få in en tid istället för 1.0f - Hälsningar Johan och Andreas :) if (modelJob->Model->m_RawModel->m_Skeleton != nullptr) { -#ifdef USING_ASSIMP_AS_IMPORTER - auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("combinedAnim_0"); -#else auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("running"); -#endif if (animation != nullptr) { std::vector frameBones = modelJob->Model->m_RawModel->m_Skeleton->GetFrameBones( *animation, - tempFrameCounter + 1.0f ); glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "Bones"), frameBones.size(), GL_FALSE, glm::value_ptr(frameBones[0])); } } - // -3 - 9 + glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); glDrawElements(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, (void*)(modelJob->StartIndex * sizeof(unsigned int))); diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index 7c387dd9..3bad2ae5 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -162,8 +162,9 @@ void RawModelCustom::ReadMaterialSingle(unsigned int &offset, char* fileData, un if (offset + nameLengths[1] > fileByteSize) { throw Resource::FailedLoadingException("Reading Material NormalMap path failed"); } - - newMaterial.NormalMapPath = (fileData + offset); + newMaterial.NormalMapPath = "Textures/"; + newMaterial.NormalMapPath += (fileData + offset); + newMaterial.NormalMapPath += ".png"; offset += nameLengths[1]; } @@ -171,8 +172,9 @@ void RawModelCustom::ReadMaterialSingle(unsigned int &offset, char* fileData, un if (offset + nameLengths[2] > fileByteSize) { throw Resource::FailedLoadingException("Reading Material SpecularMap path failed"); } - - newMaterial.SpecularMapPath = (fileData + offset); + newMaterial.SpecularMapPath = "Textures/"; + newMaterial.SpecularMapPath += (fileData + offset); + newMaterial.SpecularMapPath += ".png"; offset += nameLengths[2]; } @@ -180,8 +182,9 @@ void RawModelCustom::ReadMaterialSingle(unsigned int &offset, char* fileData, un if (offset + nameLengths[3] > fileByteSize) { throw Resource::FailedLoadingException("Reading Material IncandescenceMap path failed"); } - - newMaterial.IncandescenceMapPath = (fileData + offset); + newMaterial.IncandescenceMapPath = "Textures/"; + newMaterial.IncandescenceMapPath += (fileData + offset); + newMaterial.IncandescenceMapPath += ".png"; offset += nameLengths[3]; } diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 5d9d474d..16de4961 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -99,14 +99,14 @@ void RenderSystem::fillModels(std::list>& jobs, World #ifdef USING_ASSIMP_AS_IMPORTER model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.obj"); // 360NoScope StillLoading mesh #else - model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); // 360NoScope StillLoading mesh + model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.mesh"); #endif } catch (const std::exception&) { try { #ifdef USING_ASSIMP_AS_IMPORTER model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.obj"); // 360NoScope Error mesh #else - model = ResourceManager::Load<::Model>("Models/coolCube.mesh"); // 360NoScope Error mesh + model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.mesh"); #endif } catch (const std::exception&) { continue; diff --git a/src/Engine/Sound/SoundSystem.cpp b/src/Engine/Sound/SoundSystem.cpp index 2494581d..a55c1fee 100644 --- a/src/Engine/Sound/SoundSystem.cpp +++ b/src/Engine/Sound/SoundSystem.cpp @@ -198,7 +198,7 @@ bool SoundSystem::OnPlaySoundOnPosition(const Events::PlaySoundOnPosition & e) (float&)(double)emitter["RollOffFactor"] = e.RollOffFactor; (float&)(double)emitter["ReferenceDistance"] = e.ReferenceDistance; auto model = m_World->AttachComponent(emitterID, "Model"); - (std::string&)model["Resource"] = "Models/Core/UnitCube.obj"; // 360NoScope UnitCube + (std::string&)model["Resource"] = "Models/Core/UnitCube.mesh"; // 360NoScope UnitCube source->Type = SoundType::SFX; m_Sources[emitterID] = source; playSound(source); diff --git a/src/Tests/CollisionTest.cpp b/src/Tests/CollisionTest.cpp index 767fbe3a..42d7667c 100644 --- a/src/Tests/CollisionTest.cpp +++ b/src/Tests/CollisionTest.cpp @@ -108,7 +108,7 @@ BOOST_AUTO_TEST_CASE(collisionTest2) BOOST_AUTO_TEST_CASE(rayVsModelTest) { //simple box test - RayTest("Models/Core/UnitCube.obj"); // 360NoScope Unitcube + RayTest("Models/Core/UnitCube.mesh"); // 360NoScope Unitcube } BOOST_AUTO_TEST_CASE(rayVsModelTest2) @@ -130,7 +130,7 @@ BOOST_AUTO_TEST_CASE(rayVsModelTest2) someAABB = AABB(minPos, maxPos); //using a rawmodel here, else we have to init the renderingsystem ResourceManager::RegisterType("RawModel"); - auto unitBox = ResourceManager::Load("Models/Core/UnitCube.obj"); // 360NoScope unitcube + auto unitBox = ResourceManager::Load("Models/Core/UnitCube.mesh"); // 360NoScope unitcube BOOST_CHECK(unitBox != nullptr); for (size_t i = 0; i < 1000000; i++) @@ -189,19 +189,19 @@ BOOST_AUTO_TEST_CASE(rayVsModelTest2) BOOST_AUTO_TEST_CASE(rayVsModelTest3) { //simple test - RayTest("Models/Core/UnitSphere.obj"); // 360NoScope unitSphere + RayTest("Models/Core/UnitSphere.mesh"); // 360NoScope unitSphere } BOOST_AUTO_TEST_CASE(rayVsModelTest4) { //simple test - RayTest("Models/Core/UnitCylinder.obj"); // 360NoScope unitCylinder + RayTest("Models/Core/UnitCylinder.mesh"); // 360NoScope unitCylinder } BOOST_AUTO_TEST_CASE(rayVsModelTest5) { //simple test - RayTest("Models/Core/UnitRaptor.obj"); // 360NoScope unitRaptor + RayTest("Models/Core/UnitRaptor.mesh"); // 360NoScope unitRaptor } BOOST_AUTO_TEST_CASE(octTest) { diff --git a/src/Tests/HealthSystemTest.cpp b/src/Tests/HealthSystemTest.cpp index 7c3ad641..6f157352 100644 --- a/src/Tests/HealthSystemTest.cpp +++ b/src/Tests/HealthSystemTest.cpp @@ -55,7 +55,7 @@ GameHealthSystemTest::GameHealthSystemTest() EntityID playerID = m_World->CreateEntity(); ComponentWrapper transform = m_World->AttachComponent(playerID, "Transform"); ComponentWrapper model = m_World->AttachComponent(playerID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere + model["Resource"] = "Models/Core/UnitSphere.mesh"; // 360NoScope UnitSphere ComponentWrapper player = m_World->AttachComponent(playerID, "Player"); ComponentWrapper health = m_World->AttachComponent(playerID, "Health"); healthsID = playerID; @@ -80,7 +80,7 @@ GameHealthSystemTest::GameHealthSystemTest() EntityID playerID2 = m_World->CreateEntity(); ComponentWrapper transform2 = m_World->AttachComponent(playerID2, "Transform"); ComponentWrapper model2 = m_World->AttachComponent(playerID2, "Model"); - model2["Resource"] = "Models/Core/UnitSphere.obj"; // 360NoScope UnitSphere + model2["Resource"] = "Models/Core/UnitSphere.mesh"; // 360NoScope UnitSphere ComponentWrapper player2 = m_World->AttachComponent(playerID2, "Player"); ComponentWrapper health2 = m_World->AttachComponent(playerID2, "Health"); //END TEST diff --git a/src/Tests/OctTreeTestGameClass.cpp b/src/Tests/OctTreeTestGameClass.cpp index d03153e7..9ddee19b 100644 --- a/src/Tests/OctTreeTestGameClass.cpp +++ b/src/Tests/OctTreeTestGameClass.cpp @@ -149,7 +149,7 @@ void Game::Tick() ComponentWrapper transform = m_World->AttachComponent(m_BoxID, "Transform"); transform["Scale"] = boxSize; ComponentWrapper model = m_World->AttachComponent(m_BoxID, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope UnitBox + model["Resource"] = "Models/Core/UnitBox.mesh"; // 360NoScope UnitBox m_World->createTestEntitiesTest2(); } diff --git a/src/Tests/OctTreeTestHardCodedTestWorld.h b/src/Tests/OctTreeTestHardCodedTestWorld.h index 89c3c3f3..9c8f3988 100644 --- a/src/Tests/OctTreeTestHardCodedTestWorld.h +++ b/src/Tests/OctTreeTestHardCodedTestWorld.h @@ -112,7 +112,7 @@ private: ComponentWrapper transform = world.AttachComponent(entityCollisionBox, "Transform"); transform["Position"] = glm::vec3(0.f, 2.f, 0.f); ComponentWrapper model = world.AttachComponent(entityCollisionBox, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope UnitBox + model["Resource"] = "Models/Core/UnitBox.mesh"; // 360NoScope UnitBox } void AddBoxModel(const glm::vec3 ¢er, const float &halfSize, Octree::Child* child, EntityID &outEntityId) { @@ -124,7 +124,7 @@ private: transform["Position"] = center; transform["Scale"] = glm::vec3(1.0f, 1.0f, 1.0f)*halfSize*2.0f*0.97f; ComponentWrapper model = world.AttachComponent(entityDummyScene, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope unitBox + model["Resource"] = "Models/Core/UnitBox.mesh"; // 360NoScope unitBox model["Color"] = glm::vec4(0.0f, 0.0f, 0.0f, 1.0f); if (child->m_DynamicObjIndices.size() != 0) model["Color"] = glm::vec4(1.0f, 1.0f, 1.0f, 1.0f); diff --git a/src/Tests/OldOctTree.cpp b/src/Tests/OldOctTree.cpp index a94bf465..ec51b522 100644 --- a/src/Tests/OldOctTree.cpp +++ b/src/Tests/OldOctTree.cpp @@ -112,7 +112,7 @@ void OctTree::Update(float dt, World* world, Camera* cam) ComponentWrapper transform = world->AttachComponent(m_BoxID, "Transform"); transform["Scale"] = boxSize; ComponentWrapper model = world->AttachComponent(m_BoxID, "Model"); - model["Resource"] = "Models/Core/UnitBox.obj"; // 360NoScope UnitBox + model["Resource"] = "Models/Core/UnitBox.mesh"; // 360NoScope UnitBox m_UpdatedOnce = true; } diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index f83c6c9f..1f52472e 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -26,8 +26,8 @@ BOOST_AUTO_TEST_CASE(resourceManagerTest) //configfile without register //check so output says "EE failed to load: type not registered..." - auto m_ScreenQuadNoRegister = ResourceManager::Load("Models/Core/ScreenQuad.obj"); // 360NoScope ScreenQuad - BOOST_CHECK(!ResourceManager::IsResourceLoaded("Model", "Models/Core/ScreenQuad.obj")); + auto m_ScreenQuadNoRegister = ResourceManager::Load("Models/Core/ScreenQuad.mesh"); // 360NoScope ScreenQuad + BOOST_CHECK(!ResourceManager::IsResourceLoaded("Model", "Models/Core/ScreenQuad.mesh")); //there is no error feedback to check if you try to release the wrong resources - hence that cant be tested either } diff --git a/tools/MayaExporter/MayaExporter/Material.cpp b/tools/MayaExporter/MayaExporter/Material.cpp index 8f6b0a62..0a897e6e 100644 --- a/tools/MayaExporter/MayaExporter/Material.cpp +++ b/tools/MayaExporter/MayaExporter/Material.cpp @@ -57,22 +57,27 @@ void Material::grabPhongProperties(MaterialNode& material_node, MFnDependencyNod bool Material::findColorTexture(MaterialNode& material_node, MFnDependencyNode& node) { MPlugArray AllConnections; - + m_Plug = node.findPlug("color", true); m_Plug.connectedTo(AllConnections, true, false); for (int i = 0; i < AllConnections.length(); i++) { if (AllConnections[i].node().hasFn(MFn::kFileTexture)) { MFnDependencyNode TextureNode(AllConnections[i].node()); - - std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); + + std::string FullPath = TextureNode.findPlug("fileTextureName").asString().asChar(); m_TexturePaths.push_back(FullPath); - FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + MString workspace; + MStatus status = MGlobal::executeCommand(MString("workspace -q -rd;"), + workspace); + FullPath = FullPath.substr(workspace.length()); + FullPath = FullPath.substr(FullPath.find_first_of("/") + 1); material_node.ColorMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); material_node.ColorMapFileLength = material_node.ColorMapFile.length() + 1; // Test + MGlobal::displayInfo(MString() + "getAbsolutePathToResources: " + workspace); MGlobal::displayInfo(MString() + "Texture file: " + FullPath.c_str()); return true; } @@ -101,7 +106,11 @@ bool Material::findNormalTexture(MaterialNode& material_node, MFnDependencyNode& std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); m_TexturePaths.push_back(FullPath); - FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + MString workspace; + MStatus status = MGlobal::executeCommand(MString("workspace -q -rd;"), + workspace); + FullPath = FullPath.substr(workspace.length()); + FullPath = FullPath.substr(FullPath.find_first_of("/") + 1); material_node.NormalMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); material_node.NormalMapFileLength = material_node.NormalMapFile.length() + 1; return true; @@ -127,7 +136,11 @@ bool Material::findSpecularTexture(MaterialNode& material_node, MFnDependencyNod std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); m_TexturePaths.push_back(FullPath); - FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + MString workspace; + MStatus status = MGlobal::executeCommand(MString("workspace -q -rd;"), + workspace); + FullPath = FullPath.substr(workspace.length()); + FullPath = FullPath.substr(FullPath.find_first_of("/") + 1); material_node.SpecularMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); material_node.SpecularMapFileLength = material_node.SpecularMapFile.length() + 1; return true; @@ -150,7 +163,11 @@ bool Material::findIncandescenceTexture(MaterialNode& material_node, MFnDependen std::string FullPath = TextureNode.findPlug("ftn").asString().asChar(); m_TexturePaths.push_back(FullPath); - FullPath = FullPath.substr(FullPath.find_last_of("/") + 1); + MString workspace; + MStatus status = MGlobal::executeCommand(MString("workspace -q -rd;"), + workspace); + FullPath = FullPath.substr(workspace.length()); + FullPath = FullPath.substr(FullPath.find_first_of("/") + 1); material_node.IncandescenceMapFile = FullPath.erase(FullPath.find_last_of("."), FullPath.find_last_of(".") - FullPath.size()); material_node.IncandescenceMapFileLength = material_node.IncandescenceMapFile.length() + 1; return true; diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 897cc655..4f32af84 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -60,7 +60,7 @@ Menu::Menu(QDialog* dialog) m_ExportPath = new QLineEdit; m_FileDialog = new QFileDialog; - QString tmpPath("C:/Users/Nickelodion/Desktop/animTest"); + QString tmpPath("C:/Users/Nickelodion/Desktop/workspace/tacticalZ/assets/models/"); m_ExportPath->setText(tmpPath); QLabel* exportLabel = new QLabel; exportLabel->setText("Export Path:"); From 97d70f8e32917396a6396a0b87aafded4fe6969e Mon Sep 17 00:00:00 2001 From: Jocke Date: Sun, 24 Jan 2016 11:36:01 +0100 Subject: [PATCH 199/224] Fixed in client for shoot event. Weapon system now damages health on any target not only players. --- resources/DefaultInput.ini | 3 ++- src/Engine/Network/Client.cpp | 4 ++-- src/Game/Systems/HealthSystem.cpp | 1 - src/Game/Systems/WeaponSystem.cpp | 4 ++-- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/resources/DefaultInput.ini b/resources/DefaultInput.ini index 5ed46241..d07ed6a3 100644 --- a/resources/DefaultInput.ini +++ b/resources/DefaultInput.ini @@ -21,4 +21,5 @@ F1=ToggleEditor X=EditorToggleTransformSpace C=ConnectToServer N=SwitchToServer -M=SwitchToClient \ No newline at end of file +M=SwitchToClient +P=SwitchToPlayer \ No newline at end of file diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 387961ef..2a4f531e 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -310,9 +310,9 @@ bool Client::OnInputCommand(const Events::InputCommand & e) bool Client::OnPlayerDamage(const Events::PlayerDamage & e) { - Packet packet(MessageType::OnInputCommand, m_SendPacketID); + Packet packet(MessageType::OnPlayerDamage, m_SendPacketID); packet.WritePrimitive(e.DamageAmount); - packet.WritePrimitive(e.PlayerDamagedID); + packet.WritePrimitive(m_ClientIDToServerID.at(e.PlayerDamagedID)); send(packet); return false; } diff --git a/src/Game/Systems/HealthSystem.cpp b/src/Game/Systems/HealthSystem.cpp index 5e5be33e..4190e04f 100644 --- a/src/Game/Systems/HealthSystem.cpp +++ b/src/Game/Systems/HealthSystem.cpp @@ -12,7 +12,6 @@ HealthSystem::HealthSystem(World* m_World, EventBroker* eventBroker) void HealthSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) { //if entityID of health is 9 then the players ID is also 9 (player,health are connected to the same entity) - ComponentWrapper player = m_World->GetComponent(component.EntityID, "Player"); double maxHealth = (double)component["MaxHealth"]; //process the DeltaHealthVector and change the entitys health accordingly diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp index 11f76490..da5b057b 100644 --- a/src/Game/Systems/WeaponSystem.cpp +++ b/src/Game/Systems/WeaponSystem.cpp @@ -22,8 +22,8 @@ void WeaponSystem::Update(double dt) continue; } //if its a player, do PlayerDamage event - const bool hasPlayerComponent = m_World->HasComponent(pickDataFromShot.Entity, "Player"); - if (hasPlayerComponent) { + const bool hasHealthComponent = m_World->HasComponent(pickDataFromShot.Entity, "Health"); + if (hasHealthComponent) { Events::PlayerDamage ePlayerDamage; //TODO: damage based on weapontype/class? //TODO: multiple shots at the same time? (shotgunner) From 7567f47a68afdfff10e0bafabe3ef2fa36289db8 Mon Sep 17 00:00:00 2001 From: Jocke Date: Sun, 24 Jan 2016 11:56:46 +0100 Subject: [PATCH 200/224] Weapon system now searches parents for health component (stops at first health component). --- src/Game/Systems/WeaponSystem.cpp | 36 +++++++++++++++---------------- 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp index da5b057b..8ee55c76 100644 --- a/src/Game/Systems/WeaponSystem.cpp +++ b/src/Game/Systems/WeaponSystem.cpp @@ -11,25 +11,23 @@ WeaponSystem::WeaponSystem(World* world, EventBroker* eventBroker, IRenderer* re void WeaponSystem::Update(double dt) { - for (int i = m_EShootVector.size(); i > 0; i--) - { - //TODO: check if player has enough ammo and if weapon has a cooldown or not - + for (int i = m_EShootVector.size(); i > 0; i--) { //pick the object PickData pickDataFromShot = m_Renderer->Pick(std::get<1>(m_EShootVector[i - 1])); - if (pickDataFromShot.Entity == EntityID_Invalid) { - m_EShootVector.erase(m_EShootVector.begin() + i - 1); - continue; - } - //if its a player, do PlayerDamage event - const bool hasHealthComponent = m_World->HasComponent(pickDataFromShot.Entity, "Health"); - if (hasHealthComponent) { - Events::PlayerDamage ePlayerDamage; - //TODO: damage based on weapontype/class? - //TODO: multiple shots at the same time? (shotgunner) - ePlayerDamage.DamageAmount = 25; - ePlayerDamage.PlayerDamagedID = pickDataFromShot.Entity; - m_EventBroker->Publish(ePlayerDamage); + EntityID entityID = pickDataFromShot.Entity; + while (entityID != EntityID_Invalid) { + // If has health + if (m_World->HasComponent(entityID, "Health")) { + Events::PlayerDamage ePlayerDamage; + //TODO: damage based on weapontype/class? + //TODO: multiple shots at the same time? (shotgunner) + ePlayerDamage.DamageAmount = 25; + ePlayerDamage.PlayerDamagedID = entityID; + m_EventBroker->Publish(ePlayerDamage); + break; + } else { + entityID = m_World->GetParent(entityID); + } } m_EShootVector.erase(m_EShootVector.begin() + i - 1); } @@ -44,8 +42,10 @@ bool WeaponSystem::OnInputCommand(const Events::InputCommand& e) } return true; } -bool WeaponSystem::OnShoot(const Events::Shoot& e) { +bool WeaponSystem::OnShoot(const Events::Shoot& e) +{ //screen center, based on current resolution! + //TODO: check if player has enough ammo and if weapon has a cooldown or not Rectangle screenResolution = m_Renderer->Resolution(); glm::vec2 centerScreen = glm::vec2(screenResolution.Width / 2, screenResolution.Height / 2); m_EShootVector.push_back(std::make_pair(e.shooter, centerScreen)); From b5b1140f5c3a29b3fc91969df603507c7195c86d Mon Sep 17 00:00:00 2001 From: antc13 Date: Sun, 24 Jan 2016 13:28:40 +0100 Subject: [PATCH 201/224] Custom Animations should now work. We also save color values if there's no texture. --- include/Engine/Rendering/RawModelCustom.h | 3 + resources/Schema/Entities/AnimatedArmy | 273 ++++++++++++++++++ resources/Shaders/ForwardPlus.vert.glsl | 2 +- src/Engine/Rendering/DrawFinalPass.cpp | 6 +- src/Engine/Rendering/RawModelCustom.cpp | 15 +- tools/MayaExporter/MayaExporter/Material.cpp | 30 +- tools/MayaExporter/MayaExporter/Material.h | 9 + tools/MayaExporter/MayaExporter/Menu.cpp | 7 +- tools/MayaExporter/MayaExporter/Mesh.cpp | 14 +- .../MayaExporter/MayaExporter/WriteToFile.cpp | 9 +- tools/MayaExporter/MayaExporter/WriteToFile.h | 1 + 11 files changed, 341 insertions(+), 28 deletions(-) create mode 100644 resources/Schema/Entities/AnimatedArmy diff --git a/include/Engine/Rendering/RawModelCustom.h b/include/Engine/Rendering/RawModelCustom.h index 2dea51ff..a1a2f1f6 100644 --- a/include/Engine/Rendering/RawModelCustom.h +++ b/include/Engine/Rendering/RawModelCustom.h @@ -48,6 +48,9 @@ public: { float SpecularExponent; float ReflectionFactor; + float DiffuseColor[3]; + float SpecularColor[3]; + float IncandescenceColor[3]; unsigned int StartIndex; unsigned int EndIndex; //float Transparency; diff --git a/resources/Schema/Entities/AnimatedArmy b/resources/Schema/Entities/AnimatedArmy new file mode 100644 index 00000000..b711a0fe --- /dev/null +++ b/resources/Schema/Entities/AnimatedArmy @@ -0,0 +1,273 @@ + + + + + + + + + + + + + + + + + + + + + + + models/dummyscene.mesh + + + + + + + + + + + models/animtest. + + + + + + + + + + + models/animTest.mesh + + + + + + + + + + + models/animTest.mesh + + + + + + + + + + + models/animTest.mesh + + + + + + + + + + + 0.13000047206878662 + + + + + + + + + + + + 0.30000001192092896 + + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + 0.80000001192092896 + + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + + + 0.50999981164932251 + + + + + + + + + + + + + 5 + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + 5 + + + + + + + + + + + + 5 + + + + + + + + + + + + diff --git a/resources/Shaders/ForwardPlus.vert.glsl b/resources/Shaders/ForwardPlus.vert.glsl index cb5f41b3..c51216cb 100644 --- a/resources/Shaders/ForwardPlus.vert.glsl +++ b/resources/Shaders/ForwardPlus.vert.glsl @@ -24,7 +24,7 @@ void main() mat4 boneTransform = mat4(1); - if(BoneWeights[0] > 0.f){ + if(BoneWeights[0] > 0.0f){ boneTransform = BoneWeights[0] * Bones[int(BoneIndices[0])] + BoneWeights[1] * Bones[int(BoneIndices[1])] + BoneWeights[2] * Bones[int(BoneIndices[2])] diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index afb27d69..7be1223a 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -21,7 +21,7 @@ void DrawFinalPass::InitializeShaderPrograms() m_ForwardPlusProgram->Compile(); m_ForwardPlusProgram->Link(); } - +static double tempTime = 0.0; void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); @@ -53,14 +53,14 @@ void DrawFinalPass::Draw(RenderScene& scene) glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); } - + tempTime += 0.01f; //TODO: Fixa så att modelsJobs kan spela upp olika animationer och så att den kan få in en tid istället för 1.0f - Hälsningar Johan och Andreas :) if (modelJob->Model->m_RawModel->m_Skeleton != nullptr) { auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("running"); if (animation != nullptr) { std::vector frameBones = modelJob->Model->m_RawModel->m_Skeleton->GetFrameBones( *animation, - 1.0f + tempTime ); glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "Bones"), frameBones.size(), GL_FALSE, glm::value_ptr(frameBones[0])); } diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index 3bad2ae5..de87d5fc 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -129,8 +129,8 @@ void RawModelCustom::ReadMaterialSingle(unsigned int &offset, char* fileData, un unsigned int* nameLengths = (unsigned int*)(fileData + offset); offset += sizeof(unsigned int) * 4; - if (offset + sizeof(float) * 2 > fileByteSize) { - throw Resource::FailedLoadingException("Reading Material specular and reflection values failed"); + if (offset + sizeof(float) * 11 + sizeof(unsigned int) * 2 > fileByteSize) { + throw Resource::FailedLoadingException("Reading Material specular, reflection, color and start and end index values failed"); } newMaterial.SpecularExponent = *(float*)(fileData + offset); @@ -138,9 +138,12 @@ void RawModelCustom::ReadMaterialSingle(unsigned int &offset, char* fileData, un newMaterial.ReflectionFactor = *(float*)(fileData + offset); offset += sizeof(float); - if (offset + sizeof(unsigned int) * 2 > fileByteSize) { - throw Resource::FailedLoadingException("Reading Material start and end index values failed"); - } + memcpy(newMaterial.DiffuseColor, fileData + offset, sizeof(float) * 3); + offset += sizeof(float) * 3; + memcpy(newMaterial.SpecularColor, fileData + offset, sizeof(float) * 3); + offset += sizeof(float) * 3; + memcpy(newMaterial.IncandescenceColor, fileData + offset, sizeof(float) * 3); + offset += sizeof(float) * 3; newMaterial.StartIndex = *(unsigned int*)(fileData + offset); offset += sizeof(unsigned int); @@ -202,7 +205,7 @@ void RawModelCustom::ReadAnimationFile(std::string filePath) if (!in.is_open()) { //throw Resource::FailedLoadingException("Open animation file failed"); - return; // AJABAJA!!!!!!!! + return; } unsigned int fileByteSize = in.tellg(); diff --git a/tools/MayaExporter/MayaExporter/Material.cpp b/tools/MayaExporter/MayaExporter/Material.cpp index 0a897e6e..03521231 100644 --- a/tools/MayaExporter/MayaExporter/Material.cpp +++ b/tools/MayaExporter/MayaExporter/Material.cpp @@ -5,23 +5,30 @@ void Material::grabLambertProperties(MaterialNode& material_node, MFnDependencyN material_node.Name = node.name().asChar(); if (!findColorTexture(material_node, node)) { - MGlobal::displayWarning(MString() + "Material " + node.name() + " has no color texture. Please apply a texture insted of using a value"); + node.findPlug("colorR").getValue(material_node.DiffuseColor[0]); + node.findPlug("colorG").getValue(material_node.DiffuseColor[1]); + node.findPlug("colorB").getValue(material_node.DiffuseColor[2]); + } - if (findIncandescenceTexture(material_node, node)) { - MGlobal::displayWarning(MString() + "Material " + node.name() + " has no Incandescence texture. Please apply a texture insted of using value"); + if (!findIncandescenceTexture(material_node, node)) { + node.findPlug("incandescenceR").getValue(material_node.IncandescenceColor[0]); + node.findPlug("incandescenceG").getValue(material_node.IncandescenceColor[1]); + node.findPlug("incandescenceB").getValue(material_node.IncandescenceColor[2]); } if (findNormalTexture(material_node, node)) { - MGlobal::displayWarning(MString() + "Material " + node.name() + " has no normal texture. Please apply a texture to it"); + MGlobal::displayWarning(MString() + "Material " + node.name() + " has no normal texture."); } } void Material::grabBlinnProperties(MaterialNode& material_node, MFnDependencyNode& node) { - if (findSpecularTexture(material_node, node)) { - MGlobal::displayWarning(MString() + "Material " + node.name() + " has no specular texture. Please apply a specular to it"); + if (!findSpecularTexture(material_node, node)) { + node.findPlug("specularColorR").getValue(material_node.SpecularColor[0]); + node.findPlug("specularColorG").getValue(material_node.SpecularColor[1]); + node.findPlug("specularColorB").getValue(material_node.SpecularColor[2]); } m_Plug = node.findPlug("reflectivity"); @@ -43,8 +50,10 @@ void Material::grabBlinnProperties(MaterialNode& material_node, MFnDependencyNod void Material::grabPhongProperties(MaterialNode& material_node, MFnDependencyNode& node) { - if (findSpecularTexture(material_node, node)) { - MGlobal::displayWarning(MString() + "Material " + node.name() + " has no specular texture. Please apply a specular to it"); + if (!findSpecularTexture(material_node, node)) { + node.findPlug("specularColorR").getValue(material_node.SpecularColor[0]); + node.findPlug("specularColorG").getValue(material_node.SpecularColor[1]); + node.findPlug("specularColorB").getValue(material_node.SpecularColor[2]); } m_Plug = node.findPlug("reflectivity"); @@ -188,20 +197,21 @@ std::vector* Material::DoIt(Mesh mesh) // All materials we care about inherit from Lambert MItDependencyNodes matIt(MFn::kLambert); m_AllMaterials.clear(); - int totalIndices = 0; while (!matIt.isDone()) { MFnDependencyNode MaterialFnDN(matIt.thisNode()); MaterialNode MaterialStorage; bool meshHasMaterial = false; //Mesh Indices is a map with : indices> + int totalIndices = 0; for (auto aMeshMaterial : mesh.Indices) { + MGlobal::displayInfo(MString() + "Material: " + aMeshMaterial.first.c_str() + " " + MaterialFnDN.name().asChar()); if (aMeshMaterial.first.compare(MaterialFnDN.name().asChar()) == 0) { meshHasMaterial = true; MaterialStorage.IndexStart = totalIndices; MaterialStorage.IndexEnd = totalIndices + aMeshMaterial.second.size() - 1; - totalIndices += aMeshMaterial.second.size(); break; } + totalIndices += aMeshMaterial.second.size(); } if (meshHasMaterial) { grabLambertProperties(MaterialStorage, MaterialFnDN); diff --git a/tools/MayaExporter/MayaExporter/Material.h b/tools/MayaExporter/MayaExporter/Material.h index 4b567d8b..341843e8 100644 --- a/tools/MayaExporter/MayaExporter/Material.h +++ b/tools/MayaExporter/MayaExporter/Material.h @@ -19,15 +19,18 @@ public: float ReflectionFactor; float SpecularExponent; + float DiffuseColor[3]{ 1.0f }; unsigned int ColorMapFileLength = 0; std::string ColorMapFile; + float SpecularColor[3]{ 1.0f }; unsigned int SpecularMapFileLength = 0; std::string SpecularMapFile; unsigned int NormalMapFileLength = 0; std::string NormalMapFile; + float IncandescenceColor[3]{ 1.0f }; unsigned int IncandescenceMapFileLength = 0; std::string IncandescenceMapFile; @@ -43,6 +46,9 @@ public: out.write((char*)&SpecularExponent, sizeof(float)); out.write((char*)&ReflectionFactor, sizeof(float)); + out.write((char*)&DiffuseColor, sizeof(float) * 3); + out.write((char*)&SpecularColor, sizeof(float) * 3); + out.write((char*)&IncandescenceColor, sizeof(float) * 3); out.write((char*)&IndexStart, sizeof(unsigned int)); out.write((char*)&IndexEnd, sizeof(unsigned int)); @@ -64,6 +70,9 @@ public: out << "SpecularExponent: " << SpecularExponent << endl; out << "ReflectionFactor: " << ReflectionFactor << endl; + out << "DiffuseColor: " << DiffuseColor[0] << " " << DiffuseColor[1] << " " << DiffuseColor[2] << endl; + out << "SpecularColor: " << SpecularColor[0] << " " << SpecularColor[1] << " " << SpecularColor[2] << endl; + out << "IncandescenceColor: " << IncandescenceColor[0] << " " << IncandescenceColor[1] << " " << IncandescenceColor[2] << endl; out << "IndexStart: " << IndexStart << endl; out << "IndexEnd: " << IndexEnd << endl; diff --git a/tools/MayaExporter/MayaExporter/Menu.cpp b/tools/MayaExporter/MayaExporter/Menu.cpp index 4f32af84..9cc6de91 100644 --- a/tools/MayaExporter/MayaExporter/Menu.cpp +++ b/tools/MayaExporter/MayaExporter/Menu.cpp @@ -104,9 +104,10 @@ Menu::Menu(QDialog* dialog) // Set the layout for our window dialog->setLayout(baseLayout); - for (unsigned int i = 0; i < 3; i++) { - this->AddClipClicked(true); - } + this->AddClipClicked(true); + //for (unsigned int i = 0; i < 3; i++) { + // this->AddClipClicked(true); + //} } diff --git a/tools/MayaExporter/MayaExporter/Mesh.cpp b/tools/MayaExporter/MayaExporter/Mesh.cpp index 26d5c7b2..6af8a557 100644 --- a/tools/MayaExporter/MayaExporter/Mesh.cpp +++ b/tools/MayaExporter/MayaExporter/Mesh.cpp @@ -309,12 +309,22 @@ Mesh MeshClass::GetMeshData(MObjectArray object) if (hasSkin) { + float totalWeight = 0.0f; + unsigned int totalBones = 0; MIntArray jointIDs /* ??? */; weights.selectAncestorLogicalIndex(vertexIndex, weightListObject); weights.getExistingArrayAttributeIndices(jointIDs); for (unsigned int i = 0; i < jointIDs.length() && i < 4; i++) { - thisVertex.BoneIndices[i] = jointIDs[i]; - thisVertex.BoneWeights[i] = weights[i].asFloat(); + if (weights[i].asFloat() > 0.001f) { + thisVertex.BoneIndices[totalBones] = jointIDs[i]; + thisVertex.BoneWeights[totalBones] = weights[i].asFloat(); + totalWeight = totalWeight + weights[i].asFloat(); + totalBones++; + } + } + + for (unsigned int i = 0; i < 4; i++) { + thisVertex.BoneWeights[i] = thisVertex.BoneWeights[i] / totalWeight; } } diff --git a/tools/MayaExporter/MayaExporter/WriteToFile.cpp b/tools/MayaExporter/MayaExporter/WriteToFile.cpp index 10883416..a0368c4f 100644 --- a/tools/MayaExporter/MayaExporter/WriteToFile.cpp +++ b/tools/MayaExporter/MayaExporter/WriteToFile.cpp @@ -25,10 +25,13 @@ bool WriteToFile::ASCIIFilePath(string filePathAndFileName) void WriteToFile::OpenFiles() { - if (binFile) - binFile.open(binFileName, ofstream::binary); - if (ASCIIFile) + if (binFile) { + binFile.open(binFileName, ofstream::binary); + } + if (ASCIIFile){ ASCIIFile.open(ASCIIFileName); + ASCIIFile << std::fixed << std::setprecision(3); + } } void WriteToFile::CloseFiles() diff --git a/tools/MayaExporter/MayaExporter/WriteToFile.h b/tools/MayaExporter/MayaExporter/WriteToFile.h index 91ca7103..216fcfc9 100644 --- a/tools/MayaExporter/MayaExporter/WriteToFile.h +++ b/tools/MayaExporter/MayaExporter/WriteToFile.h @@ -5,6 +5,7 @@ #include "OutputData.h" #include #include +#include using namespace std; From 67477ff3ae02fd5907d049418b6a380812aed91c Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 13:49:45 +0100 Subject: [PATCH 202/224] EEntityDeleted and EComponentDeleted events published by World --- include/Engine/Core/EComponentDeleted.h | 21 ++++++ include/Engine/Core/EEntityDeleted.h | 19 +++++ include/Engine/Core/World.h | 6 ++ src/Engine/Core/World.cpp | 93 ++++++++++++++++--------- src/Game/Game.cpp | 2 +- 5 files changed, 108 insertions(+), 33 deletions(-) create mode 100644 include/Engine/Core/EComponentDeleted.h create mode 100644 include/Engine/Core/EEntityDeleted.h diff --git a/include/Engine/Core/EComponentDeleted.h b/include/Engine/Core/EComponentDeleted.h new file mode 100644 index 00000000..6d9c468d --- /dev/null +++ b/include/Engine/Core/EComponentDeleted.h @@ -0,0 +1,21 @@ +#ifndef EComponentDeleted_h__ +#define EComponentDeleted_h__ + +#include "../Common.h" +#include "Event.h" +#include "Entity.h" + +namespace Events +{ + +struct ComponentDeleted : Event +{ + EntityID Entity; + std::string ComponentType; + // True if the component was deleted as a result of the entity it was attached to being deleted + bool Cascaded; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Engine/Core/EEntityDeleted.h b/include/Engine/Core/EEntityDeleted.h new file mode 100644 index 00000000..80e20e17 --- /dev/null +++ b/include/Engine/Core/EEntityDeleted.h @@ -0,0 +1,19 @@ +#ifndef EEntityDeleted_h__ +#define EEntityDeleted_h__ + +#include "Event.h" +#include "Entity.h" + +namespace Events +{ + +struct EntityDeleted : Event +{ + EntityID DeletedEntity; + // True if the entity deletion was triggered because the entity's parent was deleted before it + bool Cascaded; +}; + +} + +#endif \ No newline at end of file diff --git a/include/Engine/Core/World.h b/include/Engine/Core/World.h index b201d4ac..35394b9f 100644 --- a/include/Engine/Core/World.h +++ b/include/Engine/Core/World.h @@ -5,11 +5,15 @@ #include "Entity.h" #include "ObjectPool.h" #include "ComponentPool.h" +#include "EventBroker.h" class World { public: World() = default; + World(EventBroker* eventBroker) + : m_EventBroker(eventBroker) + { } ~World(); // Create empty entity @@ -46,6 +50,7 @@ public: std::string GetName(EntityID entity) const; private: + EventBroker* m_EventBroker = nullptr; EntityID m_CurrentEntityID = 0; std::unordered_map m_EntityParents; @@ -55,6 +60,7 @@ private: std::unordered_map m_EntityNames; EntityID generateEntityID(); + void deleteEntityRecursive(EntityID entity, bool cascaded = false); }; #endif \ No newline at end of file diff --git a/src/Engine/Core/World.cpp b/src/Engine/Core/World.cpp index 477e2ab2..97e3ba9f 100644 --- a/src/Engine/Core/World.cpp +++ b/src/Engine/Core/World.cpp @@ -1,4 +1,6 @@ #include "Core/World.h" +#include "Core/EEntityDeleted.h" +#include "Core/EComponentDeleted.h" World::~World() { @@ -21,37 +23,7 @@ EntityID World::CreateEntity(EntityID parent /*= 0*/) void World::DeleteEntity(EntityID entity) { - // Delete components - for (auto& pair : m_ComponentPools) { - auto& pool = pair.second; - if (pool->KnowsEntity(entity)) { - auto& c = pool->GetByEntity(entity); - pool->Delete(c); - } - } - - // Loop through children - std::vector childrenToDelete; - auto children = m_EntityChildren.equal_range(entity); - for (auto it = children.first; it != children.second; ++it) { - childrenToDelete.push_back(it->second); - } - for (auto& child : childrenToDelete) { - DeleteEntity(child); - } - - EntityID parent = m_EntityParents.at(entity); - m_EntityParents.erase(entity); - auto parentChildren = m_EntityChildren.equal_range(parent); - for (auto it = parentChildren.first; it != parentChildren.second; ++it) { - if (it->second == entity) { - m_EntityChildren.erase(it); - break; - } - } - - // Erase potential name - m_EntityNames.erase(entity); + deleteEntityRecursive(entity, false); } bool World::ValidEntity(EntityID entity) const @@ -96,7 +68,15 @@ void World::DeleteComponent(EntityID entity, const std::string& componentType) { ComponentPool* pool = m_ComponentPools.at(componentType); ComponentWrapper c = pool->GetByEntity(entity); - return pool->Delete(c); + pool->Delete(c); + + if (m_EventBroker != nullptr) { + Events::ComponentDeleted e; + e.Entity = entity; + e.ComponentType = componentType; + e.Cascaded = false; + m_EventBroker->Publish(e); + } } const ComponentPool* World::GetComponents(const std::string& componentType) @@ -155,3 +135,52 @@ EntityID World::generateEntityID() return m_CurrentEntityID++; } +void World::deleteEntityRecursive(EntityID entity, bool cascaded /*= false*/) +{ + if (m_EventBroker != nullptr) { + Events::EntityDeleted e; + e.DeletedEntity = entity; + e.Cascaded = cascaded; + m_EventBroker->Publish(e); + } + + // Delete components + for (auto& pair : m_ComponentPools) { + auto& pool = pair.second; + if (pool->KnowsEntity(entity)) { + auto& c = pool->GetByEntity(entity); + pool->Delete(c); + if (m_EventBroker != nullptr) { + Events::ComponentDeleted e; + e.Entity = entity; + e.ComponentType = pair.first; + e.Cascaded = true; + m_EventBroker->Publish(e); + } + } + } + + // Loop through children + std::vector childrenToDelete; + auto children = m_EntityChildren.equal_range(entity); + for (auto it = children.first; it != children.second; ++it) { + childrenToDelete.push_back(it->second); + } + for (auto& child : childrenToDelete) { + deleteEntityRecursive(child, true); + } + + EntityID parent = m_EntityParents.at(entity); + m_EntityParents.erase(entity); + auto parentChildren = m_EntityChildren.equal_range(parent); + for (auto it = parentChildren.first; it != parentChildren.second; ++it) { + if (it->second == entity) { + m_EntityChildren.erase(it); + break; + } + } + + // Erase potential name + m_EntityNames.erase(entity); +} + diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 384c4a5b..5de61b8c 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -57,7 +57,7 @@ Game::Game(int argc, char* argv[]) m_FrameStack->Height = m_Renderer->Resolution().Height; // Create a world - m_World = new World(); + m_World = new World(m_EventBroker); std::string mapToLoad = m_Config->Get("Debug.LoadMap", ""); if (!mapToLoad.empty()) { auto file = ResourceManager::Load(mapToLoad); From 8286d052b34801763295e6ab487100c1f9606a2d Mon Sep 17 00:00:00 2001 From: antc13 Date: Sun, 24 Jan 2016 14:18:04 +0100 Subject: [PATCH 203/224] Changed color values from floats to glm::vec4 --- include/Engine/Rendering/ModelJob.h | 8 ++++++++ include/Engine/Rendering/RawModelCustom.h | 6 +++--- resources/Shaders/ForwardPlus.frag.glsl | 3 ++- src/Engine/Rendering/DrawFinalPass.cpp | 1 + src/Engine/Rendering/RawModelCustom.cpp | 6 +++--- src/Engine/Rendering/Skeleton.cpp | 2 +- 6 files changed, 18 insertions(+), 8 deletions(-) diff --git a/include/Engine/Rendering/ModelJob.h b/include/Engine/Rendering/ModelJob.h index a88530e7..01f4cca4 100644 --- a/include/Engine/Rendering/ModelJob.h +++ b/include/Engine/Rendering/ModelJob.h @@ -24,6 +24,10 @@ struct ModelJob : RenderJob DiffuseTexture = matGroup.Texture.get(); NormalTexture = matGroup.NormalMap.get(); SpecularTexture = matGroup.SpecularMap.get(); + IncandescenceTexture = matGroup.IncandescenceMap.get(); + DiffuseColor = matGroup.DiffuseColor; + SpecularColor = matGroup.SpecularColor; + IncandescenceColor = matGroup.IncandescenceColor; StartIndex = matGroup.StartIndex; EndIndex = matGroup.EndIndex; Matrix = matrix; @@ -43,9 +47,13 @@ struct ModelJob : RenderJob const Texture* DiffuseTexture; const Texture* NormalTexture; const Texture* SpecularTexture; + const Texture* IncandescenceTexture; float Shininess = 0.f; glm::vec4 Color; const ::Model* Model = nullptr; + glm::vec4 DiffuseColor; + glm::vec4 SpecularColor; + glm::vec4 IncandescenceColor; unsigned int StartIndex = 0; unsigned int EndIndex = 0; World* World; diff --git a/include/Engine/Rendering/RawModelCustom.h b/include/Engine/Rendering/RawModelCustom.h index a1a2f1f6..f1bc0e24 100644 --- a/include/Engine/Rendering/RawModelCustom.h +++ b/include/Engine/Rendering/RawModelCustom.h @@ -48,9 +48,9 @@ public: { float SpecularExponent; float ReflectionFactor; - float DiffuseColor[3]; - float SpecularColor[3]; - float IncandescenceColor[3]; + glm::vec4 DiffuseColor{ 1.0f, 1.0f, 1.0f, 1.0f }; + glm::vec4 SpecularColor{ 1.0f, 1.0f, 1.0f, 1.0f }; + glm::vec4 IncandescenceColor{ 1.0f, 1.0f, 1.0f, 1.0f }; unsigned int StartIndex; unsigned int EndIndex; //float Transparency; diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index b9db56d3..2a524096 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -4,6 +4,7 @@ uniform mat4 M; uniform mat4 V; uniform mat4 P; uniform vec4 Color; +uniform vec4 DiffuseColor; uniform vec2 ScreenDimensions; uniform sampler2D texture0; @@ -129,7 +130,7 @@ void main() totalLighting.Specular += result.Specular; } - fragmentColor += (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; + fragmentColor += DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * texel * Color; //fragmentColor += Input.DiffuseColor; //fragmentColor += Input.DiffuseColor * (totalLighting.Diffuse) * texel * Color; //fragmentColor += Input.DiffuseColor + vec4(0.0, LightGrids.Data[currentTile].Amount/3, 0, 1); diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 7be1223a..2b126951 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -45,6 +45,7 @@ void DrawFinalPass::Draw(RenderScene& scene) //TODO: Kolla upp "header/include/common" shader saken så man slipper skicka in asmycket uniforms glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); glUniform4fv(glGetUniformLocation(shaderHandle, "Color"), 1, glm::value_ptr(modelJob->Color)); + glUniform4fv(glGetUniformLocation(shaderHandle, "DiffuseColor"), 1, glm::value_ptr(modelJob->DiffuseColor)); if(modelJob->DiffuseTexture != nullptr) { glActiveTexture(GL_TEXTURE0); diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index de87d5fc..fca796ac 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -138,11 +138,11 @@ void RawModelCustom::ReadMaterialSingle(unsigned int &offset, char* fileData, un newMaterial.ReflectionFactor = *(float*)(fileData + offset); offset += sizeof(float); - memcpy(newMaterial.DiffuseColor, fileData + offset, sizeof(float) * 3); + memcpy(&newMaterial.DiffuseColor[0], fileData + offset, sizeof(float) * 3); offset += sizeof(float) * 3; - memcpy(newMaterial.SpecularColor, fileData + offset, sizeof(float) * 3); + memcpy(&newMaterial.SpecularColor[0], fileData + offset, sizeof(float) * 3); offset += sizeof(float) * 3; - memcpy(newMaterial.IncandescenceColor, fileData + offset, sizeof(float) * 3); + memcpy(&newMaterial.IncandescenceColor[0], fileData + offset, sizeof(float) * 3); offset += sizeof(float) * 3; newMaterial.StartIndex = *(unsigned int*)(fileData + offset); diff --git a/src/Engine/Rendering/Skeleton.cpp b/src/Engine/Rendering/Skeleton.cpp index 986e634c..1f150b00 100644 --- a/src/Engine/Rendering/Skeleton.cpp +++ b/src/Engine/Rendering/Skeleton.cpp @@ -90,7 +90,7 @@ void Skeleton::AccumulateBoneTransforms(bool noRootMotion, const Animation::Keyf int k = 0; } else { if (bone->Parent) { - boneMatrix = parentMatrix * bone->Parent->OffsetMatrix * glm::translate(glm::vec3(1.718, 0, 0)); // * glm::inverse(bone->OffsetMatrix); + boneMatrix = parentMatrix; // * glm::inverse(bone->OffsetMatrix); } boneMatrices[bone->ID] = boneMatrix; // * bone->OffsetMatrix; } From 373bb33cf0f58934d55db75f950b2addcf5ce907 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 15:20:34 +0100 Subject: [PATCH 204/224] Player jumping taking air acceleration into account --- resources/Schema/Entities/Player.xml | 9 +++-- src/Engine/Collision/CollisionSystem.cpp | 2 +- src/Game/Systems/PlayerMovementSystem.cpp | 42 ++++++++++++++--------- 3 files changed, 33 insertions(+), 20 deletions(-) diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 58550357..00d2e295 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -6,12 +6,13 @@ + - false + - 7 + 5 @@ -19,7 +20,8 @@ - + + @@ -29,6 +31,7 @@ + diff --git a/src/Engine/Collision/CollisionSystem.cpp b/src/Engine/Collision/CollisionSystem.cpp index 0c77c306..ba841e36 100644 --- a/src/Engine/Collision/CollisionSystem.cpp +++ b/src/Engine/Collision/CollisionSystem.cpp @@ -31,7 +31,7 @@ void CollisionSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& c } if (Collision::AABBVsAABB(boxA, boxB, resolutionVector)) { (glm::vec3&)cTransform["Position"] += resolutionVector; - cPhysics["Velocity"] = glm::vec3(0, 0, 0); + ((glm::vec3&)cPhysics["Velocity"]).y = 0.f; } } diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index ae54d684..5c75a673 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -48,8 +48,12 @@ void PlayerMovementSystem::Update(double dt) } glm::vec3& velocity = cPhysics["Velocity"]; ImGui::Text("velocity: (%f, %f, %f)", velocity.x, velocity.y, velocity.z); - ImGui::Text("wishDirection: (%f, %f, %f)", wishDirection.x, wishDirection.y, wishDirection.z); - float currentSpeedProj = glm::dot(velocity, wishDirection); + glm::vec3 groundVelocity(0.f, 0.f, 0.f); + groundVelocity.x = glm::dot(velocity, glm::vec3(1.f, 0.f, 0.f)); + groundVelocity.z = glm::dot(velocity, glm::vec3(0.f, 0.f, 1.f)); + ImGui::Text("groundVelocity: (%f, %f, %f) |%f|", groundVelocity.x, groundVelocity.y, groundVelocity.z, glm::length(wishDirection)); + ImGui::Text("wishDirection: (%f, %f, %f) |%f|", wishDirection.x, wishDirection.y, wishDirection.z, glm::length(wishDirection)); + float currentSpeedProj = glm::dot(groundVelocity, wishDirection); float addSpeed = wishSpeed - currentSpeedProj; ImGui::Text("currentSpeedProj: %f", currentSpeedProj); ImGui::Text("wishSpeed: %f", wishSpeed); @@ -58,20 +62,20 @@ void PlayerMovementSystem::Update(double dt) if (addSpeed > 0) { static float accel = 15.f; ImGui::InputFloat("accel", &accel); - float actualAccel = accel; - static float surfaceFriction = 1.f; + static float airAccel = 0.5f; + ImGui::InputFloat("airAccel", &airAccel); + float actualAccel = (velocity.y != 0) ? airAccel : accel; + static float surfaceFriction = 5.f; ImGui::InputFloat("surfaceFriction", &surfaceFriction); float accelerationSpeed = actualAccel * (float)dt * wishSpeed * surfaceFriction; accelerationSpeed = glm::min(accelerationSpeed, addSpeed); velocity += accelerationSpeed * wishDirection; ImGui::Text("velocity: (%f, %f, %f) |%f|", velocity.x, velocity.y, velocity.z, glm::length(velocity)); } - //pos += controller->Movement() * glm::inverse(glm::quat(ori)) * speed * (float)dt; - //glm::vec3& velocity = player["Physics"]["Velocity"]; - //if (controller->Jumping() && !controller->Crouching() && velocity.y == 0.f) { - // velocity.y += 4.f; - //} + if (controller->Jumping() && !controller->Crouching() && velocity.y == 0.f) { + velocity.y += 4.f; + } //if (player.HasComponent("AABB")) { // glm::vec3& size = player["AABB"]["Size"]; @@ -93,20 +97,26 @@ void PlayerMovementSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapp if (!entity.HasComponent("Physics")) { return; } - ComponentWrapper& cPhysics = entity["Physics"]; + ComponentWrapper& cPhysics = entity["Physics"]; glm::vec3& velocity = cPhysics["Velocity"]; - if (cPhysics["Gravity"]) { - velocity.y -= 9.82f * (float)dt; - } // Ground friction float speed = glm::length(velocity); - static float groundFriction = 7.f; + static float groundFriction = 7.f; ImGui::InputFloat("groundFriction", &groundFriction); + static float airFriction = 0.f; + ImGui::InputFloat("airFriction", &airFriction); + float friction = (velocity.y != 0) ? airFriction : groundFriction; if (speed > 0) { - float drop = speed * groundFriction * (float)dt; - velocity *= glm::max(speed - drop, 0.f) / speed; + float drop = speed * friction * (float)dt; + float multiplier = glm::max(speed - drop, 0.f) / speed; + velocity.x *= multiplier; + velocity.z *= multiplier; + } + + if (cPhysics["Gravity"]) { + velocity.y -= 9.82f * (float)dt; } glm::vec3& position = cTransform["Position"]; From 666f1fd8784a9aed5439ae5f1df0d0335996bd31 Mon Sep 17 00:00:00 2001 From: antc13 Date: Sun, 24 Jan 2016 15:30:20 +0100 Subject: [PATCH 205/224] Removed temp variables & the "forced" animation in DrawFinalPass --- resources/Shaders/ForwardPlus.frag.glsl | 4 +-- .../Rendering/DrawColorCorrectionPass.cpp | 2 +- src/Engine/Rendering/DrawFinalPass.cpp | 30 +++++++------------ src/Engine/Rendering/RawModelAssimp.cpp | 1 - src/Engine/Rendering/RawModelCustom.cpp | 1 - src/Engine/Rendering/RenderSystem.cpp | 12 ++------ src/Engine/Rendering/Skeleton.cpp | 1 - tools/MayaExporter/MayaExporter/Material.h | 6 ++-- 8 files changed, 19 insertions(+), 38 deletions(-) diff --git a/resources/Shaders/ForwardPlus.frag.glsl b/resources/Shaders/ForwardPlus.frag.glsl index e158640e..57b1d627 100644 --- a/resources/Shaders/ForwardPlus.frag.glsl +++ b/resources/Shaders/ForwardPlus.frag.glsl @@ -4,6 +4,7 @@ uniform mat4 M; uniform mat4 V; uniform mat4 P; uniform vec4 Color; +uniform vec4 DiffuseColor; uniform vec2 ScreenDimensions; layout (binding = 0) uniform sampler2D DiffuseTexture; layout (binding = 1) uniform sampler2D GlowMap; @@ -46,7 +47,6 @@ in VertexData{ vec3 Position; vec3 Normal; vec2 TextureCoordinate; - vec4 DiffuseColor; }Input; out vec4 sceneColor; @@ -135,7 +135,7 @@ void main() } //sceneColor += Input.DiffuseColor; - vec4 color_result = Input.DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * diffuseTexel * Color; + vec4 color_result = DiffuseColor * (totalLighting.Diffuse + totalLighting.Specular) * diffuseTexel * Color; //bloomColor = vec4(0.3, 0.8, 0.6, 1.0); sceneColor = vec4(color_result.xyz, clamp(color_result.a, 0, 1)); //These if statements should be removed if they are slow. diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp index c9789602..5989584e 100644 --- a/src/Engine/Rendering/DrawColorCorrectionPass.cpp +++ b/src/Engine/Rendering/DrawColorCorrectionPass.cpp @@ -5,7 +5,7 @@ DrawColorCorrectionPass::DrawColorCorrectionPass(IRenderer* renderer) m_Renderer = renderer; m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); - m_Exposure = 1; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. + m_Exposure = 0.4; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. InitializeShaderPrograms(); } diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index fddc0338..9977f194 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -43,7 +43,7 @@ void DrawFinalPass::InitializeShaderPrograms() m_ForwardPlusProgram->BindFragDataLocation(1, "bloomColor"); m_ForwardPlusProgram->Link(); } -static double tempTime = 0.0; + void DrawFinalPass::Draw(RenderScene& scene) { GLERROR("DrawFinalPass::Draw: Pre"); @@ -65,6 +65,7 @@ void DrawFinalPass::Draw(RenderScene& scene) glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); glUniform2f(glGetUniformLocation(shaderHandle, "ScreenDimensions"), m_Renderer->Resolution().Width, m_Renderer->Resolution().Height); + //TODO: Render: Add code for more jobs than modeljobs. for (auto &job : scene.ForwardJobs) { auto modelJob = std::dynamic_pointer_cast(job); @@ -80,33 +81,24 @@ void DrawFinalPass::Draw(RenderScene& scene) } else { glBindTexture(GL_TEXTURE_2D, m_WhiteTexture->m_Texture); } - tempTime += 0.01f; - //TODO: Fixa så att modelsJobs kan spela upp olika animationer och så att den kan få in en tid istället för 1.0f - Hälsningar Johan och Andreas :) - if (modelJob->Model->m_RawModel->m_Skeleton != nullptr) { - auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("running"); - if (animation != nullptr) { - std::vector frameBones = modelJob->Model->m_RawModel->m_Skeleton->GetFrameBones( - *animation, - tempTime glActiveTexture(GL_TEXTURE1); - glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); - - /*if(modelJob->GlowMap != nullptr) { - glBindTexture(GL_TEXTURE_2D, modelJob->GlowMap->m_Texture); + if (modelJob->IncandescenceTexture != nullptr) { + glBindTexture(GL_TEXTURE_2D, modelJob->IncandescenceTexture->m_Texture); } else { glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); - }*/ - ); - glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "Bones"), frameBones.size(), GL_FALSE, glm::value_ptr(frameBones[0])); - } } - + + /*if(modelJob->GlowMap != nullptr) { + glBindTexture(GL_TEXTURE_2D, modelJob->GlowMap->m_Texture); + } else { + glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); + }*/ + glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); glDrawElements(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, (void*)(modelJob->StartIndex * sizeof(unsigned int))); } } - m_FinalPassFrameBuffer.Unbind(); GLERROR("DrawFinalPass::Draw: END"); delete state; } diff --git a/src/Engine/Rendering/RawModelAssimp.cpp b/src/Engine/Rendering/RawModelAssimp.cpp index 6bc3f3f7..7bf72a22 100644 --- a/src/Engine/Rendering/RawModelAssimp.cpp +++ b/src/Engine/Rendering/RawModelAssimp.cpp @@ -273,7 +273,6 @@ RawModelAssimp::RawModelAssimp(std::string fileName) m_Skeleton->Animations[animationName] = skelAnim; } - int k = 0; } RawModelAssimp::~RawModelAssimp() diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index fca796ac..74c524c9 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -8,7 +8,6 @@ RawModelCustom::RawModelCustom(std::string fileName) ReadMeshFile(fileName); ReadMaterialFile(fileName); ReadAnimationFile(fileName); - int k = 0; } void RawModelCustom::ReadMeshFile(std::string filePath) diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 455e25e9..334b3b1b 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -51,18 +51,10 @@ void RenderSystem::fillModels(std::list>& jobs) model = ResourceManager::Load<::Model, true>(resource); } catch (const Resource::StillLoadingException&) { //continue; -#ifdef USING_ASSIMP_AS_IMPORTER - model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.obj"); // 360NoScope StillLoading mesh -#else - model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.mesh"); -#endif + model = ResourceManager::Load<::Model>("Models/Core/Error.mesh"); } catch (const std::exception&) { try { -#ifdef USING_ASSIMP_AS_IMPORTER - model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.obj"); // 360NoScope Error mesh -#else - model = ResourceManager::Load<::Model>("Models/WidgetPlaneZ.mesh"); -#endif + model = ResourceManager::Load<::Model>("Models/Core/Error.mesh"); } catch (const std::exception&) { continue; } diff --git a/src/Engine/Rendering/Skeleton.cpp b/src/Engine/Rendering/Skeleton.cpp index 1f150b00..cebabb67 100644 --- a/src/Engine/Rendering/Skeleton.cpp +++ b/src/Engine/Rendering/Skeleton.cpp @@ -87,7 +87,6 @@ void Skeleton::AccumulateBoneTransforms(bool noRootMotion, const Animation::Keyf boneMatrix = parentMatrix * (glm::translate(positionInterp) * glm::toMat4(rotationInterp) * glm::scale(scaleInterp)); boneMatrices[bone->ID] = boneMatrix * bone->OffsetMatrix; - int k = 0; } else { if (bone->Parent) { boneMatrix = parentMatrix; // * glm::inverse(bone->OffsetMatrix); diff --git a/tools/MayaExporter/MayaExporter/Material.h b/tools/MayaExporter/MayaExporter/Material.h index 341843e8..e405dd07 100644 --- a/tools/MayaExporter/MayaExporter/Material.h +++ b/tools/MayaExporter/MayaExporter/Material.h @@ -19,18 +19,18 @@ public: float ReflectionFactor; float SpecularExponent; - float DiffuseColor[3]{ 1.0f }; + float DiffuseColor[3]{ 1.0f, 1.0f, 1.0f }; unsigned int ColorMapFileLength = 0; std::string ColorMapFile; - float SpecularColor[3]{ 1.0f }; + float SpecularColor[3]{ 1.0f, 1.0f, 1.0f }; unsigned int SpecularMapFileLength = 0; std::string SpecularMapFile; unsigned int NormalMapFileLength = 0; std::string NormalMapFile; - float IncandescenceColor[3]{ 1.0f }; + float IncandescenceColor[3]{ 1.0f, 1.0f, 1.0f }; unsigned int IncandescenceMapFileLength = 0; std::string IncandescenceMapFile; From 3261e21d9663e31a56025a2d00185dac99bec15a Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 15:46:01 +0100 Subject: [PATCH 206/224] Coloring players depending on team and created a blue spawn in MovementTest --- resources/Schema/Entities/MovementTest.xml | 47 +++++++++++++++++++++- src/Game/Systems/PlayerSpawnSystem.cpp | 22 +++++++++- 2 files changed, 66 insertions(+), 3 deletions(-) diff --git a/resources/Schema/Entities/MovementTest.xml b/resources/Schema/Entities/MovementTest.xml index 00f94120..26d25edb 100644 --- a/resources/Schema/Entities/MovementTest.xml +++ b/resources/Schema/Entities/MovementTest.xml @@ -22,7 +22,7 @@ - + @@ -133,6 +133,51 @@ + + + + + Schema/Entities/Player.xml + + + + + + + + + + + + + + + + + Models/Assault.obj + + + + + + + + + + + + + Models/Assault.obj + + + + + + + + + + diff --git a/src/Game/Systems/PlayerSpawnSystem.cpp b/src/Game/Systems/PlayerSpawnSystem.cpp index fe377866..84dce05c 100644 --- a/src/Game/Systems/PlayerSpawnSystem.cpp +++ b/src/Game/Systems/PlayerSpawnSystem.cpp @@ -78,6 +78,9 @@ bool PlayerSpawnSystem::OnPlayerSpawned(Events::PlayerSpawned& e) m_World->DeleteEntity(m_PlayerEntities[e.PlayerID].ID); } + // Store the player for future reference + m_PlayerEntities[e.PlayerID] = e.Player; + // Set the camera to the correct entity EntityWrapper cameraEntity = e.Player.FirstChildByName("Camera"); if (cameraEntity.Valid()) { @@ -86,8 +89,23 @@ bool PlayerSpawnSystem::OnPlayerSpawned(Events::PlayerSpawned& e) m_EventBroker->Publish(e); } - // Store the player for future reference - m_PlayerEntities[e.PlayerID] = e.Player; + // HACK: Set the player model color to team color + EntityWrapper playerModel = e.Player.FirstChildByName("PlayerModel"); + if (playerModel.Valid() && e.Player.HasComponent("Team")) { + ComponentWrapper cTeam = e.Player["Team"]; + ComponentWrapper cModel = playerModel["Model"]; + if ((ComponentInfo::EnumType)cTeam["Team"] == cTeam["Team"].Enum("Red")) { + cModel["Color"] = glm::vec3(1.f, 0.f, 0.f); + } else if ((ComponentInfo::EnumType)cTeam["Team"] == cTeam["Team"].Enum("Blue")) { + cModel["Color"] = glm::vec3(0.f, 0.25f, 1.f); + } + } + + // TODO: Set the player name to whatever + //EntityWrapper playerName = e.Player.FirstChildByName("PlayerName"); + //if (playerName.Valid()) { + // playerName["Text"]["Content"] = ???; + //} return true; } \ No newline at end of file From 96a735c54289ca80108f6a0c2d48101418801347 Mon Sep 17 00:00:00 2001 From: antc13 Date: Sun, 24 Jan 2016 16:12:31 +0100 Subject: [PATCH 207/224] Changed .obj to .mesh for all meshes. --- assets | 2 +- .../{AnimatedArmy => AnimatedArmy.xml} | 0 resources/Schema/Entities/CaptureTest.xml | 14 ++++++------- .../Schema/Entities/CaptureTestState1.xml | 14 ++++++------- .../Schema/Entities/CaptureTestState2.xml | 14 ++++++------- .../Schema/Entities/CaptureTestState3.xml | 20 +++++++++---------- .../Schema/Entities/CaptureTestState4.xml | 20 +++++++++---------- resources/Schema/Entities/CollisionTest1.xml | 2 +- .../Schema/Entities/EditorWidgetRotate.xml | 6 +++--- .../Schema/Entities/EditorWidgetScale.xml | 8 ++++---- .../Schema/Entities/EditorWidgetTranslate.xml | 14 ++++++------- resources/Schema/Entities/Empty.xml | 12 ++++++++++- resources/Schema/Entities/RenderingWorld.xml | 14 ++++++------- resources/Schema/Entities/ShootEventTest.xml | 20 +++++++++---------- resources/Schema/Entities/Test.xml | 4 ++-- src/Engine/Editor/EditorRenderSystem.cpp | 2 +- src/Engine/Rendering/DrawBloomPass.cpp | 2 +- .../Rendering/DrawColorCorrectionPass.cpp | 2 +- src/Engine/Rendering/DrawFinalPass.cpp | 12 +++++++++++ src/Engine/Rendering/DrawScreenQuadPass.cpp | 2 +- src/Engine/Rendering/RawModelCustom.cpp | 3 +++ src/Tests/ResourceManagerTest.cpp | 2 +- 22 files changed, 107 insertions(+), 82 deletions(-) rename resources/Schema/Entities/{AnimatedArmy => AnimatedArmy.xml} (100%) diff --git a/assets b/assets index e8174f63..068fbb2d 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit e8174f630fc3242e15ada1346b42c72f44cbc854 +Subproject commit 068fbb2d20682dd60f186c82172d7731e60ed7e9 diff --git a/resources/Schema/Entities/AnimatedArmy b/resources/Schema/Entities/AnimatedArmy.xml similarity index 100% rename from resources/Schema/Entities/AnimatedArmy rename to resources/Schema/Entities/AnimatedArmy.xml diff --git a/resources/Schema/Entities/CaptureTest.xml b/resources/Schema/Entities/CaptureTest.xml index 70a8ae14..5f657e51 100644 --- a/resources/Schema/Entities/CaptureTest.xml +++ b/resources/Schema/Entities/CaptureTest.xml @@ -9,7 +9,7 @@ - ../assets/Models/DummyScene.obj + ../assets/Models/DummyScene.mesh @@ -41,7 +41,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -61,7 +61,7 @@ 1 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -81,7 +81,7 @@ 2 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -102,7 +102,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -120,7 +120,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -138,7 +138,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/CaptureTestState1.xml b/resources/Schema/Entities/CaptureTestState1.xml index 75b14858..ffabd5c2 100644 --- a/resources/Schema/Entities/CaptureTestState1.xml +++ b/resources/Schema/Entities/CaptureTestState1.xml @@ -9,7 +9,7 @@ - ../assets/Models/DummyScene.obj + ../assets/Models/DummyScene.mesh @@ -42,7 +42,7 @@ 6.9158446328696002 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -63,7 +63,7 @@ 1 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -83,7 +83,7 @@ 2 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -104,7 +104,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -122,7 +122,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -140,7 +140,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/CaptureTestState2.xml b/resources/Schema/Entities/CaptureTestState2.xml index 77673324..29abdfbd 100644 --- a/resources/Schema/Entities/CaptureTestState2.xml +++ b/resources/Schema/Entities/CaptureTestState2.xml @@ -9,7 +9,7 @@ - ../assets/Models/DummyScene.obj + ../assets/Models/DummyScene.mesh @@ -41,7 +41,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -61,7 +61,7 @@ 1 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -79,7 +79,7 @@ 2 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -98,7 +98,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -116,7 +116,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -134,7 +134,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/CaptureTestState3.xml b/resources/Schema/Entities/CaptureTestState3.xml index 99da90a6..ff875dc4 100644 --- a/resources/Schema/Entities/CaptureTestState3.xml +++ b/resources/Schema/Entities/CaptureTestState3.xml @@ -9,7 +9,7 @@ - ../assets/Models/DummyScene.obj + ../assets/Models/DummyScene.mesh @@ -41,7 +41,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -61,7 +61,7 @@ 1 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -81,7 +81,7 @@ 2 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -101,7 +101,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -122,7 +122,7 @@ 4 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -140,7 +140,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -158,7 +158,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -176,7 +176,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -194,7 +194,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/CaptureTestState4.xml b/resources/Schema/Entities/CaptureTestState4.xml index 695df52e..740d7e7b 100644 --- a/resources/Schema/Entities/CaptureTestState4.xml +++ b/resources/Schema/Entities/CaptureTestState4.xml @@ -9,7 +9,7 @@ - ../assets/Models/DummyScene.obj + ../assets/Models/DummyScene.mesh @@ -41,7 +41,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -61,7 +61,7 @@ 1 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -79,7 +79,7 @@ 2 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -96,7 +96,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -115,7 +115,7 @@ 4 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -133,7 +133,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -151,7 +151,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -169,7 +169,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -187,7 +187,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/CollisionTest1.xml b/resources/Schema/Entities/CollisionTest1.xml index f0b310e1..e731a17a 100644 --- a/resources/Schema/Entities/CollisionTest1.xml +++ b/resources/Schema/Entities/CollisionTest1.xml @@ -24,7 +24,7 @@ false - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/EditorWidgetRotate.xml b/resources/Schema/Entities/EditorWidgetRotate.xml index b918794e..88452aac 100644 --- a/resources/Schema/Entities/EditorWidgetRotate.xml +++ b/resources/Schema/Entities/EditorWidgetRotate.xml @@ -18,7 +18,7 @@ - Models/RotationWidgetX.obj + Models/RotationWidgetX.mesh @@ -33,7 +33,7 @@ - Models/RotationWidgetY.obj + Models/RotationWidgetY.mesh @@ -48,7 +48,7 @@ - Models/RotationWidgetZ.obj + Models/RotationWidgetZ.mesh diff --git a/resources/Schema/Entities/EditorWidgetScale.xml b/resources/Schema/Entities/EditorWidgetScale.xml index 15bcb38b..786b079e 100644 --- a/resources/Schema/Entities/EditorWidgetScale.xml +++ b/resources/Schema/Entities/EditorWidgetScale.xml @@ -3,7 +3,7 @@ - Models/ScaleWidgetOrigin.obj + Models/ScaleWidgetOrigin.mesh @@ -20,7 +20,7 @@ - Models/ScaleWidgetX.obj + Models/ScaleWidgetX.mesh @@ -34,7 +34,7 @@ - Models/ScaleWidgetY.obj + Models/ScaleWidgetY.mesh @@ -48,7 +48,7 @@ - Models/ScaleWidgetZ.obj + Models/ScaleWidgetZ.mesh diff --git a/resources/Schema/Entities/EditorWidgetTranslate.xml b/resources/Schema/Entities/EditorWidgetTranslate.xml index a9b7eaff..d4ed5e76 100644 --- a/resources/Schema/Entities/EditorWidgetTranslate.xml +++ b/resources/Schema/Entities/EditorWidgetTranslate.xml @@ -3,7 +3,7 @@ - Models/TranslationWidgetOrigin.obj + Models/TranslationWidgetOrigin.mesh @@ -18,7 +18,7 @@ - Models/TranslationWidgetX.obj + Models/TranslationWidgetX.mesh @@ -30,7 +30,7 @@ - Models/TranslationWidgetY.obj + Models/TranslationWidgetY.mesh @@ -42,7 +42,7 @@ - Models/TranslationWidgetZ.obj + Models/TranslationWidgetZ.mesh @@ -54,7 +54,7 @@ - Models/WidgetPlaneX.obj + Models/WidgetPlaneX.mesh @@ -66,7 +66,7 @@ - Models/WidgetPlaneY.obj + Models/WidgetPlaneY.mesh @@ -78,7 +78,7 @@ - Models/WidgetPlaneZ.obj + Models/WidgetPlaneZ.mesh diff --git a/resources/Schema/Entities/Empty.xml b/resources/Schema/Entities/Empty.xml index 6efd8318..c9b8924f 100644 --- a/resources/Schema/Entities/Empty.xml +++ b/resources/Schema/Entities/Empty.xml @@ -5,6 +5,16 @@ - + + + + + + + + + + + diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 69b18982..796a66f0 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -12,7 +12,7 @@ ActionCamera - Models/Camera.obj + Models/Camera.mesh @@ -39,7 +39,7 @@ - Models/Core/UnitPlane.obj + Models/Core/UnitPlane.mesh @@ -51,7 +51,7 @@ - Models/Assault.obj + Models/Assault.mesh @@ -190,7 +190,7 @@ - Models/Assault.obj + Models/Assault.mesh @@ -205,7 +205,7 @@ - Models/Camera.obj + Models/Camera.mesh false @@ -237,7 +237,7 @@ 0.80000001192092896 - Models/DirectionalLightWidget.obj + Models/DirectionalLightWidget.mesh @@ -249,7 +249,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/ShootEventTest.xml b/resources/Schema/Entities/ShootEventTest.xml index eae333b6..9e9adf50 100644 --- a/resources/Schema/Entities/ShootEventTest.xml +++ b/resources/Schema/Entities/ShootEventTest.xml @@ -9,7 +9,7 @@ - ../assets/Models/DummyScene.obj + ../assets/Models/DummyScene.mesh @@ -41,7 +41,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -61,7 +61,7 @@ 1 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -79,7 +79,7 @@ 2 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -96,7 +96,7 @@ 3 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -115,7 +115,7 @@ 4 - ../assets/Models/Core/UnitSphere.obj + ../assets/Models/Core/UnitSphere.mesh @@ -133,7 +133,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -151,7 +151,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -171,7 +171,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh @@ -191,7 +191,7 @@ - ../assets/Models/Core/UnitCube.obj + ../assets/Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/Test.xml b/resources/Schema/Entities/Test.xml index 42e2660e..1f8da1a3 100644 --- a/resources/Schema/Entities/Test.xml +++ b/resources/Schema/Entities/Test.xml @@ -6,7 +6,7 @@ - Models/DummyScene.obj + Models/DummyScene.mesh @@ -19,7 +19,7 @@ - Models/Camera.obj + Models/Camera.mesh diff --git a/src/Engine/Editor/EditorRenderSystem.cpp b/src/Engine/Editor/EditorRenderSystem.cpp index 2e31e3f0..ed054052 100644 --- a/src/Engine/Editor/EditorRenderSystem.cpp +++ b/src/Engine/Editor/EditorRenderSystem.cpp @@ -39,7 +39,7 @@ void EditorRenderSystem::Update(double dt) continue; } catch (const std::exception&) { try { - model = ResourceManager::Load<::Model>("Models/Core/Error.obj"); + model = ResourceManager::Load<::Model>("Models/Core/Error.mesh"); } catch (const std::exception&) { continue; } diff --git a/src/Engine/Rendering/DrawBloomPass.cpp b/src/Engine/Rendering/DrawBloomPass.cpp index 1ad97eb5..8fe1d807 100644 --- a/src/Engine/Rendering/DrawBloomPass.cpp +++ b/src/Engine/Rendering/DrawBloomPass.cpp @@ -4,7 +4,7 @@ DrawBloomPass::DrawBloomPass(IRenderer* renderer) { m_Renderer = renderer; - m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.mesh"); InitializeTextures(); InitializeBuffers(); diff --git a/src/Engine/Rendering/DrawColorCorrectionPass.cpp b/src/Engine/Rendering/DrawColorCorrectionPass.cpp index 5989584e..ba9efe3e 100644 --- a/src/Engine/Rendering/DrawColorCorrectionPass.cpp +++ b/src/Engine/Rendering/DrawColorCorrectionPass.cpp @@ -4,7 +4,7 @@ DrawColorCorrectionPass::DrawColorCorrectionPass(IRenderer* renderer) { m_Renderer = renderer; - m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.mesh"); m_Exposure = 0.4; //TODO: Renderer: Fixa så att denna går att ändra på genom komponent eller setting. InitializeShaderPrograms(); diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index 9977f194..ca2a9d77 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -94,6 +94,18 @@ void DrawFinalPass::Draw(RenderScene& scene) glBindTexture(GL_TEXTURE_2D, m_BlackTexture->m_Texture); }*/ + //TODO: Fixa så att modelsJobs kan spela upp olika animationer och så att den kan få in en tid istället för 1.0f - Hälsningar Johan och Andreas :) + if (modelJob->Model->m_RawModel->m_Skeleton != nullptr) { + auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("running"); + if (animation != nullptr) { + std::vector frameBones = modelJob->Model->m_RawModel->m_Skeleton->GetFrameBones( + *animation, + 0.0f + ); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "Bones"), frameBones.size(), GL_FALSE, glm::value_ptr(frameBones[0])); + } + } + glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); glDrawElements(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, (void*)(modelJob->StartIndex * sizeof(unsigned int))); diff --git a/src/Engine/Rendering/DrawScreenQuadPass.cpp b/src/Engine/Rendering/DrawScreenQuadPass.cpp index 4b155fc9..b17f5e29 100644 --- a/src/Engine/Rendering/DrawScreenQuadPass.cpp +++ b/src/Engine/Rendering/DrawScreenQuadPass.cpp @@ -4,7 +4,7 @@ DrawScreenQuadPass::DrawScreenQuadPass(IRenderer* renderer) { m_Renderer = renderer; - m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.obj"); + m_ScreenQuad = ResourceManager::Load("Models/Core/ScreenQuad.mesh"); InitializeShaderPrograms(); } diff --git a/src/Engine/Rendering/RawModelCustom.cpp b/src/Engine/Rendering/RawModelCustom.cpp index 74c524c9..83f6e703 100644 --- a/src/Engine/Rendering/RawModelCustom.cpp +++ b/src/Engine/Rendering/RawModelCustom.cpp @@ -4,6 +4,9 @@ RawModelCustom::RawModelCustom(std::string fileName) { + if(fileName.substr(fileName.find_last_of(".")).compare(".mesh") != 0) { + throw Resource::FailedLoadingException("Unknown model file format. Please use \".mesh\" files."); + } fileName = fileName.erase(fileName.find_last_of("."), fileName.find_last_of(".") - fileName.size()); ReadMeshFile(fileName); ReadMaterialFile(fileName); diff --git a/src/Tests/ResourceManagerTest.cpp b/src/Tests/ResourceManagerTest.cpp index df1fd76d..1f9f4991 100644 --- a/src/Tests/ResourceManagerTest.cpp +++ b/src/Tests/ResourceManagerTest.cpp @@ -26,7 +26,7 @@ BOOST_AUTO_TEST_CASE(resourceManagerTest) BOOST_CHECK(!ResourceManager::IsResourceLoaded("ConfigFile", "Config.ini")); //configfile without register - BOOST_CHECK_THROW(ResourceManager::Load("Models/Core/ScreenQuad.obj"),Resource::FailedLoadingException); + BOOST_CHECK_THROW(ResourceManager::Load("Models/Core/ScreenQuad.mesh"),Resource::FailedLoadingException); //there is no error feedback to check if you try to release the wrong resources - hence that cant be tested either } From aa115befa936512a9d7a33c36db1e6cac040023a Mon Sep 17 00:00:00 2001 From: antc13 Date: Sun, 24 Jan 2016 17:04:12 +0100 Subject: [PATCH 208/224] UnitRaptor is now displayed while models are being loaded in. --- src/Engine/Rendering/RenderSystem.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Engine/Rendering/RenderSystem.cpp b/src/Engine/Rendering/RenderSystem.cpp index 9496fe7a..58bbd1ee 100644 --- a/src/Engine/Rendering/RenderSystem.cpp +++ b/src/Engine/Rendering/RenderSystem.cpp @@ -59,7 +59,7 @@ void RenderSystem::fillModels(std::list>& jobs) model = ResourceManager::Load<::Model, true>(resource); } catch (const Resource::StillLoadingException&) { //continue; - model = ResourceManager::Load<::Model>("Models/Core/Error.mesh"); + model = ResourceManager::Load<::Model>("Models/Core/UnitRaptor.mesh"); } catch (const std::exception&) { try { model = ResourceManager::Load<::Model>("Models/Core/Error.mesh"); From af2f017cb4664321d381e1008ce32e279af85fc2 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sun, 24 Jan 2016 17:05:34 +0100 Subject: [PATCH 209/224] AnimationSystem base WIP --- include/Engine/Rendering/AnimationSystem.h | 28 +++++++++++ include/Engine/Rendering/EAnimationComplete.h | 18 ++++++++ resources/Schema/Components.xsd | 1 + resources/Schema/Components/Animation.xml | 6 +++ resources/Schema/Components/Animation.xsd | 16 +++++++ resources/Schema/Entities/RenderingWorld.xml | 46 +++++++++++++++---- src/Engine/Rendering/AnimationSystem.cpp | 32 +++++++++++++ 7 files changed, 138 insertions(+), 9 deletions(-) create mode 100644 include/Engine/Rendering/AnimationSystem.h create mode 100644 include/Engine/Rendering/EAnimationComplete.h create mode 100644 resources/Schema/Components/Animation.xml create mode 100644 resources/Schema/Components/Animation.xsd create mode 100644 src/Engine/Rendering/AnimationSystem.cpp diff --git a/include/Engine/Rendering/AnimationSystem.h b/include/Engine/Rendering/AnimationSystem.h new file mode 100644 index 00000000..0876bfd7 --- /dev/null +++ b/include/Engine/Rendering/AnimationSystem.h @@ -0,0 +1,28 @@ +#ifndef AnimationSystem_h__ +#define AnimationSystem_h__ + +#include "GLM.h" + +#include "Common.h" +#include "Core/System.h" +#include "Core/ResourceManager.h" +#include "Rendering/Model.h" +#include "Rendering/EAnimationComplete.h" + +class AnimationSystem : public PureSystem +{ +public: + AnimationSystem(World* world, EventBroker* eventBroker) + : System(world, eventBroker) + , PureSystem("Animation") + { + + } + ~AnimationSystem() { } + virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& animationComponent, double dt) override; +private: + + +}; + +#endif \ No newline at end of file diff --git a/include/Engine/Rendering/EAnimationComplete.h b/include/Engine/Rendering/EAnimationComplete.h new file mode 100644 index 00000000..00519a38 --- /dev/null +++ b/include/Engine/Rendering/EAnimationComplete.h @@ -0,0 +1,18 @@ +#ifndef Events_AnimationComplete_h__ +#define Events_AnimationComplete_h__ + +#include "../Core/EventBroker.h" +#include "../Core/EntityWrapper.h" + +namespace Events +{ + +struct AnimationComplete : Event +{ + EntityWrapper Entity; + std::string Name; +}; + +} + +#endif diff --git a/resources/Schema/Components.xsd b/resources/Schema/Components.xsd index 12d94611..d663f695 100644 --- a/resources/Schema/Components.xsd +++ b/resources/Schema/Components.xsd @@ -23,4 +23,5 @@ + \ No newline at end of file diff --git a/resources/Schema/Components/Animation.xml b/resources/Schema/Components/Animation.xml new file mode 100644 index 00000000..01af2747 --- /dev/null +++ b/resources/Schema/Components/Animation.xml @@ -0,0 +1,6 @@ + + + + 0 + true + \ No newline at end of file diff --git a/resources/Schema/Components/Animation.xsd b/resources/Schema/Components/Animation.xsd new file mode 100644 index 00000000..0dd21f29 --- /dev/null +++ b/resources/Schema/Components/Animation.xsd @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 69b18982..f8aa2491 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -8,9 +8,7 @@ - - ActionCamera - + Models/Camera.obj @@ -25,7 +23,9 @@ Camera #2 Fonts/DroidSans.ttf,64 - 0 + + + @@ -79,7 +79,7 @@ - + @@ -200,9 +200,7 @@ - - MainCamera - + Models/Camera.obj @@ -219,7 +217,9 @@ Taiwan #1 Fonts/DroidSans.ttf,64 - 0 + + + @@ -257,6 +257,34 @@ + + + + + Models/Arm.dae + + + + + + + + + + + + + + Models/Sid_Flying.dae + + + + + + + + + diff --git a/src/Engine/Rendering/AnimationSystem.cpp b/src/Engine/Rendering/AnimationSystem.cpp new file mode 100644 index 00000000..b65c5a33 --- /dev/null +++ b/src/Engine/Rendering/AnimationSystem.cpp @@ -0,0 +1,32 @@ +#include "Rendering/AnimationSystem.h" + +void AnimationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& animationComponent, double dt) +{ + if(!entity.HasComponent("Model")) { + return; + } + + Model* model = ResourceManager::Load(entity["Model"]["Resource"]); + //Skeleton* skeleton = model->m_Skeleton; + //auto animation == skeleton->GetAnimation(animation["Name"]); + + double animationSpeed = (double)animationComponent["Speed"]; + + if( animationSpeed != 0.0) { + double nextTime = (double)animationComponent["Time"] + animationSpeed * dt; + + if (!animationComponent["Loop"] && glm::abs(nextTime) > animation->Duration) { + (double&)animationComponent["Time"] = glm::sign(nextTime) * animation->Duration; + (double&)animationComponent["Speed"] = 0.0; + Events::AnimationComplete e; + e.Entity = entity; + // e.Name = animationComponent->Name; + m_EventBroker->Publish(e); + } else { + (double&)animationComponent["Time"] = nextTime; + } + + } + +} + From 235b26ad616ada2ce3e4292b81499d19fa532acc Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 17:16:18 +0100 Subject: [PATCH 210/224] WIP shoot --- include/Engine/Core/EPlayerDamage.h | 6 +-- include/Engine/Core/EShoot.h | 6 +-- include/Engine/Core/EntityWrapper.h | 3 +- include/Game/Systems/WeaponSystem.h | 19 ++++--- resources/Schema/Entities/Player.xml | 5 +- src/Engine/Core/EntityWrapper.cpp | 12 +++++ src/Engine/Network/Client.cpp | 4 +- src/Engine/Network/Server.cpp | 4 +- src/Game/Systems/HealthSystem.cpp | 2 +- src/Game/Systems/WeaponSystem.cpp | 80 +++++++++++++++++++--------- 10 files changed, 93 insertions(+), 48 deletions(-) diff --git a/include/Engine/Core/EPlayerDamage.h b/include/Engine/Core/EPlayerDamage.h index e0f2acd7..a7e135ce 100644 --- a/include/Engine/Core/EPlayerDamage.h +++ b/include/Engine/Core/EPlayerDamage.h @@ -2,15 +2,15 @@ #define EPlayerDamage_h__ #include "EventBroker.h" -#include "../Core/Entity.h" +#include "../Core/EntityWrapper.h" namespace Events { struct PlayerDamage : Event { - double DamageAmount; - EntityID PlayerDamagedID; + EntityWrapper Player; + double Damage; }; } diff --git a/include/Engine/Core/EShoot.h b/include/Engine/Core/EShoot.h index fd54122f..76821a24 100644 --- a/include/Engine/Core/EShoot.h +++ b/include/Engine/Core/EShoot.h @@ -2,16 +2,14 @@ #define EShoot_h__ #include "EventBroker.h" -#include "../Core/Entity.h" -#include "Engine/GLM.h" +#include "../Core/EntityWrapper.h" namespace Events { struct Shoot : Event { - //ID for who made the shot - EntityID shooter; + EntityWrapper Player; }; } diff --git a/include/Engine/Core/EntityWrapper.h b/include/Engine/Core/EntityWrapper.h index 711f5045..79bae9ed 100644 --- a/include/Engine/Core/EntityWrapper.h +++ b/include/Engine/Core/EntityWrapper.h @@ -23,9 +23,10 @@ struct EntityWrapper static const EntityWrapper Invalid; - bool HasComponent(const std::string& componentName); + bool HasComponent(const std::string& componentType); EntityWrapper Parent(); EntityWrapper FirstChildByName(const std::string& name); + EntityWrapper FirstParentWithComponent(const std::string& componentType); bool IsChildOf(EntityWrapper potentialParent); bool Valid(); diff --git a/include/Game/Systems/WeaponSystem.h b/include/Game/Systems/WeaponSystem.h index 5acf72b3..0397b1a3 100644 --- a/include/Game/Systems/WeaponSystem.h +++ b/include/Game/Systems/WeaponSystem.h @@ -9,6 +9,7 @@ #include "Core/System.h" #include "Core/EPlayerDamage.h" #include "Core/EShoot.h" +#include "Core/EPlayerSpawned.h" #include "Input/EInputCommand.h" #include @@ -23,16 +24,18 @@ public: virtual void Update(double dt) override; private: - //methods which will take care of specific events - EventRelay m_EShoot; - bool WeaponSystem::OnShoot(const Events::Shoot& e); - - EventRelay m_EInputCommand; - bool WeaponSystem::OnInputCommand(const Events::InputCommand& e); - IRenderer* m_Renderer; - std::vector> m_EShootVector; + // State + EntityWrapper m_LocalPlayer = EntityWrapper::Invalid; + + // Events + EventRelay m_EPlayerSpawned; + bool WeaponSystem::OnPlayerSpawned(const Events::PlayerSpawned& e); + EventRelay m_EShoot; + bool WeaponSystem::OnShoot(const Events::Shoot& e); + EventRelay m_EInputCommand; + bool WeaponSystem::OnInputCommand(const Events::InputCommand& e); }; #endif \ No newline at end of file diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 00d2e295..4ac1d205 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -9,7 +9,7 @@ - + false 5 @@ -20,7 +20,7 @@ - + @@ -82,6 +82,7 @@ Models/AssaultHeadless.obj + diff --git a/src/Engine/Core/EntityWrapper.cpp b/src/Engine/Core/EntityWrapper.cpp index 55d341e1..02d9246a 100644 --- a/src/Engine/Core/EntityWrapper.cpp +++ b/src/Engine/Core/EntityWrapper.cpp @@ -36,6 +36,18 @@ EntityWrapper EntityWrapper::FirstChildByName(const std::string& name) return EntityWrapper::Invalid; } +EntityWrapper EntityWrapper::FirstParentWithComponent(const std::string& componentType) +{ + EntityWrapper entity = *this; + while (entity.Parent().Valid()) { + entity = entity.Parent(); + if (entity.HasComponent(componentType)) { + return entity; + } + } + return EntityWrapper::Invalid; +} + bool EntityWrapper::IsChildOf(EntityWrapper potentialParent) { EntityWrapper entity = *this; diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 1dd2bd04..5ddba631 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -327,8 +327,8 @@ bool Client::OnInputCommand(const Events::InputCommand & e) bool Client::OnPlayerDamage(const Events::PlayerDamage & e) { Packet packet(MessageType::OnInputCommand, m_SendPacketID); - packet.WritePrimitive(e.DamageAmount); - packet.WritePrimitive(e.PlayerDamagedID); + packet.WritePrimitive(e.Damage); + packet.WritePrimitive(e.Player.ID); send(packet); return false; } diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 9d0a83d9..77702960 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -286,8 +286,8 @@ void Server::parseOnInputCommand(Packet& packet) void Server::parseOnPlayerDamage(Packet & packet) { Events::PlayerDamage e; - e.DamageAmount = packet.ReadPrimitive(); - e.PlayerDamagedID = packet.ReadPrimitive(); + e.Damage = packet.ReadPrimitive(); + e.Player = EntityWrapper(m_World, packet.ReadPrimitive()); m_EventBroker->Publish(e); //LOG_DEBUG("Server::parseOnPlayerDamage: Command is %s. Value is %f. PlayerID is %i.", e.DamageAmount, e.PlayerDamagedID, e.TypeOfDamage.c_str()); } diff --git a/src/Game/Systems/HealthSystem.cpp b/src/Game/Systems/HealthSystem.cpp index 5e5be33e..64b8e51b 100644 --- a/src/Game/Systems/HealthSystem.cpp +++ b/src/Game/Systems/HealthSystem.cpp @@ -49,7 +49,7 @@ void HealthSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& comp bool HealthSystem::OnPlayerDamaged(const Events::PlayerDamage& e) { //save the changed HP to a vector. it will be taken care of in UpdateComponent - m_DeltaHealthVector.push_back(std::make_tuple(e.PlayerDamagedID, -e.DamageAmount)); + //m_DeltaHealthVector.push_back(std::make_tuple(e.PlayerDamagedID, -e.DamageAmount)); return true; } diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp index 11f76490..8a88eb13 100644 --- a/src/Game/Systems/WeaponSystem.cpp +++ b/src/Game/Systems/WeaponSystem.cpp @@ -5,49 +5,79 @@ WeaponSystem::WeaponSystem(World* world, EventBroker* eventBroker, IRenderer* re , ImpureSystem() , m_Renderer(renderer) { + EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &WeaponSystem::OnPlayerSpawned); EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &WeaponSystem::OnInputCommand); EVENT_SUBSCRIBE_MEMBER(m_EShoot, &WeaponSystem::OnShoot); } void WeaponSystem::Update(double dt) { - for (int i = m_EShootVector.size(); i > 0; i--) - { - //TODO: check if player has enough ammo and if weapon has a cooldown or not - //pick the object - PickData pickDataFromShot = m_Renderer->Pick(std::get<1>(m_EShootVector[i - 1])); - if (pickDataFromShot.Entity == EntityID_Invalid) { - m_EShootVector.erase(m_EShootVector.begin() + i - 1); - continue; - } - //if its a player, do PlayerDamage event - const bool hasPlayerComponent = m_World->HasComponent(pickDataFromShot.Entity, "Player"); - if (hasPlayerComponent) { - Events::PlayerDamage ePlayerDamage; - //TODO: damage based on weapontype/class? - //TODO: multiple shots at the same time? (shotgunner) - ePlayerDamage.DamageAmount = 25; - ePlayerDamage.PlayerDamagedID = pickDataFromShot.Entity; - m_EventBroker->Publish(ePlayerDamage); - } - m_EShootVector.erase(m_EShootVector.begin() + i - 1); +} + +bool WeaponSystem::OnPlayerSpawned(const Events::PlayerSpawned& e) +{ + if (e.PlayerID == -1) { + m_LocalPlayer = e.Player; } + return true; } bool WeaponSystem::OnInputCommand(const Events::InputCommand& e) { + // Only shoot client-side! + if (e.PlayerID != -1) { + return false; + } + + // Only shoot if the player is alive + if (!m_LocalPlayer.Valid()) { + return false; + } + if (e.Command == "PrimaryFire" && e.Value > 0) { Events::Shoot eShoot; - eShoot.shooter = e.PlayerID; + eShoot.Player = m_LocalPlayer; m_EventBroker->Publish(eShoot); } + return true; } -bool WeaponSystem::OnShoot(const Events::Shoot& e) { - //screen center, based on current resolution! + +bool WeaponSystem::OnShoot(const Events::Shoot& eShoot) { + // Screen center, based on current resolution! Rectangle screenResolution = m_Renderer->Resolution(); glm::vec2 centerScreen = glm::vec2(screenResolution.Width / 2, screenResolution.Height / 2); - m_EShootVector.push_back(std::make_pair(e.shooter, centerScreen)); + + // TODO: check if player has enough ammo and if weapon has a cooldown or not + + // Pick middle of screen + PickData pickData = m_Renderer->Pick(centerScreen); + if (pickData.Entity == EntityID_Invalid) { + return false; + } + + EntityWrapper player(m_World, pickData.Entity); + + // Only care about players being hit + if (!player.HasComponent("Player")) { + player = player.FirstParentWithComponent("Player"); + } + if (!player.Valid()) { + return false; + } + + // Check for friendly fire + EntityWrapper shooter = eShoot.Player; + if ((ComponentInfo::EnumType)player["Team"]["Team"] == (ComponentInfo::EnumType)shooter["Team"]["Team"]) { + return false; + } + + // TODO: Weapon damage calculations etc + Events::PlayerDamage ePlayerDamage; + ePlayerDamage.Player = player; + ePlayerDamage.Damage = 100; + m_EventBroker->Publish(ePlayerDamage); + return true; -} \ No newline at end of file +} From 2eaad2aa00c62607e8a963e995a72451d2c62dd0 Mon Sep 17 00:00:00 2001 From: stiffly Date: Sun, 24 Jan 2016 17:15:26 +0100 Subject: [PATCH 211/224] Client now responds to deleted entity and component in server --- include/Engine/Network/Client.h | 3 ++ include/Engine/Network/MessageType.h | 4 ++- include/Engine/Network/Server.h | 6 ++++ src/Engine/Network/Client.cpp | 49 ++++++++++++++++++++++++++-- src/Engine/Network/Server.cpp | 23 +++++++++++++ src/Game/Game.cpp | 2 +- 6 files changed, 83 insertions(+), 4 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index 92d78f4a..e2ba8bc2 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -79,6 +79,8 @@ private: void parsePing(); void parseKick(); void parsePlayersSpawned(Packet& packet); + void parseEntityDeletion(Packet& packet); + void parseComponentDeletion(Packet& packet); void InterpolateFields(Packet & packet, const ComponentInfo & componentInfo, const EntityID & entityID, const std::string & componentType); void parseSnapshot(Packet& packet); void identifyPacketLoss(); @@ -92,6 +94,7 @@ private: // Returns if server EntityID exist in map bool serverClientMapsHasEntity(EntityID serverEntityID); void insertIntoServerClientMaps(EntityID serverEntityID, EntityID clientEntityID); + void deleteFromServerClientMaps(EntityID serverEntityID, EntityID clientEntityID); // Events EventBroker* m_EventBroker; diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index 13ac5e9d..894feea0 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -15,7 +15,9 @@ enum class MessageType PlayerConnected, BecomePlayer, Kick, - OnPlayerSpawned + OnPlayerSpawned, + EntityDeleted, + ComponentDeleted }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 35e6d855..00de3444 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -16,6 +16,8 @@ #include "Core/EPlayerDamage.h" #include "Network/EPlayerDisconnected.h" #include "Core/EPlayerSpawned.h" +#include "Core/EEntityDeleted.h" +#include "Core/EComponentDeleted.h" class Server : public Network { @@ -83,6 +85,10 @@ private: bool OnInputCommand(const Events::InputCommand& e); EventRelay m_EPlayerSpawned; bool OnPlayerSpawned(const Events::PlayerSpawned& e); + EventRelay m_EEntityDeleted; + bool OnEntityDeleted(const Events::EntityDeleted& e); + EventRelay m_EComponentDeleted; + bool OnComponentDeleted(const Events::ComponentDeleted& e); }; #endif diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 2a4f531e..699a82aa 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -96,6 +96,12 @@ void Client::parseMessageType(Packet& packet) case MessageType::OnPlayerSpawned: parsePlayersSpawned(packet); break; + case MessageType::EntityDeleted: + parseEntityDeletion(packet); + break; + case MessageType::ComponentDeleted: + parseComponentDeletion(packet); + break; default: break; } @@ -142,6 +148,25 @@ void Client::parsePlayersSpawned(Packet& packet) m_EventBroker->Publish(e); } +void Client::parseEntityDeletion(Packet & packet) +{ + EntityID entityToDelete = packet.ReadPrimitive(); + EntityID localEntity = m_ServerIDToClientID.at(entityToDelete); + if (m_World->ValidEntity(localEntity)) { + m_World->DeleteEntity(localEntity); + deleteFromServerClientMaps(entityToDelete, localEntity); + } +} + +void Client::parseComponentDeletion(Packet & packet) +{ + EntityID entity = packet.ReadPrimitive(); + std::string componentType = packet.ReadString(); + if (m_World->HasComponent(entity, componentType)) { + m_World->DeleteComponent(m_ServerIDToClientID.at(entity), componentType); + } +} + // Fields with strings will not work right now void Client::InterpolateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType) { @@ -370,12 +395,26 @@ void Client::becomePlayer() bool Client::clientServerMapsHasEntity(EntityID clientEntityID) { - return m_ClientIDToServerID.find(clientEntityID) != m_ClientIDToServerID.end(); + if (m_ClientIDToServerID.find(clientEntityID) != m_ClientIDToServerID.end()) { + if (m_World->ValidEntity(clientEntityID)) { + return true; + } + EntityID serverEntityID = m_ClientIDToServerID.at(clientEntityID); + deleteFromServerClientMaps(serverEntityID, clientEntityID); + } + return false; } bool Client::serverClientMapsHasEntity(EntityID serverEntityID) { - return m_ServerIDToClientID.find(serverEntityID) != m_ServerIDToClientID.end(); + if (m_ServerIDToClientID.find(serverEntityID) != m_ServerIDToClientID.end()) { + EntityID localEntityID = m_ServerIDToClientID.at(serverEntityID); + if (m_World->ValidEntity(localEntityID)) { + return true; + } + deleteFromServerClientMaps(serverEntityID, localEntityID); + } + return false; } void Client::insertIntoServerClientMaps(EntityID serverEntityID, EntityID clientEntityID) @@ -384,3 +423,9 @@ void Client::insertIntoServerClientMaps(EntityID serverEntityID, EntityID client m_ClientIDToServerID.insert(std::make_pair(clientEntityID, serverEntityID)); } + +void Client::deleteFromServerClientMaps(EntityID serverEntityID, EntityID clientEntityID) +{ + m_ServerIDToClientID.erase(serverEntityID); + m_ClientIDToServerID.erase(clientEntityID); +} diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 98774b99..d8064c3a 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -21,6 +21,8 @@ void Server::Start(World* world, EventBroker* eventBroker) // Subscribe to events EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Server::OnInputCommand); EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &Server::OnPlayerSpawned); + EVENT_SUBSCRIBE_MEMBER(m_EEntityDeleted, &Server::OnEntityDeleted); + EVENT_SUBSCRIBE_MEMBER(m_EComponentDeleted, &Server::OnComponentDeleted); for (size_t i = 0; i < m_MaxConnections; i++) { m_PlayerDefinitions[i].StopTime = std::clock(); } @@ -465,3 +467,24 @@ bool Server::OnPlayerSpawned(const Events::PlayerSpawned & e) send(e.PlayerID, packet); return false; } + +bool Server::OnEntityDeleted(const Events::EntityDeleted & e) +{ + if (!e.Cascaded) { + Packet packet = Packet(MessageType::EntityDeleted); + packet.WritePrimitive(e.DeletedEntity); + broadcast(packet); + } + return false; +} + +bool Server::OnComponentDeleted(const Events::ComponentDeleted & e) +{ + if (!e.Cascaded) { + Packet packet = Packet(MessageType::ComponentDeleted); + packet.WritePrimitive(e.Entity); + packet.WriteString(e.ComponentType); + broadcast(packet); + } + return false; +} diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 5de61b8c..ef51aca6 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -77,7 +77,7 @@ Game::Game(int argc, char* argv[]) // All systems with orderlevel 0 will be updated first. unsigned int updateOrderLevel = 0; m_SystemPipeline->AddSystem(updateOrderLevel); - m_SystemPipeline->AddSystem(updateOrderLevel); + //m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); From 8d61632c26d3f3df578bea005cd019e3f3824ea7 Mon Sep 17 00:00:00 2001 From: stiffly Date: Sun, 24 Jan 2016 17:40:43 +0100 Subject: [PATCH 212/224] No longer spawns a f**king sphere. --- src/Engine/Network/Server.cpp | 8 -------- 1 file changed, 8 deletions(-) diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index d8064c3a..325ff845 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -409,14 +409,6 @@ void Server::createPlayer() for (PlayerID playerIndex = 0; playerIndex < m_MaxConnections; playerIndex++) { if (m_PlayerDefinitions[playerIndex].Endpoint.address() == boost::asio::ip::address()) { m_PlayerDefinitions[playerIndex] = m_ConnectedUsers[userIndex]; - EntityID entityID = m_World->CreateEntity(); - ComponentWrapper transform = m_World->AttachComponent(entityID, "Transform"); - transform["Position"] = glm::vec3(-1.5f, 0.f, 0.f); - ComponentWrapper model = m_World->AttachComponent(entityID, "Model"); - model["Resource"] = "Models/Core/UnitSphere.obj"; - model["Color"] = glm::vec4(rand()%255 / 255.f, rand()%255 / 255.f, rand() %255 / 255.f, 1.f); - ComponentWrapper player = m_World->AttachComponent(entityID, "Player"); - m_PlayerDefinitions[playerIndex].EntityID = entityID; return; } } From 8cf9caf7aaf191cb0b13124a7228d7e74e88593c Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sun, 24 Jan 2016 18:31:23 +0100 Subject: [PATCH 213/224] AnimationSystem working --- include/Engine/Rendering/AnimationSystem.h | 1 + include/Engine/Rendering/ModelJob.h | 14 +++++ resources/Schema/Entities/FastWorld.xml | 66 ++++++++++++++++++++ resources/Schema/Entities/RenderingWorld.xml | 12 ++-- src/Engine/Rendering/AnimationSystem.cpp | 16 +++-- src/Engine/Rendering/DrawFinalPass.cpp | 9 +-- src/Game/Game.cpp | 2 + 7 files changed, 103 insertions(+), 17 deletions(-) create mode 100644 resources/Schema/Entities/FastWorld.xml diff --git a/include/Engine/Rendering/AnimationSystem.h b/include/Engine/Rendering/AnimationSystem.h index 0876bfd7..fcdcbc92 100644 --- a/include/Engine/Rendering/AnimationSystem.h +++ b/include/Engine/Rendering/AnimationSystem.h @@ -8,6 +8,7 @@ #include "Core/ResourceManager.h" #include "Rendering/Model.h" #include "Rendering/EAnimationComplete.h" +#include "Rendering/Skeleton.h" class AnimationSystem : public PureSystem { diff --git a/include/Engine/Rendering/ModelJob.h b/include/Engine/Rendering/ModelJob.h index 01f4cca4..ccfd209c 100644 --- a/include/Engine/Rendering/ModelJob.h +++ b/include/Engine/Rendering/ModelJob.h @@ -13,6 +13,7 @@ #include "Camera.h" #include "../Core/World.h" #include "../Core/Transform.h" +#include "Skeleton.h" struct ModelJob : RenderJob { @@ -37,6 +38,14 @@ struct ModelJob : RenderJob glm::vec3 worldpos = glm::vec3(camera->ViewMatrix() * glm::vec4(abspos, 1)); Depth = worldpos.z; World = world; + + Skeleton = Model->m_RawModel->m_Skeleton; + + if (world->HasComponent(Entity, "Animation")) { + auto animationComponent = world->GetComponent(Entity, "Animation"); + Animation = model->m_RawModel->m_Skeleton->GetAnimation(animationComponent["Name"]); + AnimationTime = (double)animationComponent["Time"]; + } }; unsigned int TextureID; @@ -51,6 +60,11 @@ struct ModelJob : RenderJob float Shininess = 0.f; glm::vec4 Color; const ::Model* Model = nullptr; + ::Skeleton* Skeleton = nullptr; + const ::Skeleton::Animation* Animation = nullptr; + + float AnimationTime = 0.f; + glm::vec4 DiffuseColor; glm::vec4 SpecularColor; glm::vec4 IncandescenceColor; diff --git a/resources/Schema/Entities/FastWorld.xml b/resources/Schema/Entities/FastWorld.xml new file mode 100644 index 00000000..655a9766 --- /dev/null +++ b/resources/Schema/Entities/FastWorld.xml @@ -0,0 +1,66 @@ + + + + + + + + + + + + + + Models/Core/UnitSphere.mesh + + + + + + + + + + + + running + + 1 + + + Models/Animtest.mesh + + + + + + + + + + + + + + + + + + + + + Got to Go FAST!!!! + Fonts/DroidSans.ttf,60 + + + + + + + + + + + + + diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 6b2dc510..2c101dc6 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -64,6 +64,7 @@ Welcome! Fonts/DroidSans.ttf,1280 + @@ -79,7 +80,7 @@ - + @@ -261,7 +262,7 @@ - Models/Arm.dae + asd @@ -273,14 +274,15 @@ - + + + - Models/Sid_Flying.dae + Models/Animtest.mesh - diff --git a/src/Engine/Rendering/AnimationSystem.cpp b/src/Engine/Rendering/AnimationSystem.cpp index b65c5a33..e699866b 100644 --- a/src/Engine/Rendering/AnimationSystem.cpp +++ b/src/Engine/Rendering/AnimationSystem.cpp @@ -7,25 +7,29 @@ void AnimationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& a } Model* model = ResourceManager::Load(entity["Model"]["Resource"]); - //Skeleton* skeleton = model->m_Skeleton; - //auto animation == skeleton->GetAnimation(animation["Name"]); + Skeleton* skeleton = model->m_RawModel->m_Skeleton; + const Skeleton::Animation* animation = skeleton->GetAnimation(animationComponent["Name"]); double animationSpeed = (double)animationComponent["Speed"]; if( animationSpeed != 0.0) { double nextTime = (double)animationComponent["Time"] + animationSpeed * dt; - if (!animationComponent["Loop"] && glm::abs(nextTime) > animation->Duration) { + + if (!(bool)animationComponent["Loop"] && glm::abs(nextTime) > animation->Duration) { (double&)animationComponent["Time"] = glm::sign(nextTime) * animation->Duration; (double&)animationComponent["Speed"] = 0.0; Events::AnimationComplete e; e.Entity = entity; - // e.Name = animationComponent->Name; + e.Name = (std::string)animationComponent["Name"]; m_EventBroker->Publish(e); } else { - (double&)animationComponent["Time"] = nextTime; + if (glm::abs(nextTime) > animation->Duration) { + (double&)animationComponent["Time"] = glm::abs(nextTime) - animation->Duration; + } else { + (double&)animationComponent["Time"] = nextTime; + } } - } } diff --git a/src/Engine/Rendering/DrawFinalPass.cpp b/src/Engine/Rendering/DrawFinalPass.cpp index ca2a9d77..9abf69d3 100644 --- a/src/Engine/Rendering/DrawFinalPass.cpp +++ b/src/Engine/Rendering/DrawFinalPass.cpp @@ -96,12 +96,9 @@ void DrawFinalPass::Draw(RenderScene& scene) //TODO: Fixa så att modelsJobs kan spela upp olika animationer och så att den kan få in en tid istället för 1.0f - Hälsningar Johan och Andreas :) if (modelJob->Model->m_RawModel->m_Skeleton != nullptr) { - auto animation = modelJob->Model->m_RawModel->m_Skeleton->GetAnimation("running"); - if (animation != nullptr) { - std::vector frameBones = modelJob->Model->m_RawModel->m_Skeleton->GetFrameBones( - *animation, - 0.0f - ); + + if (modelJob->Animation != nullptr) { + std::vector frameBones = modelJob->Skeleton->GetFrameBones( *modelJob->Animation, modelJob->AnimationTime); glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "Bones"), frameBones.size(), GL_FALSE, glm::value_ptr(frameBones[0])); } } diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 384c4a5b..a8e1a947 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -10,6 +10,7 @@ #include "Core/EntityFileWriter.h" #include "Game/Systems/CapturePointSystem.h" #include "Game/Systems/WeaponSystem.h" +#include "../Engine/Rendering/AnimationSystem.h" Game::Game(int argc, char* argv[]) { @@ -86,6 +87,7 @@ Game::Game(int argc, char* argv[]) // Populate Octree with collidables ++updateOrderLevel; m_SystemPipeline->AddSystem(updateOrderLevel, m_OctreeCollision); + m_SystemPipeline->AddSystem(updateOrderLevel); // Collision and TriggerSystem should update after player. ++updateOrderLevel; m_SystemPipeline->AddSystem(updateOrderLevel, m_OctreeCollision); From 9f3d887ac4e83e79ac19811bd8fbddd14a3feaf3 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 18:37:36 +0100 Subject: [PATCH 214/224] Networking bugfixes --- resources/Schema/Entities/Player.xml | 7 ++----- src/Engine/Core/World.cpp | 5 +++++ src/Game/Systems/InterpolationSystem.cpp | 12 ++++++++---- 3 files changed, 15 insertions(+), 9 deletions(-) diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 4ac1d205..8d6b16a4 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -8,9 +8,7 @@ - - false - + 5 @@ -20,7 +18,7 @@ - + @@ -31,7 +29,6 @@ - diff --git a/src/Engine/Core/World.cpp b/src/Engine/Core/World.cpp index 97e3ba9f..0c4c9ce4 100644 --- a/src/Engine/Core/World.cpp +++ b/src/Engine/Core/World.cpp @@ -137,6 +137,11 @@ EntityID World::generateEntityID() void World::deleteEntityRecursive(EntityID entity, bool cascaded /*= false*/) { + // Don't attempt to delete entities that don't exist anyway + if (!ValidEntity(entity)) { + return; + } + if (m_EventBroker != nullptr) { Events::EntityDeleted e; e.DeletedEntity = entity; diff --git a/src/Game/Systems/InterpolationSystem.cpp b/src/Game/Systems/InterpolationSystem.cpp index 2b6e82f2..bfb6952a 100644 --- a/src/Game/Systems/InterpolationSystem.cpp +++ b/src/Game/Systems/InterpolationSystem.cpp @@ -12,6 +12,11 @@ InterpolationSystem::InterpolationSystem(World* world, EventBroker* eventBroker) void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& transform, double dt) { + // Don't interpolate entities that might already have been removed + if (!entity.Valid()) { + return; + } + if (m_NextTransform.find(transform.EntityID) != m_NextTransform.end()) { // Exists in map m_NextTransform[transform.EntityID].interpolationTime += dt; Transform sTransform = m_NextTransform[transform.EntityID]; @@ -31,11 +36,10 @@ void InterpolationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrappe // Position glm::vec3 nextPosition = sTransform.Position; glm::vec3 currentPosition = static_cast(transform["Position"]); - // HACK: Hardcoded tolerance value for player position desync = 1 - if (isLocalPlayer && glm::length(nextPosition - currentPosition) < 1.f) { - return; + // HACK: Don't force position for players + if (!isLocalPlayer) { + (glm::vec3&)transform["Position"] += vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); } - (glm::vec3&)transform["Position"] += vectorInterpolation(currentPosition, nextPosition, sTransform.interpolationTime); // Orientation // Don't force orientation for players if (!isLocalPlayer) { From 0fb1dbcae1a7ca75b34e445432e82238cf8d3c7d Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 19:00:50 +0100 Subject: [PATCH 215/224] Client now has authority over its own absolute position and orientation until we have reliable input messaging --- include/Engine/Network/Client.h | 6 +++++- include/Engine/Network/MessageType.h | 3 ++- include/Engine/Network/Server.h | 1 + src/Engine/Network/Client.cpp | 31 +++++++++++++++++++++++++++- src/Engine/Network/Server.cpp | 23 +++++++++++++++++++++ 5 files changed, 61 insertions(+), 3 deletions(-) diff --git a/include/Engine/Network/Client.h b/include/Engine/Network/Client.h index e2ba8bc2..4f1baa67 100644 --- a/include/Engine/Network/Client.h +++ b/include/Engine/Network/Client.h @@ -50,6 +50,7 @@ private: PlayerID m_PlayerID = -1; EntityID m_ServerEntityID = std::numeric_limits::max(); bool m_IsConnected = false; + EntityWrapper m_LocalPlayer = EntityWrapper::Invalid; // Server Client Lookup map // Assumes that root node for client and server is EntityID 0. @@ -87,6 +88,7 @@ private: bool hasServerTimedOut(); EntityID createPlayer(); void sendInputCommands(); + void sendLocalPlayerTransform(); void becomePlayer(); // Mapping Logic // Returns if local EntityID exist in map @@ -100,8 +102,10 @@ private: EventBroker* m_EventBroker; EventRelay m_EInputCommand; bool OnInputCommand(const Events::InputCommand& e); - EventRelay m_EPlayeDamage; + EventRelay m_EPlayerDamage; bool OnPlayerDamage(const Events::PlayerDamage& e); + EventRelay m_EPlayerSpawned; + bool OnPlayerSpawned(const Events::PlayerSpawned& e); }; #endif diff --git a/include/Engine/Network/MessageType.h b/include/Engine/Network/MessageType.h index 894feea0..85f22649 100644 --- a/include/Engine/Network/MessageType.h +++ b/include/Engine/Network/MessageType.h @@ -17,7 +17,8 @@ enum class MessageType Kick, OnPlayerSpawned, EntityDeleted, - ComponentDeleted + ComponentDeleted, + PlayerTransform }; #endif diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 00de3444..3ef0a0aa 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -89,6 +89,7 @@ private: bool OnEntityDeleted(const Events::EntityDeleted& e); EventRelay m_EComponentDeleted; bool OnComponentDeleted(const Events::ComponentDeleted& e); + void parsePlayerTransform(Packet& packet); }; #endif diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 9b20ef00..3fd9217b 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -31,7 +31,8 @@ void Client::Start(World* world, EventBroker* eventBroker) // Subscribe to events EVENT_SUBSCRIBE_MEMBER(m_EInputCommand, &Client::OnInputCommand); - EVENT_SUBSCRIBE_MEMBER(m_EPlayeDamage, &Client::OnPlayerDamage); + EVENT_SUBSCRIBE_MEMBER(m_EPlayerDamage, &Client::OnPlayerDamage); + EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &Client::OnPlayerSpawned); m_Socket.connect(m_ReceiverEndpoint); LOG_INFO("I am client. BIP BOP"); @@ -48,6 +49,7 @@ void Client::Update() sendInputCommands(); m_TimeSinceSentInputs = std::clock(); } + sendLocalPlayerTransform(); } Network::Update(); } @@ -342,6 +344,33 @@ bool Client::OnPlayerDamage(const Events::PlayerDamage & e) return false; } +bool Client::OnPlayerSpawned(const Events::PlayerSpawned& e) +{ + if (e.PlayerID == -1) { + m_LocalPlayer = e.Player; + } + return true; +} + +void Client::sendLocalPlayerTransform() +{ + if (!m_LocalPlayer.Valid()) { + return; + } + + ComponentWrapper cTransform = m_LocalPlayer["Transform"]; + glm::vec3& position = cTransform["Position"]; + glm::vec3& orientation = cTransform["Orientation"]; + Packet packet(MessageType::PlayerTransform, m_SendPacketID); + packet.WritePrimitive(position.x); + packet.WritePrimitive(position.y); + packet.WritePrimitive(position.z); + packet.WritePrimitive(orientation.x); + packet.WritePrimitive(orientation.y); + packet.WritePrimitive(orientation.z); + send(packet); +} + void Client::identifyPacketLoss() { // if no packets lost, difference should be equal to 1 diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index ff3ca6d0..ff57efed 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -101,6 +101,9 @@ void Server::parseMessageType(Packet& packet) case MessageType::BecomePlayer: createPlayer(); break; + case MessageType::PlayerTransform: + parsePlayerTransform(packet); + break; default: break; } @@ -488,3 +491,23 @@ bool Server::OnComponentDeleted(const Events::ComponentDeleted & e) } return false; } + +void Server::parsePlayerTransform(Packet& packet) +{ + glm::vec3 position; + glm::vec3 orientation; + position.x = packet.ReadPrimitive(); + position.y = packet.ReadPrimitive(); + position.z = packet.ReadPrimitive(); + orientation.x = packet.ReadPrimitive(); + orientation.y = packet.ReadPrimitive(); + orientation.z = packet.ReadPrimitive(); + + PlayerID playerID = GetPlayerIDFromEndpoint(m_ReceiverEndpoint); + EntityWrapper player(m_World, m_PlayerDefinitions[playerID].EntityID); + + if (player.Valid()) { + player["Transform"]["Position"] = position; + player["Transform"]["Orientation"] = orientation; + } +} From d4797b0808cfc6ae98353d3f4451d9fc7c5b755a Mon Sep 17 00:00:00 2001 From: Tleety Date: Sun, 24 Jan 2016 21:08:01 +0100 Subject: [PATCH 216/224] Some entity files --- resources/Schema/Entities/CollidableCube.xml | 2 +- resources/Schema/Entities/GameMap.xml | 128 +++++++++++++++++++ resources/Schema/Entities/PointLight.xml | 16 +++ 3 files changed, 145 insertions(+), 1 deletion(-) create mode 100644 resources/Schema/Entities/GameMap.xml create mode 100644 resources/Schema/Entities/PointLight.xml diff --git a/resources/Schema/Entities/CollidableCube.xml b/resources/Schema/Entities/CollidableCube.xml index ebba54be..fd800a8b 100644 --- a/resources/Schema/Entities/CollidableCube.xml +++ b/resources/Schema/Entities/CollidableCube.xml @@ -5,7 +5,7 @@ - Models/Core/UnitCube.obj + Models/Core/UnitCube.mesh diff --git a/resources/Schema/Entities/GameMap.xml b/resources/Schema/Entities/GameMap.xml new file mode 100644 index 00000000..8841e3c9 --- /dev/null +++ b/resources/Schema/Entities/GameMap.xml @@ -0,0 +1,128 @@ + + + + + + + + + + + + Models\MapVersion1.mesh + + + + + + + + + 2 + + + Models/DirectionalLightWidget.mesh + false + + + + + + + + + + + + + 8 + 2.7999999523162842 + + + + + + + + + + + 8 + 2.7999999523162842 + + + + + + + + + + + + + Models/Core/UnitCube.mesh + + + + + + + + + + + + + Models/Core/UnitCube.mesh + + + + + + + + + + + + + Models/Core/UnitCube.mesh + + + + + + + + + + + + + + Models/Core/UnitCube.mesh + + + + + + + + + + + + + Models/Core/UnitCube.mesh + + + + + + + + + + + diff --git a/resources/Schema/Entities/PointLight.xml b/resources/Schema/Entities/PointLight.xml new file mode 100644 index 00000000..64c02753 --- /dev/null +++ b/resources/Schema/Entities/PointLight.xml @@ -0,0 +1,16 @@ + + + + + + 8 + 2.7999999523162842 + + + + + + + + + From a304b00038997f6a153d55af94c92bfa8a746c6f Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sun, 24 Jan 2016 21:12:41 +0100 Subject: [PATCH 217/224] fixed crashes --- assets | 2 +- include/Engine/Rendering/ModelJob.h | 2 +- resources/Schema/Entities/FastWorld.xml | 48 +++++++++++--------- resources/Schema/Entities/RenderingWorld.xml | 6 ++- src/Engine/Rendering/AnimationSystem.cpp | 41 +++++++++++------ 5 files changed, 59 insertions(+), 40 deletions(-) diff --git a/assets b/assets index 068fbb2d..5f3ab8b3 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 068fbb2d20682dd60f186c82172d7731e60ed7e9 +Subproject commit 5f3ab8b35ddce150e972445fb2894fb9e9637258 diff --git a/include/Engine/Rendering/ModelJob.h b/include/Engine/Rendering/ModelJob.h index ccfd209c..32d89293 100644 --- a/include/Engine/Rendering/ModelJob.h +++ b/include/Engine/Rendering/ModelJob.h @@ -41,7 +41,7 @@ struct ModelJob : RenderJob Skeleton = Model->m_RawModel->m_Skeleton; - if (world->HasComponent(Entity, "Animation")) { + if (world->HasComponent(Entity, "Animation") && Skeleton != nullptr) { auto animationComponent = world->GetComponent(Entity, "Animation"); Animation = model->m_RawModel->m_Skeleton->GetAnimation(animationComponent["Name"]); AnimationTime = (double)animationComponent["Time"]; diff --git a/resources/Schema/Entities/FastWorld.xml b/resources/Schema/Entities/FastWorld.xml index 655a9766..68d1dccb 100644 --- a/resources/Schema/Entities/FastWorld.xml +++ b/resources/Schema/Entities/FastWorld.xml @@ -17,25 +17,46 @@ - + + + - running - - 1 + Crouch Walk + + 32 - Models/Animtest.mesh + Models/AssaultAnimated.mesh - + + + + + pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew pew + Fonts/DroidSans.ttf,60 + + + + + + + + + + + + + + @@ -46,21 +67,6 @@ - - - - Got to Go FAST!!!! - Fonts/DroidSans.ttf,60 - - - - - - - - - - diff --git a/resources/Schema/Entities/RenderingWorld.xml b/resources/Schema/Entities/RenderingWorld.xml index 2c101dc6..e860fd04 100644 --- a/resources/Schema/Entities/RenderingWorld.xml +++ b/resources/Schema/Entities/RenderingWorld.xml @@ -80,7 +80,7 @@ - + @@ -275,7 +275,9 @@ - + running + + 1 Models/Animtest.mesh diff --git a/src/Engine/Rendering/AnimationSystem.cpp b/src/Engine/Rendering/AnimationSystem.cpp index e699866b..2126362f 100644 --- a/src/Engine/Rendering/AnimationSystem.cpp +++ b/src/Engine/Rendering/AnimationSystem.cpp @@ -6,31 +6,42 @@ void AnimationSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& a return; } - Model* model = ResourceManager::Load(entity["Model"]["Resource"]); + Model* model; + try { + model = ResourceManager::Load<::Model, true>(entity["Model"]["Resource"]); + } catch (const std::exception&) { + return; + } + + Skeleton* skeleton = model->m_RawModel->m_Skeleton; const Skeleton::Animation* animation = skeleton->GetAnimation(animationComponent["Name"]); - double animationSpeed = (double)animationComponent["Speed"]; + if(animation != nullptr) { + double animationSpeed = (double)animationComponent["Speed"]; - if( animationSpeed != 0.0) { - double nextTime = (double)animationComponent["Time"] + animationSpeed * dt; + if (animationSpeed != 0.0) { + double nextTime = (double)animationComponent["Time"] + animationSpeed * dt; - if (!(bool)animationComponent["Loop"] && glm::abs(nextTime) > animation->Duration) { - (double&)animationComponent["Time"] = glm::sign(nextTime) * animation->Duration; - (double&)animationComponent["Speed"] = 0.0; - Events::AnimationComplete e; - e.Entity = entity; - e.Name = (std::string)animationComponent["Name"]; - m_EventBroker->Publish(e); - } else { - if (glm::abs(nextTime) > animation->Duration) { - (double&)animationComponent["Time"] = glm::abs(nextTime) - animation->Duration; + if (!(bool)animationComponent["Loop"] && glm::abs(nextTime) > animation->Duration) { + (double&)animationComponent["Time"] = glm::sign(nextTime) * animation->Duration; + (double&)animationComponent["Speed"] = 0.0; + Events::AnimationComplete e; + e.Entity = entity; + e.Name = (std::string)animationComponent["Name"]; + m_EventBroker->Publish(e); } else { - (double&)animationComponent["Time"] = nextTime; + if (glm::abs(nextTime) > animation->Duration) { + (double&)animationComponent["Time"] = glm::abs(nextTime) - animation->Duration; + } else { + (double&)animationComponent["Time"] = nextTime; + } } } } + + } From 382eff169fd20e2b562a7d1431f55bf65e008abd Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 21:20:43 +0100 Subject: [PATCH 218/224] Server refactoring to remove player dependency and lots of fixes. --- include/Engine/Network/Network.h | 1 - include/Engine/Network/PlayerDefinition.h | 3 +- include/Engine/Network/Server.h | 8 +- src/Engine/Network/Client.cpp | 14 +- src/Engine/Network/Server.cpp | 158 +++++++--------------- 5 files changed, 67 insertions(+), 117 deletions(-) diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index 480ac602..03fcc0f3 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -15,7 +15,6 @@ #define INPUTSIZE 4097 typedef unsigned int PlayerID; typedef unsigned int PacketID; -typedef unsigned int UserID; class Network { diff --git a/include/Engine/Network/PlayerDefinition.h b/include/Engine/Network/PlayerDefinition.h index 4b8b8e6e..863948b3 100644 --- a/include/Engine/Network/PlayerDefinition.h +++ b/include/Engine/Network/PlayerDefinition.h @@ -1,9 +1,10 @@ #ifndef PlayerDefinition_h__ #define PlayerDefinition_h__ #include +#include "../Core/Entity.h" struct PlayerDefinition { - int EntityID = -1; + ::EntityID EntityID = EntityID_Invalid; std::string Name = ""; boost::asio::ip::udp::endpoint Endpoint; unsigned int PacketID; diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 3ef0a0aa..17029809 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -33,8 +33,7 @@ private: boost::asio::ip::udp::socket m_Socket; // Sending messages to client logic - PlayerDefinition m_PlayerDefinitions[8]; // - std::vector m_ConnectedUsers; + std::map m_ConnectedPlayers; char readBuffer[INPUTSIZE] = { 0 }; int bytesRead = 0; // time for previouse message @@ -45,6 +44,7 @@ private: int pingIntervalMs; int snapshotInterval; int checkTimeOutInterval = 100; + int m_NextPlayerID = 0; //Timers std::clock_t m_StartPingTime; @@ -60,7 +60,6 @@ private: // Private member functions int receive(char* data); void readFromClients(); - void send(Packet& packet, UserID user); void send(PlayerID player, Packet& packet); void send(Packet& packet); void broadcast(Packet& packet); @@ -68,7 +67,7 @@ private: void addChildrenToPacket(Packet& packet, EntityID entityID); void sendPing(); void checkForTimeOuts(); - void disconnect(UserID user); + void disconnect(PlayerID playerID); void parseMessageType(Packet& packet); void parseOnInputCommand(Packet& packet); void parseOnPlayerDamage(Packet& packet); @@ -77,7 +76,6 @@ private: void parseClientPing(); void parsePing(); void identifyPacketLoss(); - void createPlayer(); void kick(PlayerID player); PlayerID GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint); // Debug event diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 3fd9217b..e32afd57 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -153,10 +153,13 @@ void Client::parsePlayersSpawned(Packet& packet) void Client::parseEntityDeletion(Packet & packet) { EntityID entityToDelete = packet.ReadPrimitive(); - EntityID localEntity = m_ServerIDToClientID.at(entityToDelete); - if (m_World->ValidEntity(localEntity)) { - m_World->DeleteEntity(localEntity); - deleteFromServerClientMaps(entityToDelete, localEntity); + // TODO: What if an entity that didn't previously exist comes as a delete request and later comes in a delayed snapshot? + if (m_ServerIDToClientID.find(entityToDelete) != m_ServerIDToClientID.end()) { + EntityID localEntity = m_ServerIDToClientID.at(entityToDelete); + if (m_World->ValidEntity(localEntity)) { + m_World->DeleteEntity(localEntity); + deleteFromServerClientMaps(entityToDelete, localEntity); + } } } @@ -219,6 +222,9 @@ void Client::parseSnapshot(Packet& packet) if (componentType == "Transform") { // Interpolate only transform components InterpolateFields(packet, componentInfo, localEntityID, componentType); + } else if (componentType == "Physics" && m_World->HasComponent(localEntityID, "Player")) { + // HACK: Ignore velocity of physics + packet.ReadData(componentInfo.Stride); } else { // Set component values updateFields(packet, componentInfo, localEntityID, componentType); diff --git a/src/Engine/Network/Server.cpp b/src/Engine/Network/Server.cpp index 74e4a15c..a29f4f02 100644 --- a/src/Engine/Network/Server.cpp +++ b/src/Engine/Network/Server.cpp @@ -23,9 +23,6 @@ void Server::Start(World* world, EventBroker* eventBroker) EVENT_SUBSCRIBE_MEMBER(m_EPlayerSpawned, &Server::OnPlayerSpawned); EVENT_SUBSCRIBE_MEMBER(m_EEntityDeleted, &Server::OnEntityDeleted); EVENT_SUBSCRIBE_MEMBER(m_EComponentDeleted, &Server::OnComponentDeleted); - for (size_t i = 0; i < m_MaxConnections; i++) { - m_PlayerDefinitions[i].StopTime = std::clock(); - } LOG_INFO("I am Server. BIP BOP\n"); } @@ -98,9 +95,6 @@ void Server::parseMessageType(Packet& packet) case MessageType::OnPlayerDamage: parseOnPlayerDamage(packet); break; - case MessageType::BecomePlayer: - createPlayer(); - break; case MessageType::PlayerTransform: parsePlayerTransform(packet); break; @@ -124,31 +118,22 @@ int Server::receive(char * data) return length; } -void Server::send(Packet& packet, UserID user) -{ - int bytesSent = m_Socket.send_to( - boost::asio::buffer(packet.Data(), packet.Size()), - m_ConnectedUsers[user].Endpoint, - 0); - // Network Debug data - if (isReadingData) { - m_NetworkData.TotalDataSent += packet.Size(); - m_NetworkData.DataSentThisInterval += packet.Size(); - m_NetworkData.AmountOfMessagesSent++; - } -} - void Server::send(PlayerID player, Packet& packet) { - int bytesSent = m_Socket.send_to( - boost::asio::buffer(packet.Data(), packet.Size()), - m_PlayerDefinitions[player].Endpoint, - 0); - // Network Debug data - if (isReadingData) { - m_NetworkData.TotalDataSent += packet.Size(); - m_NetworkData.DataSentThisInterval += packet.Size(); - m_NetworkData.AmountOfMessagesSent++; + try { + int bytesSent = m_Socket.send_to( + boost::asio::buffer(packet.Data(), packet.Size()), + m_ConnectedPlayers[player].Endpoint, + 0); + // Network Debug data + if (isReadingData) { + m_NetworkData.TotalDataSent += packet.Size(); + m_NetworkData.DataSentThisInterval += packet.Size(); + m_NetworkData.AmountOfMessagesSent++; + } + } catch (const boost::system::system_error& e) { + // TODO: Clean up invalid endpoints out of m_ConnectedPlayers later + m_ConnectedPlayers[player].Endpoint = boost::asio::ip::udp::endpoint(); } } @@ -169,11 +154,9 @@ void Server::send(Packet & packet) void Server::broadcast(Packet& packet) { - for (int i = 0; i < m_ConnectedUsers.size(); i++) { - if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { - packet.ChangePacketID(m_ConnectedUsers[i].PacketID); - send(packet, i); - } + for (auto& kv : m_ConnectedPlayers) { + packet.ChangePacketID(kv.second.PacketID); + send(kv.first, packet); } } @@ -231,12 +214,12 @@ void Server::addChildrenToPacket(Packet & packet, EntityID entityID) void Server::sendPing() { // Prints connected players ping - for (int i = 0; i < m_ConnectedUsers.size(); i++) { - if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { - int ping = 1000 * (m_ConnectedUsers[i].StopTime - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); - LOG_INFO("Last packetID received %i: User %i's ping: %i", m_ConnectedUsers[i].PacketID, i, std::abs(ping)); - } - } + //for (int i = 0; i < m_ConnectedPlayers.size(); i++) { + // if (m_ConnectedPlayers[i].Endpoint.address() != boost::asio::ip::address()) { + // int ping = 1000 * (m_ConnectedPlayers[i].StopTime - m_StartPingTime) / static_cast(CLOCKS_PER_SEC); + // LOG_INFO("Last packetID received %i: User %i's ping: %i", m_ConnectedPlayers[i].PacketID, i, std::abs(ping)); + // } + //} // Create ping message Packet packet(MessageType::Ping); packet.WriteString("Ping from server"); @@ -251,9 +234,9 @@ void Server::checkForTimeOuts() int startPing = 1000 * m_StartPingTime / static_cast(CLOCKS_PER_SEC); - for (int i = 0; i < m_ConnectedUsers.size(); i++) { - if (m_ConnectedUsers[i].Endpoint.address() != boost::asio::ip::address()) { - int stopPing = 1000 * m_ConnectedUsers[i].StopTime / + for (int i = 0; i < m_ConnectedPlayers.size(); i++) { + if (m_ConnectedPlayers[i].Endpoint.address() != boost::asio::ip::address()) { + int stopPing = 1000 * m_ConnectedPlayers[i].StopTime / static_cast(CLOCKS_PER_SEC); if (startPing > stopPing + m_TimeoutMs) { LOG_INFO("User %i timed out!", i); @@ -263,35 +246,24 @@ void Server::checkForTimeOuts() } } -void Server::disconnect(UserID user) +void Server::disconnect(PlayerID playerID) { //broadcast("A player disconnected"); - LOG_INFO("User %s disconnected/timed out", m_PlayerDefinitions[user].Name.c_str()); + LOG_INFO("User %s disconnected/timed out", m_ConnectedPlayers[playerID].Name.c_str()); // Remove enteties and stuff (When we can remove entity, remove it and tell clients to remove the copy they have) Events::PlayerDisconnected e; - e.Entity = m_PlayerDefinitions[user].EntityID; - e.PlayerID = user; + e.Entity = m_ConnectedPlayers[playerID].EntityID; + e.PlayerID = playerID; m_EventBroker->Publish(e); - m_PlayerDefinitions[user].Endpoint = boost::asio::ip::udp::endpoint(); - m_PlayerDefinitions[user].EntityID = -1; - m_PlayerDefinitions[user].Name = ""; - m_PlayerDefinitions[user].PacketID = 0; - m_ConnectedUsers.erase(m_ConnectedUsers.begin() + user); + m_ConnectedPlayers.erase(playerID); } void Server::parseOnInputCommand(Packet& packet) { PlayerID player = -1; // Check which player it was who sent the message - for (int i = 0; i < m_MaxConnections; i++) { - // if the player is connected set playerID to the correct PlayerID - if (m_PlayerDefinitions[i].Endpoint.address() == m_ReceiverEndpoint.address() - && m_PlayerDefinitions[i].Endpoint.port() == m_ReceiverEndpoint.port()) { - player = i; - break; - } - } + player = GetPlayerIDFromEndpoint(m_ReceiverEndpoint); if (player != -1) { while (packet.DataReadSize() < packet.Size()) { Events::InputCommand e; @@ -320,9 +292,9 @@ void Server::parseConnect(Packet& packet) if (GetPlayerIDFromEndpoint(m_ReceiverEndpoint) != -1) { return; } - for (int i = 0; i < m_ConnectedUsers.size(); i++) { - if (m_ConnectedUsers[i].Endpoint.address() == m_ReceiverEndpoint.address() && - m_ConnectedUsers[i].Endpoint.port() == m_ReceiverEndpoint.port()) { + for (auto& kv : m_ConnectedPlayers) { + if (kv.second.Endpoint.address() == m_ReceiverEndpoint.address() && + kv.second.Endpoint.port() == m_ReceiverEndpoint.port()) { // Already connected return; } @@ -334,11 +306,11 @@ void Server::parseConnect(Packet& packet) pd.Name = packet.ReadString(); pd.PacketID = 0; pd.StopTime = std::clock(); - m_ConnectedUsers.push_back(pd); + m_ConnectedPlayers[m_NextPlayerID++] = pd; LOG_INFO("Spectator \"%s\" connected on IP: %s", pd.Name.c_str(), pd.Endpoint.address().to_string().c_str()); // Send a message to the player that connected - Packet connnectPacket(MessageType::Connect, m_ConnectedUsers[m_ConnectedUsers.size() - 1].PacketID); + Packet connnectPacket(MessageType::Connect, pd.PacketID); send(connnectPacket); // Send notification that a player has connected @@ -350,9 +322,10 @@ void Server::parseDisconnect() { LOG_INFO("%i: Parsing disconnect", m_PacketID); - for (int i = 0; i < m_ConnectedUsers.size(); i++) { - if (m_ConnectedUsers[i].Endpoint.address() == m_ReceiverEndpoint.address()) { - disconnect(i); + for (auto& kv : m_ConnectedPlayers) { + if (kv.second.Endpoint.address() == m_ReceiverEndpoint.address() && + kv.second.Endpoint.port() == m_ReceiverEndpoint.port()) { + disconnect(kv.first); break; } } @@ -366,16 +339,16 @@ void Server::parseClientPing() return; } // Return ping - Packet packet(MessageType::Ping, m_PlayerDefinitions[player].PacketID); + Packet packet(MessageType::Ping, m_ConnectedPlayers[player].PacketID); packet.WriteString("Ping received"); send(packet); } void Server::parsePing() { - for (int i = 0; i < m_ConnectedUsers.size(); i++) { - if (m_ConnectedUsers[i].Endpoint.address() == m_ReceiverEndpoint.address()) { - m_ConnectedUsers[i].StopTime = std::clock(); + for (int i = 0; i < m_ConnectedPlayers.size(); i++) { + if (m_ConnectedPlayers[i].Endpoint.address() == m_ReceiverEndpoint.address()) { + m_ConnectedPlayers[i].StopTime = std::clock(); break; } } @@ -390,35 +363,6 @@ void Server::identifyPacketLoss() } } -void Server::createPlayer() -{ - if (GetPlayerIDFromEndpoint(m_ReceiverEndpoint) != -1) { - // Already connected as player - LOG_WARNING("Already connected!"); - return; - } - UserID userIndex; - for (userIndex = 0; userIndex < m_ConnectedUsers.size(); userIndex++) { - if (m_ConnectedUsers[userIndex].Endpoint.address() == m_ReceiverEndpoint.address() && - m_ConnectedUsers[userIndex].Endpoint.port() == m_ReceiverEndpoint.port()) { - // Found user - break; - } - } - if (userIndex == m_ConnectedUsers.size()) { - LOG_WARNING("Not a recognized user!"); - return; - } - for (PlayerID playerIndex = 0; playerIndex < m_MaxConnections; playerIndex++) { - if (m_PlayerDefinitions[playerIndex].Endpoint.address() == boost::asio::ip::address()) { - m_PlayerDefinitions[playerIndex] = m_ConnectedUsers[userIndex]; - return; - } - } - LOG_WARNING("Server is full!"); - -} - void Server::kick(PlayerID player) { disconnect(player); @@ -428,10 +372,10 @@ void Server::kick(PlayerID player) PlayerID Server::GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint) { - for (int i = 0; i < m_MaxConnections; i++) { - if (m_PlayerDefinitions[i].Endpoint.address() == endpoint.address() && - m_PlayerDefinitions[i].Endpoint.port() == endpoint.port()) { - return i; + for (auto& kv : m_ConnectedPlayers) { + if (kv.second.Endpoint.address() == endpoint.address() && + kv.second.Endpoint.port() == endpoint.port()) { + return kv.first; } } return -1; @@ -456,6 +400,8 @@ bool Server::OnInputCommand(const Events::InputCommand & e) bool Server::OnPlayerSpawned(const Events::PlayerSpawned & e) { + m_ConnectedPlayers[e.PlayerID].EntityID = e.Player.ID; + Packet packet = Packet(MessageType::OnPlayerSpawned); packet.WritePrimitive(e.Player.ID); packet.WritePrimitive(e.Spawner.ID); @@ -496,7 +442,7 @@ void Server::parsePlayerTransform(Packet& packet) orientation.z = packet.ReadPrimitive(); PlayerID playerID = GetPlayerIDFromEndpoint(m_ReceiverEndpoint); - EntityWrapper player(m_World, m_PlayerDefinitions[playerID].EntityID); + EntityWrapper player(m_World, m_ConnectedPlayers.at(playerID).EntityID); if (player.Valid()) { player["Transform"]["Position"] = position; From 47d2fb6a9bbb84a3dff41f29b662603b5c072e6e Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 22:20:42 +0100 Subject: [PATCH 219/224] Fixed wrong drawing function used in PickingPass --- src/Engine/Rendering/PickingPass.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index f063b344..350d471f 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -90,7 +90,7 @@ void PickingPass::Draw(RenderScene& scene) glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); - glDrawElementsBaseVertex(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, nullptr, modelJob->StartIndex); + glDrawElements(GL_TRIANGLES, modelJob->EndIndex - modelJob->StartIndex + 1, GL_UNSIGNED_INT, (void*)(modelJob->StartIndex * sizeof(unsigned int))); } } From f8b9606cdfdaf93f3ddb8ea363f2b2211c5111bb Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sun, 24 Jan 2016 22:59:53 +0100 Subject: [PATCH 220/224] Picking animation fix --- include/Engine/Rendering/PickingPass.h | 5 +---- resources/Shaders/Picking.vert.glsl | 20 ++++++++++++-------- src/Engine/Rendering/PickingPass.cpp | 22 +++++++++++++++------- 3 files changed, 28 insertions(+), 19 deletions(-) diff --git a/include/Engine/Rendering/PickingPass.h b/include/Engine/Rendering/PickingPass.h index 5fc88982..da3ed31b 100644 --- a/include/Engine/Rendering/PickingPass.h +++ b/include/Engine/Rendering/PickingPass.h @@ -1,8 +1,6 @@ #ifndef PickingPass_h__ #define PickingPass_h__ - - #include "IRenderer.h" #include "PickingPassState.h" #include "FrameBuffer.h" @@ -10,8 +8,7 @@ #include "Util/UnorderedMapiVec2.h" #include "../Core/EventBroker.h" #include "../Core/World.h" - - +#include "Rendering/Skeleton.h" class PickingPass { diff --git a/resources/Shaders/Picking.vert.glsl b/resources/Shaders/Picking.vert.glsl index b2857cea..205a8fdd 100644 --- a/resources/Shaders/Picking.vert.glsl +++ b/resources/Shaders/Picking.vert.glsl @@ -3,18 +3,15 @@ uniform mat4 M; uniform mat4 V; uniform mat4 P; +uniform mat4 Bones[100]; layout(location = 0) in vec3 Position; layout(location = 1) in vec3 Normal; layout(location = 2) in vec3 Tangent; layout(location = 3) in vec3 BiTangent; layout(location = 4) in vec2 TextureCoords; -layout(location = 5) in vec4 DiffuseVertexColor; -layout(location = 6) in vec4 SpecularVertexColor; -layout(location = 7) in vec4 BoneIndices1; -layout(location = 8) in vec4 BoneIndices2; -layout(location = 9) in vec4 BoneWeights1; -layout(location = 10) in vec4 BoneWeights2; +layout(location = 5) in vec4 BoneIndices; +layout(location = 6) in vec4 BoneWeights; out VertexData{ vec3 Position; @@ -22,7 +19,14 @@ out VertexData{ void main() { - gl_Position = P * V* M * vec4(Position, 1.0); + mat4 boneTransform = mat4(1); + if(BoneWeights[0] > 0.0f){ + boneTransform = BoneWeights[0] * Bones[int(BoneIndices[0])] + + BoneWeights[1] * Bones[int(BoneIndices[1])] + + BoneWeights[2] * Bones[int(BoneIndices[2])] + + BoneWeights[3] * Bones[int(BoneIndices[3])]; + } - Output.Position = Position; + gl_Position = P*V*M*boneTransform * vec4(Position, 1.0); + Output.Position = (boneTransform * vec4(Position, 1.0)).xyz; } \ No newline at end of file diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 350d471f..c7e23479 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -48,7 +48,7 @@ void PickingPass::Draw(RenderScene& scene) PickingPassState* state = new PickingPassState(m_PickingBuffer.GetHandle()); //TODO: Render: Add code for more jobs than modeljobs. - GLuint ShaderHandle = m_PickingProgram->GetHandle(); + GLuint shaderHandle = m_PickingProgram->GetHandle(); m_PickingProgram->Bind(); if (scene.ClearDepth) { @@ -75,18 +75,26 @@ void PickingPass::Draw(RenderScene& scene) m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); if (m_ColorCounter[0] > 255) { m_ColorCounter[0] = 0; - m_ColorCounter[1]++; + m_ColorCounter[1] += 5; } else { - m_ColorCounter[0]++; + m_ColorCounter[0] += 50; } } m_PickingColorsToEntity[glm::ivec2(pickColor[0], pickColor[1])] = pickInfo; - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); - glUniformMatrix4fv(glGetUniformLocation(ShaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); - glUniform2fv(glGetUniformLocation(ShaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "M"), 1, GL_FALSE, glm::value_ptr(modelJob->Matrix)); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "V"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ViewMatrix())); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "P"), 1, GL_FALSE, glm::value_ptr(scene.Camera->ProjectionMatrix())); + glUniform2fv(glGetUniformLocation(shaderHandle, "PickingColor"), 1, glm::value_ptr(glm::vec2(pickColor[0], pickColor[1]))); + + if (modelJob->Model->m_RawModel->m_Skeleton != nullptr) { + + if (modelJob->Animation != nullptr) { + std::vector frameBones = modelJob->Skeleton->GetFrameBones(*modelJob->Animation, modelJob->AnimationTime); + glUniformMatrix4fv(glGetUniformLocation(shaderHandle, "Bones"), frameBones.size(), GL_FALSE, glm::value_ptr(frameBones[0])); + } + } glBindVertexArray(modelJob->Model->VAO); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, modelJob->Model->ElementBuffer); From b6ba8a5bd790dfa667a9874a787fe155edac25fa Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 23:05:26 +0100 Subject: [PATCH 221/224] Network snapshot buffer size increased, needs to be looked over later --- include/Engine/Network/Network.h | 2 +- include/Engine/Network/Server.h | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/include/Engine/Network/Network.h b/include/Engine/Network/Network.h index 03fcc0f3..e1e64fc1 100644 --- a/include/Engine/Network/Network.h +++ b/include/Engine/Network/Network.h @@ -12,7 +12,7 @@ #include #include -#define INPUTSIZE 4097 +#define INPUTSIZE 32000 typedef unsigned int PlayerID; typedef unsigned int PacketID; diff --git a/include/Engine/Network/Server.h b/include/Engine/Network/Server.h index 17029809..11f983a9 100644 --- a/include/Engine/Network/Server.h +++ b/include/Engine/Network/Server.h @@ -34,6 +34,7 @@ private: // Sending messages to client logic std::map m_ConnectedPlayers; + // HACK: Fix INPUTSIZE char readBuffer[INPUTSIZE] = { 0 }; int bytesRead = 0; // time for previouse message From 79fe7693a659fee3dea2c9825aad0124b9c73a65 Mon Sep 17 00:00:00 2001 From: viktorljung Date: Sun, 24 Jan 2016 23:05:45 +0100 Subject: [PATCH 222/224] picking values fixed --- src/Engine/Rendering/PickingPass.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index c7e23479..0d89f355 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -75,9 +75,9 @@ void PickingPass::Draw(RenderScene& scene) m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); if (m_ColorCounter[0] > 255) { m_ColorCounter[0] = 0; - m_ColorCounter[1] += 5; + m_ColorCounter[1]++; } else { - m_ColorCounter[0] += 50; + m_ColorCounter[0]++; } } From d0de169613643c959ab6bfb2f9b1228c7f957e72 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 23:05:52 +0100 Subject: [PATCH 223/224] Instagib! --- include/Game/Systems/HealthSystem.h | 2 +- resources/Schema/Entities/Empty.xml | 12 +-- resources/Schema/Entities/MovementTest.xml | 117 +++++++++++++++++++++ src/Engine/Network/Client.cpp | 2 +- src/Engine/Rendering/PickingPass.cpp | 4 +- src/Game/Game.cpp | 2 +- src/Game/Systems/HealthSystem.cpp | 12 ++- src/Game/Systems/WeaponSystem.cpp | 17 +-- 8 files changed, 142 insertions(+), 26 deletions(-) diff --git a/include/Game/Systems/HealthSystem.h b/include/Game/Systems/HealthSystem.h index f9843f11..3b069349 100644 --- a/include/Game/Systems/HealthSystem.h +++ b/include/Game/Systems/HealthSystem.h @@ -24,7 +24,7 @@ public: private: //methods which will take care of specific events EventRelay m_EPlayerDamage; - bool HealthSystem::OnPlayerDamaged(const Events::PlayerDamage& e); + bool HealthSystem::OnPlayerDamaged(Events::PlayerDamage& e); EventRelay m_EPlayerHealthPickup; bool HealthSystem::OnPlayerHealthPickup(const Events::PlayerHealthPickup& e); diff --git a/resources/Schema/Entities/Empty.xml b/resources/Schema/Entities/Empty.xml index c9b8924f..6efd8318 100644 --- a/resources/Schema/Entities/Empty.xml +++ b/resources/Schema/Entities/Empty.xml @@ -5,16 +5,6 @@ - - - - - - - - - - - + diff --git a/resources/Schema/Entities/MovementTest.xml b/resources/Schema/Entities/MovementTest.xml index 40de747a..6551bd75 100644 --- a/resources/Schema/Entities/MovementTest.xml +++ b/resources/Schema/Entities/MovementTest.xml @@ -178,6 +178,123 @@ + + + + + + + + + + false + + + 5 + + + + + + + + + + + + + + + + + + + + + + + + Fonts/DroidSans.ttf,100 + + false + + + + + + + + + + + + + Models/Camera.mesh + + + + + + + + + + + + + + + Models/Camera.mesh + false + + + + + + + + + + + + Models/AssaultHeadless.mesh + + + + + + + + + + + + Models/Core/UnitCube.mesh + + false + + + + + + + + + + + + Models/Core/UnitCube.mesh + + false + + + + + + + + + diff --git a/src/Engine/Network/Client.cpp b/src/Engine/Network/Client.cpp index 4ebf551d..dd590a6a 100644 --- a/src/Engine/Network/Client.cpp +++ b/src/Engine/Network/Client.cpp @@ -345,7 +345,7 @@ bool Client::OnPlayerDamage(const Events::PlayerDamage & e) { Packet packet(MessageType::OnPlayerDamage, m_SendPacketID); packet.WritePrimitive(e.Damage); - packet.WritePrimitive(e.Player.ID); + packet.WritePrimitive(m_ClientIDToServerID.at(e.Player.ID)); send(packet); return false; } diff --git a/src/Engine/Rendering/PickingPass.cpp b/src/Engine/Rendering/PickingPass.cpp index 350d471f..3f8dd9b0 100644 --- a/src/Engine/Rendering/PickingPass.cpp +++ b/src/Engine/Rendering/PickingPass.cpp @@ -75,9 +75,9 @@ void PickingPass::Draw(RenderScene& scene) m_EntityColors[std::make_tuple(pickInfo.Entity, pickInfo.World, pickInfo.Camera)] = glm::ivec2(pickColor[0], pickColor[1]); if (m_ColorCounter[0] > 255) { m_ColorCounter[0] = 0; - m_ColorCounter[1]++; + m_ColorCounter[1] += 5; } else { - m_ColorCounter[0]++; + m_ColorCounter[0] += 50; } } diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index ef51aca6..5de61b8c 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -77,7 +77,7 @@ Game::Game(int argc, char* argv[]) // All systems with orderlevel 0 will be updated first. unsigned int updateOrderLevel = 0; m_SystemPipeline->AddSystem(updateOrderLevel); - //m_SystemPipeline->AddSystem(updateOrderLevel); + m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); m_SystemPipeline->AddSystem(updateOrderLevel); diff --git a/src/Game/Systems/HealthSystem.cpp b/src/Game/Systems/HealthSystem.cpp index 7f0bbb09..9e118070 100644 --- a/src/Game/Systems/HealthSystem.cpp +++ b/src/Game/Systems/HealthSystem.cpp @@ -45,10 +45,16 @@ void HealthSystem::UpdateComponent(EntityWrapper& entity, ComponentWrapper& comp } } -bool HealthSystem::OnPlayerDamaged(const Events::PlayerDamage& e) +bool HealthSystem::OnPlayerDamaged(Events::PlayerDamage& e) { - //save the changed HP to a vector. it will be taken care of in UpdateComponent - //m_DeltaHealthVector.push_back(std::make_tuple(e.PlayerDamagedID, -e.DamageAmount)); + ComponentWrapper cHealth = e.Player["Health"]; + double& health = cHealth["Health"]; + health -= e.Damage; + + if (health <= 0.0) { + m_World->DeleteEntity(e.Player.ID); + } + return true; } diff --git a/src/Game/Systems/WeaponSystem.cpp b/src/Game/Systems/WeaponSystem.cpp index f72fd7dd..b210b564 100644 --- a/src/Game/Systems/WeaponSystem.cpp +++ b/src/Game/Systems/WeaponSystem.cpp @@ -25,11 +25,6 @@ bool WeaponSystem::OnPlayerSpawned(const Events::PlayerSpawned& e) bool WeaponSystem::OnInputCommand(const Events::InputCommand& e) { - // Only shoot client-side! - if (e.PlayerID != -1) { - return false; - } - // Only shoot if the player is alive if (!m_LocalPlayer.Valid()) { return false; @@ -44,9 +39,17 @@ bool WeaponSystem::OnInputCommand(const Events::InputCommand& e) return true; } -bool WeaponSystem::OnShoot(const Events::Shoot& eShoot) { +bool WeaponSystem::OnShoot(const Events::Shoot& eShoot) +{ + // TODO: Weapon firing effects here + + // Only run further picking code client-side! + if (eShoot.Player != m_LocalPlayer) { + return false; + } + // Screen center, based on current resolution! - //TODO: check if player has enough ammo and if weapon has a cooldown or not + // TODO: check if player has enough ammo and if weapon has a cooldown or not Rectangle screenResolution = m_Renderer->Resolution(); glm::vec2 centerScreen = glm::vec2(screenResolution.Width / 2, screenResolution.Height / 2); From 04f6233d99374aa5b20a1641a119ac1b32c36539 Mon Sep 17 00:00:00 2001 From: sippeangelo Date: Sun, 24 Jan 2016 23:44:29 +0100 Subject: [PATCH 224/224] Crude animations --- assets | 2 +- resources/Schema/Entities/MovementTest.xml | 2 +- resources/Schema/Entities/Player.xml | 15 +++++----- src/Game/Systems/PlayerMovementSystem.cpp | 34 ++++++++++++++++++++-- 4 files changed, 41 insertions(+), 12 deletions(-) diff --git a/assets b/assets index 5f3ab8b3..75778193 160000 --- a/assets +++ b/assets @@ -1 +1 @@ -Subproject commit 5f3ab8b35ddce150e972445fb2894fb9e9637258 +Subproject commit 757781933738bc4158c5c26750594b70acd537cd diff --git a/resources/Schema/Entities/MovementTest.xml b/resources/Schema/Entities/MovementTest.xml index 6551bd75..199174ae 100644 --- a/resources/Schema/Entities/MovementTest.xml +++ b/resources/Schema/Entities/MovementTest.xml @@ -198,7 +198,7 @@ - + diff --git a/resources/Schema/Entities/Player.xml b/resources/Schema/Entities/Player.xml index 1ec7927b..1ee21a33 100644 --- a/resources/Schema/Entities/Player.xml +++ b/resources/Schema/Entities/Player.xml @@ -7,7 +7,6 @@ - 5 @@ -18,8 +17,7 @@ - - + @@ -51,6 +49,7 @@ Models/Camera.mesh + false @@ -77,13 +76,15 @@ + + Hold Pos + 1 + - Models/AssaultHeadless.mesh + Models/AssaultAnimated.mesh - - - + diff --git a/src/Game/Systems/PlayerMovementSystem.cpp b/src/Game/Systems/PlayerMovementSystem.cpp index 5c75a673..0f6588be 100644 --- a/src/Game/Systems/PlayerMovementSystem.cpp +++ b/src/Game/Systems/PlayerMovementSystem.cpp @@ -36,15 +36,18 @@ void PlayerMovementSystem::Update(double dt) glm::vec3& ori = cTransform["Orientation"]; ori.y += controller->Rotation().y; + float playerMovementSpeed = player["Player"]["MovementSpeed"]; + float playerCrouchSpeed = player["Player"]["CrouchSpeed"]; + if (player.HasComponent("Physics")) { ComponentWrapper cPhysics = player["Physics"]; glm::vec3 wishDirection = controller->Movement() * glm::inverse(glm::quat(ori)); float wishSpeed; if (controller->Crouching()) { - wishSpeed = player["Player"]["CrouchSpeed"]; + wishSpeed = playerCrouchSpeed; } else { - wishSpeed = player["Player"]["MovementSpeed"]; + wishSpeed = playerMovementSpeed; } glm::vec3& velocity = cPhysics["Velocity"]; ImGui::Text("velocity: (%f, %f, %f)", velocity.x, velocity.y, velocity.z); @@ -85,8 +88,33 @@ void PlayerMovementSystem::Update(double dt) // size = glm::vec3(1.f, 1.6f, 1.f); // } //} + + // Animations + EntityWrapper playerModel = player.FirstChildByName("PlayerModel"); + if (playerModel.Valid()) { + ComponentWrapper cAnimation = playerModel["Animation"]; + + float movementLength = glm::length(groundVelocity); + if (glm::length(controller->Movement()) > 0.f) { + if (controller->Crouching()) { + cAnimation["Name"] = "Crouch Walk"; + (double&)cAnimation["Speed"] = 1.f * -glm::sign(controller->Movement().z); + } else { + cAnimation["Name"] = "Run"; + (double&)cAnimation["Speed"] = 2.f * -glm::sign(controller->Movement().z); + } + } else { + if (controller->Crouching()) { + cAnimation["Name"] = "Crouch"; + (double&)cAnimation["Speed"] = 1.f; + } else { + cAnimation["Name"] = "Hold Pos"; + (double&)cAnimation["Speed"] = 1.f; + } + } + } } - + controller->Reset(); } }