diff options
| author | Manolo Gouy <Manolo> | 2017-06-27 12:17:29 +0000 |
|---|---|---|
| committer | Manolo Gouy <Manolo> | 2017-06-27 12:17:29 +0000 |
| commit | 7f15c3010c4bca0e1e8598dd12a6bc637c10f8e6 (patch) | |
| tree | da6ace2faa96ef49472495d54a5b19293e63bc47 /src/drivers/GDI | |
| parent | 7fbf318c53bc194919cf518536e108bc75edaa80 (diff) | |
WIN32 platform: more progress for full HiDPI support
git-svn-id: file:///fltk/svn/fltk/branches/branch-1.4@12273 ea41ed52-d2ee-0310-a9c1-e6b18d33e121
Diffstat (limited to 'src/drivers/GDI')
| -rw-r--r-- | src/drivers/GDI/Fl_GDI_Graphics_Driver.H | 2 | ||||
| -rw-r--r-- | src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx | 48 | ||||
| -rw-r--r-- | src/drivers/GDI/Fl_GDI_Graphics_Driver_color.cxx | 29 | ||||
| -rw-r--r-- | src/drivers/GDI/Fl_GDI_Graphics_Driver_line_style.cxx | 6 | ||||
| -rw-r--r-- | src/drivers/GDI/Fl_GDI_Graphics_Driver_rect.cxx | 53 |
5 files changed, 88 insertions, 50 deletions
diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver.H b/src/drivers/GDI/Fl_GDI_Graphics_Driver.H index 0ab48418b..a491a18aa 100644 --- a/src/drivers/GDI/Fl_GDI_Graphics_Driver.H +++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver.H @@ -89,7 +89,7 @@ public: void XDestroyRegion(Fl_Region r); void translate_all(int x, int y); void untranslate_all(void); - static HRGN scale_region(HRGN r, float f, Fl_GDI_Graphics_Driver *dr, bool keep/*, bool inflate=false*/); + static HRGN scale_region(HRGN r, float f, Fl_GDI_Graphics_Driver *dr); virtual void scale(float f); virtual float scale(); protected: diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx b/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx index 41948b83a..9ef0c67a0 100644 --- a/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx +++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver.cxx @@ -232,7 +232,7 @@ void Fl_GDI_Graphics_Driver::scale(float f) { if (f != scale_) { size_ = 0; scale_ = f; - //line_style(FL_SOLID); // scale also default line width +//fprintf(LOG,"set scale to %f\n",f);fflush(LOG); } } @@ -242,45 +242,35 @@ float Fl_GDI_Graphics_Driver::scale() { /* Rescale region r with factor f and returns the scaled region. - The input region is deleted if keep is false. - //The input region is inflated by 1 unit before rescaling if inflate is true. Region r is returned unchanged if r is null or f is 1. + The input region is deleted if dr is null. */ -HRGN Fl_GDI_Graphics_Driver::scale_region(HRGN r, float f, Fl_GDI_Graphics_Driver *dr, bool keep/*, bool inflate*/) { +HRGN Fl_GDI_Graphics_Driver::scale_region(HRGN r, float f, Fl_GDI_Graphics_Driver *dr) { if (r && f != 1) { DWORD size = GetRegionData(r, 0, NULL); RGNDATA *pdata = (RGNDATA*)malloc(size); GetRegionData(r, size, pdata); - if (!keep) DeleteObject(r); - /*if (inflate) { // seems no longer useful - RECT *rects = (RECT*)&(pdata->Buffer); - for (DWORD i = 0; i < pdata->rdh.nCount; i++) { - InflateRect(rects+i, 1, 1); - } - }*/ + if (!dr) DeleteObject(r); POINT pt = {0, 0}; - if (dr && dr->depth >= 1) { // account for both scaling and translation + if (dr && dr->depth >= 1) { // account for translation GetWindowOrgEx((HDC)dr->gc(), &pt); pt.x *= (f - 1); pt.y *= (f - 1); } - XFORM xform = {f, 0, 0, f, (FLOAT)pt.x , (FLOAT)pt.y}; - r = ExtCreateRegion(&xform, size, pdata); - free(pdata); - - if (dr && int(f) != f && f > 1) { // needed for clean checkers demo - DWORD size = GetRegionData(r, 0, NULL); - RGNDATA *pdata = (RGNDATA*)malloc(size); - GetRegionData(r, size, pdata); - DeleteObject(r); - RECT *rects = (RECT*)&(pdata->Buffer); - for (DWORD i = 0; i < pdata->rdh.nCount; i++) { - InflateRect(rects+i, 1, 1); - } - r = ExtCreateRegion(NULL, size, pdata); - free(pdata); + RECT *rects = (RECT*)&(pdata->Buffer); + int delta = (f > 1.75 ? 1 : 0) - int(f/2); + for (DWORD i = 0; i < pdata->rdh.nCount; i++) { + int x = rects[i].left * f + pt.x; + int y = rects[i].top * f + pt.y; + RECT R2; + R2.left = x + delta; + R2.top = y + delta; + R2.right = int(rects[i].right * f) + pt.x - x + R2.left; + R2.bottom = int(rects[i].bottom * f) + pt.y - y + R2.top; + rects[i] = R2; } - + r = ExtCreateRegion(NULL, size, pdata); + free(pdata); } return r; } @@ -288,7 +278,7 @@ HRGN Fl_GDI_Graphics_Driver::scale_region(HRGN r, float f, Fl_GDI_Graphics_Drive Fl_Region Fl_GDI_Graphics_Driver::scale_clip(float f) { HRGN r = rstack[rstackptr]; - HRGN r2 = scale_region(r, f, this, true); + HRGN r2 = scale_region(r, f, this); return (r == r2 ? NULL : (rstack[rstackptr] = r2, r)); } diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver_color.cxx b/src/drivers/GDI/Fl_GDI_Graphics_Driver_color.cxx index 064205345..584a7f47e 100644 --- a/src/drivers/GDI/Fl_GDI_Graphics_Driver_color.cxx +++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver_color.cxx @@ -75,7 +75,7 @@ static void clear_xmap(Fl_XMap& xmap) { } } -static void set_xmap(Fl_XMap& xmap, COLORREF c) { +static void set_xmap(Fl_XMap& xmap, COLORREF c, int lw) { xmap.rgb = c; if (xmap.pen) { HDC gc = (HDC)fl_graphics_driver->gc(); @@ -83,7 +83,12 @@ static void set_xmap(Fl_XMap& xmap, COLORREF c) { if (oldpen != xmap.pen)SelectObject(gc,oldpen); // if old one not xmap.pen, need to put it back DeleteObject(xmap.pen); // delete pen } - xmap.pen = CreatePen(PS_SOLID, 1, xmap.rgb); // get a pen into xmap.pen +// xmap.pen = CreatePen(PS_SOLID, 1, xmap.rgb); // get a pen into xmap.pen + LOGBRUSH penbrush = {BS_SOLID, xmap.rgb, 0}; + xmap.pen = ExtCreatePen(PS_GEOMETRIC | PS_ENDCAP_FLAT | PS_JOIN_ROUND, lw, &penbrush, 0, 0); +#ifdef FLTK_HIDPI_SUPPORT + xmap.pwidth = lw; +#endif xmap.brush = -1; } @@ -94,14 +99,19 @@ void Fl_GDI_Graphics_Driver::color(Fl_Color i) { } else { Fl_Graphics_Driver::color(i); Fl_XMap &xmap = fl_xmap[i]; - if (!xmap.pen) { + int tw = line_width_ ? line_width_ : int(scale_); if (!tw) tw = 1; + if (!xmap.pen +#ifdef FLTK_HIDPI_SUPPORT + || xmap.pwidth != tw +#endif + ) { #if USE_COLORMAP if (fl_palette) { - set_xmap(xmap, PALETTEINDEX(i)); + set_xmap(xmap, PALETTEINDEX(i), tw); } else { #endif unsigned c = fl_cmap[i]; - set_xmap(xmap, RGB(uchar(c>>24), uchar(c>>16), uchar(c>>8))); + set_xmap(xmap, RGB(uchar(c>>24), uchar(c>>16), uchar(c>>8)), tw); #if USE_COLORMAP } #endif @@ -115,9 +125,14 @@ void Fl_GDI_Graphics_Driver::color(uchar r, uchar g, uchar b) { static Fl_XMap xmap; COLORREF c = RGB(r,g,b); Fl_Graphics_Driver::color( fl_rgb_color(r, g, b) ); - if (!xmap.pen || c != xmap.rgb) { + int tw = line_width_ ? line_width_ : int(scale_); if (!tw) tw = 1; + if (!xmap.pen || c != xmap.rgb +#ifdef FLTK_HIDPI_SUPPORT + || tw != xmap.pwidth +#endif + ) { clear_xmap(xmap); - set_xmap(xmap, c); + set_xmap(xmap, c, tw); } fl_current_xmap = ⟼ SelectObject(gc_, (HGDIOBJ)(xmap.pen)); diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver_line_style.cxx b/src/drivers/GDI/Fl_GDI_Graphics_Driver_line_style.cxx index 35281265c..63b32de43 100644 --- a/src/drivers/GDI/Fl_GDI_Graphics_Driver_line_style.cxx +++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver_line_style.cxx @@ -50,9 +50,11 @@ void Fl_GDI_Graphics_Driver::line_style_unscaled(int style, float width, char* d } else { s1 |= style & 0xff; // allow them to pass any low 8 bits for style } - if ((style || n) && !width) width = 1; // fix cards that do nothing for 0? + if ((style || n) && !width) width = scale_; // fix cards that do nothing for 0? + if (!fl_current_xmap) color(FL_BLACK); LOGBRUSH penbrush = {BS_SOLID,fl_RGB(),0}; // can this be fl_brush()? - HPEN newpen = ExtCreatePen(s1, width, &penbrush, n, n ? a : 0); + int tw = width < 1? 1: width; + HPEN newpen = ExtCreatePen(s1, tw, &penbrush, n, n ? a : 0); if (!newpen) { Fl::error("fl_line_style(): Could not create GDI pen object."); return; diff --git a/src/drivers/GDI/Fl_GDI_Graphics_Driver_rect.cxx b/src/drivers/GDI/Fl_GDI_Graphics_Driver_rect.cxx index 86698e386..c6d6b3d04 100644 --- a/src/drivers/GDI/Fl_GDI_Graphics_Driver_rect.cxx +++ b/src/drivers/GDI/Fl_GDI_Graphics_Driver_rect.cxx @@ -41,10 +41,13 @@ void Fl_GDI_Graphics_Driver::point_unscaled(float x, float y) { void Fl_GDI_Graphics_Driver::rect_unscaled(float x, float y, float w, float h) { if (w<=0 || h<=0) return; + int line_delta_ = (scale_ > 1.75 ? 1 : 0);//TMP + x += line_delta_; y += line_delta_; + int tw = line_width_ ? line_width_ : 1; // true line width MoveToEx(gc_, x, y, 0L); - LineTo(gc_, x+w-1, y); - LineTo(gc_, x+w-1, y+h-1); - LineTo(gc_, x, y+h-1); + LineTo(gc_, x+w-tw, y); + LineTo(gc_, x+w-tw, y+h-tw); + LineTo(gc_, x, y+h-tw); LineTo(gc_, x, y); } @@ -80,16 +83,31 @@ void Fl_GDI_Graphics_Driver::line_unscaled(float x, float y, float x1, float y1, SetPixel(gc_, x2, y2, fl_RGB()); } +//extern FILE*LOG; void Fl_GDI_Graphics_Driver::xyline_unscaled(float x, float y, float x1) { - MoveToEx(gc_, x, y, 0L); LineTo(gc_, x1+1, y); + int line_delta_ = (scale_ > 1.75 ? 1 : 0); + int tw = line_width_ ? line_width_ : 1; // true line width + if (x > x1) { float exch = x; x = x1; x1 = exch; } + int ix = x+line_delta_; if (scale_ >= 2) ix -= int(scale_/2); + int iy = y+line_delta_; + int ix1 = int(x1/scale_+1.5)*scale_-1; // extend line to pixel before line beginning at x1/scale_ + 1 + ix1 += line_delta_; if (scale_ >= 2) ix1 -= 1;; if (scale_ >= 4) ix1 -= 1; + MoveToEx(gc_, ix, iy, 0L); LineTo(gc_, ix1+1, iy); + // try and make sure no unfilled area lies between xyline(x,y,x1) and xyline(x,y+1,x1) + if (int(scale_) != scale_ && y+line_delta_ + scale_ >= iy + tw+1 - 0.001 ) { + MoveToEx(gc_, ix, iy+1, 0L); LineTo(gc_, ix1+1, iy+1); + } +//fprintf(LOG,"xyline_unscaled tw=%d s=%f gc_=%p\n",tw,scale_,gc_);fflush(LOG); } void Fl_GDI_Graphics_Driver::xyline_unscaled(float x, float y, float x1, float y2) { - if (y2 < y) y2--; + /*if (y2 < y) y2--; else y2++; MoveToEx(gc_, x, y, 0L); LineTo(gc_, x1, y); - LineTo(gc_, x1, y2); + LineTo(gc_, x1, y2);*/ + xyline_unscaled(x, y, x1); + yxline_unscaled(x1, y, y2); } void Fl_GDI_Graphics_Driver::xyline_unscaled(float x, float y, float x1, float y2, float x3) { @@ -102,17 +120,30 @@ void Fl_GDI_Graphics_Driver::xyline_unscaled(float x, float y, float x1, float y } void Fl_GDI_Graphics_Driver::yxline_unscaled(float x, float y, float y1) { - if (y1 < y) y1--; - else y1++; - MoveToEx(gc_, x, y, 0L); LineTo(gc_, x, y1); + if (y1 < y) { float exch = y; y = y1; y1 = exch;} + int line_delta_ = (scale_ > 1.75 ? 1 : 0); + int tw = line_width_ ? line_width_ : 1; // true line width + + int ix = x+line_delta_; + int iy = y+line_delta_; if (scale_ >= 2) iy -= int(scale_/2); + int iy1 = int(y1/scale_+1.5)*scale_-1; + iy1 += line_delta_; if (scale_ >= 2) iy1 -= 1;; if (scale_ >= 4) iy1 -= 1; // extend line to pixel before line beginning at y1/scale_ + 1 + MoveToEx(gc_, ix, iy, 0L); LineTo(gc_, ix, iy1+1); + // try and make sure no unfilled area lies between yxline(x,y,y1) and yxline(x+1,y,y1) + if (int(scale_) != scale_ && x+line_delta_+scale_ >= ix + tw+1 -0.001) { + MoveToEx(gc_, ix+1, iy, 0L); LineTo(gc_, ix+1, iy1+1); + } + } void Fl_GDI_Graphics_Driver::yxline_unscaled(float x, float y, float y1, float x2) { - if (x2 > x) x2++; + /*if (x2 > x) x2++; else x2--; MoveToEx(gc_, x, y, 0L); LineTo(gc_, x, y1); - LineTo(gc_, x2, y1); + LineTo(gc_, x2, y1);*/ + yxline_unscaled(x, y, y1); + xyline_unscaled(x, y1, x2); } void Fl_GDI_Graphics_Driver::yxline_unscaled(float x, float y, float y1, float x2, float y3) { |
