Files
Sprinter-SDCC/libc/bgi/_bgi_styled_line.c
T
snark13 b26560c409 libc: BGI Фаза 2d-2 — setlinestyle (стили и толщина линий)
setlinestyle/getlinesettings: SOLID/DOTTED/CENTER/DASHED/USERBIT +
NORM/THICK. _bgi_styled_line — Брезенхэм с 16-битной маской (пропуск
пикселя по биту) и дублированием ±1 перпендикулярно оси для THICK;
SOLID+NORM идёт быстрым путём (accel _bgi_lineseg). line/lineto/linerel/
rectangle/drawpoly переведены на него. Проверено в MAME (tests/bgitest).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-08 16:14:03 +03:00

59 lines
1.9 KiB
C

/*
* _bgi_styled_line — отрезок текущим стилем и толщиной линии.
*
* SOLID+NORM → быстрый _bgi_lineseg (accel). Иначе — Брезенхэм с
* 16-битной маской (бит на шаг; когда бит 0 — пропуск) и, для THICK,
* дублированием перпендикулярно основной оси (±1). Всё raw в одной
* W3-скобке.
*/
#include "_bgi.h"
/* Маски стандартных стилей (SOLID/DOTTED/CENTER/DASHED). */
static const uint16_t _bgi_line_pat[4] = { 0xFFFF, 0xCCCC, 0xFF18, 0xF8F8 };
void _bgi_styled_line(int x0, int y0, int x1, int y1, uint8_t color)
{
uint16_t pat;
uint8_t bit, style, thick;
int dx, dy, sx, sy, err, e2, major_x;
style = _bgi_line_style;
thick = _bgi_line_thick;
if (style == SOLID_LINE && thick <= 1) {
_bgi_lineseg(x0, y0, x1, y1, color);
return;
}
pat = (style == USERBIT_LINE) ? _bgi_line_pattern
: _bgi_line_pat[style & 3];
dx = x1 - x0; if (dx < 0) dx = -dx;
dy = y1 - y0; if (dy < 0) dy = -dy;
sx = (x0 < x1) ? 1 : -1;
sy = (y0 < y1) ? 1 : -1;
err = dx - dy;
major_x = (dx >= dy);
bit = 0;
_bgi_begin();
for (;;) {
if ((pat >> (bit & 15)) & 1) {
_bgi_plot_raw(x0, y0, color);
if (thick > 1) {
if (major_x) {
_bgi_plot_raw(x0, y0 - 1, color);
_bgi_plot_raw(x0, y0 + 1, color);
} else {
_bgi_plot_raw(x0 - 1, y0, color);
_bgi_plot_raw(x0 + 1, y0, color);
}
}
}
bit++;
if (x0 == x1 && y0 == y1) break;
e2 = 2 * err;
if (e2 > -dy) { err -= dy; x0 += sx; }
if (e2 < dx) { err += dx; y0 += sy; }
}
_bgi_end();
}