Таблица

При построении приложения консоли может быть полезным отображать данные в табличном виде:

1
2
3
4
5
6
7
8
+---------------+--------------------------+------------------+
| ISBN          | Название                 | Автор            |
+---------------+--------------------------+------------------+
| 99921-58-10-7 | Божественная комедия     | Данте Алигьери   |
| 9971-5-0210-0 | Рассказ о двух городах   | Чарльз Дикенс    |
| 960-425-059-0 | Властелин колец          | Дж. Р. Р. Толкиен|
| 80-902734-1-6 | И никого не стало        | Агата Кристи     |
+---------------+--------------------------+------------------+

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

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
use Symfony\Component\Console\Helper\Table;
// ...

class SomeCommand extends Command
{
    public function execute(InputInterface $input, OutputInterface $output)
    {
        $table = new Table($output);
        $table
            ->setHeaders(array('ISBN', 'Название', 'Автор'))
            ->setRows(array(
                array('99921-58-10-7', 'Божественная комедия', 'Данте Алигьери'),
                array('9971-5-0210-0', 'Рассказ о двух городах', 'Чарльз Дикенс'),
                array('960-425-059-0', 'Властелин колец', 'Дж. Р. Р. Толкиен'),
                array('80-902734-1-6', 'И никого не стало', 'Агата Кристи'),
            ))
        ;
        $table->render();
    }
}

Вы можете добавлять разделитель таблицы где-угодно в выводе, передав экземпляр TableSeparator в качестве строки:

1
2
3
4
5
6
7
8
9
use Symfony\Component\Console\Helper\TableSeparator;

$table->setRows(array(
    array('99921-58-10-7', 'Божественная комедия', 'Данте Алигьери'),
    array('9971-5-0210-0', 'Рассказ о двух городах', 'Чарльз Дикенс'),
    new TableSeparator(),
    array('960-425-059-0', 'Властелин колец', 'Дж. Р. Р. Толкиен'),
    array('80-902734-1-6', 'И никого не стало', 'Агата Кристи'),
));
1
2
3
4
5
6
7
8
9
+---------------+--------------------------+------------------+
| ISBN          | Название                 | Автор            |
+---------------+--------------------------+------------------+
| 99921-58-10-7 | Божественная комедия     | Данте Алигьери   |
| 9971-5-0210-0 | Рассказ о двух городах   | Чарльз Дикенс    |
+---------------+--------------------------+------------------+
| 960-425-059-0 | Властелин колец          | Дж. Р. Р. Толкиен|
| 80-902734-1-6 | И никого не стало        | Агата Кристи     |
+---------------+--------------------------+------------------+

По умолчанию, ширина столбцов вычисляется автоматически, основываясь на их содержании. Используйте метод setColumnWidths(), чтобы ясно установить ширину столбцов:

1
2
3
// ...
$table->setColumnWidths(array(10, 0, 30));
$table->render();

В этом примере, ширина первого столбца будет 10, последнего - 30, а ширина второго будет вычисляться автоматически, в связи со значением 0. Выводом этой команды будет:

1
2
3
4
5
6
7
8
9
+---------------+--------------------------+--------------------------------+
| ISBN          | Название                 | Автор                          |
+---------------+--------------------------+--------------------------------+
| 99921-58-10-7 | Божественная комедия     | Данте Алигьери                 |
| 9971-5-0210-0 | Рассказ о двух городах   | Чарльз Дикенс                  |
+---------------+--------------------------+--------------------------------+
| 960-425-059-0 | Властелин колец          | Дж. Р. Р. Толкиен              |
| 80-902734-1-6 | И никого не стало        | Агата Кристи                   |
+---------------+--------------------------+--------------------------------+

Заметьте, что определённая ширина столбцов всегда воспринимается, как минимальная ширина столбца. Если содержание не помещается, заданная ширина будет увеличена до максимальной длины содержания. Поэтому в предыдущем примере первый столбец имеет ширину в 13 знаков, хотя пользователь определил 10.

Вы также можете устанавливать ширину индивидуально для каждого столбца с помощью метода setColumnWidth(). Его первым аргументом будет индекс столбца (начиная с 0), а вторым - ширина столбца:

