Подтвердить что ты не робот

Как создать пользовательскую графическую консоль/терминал в Windows?

Консольный интерфейс Windows (думаю, cmd) - для пользователя довольно простой графический интерфейс. Однако уровень эффективности, с которым он обрабатывает рендеринг, ввод пользователя и прокрутку, очень высок. Методы, используемые для создания этого интерфейса, несомненно, сильно отличаются от методов традиционного графического интерфейса рабочего стола.

Я заинтересован в создании моей собственной пользовательской консоли/терминала для Windows, предпочтительно используя С# и .NET-технологии (например, управляемые GDI + или WPF). В качестве отправной точки я бы очень хотел просто воссоздать стандартную простую оболочку Windows. Затем я мог расширять вещи и добавлять туда функции.

Я ищу общие рекомендации по созданию такого пользовательского интерфейса консоли, но некоторые конкретные моменты включают в себя:

  • Какую модель рендеринга я должен использовать? Цикл рендеринга? Частичные обновления (например, WPF)? Модель WinForms (не знаете, как это работает)?

  • Какое кэширование используется в модели рендеринга?

  • Как загружаются шрифты и как они отображаются? Являются ли они стандартными шрифтами TrueType, растровыми шрифтами или чем-то еще?

  • Как прокручивается так эффективно?

  • Что-нибудь еще, что вы думаете, может быть уместным!

Любое объяснение того, как встроенный пользовательский интерфейс консоли Windows (или даже превосходный пользовательский интерфейс Linux) выполняет эти действия - и как я могу имитировать их - был бы идеальным. Фактически.

Изменить: Чтобы быть ясным, я действительно хочу сделать это полностью с нуля. На основе графической структуры, такой как GDI + или WPF, но не более.

4b9b3361

Ответ 1

Я как-то реализовал окно вывода текста с нуля - мне нужен тот, который работает как окно вывода в Visual Studio. Это оказалось сложнее, чем я ожидал, и это было без каких-либо возможностей ввода.

К сожалению, код находится на С++ и принадлежит бывшему работодателю, поэтому я не могу поделиться им с вами. Но я могу дать вам представление о том, чего ожидать.

Вам нужен способ хранения строк вывода, которые вы можете быстро индексировать. Если вы собираетесь разместить лимит на количество отображаемых строк, также нужно будет легко стереть строки сверху. В С++ a deque<string> был идеальным, я не знаю, что эквивалент (если есть) в С#.

Вам понадобятся обработчики для следующих сообщений Windows, в определенном порядке.

  • WM_LBUTTONDOWN - для начала выбора. Используйте SetCapture для отслеживания мыши, пока кнопка не установлена.
  • WM_LBUTTONUP - для завершения выбора.
  • WM_RBUTTONUP - перевести на WM_CONTEXTMENU.
  • WM_CONTEXTMENU - отображение меню с помощью Copy/Cut/Paste и всего, что вы хотите.
  • WM_KEYDOWN - ответить на 4 клавиши курсора, Главная/Конец, PageUp/PageDown. Ctrl-A/Ctrl-C/Ctrl-X/Ctrl-V/Ctrl-D.
  • WM_PAINT - для рисования содержимого окна.
  • WM_SIZE - обновлять полосы прокрутки при изменении размера окна.
  • WM_VSCROLL - обновление видимой части окна во время вертикальной прокрутки.
  • WM_HSCROLL - обновить видимую часть окна во время горизонтальной прокрутки.
  • WM_CREATE - для инициализации при создании окна.
  • WM_SETFOCUS - создать системный карет, чтобы показывать текущую позицию в окне.
  • WM_KILLFOCUS - убить каретку, так как только окно с включенным в настоящее время окном должно показывать каретку.
  • WM_MOUSEMOVE - отслеживать изменения в выборе, пока левая кнопка мыши не работает.
  • WM_CAPTURECHANGED - для завершения выбора.
  • WM_TIMER - автоматическая прокрутка, когда курсор покидает окно во время выбора.
  • WM_GETDLGCODE - добавить DLGC_WANTARROWS, чтобы клавиши со стрелками прошли.
  • WM_MOUSEWHEEL - ответить на колесо мыши для прокрутки.

Так как строки добавляются в текстовый буфер, отрегулируйте диапазон полос прокрутки. В вертикальном диапазоне полос прокрутки будет общее количество линий, а диапазон горизонтальной полосы прокрутки будет шириной самой широкой линии.

