Tulip  4.6.0
Better Visualization Through Research
library/tulip-gui/include/tulip/TulipProject.h
00001 /*
00002  *
00003  * This file is part of Tulip (www.tulip-software.org)
00004  *
00005  * Authors: David Auber and the Tulip development Team
00006  * from LaBRI, University of Bordeaux
00007  *
00008  * Tulip is free software; you can redistribute it and/or modify
00009  * it under the terms of the GNU Lesser General Public License
00010  * as published by the Free Software Foundation, either version 3
00011  * of the License, or (at your option) any later version.
00012  *
00013  * Tulip is distributed in the hope that it will be useful,
00014  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00015  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
00016  * See the GNU General Public License for more details.
00017  *
00018  */
00019 
00020 #ifndef TULIPPROJECT_H
00021 #define TULIPPROJECT_H
00022 
00023 #include <QDir>
00024 #include <QString>
00025 #include <QStringList>
00026 #include <QDate>
00027 #include <QObject>
00028 #include <QIODevice>
00029 
00030 #include <tulip/tulipconf.h>
00031 
00032 #include <fstream>
00033 
00034 namespace tlp {
00035 
00036 class PluginProgress;
00037 
00038 /**
00039   @ingroup Plugins
00040 
00041   @brief The TulipProject object handles the content of a Tulip project.
00042 
00043   All tulip projects contain a set of defined static meta-information:
00044   @list
00045   @li name (QString): the name of the project
00046   @li description (QString): Comments about the project
00047   @li author (QString): the author of the project
00048   @li perspective (QString): the name of the perspective plugin associated to the project
00049   @li date (QDate): the date of project's last modification
00050   @li version (QString): the version of the Tulip project format
00051   @endlist
00052 
00053   Alongside this information, one can store any kind of file into a Tulip project. Since a project is meant to be associated to a specific perspective, the responisbility of those file
00054   is left to the perspective.
00055 
00056   A TulipProject DOES NOT automatically save to disk. One will have to call the write() method to serialize data.
00057   @warning Precise implementation of the TulipProject object should NOT be known or used by the user since it could be subject to changes.
00058 
00059   If something wrong happens when calling a method from TulipProject, this method will return either false or a invalid result (see specific method documentation). The last error message can be retrieved with the lastError() method.
00060 
00061   After opening and before saving a project, user will be able to list/delete files and directories available in the project and open them using std filestreams or Qt's QIODevice.
00062   Files can be opened using the stdFileStram and fileStream methods. They will always be opened in Read/Write mode.
00063 
00064   Files in a tulip project are identified by their path. Those path ar similar to the path of a standard file system and use the "/" character as a separator.
00065   The root directory is identified by "/".
00066 
00067   @warning TulipProject paths ALWAYS use the "/" character as a directory separator. This is OS-independant.
00068 
00069   @note A file called graph.tlp located at the top-level directory will be identified by the "/graph.tlp" path while the file "graph.tlp" located in the "data" directory will be identified by "/data/graph.tlp".
00070   */
00071 class TLP_QT_SCOPE TulipProject: public QObject {
00072   Q_OBJECT
00073 
00074   TulipProject();
00075   TulipProject(const QString &);
00076 public:
00077 
00078   virtual ~TulipProject();
00079 
00080   /**
00081     @brief Starts a new TulipProject from scratch
00082 
00083     This method builds up a new TulipProject file without taking any input.
00084     @see openProject()
00085     */
00086   static TulipProject *newProject();
00087 
00088   /**
00089     @brief Opens a previously saved tulip project file and returns the corresponding project
00090 
00091     This method will unpack a tulip project file into some directory and allow the user to manipulate the files.
00092     @see TulipProject::save()
00093     @param file The file to open.
00094     @param progress A progress handler.
00095     @return a pointer to a TulipProject object.
00096     */
00097   static TulipProject *openProject(const QString &file, tlp::PluginProgress *progress=NULL);
00098 
00099   /**
00100     @brief Opens a previously saved tulip project file
00101 
00102     This method will unpack a tulip project file into some directory and allow the user to manipulate the files.
00103     @see TulipProject::save()
00104     @param file The file to open.
00105     @param progress A progress handler.
00106     @return true if the file has been successfully opened
00107     */
00108   bool openProjectFile(const QString &file, tlp::PluginProgress *progress=NULL);
00109 
00110   /**
00111     @brief Restores a project which has already been extracted into path
00112 
00113     @warning Using several TulipProject instances on the same directory may result in undefined behavior. This method should only be used for crash handling purposes.
00114     @param path The path where the archive was previously extracted
00115     @return a pointer to a TulipProject object.
00116     */
00117   static TulipProject *restoreProject(const QString &path);
00118 
00119 
00120   /**
00121     @brief Writes files in the TulipProject into a packed archive.
00122 
00123     This method packs every file in the project into a single archive.
00124     @note This method DOES NOT close the project. It only  commits changes to the specified file. A TulipProject is only closed when destroyed.
00125     @param file Absolute path where files should be packed.
00126     @param progress A progress handler
00127     @return False if method failed
00128     */
00129   bool write(const QString &file,tlp::PluginProgress *progress=NULL);
00130 
00131   /**
00132     @brief Lists entries in a directory
00133 
00134     @see QDir documentation for a complete description of filtering arguments
00135     @param path The path to scan. @see TulipProject
00136     @return The list of files and directories present in the given directory
00137     */
00138   QStringList entryList(const QString &path, QDir::Filters filters = QDir::NoFilter, QDir::SortFlags sort = QDir::NoSort);
00139 
00140   /**
00141     @brief Lists entries in a directory
00142 
00143     @see QDir documentation for a complete description of filtering arguments
00144     @param path The path to scan. @see TulipProject
00145     @return The list of files and directories present in the given directory
00146     */
00147   QStringList entryList(const QString &path, const QStringList &nameFilters, QDir::Filters filters = QDir::NoFilter, QDir::SortFlags sort = QDir::NoSort);
00148 
00149   /**
00150     @brief Checks if the specified file/folder exists
00151 
00152     @param path The path to check.
00153     @return true if the path exists.
00154     */
00155   bool exists(const QString &path);
00156 
00157   /**
00158     @brief Recursively creates the specified path.
00159 
00160     Created folders will be empty
00161     @return true if path was successfully created.
00162     */
00163   bool mkpath(const QString &path);
00164 
00165   /**
00166     @brief Checks if the given path is a directory.
00167 
00168     @param path The path to check. @see TulipProject
00169     @return true/false wether the path is a directory.
00170     */
00171   bool isDir(const QString &path);
00172 
00173   /**
00174     @brief Removes a file from the project.
00175 
00176     If the given path points to a directory, or if the file does not exist, this method will fail and return false
00177     @param path The path to delete. @see TulipProject
00178     */
00179   bool removeFile(const QString &path);
00180 
00181   /**
00182     @brief Removes a directory from the project.
00183 
00184     If the given file points to a file, or if the directory does not exist, or if the directory is not empty, this method will fail and return false.
00185     @see removeAllDir to remove a non-empty directory.
00186     @param path The path to delete. @see TulipProject
00187     */
00188   bool removeDir(const QString &path);
00189 
00190   /**
00191     @brief Removes a directory and all its content from the project.
00192 
00193     If the given file points to a file, or if the directory does not exist, this method will fail and return false.
00194     @warning This will remove every file stored in the specified directory.
00195     @param path The path to delete. @see TulipProject
00196     */
00197   bool removeAllDir(const QString &path);
00198 
00199   /**
00200     @brief Copies a file from the local filesystem into the project
00201 
00202     @param source The absolute path of the file to copy
00203     @param destination The project path where to copy the file
00204     @return false if copy failed
00205     */
00206   bool copy(const QString& source, const QString& destination);
00207 
00208   /**
00209     @brief Creates a empty file
00210 
00211     This method is similar to the UNIX's touch shell command. Except it won't renew the file's creation date if the file already exists.
00212     @param file the file to create
00213     @return true if file creation was sucessful.
00214     */
00215   bool touch(const QString& path);
00216 
00217   /**
00218     @brief Gets a STL file stream (default to R/W access mode) to the given path.
00219 
00220     @warning This method does not check if the given path is a directory or a file. User might get an invalid filestream.
00221     @warning It is up to the user to delete the std::fstream returned.
00222     @param path The path to open. @see TulipProject
00223     @return an opened filestream on the given path.
00224     */
00225   std::fstream *stdFileStream(const QString &path, std::ios_base::openmode=std::fstream::in | std::fstream::out | std::fstream::app);
00226 
00227   /**
00228     @brief Gets a Qt I/O device (default to R/W access mode) to the given path.
00229 
00230     @warning This method does not check if the given path is a directory or a file. User might get an invalid filestream.
00231     @warning User SHOULD NOT cast the QIODevice returned by this method into any of its subclass since the implementation might change in future versions.
00232     @warning It is up to the user to delete the QIODevice returned.
00233     @param path The path to open. @see TulipProject
00234     @param mode The opening mode as described in the Qt documentation.
00235     @return an opened Qt device on the given path.
00236     */
00237   QIODevice *fileStream(const QString &path, QIODevice::OpenMode mode=QIODevice::ReadWrite);
00238 
00239   /**
00240     @brief Returns the last error raised.
00241 
00242     @note The returned string is null if no error was raised.
00243     */
00244   QString lastError() const {
00245     return _lastError;
00246   }
00247 
00248   /**
00249     @brief Check if the object is a valid TulipProject.
00250 
00251     @warning Calling methods on invalid TulipProject instances may result in undefined behavior.
00252     */
00253   bool isValid() const {
00254     return _isValid;
00255   }
00256 
00257   /**
00258     @brief Return the archive file associated with this project.
00259 
00260     If the project has been opened from an existing file or if the write method has already been called, this method will return the last file path specified.
00261     In other cases, this method will return an empty string.
00262     */
00263   QString projectFile() const {
00264     return _projectFile;
00265   }
00266 
00267   /**
00268     @brief This method returns the real absolute path corresponding to / in the TulipProject.
00269 
00270     This can be used to create a TulipProject directly from a path.
00271     @warning Using several TulipProject instances at the same time on the same path may result in undefined behavior.
00272     */
00273   QString absoluteRootPath() const;
00274 
00275   // Developer note: Every field in the TulipProject tagged as a Q_PROPERTY will automaticaly be serialized in the project.xml file
00276   /**
00277     @brief the name of the project
00278     */
00279   Q_PROPERTY(QString name READ name WRITE setName)
00280   /**
00281    * @see name
00282    */
00283   QString name() const;
00284 
00285   /**
00286     @brief User-written description of the project
00287     */
00288   Q_PROPERTY(QString description READ description WRITE setDescription)
00289   /**
00290    * @see description
00291    */
00292   QString description() const;
00293 
00294   /**
00295     @brief Name of the author
00296     */
00297   Q_PROPERTY(QString author READ author WRITE setAuthor)
00298   /**
00299    * @see author
00300    */
00301   QString author() const;
00302 
00303   /**
00304     @brief Name of the perspective associated to the project.
00305 
00306     When the user open a project from Tulip, this porperty is first read to identify find kind of perspective plugin should be launched to
00307     open the project
00308 
00309     @warning If the perspective name associated to the project is invalid or correspond to a missing plugin, tulip may not be able to open the file.
00310     */
00311   Q_PROPERTY(QString perspective READ perspective WRITE setPerspective)
00312   /**
00313    * @see perspective
00314    */
00315   QString perspective() const;
00316 
00317   /**
00318     @brief The version of the Tulip project format with which the file was created.
00319     Project from older format versions will always by saved into the newest version available.
00320     */
00321   QString version() const;
00322 
00323   /**
00324     @brief Returns the absolute filesystem path used to store the file
00325     @warning Be cautious though since directly modifying project files without using TulipProject methods could result in undefined behavior.
00326     */
00327   QString toAbsolutePath(const QString &relativePath);
00328 
00329 signals:
00330   void projectFileChanged(const QString& projectFile);
00331 
00332 public slots:
00333   /**
00334    * @see name
00335    */
00336   void setName(const QString &);
00337   /**
00338    * @see description
00339    */
00340   void setDescription(const QString &);
00341   /**
00342    * @see author
00343    */
00344   void setAuthor(const QString &);
00345   /**
00346    * @see perspective
00347    */
00348   void setPerspective(const QString &);
00349 
00350 private:
00351   static QString temporaryPath();
00352 
00353   bool writeMetaInfos();
00354   bool readMetaInfos();
00355 
00356   bool removeAllDirPrivate(const QString &path);
00357 
00358   // Core fileset
00359   QDir _rootDir;
00360   QDir _dataDir;
00361   QString _projectFile;
00362 
00363   // Meta information
00364   QString _author;
00365   QString _name;
00366   QString _description;
00367   QString _perspective;
00368 
00369   // Error handling
00370   QString _lastError;
00371   bool _isValid;
00372 };
00373 
00374 }
00375 #endif // TULIPPROJECT_H
 All Classes Files Functions Variables Enumerations Enumerator Properties