From 04a06f8ce7298b708028011e7e378bb864f86156 Mon Sep 17 00:00:00 2001 From: cxl Date: Mon, 6 Jul 2009 20:31:00 +0000 Subject: [PATCH] developing new draw git-svn-id: svn://ultimatepp.org/upp/trunk@1372 f0d560ea-af0d-0410-9eb7-867de7ffcac7 --- {uppsrc => olddraw}/Painter/Approximate.cpp | 0 {uppsrc => olddraw}/Painter/BufferPainter.h | 0 {uppsrc => olddraw}/Painter/Context.cpp | 0 {uppsrc => olddraw}/Painter/Copying | 0 {uppsrc => olddraw}/Painter/Dasher.cpp | 0 {uppsrc => olddraw}/Painter/DrawOp.cpp | 0 {uppsrc => olddraw}/Painter/Fillers.cpp | 0 {uppsrc => olddraw}/Painter/Fillers.h | 0 {uppsrc => olddraw}/Painter/FontWin32.cpp | 0 {uppsrc => olddraw}/Painter/FontX11.cpp | 0 {uppsrc => olddraw}/Painter/Gradient.cpp | 0 {uppsrc => olddraw}/Painter/Image.cpp | 0 {uppsrc => olddraw}/Painter/Interpolator.cpp | 0 {uppsrc => olddraw}/Painter/Mask.cpp | 0 {uppsrc => olddraw}/Painter/OnPath.cpp | 0 .../Painter/PaintPainting.icpp | 0 {uppsrc => olddraw}/Painter/Painter.cpp | 0 {uppsrc => olddraw}/Painter/Painter.h | 0 {uppsrc => olddraw}/Painter/Painter.hpp | 0 {uppsrc => olddraw}/Painter/Painter.upp | 0 {uppsrc => olddraw}/Painter/PainterPath.cpp | 0 {uppsrc => olddraw}/Painter/Painting.cpp | 0 {uppsrc => olddraw}/Painter/Painting.h | 0 {uppsrc => olddraw}/Painter/Path.cpp | 0 .../Painter/RadialGradient.cpp | 0 {uppsrc => olddraw}/Painter/Rasterizer.cpp | 0 {uppsrc => olddraw}/Painter/Rasterizer3.h | 0 .../Painter/RasterizerClip.cpp | 0 {uppsrc => olddraw}/Painter/Render.cpp | 0 {uppsrc => olddraw}/Painter/RenderChar.cpp | 0 {uppsrc => olddraw}/Painter/Stroker.cpp | 0 {uppsrc => olddraw}/Painter/SvgArc.cpp | 0 {uppsrc => olddraw}/Painter/Transformer.cpp | 0 {uppsrc => olddraw}/Painter/Xform2D.cpp | 0 {uppsrc => olddraw}/Painter/init | 0 .../srcimp.tpp/SubpixelFiller$en-us.tpp | 0 {uppsrc => olddraw}/PdfDraw/Copying | 0 {uppsrc => olddraw}/PdfDraw/PdfDraw.cpp | 0 {uppsrc => olddraw}/PdfDraw/PdfDraw.h | 0 {uppsrc => olddraw}/PdfDraw/PdfDraw.upp | 0 {uppsrc => olddraw}/PdfDraw/PdfReport.icpp | 0 {uppsrc => olddraw}/PdfDraw/TTFReader.cpp | 0 {uppsrc => olddraw}/PdfDraw/TTFStream.cpp | 0 {uppsrc => olddraw}/PdfDraw/TTFStruct.cpp | 0 {uppsrc => olddraw}/PdfDraw/TTFSubset.cpp | 0 {uppsrc => olddraw}/PdfDraw/init | 0 {uppsrc => olddraw}/PdfDraw/ttf.h | 0 uppsrc/CtrlCore/BackDraw.cpp | 2 +- uppsrc/CtrlCore/CtrlCore.h | 2 +- uppsrc/CtrlCore/CtrlCore.upp | 16 + uppsrc/CtrlCore/DrawOpWin32.cpp | 32 +- uppsrc/CtrlCore/DrawOpX11.cpp | 606 +++--- uppsrc/CtrlCore/DrawTextWin32.cpp | 4 +- uppsrc/CtrlCore/DrawTextX11.cpp | 414 ++-- uppsrc/CtrlCore/DrawWin32.cpp | 72 +- uppsrc/CtrlCore/DrawWin32.h | 7 + uppsrc/CtrlCore/DrawX11.cpp | 904 ++++----- uppsrc/CtrlCore/DrawX11.h | 286 ++- uppsrc/CtrlCore/ImageWin32.cpp | 32 +- uppsrc/CtrlCore/ImageX11.cpp | 872 ++++----- uppsrc/CtrlCore/MetaFile.cpp | 2 +- uppsrc/CtrlCore/SystemDraw.cpp | 14 +- uppsrc/CtrlCore/SystemDraw.h | 29 + uppsrc/CtrlCore/init | 2 +- uppsrc/Draw/Draw.cpp | 20 - uppsrc/Draw/Draw.h | 1719 ++++++++--------- uppsrc/Draw/Draw.upp | 160 +- uppsrc/Draw/DrawData.cpp | 2 +- uppsrc/Draw/DrawUtil.cpp | 133 -- uppsrc/Draw/Font.cpp | 684 +++---- uppsrc/Draw/FontInt.h | 2 +- uppsrc/Draw/Image.cpp | 15 - uppsrc/Draw/Image.h | 666 ++++--- uppsrc/RichText/ParaData.cpp | 12 +- 74 files changed, 3278 insertions(+), 3431 deletions(-) rename {uppsrc => olddraw}/Painter/Approximate.cpp (100%) rename {uppsrc => olddraw}/Painter/BufferPainter.h (100%) rename {uppsrc => olddraw}/Painter/Context.cpp (100%) rename {uppsrc => olddraw}/Painter/Copying (100%) rename {uppsrc => olddraw}/Painter/Dasher.cpp (100%) rename {uppsrc => olddraw}/Painter/DrawOp.cpp (100%) rename {uppsrc => olddraw}/Painter/Fillers.cpp (100%) rename {uppsrc => olddraw}/Painter/Fillers.h (100%) rename {uppsrc => olddraw}/Painter/FontWin32.cpp (100%) rename {uppsrc => olddraw}/Painter/FontX11.cpp (100%) rename {uppsrc => olddraw}/Painter/Gradient.cpp (100%) rename {uppsrc => olddraw}/Painter/Image.cpp (100%) rename {uppsrc => olddraw}/Painter/Interpolator.cpp (100%) rename {uppsrc => olddraw}/Painter/Mask.cpp (100%) rename {uppsrc => olddraw}/Painter/OnPath.cpp (100%) rename {uppsrc => olddraw}/Painter/PaintPainting.icpp (100%) rename {uppsrc => olddraw}/Painter/Painter.cpp (100%) rename {uppsrc => olddraw}/Painter/Painter.h (100%) rename {uppsrc => olddraw}/Painter/Painter.hpp (100%) rename {uppsrc => olddraw}/Painter/Painter.upp (100%) rename {uppsrc => olddraw}/Painter/PainterPath.cpp (100%) rename {uppsrc => olddraw}/Painter/Painting.cpp (100%) rename {uppsrc => olddraw}/Painter/Painting.h (100%) rename {uppsrc => olddraw}/Painter/Path.cpp (100%) rename {uppsrc => olddraw}/Painter/RadialGradient.cpp (100%) rename {uppsrc => olddraw}/Painter/Rasterizer.cpp (100%) rename {uppsrc => olddraw}/Painter/Rasterizer3.h (100%) rename {uppsrc => olddraw}/Painter/RasterizerClip.cpp (100%) rename {uppsrc => olddraw}/Painter/Render.cpp (100%) rename {uppsrc => olddraw}/Painter/RenderChar.cpp (100%) rename {uppsrc => olddraw}/Painter/Stroker.cpp (100%) rename {uppsrc => olddraw}/Painter/SvgArc.cpp (100%) rename {uppsrc => olddraw}/Painter/Transformer.cpp (100%) rename {uppsrc => olddraw}/Painter/Xform2D.cpp (100%) rename {uppsrc => olddraw}/Painter/init (100%) rename {uppsrc => olddraw}/Painter/srcimp.tpp/SubpixelFiller$en-us.tpp (100%) rename {uppsrc => olddraw}/PdfDraw/Copying (100%) rename {uppsrc => olddraw}/PdfDraw/PdfDraw.cpp (100%) rename {uppsrc => olddraw}/PdfDraw/PdfDraw.h (100%) rename {uppsrc => olddraw}/PdfDraw/PdfDraw.upp (100%) rename {uppsrc => olddraw}/PdfDraw/PdfReport.icpp (100%) rename {uppsrc => olddraw}/PdfDraw/TTFReader.cpp (100%) rename {uppsrc => olddraw}/PdfDraw/TTFStream.cpp (100%) rename {uppsrc => olddraw}/PdfDraw/TTFStruct.cpp (100%) rename {uppsrc => olddraw}/PdfDraw/TTFSubset.cpp (100%) rename {uppsrc => olddraw}/PdfDraw/init (100%) rename {uppsrc => olddraw}/PdfDraw/ttf.h (100%) diff --git a/uppsrc/Painter/Approximate.cpp b/olddraw/Painter/Approximate.cpp similarity index 100% rename from uppsrc/Painter/Approximate.cpp rename to olddraw/Painter/Approximate.cpp diff --git a/uppsrc/Painter/BufferPainter.h b/olddraw/Painter/BufferPainter.h similarity index 100% rename from uppsrc/Painter/BufferPainter.h rename to olddraw/Painter/BufferPainter.h diff --git a/uppsrc/Painter/Context.cpp b/olddraw/Painter/Context.cpp similarity index 100% rename from uppsrc/Painter/Context.cpp rename to olddraw/Painter/Context.cpp diff --git a/uppsrc/Painter/Copying b/olddraw/Painter/Copying similarity index 100% rename from uppsrc/Painter/Copying rename to olddraw/Painter/Copying diff --git a/uppsrc/Painter/Dasher.cpp b/olddraw/Painter/Dasher.cpp similarity index 100% rename from uppsrc/Painter/Dasher.cpp rename to olddraw/Painter/Dasher.cpp diff --git a/uppsrc/Painter/DrawOp.cpp b/olddraw/Painter/DrawOp.cpp similarity index 100% rename from uppsrc/Painter/DrawOp.cpp rename to olddraw/Painter/DrawOp.cpp diff --git a/uppsrc/Painter/Fillers.cpp b/olddraw/Painter/Fillers.cpp similarity index 100% rename from uppsrc/Painter/Fillers.cpp rename to olddraw/Painter/Fillers.cpp diff --git a/uppsrc/Painter/Fillers.h b/olddraw/Painter/Fillers.h similarity index 100% rename from uppsrc/Painter/Fillers.h rename to olddraw/Painter/Fillers.h diff --git a/uppsrc/Painter/FontWin32.cpp b/olddraw/Painter/FontWin32.cpp similarity index 100% rename from uppsrc/Painter/FontWin32.cpp rename to olddraw/Painter/FontWin32.cpp diff --git a/uppsrc/Painter/FontX11.cpp b/olddraw/Painter/FontX11.cpp similarity index 100% rename from uppsrc/Painter/FontX11.cpp rename to olddraw/Painter/FontX11.cpp diff --git a/uppsrc/Painter/Gradient.cpp b/olddraw/Painter/Gradient.cpp similarity index 100% rename from uppsrc/Painter/Gradient.cpp rename to olddraw/Painter/Gradient.cpp diff --git a/uppsrc/Painter/Image.cpp b/olddraw/Painter/Image.cpp similarity index 100% rename from uppsrc/Painter/Image.cpp rename to olddraw/Painter/Image.cpp diff --git a/uppsrc/Painter/Interpolator.cpp b/olddraw/Painter/Interpolator.cpp similarity index 100% rename from uppsrc/Painter/Interpolator.cpp rename to olddraw/Painter/Interpolator.cpp diff --git a/uppsrc/Painter/Mask.cpp b/olddraw/Painter/Mask.cpp similarity index 100% rename from uppsrc/Painter/Mask.cpp rename to olddraw/Painter/Mask.cpp diff --git a/uppsrc/Painter/OnPath.cpp b/olddraw/Painter/OnPath.cpp similarity index 100% rename from uppsrc/Painter/OnPath.cpp rename to olddraw/Painter/OnPath.cpp diff --git a/uppsrc/Painter/PaintPainting.icpp b/olddraw/Painter/PaintPainting.icpp similarity index 100% rename from uppsrc/Painter/PaintPainting.icpp rename to olddraw/Painter/PaintPainting.icpp diff --git a/uppsrc/Painter/Painter.cpp b/olddraw/Painter/Painter.cpp similarity index 100% rename from uppsrc/Painter/Painter.cpp rename to olddraw/Painter/Painter.cpp diff --git a/uppsrc/Painter/Painter.h b/olddraw/Painter/Painter.h similarity index 100% rename from uppsrc/Painter/Painter.h rename to olddraw/Painter/Painter.h diff --git a/uppsrc/Painter/Painter.hpp b/olddraw/Painter/Painter.hpp similarity index 100% rename from uppsrc/Painter/Painter.hpp rename to olddraw/Painter/Painter.hpp diff --git a/uppsrc/Painter/Painter.upp b/olddraw/Painter/Painter.upp similarity index 100% rename from uppsrc/Painter/Painter.upp rename to olddraw/Painter/Painter.upp diff --git a/uppsrc/Painter/PainterPath.cpp b/olddraw/Painter/PainterPath.cpp similarity index 100% rename from uppsrc/Painter/PainterPath.cpp rename to olddraw/Painter/PainterPath.cpp diff --git a/uppsrc/Painter/Painting.cpp b/olddraw/Painter/Painting.cpp similarity index 100% rename from uppsrc/Painter/Painting.cpp rename to olddraw/Painter/Painting.cpp diff --git a/uppsrc/Painter/Painting.h b/olddraw/Painter/Painting.h similarity index 100% rename from uppsrc/Painter/Painting.h rename to olddraw/Painter/Painting.h diff --git a/uppsrc/Painter/Path.cpp b/olddraw/Painter/Path.cpp similarity index 100% rename from uppsrc/Painter/Path.cpp rename to olddraw/Painter/Path.cpp diff --git a/uppsrc/Painter/RadialGradient.cpp b/olddraw/Painter/RadialGradient.cpp similarity index 100% rename from uppsrc/Painter/RadialGradient.cpp rename to olddraw/Painter/RadialGradient.cpp diff --git a/uppsrc/Painter/Rasterizer.cpp b/olddraw/Painter/Rasterizer.cpp similarity index 100% rename from uppsrc/Painter/Rasterizer.cpp rename to olddraw/Painter/Rasterizer.cpp diff --git a/uppsrc/Painter/Rasterizer3.h b/olddraw/Painter/Rasterizer3.h similarity index 100% rename from uppsrc/Painter/Rasterizer3.h rename to olddraw/Painter/Rasterizer3.h diff --git a/uppsrc/Painter/RasterizerClip.cpp b/olddraw/Painter/RasterizerClip.cpp similarity index 100% rename from uppsrc/Painter/RasterizerClip.cpp rename to olddraw/Painter/RasterizerClip.cpp diff --git a/uppsrc/Painter/Render.cpp b/olddraw/Painter/Render.cpp similarity index 100% rename from uppsrc/Painter/Render.cpp rename to olddraw/Painter/Render.cpp diff --git a/uppsrc/Painter/RenderChar.cpp b/olddraw/Painter/RenderChar.cpp similarity index 100% rename from uppsrc/Painter/RenderChar.cpp rename to olddraw/Painter/RenderChar.cpp diff --git a/uppsrc/Painter/Stroker.cpp b/olddraw/Painter/Stroker.cpp similarity index 100% rename from uppsrc/Painter/Stroker.cpp rename to olddraw/Painter/Stroker.cpp diff --git a/uppsrc/Painter/SvgArc.cpp b/olddraw/Painter/SvgArc.cpp similarity index 100% rename from uppsrc/Painter/SvgArc.cpp rename to olddraw/Painter/SvgArc.cpp diff --git a/uppsrc/Painter/Transformer.cpp b/olddraw/Painter/Transformer.cpp similarity index 100% rename from uppsrc/Painter/Transformer.cpp rename to olddraw/Painter/Transformer.cpp diff --git a/uppsrc/Painter/Xform2D.cpp b/olddraw/Painter/Xform2D.cpp similarity index 100% rename from uppsrc/Painter/Xform2D.cpp rename to olddraw/Painter/Xform2D.cpp diff --git a/uppsrc/Painter/init b/olddraw/Painter/init similarity index 100% rename from uppsrc/Painter/init rename to olddraw/Painter/init diff --git a/uppsrc/Painter/srcimp.tpp/SubpixelFiller$en-us.tpp b/olddraw/Painter/srcimp.tpp/SubpixelFiller$en-us.tpp similarity index 100% rename from uppsrc/Painter/srcimp.tpp/SubpixelFiller$en-us.tpp rename to olddraw/Painter/srcimp.tpp/SubpixelFiller$en-us.tpp diff --git a/uppsrc/PdfDraw/Copying b/olddraw/PdfDraw/Copying similarity index 100% rename from uppsrc/PdfDraw/Copying rename to olddraw/PdfDraw/Copying diff --git a/uppsrc/PdfDraw/PdfDraw.cpp b/olddraw/PdfDraw/PdfDraw.cpp similarity index 100% rename from uppsrc/PdfDraw/PdfDraw.cpp rename to olddraw/PdfDraw/PdfDraw.cpp diff --git a/uppsrc/PdfDraw/PdfDraw.h b/olddraw/PdfDraw/PdfDraw.h similarity index 100% rename from uppsrc/PdfDraw/PdfDraw.h rename to olddraw/PdfDraw/PdfDraw.h diff --git a/uppsrc/PdfDraw/PdfDraw.upp b/olddraw/PdfDraw/PdfDraw.upp similarity index 100% rename from uppsrc/PdfDraw/PdfDraw.upp rename to olddraw/PdfDraw/PdfDraw.upp diff --git a/uppsrc/PdfDraw/PdfReport.icpp b/olddraw/PdfDraw/PdfReport.icpp similarity index 100% rename from uppsrc/PdfDraw/PdfReport.icpp rename to olddraw/PdfDraw/PdfReport.icpp diff --git a/uppsrc/PdfDraw/TTFReader.cpp b/olddraw/PdfDraw/TTFReader.cpp similarity index 100% rename from uppsrc/PdfDraw/TTFReader.cpp rename to olddraw/PdfDraw/TTFReader.cpp diff --git a/uppsrc/PdfDraw/TTFStream.cpp b/olddraw/PdfDraw/TTFStream.cpp similarity index 100% rename from uppsrc/PdfDraw/TTFStream.cpp rename to olddraw/PdfDraw/TTFStream.cpp diff --git a/uppsrc/PdfDraw/TTFStruct.cpp b/olddraw/PdfDraw/TTFStruct.cpp similarity index 100% rename from uppsrc/PdfDraw/TTFStruct.cpp rename to olddraw/PdfDraw/TTFStruct.cpp diff --git a/uppsrc/PdfDraw/TTFSubset.cpp b/olddraw/PdfDraw/TTFSubset.cpp similarity index 100% rename from uppsrc/PdfDraw/TTFSubset.cpp rename to olddraw/PdfDraw/TTFSubset.cpp diff --git a/uppsrc/PdfDraw/init b/olddraw/PdfDraw/init similarity index 100% rename from uppsrc/PdfDraw/init rename to olddraw/PdfDraw/init diff --git a/uppsrc/PdfDraw/ttf.h b/olddraw/PdfDraw/ttf.h similarity index 100% rename from uppsrc/PdfDraw/ttf.h rename to olddraw/PdfDraw/ttf.h diff --git a/uppsrc/CtrlCore/BackDraw.cpp b/uppsrc/CtrlCore/BackDraw.cpp index 9e20215b2..7a011bf1a 100644 --- a/uppsrc/CtrlCore/BackDraw.cpp +++ b/uppsrc/CtrlCore/BackDraw.cpp @@ -1,4 +1,4 @@ -#include "Draw.h" +#include "SystemDraw.h" NAMESPACE_UPP diff --git a/uppsrc/CtrlCore/CtrlCore.h b/uppsrc/CtrlCore/CtrlCore.h index 71b9570f6..805d1613d 100644 --- a/uppsrc/CtrlCore/CtrlCore.h +++ b/uppsrc/CtrlCore/CtrlCore.h @@ -1,7 +1,7 @@ #ifndef CTRLCORE_H #define CTRLCORE_H -#include +#include "SystemDraw.h" NAMESPACE_UPP diff --git a/uppsrc/CtrlCore/CtrlCore.upp b/uppsrc/CtrlCore/CtrlCore.upp index be3433edd..37bec5c00 100644 --- a/uppsrc/CtrlCore/CtrlCore.upp +++ b/uppsrc/CtrlCore/CtrlCore.upp @@ -7,6 +7,22 @@ uses library(WIN32 !MSC8ARM) "advapi32 comdlg32 comctl32"; file + SystemDraw readonly separator, + DrawWin32.h, + DrawWin32.cpp, + DrawOpWin32.cpp, + DrawTextWin32.cpp, + ImageWin32.cpp, + MetaFile.cpp, + DrawX11.h, + DrawX11.cpp, + DrawOpX11.cpp, + DrawTextX11.cpp, + ImageX11.cpp, + SystemDraw.h, + BackDraw.cpp, + SystemDraw.cpp, + DrawUtil.cpp, Core readonly separator, CtrlCore.h, Win32Keys.i, diff --git a/uppsrc/CtrlCore/DrawOpWin32.cpp b/uppsrc/CtrlCore/DrawOpWin32.cpp index 8232eb4ca..b6c9445b5 100644 --- a/uppsrc/CtrlCore/DrawOpWin32.cpp +++ b/uppsrc/CtrlCore/DrawOpWin32.cpp @@ -1,4 +1,4 @@ -#include "Draw.h" +#include "SystemDraw.h" NAMESPACE_UPP @@ -10,7 +10,7 @@ NAMESPACE_UPP void SystemDraw::BeginOp() { LTIMING("Begin"); - DrawLock __; + GuiLock __; Cloff& w = cloff.Add(); w.org = actual_offset; w.hrgn = CreateRectRgn(0, 0, 0, 0); @@ -25,7 +25,7 @@ void SystemDraw::BeginOp() void SystemDraw::OffsetOp(Point p) { - DrawLock __; + GuiLock __; Begin(); actual_offset += p; LTIMING("Offset"); @@ -34,7 +34,7 @@ void SystemDraw::OffsetOp(Point p) bool SystemDraw::ClipOp(const Rect& r) { - DrawLock __; + GuiLock __; Begin(); LTIMING("Clip"); return IntersectClip(r); @@ -42,7 +42,7 @@ bool SystemDraw::ClipOp(const Rect& r) bool SystemDraw::ClipoffOp(const Rect& r) { - DrawLock __; + GuiLock __; Begin(); LTIMING("Clipoff"); LLOG("ClipoffOp " << r << ", GetClip() = " << GetClip() << ", actual_offset = " << actual_offset); @@ -55,7 +55,7 @@ bool SystemDraw::ClipoffOp(const Rect& r) void SystemDraw::EndOp() { - DrawLock __; + GuiLock __; LTIMING("End"); ASSERT(cloff.GetCount()); Cloff& w = cloff.Top(); @@ -69,7 +69,7 @@ void SystemDraw::EndOp() bool SystemDraw::ExcludeClipOp(const Rect& r) { - DrawLock __; + GuiLock __; #ifdef PLATFORM_WINCE int q = ExcludeClipRect(handle, r.left, r.top, r.right, r.bottom); #else @@ -85,7 +85,7 @@ bool SystemDraw::ExcludeClipOp(const Rect& r) bool SystemDraw::IntersectClipOp(const Rect& r) { - DrawLock __; + GuiLock __; #ifdef PLATFORM_WINCE int q = IntersectClipRect(handle, r.left, r.top, r.right, r.bottom); #else @@ -101,7 +101,7 @@ bool SystemDraw::IntersectClipOp(const Rect& r) bool SystemDraw::IsPaintingOp(const Rect& r) const { - DrawLock __; + GuiLock __; LTIMING("IsPainting"); LLOG("SystemDraw::IsPaintingOp r: " << r); return ::RectVisible(handle, r); @@ -109,7 +109,7 @@ bool SystemDraw::IsPaintingOp(const Rect& r) const void SystemDraw::DrawRectOp(int x, int y, int cx, int cy, Color color) { - DrawLock __; + GuiLock __; LTIMING("DrawRect"); LLOG("DrawRect " << RectC(x, y, cx, cy) << ": " << color); if(IsNull(color)) return; @@ -124,7 +124,7 @@ void SystemDraw::DrawRectOp(int x, int y, int cx, int cy, Color color) void SystemDraw::DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color) { - DrawLock __; + GuiLock __; if(IsNull(width) || IsNull(color)) return; SetDrawPen(width, color); ::MoveToEx(handle, x1, y1, NULL); @@ -137,7 +137,7 @@ void SystemDraw::DrawPolyPolylineOp(const Point *vertices, int vertex_count, const int *counts, int count_count, int width, Color color, Color doxor) { - DrawLock __; + GuiLock __; ASSERT(count_count > 0 && vertex_count > 0); if(vertex_count < 2 || IsNull(color)) return; @@ -161,7 +161,7 @@ static void DrawPolyPolyPolygonRaw( const int *subpolygon_counts, int subpolygon_count_count, const int *disjunct_polygon_counts, int disjunct_polygon_count_count) { - DrawLock __; + GuiLock __; for(int i = 0; i < disjunct_polygon_count_count; i++, disjunct_polygon_counts++) { int poly = *disjunct_polygon_counts; @@ -192,7 +192,7 @@ void SystemDraw::DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, const int *disjunct_polygon_counts, int disjunct_polygon_count_count, Color color, int width, Color outline, uint64 pattern, Color doxor) { - DrawLock __; + GuiLock __; if(vertex_count == 0) return; bool is_xor = !IsNull(doxor); @@ -262,7 +262,7 @@ void SystemDraw::DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, void SystemDraw::DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color) { - DrawLock __; + GuiLock __; SetDrawPen(width, color); ::Arc(GetHandle(), rc.left, rc.top, rc.right, rc.bottom, start.x, start.y, end.x, end.y); } @@ -271,7 +271,7 @@ void SystemDraw::DrawArcOp(const Rect& rc, Point start, Point end, int width, Co void SystemDraw::DrawEllipseOp(const Rect& r, Color color, int width, Color pencolor) { - DrawLock __; + GuiLock __; SetColor(color); SetDrawPen(width, pencolor); ::Ellipse(GetHandle(), r.left, r.top, r.right, r.bottom); diff --git a/uppsrc/CtrlCore/DrawOpX11.cpp b/uppsrc/CtrlCore/DrawOpX11.cpp index 5a70420c8..ea9c5432c 100644 --- a/uppsrc/CtrlCore/DrawOpX11.cpp +++ b/uppsrc/CtrlCore/DrawOpX11.cpp @@ -1,303 +1,303 @@ -#include "Draw.h" - -NAMESPACE_UPP - -#ifdef PLATFORM_X11 - -#define LLOG(x) // LOG(x) -#define LTIMING(x) // TIMING(x) - -void SystemDraw::BeginOp() -{ - Cloff f = cloff.Top(); - Vector newclip; - newclip <<= clip.Top(); - f.clipi = clip.GetCount(); - clip.Add() = newclip; - cloff.Add(f); -} - -void SystemDraw::OffsetOp(Point p) -{ - Cloff f = cloff.Top(); - f.offseti = offset.GetCount(); - actual_offset += p; - offset.Add(actual_offset); - cloff.Add(f); -} - -bool SystemDraw::ClipOp(const Rect& r) -{ - LLOG("SystemDraw::ClipOp(" << r << ")"); - Cloff f = cloff.Top(); - bool ch = false; - Vector newclip = Intersect(clip.Top(), r + actual_offset, ch); - if(ch) { - f.clipi = clip.GetCount(); - clip.Add() = newclip; - } - cloff.Add(f); - if(ch) - SetClip(); - return clip.Top().GetCount(); -} - -bool SystemDraw::ClipoffOp(const Rect& r) -{ - LLOG("SystemDraw::ClipOffOp(" << r << ")"); - Cloff f = cloff.Top(); - bool ch = false; - Vector newclip = Intersect(clip.Top(), r + actual_offset, ch); - if(ch) { - f.clipi = clip.GetCount(); - clip.Add() = newclip; - } - f.offseti = offset.GetCount(); - actual_offset += r.TopLeft(); - offset.Add(actual_offset); - cloff.Add(f); - if(ch) - SetClip(); - return clip.Top().GetCount(); -} - -void SystemDraw::EndOp() -{ - ASSERT(cloff.GetCount()); - cloff.Drop(); - actual_offset = offset[cloff.Top().offseti]; - clip.SetCount(cloff.Top().clipi + 1); - SetClip(); -} - -bool SystemDraw::ExcludeClipOp(const Rect& r) -{ - LLOG("SystemDraw::ExcludeClipOp(" << r << ")"); - CloneClip(); - Vector& cl = clip.Top(); - bool ch = false; - Vector ncl = Subtract(cl, r + actual_offset, ch); - if(ch) { - cl = ncl; - SetClip(); - } - return clip.Top().GetCount(); -} - -bool SystemDraw::IntersectClipOp(const Rect& r) -{ - CloneClip(); - Vector& cl = clip.Top(); - bool ch = false; - Vector ncl = Intersect(cl, r + actual_offset, ch); - if(ch) { - cl = ncl; - SetClip(); - } - return clip.Top().GetCount(); -} - -bool SystemDraw::IsPaintingOp(const Rect& r) const -{ - LTIMING("IsPaintingOp"); - Rect rr = r + actual_offset; - const Vector& cl = clip[cloff.Top().clipi]; - for(int i = 0; i < cl.GetCount(); i++) - if(cl[i].Intersects(rr)) - return true; - return false; -} - -void SystemDraw::DrawRectOp(int x, int y, int cx, int cy, Color color) -{ - LTIMING("DrawRect"); - DrawLock __; - LLOG("DrawRect " << RectC(x, y, cx, cy) << ": " << color); - if(IsNull(color)) return; - if(cx <= 0 || cy <= 0) return; - if(color == InvertColor) { - XSetFunction(Xdisplay, gc, GXinvert); - XFillRectangle(Xdisplay, dw, gc, x + actual_offset.x, y + actual_offset.y, cx, cy); - XSetFunction(Xdisplay, gc, GXcopy); - } - else { - SetForeground(color); - XFillRectangle(Xdisplay, dw, gc, x + actual_offset.x, y + actual_offset.y, cx, cy); - } -} - -void SystemDraw::DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color) -{ - DrawLock __; - if(IsNull(width) || IsNull(color)) return; - SetLineStyle(width); - SetForeground(color); - XDrawLine(Xdisplay, dw, gc, - x1 + actual_offset.x, y1 + actual_offset.y, - x2 + actual_offset.x, y2 + actual_offset.y); -} - -void SystemDraw::DrawPolyPolylineOp(const Point *vertices, int vertex_count, - const int *counts, int count_count, - int width, Color color, Color doxor) -{ - DrawLock __; - ASSERT(count_count > 0 && vertex_count > 0); - if(vertex_count < 2 || IsNull(color)) - return; - XGCValues gcv_old, gcv_new; - XGetGCValues(Xdisplay, GetGC(), GCForeground | GCLineWidth | GCFunction, &gcv_old); - gcv_new.function = IsNull(doxor) ? X11_ROP2_COPY : X11_ROP2_XOR; - gcv_new.foreground = GetXPixel(color) ^ (IsNull(doxor) ? 0 : GetXPixel(doxor)); - gcv_new.line_width = width; - XChangeGC(Xdisplay, GetGC(), GCForeground | GCLineWidth | GCFunction, &gcv_new); - enum { REQUEST_LENGTH = 256 }; // X server XDrawLines request length (heuristic) - Point offset = GetOffset(); - if(vertex_count == 2) - XDrawLine(Xdisplay, GetDrawable(), GetGC(), - vertices[0].x + offset.x, vertices[0].y + offset.y, - vertices[1].x + offset.x, vertices[1].y + offset.y); - else if(count_count == 1 || vertex_count > count_count * (REQUEST_LENGTH + 2)) { - for(; --count_count >= 0; counts++) - { - Buffer part(*counts); - for(XPoint *vo = part, *ve = vo + *counts; vo < ve; vo++, vertices++) - { - vo -> x = (short)(vertices -> x + offset.x); - vo -> y = (short)(vertices -> y + offset.y); - } - XDrawLines(Xdisplay, GetDrawable(), GetGC(), part, *counts, CoordModeOrigin); - } - } - else { - int segment_count = vertex_count - count_count; - Buffer segments(segment_count); - XSegment *so = segments; - while(--count_count >= 0) - { - const Point *end = vertices + *counts++; - so -> x1 = (short)(vertices -> x + offset.x); - so -> y1 = (short)(vertices -> y + offset.y); - vertices++; - so -> x2 = (short)(vertices -> x + offset.x); - so -> y2 = (short)(vertices -> y + offset.y); - so++; - while(++vertices < end) { - so -> x1 = so[-1].x2; - so -> y1 = so[-1].y2; - so -> x2 = (short)(vertices -> x + offset.x); - so -> y2 = (short)(vertices -> y + offset.y); - so++; - } - } - ASSERT(so == segments + segment_count); - XDrawSegments(Xdisplay, GetDrawable(), GetGC(), segments, segment_count); - } - XChangeGC(Xdisplay, GetGC(), GCForeground | GCLineWidth | GCFunction, &gcv_old); -} - -static void DrawPolyPolyPolygonRaw(SystemDraw& draw, const Point *vertices, int vertex_count, - const int *subpolygon_counts, int subpolygon_count_count, const int *, int) -{ - DrawLock __; - Point offset = draw.GetOffset(); - const Point *in = vertices; - for(int i = 0; i < subpolygon_count_count; i++) { - int n = subpolygon_counts[i]; - Buffer out_points(n); - XPoint *t = out_points; - XPoint *e = t + n; - while(t < e) { - t->x = (short)(in->x + offset.x); - t->y = (short)(in->y + offset.y); - t++; - in++; - } - XFillPolygon(Xdisplay, draw.GetDrawable(), draw.GetGC(), out_points, n, Nonconvex, CoordModeOrigin); - } -} - -void SystemDraw::DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, - const int *subpolygon_counts, int subpolygon_count_count, - const int *disjunct_polygon_counts, int disjunct_polygon_count_count, - Color color, int width, Color outline, uint64 pattern, Color doxor) -{ - DrawLock __; - if(vertex_count == 0) - return; - - bool is_xor = !IsNull(doxor); - XGCValues gcv_old, gcv_new; - XGetGCValues(Xdisplay, GetGC(), GCForeground | GCFunction | GCLineWidth, &gcv_old); - unsigned xor_pixel = (is_xor ? GetXPixel(doxor) : 0); - if(!IsNull(color)) - { - gcv_new.foreground = GetXPixel(color) ^ xor_pixel; - gcv_new.function = is_xor ? X11_ROP2_XOR : X11_ROP2_COPY; - XChangeGC(Xdisplay, GetGC(), GCForeground | GCFunction, &gcv_new); - DrawPolyPolyPolygonRaw(*this, vertices, vertex_count, - subpolygon_counts, subpolygon_count_count, - disjunct_polygon_counts, disjunct_polygon_count_count); - } - if(!IsNull(outline)) - { - gcv_new.foreground = GetXPixel(outline) ^ xor_pixel; - gcv_new.line_width = width; - XChangeGC(Xdisplay, GetGC(), GCForeground | GCLineWidth, &gcv_new); - Point offset = GetOffset(); - for(const int *sp = subpolygon_counts, *se = sp + subpolygon_count_count; sp < se; sp++) - { - Buffer segment(*sp + 1); - XPoint *out = segment; - for(const Point *end = vertices + *sp; vertices < end; vertices++, out++) - { - out -> x = (short)(vertices -> x + offset.x); - out -> y = (short)(vertices -> y + offset.y); - } - *out = segment[0]; - XDrawLines(Xdisplay, GetDrawable(), GetGC(), segment, *sp + 1, CoordModeOrigin); - } - } - XChangeGC(Xdisplay, GetGC(), GCForeground | GCFunction | GCLineWidth, &gcv_old); -} - -void SystemDraw::DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor) -{ - DrawLock __; - SetLineStyle(pen); - if(!IsNull(color)) { - SetForeground(color); - XFillArc(Xdisplay, dw, gc, r.left + actual_offset.x, r.top + actual_offset.y, - r.Width() - 1, r.Height() - 1, 0, 360 * 64); - } - if(!IsNull(pencolor) && !IsNull(pen)) { - SetForeground(pencolor); - XDrawArc(Xdisplay, dw, gc, r.left + actual_offset.x, r.top + actual_offset.y, - r.Width() - 1, r.Height() - 1, 0, 360 * 64); - } -} - -void SystemDraw::DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color) -{ - DrawLock __; - XGCValues gcv, gcv_old; - XGetGCValues(Xdisplay, GetGC(), GCForeground, &gcv_old); - Point offset = GetOffset(); - gcv.foreground = GetXPixel(color); - XChangeGC(Xdisplay, GetGC(), GCForeground, &gcv); - Point centre = rc.CenterPoint(); - int angle1 = fround(360 * 64 / (2 * M_PI) * - atan2(centre.y - start.y, start.x - centre.x)); - int angle2 = fround(360 * 64 / (2 * M_PI) * - atan2(centre.y - end.y, end.x - centre.x)); - if(angle2 <= angle1) - angle2 += 360 * 64; - angle2 -= angle1; - XDrawArc(Xdisplay, GetDrawable(), GetGC(), rc.left + offset.x, rc.top + offset.y, - rc.Width(), rc.Height(), angle1, angle2); - XChangeGC(Xdisplay, GetGC(), GCForeground, &gcv_old); -} - -#endif - -END_UPP_NAMESPACE +#include "SystemDraw.h" + +NAMESPACE_UPP + +#ifdef PLATFORM_X11 + +#define LLOG(x) // LOG(x) +#define LTIMING(x) // TIMING(x) + +void SystemDraw::BeginOp() +{ + Cloff f = cloff.Top(); + Vector newclip; + newclip <<= clip.Top(); + f.clipi = clip.GetCount(); + clip.Add() = newclip; + cloff.Add(f); +} + +void SystemDraw::OffsetOp(Point p) +{ + Cloff f = cloff.Top(); + f.offseti = offset.GetCount(); + actual_offset += p; + offset.Add(actual_offset); + cloff.Add(f); +} + +bool SystemDraw::ClipOp(const Rect& r) +{ + LLOG("SystemDraw::ClipOp(" << r << ")"); + Cloff f = cloff.Top(); + bool ch = false; + Vector newclip = Intersect(clip.Top(), r + actual_offset, ch); + if(ch) { + f.clipi = clip.GetCount(); + clip.Add() = newclip; + } + cloff.Add(f); + if(ch) + SetClip(); + return clip.Top().GetCount(); +} + +bool SystemDraw::ClipoffOp(const Rect& r) +{ + LLOG("SystemDraw::ClipOffOp(" << r << ")"); + Cloff f = cloff.Top(); + bool ch = false; + Vector newclip = Intersect(clip.Top(), r + actual_offset, ch); + if(ch) { + f.clipi = clip.GetCount(); + clip.Add() = newclip; + } + f.offseti = offset.GetCount(); + actual_offset += r.TopLeft(); + offset.Add(actual_offset); + cloff.Add(f); + if(ch) + SetClip(); + return clip.Top().GetCount(); +} + +void SystemDraw::EndOp() +{ + ASSERT(cloff.GetCount()); + cloff.Drop(); + actual_offset = offset[cloff.Top().offseti]; + clip.SetCount(cloff.Top().clipi + 1); + SetClip(); +} + +bool SystemDraw::ExcludeClipOp(const Rect& r) +{ + LLOG("SystemDraw::ExcludeClipOp(" << r << ")"); + CloneClip(); + Vector& cl = clip.Top(); + bool ch = false; + Vector ncl = Subtract(cl, r + actual_offset, ch); + if(ch) { + cl = ncl; + SetClip(); + } + return clip.Top().GetCount(); +} + +bool SystemDraw::IntersectClipOp(const Rect& r) +{ + CloneClip(); + Vector& cl = clip.Top(); + bool ch = false; + Vector ncl = Intersect(cl, r + actual_offset, ch); + if(ch) { + cl = ncl; + SetClip(); + } + return clip.Top().GetCount(); +} + +bool SystemDraw::IsPaintingOp(const Rect& r) const +{ + LTIMING("IsPaintingOp"); + Rect rr = r + actual_offset; + const Vector& cl = clip[cloff.Top().clipi]; + for(int i = 0; i < cl.GetCount(); i++) + if(cl[i].Intersects(rr)) + return true; + return false; +} + +void SystemDraw::DrawRectOp(int x, int y, int cx, int cy, Color color) +{ + LTIMING("DrawRect"); + GuiLock __; + LLOG("DrawRect " << RectC(x, y, cx, cy) << ": " << color); + if(IsNull(color)) return; + if(cx <= 0 || cy <= 0) return; + if(color == InvertColor) { + XSetFunction(Xdisplay, gc, GXinvert); + XFillRectangle(Xdisplay, dw, gc, x + actual_offset.x, y + actual_offset.y, cx, cy); + XSetFunction(Xdisplay, gc, GXcopy); + } + else { + SetForeground(color); + XFillRectangle(Xdisplay, dw, gc, x + actual_offset.x, y + actual_offset.y, cx, cy); + } +} + +void SystemDraw::DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color) +{ + GuiLock __; + if(IsNull(width) || IsNull(color)) return; + SetLineStyle(width); + SetForeground(color); + XDrawLine(Xdisplay, dw, gc, + x1 + actual_offset.x, y1 + actual_offset.y, + x2 + actual_offset.x, y2 + actual_offset.y); +} + +void SystemDraw::DrawPolyPolylineOp(const Point *vertices, int vertex_count, + const int *counts, int count_count, + int width, Color color, Color doxor) +{ + GuiLock __; + ASSERT(count_count > 0 && vertex_count > 0); + if(vertex_count < 2 || IsNull(color)) + return; + XGCValues gcv_old, gcv_new; + XGetGCValues(Xdisplay, GetGC(), GCForeground | GCLineWidth | GCFunction, &gcv_old); + gcv_new.function = IsNull(doxor) ? X11_ROP2_COPY : X11_ROP2_XOR; + gcv_new.foreground = GetXPixel(color) ^ (IsNull(doxor) ? 0 : GetXPixel(doxor)); + gcv_new.line_width = width; + XChangeGC(Xdisplay, GetGC(), GCForeground | GCLineWidth | GCFunction, &gcv_new); + enum { REQUEST_LENGTH = 256 }; // X server XDrawLines request length (heuristic) + Point offset = GetOffset(); + if(vertex_count == 2) + XDrawLine(Xdisplay, GetDrawable(), GetGC(), + vertices[0].x + offset.x, vertices[0].y + offset.y, + vertices[1].x + offset.x, vertices[1].y + offset.y); + else if(count_count == 1 || vertex_count > count_count * (REQUEST_LENGTH + 2)) { + for(; --count_count >= 0; counts++) + { + Buffer part(*counts); + for(XPoint *vo = part, *ve = vo + *counts; vo < ve; vo++, vertices++) + { + vo -> x = (short)(vertices -> x + offset.x); + vo -> y = (short)(vertices -> y + offset.y); + } + XDrawLines(Xdisplay, GetDrawable(), GetGC(), part, *counts, CoordModeOrigin); + } + } + else { + int segment_count = vertex_count - count_count; + Buffer segments(segment_count); + XSegment *so = segments; + while(--count_count >= 0) + { + const Point *end = vertices + *counts++; + so -> x1 = (short)(vertices -> x + offset.x); + so -> y1 = (short)(vertices -> y + offset.y); + vertices++; + so -> x2 = (short)(vertices -> x + offset.x); + so -> y2 = (short)(vertices -> y + offset.y); + so++; + while(++vertices < end) { + so -> x1 = so[-1].x2; + so -> y1 = so[-1].y2; + so -> x2 = (short)(vertices -> x + offset.x); + so -> y2 = (short)(vertices -> y + offset.y); + so++; + } + } + ASSERT(so == segments + segment_count); + XDrawSegments(Xdisplay, GetDrawable(), GetGC(), segments, segment_count); + } + XChangeGC(Xdisplay, GetGC(), GCForeground | GCLineWidth | GCFunction, &gcv_old); +} + +static void DrawPolyPolyPolygonRaw(SystemDraw& draw, const Point *vertices, int vertex_count, + const int *subpolygon_counts, int subpolygon_count_count, const int *, int) +{ + GuiLock __; + Point offset = draw.GetOffset(); + const Point *in = vertices; + for(int i = 0; i < subpolygon_count_count; i++) { + int n = subpolygon_counts[i]; + Buffer out_points(n); + XPoint *t = out_points; + XPoint *e = t + n; + while(t < e) { + t->x = (short)(in->x + offset.x); + t->y = (short)(in->y + offset.y); + t++; + in++; + } + XFillPolygon(Xdisplay, draw.GetDrawable(), draw.GetGC(), out_points, n, Nonconvex, CoordModeOrigin); + } +} + +void SystemDraw::DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, + const int *subpolygon_counts, int subpolygon_count_count, + const int *disjunct_polygon_counts, int disjunct_polygon_count_count, + Color color, int width, Color outline, uint64 pattern, Color doxor) +{ + GuiLock __; + if(vertex_count == 0) + return; + + bool is_xor = !IsNull(doxor); + XGCValues gcv_old, gcv_new; + XGetGCValues(Xdisplay, GetGC(), GCForeground | GCFunction | GCLineWidth, &gcv_old); + unsigned xor_pixel = (is_xor ? GetXPixel(doxor) : 0); + if(!IsNull(color)) + { + gcv_new.foreground = GetXPixel(color) ^ xor_pixel; + gcv_new.function = is_xor ? X11_ROP2_XOR : X11_ROP2_COPY; + XChangeGC(Xdisplay, GetGC(), GCForeground | GCFunction, &gcv_new); + DrawPolyPolyPolygonRaw(*this, vertices, vertex_count, + subpolygon_counts, subpolygon_count_count, + disjunct_polygon_counts, disjunct_polygon_count_count); + } + if(!IsNull(outline)) + { + gcv_new.foreground = GetXPixel(outline) ^ xor_pixel; + gcv_new.line_width = width; + XChangeGC(Xdisplay, GetGC(), GCForeground | GCLineWidth, &gcv_new); + Point offset = GetOffset(); + for(const int *sp = subpolygon_counts, *se = sp + subpolygon_count_count; sp < se; sp++) + { + Buffer segment(*sp + 1); + XPoint *out = segment; + for(const Point *end = vertices + *sp; vertices < end; vertices++, out++) + { + out -> x = (short)(vertices -> x + offset.x); + out -> y = (short)(vertices -> y + offset.y); + } + *out = segment[0]; + XDrawLines(Xdisplay, GetDrawable(), GetGC(), segment, *sp + 1, CoordModeOrigin); + } + } + XChangeGC(Xdisplay, GetGC(), GCForeground | GCFunction | GCLineWidth, &gcv_old); +} + +void SystemDraw::DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor) +{ + GuiLock __; + SetLineStyle(pen); + if(!IsNull(color)) { + SetForeground(color); + XFillArc(Xdisplay, dw, gc, r.left + actual_offset.x, r.top + actual_offset.y, + r.Width() - 1, r.Height() - 1, 0, 360 * 64); + } + if(!IsNull(pencolor) && !IsNull(pen)) { + SetForeground(pencolor); + XDrawArc(Xdisplay, dw, gc, r.left + actual_offset.x, r.top + actual_offset.y, + r.Width() - 1, r.Height() - 1, 0, 360 * 64); + } +} + +void SystemDraw::DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color) +{ + GuiLock __; + XGCValues gcv, gcv_old; + XGetGCValues(Xdisplay, GetGC(), GCForeground, &gcv_old); + Point offset = GetOffset(); + gcv.foreground = GetXPixel(color); + XChangeGC(Xdisplay, GetGC(), GCForeground, &gcv); + Point centre = rc.CenterPoint(); + int angle1 = fround(360 * 64 / (2 * M_PI) * + atan2(centre.y - start.y, start.x - centre.x)); + int angle2 = fround(360 * 64 / (2 * M_PI) * + atan2(centre.y - end.y, end.x - centre.x)); + if(angle2 <= angle1) + angle2 += 360 * 64; + angle2 -= angle1; + XDrawArc(Xdisplay, GetDrawable(), GetGC(), rc.left + offset.x, rc.top + offset.y, + rc.Width(), rc.Height(), angle1, angle2); + XChangeGC(Xdisplay, GetGC(), GCForeground, &gcv_old); +} + +#endif + +END_UPP_NAMESPACE diff --git a/uppsrc/CtrlCore/DrawTextWin32.cpp b/uppsrc/CtrlCore/DrawTextWin32.cpp index 390f6ec2f..06c082a0a 100644 --- a/uppsrc/CtrlCore/DrawTextWin32.cpp +++ b/uppsrc/CtrlCore/DrawTextWin32.cpp @@ -1,4 +1,4 @@ -#include "Draw.h" +#include "SystemDraw.h" NAMESPACE_UPP @@ -22,7 +22,7 @@ void SystemDraw::DrawTextOp(int x, int y, int angle, const wchar *text, Font fon n -= 30000; text += 30000; } - DrawLock __; + GuiLock __; COLORREF cr = GetColor(ink); if(cr != lastTextColor) { LLOG("Setting text color: " << ink); diff --git a/uppsrc/CtrlCore/DrawTextX11.cpp b/uppsrc/CtrlCore/DrawTextX11.cpp index f483cdbb4..3078aea47 100644 --- a/uppsrc/CtrlCore/DrawTextX11.cpp +++ b/uppsrc/CtrlCore/DrawTextX11.cpp @@ -1,207 +1,207 @@ -#include "Draw.h" - -NAMESPACE_UPP - -#ifdef PLATFORM_X11 - -#define LTIMING(x) -#define LLOG(x) - -int gtk_antialias = -1; -int gtk_hinting = -1; -String gtk_hintstyle; -String gtk_rgba; - -XftFont *CreateXftFont(Font font, int angle) -{ - LTIMING("CreateXftFont"); - XftFont *xftfont; - double sina, cosa; - Std(font); - int hg = abs(font.GetHeight()); - if(hg == 0) hg = 10; - int i = font.GetFace(); - if(i < 0 || i >= Font::GetFaceCount()) - i = 0; - String face = font.GetFaceName(); - FcPattern *p = FcPatternCreate(); - FcPatternAddString(p, FC_FAMILY, (FcChar8*)~face); - FcPatternAddInteger(p, FC_SLANT, font.IsItalic() ? 110 : 0); - FcPatternAddInteger(p, FC_PIXEL_SIZE, hg); - FcPatternAddInteger(p, FC_WEIGHT, font.IsBold() ? 200 : 100); - FcPatternAddBool(p, FC_MINSPACE, 1); - if(angle) { - FcMatrix mx; - Draw::SinCos(angle, sina, cosa); - mx.xx = cosa; - mx.xy = -sina; - mx.yx = sina; - mx.yy = cosa; - FcPatternAddMatrix(p, FC_MATRIX, &mx); - } - FcResult result; - FcPattern *m = XftFontMatch(Xdisplay, Xscreenno, p, &result); - if(font.IsNonAntiAliased() || gtk_antialias >= 0) { - FcPatternDel(m, FC_ANTIALIAS); - FcPatternAddBool(m, FC_ANTIALIAS, - font.IsNonAntiAliased() ? FcFalse : gtk_antialias ? FcTrue : FcFalse); - } - if(gtk_hinting >= 0) { - FcPatternDel(m, FC_HINTING); - FcPatternAddBool(m, FC_HINTING, gtk_hinting); - } - const char *hs[] = { "hintnone", "hintslight", "hintmedium", "hintfull" }; - for(int i = 0; i < 4; i++) - if(gtk_hintstyle == hs[i]) { - FcPatternDel(m, FC_HINT_STYLE); - FcPatternAddInteger(m, FC_HINT_STYLE, i); - } - const char *rgba[] = { "_", "rgb", "bgr", "vrgb", "vbgr" }; - for(int i = 0; i < __countof(rgba); i++) - if(gtk_rgba == rgba[i]) { - FcPatternDel(m, FC_RGBA); - FcPatternAddInteger(m, FC_RGBA, i); - } - xftfont = XftFontOpenPattern(Xdisplay, m); - FcPatternDestroy(p); - return xftfont; -} - -#define FONTCACHE 37 - -struct XftEntry { - Font font; - int angle; - XftFont *xftfont; -}; - -XftFont *GetXftFont(Font fnt, int angle) -{ - static XftEntry cache[FONTCACHE]; - ONCELOCK { - for(int i = 0; i < FONTCACHE; i++) - cache[i].font.Height(-30000); - } - XftEntry be; - be = cache[0]; - for(int i = 0; i < FONTCACHE; i++) { - XftEntry e = cache[i]; - if(i) - cache[i] = be; - if(e.font == fnt && e.angle == angle) { - if(i) - cache[0] = e; - return e.xftfont; - } - be = e; - } - if(be.xftfont) { - XftFontClose(Xdisplay, be.xftfont); - } - be.font = fnt; - be.angle = angle; - be.xftfont = CreateXftFont(fnt, angle); - cache[0] = be; - return be.xftfont; -} - -void SystemDraw::DrawTextOp(int x, int y, int angle, const wchar *text, Font font, - Color ink, int n, const int *dx) { - DrawLock __; - LTIMING("DrawText"); - LLOG("DrawText " << ToUtf8(WString(text, n)) << " color:" << ink << " font:" << font); - //TODO - X11 seems to crash when displaying too long strings (?) - int ox = x + actual_offset.x; - int oy = y + actual_offset.y; - SetForeground(ink); - XftColor c; - c.color.red = ink.GetR() << 8; - c.color.green = ink.GetG() << 8; - c.color.blue = ink.GetB() << 8; - c.color.alpha = 0xffff; - c.pixel = GetXPixel(ink.GetR(), ink.GetG(), ink.GetB()); - XftFont *xftfont = GetXftFont(font, angle); - Size offset = Point(0, 0); - double sina, cosa; - int ascent = font.Info().GetAscent(); - if(angle) { - SinCos(angle, sina, cosa); - offset.cx = fround(ascent * sina); - offset.cy = fround(ascent * cosa); - } - int hg = abs(font.GetHeight()); - if(hg == 0) hg = 10; - int underline_thickness = max(hg / 20, 1); - int underline_position = max(hg / 15, int(font.Info().GetDescent() > 0)); - if(angle) { - int xpos = 0; - for(int i = 0; i < n; i++) { - wchar h = text[i]; - XftDrawString16(xftdraw, &c, xftfont, - int(ox + xpos * cosa + offset.cx), - int(oy - xpos * sina + offset.cy), - (FcChar16 *)&h, 1); - xpos += dx ? dx[i] : lastFont[text[i]]; - } - if(font.IsUnderline() || font.IsStrikeout()) { - x += offset.cx; - y += offset.cy; - if(font.IsUnderline()) - DrawLine( - int(x + underline_position * sina), - int(y + underline_position * cosa), - int(x + xpos * cosa + underline_position * sina), - int(y - xpos * sina + underline_position * cosa), - underline_thickness, - ink - ); - if(font.IsStrikeout()) { - int p = 2 * ascent / 3; - DrawLine( - int(x + p * sina), - int(y + p * cosa), - int(x + xpos * cosa + p * sina), - int(y - xpos * sina + p * cosa), - underline_thickness, - ink - ); - } - } - } - else { - if(dx) { - int xpos = ox; - Buffer ch(n); - for(int i = 0; i < n; i++) { - ch[i].ucs4 = text[i]; - ch[i].x = xpos; - ch[i].y = oy + ascent; - xpos += dx[i]; - } - XftDrawCharSpec(xftdraw, &c, xftfont, ch, n); - } - else - XftDrawString16(xftdraw, &c, xftfont, ox, oy + ascent, - (FcChar16 *)text, n); - LLOG("XftColor: r=" << c.color.red << ", g=" << c.color.green << ", b=" << c.color.blue - << ", alpha=" << c.color.alpha << ", pixel=" << FormatIntHex(c.pixel)); - if(font.IsUnderline() || font.IsStrikeout()) { - int cx; - if(dx && n > 0) { - cx = 0; - Sum(cx, dx, dx + n - 1); - cx += lastFont[text[n - 1]]; - } - else - cx = GetTextSize(text, font, n).cx; - if(font.IsUnderline()) - DrawRect(x, y + ascent + underline_position, cx, underline_thickness, ink); - if(font.IsStrikeout()) - DrawRect(x, y + 2 * ascent / 3, cx, underline_thickness, ink); - } - } -} - -#endif - -END_UPP_NAMESPACE +#include "SystemDraw.h" + +NAMESPACE_UPP + +#ifdef PLATFORM_X11 + +#define LTIMING(x) +#define LLOG(x) + +int gtk_antialias = -1; +int gtk_hinting = -1; +String gtk_hintstyle; +String gtk_rgba; + +XftFont *CreateXftFont(Font font, int angle) +{ + LTIMING("CreateXftFont"); + XftFont *xftfont; + double sina, cosa; + Std(font); + int hg = abs(font.GetHeight()); + if(hg == 0) hg = 10; + int i = font.GetFace(); + if(i < 0 || i >= Font::GetFaceCount()) + i = 0; + String face = font.GetFaceName(); + FcPattern *p = FcPatternCreate(); + FcPatternAddString(p, FC_FAMILY, (FcChar8*)~face); + FcPatternAddInteger(p, FC_SLANT, font.IsItalic() ? 110 : 0); + FcPatternAddInteger(p, FC_PIXEL_SIZE, hg); + FcPatternAddInteger(p, FC_WEIGHT, font.IsBold() ? 200 : 100); + FcPatternAddBool(p, FC_MINSPACE, 1); + if(angle) { + FcMatrix mx; + Draw::SinCos(angle, sina, cosa); + mx.xx = cosa; + mx.xy = -sina; + mx.yx = sina; + mx.yy = cosa; + FcPatternAddMatrix(p, FC_MATRIX, &mx); + } + FcResult result; + FcPattern *m = XftFontMatch(Xdisplay, Xscreenno, p, &result); + if(font.IsNonAntiAliased() || gtk_antialias >= 0) { + FcPatternDel(m, FC_ANTIALIAS); + FcPatternAddBool(m, FC_ANTIALIAS, + font.IsNonAntiAliased() ? FcFalse : gtk_antialias ? FcTrue : FcFalse); + } + if(gtk_hinting >= 0) { + FcPatternDel(m, FC_HINTING); + FcPatternAddBool(m, FC_HINTING, gtk_hinting); + } + const char *hs[] = { "hintnone", "hintslight", "hintmedium", "hintfull" }; + for(int i = 0; i < 4; i++) + if(gtk_hintstyle == hs[i]) { + FcPatternDel(m, FC_HINT_STYLE); + FcPatternAddInteger(m, FC_HINT_STYLE, i); + } + const char *rgba[] = { "_", "rgb", "bgr", "vrgb", "vbgr" }; + for(int i = 0; i < __countof(rgba); i++) + if(gtk_rgba == rgba[i]) { + FcPatternDel(m, FC_RGBA); + FcPatternAddInteger(m, FC_RGBA, i); + } + xftfont = XftFontOpenPattern(Xdisplay, m); + FcPatternDestroy(p); + return xftfont; +} + +#define FONTCACHE 37 + +struct XftEntry { + Font font; + int angle; + XftFont *xftfont; +}; + +XftFont *GetXftFont(Font fnt, int angle) +{ + static XftEntry cache[FONTCACHE]; + ONCELOCK { + for(int i = 0; i < FONTCACHE; i++) + cache[i].font.Height(-30000); + } + XftEntry be; + be = cache[0]; + for(int i = 0; i < FONTCACHE; i++) { + XftEntry e = cache[i]; + if(i) + cache[i] = be; + if(e.font == fnt && e.angle == angle) { + if(i) + cache[0] = e; + return e.xftfont; + } + be = e; + } + if(be.xftfont) { + XftFontClose(Xdisplay, be.xftfont); + } + be.font = fnt; + be.angle = angle; + be.xftfont = CreateXftFont(fnt, angle); + cache[0] = be; + return be.xftfont; +} + +void SystemDraw::DrawTextOp(int x, int y, int angle, const wchar *text, Font font, + Color ink, int n, const int *dx) { + GuiLock __; + LTIMING("DrawText"); + LLOG("DrawText " << ToUtf8(WString(text, n)) << " color:" << ink << " font:" << font); + //TODO - X11 seems to crash when displaying too long strings (?) + int ox = x + actual_offset.x; + int oy = y + actual_offset.y; + SetForeground(ink); + XftColor c; + c.color.red = ink.GetR() << 8; + c.color.green = ink.GetG() << 8; + c.color.blue = ink.GetB() << 8; + c.color.alpha = 0xffff; + c.pixel = GetXPixel(ink.GetR(), ink.GetG(), ink.GetB()); + XftFont *xftfont = GetXftFont(font, angle); + Size offset = Point(0, 0); + double sina, cosa; + int ascent = font.Info().GetAscent(); + if(angle) { + SinCos(angle, sina, cosa); + offset.cx = fround(ascent * sina); + offset.cy = fround(ascent * cosa); + } + int hg = abs(font.GetHeight()); + if(hg == 0) hg = 10; + int underline_thickness = max(hg / 20, 1); + int underline_position = max(hg / 15, int(font.Info().GetDescent() > 0)); + if(angle) { + int xpos = 0; + for(int i = 0; i < n; i++) { + wchar h = text[i]; + XftDrawString16(xftdraw, &c, xftfont, + int(ox + xpos * cosa + offset.cx), + int(oy - xpos * sina + offset.cy), + (FcChar16 *)&h, 1); + xpos += dx ? dx[i] : lastFont[text[i]]; + } + if(font.IsUnderline() || font.IsStrikeout()) { + x += offset.cx; + y += offset.cy; + if(font.IsUnderline()) + DrawLine( + int(x + underline_position * sina), + int(y + underline_position * cosa), + int(x + xpos * cosa + underline_position * sina), + int(y - xpos * sina + underline_position * cosa), + underline_thickness, + ink + ); + if(font.IsStrikeout()) { + int p = 2 * ascent / 3; + DrawLine( + int(x + p * sina), + int(y + p * cosa), + int(x + xpos * cosa + p * sina), + int(y - xpos * sina + p * cosa), + underline_thickness, + ink + ); + } + } + } + else { + if(dx) { + int xpos = ox; + Buffer ch(n); + for(int i = 0; i < n; i++) { + ch[i].ucs4 = text[i]; + ch[i].x = xpos; + ch[i].y = oy + ascent; + xpos += dx[i]; + } + XftDrawCharSpec(xftdraw, &c, xftfont, ch, n); + } + else + XftDrawString16(xftdraw, &c, xftfont, ox, oy + ascent, + (FcChar16 *)text, n); + LLOG("XftColor: r=" << c.color.red << ", g=" << c.color.green << ", b=" << c.color.blue + << ", alpha=" << c.color.alpha << ", pixel=" << FormatIntHex(c.pixel)); + if(font.IsUnderline() || font.IsStrikeout()) { + int cx; + if(dx && n > 0) { + cx = 0; + Sum(cx, dx, dx + n - 1); + cx += lastFont[text[n - 1]]; + } + else + cx = GetTextSize(text, font, n).cx; + if(font.IsUnderline()) + DrawRect(x, y + ascent + underline_position, cx, underline_thickness, ink); + if(font.IsStrikeout()) + DrawRect(x, y + 2 * ascent / 3, cx, underline_thickness, ink); + } + } +} + +#endif + +END_UPP_NAMESPACE diff --git a/uppsrc/CtrlCore/DrawWin32.cpp b/uppsrc/CtrlCore/DrawWin32.cpp index 9b9b695e4..137bca3b7 100644 --- a/uppsrc/CtrlCore/DrawWin32.cpp +++ b/uppsrc/CtrlCore/DrawWin32.cpp @@ -1,4 +1,4 @@ -#include "Draw.h" +#include "SystemDraw.h" NAMESPACE_UPP @@ -11,7 +11,7 @@ static COLORREF sLightGray; dword SystemDraw::GetInfo() const { - return native || !(style & DOTS) ? style|NATIVE : style; + return DATABANDS|(native || !(style & DOTS) ? style|NATIVE : style); } Size SystemDraw::GetPageSize() const @@ -110,7 +110,7 @@ void SystemDraw::InitColors() void SystemDraw::SetColor(Color color) { - DrawLock __; + GuiLock __; LLOG("SetColor " << color); if(color != lastColor) { LLOG("Setting, lastColor:" << FormatIntHex(lastColor.GetRaw()) @@ -133,7 +133,7 @@ void SystemDraw::SetColor(Color color) } void SystemDraw::SetDrawPen(int width, Color color) { - DrawLock __; + GuiLock __; if(IsNull(width)) width = PEN_NULL; if(width != lastPen || color != lastPenColor) { @@ -155,7 +155,7 @@ void SystemDraw::SetDrawPen(int width, Color color) { } void SystemDraw::SetOrg() { - DrawLock __; + GuiLock __; #ifdef PLATFORM_WINCE ::SetViewportOrgEx(handle, actual_offset.x, actual_offset.y, 0); #else @@ -167,26 +167,26 @@ void SystemDraw::SetOrg() { #ifndef PLATFORM_WINCE Point SystemDraw::LPtoDP(Point p) const { - DrawLock __; + GuiLock __; ::LPtoDP(handle, p, 1); return p; } Point SystemDraw::DPtoLP(Point p) const { - DrawLock __; + GuiLock __; ::DPtoLP(handle, p, 1); return p; } Rect SystemDraw::LPtoDP(const Rect& r) const { - DrawLock __; + GuiLock __; Rect w = r; ::LPtoDP(handle, reinterpret_cast(&w), 2); return w; } Rect SystemDraw::DPtoLP(const Rect& r) const { - DrawLock __; + GuiLock __; Rect w = r; ::LPtoDP(handle, reinterpret_cast(&w), 2); return w; @@ -194,7 +194,7 @@ Rect SystemDraw::DPtoLP(const Rect& r) const { #endif Size SystemDraw::GetSizeCaps(int i, int j) const { - DrawLock __; + GuiLock __; return Size(GetDeviceCaps(handle, i), GetDeviceCaps(handle, j)); } @@ -232,7 +232,7 @@ int SystemDraw::GetCloffLevel() const } void SystemDraw::LoadCaps() { - DrawLock __; + GuiLock __; color16 = false; palette = (GetDeviceCaps(handle, RASTERCAPS) & RC_PALETTE); if(palette) @@ -243,7 +243,7 @@ void SystemDraw::LoadCaps() { } void SystemDraw::Cinit() { - DrawLock __; + GuiLock __; lastColor = Color::FromCR(COLORREF(-5)); lastPenColor = Color::FromCR(COLORREF(-5)); lastTextColor = COLORREF(-1); @@ -253,7 +253,7 @@ void SystemDraw::Cinit() { } void SystemDraw::Init() { - DrawLock __; + GuiLock __; Cinit(); SetBkMode(handle, TRANSPARENT); ::SetTextAlign(handle, TA_BASELINE); @@ -266,12 +266,12 @@ void SystemDraw::Init() { } void SystemDraw::Reset() { - DrawLock __; + GuiLock __; style = GUI; } SystemDraw::SystemDraw() { - DrawLock __; + GuiLock __; native = 0; InitColors(); actual_offset = Point(0, 0); @@ -280,7 +280,7 @@ SystemDraw::SystemDraw() { } SystemDraw::SystemDraw(HDC hdc) { - DrawLock __; + GuiLock __; native = 0; InitColors(); Reset(); @@ -288,7 +288,7 @@ SystemDraw::SystemDraw(HDC hdc) { } void SystemDraw::Unselect0() { - DrawLock __; + GuiLock __; if(orgPen) SelectObject(handle, orgPen); if(orgBrush) SelectObject(handle, orgBrush); if(actPen) DeleteObject(actPen); @@ -297,33 +297,33 @@ void SystemDraw::Unselect0() { } void SystemDraw::Unselect() { - DrawLock __; + GuiLock __; while(cloff.GetCount()) End(); Unselect0(); } SystemDraw::~SystemDraw() { - DrawLock __; + GuiLock __; if(handle) Unselect(); } HDC SystemDraw::BeginGdi() { - DrawLock __; + GuiLock __; Begin(); return handle; } void SystemDraw::EndGdi() { - DrawLock __; + GuiLock __; Unselect0(); End(); } void BackDraw::Create(SystemDraw& w, int cx, int cy) { ASSERT(w.GetHandle()); - DrawLock __; + GuiLock __; Destroy(); size.cx = cx; size.cy = cy; @@ -342,7 +342,7 @@ void BackDraw::Create(SystemDraw& w, int cx, int cy) { } void BackDraw::Put(SystemDraw& w, int x, int y) { - DrawLock __; + GuiLock __; ASSERT(handle); LTIMING("BackDraw::Put"); #ifdef PLATFORM_WINCE @@ -354,7 +354,7 @@ void BackDraw::Put(SystemDraw& w, int x, int y) { } void BackDraw::Destroy() { - DrawLock __; + GuiLock __; if(handle) { Unselect(); ::SelectObject(handle, hbmpold); @@ -365,7 +365,7 @@ void BackDraw::Destroy() { } ScreenDraw::ScreenDraw(bool ic) { - DrawLock __; + GuiLock __; #ifdef PLATFORM_WINCE Attach(CreateDC(NULL, NULL, NULL, NULL)); #else @@ -378,7 +378,7 @@ ScreenDraw::ScreenDraw(bool ic) { } ScreenDraw::~ScreenDraw() { - DrawLock __; + GuiLock __; Unselect(); DeleteDC(handle); } @@ -387,7 +387,7 @@ ScreenDraw::~ScreenDraw() { void PrintDraw::InitPrinter() { - DrawLock __; + GuiLock __; Init(); style = PRINTER|DOTS; DotsMode(); @@ -400,7 +400,7 @@ void PrintDraw::InitPrinter() void PrintDraw::StartPage() { - DrawLock __; + GuiLock __; if(aborted) return; Unselect(); if(::StartPage(handle) <= 0) @@ -411,7 +411,7 @@ void PrintDraw::StartPage() void PrintDraw::EndPage() { - DrawLock __; + GuiLock __; if(aborted) return; Unselect(); if(::EndPage(handle) <= 0) @@ -421,7 +421,7 @@ void PrintDraw::EndPage() PrintDraw::PrintDraw(HDC hdc, const char *docname) : SystemDraw(hdc) { - DrawLock __; + GuiLock __; DOCINFO di; memset(&di, 0, sizeof(di)); di.cbSize = sizeof(di); @@ -434,7 +434,7 @@ PrintDraw::PrintDraw(HDC hdc, const char *docname) } PrintDraw::~PrintDraw() { - DrawLock __; + GuiLock __; if(aborted) ::AbortDoc(handle); else @@ -445,16 +445,6 @@ PrintDraw::~PrintDraw() { #endif -bool ScreenInPaletteMode() -{ - return ScreenInfo().PaletteMode(); -} - -Size GetScreenSize() -{ - return ScreenInfo().GetPageSize(); -} - #endif END_UPP_NAMESPACE diff --git a/uppsrc/CtrlCore/DrawWin32.h b/uppsrc/CtrlCore/DrawWin32.h index e225c6ed2..cd81e682f 100644 --- a/uppsrc/CtrlCore/DrawWin32.h +++ b/uppsrc/CtrlCore/DrawWin32.h @@ -1,5 +1,7 @@ #ifdef PLATFORM_WIN32 +NAMESPACE_UPP + class SystemDraw : public Draw { public: virtual dword GetInfo() const; @@ -253,4 +255,9 @@ inline void DrawEllipse(HDC hdc, const Rect& rc) { Ellipse(hdc, inline void DrawRect(HDC hdc, const Rect& rc) { Rectangle(hdc, rc.left, rc.top, rc.right, rc.bottom); } +HDC ScreenHDC(); +HPALETTE GetQlibPalette(); + +END_UPP_NAMESPACE + #endif diff --git a/uppsrc/CtrlCore/DrawX11.cpp b/uppsrc/CtrlCore/DrawX11.cpp index 046745bbe..b9ed0f864 100644 --- a/uppsrc/CtrlCore/DrawX11.cpp +++ b/uppsrc/CtrlCore/DrawX11.cpp @@ -1,452 +1,452 @@ -#include "Draw.h" - -#ifdef PLATFORM_X11 - -#define Time XTime -#define Font XFont -#define Display XDisplay -#define Picture XPicture - -#ifndef flagNOGTK -#include -#include -#include -#endif - -#undef Picture -#undef Time -#undef Font -#undef Display - -NAMESPACE_UPP - -#define LLOG(x) //LOG(x) -#define LTIMING(x) //TIMING(x) - -XDisplay *Xdisplay; -int Xscreenno; -Visual *Xvisual; -Window Xroot; -Screen *Xscreen; -Colormap Xcolormap; -int Xheight; -int Xwidth; -int XheightMM; -int XwidthMM; -int Xdepth; -dword Xblack; -dword Xwhite; -int Xconnection; -byte *Xmapcolor; -byte *Xunmapcolor; -bool Xpalette; - -dword (*Xgetpixel)(int r, int g, int b); - -EXITBLOCK -{ - if(Xdisplay) { -// No CloseDisplay for now... - XCloseDisplay(Xdisplay); - LLOG("Xdisplay closed"); - Xdisplay = NULL; - } - if(Xmapcolor) - delete[] Xmapcolor; - if(Xunmapcolor) - delete[] Xunmapcolor; -} - -void XError() -{ - Panic("X11 error !"); -} - -void XError(const char *s) -{ - Panic(String("X11 error:") + s + " !"); -} - -static int sAcs; - -bool sAllocColor(int xr, int xg, int xb) -{ - XColor ce; - ce.red = xr; - ce.green = xg; - ce.blue = xb; - ce.flags = DoRed | DoGreen | DoBlue; - if(!XAllocColor(Xdisplay, Xcolormap, &ce)) return false; - sAcs++; - return sAcs < 257; -} - -void sAllocColors() -{ - int r, g, b; - for(r = 0; r < 2; r++) - for(g = 0; g < 2; g++) - for(b = 0; b < 2; b++) - if(!sAllocColor(65535 * r, 65535 * g, 65535 * b)) return; - for(r = 0; r < 3; r++) - for(g = 0; g < 3; g++) - for(b = 0; b < 3; b++) - if((r == 1 || g == 1 || b == 1) && - !sAllocColor((65535 * r) / 2, (65535 * g) / 2, (65535 * b) / 2)) return; - for(r = 5; r >= 0; r--) - for(g = 5; g >= 0; g--) - for(b = 5; b >= 0; b--) - if((r != 0 && r != 5 || g != 0 && g != 5 || b != 0 && b != 5) && - !sAllocColor((65535 * r) / 5, (65535 * g) / 5, (65535 * b) / 5)) return; - for(r = 1; r <= 11; r += 2) - if(!sAllocColor((65535 * r) / 11, (65535 * r) / 11, (65535 * r) / 11)) return; - for(int r = 255; r >= 0; r--) - if(!sAllocColor(r << 8, r << 8, r << 8)) return; -} - -dword GetPseudoColorPixel(int r, int g, int b) -{ - return Xmapcolor[r * 11 / 255 * (24 * 12) + g * 23 / 255 * 12 + b * 11 / 255]; -} - -static -struct Xshift { - dword mask; - int bits; - int shift; - dword Do(int c) { return (c >> bits << shift) & mask; } -} -Xred, Xgreen, Xblue; - -Xshift CalcXShift(dword mask) -{ - Xshift f; - f.mask = mask; - f.shift = 0; - f.bits = 0; - while((mask & 1) == 0) { - mask >>= 1; - f.shift++; - } - while((mask & 1) == 1) { - mask >>= 1; - f.bits++; - } - f.bits = 8 - f.bits; - if(f.bits < 0) { - f.shift += f.bits; - f.bits = 0; - } - LLOG("xshift(" << FormatIntHex(mask) << "): mask = " - << FormatIntHex(f.mask) << ", bits = " << f.bits << ", shift = " << f.shift); - return f; -} - -dword GetTrueColorPixel(int r, int g, int b) -{ - return Xred.Do(r) | Xgreen.Do(g) | Xblue.Do(b); -} - -inline int ssq(int x) { return x * x; } - -void InitX11Draw(XDisplay *display) -{ - Xdisplay = display; - if(!Xdisplay) { - puts(NFormat("No X11 display, errno = %d, %s", errno, strerror(errno))); - fflush(stdout); - XError(); - } - int Xscreenno = DefaultScreen(Xdisplay); - Xroot = RootWindow(Xdisplay, Xscreenno); - Xscreen = ScreenOfDisplay(Xdisplay, Xscreenno); - Xcolormap = DefaultColormap(Xdisplay, Xscreenno); -// Xcolormap = (Colormap)GDK().gdk_x11_colormap_get_xcolormap(GDK().gdk_rgb_get_colormap()); - Xheight = DisplayHeight(Xdisplay, Xscreenno); - Xwidth = DisplayWidth(Xdisplay, Xscreenno); - XheightMM = DisplayHeightMM(Xdisplay, Xscreenno); - XwidthMM = DisplayWidthMM(Xdisplay, Xscreenno); - LLOG("Xwidth = " << Xwidth << ", XwidthMM = " << XwidthMM); - LLOG("Xheight = " << Xheight << ", XheightMM = " << XheightMM); - Xdepth = DefaultDepth(Xdisplay, Xscreenno); - Xblack = BlackPixel(Xdisplay, 0); - Xwhite = WhitePixel(Xdisplay, 0); - Xconnection = XConnectionNumber(Xdisplay); - Xvisual = DefaultVisual(Xdisplay, Xscreenno); - Visual *v = Xvisual; - if(v->c_class == TrueColor) { - Xred = CalcXShift(v->red_mask); - Xgreen = CalcXShift(v->green_mask); - Xblue = CalcXShift(v->blue_mask); - Xgetpixel = GetTrueColorPixel; - } - else { - Xpalette = true; - sAllocColors(); - int colorcount = max(1 << Xdepth, 256); - Buffer cs(colorcount); - int i; - for(i = 0; i < colorcount; i++) - cs[i].pixel = i; - XQueryColors(Xdisplay, Xcolormap, cs, colorcount); - Xunmapcolor = new byte[3 * colorcount]; - for(i = 0; i < colorcount; i++) - { - Xunmapcolor[3 * i + 0] = cs[i].blue; - Xunmapcolor[3 * i + 1] = cs[i].green; - Xunmapcolor[3 * i + 2] = cs[i].red; - } - byte *cm = Xmapcolor = new byte[12 * 24 * 12]; - for(int r = 0; r < 12; r++) - for(int g = 0; g < 24; g++) - for(int b = 0; b < 12; b++) { - int mind = INT_MAX; - int mini; - for(int i = 0; i < colorcount; i++) { - int d = ssq(r * 255 / 11 - (cs[i].red >> 8)) + - ssq(g * 255 / 23 - (cs[i].green >> 8)) + - ssq(b * 255 / 11 - (cs[i].blue >> 8)); - if(d < mind) { - mini = i; - mind = d; - } - } - *cm++ = mini; - } - Xgetpixel = GetPseudoColorPixel; - } -// XFree(v); - - Font::SetStdFont(ScreenSans(12)); -} - -void InitX11Draw(const char *dispname) -{ -#ifdef flagNOGTK - if(!dispname || !*dispname) { - int f = Environment().Find("DISPLAY"); - dispname = (f >= 0 ? ~Environment()[f] : ":0.0"); - } - InitX11Draw(XOpenDisplay(dispname)); -#else - MemoryIgnoreLeaksBlock __; - const Vector& cmd = CommandLine(); - char **argv = (char**) MemoryAllocPermanent(sizeof(char *) * cmd.GetCount()); - for(int i = 0; i < cmd.GetCount(); i++) - argv[i] = PermanentCopy(cmd[i]); - int argc = cmd.GetCount(); - gtk_init (&argc, &argv); - GtkWidget *w = gtk_window_new(GTK_WINDOW_TOPLEVEL); - GdkDisplay *d = gtk_widget_get_display(w); - gdk_x11_display_get_xdisplay(d); - InitX11Draw(gdk_x11_display_get_xdisplay(d)); - gtk_widget_destroy(w); -#endif -} - -void SetClip(GC gc, XftDraw *xftdraw, const Vector& cl) -{ - DrawLock __; - LTIMING("SetClip"); - Buffer xr(cl.GetCount()); - LLOG("SetClip"); - for(int i = 0; i < cl.GetCount(); i++) { - XRectangle& r = xr[i]; - const Rect& cr = cl[i]; - LLOG("[" << i << "] = " << cr); - r.x = cr.left; - r.y = cr.top; - r.width = cr.Width(); - r.height = cr.Height(); - } - XSetClipRectangles(Xdisplay, gc, 0, 0, xr, cl.GetCount(), Unsorted); - LLOG("XftDrawSetClipRectangles, # = " << cl.GetCount() << ", xftdraw = " << FormatIntHex(xftdraw)); - XftDrawSetClipRectangles(xftdraw, 0, 0, xr, cl.GetCount()); - LLOG("//XftDrawSetClipRectangles"); -} - -void SystemDraw::CloneClip() -{ - if(cloff.GetCount() > 1 && cloff.Top().clipi == cloff[cloff.GetCount() - 2].clipi) { - cloff.Top().clipi = clip.GetCount(); - Vector& c = clip.Add(); - c <<= clip[clip.GetCount() - 2]; - } -} - -void SystemDraw::SetForeground(Color color) -{ - DrawLock __; - LTIMING("SetForeground"); - int p = GetXPixel(color.GetR(), color.GetG(), color.GetB()); - if(p == foreground) return; - LTIMING("XSetForeground"); - LLOG("XSetForeground " << color); - foreground = p; - XSetForeground(Xdisplay, gc, foreground); -} - -void SystemDraw::SetClip() { - DrawLock __; - if(dw == Xroot) return; - LTIMING("SetClip"); - UPP::SetClip(gc, xftdraw, clip.Top()); -} - -void SystemDraw::SetLineStyle(int width) -{ - DrawLock __; - if(width == linewidth) return; - linewidth = width; - if(IsNull(width)) - width = 1; - if(width < PEN_SOLID) { - static const char dash[] = { 18, 6 }; - static const char dot[] = { 3, 3 }; - static const char dashdot[] = { 9, 6, 3, 6 }; - static const char dashdotdot[] = { 9, 3, 3, 3, 3, 3 }; - static struct { - const char *dash; - int len; - } ds[] = { - { dash, __countof(dash) }, - { dot, __countof(dot) }, - { dashdot, __countof(dashdot) }, - { dashdotdot, __countof(dashdotdot) } - }; - int i = -(width - PEN_DASH); - ASSERT(i >= 0 && i < 4); - XSetDashes(Xdisplay, gc, 0, ds[i].dash, ds[i].len); - } - XSetLineAttributes(Xdisplay, gc, max(width, 1), - width < PEN_SOLID ? LineOnOffDash : LineSolid, CapRound, JoinRound); -} - -void SystemDraw::Init() -{ - DrawLock __; - pageSize = Size(Xwidth, Xheight); - cloff.Clear(); - clip.Clear(); - foreground = linewidth = Null; -} - -void SystemDraw::Init(const Vector& _clip, Point _offset) -{ - DrawLock __; - Init(); - clip.Add() <<= _clip; - offset.Add(_offset); - actual_offset = _offset; - Cloff& f = cloff.Add(); - f.offseti = 0; - f.clipi = 0; - SetClip(); -} - -dword SystemDraw::GetInfo() const -{ - return 0; -} - -Size SystemDraw::GetPageSize() const -{ - return pageSize; -} - -SystemDraw::SystemDraw() -{ - DrawLock __; - dw = None; - gc = None; - actual_offset = Point(0, 0); - Init(); -} - -Size SystemDraw::GetNativeDpi() const -{ - return Size(96, 96); -} - -void SystemDraw::BeginNative() {} -void SystemDraw::EndNative() {} - -int SystemDraw::GetCloffLevel() const -{ - return cloff.GetCount(); -} - -Rect SystemDraw::GetClip() const -{ - LLOG("Draw::GetClipOp; #clip = " << clip.GetCount() << ", #cloff = " << cloff.GetCount() - << ", clipi = " << cloff.Top().clipi); - const Vector& cl = clip[cloff.Top().clipi]; - Rect box(0, 0, 0, 0); - if(!cl.GetCount()) return box; - box = cl[0]; - LLOG("cl[0] = " << box); - for(int i = 1; i < cl.GetCount(); i++) { - LLOG("cl[" << i << "] = " << cl[i]); - box |= cl[i]; - } - LLOG("out box = " << box << ", actual offset = " << actual_offset); - return box - actual_offset; -} - -SystemDraw::SystemDraw(Drawable _dw, GC _gc, XftDraw *_xftdraw, const Vector& _clip) -{ - LLOG("SystemDraw"); - dw = _dw; - gc = _gc; - xftdraw = _xftdraw; - Init(_clip); -} - -void BackDraw::Create(SystemDraw& w, int cx, int cy) -{ - DrawLock __; - LLOG("Creating BackDraw " << cx << "x" << cy); - Destroy(); - size.cx = cx; - size.cy = cy; - dw = XCreatePixmap(Xdisplay, w.GetDrawable(), max(cx, 1), max(cy, 1), Xdepth); - gc = XCreateGC(Xdisplay, dw, 0, 0); - xftdraw = XftDrawCreate(Xdisplay, (Drawable) dw, - DefaultVisual(Xdisplay, Xscreenno), Xcolormap); - Vector clip; - clip.Add(RectC(0, 0, cx, cy)); - Init(clip, Point(0, 0)); -} - -void BackDraw::Put(SystemDraw& w, int x, int y) -{ - DrawLock __; - LLOG("Putting BackDraw"); - ASSERT(dw != None); - XCopyArea(Xdisplay, dw, w.GetDrawable(), w.GetGC(), 0, 0, size.cx, size.cy, - x + w.GetOffset().x, y + w.GetOffset().y); -} - -void BackDraw::Destroy() -{ - DrawLock __; - if(dw != None) { - XftDrawDestroy(xftdraw); - XFreePixmap(Xdisplay, dw); - XFreeGC(Xdisplay, gc); - } -} - -bool ScreenInPaletteMode() -{ - return Xpalette; -} - -Size GetScreenSize() -{ - return Size(Xwidth, Xheight); -} - -END_UPP_NAMESPACE - -#endif +#include "SystemDraw.h" + +#ifdef PLATFORM_X11 + +#define Time XTime +#define Font XFont +#define Display XDisplay +#define Picture XPicture + +#ifndef flagNOGTK +#include +#include +#include +#endif + +#undef Picture +#undef Time +#undef Font +#undef Display + +NAMESPACE_UPP + +#define LLOG(x) //LOG(x) +#define LTIMING(x) //TIMING(x) + +XDisplay *Xdisplay; +int Xscreenno; +Visual *Xvisual; +Window Xroot; +Screen *Xscreen; +Colormap Xcolormap; +int Xheight; +int Xwidth; +int XheightMM; +int XwidthMM; +int Xdepth; +dword Xblack; +dword Xwhite; +int Xconnection; +byte *Xmapcolor; +byte *Xunmapcolor; +bool Xpalette; + +dword (*Xgetpixel)(int r, int g, int b); + +EXITBLOCK +{ + if(Xdisplay) { +// No CloseDisplay for now... + XCloseDisplay(Xdisplay); + LLOG("Xdisplay closed"); + Xdisplay = NULL; + } + if(Xmapcolor) + delete[] Xmapcolor; + if(Xunmapcolor) + delete[] Xunmapcolor; +} + +void XError() +{ + Panic("X11 error !"); +} + +void XError(const char *s) +{ + Panic(String("X11 error:") + s + " !"); +} + +static int sAcs; + +bool sAllocColor(int xr, int xg, int xb) +{ + XColor ce; + ce.red = xr; + ce.green = xg; + ce.blue = xb; + ce.flags = DoRed | DoGreen | DoBlue; + if(!XAllocColor(Xdisplay, Xcolormap, &ce)) return false; + sAcs++; + return sAcs < 257; +} + +void sAllocColors() +{ + int r, g, b; + for(r = 0; r < 2; r++) + for(g = 0; g < 2; g++) + for(b = 0; b < 2; b++) + if(!sAllocColor(65535 * r, 65535 * g, 65535 * b)) return; + for(r = 0; r < 3; r++) + for(g = 0; g < 3; g++) + for(b = 0; b < 3; b++) + if((r == 1 || g == 1 || b == 1) && + !sAllocColor((65535 * r) / 2, (65535 * g) / 2, (65535 * b) / 2)) return; + for(r = 5; r >= 0; r--) + for(g = 5; g >= 0; g--) + for(b = 5; b >= 0; b--) + if((r != 0 && r != 5 || g != 0 && g != 5 || b != 0 && b != 5) && + !sAllocColor((65535 * r) / 5, (65535 * g) / 5, (65535 * b) / 5)) return; + for(r = 1; r <= 11; r += 2) + if(!sAllocColor((65535 * r) / 11, (65535 * r) / 11, (65535 * r) / 11)) return; + for(int r = 255; r >= 0; r--) + if(!sAllocColor(r << 8, r << 8, r << 8)) return; +} + +dword GetPseudoColorPixel(int r, int g, int b) +{ + return Xmapcolor[r * 11 / 255 * (24 * 12) + g * 23 / 255 * 12 + b * 11 / 255]; +} + +static +struct Xshift { + dword mask; + int bits; + int shift; + dword Do(int c) { return (c >> bits << shift) & mask; } +} +Xred, Xgreen, Xblue; + +Xshift CalcXShift(dword mask) +{ + Xshift f; + f.mask = mask; + f.shift = 0; + f.bits = 0; + while((mask & 1) == 0) { + mask >>= 1; + f.shift++; + } + while((mask & 1) == 1) { + mask >>= 1; + f.bits++; + } + f.bits = 8 - f.bits; + if(f.bits < 0) { + f.shift += f.bits; + f.bits = 0; + } + LLOG("xshift(" << FormatIntHex(mask) << "): mask = " + << FormatIntHex(f.mask) << ", bits = " << f.bits << ", shift = " << f.shift); + return f; +} + +dword GetTrueColorPixel(int r, int g, int b) +{ + return Xred.Do(r) | Xgreen.Do(g) | Xblue.Do(b); +} + +inline int ssq(int x) { return x * x; } + +void InitX11Draw(XDisplay *display) +{ + Xdisplay = display; + if(!Xdisplay) { + puts(NFormat("No X11 display, errno = %d, %s", errno, strerror(errno))); + fflush(stdout); + XError(); + } + int Xscreenno = DefaultScreen(Xdisplay); + Xroot = RootWindow(Xdisplay, Xscreenno); + Xscreen = ScreenOfDisplay(Xdisplay, Xscreenno); + Xcolormap = DefaultColormap(Xdisplay, Xscreenno); +// Xcolormap = (Colormap)GDK().gdk_x11_colormap_get_xcolormap(GDK().gdk_rgb_get_colormap()); + Xheight = DisplayHeight(Xdisplay, Xscreenno); + Xwidth = DisplayWidth(Xdisplay, Xscreenno); + XheightMM = DisplayHeightMM(Xdisplay, Xscreenno); + XwidthMM = DisplayWidthMM(Xdisplay, Xscreenno); + LLOG("Xwidth = " << Xwidth << ", XwidthMM = " << XwidthMM); + LLOG("Xheight = " << Xheight << ", XheightMM = " << XheightMM); + Xdepth = DefaultDepth(Xdisplay, Xscreenno); + Xblack = BlackPixel(Xdisplay, 0); + Xwhite = WhitePixel(Xdisplay, 0); + Xconnection = XConnectionNumber(Xdisplay); + Xvisual = DefaultVisual(Xdisplay, Xscreenno); + Visual *v = Xvisual; + if(v->c_class == TrueColor) { + Xred = CalcXShift(v->red_mask); + Xgreen = CalcXShift(v->green_mask); + Xblue = CalcXShift(v->blue_mask); + Xgetpixel = GetTrueColorPixel; + } + else { + Xpalette = true; + sAllocColors(); + int colorcount = max(1 << Xdepth, 256); + Buffer cs(colorcount); + int i; + for(i = 0; i < colorcount; i++) + cs[i].pixel = i; + XQueryColors(Xdisplay, Xcolormap, cs, colorcount); + Xunmapcolor = new byte[3 * colorcount]; + for(i = 0; i < colorcount; i++) + { + Xunmapcolor[3 * i + 0] = cs[i].blue; + Xunmapcolor[3 * i + 1] = cs[i].green; + Xunmapcolor[3 * i + 2] = cs[i].red; + } + byte *cm = Xmapcolor = new byte[12 * 24 * 12]; + for(int r = 0; r < 12; r++) + for(int g = 0; g < 24; g++) + for(int b = 0; b < 12; b++) { + int mind = INT_MAX; + int mini; + for(int i = 0; i < colorcount; i++) { + int d = ssq(r * 255 / 11 - (cs[i].red >> 8)) + + ssq(g * 255 / 23 - (cs[i].green >> 8)) + + ssq(b * 255 / 11 - (cs[i].blue >> 8)); + if(d < mind) { + mini = i; + mind = d; + } + } + *cm++ = mini; + } + Xgetpixel = GetPseudoColorPixel; + } +// XFree(v); + + Font::SetStdFont(ScreenSans(12)); +} + +void InitX11Draw(const char *dispname) +{ +#ifdef flagNOGTK + if(!dispname || !*dispname) { + int f = Environment().Find("DISPLAY"); + dispname = (f >= 0 ? ~Environment()[f] : ":0.0"); + } + InitX11Draw(XOpenDisplay(dispname)); +#else + MemoryIgnoreLeaksBlock __; + const Vector& cmd = CommandLine(); + char **argv = (char**) MemoryAllocPermanent(sizeof(char *) * cmd.GetCount()); + for(int i = 0; i < cmd.GetCount(); i++) + argv[i] = PermanentCopy(cmd[i]); + int argc = cmd.GetCount(); + gtk_init (&argc, &argv); + GtkWidget *w = gtk_window_new(GTK_WINDOW_TOPLEVEL); + GdkDisplay *d = gtk_widget_get_display(w); + gdk_x11_display_get_xdisplay(d); + InitX11Draw(gdk_x11_display_get_xdisplay(d)); + gtk_widget_destroy(w); +#endif +} + +void SetClip(GC gc, XftDraw *xftdraw, const Vector& cl) +{ + GuiLock __; + LTIMING("SetClip"); + Buffer xr(cl.GetCount()); + LLOG("SetClip"); + for(int i = 0; i < cl.GetCount(); i++) { + XRectangle& r = xr[i]; + const Rect& cr = cl[i]; + LLOG("[" << i << "] = " << cr); + r.x = cr.left; + r.y = cr.top; + r.width = cr.Width(); + r.height = cr.Height(); + } + XSetClipRectangles(Xdisplay, gc, 0, 0, xr, cl.GetCount(), Unsorted); + LLOG("XftDrawSetClipRectangles, # = " << cl.GetCount() << ", xftdraw = " << FormatIntHex(xftdraw)); + XftDrawSetClipRectangles(xftdraw, 0, 0, xr, cl.GetCount()); + LLOG("//XftDrawSetClipRectangles"); +} + +void SystemDraw::CloneClip() +{ + if(cloff.GetCount() > 1 && cloff.Top().clipi == cloff[cloff.GetCount() - 2].clipi) { + cloff.Top().clipi = clip.GetCount(); + Vector& c = clip.Add(); + c <<= clip[clip.GetCount() - 2]; + } +} + +void SystemDraw::SetForeground(Color color) +{ + GuiLock __; + LTIMING("SetForeground"); + int p = GetXPixel(color.GetR(), color.GetG(), color.GetB()); + if(p == foreground) return; + LTIMING("XSetForeground"); + LLOG("XSetForeground " << color); + foreground = p; + XSetForeground(Xdisplay, gc, foreground); +} + +void SystemDraw::SetClip() { + GuiLock __; + if(dw == Xroot) return; + LTIMING("SetClip"); + UPP::SetClip(gc, xftdraw, clip.Top()); +} + +void SystemDraw::SetLineStyle(int width) +{ + GuiLock __; + if(width == linewidth) return; + linewidth = width; + if(IsNull(width)) + width = 1; + if(width < PEN_SOLID) { + static const char dash[] = { 18, 6 }; + static const char dot[] = { 3, 3 }; + static const char dashdot[] = { 9, 6, 3, 6 }; + static const char dashdotdot[] = { 9, 3, 3, 3, 3, 3 }; + static struct { + const char *dash; + int len; + } ds[] = { + { dash, __countof(dash) }, + { dot, __countof(dot) }, + { dashdot, __countof(dashdot) }, + { dashdotdot, __countof(dashdotdot) } + }; + int i = -(width - PEN_DASH); + ASSERT(i >= 0 && i < 4); + XSetDashes(Xdisplay, gc, 0, ds[i].dash, ds[i].len); + } + XSetLineAttributes(Xdisplay, gc, max(width, 1), + width < PEN_SOLID ? LineOnOffDash : LineSolid, CapRound, JoinRound); +} + +void SystemDraw::Init() +{ + GuiLock __; + pageSize = Size(Xwidth, Xheight); + cloff.Clear(); + clip.Clear(); + foreground = linewidth = Null; +} + +void SystemDraw::Init(const Vector& _clip, Point _offset) +{ + GuiLock __; + Init(); + clip.Add() <<= _clip; + offset.Add(_offset); + actual_offset = _offset; + Cloff& f = cloff.Add(); + f.offseti = 0; + f.clipi = 0; + SetClip(); +} + +dword SystemDraw::GetInfo() const +{ + return 0; +} + +Size SystemDraw::GetPageSize() const +{ + return pageSize; +} + +SystemDraw::SystemDraw() +{ + GuiLock __; + dw = None; + gc = None; + actual_offset = Point(0, 0); + Init(); +} + +Size SystemDraw::GetNativeDpi() const +{ + return Size(96, 96); +} + +void SystemDraw::BeginNative() {} +void SystemDraw::EndNative() {} + +int SystemDraw::GetCloffLevel() const +{ + return cloff.GetCount(); +} + +Rect SystemDraw::GetClip() const +{ + LLOG("Draw::GetClipOp; #clip = " << clip.GetCount() << ", #cloff = " << cloff.GetCount() + << ", clipi = " << cloff.Top().clipi); + const Vector& cl = clip[cloff.Top().clipi]; + Rect box(0, 0, 0, 0); + if(!cl.GetCount()) return box; + box = cl[0]; + LLOG("cl[0] = " << box); + for(int i = 1; i < cl.GetCount(); i++) { + LLOG("cl[" << i << "] = " << cl[i]); + box |= cl[i]; + } + LLOG("out box = " << box << ", actual offset = " << actual_offset); + return box - actual_offset; +} + +SystemDraw::SystemDraw(Drawable _dw, GC _gc, XftDraw *_xftdraw, const Vector& _clip) +{ + LLOG("SystemDraw"); + dw = _dw; + gc = _gc; + xftdraw = _xftdraw; + Init(_clip); +} + +void BackDraw::Create(SystemDraw& w, int cx, int cy) +{ + GuiLock __; + LLOG("Creating BackDraw " << cx << "x" << cy); + Destroy(); + size.cx = cx; + size.cy = cy; + dw = XCreatePixmap(Xdisplay, w.GetDrawable(), max(cx, 1), max(cy, 1), Xdepth); + gc = XCreateGC(Xdisplay, dw, 0, 0); + xftdraw = XftDrawCreate(Xdisplay, (Drawable) dw, + DefaultVisual(Xdisplay, Xscreenno), Xcolormap); + Vector clip; + clip.Add(RectC(0, 0, cx, cy)); + Init(clip, Point(0, 0)); +} + +void BackDraw::Put(SystemDraw& w, int x, int y) +{ + GuiLock __; + LLOG("Putting BackDraw"); + ASSERT(dw != None); + XCopyArea(Xdisplay, dw, w.GetDrawable(), w.GetGC(), 0, 0, size.cx, size.cy, + x + w.GetOffset().x, y + w.GetOffset().y); +} + +void BackDraw::Destroy() +{ + GuiLock __; + if(dw != None) { + XftDrawDestroy(xftdraw); + XFreePixmap(Xdisplay, dw); + XFreeGC(Xdisplay, gc); + } +} + +bool ScreenInPaletteMode() +{ + return Xpalette; +} + +Size GetScreenSize() +{ + return Size(Xwidth, Xheight); +} + +END_UPP_NAMESPACE + +#endif diff --git a/uppsrc/CtrlCore/DrawX11.h b/uppsrc/CtrlCore/DrawX11.h index 047108272..e711b9666 100644 --- a/uppsrc/CtrlCore/DrawX11.h +++ b/uppsrc/CtrlCore/DrawX11.h @@ -1,107 +1,179 @@ -#ifdef PLATFORM_X11 - -void SetClip(GC gc, XftDraw *xftdraw, const Vector& cl); - -class SystemDraw : public Draw { -public: - virtual dword GetInfo() const; - virtual Size GetPageSize() const; - - virtual void BeginOp(); - virtual void EndOp(); - virtual void OffsetOp(Point p); - virtual bool ClipOp(const Rect& r); - virtual bool ClipoffOp(const Rect& r); - virtual bool ExcludeClipOp(const Rect& r); - virtual bool IntersectClipOp(const Rect& r); - virtual bool IsPaintingOp(const Rect& r) const; - - virtual void DrawRectOp(int x, int y, int cx, int cy, Color color); - virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); - virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color); - - virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, - const int *counts, int count_count, - int width, Color color, Color doxor); - virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, - const int *subpolygon_counts, int scc, - const int *disjunct_polygon_counts, int dpcc, - Color color, int width, Color outline, - uint64 pattern, Color doxor); - virtual void DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color); - - virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor); - virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, - Color ink, int n, const int *dx); - - virtual Size GetNativeDpi() const; - virtual void BeginNative(); - virtual void EndNative(); - - virtual int GetCloffLevel() const; - -private: - Size pageSize; - - SystemDraw(); - - friend class ImageDraw; - friend class FontInfo; - friend class Font; - friend class ViewDraw; - - friend void StaticExitDraw_(); - friend Font StdFont(); - - FontInfo lastFont; - - Point actual_offset; - Point actual_offset_bak; - struct Cloff : Moveable { - Point org; - int clipi; - int offseti; - Rect drawingclip; - }; - - Array cloff; - Rect drawingclip; - Vector< Vector > clip; - Vector offset; - - Drawable dw; - GC gc; - XftDraw *xftdraw; - - int foreground; - int linewidth; - - void Init(); - void Init(const Vector& clip, Point offset = Point(0, 0)); - void CloneClip(); - - friend class BackDraw; - friend class ScreenDraw; - -public: - static void Flush() { XSync(Xdisplay, false); } - - Point GetOffset() const { return actual_offset; } - - static XftFont *CreateXftFont(Font f, int angle); - XftDraw *GetXftDraw() const { return xftdraw; } - - Rect GetClip() const; - - void SetForeground(Color color); - void SetLineStyle(int width); - void SetClip(); - - Drawable GetDrawable() const { return dw; } - GC GetGC() const { return gc; } - const Vector& GetClipList() const { return clip.Top(); } - - SystemDraw(Drawable dw, GC gc, XftDraw *xftdraw, const Vector& clip); -}; - -#endif +#ifdef PLATFORM_X11 + +#define Time XTime +#define Font XFont +#define Display XDisplay +#define Picture XPicture + +#include +#include +#include + +#include +#include + +#undef Picture +#undef Time +#undef Font +#undef Display + +#undef True +#undef False + +#define XFalse 0 +#define XTrue 1 + +NAMESPACE_UPP + +extern XDisplay *Xdisplay; +extern Visual *Xvisual; +extern int Xscreenno; +extern Window Xroot; +extern Screen *Xscreen; +extern Colormap Xcolormap; +extern int Xheight; +extern int Xwidth; +extern int XheightMM; +extern int XwidthMM; +extern int Xdepth; +extern dword Xblack; +extern dword Xwhite; +extern int Xconnection; + +extern dword (*Xgetpixel)(int r, int g, int b); + +void InitX11Draw(const char *dispname = NULL); +void InitX11Draw(XDisplay *display); + +void XError(); +void XError(const char *s); + +inline dword GetXPixel(int r, int g, int b) { return (*Xgetpixel)(r, g, b); } +inline dword GetXPixel(Color color) { return (*Xgetpixel)(color.GetR(), color.GetG(), color.GetB()); } + +enum { + X11_ROP2_ZERO, + X11_ROP2_AND, + X11_ROP2_AND_NOT, + X11_ROP2_COPY, + X11_ROP2_NOT_AND, + X11_ROP2_NOP, + X11_ROP2_XOR, + X11_ROP2_OR, + X11_ROP2_NOT_AND_NOT, + X11_ROP2_NOT_XOR, + X11_ROP2_INVERT, + X11_ROP2_OR_NOT, + X11_ROP2_NOT_COPY, + X11_ROP2_NOT_OR, + X11_ROP2_NOT_OR_NOT, + X11_ROP2_ONE, +}; + +void SetClip(GC gc, XftDraw *xftdraw, const Vector& cl); + +class SystemDraw : public Draw { +public: + virtual dword GetInfo() const; + virtual Size GetPageSize() const; + + virtual void BeginOp(); + virtual void EndOp(); + virtual void OffsetOp(Point p); + virtual bool ClipOp(const Rect& r); + virtual bool ClipoffOp(const Rect& r); + virtual bool ExcludeClipOp(const Rect& r); + virtual bool IntersectClipOp(const Rect& r); + virtual bool IsPaintingOp(const Rect& r) const; + + virtual void DrawRectOp(int x, int y, int cx, int cy, Color color); + virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); + virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color); + + virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, + const int *counts, int count_count, + int width, Color color, Color doxor); + virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, + const int *subpolygon_counts, int scc, + const int *disjunct_polygon_counts, int dpcc, + Color color, int width, Color outline, + uint64 pattern, Color doxor); + virtual void DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color); + + virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor); + virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, + Color ink, int n, const int *dx); + + virtual Size GetNativeDpi() const; + virtual void BeginNative(); + virtual void EndNative(); + + virtual int GetCloffLevel() const; + +private: + Size pageSize; + + SystemDraw(); + + friend class ImageDraw; + friend class FontInfo; + friend class Font; + friend class ViewDraw; + + friend void StaticExitDraw_(); + friend Font StdFont(); + + FontInfo lastFont; + + Point actual_offset; + Point actual_offset_bak; + struct Cloff : Moveable { + Point org; + int clipi; + int offseti; + Rect drawingclip; + }; + + Array cloff; + Rect drawingclip; + Vector< Vector > clip; + Vector offset; + + Drawable dw; + GC gc; + XftDraw *xftdraw; + + int foreground; + int linewidth; + + void Init(); + void Init(const Vector& clip, Point offset = Point(0, 0)); + void CloneClip(); + + friend class BackDraw; + friend class ScreenDraw; + +public: + static void Flush() { XSync(Xdisplay, false); } + + Point GetOffset() const { return actual_offset; } + + static XftFont *CreateXftFont(Font f, int angle); + XftDraw *GetXftDraw() const { return xftdraw; } + + Rect GetClip() const; + + void SetForeground(Color color); + void SetLineStyle(int width); + void SetClip(); + + Drawable GetDrawable() const { return dw; } + GC GetGC() const { return gc; } + const Vector& GetClipList() const { return clip.Top(); } + + SystemDraw(Drawable dw, GC gc, XftDraw *xftdraw, const Vector& clip); +}; + +END_UPP_NAMESPACE + +#endif diff --git a/uppsrc/CtrlCore/ImageWin32.cpp b/uppsrc/CtrlCore/ImageWin32.cpp index ebd24abf8..cbcdc16f5 100644 --- a/uppsrc/CtrlCore/ImageWin32.cpp +++ b/uppsrc/CtrlCore/ImageWin32.cpp @@ -1,4 +1,4 @@ -#include "Draw.h" +#include "SystemDraw.h" #ifdef PLATFORM_WIN32 #include @@ -60,7 +60,7 @@ BitmapInfo32__::BitmapInfo32__(int cx, int cy) HBITMAP CreateBitMask(const RGBA *data, Size sz, Size tsz, Size csz, RGBA *ct) { - DrawLock __; + GuiLock __; memset(ct, 0, tsz.cx * tsz.cy * sizeof(RGBA)); int linelen = (tsz.cx + 15) >> 4 << 1; Buffer mask(tsz.cy * linelen, 0xff); @@ -90,7 +90,7 @@ HBITMAP CreateBitMask(const RGBA *data, Size sz, Size tsz, Size csz, RGBA *ct) void SetSurface(HDC dc, int x, int y, int cx, int cy, const RGBA *pixels) { - DrawLock __; + GuiLock __; BitmapInfo32__ bi(cx, cy); ::SetDIBitsToDevice(dc, x, y, cx, cy, 0, 0, 0, cy, pixels, bi, DIB_RGB_COLORS); @@ -125,7 +125,7 @@ public: void DrawSurface::Init(SystemDraw& w, int _x, int _y, int cx, int cy) { - DrawLock __; + GuiLock __; dc = w.GetHandle(); size = Size(cx, cy); x = _x; @@ -149,7 +149,7 @@ DrawSurface::DrawSurface(SystemDraw& w, int x, int y, int cx, int cy) DrawSurface::~DrawSurface() { - DrawLock __; + GuiLock __; ::BitBlt(dc, x, y, size.cx, size.cy, dcMem, 0, 0, SRCCOPY); ::DeleteObject(::SelectObject(dcMem, hbmpOld)); ::DeleteDC(dcMem); @@ -166,17 +166,17 @@ void Image::Data::SysRelease() { SystemData& sd = Sys(); if(sd.hbmp) { - DrawLock __; + GuiLock __; DeleteObject(sd.hbmp); ResCount -= !paintonly; } if(sd.hmask) { - DrawLock __; + GuiLock __; DeleteObject(sd.hmask); ResCount -= !paintonly; } if(sd.himg) { - DrawLock __; + GuiLock __; DeleteObject(sd.himg); ResCount -= !paintonly; } @@ -191,7 +191,7 @@ typedef BOOL (WINAPI *tAlphaBlend)(HDC hdcDest, int nXOriginDest, int nYOriginDe static tAlphaBlend fnAlphaBlend() { - DrawLock __; + GuiLock __; static tAlphaBlend pSet; static bool inited = false; if(!inited) { @@ -227,7 +227,7 @@ int Image::Data::GetResCount() const void Image::Data::CreateHBMP(HDC dc, const RGBA *data) { - DrawLock __; + GuiLock __; SystemData& sd = Sys(); Size sz = buffer.GetSize(); BitmapInfo32__ bi(sz.cx, sz.cy); @@ -250,7 +250,7 @@ void Image::Data::CreateHBMP(HDC dc, const RGBA *data) void Image::Data::Paint(SystemDraw& w, int x, int y, const Rect& src, Color c) { - DrawLock __; + GuiLock __; SystemData& sd = Sys(); ASSERT(!paintonly || IsNull(c)); int max = IsWinNT() ? 250 : 100; @@ -365,7 +365,7 @@ void Image::Data::Paint(SystemDraw& w, int x, int y, const Rect& src, Color c) void ImageDraw::Section::Init(int cx, int cy) { - DrawLock __; + GuiLock __; dc = ::CreateCompatibleDC(ScreenHDC()); BitmapInfo32__ bi(cx, cy); hbmp = CreateDIBSection(dc, bi, DIB_RGB_COLORS, (void **)&pixels, NULL, 0); @@ -374,14 +374,14 @@ void ImageDraw::Section::Init(int cx, int cy) ImageDraw::Section::~Section() { - DrawLock __; + GuiLock __; ::DeleteObject(::SelectObject(dc, hbmpOld)); ::DeleteDC(dc); } void ImageDraw::Init() { - DrawLock __; + GuiLock __; rgb.Init(size.cx, size.cy); a.Init(size.cx, size.cy); Attach(rgb.dc); @@ -468,7 +468,7 @@ Image Image::SizeBottomRight() { return Null; } static Image sWin32Icon(HICON icon, bool cursor) { - DrawLock __; + GuiLock __; ICONINFO iconinfo; if(!icon || !GetIconInfo(icon, &iconinfo)) return Image(); @@ -573,7 +573,7 @@ Image Win32Cursor(int id) HICON IconWin32(const Image& img, bool cursor) { - DrawLock __; + GuiLock __; if(img.IsEmpty()) return NULL; if(cursor) { diff --git a/uppsrc/CtrlCore/ImageX11.cpp b/uppsrc/CtrlCore/ImageX11.cpp index 036f8c8e2..a2f9b9faf 100644 --- a/uppsrc/CtrlCore/ImageX11.cpp +++ b/uppsrc/CtrlCore/ImageX11.cpp @@ -1,436 +1,436 @@ -#include "Draw.h" - -NAMESPACE_UPP - -#ifdef PLATFORM_X11 - -struct Image::Data::SystemData { - int cursor_cheat; - XPicture picture; - XPicture picture8; -}; - -Image::Data::SystemData& Image::Data::Sys() const -{ - ASSERT(sizeof(system_buffer) >= sizeof(SystemData)); - return *(SystemData *)system_buffer; -} - -void Image::SetCursorCheat(int id) -{ - data->Sys().cursor_cheat = id; -} - -int Image::GetCursorCheat() const -{ - return data ? data->Sys().cursor_cheat : -1; -} - -static void sInitXImage(XImage& ximg, Size sz) -{ - Zero(ximg); - ximg.width = sz.cx; - ximg.height = sz.cy; - ximg.xoffset = 0; - ximg.format = ZPixmap; - ximg.bitmap_bit_order = MSBFirst; -#ifdef CPU_LITTLE_ENDIAN - ximg.byte_order = LSBFirst; -#else - ximg.byte_order = MSBFirst; -#endif -} - -void SetSurface(SystemDraw& w, int x, int y, int cx, int cy, const RGBA *pixels) -{ - DrawLock __; - Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, cx, cy, 24); - XPicture picture = XRenderCreatePicture( - Xdisplay, pixmap, - XRenderFindStandardFormat(Xdisplay, PictStandardRGB24), - 0, 0 - ); - XImage ximg; - sInitXImage(ximg, Size(cx, cy)); - ximg.bitmap_pad = 32; - ximg.bytes_per_line = 4 * cx; - ximg.bits_per_pixel = 32; - ximg.blue_mask = 0x00ff0000; - ximg.green_mask = 0x0000ff00; - ximg.red_mask = 0x000000ff; - Buffer pma; - ximg.bitmap_unit = 32; - ximg.depth = 24; - ximg.data = (char *)pixels; - XInitImage(&ximg); - GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); - XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, cx, cy); - XFreeGC(Xdisplay, gc); - XFreePixmap(Xdisplay, pixmap); - XRenderComposite(Xdisplay, PictOpOver, - picture, 0, XftDrawPicture(w.GetXftDraw()), - 0, 0, 0, 0, x, y, cx, cy); - XRenderFreePicture(Xdisplay, picture); -} - -int Image::Data::GetResCount() const -{ - return !!Sys().picture + !!Sys().picture8; -} - -void Image::Data::SysInit() -{ - SystemData& sd = Sys(); - sd.picture = 0; - sd.picture8 = 0; - sd.cursor_cheat = -1; -} - -void Image::Data::SysRelease() -{ - SystemData& sd = Sys(); - if(sd.picture) { - DrawLock __; - if(Xdisplay) XRenderFreePicture(Xdisplay, sd.picture); - ResCount -= !paintonly; - sd.picture = 0; - } - if(sd.picture8) { - DrawLock __; - if(Xdisplay) XRenderFreePicture(Xdisplay, sd.picture8); - ResCount -= !paintonly; - sd.picture8 = 0; - } -} - -struct XRSolidFill { - Color color; - XPicture picture; - Pixmap pixmap; -}; - -enum { XRSolidFillCount = 67 }; - -static XRSolidFill sFill[XRSolidFillCount]; - -inline int s255d16(int x) -{ - return (x << 8)|x; -} - -static XPicture sGetSolidFill(Color c) -{ - DrawLock __; - int q = GetHashValue(c) % (int)XRSolidFillCount; - XRSolidFill& f = sFill[q]; - if(f.color == c && f.picture) - return f.picture; - if(f.picture) - XRenderFreePicture(Xdisplay, f.picture); - if(f.pixmap) - XFreePixmap(Xdisplay, f.pixmap); - f.pixmap = XCreatePixmap(Xdisplay, Xroot, 1, 1, 32); - XRenderPictureAttributes attr; - attr.repeat = XTrue; - f.picture = XRenderCreatePicture(Xdisplay, f.pixmap, - XRenderFindStandardFormat(Xdisplay, PictStandardARGB32), - CPRepeat, &attr); - f.color = c; - XRenderColor xc; - xc.red = s255d16(c.GetR()); - xc.green = s255d16(c.GetG()); - xc.blue = s255d16(c.GetB()); - xc.alpha = 65535; - XRenderFillRectangle(Xdisplay, PictOpSrc, f.picture, &xc, 0, 0, 1, 1); - return f.picture; -} - -void Image::Data::Paint(SystemDraw& w, int x, int y, const Rect& src, Color c) -{ - DrawLock __; - SystemData& sd = Sys(); - while(ResCount > 512) { - Image::Data *l = ResData->GetPrev(); - l->SysRelease(); - l->Unlink(); - } - x += w.GetOffset().x; - y += w.GetOffset().y; - Size sz = buffer.GetSize(); - int len = sz.cx * sz.cy; - Rect sr = src & sz; - Size ssz = sr.Size(); - if(sr.IsEmpty()) - return; - if(GetKind() == IMAGE_EMPTY) - return; - if(GetKind() == IMAGE_OPAQUE && !IsNull(c)) { - w.DrawRect(x, y, sz.cx, sz.cy, c); - return; - } - if(GetKind() == IMAGE_OPAQUE && paintcount == 0 && sr == Rect(sz)) { - SetSurface(w, x, y, sz.cx, sz.cy, buffer); - paintcount++; - return; - } - Unlink(); - LinkAfter(ResData); - if(IsNull(c)) { - if(!sd.picture) { - bool opaque = GetKind() == IMAGE_OPAQUE; - Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, sz.cx, sz.cy, opaque ? 24 : 32); - sd.picture = XRenderCreatePicture( - Xdisplay, pixmap, - XRenderFindStandardFormat(Xdisplay, opaque ? PictStandardRGB24 - : PictStandardARGB32), - 0, 0 - ); - ResCount++; - XImage ximg; - sInitXImage(ximg, sz); - ximg.bitmap_pad = 32; - ximg.bytes_per_line = 4 * sz.cx; - ximg.bits_per_pixel = 32; - ximg.blue_mask = 0x00ff0000; - ximg.green_mask = 0x0000ff00; - ximg.red_mask = 0x000000ff; - ximg.bitmap_unit = 32; - ximg.data = (char *)~buffer; - ximg.depth = opaque ? 24 : 32; - XInitImage(&ximg); - GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); - XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, sz.cx, sz.cy); - XFreeGC(Xdisplay, gc); - XFreePixmap(Xdisplay, pixmap); - PaintOnlyShrink(); - } - XRenderComposite(Xdisplay, PictOpOver, - sd.picture, 0, XftDrawPicture(w.GetXftDraw()), - sr.left, sr.top, 0, 0, x, y, ssz.cx, ssz.cy); - } - else { - ASSERT(!paintonly); - if(!sd.picture8) { - Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, sz.cx, sz.cy, 8); - sd.picture8 = XRenderCreatePicture(Xdisplay, pixmap, - XRenderFindStandardFormat(Xdisplay, PictStandardA8), - 0, 0); - ResCount++; - Buffer ab(len); - byte *t = ab; - const RGBA *s = buffer; - const RGBA *e = s + len; - while(s < e) - *t++ = (s++)->a; - XImage ximg; - sInitXImage(ximg, sz); - ximg.data = (char *)~ab; - ximg.bitmap_unit = 8; - ximg.bitmap_pad = 8; - ximg.depth = 8; - ximg.bytes_per_line = sz.cx; - ximg.bits_per_pixel = 8; - XInitImage(&ximg); - GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); - XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, sz.cx, sz.cy); - XFreeGC(Xdisplay, gc); - XFreePixmap(Xdisplay, pixmap); - } - XRenderComposite(Xdisplay, PictOpOver, - sGetSolidFill(c), sd.picture8, XftDrawPicture(w.GetXftDraw()), - sr.left, sr.top, 0, 0, x, y, ssz.cx, ssz.cy); - } -} - -void ImageDraw::Init() -{ - DrawLock __; - dw = XCreatePixmap(Xdisplay, Xroot, max(size.cx, 1), max(size.cy, 1), Xdepth); - gc = XCreateGC(Xdisplay, dw, 0, 0); - xftdraw = XftDrawCreate(Xdisplay, (Drawable) dw, DefaultVisual(Xdisplay, Xscreenno), Xcolormap); - - alpha.dw = XCreatePixmap(Xdisplay, Xroot, max(size.cx, 1), max(size.cy, 1), Xdepth); - alpha.gc = XCreateGC(Xdisplay, alpha.dw, 0, 0); - alpha.xftdraw = XftDrawCreate(Xdisplay, (Drawable) alpha.dw, DefaultVisual(Xdisplay, Xscreenno), Xcolormap); - - Vector clip; - clip.Add(RectC(0, 0, size.cx, size.cy)); - SystemDraw::Init(clip, Point(0, 0)); - alpha.Init(clip, Point(0, 0)); - - has_alpha = false; -} - -ImageDraw::operator Image() const -{ - DrawLock __; - XImage *xim = XGetImage(Xdisplay, dw, 0, 0, max(size.cx, 1), max(size.cy, 1), AllPlanes, ZPixmap); - Visual *v = DefaultVisual(Xdisplay, Xscreenno); - RasterFormat fmt; - - RGBA palette[256]; - - switch(xim->depth) { - case 15: - case 16: - if(xim->byte_order == LSBFirst) - fmt.Set16le(v->red_mask, v->green_mask, v->blue_mask); - else - fmt.Set16be(v->red_mask, v->green_mask, v->blue_mask); - break; - case 8: { - int n = min(v->map_entries, 256); - XColor colors[256]; - for(int i = 0; i < 256; i++) { - colors[i].pixel = i; - colors[i].flags = DoRed|DoGreen|DoBlue; - } - XQueryColors(Xdisplay, Xcolormap, colors, n); - XColor *s = colors; - XColor *e = s + n; - while(s < e) { - RGBA& t = palette[s->pixel]; - t.r = s->red >> 8; - t.g = s->green >> 8; - t.b = s->blue >> 8; - t.a = 255; - s++; - } - fmt.Set8(); - break; - } - default: - if(xim->bits_per_pixel == 32) - if(xim->byte_order == LSBFirst) - fmt.Set32le(v->red_mask, v->green_mask, v->blue_mask); - else - fmt.Set32be(v->red_mask, v->green_mask, v->blue_mask); - else - if(xim->byte_order == LSBFirst) - fmt.Set24le(v->red_mask, v->green_mask, v->blue_mask); - else - fmt.Set24be(v->red_mask, v->green_mask, v->blue_mask); - break; - } - - ImageBuffer ib(size); - const byte *s = (const byte *)xim->data; - RGBA *t = ib; - for(int y = 0; y < size.cy; y++) { - fmt.Read(t, s, size.cx, palette); - s += xim->bytes_per_line; - t += size.cx; - } - XDestroyImage(xim); - if(has_alpha) { - xim = XGetImage(Xdisplay, alpha.dw, 0, 0, size.cx, size.cy, AllPlanes, ZPixmap); - const byte *s = (const byte *)xim->data; - t = ib; - Buffer line(size.cx); - for(int y = 0; y < size.cy; y++) { - fmt.Read(line, s, size.cx, palette); - for(int x = 0; x < size.cx; x++) - (t++)->a = line[x].r; - s += xim->bytes_per_line; - } - XDestroyImage(xim); - } - Premultiply(ib); - return ib; -} - -ImageDraw::ImageDraw(Size sz) -{ - size = sz; - Init(); -} - -ImageDraw::ImageDraw(int cx, int cy) -{ - size = Size(cx, cy); - Init(); -} - -ImageDraw::~ImageDraw() -{ - DrawLock __; - XftDrawDestroy(xftdraw); - XFreePixmap(Xdisplay, dw); - XFreeGC(Xdisplay, gc); - XftDrawDestroy(alpha.xftdraw); - XFreePixmap(Xdisplay, alpha.dw); - XFreeGC(Xdisplay, alpha.gc); -} - -Image sX11Cursor__(int c) -{ - ImageBuffer b(32, 32); - Image m(b); - m.SetCursorCheat(c); - return m; -} - -#include - -#define FCURSOR_(x) { Image h; INTERLOCKED { static Image m = sX11Cursor__(x); h = m; } return h; } - -Image Image::Arrow() FCURSOR_(XC_left_ptr) -Image Image::Wait() FCURSOR_(XC_watch) -Image Image::IBeam() FCURSOR_(XC_xterm) -Image Image::No() FCURSOR_(XC_circle) -Image Image::SizeAll() FCURSOR_(XC_fleur) -Image Image::SizeHorz() FCURSOR_(XC_sb_h_double_arrow) -Image Image::SizeVert() FCURSOR_(XC_double_arrow) -Image Image::SizeTopLeft() FCURSOR_(XC_top_left_corner) -Image Image::SizeTop() FCURSOR_(XC_top_side) -Image Image::SizeTopRight() FCURSOR_(XC_top_right_corner) -Image Image::SizeLeft() FCURSOR_(XC_left_side) -Image Image::SizeRight() FCURSOR_(XC_right_side) -Image Image::SizeBottomLeft() FCURSOR_(XC_bottom_left_corner) -Image Image::SizeBottom() FCURSOR_(XC_bottom_side) -Image Image::SizeBottomRight() FCURSOR_(XC_bottom_right_corner) -Image Image::Cross() FCURSOR_(XC_crosshair) -Image Image::Hand() FCURSOR_(XC_hand1) - -Cursor X11Cursor(const Image& img) -{ - DrawLock __; - int q = img.GetCursorCheat(); - if(q >= 0) - return XCreateFontCursor(Xdisplay, q); - int len = img.GetLength(); - Size sz = img.GetSize(); - Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, sz.cx, sz.cy, 32); - XPicture picture = XRenderCreatePicture( - Xdisplay, pixmap, - XRenderFindStandardFormat(Xdisplay, PictStandardARGB32), - 0, 0 - ); - XImage ximg; - sInitXImage(ximg, sz); - ximg.bitmap_pad = 32; - ximg.bytes_per_line = 4 * sz.cx; - ximg.bits_per_pixel = 32; - ximg.blue_mask = 0x00ff0000; - ximg.green_mask = 0x0000ff00; - ximg.red_mask = 0x000000ff; - Buffer pma; - pma.Alloc(len); - memcpy(pma, ~img, len * sizeof(RGBA)); - ximg.bitmap_unit = 32; - ximg.depth = 32; - ximg.data = (char *)~pma; - XInitImage(&ximg); - GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); - XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, sz.cx, sz.cy); - XFreeGC(Xdisplay, gc); - XFreePixmap(Xdisplay, pixmap); - Point p = img.GetHotSpot(); - Cursor c = XRenderCreateCursor(Xdisplay, picture, p.x, p.y); - XRenderFreePicture(Xdisplay, picture); - return c; -} - -#endif - -END_UPP_NAMESPACE +#include "SystemDraw.h" + +NAMESPACE_UPP + +#ifdef PLATFORM_X11 + +struct Image::Data::SystemData { + int cursor_cheat; + XPicture picture; + XPicture picture8; +}; + +Image::Data::SystemData& Image::Data::Sys() const +{ + ASSERT(sizeof(system_buffer) >= sizeof(SystemData)); + return *(SystemData *)system_buffer; +} + +void Image::SetCursorCheat(int id) +{ + data->Sys().cursor_cheat = id; +} + +int Image::GetCursorCheat() const +{ + return data ? data->Sys().cursor_cheat : -1; +} + +static void sInitXImage(XImage& ximg, Size sz) +{ + Zero(ximg); + ximg.width = sz.cx; + ximg.height = sz.cy; + ximg.xoffset = 0; + ximg.format = ZPixmap; + ximg.bitmap_bit_order = MSBFirst; +#ifdef CPU_LITTLE_ENDIAN + ximg.byte_order = LSBFirst; +#else + ximg.byte_order = MSBFirst; +#endif +} + +void SetSurface(SystemDraw& w, int x, int y, int cx, int cy, const RGBA *pixels) +{ + GuiLock __; + Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, cx, cy, 24); + XPicture picture = XRenderCreatePicture( + Xdisplay, pixmap, + XRenderFindStandardFormat(Xdisplay, PictStandardRGB24), + 0, 0 + ); + XImage ximg; + sInitXImage(ximg, Size(cx, cy)); + ximg.bitmap_pad = 32; + ximg.bytes_per_line = 4 * cx; + ximg.bits_per_pixel = 32; + ximg.blue_mask = 0x00ff0000; + ximg.green_mask = 0x0000ff00; + ximg.red_mask = 0x000000ff; + Buffer pma; + ximg.bitmap_unit = 32; + ximg.depth = 24; + ximg.data = (char *)pixels; + XInitImage(&ximg); + GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); + XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, cx, cy); + XFreeGC(Xdisplay, gc); + XFreePixmap(Xdisplay, pixmap); + XRenderComposite(Xdisplay, PictOpOver, + picture, 0, XftDrawPicture(w.GetXftDraw()), + 0, 0, 0, 0, x, y, cx, cy); + XRenderFreePicture(Xdisplay, picture); +} + +int Image::Data::GetResCount() const +{ + return !!Sys().picture + !!Sys().picture8; +} + +void Image::Data::SysInit() +{ + SystemData& sd = Sys(); + sd.picture = 0; + sd.picture8 = 0; + sd.cursor_cheat = -1; +} + +void Image::Data::SysRelease() +{ + SystemData& sd = Sys(); + if(sd.picture) { + GuiLock __; + if(Xdisplay) XRenderFreePicture(Xdisplay, sd.picture); + ResCount -= !paintonly; + sd.picture = 0; + } + if(sd.picture8) { + GuiLock __; + if(Xdisplay) XRenderFreePicture(Xdisplay, sd.picture8); + ResCount -= !paintonly; + sd.picture8 = 0; + } +} + +struct XRSolidFill { + Color color; + XPicture picture; + Pixmap pixmap; +}; + +enum { XRSolidFillCount = 67 }; + +static XRSolidFill sFill[XRSolidFillCount]; + +inline int s255d16(int x) +{ + return (x << 8)|x; +} + +static XPicture sGetSolidFill(Color c) +{ + GuiLock __; + int q = GetHashValue(c) % (int)XRSolidFillCount; + XRSolidFill& f = sFill[q]; + if(f.color == c && f.picture) + return f.picture; + if(f.picture) + XRenderFreePicture(Xdisplay, f.picture); + if(f.pixmap) + XFreePixmap(Xdisplay, f.pixmap); + f.pixmap = XCreatePixmap(Xdisplay, Xroot, 1, 1, 32); + XRenderPictureAttributes attr; + attr.repeat = XTrue; + f.picture = XRenderCreatePicture(Xdisplay, f.pixmap, + XRenderFindStandardFormat(Xdisplay, PictStandardARGB32), + CPRepeat, &attr); + f.color = c; + XRenderColor xc; + xc.red = s255d16(c.GetR()); + xc.green = s255d16(c.GetG()); + xc.blue = s255d16(c.GetB()); + xc.alpha = 65535; + XRenderFillRectangle(Xdisplay, PictOpSrc, f.picture, &xc, 0, 0, 1, 1); + return f.picture; +} + +void Image::Data::Paint(SystemDraw& w, int x, int y, const Rect& src, Color c) +{ + GuiLock __; + SystemData& sd = Sys(); + while(ResCount > 512) { + Image::Data *l = ResData->GetPrev(); + l->SysRelease(); + l->Unlink(); + } + x += w.GetOffset().x; + y += w.GetOffset().y; + Size sz = buffer.GetSize(); + int len = sz.cx * sz.cy; + Rect sr = src & sz; + Size ssz = sr.Size(); + if(sr.IsEmpty()) + return; + if(GetKind() == IMAGE_EMPTY) + return; + if(GetKind() == IMAGE_OPAQUE && !IsNull(c)) { + w.DrawRect(x, y, sz.cx, sz.cy, c); + return; + } + if(GetKind() == IMAGE_OPAQUE && paintcount == 0 && sr == Rect(sz)) { + SetSurface(w, x, y, sz.cx, sz.cy, buffer); + paintcount++; + return; + } + Unlink(); + LinkAfter(ResData); + if(IsNull(c)) { + if(!sd.picture) { + bool opaque = GetKind() == IMAGE_OPAQUE; + Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, sz.cx, sz.cy, opaque ? 24 : 32); + sd.picture = XRenderCreatePicture( + Xdisplay, pixmap, + XRenderFindStandardFormat(Xdisplay, opaque ? PictStandardRGB24 + : PictStandardARGB32), + 0, 0 + ); + ResCount++; + XImage ximg; + sInitXImage(ximg, sz); + ximg.bitmap_pad = 32; + ximg.bytes_per_line = 4 * sz.cx; + ximg.bits_per_pixel = 32; + ximg.blue_mask = 0x00ff0000; + ximg.green_mask = 0x0000ff00; + ximg.red_mask = 0x000000ff; + ximg.bitmap_unit = 32; + ximg.data = (char *)~buffer; + ximg.depth = opaque ? 24 : 32; + XInitImage(&ximg); + GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); + XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, sz.cx, sz.cy); + XFreeGC(Xdisplay, gc); + XFreePixmap(Xdisplay, pixmap); + PaintOnlyShrink(); + } + XRenderComposite(Xdisplay, PictOpOver, + sd.picture, 0, XftDrawPicture(w.GetXftDraw()), + sr.left, sr.top, 0, 0, x, y, ssz.cx, ssz.cy); + } + else { + ASSERT(!paintonly); + if(!sd.picture8) { + Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, sz.cx, sz.cy, 8); + sd.picture8 = XRenderCreatePicture(Xdisplay, pixmap, + XRenderFindStandardFormat(Xdisplay, PictStandardA8), + 0, 0); + ResCount++; + Buffer ab(len); + byte *t = ab; + const RGBA *s = buffer; + const RGBA *e = s + len; + while(s < e) + *t++ = (s++)->a; + XImage ximg; + sInitXImage(ximg, sz); + ximg.data = (char *)~ab; + ximg.bitmap_unit = 8; + ximg.bitmap_pad = 8; + ximg.depth = 8; + ximg.bytes_per_line = sz.cx; + ximg.bits_per_pixel = 8; + XInitImage(&ximg); + GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); + XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, sz.cx, sz.cy); + XFreeGC(Xdisplay, gc); + XFreePixmap(Xdisplay, pixmap); + } + XRenderComposite(Xdisplay, PictOpOver, + sGetSolidFill(c), sd.picture8, XftDrawPicture(w.GetXftDraw()), + sr.left, sr.top, 0, 0, x, y, ssz.cx, ssz.cy); + } +} + +void ImageDraw::Init() +{ + GuiLock __; + dw = XCreatePixmap(Xdisplay, Xroot, max(size.cx, 1), max(size.cy, 1), Xdepth); + gc = XCreateGC(Xdisplay, dw, 0, 0); + xftdraw = XftDrawCreate(Xdisplay, (Drawable) dw, DefaultVisual(Xdisplay, Xscreenno), Xcolormap); + + alpha.dw = XCreatePixmap(Xdisplay, Xroot, max(size.cx, 1), max(size.cy, 1), Xdepth); + alpha.gc = XCreateGC(Xdisplay, alpha.dw, 0, 0); + alpha.xftdraw = XftDrawCreate(Xdisplay, (Drawable) alpha.dw, DefaultVisual(Xdisplay, Xscreenno), Xcolormap); + + Vector clip; + clip.Add(RectC(0, 0, size.cx, size.cy)); + SystemDraw::Init(clip, Point(0, 0)); + alpha.Init(clip, Point(0, 0)); + + has_alpha = false; +} + +ImageDraw::operator Image() const +{ + GuiLock __; + XImage *xim = XGetImage(Xdisplay, dw, 0, 0, max(size.cx, 1), max(size.cy, 1), AllPlanes, ZPixmap); + Visual *v = DefaultVisual(Xdisplay, Xscreenno); + RasterFormat fmt; + + RGBA palette[256]; + + switch(xim->depth) { + case 15: + case 16: + if(xim->byte_order == LSBFirst) + fmt.Set16le(v->red_mask, v->green_mask, v->blue_mask); + else + fmt.Set16be(v->red_mask, v->green_mask, v->blue_mask); + break; + case 8: { + int n = min(v->map_entries, 256); + XColor colors[256]; + for(int i = 0; i < 256; i++) { + colors[i].pixel = i; + colors[i].flags = DoRed|DoGreen|DoBlue; + } + XQueryColors(Xdisplay, Xcolormap, colors, n); + XColor *s = colors; + XColor *e = s + n; + while(s < e) { + RGBA& t = palette[s->pixel]; + t.r = s->red >> 8; + t.g = s->green >> 8; + t.b = s->blue >> 8; + t.a = 255; + s++; + } + fmt.Set8(); + break; + } + default: + if(xim->bits_per_pixel == 32) + if(xim->byte_order == LSBFirst) + fmt.Set32le(v->red_mask, v->green_mask, v->blue_mask); + else + fmt.Set32be(v->red_mask, v->green_mask, v->blue_mask); + else + if(xim->byte_order == LSBFirst) + fmt.Set24le(v->red_mask, v->green_mask, v->blue_mask); + else + fmt.Set24be(v->red_mask, v->green_mask, v->blue_mask); + break; + } + + ImageBuffer ib(size); + const byte *s = (const byte *)xim->data; + RGBA *t = ib; + for(int y = 0; y < size.cy; y++) { + fmt.Read(t, s, size.cx, palette); + s += xim->bytes_per_line; + t += size.cx; + } + XDestroyImage(xim); + if(has_alpha) { + xim = XGetImage(Xdisplay, alpha.dw, 0, 0, size.cx, size.cy, AllPlanes, ZPixmap); + const byte *s = (const byte *)xim->data; + t = ib; + Buffer line(size.cx); + for(int y = 0; y < size.cy; y++) { + fmt.Read(line, s, size.cx, palette); + for(int x = 0; x < size.cx; x++) + (t++)->a = line[x].r; + s += xim->bytes_per_line; + } + XDestroyImage(xim); + } + Premultiply(ib); + return ib; +} + +ImageDraw::ImageDraw(Size sz) +{ + size = sz; + Init(); +} + +ImageDraw::ImageDraw(int cx, int cy) +{ + size = Size(cx, cy); + Init(); +} + +ImageDraw::~ImageDraw() +{ + GuiLock __; + XftDrawDestroy(xftdraw); + XFreePixmap(Xdisplay, dw); + XFreeGC(Xdisplay, gc); + XftDrawDestroy(alpha.xftdraw); + XFreePixmap(Xdisplay, alpha.dw); + XFreeGC(Xdisplay, alpha.gc); +} + +Image sX11Cursor__(int c) +{ + ImageBuffer b(32, 32); + Image m(b); + m.SetCursorCheat(c); + return m; +} + +#include + +#define FCURSOR_(x) { Image h; INTERLOCKED { static Image m = sX11Cursor__(x); h = m; } return h; } + +Image Image::Arrow() FCURSOR_(XC_left_ptr) +Image Image::Wait() FCURSOR_(XC_watch) +Image Image::IBeam() FCURSOR_(XC_xterm) +Image Image::No() FCURSOR_(XC_circle) +Image Image::SizeAll() FCURSOR_(XC_fleur) +Image Image::SizeHorz() FCURSOR_(XC_sb_h_double_arrow) +Image Image::SizeVert() FCURSOR_(XC_double_arrow) +Image Image::SizeTopLeft() FCURSOR_(XC_top_left_corner) +Image Image::SizeTop() FCURSOR_(XC_top_side) +Image Image::SizeTopRight() FCURSOR_(XC_top_right_corner) +Image Image::SizeLeft() FCURSOR_(XC_left_side) +Image Image::SizeRight() FCURSOR_(XC_right_side) +Image Image::SizeBottomLeft() FCURSOR_(XC_bottom_left_corner) +Image Image::SizeBottom() FCURSOR_(XC_bottom_side) +Image Image::SizeBottomRight() FCURSOR_(XC_bottom_right_corner) +Image Image::Cross() FCURSOR_(XC_crosshair) +Image Image::Hand() FCURSOR_(XC_hand1) + +Cursor X11Cursor(const Image& img) +{ + GuiLock __; + int q = img.GetCursorCheat(); + if(q >= 0) + return XCreateFontCursor(Xdisplay, q); + int len = img.GetLength(); + Size sz = img.GetSize(); + Pixmap pixmap = XCreatePixmap(Xdisplay, Xroot, sz.cx, sz.cy, 32); + XPicture picture = XRenderCreatePicture( + Xdisplay, pixmap, + XRenderFindStandardFormat(Xdisplay, PictStandardARGB32), + 0, 0 + ); + XImage ximg; + sInitXImage(ximg, sz); + ximg.bitmap_pad = 32; + ximg.bytes_per_line = 4 * sz.cx; + ximg.bits_per_pixel = 32; + ximg.blue_mask = 0x00ff0000; + ximg.green_mask = 0x0000ff00; + ximg.red_mask = 0x000000ff; + Buffer pma; + pma.Alloc(len); + memcpy(pma, ~img, len * sizeof(RGBA)); + ximg.bitmap_unit = 32; + ximg.depth = 32; + ximg.data = (char *)~pma; + XInitImage(&ximg); + GC gc = XCreateGC(Xdisplay, pixmap, 0, 0); + XPutImage(Xdisplay, pixmap, gc, &ximg, 0, 0, 0, 0, sz.cx, sz.cy); + XFreeGC(Xdisplay, gc); + XFreePixmap(Xdisplay, pixmap); + Point p = img.GetHotSpot(); + Cursor c = XRenderCreateCursor(Xdisplay, picture, p.x, p.y); + XRenderFreePicture(Xdisplay, picture); + return c; +} + +#endif + +END_UPP_NAMESPACE diff --git a/uppsrc/CtrlCore/MetaFile.cpp b/uppsrc/CtrlCore/MetaFile.cpp index c242c54b4..75552c706 100644 --- a/uppsrc/CtrlCore/MetaFile.cpp +++ b/uppsrc/CtrlCore/MetaFile.cpp @@ -1,4 +1,4 @@ -#include "Draw.h" +#include "SystemDraw.h" NAMESPACE_UPP diff --git a/uppsrc/CtrlCore/SystemDraw.cpp b/uppsrc/CtrlCore/SystemDraw.cpp index 8b196bc22..920d91f28 100644 --- a/uppsrc/CtrlCore/SystemDraw.cpp +++ b/uppsrc/CtrlCore/SystemDraw.cpp @@ -1,4 +1,4 @@ -#include "Draw.h" +#include "SystemDraw.h" NAMESPACE_UPP @@ -6,7 +6,7 @@ NAMESPACE_UPP void SystemDraw::DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color) { - DrawLock __; + GuiLock __; LTIMING("DrawImageOp"); bool tonative = !IsNative(); if(tonative) { @@ -40,4 +40,14 @@ void SystemDraw::DrawImageOp(int x, int y, int cx, int cy, const Image& img, con EndNative(); } + +Draw& ImageDraw::Alpha() +{ + if(!has_alpha) { + alpha.DrawRect(size, GrayColor(0)); + has_alpha = true; + } + return alpha; +} + END_UPP_NAMESPACE diff --git a/uppsrc/CtrlCore/SystemDraw.h b/uppsrc/CtrlCore/SystemDraw.h index b4147a95d..0451312af 100644 --- a/uppsrc/CtrlCore/SystemDraw.h +++ b/uppsrc/CtrlCore/SystemDraw.h @@ -1,3 +1,25 @@ +#include + +#ifdef PLATFORM_WIN32 +#include "DrawWin32.h" +#endif + +#ifdef PLATFORM_X11 +#include "DrawX11.h" +#endif + +NAMESPACE_UPP + +typedef DrawLock GuiLock; + +inline void EnterGuiMutex() { EnterGMutex(); } +inline void EnterGuiMutex(int n) { EnterGMutex(n); } +inline void LeaveGuiMutex() { LeaveGMutex(); } +inline int LeaveGuiMutexAll() { return LeaveGMutexAll(); } + +bool ScreenInPaletteMode(); +Size GetScreenSize(); + class BackDraw : public SystemDraw { public: virtual bool IsPaintingOp(const Rect& r) const; @@ -76,3 +98,10 @@ public: ImageDraw(int cx, int cy); ~ImageDraw(); }; + +typedef ImageDraw SystemImageDraw; + +void DrawDragRect(SystemDraw& w, const Rect& rect1, const Rect& rect2, const Rect& clip, int n, + Color color, uint64 pattern); + +END_UPP_NAMESPACE diff --git a/uppsrc/CtrlCore/init b/uppsrc/CtrlCore/init index 635cfa7a7..6ee00ffd7 100644 --- a/uppsrc/CtrlCore/init +++ b/uppsrc/CtrlCore/init @@ -2,7 +2,7 @@ #define _CtrlCore_icpp_init_stub #include "Draw/init" #include "plugin\bmp/init" -#define BLITZ_INDEX__ F3E00C8C1D354C9B98AA929A9E9F39109 +#define BLITZ_INDEX__ F50C6488AA9AC98A955BA0CD0115A83C1 #include "CtrlCore.icpp" #undef BLITZ_INDEX__ #endif diff --git a/uppsrc/Draw/Draw.cpp b/uppsrc/Draw/Draw.cpp index c76644218..6f4c234ca 100644 --- a/uppsrc/Draw/Draw.cpp +++ b/uppsrc/Draw/Draw.cpp @@ -411,26 +411,6 @@ void Draw::DrawPainting(int x, int y, int cx, int cy, const Painting& ig) DrawPainting(RectC(x, y, cx, cy), ig); } -#ifdef PLATFORM_WIN32_ -HDC Draw::BeginGdi() -{ - SystemDraw *w = dynamic_cast(this); - return w ? w->BeginGdi() : NULL; -} - -void Draw::EndGdi() -{ - SystemDraw *w = dynamic_cast(this); - if(w) w->EndGdi(); -} - -void Draw::Flush() -{ - SystemDraw::Flush(); -} - -#endif - // --------------------------- dword NilDraw::GetInfo() const { return DOTS; } diff --git a/uppsrc/Draw/Draw.h b/uppsrc/Draw/Draw.h index 75d40c51e..7292da448 100644 --- a/uppsrc/Draw/Draw.h +++ b/uppsrc/Draw/Draw.h @@ -1,912 +1,807 @@ -#ifndef DRAW_H -#define DRAW_H - -#define SYSTEMDRAW 1 - -#include - -#ifdef PLATFORM_X11 - -#define Time XTime -#define Font XFont -#define Display XDisplay -#define Picture XPicture - -#include -#include -#include - -#include -#include - -#undef Picture -#undef Time -#undef Font -#undef Display - -#undef True -#undef False - -#define XFalse 0 -#define XTrue 1 -#endif - - -NAMESPACE_UPP - -#ifdef PLATFORM_X11 - -extern XDisplay *Xdisplay; -extern Visual *Xvisual; -extern int Xscreenno; -extern Window Xroot; -extern Screen *Xscreen; -extern Colormap Xcolormap; -extern int Xheight; -extern int Xwidth; -extern int XheightMM; -extern int XwidthMM; -extern int Xdepth; -extern dword Xblack; -extern dword Xwhite; -extern int Xconnection; - -extern dword (*Xgetpixel)(int r, int g, int b); - -void InitX11Draw(const char *dispname = NULL); -void InitX11Draw(XDisplay *display); - -void XError(); -void XError(const char *s); - -inline dword GetXPixel(int r, int g, int b) { return (*Xgetpixel)(r, g, b); } -inline dword GetXPixel(Color color) { return (*Xgetpixel)(color.GetR(), color.GetG(), color.GetB()); } - -enum { - X11_ROP2_ZERO, - X11_ROP2_AND, - X11_ROP2_AND_NOT, - X11_ROP2_COPY, - X11_ROP2_NOT_AND, - X11_ROP2_NOP, - X11_ROP2_XOR, - X11_ROP2_OR, - X11_ROP2_NOT_AND_NOT, - X11_ROP2_NOT_XOR, - X11_ROP2_INVERT, - X11_ROP2_OR_NOT, - X11_ROP2_NOT_COPY, - X11_ROP2_NOT_OR, - X11_ROP2_NOT_OR_NOT, - X11_ROP2_ONE, -}; - -#endif - -class Drawing; -class Draw; -class Painting; -class SystemDraw; - -#ifdef PLATFORM_WIN32 -HDC ScreenHDC(); -#endif - -bool ScreenInPaletteMode(); -Size GetScreenSize(); - -#include "Image.h" - -#ifdef _MULTITHREADED -void EnterGuiMutex(); -void EnterGuiMutex(int n); -void LeaveGuiMutex(); -int LeaveGuiMutexAll(); - -struct GuiLock { - GuiLock() { EnterGuiMutex(); } - ~GuiLock() { LeaveGuiMutex(); } -}; -#else -inline void EnterGuiMutex() {} -inline void EnterGuiMutex(int n) {} -inline void LeaveGuiMutex() {} -inline int LeaveGuiMutexAll() { return 0; } - -struct GuiLock { - GuiLock() {} - ~GuiLock() {} -}; -#endif - -typedef GuiLock DrawLock; - -const int FONT_V = 40; - -#include "FontInt.h" - -class FontInfo; - -class Font : AssignValueTypeNo >{ - union { - int64 data; - struct { - word face; - word flags; - int16 height; - int16 width; - } v; - }; - - static Font AStdFont; - static Size StdFontSize; - - static const Vector& List(); - static void SyncStdFont(); - static void InitStdFont(); - - const CommonFontInfo& Fi() const; - - friend void sInitFonts(); - -public: - enum { - FIXEDPITCH = 0x0001, - SCALEABLE = 0x0002, - LOCAL = 0x0010, - }; - - static int GetFaceCount(); - static String GetFaceName(int index); - static int FindFaceNameIndex(const String& name); - static dword GetFaceInfo(int index); - - static void SetStdFont(Font font); - static Font GetStdFont(); - static Size GetStdFontSize(); - - enum { - STDFONT, - SCREEN_SERIF, - SCREEN_SANS, - SCREEN_FIXED, - ROMAN, - ARIAL, - COURIER, - #ifdef PLATFORM_WIN32 - SYMBOL, - WINGDINGS, - TAHOMA, - #endif - OTHER, - }; - - int GetFace() const { return v.face; } - int GetHeight() const; - int GetWidth() const { return v.width; } - bool IsBold() const { return v.flags & 0x8000; } - bool IsItalic() const { return v.flags & 0x4000; } - bool IsUnderline() const { return v.flags & 0x2000; } - bool IsStrikeout() const { return v.flags & 0x1000; } - bool IsNonAntiAliased() const { return v.flags & 0x800; } - bool IsTrueTypeOnly() const { return v.flags & 0x400; } - String GetFaceName() const; - dword GetFaceInfo() const; - int64 AsInt64() const { return data; } - - Font& Face(int n) { v.face = n; return *this; } - Font& Height(int n) { v.height = n; return *this; } - Font& Width(int n) { v.width = n; return *this; } - Font& Bold() { v.flags |= 0x8000; return *this; } - Font& NoBold() { v.flags &= ~0x8000; return *this; } - Font& Bold(bool b) { return b ? Bold() : NoBold(); } - Font& Italic() { v.flags |= 0x4000; return *this; } - Font& NoItalic() { v.flags &= ~0x4000; return *this; } - Font& Italic(bool b) { return b ? Italic() : NoItalic(); } - Font& Underline() { v.flags |= 0x2000; return *this; } - Font& NoUnderline() { v.flags &= ~0x2000; return *this; } - Font& Underline(bool b) { return b ? Underline() : NoUnderline(); } - Font& Strikeout() { v.flags |= 0x1000; return *this; } - Font& NoStrikeout() { v.flags &= ~0x1000; return *this; } - Font& Strikeout(bool b) { return b ? Strikeout() : NoStrikeout(); } - Font& NonAntiAliased() { v.flags |= 0x800; return *this; } - Font& NoNonAntiAliased() { v.flags &= ~0x800; return *this; } - Font& NonAntiAliased(bool b) { return b ? NonAntiAliased() : NoNonAntiAliased(); } - Font& TrueTypeOnly() { v.flags |= 0x400; return *this; } - Font& NoTrueTypeOnly() { v.flags &= ~0x400; return *this; } - Font& TrueTypeOnly(bool b) { return b ? TrueTypeOnly() : NoTrueTypeOnly(); } - Font& FaceName(const String& name); - - Font operator()() const { return *this; } - Font operator()(int n) const { return Font(*this).Height(n); } - - - int GetAscent() const { return Fi().ascent; } - int GetDescent() const { return Fi().descent; } - int GetCy() const { return Fi().height; } - int GetExternal() const { return Fi().external; } - int GetInternal() const { return Fi().internal; } - int GetLineHeight() const { return Fi().lineheight; } - int GetOverhang() const { return Fi().overhang; } - int GetAveWidth() const { return Fi().avewidth; } - int GetMaxWidth() const { return Fi().maxwidth; } - int HasChar(int ch) const; - int GetWidth(int c) const; - int operator[](int c) const { return GetWidth(c); } - int GetLeftSpace(int c) const; - int GetRightSpace(int c) const; - bool IsFixedPitch() const { return Fi().fixedpitch; } - bool IsScaleable() const { return Fi().scaleable; } -#ifdef PLATFORM_POSIX - String GetPath() const { return Fi().path; } -#endif - - void Serialize(Stream& s); - - bool operator==(Font f) const { return v.face == f.v.face && v.flags == f.v.flags && - v.width == f.v.width && v.height == f.v.height; } - bool operator!=(Font f) const { return !operator==(f); } - - dword GetHashValue() const { return CombineHash(v.width, v.flags, v.height, v.face); } - bool IsNull() const { return v.face == 0xffff; } - - Font() { v.height = v.width = 0; v.face = v.flags = 0; } - Font(int face, int height) { v.face = face; v.height = height; v.flags = 0; v.width = 0; } - Font(const Nuller&) { v.face = 0xffff; v.height = v.width = 0; v.flags = 0; } - - operator Value() const { return RichValue(*this); } - Font(const Value& q) { *this = RichValue::Extract(q); } - -// BW compatibility - FontInfo Info() const; -}; - -//BW compatibility -class FontInfo { - Font font; - friend class Font; -public: - int GetAscent() const { return font.GetAscent(); } - int GetDescent() const { return font.GetDescent(); } - int GetExternal() const { return font.GetExternal(); } - int GetInternal() const { return font.GetInternal(); } - int GetHeight() const { return font.GetCy(); } - int GetLineHeight() const { return font.GetLineHeight(); } - int GetOverhang() const { return font.GetOverhang(); } - int GetAveWidth() const { return font.GetAveWidth(); } - int GetMaxWidth() const { return font.GetMaxWidth(); } - int HasChar(int c) const { return font.HasChar(c); } - int GetWidth(int c) const { return font.GetWidth(c); } - int operator[](int c) const { return GetWidth(c); } - int GetLeftSpace(int c) const { return font.GetLeftSpace(c); } - int GetRightSpace(int c) const { return font.GetRightSpace(c); } - bool IsFixedPitch() const { return font.IsFixedPitch(); } - bool IsScaleable() const { return font.IsScaleable(); } - int GetFontHeight() const { return font.GetHeight(); } - Font GetFont() const { return font; } -#ifdef PLATFORM_POSIX - String GetFileName() const { return font.GetPath(); } -#endif -}; - -struct ComposedGlyph { - wchar basic_char; - Point mark_pos; - wchar mark_char; - Font mark_font; -}; - -bool Compose(Font fnt, int chr, ComposedGlyph& cs); - -template<> -inline bool IsNull(const Font& f) { return f.IsNull(); } - -template<> -inline unsigned GetHashValue(const Font& f) { return f.GetHashValue(); } - -template<> -String AsString(const Font& f); - -inline void SetStdFont(Font font) { Font::SetStdFont(font); } -inline Font GetStdFont() { return Font::GetStdFont(); } -inline Size GetStdFontSize() { return Font::GetStdFontSize(); } -inline int GetStdFontCy() { return GetStdFontSize().cy; } - -Font StdFont(); - -inline Font StdFont(int h) { return StdFont().Height(h); } - -struct ScreenSans : public Font { ScreenSans(int n = 0) : Font(SCREEN_SANS, n) {} }; -struct ScreenSerif : public Font { ScreenSerif(int n = 0) : Font(SCREEN_SERIF, n) {} }; -struct ScreenFixed : public Font { ScreenFixed(int n = 0) : Font(SCREEN_FIXED, n) {} }; - -struct Roman : public Font { Roman(int n) : Font(ROMAN, n) {} }; -struct Arial : public Font { Arial(int n) : Font(ARIAL, n) {} }; -struct Courier : public Font { Courier(int n) : Font(COURIER, n) {} }; - -#ifdef PLATFORM_WIN32 -struct Symbol : public Font { Symbol(int n) : Font(SYMBOL, n) {} }; -struct WingDings : public Font { WingDings(int n) : Font(WINGDINGS, n) {} }; -struct Tahoma : public Font { Tahoma(int n) : Font(TAHOMA, n) {} }; -#endif - -#ifdef PLATFORM_WIN32 -#ifndef PLATFORM_WINCE -HPALETTE GetQlibPalette(); -#endif -#endif - -Size GetTextSize(const wchar *text, Font font, int n = -1); -Size GetTextSize(const WString& text, Font font); -Size GetTextSize(const char *text, byte charset, Font font, int n = -1); -Size GetTextSize(const char *text, Font font, int n = -1); -Size GetTextSize(const String& text, Font font); - -enum { - PEN_NULL = -1, - PEN_SOLID = -2, - PEN_DASH = -3, -#ifndef PLATFORM_WINCE - PEN_DOT = -4, - PEN_DASHDOT = -5, - PEN_DASHDOTDOT = -6, -#endif -}; - -class Image; - -//DEPRECATED: TODO -Color SBlack(); -Color SGray(); -Color SLtGray(); -Color SWhiteGray(); -Color SWhite(); -Color SRed(); -Color SGreen(); -Color SBrown(); -Color SBlue(); -Color SMagenta(); -Color SCyan(); -Color SYellow(); -Color SLtRed(); -Color SLtGreen(); -Color SLtYellow(); -Color SLtBlue(); -Color SLtMagenta(); -Color SLtCyan(); -//END OF DEPRECATED - -Color SColorPaper(); -Color SColorText(); -Color SColorHighlight(); -Color SColorHighlightText();// -Color SColorMenu(); -Color SColorMenuText(); -Color SColorInfo(); -Color SColorInfoText();// -Color SColorMark(); -Color SColorDisabled(); -Color SColorLight(); -Color SColorFace(); -Color SColorLabel(); -Color SColorShadow(); - -Color SColorLtFace(); -Color SColorDkShadow(); - - -void SBlack_Write(Color c); -void SGray_Write(Color c); -void SLtGray_Write(Color c); -void SWhiteGray_Write(Color c); -void SWhite_Write(Color c); -void SRed_Write(Color c); -void SGreen_Write(Color c); -void SBrown_Write(Color c); -void SBlue_Write(Color c); -void SMagenta_Write(Color c); -void SCyan_Write(Color c); -void SYellow_Write(Color c); -void SLtRed_Write(Color c); -void SLtGreen_Write(Color c); -void SLtYellow_Write(Color c); -void SLtBlue_Write(Color c); -void SLtMagenta_Write(Color c); -void SLtCyan_Write(Color c); - -void SColorPaper_Write(Color c); -void SColorText_Write(Color c); -void SColorHighlight_Write(Color c); -void SColorHighlightText_Write(Color c);// -void SColorMenu_Write(Color c); -void SColorMenuText_Write(Color c); -void SColorInfo_Write(Color c); -void SColorInfoText_Write(Color c);// -void SColorMark_Write(Color c); -void SColorDisabled_Write(Color c); -void SColorLight_Write(Color c); -void SColorFace_Write(Color c); -void SColorLabel_Write(Color c); -void SColorShadow_Write(Color c); - -void SColorLtFace_Write(Color c); -void SColorDkShadow_Write(Color c); - - -inline Color InvertColor() { return Color(255, 0); } -inline Color DefaultInk() { return Black(); } //TODO! - -class Painting : AssignValueTypeNo > { - String cmd; - ValueArray data; - Sizef size; - - friend class PaintingPainter; - friend class Painter; - -public: - Sizef GetSize() const { return size; } - - void Clear() { size = Null; data.Clear(); cmd.Clear(); } - void Serialize(Stream& s) { s % cmd % data % size; } - bool IsNullInstance() const { return cmd.IsEmpty(); } - bool operator==(const Painting& b) const { return cmd == b.cmd && data == b.data && size == b.size; } - unsigned GetHashValue() const { return CombineHash(cmd, data); } - String ToString() const { return "painting " + AsString(size); } - - operator Value() const { return RichValue(*this); } - Painting(const Value& q) { *this = RichValue::Extract(q); } - - Painting() { size = Null; } - Painting(const Nuller&) { size = Null; } -}; - -enum { - MODE_ANTIALIASED = 0, - MODE_NOAA = 1, - MODE_SUBPIXEL = 2, -}; - -bool HasPainter(); -void PaintImageBuffer(ImageBuffer& ib, const Painting& p, Size sz, Point pos, int mode = MODE_ANTIALIASED); -void PaintImageBuffer(ImageBuffer& ib, const Painting& p, int mode = MODE_ANTIALIASED); -void PaintImageBuffer(ImageBuffer& ib, const Drawing& p, int mode = MODE_ANTIALIASED); - -class Draw : NoCopy { -private: - struct DrawingPos; - -public: - enum { - DOTS = 0x001, - GUI = 0x002, - PRINTER = 0x004, - NATIVE = 0x008, - }; - - virtual dword GetInfo() const = 0; - - virtual Size GetPageSize() const; - virtual void StartPage(); - virtual void EndPage(); - - virtual void BeginOp() = 0; - virtual void EndOp() = 0; - virtual void OffsetOp(Point p) = 0; - virtual bool ClipOp(const Rect& r) = 0; - virtual bool ClipoffOp(const Rect& r) = 0; - virtual bool ExcludeClipOp(const Rect& r) = 0; - virtual bool IntersectClipOp(const Rect& r) = 0; - virtual bool IsPaintingOp(const Rect& r) const = 0; - - virtual void DrawRectOp(int x, int y, int cx, int cy, Color color) = 0; - virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color) = 0; - virtual void DrawDataOp(int x, int y, int cx, int cy, const String& data, const char *id); - virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color) = 0; - - virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, - const int *counts, int count_count, - int width, Color color, Color doxor) = 0; - virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, - const int *subpolygon_counts, int scc, - const int *disjunct_polygon_counts, int dpcc, - Color color, int width, Color outline, - uint64 pattern, Color doxor) = 0; - virtual void DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color) = 0; - - virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor) = 0; - virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, - Color ink, int n, const int *dx) = 0; - virtual void DrawDrawingOp(const Rect& target, const Drawing& w); - virtual void DrawPaintingOp(const Rect& target, const Painting& w); - - virtual Size GetNativeDpi() const; - virtual void BeginNative(); - virtual void EndNative(); - - virtual int GetCloffLevel() const; - - virtual ~Draw(); - -// -------------- - Size GetPixelsPerInch() const; - Size GetPageMMs() const; - - bool Dots() const { return GetInfo() & DOTS; } - bool Pixels() const { return !Dots(); } - bool IsGui() const { return GetInfo() & GUI; } - bool IsPrinter() const { return GetInfo() & PRINTER; } - bool IsNative() const { return GetInfo() & NATIVE; } - - int GetNativeX(int x) const; - int GetNativeY(int x) const; - void Native(int& x, int& y) const; - void Native(Point& p) const; - void Native(Size& sz) const; - void Native(Rect& r) const; - - void Begin() { BeginOp(); } - void End() { EndOp(); } - void Offset(Point p) { OffsetOp(p); } - void Offset(int x, int y); - bool Clip(const Rect& r) { return ClipOp(r); } - bool Clip(int x, int y, int cx, int cy); - bool Clipoff(const Rect& r) { return ClipoffOp(r); } - bool Clipoff(int x, int y, int cx, int cy); - bool ExcludeClip(const Rect& r) { return ExcludeClipOp(r); } - bool ExcludeClip(int x, int y, int cx, int cy); - bool IntersectClip(const Rect& r) { return IntersectClipOp(r); } - bool IntersectClip(int x, int y, int cx, int cy); - bool IsPainting(const Rect& r) const { return IsPaintingOp(r); } - bool IsPainting(int x, int y, int cx, int cy) const; - - void DrawRect(int x, int y, int cx, int cy, Color color); - void DrawRect(const Rect& rect, Color color); - - void DrawImage(int x, int y, int cx, int cy, const Image& img, const Rect& src); - void DrawImage(int x, int y, int cx, int cy, const Image& img); - void DrawImage(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); - void DrawImage(int x, int y, int cx, int cy, const Image& img, Color color); - - void DrawImage(const Rect& r, const Image& img, const Rect& src); - void DrawImage(const Rect& r, const Image& img); - void DrawImage(const Rect& r, const Image& img, const Rect& src, Color color); - void DrawImage(const Rect& r, const Image& img, Color color); - - void DrawImage(int x, int y, const Image& img, const Rect& src); - void DrawImage(int x, int y, const Image& img); - void DrawImage(int x, int y, const Image& img, const Rect& src, Color color); - void DrawImage(int x, int y, const Image& img, Color color); - - void DrawData(int x, int y, int cx, int cy, const String& data, const char *type); - void DrawData(const Rect& r, const String& data, const char *type); - - void DrawLine(int x1, int y1, int x2, int y2, int width = 0, Color color = DefaultInk); - void DrawLine(Point p1, Point p2, int width = 0, Color color = DefaultInk); - - void DrawEllipse(const Rect& r, Color color = DefaultInk, - int pen = Null, Color pencolor = DefaultInk); - void DrawEllipse(int x, int y, int cx, int cy, Color color = DefaultInk, - int pen = Null, Color pencolor = DefaultInk); - - void DrawArc(const Rect& rc, Point start, Point end, int width = 0, Color color = DefaultInk); - - void DrawPolyPolyline(const Point *vertices, int vertex_count, - const int *counts, int count_count, - int width = 0, Color color = DefaultInk, Color doxor = Null); - void DrawPolyPolyline(const Vector& vertices, const Vector& counts, - int width = 0, Color color = DefaultInk, Color doxor = Null); - void DrawPolyline(const Point *vertices, int count, - int width = 0, Color color = DefaultInk, Color doxor = Null); - void DrawPolyline(const Vector& vertices, - int width = 0, Color color = DefaultInk, Color doxor = Null); - - void DrawPolyPolyPolygon(const Point *vertices, int vertex_count, - const int *subpolygon_counts, int subpolygon_count_count, - const int *disjunct_polygon_counts, int disjunct_polygon_count_count, - Color color = DefaultInk, int width = 0, Color outline = Null, - uint64 pattern = 0, Color doxor = Null); - void DrawPolyPolyPolygon(const Vector& vertices, - const Vector& subpolygon_counts, - const Vector& disjunct_polygon_counts, - Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); - void DrawPolyPolygon(const Point *vertices, int vertex_count, - const int *subpolygon_counts, int subpolygon_count_count, - Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); - void DrawPolyPolygon(const Vector& vertices, const Vector& subpolygon_counts, - Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); - void DrawPolygons(const Point *vertices, int vertex_count, - const int *polygon_counts, int polygon_count_count, - Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); - void DrawPolygons(const Vector& vertices, const Vector& polygon_counts, - Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); - void DrawPolygon(const Point *vertices, int vertex_count, - Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); - void DrawPolygon(const Vector& vertices, - Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); - - void DrawDrawing(const Rect& r, const Drawing& iw) { DrawDrawingOp(r, iw); } - void DrawDrawing(int x, int y, int cx, int cy, const Drawing& iw); - - void DrawPainting(const Rect& r, const Painting& iw) { DrawPaintingOp(r, iw); } - void DrawPainting(int x, int y, int cx, int cy, const Painting& iw); - - void DrawText(int x, int y, int angle, const wchar *text, Font font = StdFont(), - Color ink = DefaultInk, int n = -1, const int *dx = NULL); - void DrawText(int x, int y, const wchar *text, Font font = StdFont(), - Color ink = DefaultInk, int n = -1, const int *dx = NULL); - - void DrawText(int x, int y, const WString& text, Font font = StdFont(), - Color ink = DefaultInk, const int *dx = NULL); - void DrawText(int x, int y, int angle, const WString& text, Font font = StdFont(), - Color ink = DefaultInk, const int *dx = NULL); - - void DrawText(int x, int y, int angle, const char *text, byte charset, - Font font = StdFont(), Color ink = DefaultInk, int n = -1, const int *dx = NULL); - void DrawText(int x, int y, const char *text, byte charset, Font font = StdFont(), - Color ink = DefaultInk, int n = -1, const int *dx = NULL); - - void DrawText(int x, int y, int angle, const char *text, - Font font = StdFont(), Color ink = DefaultInk, int n = -1, const int *dx = NULL); - void DrawText(int x, int y, const char *text, Font font = StdFont(), - Color ink = DefaultInk, int n = -1, const int *dx = NULL); - - void DrawText(int x, int y, const String& text, Font font = StdFont(), - Color ink = DefaultInk, const int *dx = NULL); - void DrawText(int x, int y, int angle, const String& text, Font font = StdFont(), - Color ink = DefaultInk, const int *dx = NULL); - - static void SinCos(int angle, double& sina, double& cosa); - - // deprecated: - static void SetStdFont(Font font) { UPP::SetStdFont(font); } - static Font GetStdFont() { return UPP::GetStdFont(); } - static Size GetStdFontSize() { return UPP::GetStdFontSize(); } - static int GetStdFontCy() { return GetStdFontSize().cy; } - - -#ifdef PLATFORM_WIN32_ - static void Flush(); - HDC BeginGdi(); - void EndGdi(); -#endif -}; - -void DrawImageBandRLE(Draw& w, int x, int y, const Image& m, int minp); - -class DataDrawer { - typedef DataDrawer *(*Factory)(); - template static DataDrawer *FactoryFn() { return new T; } - static void AddFormat(const char *id, Factory f); - static VectorMap& Map(); - -public: - virtual void Open(const String& data, int cx, int cy) = 0; - virtual void Render(ImageBuffer& ib) = 0; - virtual ~DataDrawer(); - - static One Create(const String& id); - - template static void Register(const char *id) { AddFormat(id, &DataDrawer::FactoryFn); } -}; - -class Drawing : AssignValueTypeNo > { - Size size; - String data; - ValueArray val; - - friend class DrawingDraw; - friend class Draw; - -public: - operator bool() const { return !data.IsEmpty(); } - Size GetSize() const { return size; } - void SetSize(Size sz) { size = sz; } - void SetSize(int cx, int cy) { size = Size(cx, cy); } - - Size RatioSize(int cx, int cy) const; - Size RatioSize(Size sz) const { return RatioSize(sz.cx, sz.cy); } - - void Clear() { data.Clear(); size = Null; } - - void Append(Drawing& dw); - - void Serialize(Stream& s); - - bool IsNullInstance() const { return data.IsEmpty(); } - bool operator==(const Drawing& b) const { return val == b.val && data == b.data && size == b.size; } - String ToString() const { return "drawing " + AsString(size); } - unsigned GetHashValue() const { return CombineHash(data, val); } - - operator Value() const { return RichValue(*this); } - Drawing(const Value& src); - - Drawing() { size = Null; } - Drawing(const Nuller&) { size = Null; } -}; - -class DrawingDraw : public Draw { -public: - virtual dword GetInfo() const; - virtual Size GetPageSize() const; - virtual void BeginOp(); - virtual void EndOp(); - virtual void OffsetOp(Point p); - virtual bool ClipOp(const Rect& r); - virtual bool ClipoffOp(const Rect& r); - virtual bool ExcludeClipOp(const Rect& r); - virtual bool IntersectClipOp(const Rect& r); - virtual bool IsPaintingOp(const Rect& r) const; - - virtual void DrawRectOp(int x, int y, int cx, int cy, Color color); - virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); - virtual void DrawDataOp(int x, int y, int cx, int cy, const String& data, const char *id); - virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color); - virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, - const int *counts, int count_count, - int width, Color color, Color doxor); - virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, - const int *subpolygon_counts, int scc, - const int *disjunct_polygon_counts, int dpcc, - Color color, int width, Color outline, - uint64 pattern, Color doxor); - virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor); - virtual void DrawArcOp(const Rect& rc, Point start, Point end, int pen, Color pencolor); - virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, - Color ink, int n, const int *dx); - - virtual void DrawDrawingOp(const Rect& target, const Drawing& w); - virtual void DrawPaintingOp(const Rect& target, const Painting& w); - -private: - Size size; - StringStream drawing; - ValueArray val; - - Stream& DrawingOp(int code); - -public: - void Create(int cx, int cy); - void Create(Size sz); - - Size GetSize() const { return size; } - - Drawing GetResult(); - operator Drawing() { return GetResult(); } - - DrawingDraw(); - DrawingDraw(int cx, int cy); - DrawingDraw(Size sz); -}; - -class NilDraw : public Draw { -public: - virtual dword GetInfo() const; - virtual Size GetPageSize() const; - virtual void BeginOp(); - virtual void EndOp(); - virtual void OffsetOp(Point p); - virtual bool ClipOp(const Rect& r); - virtual bool ClipoffOp(const Rect& r); - virtual bool ExcludeClipOp(const Rect& r); - virtual bool IntersectClipOp(const Rect& r); - virtual bool IsPaintingOp(const Rect& r) const; - - virtual void DrawRectOp(int x, int y, int cx, int cy, Color color); - virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); - virtual void DrawDataOp(int x, int y, int cx, int cy, const String& data, const char *id); - virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color); - virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, - const int *counts, int count_count, - int width, Color color, Color doxor); - virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, - const int *subpolygon_counts, int scc, - const int *disjunct_polygon_counts, int dpcc, - Color color, int width, Color outline, - uint64 pattern, Color doxor); - virtual void DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color); - virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor); - virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, - Color ink, int n, const int *dx); - virtual void DrawDrawingOp(const Rect& target, const Drawing& w); - virtual void DrawPaintingOp(const Rect& target, const Painting& w); -}; - -void AddNotEmpty(Vector& result, int left, int right, int top, int bottom); -bool Subtract(const Rect& r, const Rect& sub, Vector& result); -bool Subtract(const Vector& rr, const Rect& sub, Vector& result); -Vector Subtract(const Vector& rr, const Rect& sub, bool& changed); -Vector Intersect(const Vector& b, const Rect& a, bool& changed); - -void Subtract(Vector& rr, const Rect& sub); -void Union(Vector& rr, const Rect& add); - -void DrawRect(Draw& w, const Rect& rect, const Image& img, bool ralgn = false); //??? TODO -void DrawRect(Draw& w, int x, int y, int cx, int cy, const Image& img, bool ra = false); - -void DrawTiles(Draw& w, int x, int y, int cx, int cy, const Image& img); -void DrawTiles(Draw& w, const Rect& rect, const Image& img); - -void DrawFatFrame(Draw& w, int x, int y, int cx, int cy, Color color, int n); -void DrawFatFrame(Draw& w, const Rect& r, Color color, int n); - -void DrawFrame(Draw& w, int x, int y, int cx, int cy, - Color leftcolor, Color topcolor, Color rightcolor, Color bottomcolor); -void DrawFrame(Draw& w, const Rect& r, - Color leftcolor, Color topcolor, Color rightcolor, Color bottomcolor); -void DrawFrame(Draw& w, int x, int y, int cx, int cy, - Color topleftcolor, Color bottomrightcolor); -void DrawFrame(Draw& w, const Rect& r, - Color topleftcolor, Color bottomrightcolor); -void DrawFrame(Draw& w, int x, int y, int cx, int cy, Color color); -void DrawFrame(Draw& w, const Rect& r, Color color); - -void DrawBorder(Draw& w, int x, int y, int cx, int cy, const ColorF *colors_ltrd); //TODO -void DrawBorder(Draw& w, const Rect& r, const ColorF *colors_ltrd); - -const ColorF *BlackBorder(); -const ColorF *ButtonPushBorder(); -const ColorF *EdgeButtonBorder(); -const ColorF *DefButtonBorder(); -const ColorF *ButtonBorder(); -const ColorF *InsetBorder(); -const ColorF *OutsetBorder(); -const ColorF *ThinOutsetBorder(); -const ColorF *ThinInsetBorder(); - -void DrawBorder(Draw& w, int x, int y, int cx, int cy, const ColorF *(*colors_ltrd)()); -void DrawBorder(Draw& w, const Rect& r, const ColorF *(*colors_ltrd)()); - -void DrawRectMinusRect(Draw& w, const Rect& rect, const Rect& inner, Color color); - -void DrawHighlightImage(Draw& w, int x, int y, const Image& img, bool highlight = true, - bool enabled = true, Color maskcolor = SColorPaper); - -Color GradientColor(Color fc, Color tc, int i, int n); - -void DrawDragRect(SystemDraw& w, const Rect& rect1, const Rect& rect2, const Rect& clip, int n, Color color, uint64 pattern); - -enum { - BUTTON_NORMAL, BUTTON_OK, BUTTON_HIGHLIGHT, BUTTON_PUSH, BUTTON_DISABLED, BUTTON_CHECKED, - BUTTON_VERTICAL = 0x100, - BUTTON_EDGE = 0x200, - BUTTON_TOOL = 0x400, - BUTTON_SCROLL = 0x800, -}; - -void DrawXPButton(Draw& w, Rect r, int type); - -void DrawTextEllipsis(Draw& w, int x, int y, int cx, const char *text, const char *ellipsis, - Font font = StdFont(), Color ink = SColorText(), int n = -1); -void DrawTextEllipsis(Draw& w, int x, int y, int cx, const wchar *text, const char *ellipsis, - Font font = StdFont(), Color ink = SColorText(), int n = -1); -Size GetTLTextSize(const wchar *text, Font font = StdFont()); -int GetTLTextHeight(const wchar *s, Font font = StdFont()); -void DrawTLText(Draw& draw, int x, int y, int cx, const wchar *text, Font font = StdFont(), - Color ink = SColorText(), int accesskey = 0); - - -typedef String (*DrawingToPdfFnType)(const Array& report, Size pagesize, int margin); - -void SetDrawingToPdfFn(DrawingToPdfFnType Pdf); -DrawingToPdfFnType GetDrawingToPdfFn(); - -#ifdef PLATFORM_WIN32 -#include "DrawWin32.h" -#endif - -#ifdef PLATFORM_X11 -#include "DrawX11.h" -#endif - -#include "SystemDraw.h" - -#include "Display.h" -#include "Debug.h" -#include "Cham.h" - -typedef ImageDraw SystemImageDraw; - -END_UPP_NAMESPACE - -#endif +#ifndef DRAW_H +#define DRAW_H + +#define SYSTEMDRAW 1 + +#include + +NAMESPACE_UPP + +class Drawing; +class Draw; +class Painting; +class SystemDraw; + +#ifdef _MULTITHREADED +void EnterGMutex(); +void EnterGMutex(int n); +void LeaveGMutex(); +int LeaveGMutexAll(); + +struct DrawLock { + DrawLock() { EnterGMutex(); } + ~DrawLock() { LeaveGMutex(); } +}; +#else +inline void EnterGMutex() {} +inline void EnterGMutex(int n) {} +inline void LeaveGMutex() {} +inline int LeaveGMutexAll() { return 0; } + +struct DrawLock { + DrawLock() {} + ~DrawLock() {} +}; +#endif + +#include "Image.h" + +const int FONT_V = 40; + +#include "FontInt.h" + +class FontInfo; + +class Font : AssignValueTypeNo >{ + union { + int64 data; + struct { + word face; + word flags; + int16 height; + int16 width; + } v; + }; + + static Font AStdFont; + static Size StdFontSize; + + static const Vector& List(); + static void SyncStdFont(); + static void InitStdFont(); + + const CommonFontInfo& Fi() const; + + friend void sInitFonts(); + +public: + enum { + FIXEDPITCH = 0x0001, + SCALEABLE = 0x0002, + LOCAL = 0x0010, + }; + + static int GetFaceCount(); + static String GetFaceName(int index); + static int FindFaceNameIndex(const String& name); + static dword GetFaceInfo(int index); + + static void SetStdFont(Font font); + static Font GetStdFont(); + static Size GetStdFontSize(); + + enum { + STDFONT, + SCREEN_SERIF, + SCREEN_SANS, + SCREEN_FIXED, + ROMAN, + ARIAL, + COURIER, + #ifdef PLATFORM_WIN32 + SYMBOL, + WINGDINGS, + TAHOMA, + #endif + OTHER, + }; + + int GetFace() const { return v.face; } + int GetHeight() const; + int GetWidth() const { return v.width; } + bool IsBold() const { return v.flags & 0x8000; } + bool IsItalic() const { return v.flags & 0x4000; } + bool IsUnderline() const { return v.flags & 0x2000; } + bool IsStrikeout() const { return v.flags & 0x1000; } + bool IsNonAntiAliased() const { return v.flags & 0x800; } + bool IsTrueTypeOnly() const { return v.flags & 0x400; } + String GetFaceName() const; + dword GetFaceInfo() const; + int64 AsInt64() const { return data; } + + Font& Face(int n) { v.face = n; return *this; } + Font& Height(int n) { v.height = n; return *this; } + Font& Width(int n) { v.width = n; return *this; } + Font& Bold() { v.flags |= 0x8000; return *this; } + Font& NoBold() { v.flags &= ~0x8000; return *this; } + Font& Bold(bool b) { return b ? Bold() : NoBold(); } + Font& Italic() { v.flags |= 0x4000; return *this; } + Font& NoItalic() { v.flags &= ~0x4000; return *this; } + Font& Italic(bool b) { return b ? Italic() : NoItalic(); } + Font& Underline() { v.flags |= 0x2000; return *this; } + Font& NoUnderline() { v.flags &= ~0x2000; return *this; } + Font& Underline(bool b) { return b ? Underline() : NoUnderline(); } + Font& Strikeout() { v.flags |= 0x1000; return *this; } + Font& NoStrikeout() { v.flags &= ~0x1000; return *this; } + Font& Strikeout(bool b) { return b ? Strikeout() : NoStrikeout(); } + Font& NonAntiAliased() { v.flags |= 0x800; return *this; } + Font& NoNonAntiAliased() { v.flags &= ~0x800; return *this; } + Font& NonAntiAliased(bool b) { return b ? NonAntiAliased() : NoNonAntiAliased(); } + Font& TrueTypeOnly() { v.flags |= 0x400; return *this; } + Font& NoTrueTypeOnly() { v.flags &= ~0x400; return *this; } + Font& TrueTypeOnly(bool b) { return b ? TrueTypeOnly() : NoTrueTypeOnly(); } + Font& FaceName(const String& name); + + Font operator()() const { return *this; } + Font operator()(int n) const { return Font(*this).Height(n); } + + + int GetAscent() const { return Fi().ascent; } + int GetDescent() const { return Fi().descent; } + int GetCy() const { return Fi().height; } + int GetExternal() const { return Fi().external; } + int GetInternal() const { return Fi().internal; } + int GetLineHeight() const { return Fi().lineheight; } + int GetOverhang() const { return Fi().overhang; } + int GetAveWidth() const { return Fi().avewidth; } + int GetMaxWidth() const { return Fi().maxwidth; } + int HasChar(int ch) const; + int GetWidth(int c) const; + int operator[](int c) const { return GetWidth(c); } + int GetLeftSpace(int c) const; + int GetRightSpace(int c) const; + bool IsFixedPitch() const { return Fi().fixedpitch; } + bool IsScaleable() const { return Fi().scaleable; } +#ifdef PLATFORM_POSIX + String GetPath() const { return Fi().path; } +#endif + + void Serialize(Stream& s); + + bool operator==(Font f) const { return v.face == f.v.face && v.flags == f.v.flags && + v.width == f.v.width && v.height == f.v.height; } + bool operator!=(Font f) const { return !operator==(f); } + + dword GetHashValue() const { return CombineHash(v.width, v.flags, v.height, v.face); } + bool IsNull() const { return v.face == 0xffff; } + + Font() { v.height = v.width = 0; v.face = v.flags = 0; } + Font(int face, int height) { v.face = face; v.height = height; v.flags = 0; v.width = 0; } + Font(const Nuller&) { v.face = 0xffff; v.height = v.width = 0; v.flags = 0; } + + operator Value() const { return RichValue(*this); } + Font(const Value& q) { *this = RichValue::Extract(q); } + +// BW compatibility + FontInfo Info() const; +}; + +//BW compatibility +class FontInfo { + Font font; + friend class Font; +public: + int GetAscent() const { return font.GetAscent(); } + int GetDescent() const { return font.GetDescent(); } + int GetExternal() const { return font.GetExternal(); } + int GetInternal() const { return font.GetInternal(); } + int GetHeight() const { return font.GetCy(); } + int GetLineHeight() const { return font.GetLineHeight(); } + int GetOverhang() const { return font.GetOverhang(); } + int GetAveWidth() const { return font.GetAveWidth(); } + int GetMaxWidth() const { return font.GetMaxWidth(); } + int HasChar(int c) const { return font.HasChar(c); } + int GetWidth(int c) const { return font.GetWidth(c); } + int operator[](int c) const { return GetWidth(c); } + int GetLeftSpace(int c) const { return font.GetLeftSpace(c); } + int GetRightSpace(int c) const { return font.GetRightSpace(c); } + bool IsFixedPitch() const { return font.IsFixedPitch(); } + bool IsScaleable() const { return font.IsScaleable(); } + int GetFontHeight() const { return font.GetHeight(); } + Font GetFont() const { return font; } +#ifdef PLATFORM_POSIX + String GetFileName() const { return font.GetPath(); } +#endif +}; + +struct ComposedGlyph { + wchar basic_char; + Point mark_pos; + wchar mark_char; + Font mark_font; +}; + +bool Compose(Font fnt, int chr, ComposedGlyph& cs); + +template<> +inline bool IsNull(const Font& f) { return f.IsNull(); } + +template<> +inline unsigned GetHashValue(const Font& f) { return f.GetHashValue(); } + +template<> +String AsString(const Font& f); + +inline void SetStdFont(Font font) { Font::SetStdFont(font); } +inline Font GetStdFont() { return Font::GetStdFont(); } +inline Size GetStdFontSize() { return Font::GetStdFontSize(); } +inline int GetStdFontCy() { return GetStdFontSize().cy; } + +Font StdFont(); + +inline Font StdFont(int h) { return StdFont().Height(h); } + +struct ScreenSans : public Font { ScreenSans(int n = 0) : Font(SCREEN_SANS, n) {} }; +struct ScreenSerif : public Font { ScreenSerif(int n = 0) : Font(SCREEN_SERIF, n) {} }; +struct ScreenFixed : public Font { ScreenFixed(int n = 0) : Font(SCREEN_FIXED, n) {} }; + +struct Roman : public Font { Roman(int n) : Font(ROMAN, n) {} }; +struct Arial : public Font { Arial(int n) : Font(ARIAL, n) {} }; +struct Courier : public Font { Courier(int n) : Font(COURIER, n) {} }; + +#ifdef PLATFORM_WIN32 +struct Symbol : public Font { Symbol(int n) : Font(SYMBOL, n) {} }; +struct WingDings : public Font { WingDings(int n) : Font(WINGDINGS, n) {} }; +struct Tahoma : public Font { Tahoma(int n) : Font(TAHOMA, n) {} }; +#endif + +Size GetTextSize(const wchar *text, Font font, int n = -1); +Size GetTextSize(const WString& text, Font font); +Size GetTextSize(const char *text, byte charset, Font font, int n = -1); +Size GetTextSize(const char *text, Font font, int n = -1); +Size GetTextSize(const String& text, Font font); + +enum { + PEN_NULL = -1, + PEN_SOLID = -2, + PEN_DASH = -3, +#ifndef PLATFORM_WINCE + PEN_DOT = -4, + PEN_DASHDOT = -5, + PEN_DASHDOTDOT = -6, +#endif +}; + +class Image; + +//DEPRECATED: TODO +Color SBlack(); +Color SGray(); +Color SLtGray(); +Color SWhiteGray(); +Color SWhite(); +Color SRed(); +Color SGreen(); +Color SBrown(); +Color SBlue(); +Color SMagenta(); +Color SCyan(); +Color SYellow(); +Color SLtRed(); +Color SLtGreen(); +Color SLtYellow(); +Color SLtBlue(); +Color SLtMagenta(); +Color SLtCyan(); +//END OF DEPRECATED + +Color SColorPaper(); +Color SColorText(); +Color SColorHighlight(); +Color SColorHighlightText();// +Color SColorMenu(); +Color SColorMenuText(); +Color SColorInfo(); +Color SColorInfoText();// +Color SColorMark(); +Color SColorDisabled(); +Color SColorLight(); +Color SColorFace(); +Color SColorLabel(); +Color SColorShadow(); + +Color SColorLtFace(); +Color SColorDkShadow(); + + +void SBlack_Write(Color c); +void SGray_Write(Color c); +void SLtGray_Write(Color c); +void SWhiteGray_Write(Color c); +void SWhite_Write(Color c); +void SRed_Write(Color c); +void SGreen_Write(Color c); +void SBrown_Write(Color c); +void SBlue_Write(Color c); +void SMagenta_Write(Color c); +void SCyan_Write(Color c); +void SYellow_Write(Color c); +void SLtRed_Write(Color c); +void SLtGreen_Write(Color c); +void SLtYellow_Write(Color c); +void SLtBlue_Write(Color c); +void SLtMagenta_Write(Color c); +void SLtCyan_Write(Color c); + +void SColorPaper_Write(Color c); +void SColorText_Write(Color c); +void SColorHighlight_Write(Color c); +void SColorHighlightText_Write(Color c);// +void SColorMenu_Write(Color c); +void SColorMenuText_Write(Color c); +void SColorInfo_Write(Color c); +void SColorInfoText_Write(Color c);// +void SColorMark_Write(Color c); +void SColorDisabled_Write(Color c); +void SColorLight_Write(Color c); +void SColorFace_Write(Color c); +void SColorLabel_Write(Color c); +void SColorShadow_Write(Color c); + +void SColorLtFace_Write(Color c); +void SColorDkShadow_Write(Color c); + + +inline Color InvertColor() { return Color(255, 0); } +inline Color DefaultInk() { return Black(); } //TODO! + +class Painting : AssignValueTypeNo > { + String cmd; + ValueArray data; + Sizef size; + + friend class PaintingPainter; + friend class Painter; + +public: + Sizef GetSize() const { return size; } + + void Clear() { size = Null; data.Clear(); cmd.Clear(); } + void Serialize(Stream& s) { s % cmd % data % size; } + bool IsNullInstance() const { return cmd.IsEmpty(); } + bool operator==(const Painting& b) const { return cmd == b.cmd && data == b.data && size == b.size; } + unsigned GetHashValue() const { return CombineHash(cmd, data); } + String ToString() const { return "painting " + AsString(size); } + + operator Value() const { return RichValue(*this); } + Painting(const Value& q) { *this = RichValue::Extract(q); } + + Painting() { size = Null; } + Painting(const Nuller&) { size = Null; } +}; + +enum { + MODE_ANTIALIASED = 0, + MODE_NOAA = 1, + MODE_SUBPIXEL = 2, +}; + +bool HasPainter(); +void PaintImageBuffer(ImageBuffer& ib, const Painting& p, Size sz, Point pos, int mode = MODE_ANTIALIASED); +void PaintImageBuffer(ImageBuffer& ib, const Painting& p, int mode = MODE_ANTIALIASED); +void PaintImageBuffer(ImageBuffer& ib, const Drawing& p, int mode = MODE_ANTIALIASED); + +class Draw : NoCopy { +private: + struct DrawingPos; + +public: + enum { + DOTS = 0x001, + GUI = 0x002, + PRINTER = 0x004, + NATIVE = 0x008, + DATABANDS = 0x010, + }; + + virtual dword GetInfo() const = 0; + + virtual Size GetPageSize() const; + virtual void StartPage(); + virtual void EndPage(); + + virtual void BeginOp() = 0; + virtual void EndOp() = 0; + virtual void OffsetOp(Point p) = 0; + virtual bool ClipOp(const Rect& r) = 0; + virtual bool ClipoffOp(const Rect& r) = 0; + virtual bool ExcludeClipOp(const Rect& r) = 0; + virtual bool IntersectClipOp(const Rect& r) = 0; + virtual bool IsPaintingOp(const Rect& r) const = 0; + + virtual void DrawRectOp(int x, int y, int cx, int cy, Color color) = 0; + virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color) = 0; + virtual void DrawDataOp(int x, int y, int cx, int cy, const String& data, const char *id); + virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color) = 0; + + virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, + const int *counts, int count_count, + int width, Color color, Color doxor) = 0; + virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, + const int *subpolygon_counts, int scc, + const int *disjunct_polygon_counts, int dpcc, + Color color, int width, Color outline, + uint64 pattern, Color doxor) = 0; + virtual void DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color) = 0; + + virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor) = 0; + virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, + Color ink, int n, const int *dx) = 0; + virtual void DrawDrawingOp(const Rect& target, const Drawing& w); + virtual void DrawPaintingOp(const Rect& target, const Painting& w); + + virtual Size GetNativeDpi() const; + virtual void BeginNative(); + virtual void EndNative(); + + virtual int GetCloffLevel() const; + + virtual ~Draw(); + +// -------------- + Size GetPixelsPerInch() const; + Size GetPageMMs() const; + + bool Dots() const { return GetInfo() & DOTS; } + bool Pixels() const { return !Dots(); } + bool IsGui() const { return GetInfo() & GUI; } + bool IsPrinter() const { return GetInfo() & PRINTER; } + bool IsNative() const { return GetInfo() & NATIVE; } + + int GetNativeX(int x) const; + int GetNativeY(int x) const; + void Native(int& x, int& y) const; + void Native(Point& p) const; + void Native(Size& sz) const; + void Native(Rect& r) const; + + void Begin() { BeginOp(); } + void End() { EndOp(); } + void Offset(Point p) { OffsetOp(p); } + void Offset(int x, int y); + bool Clip(const Rect& r) { return ClipOp(r); } + bool Clip(int x, int y, int cx, int cy); + bool Clipoff(const Rect& r) { return ClipoffOp(r); } + bool Clipoff(int x, int y, int cx, int cy); + bool ExcludeClip(const Rect& r) { return ExcludeClipOp(r); } + bool ExcludeClip(int x, int y, int cx, int cy); + bool IntersectClip(const Rect& r) { return IntersectClipOp(r); } + bool IntersectClip(int x, int y, int cx, int cy); + bool IsPainting(const Rect& r) const { return IsPaintingOp(r); } + bool IsPainting(int x, int y, int cx, int cy) const; + + void DrawRect(int x, int y, int cx, int cy, Color color); + void DrawRect(const Rect& rect, Color color); + + void DrawImage(int x, int y, int cx, int cy, const Image& img, const Rect& src); + void DrawImage(int x, int y, int cx, int cy, const Image& img); + void DrawImage(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); + void DrawImage(int x, int y, int cx, int cy, const Image& img, Color color); + + void DrawImage(const Rect& r, const Image& img, const Rect& src); + void DrawImage(const Rect& r, const Image& img); + void DrawImage(const Rect& r, const Image& img, const Rect& src, Color color); + void DrawImage(const Rect& r, const Image& img, Color color); + + void DrawImage(int x, int y, const Image& img, const Rect& src); + void DrawImage(int x, int y, const Image& img); + void DrawImage(int x, int y, const Image& img, const Rect& src, Color color); + void DrawImage(int x, int y, const Image& img, Color color); + + void DrawData(int x, int y, int cx, int cy, const String& data, const char *type); + void DrawData(const Rect& r, const String& data, const char *type); + + void DrawLine(int x1, int y1, int x2, int y2, int width = 0, Color color = DefaultInk); + void DrawLine(Point p1, Point p2, int width = 0, Color color = DefaultInk); + + void DrawEllipse(const Rect& r, Color color = DefaultInk, + int pen = Null, Color pencolor = DefaultInk); + void DrawEllipse(int x, int y, int cx, int cy, Color color = DefaultInk, + int pen = Null, Color pencolor = DefaultInk); + + void DrawArc(const Rect& rc, Point start, Point end, int width = 0, Color color = DefaultInk); + + void DrawPolyPolyline(const Point *vertices, int vertex_count, + const int *counts, int count_count, + int width = 0, Color color = DefaultInk, Color doxor = Null); + void DrawPolyPolyline(const Vector& vertices, const Vector& counts, + int width = 0, Color color = DefaultInk, Color doxor = Null); + void DrawPolyline(const Point *vertices, int count, + int width = 0, Color color = DefaultInk, Color doxor = Null); + void DrawPolyline(const Vector& vertices, + int width = 0, Color color = DefaultInk, Color doxor = Null); + + void DrawPolyPolyPolygon(const Point *vertices, int vertex_count, + const int *subpolygon_counts, int subpolygon_count_count, + const int *disjunct_polygon_counts, int disjunct_polygon_count_count, + Color color = DefaultInk, int width = 0, Color outline = Null, + uint64 pattern = 0, Color doxor = Null); + void DrawPolyPolyPolygon(const Vector& vertices, + const Vector& subpolygon_counts, + const Vector& disjunct_polygon_counts, + Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); + void DrawPolyPolygon(const Point *vertices, int vertex_count, + const int *subpolygon_counts, int subpolygon_count_count, + Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); + void DrawPolyPolygon(const Vector& vertices, const Vector& subpolygon_counts, + Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); + void DrawPolygons(const Point *vertices, int vertex_count, + const int *polygon_counts, int polygon_count_count, + Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); + void DrawPolygons(const Vector& vertices, const Vector& polygon_counts, + Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); + void DrawPolygon(const Point *vertices, int vertex_count, + Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); + void DrawPolygon(const Vector& vertices, + Color color = DefaultInk, int width = 0, Color outline = Null, uint64 pattern = 0, Color doxor = Null); + + void DrawDrawing(const Rect& r, const Drawing& iw) { DrawDrawingOp(r, iw); } + void DrawDrawing(int x, int y, int cx, int cy, const Drawing& iw); + + void DrawPainting(const Rect& r, const Painting& iw) { DrawPaintingOp(r, iw); } + void DrawPainting(int x, int y, int cx, int cy, const Painting& iw); + + void DrawText(int x, int y, int angle, const wchar *text, Font font = StdFont(), + Color ink = DefaultInk, int n = -1, const int *dx = NULL); + void DrawText(int x, int y, const wchar *text, Font font = StdFont(), + Color ink = DefaultInk, int n = -1, const int *dx = NULL); + + void DrawText(int x, int y, const WString& text, Font font = StdFont(), + Color ink = DefaultInk, const int *dx = NULL); + void DrawText(int x, int y, int angle, const WString& text, Font font = StdFont(), + Color ink = DefaultInk, const int *dx = NULL); + + void DrawText(int x, int y, int angle, const char *text, byte charset, + Font font = StdFont(), Color ink = DefaultInk, int n = -1, const int *dx = NULL); + void DrawText(int x, int y, const char *text, byte charset, Font font = StdFont(), + Color ink = DefaultInk, int n = -1, const int *dx = NULL); + + void DrawText(int x, int y, int angle, const char *text, + Font font = StdFont(), Color ink = DefaultInk, int n = -1, const int *dx = NULL); + void DrawText(int x, int y, const char *text, Font font = StdFont(), + Color ink = DefaultInk, int n = -1, const int *dx = NULL); + + void DrawText(int x, int y, const String& text, Font font = StdFont(), + Color ink = DefaultInk, const int *dx = NULL); + void DrawText(int x, int y, int angle, const String& text, Font font = StdFont(), + Color ink = DefaultInk, const int *dx = NULL); + + static void SinCos(int angle, double& sina, double& cosa); + + // deprecated: + static void SetStdFont(Font font) { UPP::SetStdFont(font); } + static Font GetStdFont() { return UPP::GetStdFont(); } + static Size GetStdFontSize() { return UPP::GetStdFontSize(); } + static int GetStdFontCy() { return GetStdFontSize().cy; } + + +#ifdef PLATFORM_WIN32_ + static void Flush(); + HDC BeginGdi(); + void EndGdi(); +#endif +}; + +void DrawImageBandRLE(Draw& w, int x, int y, const Image& m, int minp); + +class DataDrawer { + typedef DataDrawer *(*Factory)(); + template static DataDrawer *FactoryFn() { return new T; } + static void AddFormat(const char *id, Factory f); + static VectorMap& Map(); + +public: + virtual void Open(const String& data, int cx, int cy) = 0; + virtual void Render(ImageBuffer& ib) = 0; + virtual ~DataDrawer(); + + static One Create(const String& id); + + template static void Register(const char *id) { AddFormat(id, &DataDrawer::FactoryFn); } +}; + +class Drawing : AssignValueTypeNo > { + Size size; + String data; + ValueArray val; + + friend class DrawingDraw; + friend class Draw; + +public: + operator bool() const { return !data.IsEmpty(); } + Size GetSize() const { return size; } + void SetSize(Size sz) { size = sz; } + void SetSize(int cx, int cy) { size = Size(cx, cy); } + + Size RatioSize(int cx, int cy) const; + Size RatioSize(Size sz) const { return RatioSize(sz.cx, sz.cy); } + + void Clear() { data.Clear(); size = Null; } + + void Append(Drawing& dw); + + void Serialize(Stream& s); + + bool IsNullInstance() const { return data.IsEmpty(); } + bool operator==(const Drawing& b) const { return val == b.val && data == b.data && size == b.size; } + String ToString() const { return "drawing " + AsString(size); } + unsigned GetHashValue() const { return CombineHash(data, val); } + + operator Value() const { return RichValue(*this); } + Drawing(const Value& src); + + Drawing() { size = Null; } + Drawing(const Nuller&) { size = Null; } +}; + +class DrawingDraw : public Draw { +public: + virtual dword GetInfo() const; + virtual Size GetPageSize() const; + virtual void BeginOp(); + virtual void EndOp(); + virtual void OffsetOp(Point p); + virtual bool ClipOp(const Rect& r); + virtual bool ClipoffOp(const Rect& r); + virtual bool ExcludeClipOp(const Rect& r); + virtual bool IntersectClipOp(const Rect& r); + virtual bool IsPaintingOp(const Rect& r) const; + + virtual void DrawRectOp(int x, int y, int cx, int cy, Color color); + virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); + virtual void DrawDataOp(int x, int y, int cx, int cy, const String& data, const char *id); + virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color); + virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, + const int *counts, int count_count, + int width, Color color, Color doxor); + virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, + const int *subpolygon_counts, int scc, + const int *disjunct_polygon_counts, int dpcc, + Color color, int width, Color outline, + uint64 pattern, Color doxor); + virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor); + virtual void DrawArcOp(const Rect& rc, Point start, Point end, int pen, Color pencolor); + virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, + Color ink, int n, const int *dx); + + virtual void DrawDrawingOp(const Rect& target, const Drawing& w); + virtual void DrawPaintingOp(const Rect& target, const Painting& w); + +private: + Size size; + StringStream drawing; + ValueArray val; + + Stream& DrawingOp(int code); + +public: + void Create(int cx, int cy); + void Create(Size sz); + + Size GetSize() const { return size; } + + Drawing GetResult(); + operator Drawing() { return GetResult(); } + + DrawingDraw(); + DrawingDraw(int cx, int cy); + DrawingDraw(Size sz); +}; + +class NilDraw : public Draw { +public: + virtual dword GetInfo() const; + virtual Size GetPageSize() const; + virtual void BeginOp(); + virtual void EndOp(); + virtual void OffsetOp(Point p); + virtual bool ClipOp(const Rect& r); + virtual bool ClipoffOp(const Rect& r); + virtual bool ExcludeClipOp(const Rect& r); + virtual bool IntersectClipOp(const Rect& r); + virtual bool IsPaintingOp(const Rect& r) const; + + virtual void DrawRectOp(int x, int y, int cx, int cy, Color color); + virtual void DrawImageOp(int x, int y, int cx, int cy, const Image& img, const Rect& src, Color color); + virtual void DrawDataOp(int x, int y, int cx, int cy, const String& data, const char *id); + virtual void DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color); + virtual void DrawPolyPolylineOp(const Point *vertices, int vertex_count, + const int *counts, int count_count, + int width, Color color, Color doxor); + virtual void DrawPolyPolyPolygonOp(const Point *vertices, int vertex_count, + const int *subpolygon_counts, int scc, + const int *disjunct_polygon_counts, int dpcc, + Color color, int width, Color outline, + uint64 pattern, Color doxor); + virtual void DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color); + virtual void DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor); + virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font, + Color ink, int n, const int *dx); + virtual void DrawDrawingOp(const Rect& target, const Drawing& w); + virtual void DrawPaintingOp(const Rect& target, const Painting& w); +}; + +void AddNotEmpty(Vector& result, int left, int right, int top, int bottom); +bool Subtract(const Rect& r, const Rect& sub, Vector& result); +bool Subtract(const Vector& rr, const Rect& sub, Vector& result); +Vector Subtract(const Vector& rr, const Rect& sub, bool& changed); +Vector Intersect(const Vector& b, const Rect& a, bool& changed); + +void Subtract(Vector& rr, const Rect& sub); +void Union(Vector& rr, const Rect& add); + +void DrawRect(Draw& w, const Rect& rect, const Image& img, bool ralgn = false); //??? TODO +void DrawRect(Draw& w, int x, int y, int cx, int cy, const Image& img, bool ra = false); + +void DrawTiles(Draw& w, int x, int y, int cx, int cy, const Image& img); +void DrawTiles(Draw& w, const Rect& rect, const Image& img); + +void DrawFatFrame(Draw& w, int x, int y, int cx, int cy, Color color, int n); +void DrawFatFrame(Draw& w, const Rect& r, Color color, int n); + +void DrawFrame(Draw& w, int x, int y, int cx, int cy, + Color leftcolor, Color topcolor, Color rightcolor, Color bottomcolor); +void DrawFrame(Draw& w, const Rect& r, + Color leftcolor, Color topcolor, Color rightcolor, Color bottomcolor); +void DrawFrame(Draw& w, int x, int y, int cx, int cy, + Color topleftcolor, Color bottomrightcolor); +void DrawFrame(Draw& w, const Rect& r, + Color topleftcolor, Color bottomrightcolor); +void DrawFrame(Draw& w, int x, int y, int cx, int cy, Color color); +void DrawFrame(Draw& w, const Rect& r, Color color); + +void DrawBorder(Draw& w, int x, int y, int cx, int cy, const ColorF *colors_ltrd); //TODO +void DrawBorder(Draw& w, const Rect& r, const ColorF *colors_ltrd); + +const ColorF *BlackBorder(); +const ColorF *ButtonPushBorder(); +const ColorF *EdgeButtonBorder(); +const ColorF *DefButtonBorder(); +const ColorF *ButtonBorder(); +const ColorF *InsetBorder(); +const ColorF *OutsetBorder(); +const ColorF *ThinOutsetBorder(); +const ColorF *ThinInsetBorder(); + +void DrawBorder(Draw& w, int x, int y, int cx, int cy, const ColorF *(*colors_ltrd)()); +void DrawBorder(Draw& w, const Rect& r, const ColorF *(*colors_ltrd)()); + +void DrawRectMinusRect(Draw& w, const Rect& rect, const Rect& inner, Color color); + +void DrawHighlightImage(Draw& w, int x, int y, const Image& img, bool highlight = true, + bool enabled = true, Color maskcolor = SColorPaper); + +Color GradientColor(Color fc, Color tc, int i, int n); + +enum { + BUTTON_NORMAL, BUTTON_OK, BUTTON_HIGHLIGHT, BUTTON_PUSH, BUTTON_DISABLED, BUTTON_CHECKED, + BUTTON_VERTICAL = 0x100, + BUTTON_EDGE = 0x200, + BUTTON_TOOL = 0x400, + BUTTON_SCROLL = 0x800, +}; + +void DrawXPButton(Draw& w, Rect r, int type); + +void DrawTextEllipsis(Draw& w, int x, int y, int cx, const char *text, const char *ellipsis, + Font font = StdFont(), Color ink = SColorText(), int n = -1); +void DrawTextEllipsis(Draw& w, int x, int y, int cx, const wchar *text, const char *ellipsis, + Font font = StdFont(), Color ink = SColorText(), int n = -1); +Size GetTLTextSize(const wchar *text, Font font = StdFont()); +int GetTLTextHeight(const wchar *s, Font font = StdFont()); +void DrawTLText(Draw& draw, int x, int y, int cx, const wchar *text, Font font = StdFont(), + Color ink = SColorText(), int accesskey = 0); + + +typedef String (*DrawingToPdfFnType)(const Array& report, Size pagesize, int margin); + +void SetDrawingToPdfFn(DrawingToPdfFnType Pdf); +DrawingToPdfFnType GetDrawingToPdfFn(); + +#include "Display.h" +#include "Cham.h" + +END_UPP_NAMESPACE + +#endif diff --git a/uppsrc/Draw/Draw.upp b/uppsrc/Draw/Draw.upp index 9b6676eb7..944aa92b7 100644 --- a/uppsrc/Draw/Draw.upp +++ b/uppsrc/Draw/Draw.upp @@ -1,81 +1,79 @@ -description "Fundamental graphics operations, including raster image processing\377B128,0,255"; - -acceptflags - NOGTK; - -uses - Core; - -library((LINUX | BSD) & !NOGTK) "gtk-x11-2.0 gdk-x11-2.0 atk-1.0 gdk_pixbuf-2.0 m pangocairo-1.0 fontconfig Xext Xrender Xinerama Xi Xrandr Xcursor Xfixes pango-1.0 cairo X11 gobject-2.0 gmodule-2.0 glib-2.0"; - -library(WIN32 !MSC8ARM) "user32 gdi32"; - -library(LINUX) X11; - -library(LINUX) dl; - -library(LINUX !XLFD) Xft; - -library(BSD) "X11 Xau Xdmcp"; - -library(BSD !XLFD) "Xft fontconfig Xrender freetype expat"; - -library(LINUX !XLFD !SHARED) "fontconfig Xrender freetype expat"; - -library(OSX11) "X11 Xft fontconfig Xrender freetype expat"; - -library(FREEBSD) xcb; - -file - Draw.h, - Mt.cpp, - FontInt.h, - Font.cpp, - FontCR.cpp, - FontWin32.cpp, - FontFc.cpp, - Draw.cpp, - DrawText.cpp, - DrawData.cpp, - Drawing.cpp, - DrawUtil.cpp, - DrawTextUtil.cpp, - Display.h, - Display.cpp, - Debug.h, - Debug.cpp, - Image readonly separator, - Image.h, - Image.cpp, - ImageBlit.cpp, - Raster.h, - RasterFormat.cpp, - RasterWrite.cpp, - Palette.cpp, - Raster.cpp, - RasterEncoder.cpp, - ImageOp.h, - ImageOp.cpp, - ImageChOp.cpp, - ImageScale.cpp, - MakeCache.cpp, - DrawRasterData.cpp, - iml.h, - iml_header.h, - iml_source.h, - DrawImg.iml, - Chameleon readonly separator, - Cham.h, - Cham.cpp, - SSettings.cpp, - GTK-dli readonly separator, - gobj.dli, - gdk.dli, - gpixbuf.dli, - gtk.dli, - gnome.dli, - Info readonly separator, - src.tpp, - srcdoc.tpp, - Copying; - +description "Fundamental graphics operations, including raster image processing\377B128,0,255"; + +acceptflags + NOGTK; + +uses + Core; + +library((LINUX | BSD) & !NOGTK) "gtk-x11-2.0 gdk-x11-2.0 atk-1.0 gdk_pixbuf-2.0 m pangocairo-1.0 fontconfig Xext Xrender Xinerama Xi Xrandr Xcursor Xfixes pango-1.0 cairo X11 gobject-2.0 gmodule-2.0 glib-2.0"; + +library(WIN32 !MSC8ARM) "user32 gdi32"; + +library(LINUX) X11; + +library(LINUX) dl; + +library(LINUX !XLFD) Xft; + +library(BSD) "X11 Xau Xdmcp"; + +library(BSD !XLFD) "Xft fontconfig Xrender freetype expat"; + +library(LINUX !XLFD !SHARED) "fontconfig Xrender freetype expat"; + +library(OSX11) "X11 Xft fontconfig Xrender freetype expat"; + +library(FREEBSD) xcb; + +file + Draw.h, + DrawLock.cpp, + FontInt.h, + Font.cpp, + FontCR.cpp, + FontWin32.cpp, + FontFc.cpp, + Draw.cpp, + DrawText.cpp, + DrawData.cpp, + Drawing.cpp, + DrawUtil.cpp, + DrawTextUtil.cpp, + Display.h, + Display.cpp, + Image readonly separator, + Image.h, + Image.cpp, + ImageBlit.cpp, + Raster.h, + RasterFormat.cpp, + RasterWrite.cpp, + Palette.cpp, + Raster.cpp, + RasterEncoder.cpp, + ImageOp.h, + ImageOp.cpp, + ImageChOp.cpp, + ImageScale.cpp, + MakeCache.cpp, + DrawRasterData.cpp, + iml.h, + iml_header.h, + iml_source.h, + DrawImg.iml, + Chameleon readonly separator, + Cham.h, + Cham.cpp, + SSettings.cpp, + GTK-dli readonly separator, + gobj.dli, + gdk.dli, + gpixbuf.dli, + gtk.dli, + gnome.dli, + Info readonly separator, + src.tpp, + srcdoc.tpp, + Copying; + diff --git a/uppsrc/Draw/DrawData.cpp b/uppsrc/Draw/DrawData.cpp index 6fa722e48..3edb2225f 100644 --- a/uppsrc/Draw/DrawData.cpp +++ b/uppsrc/Draw/DrawData.cpp @@ -102,7 +102,7 @@ void Draw::DrawDataOp(int x, int y, int cx, int cy, const String& data, const ch One dd = DataDrawer::Create(id); if(dd) { dd->Open(data, cx, cy); - if((cx > 2048 || cy > 2048) && dynamic_cast(this)) { + if((cx > 2048 || cy > 2048) && GetInfo() & DATABANDS) { int yy = 0; while(yy < cy) { int ccy = min(cy - yy, 32); diff --git a/uppsrc/Draw/DrawUtil.cpp b/uppsrc/Draw/DrawUtil.cpp index b5efd537a..682730ac1 100644 --- a/uppsrc/Draw/DrawUtil.cpp +++ b/uppsrc/Draw/DrawUtil.cpp @@ -484,139 +484,6 @@ void DrawXPButton(Draw& w, Rect r, int type) } } -#ifdef PLATFORM_WIN32 - -HRGN GetFrameRgn(const Rect& rect, int n) { - HRGN rgn = CreateRectRgnIndirect(rect); - Rect r = rect; - r.Deflate(n); - if(r.Width() > 0 && r.Height() > 0) { - HRGN rgnin = CreateRectRgnIndirect(r); - CombineRgn(rgn, rgn, rgnin, RGN_XOR); - DeleteObject(rgnin); - } - return rgn; -} - -void DrawDragRect(SystemDraw& w, const Rect& _rect1, const Rect& _rect2, const Rect& _clip, int n, Color color, uint64 pattern) -{ - Point o = w.GetOffset(); - Rect rect1 = _rect1 + o; - Rect rect2 = _rect2 + o; - Rect clip = _clip + o; - HDC hdc = w.BeginGdi(); - word wpat[8] = { - (byte)(pattern >> 56), (byte)(pattern >> 48), (byte)(pattern >> 40), (byte)(pattern >> 32), - (byte)(pattern >> 24), (byte)(pattern >> 16), (byte)(pattern >> 8), (byte)(pattern >> 0), - }; - HBITMAP bitmap = CreateBitmap(8, 8, 1, 1, wpat); - HBRUSH brush = ::CreatePatternBrush(bitmap); - DeleteObject(bitmap); - SetTextColor(hdc, color); - SetBkColor(hdc, SColorText()); - Point offset; -#ifdef PLATFORM_WINCE - offset = Point(0, 0); -#else - ::GetViewportOrgEx(hdc, offset); -#endif - HRGN rgn = GetFrameRgn(rect1 + offset, n); - HRGN rgn2 = GetFrameRgn(rect2 + offset, n); - HRGN cliprgn = CreateRectRgnIndirect(clip + offset); - CombineRgn(rgn, rgn, rgn2, RGN_XOR); - CombineRgn(rgn, rgn, cliprgn, RGN_AND); - SelectClipRgn(hdc, rgn); - Rect r; - GetClipBox(hdc, r); - HBRUSH obrush = (HBRUSH) SelectObject(hdc, brush); - PatBlt(hdc, r.left, r.top, r.Width(), r.Height(), PATINVERT); - SelectObject(hdc, obrush); - SelectClipRgn(hdc, NULL); - DeleteObject(rgn); - DeleteObject(rgn2); - DeleteObject(cliprgn); - ReleaseDC(NULL, hdc); - DeleteObject(brush); - w.EndGdi(); -} - -#endif - -#ifdef PLATFORM_X11 - -Vector RectRgn(const Rect& r) -{ - Vector q; - q.Add(r); - return q; -} - -Vector Intersect(const Vector& r1, const Vector& r2) -{ - Vector q; - for(int i = 0; i < r1.GetCount(); i++) - for(int j = 0; j < r2.GetCount(); j++) { - Rect r = r1[i] & r2[j]; - if(!r.IsEmpty()) - q.Add(r); - } - return q; -} - -Vector Subtract(const Vector& r1, const Vector& r2) -{ - Vector q; - bool dummy; - q <<= r1; - for(int i = 0; i < r2.GetCount(); i++) - q = Subtract(q, r2[i], dummy); - return q; -} - - -Vector Xor(const Vector& r1, const Vector& r2) -{ - Vector is = Intersect(r1, r2); - Vector q = Subtract(r1, is); - q.Append(Subtract(r2, is)); - return q; -} - -Vector GetFrameRgn(const Rect& rect, int n) { - Vector q = RectRgn(rect); - q.Add(rect); - Rect r = rect; - r.Deflate(n); - if(r.Width() > 0 && r.Height() > 0) - q = Xor(q, RectRgn(r)); - return q; -} - -void DrawDragRect(SystemDraw& w, const Rect& rect1, const Rect& rect2, const Rect& clip, int n, - Color color, uint64 pattern) -{ - char bd[8]; - for(int i = 0; i < 8; i++) - bd[i] = ~(byte)(pattern >> (8 * (7 - i))); - Pixmap stipple = XCreateBitmapFromData(Xdisplay, w.GetDrawable(), bd, 8, 8); - Point offset = w.GetOffset(); - GC gc = XCreateGC(Xdisplay, w.GetDrawable(), 0, 0); - SetClip(gc, w.GetXftDraw(), - Intersect(Xor(GetFrameRgn(rect1 + offset, n), GetFrameRgn(rect2 + offset, n)), - RectRgn(clip + offset))); - - XGCValues gcv; - gcv.function = X11_ROP2_XOR; - gcv.foreground = GetXPixel(color); - gcv.fill_style = FillStippled; - gcv.stipple = stipple; - XChangeGC(Xdisplay, gc, GCForeground|GCFunction|GCStipple|GCFillStyle, &gcv); - XFillRectangle(Xdisplay, w.GetDrawable(), gc, 0, 0, Xwidth, Xheight); - XFreePixmap(Xdisplay, stipple); -} - -#endif - static DrawingToPdfFnType sPdf; void SetDrawingToPdfFn(DrawingToPdfFnType Pdf) diff --git a/uppsrc/Draw/Font.cpp b/uppsrc/Draw/Font.cpp index bcd73c76a..9e7ddc5ab 100644 --- a/uppsrc/Draw/Font.cpp +++ b/uppsrc/Draw/Font.cpp @@ -1,341 +1,343 @@ -#include "Draw.h" - -#define LLOG(x) - -NAMESPACE_UPP - -CommonFontInfo GetFontInfoSys(Font font); -GlyphInfo GetGlyphInfoSys(Font font, int chr); -void GetStdFontSys(String& name, int& height); -Vector GetAllFacesSys(); - -bool Replace(Font fnt, int chr, Font& rfnt); - -void Std(Font& font) -{ - if(IsNull(font)) - font = StdFont(); - if(font.GetFace() == 0) - font.Face(GetStdFont().GetFace()); - if(font.GetHeight() == 0) - font.Height(GetStdFont().GetHeight()); -} - -Size Font::StdFontSize; -Font Font::AStdFont; - -INITBLOCK { - RichValue::Register(); -} - -const Vector& Font::List() -{ - static Vector *q; - ONCELOCK { - static Vector x; - x = GetAllFacesSys(); - q = &x; - } - return *q; -} - -void sInitFonts() -{ - Font::List(); - GetStdFont(); -} - -INITBLOCK { - sInitFonts(); -} - -int Font::GetFaceCount() -{ - return List().GetCount(); -} - -String Font::GetFaceName(int index) -{ - if(index == 0) - return "STDFONT"; - const Vector& l = List(); - if(index >= 0 && index < l.GetCount()) - return l[index].name; - return Null; -} - -dword Font::GetFaceInfo(int index) -{ - const Vector& l = List(); - if(index >= 0 && index < l.GetCount()) - return l[index].info; - return 0; -} - -int FontFilter(int c) -{ - return c >= 'a' && c <= 'z' || c >= '0' && c <= '9' ? c : c >= 'A' && c <= 'Z' ? ToLower(c) : 0; -} - -int Font::FindFaceNameIndex(const String& name) { - if(name == "STDFONT") - return 0; - for(int i = 1; i < GetFaceCount(); i++) - if(GetFaceName(i) == name) - return i; - String n = Filter(name, FontFilter); - for(int i = 1; i < GetFaceCount(); i++) - if(Filter(GetFaceName(i), FontFilter) == n) - return i; - return 0; -} - -void Font::SyncStdFont() -{ - DrawLock __; - StdFontSize = Size(AStdFont.GetAveWidth(), AStdFont().Bold().GetCy()); -} - -void Font::SetStdFont(Font font) -{ - DrawLock __; - InitStdFont(); - AStdFont = font; - SyncStdFont(); - DLOG("SetStdFont " << font); -} - -void Font::InitStdFont() -{ - ONCELOCK { - DrawLock __; - List(); - AStdFont = Arial(12); - String name; - int height = 0; - GetStdFontSys(name, height); - int q = FindFaceNameIndex(name); - if(q > 0) - SetStdFont(Font(q, max(height, 1))); - } -} - -Font Font::GetStdFont() -{ - InitStdFont(); - return AStdFont; -} - -Size Font::GetStdFontSize() -{ - InitStdFont(); - return StdFontSize; -} - -Font StdFont() -{ - return Font(0, 0); -} - -int Font::GetHeight() const -{ - return v.height ? v.height : GetStdFont().GetHeight(); -} - -String Font::GetFaceName() const { - if(IsNull()) return String(); - if(GetFace() == 0) - return "STDFONT"; - return GetFaceName(GetFace()); -} - -dword Font::GetFaceInfo() const { - if(IsNull()) return 0; - return GetFaceInfo(GetFace()); -} - -Font& Font::FaceName(const String& name) { - int n = FindFaceNameIndex(name); - Face(n < 0 ? 0xffff : n); - return *this; -} - -void Font::Serialize(Stream& s) { - int version = 1; - s / version; - if(version >= 1) { - int f = GetFace(); - if(f > COURIER) - f = -1; - s / f; - String name; - if(f < 0) { - name = GetFaceName(); - s % name; - } - if(s.IsLoading()) - if(f >= 0) - Face(f); - else - FaceName(name); - } - else { - String name = GetFaceName(); - s % name; - if(s.IsLoading()) { - FaceName(name); - if(IsNull()) - Face(COURIER); - } - } - s % v.flags % v.height % v.width; -} - -template<> -String AsString(const Font& f) { - if(IsNull(f)) return ""; - String s = "<" + f.GetFaceName() + Format(":%d", f.GetHeight()); - if(f.IsBold()) - s += " Bold"; - if(f.IsItalic()) - s += " Italic"; - if(f.IsUnderline()) - s += " Underline"; - if(f.IsStrikeout()) - s += " Strikeout"; - return s + '>'; -} - -struct CharEntry { - int64 font; - GlyphInfo info; - word chr; -}; - -CharEntry fc_cache_global[4093]; - -bool IsNormal(Font font, int chr) -{ - DrawLock __; - CharEntry& e = fc_cache_global[CombineHash(font.GetHashValue(), chr) % 4093]; - if(e.font == font.AsInt64() || e.chr == chr) - return e.info.IsNormal(); - return GetGlyphInfoSys(font, chr).IsNormal(); -} - -CharEntry GetGlyphEntry(Font font, int chr, unsigned hash) -{ - DrawLock __; - CharEntry& e = fc_cache_global[hash % 4093]; - if(e.font != font.AsInt64() || e.chr != chr) { - e.font = font.AsInt64(); - e.chr = chr; - e.info = GetGlyphInfoSys(font, chr); - if(!e.info.IsNormal()) { - ComposedGlyph cg; - Font rfnt; - if(Compose(font, chr, cg)) { - e.info.lspc = -1; - e.info.rspc = cg.basic_char; - } - else - if(Replace(font, chr, rfnt)) { - e.info.lspc = rfnt.GetFace(); - e.info.rspc = rfnt.GetHeight(); - } - else - e.info.lspc = -2; - } - } - return e; -} - -thread__ CharEntry fc_cache[512]; - -GlyphInfo GetGlyphInfo(Font font, int chr) -{ - Std(font); - unsigned hash = CombineHash(font.GetHashValue(), chr); - CharEntry& e = fc_cache[hash & 511]; - if(e.font != font.AsInt64() || e.chr != chr) - e = GetGlyphEntry(font, chr, hash); - return e.info; -} - -void GlyphMetrics(GlyphInfo& f, Font font, int chr) -{ - if(f.IsReplaced()) - f = GetGlyphInfo(font().Face(f.lspc).Height(f.rspc), chr); - if(f.IsComposed()) { - f = GetGlyphInfo(font, f.rspc); - if(f.IsComposedLM()) - f.rspc += f.width / 2; - } -} - -GlyphInfo GetGlyphMetrics(Font font, int chr) -{ - GlyphInfo f = GetGlyphInfo(font, chr); - if(f.IsMissing()) - f = GetGlyphInfo(font, '?'); - GlyphMetrics(f, font, chr); - return f; -} - -struct FontEntry { - CommonFontInfo info; - int64 font; -}; - -thread__ FontEntry fi_cache[64]; - -const CommonFontInfo& GetFontInfo(Font font) -{ - Std(font); - unsigned hash = font.GetHashValue() & 63; - FontEntry& e = fi_cache[hash]; - if(e.font != font.AsInt64()) { - DrawLock __; - e.font = font.AsInt64(); - e.info = GetFontInfoSys(font); - } - return e.info; -} - -int Font::GetWidth(int c) const { - return GetGlyphMetrics(*this, c).width; -} - -int Font::GetLeftSpace(int c) const { - return GetGlyphMetrics(*this, c).lspc; -} - -int Font::GetRightSpace(int c) const { - return GetGlyphMetrics(*this, c).rspc; -} - -thread__ int64 lastFiFont = INT_MIN; -thread__ CommonFontInfo lastFontInfo; -thread__ int64 lastStdFont = INT_MIN; - -const CommonFontInfo& Font::Fi() const -{ - if(lastStdFont != AStdFont.AsInt64()) { - lastFiFont = INT_MIN; - lastStdFont = AStdFont.AsInt64(); - } - if(AsInt64() == lastFiFont) - return lastFontInfo; - lastFontInfo = GetFontInfo(*this); - lastFiFont = AsInt64(); - return lastFontInfo; -} - -FontInfo Font::Info() const -{ - FontInfo h; - h.font = *this; - return h; -} - -END_UPP_NAMESPACE +#include "Draw.h" + +#define LLOG(x) + +NAMESPACE_UPP + +CommonFontInfo GetFontInfoSys(Font font); +GlyphInfo GetGlyphInfoSys(Font font, int chr); +void GetStdFontSys(String& name, int& height); +Vector GetAllFacesSys(); + +bool Replace(Font fnt, int chr, Font& rfnt); + +void Std(Font& font) +{ + if(IsNull(font)) + font = StdFont(); + if(font.GetFace() == 0) + font.Face(GetStdFont().GetFace()); + if(font.GetHeight() == 0) + font.Height(GetStdFont().GetHeight()); +} + +Size Font::StdFontSize; +Font Font::AStdFont; + +INITBLOCK { + RichValue::Register(); +} + +const Vector& Font::List() +{ + static Vector *q; + ONCELOCK { + static Vector x; + x = GetAllFacesSys(); + q = &x; + } + return *q; +} + +void sInitFonts() +{ + Font::List(); + GetStdFont(); +} + +INITBLOCK { + sInitFonts(); +} + +int Font::GetFaceCount() +{ + return List().GetCount(); +} + +String Font::GetFaceName(int index) +{ + if(index == 0) + return "STDFONT"; + const Vector& l = List(); + if(index >= 0 && index < l.GetCount()) + return l[index].name; + return Null; +} + +dword Font::GetFaceInfo(int index) +{ + const Vector& l = List(); + if(index >= 0 && index < l.GetCount()) + return l[index].info; + return 0; +} + +int FontFilter(int c) +{ + return c >= 'a' && c <= 'z' || c >= '0' && c <= '9' ? c : c >= 'A' && c <= 'Z' ? ToLower(c) : 0; +} + +int Font::FindFaceNameIndex(const String& name) { + if(name == "STDFONT") + return 0; + for(int i = 1; i < GetFaceCount(); i++) + if(GetFaceName(i) == name) + return i; + String n = Filter(name, FontFilter); + for(int i = 1; i < GetFaceCount(); i++) + if(Filter(GetFaceName(i), FontFilter) == n) + return i; + return 0; +} + +void Font::SyncStdFont() +{ + DrawLock __; + StdFontSize = Size(AStdFont.GetAveWidth(), AStdFont().Bold().GetCy()); +} + +void Font::SetStdFont(Font font) +{ + DrawLock __; + static bool x; + InitStdFont(); + AStdFont = font; + SyncStdFont(); +} + +void Font::InitStdFont() +{ + ONCELOCK { + DrawLock __; + List(); + AStdFont = Arial(12); + String name; + int height = 0; + GetStdFontSys(name, height); + int q = FindFaceNameIndex(name); + if(q > 0) { + AStdFont = Font(q, max(height, 1)); + SyncStdFont(); + } + } +} + +Font Font::GetStdFont() +{ + InitStdFont(); + return AStdFont; +} + +Size Font::GetStdFontSize() +{ + InitStdFont(); + return StdFontSize; +} + +Font StdFont() +{ + return Font(0, 0); +} + +int Font::GetHeight() const +{ + return v.height ? v.height : GetStdFont().GetHeight(); +} + +String Font::GetFaceName() const { + if(IsNull()) return String(); + if(GetFace() == 0) + return "STDFONT"; + return GetFaceName(GetFace()); +} + +dword Font::GetFaceInfo() const { + if(IsNull()) return 0; + return GetFaceInfo(GetFace()); +} + +Font& Font::FaceName(const String& name) { + int n = FindFaceNameIndex(name); + Face(n < 0 ? 0xffff : n); + return *this; +} + +void Font::Serialize(Stream& s) { + int version = 1; + s / version; + if(version >= 1) { + int f = GetFace(); + if(f > COURIER) + f = -1; + s / f; + String name; + if(f < 0) { + name = GetFaceName(); + s % name; + } + if(s.IsLoading()) + if(f >= 0) + Face(f); + else + FaceName(name); + } + else { + String name = GetFaceName(); + s % name; + if(s.IsLoading()) { + FaceName(name); + if(IsNull()) + Face(COURIER); + } + } + s % v.flags % v.height % v.width; +} + +template<> +String AsString(const Font& f) { + if(IsNull(f)) return ""; + String s = "<" + f.GetFaceName() + Format(":%d", f.GetHeight()); + if(f.IsBold()) + s += " Bold"; + if(f.IsItalic()) + s += " Italic"; + if(f.IsUnderline()) + s += " Underline"; + if(f.IsStrikeout()) + s += " Strikeout"; + return s + '>'; +} + +struct CharEntry { + int64 font; + GlyphInfo info; + word chr; +}; + +CharEntry fc_cache_global[4093]; + +bool IsNormal(Font font, int chr) +{ + DrawLock __; + CharEntry& e = fc_cache_global[CombineHash(font.GetHashValue(), chr) % 4093]; + if(e.font == font.AsInt64() || e.chr == chr) + return e.info.IsNormal(); + return GetGlyphInfoSys(font, chr).IsNormal(); +} + +CharEntry GetGlyphEntry(Font font, int chr, unsigned hash) +{ + DrawLock __; + CharEntry& e = fc_cache_global[hash % 4093]; + if(e.font != font.AsInt64() || e.chr != chr) { + e.font = font.AsInt64(); + e.chr = chr; + e.info = GetGlyphInfoSys(font, chr); + if(!e.info.IsNormal()) { + ComposedGlyph cg; + Font rfnt; + if(Compose(font, chr, cg)) { + e.info.lspc = -1; + e.info.rspc = cg.basic_char; + } + else + if(Replace(font, chr, rfnt)) { + e.info.lspc = rfnt.GetFace(); + e.info.rspc = rfnt.GetHeight(); + } + else + e.info.lspc = -2; + } + } + return e; +} + +thread__ CharEntry fc_cache[512]; + +GlyphInfo GetGlyphInfo(Font font, int chr) +{ + Std(font); + unsigned hash = CombineHash(font.GetHashValue(), chr); + CharEntry& e = fc_cache[hash & 511]; + if(e.font != font.AsInt64() || e.chr != chr) + e = GetGlyphEntry(font, chr, hash); + return e.info; +} + +void GlyphMetrics(GlyphInfo& f, Font font, int chr) +{ + if(f.IsReplaced()) + f = GetGlyphInfo(font().Face(f.lspc).Height(f.rspc), chr); + if(f.IsComposed()) { + f = GetGlyphInfo(font, f.rspc); + if(f.IsComposedLM()) + f.rspc += f.width / 2; + } +} + +GlyphInfo GetGlyphMetrics(Font font, int chr) +{ + GlyphInfo f = GetGlyphInfo(font, chr); + if(f.IsMissing()) + f = GetGlyphInfo(font, '?'); + GlyphMetrics(f, font, chr); + return f; +} + +struct FontEntry { + CommonFontInfo info; + int64 font; +}; + +thread__ FontEntry fi_cache[64]; + +const CommonFontInfo& GetFontInfo(Font font) +{ + Std(font); + unsigned hash = font.GetHashValue() & 63; + FontEntry& e = fi_cache[hash]; + if(e.font != font.AsInt64()) { + DrawLock __; + e.font = font.AsInt64(); + e.info = GetFontInfoSys(font); + } + return e.info; +} + +int Font::GetWidth(int c) const { + return GetGlyphMetrics(*this, c).width; +} + +int Font::GetLeftSpace(int c) const { + return GetGlyphMetrics(*this, c).lspc; +} + +int Font::GetRightSpace(int c) const { + return GetGlyphMetrics(*this, c).rspc; +} + +thread__ int64 lastFiFont = INT_MIN; +thread__ CommonFontInfo lastFontInfo; +thread__ int64 lastStdFont = INT_MIN; + +const CommonFontInfo& Font::Fi() const +{ + if(lastStdFont != AStdFont.AsInt64()) { + lastFiFont = INT_MIN; + lastStdFont = AStdFont.AsInt64(); + } + if(AsInt64() == lastFiFont) + return lastFontInfo; + lastFontInfo = GetFontInfo(*this); + lastFiFont = AsInt64(); + return lastFontInfo; +} + +FontInfo Font::Info() const +{ + FontInfo h; + h.font = *this; + return h; +} + +END_UPP_NAMESPACE diff --git a/uppsrc/Draw/FontInt.h b/uppsrc/Draw/FontInt.h index 9b0f6b3f5..cf3848cda 100644 --- a/uppsrc/Draw/FontInt.h +++ b/uppsrc/Draw/FontInt.h @@ -8,7 +8,7 @@ struct FaceInfo : Moveable { dword info; }; -struct CommonFontInfo : Moveable { +struct CommonFontInfo { int ascent; int descent; int external; diff --git a/uppsrc/Draw/Image.cpp b/uppsrc/Draw/Image.cpp index 914f9176c..f6068efec 100644 --- a/uppsrc/Draw/Image.cpp +++ b/uppsrc/Draw/Image.cpp @@ -95,12 +95,6 @@ ImageBuffer::ImageBuffer(Image& img) Set(img); } -ImageBuffer::ImageBuffer(ImageDraw& w) -{ - Image img = w; - Set(img); -} - ImageBuffer::ImageBuffer(ImageBuffer& b) { kind = b.kind; @@ -345,15 +339,6 @@ void Image::Data::PaintOnlyShrink() } } -Draw& ImageDraw::Alpha() -{ - if(!has_alpha) { - alpha.DrawRect(size, GrayColor(0)); - has_alpha = true; - } - return alpha; -} - static void sMultiply(ImageBuffer& b, int (*op)(RGBA *t, const RGBA *s, int len)) { if(b.GetKind() != IMAGE_OPAQUE && b.GetKind() != IMAGE_EMPTY) diff --git a/uppsrc/Draw/Image.h b/uppsrc/Draw/Image.h index 304f7976f..e139d9600 100644 --- a/uppsrc/Draw/Image.h +++ b/uppsrc/Draw/Image.h @@ -1,334 +1,332 @@ -#define NEWIMAGE - -enum ImageKind { - IMAGE_UNKNOWN, - IMAGE_EMPTY, - IMAGE_ALPHA, - IMAGE_MASK, - IMAGE_OPAQUE, -}; - -inline bool operator==(const RGBA& a, const RGBA& b) -{ - return a.r == b.r && a.g == b.g && a.b == b.b && a.a == b.a; -} - -inline bool operator!=(const RGBA& a, const RGBA& b) -{ - return !(a == b); -} - -inline RGBA RGBAZero() { RGBA c; c.r = c.g = c.b = c.a = 0; return c; } - -void Fill(RGBA *t, const RGBA& src, int n); -void FillColor(RGBA *t, const RGBA& src, int n); - -void Copy(RGBA *t, const RGBA *s, int n); - -int Premultiply(RGBA *t, const RGBA *s, int len); -int Unmultiply(RGBA *t, const RGBA *s, int len); - -void AlphaBlend(RGBA *t, const RGBA *s, int len); -void AlphaBlend(RGBA *t, const RGBA *s, int len, Color color); - -void AlphaBlendOpaque(RGBA *t, const RGBA *s, int len, Color color); -void AlphaBlendOpaque(RGBA *t, const RGBA *s, int len); - -void AlphaBlendStraight(RGBA *b, const RGBA *f, int len); -void AlphaBlendStraight(RGBA *b, const RGBA *f, int len, Color color); -void AlphaBlendStraightOpaque(RGBA *t, const RGBA *s, int len); -void AlphaBlendStraightOpaque(RGBA *t, const RGBA *s, int len, int alpha); - -int GetChMaskPos32(dword mask); -void AlphaBlendOverBgST(RGBA *b, RGBA bg, int len); - -const byte *UnpackRLE(RGBA *t, const byte *src, int len); -String PackRLE(const RGBA *s, int len); - -inline int Grayscale(int r, int g, int b) { return (77 * r + 151 * g + 28 * b) >> 8; } -inline int Grayscale(const RGBA& c) { return Grayscale(c.r, c.g, c.b); } -inline byte Saturate255(int x) { return byte(~(x >> 24) & (x | (-(x >> 8) >> 24)) & 0xff); } - -class Image; -class ImageDraw; - -class ImageBuffer : NoCopy { - mutable int kind; - Size size; - Buffer pixels; - Point hotspot; - Point spot2; - Size dots; - - void Set(Image& img); - void DeepCopy(const ImageBuffer& img); - - RGBA* Line(int i) const { ASSERT(i >= 0 && i < size.cy); return (RGBA *)~pixels + i * size.cx; } - friend void DropPixels___(ImageBuffer& b) { b.pixels.Clear(); } - - friend class Image; - -public: - void SetKind(int k) { kind = k; } - int GetKind() const { return kind; } - int ScanKind() const; - int GetScanKind() const { return kind == IMAGE_UNKNOWN ? ScanKind() : kind; } - - void SetHotSpot(Point p) { hotspot = p; } - Point GetHotSpot() const { return hotspot; } - - void Set2ndSpot(Point p) { spot2 = p; } - Point Get2ndSpot() const { return spot2; } - - void SetDots(Size sz) { dots = sz; } - Size GetDots() const { return dots; } - - Size GetSize() const { return size; } - int GetWidth() const { return size.cx; } - int GetHeight() const { return size.cy; } - int GetLength() const { return size.cx * size.cy; } - - RGBA *operator[](int i) { return Line(i); } - const RGBA *operator[](int i) const { return Line(i); } - RGBA *operator~() { return pixels; } - operator RGBA*() { return pixels; } - const RGBA *operator~() const { return pixels; } - operator const RGBA*() const { return pixels; } - - void Create(int cx, int cy); - void Create(Size sz) { Create(sz.cx, sz.cy); } - bool IsEmpty() const { return (size.cx | size.cy) == 0; } - void Clear() { Create(0, 0); } - - void operator=(Image& img); - void operator=(ImageBuffer& img); - - ImageBuffer() { Create(0, 0); } - ImageBuffer(int cx, int cy) { Create(cx, cy); } - ImageBuffer(Size sz) { Create(sz.cx, sz.cy); } - ImageBuffer(Image& img); - ImageBuffer(ImageDraw& w); - ImageBuffer(ImageBuffer& b); -}; - -void Premultiply(ImageBuffer& b); -void Unmultiply(ImageBuffer& b); - -void SetSurface(Draw& w, int x, int y, int cx, int cy, const RGBA *pixels); - -class Image : public AssignValueTypeNo< Image, 150, Moveable > { -private: - struct Data : Link { - Atomic refcount; - int64 serial; - int paintcount; - - static Link ResData[1]; - static int ResCount; - - void Retain() { AtomicInc(refcount); } - void Release() { if(AtomicDec(refcount) == 0) delete this; } - - struct SystemData; - - void *system_buffer[6]; - SystemData& Sys() const; - int GetResCount() const; - -#ifdef PLATFORM_WIN32 - void CreateHBMP(HDC dc, const RGBA *data); -#endif - - ImageBuffer buffer; - bool paintonly; - - void SysInit(); - void SysRelease(); - int GetKind(); - void Paint(SystemDraw& w, int x, int y, const Rect& src, Color c); - void PaintOnlyShrink(); - - Data(ImageBuffer& b); - ~Data(); - }; - - Data *data; - - static Link ResData[1]; - static int ResCount; - - void Set(ImageBuffer& b); - - friend class ImageBuffer; - friend struct Data; - - friend class SystemDraw; - - void PaintImage(SystemDraw& w, int x, int y, const Rect& src, Color c) const; - - friend void SetPaintOnly___(Image& m); - friend void DrawImageBandRLE(Draw& w, int x, int y, const Image& m, int minp); - -#ifdef PLATFORM_WIN32 -#ifndef PLATFORM_WINCE - void SetCursorCheat(LPCSTR id); - LPCSTR GetCursorCheat() const; - friend Image Win32IconCursor(LPCSTR id, int iconsize, bool cursor); - friend HICON IconWin32(const Image& img, bool cursor); -#endif -#endif - -#ifdef PLATFORM_X11 - void SetCursorCheat(int id); - int GetCursorCheat() const; - friend Cursor X11Cursor(const Image&); - friend Image sX11Cursor__(int c); -#endif - -public: - const RGBA* operator~() const; - operator const RGBA*() const; - const RGBA* operator[](int i) const; - - Size GetSize() const; - int GetWidth() const { return GetSize().cx; } - int GetHeight() const { return GetSize().cy; } - int GetLength() const; - Point GetHotSpot() const; - Point Get2ndSpot() const; - Size GetDots() const; - int GetKindNoScan() const; - int GetKind() const; - - int64 GetSerialId() const { return data ? data->serial : 0; } - bool IsSame(const Image& img) const { return GetSerialId() == img.GetSerialId(); } - - bool operator==(const Image& img) const; - bool operator!=(const Image& img) const; - dword GetHashValue() const; - String ToString() const; - - void Serialize(Stream& s); - void Clear(); - - Image& operator=(const Image& img); - Image& operator=(ImageBuffer& img); - - bool IsNullInstance() const { Size sz = GetSize(); return (sz.cx|sz.cy) == 0; } - - bool IsEmpty() const { return IsNullInstance(); } - operator Value() const { return RichValue(*this); } - - Image() { data = NULL; } - Image(const Nuller&) { data = NULL; } - Image(const Value& src); - Image(const Image& img); - Image(Image (*fn)()); - Image(ImageBuffer& b); - ~Image(); - - - static Image Arrow(); - static Image Wait(); - static Image IBeam(); - static Image No(); - static Image SizeAll(); - static Image SizeHorz(); - static Image SizeVert(); - static Image SizeTopLeft(); - static Image SizeTop(); - static Image SizeTopRight(); - static Image SizeLeft(); - static Image SizeRight(); - static Image SizeBottomLeft(); - static Image SizeBottom(); - static Image SizeBottomRight(); - static Image Cross(); - static Image Hand(); - - // IML support ("private"), deprecated - legacy .iml - struct Init { - const char *const *scans; - int16 scan_count; - char info[24]; - }; - explicit Image(const Init& init); -}; - -Image Premultiply(const Image& img); -Image Unmultiply(const Image& img); - -Vector UnpackImlData(const void *ptr, int len); -Vector UnpackImlData(const String& d); - -class Iml { - struct IImage : Moveable { - bool loaded; - Image image; - - IImage() { loaded = false; } - }; - struct Data : Moveable { - const char *data; - int len, count; - }; - Vector data; - VectorMap map; - const Image::Init *img_init; - const char **name; - bool premultiply; - - void Init(int n); - -public: - void Enter(); - void Leave(); - void Reset(); - int GetCount() const { return map.GetCount(); } - String GetId(int i) { return map.GetKey(i); } - Image Get(int i); - int Find(const String& s) const { return map.Find(s); } - void Set(int i, const Image& img); - void Premultiplied() { premultiply = false; } - -#ifdef _DEBUG - int GetBinSize() const; -#endif - - Iml(const Image::Init *img_init, const char **name, int n);//Deprecated - legacy .iml - void AddData(const byte *data, int len, int count); -}; - -void Register(const char *imageclass, Iml& iml); - -int GetImlCount(); -String GetImlName(int i); -Iml& GetIml(int i); -int FindIml(const char *name); -Image GetImlImage(const char *name); -void SetImlImage(const char *name, const Image& m); - -String StoreImageAsString(const Image& img); -Image LoadImageFromString(const String& s); -Size GetImageStringSize(const String& src); -Size GetImageStringDots(const String& src); - -#include "Raster.h" -#include "ImageOp.h" - -#ifdef PLATFORM_WIN32 -#ifndef PLATFORM_WINCE - -Image Win32Icon(LPCSTR id, int iconsize = 0); -Image Win32Icon(int id, int iconsize = 0); -Image Win32Cursor(LPCSTR id); -Image Win32Cursor(int id); -HICON IconWin32(const Image& img, bool cursor = false); -Image Win32DllIcon(const char *dll, int ii, bool large); - -#endif -#endif - -#ifdef PLATFORM_X11 -Cursor X11Cursor(const Image& img); -#endif +#define NEWIMAGE + +enum ImageKind { + IMAGE_UNKNOWN, + IMAGE_EMPTY, + IMAGE_ALPHA, + IMAGE_MASK, + IMAGE_OPAQUE, +}; + +inline bool operator==(const RGBA& a, const RGBA& b) +{ + return a.r == b.r && a.g == b.g && a.b == b.b && a.a == b.a; +} + +inline bool operator!=(const RGBA& a, const RGBA& b) +{ + return !(a == b); +} + +inline RGBA RGBAZero() { RGBA c; c.r = c.g = c.b = c.a = 0; return c; } + +void Fill(RGBA *t, const RGBA& src, int n); +void FillColor(RGBA *t, const RGBA& src, int n); + +void Copy(RGBA *t, const RGBA *s, int n); + +int Premultiply(RGBA *t, const RGBA *s, int len); +int Unmultiply(RGBA *t, const RGBA *s, int len); + +void AlphaBlend(RGBA *t, const RGBA *s, int len); +void AlphaBlend(RGBA *t, const RGBA *s, int len, Color color); + +void AlphaBlendOpaque(RGBA *t, const RGBA *s, int len, Color color); +void AlphaBlendOpaque(RGBA *t, const RGBA *s, int len); + +void AlphaBlendStraight(RGBA *b, const RGBA *f, int len); +void AlphaBlendStraight(RGBA *b, const RGBA *f, int len, Color color); +void AlphaBlendStraightOpaque(RGBA *t, const RGBA *s, int len); +void AlphaBlendStraightOpaque(RGBA *t, const RGBA *s, int len, int alpha); + +int GetChMaskPos32(dword mask); +void AlphaBlendOverBgST(RGBA *b, RGBA bg, int len); + +const byte *UnpackRLE(RGBA *t, const byte *src, int len); +String PackRLE(const RGBA *s, int len); + +inline int Grayscale(int r, int g, int b) { return (77 * r + 151 * g + 28 * b) >> 8; } +inline int Grayscale(const RGBA& c) { return Grayscale(c.r, c.g, c.b); } +inline byte Saturate255(int x) { return byte(~(x >> 24) & (x | (-(x >> 8) >> 24)) & 0xff); } + +class Image; + +class ImageBuffer : NoCopy { + mutable int kind; + Size size; + Buffer pixels; + Point hotspot; + Point spot2; + Size dots; + + void Set(Image& img); + void DeepCopy(const ImageBuffer& img); + + RGBA* Line(int i) const { ASSERT(i >= 0 && i < size.cy); return (RGBA *)~pixels + i * size.cx; } + friend void DropPixels___(ImageBuffer& b) { b.pixels.Clear(); } + + friend class Image; + +public: + void SetKind(int k) { kind = k; } + int GetKind() const { return kind; } + int ScanKind() const; + int GetScanKind() const { return kind == IMAGE_UNKNOWN ? ScanKind() : kind; } + + void SetHotSpot(Point p) { hotspot = p; } + Point GetHotSpot() const { return hotspot; } + + void Set2ndSpot(Point p) { spot2 = p; } + Point Get2ndSpot() const { return spot2; } + + void SetDots(Size sz) { dots = sz; } + Size GetDots() const { return dots; } + + Size GetSize() const { return size; } + int GetWidth() const { return size.cx; } + int GetHeight() const { return size.cy; } + int GetLength() const { return size.cx * size.cy; } + + RGBA *operator[](int i) { return Line(i); } + const RGBA *operator[](int i) const { return Line(i); } + RGBA *operator~() { return pixels; } + operator RGBA*() { return pixels; } + const RGBA *operator~() const { return pixels; } + operator const RGBA*() const { return pixels; } + + void Create(int cx, int cy); + void Create(Size sz) { Create(sz.cx, sz.cy); } + bool IsEmpty() const { return (size.cx | size.cy) == 0; } + void Clear() { Create(0, 0); } + + void operator=(Image& img); + void operator=(ImageBuffer& img); + + ImageBuffer() { Create(0, 0); } + ImageBuffer(int cx, int cy) { Create(cx, cy); } + ImageBuffer(Size sz) { Create(sz.cx, sz.cy); } + ImageBuffer(Image& img); + ImageBuffer(ImageBuffer& b); +}; + +void Premultiply(ImageBuffer& b); +void Unmultiply(ImageBuffer& b); + +void SetSurface(Draw& w, int x, int y, int cx, int cy, const RGBA *pixels); + +class Image : public AssignValueTypeNo< Image, 150, Moveable > { +private: + struct Data : Link { + Atomic refcount; + int64 serial; + int paintcount; + + static Link ResData[1]; + static int ResCount; + + void Retain() { AtomicInc(refcount); } + void Release() { if(AtomicDec(refcount) == 0) delete this; } + + struct SystemData; + + void *system_buffer[6]; + SystemData& Sys() const; + int GetResCount() const; + +#ifdef PLATFORM_WIN32 + void CreateHBMP(HDC dc, const RGBA *data); +#endif + + ImageBuffer buffer; + bool paintonly; + + void SysInit(); + void SysRelease(); + int GetKind(); + void Paint(SystemDraw& w, int x, int y, const Rect& src, Color c); + void PaintOnlyShrink(); + + Data(ImageBuffer& b); + ~Data(); + }; + + Data *data; + + static Link ResData[1]; + static int ResCount; + + void Set(ImageBuffer& b); + + friend class ImageBuffer; + friend struct Data; + + friend class SystemDraw; + + void PaintImage(SystemDraw& w, int x, int y, const Rect& src, Color c) const; + + friend void SetPaintOnly___(Image& m); + friend void DrawImageBandRLE(Draw& w, int x, int y, const Image& m, int minp); + +#ifdef PLATFORM_WIN32 +#ifndef PLATFORM_WINCE + void SetCursorCheat(LPCSTR id); + LPCSTR GetCursorCheat() const; + friend Image Win32IconCursor(LPCSTR id, int iconsize, bool cursor); + friend HICON IconWin32(const Image& img, bool cursor); +#endif +#endif + +#ifdef PLATFORM_X11 + void SetCursorCheat(int id); + int GetCursorCheat() const; + friend Cursor X11Cursor(const Image&); + friend Image sX11Cursor__(int c); +#endif + +public: + const RGBA* operator~() const; + operator const RGBA*() const; + const RGBA* operator[](int i) const; + + Size GetSize() const; + int GetWidth() const { return GetSize().cx; } + int GetHeight() const { return GetSize().cy; } + int GetLength() const; + Point GetHotSpot() const; + Point Get2ndSpot() const; + Size GetDots() const; + int GetKindNoScan() const; + int GetKind() const; + + int64 GetSerialId() const { return data ? data->serial : 0; } + bool IsSame(const Image& img) const { return GetSerialId() == img.GetSerialId(); } + + bool operator==(const Image& img) const; + bool operator!=(const Image& img) const; + dword GetHashValue() const; + String ToString() const; + + void Serialize(Stream& s); + void Clear(); + + Image& operator=(const Image& img); + Image& operator=(ImageBuffer& img); + + bool IsNullInstance() const { Size sz = GetSize(); return (sz.cx|sz.cy) == 0; } + + bool IsEmpty() const { return IsNullInstance(); } + operator Value() const { return RichValue(*this); } + + Image() { data = NULL; } + Image(const Nuller&) { data = NULL; } + Image(const Value& src); + Image(const Image& img); + Image(Image (*fn)()); + Image(ImageBuffer& b); + ~Image(); + + + static Image Arrow(); + static Image Wait(); + static Image IBeam(); + static Image No(); + static Image SizeAll(); + static Image SizeHorz(); + static Image SizeVert(); + static Image SizeTopLeft(); + static Image SizeTop(); + static Image SizeTopRight(); + static Image SizeLeft(); + static Image SizeRight(); + static Image SizeBottomLeft(); + static Image SizeBottom(); + static Image SizeBottomRight(); + static Image Cross(); + static Image Hand(); + + // IML support ("private"), deprecated - legacy .iml + struct Init { + const char *const *scans; + int16 scan_count; + char info[24]; + }; + explicit Image(const Init& init); +}; + +Image Premultiply(const Image& img); +Image Unmultiply(const Image& img); + +Vector UnpackImlData(const void *ptr, int len); +Vector UnpackImlData(const String& d); + +class Iml { + struct IImage : Moveable { + bool loaded; + Image image; + + IImage() { loaded = false; } + }; + struct Data : Moveable { + const char *data; + int len, count; + }; + Vector data; + VectorMap map; + const Image::Init *img_init; + const char **name; + bool premultiply; + + void Init(int n); + +public: + void Enter(); + void Leave(); + void Reset(); + int GetCount() const { return map.GetCount(); } + String GetId(int i) { return map.GetKey(i); } + Image Get(int i); + int Find(const String& s) const { return map.Find(s); } + void Set(int i, const Image& img); + void Premultiplied() { premultiply = false; } + +#ifdef _DEBUG + int GetBinSize() const; +#endif + + Iml(const Image::Init *img_init, const char **name, int n);//Deprecated - legacy .iml + void AddData(const byte *data, int len, int count); +}; + +void Register(const char *imageclass, Iml& iml); + +int GetImlCount(); +String GetImlName(int i); +Iml& GetIml(int i); +int FindIml(const char *name); +Image GetImlImage(const char *name); +void SetImlImage(const char *name, const Image& m); + +String StoreImageAsString(const Image& img); +Image LoadImageFromString(const String& s); +Size GetImageStringSize(const String& src); +Size GetImageStringDots(const String& src); + +#include "Raster.h" +#include "ImageOp.h" + +#ifdef PLATFORM_WIN32 +#ifndef PLATFORM_WINCE + +Image Win32Icon(LPCSTR id, int iconsize = 0); +Image Win32Icon(int id, int iconsize = 0); +Image Win32Cursor(LPCSTR id); +Image Win32Cursor(int id); +HICON IconWin32(const Image& img, bool cursor = false); +Image Win32DllIcon(const char *dll, int ii, bool large); + +#endif +#endif + +#ifdef PLATFORM_X11 +Cursor X11Cursor(const Image& img); +#endif diff --git a/uppsrc/RichText/ParaData.cpp b/uppsrc/RichText/ParaData.cpp index bdf5d91af..7215eb00c 100644 --- a/uppsrc/RichText/ParaData.cpp +++ b/uppsrc/RichText/ParaData.cpp @@ -718,11 +718,9 @@ void RichPara::Dump() String RichPara::CharFormat::ToString() const { String out; - out - << Font(*this) - << ", ink " << DumpColor(ink); + out << Font(*this) << ", ink " << ink; if(!UPP::IsNull(paper)) - out << ", paper " << DumpColor(paper); + out << ", paper " << paper; switch(sscript) { case 0: break; @@ -730,7 +728,7 @@ String RichPara::CharFormat::ToString() const case 2: out << ", subscript"; break; default: out << ", sscript(" << (int)sscript << ")"; break; } - out << ", lang " << DumpLanguage(language); + out << ", lang " << LNGAsText(language); if(!UPP::IsNull(link)) out << ", link " << link; if(capitals) @@ -746,7 +744,7 @@ String RichPara::Format::ToString() const if(!UPP::IsNull(label)) out << "label <" << label << ">: "; out - << DumpAlign(align) << ", left " << lm << ", right " << rm + << align << ", left " << lm << ", right " << rm << ", indent " << indent << ", before " << before << ", after " << after << ", tabsize " << tabsize << ", bullet " << bullet << (newpage ? ", newpage" : "") @@ -756,7 +754,7 @@ String RichPara::Format::ToString() const int i; for(i = 0; i < tab.GetCount(); i++) out << (i ? "\n" : ", ") - << "tab[" << i << "] = " << tab[i].pos << ", align " << DumpAlign(tab[i].align) + << "tab[" << i << "] = " << tab[i].pos << ", align " << tab[i].align << ", fill " << FormatIntHex(tab[i].fillchar, 2); out << "\n"; out << "before_number " << before_number << ", after_number " << after_number