From 721b90bb7e872a5b835380f2c973d8e45d163d5f Mon Sep 17 00:00:00 2001 From: Azat Khuzhin Date: Fri, 19 Nov 2021 16:18:28 +0300 Subject: [PATCH] Add history_move_{next/prevoius} Right now there is UP/DOWN arrows, that is binded to history_prevous/history_next accordingly. But in case of multiline history entry it will navigate through the lines in the current history itemfirst, and this may not be the requird behavior. So now replxx will have history_move_*, that will always navigate through history, regardless of new lines in query. New history_move_{next/prev} binded to M-UP/M-DOWN (like in readline). --- examples/cxx-api.cxx | 2 ++ include/replxx.h | 2 ++ include/replxx.hxx | 2 ++ src/replxx_impl.cxx | 16 ++++++++++++++++ src/replxx_impl.hxx | 2 ++ 5 files changed, 24 insertions(+) diff --git a/examples/cxx-api.cxx b/examples/cxx-api.cxx index 8104b32..5458d3b 100644 --- a/examples/cxx-api.cxx +++ b/examples/cxx-api.cxx @@ -446,6 +446,8 @@ int main( int argc_, char** argv_ ) { rx.bind_key_internal( Replxx::KEY::RIGHT, "move_cursor_right" ); rx.bind_key_internal( Replxx::KEY::UP, "history_previous" ); rx.bind_key_internal( Replxx::KEY::DOWN, "history_next" ); + rx.bind_key_internal( Replxx::KEY::meta( Replxx::KEY::UP ), "history_move_previous" ); + rx.bind_key_internal( Replxx::KEY::meta( Replxx::KEY::DOWN ), "history_move_next" ); rx.bind_key_internal( Replxx::KEY::PAGE_UP, "history_first" ); rx.bind_key_internal( Replxx::KEY::PAGE_DOWN, "history_last" ); rx.bind_key_internal( Replxx::KEY::HOME, "move_cursor_to_begining_of_line" ); diff --git a/include/replxx.h b/include/replxx.h index 1dcfddc..29d01e7 100644 --- a/include/replxx.h +++ b/include/replxx.h @@ -163,6 +163,8 @@ typedef enum { REPLXX_ACTION_MOVE_CURSOR_RIGHT, REPLXX_ACTION_HISTORY_NEXT, REPLXX_ACTION_HISTORY_PREVIOUS, + REPLXX_ACTION_HISTORY_MOVE_NEXT, + REPLXX_ACTION_HISTORY_MOVE_PREVIOUS, REPLXX_ACTION_HISTORY_FIRST, REPLXX_ACTION_HISTORY_LAST, REPLXX_ACTION_HISTORY_RESTORE, diff --git a/include/replxx.hxx b/include/replxx.hxx index ce48139..6205c0b 100644 --- a/include/replxx.hxx +++ b/include/replxx.hxx @@ -178,6 +178,8 @@ public: MOVE_CURSOR_RIGHT, HISTORY_NEXT, HISTORY_PREVIOUS, + HISTORY_MOVE_NEXT, + HISTORY_MOVE_PREVIOUS, HISTORY_FIRST, HISTORY_LAST, HISTORY_RESTORE, diff --git a/src/replxx_impl.cxx b/src/replxx_impl.cxx index 4bf91c2..617ccda 100644 --- a/src/replxx_impl.cxx +++ b/src/replxx_impl.cxx @@ -80,6 +80,8 @@ char const COMMIT_LINE[] = "commit_line"; char const CLEAR_SCREEN[] = "clear_screen"; char const COMPLETE_NEXT[] = "complete_next"; char const COMPLETE_PREVIOUS[] = "complete_previous"; +char const HISTORY_MOVE_NEXT[] = "history_move_next"; +char const HISTORY_MOVE_PREVIOUS[] = "history_move_previous"; char const HISTORY_NEXT[] = "history_next"; char const HISTORY_PREVIOUS[] = "history_previous"; char const HISTORY_LAST[] = "history_last"; @@ -237,6 +239,8 @@ Replxx::ReplxxImpl::ReplxxImpl( FILE*, FILE*, FILE* ) _namedActions[action_names::COMPLETE_PREVIOUS] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::COMPLETE_PREVIOUS, _1 ); _namedActions[action_names::HISTORY_NEXT] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::HISTORY_NEXT, _1 ); _namedActions[action_names::HISTORY_PREVIOUS] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::HISTORY_PREVIOUS, _1 ); + _namedActions[action_names::HISTORY_MOVE_NEXT] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::HISTORY_MOVE_NEXT, _1 ); + _namedActions[action_names::HISTORY_MOVE_PREVIOUS] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::HISTORY_MOVE_PREVIOUS, _1 ); _namedActions[action_names::HISTORY_LAST] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::HISTORY_LAST, _1 ); _namedActions[action_names::HISTORY_FIRST] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::HISTORY_FIRST, _1 ); _namedActions[action_names::HISTORY_RESTORE] = std::bind( &ReplxxImpl::invoke, this, Replxx::ACTION::HISTORY_RESTORE, _1 ); @@ -302,6 +306,8 @@ Replxx::ReplxxImpl::ReplxxImpl( FILE*, FILE*, FILE* ) bind_key( Replxx::KEY::control( 'P' ), _namedActions.at( action_names::COMPLETE_PREVIOUS ) ); bind_key( Replxx::KEY::DOWN + 0, _namedActions.at( action_names::HISTORY_NEXT ) ); bind_key( Replxx::KEY::UP + 0, _namedActions.at( action_names::HISTORY_PREVIOUS ) ); + bind_key( Replxx::KEY::meta( Replxx::KEY::DOWN ), _namedActions.at( action_names::HISTORY_MOVE_NEXT ) ); + bind_key( Replxx::KEY::meta( Replxx::KEY::UP ), _namedActions.at( action_names::HISTORY_MOVE_PREVIOUS ) ); bind_key( Replxx::KEY::meta( '<' ), _namedActions.at( action_names::HISTORY_FIRST ) ); bind_key( Replxx::KEY::PAGE_UP + 0, _namedActions.at( action_names::HISTORY_FIRST ) ); bind_key( Replxx::KEY::meta( '>' ), _namedActions.at( action_names::HISTORY_LAST ) ); @@ -354,6 +360,8 @@ Replxx::ACTION_RESULT Replxx::ReplxxImpl::invoke( Replxx::ACTION action_, char32 case ( Replxx::ACTION::MOVE_CURSOR_RIGHT ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::move_one_char_right, code ) ); case ( Replxx::ACTION::HISTORY_NEXT ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::history_next, code ) ); case ( Replxx::ACTION::HISTORY_PREVIOUS ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::history_previous, code ) ); + case ( Replxx::ACTION::HISTORY_MOVE_NEXT ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::history_move_next, code ) ); + case ( Replxx::ACTION::HISTORY_MOVE_PREVIOUS ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::history_move_previous, code ) ); case ( Replxx::ACTION::HISTORY_FIRST ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::history_first, code ) ); case ( Replxx::ACTION::HISTORY_LAST ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::history_last, code ) ); case ( Replxx::ACTION::HISTORY_RESTORE_CURRENT ): return ( action( MOVE_CURSOR | RESET_KILL_ACTION, &Replxx::ReplxxImpl::history_restore_current, code ) ); @@ -1919,6 +1927,14 @@ Replxx::ACTION_RESULT Replxx::ReplxxImpl::history_next( char32_t ) { return ( history_move( false ) ); } +Replxx::ACTION_RESULT Replxx::ReplxxImpl::history_move_next( char32_t ) { + return ( history_move( false ) ); +} + +Replxx::ACTION_RESULT Replxx::ReplxxImpl::history_move_previous( char32_t ) { + return ( history_move( true ) ); +} + Replxx::ACTION_RESULT Replxx::ReplxxImpl::history_move( bool previous_ ) { // if not already recalling, add the current line to the history list so // we don't have to special case it diff --git a/src/replxx_impl.hxx b/src/replxx_impl.hxx index a5e3f15..537e35c 100644 --- a/src/replxx_impl.hxx +++ b/src/replxx_impl.hxx @@ -243,6 +243,8 @@ private: Replxx::ACTION_RESULT commit_line( char32_t ); Replxx::ACTION_RESULT history_next( char32_t ); Replxx::ACTION_RESULT history_previous( char32_t ); + Replxx::ACTION_RESULT history_move_next( char32_t ); + Replxx::ACTION_RESULT history_move_previous( char32_t ); Replxx::ACTION_RESULT history_move( bool ); Replxx::ACTION_RESULT history_first( char32_t ); Replxx::ACTION_RESULT history_last( char32_t );