added "userdir" settings which can be used to overwrite default save (and load) directories

This commit is contained in:
thrust26 2020-12-24 11:48:15 +01:00
parent a0812dc10f
commit 18cc04c9ca
12 changed files with 127 additions and 23 deletions

View File

@ -1352,7 +1352,7 @@ string CartDebug::saveDisassembly(string path)
if(path.empty())
path = myOSystem.defaultSaveDir().getPath()
path = myOSystem.userSaveDir().getPath()
+ myConsole.properties().get(PropType::Cart_Name) + ".asm";
else
// Append default extension when missing
@ -1380,7 +1380,7 @@ string CartDebug::saveDisassembly(string path)
string CartDebug::saveRom(string path)
{
if(path.empty())
path = myOSystem.defaultSaveDir().getPath()
path = myOSystem.userSaveDir().getPath()
+ myConsole.properties().get(PropType::Cart_Name) + ".a26";
else
// Append default extension when missing
@ -1406,7 +1406,7 @@ string CartDebug::saveAccessFile(string path)
try
{
if(path.empty())
path = myOSystem.defaultSaveDir().getPath()
path = myOSystem.userSaveDir().getPath()
+ myConsole.properties().get(PropType::Cart_Name) + ".csv";
else
// Append default extension when missing

View File

@ -683,7 +683,7 @@ string DebuggerParser::saveScriptFile(string file)
// Use default path if no path is provided
if(file.find_first_of(FilesystemNode::PATH_SEPARATOR) == string::npos)
file = debugger.myOSystem.defaultSaveDir().getPath() + file;
file = debugger.myOSystem.userSaveDir().getPath() + file;
FilesystemNode node(file);
@ -1144,7 +1144,7 @@ void DebuggerParser::executeDump()
else
{
ostringstream file;
file << debugger.myOSystem.defaultSaveDir()
file << debugger.myOSystem.userSaveDir()
<< debugger.myOSystem.console().properties().get(PropType::Cart_Name) << "_dbg_";
if(execDepth > 0)
{
@ -1240,7 +1240,7 @@ void DebuggerParser::executeExec()
file += ".script";
FilesystemNode node(file);
if (!node.exists())
node = FilesystemNode(debugger.myOSystem.defaultSaveDir().getPath() + file);
node = FilesystemNode(debugger.myOSystem.userSaveDir().getPath() + file);
if (argCount == 2) {
execPrefix = argStrings[1];
@ -1910,7 +1910,7 @@ void DebuggerParser::executeSaveses()
{
ostringstream filename;
auto timeinfo = BSPF::localTime();
filename << debugger.myOSystem.defaultSaveDir()
filename << debugger.myOSystem.userSaveDir()
<< std::put_time(&timeinfo, "session_%F_%H-%M-%S.txt");
if(argCount && argStrings[0] == "?")

View File

@ -466,7 +466,7 @@ void DebuggerDialog::showBrowser(BrowserType type, const string& defaultName)
{
createBrowser("Save " + title + " as");
const string path = instance().defaultSaveDir().getPath() + defaultName;
const string path = instance().userSaveDir().getPath() + defaultName;
myBrowser->show(path, BrowserDialog::FileSave, cmd, kBdCancelCmd);
}
}

View File

@ -246,6 +246,14 @@ void OSystem::loadConfig(const Settings::Options& options)
mySettings->load(options);
// TODO: check if affected by '-baseDir'and 'basedirinapp' params
string userDir = mySettings->getString("userdir");
if(userDir.empty())
userDir = defSaveDir;
myUserSaveDir = FilesystemNode(userDir);
if(!myUserSaveDir.isDirectory())
myUserSaveDir.makeDir();
Logger::instance().setLogParameters(mySettings->getInt("loglevel"),
mySettings->getBool("logtoconsole"));
Logger::debug("Loading config options ...");
@ -333,6 +341,14 @@ void OSystem::setConfigPaths()
#endif
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void OSystem::setUserDir(const string& path)
{
mySettings->setValue("userdir", path);
myUserSaveDir = FilesystemNode(path);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
bool OSystem::checkUserPalette(bool outputError) const
{

View File

@ -323,6 +323,7 @@ class OSystem
*/
const FilesystemNode& defaultSaveDir() const { return myDefaultSaveDir; }
const FilesystemNode& defaultLoadDir() const { return myDefaultLoadDir; }
const FilesystemNode& userSaveDir() const { return myUserSaveDir; }
/**
Open the given ROM and return an array containing its contents.
@ -427,6 +428,9 @@ class OSystem
static void overrideBaseDir(const string& path) { ourOverrideBaseDir = path; }
static void overrideBaseDirWithApp() { ourOverrideBaseDirWithApp = true; }
// Update the path of the user directory
void setUserDir(const string& path);
public:
//////////////////////////////////////////////////////////////////////
// The following methods are system-specific and can be overrided in
@ -552,7 +556,8 @@ class OSystem
private:
FilesystemNode myBaseDir, myStateDir, mySnapshotSaveDir, mySnapshotLoadDir,
myNVRamDir, myCfgDir, myDefaultSaveDir, myDefaultLoadDir;
myNVRamDir, myCfgDir, myDefaultSaveDir, myDefaultLoadDir,
myUserSaveDir;
FilesystemNode myCheatFile, myConfigFile, myPaletteFile, myPropertiesFile;
FilesystemNode myRomFile; string myRomMD5;

View File

@ -135,6 +135,8 @@ Settings::Settings()
// Config files and paths
setPermanent("romdir", "");
setPermanent("userdir", "");
setPermanent("saveuserdir", "false");
// ROM browser options
setPermanent("exitlauncher", "false");
@ -572,6 +574,8 @@ void Settings::usage() const
<< " -basic_settings <0|1> Display only a basic settings dialog\n"
<< " -romdir <dir> Set the directory where the ROM launcher will\n"
<< " start\n"
<< " -userdir <dir> The directory to save user files to\n"
<< " -saveuserdir <1|0> Update user directory when navigating in browser\n"
<< " -avoxport <name> The name of the serial port where an AtariVox is\n"
<< " connected\n"
<< " -holdreset Start the emulator with the Game Reset switch\n"

View File

@ -61,8 +61,13 @@ BrowserDialog::BrowserDialog(GuiObject* boss, const GUI::Font& font,
_currentPath = new EditTextWidget(this, font, xpos + t->getWidth(), ypos,
_w - t->getWidth() - 2 * xpos, lineHeight);
_currentPath->setEditable(false);
xpos = _w - (HBORDER + _font.getStringWidth("Save") + CheckboxWidget::prefixSize(_font));
_savePathBox = new CheckboxWidget(this, font, xpos, ypos + 2, "Save");
_savePathBox->setToolTip("Check to save current path as default.");
// Add file list
ypos += lineHeight + VGAP * 2;
xpos = HBORDER; ypos += lineHeight + VGAP * 2;
_fileList = new FileListWidget(this, font, xpos, ypos, _w - 2 * xpos,
_h - selectHeight - buttonHeight - ypos - VBORDER * 2);
_fileList->setEditable(false);
@ -71,9 +76,9 @@ BrowserDialog::BrowserDialog(GuiObject* boss, const GUI::Font& font,
// Add currently selected item
ypos += _fileList->getHeight() + VGAP * 2;
_type = new StaticTextWidget(this, font, xpos, ypos + 2, "Name ");
_selected = new EditTextWidget(this, font, xpos + _type->getWidth(), ypos,
_w - _type->getWidth() - 2 * xpos, lineHeight, "");
_name = new StaticTextWidget(this, font, xpos, ypos + 2, "Name ");
_selected = new EditTextWidget(this, font, xpos + _name->getWidth(), ypos,
_w - _name->getWidth() - 2 * xpos, lineHeight, "");
addFocusWidget(_selected);
// Buttons
@ -110,6 +115,9 @@ BrowserDialog::BrowserDialog(GuiObject* boss, const GUI::Font& font,
addFocusWidget(b);
addOKWidget(b);
#endif
// add last to avoid focus problems
addFocusWidget(_savePathBox);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -117,6 +125,11 @@ void BrowserDialog::show(const string& startpath,
BrowserDialog::ListMode mode, int cmd, int cancelCmd,
const string& ext)
{
const int fontWidth = _font.getMaxCharWidth(),
//fontHeight = _font.getFontHeight(),
HBORDER = fontWidth * 1.25;
//VGAP = fontHeight / 4;
_mode = mode;
_cmd = cmd;
_cancelCmd = cancelCmd;
@ -140,10 +153,17 @@ void BrowserDialog::show(const string& startpath,
_fileList->setNameFilter([ext](const FilesystemNode& node) {
return BSPF::endsWithIgnoreCase(node.getName(), ext);
});
//_fileList->setHeight(_selected->getTop() - VGAP * 2 - _fileList->getTop());
_currentPath->setWidth(_savePathBox->getLeft() - _currentPath->getLeft() - fontWidth);
_savePathBox->setEnabled(true);
_savePathBox->clearFlags(Widget::FLAG_INVISIBLE);
_savePathBox->setState(instance().settings().getBool("saveuserdir"));
_name->clearFlags(Widget::FLAG_INVISIBLE);
_selected->clearFlags(Widget::FLAG_INVISIBLE);
_selected->setEditable(false);
_selected->setEnabled(false);
_selected->clearFlags(Widget::FLAG_INVISIBLE);
_type->clearFlags(Widget::FLAG_INVISIBLE);
_okWidget->setLabel("Load");
break;
@ -152,22 +172,36 @@ void BrowserDialog::show(const string& startpath,
_fileList->setNameFilter([ext](const FilesystemNode& node) {
return BSPF::endsWithIgnoreCase(node.getName(), ext);
});
//_fileList->setHeight(_selected->getTop() - VGAP * 2 - _fileList->getTop());
_currentPath->setWidth(_savePathBox->getLeft() - _currentPath->getLeft() - fontWidth);
_savePathBox->setEnabled(true);
_savePathBox->clearFlags(Widget::FLAG_INVISIBLE);
_savePathBox->setState(instance().settings().getBool("saveuserdir"));
_name->clearFlags(Widget::FLAG_INVISIBLE);
_selected->clearFlags(Widget::FLAG_INVISIBLE);
_selected->setEditable(true);
_selected->setEnabled(true);
_selected->clearFlags(Widget::FLAG_INVISIBLE);
_type->clearFlags(Widget::FLAG_INVISIBLE);
_okWidget->setLabel("Save");
_selected->setText(fileName);
_okWidget->setLabel("Save");
fileSelected = false;
break;
case Directories:
_fileList->setListMode(FilesystemNode::ListMode::DirectoriesOnly);
_fileList->setNameFilter([](const FilesystemNode&) { return true; });
// TODO: scrollbar affected too!
//_fileList->setHeight(_selected->getBottom() - _fileList->getTop());
_currentPath->setWidth(_savePathBox->getRight() - _currentPath->getLeft());
_savePathBox->setEnabled(false);
_savePathBox->setFlags(Widget::FLAG_INVISIBLE);
_name->setFlags(Widget::FLAG_INVISIBLE);
_selected->setFlags(Widget::FLAG_INVISIBLE);
_selected->setEditable(false);
_selected->setEnabled(false);
_selected->setFlags(Widget::FLAG_INVISIBLE);
_type->setFlags(Widget::FLAG_INVISIBLE);
_okWidget->setLabel("OK");
break;
}
@ -177,6 +211,7 @@ void BrowserDialog::show(const string& startpath,
_fileList->setDirectory(FilesystemNode(directory), fileName);
else
_fileList->setDirectory(FilesystemNode(startpath));
updateUI(fileSelected);
// Finally, open the dialog after it has been fully updated
@ -207,6 +242,15 @@ void BrowserDialog::handleCommand(CommandSender* sender, int cmd,
case FileListWidget::ItemActivated:
// Send a signal to the calling class that a selection has been made
// Since we aren't derived from a widget, we don't have a 'data' or 'id'
if(_mode != Directories)
{
// TODO: check if affected by '-baseDir'and 'basedirinapp' params
bool savePath = _savePathBox->getState();
instance().settings().setValue("saveuserdir", savePath);
if(savePath)
instance().setUserDir(_fileList->currentDir().getShortPath());
}
if(_cmd) sendCommand(_cmd, -1, -1);
close();
break;

View File

@ -67,9 +67,10 @@ class BrowserDialog : public Dialog, public CommandSender
FileListWidget* _fileList{nullptr};
EditTextWidget* _currentPath{nullptr};
StaticTextWidget* _type{nullptr};
StaticTextWidget* _name{nullptr};
EditTextWidget* _selected{nullptr};
ButtonWidget* _goUpButton{nullptr};
CheckboxWidget* _savePathBox{nullptr};
BrowserDialog::ListMode _mode{Directories};

View File

@ -1397,7 +1397,7 @@ void GameInfoDialog::handleCommand(CommandSender* sender, int cmd,
// to re-create it as necessary
createBrowser("Export properties as");
myBrowser->show(instance().defaultSaveDir().getPath() + myGameFile.getNameWithExt(".pro"),
myBrowser->show(instance().userSaveDir().getPath() + myGameFile.getNameWithExt(".pro"),
BrowserDialog::FileSave, kExportChosen);
break;

View File

@ -131,7 +131,7 @@ void SnapshotDialog::saveConfig()
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void SnapshotDialog::setDefaults()
{
mySnapSavePath->setText(instance().defaultSaveDir().getShortPath());
mySnapSavePath->setText(instance().userSaveDir().getShortPath());
mySnapInterval->setValue(2);
mySnapName->setState(false);
mySnapSingle->setState(false);

View File

@ -203,6 +203,36 @@ void Widget::setPos(const Common::Point& pos)
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Widget::setWidth(int w)
{
setSize(w, _h);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Widget::setHeight(int h)
{
setSize(_w, h);
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Widget::setSize(int w, int h)
{
setSize(Common::Point(w, h));
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Widget::setSize(const Common::Point& pos)
{
if(pos != Common::Point(_w, _h))
{
_w = pos.x;
_h = pos.y;
// we have to redraw the whole dialog!
dialog().setDirty();
}
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Widget::handleMouseEntered()
{

View File

@ -57,6 +57,10 @@ class Widget : public GuiObject
virtual void setPosY(int y);
virtual void setPos(int x, int y);
virtual void setPos(const Common::Point& pos);
void setWidth(int w) override;
void setHeight(int h) override;
virtual void setSize(int w, int h);
virtual void setSize(const Common::Point& pos);
virtual bool handleText(char text) { return false; }
virtual bool handleKeyDown(StellaKey key, StellaMod mod) { return false; }