2012-07-27 16:58:27 +00:00
|
|
|
#include "FolderData.h"
|
|
|
|
|
#include "SystemData.h"
|
2013-06-28 12:54:14 +00:00
|
|
|
#include "GameData.h"
|
2012-08-02 04:03:15 +00:00
|
|
|
#include <algorithm>
|
2012-08-08 00:50:45 +00:00
|
|
|
#include <iostream>
|
2012-07-27 16:58:27 +00:00
|
|
|
|
Support sorting of game list via input
You can now map the functions "sortordernext" and "sortorderprevious" to
inputs (in es_input.cfg) and toggle the game list sort order with them.
The order is: "file name, ascending" (default), "file name, descending",
"rating ascending", "rating descending", "user rating ascending", "user
rating descending", "time played ascending", "times played descending",
"last played time ascending", "last played time descending".
2013-06-28 17:44:28 +00:00
|
|
|
|
|
|
|
|
std::map<FolderData::ComparisonFunction*, std::string> FolderData::sortStateNameMap;
|
|
|
|
|
|
2013-06-28 12:54:14 +00:00
|
|
|
bool FolderData::isFolder() const { return true; }
|
|
|
|
|
const std::string & FolderData::getName() const { return mName; }
|
|
|
|
|
const std::string & FolderData::getPath() const { return mPath; }
|
2012-07-27 16:58:27 +00:00
|
|
|
unsigned int FolderData::getFileCount() { return mFileVector.size(); }
|
2013-06-28 12:54:14 +00:00
|
|
|
|
2012-07-27 16:58:27 +00:00
|
|
|
|
|
|
|
|
FolderData::FolderData(SystemData* system, std::string path, std::string name)
|
Support sorting of game list via input
You can now map the functions "sortordernext" and "sortorderprevious" to
inputs (in es_input.cfg) and toggle the game list sort order with them.
The order is: "file name, ascending" (default), "file name, descending",
"rating ascending", "rating descending", "user rating ascending", "user
rating descending", "time played ascending", "times played descending",
"last played time ascending", "last played time descending".
2013-06-28 17:44:28 +00:00
|
|
|
: mSystem(system), mPath(path), mName(name)
|
2012-07-27 16:58:27 +00:00
|
|
|
{
|
Support sorting of game list via input
You can now map the functions "sortordernext" and "sortorderprevious" to
inputs (in es_input.cfg) and toggle the game list sort order with them.
The order is: "file name, ascending" (default), "file name, descending",
"rating ascending", "rating descending", "user rating ascending", "user
rating descending", "time played ascending", "times played descending",
"last played time ascending", "last played time descending".
2013-06-28 17:44:28 +00:00
|
|
|
//first created folder data initializes the list
|
|
|
|
|
if (sortStateNameMap.empty()) {
|
|
|
|
|
sortStateNameMap[compareFileName] = "file name";
|
|
|
|
|
sortStateNameMap[compareRating] = "rating";
|
|
|
|
|
sortStateNameMap[compareUserRating] = "user rating";
|
|
|
|
|
sortStateNameMap[compareTimesPlayed] = "times played";
|
|
|
|
|
sortStateNameMap[compareLastPlayed] = "last time played";
|
|
|
|
|
}
|
2012-07-27 16:58:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
FolderData::~FolderData()
|
|
|
|
|
{
|
|
|
|
|
for(unsigned int i = 0; i < mFileVector.size(); i++)
|
|
|
|
|
{
|
|
|
|
|
delete mFileVector.at(i);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
mFileVector.clear();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void FolderData::pushFileData(FileData* file)
|
|
|
|
|
{
|
|
|
|
|
mFileVector.push_back(file);
|
|
|
|
|
}
|
|
|
|
|
|
Support sorting of game list via input
You can now map the functions "sortordernext" and "sortorderprevious" to
inputs (in es_input.cfg) and toggle the game list sort order with them.
The order is: "file name, ascending" (default), "file name, descending",
"rating ascending", "rating descending", "user rating ascending", "user
rating descending", "time played ascending", "times played descending",
"last played time ascending", "last played time descending".
2013-06-28 17:44:28 +00:00
|
|
|
//sort this folder and any subfolders
|
|
|
|
|
void FolderData::sort(ComparisonFunction & comparisonFunction, bool ascending)
|
|
|
|
|
{
|
|
|
|
|
std::sort(mFileVector.begin(), mFileVector.end(), comparisonFunction);
|
|
|
|
|
|
|
|
|
|
for(unsigned int i = 0; i < mFileVector.size(); i++)
|
|
|
|
|
{
|
|
|
|
|
if(mFileVector.at(i)->isFolder())
|
|
|
|
|
((FolderData*)mFileVector.at(i))->sort(comparisonFunction, ascending);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (!ascending) {
|
|
|
|
|
std::reverse(mFileVector.begin(), mFileVector.end());
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2012-08-02 04:03:15 +00:00
|
|
|
//returns if file1 should come before file2
|
2013-06-28 12:54:14 +00:00
|
|
|
bool FolderData::compareFileName(const FileData* file1, const FileData* file2)
|
2012-08-02 04:03:15 +00:00
|
|
|
{
|
|
|
|
|
std::string name1 = file1->getName();
|
|
|
|
|
std::string name2 = file2->getName();
|
|
|
|
|
|
2013-05-27 17:13:38 +00:00
|
|
|
//min of name1/name2 .length()s
|
|
|
|
|
unsigned int count = name1.length() > name2.length() ? name2.length() : name1.length();
|
|
|
|
|
for(unsigned int i = 0; i < count; i++)
|
2012-08-02 04:03:15 +00:00
|
|
|
{
|
2012-08-08 00:50:45 +00:00
|
|
|
if(toupper(name1[i]) != toupper(name2[i]))
|
2012-08-02 04:03:15 +00:00
|
|
|
{
|
2013-06-28 12:54:14 +00:00
|
|
|
return toupper(name1[i]) < toupper(name2[i]);
|
2012-08-02 04:03:15 +00:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2013-06-28 12:54:14 +00:00
|
|
|
return name1.length() < name2.length();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool FolderData::compareRating(const FileData* file1, const FileData* file2)
|
|
|
|
|
{
|
|
|
|
|
//we need game data. try to cast
|
|
|
|
|
const GameData * game1 = dynamic_cast<const GameData*>(file1);
|
|
|
|
|
const GameData * game2 = dynamic_cast<const GameData*>(file2);
|
|
|
|
|
if (game1 != nullptr && game2 != nullptr) {
|
2013-08-14 12:16:49 +00:00
|
|
|
return const_cast<GameData*>(game1)->metadata()->getFloat("rating") < const_cast<GameData*>(game2)->metadata()->getFloat("rating");
|
2013-06-28 12:54:14 +00:00
|
|
|
}
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
2013-06-28 15:25:18 +00:00
|
|
|
bool FolderData::compareUserRating(const FileData* file1, const FileData* file2)
|
|
|
|
|
{
|
|
|
|
|
//we need game data. try to cast
|
|
|
|
|
const GameData * game1 = dynamic_cast<const GameData*>(file1);
|
|
|
|
|
const GameData * game2 = dynamic_cast<const GameData*>(file2);
|
|
|
|
|
if (game1 != nullptr && game2 != nullptr) {
|
2013-08-14 12:16:49 +00:00
|
|
|
return const_cast<GameData*>(game1)->metadata()->getFloat("userrating") < const_cast<GameData*>(game2)->metadata()->getFloat("userrating");
|
2013-06-28 15:25:18 +00:00
|
|
|
}
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
2013-06-28 12:54:14 +00:00
|
|
|
bool FolderData::compareTimesPlayed(const FileData* file1, const FileData* file2)
|
|
|
|
|
{
|
|
|
|
|
//we need game data. try to cast
|
|
|
|
|
const GameData * game1 = dynamic_cast<const GameData*>(file1);
|
|
|
|
|
const GameData * game2 = dynamic_cast<const GameData*>(file2);
|
|
|
|
|
if (game1 != nullptr && game2 != nullptr) {
|
2013-08-14 12:16:49 +00:00
|
|
|
return const_cast<GameData*>(game1)->metadata()->getInt("playcount") < const_cast<GameData*>(game2)->metadata()->getInt("playcount");
|
2013-06-28 12:54:14 +00:00
|
|
|
}
|
|
|
|
|
return false;
|
2012-08-02 04:03:15 +00:00
|
|
|
}
|
|
|
|
|
|
2013-06-28 15:25:18 +00:00
|
|
|
bool FolderData::compareLastPlayed(const FileData* file1, const FileData* file2)
|
|
|
|
|
{
|
|
|
|
|
//we need game data. try to cast
|
|
|
|
|
const GameData * game1 = dynamic_cast<const GameData*>(file1);
|
|
|
|
|
const GameData * game2 = dynamic_cast<const GameData*>(file2);
|
|
|
|
|
if (game1 != nullptr && game2 != nullptr) {
|
2013-08-14 12:16:49 +00:00
|
|
|
return const_cast<GameData*>(game1)->metadata()->getTime("lastplayed") < const_cast<GameData*>(game2)->metadata()->getTime("lastplayed");
|
2013-06-28 15:25:18 +00:00
|
|
|
}
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
Support sorting of game list via input
You can now map the functions "sortordernext" and "sortorderprevious" to
inputs (in es_input.cfg) and toggle the game list sort order with them.
The order is: "file name, ascending" (default), "file name, descending",
"rating ascending", "rating descending", "user rating ascending", "user
rating descending", "time played ascending", "times played descending",
"last played time ascending", "last played time descending".
2013-06-28 17:44:28 +00:00
|
|
|
std::string FolderData::getSortStateName(ComparisonFunction & comparisonFunction, bool ascending)
|
2012-08-02 04:03:15 +00:00
|
|
|
{
|
Support sorting of game list via input
You can now map the functions "sortordernext" and "sortorderprevious" to
inputs (in es_input.cfg) and toggle the game list sort order with them.
The order is: "file name, ascending" (default), "file name, descending",
"rating ascending", "rating descending", "user rating ascending", "user
rating descending", "time played ascending", "times played descending",
"last played time ascending", "last played time descending".
2013-06-28 17:44:28 +00:00
|
|
|
std::string temp = sortStateNameMap[comparisonFunction];
|
|
|
|
|
if (ascending) {
|
|
|
|
|
temp.append(" (ascending)");
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
temp.append(" (descending)");
|
2012-08-08 00:50:45 +00:00
|
|
|
}
|
Support sorting of game list via input
You can now map the functions "sortordernext" and "sortorderprevious" to
inputs (in es_input.cfg) and toggle the game list sort order with them.
The order is: "file name, ascending" (default), "file name, descending",
"rating ascending", "rating descending", "user rating ascending", "user
rating descending", "time played ascending", "times played descending",
"last played time ascending", "last played time descending".
2013-06-28 17:44:28 +00:00
|
|
|
return temp;
|
2012-08-02 04:03:15 +00:00
|
|
|
}
|
2013-06-28 12:54:14 +00:00
|
|
|
|
|
|
|
|
FileData* FolderData::getFile(unsigned int i) const
|
|
|
|
|
{
|
|
|
|
|
return mFileVector.at(i);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
std::vector<FileData*> FolderData::getFiles(bool onlyFiles) const
|
|
|
|
|
{
|
|
|
|
|
std::vector<FileData*> temp;
|
|
|
|
|
//now check if a child is a folder and get those children in turn
|
|
|
|
|
std::vector<FileData*>::const_iterator fdit = mFileVector.cbegin();
|
|
|
|
|
while(fdit != mFileVector.cend()) {
|
|
|
|
|
//dynamically try to cast to FolderData type
|
|
|
|
|
FolderData * folder = dynamic_cast<FolderData*>(*fdit);
|
|
|
|
|
if (folder != nullptr) {
|
|
|
|
|
//add this only when user wanted it
|
|
|
|
|
if (!onlyFiles) {
|
|
|
|
|
temp.push_back(*fdit);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
temp.push_back(*fdit);
|
|
|
|
|
}
|
|
|
|
|
++fdit;
|
|
|
|
|
}
|
|
|
|
|
return temp;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
std::vector<FileData*> FolderData::getFilesRecursive(bool onlyFiles) const
|
|
|
|
|
{
|
|
|
|
|
std::vector<FileData*> temp;
|
|
|
|
|
//now check if a child is a folder and get those children in turn
|
|
|
|
|
std::vector<FileData*>::const_iterator fdit = mFileVector.cbegin();
|
|
|
|
|
while(fdit != mFileVector.cend()) {
|
|
|
|
|
//dynamically try to cast to FolderData type
|
|
|
|
|
FolderData * folder = dynamic_cast<FolderData*>(*fdit);
|
|
|
|
|
if (folder != nullptr) {
|
|
|
|
|
//add this onyl when user wanted it
|
|
|
|
|
if (!onlyFiles) {
|
|
|
|
|
temp.push_back(*fdit);
|
|
|
|
|
}
|
|
|
|
|
//worked. Is actual folder data. recurse
|
|
|
|
|
std::vector<FileData*> children = folder->getFilesRecursive(onlyFiles);
|
|
|
|
|
//insert children into return vector
|
|
|
|
|
temp.insert(temp.end(), children.cbegin(), children.cend());
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
temp.push_back(*fdit);
|
|
|
|
|
}
|
|
|
|
|
++fdit;
|
|
|
|
|
}
|
|
|
|
|
return temp;
|
2013-08-14 12:16:49 +00:00
|
|
|
}
|