Add option to uniform line drawing in scaled mode (#167)

This commit is contained in:
Matthias Melcher
2025-11-01 14:33:06 +01:00
parent d14bd1bfec
commit ccbb424046
3 changed files with 18 additions and 3 deletions

View File

@@ -229,6 +229,16 @@ inline void fl_point(int x, int y) {
array results in a solid line. Odd array sizes are not supported
and result in undefined behavior.
In scaled mode, horizontal and vertical lines are drawn with different line
widths, depending on the position of the line on screen, to adapt for gaps
when drawing adjacent lines. Setting \c FL_UNIFORM_WIDTH will make all lines
the same width, regardless of their position. This improves line drawings,
but may produce small gaps when drawing gradients or filling areas.
\note When changing the line style inside a `draw()` method, make sure to
reset the line styles by calling \c fl_line_style(0) at the end of a
drawing routine or FLTK frame and box drawing will fail.
\note Because of how line styles are implemented on Win32 systems,
you \e must set the line style \e after setting the drawing
color. If you set the color after the line style you will lose
@@ -260,7 +270,9 @@ enum {
FL_JOIN_MITER = 0x1000, ///< join style: line join extends to a point
FL_JOIN_ROUND = 0x2000, ///< join style: line join is rounded
FL_JOIN_BEVEL = 0x3000 ///< join style: line join is tidied
FL_JOIN_BEVEL = 0x3000, ///< join style: line join is tidied
FL_UNIFORM_WIDTH = 0x10000 ///< use uniform line width, even in scaled contexts
};
/**

View File

@@ -799,6 +799,7 @@ Fl_Font_Descriptor::Fl_Font_Descriptor(const char* name, Fl_Fontsize Size) {
}
Fl_Scalable_Graphics_Driver::Fl_Scalable_Graphics_Driver() : Fl_Graphics_Driver() {
line_style_ = 0;
line_width_ = 0;
fontsize_ = -1;
is_solid_ = true;
@@ -850,7 +851,7 @@ void Fl_Scalable_Graphics_Driver::xyline(int x, int y, int x1) {
float s = scale(); int s_int = int(s);
int xx = (x < x1 ? x : x1);
int xx1 = (x < x1 ? x1 : x);
if (s != s_int && line_width_ <= s_int) {
if ( (s != s_int) && (line_width_ <= s_int) && !(line_style_ & FL_UNIFORM_WIDTH) ) {
int lwidth = this->floor((y+1)) - this->floor(y);
bool need_change_width = (lwidth != s_int && is_solid_);
void *data = NULL;
@@ -870,7 +871,7 @@ void Fl_Scalable_Graphics_Driver::yxline(int x, int y, int y1) {
float s = scale(); int s_int = int(s);
int yy = (y < y1 ? y : y1);
int yy1 = (y < y1 ? y1 : y);
if (s != s_int && line_width_ <= s_int) {
if ( (s != s_int) && (line_width_ <= s_int) && !(line_style_ & FL_UNIFORM_WIDTH)) {
int lwidth = (this->floor((x+1)) - this->floor(x));
bool need_change_width = (lwidth != s_int && is_solid_);
void *data = NULL;
@@ -1051,6 +1052,7 @@ void Fl_Scalable_Graphics_Driver::draw_circle(int x0, int y0, int d, Fl_Color c)
void Fl_Scalable_Graphics_Driver::line_style(int style, int width, char* dashes) {
line_style_ = style;
if (width == 0) line_width_ = int(scale() < 2 ? 0 : scale());
else line_width_ = int(width>0 ? width*scale() : -width*scale());
is_solid_ = ((style & 0xff) == FL_SOLID && (!dashes || !*dashes));

View File

@@ -43,6 +43,7 @@ public:
static int floor(int x, float s);
inline int floor(int x) { return Fl_Scalable_Graphics_Driver::floor(x, scale()); }
protected:
int line_style_;
int line_width_;
bool is_solid_;
Fl_Scalable_Graphics_Driver();