Печать прямоугольников в терминал


Я пытаюсь написать текстовый редактор для Linux, который выглядит как MS-DOS EDIT.

Однако я застрял, потому что не могу понять, как нарисовать тонкие прямоугольники вокруг экрана редактора и диалогового окна. Я знаю, что команда Linux dialog может сделать что-то подобное:

Как я могу нарисовать такие прямоугольники вокруг экрана (желательно без проклятий)?

4 2

4 ответа:

┏━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┓
┃These are box-drawing characters.      ┃
┡━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┩
│They live in the U+2500-U+257F range of│
│Unicode characters.                    │
└───────────────────────────────────────┘

░▒▓▛▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▜▓▒░
░▒▓▌ The shadows are block elements, ▐▓▒░
░▒▓▌ Unicode U+2580-U+259F.          ▐▓▒░
░▒▓▙▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▟▓▒░

Когда-то коробочные символы и блочные элементы и были распространены в CP-437. Современные терминалы, скорее всего, ожидают UTF-8. (Они не очень хорошо работают в веб-браузерах... смотрите здесь , если приведенный выше текст выглядит странно.)

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

Библиотекаncurses - хороший способ сделать то, что вы хотите, хотя вы говорите, что хотите альтернативы. Вы можете использовать прямоугольник Unicode-рисование символов в качестве широких символов. Они включают в себя все символы кодовой страницы MS-DOS 437.

Современные дистрибутивы должны быть настроены на поддержку UTF-8 по умолчанию, так что это должно работать. (Я рекомендую сохранить исходный файл как UTF-8 с меткой порядка байтов.)
#define _XOPEN_SOURCE 700

#include <locale.h>
#include <stdio.h>
#include <stdlib.h>
#include <wchar.h>

int main(void)
{
  setlocale( LC_ALL, "" );
  fputws( L"╒╩╤╣\n", stdout );

  return EXIT_SUCCESS;
}

Без проклятий можно проверить переменные окружения LINES и COLS, чтобы получить размеры терминала. Управляющие символы для печати цветов и тому подобного на консоли Linux находятся в console_codes(4) man Страница (и являются вариантом управляющих кодов VT102, которые являются суперпозицией VT100, суперпозицией стандартных терминалов ANSI). Если вы хотите вызвать его из программы, такой как gnome_terminal, проверьте ее документацию тоже, но она, вероятно, будет реализовывать расширение xterm, которое является расширением VT102 и т. д. Один из них, который очень полезен, это то, что форма кормит характер '\L' очистит экран и позволит вам перерисовать его. Вы также можете использовать terminfo или termcap для более абстрактного и общего интерфейса, но на практике никто больше не использует ничего, кроме расширения цвета VT100 plus ANSI.

Убедитесь, что ваш шрифт терминала содержит символы рисования линий, которые вы хотите использовать! Дежавю Санс моно-отличный шрифт моноширинный, особенно для ее освещения в Юникоде. Кроме того, вы можете проверить, что ваш языковой стандарт установлен правильно с помощью locale команда; имена локалей, которые вы видите, должны заканчиваться чем-то вроде .utf8 или UTF-8.

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

Учитывая, что ваш вопрос помечен Linux, проще всего было бы использовать библиотеку ncurses . Почему вы предпочитаете не использовать его и должны изобрести это колесо?

Если вы можете ожидать, по крайней мере, эмуляции VT100 (разумно), то вы можете использовать базовый чертеж линии, но более высокие уровни имеют больше персонажей.

Это немного старый, но посмотрите на пример кода окна здесь:

Вы также можете заглянуть в xterm escape-символы (расширяет набор VT100):

Вы ищете символы для рисования в коробке. Вот полная таблица.

Предполагая, что в вашей системе установлен шрифт Unicode, что делают большинство современных дистрибутивов, вы можете распечатать их на своем терминале следующим образом:

#include <wchar.h>
#include <locale.h>
...
    setlocale(LC_ALL,"en_US.UTF-8");
    wprintf(L"\u250C\u2500\u2510\n");    // ┏━┓
    wprintf(L"\u2502 \u2502\n");         // │   │
    wprintf(L"\u2514\u2500\u2518\n");    // └━─┘