Sat, 03 Aug 2013 04:44:30 +0300
now with changelog entry
/* * LDForge: LDraw parts authoring CAD * Copyright (C) 2013 Santeri Piippo * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. */ #include <errno.h> #include <time.h> #include <QDir> #include <QTextStream> #include "common.h" #include "config.h" #include "misc.h" #include "gui.h" config* g_configPointers[MAX_CONFIG]; static ushort g_cfgPointerCursor = 0; // ============================================================================= // Load the configuration from file bool config::load() { print ("config::load: Loading configuration file...\n"); print ("config::load: Path to configuration is %1\n", filepath()); // Locale must be disabled for atof setlocale (LC_NUMERIC, "C"); File f (filepath(), File::Read); int ln = 0; if (!f) return false; // Read the values. for (str line : f) { ln++; if (line.isEmpty() || line[0] == '#') continue; // Empty line or comment. // Find the equals sign. int equals = line.indexOf ('='); if (equals == -1) { fprint (stderr, "couldn't find `=` sign in entry `%1`\n", line); continue; } str entry = line.left (equals); str valstring = line.right (line.length() - equals - 1); // Find the config entry for this. config* cfg = null; for (config* i : g_configPointers) { if (!i) break; if (entry == i->name) cfg = i; } if (!cfg) { fprint (stderr, "unknown config `%1`\n", entry); continue; } switch (cfg->getType()) { case Type_int: static_cast<intconfig*> (cfg)->value = valstring.toInt(); break; case Type_str: static_cast<strconfig*> (cfg)->value = valstring; break; case Type_float: static_cast<floatconfig*> (cfg)->value = valstring.toFloat(); break; case Type_bool: { bool& val = static_cast<boolconfig*> (cfg)->value; if (valstring.toUpper() == "TRUE" || valstring == "1") val = true; elif (valstring.toUpper() == "FALSE" || valstring == "0") val = false; break; } case Type_keyseq: static_cast<keyseqconfig*> (cfg)->value = keyseq::fromString (valstring); break; default: break; } } f.close(); return true; } extern_cfg (str, io_ldpath); // ============================================================================= // Save the configuration to disk bool config::save() { // The function will write floats, disable the locale now so that they // are written properly. setlocale (LC_NUMERIC, "C"); // If the directory doesn't exist, create it now. if (QDir (dirpath()).exists() == false) { fprint (stderr, "Creating config path %1...\n", dirpath()); if (!QDir().mkpath (dirpath())) { critical ("Failed to create the configuration directory. Configuration cannot be saved!\n"); return false; } } File f (filepath(), File::Write); print ("writing cfg to %1\n", filepath()); if (!f) { critical (fmt (QObject::tr ("Cannot save configuration, cannot open %1 for writing: %2\n"), filepath(), strerror (errno))); return false; } fprint (f, "# Configuration file for " APPNAME "\n"); str valstring; for (config* cfg : g_configPointers) { if (!cfg) break; if (cfg->isDefault()) continue; switch (cfg->getType()) { case Type_int: valstring = fmt ("%1", static_cast<intconfig*> (cfg)->value); break; case Type_str: valstring = static_cast<strconfig*> (cfg)->value; break; case Type_float: valstring = fmt ("%1", static_cast<floatconfig*> (cfg)->value); break; case Type_bool: valstring = (static_cast<boolconfig*> (cfg)->value) ? "true" : "false"; break; case Type_keyseq: valstring = static_cast<keyseqconfig*> (cfg)->value.toString(); break; default: break; } // Write the entry now. fprint (f, "%1=%2\n", cfg->name, valstring); } f.close(); return true; } // ============================================================================= void config::reset() { for (config* cfg : g_configPointers) { if (!cfg) break; cfg->resetValue(); } } // ============================================================================= str config::filepath() { str path = fmt ("%1%2.cfg", dirpath(), str (APPNAME).toLower()); return path; } // ============================================================================= str config::dirpath() { #ifndef _WIN32 return fmt ("%1" DIRSLASH ".%2" DIRSLASH, QDir::homePath(), str (APPNAME).toLower()); #else return fmt ("%1" DIRSLASH APPNAME DIRSLASH, QDir::homePath()); #endif // _WIN32 } void addConfig (config* ptr) { if (g_cfgPointerCursor == 0) memset (g_configPointers, 0, sizeof g_configPointers); assert (g_cfgPointerCursor < MAX_CONFIG); g_configPointers[g_cfgPointerCursor++] = ptr; }