public override bool OnHandleEvent(EventArgs e)
        {
            // handle key down events
            if (e is ConsoleKeyDownEventArgs keyDown)
            {
                switch (keyDown.KeyChar)
                {
                    #region -- Return --
                case '\r':
                    var command = Command;
                    if (currentLineIndex >= lines.Count - 1 && manager.CanExecute(command))
                    {
                        executeCommandOnKeyUp = command;
                    }
                    else
                    {
                        InsertNewLine();
                        Invalidate();
                    }
                    return(true);

                    #endregion
                    #region -- Escape --
                case '\x1B':
                    if (lastInputCommand != null)
                    {
                        ResetLastInputCommand();
                        Invalidate();
                    }
                    else if (currentLineIndex > 0 || currentLineOffset > 0)
                    {
                        currentLineIndex  = 0;
                        currentLineOffset = 0;
                        Invalidate();
                    }
                    else if (CurrentLine.ContentLength > 0 && lines.Count > 0)
                    {
                        Command = String.Empty;
                        Invalidate();
                    }
                    return(true);

                    #endregion
                    #region -- Backspace --
                case '\b':
                    CurrentLine.FixLineEnd(ref currentLineOffset);
                    if (currentLineOffset > 0)
                    {
                        ClearLastInputCommand();
                        currentLineOffset--;
                        if (CurrentLine.Remove(currentLineOffset))
                        {
                            Invalidate();
                        }
                    }
                    else if (currentLineIndex > 0)
                    {
                        ClearLastInputCommand();

                        if (currentLineIndex >= lines.Count)
                        {
                            currentLineIndex = lines.Count - 1;
                        }

                        var prevLine = lines[currentLineIndex - 1];
                        var currLine = CurrentLine;

                        currentLineOffset = prevLine.ContentLength;

                        if (currLine.ContentLength > 0)                                 // copy content
                        {
                            prevLine.InsertLine(currentLineOffset, currLine.content);
                        }

                        lines.RemoveAt(currentLineIndex);
                        currentLineIndex--;

                        Invalidate();
                    }
                    return(true);

                    #endregion
                    #region -- Tab --
                case '\t':
                    for (var i = 0; i < 4; i++)
                    {
                        if (CurrentLine.Insert(ref currentLineOffset, ' ', overwrite))
                        {
                            ClearLastInputCommand();
                            currentLineOffset++;
                            Invalidate();
                        }
                    }
                    return(true);

                    #endregion
                default:
                    if (!Char.IsControl(keyDown.KeyChar))
                    {
                        #region -- Char --
                        if (CurrentLine.Insert(ref currentLineOffset, keyDown.KeyChar, overwrite))
                        {
                            ClearLastInputCommand();
                            currentLineOffset++;
                            Invalidate();
                        }
                        #endregion
                        return(true);
                    }
                    else
                    {
                        switch (keyDown.Key)
                        {
                            #region -- Delete --
                        case ConsoleKey.Delete:
                            if (currentLineOffset >= CurrentLine.ContentLength)
                            {
                                ClearLastInputCommand();

                                if (currentLineIndex < lines.Count - 1)
                                {
                                    CurrentLine.InsertLine(currentLineOffset, lines[currentLineIndex + 1].content);
                                    lines.RemoveAt(currentLineIndex + 1);
                                    Invalidate();
                                }
                            }
                            else if (CurrentLine.Remove(currentLineOffset))
                            {
                                ClearLastInputCommand();
                                Invalidate();
                            }
                            return(true);

                            #endregion
                            #region -- Up,Down,Left,Right --
                        case ConsoleKey.UpArrow:
                            if (currentLineIndex > 0)
                            {
                                if (currentLineIndex >= lines.Count)
                                {
                                    if (lines.Count > 1)
                                    {
                                        currentLineIndex = lines.Count - 2;
                                    }
                                    else
                                    {
                                        currentLineIndex = 0;
                                    }
                                }
                                else
                                {
                                    currentLineIndex--;
                                }
                                Invalidate();
                            }

                            InvalidateCursor();
                            return(true);

                        case ConsoleKey.DownArrow:
                            if (currentLineIndex < lines.Count - 1)
                            {
                                currentLineIndex++;
                                Invalidate();
                            }
                            else if (currentLineIndex >= lines.Count)
                            {
                                currentLineIndex = lines.Count - 1;
                            }

                            InvalidateCursor();
                            return(true);

                        case ConsoleKey.LeftArrow:
                            if ((keyDown.KeyModifiers & ConsoleKeyModifiers.CtrlPressed) != 0)
                            {
                                MoveCursorByToken(CurrentLine.Content, true);
                                InvalidateCursor();
                                return(true);
                            }
                            else if (currentLineOffset > 0)
                            {
                                if (currentLineOffset < CurrentLine.ContentLength)
                                {
                                    currentLineOffset--;
                                }
                                else
                                {
                                    currentLineOffset = CurrentLine.ContentLength - 1;
                                }
                            }
                            else
                            {
                                currentLineOffset = 0;
                            }

                            Invalidate();
                            InvalidateCursor();
                            return(true);

                        case ConsoleKey.RightArrow:
                            if ((keyDown.KeyModifiers & ConsoleKeyModifiers.CtrlPressed) != 0)
                            {
                                MoveCursorByToken(CurrentLine.Content, false);
                                InvalidateCursor();
                                return(true);
                            }
                            else if (currentLineOffset < CurrentLine.ContentLength)
                            {
                                currentLineOffset++;
                            }
                            else
                            {
                                currentLineOffset = CurrentLine.ContentLength;
                            }

                            Invalidate();
                            InvalidateCursor();
                            return(true);

                            #endregion
                        }
                    }
                    break;
                }
            }
            else if (e is ConsoleKeyUpEventArgs keyUp)
            {
                switch (keyUp.Key)
                {
                    #region -- Home,End,Up,Down,PageUp,PageDown --
                case ConsoleKey.Enter:
                    if (executeCommandOnKeyUp != null)
                    {
                        ClearLastInputCommand();

                        if (commandAccepted != null)
                        {
                            commandAccepted.SetResult(executeCommandOnKeyUp);
                        }

                        executeCommandOnKeyUp = null;
                    }
                    break;

                case ConsoleKey.PageUp:
                    MoveHistory(false);
                    return(true);

                case ConsoleKey.UpArrow:
                {
                    if ((keyUp.KeyModifiers & ConsoleKeyModifiers.AltPressed) != 0)
                    {
                        MoveHistory(false);
                        return(true);
                    }
                }
                break;

                case ConsoleKey.PageDown:
                    MoveHistory(true);
                    return(true);

                case ConsoleKey.DownArrow:
                {
                    if (manager is IConsoleReadLineHistory history && (keyUp.KeyModifiers & ConsoleKeyModifiers.AltPressed) != 0)
                    {
                        MoveHistory(true);
                        return(true);
                    }
                }
                break;

                case ConsoleKey.End:
                    if ((keyUp.KeyModifiers & ConsoleKeyModifiers.CtrlPressed) != 0)
                    {
                        currentLineIndex = lines.Count - 1;
                    }
                    currentLineOffset = CurrentLine.ContentLength;
                    Invalidate();
                    return(true);

                case ConsoleKey.Home:
                    if ((keyUp.KeyModifiers & ConsoleKeyModifiers.CtrlPressed) != 0)
                    {
                        currentLineIndex = 0;
                    }
                    currentLineOffset = 0;
                    Invalidate();
                    return(true);

                    #endregion
                    #region -- Insert --
                case ConsoleKey.Insert:
                    overwrite = !overwrite;
                    Invalidate();
                    return(true);

                case ConsoleKey.V:
                    if ((keyUp.KeyModifiers & ConsoleKeyModifiers.CtrlPressed) != 0)
                    {
                        var clipText = GetClipboardText();
                        var first    = true;
                        foreach (var(startAt, len) in Procs.SplitNewLinesTokens(clipText))
                        {
                            if (first)
                            {
                                first = false;
                            }
                            else                                     // new line
                            {
                                InsertNewLine();
                            }

                            CurrentLine.InsertLine(ref currentLineOffset, clipText, startAt, len);
                            Invalidate();
                        }
                        return(true);
                    }
                    break;

                    #endregion
                default:
                {
                    //if (manager is IConsoleReadLineHistory history && (keyUp.KeyModifiers & ConsoleKeyModifiers.CtrlPressed) != 0 && keyUp.Key == ConsoleKey.R)
                    //	;
                }
                break;
                }
            }

            return(base.OnHandleEvent(e));
        }         // proc OnHandleEvent