1
2
3
4
// ...
$table->setColumnWidth(0, 10);
$table->setColumnWidth(2, 30);
$table->render();

Стиль таблицы может быть изменён на любой встроенный стиль через setStyle():

1
2
3
4
5
6
// то же самое, что ничего не вызывать
$table->setStyle('default');

// изменяет стиль по умолчанию на компактный
$table->setStyle('compact');
$table->render();

Этот код приводит к:

1
2
3
4
5
ISBN          Название                 Автор
99921-58-10-7 Божественная комедия     Данте Алигьери
9971-5-0210-0 Рассказ о двух городах   Чарльз Дикенс
960-425-059-0 Властелин колец          Дж. Р. Р. Толкиен
80-902734-1-6 И никого не стало        Агата Кристи

Вы также можете установить стиль borderless:

1
2
$table->setStyle('borderless');
$table->render();

Что выведет:

1
2
3
4
5
6
7
8
=============== ========================== ==================
 ISBN            Название                   Автор
=============== ========================== ==================
 99921-58-10-7   Божественная комедия       Данте Алигьери
 9971-5-0210-0   Рассказ о двух городах     Чарльз Дикенс
 960-425-059-0   Властелин колец            Дж. Р. Р. Толкиен
 80-902734-1-6   И никого не стало          Агата Кристи
=============== ========================== ==================

Вы также можете установить стиль box:

1
2
$table->setStyle('box');
$table->render();

Что выведет:

1
2
3
4
5
6
7
8
┌───────────────┬──────────────────────────┬──────────────────┐
│ ISBN          │ Название                 │ Автор            │
├───────────────┼──────────────────────────┼──────────────────┤
│ 99921-58-10-7 │ Божественная комедия     │ Данте Алигьери   │
│ 9971-5-0210-0 │ Рассказ о двух городах   │ Чарльз Дикенс    │
│ 960-425-059-0 │ Властелин колец          │ Дж. Р. Р. Толкиен│
│ 80-902734-1-6 │ И никого не стало        │ Агата Кристи     │
└───────────────┴──────────────────────────┴──────────────────┘

New in version 4.1: Стиль box был представлен в Symfony 4.1.

Вы также можете установить стиль box-double:

1
2
$table->setStyle('box-double');
$table->render();

Что выведет:

1
2
3
4
5
6
7
8
╔═══════════════╤══════════════════════════╤══════════════════╗
║ ISBN          │ Название                 │ Автор            ║
╠═══════════════╪══════════════════════════╪══════════════════╣
║ 99921-58-10-7 │ Божественная комедия     │ Данте Алигьери   ║
║ 9971-5-0210-0 │ Рассказ о двух городах   │ Чарльз Дикенс    ║
║ 960-425-059-0 │ Властелин колец          │ Дж. Р. Р. Толкиен║
║ 80-902734-1-6 │  И никого не стало       │ Агата Кристи     ║
╚═══════════════╧══════════════════════════╧══════════════════╝

New in version 4.1: Стиль box-double был представлен в Symfony 4.1.

Если встроенные стили не соответствуют вашим нуждам, определите свой собственный:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
use Symfony\Component\Console\Helper\TableStyle;

// по умолчанию, базируется на стиле по умолчанию
$tableStyle = new TableStyle();

// настраивает стиль
$tableStyle
    ->setDefaultCrossingChars('<fg=magenta>|</>')
    ->setVerticalBorderChars('<fg=magenta>-</>')
    ->setDefaultCrossingChar(' ')
;

// использует стиль по умолчанию для этой таблицы
$table->setStyle($tableStyle);

Вот полный список того, что вы можете настроить:

New in version 4.1: Метод setDefaultCrossingChars был представлен в Symfony 4.1. Он замещает устаревший метод setHorizontalBorderChar.

Также, был представлен метод setVerticalBorderChars. Используйте его вместо устаревшего метода setVerticalBorderChar.

Методы setCrossingChars() и setDefaultCrossingChar() также новые. Ранее вы могли использовать только уже устаревший метод setCrossingChar().

