/* Copyright (C) 2012 Sebastian Herbord. All rights reserved. This file is part of Mod Organizer. Mod Organizer 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. Mod Organizer 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 Mod Organizer. If not, see . */ #ifndef FOMODINSTALLERDIALOG_H #define FOMODINSTALLERDIALOG_H #include "installdialog.h" #include #include #include #include #include namespace Ui { class FomodInstallerDialog; } class Condition : public QObject { Q_OBJECT public: Condition(QObject *parent = NULL) : QObject(parent) { } Condition(const Condition &reference) : QObject(reference.parent()), m_Name(reference.m_Name), m_Value(reference.m_Value) { } Condition(const QString &name, const QString &value) : QObject(), m_Name(name), m_Value(value) { } QString m_Name; QString m_Value; private: Condition &operator=(const Condition&); }; Q_DECLARE_METATYPE(Condition) class FileDescriptor : public QObject { Q_OBJECT public: FileDescriptor(QObject *parent) : QObject(parent), m_Source(), m_Destination(), m_Priority(0), m_IsFolder(false), m_AlwaysInstall(false), m_InstallIfUsable(false) {} FileDescriptor(const FileDescriptor &reference) : QObject(reference.parent()), m_Source(reference.m_Source), m_Destination(reference.m_Destination), m_Priority(reference.m_Priority), m_IsFolder(reference.m_IsFolder), m_AlwaysInstall(reference.m_AlwaysInstall), m_InstallIfUsable(reference.m_InstallIfUsable) {} QString m_Source; QString m_Destination; int m_Priority; bool m_IsFolder; bool m_AlwaysInstall; bool m_InstallIfUsable; private: FileDescriptor &operator=(const FileDescriptor&); }; Q_DECLARE_METATYPE(FileDescriptor*) class FomodInstallerDialog : public QDialog { Q_OBJECT public: explicit FomodInstallerDialog(const QString &modName, bool nameWasGuessed, const QString &fomodPath, QWidget *parent = 0); ~FomodInstallerDialog(); void initData(); /** * @return bool true if the user requested the manual dialog **/ bool manualRequested() const { return m_Manual; } /** * @return QString the (user-modified) name to be used for the mod **/ QString getName() const; /** * @brief retrieve the updated archive tree from the dialog. The caller is responsible to delete the returned tree. * * @note This call is destructive on the input tree! * * @param tree input tree. (TODO isn't this the same as the tree passed in the constructor?) * @return DataTree* a new tree with only the selected options and directories arranged correctly. The caller takes custody of this pointer! **/ MOBase::DirectoryTree *updateTree(MOBase::DirectoryTree *tree); protected: virtual bool eventFilter(QObject *object, QEvent *event); private slots: void on_cancelBtn_clicked(); void on_manualBtn_clicked(); void on_websiteLabel_linkActivated(const QString &link); void on_nextBtn_clicked(); void on_prevBtn_clicked(); private: enum ItemOrder { ORDER_ASCENDING, ORDER_DESCENDING, ORDER_EXPLICIT }; enum GroupType { TYPE_SELECTATLEASTONE, TYPE_SELECTATMOSTONE, TYPE_SELECTEXACTLYONE, TYPE_SELECTANY, TYPE_SELECTALL }; enum PluginType { TYPE_REQUIRED, TYPE_RECOMMENDED, TYPE_OPTIONAL, TYPE_NOTUSABLE, TYPE_COULDBEUSABLE }; struct Plugin { QString m_Name; QString m_Description; QString m_ImagePath; PluginType m_Type; std::vector m_Conditions; std::vector m_Files; }; struct ConditionalInstall { enum { OP_AND, OP_OR } m_Operator; std::vector m_Conditions; std::vector m_Files; }; private: static int bomOffset(const QByteArray &buffer); QString readContent(QXmlStreamReader &reader); void parseInfo(const QByteArray &data); static ItemOrder getItemOrder(const QString &orderString); static GroupType getGroupType(const QString &typeString); static PluginType getPluginType(const QString &typeString); static bool byPriority(const FileDescriptor *LHS, const FileDescriptor *RHS); bool copyFileIterator(MOBase::DirectoryTree *sourceTree, MOBase::DirectoryTree *destinationTree, FileDescriptor *descriptor); void readFileList(QXmlStreamReader &reader, std::vector &fileList); void readPluginType(QXmlStreamReader &reader, Plugin &plugin); void readConditionFlags(QXmlStreamReader &reader, Plugin &plugin); FomodInstallerDialog::Plugin readPlugin(QXmlStreamReader &reader); void readPlugins(QXmlStreamReader &reader, GroupType groupType, QLayout *layout); void readGroup(QXmlStreamReader &reader, QLayout *layout); void readGroups(QXmlStreamReader &reader, QLayout *layout); void readVisible(QXmlStreamReader &reader, QVariantList &conditions); QGroupBox *readInstallerStep(QXmlStreamReader &reader); ConditionalInstall readConditionalPattern(QXmlStreamReader &reader); void readConditionalFileInstalls(QXmlStreamReader &reader); void readInstallerSteps(QXmlStreamReader &reader); void parseModuleConfig(const QByteArray &data); void highlightControl(QAbstractButton *button); bool testCondition(int maxIndex, const QString &flag, const QString &value); bool testVisible(int pageIndex); bool nextPage(); void activateCurrentPage(); void moveTree(MOBase::DirectoryTree::Node *target, MOBase::DirectoryTree::Node *source); MOBase::DirectoryTree::Node *findNode(MOBase::DirectoryTree::Node *node, const QString &path, bool create); void copyLeaf(MOBase::DirectoryTree::Node *sourceTree, const QString &sourcePath, MOBase::DirectoryTree::Node *destinationTree, const QString &destinationPath); private: Ui::FomodInstallerDialog *ui; bool m_NameWasGuessed; QString m_FomodPath; bool m_Manual; // ItemOrder m_StepOrder; // std::vector m_Steps; std::vector m_RequiredFiles; std::vector m_ConditionalInstalls; }; #endif // FOMODINSTALLERDIALOG_H