mirror of
https://github.com/amyinspace/MagicSetEditor2.git
synced 2026-06-12 05:36:59 -04:00
Added installer code.
git-svn-id: svn://svn.code.sf.net/p/magicseteditor/code/trunk@561 0fc631ac-6414-0410-93d0-97cfa31319b6
This commit is contained in:
+89
-11
@@ -7,11 +7,24 @@
|
|||||||
// ----------------------------------------------------------------------------- : Includes
|
// ----------------------------------------------------------------------------- : Includes
|
||||||
|
|
||||||
#include <data/installer.hpp>
|
#include <data/installer.hpp>
|
||||||
|
#include <data/locale.hpp>
|
||||||
|
#include <data/game.hpp>
|
||||||
|
#include <data/stylesheet.hpp>
|
||||||
|
#include <data/symbol_font.hpp>
|
||||||
|
#include <data/export_template.hpp>
|
||||||
#include <util/io/package_manager.hpp>
|
#include <util/io/package_manager.hpp>
|
||||||
|
#include <util/platform.hpp>
|
||||||
#include <script/to_value.hpp>
|
#include <script/to_value.hpp>
|
||||||
#include <wx/filename.h>
|
#include <wx/filename.h>
|
||||||
|
#include <wx/wfstream.h>
|
||||||
|
#include <wx/zipstrm.h>
|
||||||
|
#include <wx/stdpaths.h>
|
||||||
|
|
||||||
DECLARE_TYPEOF_COLLECTION(String);
|
DECLARE_TYPEOF_COLLECTION(String);
|
||||||
|
DECLARE_TYPEOF_COLLECTION(PackageP);
|
||||||
|
DECLARE_TYPEOF_COLLECTION(PackageDependencyP);
|
||||||
|
DECLARE_POINTER_TYPE(wxFileInputStream);
|
||||||
|
DECLARE_POINTER_TYPE(wxZipInputStream);
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : Installer
|
// ----------------------------------------------------------------------------- : Installer
|
||||||
|
|
||||||
@@ -24,31 +37,96 @@ IMPLEMENT_REFLECTION(Installer) {
|
|||||||
|
|
||||||
// ----------------------------------------------------------------------------- : Installing
|
// ----------------------------------------------------------------------------- : Installing
|
||||||
|
|
||||||
void Installer::installFrom(const String& filename, bool message_on_success) {
|
void Installer::installFrom(const String& filename, bool message_on_success, bool local) {
|
||||||
Installer i;
|
Installer i;
|
||||||
i.open(filename);
|
i.open(filename);
|
||||||
i.install();
|
try {
|
||||||
|
i.install(local);
|
||||||
|
}
|
||||||
|
catch (Error& e) {
|
||||||
|
handle_error(e);
|
||||||
|
return;
|
||||||
|
}
|
||||||
if (message_on_success) {
|
if (message_on_success) {
|
||||||
wxMessageBox(String::Format(_("'%s' successfully installed %d package%s."), i.name().c_str(), i.packages.size(), i.packages.size() == 1 ? _("") : _("s")),
|
wxMessageBox(String::Format(_("'%s' successfully installed %d package%s."), i.name().c_str(), i.packages.size(), i.packages.size() == 1 ? _("") : _("s")),
|
||||||
_("Magic Set Editor"), wxOK | wxICON_INFORMATION);
|
_("Magic Set Editor"), wxOK | wxICON_INFORMATION);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Installer::install() {
|
struct dependency_check : public unary_function<bool, PackagedP> {
|
||||||
// Walk over all files in this installer
|
dependency_check(PackageDependencyP dep) : dep (dep) {}
|
||||||
|
bool operator () (PackagedP package) {
|
||||||
|
return package->name() == dep->package && package->version >= dep->version;
|
||||||
|
}
|
||||||
|
private:
|
||||||
|
PackageDependencyP dep;
|
||||||
|
};
|
||||||
|
|
||||||
|
void Installer::install(bool local) {
|
||||||
|
// Destination directory
|
||||||
|
String install_dir = local ? ::packages.getLocalDataDir() : ::packages.getGlobalDataDir();
|
||||||
|
if (!wxDirExists(install_dir))
|
||||||
|
wxMkdir(install_dir, 0755);
|
||||||
|
|
||||||
|
// All the packages we're installing.
|
||||||
|
vector<PackagedP> new_packages;
|
||||||
|
|
||||||
|
FOR_EACH(p, packages) {
|
||||||
|
if (wxDirExists(install_dir + _("/") + p) || wxFileExists(install_dir + _("/") + p))
|
||||||
|
throw PackageError(_("Package ") + p + _(" is already installed. Overwriting currently not supported."));
|
||||||
|
PackagedP pack;
|
||||||
|
wxString fn(wxFileName(p).GetExt());
|
||||||
|
if (fn == _("mse-game")) pack = new_intrusive<Game>();
|
||||||
|
else if (fn == _("mse-style")) pack = new_intrusive<StyleSheet>();
|
||||||
|
else if (fn == _("mse-locale")) pack = new_intrusive<Locale>();
|
||||||
|
else if (fn == _("mse-include")) pack = new_intrusive<IncludePackage>();
|
||||||
|
else if (fn == _("mse-symbol-font")) pack = new_intrusive<SymbolFont>();
|
||||||
|
else if (fn == _("mse-export-template")) pack = new_intrusive<ExportTemplate>();
|
||||||
|
else {
|
||||||
|
throw PackageError(_("Unrecognized package type: '") + fn + _("'\nwhile trying to install: ") + p);
|
||||||
|
}
|
||||||
|
Reader reader(openIn(p + _("/") + fn.Mid(4)));
|
||||||
|
pack->Packaged::reflect_impl(reader);
|
||||||
|
new_packages.push_back(pack);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Check dependencies for each and every package.
|
||||||
|
FOR_EACH(p, new_packages) {
|
||||||
|
FOR_EACH(d, p->dependencies) {
|
||||||
|
if (find_if(new_packages.begin(), new_packages.end(), dependency_check(d)) == new_packages.end() &&
|
||||||
|
!::packages.checkDependency(*d, false)) {
|
||||||
|
throw PackageError(_("Unmet dependency for package ") + p->relativeFilename() + _(": ") + d->package + _(", version ") + d->version.toString() + _(" or higher."));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const FileInfos& file_infos = getFileInfos();
|
const FileInfos& file_infos = getFileInfos();
|
||||||
for (FileInfos::const_iterator it = file_infos.begin() ; it != file_infos.end() ; ++it) {
|
for (FileInfos::const_iterator it = file_infos.begin() ; it != file_infos.end() ; ++it) {
|
||||||
// const String& filename = it->first;
|
String file = it->first;
|
||||||
//
|
|
||||||
}
|
wxFileName fn(file);
|
||||||
// REMOVE?
|
wxArrayString dirs = fn.GetDirs();
|
||||||
FOR_EACH(p, packages) {
|
|
||||||
install(p);
|
if (fn.IsDir() || !dirs.GetCount() || find(packages.begin(), packages.end(), dirs[0]) == packages.end())
|
||||||
|
continue;
|
||||||
|
|
||||||
|
String current_dir = install_dir;
|
||||||
|
for (size_t j = 0; j < dirs.GetCount(); ++j) {
|
||||||
|
current_dir += _("/") + dirs[j];
|
||||||
|
if (!wxDirExists(current_dir) && !wxMkdir(current_dir, 0755))
|
||||||
|
throw PackageError(_("Cannot create folder ") + current_dir + _(" for install. Warning: some packages may have been installed anyway, and some may only be partially installed."));
|
||||||
|
}
|
||||||
|
|
||||||
|
InputStreamP is = openIn(file);
|
||||||
|
wxFileOutputStream os (install_dir + _("/") + file);
|
||||||
|
if (!os.IsOk())
|
||||||
|
throw PackageError(_("Cannot create file ") + install_dir + _("/") + file + _(" for install. Warning: some packages may have been installed anyway, and some may only be partially installed."));
|
||||||
|
os.Write(*is);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Installer::install(const String& package) {
|
void Installer::install(const String& package) {
|
||||||
// 1. Make sure the package is not loaded
|
|
||||||
// TODO
|
// TODO
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -21,9 +21,9 @@ class Installer : public Packaged {
|
|||||||
vector<String> packages; ///< Packages to install
|
vector<String> packages; ///< Packages to install
|
||||||
|
|
||||||
/// Load an installer from a file, and run it
|
/// Load an installer from a file, and run it
|
||||||
static void installFrom(const String& filename, bool message_on_success);
|
static void installFrom(const String& filename, bool message_on_success, bool local);
|
||||||
/// Install all the packages
|
/// Install all the packages
|
||||||
void install();
|
void install(bool local);
|
||||||
/// Install a specific package
|
/// Install a specific package
|
||||||
void install(const String& package);
|
void install(const String& package);
|
||||||
|
|
||||||
|
|||||||
@@ -156,7 +156,7 @@ IndexMap<FieldP,ValueP>& Settings::exportOptionsFor(const ExportTemplate& export
|
|||||||
/// Retrieve the directory to use for settings and other data files
|
/// Retrieve the directory to use for settings and other data files
|
||||||
String user_settings_dir() {
|
String user_settings_dir() {
|
||||||
String dir = wxStandardPaths::Get().GetUserDataDir();
|
String dir = wxStandardPaths::Get().GetUserDataDir();
|
||||||
if (!wxDirExists(dir)) wxMkDir(dir);
|
if (!wxDirExists(dir)) wxMkdir(dir);
|
||||||
return dir + _("/");
|
return dir + _("/");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -64,7 +64,7 @@ void HtmlExportWindow::onOk(wxCommandEvent&) {
|
|||||||
info.directory_relative = fn.GetName() + _("-files");
|
info.directory_relative = fn.GetName() + _("-files");
|
||||||
fn.SetFullName(info.directory_relative);
|
fn.SetFullName(info.directory_relative);
|
||||||
info.directory_absolute = fn.GetFullPath();
|
info.directory_absolute = fn.GetFullPath();
|
||||||
wxMkDir(info.directory_absolute);
|
wxMkdir(info.directory_absolute);
|
||||||
}
|
}
|
||||||
// run export script
|
// run export script
|
||||||
Context& ctx = set->getContext();
|
Context& ctx = set->getContext();
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ DECLARE_TYPEOF_COLLECTION(pair_ThumbnailRequestP_Image);
|
|||||||
String user_settings_dir();
|
String user_settings_dir();
|
||||||
String image_cache_dir() {
|
String image_cache_dir() {
|
||||||
String dir = user_settings_dir() + _("/cache");
|
String dir = user_settings_dir() + _("/cache");
|
||||||
if (!wxDirExists(dir)) wxMkDir(dir);
|
if (!wxDirExists(dir)) wxMkdir(dir);
|
||||||
return dir + _("/");
|
return dir + _("/");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+12
-8
@@ -94,9 +94,13 @@ bool MSE::OnInit() {
|
|||||||
return true;
|
return true;
|
||||||
} else if (f.GetExt() == _("mse-installer")) {
|
} else if (f.GetExt() == _("mse-installer")) {
|
||||||
// Installer; install it
|
// Installer; install it
|
||||||
Installer::installFrom(argv[1], true);
|
bool local = false;
|
||||||
packages.destroy();
|
if (argc > 2) {
|
||||||
return false;
|
String arg2 = argv[2];
|
||||||
|
local = arg2 == _("--local");
|
||||||
|
}
|
||||||
|
Installer::installFrom(argv[1], true, local);
|
||||||
|
return true;
|
||||||
} else if (arg == _("--symbol-editor")) {
|
} else if (arg == _("--symbol-editor")) {
|
||||||
Window* wnd = new SymbolWindow(nullptr);
|
Window* wnd = new SymbolWindow(nullptr);
|
||||||
wnd->Show();
|
wnd->Show();
|
||||||
@@ -112,8 +116,7 @@ bool MSE::OnInit() {
|
|||||||
} else {
|
} else {
|
||||||
inst.saveAs(inst.prefered_filename, false);
|
inst.saveAs(inst.prefered_filename, false);
|
||||||
}
|
}
|
||||||
packages.destroy();
|
return true;
|
||||||
return false;
|
|
||||||
} else if (arg == _("--help") || arg == _("-?")) {
|
} else if (arg == _("--help") || arg == _("-?")) {
|
||||||
// command line help
|
// command line help
|
||||||
write_stdout( String(_("Magic Set Editor\n\n"))
|
write_stdout( String(_("Magic Set Editor\n\n"))
|
||||||
@@ -128,17 +131,18 @@ bool MSE::OnInit() {
|
|||||||
+ _(" -v --version \tShow version information.\n")
|
+ _(" -v --version \tShow version information.\n")
|
||||||
+ _(" --create-installer\n")
|
+ _(" --create-installer\n")
|
||||||
+ _(" FILE [FILE]...\tCreate an instaler named FILE, containing the listed packges.\n") );
|
+ _(" FILE [FILE]...\tCreate an instaler named FILE, containing the listed packges.\n") );
|
||||||
return false;
|
return true;
|
||||||
} else if (arg == _("--version") || arg == _("-v")) {
|
} else if (arg == _("--version") || arg == _("-v")) {
|
||||||
// dump version
|
// dump version
|
||||||
write_stdout( _("Magic Set Editor\nVersion ") + app_version.toString() + version_suffix );
|
write_stdout( _("Magic Set Editor\nVersion ") + app_version.toString() + version_suffix );
|
||||||
packages.destroy();
|
return true;
|
||||||
return false;
|
|
||||||
} else {
|
} else {
|
||||||
handle_error(_("Invalid command line argument:\n") + String(argv[1]));
|
handle_error(_("Invalid command line argument:\n") + String(argv[1]));
|
||||||
}
|
}
|
||||||
} catch (const Error& e) {
|
} catch (const Error& e) {
|
||||||
handle_error(e);
|
handle_error(e);
|
||||||
|
OnExit();
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -497,3 +497,11 @@ void Packaged::validate(Version) {
|
|||||||
packages.checkDependency(*dep, true);
|
packages.checkDependency(*dep, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------- : IncludePackage
|
||||||
|
|
||||||
|
String IncludePackage::typeName() const { return _("include"); }
|
||||||
|
|
||||||
|
IMPLEMENT_REFLECTION(IncludePackage) {
|
||||||
|
REFLECT_BASE(Packaged);
|
||||||
|
}
|
||||||
+10
-1
@@ -171,8 +171,8 @@ class Package : public IntrusivePtrVirtualBase {
|
|||||||
void openDirectory();
|
void openDirectory();
|
||||||
void openSubdir(const String&);
|
void openSubdir(const String&);
|
||||||
void openZipfile();
|
void openZipfile();
|
||||||
void saveToDirectory(const String&, bool);
|
|
||||||
void saveToZipfile(const String&, bool);
|
void saveToZipfile(const String&, bool);
|
||||||
|
void saveToDirectory(const String&, bool);
|
||||||
FileInfos::iterator addFile(const String& file);
|
FileInfos::iterator addFile(const String& file);
|
||||||
static String toStandardName(const String& file);
|
static String toStandardName(const String& file);
|
||||||
};
|
};
|
||||||
@@ -228,5 +228,14 @@ class Packaged : public Package {
|
|||||||
friend struct JustAsPackageProxy;
|
friend struct JustAsPackageProxy;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// ----------------------------------------------------------------------------- : IncludePackage
|
||||||
|
|
||||||
|
/// A package that just contains a bunch of files that are used from other packages
|
||||||
|
class IncludePackage : public Packaged {
|
||||||
|
protected:
|
||||||
|
String typeName() const;
|
||||||
|
DECLARE_REFLECTION();
|
||||||
|
};
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : EOF
|
// ----------------------------------------------------------------------------- : EOF
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -15,21 +15,6 @@
|
|||||||
#include <data/export_template.hpp>
|
#include <data/export_template.hpp>
|
||||||
#include <wx/stdpaths.h>
|
#include <wx/stdpaths.h>
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : IncludePackage
|
|
||||||
|
|
||||||
/// A package that just contains a bunch of files that are used from other packages
|
|
||||||
class IncludePackage : public Packaged {
|
|
||||||
protected:
|
|
||||||
String typeName() const;
|
|
||||||
DECLARE_REFLECTION();
|
|
||||||
};
|
|
||||||
|
|
||||||
String IncludePackage::typeName() const { return _("include"); }
|
|
||||||
|
|
||||||
IMPLEMENT_REFLECTION(IncludePackage) {
|
|
||||||
REFLECT_BASE(Packaged);
|
|
||||||
}
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : PackageManager
|
// ----------------------------------------------------------------------------- : PackageManager
|
||||||
|
|
||||||
PackageManager packages;
|
PackageManager packages;
|
||||||
|
|||||||
@@ -71,6 +71,9 @@ class PackageManager {
|
|||||||
/// Check if the given dependency is currently installed
|
/// Check if the given dependency is currently installed
|
||||||
bool checkDependency(const PackageDependency& dep, bool report_errors = false);
|
bool checkDependency(const PackageDependency& dep, bool report_errors = false);
|
||||||
|
|
||||||
|
inline String getGlobalDataDir() const { return global_data_directory; }
|
||||||
|
inline String getLocalDataDir() const { return local_data_directory; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
map<String, PackagedP> loaded_packages;
|
map<String, PackagedP> loaded_packages;
|
||||||
String global_data_directory;
|
String global_data_directory;
|
||||||
|
|||||||
@@ -21,15 +21,6 @@
|
|||||||
|
|
||||||
// ----------------------------------------------------------------------------- : Linux
|
// ----------------------------------------------------------------------------- : Linux
|
||||||
|
|
||||||
#ifdef __linux__
|
|
||||||
|
|
||||||
/// wxMkDir as documented
|
|
||||||
inline void wxMkDir(const String& dir) {
|
|
||||||
wxMkDir(wxConvLocal.cWX2MB(dir), 0777);
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------- : GCC
|
// ----------------------------------------------------------------------------- : GCC
|
||||||
|
|
||||||
#ifdef __GNUC__
|
#ifdef __GNUC__
|
||||||
|
|||||||
Reference in New Issue
Block a user