TuttleOFX  1
Sequence.hpp
Go to the documentation of this file.
00001 #ifndef _SEQUENCE_PARSER_SEQUENCE_HPP_
00002 #define _SEQUENCE_PARSER_SEQUENCE_HPP_
00003 
00004 #include "FileObject.hpp"
00005 #include "commonDefinitions.hpp"
00006 
00007 #include <boost/lexical_cast.hpp>
00008 #include <iomanip>
00009 #include <set>
00010 
00011 namespace sequenceParser {
00012 
00013 namespace detail {
00014 class FileNumbers;
00015 }
00016 
00017 /**
00018  * @brief A sequence of numbered files.
00019  */
00020 class Sequence : public FileObject
00021 {
00022 
00023 public:
00024         /**
00025          * List all recognized pattern types.
00026          */
00027         enum EPattern
00028         {
00029 
00030                 ePatternNone = 0,
00031                 ePatternStandard = 1,
00032                 ePatternCStyle = ePatternStandard * 2,
00033                 ePatternFrame = ePatternCStyle * 2,
00034                 ePatternFrameNeg = ePatternFrame * 2,
00035 
00036                 ePatternDefault = ePatternCStyle + ePatternStandard,
00037                 ePatternAll = ePatternCStyle + ePatternStandard + ePatternFrameNeg
00038         };
00039 
00040         Sequence()
00041         : FileObject()
00042         {
00043                 clear();
00044         }
00045 
00046         Sequence( const boost::filesystem::path& directory, const std::string& prefix, const std::size_t padding, const std::string& suffix, const Time firstTime, const Time lastTime, const Time step = 1, const EMaskOptions options = eMaskOptionsDefault, const bool strictPadding = false )
00047                 : FileObject( directory, eMaskTypeSequence, options )
00048         {
00049                 init( prefix, padding, suffix, firstTime, lastTime, step, strictPadding );
00050         }
00051 
00052         Sequence( const boost::filesystem::path& directory, const std::string& pattern, const Time firstTime, const Time lastTime, const Time step, const EMaskOptions options = eMaskOptionsDefault, const EPattern accept = ePatternDefault ) :
00053         FileObject( directory, eMaskTypeSequence, options )
00054         {
00055                 init( pattern, firstTime, lastTime, step, accept );
00056         }
00057 
00058         Sequence( const boost::filesystem::path& directory, const Time firstTime, const Time lastTime, const Time step, const EMaskOptions options = eMaskOptionsDefault, const EPattern accept = ePatternDefault ) :
00059         FileObject( directory, eMaskTypeSequence, options )
00060         {
00061                 init( firstTime, lastTime, step, accept );
00062         }
00063 
00064         /**
00065          * @todo check if we put a pattern with full path: /home/foo/images/foo.####.jpg
00066          */
00067         Sequence( const boost::filesystem::path& directory, const EMaskOptions options = eMaskOptionsDefault, const EPattern accept = ePatternDefault );
00068 
00069         Sequence( const Sequence& v )
00070         {
00071                 operator=( v );
00072         }
00073 
00074         Sequence( const boost::filesystem::path& directory, const Sequence& v, const EMaskOptions& options )
00075         {
00076                 operator=( v );
00077                 _options = options;
00078                 setDirectory( directory );
00079         }
00080 
00081         ~Sequence();
00082 
00083         Sequence& operator=( const Sequence& other )
00084         {
00085                 FileObject::operator=( other );
00086                 _prefix = other._prefix;
00087                 _suffix = other._suffix;
00088                 _strictPadding = other._strictPadding;
00089                 _padding = other._padding;
00090                 _step = other._step;
00091                 _firstTime = other._firstTime;
00092                 _lastTime = other._lastTime;
00093                 _nbFiles = other._nbFiles;
00094                 return *this;
00095         }
00096         
00097         Sequence* clone() const { return new Sequence(*this); }
00098         
00099 private:
00100         /**
00101          * @brief Construct a sequence from a pattern and given informations.
00102          * @warning No check on your filesystem.
00103          * @warning the directory must be set
00104          */
00105         void init( const std::string& prefix, const std::size_t padding, const std::string& suffix, const Time firstTime, const Time lastTime, const Time step = 1, const bool strictPadding = false );
00106 
00107         /**
00108          * @brief Construct a sequence from a pattern and given informations.
00109          * @warning No check on your filesystem.
00110          * @warning the directory must be set
00111          */
00112         bool init( const std::string& pattern, const Time firstTime, const Time lastTime, const Time step, const EPattern accept = ePatternDefault );
00113 
00114         /**
00115          * @brief Construct a sequence from a pattern and given informations.
00116          * @warning No check on your filesystem.
00117          * @warning the directory must be set
00118          */
00119         inline bool init( const Time firstTime, const Time lastTime, const Time step, const EPattern accept = ePatternDefault );
00120 
00121 public:
00122         /**
00123          * @brief Construct a sequence from a pattern and given informations.
00124          * @warning No check on your filesystem.
00125          * @warning the directory must be set
00126          */
00127         inline bool initFromPattern( const boost::filesystem::path& dir, const std::string& pattern, const Time firstTime, const Time lastTime, const Time step, const EMaskOptions options = eMaskOptionsDefault, const EPattern accept = ePatternDefault );
00128 
00129         /**
00130          * @brief Init from directory and pattern.
00131          * @warning search on your filesystem, to detect the range.
00132          */
00133         bool initFromDetection( const std::string& pattern, const EPattern accept = ePatternDefault );
00134 
00135         /**
00136          * @brief Init from full pattern.
00137          * @warning search on your filesystem, to detect the range.
00138          */
00139         inline bool initFromDetection( const EPattern& accept = ePatternDefault );
00140 
00141         /**
00142          * @brief Find the biggest common step from a set of all steps.
00143          */
00144         void extractStep( const std::set<std::size_t>& steps );
00145 
00146         /**
00147          * @brief Extract step from a sorted vector of time values.
00148          */
00149         void extractStep( const std::vector<Time>& times );
00150 
00151 // TODO: move that outside of that class!
00152         /**
00153          * @brief Extract step from a sorted vector of time values.
00154          */
00155         void extractStep( const std::vector<detail::FileNumbers>::const_iterator& timesBegin, const std::vector<detail::FileNumbers>::const_iterator& timesEnd, const std::size_t i );
00156 
00157         std::size_t getPaddingFromStringNumber( const std::string& timeStr );
00158 
00159         /**
00160          * @brief extract the padding from a vector of frame numbers
00161          * @param[in] timesStr vector of frame numbers in string format
00162          */
00163         void extractPadding( const std::vector<std::string>& timesStr );
00164 
00165         void extractPadding( const std::vector<detail::FileNumbers>::const_iterator& timesBegin, const std::vector<detail::FileNumbers>::const_iterator& timesEnd, const std::size_t i );
00166 
00167         /**
00168          * @brief return if the padding is strict (at least one frame begins with a '0' padding character).
00169          * @param[in] timesStr vector of frame numbers in string format
00170          * @param[in] padding previously detected padding
00171          */
00172         void extractIsStrictPadding( const std::vector<std::string>& timesStr, const std::size_t padding );
00173 
00174         void extractIsStrictPadding( const std::vector<detail::FileNumbers>& times, const std::size_t i, const std::size_t padding );
00175 
00176 public:
00177         inline std::string getAbsoluteFilenameAt( const Time time ) const;
00178 
00179         inline std::string getFilenameAt( const Time time ) const;
00180 
00181         inline std::string getFirstFilename() const;
00182 
00183         inline std::string getAbsoluteFirstFilename() const;
00184 
00185         inline std::string getAbsoluteLastFilename() const;
00186 
00187         /// @return pattern character in standard style
00188         inline char getPatternCharacter() const;
00189 
00190         /// @return a string pattern using standard style
00191         inline std::string getStandardPattern() const;
00192 
00193         inline std::string getAbsoluteStandardPattern() const;
00194 
00195         /// @return a string pattern using C Style
00196         inline std::string getCStylePattern() const;
00197 
00198         inline std::string getAbsoluteCStylePattern() const;
00199 
00200         inline std::pair<Time, Time> getRange() const;
00201 
00202         inline std::size_t getStep() const;
00203 
00204         inline Time getFirstTime() const;
00205 
00206         inline Time getLastTime() const;
00207 
00208         inline std::size_t getDuration() const;
00209 
00210         inline Time getNbFiles() const;
00211 
00212         inline std::size_t getPadding() const;
00213 
00214         inline bool isStrictPadding() const;
00215 
00216         inline bool hasMissingFile() const;
00217 
00218         inline std::size_t getNbMissingFiles() const;
00219 
00220         /// @brief filename without frame number
00221         inline std::string getIdentification() const;
00222 
00223         inline std::string getPrefix() const;
00224 
00225         inline std::string getSuffix() const;
00226 
00227         /**
00228          * @brief Check if the filename is inside the sequence and return it's time value.
00229          * @param[out] time: the time extract from the filename (only if contained in the sequence)
00230          * @return if the filename is contained inside the sequence
00231          */
00232         bool isIn( const std::string& filename, Time& time, std::string& timeStr );
00233 
00234         EPattern checkPattern( const std::string& pattern );
00235 
00236         bool operator<(const Sequence& other ) const
00237         {
00238                 return getAbsoluteStandardPattern() < other.getAbsoluteStandardPattern();
00239         }
00240 
00241         bool operator==(const Sequence& other ) const
00242         {
00243                 /*
00244                 std::cout << "_prefix: " << _prefix << " -> " << other._prefix << std::endl;
00245                 std::cout << "_suffix: " << _suffix << " -> " << other._suffix << std::endl;
00246                 std::cout << "_padding: " << _padding << " -> " << other._padding << std::endl;
00247                 std::cout << "_step: " << _step << " -> " << other._step << std::endl;
00248                 std::cout << "_firstTime: " << _firstTime << " -> " << other._firstTime << std::endl;
00249                 std::cout << "_lastTime: " << _lastTime << " -> " << other._lastTime << std::endl;
00250                 std::cout << "_nbFiles: " << _nbFiles << " -> " << other._nbFiles << std::endl;
00251                 */
00252                 return
00253                         ( _prefix == other._prefix ) &&
00254                         ( _suffix == other._suffix ) &&
00255                         ( _padding == other._padding ) &&
00256                         ( _step == other._step ) &&
00257                         ( _firstTime == other._firstTime ) &&
00258                         ( _lastTime == other._lastTime ) &&
00259                         ( _nbFiles == other._nbFiles );
00260         }
00261 
00262         bool operator!=(const Sequence& other ) const
00263         {
00264                 return !operator==( other );
00265         }
00266 
00267 protected:
00268 
00269         /**
00270          * @brief Partial initialization, using only pattern informations.
00271          * @warning You don't have all informations like range, directory, etc.
00272          */
00273         bool retrieveInfosFromPattern( const std::string& pattern, const EPattern& accept, std::string& prefix, std::string& suffix, std::size_t& padding, bool& strictPadding ) const;
00274 
00275 private:
00276 
00277         std::ostream& getCout( std::ostream& os ) const;
00278 
00279         std::vector<boost::filesystem::path> getFiles() const;
00280 
00281 protected:
00282 
00283         inline void clear()
00284         {
00285                 FileObject::clear();
00286                 _prefix.clear();
00287                 _suffix.clear();
00288                 _padding = 0;
00289                 _step = 1;
00290                 _firstTime = 0;
00291                 _lastTime = 0;
00292                 _nbFiles = 0;
00293         }
00294 
00295 public:
00296         std::string _prefix; ///< filename prefix
00297         std::string _suffix; ///< filename suffix
00298         bool _strictPadding; ///<
00299         std::size_t _padding; ///< padding, no padding if 0, fixed padding otherwise
00300         std::size_t _step; ///< step
00301         Time _firstTime; ///< begin time
00302         Time _lastTime; ///< end time
00303         std::size_t _nbFiles; ///< number of frames
00304         static const char _fillCar = '0'; ///< Filling character
00305 };
00306 
00307 #include <Sequence.tcc>
00308 
00309 
00310 }
00311 
00312 #endif // _SEQUENCE_HPP_