Tip

Вы также можете зарегистрировать стиль глобально:

1
2
3
4
5
// регистрирует стиль под цветным названием
Table::setStyleDefinition('colorful', $tableStyle);

// применяет пользовательский стиль для заданной таблицы
$table->setStyle('colorful');

Этот метод также может быть использован для переопределения встроенного стиля.

Объединение нескольких столбцов и строк

Чтобы сделать ячейку таблицы, объединяющую несколько столбцов, вы можете использовать TableCell:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
use Symfony\Component\Console\Helper\Table;
use Symfony\Component\Console\Helper\TableSeparator;
use Symfony\Component\Console\Helper\TableCell;

$table = new Table($output);
$table
    ->setHeaders(array('ISBN', 'Название', 'Автор'))
    ->setRows(array(
        array('99921-58-10-7', 'Божественная комедия', 'Данте Алигьери'),
        new TableSeparator(),
        array(new TableCell('Это значение объединяет три столбца.', array('colspan' => 3))),
    ))
;
$table->render();

Это приводит к:

1
2
3
4
5
6
7
+---------------+----------------------+-----------------+
| ISBN          | Название             | Автор           |
+---------------+----------------------+-----------------+
| 99921-58-10-7 | Божественная комедия | Данте Алигьери  |
+---------------+----------------------+-----------------+
| Это значение объединяет 3 столбца.                     |
+---------------+----------------------+-----------------+

Tip

Вы можете создать название страницы в несколько строк, используя ячейку, объединяющую всю ширину таблицы:

1
2
3
4
5
$table->setHeaders(array(
    array(new TableCell('Главное название таблицы', array('colspan' => 3))),
    array('ISBN', 'Название', 'Автор'),
))
// ...

Это генерирует:

1
2
3
4
5
6
7
+-------+----------+--------+
| Главное название таблицы  |
+-------+----------+--------+
| ISBN  | Название | Автор  |
+-------+----------+--------+
| ...                       |
+-------+----------+--------+

Схожим образом вы можете объединять несколько рядов:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
use Symfony\Component\Console\Helper\Table;
use Symfony\Component\Console\Helper\TableCell;

$table = new Table($output);
$table
    ->setHeaders(array('ISBN', 'Название', 'Автор'))
    ->setRows(array(
        array(
            '978-0521567817',
            'De Monarchia',
            new TableCell("Данте Алигьери\nspans multiple rows", array('rowspan' => 2)),
        ),
        array('978-0804169127', 'Divine Comedy'),
    ))
;
$table->render();

Это выводит:

1
2
3
4
5
6
+----------------+----------------------+----------------------------+
| ISBN           | Название             | Автор                      |
+----------------+----------------------+----------------------------+
| 978-0521567817 | Монархия             | Данте Алигьери             |
| 978-0804169127 | Божественная комедия | объединяет несколько строк |
+----------------+----------------------+----------------------------+

Вы можете использовать опции colspan и rowspan одновременно, что позволяет вам создавать любой желаемый макет таблицы.

Изменение отображённых таблиц

New in version 4.1: Функция изменять отображённые таблицы была представлена в Symfony 4.1.

Метод render() требует передачи всего содержания таблицы. Однако, иногда эта информация недоступна заранее, так как она генерируется динамически. В таких случаях, используйте метод appendRow(), который берёт те же аргументы, что и метод addRow(), чтобы добавить ряды внизу уже отображённой таблицы.

Единственным требованием для добавления рядов является отображение таблицы внутри Раздела вывода Console:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
use Symfony\Component\Console\Helper\Table;
// ...

class SomeCommand extends Command
{
    public function execute(InputInterface $input, OutputInterface $output)
    {
        $section = $output->section();
        $table = new Table($section);

        $table->addRow(['Row 1']);
        $table->render();

        $table->addRow(['Row 2']);
    }
}

Это отобразит следующую таблицу в терминале:

1
2
3
4
+-------+
| Ряд 1 |
| Ряд 2 |
+-------+

Эта документация является переводом официальной документации Symfony и предоставляется по свободной лицензии CC BY-SA 3.0.