namespace gui;
-#if defined(__unix__) || defined(__APPLE__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
#define property _property
#define new _new
#define class _class
#if defined(__WIN32__)
#define WIN32_LEAN_AND_MEAN
+#define String _String
#include <winsock.h>
+#undef String
static WSADATA wsaData;
#elif defined(__unix__) || defined(__APPLE__)
default:
#define uint _uint
+#define set _set
#include <sys/time.h>
#include <unistd.h>
+#include <sys/select.h>
#include <netinet/in.h>
#include <netdb.h>
#include <sys/time.h>
#include <arpa/inet.h>
-private:
+#undef set
#undef uint
+
+private:
typedef int SOCKET;
typedef struct hostent HOSTENT;
typedef struct sockaddr SOCKADDR;
import "network"
#endif
-#if defined(__APPLE__)
+#if defined(__APPLE__) && !defined(ECERE_VANILLA)
import "CocoaInterface"
-#elif defined(__unix__)
+#endif
+
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
import "XInterface"
#endif
import "Window"
+/*static */bool guiApplicationInitialized = false;
GuiApplication guiApp;
int terminateX;
modeSwitchFailed = ErrorCode { VeryFatal, 4 }
};
-static char * errorMessages[] =
-{
- "No error",
- "Graphics driver not supported by any user interface system",
- "Window creation failed",
- "Window graphics loading failed",
- "Driver/Mode switch failed"
-};
+static Array<String> errorMessages
+{ [
+ $"No error",
+ $"Graphics driver not supported by any user interface system",
+ $"Window creation failed",
+ $"Window graphics loading failed",
+ $"Driver/Mode switch failed"
+] };
public class GuiApplication : Application
{
char appName[1024];
uint timerResolution;
- Size virtualScreen;
+ Size virtualScreen;
Point virtualScreenPos;
- int mainThread;
+ int64 mainThread;
GuiApplication()
{
SystemCursor c;
-
+
mainThread = GetCurrentThreadID();
if(!guiApp)
guiApp = this;
- strcpy(appName, "ECERE Application");
+ strcpy(appName, $"ECERE Application");
processAll = true;
delete desktop;
customCursors.Clear();
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XUnlockDisplay(xGlobalDisplay);
#endif
- lockMutex.Release();
+#if !defined(__ANDROID__)
+ // Because destruction of app won't be from main thread
+ if(guiApplicationInitialized)
+ lockMutex.Release();
+#endif
if(interfaceDriver)
{
delete globalSystem.fileMonitorThread;
UnapplySkin(class(Window));
+
+ // Stop all timers
+ {
+ Timer timer, nextTimer;
+ for(timer = windowTimers.first; timer; timer = nextTimer)
+ {
+ nextTimer = timer.next;
+ timer.Stop();
+ }
+ }
}
bool UpdateTimers()
}
// --- Mouse-based window movement ---
- void SetCurrentCursor(Cursor cursor)
+ void SetCurrentCursor(Window window, Cursor cursor)
{
currentCursor = cursor;
if(cursor)
{
if(fullScreenMode && cursor.bitmap)
- interfaceDriver.SetMouseCursor((SystemCursor)-1);
+ interfaceDriver.SetMouseCursor(window ? window : desktop, (SystemCursor)-1);
else
{
- interfaceDriver.SetMouseCursor(cursor.systemCursor);
+ interfaceDriver.SetMouseCursor(window ? window : desktop, cursor.systemCursor);
cursorBackground.Free();
}
}
bool IsModeSwitching()
{
return modeSwitching;
- }
+ }
public bool SetDesktopPosition(int x, int y, int w, int h, bool moveChildren)
{
{
child.x = desktop.x;
child.y = desktop.y;
- child.ComputeAnchors(,
- A_LEFT,A_LEFT,A_OFFSET,A_OFFSET,
+ child.ComputeAnchors(,
+ A_LEFT,A_LEFT,A_OFFSET,A_OFFSET,
&x, &y, &w, &h);
child.Position(, x, y, w, h, false, true, true, true, false);
- }
+ }
}
}*/
if(desktop.display)
}
void SetAppFocus(bool state)
- {
+ {
// Shouldn't be property here
desktop.active = state;
}
bool result = false;
subclass(Skin) skin;
OldLink link;
-
+
for(link = class(Skin).derivatives.first; link; link = link.next)
{
skin = link.data;
break;
}
if(!link) skin = null;
-
+
if(skin)
{
if(skin != currentSkin || !currentSkin)
}
UnapplySkin(class(Window));
-
+
currentSkin = skin;
ApplySkin(class(Window), skin.name, null);
void Initialize(bool switchMode)
{
- static bool initialized = false;
-
// TODO:
// if(!initialized && eClass_IsDerived(__ecereModule->app->module.inst.class, guiApplicationClass))
- if(!initialized)
+ if(!guiApplicationInitialized)
{
char * defaultDriver = null;
-#if defined(ECERE_VANILLA)
+#if defined(ECERE_VANILLA) || defined(ECERE_ONEDRIVER)
char * driver = null;
#else
GetEnvironment("ECERE_DRIVER", driverStorage, sizeof(driverStorage));
if(driverStorage[0]) driver = driverStorage;
#endif
- initialized = true;
+ guiApplicationInitialized = true;
fullScreenMode = true; // Needs to start at true for the desktop to resize
// Set this to true earlier so we can override it!
errorLevel = 2;
lockMutex.Wait();
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XLockDisplay(xGlobalDisplay);
#endif
// Setup Desktop
if(!desktop)
{
- desktop = Window { };
+ desktop = Window { nativeDecorations = false };
incref desktop;
incref desktop;
desktop.childrenOrder.circ = true;
desktop.background = blue;
desktop.rootWindow = desktop;
desktop.cursor = GetCursor(arrow);
- desktop.caption = new char[strlen(appName) + 1];
- strcpy(desktop.caption, appName);
+ desktop.caption = appName;
*&desktop.visible = true;
desktop.position = Point { };
desktop.mutex = Mutex { };
{
if(driver)
defaultDriver = driver;
- else if(this.isGUIApp && !textMode)
+ else if((this.isGUIApp & 1) && !textMode)
defaultDriver = "GDI";
else
defaultDriver = "Win32Console";
if (driver) {
defaultDriver = driver;
} else {
- defaultDriver = "CocoaOpenGL";
+ defaultDriver = "X"; //"CocoaOpenGL";
}
- }
+ }
+ #elif defined(__ANDROID__)
+ {
+ if(driver)
+ defaultDriver = driver;
+ else
+ defaultDriver = "OpenGL";
+ }
#else
- if(this.isGUIApp && !textMode)
+ if((this.isGUIApp & 1) && !textMode)
{
char * display = getenv("DISPLAY");
#endif
#if defined(__APPLE__)
- SwitchMode(true, "CocoaOpenGL", 0, 0, 0, null, true);
+ SwitchMode(true, "X" /*"CocoaOpenGL"*/, 0, 0, 0, null, true);
#endif
#if defined(__unix__)
#endif
}
if(!interfaceDriver)
- initialized = false;
+ guiApplicationInitialized = false;
}
else
defaultDisplayDriver = defaultDriver;
if(!Cycle(wait))
wait = false;
- if(wait)
+ if(wait)
Wait();
else
{
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XUnlockDisplay(xGlobalDisplay);
#endif
lockMutex.Release();
lockMutex.Wait();
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XLockDisplay(xGlobalDisplay);
#endif
}
}
Terminate();
+
+#if defined(__ANDROID__)
+ // Because destruction of GuiApp won't be from main thread
+ lockMutex.Release();
+#endif
}
void Wait(void)
{
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XUnlockDisplay(xGlobalDisplay);
#endif
lockMutex.Wait();
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XLockDisplay(xGlobalDisplay);
#endif
result |= UpdateTimers();
result |= ProcessFileNotifications();
*/
-
+
result |= ProcessFileNotifications();
result |= UpdateTimers();
result |= interfaceDriver.ProcessInput(useProcessAll && processAll);
#if !defined(ECERE_VANILLA) && !defined(ECERE_NO3D)
if(Desktop3DUpdateDisplay()) return;
#endif
-
+
if(interfaceDriver)
{
if(fullScreenMode && desktop.display)
PauseNetworkEvents();
network.mutex.Wait();
-
+
#ifdef DEBUG_SOCKETS
if(network.connectEvent || network.networkEvent)
Log("[P] [NProcess]\n");
FD_SET(socket.s, &network.readSet);
FD_SET(socket.s, &network.exceptSet);
network.mutex.Release();
-
+
// printf("Calling OnConnect on %s\n", socket._class.name);
socket.OnConnect();
network.mutex.Wait();
- network.sockets.Add(socket);
+ if(socket._connected)
+ network.sockets.Add(socket);
}
gotEvent |= true;
goOn = true;
if(skinName)
{
OldLink link;
-
+
for(link = class(Skin).derivatives.first; link; link = link.next)
{
skin = link.data;
break;
}
if(!link)
- inter = null;
+ inter = null;
}
-
+
/*
if(driverName)
- {
+ {
#if defined(__WIN32__)
#if !defined(ECERE_VANILLA)
if(!strcmp(driverName, "Win32Console")) inter = (subclass(Interface))class(Win32ConsoleInterface); else
}
*/
- if(interfaceDriver && (!driverName || (fbDriver && !strcmp(fbDriver, driverName))) &&
+ if(interfaceDriver && (!driverName || (fbDriver && !strcmp(fbDriver, driverName))) &&
fullScreen == fbFullScreen &&
(!resolution || resolution == fbResolution) &&
(!colorDepth || colorDepth == fbColorDepth) &&
{
if(!fbDriver || (driverName && strcmp(fbDriver, driverName)))
defaultDisplayDriver = driverName;
-
+
if(!skinName || !SelectSkin(skinName))
{
if(!currentSkin || currentSkin.textMode != textMode ||
{
OldLink link;
subclass(Skin) skin = null;
-
+
for(link = class(Skin).derivatives.first; link; link = link.next)
{
skin = link.data;
if(!link) skin = null;
if(skin)
+#if !defined(__ANDROID__)
SelectSkin(skin.name);
+#else
+ currentSkin = skin;
+#endif
}
}
if(currentSkin && desktop.SetupDisplay())
{
desktop.active = true;
-
+
if(fullScreen)
{
desktop.display.Lock(false);
if(!result && fallBack && fbDriver)
{
if(!SwitchMode(fbFullScreen, fbDriver, fbResolution, fbColorDepth, fbRefreshRate, null, false))
- Log("Error falling back to previous video mode.\n");
+ Log($"Error falling back to previous video mode.\n");
}
return result;
}
bool activity = false;
FileMonitor monitor, next;
static int reentrant = 0;
-
- // printf("[%d] Waiting in ProcessFileNotifications for fileMonitor Mutex %x...\n", GetCurrentThreadID(), globalSystem.fileMonitorMutex);
+
+ // Reentrant FileNotification is asking for trouble since each monitor is spawning a Modal() MessageBox
+ if(reentrant) return false;
+ // printf("[%d] Waiting in ProcessFileNotifications for fileMonitor Mutex %x...\n", (int)GetCurrentThreadID(), globalSystem.fileMonitorMutex);
globalSystem.fileMonitorMutex.Wait();
reentrant++;
for(monitor = globalSystem.fileMonitors.first; monitor; monitor = next)
next = monitor.next;
incref monitor;
-
+ if(next)
+ incref next;
+
if(!monitor.reentrant && !monitor.toBeFreed)
{
monitor.reentrant = true;
monitor.reentrant = false;
}
delete monitor;
+ if(next && next._refCount > 1)
+ next._refCount--;
+ else
+ delete next;
}
reentrant--;
if(!reentrant)
monitor.FreeMonitor();
}
}
- // printf("[%d] Releasing in ProcessFileNotifications fileMonitor Mutex %x...\n", GetCurrentThreadID(), globalSystem.fileMonitorMutex);
+ // printf("[%d] Releasing in ProcessFileNotifications fileMonitor Mutex %x...\n", (int)GetCurrentThreadID(), globalSystem.fileMonitorMutex);
globalSystem.fileMonitorMutex.Release();
return activity;
}
void Lock(void)
{
lockMutex.Wait();
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XLockDisplay(xGlobalDisplay);
#endif
void Unlock(void)
{
-#if defined(__unix__)
+#if (defined(__unix__) || defined(__APPLE__)) && !defined(__ANDROID__)
if(xGlobalDisplay)
XUnlockDisplay(xGlobalDisplay);
#endif
{
return interfaceDriver.GetMouseState(buttons, x, y);
}
-
+
// Properties
property char * appName
{
{
set
{
- SwitchMode(value, defaultDisplayDriver, resolution,
+ SwitchMode(value, defaultDisplayDriver, resolution,
pixelFormat, refreshRate, currentSkin ? currentSkin.name : null, true);
}
get { return this ? fullScreen : false; }
{
set
{
- SwitchMode( fullScreen, value, resolution, pixelFormat, refreshRate,
+ SwitchMode( fullScreen, value, resolution, pixelFormat, refreshRate,
currentSkin ? currentSkin.name : null, true);
- }
+ }
get { return this ? defaultDisplayDriver : null; }
};
property Resolution resolution
{
set
{
- SwitchMode(fullScreen, defaultDisplayDriver, value, pixelFormat, refreshRate,
+ SwitchMode(fullScreen, defaultDisplayDriver, value, pixelFormat, refreshRate,
currentSkin ? currentSkin.name : null, true);
}
get { return this ? resolution : 0; }
{
set
{
- SwitchMode(fullScreen, defaultDisplayDriver, resolution,
+ SwitchMode(fullScreen, defaultDisplayDriver, resolution,
pixelFormat, refreshRate, currentSkin ? currentSkin.name : null, true);
}
get { return this ? pixelFormat : 0; }
{
set
{
- SwitchMode(fullScreen, defaultDisplayDriver, resolution,
+ SwitchMode(fullScreen, defaultDisplayDriver, resolution,
pixelFormat, refreshRate, currentSkin ? currentSkin.name : null, true);
}
get { return this ? refreshRate : 0; }
property int numSkins { get { return 0; } };
property uint timerResolution
{
- set { timerResolution = value; if(interfaceDriver) interfaceDriver.SetTimerResolution(value); }
+ set { timerResolution = value; if(interfaceDriver) interfaceDriver.SetTimerResolution(value); }
};
};