Лучше всего иметь один шрифт, который является моноширинным - он делает вычисления намного проще. Специфическая технология шрифтов не имеет большого значения. Вам просто нужно иметь возможность отслеживать позиции символов.

Как прокручивается так эффективно? Вы отслеживаете верхнюю и нижнюю строки окна при прокрутке, и когда появляется сообщение с краской, вы рисуете только строки, которые в настоящее время видны. Остальные все еще находятся в буфере, но их не трогают. Он может разжечь содержимое окна, когда он прокручивает и только красить детали, которые поступают сверху или снизу, но с сегодняшними процессорами это потраченное впустую усилие - окно сделает полную перерисовку так быстро, что вы не заметите.

Изменить: Кстати, я столкнулся с этим руководством Microsoft, чтобы прокрутить строки, которые должны быть необходимы для чтения этой задачи. http://msdn.microsoft.com/en-us/library/windows/desktop/bb787527.aspx

Ответ 2

Если вы хотите создать красивую замену командной строки на .NET, я предлагаю посмотреть http://poshconsole.codeplex.com/ Он использует WPF для графических элементов и он реализует хост PowerShell script. PowerShell - это замена Microsoft для почтенной командной строки. PowerShell устанавливается по умолчанию в Windows 7, но вы можете загрузить его для XP и Vista. PowerShell очень расширяемый, хотя сценарии использования объектов .NET напрямую. Он также может быть встроен в другие программы.

WPF + PowerShell станет отличным отправным местом для того, что вы хотите сделать. Если бы вы захотели, вы могли бы заменить PowerShell на свой собственный механизм командной строки/сценариев. Если бы вы были очень амбициозны, вы могли бы взломать реализацию собственного языка сценариев в DLR, чтобы действовать как ваш интерпретатор команд.

Желаем удачи.

Ответ 3

Посмотрите Console проект с открытым исходным кодом. Он делает много, и делает это очень хорошо. Он обеспечивает единую консоль для любого, на чем основан символ. Я запускаю cmd, bash и python каждый на своей вкладке.

Это на С++, но это не даст удовольствия писать его самостоятельно.

Ответ 4

У меня был большой успех с RichTextBox для вывода. На самом деле он делает все, что вам может пожелать: настройка цвета, эффективный рендеринг и прокрутка, операции с буфером обмена и т.д. Вход был организован путем перехвата событий KeyPress окна.

Ответ 5

Если скорость имеет первостепенное значение, то XNA - очень быстрый способ (минимальное кодирование), чтобы нарисовать текст на высокой скорости. Он может обрабатывать тысячи спрайтов при 100 FPS. Используя SpriteBatch:: DrawString() и SpriteFont вы можете получить высокоскоростную "консоль" с очень небольшим усилием кодирования. Стандартный класс "Игра" может быть изменен для повторного рисования только субрегионов экрана по требованию. Предостережения включают несовершенный кернинг, который придаст тексту размытому виду (вы можете это исправить, отключив сглаживание и будьте осторожны с вашими проекциями и расположением спрайтов). Если это проблема, возможно, Direct2D предлагает лучшее решение (или любое из уже упомянутых решений).

Ответ 6

Как первый и простой подход, я бы использовал TextBox в многострочном режиме. Следите за событиями TextChanged или KeyPressed или KeyUp и действуйте соответствующим образом. Позже вы можете создать свой собственный элемент управления, выведя его из простого элемента управления Panel, например. Рендеринг происходит путем переопределения метода OnPaint (WinForms). Никакой цикл не требуется, просто вызов Invalidate или Refresh.

Используйте строковый массив или List<string> или LinkedList<string> как строковый буфер или просто используйте текст, хранящийся в текстовом поле.

Если вы создаете свой собственный элемент управления с помощью WinForms, System.Windows.Forms.TextRenderer - хороший выбор для рендеринга текста. Он будет использоваться в OnPaint.

Прокрутка - сложная вещь, если вы создаете свой собственный контроль. System.Windows.Controls.Panel уже содержит поддержку прокрутки, однако вам все равно нужно указать элементу управления, как размещать и изменять размеры кнопок прокрутки при изменении текста. С другой стороны, вы перемещаете свой текст, когда пользователь перемещает полосы прокрутки и соответственно обновляет отображение. Производительность не должна быть проблемой для такого простого элемента управления.

Ответ 7

FastColoredTextBox проект на github имеет пример Консоль. Это:

  • Эффективный и быстрый
  • Цветное
  • Доступно в WPF и WinForm
  • В С# и легко читается

Я думаю, что чтение кода вам очень поможет.