diff --git a/uppsrc/CtrlCore/CtrlCore.h b/uppsrc/CtrlCore/CtrlCore.h index 7443895cf..fdb35720e 100644 --- a/uppsrc/CtrlCore/CtrlCore.h +++ b/uppsrc/CtrlCore/CtrlCore.h @@ -580,8 +580,10 @@ private: static Callback CtrlCall; static bool DoCall(); - static bool PeekMsg(MSG& msg); +#ifdef PLATFORM_WIN32 + static bool PeekMsg(MSG& msg); +#endif // System window interface... void WndShow0(bool b); @@ -693,8 +695,6 @@ protected: friend void sSetCursor(Ctrl *ctrl, const Image& m); - typedef Ctrl CLASSNAME; - public: virtual void NcCreate(HWND hwnd); virtual void NcDestroy(); @@ -707,6 +707,8 @@ public: static Ctrl *CtrlFromHWND(HWND hwnd); #endif + typedef Ctrl CLASSNAME; + #ifdef PLATFORM_X11 protected: struct XWindow { diff --git a/uppsrc/CtrlCore/CtrlMt.cpp b/uppsrc/CtrlCore/CtrlMt.cpp index 94b4216e0..36442b738 100644 --- a/uppsrc/CtrlCore/CtrlMt.cpp +++ b/uppsrc/CtrlCore/CtrlMt.cpp @@ -1,192 +1,194 @@ -#include "CtrlCore.h" - -#define LLOG(x) // LOG(x) - -NAMESPACE_UPP - -#ifdef _MULTITHREADED - -static int NonMain; -static StaticMutex NonMainLock; - -void EnterGuiMutex() -{ - LLOG("Thread " << IsMainThread() << " trying to lock"); - bool nonmain = !IsMainThread(); - if(nonmain) - NonMainLock.Enter(); - EnterGMutex(); - if(nonmain) - NonMain++; - LLOG("Thread " << IsMainThread() << " LOCK"); -} - -void LeaveGuiMutex() -{ - LLOG("Thread " << IsMainThread() << " trying to unlock"); - bool nonmain = !IsMainThread(); - if(nonmain) - NonMain--; - LeaveGMutex(); - if(nonmain) - NonMainLock.Leave(); - LLOG("Thread " << IsMainThread() << " UNLOCK"); -} - -struct Ctrl::CallBox { - Semaphore sem; - Callback cb; -}; - -void Ctrl::PerformCall(Ctrl::CallBox *cbox) -{ - cbox->cb(); - LLOG("Sem release"); - cbox->sem.Release(); -} - -Callback Ctrl::CtrlCall; - -void WakeUpGuiThread(); - -bool Ctrl::DoCall() -{ - LLOG("DoCall"); - CtrlCall(); - CtrlCall.Clear(); - LLOG("--- DoCall, nonmain: " << NonMain); - return NonMain; -} - -void Ctrl::ICall(Callback cb) -{ - LLOG("Ctrl::Call " << IsMainThread() << ", nonmain: " << NonMain); - if(IsMainThread()) - cb(); - else { - CallBox cbox; - cbox.cb = cb; - CtrlCall = callback1(PerformCall, &cbox); - int level = LeaveGMutexAll(); - WakeUpGuiThread(); - LLOG("Waiting for semaphore"); - if(!Thread::IsShutdownThreads()) - cbox.sem.Wait(); - EnterGMutex(level); - } - LLOG("-- Ctrl::Call " << IsMainThread()); -} - -void Ctrl::Call(Callback cb) -{ - if(IsMainThread()) - cb(); - else { - CallBox cbox; - DLOG("EventLoop 1"); - cbox.cb = cb; - DLOG("EventLoop 2"); - UPP::PostCallback(callback1(PerformCall, &cbox)); - int n = NonMain; - int nn = n; - NonMain = 0; - for(int i = 0; i < n; i++) - NonMainLock.Leave(); - int level = LeaveGMutexAll(); - WakeUpGuiThread(); - if(!Thread::IsShutdownThreads()) - cbox.sem.Wait(); - for(int i = 0; i < n; i++) - NonMainLock.Enter(); - EnterGMutex(level); - NonMain = n; - } -} - -#else - -bool Ctrl::DoCall() -{ - return false; -} - -void Ctrl::ICall(Callback cb) -{ - cb(); -} - -void Ctrl::Call(Callback cb) -{ - cb(); -} -#endif - -void Ctrl::GuiSleep(int ms) -{ - Call(callback1(&Ctrl::GuiSleep0, ms)); -} - -void Ctrl::WndDestroy() -{ - ICall(callback(this, &Ctrl::WndDestroy0)); -} - -void Ctrl::WndCreateCaret(const Rect& cr) -{ - ICall(THISBACK1(WndCreateCaret0, cr)); -} - -void Ctrl::WndShow(bool b) -{ - ICall(THISBACK1(WndShow0, b)); -} - -void Ctrl::WndUpdate() -{ - ICall(THISBACK(WndUpdate0)); -} - -void Ctrl::SetWndForeground() -{ - ICall(THISBACK(SetWndForeground0)); -} - -bool Ctrl::WndEnable(bool b) -{ - ICall(THISBACK1(WndEnable0, &b)); - return b; -} - -bool Ctrl::SetWndFocus() -{ - bool b; - ICall(THISBACK1(SetWndFocus0, &b)); - return b; -} - -void Ctrl::WndInvalidateRect(const Rect& r) -{ - ICall(THISBACK1(WndInvalidateRect0, r)); -} - -void Ctrl::WndSetPos(const Rect& rect) -{ - ICall(THISBACK1(WndSetPos0, rect)); -} - -void Ctrl::WndUpdate(const Rect& r) -{ - ICall(THISBACK1(WndUpdate0r, r)); -} - -void Ctrl::WndScrollView(const Rect& r, int dx, int dy) -{ - ICall(THISBACK3(WndScrollView0, r, dx, dy)); -} - -void Ctrl::EventLoop(Ctrl *ctrl) -{ - Call(callback1(&Ctrl::EventLoop0, ctrl)); -} - -END_UPP_NAMESPACE +#include "CtrlCore.h" + +#define LLOG(x) // LOG(x) + +NAMESPACE_UPP + +#ifdef _MULTITHREADED + +static int NonMain; +static StaticMutex NonMainLock; + +void EnterGuiMutex() +{ + LLOG("Thread " << IsMainThread() << " trying to lock"); + bool nonmain = !IsMainThread(); + if(nonmain) + NonMainLock.Enter(); + EnterGMutex(); + if(nonmain) + NonMain++; + LLOG("Thread " << IsMainThread() << " LOCK"); +} + +void LeaveGuiMutex() +{ + LLOG("Thread " << IsMainThread() << " trying to unlock"); + bool nonmain = !IsMainThread(); + if(nonmain) + NonMain--; + LeaveGMutex(); + if(nonmain) + NonMainLock.Leave(); + LLOG("Thread " << IsMainThread() << " UNLOCK"); +} + +struct Ctrl::CallBox { + Semaphore sem; + Callback cb; +}; + +void Ctrl::PerformCall(Ctrl::CallBox *cbox) +{ + cbox->cb(); + LLOG("Sem release"); + cbox->sem.Release(); +} + +Callback Ctrl::CtrlCall; + +void WakeUpGuiThread(); + +bool Ctrl::DoCall() +{ + LLOG("DoCall"); + CtrlCall(); + CtrlCall.Clear(); + LLOG("--- DoCall, nonmain: " << NonMain); + return NonMain; +} + +void Ctrl::ICall(Callback cb) +{ + LLOG("Ctrl::Call " << IsMainThread() << ", nonmain: " << NonMain); + if(IsMainThread()) + cb(); + else { + CallBox cbox; + cbox.cb = cb; + CtrlCall = callback1(PerformCall, &cbox); + int level = LeaveGMutexAll(); + WakeUpGuiThread(); + LLOG("Waiting for semaphore"); + if(!Thread::IsShutdownThreads()) + cbox.sem.Wait(); + EnterGMutex(level); + } + LLOG("-- Ctrl::Call " << IsMainThread()); +} + +void Ctrl::Call(Callback cb) +{ + if(IsMainThread()) + cb(); + else { + CallBox cbox; + DLOG("EventLoop 1"); + cbox.cb = cb; + DLOG("EventLoop 2"); + UPP::PostCallback(callback1(PerformCall, &cbox)); + int n = NonMain; + int nn = n; + NonMain = 0; + for(int i = 0; i < n; i++) + NonMainLock.Leave(); + int level = LeaveGMutexAll(); + WakeUpGuiThread(); + if(!Thread::IsShutdownThreads()) + cbox.sem.Wait(); + for(int i = 0; i < n; i++) + NonMainLock.Enter(); + EnterGMutex(level); + NonMain = n; + } +} + +#else + +bool Ctrl::DoCall() +{ + return false; +} + +void Ctrl::ICall(Callback cb) +{ + cb(); +} + +void Ctrl::Call(Callback cb) +{ + cb(); +} +#endif + +void Ctrl::GuiSleep(int ms) +{ + Call(callback1(&Ctrl::GuiSleep0, ms)); +} + +void Ctrl::WndDestroy() +{ + ICall(callback(this, &Ctrl::WndDestroy0)); +} + +#ifdef PLATFORM_WIN32 +void Ctrl::WndCreateCaret(const Rect& cr) +{ + ICall(THISBACK1(WndCreateCaret0, cr)); +} +#endif + +void Ctrl::WndShow(bool b) +{ + ICall(THISBACK1(WndShow0, b)); +} + +void Ctrl::WndUpdate() +{ + ICall(THISBACK(WndUpdate0)); +} + +void Ctrl::SetWndForeground() +{ + ICall(THISBACK(SetWndForeground0)); +} + +bool Ctrl::WndEnable(bool b) +{ + ICall(THISBACK1(WndEnable0, &b)); + return b; +} + +bool Ctrl::SetWndFocus() +{ + bool b; + ICall(THISBACK1(SetWndFocus0, &b)); + return b; +} + +void Ctrl::WndInvalidateRect(const Rect& r) +{ + ICall(THISBACK1(WndInvalidateRect0, r)); +} + +void Ctrl::WndSetPos(const Rect& rect) +{ + ICall(THISBACK1(WndSetPos0, rect)); +} + +void Ctrl::WndUpdate(const Rect& r) +{ + ICall(THISBACK1(WndUpdate0r, r)); +} + +void Ctrl::WndScrollView(const Rect& r, int dx, int dy) +{ + ICall(THISBACK3(WndScrollView0, r, dx, dy)); +} + +void Ctrl::EventLoop(Ctrl *ctrl) +{ + Call(callback1(&Ctrl::EventLoop0, ctrl)); +} + +END_UPP_NAMESPACE diff --git a/uppsrc/CtrlCore/X11Wnd.cpp b/uppsrc/CtrlCore/X11Wnd.cpp index 0a69d6292..02cecdee8 100644 --- a/uppsrc/CtrlCore/X11Wnd.cpp +++ b/uppsrc/CtrlCore/X11Wnd.cpp @@ -70,7 +70,7 @@ void Ctrl::DoPaint(const Vector& invalid) } } -void Ctrl::WndScrollView(const Rect& r, int dx, int dy) +void Ctrl::WndScrollView0(const Rect& r, int dx, int dy) { GuiLock __; if(r.IsEmpty() || !GetWindow()) return; @@ -314,9 +314,12 @@ void Ctrl::GuiSleep0(int ms) timeout.tv_sec = ms / 1000; timeout.tv_usec = ms % 1000 * 1000; XFlush(Xdisplay); - int level = LeaveGuiMutexAll(); - select(Xconnection + 1, &fdset, NULL, NULL, &timeout); - PerformCall(); + do { + int level = LeaveGMutexAll(); + select(Xconnection + 1, &fdset, NULL, NULL, &timeout); + EnterGMutex(level); + } + while(DoCall()); } static int granularity = 10; @@ -350,9 +353,12 @@ void Ctrl::EventLoop0(Ctrl *ctrl) timeout.tv_sec = 0; timeout.tv_usec = 1000 * granularity; XFlush(Xdisplay); - int level = LeaveGuiMutexAll(); - select(Xconnection + 1, &fdset, NULL, NULL, &timeout); - PerformCall(); + do { + int level = LeaveGMutexAll(); + select(Xconnection + 1, &fdset, NULL, NULL, &timeout); + EnterGMutex(level); + } + while(DoCall()); // GuiSleep()(granularity); SyncMousePos(); while(IsWaitingEvent()) { @@ -606,7 +612,7 @@ Ctrl *Ctrl::GetOwner() return q >= 0 ? Xwindow()[q].owner : NULL; } -void Ctrl::WndShow(bool b) +void Ctrl::WndShow0(bool b) { GuiLock __; LLOG("WndShow " << b); @@ -624,7 +630,7 @@ void Ctrl::WndShow(bool b) } } -void Ctrl::WndUpdate() +void Ctrl::WndUpdate0() { GuiLock __; LTIMING("WndUpdate"); @@ -641,7 +647,7 @@ void Ctrl::WndUpdate() } } -void Ctrl::WndUpdate(const Rect& r) +void Ctrl::WndUpdate0r(const Rect& r) { GuiLock __; LTIMING("WndUpdate Rect"); @@ -657,7 +663,7 @@ void Ctrl::WndUpdate(const Rect& r) xw.invalid = Subtract(xw.invalid, r, dummy); } -void Ctrl::WndSetPos(const Rect& r) +void Ctrl::WndSetPos0(const Rect& r) { GuiLock __; if(!top) return; @@ -798,10 +804,11 @@ void Ctrl::KillFocus(Window window) w.ctrl->KillFocusWnd(); } -bool Ctrl::SetWndFocus() +void Ctrl::SetWndFocus0(bool *b) { GuiLock __; LLOG("SetWndFocus " << Name()); + *b = false; if(top && top->window != focusWindow && IsEnabled() && IsVisible()) { LLOG("Setting focus... "); LTIMING("XSetInfputFocus"); @@ -809,9 +816,8 @@ bool Ctrl::SetWndFocus() XSetInputFocus(Xdisplay, top->window, RevertToParent, CurrentTime); focusWindow = top->window; SetFocusWnd(); - return true; + *b = true; } - return false; } bool Ctrl::HasWndFocus() const @@ -934,7 +940,7 @@ void Ctrl::AddGlobalRepaint() } } -void Ctrl::WndInvalidateRect(const Rect& r) +void Ctrl::WndInvalidateRect0(const Rect& r) { GuiLock __; if(!top) return; @@ -942,7 +948,7 @@ void Ctrl::WndInvalidateRect(const Rect& r) Invalidate(Xwindow().Get(top->window), r); } -void Ctrl::SetWndForeground() +void Ctrl::SetWndForeground0() { GuiLock __; LLOG("SetWndForeground " << Name()); @@ -967,17 +973,20 @@ bool Ctrl::IsWndForeground() const return ~focusCtrlWnd == (q ? q : GetTopCtrl()); } -bool Ctrl::WndEnable(bool b) +void Ctrl::WndEnable0(bool *b) { GuiLock __; LLOG("WndEnable"); - if(!top) return false; - if(!b) { + if(!top) { + *b = false; + return; + } + if(!*b) { ReleaseCapture(); if(HasWndFocus()) XSetInputFocus(Xdisplay, None, RevertToPointerRoot, CurrentTime); } - return true; + *b = true; } // 01/12/2007 - mdelfede diff --git a/uppsrc/CtrlLib/ChGtk.cpp b/uppsrc/CtrlLib/ChGtk.cpp index 875a31ca4..932e37a5e 100644 --- a/uppsrc/CtrlLib/ChGtk.cpp +++ b/uppsrc/CtrlLib/ChGtk.cpp @@ -560,13 +560,7 @@ bool IsEmptyImage(const Image& m) Image GtkThemeIcon(const char *name, int size) { -<<<<<<< .mine Image m = GetGTK(gtk__parent(), size, 0, name, GTK_THEMEICON, 0, 0); -======= - Image m = GetGTK(gtk__parent(), size ? GTK_ICON_SIZE_LARGE_TOOLBAR - : GTK_ICON_SIZE_SMALL_TOOLBAR, - 0, name, GTK_THEMEICON, 0, 0); ->>>>>>> .r1505 Size sz = m.GetSize(); int rsz = size ? 48 : 16; if(sz.cx > rsz || sz.cy > rsz)