123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141 |
- #ifndef REPLXX_HISTORY_HXX_INCLUDED
- #define REPLXX_HISTORY_HXX_INCLUDED 1
-
- #include <list>
- #include <unordered_map>
-
- #include "unicodestring.hxx"
- #include "utf8string.hxx"
- #include "conversion.hxx"
- #include "util.hxx"
-
- namespace std {
- template<>
- struct hash<replxx::UnicodeString> {
- std::size_t operator()( replxx::UnicodeString const& us_ ) const {
- std::size_t h( 0 );
- char32_t const* p( us_.get() );
- char32_t const* e( p + us_.length() );
- while ( p != e ) {
- h *= 31;
- h += *p;
- ++ p;
- }
- return ( h );
- }
- };
- }
-
- namespace replxx {
-
- class History {
- public:
- class Entry {
- std::string _timestamp;
- UnicodeString _text;
- public:
- Entry( std::string const& timestamp_, UnicodeString const& text_ )
- : _timestamp( timestamp_ )
- , _text( text_ ) {
- }
- std::string const& timestamp( void ) const {
- return ( _timestamp );
- }
- UnicodeString const& text( void ) const {
- return ( _text );
- }
- bool operator < ( Entry const& other_ ) const {
- return ( _timestamp < other_._timestamp );
- }
- };
- typedef std::list<Entry> entries_t;
- typedef std::unordered_map<UnicodeString, entries_t::const_iterator> locations_t;
- private:
- entries_t _entries;
- locations_t _locations;
- int _maxSize;
- entries_t::const_iterator _current;
- entries_t::const_iterator _yankPos;
- /*
- * _previous and _recallMostRecent are used to allow
- * HISTORY_NEXT action (a down-arrow key) to have a special meaning
- * if invoked after a line from history was accepted without
- * any modification.
- * Special meaning is: a down arrow shall jump to the line one
- * after previously accepted from history.
- */
- entries_t::const_iterator _previous;
- bool _recallMostRecent;
- bool _unique;
- public:
- History( void );
- void add( UnicodeString const& line, std::string const& when = now_ms_str() );
- bool save( std::string const& filename, bool );
- bool load( std::string const& filename );
- void clear( void );
- void set_max_size( int len );
- void set_unique( bool unique_ ) {
- _unique = unique_;
- remove_duplicates();
- }
- void reset_yank_iterator();
- bool next_yank_position( void );
- void reset_recall_most_recent( void ) {
- _recallMostRecent = false;
- }
- void commit_index( void ) {
- _previous = _current;
- _recallMostRecent = true;
- }
- bool is_empty( void ) const {
- return ( _entries.empty() );
- }
- void update_last( UnicodeString const& );
- void drop_last( void );
- bool is_last( void ) const;
- bool move( bool );
- UnicodeString const& current( void ) const {
- return ( _current->text() );
- }
- UnicodeString const& yank_line( void ) const {
- return ( _yankPos->text() );
- }
- void jump( bool, bool = true );
- bool common_prefix_search( UnicodeString const&, int, bool );
- int size( void ) const {
- return ( static_cast<int>( _entries.size() ) );
- }
- Replxx::HistoryScan::impl_t scan( void ) const;
- void save_pos( void );
- void restore_pos( void );
- private:
- History( History const& ) = delete;
- History& operator = ( History const& ) = delete;
- bool move( entries_t::const_iterator&, int, bool = false ) const;
- entries_t::const_iterator moved( entries_t::const_iterator, int, bool = false ) const;
- void erase( entries_t::const_iterator );
- void trim_to_max_size( void );
- void remove_duplicate( UnicodeString const& );
- void remove_duplicates( void );
- bool do_load( std::string const& );
- entries_t::const_iterator last( void ) const;
- void sort( void );
- void reset_iters( void );
- };
-
- class Replxx::HistoryScanImpl {
- History::entries_t const& _entries;
- History::entries_t::const_iterator _it;
- mutable Utf8String _utf8Cache;
- mutable Replxx::HistoryEntry _entryCache;
- mutable bool _cacheValid;
- public:
- HistoryScanImpl( History::entries_t const& );
- bool next( void );
- Replxx::HistoryEntry const& get( void ) const;
- };
-
- }
-
- #endif
|