594 lines
13 KiB
Rust
594 lines
13 KiB
Rust
use serde::{Deserialize, Serialize};
|
|
|
|
#[derive(Clone, Copy, Serialize, Deserialize)]
|
|
#[derive(Debug)]
|
|
#[serde(into = "&str")]
|
|
#[serde(try_from = "&str")]
|
|
pub enum Action {
|
|
App(AppAction),
|
|
Buffer(BufferAction),
|
|
Cursor(CursorAction),
|
|
}
|
|
|
|
impl Action {
|
|
pub const fn clears_popups(self) -> bool {
|
|
use Action::*;
|
|
|
|
match self {
|
|
App(app_action) => app_action.clears_popups(),
|
|
Buffer(buffer_action) => buffer_action.clears_popups(),
|
|
Cursor(cursor_action) => cursor_action.clears_popups(),
|
|
}
|
|
}
|
|
|
|
pub const fn is_inspection(self) -> bool {
|
|
use Action::*;
|
|
use BufferAction::*;
|
|
|
|
matches!(self, Buffer(InspectSelection | InspectSelectionColor))
|
|
}
|
|
}
|
|
|
|
impl From<Action> for &str {
|
|
fn from(action: Action) -> Self {
|
|
match action {
|
|
Action::App(app_action) => app_action.into(),
|
|
Action::Buffer(buffer_action) => buffer_action.into(),
|
|
Action::Cursor(cursor_action) => cursor_action.into(),
|
|
}
|
|
}
|
|
}
|
|
|
|
impl TryFrom<&str> for Action {
|
|
type Error = String;
|
|
|
|
fn try_from(string: &str) -> Result<Self, String> {
|
|
AppAction::try_from(string).map(Self::from)
|
|
.or_else(|()| BufferAction::try_from(string).map(Self::from))
|
|
.or_else(|()| CursorAction::try_from(string).map(Self::from))
|
|
.map_err(|()| format!("invalid action: {string}"))
|
|
}
|
|
}
|
|
|
|
// actions that act on the app as a whole, not just one buffer
|
|
#[derive(Debug, Clone, Copy, Deserialize)]
|
|
pub enum AppAction {
|
|
QuitIfSaved,
|
|
Quit,
|
|
|
|
PreviousBuffer,
|
|
NextBuffer,
|
|
|
|
Yank,
|
|
}
|
|
|
|
impl AppAction {
|
|
const fn clears_popups(self) -> bool {
|
|
use AppAction::*;
|
|
|
|
#[allow(clippy::match_same_arms)]
|
|
match self {
|
|
QuitIfSaved => true,
|
|
Quit => true,
|
|
|
|
PreviousBuffer => false,
|
|
NextBuffer => false,
|
|
|
|
Yank => false,
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<AppAction> for &str {
|
|
fn from(app_action: AppAction) -> Self {
|
|
use AppAction::*;
|
|
|
|
match app_action {
|
|
QuitIfSaved => "quit_if_saved",
|
|
Quit => "quit",
|
|
|
|
PreviousBuffer => "previous_buffer",
|
|
NextBuffer => "next_buffer",
|
|
|
|
Yank => "yank",
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<AppAction> for Action {
|
|
fn from(app_action: AppAction) -> Self {
|
|
Self::App(app_action)
|
|
}
|
|
}
|
|
|
|
impl TryFrom<&str> for AppAction {
|
|
type Error = ();
|
|
|
|
fn try_from(string: &str) -> Result<Self, ()> {
|
|
use AppAction::*;
|
|
|
|
match string {
|
|
"quit_if_saved" => Ok(QuitIfSaved),
|
|
"quit" => Ok(Quit),
|
|
|
|
"previous_buffer" => Ok(PreviousBuffer),
|
|
"next_buffer" => Ok(NextBuffer),
|
|
|
|
"yank" => Ok(Yank),
|
|
|
|
_ => Err(()),
|
|
}
|
|
}
|
|
}
|
|
|
|
#[derive(Clone, Copy, Deserialize)]
|
|
#[derive(Debug)]
|
|
pub enum BufferAction {
|
|
NormalMode,
|
|
SelectMode,
|
|
|
|
Goto,
|
|
View,
|
|
Replace,
|
|
Space,
|
|
Repeat,
|
|
To,
|
|
|
|
ScrollDown,
|
|
ScrollUp,
|
|
|
|
PageCursorHalfDown,
|
|
PageCursorHalfUp,
|
|
|
|
PageDown,
|
|
PageUp,
|
|
|
|
CollapseSelection,
|
|
FlipSelections,
|
|
|
|
Delete,
|
|
|
|
Undo,
|
|
Redo,
|
|
|
|
Save,
|
|
|
|
CopySelectionOnNextLine,
|
|
|
|
RotateSelectionsBackward,
|
|
RotateSelectionsForward,
|
|
|
|
KeepPrimarySelection,
|
|
RemovePrimarySelection,
|
|
|
|
SplitSelectionsInto1s,
|
|
SplitSelectionsInto2s,
|
|
SplitSelectionsInto3s,
|
|
SplitSelectionsInto4s,
|
|
SplitSelectionsInto5s,
|
|
SplitSelectionsInto6s,
|
|
SplitSelectionsInto7s,
|
|
SplitSelectionsInto8s,
|
|
SplitSelectionsInto9s,
|
|
|
|
JumpToSelectedOffset,
|
|
JumpToSelectedOffsetRelativeToMark,
|
|
|
|
ToggleMark,
|
|
|
|
AlignViewCenter,
|
|
AlignViewBottom,
|
|
AlignViewTop,
|
|
|
|
FindTillMark,
|
|
FindTillNull,
|
|
FindTillFF,
|
|
|
|
ExtendTillMark,
|
|
ExtendTillNull,
|
|
ExtendTillFF,
|
|
|
|
InspectSelection,
|
|
InspectSelectionColor,
|
|
}
|
|
|
|
impl BufferAction {
|
|
const fn clears_popups(self) -> bool {
|
|
use BufferAction::*;
|
|
|
|
#[allow(clippy::match_same_arms)]
|
|
match self {
|
|
NormalMode => false,
|
|
SelectMode => false,
|
|
|
|
Goto => false,
|
|
View => false,
|
|
Replace => true,
|
|
Space => false,
|
|
Repeat => true,
|
|
To => false,
|
|
|
|
ScrollDown => true,
|
|
ScrollUp => true,
|
|
|
|
PageCursorHalfDown => true,
|
|
PageCursorHalfUp => true,
|
|
|
|
PageDown => true,
|
|
PageUp => true,
|
|
|
|
CollapseSelection => true,
|
|
FlipSelections => false,
|
|
|
|
Delete => true,
|
|
|
|
Undo => true,
|
|
Redo => true,
|
|
|
|
Save => false,
|
|
|
|
CopySelectionOnNextLine => true,
|
|
|
|
RotateSelectionsBackward => false,
|
|
RotateSelectionsForward => false,
|
|
|
|
KeepPrimarySelection => true,
|
|
RemovePrimarySelection => true,
|
|
|
|
SplitSelectionsInto1s => true,
|
|
SplitSelectionsInto2s => true,
|
|
SplitSelectionsInto3s => true,
|
|
SplitSelectionsInto4s => true,
|
|
SplitSelectionsInto5s => true,
|
|
SplitSelectionsInto6s => true,
|
|
SplitSelectionsInto7s => true,
|
|
SplitSelectionsInto8s => true,
|
|
SplitSelectionsInto9s => true,
|
|
|
|
JumpToSelectedOffset => true,
|
|
JumpToSelectedOffsetRelativeToMark => true,
|
|
|
|
ToggleMark => false,
|
|
|
|
AlignViewCenter => false,
|
|
AlignViewBottom => false,
|
|
AlignViewTop => false,
|
|
|
|
FindTillMark => true,
|
|
FindTillNull => true,
|
|
FindTillFF => true,
|
|
|
|
ExtendTillMark => true,
|
|
ExtendTillNull => true,
|
|
ExtendTillFF => true,
|
|
|
|
InspectSelection => true,
|
|
InspectSelectionColor => true,
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<BufferAction> for &str {
|
|
fn from(buffer_action: BufferAction) -> Self {
|
|
use BufferAction::*;
|
|
|
|
match buffer_action {
|
|
NormalMode => "normal_mode",
|
|
SelectMode => "select_mode",
|
|
|
|
Goto => "goto",
|
|
View => "view",
|
|
Replace => "replace",
|
|
Space => "space",
|
|
Repeat => "repeat",
|
|
To => "to",
|
|
|
|
ScrollDown => "scroll_down",
|
|
ScrollUp => "scroll_up",
|
|
|
|
PageCursorHalfDown => "page_cursor_half_down",
|
|
PageCursorHalfUp => "page_cursor_half_up",
|
|
|
|
PageDown => "page_down",
|
|
PageUp => "page_up",
|
|
|
|
CollapseSelection => "collapse_selection",
|
|
FlipSelections => "flip_selections",
|
|
|
|
Delete => "delete",
|
|
|
|
Undo => "undo",
|
|
Redo => "redo",
|
|
|
|
Save => "save",
|
|
|
|
CopySelectionOnNextLine => "copy_selection_on_next_line",
|
|
|
|
RotateSelectionsBackward => "rotate_selections_backward",
|
|
RotateSelectionsForward => "rotate_selections_forward",
|
|
|
|
KeepPrimarySelection => "keep_primary_selection",
|
|
RemovePrimarySelection => "remove_primary_selection",
|
|
|
|
SplitSelectionsInto1s => "split_selections_into_1s",
|
|
SplitSelectionsInto2s => "split_selections_into_2s",
|
|
SplitSelectionsInto3s => "split_selections_into_3s",
|
|
SplitSelectionsInto4s => "split_selections_into_4s",
|
|
SplitSelectionsInto5s => "split_selections_into_5s",
|
|
SplitSelectionsInto6s => "split_selections_into_6s",
|
|
SplitSelectionsInto7s => "split_selections_into_7s",
|
|
SplitSelectionsInto8s => "split_selections_into_8s",
|
|
SplitSelectionsInto9s => "split_selections_into_9s",
|
|
|
|
JumpToSelectedOffset => "jump_to_selected_offset",
|
|
JumpToSelectedOffsetRelativeToMark => "jump_to_selected_offset_relative_to_mark",
|
|
|
|
ToggleMark => "toggle_mark",
|
|
|
|
AlignViewCenter => "align_view_center",
|
|
AlignViewBottom => "align_view_bottom",
|
|
AlignViewTop => "align_view_top",
|
|
|
|
FindTillMark => "find_till_mark",
|
|
FindTillNull => "find_till_null",
|
|
FindTillFF => "find_till_ff",
|
|
|
|
ExtendTillMark => "extend_till_mark",
|
|
ExtendTillNull => "extend_till_null",
|
|
ExtendTillFF => "extend_till_ff",
|
|
|
|
InspectSelection => "inspect_selection",
|
|
InspectSelectionColor => "inspect_selection_color",
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<BufferAction> for Action {
|
|
fn from(buffer_action: BufferAction) -> Self {
|
|
Self::Buffer(buffer_action)
|
|
}
|
|
}
|
|
|
|
impl TryFrom<&str> for BufferAction {
|
|
type Error = ();
|
|
|
|
fn try_from(string: &str) -> Result<Self, ()> {
|
|
use BufferAction::*;
|
|
|
|
match string {
|
|
"normal_mode" => Ok(NormalMode),
|
|
"select_mode" => Ok(SelectMode),
|
|
|
|
"goto" => Ok(Goto),
|
|
"view" => Ok(View),
|
|
"replace" => Ok(Replace),
|
|
"space" => Ok(Space),
|
|
"repeat" => Ok(Repeat),
|
|
"to" => Ok(To),
|
|
|
|
"scroll_down" => Ok(ScrollDown),
|
|
"scroll_up" => Ok(ScrollUp),
|
|
|
|
"page_cursor_half_down" => Ok(PageCursorHalfDown),
|
|
"page_cursor_half_up" => Ok(PageCursorHalfUp),
|
|
|
|
"page_down" => Ok(PageDown),
|
|
"page_up" => Ok(PageUp),
|
|
|
|
"collapse_selection" => Ok(CollapseSelection),
|
|
"flip_selections" => Ok(FlipSelections),
|
|
|
|
"delete" => Ok(Delete),
|
|
|
|
"undo" => Ok(Undo),
|
|
"redo" => Ok(Redo),
|
|
|
|
"save" => Ok(Save),
|
|
|
|
"copy_selection_on_next_line" => Ok(CopySelectionOnNextLine),
|
|
|
|
"rotate_selections_backward" => Ok(RotateSelectionsBackward),
|
|
"rotate_selections_forward" => Ok(RotateSelectionsForward),
|
|
|
|
"keep_primary_selection" => Ok(KeepPrimarySelection),
|
|
"remove_primary_selection" => Ok(RemovePrimarySelection),
|
|
|
|
"split_selections_into_1s" => Ok(SplitSelectionsInto1s),
|
|
"split_selections_into_2s" => Ok(SplitSelectionsInto2s),
|
|
"split_selections_into_3s" => Ok(SplitSelectionsInto3s),
|
|
"split_selections_into_4s" => Ok(SplitSelectionsInto4s),
|
|
"split_selections_into_5s" => Ok(SplitSelectionsInto5s),
|
|
"split_selections_into_6s" => Ok(SplitSelectionsInto6s),
|
|
"split_selections_into_7s" => Ok(SplitSelectionsInto7s),
|
|
"split_selections_into_8s" => Ok(SplitSelectionsInto8s),
|
|
"split_selections_into_9s" => Ok(SplitSelectionsInto9s),
|
|
|
|
"jump_to_selected_offset" => Ok(JumpToSelectedOffset),
|
|
"jump_to_selected_offset_relative_to_mark" => Ok(JumpToSelectedOffsetRelativeToMark),
|
|
|
|
"toggle_mark" => Ok(ToggleMark),
|
|
|
|
"align_view_center" => Ok(AlignViewCenter),
|
|
"align_view_bottom" => Ok(AlignViewBottom),
|
|
"align_view_top" => Ok(AlignViewTop),
|
|
|
|
"find_till_mark" => Ok(FindTillMark),
|
|
"find_till_null" => Ok(FindTillNull),
|
|
"find_till_ff" => Ok(FindTillFF),
|
|
|
|
"extend_till_mark" => Ok(ExtendTillMark),
|
|
"extend_till_null" => Ok(ExtendTillNull),
|
|
"extend_till_ff" => Ok(ExtendTillFF),
|
|
|
|
"inspect_selection" => Ok(InspectSelection),
|
|
"inspect_selection_color" => Ok(InspectSelectionColor),
|
|
|
|
_ => Err(()),
|
|
}
|
|
}
|
|
}
|
|
|
|
#[derive(Clone, Copy, Serialize, Deserialize)]
|
|
#[derive(Debug)]
|
|
#[serde(rename_all = "snake_case")]
|
|
pub enum CursorAction {
|
|
MoveByteUp,
|
|
MoveByteDown,
|
|
MoveByteLeft,
|
|
MoveByteRight,
|
|
|
|
ExtendByteUp,
|
|
ExtendByteDown,
|
|
ExtendByteLeft,
|
|
ExtendByteRight,
|
|
|
|
GotoLineStart,
|
|
GotoLineEnd,
|
|
GotoFileStart,
|
|
GotoFileEnd,
|
|
|
|
ExtendLineStart,
|
|
ExtendLineEnd,
|
|
ExtendFileStart,
|
|
ExtendFileEnd,
|
|
|
|
MoveNextWordStart,
|
|
MoveNextWordEnd,
|
|
MovePreviousWordStart,
|
|
|
|
ExtendNextWordStart,
|
|
ExtendNextWordEnd,
|
|
ExtendPreviousWordStart,
|
|
|
|
ExtendLineBelow,
|
|
ExtendLineAbove,
|
|
}
|
|
|
|
impl CursorAction {
|
|
const fn clears_popups(self) -> bool {
|
|
use CursorAction::*;
|
|
|
|
#[allow(clippy::match_same_arms)]
|
|
match self {
|
|
MoveByteUp => true,
|
|
MoveByteDown => true,
|
|
MoveByteLeft => true,
|
|
MoveByteRight => true,
|
|
|
|
ExtendByteUp => true,
|
|
ExtendByteDown => true,
|
|
ExtendByteLeft => true,
|
|
ExtendByteRight => true,
|
|
|
|
GotoLineStart => true,
|
|
GotoLineEnd => true,
|
|
GotoFileStart => true,
|
|
GotoFileEnd => true,
|
|
|
|
ExtendLineStart => true,
|
|
ExtendLineEnd => true,
|
|
ExtendFileStart => true,
|
|
ExtendFileEnd => true,
|
|
|
|
MoveNextWordStart => true,
|
|
MoveNextWordEnd => true,
|
|
MovePreviousWordStart => true,
|
|
|
|
ExtendNextWordStart => true,
|
|
ExtendNextWordEnd => true,
|
|
ExtendPreviousWordStart => true,
|
|
|
|
ExtendLineBelow => true,
|
|
ExtendLineAbove => true,
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<CursorAction> for &str {
|
|
fn from(cursor_action: CursorAction) -> Self {
|
|
use CursorAction::*;
|
|
|
|
match cursor_action {
|
|
MoveByteUp => "move_byte_up",
|
|
MoveByteDown => "move_byte_down",
|
|
MoveByteLeft => "move_byte_left",
|
|
MoveByteRight => "move_byte_right",
|
|
|
|
ExtendByteUp => "extend_byte_up",
|
|
ExtendByteDown => "extend_byte_down",
|
|
ExtendByteLeft => "extend_byte_left",
|
|
ExtendByteRight => "extend_byte_right",
|
|
|
|
GotoLineStart => "goto_line_start",
|
|
GotoLineEnd => "goto_line_end",
|
|
GotoFileStart => "goto_file_start",
|
|
GotoFileEnd => "goto_file_end",
|
|
|
|
ExtendLineStart => "extend_line_start",
|
|
ExtendLineEnd => "extend_line_end",
|
|
ExtendFileStart => "extend_file_start",
|
|
ExtendFileEnd => "extend_file_end",
|
|
|
|
MoveNextWordStart => "move_next_word_start",
|
|
MoveNextWordEnd => "move_next_word_end",
|
|
MovePreviousWordStart => "move_previous_word_start",
|
|
|
|
ExtendNextWordStart => "extend_next_word_start",
|
|
ExtendNextWordEnd => "extend_next_word_end",
|
|
ExtendPreviousWordStart => "extend_previous_word_start",
|
|
|
|
ExtendLineBelow => "extend_line_below",
|
|
ExtendLineAbove => "extend_line_above",
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<CursorAction> for Action {
|
|
fn from(cursor_action: CursorAction) -> Self {
|
|
Self::Cursor(cursor_action)
|
|
}
|
|
}
|
|
|
|
impl TryFrom<&str> for CursorAction {
|
|
type Error = ();
|
|
|
|
fn try_from(string: &str) -> Result<Self, ()> {
|
|
use CursorAction::*;
|
|
|
|
match string {
|
|
"move_byte_up" => Ok(MoveByteUp),
|
|
"move_byte_down" => Ok(MoveByteDown),
|
|
"move_byte_left" => Ok(MoveByteLeft),
|
|
"move_byte_right" => Ok(MoveByteRight),
|
|
|
|
"extend_byte_up" => Ok(ExtendByteUp),
|
|
"extend_byte_down" => Ok(ExtendByteDown),
|
|
"extend_byte_left" => Ok(ExtendByteLeft),
|
|
"extend_byte_right" => Ok(ExtendByteRight),
|
|
|
|
"goto_line_start" => Ok(GotoLineStart),
|
|
"goto_line_end" => Ok(GotoLineEnd),
|
|
"goto_file_start" => Ok(GotoFileStart),
|
|
"goto_file_end" => Ok(GotoFileEnd),
|
|
|
|
"extend_line_start" => Ok(ExtendLineStart),
|
|
"extend_line_end" => Ok(ExtendLineEnd),
|
|
"extend_file_start" => Ok(ExtendFileStart),
|
|
"extend_file_end" => Ok(ExtendFileEnd),
|
|
|
|
"move_next_word_start" => Ok(MoveNextWordStart),
|
|
"move_next_word_end" => Ok(MoveNextWordEnd),
|
|
"move_previous_word_start" => Ok(MovePreviousWordStart),
|
|
|
|
"extend_next_word_start" => Ok(ExtendNextWordStart),
|
|
"extend_next_word_end" => Ok(ExtendNextWordEnd),
|
|
"extend_previous_word_start" => Ok(ExtendPreviousWordStart),
|
|
|
|
"extend_line_below" => Ok(ExtendLineBelow),
|
|
"extend_line_above" => Ok(ExtendLineAbove),
|
|
|
|
_ => Err(()),
|
|
}
|
|
}
|
|
}
|