Содержание урока · 10 разделов
Рамки — та часть оформления, которую замечают только когда её нет. На экране отчёт с зеброй и синей шапкой выглядит законченным, но один лист на чёрно-белом принтере — и колонки слипаются: заливка пропечаталась серым пятном, а держать строку глазами не за что. Границы решают именно эту задачу: линии задают таблице структуру, которая переживает и печать, и пересылку в другие программы. Хорошая новость: новая механика не понадобится. Рамки ячеек go-код собирает из той же подсистемы стилей, что шрифты и заливки: то же NewStyle, тот же идентификатор и SetCellStyle из урока про стили ячеек, только в структуре Style заполняется ещё одно поле — срез Borders. Разберём его по частям: типы линий, каталог стилей, комбинирование рамки с сеткой и один приём, который превращает прямоугольник диапазона в таблицу одним вызовом.
Excelize границы: структура Border по сторонам#
Поле Borders в структуре Style — это срез структур excelize.Border, и запрос excelize границы упирается в одну схему: на каждую линию — свой элемент среза. У элемента три поля. Type говорит, на какой стороне ячейки рисовать: top, bottom, left, right, а заодно diagonalDown и diagonalUp — диагонали из угла в угол. Style — вид линии строкой из каталога Excel, от тонкой thin до двойной double, полный разбор в следующем разделе. Color — строка вида #RRGGBB с решёткой, как у шрифтов. Срез — не избыточность, а честность: ячейка xlsx вправе нести до шести линий одновременно, по числу сторон и диагоналей, и API отражает это массивом вместо шести отдельных полей. Внутри файла границы живут в xl/styles.xml таблицей borders рядом с шрифтами и заливками; одинаковые комбинации схлопываются в одну запись, поэтому сетка на пятьсот ячеек не распухает файл. Ошибку NewStyle вернёт на кривом цвете или несуществующем стиле линии — проверка err здесь такой же рабочий инструмент, как и в стилях.
Шесть значений Border.Type#
| Значение | Где рисует линия | Когда пригодится |
|---|---|---|
| top | над ячейкой | верхняя граница шапки и итоговой строки |
| bottom | под ячейкой | отделение шапки от данных, линия под итогом |
| left | слева от ячейки | левый край таблицы и колонка наименований |
| right | справа от ячейки | правый край и отделение колонки итогов |
| diagonalDown | из левого верхнего угла в правый нижний | перечёркнутые позиции в актах и ведомостях |
| diagonalUp | из левого нижнего угла в правый верхний | крест-накрест вместе с diagonalDown |
Шапка с рамкой одним стилем
GOstyle, err := f.NewStyle(&excelize.Style{
Font: &excelize.Font{
Bold: true,
Color: "#FFFFFF",
},
Fill: excelize.Fill{
Type: "pattern",
Pattern: 1,
Color: []string{"#4472C4"},
},
Alignment: &excelize.Alignment{
Horizontal: "center",
Vertical: "center",
},
Borders: []excelize.Border{
{Type: "top", Style: "medium", Color: "#2F5597"},
{Type: "bottom", Style: "medium", Color: "#2F5597"},
{Type: "left", Style: "medium", Color: "#2F5597"},
{Type: "right", Style: "medium", Color: "#2F5597"},
},
})
if err != nil {
panic(err)
}
if err := f.SetCellStyle("Отчёт", "A1", "D1", style); err != nil {
panic(err)
}Полный стиль из прошлых уроков плюс четыре линии одним цветом — тёмным оттенком заливки. Четыре элемента в срезе Borders закрывают все стороны шапки; всё оформление живёт в одной структуре Style, потому что следующий SetCellStyle заменит его целиком.
Стили линий: от hair до double#
Поле Style у Border — строка, и её значения — каталог линий Excel из спецификации xlsx. Базовый набор короткий: none — линии нет, hair — самая тонкая, thin — тонкая сплошная, medium — средняя, thick — толстая, dashed и dotted — штрих и точки, double — двойная. Есть и составные: mediumDashed, dashDot, mediumDashDotDot, slantDashDot — в деловых отчётах они встречаются реже диагоналей, но в спецификации живут, и Excel рисует их честно. Практика выбора укладывается в три правила: сетке данных — thin; внешней рамке, шапке и разделителям секций — medium; итоговой строке сверху — double по бухгалтерской традиции. Цвет от толщины не зависит: серый #999999 вместо чёрного превращает сетку в фон, который не спорит с текстом, а красная medium на отрицательном итоге читается как тревога — акцент без единого условного правила. Толстые линии на каждой ячейке не поднимайте: отчёт рискует стать клетчатой бумагой из блокнота.
Стили линий, которые встречаются в отчётах#
| Style | Как выглядит | Где уместно |
|---|---|---|
| none | линии нет | снять границу на конкретной стороне |
| hair | самая тонкая | вспомогательные разделители внутри блока |
| thin | тонкая сплошная | сетка данных — основной выбор |
| medium | средняя | рамка шапки, итоговой строки, секций |
| thick | толстая | акцентный контур, внешняя рамка годового отчёта |
| dashed | штриховая | плановые значения, черновые блоки |
| dotted | точечная | служебные колонки, лёгкое разделение |
| double | двойная | итоговая строка по бухгалтерской традиции |
Комбинирование: сетка диапазона и рамка шапки#
Срез Borders принимает сколько угодно линий, и здесь проступает главный приём темы: сетка диапазона строится одним стилем. Логика простая — если каждой ячейке прямоугольника дать все четыре линии, соседние линии совпадут, и на экране это выглядит как единая сетка. Excel рисует совпадающие края друг на друге; при одинаковых Style и Color артефактов нет, а вот смешивать толщины на одном стыке не стоит: тонкая и средняя линии на общей границе выглядят рвано. Отсюда правило одной толщины внутри блока: выбрали thin — держите thin во всём прямоугольнике. Внешнюю рамку потолще делают вторым проходом: отдельный стиль, у которого внешняя сторона medium, а внутренние линии остаются thin, прикладывается к крайним строкам и колонкам. Это два стиля и несколько вызовов SetCellStyle — оба создаются до цикла, и правила урока про excelize стили работают без изменений: идентификаторы переиспользуются, в styles.xml лежат две записи вместо пятисот.
Сетка диапазона одним вызовом
GOgrid, err := f.NewStyle(&excelize.Style{
Borders: []excelize.Border{
{Type: "top", Style: "thin", Color: "#999999"},
{Type: "bottom", Style: "thin", Color: "#999999"},
{Type: "left", Style: "thin", Color: "#999999"},
{Type: "right", Style: "thin", Color: "#999999"},
},
})
if err != nil {
panic(err)
}
if err := f.SetCellStyle("Отчёт", "A2", "D500", grid); err != nil {
panic(err)
}Один стиль на пятьсот ячеек: каждая получает четыре тонкие линии, совпадающие края соседей рисуются друг на друге и выглядят сплошной сеткой. Идентификатор создан до применения — в файле одна запись границы вместо тысячи, а сетка растёт вместе с диапазоном без правок кода.
SetCellStyle перезаписывает оформление ячейки целиком: рамочный стиль без шрифта и заливки сотрёт и их. Классическая жертва — команде понадобилось «добавить рамку к данным», применили стиль только с Borders и потеряли формат цен и зебру. Линии не добавляются к прежнему оформлению: собирайте один стиль со всеми свойствами сразу или перечитывайте GetCellStyle и пересобирайте полное описание.
Диагонали и края диапазона#
Диагонали — редкие гости, но знать их стоит: diagonalDown ведёт линию из левого верхнего угла в правый нижний, diagonalUp — из левого нижнего в правый верхний, вместе они дают крест-накрест. В актах сверки и инвентаризации перечёркнутые позиции рисуют именно диагональю, потому что зачёркивание Strike из урока про стили видно только на тексте, а диагональ перечёркивает и пустую ячейку, и число. Края диапазона при приёме «четыре линии каждой ячейке» получаются той же толщины, что и внутренняя сетка, — и это хорошо: единый контур без исключений. Если макет требует среднюю линию только по внешнему периметру, соберите второй стиль с medium на внешних сторонах и приложите его к крайним строкам и колонкам диапазона. И помните про шов: соседние ячейки делят границу, Excel рисует обе линии стыка, поэтому параметры совпадающих краёв держите одинаковыми, иначе на общем ребре появится рваный стык из двух разных линий.
Чек-лист границ#
- Borders — срез excelize.Border в структуре Style: одна линия — один элемент среза.
- Type — сторона линии: top, bottom, left, right и диагонали diagonalDown, diagonalUp.
- Style — вид линии: thin для сетки, medium для рамки, double для итоговой строки.
- Color — hex с решёткой: серый #999999 делает сетку фоном, не спорящим с текстом.
- Сетка диапазона — один стиль с четырьмя линиями на весь прямоугольник, без циклов.
- Стиль заменяет оформление целиком: шрифт, заливка, формат и границы живут вместе.
NewStyle и SetCellStyle работают с книгой, которая пишется на диск, поэтому в браузерной песочнице не запускаются: там доступны только fmt, strings, strconv, math, sort, errors и time без файлового ввода-вывода. Структуру Border и сетку стилей соберите локально и посмотрите результат в Excel или LibreOffice; интерактивы на этой странице работают без файлов.
Кейс про прайс-лист на чёрно-белом принтере. Отчёт поставщика ходил между офисами в PDF, и на цветном экране всё читалось, а на распечатке секретаря колонки слипались: серая зебра печаталась пятном, глазами держать строку было нечем. Починили одним стилем: сетка thin серым #999999 на весь диапазон данных, шапке добавили medium сверху и снизу, итоговой строке — double. Печать стала читаемой без единого нового цикла: один NewStyle до цикла, один SetCellStyle на диапазон, пара вызовов на шапку и итог. Спорная часть: границ нужны не всем файлам. Выгрузка, которую завтра загрузят в другую систему, живёт без линий вообще — там важнее сырые значения из урока про чтение ячеек; рамки — интерфейс для глаз, и на файлах для машин они только распухают стили. Решение принимает потребитель файла, а не вкус разработчика.
Проверка: устройство Border
Что описывает один элемент среза Borders в структуре Style?
Проверка: замена стиля
К данным с серой зеброй применили стиль, в котором только Borders. Что станет с зеброй?
Что получит сосед снизу?
Прочитайте код и выберите, что он выведет:
style, _ := f.NewStyle(&excelize.Style{
Borders: []excelize.Border{
{Type: "bottom", Style: "thin", Color: "#000000"},
},
})
f.SetCellStyle("Sheet1", "A1", "C1", style)
// ячейка B2 стоит сразу под B1Соберите левую границу колонки
Допишите срез границ, тип линии, её вид и применение к диапазону.
Соберите рамку итоговой строки
Расставьте строки в порядке выполнения: описать линию итога, собрать стиль, проверить ошибку, приложить к строке итога, прочитать идентификатор стиля, напечатать его.
Строки
Ваша программа
Нажимайте на строки слева, чтобы собрать программу
Карточки: границы и рамки
Границы достроили стиль: в одной структуре Style теперь живут шрифт и заливка из урока про стили ячеек, форматы чисел из урока про NumFmt и CustomNumFmt и срез Borders отсюда. Следующий шаг — геометрия: в уроке про слияние ячеек и ширину столбцов рамка шапки встретится с MergeCell, и станет ясно, почему стиль прикладывают ко всему объединённому блоку. Готовая схема «данные, оформление, размеры» собирается в шаблоне экспорта отчёта из базы, а типичные перекосы оформления разобраны в уроке про ошибки excelize. Домашнее задание — одеть свой отчёт в сетку и рамки.
Песочница урока
Редактируйте код и запускайте его прямо здесь — интерпретатор работает в браузере, ничего устанавливать не нужно. За каждый запуск — +2 XP.
Запустите код, чтобы увидеть вывод.
Коротко: что запомнить
- Borders — срез excelize.Border в структуре Style: каждая линия — отдельный элемент.
- Border.Type — сторона: top, bottom, left, right, плюс диагонали diagonalDown и diagonalUp.
- Border.Style — вид линии: thin для сетки, medium для рамки, double для итоговой строки.
- Border.Color — hex с решёткой; серый #999999 мягче чёрного на печати.
- Сетка диапазона — один стиль с четырьмя линиями на весь прямоугольник.
- Стиль заменяет оформление целиком: шрифт, заливка, формат и границы живут вместе.
Домашнее задание
Возьмите свой отчёт из прошлых уроков: добавьте данным сетку тонкими линиями серого цвета одним стилем, шапке — medium по верхней и нижней стороне, итоговой строке — double сверху. Проверьте GetCellStyle, что стиль применился, и распечатайте страницу: сетка должна делить колонки и не спорить с текстом.
Личные заметкиПусто
Вопросы и ответы по уроку
Можно ли добавить рамку к уже оформленной ячейке вторым стилем?
Нет: SetCellStyle заменяет оформление целиком, и рамочный стиль без шрифта и заливки их сотрёт. Соберите один стиль со всеми свойствами — Font, Fill, NumFmt и Borders вместе — и применяйте его одним вызовом SetCellStyle.
Почему на стыке двух ячеек линия выглядит рвано?
Соседние ячейки получили линии разной толщины или цвета, и Excel рисует оба края стыка. Держите одинаковые Style и Color у совпадающих границ или задайте сетку одним стилем на весь диапазон — тогда шов не проявится.
Существует ли метод вроде SetBorder для одной стороны?
Нет: границы — часть стиля, а стиль хранится записью в styles.xml. Каждая линия — отдельный элемент среза Borders с полями Type, Style и Color; стиль собирается NewStyle и прикладывается SetCellStyle к диапазону.
Термины урока
Ключевые понятия из этого урока — короткие определения в глоссарии. Наведите на термин, чтобы вспомнить, откройте карточку для подробностей и ссылки на практику.
Изучайте дальше
Следующая ступень учебного пути
Фоновые задачи в Go: планировщик на robfig/cron
Курс по cron в Go: robfig/cron v3, синтаксис выражений, пояса, wrappers, конкурентность и graceful shutdown. 25 уроков с примерами и проектом.
- Собирать планировщик на robfig/cron v3 и запускать задачи по расписанию
- Читать и писать cron-выражения: пять полей, спецсимволы, @daily
- Управлять жизненным циклом: Start, Stop, Entry, Remove
- Держать часовые пояса и секундные расписания под контролем