diff --git a/CMakeLists.txt b/CMakeLists.txt index c38fbee..158447a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -8,7 +8,7 @@ SET(GCC_COVERAGE_LINK_FLAGS "-mwindows") SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${GCC_COVERAGE_COMPILE_FLAGS}" ) SET(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} ${GCC_COVERAGE_LINK_FLAGS}" ) -set(SOURCE_FILES main.cpp screen.cpp screen.h Marker.cpp Marker.h Fumen.cpp Fumen.h Note.cpp Note.h) +set(SOURCE_FILES main.cpp screen.cpp screen.h Marker.cpp Marker.h Fumen.cpp Fumen.h Note.cpp Note.h Chart.cpp Chart.h) set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${FEIS_SOURCE_DIR}/cmake") diff --git a/Chart.cpp b/Chart.cpp new file mode 100644 index 0000000..33b21e7 --- /dev/null +++ b/Chart.cpp @@ -0,0 +1,56 @@ +// +// Created by Syméon on 25/08/2017. +// + +#include "Chart.h" + +void Chart::addNote(Note note) { + this->Notes.insert(note); +} + +bool Chart::hasNote(Note note) { + return this->Notes.find(note) != Notes.end(); +} + +void Chart::removeNote(Note note) { + if (hasNote(note)) { + Notes.erase(Notes.find(note)); + } +} + +const std::string &Chart::getDif() const { + return dif; +} + +void Chart::setDif(const std::string &dif) { + Chart::dif = dif; +} + +int Chart::getLevel() const { + return level; +} + +void Chart::setLevel(int level) { + Chart::level = level; +} + +int Chart::getResolution() const { + return resolution; +} + +void Chart::setResolution(int resolution) { + Chart::resolution = resolution; +} + +int Chart::getNoteCount() { + return this->Notes.size(); +} + +Chart::Chart(const std::string &dif, int level, int resolution) : dif(dif), + level(level), + resolution(resolution), + Notes() {} + +const std::set &Chart::getNotes() const { + return Notes; +} diff --git a/Chart.h b/Chart.h new file mode 100644 index 0000000..3044e9a --- /dev/null +++ b/Chart.h @@ -0,0 +1,47 @@ +// +// Created by Syméon on 25/08/2017. +// + +#ifndef FEIS_CHART_H +#define FEIS_CHART_H + +#include +#include +#include "Note.h" + +// TODO : finir la classe Chart + +class Chart { + +public: + + Chart(const std::string &dif, + int level = 1, + int resolution = 240); + + const std::string &getDif() const; + void setDif(const std::string &dif); + + int getLevel() const; + void setLevel(int level); + + int getResolution() const; + void setResolution(int resolution); + + void addNote(Note note); + void removeNote(Note note); + bool hasNote(Note note); + int getNoteCount(); + const std::set &getNotes() const; + +private: + + std::string dif; + int level; + int resolution; + std::set Notes; + +}; + + +#endif //FEIS_CHART_H diff --git a/Fumen.cpp b/Fumen.cpp index 4b601f2..7fe70f8 100644 --- a/Fumen.cpp +++ b/Fumen.cpp @@ -89,22 +89,97 @@ void Fumen::loadFromMemon(std::string path) { this->setJacketPath(j["metadata"]["jacket_path"]); this->setBPM(j["metadata"]["BPM"]); this->setOffset(j["metadata"]["offset"]); - // TODO : finir la désérialisation depuis un memon + for (auto& chart_json : j["data"]) { + this->addChart(Chart(chart_json["dif"],chart_json["level"],chart_json["resolution"])); + Chart& chart = this->getFirstChartWithName(chart_json["dif"]); + for (auto& note : chart["notes"]) { + chart.addNote(Note(note["n"],note["t"],note["l"],note["p"])); + } + } + } else { + throw std::runtime_error("Memon file looks invalid : " + path); } } -void Fumen::addNote(Note note) { - this->Notes.insert(note); +void Fumen::saveAsMemon(std::string path) { + + std::ofstream fichier(path); + using json = nlohmann::json; + json j; + j["metadata"] = json::object(); + j["metadata"]["song_title"] = this->getSongTitle(); + j["metadata"]["artist"] = this->getArtist(); + j["metadata"]["music_path"] = this->getMusicPath(); + j["metadata"]["jacket_path"] = this->getJacketPath(); + j["metadata"]["BPM"] = this->getBPM(); + j["metadata"]["offset"] = this->getOffset(); + j["data"] = json::array(); + for (auto& chart : this->Charts) { + json chart_json; + chart_json["dif"] = chart.getDif(); + chart_json["level"] = chart.getLevel(); + chart_json["resolution"] = chart.getResolution(); + chart_json["notes"] = json::array(); + for (auto& note : chart.getNotes()) { + json note_json; + note_json["n"] = note.getPos(); + note_json["t"] = note.getTiming(); + note_json["l"] = note.getLength(); + note_json["p"] = note.getTrail_pos(); + chart_json["notes"].push_back(note_json); + } + j["data"].push_back(chart_json); + } + + fichier << std::setw(4) << j << std::endl; + } -void Fumen::removeNote(Note note) { - if (hasNote(note)) { - Notes.erase(Notes.find(note)); +void Fumen::addChart(Chart chart) { + if (!this->hasChartWithName(chart.getDif())) { + this->Charts.push_back(chart); + } else { + throw std::runtime_error("Tried adding chart with already existing name : " + chart.getDif()); } } -bool Fumen::hasNote(Note note) { - return this->Notes.find(note) != Notes.end(); +void Fumen::removeChartByIndex(int index) { + this->Charts.erase(this->Charts.begin()+index); +} + +void Fumen::removeAllChartsWithName(std::string dif) { + auto & chart; + for(chart = this->Charts.begin(); chart != this->Charts.end();) + { + if(chart.getDif() == dif) { + chart = this->Charts.erase(chart); + } + else { + ++chart; + } + } +} + +bool Fumen::hasChartWithName(std::string name) { + for (auto& chart : this->Charts) { + if (chart.getDif() == name) { + return true; + } + } + return false; +} + +Chart& Fumen::getChartByIndex(int index) { + return this->Charts.at(index); +} + +Chart& Fumen::getFirstChartWithName(std::string name) { + for (auto& chart: this->Charts) { + if (chart.getDif() == name) { + return chart; + } + } + throw std::runtime_error("Unable to find chart with name : " + name); } const std::string &Fumen::getSongTitle() const { @@ -165,5 +240,4 @@ Fumen::Fumen(const std::string &songTitle, musicPath(musicPath), jacketPath(jacketPath), BPM(BPM), - offset(offset), - Notes({}) {} + offset(offset) {} diff --git a/Fumen.h b/Fumen.h index 71645c2..cc05aa3 100644 --- a/Fumen.h +++ b/Fumen.h @@ -12,7 +12,9 @@ #include #include "Note.h" +#include "Chart.h" +// TODO : trouver une manière ÉLÉGANTE d'acceder aux différentes charts class Fumen { @@ -26,16 +28,21 @@ public: float offset = 0); void loadFromMemon(std::string path); - void loadFromMemo(std::string path); - void loadFromEve(std::string path); + // TODO : implementer ça + //void loadFromMemo(std::string path); + //void loadFromEve(std::string path); void saveAsMemon(std::string path); - void saveAsMemo(std::string path); - void saveAsEve(std::string path); + // TODO : implementer ça + //void saveAsMemo(std::string path); + //void saveAsEve(std::string path); - void addNote(Note note); - void removeNote(Note note); - bool hasNote(Note note); + void addChart(Chart chart); + void removeChartByIndex(int index); + void removeAllChartsWithName(std::string dif); + bool hasChartWithName(std::string name); + Chart& getChartByIndex(int index); + Chart& getFirstChartWithName(std::string name); const std::string &getSongTitle() const; void setSongTitle(const std::string &songTitle); @@ -57,7 +64,7 @@ public: private: - std::set Notes; + std::vector Charts; std::string songTitle; std::string artist; std::string musicPath;