mirror of
https://github.com/ultimatepp/ultimatepp.git
synced 2026-07-11 22:03:01 -06:00
plugin/Eigen moved to uppsrc
git-svn-id: svn://ultimatepp.org/upp/trunk@5632 f0d560ea-af0d-0410-9eb7-867de7ffcac7
This commit is contained in:
parent
c8c7b84a1a
commit
178220c490
298 changed files with 183 additions and 69 deletions
|
|
@ -1,4 +1,4 @@
|
|||
description "Eigen package demo\377";
|
||||
description "plugin/Eigen demo\377";
|
||||
|
||||
uses
|
||||
Core,
|
||||
|
|
@ -7,7 +7,7 @@ using namespace Upp;
|
|||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
struct GtkDraw : Draw {
|
||||
class CairoDraw : public Draw {
|
||||
virtual dword GetInfo() const;
|
||||
|
||||
virtual void BeginOp();
|
||||
|
|
@ -38,7 +38,6 @@ struct GtkDraw : Draw {
|
|||
virtual void DrawTextOp(int x, int y, int angle, const wchar *text, Font font,
|
||||
Color ink, int n, const int *dx);
|
||||
|
||||
cairo_t *cr;
|
||||
|
||||
private:
|
||||
void SetColor(Color c);
|
||||
|
|
@ -47,6 +46,38 @@ private:
|
|||
void Push();
|
||||
void Pop();
|
||||
Vector<Point> offset;
|
||||
|
||||
cairo_t *cr;
|
||||
CairoDraw() {}
|
||||
|
||||
friend class CairoImageDraw;
|
||||
|
||||
public:
|
||||
operator cairo_t*() { return cr; }
|
||||
|
||||
CairoDraw(cairo_t *cr) : cr(cr) {}
|
||||
};
|
||||
|
||||
class CairoImageDraw : public CairoDraw {
|
||||
cairo_surface_t *surface;
|
||||
Size isz;
|
||||
|
||||
CairoDraw alpha;
|
||||
cairo_surface_t *alpha_surface;
|
||||
|
||||
void Init(Size sz);
|
||||
void FetchStraight(ImageBuffer& b) const;
|
||||
|
||||
public:
|
||||
Draw& Alpha();
|
||||
|
||||
operator Image() const;
|
||||
|
||||
Image GetStraight() const;
|
||||
|
||||
CairoImageDraw(Size sz);
|
||||
CairoImageDraw(int cx, int cy);
|
||||
~CairoImageDraw();
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
uses
|
||||
Draw;
|
||||
Draw,
|
||||
plugin/png;
|
||||
|
||||
library
|
||||
"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";
|
||||
|
|
@ -8,6 +9,8 @@ file
|
|||
Test.iml,
|
||||
GtkApp.h,
|
||||
GtkDraw.cpp,
|
||||
ImageDraw.cpp,
|
||||
BackDraw.cpp,
|
||||
main.cpp;
|
||||
|
||||
mainconfig
|
||||
|
|
|
|||
|
|
@ -2,57 +2,59 @@
|
|||
|
||||
#include <cairo/cairo-ft.h>
|
||||
|
||||
void GtkDraw::SetColor(Color c)
|
||||
#define LLOG(x)
|
||||
|
||||
void CairoDraw::SetColor(Color c)
|
||||
{
|
||||
cairo_set_source_rgb(cr, c.GetR() / 255.0, c.GetG() / 255.0, c.GetB() / 255.0);
|
||||
}
|
||||
|
||||
dword GtkDraw::GetInfo() const
|
||||
dword CairoDraw::GetInfo() const
|
||||
{
|
||||
return DRAWTEXTLINES;
|
||||
}
|
||||
|
||||
Point GtkDraw::GetOffset() const
|
||||
Point CairoDraw::GetOffset() const
|
||||
{
|
||||
return offset.GetCount() ? offset.Top() : Point(0, 0);
|
||||
}
|
||||
|
||||
void GtkDraw::Push()
|
||||
void CairoDraw::Push()
|
||||
{
|
||||
cairo_save(cr);
|
||||
offset.Add(GetOffset());
|
||||
}
|
||||
|
||||
void GtkDraw::Pop()
|
||||
void CairoDraw::Pop()
|
||||
{
|
||||
if(offset.GetCount())
|
||||
offset.Drop();
|
||||
cairo_restore(cr);
|
||||
}
|
||||
|
||||
void GtkDraw::BeginOp()
|
||||
void CairoDraw::BeginOp()
|
||||
{
|
||||
Push();
|
||||
}
|
||||
|
||||
void GtkDraw::EndOp()
|
||||
void CairoDraw::EndOp()
|
||||
{
|
||||
Pop();
|
||||
}
|
||||
|
||||
void GtkDraw::OffsetOp(Point p)
|
||||
void CairoDraw::OffsetOp(Point p)
|
||||
{
|
||||
Push();
|
||||
offset.Top() += p;
|
||||
cairo_translate(cr, p.x, p.y);
|
||||
}
|
||||
|
||||
void GtkDraw::RectPath(const Rect& r)
|
||||
void CairoDraw::RectPath(const Rect& r)
|
||||
{
|
||||
cairo_rectangle(cr, r.left, r.top, r.GetWidth(), r.GetHeight());
|
||||
}
|
||||
|
||||
bool GtkDraw::ClipOp(const Rect& r)
|
||||
bool CairoDraw::ClipOp(const Rect& r)
|
||||
{
|
||||
Push();
|
||||
RectPath(r);
|
||||
|
|
@ -60,7 +62,7 @@ bool GtkDraw::ClipOp(const Rect& r)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool GtkDraw::ClipoffOp(const Rect& r)
|
||||
bool CairoDraw::ClipoffOp(const Rect& r)
|
||||
{
|
||||
Push();
|
||||
offset.Top() += r.TopLeft();
|
||||
|
|
@ -70,7 +72,7 @@ bool GtkDraw::ClipoffOp(const Rect& r)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool GtkDraw::ExcludeClipOp(const Rect& r)
|
||||
bool CairoDraw::ExcludeClipOp(const Rect& r)
|
||||
{
|
||||
RectPath(Rect(-99999, -99999, 99999, r.top));
|
||||
RectPath(Rect(-99999, r.top, r.left, 99999));
|
||||
|
|
@ -80,35 +82,43 @@ bool GtkDraw::ExcludeClipOp(const Rect& r)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool GtkDraw::IntersectClipOp(const Rect& r)
|
||||
bool CairoDraw::IntersectClipOp(const Rect& r)
|
||||
{
|
||||
RectPath(r);
|
||||
cairo_clip(cr);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool GtkDraw::IsPaintingOp(const Rect& r) const
|
||||
bool CairoDraw::IsPaintingOp(const Rect& r) const
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
Rect GtkDraw::GetPaintRect() const
|
||||
Rect CairoDraw::GetPaintRect() const
|
||||
{
|
||||
return Rect(0, 0, INT_MAX, INT_MAX);
|
||||
}
|
||||
|
||||
void GtkDraw::DrawRectOp(int x, int y, int cx, int cy, Color color)
|
||||
void CairoDraw::DrawRectOp(int x, int y, int cx, int cy, Color color)
|
||||
{
|
||||
SetColor(color);
|
||||
cairo_rectangle(cr, x, y, cx, cy);
|
||||
cairo_fill(cr);
|
||||
}
|
||||
|
||||
void GtkDraw::SysDrawImageOp(int x, int y, const Image& img, Color color)
|
||||
struct ImageSysData {
|
||||
Image img;
|
||||
cairo_surface_t *surface;
|
||||
|
||||
void Init(const Image& img);
|
||||
~ImageSysData();
|
||||
};
|
||||
|
||||
void ImageSysData::Init(const Image& m)
|
||||
{
|
||||
// TODO: cache cairo_surfaces
|
||||
img = m;
|
||||
Size isz = img.GetSize();
|
||||
cairo_surface_t *surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, isz.cx, isz.cy);
|
||||
surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, isz.cx, isz.cy);
|
||||
cairo_surface_flush(surface);
|
||||
byte *a = (byte *)cairo_image_surface_get_data(surface);
|
||||
int stride = cairo_format_stride_for_width(CAIRO_FORMAT_ARGB32, isz.cx);
|
||||
|
|
@ -117,18 +127,45 @@ void GtkDraw::SysDrawImageOp(int x, int y, const Image& img, Color color)
|
|||
a += stride;
|
||||
}
|
||||
cairo_surface_mark_dirty(surface);
|
||||
if(!IsNull(color)) {
|
||||
SetColor(color);
|
||||
cairo_mask_surface(cr, surface, x, y);
|
||||
}
|
||||
else {
|
||||
cairo_set_source_surface(cr, surface, x, y);
|
||||
cairo_paint(cr);
|
||||
}
|
||||
SysImageRealized(img);
|
||||
}
|
||||
|
||||
ImageSysData::~ImageSysData()
|
||||
{
|
||||
SysImageReleased(img);
|
||||
cairo_surface_destroy(surface);
|
||||
}
|
||||
|
||||
void GtkDraw::DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color)
|
||||
struct ImageSysDataMaker : LRUCache<ImageSysData, int64>::Maker {
|
||||
Image img;
|
||||
|
||||
virtual int64 Key() const { return img.GetSerialId(); }
|
||||
virtual int Make(ImageSysData& object) const { object.Init(img); return img.GetLength(); }
|
||||
};
|
||||
|
||||
void CairoDraw::SysDrawImageOp(int x, int y, const Image& img, Color color)
|
||||
{
|
||||
GuiLock __;
|
||||
if(img.GetLength() == 0)
|
||||
return;
|
||||
LLOG("SysDrawImageOp " << img.GetSerialId() << ' ' << img.GetSize());
|
||||
ImageSysDataMaker m;
|
||||
static LRUCache<ImageSysData, int64> cache;
|
||||
LLOG("SysImage cache pixels " << cache.GetSize() << ", count " << cache.GetCount());
|
||||
m.img = img;
|
||||
ImageSysData& sd = cache.Get(m);
|
||||
if(!IsNull(color)) {
|
||||
SetColor(color);
|
||||
cairo_mask_surface(cr, sd.surface, x, y);
|
||||
}
|
||||
else {
|
||||
cairo_set_source_surface(cr, sd.surface, x, y);
|
||||
cairo_paint(cr);
|
||||
}
|
||||
cache.Shrink(4 * 1024 * 768, 1000); // Cache must be after Paint because of PaintOnly!
|
||||
}
|
||||
|
||||
void CairoDraw::DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color)
|
||||
{
|
||||
SetColor(color);
|
||||
cairo_move_to(cr, x1, y1);
|
||||
|
|
@ -137,19 +174,19 @@ void GtkDraw::DrawLineOp(int x1, int y1, int x2, int y2, int width, Color color)
|
|||
cairo_stroke(cr);
|
||||
}
|
||||
|
||||
void GtkDraw::DrawPolyPolylineOp(const Point *vertices, int vertex_count, const int *counts, int count_count, int width, Color color, Color doxor)
|
||||
void CairoDraw::DrawPolyPolylineOp(const Point *vertices, int vertex_count, const int *counts, int count_count, int width, Color color, Color doxor)
|
||||
{
|
||||
}
|
||||
|
||||
void GtkDraw::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)
|
||||
void CairoDraw::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)
|
||||
{
|
||||
}
|
||||
|
||||
void GtkDraw::DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color)
|
||||
void CairoDraw::DrawArcOp(const Rect& rc, Point start, Point end, int width, Color color)
|
||||
{
|
||||
}
|
||||
|
||||
void GtkDraw::DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor)
|
||||
void CairoDraw::DrawEllipseOp(const Rect& r, Color color, int pen, Color pencolor)
|
||||
{
|
||||
}
|
||||
|
||||
|
|
@ -158,46 +195,69 @@ FcPattern *CreateFcPattern(Font font);
|
|||
FT_Face FTFace(Font fnt, String *rpath = NULL);
|
||||
};
|
||||
|
||||
void GtkDraw::DrawTextOp(int x, int y, int angle, const wchar *text, Font font, Color ink, int n, const int *dx)
|
||||
struct FontSysData {
|
||||
cairo_scaled_font_t *scaled_font;
|
||||
|
||||
void Init(Font font, int angle);
|
||||
~FontSysData() { cairo_scaled_font_destroy(scaled_font); }
|
||||
};
|
||||
|
||||
void FontSysData::Init(Font font, int angle)
|
||||
{
|
||||
DLOG("FontSysData::Init " << font << ", " << angle);
|
||||
FcPattern *p = CreateFcPattern(font);
|
||||
cairo_font_face_t *font_face = cairo_ft_font_face_create_for_pattern(p);
|
||||
FcPatternDestroy(p);
|
||||
|
||||
int xpos = 0;
|
||||
Buffer<cairo_glyph_t> gs(n);
|
||||
for(int i = 0; i < n; i++) {
|
||||
cairo_glyph_t& g = gs[i];
|
||||
g.index = FT_Get_Char_Index(FTFace(font), text[i]);
|
||||
g.x = x + xpos;
|
||||
g.y = y + font.GetAscent();
|
||||
xpos += dx ? dx[i] : font[text[i]];
|
||||
}
|
||||
|
||||
#if 1
|
||||
cairo_matrix_t font_matrix[1], ctm[1];
|
||||
cairo_matrix_init_identity(ctm);
|
||||
cairo_matrix_init_scale(font_matrix, font.GetHeight(), font.GetHeight());
|
||||
if(angle)
|
||||
cairo_matrix_rotate(font_matrix, -angle * M_2PI / 3600);
|
||||
|
||||
cairo_font_options_t *opt = cairo_font_options_create();
|
||||
|
||||
cairo_scaled_font_t *sf = cairo_scaled_font_create(font_face, font_matrix, ctm, opt);
|
||||
SetColor(ink);
|
||||
cairo_set_scaled_font(cr, sf);
|
||||
|
||||
cairo_show_glyphs(cr, gs, n);
|
||||
scaled_font = cairo_scaled_font_create(font_face, font_matrix, ctm, opt);
|
||||
|
||||
cairo_font_options_destroy(opt);
|
||||
cairo_scaled_font_destroy(sf);
|
||||
#else
|
||||
cairo_set_font_face(cr, face);
|
||||
cairo_set_font_size(cr, font.GetHeight());
|
||||
SetColor(ink);
|
||||
DDUMP(y + font.GetAscent());
|
||||
cairo_show_glyphs(cr, gs, n);
|
||||
#endif
|
||||
|
||||
cairo_font_face_destroy(font_face);
|
||||
}
|
||||
|
||||
struct FontDataSysMaker : LRUCache<FontSysData, Tuple2<Font, int> >::Maker {
|
||||
Font font;
|
||||
int angle;
|
||||
|
||||
virtual Tuple2<Font, int> Key() const { return MakeTuple(font, angle); }
|
||||
virtual int Make(FontSysData& object) const { object.Init(font, angle); return 1; }
|
||||
};
|
||||
|
||||
void CairoDraw::DrawTextOp(int x, int y, int angle, const wchar *text, Font font, Color ink, int n, const int *dx)
|
||||
{
|
||||
GuiLock __;
|
||||
|
||||
int ascent = font.GetAscent();
|
||||
double sina = 0;
|
||||
double cosa = 1;
|
||||
if(angle)
|
||||
Draw::SinCos(angle, sina, cosa);
|
||||
int xpos = 0;
|
||||
Buffer<cairo_glyph_t> gs(n);
|
||||
for(int i = 0; i < n; i++) {
|
||||
cairo_glyph_t& g = gs[i];
|
||||
g.index = GetGlyphInfo(font, text[i]).glyphi;
|
||||
g.x = fround(x + cosa * xpos + sina * ascent);
|
||||
g.y = fround(y + cosa * ascent - sina * xpos);
|
||||
xpos += dx ? dx[i] : font[text[i]];
|
||||
}
|
||||
|
||||
static LRUCache<FontSysData, Tuple2<Font, int> > cache;
|
||||
FontDataSysMaker m;
|
||||
m.font = font;
|
||||
m.angle = angle;
|
||||
FontSysData& sf = cache.Get(m);
|
||||
|
||||
cairo_set_scaled_font(cr, sf.scaled_font);
|
||||
|
||||
SetColor(ink);
|
||||
cairo_show_glyphs(cr, gs, n);
|
||||
|
||||
cache.Shrink(64);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
#ifndef _GtkApp_icpp_init_stub
|
||||
#define _GtkApp_icpp_init_stub
|
||||
#include "Draw/init"
|
||||
#include "plugin/png/init"
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@
|
|||
|
||||
void TestDraw(Draw& w)
|
||||
{
|
||||
w.DrawRect(0, 0, 10000, 10000, WhiteGray());
|
||||
w.DrawRect(0, 0, 100, 100, Yellow());
|
||||
|
||||
w.DrawLine(10, 40, 400, 20, 3, Blue());
|
||||
|
|
@ -46,23 +47,41 @@ void TestDraw(Draw& w)
|
|||
w.DrawText(0, 0, text, fnt);
|
||||
w.DrawText(0, 70, text, fnt, Blue(), dx.GetCount(), dx.Begin());
|
||||
|
||||
w.DrawText(50, 400, 200, "Angled text", Arial(100).Underline(), Black());
|
||||
w.DrawRect(50, 400, 2, 2, Black());
|
||||
w.DrawText(50, 400, 200, "Angled text", Arial(50).Underline(), Red());
|
||||
|
||||
w.DrawRect(600, 400, 2, 2, Black());
|
||||
w.DrawText(600, 400, 1000, "Angled text", Arial(50).Underline(), Black());
|
||||
w.End();
|
||||
}
|
||||
|
||||
static gboolean on_expose_event(GtkWidget *widget, GdkEventExpose *event, gpointer data)
|
||||
{
|
||||
GtkDraw w;
|
||||
w.cr = gdk_cairo_create(widget->window);
|
||||
CairoDraw w(gdk_cairo_create(widget->window));
|
||||
|
||||
TestDraw(w);
|
||||
|
||||
cairo_destroy(w.cr);
|
||||
cairo_destroy(w);
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
int main( int argc, char *argv[])
|
||||
{
|
||||
{
|
||||
CairoImageDraw w(1000, 1000);
|
||||
TestDraw(w);
|
||||
PNGEncoder().SaveFile("/home/cxl/test.png", w);
|
||||
}
|
||||
|
||||
{
|
||||
CairoImageDraw w(1000, 1000);
|
||||
TestDraw(w);
|
||||
for(int i = 0; i < 100; i++)
|
||||
w.Alpha().DrawRect(i * 10, 0, 10, 1000, GrayColor(255 - i));
|
||||
PNGEncoder().SaveFile("/home/cxl/test_alpha.png", w);
|
||||
}
|
||||
|
||||
GtkWidget *window;
|
||||
|
||||
gtk_init(&argc, &argv);
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue