mirror of
https://github.com/ultimatepp/ultimatepp.git
synced 2026-07-11 22:03:01 -06:00
uppsrc: gtk3 replaces gtk2 as default linux backend
git-svn-id: svn://ultimatepp.org/upp/trunk@13848 f0d560ea-af0d-0410-9eb7-867de7ffcac7
This commit is contained in:
parent
7b01bec9d1
commit
b3fe362f4f
39 changed files with 1230 additions and 336 deletions
|
|
@ -991,6 +991,7 @@ void Ctrl::ReSkin()
|
|||
return;
|
||||
lock++;
|
||||
ChReset();
|
||||
Csize.cx = Dsize.cx = IsNoLayoutZoom;
|
||||
if(s_chdefault)
|
||||
(*s_chdefault)();
|
||||
if(skin)
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@
|
|||
#define CTRLCORE_H
|
||||
|
||||
#include <RichText/RichText.h>
|
||||
#include <Painter/Painter.h>
|
||||
|
||||
#ifdef flagNOGTK
|
||||
#undef flagGTK
|
||||
|
|
|
|||
|
|
@ -8,10 +8,6 @@ uses
|
|||
|
||||
library(WIN32 !MSC8ARM) "advapi32 comdlg32 comctl32";
|
||||
|
||||
library((LINUX | BSD) & !NOGTK & !RAINBOW & !GTK3 & GUI & !OSX) "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((LINUX | BSD) & GTK3) "gtk-3.0 gdk-3.0 atk-1.0 gdk_3.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 !RAINBOW GUI) "X11 Xrender Xinerama";
|
||||
|
|
@ -34,6 +30,8 @@ library(DRAGONFLY) "Xext Xinerama";
|
|||
|
||||
link(OSX !X11) "-framework Foundation -framework Cocoa -framework Carbon";
|
||||
|
||||
pkg_config(POSIX !X11) gtk+-3.0;
|
||||
|
||||
file
|
||||
Core readonly separator,
|
||||
CtrlCore.h options(BUILDER_OPTION) PCH,
|
||||
|
|
@ -102,6 +100,7 @@ file
|
|||
X11DHCtrl.cpp,
|
||||
X11Event.i,
|
||||
Gtk readonly separator,
|
||||
gtk3-todo.txt,
|
||||
Gtk.h,
|
||||
GtkAfter.h,
|
||||
GtkKeys.h,
|
||||
|
|
|
|||
|
|
@ -353,6 +353,7 @@ void Ctrl::CtrlPaint(SystemDraw& w, const Rect& clip) {
|
|||
GuiLock __;
|
||||
LEVELCHECK(w, this);
|
||||
LTIMING("CtrlPaint");
|
||||
LLOG("=== CtrlPaint " << UPP::Name(this) << ", clip: " << clip << ", rect: " << GetRect() << ", view: " << GetView());
|
||||
Rect rect = GetRect().GetSize();
|
||||
Rect orect = rect.Inflated(overpaint);
|
||||
if(!IsShown() || orect.IsEmpty() || clip.IsEmpty() || !clip.Intersects(orect))
|
||||
|
|
@ -417,7 +418,7 @@ void Ctrl::CtrlPaint(SystemDraw& w, const Rect& clip) {
|
|||
Rect ocl = cl - off;
|
||||
if(ocl.Intersects(Rect(qr.GetSize()).Inflated(overpaint))) {
|
||||
w.Offset(off);
|
||||
q->CtrlPaint(w, cl - off);
|
||||
q->CtrlPaint(w, ocl);
|
||||
w.End();
|
||||
}
|
||||
}
|
||||
|
|
@ -596,7 +597,7 @@ void Ctrl::UpdateArea0(SystemDraw& draw, const Rect& clip, int backpaint)
|
|||
{
|
||||
GuiLock __;
|
||||
LTIMING("UpdateArea");
|
||||
LLOG("========== UPDATE AREA " << UPP::Name(this) << " " << clip << " ==========");
|
||||
LLOG("========== UPDATE AREA " << UPP::Name(this) << ", clip: " << clip << " ==========");
|
||||
ExcludeDHCtrls(draw, GetRect().GetSize(), clip);
|
||||
if(globalbackbuffer) {
|
||||
CtrlPaint(draw, clip);
|
||||
|
|
|
|||
|
|
@ -2,29 +2,16 @@
|
|||
|
||||
#define PLATFORM_X11 // To keep legacy code happy
|
||||
|
||||
#ifdef GDK_KEY_Delete
|
||||
#define GDKEY(x) GDK_KEY_##x
|
||||
#else
|
||||
#define GDKEY(x) GDK_##x
|
||||
#endif
|
||||
|
||||
#ifdef __clang__
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic ignored "-Wdeprecated"
|
||||
#endif
|
||||
|
||||
#ifdef __GNUC__
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
|
||||
#endif
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
#include <gdk/gdkkeysyms.h>
|
||||
|
||||
#ifdef __GNUC__
|
||||
#pragma GCC diagnostic pop
|
||||
#endif
|
||||
|
||||
#ifdef __clang__
|
||||
#pragma clang diagnostic pop
|
||||
#endif
|
||||
|
|
@ -69,10 +56,9 @@ private:
|
|||
void Pop();
|
||||
Vector<Point> offset;
|
||||
Vector<Rect> clip;
|
||||
Vector<Rect> invalid; // for IsPainting checks, if empty, only clip extents is checked
|
||||
|
||||
cairo_t *cr;
|
||||
GdkDrawable *drawable;
|
||||
GdkRegion *invalid;
|
||||
|
||||
struct TextGlyph : Moveable<TextGlyph> {
|
||||
int x;
|
||||
|
|
@ -100,12 +86,13 @@ public:
|
|||
void SetColor(Color c);
|
||||
operator cairo_t*() { return cr; }
|
||||
|
||||
void SetInvalid(GdkRegion *r) { invalid = r; }
|
||||
void PickInvalid(Vector<Rect>&& inv) { invalid = pick(inv); }
|
||||
Point GetOffset() const;
|
||||
bool CanSetSurface() { return true; }
|
||||
static void Flush() {} // TODO?
|
||||
|
||||
SystemDraw(cairo_t *cr, GdkDrawable *dw/* = NULL*/) : cr(cr), drawable(dw) { (void)drawable; invalid = NULL; }
|
||||
// SystemDraw(cairo_t *cr, GdkDrawable *dw/* = NULL*/) : cr(cr), drawable(dw) { (void)drawable; invalid = NULL; }
|
||||
SystemDraw(cairo_t *cr) : cr(cr) {}
|
||||
~SystemDraw();
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -57,11 +57,13 @@ void Ctrl::PanicMsgBox(const char *title, const char *text)
|
|||
__BREAK__;
|
||||
}
|
||||
|
||||
int Ctrl::scale;
|
||||
|
||||
void InitGtkApp(int argc, char **argv, const char **envptr)
|
||||
{
|
||||
LLOG(rmsecs() << " InitGtkApp");
|
||||
#ifdef _MULTITHREADED
|
||||
#if !GLIB_CHECK_VERSION(2, 32, 0)
|
||||
#if !GTK_CHECK_VERSION(2, 32, 0)
|
||||
if(!g_thread_supported())
|
||||
g_thread_init(NULL);
|
||||
#endif
|
||||
|
|
@ -70,6 +72,14 @@ void InitGtkApp(int argc, char **argv, const char **envptr)
|
|||
EnterGuiMutex();
|
||||
#endif
|
||||
gtk_init(&argc, &argv);
|
||||
|
||||
Ctrl::SetUHDEnabled(true);
|
||||
|
||||
Ctrl::scale = 1;
|
||||
#if GTK_CHECK_VERSION(3, 10, 0)
|
||||
Ctrl::scale = gdk_window_get_scale_factor(gdk_screen_get_root_window(gdk_screen_get_default()));
|
||||
#endif
|
||||
|
||||
Ctrl::GlobalBackBuffer();
|
||||
Ctrl::ReSkin();
|
||||
g_timeout_add(20, (GSourceFunc) Ctrl::TimeHandler, NULL);
|
||||
|
|
|
|||
|
|
@ -9,10 +9,51 @@ namespace Upp {
|
|||
Ptr<Ctrl> Ctrl::grabwindow;
|
||||
Ptr<Ctrl> Ctrl::grabpopup;
|
||||
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
GdkSeat *Ctrl::GetSeat()
|
||||
{
|
||||
return gdk_display_get_default_seat(gdk_display_get_default());
|
||||
}
|
||||
#endif
|
||||
|
||||
GdkDevice *Ctrl::GetMouseDevice()
|
||||
{
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
return gdk_seat_get_pointer(GetSeat());
|
||||
#else
|
||||
return gdk_device_manager_get_client_pointer(gdk_display_get_device_manager(gdk_display_get_default()));
|
||||
#endif
|
||||
}
|
||||
|
||||
bool Ctrl::MouseIsGrabbed()
|
||||
{
|
||||
return gdk_display_device_is_grabbed(gdk_display_get_default(), GetMouseDevice());
|
||||
}
|
||||
|
||||
bool Ctrl::GrabMouse()
|
||||
{
|
||||
return
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
gdk_seat_grab(GetSeat(), gdk(), GDK_SEAT_CAPABILITY_ALL_POINTING, true, NULL, NULL, NULL, 0)
|
||||
#else
|
||||
gdk_device_grab(GetMouseDevice(), gdk(), GDK_OWNERSHIP_APPLICATION, true, (GdkEventMask)0, NULL, GDK_CURRENT_TIME)
|
||||
#endif
|
||||
== GDK_GRAB_SUCCESS;
|
||||
}
|
||||
|
||||
void Ctrl::UngrabMouse()
|
||||
{
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
gdk_seat_ungrab(GetSeat());
|
||||
#else
|
||||
gdk_device_ungrab(GetMouseDevice(), GDK_CURRENT_TIME);
|
||||
#endif
|
||||
}
|
||||
|
||||
void Ctrl::StopGrabPopup()
|
||||
{
|
||||
if(grabpopup && gdk_pointer_is_grabbed()) {
|
||||
gdk_pointer_ungrab(CurrentTime);
|
||||
if(grabpopup && MouseIsGrabbed()) {
|
||||
UngrabMouse();
|
||||
grabpopup = NULL;
|
||||
}
|
||||
}
|
||||
|
|
@ -23,13 +64,7 @@ void Ctrl::StartGrabPopup()
|
|||
Ctrl *w = activePopup[0];
|
||||
if(w && w->IsOpen()) {
|
||||
ReleaseWndCapture0();
|
||||
static GdkCursor *NormalArrowCursor;
|
||||
ONCELOCK {
|
||||
NormalArrowCursor = gdk_cursor_new(GDK_LEFT_PTR);
|
||||
}
|
||||
if(gdk_pointer_grab(w->gdk(), FALSE,
|
||||
GdkEventMask(GDK_BUTTON_RELEASE_MASK|GDK_BUTTON_PRESS_MASK|GDK_POINTER_MOTION_MASK),
|
||||
NULL, NormalArrowCursor, CurrentTime) == GDK_GRAB_SUCCESS)
|
||||
if(w->GrabMouse())
|
||||
grabpopup = w;
|
||||
}
|
||||
}
|
||||
|
|
@ -44,9 +79,7 @@ bool Ctrl::SetWndCapture()
|
|||
return false;
|
||||
StopGrabPopup();
|
||||
ReleaseWndCapture();
|
||||
if(gdk_pointer_grab(gdk(), FALSE,
|
||||
GdkEventMask(GDK_BUTTON_RELEASE_MASK|GDK_BUTTON_PRESS_MASK|GDK_POINTER_MOTION_MASK),
|
||||
NULL, NULL, CurrentTime) == GDK_GRAB_SUCCESS) {
|
||||
if(GrabMouse()) {
|
||||
grabwindow = this;
|
||||
return true;
|
||||
}
|
||||
|
|
@ -59,7 +92,7 @@ bool Ctrl::ReleaseWndCapture0()
|
|||
ASSERT(IsMainThread());
|
||||
LLOG("ReleaseWndCapture");
|
||||
if(grabwindow) {
|
||||
gdk_pointer_ungrab(CurrentTime);
|
||||
UngrabMouse();
|
||||
grabwindow = NULL;
|
||||
StartGrabPopup();
|
||||
return true;
|
||||
|
|
@ -75,20 +108,15 @@ bool Ctrl::ReleaseWndCapture()
|
|||
bool Ctrl::HasWndCapture() const
|
||||
{
|
||||
GuiLock __;
|
||||
return this == grabwindow && grabwindow->IsOpen() && gdk_pointer_is_grabbed();
|
||||
return this == grabwindow && grabwindow->IsOpen() && MouseIsGrabbed();
|
||||
}
|
||||
|
||||
void Ctrl::CaptureSync()
|
||||
{
|
||||
if(grabwindow && grabwindow->IsOpen() && !gdk_pointer_is_grabbed()) {
|
||||
if(gdk_pointer_grab(grabwindow->gdk(), FALSE,
|
||||
GdkEventMask(GDK_BUTTON_RELEASE_MASK|GDK_BUTTON_PRESS_MASK|GDK_POINTER_MOTION_MASK),
|
||||
NULL, NULL, CurrentTime) != GDK_GRAB_SUCCESS) {
|
||||
grabwindow = NULL;
|
||||
}
|
||||
}
|
||||
if(grabwindow && grabwindow->IsOpen() && !MouseIsGrabbed() && !grabwindow->GrabMouse())
|
||||
grabwindow = NULL;
|
||||
}
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
|
@ -26,12 +26,12 @@ void Ctrl::Create(Ctrl *owner, bool popup)
|
|||
w.id = top->id;
|
||||
w.ctrl = this;
|
||||
w.gtk = top->window;
|
||||
w.gdk = top->window->window;
|
||||
w.gdk = gtk_widget_get_window(top->window);
|
||||
|
||||
TopWindow *tw = dynamic_cast<TopWindow *>(this);
|
||||
if(popup && !owner) {
|
||||
gtk_window_set_decorated(gtk(), FALSE);
|
||||
gtk_window_set_has_frame(gtk(), FALSE);
|
||||
// gtk_window_set_has_frame(gtk(), FALSE);
|
||||
gtk_window_set_type_hint(gtk(), GDK_WINDOW_TYPE_HINT_POPUP_MENU);
|
||||
}
|
||||
else
|
||||
|
|
@ -44,18 +44,21 @@ void Ctrl::Create(Ctrl *owner, bool popup)
|
|||
|
||||
gtk_widget_set_events(top->window, 0xffffffff);
|
||||
g_signal_connect(top->window, "event", G_CALLBACK(GtkEvent), (gpointer)(uintptr_t)top->id);
|
||||
g_signal_connect(top->window, "draw", G_CALLBACK(GtkDraw), (gpointer)(uintptr_t)top->id);
|
||||
|
||||
GdkWindowTypeHint hint = gtk_window_get_type_hint(gtk());
|
||||
if(tw && findarg(hint, GDK_WINDOW_TYPE_HINT_NORMAL, GDK_WINDOW_TYPE_HINT_DIALOG, GDK_WINDOW_TYPE_HINT_UTILITY) >= 0)
|
||||
tw->SyncSizeHints();
|
||||
|
||||
|
||||
Rect r = GetRect();
|
||||
gtk_window_move(gtk(), r.left, r.top);
|
||||
gtk_window_resize(gtk(), r.GetWidth(), r.GetHeight());
|
||||
|
||||
gtk_window_set_default_size (gtk(), LSC(r.GetWidth()), LSC(r.GetHeight()));
|
||||
|
||||
gtk_window_move(gtk(), LSC(r.left), LSC(r.top));
|
||||
gtk_window_resize(gtk(), LSC(r.GetWidth()), LSC(r.GetHeight()));
|
||||
|
||||
gtk_widget_realize(top->window);
|
||||
|
||||
|
||||
if(owner && owner->top)
|
||||
gtk_window_set_transient_for(gtk(), owner->gtk());
|
||||
gtk_widget_set_app_paintable(top->window, TRUE);
|
||||
|
|
@ -81,9 +84,8 @@ void Ctrl::Create(Ctrl *owner, bool popup)
|
|||
|
||||
activeCtrl = this;
|
||||
|
||||
int mousex, mousey;
|
||||
gdk_window_get_pointer(gdk(), &mousex, &mousey, NULL);
|
||||
Point m(mousex, mousey);
|
||||
GdkModifierType mod;
|
||||
Point m = GetMouseInfo(gdk(), mod);
|
||||
r = GetWndScreenRect().GetSize();
|
||||
if(r.Contains(m))
|
||||
DispatchMouse(MOUSEMOVE, m);
|
||||
|
|
|
|||
|
|
@ -42,7 +42,7 @@ void GuiPlatformGripResize(TopWindow *q)
|
|||
if(q->IsOpen()) {
|
||||
Point p = GetMousePos();
|
||||
gtk_window_begin_resize_drag(q->gtk(), GDK_WINDOW_EDGE_SOUTH_EAST,
|
||||
1, p.x, p.y, Ctrl::CurrentTime);
|
||||
1, Ctrl::LSC(p.x), Ctrl::LSC(p.y), Ctrl::CurrentTime);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -26,6 +26,18 @@ _DBG_
|
|||
static void CaptureSync();
|
||||
|
||||
static gboolean GtkEvent(GtkWidget *widget, GdkEvent *key, gpointer user_data);
|
||||
static gboolean GtkDraw(GtkWidget *widget, cairo_t *cr, gpointer data);
|
||||
|
||||
static Point GetMouseInfo(GdkWindow *win, GdkModifierType& mod);
|
||||
static GdkDevice *GetMouseDevice();
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
static GdkSeat *GetSeat();
|
||||
#endif
|
||||
static bool MouseIsGrabbed();
|
||||
bool GrabMouse();
|
||||
static void UngrabMouse();
|
||||
|
||||
static int scale; // in case GUI is scaling (e.g. in UHD mode)
|
||||
|
||||
enum {
|
||||
EVENT_NONE = -15321,
|
||||
|
|
@ -65,6 +77,7 @@ _DBG_
|
|||
void Proc();
|
||||
bool SweepConfigure(bool wait);
|
||||
bool SweepFocus(bool wait);
|
||||
void SyncWndRect(const Rect& rect);
|
||||
|
||||
static BiVector<GEvent> Events;
|
||||
static Vector< Ptr<Ctrl> > activePopup; // created with 'activate' flag - usually menu
|
||||
|
|
@ -75,7 +88,7 @@ _DBG_
|
|||
static Ptr<Ctrl> grabwindow;
|
||||
static Ptr<Ctrl> grabpopup;
|
||||
static Ptr<Ctrl> sel_ctrl;
|
||||
static Ptr<Ctrl> activeCtrl; // this is used to hold focus when popup is destroyed
|
||||
static Ptr<Ctrl> activeCtrl;
|
||||
|
||||
static int FindId(int id);
|
||||
static int FindCtrl(Ctrl *ctrl);
|
||||
|
|
@ -170,6 +183,10 @@ public: // really private:
|
|||
static Vector<dword> keyhot;
|
||||
static Vector<dword> modhot;
|
||||
static guint MouseState;
|
||||
|
||||
static int SCL(int x) { return scale * x; }
|
||||
static Rect SCL(int x, int y, int cx, int cy) { return RectC(SCL(x), SCL(y), SCL(cx), SCL(cy)); }
|
||||
static double LSC(int x) { return (double)x / scale; }
|
||||
|
||||
public:
|
||||
static void EndSession() {}
|
||||
|
|
@ -181,7 +198,7 @@ public:
|
|||
static guint32 CurrentTime;
|
||||
static GEvent CurrentEvent;
|
||||
|
||||
GdkWindow *gdk() const { return top ? top->window->window : NULL; }
|
||||
GdkWindow *gdk() const { return top ? gtk_widget_get_window(top->window) : NULL; }
|
||||
GtkWindow *gtk() const { return top ? (GtkWindow *)top->window : NULL; }
|
||||
|
||||
static GdkFilterReturn RootKeyFilter(GdkXEvent *xevent, GdkEvent *event, gpointer data);
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ Ctrl *Ctrl::GetDragAndDropSource()
|
|||
void Ctrl::GtkDragBegin(GtkWidget *widget, GdkDragContext *context, gpointer user_data)
|
||||
{
|
||||
if(IsNull(dnd_icon))
|
||||
gtk_drag_set_icon_default(context);
|
||||
gtk_drag_set_icon_default(context);
|
||||
else {
|
||||
ImageGdk m(dnd_icon);
|
||||
gtk_drag_set_icon_pixbuf(context, m, 0, 0);
|
||||
|
|
@ -114,16 +114,16 @@ int Ctrl::DoDragAndDrop(const char *fmts, const Image& sample, dword actions,
|
|||
dnd_icon = Null;
|
||||
else {
|
||||
Size sz = sample.GetSize();
|
||||
if(sz.cx > 128)
|
||||
sz.cx = 128;
|
||||
if(sz.cy > 128)
|
||||
sz.cy = 128;
|
||||
int maxsize = DPI(128);
|
||||
if(sz.cx > maxsize)
|
||||
sz.cx = maxsize;
|
||||
if(sz.cy > maxsize)
|
||||
sz.cy = maxsize;
|
||||
sz += 2;
|
||||
ImageDraw iw(sz);
|
||||
iw.DrawRect(sz, White());
|
||||
DrawFrame(iw, sz, Black());
|
||||
iw.DrawImage(1, 1, sz.cx, sz.cy, sample);
|
||||
ImageBuffer b(128, 128);
|
||||
dnd_icon = iw;
|
||||
}
|
||||
gtk_drag_begin(w->top->window, list, GdkDragAction(gdk_actions),
|
||||
|
|
@ -287,7 +287,7 @@ PasteClip Ctrl::GtkDnd(GtkWidget *widget, GdkDragContext *context, gint x, gint
|
|||
GdkModifierType mod;
|
||||
gdk_window_get_pointer(gdk_get_default_root_window(), &mx, &my, &mod);
|
||||
CurrentState = mod;
|
||||
CurrentMousePos = Point(x, y) + w->GetScreenRect().TopLeft();
|
||||
CurrentMousePos = Point(SCL(x), SCL(y)) + w->GetScreenRect().TopLeft();
|
||||
w->DnD(CurrentMousePos, clip);
|
||||
}
|
||||
gdk_drag_status(context, clip.IsAccepted() ? clip.GetAction() == DND_MOVE ? GDK_ACTION_MOVE
|
||||
|
|
|
|||
|
|
@ -119,7 +119,12 @@ bool SystemDraw::IsPaintingOp(const Rect& r) const
|
|||
cr.Intersect(GetClip());
|
||||
if(cr.IsEmpty())
|
||||
return false;
|
||||
return !invalid || gdk_region_rect_in(invalid, GdkRect(cr)) != GDK_OVERLAP_RECTANGLE_OUT;
|
||||
if(invalid.GetCount() == 0)
|
||||
return true;
|
||||
for(const Rect& ir : invalid)
|
||||
if(cr.Intersects(ir))
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
Rect SystemDraw::GetPaintRect() const
|
||||
|
|
@ -134,21 +139,10 @@ void SystemDraw::DrawRectOp(int x, int y, int cx, int cy, Color color)
|
|||
FlushText();
|
||||
cairo_rectangle(cr, x, y, cx, cy);
|
||||
if(color == InvertColor()) {
|
||||
#if GTK_CHECK_VERSION(2,24,0) && (CAIRO_VERSION_MAJOR > 1 || CAIRO_VERSION_MINOR > 9)
|
||||
SetColor(White());
|
||||
cairo_set_operator(cr, CAIRO_OPERATOR_DIFFERENCE);
|
||||
cairo_fill(cr);
|
||||
cairo_set_operator(cr, CAIRO_OPERATOR_OVER);
|
||||
#else
|
||||
if(drawable) {
|
||||
GdkGC *gc = gdk_gc_new(drawable);
|
||||
gdk_gc_set_function(gc, GDK_INVERT);
|
||||
Point o = GetOffset();
|
||||
gdk_draw_drawable(drawable, gc, drawable, x + o.x, y + o.y, x + o.x, y + o.y, cx, cy);
|
||||
gdk_gc_set_function(gc, GDK_COPY);
|
||||
gdk_gc_destroy(gc);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else {
|
||||
SetColor(color);
|
||||
|
|
|
|||
|
|
@ -4,8 +4,8 @@
|
|||
|
||||
namespace Upp {
|
||||
|
||||
#define LLOG(x) // DLOG(rmsecs() << ' ' << x)
|
||||
//_DBG_ #define LOG_EVENTS
|
||||
#define LLOG(x) // DLOG(rmsecs() << ' ' << x)
|
||||
// #define LOG_EVENTS _DBG_
|
||||
|
||||
BiVector<Ctrl::GEvent> Ctrl::Events;
|
||||
|
||||
|
|
@ -28,7 +28,7 @@ Point GetMousePos() { return Ctrl::CurrentMousePos; }
|
|||
Tuple2<int, const char *> xEvent[] = {
|
||||
{ GDK_NOTHING, "GDK_NOTHING" },
|
||||
{ GDK_DELETE, "GDK_DELETE" },
|
||||
{ GDK_DESTROY, "GDK_DESTROY" },id
|
||||
{ GDK_DESTROY, "GDK_DESTROY" },
|
||||
{ GDK_EXPOSE, "GDK_EXPOSE" },
|
||||
{ GDK_MOTION_NOTIFY, "GDK_MOTION_NOTIFY" },
|
||||
{ GDK_BUTTON_PRESS, "GDK_BUTTON_PRESS" },
|
||||
|
|
@ -57,7 +57,6 @@ Tuple2<int, const char *> xEvent[] = {
|
|||
{ GDK_DROP_FINISHED, "GDK_DROP_FINISHED" },
|
||||
{ GDK_CLIENT_EVENT, "GDK_CLIENT_EVENT" },
|
||||
{ GDK_VISIBILITY_NOTIFY, "GDK_VISIBILITY_NOTIFY" },
|
||||
{ GDK_NO_EXPOSE, "GDK_NO_EXPOSE" },
|
||||
{ GDK_SCROLL, "GDK_SCROLL" },
|
||||
{ GDK_WINDOW_STATE, "GDK_WINDOW_STATE" },
|
||||
{ GDK_SETTING, "GDK_SETTING" },
|
||||
|
|
@ -79,6 +78,42 @@ Ctrl *Ctrl::GetTopCtrlFromId(int id)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
gboolean Ctrl::GtkDraw(GtkWidget *widget, cairo_t *cr, gpointer user_data)
|
||||
{
|
||||
GuiLock __;
|
||||
Ctrl *p = GetTopCtrlFromId(user_data);
|
||||
if(p) {
|
||||
p->fullrefresh = false;
|
||||
cairo_scale(cr, 1.0 / scale, 1.0 / scale);
|
||||
p->SyncWndRect(p->GetWndScreenRect()); // avoid black areas when resizing
|
||||
|
||||
SystemDraw w(cr);
|
||||
painting = true;
|
||||
double x1, y1, x2, y2;
|
||||
cairo_clip_extents (cr, &x1, &y1, &x2, &y2);
|
||||
Rect r = RectC((int)x1, (int)y1, (int)ceil(x2 - x1), (int)ceil(y2 - y1));
|
||||
w.Clip(r); // Because of IsPainting
|
||||
|
||||
cairo_rectangle_list_t *list = cairo_copy_clip_rectangle_list(cr);
|
||||
if(list->status == CAIRO_STATUS_SUCCESS && list->num_rectangles < 10) {
|
||||
Vector<Rect> clip;
|
||||
for(int i = 0; i < list->num_rectangles; i++) {
|
||||
const cairo_rectangle_t& r = list->rectangles[i];
|
||||
clip.Add(Rect((int)r.x, (int)r.y, (int)(r.x + r.width), (int)(r.y + r.height)));
|
||||
}
|
||||
w.PickInvalid(pick(clip));
|
||||
}
|
||||
cairo_rectangle_list_destroy(list);
|
||||
|
||||
p->UpdateArea(w, r);
|
||||
w.End();
|
||||
if(p->top->dr)
|
||||
DrawDragRect(*p, *p->top->dr);
|
||||
painting = false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
gboolean Ctrl::GtkEvent(GtkWidget *widget, GdkEvent *event, gpointer user_data)
|
||||
{
|
||||
GuiLock __;
|
||||
|
|
@ -96,34 +131,9 @@ gboolean Ctrl::GtkEvent(GtkWidget *widget, GdkEvent *event, gpointer user_data)
|
|||
#endif
|
||||
|
||||
switch(event->type) {
|
||||
case GDK_EXPOSE:
|
||||
case GDK_DAMAGE:
|
||||
if(p) {
|
||||
#ifdef LOG_EVENTS
|
||||
TimeStop tm;
|
||||
#endif
|
||||
p->fullrefresh = false;
|
||||
GdkEventExpose *e = (GdkEventExpose *)event;
|
||||
SystemDraw w(gdk_cairo_create(p->gdk()), p->gdk());
|
||||
painting = true;
|
||||
Rect r = RectC(e->area.x, e->area.y, e->area.width, e->area.height);
|
||||
w.SetInvalid(e->region);
|
||||
w.Clip(r);
|
||||
p->UpdateArea(w, r);
|
||||
w.End();
|
||||
cairo_destroy(w);
|
||||
if(p->top->dr)
|
||||
DrawDragRect(*p, *p->top->dr);
|
||||
painting = false;
|
||||
#ifdef LOG_EVENTS
|
||||
LOG("* " << ev << " elapsed " << tm);
|
||||
#endif
|
||||
}
|
||||
return true;
|
||||
case GDK_DELETE:
|
||||
break;
|
||||
case GDK_FOCUS_CHANGE:
|
||||
LLOG("Focus Change " << GetSysTime());
|
||||
if(p) {
|
||||
if(((GdkEventFocus *)event)->in)
|
||||
gtk_im_context_focus_in(p->top->im_context);
|
||||
|
|
@ -152,7 +162,13 @@ gboolean Ctrl::GtkEvent(GtkWidget *widget, GdkEvent *event, gpointer user_data)
|
|||
break;
|
||||
case GDK_SCROLL: {
|
||||
GdkEventScroll *e = (GdkEventScroll *)event;
|
||||
value = findarg(e->direction, GDK_SCROLL_UP, GDK_SCROLL_LEFT) < 0 ? -120 : 120;
|
||||
if(findarg(e->direction, GDK_SCROLL_UP, GDK_SCROLL_LEFT) >= 0)
|
||||
value = 120;
|
||||
else
|
||||
if(findarg(e->direction, GDK_SCROLL_DOWN, GDK_SCROLL_RIGHT) >= 0)
|
||||
value = -120;
|
||||
else
|
||||
return false;
|
||||
break;
|
||||
}
|
||||
case GDK_KEY_PRESS:
|
||||
|
|
@ -169,8 +185,7 @@ gboolean Ctrl::GtkEvent(GtkWidget *widget, GdkEvent *event, gpointer user_data)
|
|||
case GDK_CONFIGURE: {
|
||||
retval = false;
|
||||
GdkEventConfigure *e = (GdkEventConfigure *)event;
|
||||
value = RectC(e->x, e->y, e->width, e->height);
|
||||
LLOG("GDK_CONFIGURE " << value);
|
||||
value = SCL(e->x, e->y, e->width, e->height);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
|
|
@ -232,6 +247,21 @@ void Ctrl::GEvent::operator=(const GEvent& e)
|
|||
Set(e);
|
||||
}
|
||||
|
||||
Point Ctrl::GetMouseInfo(GdkWindow *win, GdkModifierType& mod)
|
||||
{
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
GdkDisplay *display = gdk_window_get_display (win);
|
||||
GdkDevice *pointer = gdk_seat_get_pointer (gdk_display_get_default_seat (display));
|
||||
double x, y;
|
||||
gdk_window_get_device_position_double (win, pointer, &x, &y, &mod);
|
||||
return Point((int)SCL(x), (int)SCL(y));
|
||||
#else
|
||||
gint x, y;
|
||||
gdk_window_get_pointer(win, &x, &y, &mod);
|
||||
return Point(SCL(x), SCL(y));
|
||||
#endif
|
||||
}
|
||||
|
||||
void Ctrl::AddEvent(gpointer user_data, int type, const Value& value, GdkEvent *event)
|
||||
{
|
||||
if(Events.GetCount() > 50000)
|
||||
|
|
@ -240,10 +270,8 @@ void Ctrl::AddEvent(gpointer user_data, int type, const Value& value, GdkEvent *
|
|||
e.windowid = (uint32)(uintptr_t)user_data;
|
||||
e.type = type;
|
||||
e.value = value;
|
||||
gint x, y;
|
||||
GdkModifierType mod;
|
||||
gdk_window_get_pointer(gdk_get_default_root_window(), &x, &y, &mod);
|
||||
e.mousepos = Point(x, y);
|
||||
e.mousepos = GetMouseInfo(gdk_get_default_root_window(), mod);
|
||||
e.state = (mod & ~(GDK_BUTTON1_MASK|GDK_BUTTON2_MASK|GDK_BUTTON3_MASK)) | MouseState;
|
||||
e.count = 1;
|
||||
e.event = NULL;
|
||||
|
|
@ -494,7 +522,6 @@ void Ctrl::Proc()
|
|||
break;
|
||||
}
|
||||
case EVENT_FOCUS_CHANGE:
|
||||
LLOG("FOCUS_CHANGE setting NULL");
|
||||
activeCtrl = NULL;
|
||||
break;
|
||||
case GDK_DELETE: {
|
||||
|
|
@ -507,16 +534,8 @@ void Ctrl::Proc()
|
|||
}
|
||||
return;
|
||||
}
|
||||
case GDK_CONFIGURE: {
|
||||
Rect rect = CurrentEvent.value;
|
||||
if(GetRect() != rect)
|
||||
SetWndRect(rect);
|
||||
{
|
||||
TopWindow *w = dynamic_cast<TopWindow *>(this);
|
||||
if(w && w->state == TopWindow::OVERLAPPED)
|
||||
w->overlapped = rect;
|
||||
}
|
||||
}
|
||||
case GDK_CONFIGURE:
|
||||
SyncWndRect(CurrentEvent.value);
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
|
|
@ -525,6 +544,14 @@ void Ctrl::Proc()
|
|||
_this->PostInput();
|
||||
}
|
||||
|
||||
void Ctrl::SyncWndRect(const Rect& rect)
|
||||
{
|
||||
if(GetRect() != rect)
|
||||
SetWndRect(rect);
|
||||
TopWindow *w = dynamic_cast<TopWindow *>(this);
|
||||
if(w && w->state == TopWindow::OVERLAPPED)
|
||||
w->overlapped = rect;
|
||||
}
|
||||
|
||||
bool Ctrl::ProcessEvent0(bool *quit, bool fetch)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -21,19 +21,21 @@ void TopWindow::SyncSizeHints()
|
|||
return;
|
||||
GdkGeometry m;
|
||||
Size sz0 = GetRect().GetSize();
|
||||
LLOG("SyncSizeHints sz0: " << sz0 << ", sizeable: " << sizeable << ", min: " << GetMinSize() << ", max: " << GetMaxSize());
|
||||
Size sz = sz0;
|
||||
if(sizeable)
|
||||
sz = GetMinSize();
|
||||
m.min_width = sz.cx;
|
||||
m.min_height = sz.cy;
|
||||
m.min_width = LSC(sz.cx);
|
||||
m.min_height = LSC(sz.cy);
|
||||
sz = sz0;
|
||||
if(sizeable)
|
||||
sz = GetMaxSize();
|
||||
m.max_width = sz.cx;
|
||||
m.max_height = sz.cy;
|
||||
m.max_width = LSC(sz.cx);
|
||||
m.max_height = LSC(sz.cy);
|
||||
gtk_window_set_resizable(gtk(), sizeable);
|
||||
gtk_window_set_geometry_hints(gtk(), top->window, &m,
|
||||
GdkWindowHints(GDK_HINT_MIN_SIZE|GDK_HINT_MAX_SIZE));
|
||||
gtk_widget_set_size_request(top->window, m.min_width, m.min_height);
|
||||
}
|
||||
|
||||
void TopWindow::SyncTitle()
|
||||
|
|
@ -136,10 +138,10 @@ void TopWindow::Open(Ctrl *owner)
|
|||
GdkRectangle fr;
|
||||
gdk_window_get_frame_extents(gdk(), &fr);
|
||||
Rect r = GetRect();
|
||||
frameMargins.left = max(frameMargins.left, minmax(r.left - fr.x, 0, 32));
|
||||
frameMargins.right = max(frameMargins.right, minmax(fr.x + fr.width - r.right, 0, 32));
|
||||
frameMargins.top = max(frameMargins.top, minmax(r.top - fr.y, 0, 64));
|
||||
frameMargins.bottom = max(frameMargins.bottom, minmax(fr.y + fr.height - r.bottom, 0, 48));
|
||||
frameMargins.left = max(frameMargins.left, minmax(r.left - SCL(fr.x), 0, 32));
|
||||
frameMargins.right = max(frameMargins.right, minmax(SCL(fr.x + fr.width) - r.right, 0, 32));
|
||||
frameMargins.top = max(frameMargins.top, minmax(r.top - SCL(fr.y), 0, 64));
|
||||
frameMargins.bottom = max(frameMargins.bottom, minmax(SCL(fr.y + fr.height) - r.bottom, 0, 48));
|
||||
}
|
||||
|
||||
void TopWindow::Open()
|
||||
|
|
@ -214,7 +216,7 @@ void TopWindow::Overlap(bool effect)
|
|||
|
||||
TopWindow& TopWindow::TopMost(bool b, bool)
|
||||
{
|
||||
GuiLock __;
|
||||
GuiLock __;
|
||||
topmost = b;
|
||||
SyncTopMost();
|
||||
return *this;
|
||||
|
|
@ -222,7 +224,7 @@ TopWindow& TopWindow::TopMost(bool b, bool)
|
|||
|
||||
bool TopWindow::IsTopMost() const
|
||||
{
|
||||
GuiLock __;
|
||||
GuiLock __;
|
||||
return topmost;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -56,9 +56,7 @@ bool Ctrl::IsAlphaSupported()
|
|||
|
||||
bool Ctrl::IsCompositedGui()
|
||||
{
|
||||
GuiLock __;
|
||||
static bool b = gdk_display_supports_composite(gdk_display_get_default());
|
||||
return b;
|
||||
return true; // limits some GUI effects that do not play well with advanced desktops
|
||||
}
|
||||
|
||||
Vector<Ctrl *> Ctrl::GetTopCtrls()
|
||||
|
|
@ -70,6 +68,8 @@ Vector<Ctrl *> Ctrl::GetTopCtrls()
|
|||
return h;
|
||||
}
|
||||
|
||||
cairo_surface_t *CreateCairoSurface(const Image& img);
|
||||
|
||||
void Ctrl::SetMouseCursor(const Image& image)
|
||||
{
|
||||
LLOG("SetMouseCursor");
|
||||
|
|
@ -88,22 +88,31 @@ void Ctrl::SetMouseCursor(const Image& image)
|
|||
int64 aux = image.GetAuxData();
|
||||
GdkCursor *c = NULL;
|
||||
if(aux)
|
||||
c = gdk_cursor_new((GdkCursorType)(aux - 1));
|
||||
c = gdk_cursor_new_for_display(gdk_display_get_default(), (GdkCursorType)(aux - 1));
|
||||
else
|
||||
if(IsNull(image))
|
||||
c = gdk_cursor_new(GDK_BLANK_CURSOR);
|
||||
c = gdk_cursor_new_for_display(gdk_display_get_default(), GDK_BLANK_CURSOR);
|
||||
else {
|
||||
Point p = image.GetHotSpot();
|
||||
|
||||
#if GTK_CHECK_VERSION(3, 10, 0)
|
||||
cairo_surface_t *surface = CreateCairoSurface(image);
|
||||
double scale = SCL(1);
|
||||
cairo_surface_set_device_scale(surface, scale, scale);
|
||||
c = gdk_cursor_new_from_surface(gdk_display_get_default(), surface, p.x / scale, p.y / scale);
|
||||
cairo_surface_destroy(surface);
|
||||
#else
|
||||
ImageGdk m;
|
||||
m.Set(image);
|
||||
GdkPixbuf *pb = m;
|
||||
if(pb)
|
||||
c = gdk_cursor_new_from_pixbuf(gdk_display_get_default(), pb, p.x, p.y);
|
||||
#endif
|
||||
}
|
||||
if(c && topctrl->IsOpen()) {
|
||||
gdk_window_set_cursor(topctrl->gdk(), c);
|
||||
gdk_cursor_unref(c);
|
||||
gdk_flush(); // Make it visible immediately
|
||||
g_object_unref(c);
|
||||
gdk_display_flush(gdk_display_get_default()); // Make it visible immediately
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -191,14 +200,9 @@ Rect Ctrl::GetWndScreenRect() const
|
|||
if(IsOpen()) {
|
||||
gint x, y;
|
||||
gdk_window_get_position(gdk(), &x, &y);
|
||||
#if GTK_CHECK_VERSION(2, 24, 0)
|
||||
gint width = gdk_window_get_width(gdk());
|
||||
gint height = gdk_window_get_height(gdk());
|
||||
#else
|
||||
gint width, height;
|
||||
gdk_drawable_get_size(gdk(), &width, &height);
|
||||
#endif
|
||||
return RectC(x, y, width, height);
|
||||
return SCL(x, y, width, height);
|
||||
}
|
||||
return Null;
|
||||
}
|
||||
|
|
@ -218,7 +222,7 @@ void Ctrl::WndShow(bool b)
|
|||
|
||||
bool Ctrl::IsWndOpen() const {
|
||||
GuiLock __;
|
||||
return top && top->window && top->window->window;
|
||||
return top && top->window && gtk_widget_get_window(top->window);
|
||||
}
|
||||
|
||||
void Ctrl::SetAlpha(byte alpha)
|
||||
|
|
@ -243,6 +247,17 @@ Rect Ctrl::GetWorkArea() const
|
|||
void Ctrl::GetWorkArea(Array<Rect>& rc)
|
||||
{
|
||||
GuiLock __;
|
||||
#if GTK_CHECK_VERSION(3, 22, 0)
|
||||
GdkDisplay *s = gdk_display_get_default();
|
||||
int n = gdk_display_get_n_monitors(s);
|
||||
rc.Clear();
|
||||
Vector<int> netwa;
|
||||
for(int i = 0; i < n; i++) {
|
||||
GdkRectangle rr;
|
||||
gdk_monitor_get_workarea(gdk_display_get_monitor(s, i), &rr);
|
||||
rc.Add(SCL(rr.x, rr.y, rr.width, rr.height));
|
||||
}
|
||||
#else
|
||||
GdkScreen *s = gdk_screen_get_default();
|
||||
int n = gdk_screen_get_n_monitors(s);
|
||||
rc.Clear();
|
||||
|
|
@ -250,22 +265,11 @@ void Ctrl::GetWorkArea(Array<Rect>& rc)
|
|||
for(int i = 0; i < n; i++) {
|
||||
GdkRectangle rr;
|
||||
Rect r;
|
||||
#if GTK_CHECK_VERSION (3, 3, 5) // U++ does not work with gtk3 yet, but be prepared
|
||||
gdk_screen_get_monitor_workarea(s, i, &rr);
|
||||
r = RectC(r.x, r.y, r.width, r.height);
|
||||
#else
|
||||
gdk_screen_get_monitor_geometry (s, i, &rr);
|
||||
r = RectC(rr.x, rr.y, rr.width, rr.height);
|
||||
#ifdef GDK_WINDOWING_X11
|
||||
if(i == 0)
|
||||
netwa = GetPropertyInts(gdk_screen_get_root_window(gdk_screen_get_default()),
|
||||
"_NET_WORKAREA");
|
||||
if(netwa.GetCount())
|
||||
r = r & RectC(netwa[0], netwa[1], netwa[2], netwa[3]);
|
||||
#endif
|
||||
#endif
|
||||
rc.Add(r);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
Rect Ctrl::GetVirtualWorkArea()
|
||||
|
|
@ -289,8 +293,8 @@ Rect Ctrl::GetVirtualScreenArea()
|
|||
if(r.right == 0) {
|
||||
gint x, y, width, height;
|
||||
gdk_window_get_geometry(gdk_screen_get_root_window(gdk_screen_get_default()),
|
||||
&x, &y, &width, &height, NULL);
|
||||
r = RectC(x, y, width, height);
|
||||
&x, &y, &width, &height);
|
||||
r = SCL(x, y, width, height);
|
||||
}
|
||||
return r;
|
||||
}
|
||||
|
|
@ -298,18 +302,20 @@ Rect Ctrl::GetVirtualScreenArea()
|
|||
Rect Ctrl::GetPrimaryWorkArea()
|
||||
{
|
||||
GuiLock __;
|
||||
#if GTK_CHECK_VERSION(3, 22, 0)
|
||||
GdkRectangle rr;
|
||||
gdk_monitor_get_workarea(gdk_display_get_primary_monitor(gdk_display_get_default()), &rr);
|
||||
return SCL(rr.x, rr.y, rr.width, rr.height);
|
||||
#else
|
||||
static Rect r;
|
||||
if (r.right == 0) {
|
||||
Array<Rect> rc;
|
||||
GetWorkArea(rc);
|
||||
#if GTK_CHECK_VERSION(2, 20, 0)
|
||||
int primary = gdk_screen_get_primary_monitor(gdk_screen_get_default());
|
||||
#else
|
||||
int primary = 0;
|
||||
#endif
|
||||
primary >= 0 && primary < rc.GetCount() ? r = rc[primary] : r = GetVirtualScreenArea();
|
||||
}
|
||||
return r;
|
||||
#endif
|
||||
}
|
||||
|
||||
Rect Ctrl::GetPrimaryScreenArea()
|
||||
|
|
@ -392,8 +398,17 @@ void Ctrl::WndInvalidateRect(const Rect& r)
|
|||
{
|
||||
GuiLock __;
|
||||
LLOG("WndInvalidateRect " << r);
|
||||
gdk_window_invalidate_rect(gdk(), GdkRect(r), TRUE);
|
||||
// gtk_widget_queue_draw_area(top->window, r.left, r.top, r.GetWidth(), r.GetHeight());
|
||||
Rect rr;
|
||||
if(scale > 1) {
|
||||
rr.left = r.left / 2;
|
||||
rr.top = r.top / 2;
|
||||
rr.right = (r.right + 1) / 2;
|
||||
rr.bottom = (r.bottom + 1) / 2;
|
||||
}
|
||||
else
|
||||
rr = r;
|
||||
|
||||
gdk_window_invalidate_rect(gdk(), GdkRect(rr), TRUE);
|
||||
}
|
||||
|
||||
void Ctrl::WndScrollView(const Rect& r, int dx, int dy)
|
||||
|
|
@ -432,10 +447,11 @@ void Ctrl::WndSetPos(const Rect& rect)
|
|||
SweepConfigure(false); // Remove any previous GDK_CONFIGURE for this window
|
||||
if(!this_ || !IsOpen())
|
||||
return;
|
||||
|
||||
Rect m(0, 0, 0, 0);
|
||||
if(dynamic_cast<TopWindow *>(this))
|
||||
m = GetFrameMargins();
|
||||
gdk_window_move_resize(gdk(), rect.left - m.left, rect.top - m.top, rect.GetWidth(), rect.GetHeight());
|
||||
gdk_window_move_resize(gdk(), LSC(rect.left - m.left), LSC(rect.top - m.top), LSC(rect.GetWidth()), LSC(rect.GetHeight()));
|
||||
int t0 = msecs();
|
||||
do { // Wait up to 500ms for corresponding GDK_CONFIGURE to arrive
|
||||
if(SweepConfigure(true))
|
||||
|
|
@ -465,9 +481,9 @@ void Ctrl::WndUpdate()
|
|||
{
|
||||
GuiLock __;
|
||||
LLOG("WndUpdate0");
|
||||
gdk_window_process_updates(gdk(), TRUE);
|
||||
// gdk_window_process_updates(gdk(), TRUE); // deprecated
|
||||
FetchEvents(FALSE); // Should pickup GDK_EXPOSE and repaint the window
|
||||
gdk_flush();
|
||||
gdk_display_flush(gdk_display_get_default());
|
||||
}
|
||||
|
||||
Rect Ctrl::GetDefaultWindowRect()
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@ XDisplay *Xdisplay()
|
|||
|
||||
Window Xroot()
|
||||
{
|
||||
return GDK_WINDOW_XWINDOW(gdk_screen_get_root_window(gdk_screen_get_default()));
|
||||
return GDK_WINDOW_XID(gdk_screen_get_root_window(gdk_screen_get_default()));
|
||||
}
|
||||
|
||||
String GetProperty(Window w, Atom property, Atom rtype)
|
||||
|
|
@ -67,7 +67,7 @@ Atom XAtomRaw(const char *name)
|
|||
|
||||
Atom XAtom(const char *name)
|
||||
{
|
||||
GuiLock __;
|
||||
GuiLock __;
|
||||
Atom x;
|
||||
INTERLOCKED {
|
||||
static VectorMap<String, int> atoms;
|
||||
|
|
@ -83,9 +83,9 @@ Atom XAtom(const char *name)
|
|||
|
||||
Vector<int> GetPropertyInts(GdkWindow *w, const char *property)
|
||||
{
|
||||
GuiLock __;
|
||||
GuiLock __;
|
||||
Vector<int> result;
|
||||
String p = GetProperty(GDK_WINDOW_XWINDOW(w), XAtom(property), AnyPropertyType);
|
||||
String p = GetProperty(GDK_WINDOW_XID(w), XAtom(property), AnyPropertyType);
|
||||
const long int *ptr = (const long int *)~p;
|
||||
const long int *lim = ptr + p.GetLength() / sizeof(long int);
|
||||
result.Reserve(p.GetLength() / sizeof(long int));
|
||||
|
|
@ -106,11 +106,13 @@ dword X11mods(dword key)
|
|||
return mod;
|
||||
}
|
||||
|
||||
#if 0 // retained for 3.8 compatibility
|
||||
|
||||
int Ctrl::RegisterSystemHotKey(dword key, Function<void ()> cb)
|
||||
{
|
||||
GuiLock __;
|
||||
ASSERT(key >= K_DELTA);
|
||||
gdk_error_trap_push();
|
||||
gdk_x11_display_error_trap_push(gdk_display_get_default());
|
||||
KeyCode k = XKeysymToKeycode(Xdisplay(), key & 0xffff);
|
||||
dword mod = X11mods(key);
|
||||
bool r = false;
|
||||
|
|
@ -120,7 +122,7 @@ int Ctrl::RegisterSystemHotKey(dword key, Function<void ()> cb)
|
|||
r = XGrabKey(Xdisplay(), k,
|
||||
mod | (nlock * Mod2Mask) | (clock * LockMask) | (slock * Mod3Mask),
|
||||
Xroot(), true, GrabModeAsync, GrabModeAsync) || r;
|
||||
gdk_error_trap_pop();
|
||||
gdk_x11_display_error_trap_pop_ignored(gdk_display_get_default());
|
||||
if(!r) return -1;
|
||||
int q = hotkey.GetCount();
|
||||
for(int i = 0; i < hotkey.GetCount(); i++)
|
||||
|
|
@ -138,18 +140,20 @@ void Ctrl::UnregisterSystemHotKey(int id)
|
|||
{
|
||||
GuiLock __;
|
||||
if(id >= 0 && id < hotkey.GetCount() && hotkey[id]) {
|
||||
gdk_error_trap_push();
|
||||
gdk_x11_display_error_trap_push(gdk_display_get_default());
|
||||
for(dword nlock = 0; nlock < 2; nlock++)
|
||||
for(dword clock = 0; clock < 2; clock++)
|
||||
for(dword slock = 0; slock < 2; slock++)
|
||||
XUngrabKey(Xdisplay(), keyhot[id],
|
||||
modhot[id] | (nlock * Mod2Mask) | (clock * LockMask) | (slock * Mod3Mask),
|
||||
Xroot());
|
||||
gdk_error_trap_pop();
|
||||
gdk_x11_display_error_trap_pop_ignored(gdk_display_get_default());
|
||||
hotkey[id].Clear();
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
GdkFilterReturn Ctrl::RootKeyFilter(GdkXEvent *xevent, GdkEvent *Xevent, gpointer data)
|
||||
{
|
||||
XEvent *event = (XEvent *)xevent;
|
||||
|
|
|
|||
|
|
@ -317,7 +317,6 @@ void Ctrl::InitWin32(HINSTANCE hInstance)
|
|||
ReSkin();
|
||||
|
||||
OleInitialize(NULL);
|
||||
CoInitialize(NULL);
|
||||
|
||||
/* TRC 05/11/14: moved to GuiSleep to avoid thread creation in OCX DllMain
|
||||
DWORD dummy;
|
||||
|
|
|
|||
56
uppsrc/CtrlCore/gtk3-todo.txt
Normal file
56
uppsrc/CtrlCore/gtk3-todo.txt
Normal file
|
|
@ -0,0 +1,56 @@
|
|||
- Issue with editfield text clipping in the right
|
||||
- Remove warnings
|
||||
- Test dark theme
|
||||
- Test rect theme
|
||||
- Blue Menta ugly scrollbars (round)
|
||||
- TraditionalOk ugly scrollbars (centre image)
|
||||
- DropChoice STDSIZE (.TopPosZ(10))
|
||||
- LeftRoundness with DropChoice (DropChoiceRdO)
|
||||
- 3.8 theme
|
||||
- CleanTheme for X11
|
||||
- libgtk-3-dev to buildrequires
|
||||
- test DateTimeCtrl in dark mode
|
||||
- check CtrlCore/Ctrl.tpp
|
||||
- Check FileSel
|
||||
|
||||
NTH:
|
||||
- spinbutton cosmetics
|
||||
|
||||
PROBABLY DONE:
|
||||
- Problem with hot3 in scrollbar horizontal (check in SD)
|
||||
|
||||
DONE:
|
||||
|
||||
- Resizing delay
|
||||
- Refresh issue
|
||||
- Test & Fix filesel & fileselector
|
||||
- Combobox push is weird
|
||||
- right scrollbar
|
||||
- Test grip resize
|
||||
- toolbar button highlight
|
||||
- correct checks in menu
|
||||
- uword cannot be resized smaller
|
||||
- Scrollbar margins (better fit for slider)
|
||||
- Scrollbar Correct minsize, barsize...
|
||||
- FileSelector
|
||||
- Mint-Y disabled color is wrong
|
||||
- Mint-Y tooltip color is wrong
|
||||
- .iml cursors in UHD are wrong (e.g. header <-|->)
|
||||
- cxZ Uword - wrong caret
|
||||
- Combobox appearance issues (minor, round corners broken on the left)
|
||||
- spinbuttons in UWord
|
||||
- read-only dropchoice left color
|
||||
- ColorPopup background
|
||||
- Fix IsPainting
|
||||
- Header synthetise
|
||||
- Resizing fix black
|
||||
- Slider thumb
|
||||
- Remove DDUMPs
|
||||
- TabBar synthetise
|
||||
- Problem with theide menu
|
||||
- LabelBox
|
||||
- GtkStyleBool("has-backward-stepper")
|
||||
- DropChoice read only active edge
|
||||
- Scale must not be same as UHD
|
||||
- makefile pkg-config support
|
||||
- Test with 3.8
|
||||
|
|
@ -306,16 +306,25 @@ protected:
|
|||
|
||||
public:
|
||||
struct Style : ChStyle<Style> {
|
||||
Value item, topitem[3], topbar;
|
||||
Color menutext, itemtext, topitemtext[3];
|
||||
SeparatorCtrl::Style breaksep;
|
||||
Value look, arealook;
|
||||
Value popupframe, popupbody, popupiconbar;
|
||||
Value item; // hot menu item background in popup menu
|
||||
Value topitem[3]; // top menu item background normal/hot/pressed
|
||||
Value topbar; // deprecated
|
||||
Color menutext; // normal state popup menu item text
|
||||
Color itemtext; // hot state popup menu item text
|
||||
Color topitemtext[3]; // top menu item text normal/hot/pressed
|
||||
SeparatorCtrl::Style breaksep; // separator between menu bars
|
||||
Value look; // top menu background
|
||||
Value arealook; // top menu backgroung if arealook and in frame (can be null, then 'look')
|
||||
Value popupframe; // static frame of whole popup menu
|
||||
Value popupbody; // background of whole popup menu
|
||||
Value popupiconbar; // if there is special icon background in popup menu
|
||||
SeparatorCtrl::Style separator;
|
||||
Size maxiconsize;
|
||||
int leftgap, textgap;
|
||||
int lsepm, rsepm;
|
||||
Point pullshift;
|
||||
Size maxiconsize; // limit of icon size
|
||||
int leftgap; // between left border and icon
|
||||
int textgap;
|
||||
int lsepm;
|
||||
int rsepm;
|
||||
Point pullshift; // offset of submenu popup
|
||||
bool opaquetest; // If true, topmenu item can change hot text color
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -128,20 +128,278 @@ void RoundedRect(Painter& w, Rectf r, double rx, double ry, dword corner)
|
|||
RoundedRect(w, r.left, r.top, r.GetWidth(), r.GetHeight(), rx, ry, corner);
|
||||
}
|
||||
|
||||
Image MakeButton(int radius, const Image& face, int border_width, Color border_color, dword corner)
|
||||
Image MakeElement(Size sz, double radius, const Image& face, int border_width, Color border_color, Event<Painter&, const Rectf&> shape)
|
||||
{
|
||||
int q = radius + border_width + 16;
|
||||
Rectf r(0, 0, q, q);
|
||||
Rectf r(0, 0, sz.cx, sz.cy);
|
||||
ImagePainter w(r.GetSize());
|
||||
w.Clear(RGBAZero());
|
||||
RoundedRect(w, r.Deflated(border_width - 1), radius, radius, corner);
|
||||
FillImage(w, r.Deflated(border_width - 1), face);
|
||||
RoundedRect(w, r.Deflated(border_width / 2.0), radius, radius, corner);
|
||||
w.Stroke(border_width, border_color);
|
||||
Rectf dr = r.Deflated(border_width / 2.0);
|
||||
if(!IsNull(face)) {
|
||||
shape(w, dr);
|
||||
FillImage(w, r.Deflated(border_width / 2.0 - 1), face);
|
||||
}
|
||||
shape(w, dr);
|
||||
if(!IsNull(border_color))
|
||||
w.Stroke(border_width, border_color);
|
||||
Image m = w;
|
||||
Point p1(radius, radius);
|
||||
SetHotSpots(m, p1, (Point)r.BottomRight() - p1);
|
||||
Point p1(radius + border_width, radius + border_width);
|
||||
SetHotSpots(m, p1, (Point)r.BottomRight() - p1 - Point(1, 1));
|
||||
return m;
|
||||
}
|
||||
|
||||
Image MakeButton(int radius, const Image& face, int border_width, Color border_color, dword corner)
|
||||
{
|
||||
int q = radius + border_width + DPI(16);
|
||||
return MakeElement(Size(q, q), radius, face, border_width, border_color, [&](Painter& w, const Rectf& r) {
|
||||
RoundedRect(w, r, radius, radius, corner);
|
||||
});
|
||||
}
|
||||
|
||||
Image MakeButton(int radius, Color face, int border_width, Color border_color, dword corner)
|
||||
{
|
||||
return MakeButton(radius, CreateImage(Size(DPI(10), DPI(5)), face), border_width, border_color, corner);
|
||||
}
|
||||
|
||||
Image Hot3(const Image& m)
|
||||
{
|
||||
Size sz = m.GetSize();
|
||||
return WithHotSpots(m, sz.cx / 3, sz.cy / 3, sz.cx - sz.cx / 3, sz.cy - sz.cy / 3);
|
||||
}
|
||||
|
||||
Image ChHot(const Image& m, int n)
|
||||
{
|
||||
return WithHotSpots(m, DPI(n), DPI(n), 0, 0);
|
||||
}
|
||||
|
||||
Color AvgColor(const Image& m, const Rect& rr)
|
||||
{
|
||||
int r = 0;
|
||||
int g = 0;
|
||||
int b = 0;
|
||||
int n = 0;
|
||||
for(int y = rr.top; y < rr.bottom; y++)
|
||||
for(int x = rr.left; x < rr.right; x++) {
|
||||
RGBA c = m[y][x];
|
||||
Unmultiply(&c, &c, 1);
|
||||
if(c.a > 20) {
|
||||
r += c.r;
|
||||
g += c.g;
|
||||
b += c.b;
|
||||
n++;
|
||||
}
|
||||
}
|
||||
return n ? Color(r / n, g / n, b / n) : SWhite();
|
||||
}
|
||||
|
||||
Color AvgColor(const Image& m, int margin)
|
||||
{
|
||||
return AvgColor(m, Rect(m.GetSize()).Deflated(margin));
|
||||
}
|
||||
|
||||
Color GetInk(const Image& m)
|
||||
{
|
||||
RGBA avg = AvgColor(m);
|
||||
Color ink = SBlack();
|
||||
int best = 0;
|
||||
for(RGBA c : m) {
|
||||
Unmultiply(&c, &c, 1);
|
||||
if(c.a > 100) {
|
||||
c.a = 255;
|
||||
int q = Grayscale(abs(c.r - avg.r), abs(c.g - avg.g), abs(c.b - avg.b));
|
||||
if(q > best) {
|
||||
best = q;
|
||||
ink = c;
|
||||
}
|
||||
}
|
||||
}
|
||||
return ink;
|
||||
}
|
||||
|
||||
int GetRoundness(const Image& m)
|
||||
{
|
||||
Size isz = m.GetSize();
|
||||
int bestd = 0, besth = 0;
|
||||
int di = 0, hi = 0;
|
||||
int hy = isz.cy / 2;
|
||||
RGBA avg = AvgColor(m);
|
||||
auto Chk = [&](int x, int y, int& best, int& besti) {
|
||||
if(x < isz.cx && y < isz.cy) {
|
||||
RGBA c = m[y][x];
|
||||
Unmultiply(&c, &c, 1);
|
||||
if(c.a > 100) {
|
||||
int q = Grayscale(abs(c.r - avg.r), abs(c.g - avg.g), abs(c.b - avg.b));
|
||||
if(q > best) {
|
||||
best = q;
|
||||
besti = x;
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
for(int i = 0; i < 8; i++) {
|
||||
Chk(i, hy, besth, hi);
|
||||
Chk(i, i, bestd, di);
|
||||
}
|
||||
return max(di - hi, 0);
|
||||
}
|
||||
|
||||
static Value sSample;
|
||||
|
||||
void SetChameleonSample(const Value& m, bool once)
|
||||
{
|
||||
if(!once || IsNull(sSample))
|
||||
sSample = m;
|
||||
}
|
||||
|
||||
Value GetChameleonSample()
|
||||
{
|
||||
return sSample;
|
||||
}
|
||||
|
||||
Image WithRect(Image m, int x, int y, int cx, int cy, Color c)
|
||||
{
|
||||
ImageBuffer ib(m);
|
||||
for(int i = 0; i < cx; i++)
|
||||
for(int j = 0; j < cy; j++)
|
||||
ib[y + j][x + i] = c;
|
||||
return ib;
|
||||
}
|
||||
|
||||
Image WithLeftLine(const Image& m, Color c, int w)
|
||||
{
|
||||
return WithRect(m, 0, 0, w, m.GetHeight(), c);
|
||||
}
|
||||
|
||||
Image WithRightLine(const Image& m, Color c, int w)
|
||||
{
|
||||
return WithRect(m, m.GetWidth() - w, 0, w, m.GetHeight(), c);
|
||||
}
|
||||
|
||||
Image WithTopLine(const Image& m, Color c, int w)
|
||||
{
|
||||
return WithRect(m, 0, 0, m.GetWidth(), w, c);
|
||||
}
|
||||
|
||||
Image WithBottomLine(const Image& m, Color c, int w)
|
||||
{
|
||||
return WithRect(m, 0, m.GetHeight() - w, m.GetWidth(), w, c);
|
||||
}
|
||||
|
||||
void ChSynthetic(Image button100x100[4], Color text[4])
|
||||
{
|
||||
int roundness = DPI(3);
|
||||
Color ink = SColorText();
|
||||
for(int i = 0; i < 4; i++) {
|
||||
Image m = button100x100[i];
|
||||
if(i == 0) {
|
||||
ink = GetInk(m);
|
||||
roundness = GetRoundness(m) ? DPI(3) : 0;
|
||||
CtrlsImg::Set(CtrlsImg::I_EFE, WithHotSpots(MakeButton(roundness, SColorPaper(), DPI(1), ink), DPI(3), DPI(1), 0, 0));
|
||||
CtrlsImg::Set(CtrlsImg::I_VE, WithHotSpots(MakeButton(DPI(0), SColorPaper(), DPI(1), ink), DPI(2), DPI(2), 0, 0));
|
||||
EditField::StyleDefault().Write().edge[CTRL_DISABLED] = WithHotSpots(MakeButton(roundness, SColorFace(), DPI(1), ink), DPI(3), DPI(1), 0, 0);
|
||||
EditField::StyleDefault().Write().activeedge = true;
|
||||
LabelBox::SetLook(WithHotSpots(MakeButton(2 * roundness / 3, Image(), DPI(1), ink), DPI(3), DPI(3), 0, 0));
|
||||
}
|
||||
Size sz = m.GetSize();
|
||||
m = Crop(m, sz.cx / 8, sz.cy / 8, 6 * sz.cx / 8, 6 * sz.cy / 8);
|
||||
{
|
||||
auto Set = [&](Button::Style& s, const Image& arrow = Null) {
|
||||
Value l = MakeButton(0, m, DPI(1), ink, 0);
|
||||
s.look[i] = IsNull(l) ? l : ChLookWith(l, arrow);
|
||||
};
|
||||
Set(Button::StyleScroll().Write());
|
||||
Set(Button::StyleEdge().Write());
|
||||
Set(Button::StyleLeftEdge().Write());
|
||||
ScrollBar::Style& s = ScrollBar::StyleDefault().Write();
|
||||
|
||||
Set(s.up, CtrlsImg::UA());
|
||||
Set(s.down, CtrlsImg::DA());
|
||||
Set(s.left, CtrlsImg::LA());
|
||||
Set(s.right, CtrlsImg::RA());
|
||||
}
|
||||
{
|
||||
MultiButton::Style& s = MultiButton::StyleDefault().Write();
|
||||
s.clipedge = true;
|
||||
s.border = s.trivialborder = 0;
|
||||
|
||||
s.left[i] = MakeButton(roundness, m, DPI(1), ink, CORNER_TOP_LEFT|CORNER_BOTTOM_LEFT);
|
||||
s.trivial[i] = s.look[i] = s.right[i] = MakeButton(roundness, m, DPI(1), ink, CORNER_TOP_RIGHT|CORNER_BOTTOM_RIGHT);
|
||||
auto Middle = [&](Image m) {
|
||||
ImageBuffer ib(m);
|
||||
for(int y = 0; y < DPI(1); y++)
|
||||
for(int x = 0; x < ib.GetWidth(); x++) {
|
||||
ib[y][x] = ink;
|
||||
ib[ib.GetHeight() - y - 1][x] = ink;
|
||||
}
|
||||
return WithHotSpot(ib, DPI(1), DPI(1));
|
||||
};
|
||||
s.lmiddle[i] = Middle(WithRightLine(m, ink));
|
||||
s.rmiddle[i] = Middle(WithLeftLine(m, ink));
|
||||
s.monocolor[i] = s.fmonocolor[i] = text[i];
|
||||
for(int i = 0; i < 4; i++)
|
||||
s.edge[i] = EditField::StyleDefault().edge[i];
|
||||
s.margin = Rect(DPI(3), 2, DPI(1), 2);
|
||||
s.activeedge = true;
|
||||
s.stdwidth = DPI(17);
|
||||
}
|
||||
{
|
||||
SpinButtons::Style& sp = SpinButtons::StyleDefault().Write();
|
||||
if(i == 0)
|
||||
sp.dec = sp.inc = Button::StyleNormal();
|
||||
auto Spin = [&](dword corners, const Image& sm) {
|
||||
return ChLookWith(WithLeftLine(MakeButton(roundness, m, 0, Black(), corners), ink), sm, text[i]);
|
||||
};
|
||||
sp.inc.look[i] = Spin(CORNER_TOP_RIGHT, CtrlImg::spinup());
|
||||
sp.dec.look[i] = Spin(CORNER_BOTTOM_RIGHT, CtrlImg::spindown());
|
||||
sp.width = DPI(14); // DPI(17) - DPI(3) (droplist stdwidth minus frame)
|
||||
}
|
||||
{
|
||||
HeaderCtrl::Style& hs = HeaderCtrl::StyleDefault().Write();
|
||||
hs.look[i] = ChHot(WithBottomLine(WithRightLine(m, ink, 1), ink));
|
||||
}
|
||||
if(i == CTRL_DISABLED) {
|
||||
ProgressIndicator::Style& s = ProgressIndicator::StyleDefault().Write();
|
||||
s.hlook = MakeButton(roundness, m, DPI(1), ink);
|
||||
s.hchunk = MakeButton(roundness, SColorHighlight(), DPI(1), ink);
|
||||
s.bound = true;
|
||||
s.nomargins = true;
|
||||
}
|
||||
if(i == CTRL_NORMAL || i == CTRL_PRESSED) {
|
||||
Image sm = MakeElement(Size(DPI(10), DPI(20)), roundness, m, DPI(1), ink, [&](Painter& w, const Rectf& r) {
|
||||
double cx = r.GetWidth();
|
||||
double cy = r.GetHeight();
|
||||
double uy = 0.4 * cy;
|
||||
double uq = 0.5 * uy;
|
||||
w.Move(r.left, r.top + cy)
|
||||
.Line(r.left, r.top + uy)
|
||||
.Quadratic(r.left, r.top + uq, r.left + cx / 2, r.top)
|
||||
.Quadratic(r.left + cx, r.top + uq, r.left + cx, r.top + uy)
|
||||
.Line(r.left + cx, r.top + cy)
|
||||
.Close();
|
||||
});
|
||||
CtrlImg::Set(i == CTRL_PRESSED ? CtrlImg::I_hthumb1 : CtrlImg::I_hthumb, sm);
|
||||
CtrlImg::Set(i == CTRL_PRESSED ? CtrlImg::I_vthumb1 : CtrlImg::I_vthumb, RotateClockwise(sm));
|
||||
}
|
||||
{
|
||||
TabCtrl::Style& s = TabCtrl::StyleDefault().Write();
|
||||
int adj = 8;
|
||||
auto Face = [](int adj) {
|
||||
Color c = SColorFace();
|
||||
return Color(clamp(c.GetR() + adj, 0, 255),
|
||||
clamp(c.GetG() + adj, 0, 255),
|
||||
clamp(c.GetB() + adj, 0, 255));
|
||||
};
|
||||
s.body = MakeButton(0, Face(8), DPI(1), ink);
|
||||
Image t = MakeButton(roundness, Face(decode(i, CTRL_NORMAL, -20,
|
||||
CTRL_HOT, 2,
|
||||
CTRL_PRESSED, 8,
|
||||
-8)), DPI(1), ink, CORNER_TOP_LEFT|CORNER_TOP_RIGHT);
|
||||
s.first[i] = s.last[i] = s.both[i] = s.normal[i] = ChHot(Crop(t, 0, 0, t.GetWidth(), t.GetHeight() - DPI(2)), DPI(3));
|
||||
s.margin = 0;
|
||||
s.sel = Rect(0, DPI(1), 0, DPI(1));
|
||||
s.extendleft = DPI(2);
|
||||
s.text_color[i] = SColorText();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -11,4 +11,29 @@ enum {
|
|||
|
||||
void RoundedRect(Painter& w, double x, double y, double cx, double cy, double rx, double ry, dword corners);
|
||||
void RoundedRect(Painter& w, Rectf r, double rx, double ry, dword corner);
|
||||
Image MakeButton(int radius, const Image& face, int border_width, Color border_color, dword corner);
|
||||
Image MakeElement(Size sz, double radius, const Image& face, int border_width, Color border_color, Event<Painter&, const Rectf&> shape);
|
||||
Image MakeButton(int radius, const Image& face, int border_width, Color border_color = Null, dword corner = 0xff);
|
||||
Image MakeButton(int radius, Color face, int border_width, Color border_color = Null, dword corner = 0xff);
|
||||
|
||||
Image Hot3(const Image& m); // Adds resizing hotspots at 1/3
|
||||
Image ChHot(const Image& m, int n = 2); // Adds resizing hotspots DPI(n)
|
||||
Color AvgColor(const Image& m, const Rect& rr);
|
||||
Color AvgColor(const Image& m, int margin = 0);
|
||||
|
||||
Color GetInk(const Image& m); // the color that is most different from AvgColor
|
||||
int GetRoundness(const Image& m);
|
||||
|
||||
Image WithRect(Image m, int x, int y, int cx, int cy, Color c);
|
||||
Image WithLeftLine(const Image& m, Color c, int w = DPI(1));
|
||||
Image WithRightLine(const Image& m, Color c, int w = DPI(1));
|
||||
Image WithTopLine(const Image& m, Color c, int w = DPI(1));
|
||||
Image WithBottomLine(const Image& m, Color c, int w = DPI(1));
|
||||
|
||||
// Creates synthetic style based on SColors and basic button face
|
||||
void ChSynthetic(Image button100x100[4], Color text[4]);
|
||||
|
||||
// for diagnostics purposes
|
||||
#ifdef _DEBUG
|
||||
void SetChameleonSample(const Value& m, bool once = true);
|
||||
Value GetChameleonSample();
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -4,12 +4,6 @@
|
|||
|
||||
namespace Upp {
|
||||
|
||||
Image Hot3(const Image& m)
|
||||
{
|
||||
Size sz = m.GetSize();
|
||||
return WithHotSpots(m, sz.cx / 3, sz.cy / 3, sz.cx - sz.cx / 3, sz.cy - sz.cy / 3);
|
||||
}
|
||||
|
||||
Image Coco_ThemeImage(Color bg, int cx, int cy, int margin, int type,
|
||||
int value, int state, bool focus)
|
||||
{
|
||||
|
|
@ -26,29 +20,6 @@ Image Coco_ThemeImage(int cx, int cy, int margin, int type, int value, int state
|
|||
Coco_ThemeImage(Black(), cx, cy, margin, type, value, state, focus)));
|
||||
}
|
||||
|
||||
Color AvgColor(const Image& m, const Rect& rr)
|
||||
{
|
||||
int n = rr.GetWidth() * rr.GetHeight();
|
||||
if(n <= 0)
|
||||
return White();
|
||||
int r = 0;
|
||||
int g = 0;
|
||||
int b = 0;
|
||||
for(int y = rr.top; y < rr.bottom; y++)
|
||||
for(int x = rr.left; x < rr.right; x++) {
|
||||
RGBA c = m[y][x];
|
||||
r += c.r;
|
||||
g += c.g;
|
||||
b += c.b;
|
||||
}
|
||||
return Color(r / n, g / n, b / n);
|
||||
}
|
||||
|
||||
Color AvgColor(const Image& m, int margin = 0)
|
||||
{
|
||||
return AvgColor(m, Rect(m.GetSize()).Deflated(margin));
|
||||
}
|
||||
|
||||
void ClampedAutoCrop(Image *h, int count)
|
||||
{
|
||||
AutoCrop(h, count);
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
#include "CtrlLib.h"
|
||||
|
||||
#ifdef PLATFORM_X11
|
||||
#ifdef GUI_X11 // X11 uses GTK2 for look&feel
|
||||
#ifndef flagNOGTK
|
||||
|
||||
#include "ChGtk.h"
|
||||
|
|
@ -717,5 +717,18 @@ void ChHostSkin()
|
|||
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
namespace Upp {
|
||||
|
||||
void ChHostSkin() {}
|
||||
|
||||
Image GtkThemeIcon(const char *name, int rsz)
|
||||
{
|
||||
return CtrlImg::smallreporticon();
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -1,8 +1,6 @@
|
|||
|
||||
|
||||
#include "CtrlLib.h"
|
||||
|
||||
#ifdef PLATFORM_X11
|
||||
#ifdef GUI_X11
|
||||
#ifdef flagNOGTK
|
||||
|
||||
namespace Upp {
|
||||
|
|
@ -122,7 +120,7 @@ Image GetGTK0(GtkWidget *widget, int state, int shadow, const char *detail, int
|
|||
if(GTK_IS_RANGE(widget)) {
|
||||
GtkRange *r = GTK_RANGE(widget);
|
||||
#ifndef GTK_NEWSCROLLBAR
|
||||
r->has_stepper_a = r->has_stepper_b = r->has_stepper_c = r->has_stepper_d = 1;
|
||||
// r->has_stepper_a = r->has_stepper_b = r->has_stepper_c = r->has_stepper_d = 1;
|
||||
#endif
|
||||
GdkRectangle cr;
|
||||
cr.x = rect.left;
|
||||
|
|
@ -661,4 +659,4 @@ void GtkChScrollBar(Value *lbutton, Value *lbutton2,
|
|||
}
|
||||
|
||||
#endif
|
||||
#endif
|
||||
#endif
|
||||
482
uppsrc/CtrlLib/ChGtk3.cpp
Normal file
482
uppsrc/CtrlLib/ChGtk3.cpp
Normal file
|
|
@ -0,0 +1,482 @@
|
|||
#include "CtrlLib.h"
|
||||
|
||||
#ifdef GUI_GTK
|
||||
|
||||
/*
|
||||
|
||||
TODO: overpaint
|
||||
|
||||
*/
|
||||
|
||||
namespace Upp {
|
||||
|
||||
int GtkSettingsInt(const char *name)
|
||||
{
|
||||
gint h = Null;
|
||||
g_object_get(gtk_settings_get_default(), name, &h, NULL);
|
||||
return h;
|
||||
}
|
||||
|
||||
int GtkSettingsBool(const char *name)
|
||||
{
|
||||
gboolean h = false;
|
||||
g_object_get(gtk_settings_get_default(), name, &h, NULL);
|
||||
return h;
|
||||
}
|
||||
|
||||
String GtkSettingsString(const char *name)
|
||||
{
|
||||
const char *h = "";
|
||||
g_object_get(gtk_settings_get_default(), name, &h, NULL);
|
||||
return h;
|
||||
}
|
||||
|
||||
void SetupFont()
|
||||
{
|
||||
int fontface = Font::ARIAL;
|
||||
int fontheight = 13;
|
||||
bool bold = false;
|
||||
bool italic = false;
|
||||
|
||||
String font_name = GtkSettingsString("gtk-font-name");
|
||||
int xdpi = Nvl(GtkSettingsInt("gtk-xft-dpi"), 72 * 1024);
|
||||
|
||||
const char *q = strrchr(font_name, ' ');
|
||||
if(q) {
|
||||
int h = atoi(q);
|
||||
if(h)
|
||||
fontheight = h;
|
||||
String face(font_name, q);
|
||||
fontface = Font::FindFaceNameIndex(face);
|
||||
|
||||
if(fontface == 0) {
|
||||
for(;;) {
|
||||
const char *q = strrchr(face, ' ');
|
||||
if(!q) break;
|
||||
const char *s = q + 1;
|
||||
if(stricmp(s, "Bold") == 0 || stricmp(s, "Heavy") == 0)
|
||||
bold = true;
|
||||
else
|
||||
if(stricmp(s, "Italic") == 0 || stricmp(s, "Oblique") == 0)
|
||||
italic = true;
|
||||
else
|
||||
if(stricmp(s, "Regular") == 0 || stricmp(s, "Light") || stricmp(s, "Medium"))
|
||||
;
|
||||
else
|
||||
continue;
|
||||
face = String(~face, q);
|
||||
}
|
||||
fontface = Font::FindFaceNameIndex(face);
|
||||
if(fontface == 0) {
|
||||
if(ToUpper(face[0]) == 'M')
|
||||
fontface = Font::COURIER;
|
||||
else
|
||||
if(ToUpper(face[0]) == 'S' && ToUpper(face[1]) == 'e')
|
||||
fontface = Font::ROMAN;
|
||||
else
|
||||
fontface = Font::ARIAL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Font gui_font = Font(fontface, fround(Ctrl::SCL(fontheight) * xdpi + 512*72.0) / (1024*72)).Bold(bold).Italic(italic);
|
||||
Font::SetDefaultFont(gui_font);
|
||||
}
|
||||
|
||||
static Image sCurrentImage;
|
||||
|
||||
Image CairoImage(int cx, int cy, Event<cairo_t *> draw)
|
||||
{
|
||||
Image m[2];
|
||||
for(int i = 0; i < 2; i++) {
|
||||
ImageDraw iw(DPI(cx), DPI(cy));
|
||||
iw.DrawRect(0, 0, DPI(cx), DPI(cy), i ? Black() : White());
|
||||
cairo_t *cr = iw;
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
cairo_surface_set_device_scale(cairo_get_target(cr), DPI(1), DPI(1));
|
||||
#endif
|
||||
draw(cr);
|
||||
m[i] = iw;
|
||||
}
|
||||
sCurrentImage = RecreateAlpha(m[0], m[1]);
|
||||
return sCurrentImage;
|
||||
}
|
||||
|
||||
Image CairoImage(GtkStyleContext *ctx, int cx = 40, int cy = 32)
|
||||
{
|
||||
return CairoImage(cx, cy, [&](cairo_t *cr) {
|
||||
gtk_render_background(ctx, cr, 0, 0, cx, cy);
|
||||
gtk_render_frame(ctx, cr, 0, 0, cx, cy);
|
||||
});
|
||||
}
|
||||
|
||||
#if GTK_CHECK_VERSION(3, 20, 0)
|
||||
|
||||
static GtkStyleContext *sCtx = NULL;
|
||||
static GtkStateFlags sFlags;
|
||||
|
||||
void Gtk_Free()
|
||||
{
|
||||
if(sCtx)
|
||||
g_object_unref(sCtx);
|
||||
sCtx = NULL;
|
||||
}
|
||||
|
||||
void Gtk_State(int state, dword flags = 0)
|
||||
{
|
||||
sFlags = static_cast<GtkStateFlags>(decode(state, CTRL_HOT, GTK_STATE_FLAG_PRELIGHT,
|
||||
CTRL_PRESSED, GTK_STATE_FLAG_ACTIVE,
|
||||
CTRL_DISABLED, GTK_STATE_FLAG_INSENSITIVE,
|
||||
GTK_STATE_FLAG_NORMAL) | flags) ;
|
||||
gtk_style_context_set_state(sCtx, sFlags);
|
||||
}
|
||||
|
||||
static Size sCurrentSize;
|
||||
|
||||
void Gtk_New(const char *name, int state = 0, dword flags = 0)
|
||||
{
|
||||
Gtk_Free();
|
||||
sCtx = NULL;
|
||||
for(const String& element : Split(name, ' ')) {
|
||||
GtkWidgetPath *path = sCtx ? gtk_widget_path_copy(gtk_style_context_get_path(sCtx))
|
||||
: gtk_widget_path_new();
|
||||
Vector<String> s = Split(element, '.');
|
||||
if(s.GetCount()) {
|
||||
gtk_widget_path_append_type(path, G_TYPE_NONE);
|
||||
gtk_widget_path_iter_set_object_name(path, -1, s[0]);
|
||||
}
|
||||
for(int i = 1; i < s.GetCount(); i++)
|
||||
gtk_widget_path_iter_add_class(path, -1, s[i]);
|
||||
|
||||
GtkStyleContext *context2 = gtk_style_context_new();
|
||||
gtk_style_context_set_path(context2, path);
|
||||
gtk_style_context_set_parent(context2, sCtx);
|
||||
gtk_widget_path_unref(path);
|
||||
Gtk_Free();
|
||||
sCtx = context2;
|
||||
}
|
||||
ASSERT(sCtx);
|
||||
gtk_style_context_set_scale(sCtx, DPI(1));
|
||||
Gtk_State(state, flags);
|
||||
|
||||
GtkBorder margin, border, padding;
|
||||
int min_width, min_height;
|
||||
|
||||
GtkStateFlags f = gtk_style_context_get_state(sCtx);
|
||||
gtk_style_context_get_margin (sCtx, f, &margin);
|
||||
gtk_style_context_get_border (sCtx, f, &border);
|
||||
gtk_style_context_get_padding (sCtx, f, &padding);
|
||||
|
||||
gtk_style_context_get(sCtx, f, "min-width", &min_width, "min-height", &min_height, NULL);
|
||||
|
||||
min_width += margin.left + margin.right + border.left + border.right + padding.left + padding.right;
|
||||
min_height += margin.top + margin.bottom + border.top + border.bottom + padding.top + padding.bottom;
|
||||
|
||||
sCurrentSize.cx = min_width;
|
||||
sCurrentSize.cy = min_height;
|
||||
}
|
||||
|
||||
/*
|
||||
bool GtkStyleBool(const char *name)
|
||||
{
|
||||
return false;
|
||||
gboolean b = false;
|
||||
gtk_style_context_get(sCtx, gtk_style_context_get_state(sCtx), name, &b, NULL);
|
||||
return b;
|
||||
}
|
||||
|
||||
int GtkStyleInt(const char *name)
|
||||
{
|
||||
gint n = 0;
|
||||
gtk_style_context_get(sCtx, gtk_style_context_get_state(sCtx), name, &n, NULL);
|
||||
return n;
|
||||
}
|
||||
*/
|
||||
|
||||
Size GtkSize()
|
||||
{
|
||||
return sCurrentSize;
|
||||
}
|
||||
|
||||
void GtkSize(Size& sz)
|
||||
{
|
||||
sz.cx = max(sz.cx, sCurrentSize.cx);
|
||||
sz.cy = max(sz.cy, sCurrentSize.cy);
|
||||
}
|
||||
|
||||
Color GetInkColor()
|
||||
{
|
||||
GdkRGBA color;
|
||||
gtk_style_context_get_color(sCtx, sFlags, &color);
|
||||
RGBA rgba;
|
||||
rgba.r = int(255 * color.red);
|
||||
rgba.g = int(255 * color.green);
|
||||
rgba.b = int(255 * color.blue);
|
||||
rgba.a = int(255 * color.alpha);
|
||||
RGBA t = SColorPaper();
|
||||
AlphaBlend(&t, &rgba, 1);
|
||||
return t;
|
||||
}
|
||||
|
||||
void SOImages(int imli, dword flags)
|
||||
{
|
||||
for(int st = 0; st < 4; st++) {
|
||||
Gtk_State(st, flags);
|
||||
CtrlsImg::Set(imli++, CairoImage(16, 16, [&](cairo_t *cr) {
|
||||
gtk_render_check(sCtx, cr, 0, 0, 16, 16);
|
||||
}));
|
||||
}
|
||||
}
|
||||
|
||||
Image CairoImage(int cx = 40, int cy = 32)
|
||||
{
|
||||
return CairoImage(sCtx, cx, cy);
|
||||
}
|
||||
|
||||
Color GetBackgroundColor()
|
||||
{
|
||||
Image m = CairoImage(30, 30);
|
||||
Image b = CreateImage(m.GetSize(), SColorPaper());
|
||||
Over(b, m);
|
||||
return AvgColor(b);
|
||||
}
|
||||
|
||||
Image Gtk_Icon(const char *icon_name, int size)
|
||||
{
|
||||
GdkPixbuf *pixbuf = gtk_icon_theme_load_icon_for_scale(gtk_icon_theme_get_default(), icon_name,
|
||||
size, 2, (GtkIconLookupFlags)0, NULL);
|
||||
if(pixbuf) {
|
||||
int cx = gdk_pixbuf_get_width(pixbuf);
|
||||
int cy = gdk_pixbuf_get_height(pixbuf);
|
||||
|
||||
Image m = CairoImage(cx, cy, [&](cairo_t *cr) {
|
||||
gdk_cairo_set_source_pixbuf(cr, pixbuf, 0, 0);
|
||||
cairo_paint(cr);
|
||||
});
|
||||
|
||||
Size sz = m.GetSize();
|
||||
|
||||
g_object_unref(pixbuf);
|
||||
|
||||
return sz.cy > size && sz.cy ? Rescale(m, sz.cx * size / sz.cy, size) : m;
|
||||
}
|
||||
return Null;
|
||||
}
|
||||
|
||||
void ChHostSkin()
|
||||
{
|
||||
SetupFont();
|
||||
|
||||
Gtk_New("label.view");
|
||||
SColorPaper_Write(GetBackgroundColor());
|
||||
SColorText_Write(GetInkColor());
|
||||
Gtk_New("window.background");
|
||||
SColorFace_Write(GetBackgroundColor());
|
||||
Gtk_New("entry");
|
||||
Gtk_State(CTRL_DISABLED);
|
||||
SColorDisabled_Write(GetInkColor());
|
||||
Gtk_New("entry selection");
|
||||
SColorHighlight_Write(GetBackgroundColor());
|
||||
SColorHighlightText_Write(GetInkColor());
|
||||
Gtk_New("label.view");
|
||||
SColorLabel_Write(GetInkColor());
|
||||
Gtk_New("tooltip.background");
|
||||
SColorInfo_Write(GetBackgroundColor());
|
||||
SColorInfoText_Write(GetInkColor());
|
||||
|
||||
ColoredOverride(CtrlsImg::Iml(), CtrlsImg::Iml());
|
||||
|
||||
#if 0 // TODO (?)
|
||||
{ SColorLight_Write, 2*5 + 0 },
|
||||
{ SColorShadow_Write, 3*5 + 0 },
|
||||
#endif
|
||||
|
||||
Gtk_New("radiobutton radio");
|
||||
SOImages(CtrlsImg::I_S0, GTK_STATE_FLAG_NORMAL);
|
||||
SOImages(CtrlsImg::I_S1, GTK_STATE_FLAG_CHECKED);
|
||||
Gtk_New("checkbutton check");
|
||||
SOImages(CtrlsImg::I_O0, GTK_STATE_FLAG_NORMAL);
|
||||
SOImages(CtrlsImg::I_O1, GTK_STATE_FLAG_CHECKED);
|
||||
SOImages(CtrlsImg::I_O2, GTK_STATE_FLAG_INCONSISTENT);
|
||||
|
||||
CtrlImg::Set(CtrlImg::I_MenuCheck0, CtrlsImg::O0());
|
||||
CtrlImg::Set(CtrlImg::I_MenuCheck1, CtrlsImg::O1());
|
||||
CtrlImg::Set(CtrlImg::I_MenuRadio0, CtrlsImg::S0());
|
||||
CtrlImg::Set(CtrlImg::I_MenuRadio1, CtrlsImg::S1());
|
||||
|
||||
for(int i = 0; i < 6; i++)
|
||||
CtrlsImg::Set(CtrlsImg::I_DA + i, CtrlsImg::Get(CtrlsImg::I_kDA + i));
|
||||
|
||||
{
|
||||
Gtk_New("button");
|
||||
Color ink;
|
||||
Color text[4];
|
||||
Image button[4];
|
||||
for(int pass = 0; pass < 2; pass++) {
|
||||
Button::Style& s = pass ? Button::StyleOk().Write() : Button::StyleNormal().Write();
|
||||
int roundness = DPI(3);
|
||||
for(int i = 0; i < 4; i++) {
|
||||
Gtk_State(i);
|
||||
s.look[i] = Hot3(CairoImage());
|
||||
s.monocolor[i] = s.textcolor[i] = GetInkColor();
|
||||
if(pass == 0) {
|
||||
button[i] = WithHotSpots(CairoImage(100, 100), DPI(4), DPI(4), 0, 0);
|
||||
text[i] = GetInkColor();
|
||||
}
|
||||
}
|
||||
s.ok = Gtk_Icon("gtk-ok", DPI(16));
|
||||
s.cancel = Gtk_Icon("gtk-cancel", DPI(16));
|
||||
s.exit = Gtk_Icon("gtk-quit", DPI(16));
|
||||
}
|
||||
|
||||
ChSynthetic(button, text);
|
||||
|
||||
{
|
||||
auto& s = ToolButton::StyleDefault().Write();
|
||||
s.look[CTRL_NORMAL] = Image();
|
||||
s.look[CTRL_HOT] = button[CTRL_HOT];
|
||||
s.look[CTRL_PRESSED] = button[CTRL_PRESSED];
|
||||
s.look[CTRL_DISABLED] = Image();
|
||||
s.look[CTRL_CHECKED] = button[CTRL_PRESSED];
|
||||
s.look[CTRL_HOTCHECKED] = button[CTRL_HOT];
|
||||
}
|
||||
}
|
||||
|
||||
auto DialogIcon = [](int i, const char *s) { CtrlImg::Set(i, Gtk_Icon(s, DPI(48))); };
|
||||
DialogIcon(CtrlImg::I_information, "gtk-dialog-info");
|
||||
DialogIcon(CtrlImg::I_question, "gtk-dialog-question");
|
||||
DialogIcon(CtrlImg::I_exclamation, "gtk-dialog-warning");
|
||||
DialogIcon(CtrlImg::I_error, "gtk-dialog-error");
|
||||
|
||||
YesButtonImage_Write(Gtk_Icon("gtk-yes", DPI(16)));
|
||||
NoButtonImage_Write(Gtk_Icon("gtk-no", DPI(16)));
|
||||
AbortButtonImage_Write(Gtk_Icon("gtk-stop", DPI(16)));
|
||||
RetryButtonImage_Write(Gtk_Icon("gtk-refresh", DPI(16)));
|
||||
|
||||
{
|
||||
ScrollBar::Style& s = ScrollBar::StyleDefault().Write();
|
||||
s.through = true;
|
||||
static GtkWidget *proto = (GtkWidget *)gtk_scrollbar_new(GTK_ORIENTATION_HORIZONTAL, NULL); // to get style params
|
||||
gboolean stepper;
|
||||
gint minslider;
|
||||
gtk_widget_style_get(proto, "has-backward-stepper", &stepper, "min-slider-length", &minslider, NULL);
|
||||
if(!stepper)
|
||||
s.arrowsize = 0;
|
||||
Gtk_New("scrollbar.horizontal.bottom");
|
||||
Size sz = GtkSize();
|
||||
Gtk_New("scrollbar.horizontal.bottom contents");
|
||||
GtkSize(sz);
|
||||
Gtk_New("scrollbar.horizontal.bottom contents trough");
|
||||
GtkSize(sz);
|
||||
Gtk_New("scrollbar.horizontal.bottom contents trough slider");
|
||||
GtkSize(sz);
|
||||
|
||||
s.barsize = s.thumbwidth = DPI(sz.cy);
|
||||
s.thumbmin = max(minslider, s.barsize);
|
||||
|
||||
sz.cx = 2 * sz.cy;
|
||||
|
||||
for(int status = CTRL_NORMAL; status <= CTRL_DISABLED; status++) {
|
||||
Gtk_New("scrollbar.horizontal.bottom", status);
|
||||
Image m = CairoImage(sz.cx, sz.cy);
|
||||
Gtk_New("scrollbar.horizontal.bottom contents", status);
|
||||
Over(m, CairoImage(sz.cx, sz.cy));
|
||||
Gtk_New("scrollbar.horizontal.bottom contents trough", status);
|
||||
Over(m, CairoImage(sz.cx, sz.cy));
|
||||
s.hupper[status] = s.hlower[status] = ChHot(m);
|
||||
s.vupper[status] = s.vlower[status] = ChHot(RotateAntiClockwise(m)); // we have problems getting this right for vertical
|
||||
Gtk_New("scrollbar.horizontal.bottom contents trough slider", status);
|
||||
s.hthumb[status] = ChHot(CairoImage(sz.cx, sz.cy));
|
||||
|
||||
Gtk_New("scrollbar.vertical.right contents trough slider", status);
|
||||
GtkSize(sz);
|
||||
s.vthumb[status] = ChHot(CairoImage(sz.cy, sz.cx));
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
MenuBar::Style& s = MenuBar::StyleDefault().Write();
|
||||
s.pullshift.y = 0;
|
||||
|
||||
Gtk_New("menu");
|
||||
Image m = CairoImage(32, 32);
|
||||
s.pullshift.y = 0;
|
||||
int mg = DPI(2);
|
||||
s.popupframe = WithHotSpot(m, mg, mg);
|
||||
Size sz = m.GetSize();
|
||||
s.popupbody = Crop(m, mg, mg, sz.cx - 2 * mg, sz.cy - 2 * mg);
|
||||
s.leftgap = DPI(16) + Zx(6);
|
||||
SColorMenu_Write(GetBackgroundColor());
|
||||
SColorMenuText_Write(s.menutext);
|
||||
|
||||
Gtk_New("menu menuitem");
|
||||
s.menutext = GetInkColor();
|
||||
Gtk_State(CTRL_HOT);
|
||||
s.itemtext = GetInkColor();
|
||||
Color c = AvgColor(m);
|
||||
if(Diff(c, s.menutext) < 100) // menutext color too close to background color, fix it
|
||||
s.menutext = IsDark(c) ? White() : Black();
|
||||
s.item = Hot3(CairoImage(32, 16));
|
||||
|
||||
Gtk_New("menubar");
|
||||
s.look = Hot3(CairoImage(32, 16));
|
||||
Color dk = SColorText();
|
||||
Color wh = SColorPaper();
|
||||
if(IsDark(wh))
|
||||
Swap(dk, wh);
|
||||
s.topitemtext[0] = IsDark(AvgColor(sCurrentImage)) ? wh : dk;
|
||||
s.topitem[1] = s.topitem[0] = Null;
|
||||
s.topitemtext[1] = s.topitemtext[0];
|
||||
Gtk_New("menubar menuitem", CTRL_HOT);
|
||||
s.topitem[0] = Null;
|
||||
s.topitem[2] = Hot3(CairoImage(32, 16));
|
||||
s.topitemtext[2] = GetInkColor();
|
||||
}
|
||||
|
||||
Gtk_Free();
|
||||
}
|
||||
|
||||
Image GtkThemeIcon(const char *name, int rsz)
|
||||
{
|
||||
return Gtk_Icon(name, rsz);
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
Image Gtk_Icon(const char *icon_name, int size)
|
||||
{
|
||||
GdkPixbuf *pixbuf = gtk_icon_theme_load_icon(gtk_icon_theme_get_default(), icon_name,
|
||||
size, (GtkIconLookupFlags)0, NULL);
|
||||
if(pixbuf) {
|
||||
int cx = gdk_pixbuf_get_width(pixbuf);
|
||||
int cy = gdk_pixbuf_get_height(pixbuf);
|
||||
|
||||
Image m = CairoImage(cx, cy, [&](cairo_t *cr) {
|
||||
gdk_cairo_set_source_pixbuf(cr, pixbuf, 0, 0);
|
||||
cairo_paint(cr);
|
||||
});
|
||||
|
||||
Size sz = m.GetSize();
|
||||
|
||||
g_object_unref(pixbuf);
|
||||
|
||||
return sz.cy > size && sz.cy ? Rescale(m, sz.cx * size / sz.cy, size) : m;
|
||||
}
|
||||
return Null;
|
||||
}
|
||||
|
||||
Image GtkThemeIcon(const char *name, int rsz)
|
||||
{
|
||||
return Gtk_Icon(name, rsz);
|
||||
}
|
||||
|
||||
void ChHostSkin()
|
||||
{
|
||||
SetupFont();
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
@ -25,26 +25,6 @@ s_colors[] = {
|
|||
{ "Yellow", &Yellow },
|
||||
{ "WhiteGray", &WhiteGray },
|
||||
{ "White", &White },
|
||||
|
||||
//deprecated: (TODO)
|
||||
{ "SBlack", &Black },
|
||||
{ "SRed", &Red },
|
||||
{ "SGreen", &Green },
|
||||
{ "SBrown", &Brown },
|
||||
{ "SBlue", &Blue },
|
||||
{ "SMagenta", &Magenta },
|
||||
{ "SCyan", &Cyan },
|
||||
{ "SGray", &Gray },
|
||||
{ "SLtGray", &LtGray },
|
||||
{ "SLtRed", &LtRed },
|
||||
{ "SLtGreen", &LtGreen },
|
||||
{ "SLtYellow", &LtYellow },
|
||||
{ "SLtBlue", &LtBlue },
|
||||
{ "SLtMagenta", &LtMagenta },
|
||||
{ "SLtCyan", &LtCyan },
|
||||
{ "SYellow", &Yellow },
|
||||
{ "SWhiteGray", &WhiteGray },
|
||||
{ "SWhite", &White },
|
||||
};
|
||||
|
||||
Color ColorPopUp::hint[18];
|
||||
|
|
@ -102,16 +82,14 @@ ColorPopUp::~ColorPopUp() {}
|
|||
|
||||
int ColorPopUp::GetColorCount() const
|
||||
{
|
||||
return 18 + scolors * 18 + 2 * 18 + hints * 18 + 216;
|
||||
return 18 + 2 * 18 + hints * 18 + 216;
|
||||
}
|
||||
|
||||
Color ColorPopUp::GetColor(int i) const
|
||||
{
|
||||
if(!scolors)
|
||||
i += 18;
|
||||
if(i < 36)
|
||||
if(i < 18)
|
||||
return *s_colors[i].color;
|
||||
i -= 36;
|
||||
i -= 18;
|
||||
if(i < 18)
|
||||
return GrayColor(255 * (i + 1) / 20);
|
||||
if(hints) {
|
||||
|
|
@ -151,7 +129,7 @@ void ColorPopUp::Paint(Draw& w)
|
|||
Size sz = GetSize();
|
||||
int cy = GetCy();
|
||||
|
||||
w.DrawRect(sz, SColorMenu);
|
||||
w.DrawRect(sz, SColorFace());
|
||||
|
||||
int y = DPI(1);
|
||||
|
||||
|
|
@ -207,8 +185,6 @@ void ColorPopUp::Paint(Draw& w)
|
|||
}
|
||||
|
||||
DrawFilledFrame(w, x + DPI(1), y, DPI(14), DPI(14), SColorText, GetColor(i));
|
||||
if(i < 18 && scolors)
|
||||
DrawFrame(w, x + DPI(2), y + DPI(1), DPI(12), DPI(12), Blend(SColorLight, SColorHighlight));
|
||||
|
||||
if(i == colori) {
|
||||
if(GetMouseLeft())
|
||||
|
|
@ -397,7 +373,6 @@ ColorPopUp::ColorPopUp()
|
|||
norampwheel = false;
|
||||
notnull = false;
|
||||
withvoid = false;
|
||||
scolors = false;
|
||||
animating = false;
|
||||
hints = false;
|
||||
open = false;
|
||||
|
|
|
|||
|
|
@ -564,49 +564,49 @@ IMAGE_DATA(204,38,207,3,248,145,157,129,252,170,242,23,98,212,3,155,0,0,0,0,0,0,
|
|||
IMAGE_END_DATA(1088, 24)
|
||||
|
||||
IMAGE_BEGIN_DATA
|
||||
IMAGE_DATA(120,156,237,89,127,76,148,101,28,63,214,218,250,163,77,182,230,90,70,118,215,106,108,55,87,76,87,203,149,113,148,72)
|
||||
IMAGE_DATA(145,169,129,231,36,148,80,193,77,16,2,65,249,33,114,199,240,204,132,53,45,64,64,129,27,72,208,9,74,136,64,191)
|
||||
IMAGE_DATA(140,12,52,202,22,135,168,152,53,12,21,144,129,153,6,136,202,251,233,158,247,120,239,222,247,238,121,239,184,67,59,215)
|
||||
IMAGE_DATA(222,231,221,119,207,189,239,243,124,190,159,207,231,251,60,239,115,55,144,121,203,188,101,208,200,238,101,195,100,168,221,197)
|
||||
IMAGE_DATA(27,12,6,46,135,59,121,64,90,75,75,11,180,90,45,84,42,149,171,121,88,188,9,1,249,63,114,104,207,104,93,205)
|
||||
IMAGE_DATA(99,193,115,151,139,121,236,240,46,230,17,197,115,151,106,80,101,169,143,204,90,103,167,248,153,87,103,66,109,80,67,173)
|
||||
IMAGE_DATA(86,59,90,31,59,60,31,167,84,42,167,236,223,69,156,0,79,188,185,136,179,224,109,234,226,242,254,115,19,231,249,54)
|
||||
IMAGE_DATA(189,195,64,105,50,76,10,167,116,195,56,135,229,66,44,7,127,30,127,14,185,215,64,216,211,154,22,122,253,81,54,232)
|
||||
IMAGE_DATA(115,196,112,102,110,149,42,159,197,146,151,135,124,182,215,233,8,79,94,92,3,139,35,120,161,6,103,250,205,220,4,207)
|
||||
IMAGE_DATA(121,16,106,112,86,63,43,55,151,203,94,131,216,250,9,185,249,117,20,175,131,24,183,213,35,93,131,227,154,139,133,184)
|
||||
IMAGE_DATA(6,51,183,92,190,11,194,250,104,45,58,196,53,88,235,68,207,111,29,167,207,49,115,155,15,90,3,37,191,117,156,62)
|
||||
IMAGE_DATA(71,99,167,85,136,183,29,167,205,113,191,121,147,195,192,221,230,231,231,231,79,76,145,222,93,44,23,226,57,252,53,86)
|
||||
IMAGE_DATA(227,254,150,99,139,182,65,232,120,45,114,115,15,33,53,181,154,186,1,197,113,164,153,23,127,231,206,90,52,55,127,75)
|
||||
IMAGE_DATA(221,32,142,241,90,36,36,84,178,56,130,175,174,110,182,104,112,174,95,169,94,182,172,152,197,19,12,193,242,53,56,175)
|
||||
IMAGE_DATA(159,153,155,228,224,124,216,106,16,95,63,33,183,76,38,247,167,105,112,230,219,204,109,127,24,240,53,136,213,252,126,31)
|
||||
IMAGE_DATA(6,116,13,211,63,12,34,35,245,236,24,233,105,135,1,55,78,159,227,217,195,192,217,47,3,117,88,88,24,104,33,115)
|
||||
IMAGE_DATA(252,51,136,197,45,85,7,162,173,171,22,195,232,16,4,121,70,198,68,242,168,249,184,33,24,237,240,220,51,46,15,63)
|
||||
IMAGE_DATA(7,201,201,231,44,53,228,112,115,216,32,159,201,51,190,150,73,29,22,110,243,152,145,13,91,15,28,167,117,78,135,69)
|
||||
IMAGE_DATA(131,144,219,72,237,105,120,78,3,9,62,183,48,204,94,222,92,162,226,233,183,142,77,5,47,244,98,116,1,79,211,237)
|
||||
IMAGE_DATA(26,94,156,91,136,23,211,71,214,206,145,54,110,47,209,52,14,217,244,52,109,220,30,18,211,96,230,119,200,77,221,191)
|
||||
IMAGE_DATA(214,176,221,15,244,253,123,15,222,31,247,223,95,185,204,139,127,11,143,246,94,38,57,15,140,24,185,141,24,128,253,238)
|
||||
IMAGE_DATA(246,72,239,73,238,201,130,72,254,37,255,146,127,201,191,228,95,242,47,249,151,252,75,254,37,255,146,127,201,191,228,95)
|
||||
IMAGE_DATA(242,255,255,247,255,144,233,114,208,96,247,196,17,224,98,72,136,83,0,249,75,205,16,175,39,128,83,147,247,39,216,222)
|
||||
IMAGE_DATA(22,48,153,149,237,185,224,63,111,241,146,61,102,153,173,8,45,130,34,116,159,41,74,161,88,94,14,197,138,42,40,194)
|
||||
IMAGE_DATA(106,161,88,213,0,69,228,55,80,68,183,225,233,216,95,241,212,166,223,224,147,122,5,62,25,215,224,147,57,2,31,205)
|
||||
IMAGE_DATA(109,83,76,152,2,150,144,61,34,123,212,81,113,238,119,179,175,165,112,12,34,115,64,9,71,99,98,121,30,172,230,225)
|
||||
IMAGE_DATA(197,112,167,77,165,216,83,89,136,169,44,210,127,186,128,199,167,243,127,215,7,173,49,169,201,96,99,203,38,76,36,198)
|
||||
IMAGE_DATA(227,238,198,24,164,124,54,136,228,3,3,136,215,15,32,182,164,15,209,69,151,17,145,223,139,160,249,222,161,221,149,43)
|
||||
IMAGE_DATA(113,225,11,29,58,74,22,97,241,75,51,34,88,236,215,205,96,190,108,4,211,120,4,204,145,58,4,110,239,193,39,77)
|
||||
IMAGE_DATA(67,72,173,236,67,82,121,31,116,181,87,17,181,163,0,253,199,82,112,189,179,1,184,121,5,127,117,214,224,168,38,96)
|
||||
IMAGE_DATA(96,34,41,1,76,83,3,24,93,22,152,172,12,48,135,107,48,127,235,121,236,170,31,68,124,217,101,196,236,191,132,178)
|
||||
IMAGE_DATA(154,74,92,237,212,98,252,82,61,250,91,114,48,122,250,16,238,94,108,197,169,226,181,99,68,47,225,100,50,211,192,164)
|
||||
IMAGE_DATA(109,6,99,168,134,50,185,27,217,181,3,136,46,236,133,174,172,6,195,93,219,48,49,218,138,209,63,54,98,248,167,56)
|
||||
IMAGE_DATA(156,171,88,135,246,253,171,176,190,108,9,110,71,173,99,57,137,127,38,49,14,204,129,114,204,222,112,22,91,171,250,145)
|
||||
IMAGE_DATA(85,252,57,174,157,78,195,196,216,73,140,252,254,62,198,122,195,113,227,108,58,46,148,6,163,174,181,24,239,20,4,226)
|
||||
IMAGE_DATA(86,120,56,203,201,124,16,11,102,67,52,24,125,41,102,69,26,145,83,168,71,255,207,41,147,216,8,140,253,249,30,254)
|
||||
IMAGE_DATA(238,218,138,115,123,23,97,247,225,36,84,252,82,133,133,57,11,48,250,110,40,203,201,172,95,11,102,205,106,48,251,138)
|
||||
IMAGE_DATA(240,118,84,30,186,154,182,152,52,31,199,88,207,58,220,234,93,141,235,38,29,231,247,6,97,71,125,10,146,234,211,176)
|
||||
IMAGE_DATA(255,71,61,94,213,190,136,145,160,96,150,147,137,48,233,8,91,129,110,221,122,156,105,76,135,177,105,55,46,183,171,49)
|
||||
IMAGE_DATA(210,19,142,225,142,84,180,231,46,198,193,214,34,36,214,165,32,230,96,2,10,76,250,231,109,121,30,55,23,4,176,156)
|
||||
IMAGE_DATA(76,97,1,152,252,79,97,248,232,13,224,198,69,116,23,47,199,177,244,89,104,43,124,11,141,217,129,152,251,90,53,74)
|
||||
IMAGE_DATA(219,203,81,116,162,4,249,63,20,98,79,75,30,230,196,249,66,187,240,67,100,250,103,99,219,203,26,100,204,203,64,118)
|
||||
IMAGE_DATA(212,28,140,159,204,195,120,251,30,180,235,2,80,177,230,89,188,48,191,18,51,124,191,195,115,75,51,160,8,78,199,236)
|
||||
IMAGE_DATA(69,41,120,242,245,205,120,194,63,201,238,197,13,121,197,123,108,251,106,223,59,95,233,130,238,124,28,51,247,251,199,103)
|
||||
IMAGE_DATA(60,252,140,39,222,139,169,182,127,1,101,189,88,202,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0)
|
||||
IMAGE_DATA(120,156,237,89,123,76,83,87,28,190,102,89,178,63,150,72,178,152,101,46,49,221,178,133,164,49,155,209,108,25,217,28)
|
||||
IMAGE_DATA(101,19,216,156,83,167,235,50,134,48,148,71,34,10,131,161,188,68,169,193,58,39,102,209,77,16,24,143,6,100,178,10)
|
||||
IMAGE_DATA(202,80,129,109,153,99,14,117,168,75,0,121,63,228,253,28,108,62,38,232,148,251,173,231,150,219,222,219,158,219,210,162)
|
||||
IMAGE_DATA(43,89,238,185,249,229,244,222,115,190,223,247,125,191,115,238,105,3,140,27,227,198,32,153,121,144,13,211,161,118,22,175)
|
||||
IMAGE_DATA(215,235,249,28,206,228,1,105,85,85,85,208,104,52,80,169,84,142,230,225,240,6,4,20,127,43,160,105,212,56,154,199)
|
||||
IMAGE_DATA(132,231,47,7,243,88,225,29,204,35,137,231,47,213,168,202,84,31,198,92,103,187,248,5,35,11,160,214,171,161,86,171)
|
||||
IMAGE_DATA(109,173,143,21,94,136,83,42,149,51,246,239,32,78,132,39,222,28,196,153,240,22,117,113,120,255,57,137,115,125,155,221)
|
||||
IMAGE_DATA(97,160,52,24,38,133,83,58,97,156,199,242,33,149,67,56,79,56,135,220,39,67,220,211,154,6,58,221,25,46,232,115)
|
||||
IMAGE_DATA(164,112,70,110,149,42,141,195,146,151,135,124,182,214,105,11,79,94,92,61,135,35,120,177,6,123,250,141,220,4,207,123)
|
||||
IMAGE_DATA(16,107,176,87,63,51,55,159,203,90,131,212,250,137,185,133,117,148,174,131,20,183,217,35,93,131,237,154,75,133,180,6)
|
||||
IMAGE_DATA(35,183,66,177,31,226,250,104,76,58,164,53,152,235,68,207,111,30,167,207,49,114,27,15,90,61,37,191,121,156,62,39)
|
||||
IMAGE_DATA(217,74,171,24,111,57,78,155,227,124,115,35,135,129,179,109,201,146,37,158,196,20,233,157,197,242,33,157,195,51,217,108)
|
||||
IMAGE_DATA(220,211,116,108,209,54,8,29,175,193,129,3,39,16,31,95,68,221,128,210,56,210,140,139,191,111,95,9,42,43,127,162)
|
||||
IMAGE_DATA(110,16,219,120,13,162,162,10,57,28,193,23,21,85,154,52,216,215,175,84,175,93,155,197,225,9,134,96,133,26,236,215)
|
||||
IMAGE_DATA(207,200,77,114,240,62,44,53,72,175,159,152,155,97,20,158,52,13,246,124,27,185,173,15,3,161,6,169,154,63,236,195)
|
||||
IMAGE_DATA(128,174,97,246,135,65,80,144,142,27,35,61,237,48,224,199,233,115,92,123,24,216,251,101,160,246,243,243,3,45,24,219)
|
||||
IMAGE_DATA(63,131,56,220,26,181,55,206,55,148,96,28,181,162,32,207,200,152,68,30,181,16,55,134,58,43,60,255,140,207,35,204)
|
||||
IMAGE_DATA(65,114,10,57,115,245,169,252,28,46,200,103,242,76,168,101,90,135,137,219,56,86,199,133,165,7,158,211,60,167,214,164)
|
||||
IMAGE_DATA(65,204,93,71,237,105,120,94,3,9,33,183,56,140,94,222,90,173,18,232,55,143,205,4,47,246,82,231,0,158,166,219)
|
||||
IMAGE_DATA(49,188,52,183,24,47,165,143,172,157,45,109,252,94,162,105,28,179,232,105,218,248,61,36,165,193,200,111,147,155,186,127)
|
||||
IMAGE_DATA(205,97,185,31,232,251,247,1,188,63,206,191,191,10,102,158,240,22,46,237,231,25,228,204,25,49,10,11,49,0,247,221)
|
||||
IMAGE_DATA(237,146,222,149,220,211,5,145,253,203,254,101,255,178,127,217,191,236,95,246,47,251,151,253,203,254,101,255,178,127,217,191)
|
||||
IMAGE_DATA(236,255,255,239,255,17,195,101,163,193,234,137,45,64,247,186,117,118,1,228,47,53,99,130,158,0,174,76,223,95,224,122)
|
||||
IMAGE_DATA(75,192,116,86,174,231,67,248,156,153,199,60,97,154,125,227,198,4,174,54,180,161,161,177,29,141,77,29,104,106,238,68)
|
||||
IMAGE_DATA(115,235,53,180,182,117,163,173,189,7,237,29,189,232,184,214,135,206,174,126,92,235,30,64,119,207,16,122,250,134,209,219)
|
||||
IMAGE_DATA(63,130,190,129,81,244,15,254,129,129,161,49,92,186,92,11,230,49,230,113,91,197,121,216,205,186,150,226,49,72,204,1)
|
||||
IMAGE_DATA(37,108,141,73,229,153,91,205,197,139,225,76,155,73,177,103,178,16,51,89,164,255,116,1,207,205,230,255,174,115,173,177)
|
||||
IMAGE_DATA(241,219,192,69,236,167,152,138,142,196,253,173,225,136,251,102,20,219,142,14,35,82,55,140,45,57,131,8,205,236,71,96)
|
||||
IMAGE_DATA(90,47,124,61,220,214,183,20,126,136,246,239,180,168,205,241,193,170,151,231,7,114,216,31,43,193,126,95,14,182,252,20)
|
||||
IMAGE_DATA(216,83,165,240,222,211,133,47,43,198,16,95,56,136,152,252,65,104,75,70,16,178,55,29,67,103,227,112,189,254,52,112)
|
||||
IMAGE_DATA(107,0,127,213,23,227,76,178,215,240,84,76,20,216,138,211,96,181,187,193,238,78,2,123,178,24,30,59,90,177,191,108)
|
||||
IMAGE_DATA(20,145,121,253,8,207,238,67,94,113,33,70,234,53,184,219,87,134,161,170,84,76,92,61,129,251,221,213,184,146,181,105)
|
||||
IMAGE_DATA(146,232,37,156,236,174,4,176,9,219,193,234,139,160,220,214,130,148,146,97,132,102,244,66,155,87,140,241,134,157,152,154)
|
||||
IMAGE_DATA(168,198,68,231,86,140,95,138,64,115,65,48,106,178,55,32,44,111,53,254,9,9,230,56,137,127,54,58,2,236,209,124)
|
||||
IMAGE_DATA(44,218,220,132,29,199,134,176,59,235,91,252,121,53,1,83,147,23,113,187,227,99,76,246,250,227,102,83,34,218,115,87)
|
||||
IMAGE_DATA(162,180,58,11,239,166,123,227,142,191,63,199,201,126,178,5,236,230,80,176,186,92,44,12,170,67,106,134,14,67,151,227)
|
||||
IMAGE_DATA(166,177,129,152,236,249,8,55,26,118,160,249,136,15,14,158,140,65,193,239,199,176,34,117,57,38,222,91,207,113,178,97)
|
||||
IMAGE_DATA(155,192,110,12,0,251,117,38,222,9,57,140,134,138,88,131,230,115,152,236,10,198,157,222,0,92,55,232,104,61,226,139)
|
||||
IMAGE_DATA(189,101,113,136,41,75,64,246,111,58,188,166,121,9,183,125,87,114,156,108,160,65,135,223,7,104,209,134,161,177,60,17)
|
||||
IMAGE_DATA(117,21,7,209,95,163,198,237,46,127,140,215,198,163,230,192,42,28,175,206,68,116,105,28,194,143,71,33,221,160,127,89)
|
||||
IMAGE_DATA(236,11,184,181,220,139,227,100,51,210,193,166,125,5,253,231,111,2,55,187,209,146,245,62,206,38,46,196,249,140,183,81)
|
||||
IMAGE_DATA(158,226,141,165,175,23,33,183,38,31,153,23,114,144,246,107,6,14,85,29,198,226,8,119,104,86,124,134,93,158,41,216)
|
||||
IMAGE_DATA(249,74,50,146,150,37,33,37,100,49,238,94,60,140,187,53,135,80,163,245,66,193,198,231,240,162,71,33,230,187,255,140)
|
||||
IMAGE_DATA(231,215,36,225,153,149,137,88,228,19,135,167,223,216,142,167,60,99,172,94,220,117,175,186,77,238,9,112,191,247,131,214)
|
||||
IMAGE_DATA(247,222,23,225,75,127,121,114,254,163,207,186,226,189,152,105,251,23,36,79,112,33,0,0,0,0,0,0,0,0,0,0)
|
||||
IMAGE_END_DATA(1440, 15)
|
||||
|
|
|
|||
|
|
@ -2,7 +2,6 @@
|
|||
#define CTRLLIB_H
|
||||
|
||||
#include <CtrlCore/CtrlCore.h>
|
||||
#include <Painter/Painter.h>
|
||||
|
||||
#ifdef Status //X11 defines this, likely name clash...
|
||||
#undef Status
|
||||
|
|
|
|||
|
|
@ -116,6 +116,7 @@ file
|
|||
ChGtk.h,
|
||||
ChGtk0.cpp,
|
||||
ChGtk.cpp,
|
||||
ChGtk3.cpp,
|
||||
ChCocoMM.h,
|
||||
ChCocoMM.mm,
|
||||
ChCoco.h,
|
||||
|
|
|
|||
|
|
@ -165,7 +165,6 @@ private:
|
|||
|
||||
int colori;
|
||||
bool notnull;
|
||||
bool scolors;
|
||||
bool norampwheel;
|
||||
bool animating;
|
||||
bool hints;
|
||||
|
|
@ -196,7 +195,6 @@ public:
|
|||
Color Get() const;
|
||||
|
||||
ColorPopUp& NotNull(bool b = true) { notnull = b; return *this; }
|
||||
ColorPopUp& SColors(bool b = true) { scolors = b; return *this; }//Deprecated
|
||||
ColorPopUp& NullText(const char *s) { nulltext = s; Refresh(); return *this; }
|
||||
ColorPopUp& WithVoid(bool b = true) { withvoid = b; Refresh(); return *this; }
|
||||
ColorPopUp& VoidText(const char *s) { voidtext = s; Refresh(); return *this; }
|
||||
|
|
@ -239,7 +237,6 @@ public:
|
|||
ColorPusher& NotNull(bool b = true) { colors.NotNull(b); return *this; }
|
||||
ColorPusher& WithVoid(bool b = true) { colors.WithVoid(b); return *this; }
|
||||
ColorPusher& VoidText(const char *s) { voidtext = s; colors.VoidText(s); Refresh(); return *this; }
|
||||
ColorPusher& SColors(bool b = true) { colors.SColors(b); return *this; }
|
||||
ColorPusher& WithText() { withtext = true; Refresh(); return *this; }
|
||||
ColorPusher& WithHex() { withhex = true; Refresh(); return *this; }
|
||||
ColorPusher& Track(bool b = true) { track = b; return *this; }
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@ DropChoice::DropChoice() {
|
|||
AddButton().Main() <<= THISBACK(Drop);
|
||||
NoDisplay();
|
||||
list.Normal();
|
||||
list.WhenSelect = callback(this, &DropChoice::Select);
|
||||
list.WhenSelect = [=] { Select(); };
|
||||
dropfocus = true;
|
||||
EnableDrop(false);
|
||||
dropwidth = 0;
|
||||
|
|
|
|||
|
|
@ -110,7 +110,7 @@ void ActiveEdgeFrame::FramePaint(Draw& w, const Rect& r)
|
|||
{
|
||||
int i = 0;
|
||||
if(ctrl) {
|
||||
i = !ctrl->IsEnabled() ? CTRL_DISABLED
|
||||
i = !ctrl->IsEnabled() || ctrl->IsReadOnly() ? CTRL_DISABLED
|
||||
: ctrl->HasFocus() ? CTRL_PRESSED
|
||||
: mousein ? CTRL_HOT
|
||||
: CTRL_NORMAL;
|
||||
|
|
|
|||
|
|
@ -182,8 +182,8 @@ void MenuItemBase::PaintTopItem(Draw& w, int state) {
|
|||
w.DrawRect(0, 0, sz.cx, sz.cy, bg);
|
||||
Color txt = opaque ? style->topitemtext[0] : GetLabelTextColor(this);
|
||||
Color hltxt = opaque2 ? style->topitemtext[state] : GetLabelTextColor(this);
|
||||
if(!opaque && state != PUSH && style->opaquetest) { // Fix issues when text color is not compatible with transparent background (e.g. Ubuntu Ambience)]
|
||||
Color c = state == 2 ? SColorHighlight() : bg;
|
||||
if(!opaque && state != 2 && style->opaquetest) { // Fix issues when text color is not compatible with transparent background (e.g. Ubuntu Ambience)]
|
||||
Color c = state == 1 && !IsNull(style->topitem[0]) ? SColorHighlight() : bg;
|
||||
int g = Grayscale(c);
|
||||
bool dark = IsDark(c);
|
||||
if(abs(g - Grayscale(txt)) < 70)
|
||||
|
|
|
|||
|
|
@ -282,7 +282,7 @@ int MultiButton::ChState(int i)
|
|||
if(i == MAIN && frm && style->activeedge) {
|
||||
int q = 0;
|
||||
if(p)
|
||||
q = !p->IsEnabled() || !IsEnabled() || IsReadOnly() || i >= 0 && !button[i].enabled ? CTRL_DISABLED
|
||||
q = !p->IsEnabled() || !IsEnabled() || p->IsReadOnly() || i >= 0 && !button[i].enabled ? CTRL_DISABLED
|
||||
: p->HasFocus() || push ? CTRL_PRESSED
|
||||
: p->HasMouse() || hl >= 0 ? CTRL_HOT
|
||||
: CTRL_NORMAL;
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ CH_STYLE(ProgressIndicator, Style, StyleDefault)
|
|||
vlook = CtrlsImg::VPI();
|
||||
vchunk = CtrlsImg::VPIC();
|
||||
bound = false;
|
||||
nomargins = false;
|
||||
}
|
||||
|
||||
Size ProgressIndicator::GetMsz()
|
||||
|
|
@ -74,6 +75,8 @@ void ProgressIndicator::Paint(Draw& w) {
|
|||
if(sz.cy > sz.cx) {
|
||||
ChPaint(w, sz, style->vlook);
|
||||
Rect r = ChMargins(style->vlook);
|
||||
if(style->nomargins)
|
||||
r.left = r.right = r.top = r.bottom = 0;
|
||||
w.Clip(r.left, r.top, sz.cx - r.left - r.right, sz.cy - r.top - r.bottom);
|
||||
ChPaint(w, r.left, sz.cy - r.bottom - p - p0, sz.cx - r.left - r.right, p,
|
||||
style->vchunk);
|
||||
|
|
@ -81,6 +84,8 @@ void ProgressIndicator::Paint(Draw& w) {
|
|||
else {
|
||||
ChPaint(w, sz, style->hlook);
|
||||
Rect r = ChMargins(style->hlook);
|
||||
if(style->nomargins)
|
||||
r.left = r.right = r.top = r.bottom = 0;
|
||||
w.Clip(r.left, r.top, sz.cx - r.left - r.right, sz.cy - r.top - r.bottom);
|
||||
ChPaint(w, r.left + p0, r.top, p, sz.cy - r.top - r.bottom, style->hchunk);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -7,6 +7,7 @@ public:
|
|||
struct Style : ChStyle<Style> {
|
||||
bool classic;
|
||||
bool bound;
|
||||
bool nomargins;
|
||||
Value vlook, vchunk, hlook, hchunk;
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -111,6 +111,8 @@ Rect LabelBox::GetVoidRect() const
|
|||
return r;
|
||||
}
|
||||
|
||||
Value LabelBox::LabelBoxLook;
|
||||
|
||||
void PaintLabelBox(Draw& w, Size sz, Color color, int d)
|
||||
{
|
||||
bool hline = sz.cy < 2 * Draw::GetStdFontCy();
|
||||
|
|
@ -130,23 +132,31 @@ void PaintLabelBox(Draw& w, Size sz, Color color, int d)
|
|||
w.DrawRect(d + 1, 0, 1, sz.cy, SColorLight);
|
||||
}
|
||||
else {
|
||||
Color c = Nvl(color, LabelBoxColor);
|
||||
w.DrawRect(0, d + 2, 1, sz.cy - d - 4, c);
|
||||
w.DrawRect(sz.cx - 1, d + 2, 1, sz.cy - d - 4, c);
|
||||
w.DrawRect(2, sz.cy - 1, sz.cx - 4, 1, c);
|
||||
w.DrawRect(2, d, sz.cx - 4, 1, c);
|
||||
|
||||
w.DrawRect(1, d + 1, 2, 1, c);
|
||||
w.DrawRect(1, d + 2, 1, 1, c);
|
||||
|
||||
w.DrawRect(sz.cx - 3, d + 1, 2, 1, c);
|
||||
w.DrawRect(sz.cx - 2, d + 2, 1, 1, c);
|
||||
|
||||
w.DrawRect(1, sz.cy - 2, 2, 1, c);
|
||||
w.DrawRect(1, sz.cy - 3, 1, 1, c);
|
||||
|
||||
w.DrawRect(sz.cx - 3, sz.cy - 2, 2, 1, c);
|
||||
w.DrawRect(sz.cx - 2, sz.cy - 3, 1, 1, c);
|
||||
Value look = LabelBox::GetLook();
|
||||
if(IsNull(look) || !IsNull(color)) {
|
||||
Color c = Nvl(color, LabelBoxColor);
|
||||
w.DrawRect(0, d + 2, 1, sz.cy - d - 4, c);
|
||||
w.DrawRect(sz.cx - 1, d + 2, 1, sz.cy - d - 4, c);
|
||||
w.DrawRect(2, sz.cy - 1, sz.cx - 4, 1, c);
|
||||
w.DrawRect(2, d, sz.cx - 4, 1, c);
|
||||
|
||||
w.DrawRect(1, d + 1, 2, 1, c);
|
||||
w.DrawRect(1, d + 2, 1, 1, c);
|
||||
|
||||
w.DrawRect(sz.cx - 3, d + 1, 2, 1, c);
|
||||
w.DrawRect(sz.cx - 2, d + 2, 1, 1, c);
|
||||
|
||||
w.DrawRect(1, sz.cy - 2, 2, 1, c);
|
||||
w.DrawRect(1, sz.cy - 3, 1, 1, c);
|
||||
|
||||
w.DrawRect(sz.cx - 3, sz.cy - 2, 2, 1, c);
|
||||
w.DrawRect(sz.cx - 2, sz.cy - 3, 1, 1, c);
|
||||
}
|
||||
else {
|
||||
Rect r = sz;
|
||||
r.top = d;
|
||||
ChPaintEdge(w, r, look);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
|
|
|||
|
|
@ -41,10 +41,16 @@ public:
|
|||
virtual void AssignAccessKeys(dword used);
|
||||
virtual Rect GetVoidRect() const;
|
||||
|
||||
|
||||
Color color;
|
||||
|
||||
static Value LabelBoxLook;
|
||||
|
||||
public:
|
||||
LabelBox& SetColor(Color c) { color = c; return *this; }
|
||||
static void SetLook(const Value& v) { LabelBoxLook = v; }
|
||||
static Value GetLook() { return LabelBoxLook; }
|
||||
|
||||
LabelBox& SetColor(Color c) { color = c; return *this; }
|
||||
|
||||
LabelBox();
|
||||
virtual ~LabelBox();
|
||||
|
|
|
|||
|
|
@ -185,7 +185,7 @@ struct ColorProperty : public EditorProperty<ColorPusher> {
|
|||
|
||||
ColorProperty() {
|
||||
Add(editor.HSizePosZ(100, 2).TopPos(2));
|
||||
editor.WithText().SColors().NullText("Null").Track();
|
||||
editor.WithText().NullText("Null").Track();
|
||||
}
|
||||
|
||||
static ItemProperty *Create() { return new ColorProperty; }
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue