From a041d9898e6d699bd8c0c25482ec574feb03c547 Mon Sep 17 00:00:00 2001 From: "John Ankarstr\\xf6m" Date: Sat, 29 May 2021 12:54:47 +0200 Subject: First commit This is the original state of the released tarball for JWM 1.8, which will serve as my starting point for further modifications. --- src/main.c | 507 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 507 insertions(+) create mode 100644 src/main.c (limited to 'src/main.c') diff --git a/src/main.c b/src/main.c new file mode 100644 index 0000000..d9c6e78 --- /dev/null +++ b/src/main.c @@ -0,0 +1,507 @@ +/**************************************************************************** + * The main entry point and related JWM functions. + * Copyright (C) 2004 Joe Wingbermuehle + ****************************************************************************/ + +#include "jwm.h" +#include "main.h" +#include "lex.h" +#include "parse.h" +#include "help.h" +#include "error.h" +#include "event.h" + +#include "border.h" +#include "client.h" +#include "color.h" +#include "command.h" +#include "cursor.h" +#include "confirm.h" +#include "font.h" +#include "hint.h" +#include "group.h" +#include "key.h" +#include "icon.h" +#include "outline.h" +#include "taskbar.h" +#include "tray.h" +#include "traybutton.h" +#include "popup.h" +#include "pager.h" +#include "swallow.h" +#include "screen.h" +#include "root.h" +#include "desktop.h" +#include "place.h" +#include "clock.h" +#include "dock.h" +#include "theme.h" +#include "misc.h" + +Display *display = NULL; +Window rootWindow; +int rootWidth, rootHeight; +int rootDepth; +int rootScreen; +Colormap rootColormap; +Visual *rootVisual; +GC rootGC; +int colormapCount; + +int shouldExit = 0; +int shouldRestart = 0; +int isRestarting = 0; +int initializing = 0; + +unsigned int desktopCount = 4; +unsigned int currentDesktop = 0; + +char *exitCommand = NULL; + +int borderWidth = DEFAULT_BORDER_WIDTH; +int titleHeight = DEFAULT_TITLE_HEIGHT; + +unsigned int doubleClickSpeed; +unsigned int doubleClickDelta; + +FocusModelType focusModel = FOCUS_SLOPPY; + +XContext clientContext; +XContext frameContext; + +#ifdef USE_SHAPE +int haveShape; +int shapeEvent; +#endif + + +static const char *CONFIG_FILE = "/.jwmrc"; + +static void Initialize(); +static void Startup(); +static void Shutdown(); +static void Destroy(); + +static void OpenConnection(); +static void CloseConnection(); +static void StartupConnection(); +static void ShutdownConnection(); +static void EventLoop(); +static void HandleExit(); +static void DoExit(int code); +static void SendRestart(); +static void SendExit(); + +static char *configPath = NULL; +static char *displayString = NULL; + +/**************************************************************************** + ****************************************************************************/ +int main(int argc, char *argv[]) { + char *temp; + int x; + + StartDebug(); + + temp = getenv("HOME"); + if(temp) { + configPath = Allocate(strlen(temp) + strlen(CONFIG_FILE) + 1); + strcpy(configPath, temp); + strcat(configPath, CONFIG_FILE); + } else { + configPath = CopyString(CONFIG_FILE); + } + + for(x = 1; x < argc; x++) { + if(!strcmp(argv[x], "-v")) { + DisplayAbout(); + DoExit(0); + } else if(!strcmp(argv[x], "-h")) { + DisplayHelp(); + DoExit(0); + } else if(!strcmp(argv[x], "-p")) { + Initialize(); + ParseConfig(configPath); + DoExit(0); + } else if(!strcmp(argv[x], "-restart")) { + SendRestart(); + DoExit(0); + } else if(!strcmp(argv[x], "-exit")) { + SendExit(); + DoExit(0); + } else if(!strcmp(argv[x], "-display") && x + 1 < argc) { + displayString = argv[++x]; + } else { + DisplayUsage(); + DoExit(1); + } + } + + StartupConnection(); + do { + + isRestarting = shouldRestart; + shouldExit = 0; + shouldRestart = 0; + + Initialize(); + + ParseConfig(configPath); + + Startup(); + + EventLoop(); + + Shutdown(); + + Destroy(); + + } while(shouldRestart); + ShutdownConnection(); + + if(exitCommand) { + execl(SHELL_NAME, SHELL_NAME, "-c", exitCommand, NULL); + Warning("exec failed: (%s) %s", SHELL_NAME, exitCommand); + DoExit(1); + } else { + DoExit(0); + } + + /* Control shoud never get here. */ + return -1; + +} + +/**************************************************************************** + ****************************************************************************/ +void DoExit(int code) { + Destroy(); + + if(configPath) { + Release(configPath); + configPath = NULL; + } + if(exitCommand) { + Release(exitCommand); + exitCommand = NULL; + } + + StopDebug(); + exit(code); +} + +/**************************************************************************** + ****************************************************************************/ +void EventLoop() { + XEvent event; + + while(!shouldExit) { + WaitForEvent(&event); + ProcessEvent(&event); + } +} + +/**************************************************************************** + ****************************************************************************/ +void OpenConnection() { + + display = JXOpenDisplay(displayString); + if(!display) { + if(displayString) { + printf("error: could not open display %s\n", displayString); + } else { + printf("error: could not open display\n"); + } + DoExit(1); + } + + rootScreen = DefaultScreen(display); + rootWindow = RootWindow(display, rootScreen); + rootWidth = DisplayWidth(display, rootScreen); + rootHeight = DisplayHeight(display, rootScreen); + rootDepth = DefaultDepth(display, rootScreen); + rootColormap = DefaultColormap(display, rootScreen); + rootVisual = DefaultVisual(display, rootScreen); + rootGC = DefaultGC(display, rootScreen); + colormapCount = MaxCmapsOfScreen(ScreenOfDisplay(display, rootScreen)); + + XSetGraphicsExposures(display, rootGC, False); + +} + +/**************************************************************************** + ****************************************************************************/ +void StartupConnection() { + XSetWindowAttributes attr; + int temp; + + initializing = 1; + OpenConnection(); + +#if 0 + XSynchronize(display, True); +#endif + + JXSetErrorHandler(ErrorHandler); + + clientContext = XUniqueContext(); + frameContext = XUniqueContext(); + + attr.event_mask + = SubstructureRedirectMask + | SubstructureNotifyMask + | PropertyChangeMask + | ColormapChangeMask + | ButtonPressMask + | ButtonReleaseMask + | PointerMotionMask | PointerMotionHintMask; + JXChangeWindowAttributes(display, rootWindow, CWEventMask, &attr); + + signal(SIGTERM, HandleExit); + signal(SIGINT, HandleExit); + signal(SIGHUP, HandleExit); + +#ifdef USE_SHAPE + haveShape = JXShapeQueryExtension(display, &shapeEvent, &temp); + if (haveShape) { + Debug("shape extension enabled"); + } else { + Debug("shape extension disabled"); + } +#endif + + initializing = 0; + +} + +/**************************************************************************** + ****************************************************************************/ +void CloseConnection() { + JXFlush(display); + JXCloseDisplay(display); +} + +/**************************************************************************** + ****************************************************************************/ +void ShutdownConnection() { + CloseConnection(); +} + +/**************************************************************************** + ****************************************************************************/ +void HandleExit() { + signal(SIGTERM, HandleExit); + signal(SIGINT, HandleExit); + signal(SIGHUP, HandleExit); + shouldExit = 1; +} + +/**************************************************************************** + * This is called before the X connection is opened. + ****************************************************************************/ +void Initialize() { + InitializeBorders(); + InitializeClients(); + InitializeClock(); + InitializeColors(); + InitializeCommands(); + InitializeCursors(); + InitializeDesktops(); + #ifndef DISABLE_CONFIRM + InitializeDialogs(); + #endif + InitializeDock(); + InitializeFonts(); + InitializeGroups(); + InitializeHints(); + InitializeIcons(); + InitializeKeys(); + InitializeOutline(); + InitializePager(); + InitializePlacement(); + InitializePopup(); + InitializeRootMenu(); + InitializeScreens(); + InitializeSwallow(); + InitializeTaskBar(); + InitializeThemes(); + InitializeTray(); + InitializeTrayButtons(); +} + +/**************************************************************************** + * This is called after the X connection is opened. + ****************************************************************************/ +void Startup() { + + /* This order is important. */ + + StartupCommands(); + + /* First we grab the server to prevent clients from changing things + * while we're still loading. */ + JXGrabServer(display); + + StartupScreens(); + + StartupGroups(); + StartupColors(); + StartupIcons(); + StartupFonts(); + StartupCursors(); + StartupOutline(); + + StartupThemes(); + + StartupPager(); + StartupClock(); + StartupTaskBar(); + StartupTrayButtons(); + StartupDock(); + StartupTray(); + StartupKeys(); + StartupDesktops(); + StartupHints(); + StartupBorders(); + StartupPlacement(); + StartupClients(); + + #ifndef DISABLE_CONFIRM + StartupDialogs(); + #endif + StartupPopup(); + + StartupRootMenu(); + + SetDefaultCursor(rootWindow); + ReadCurrentDesktop(); + JXFlush(display); + + RestackClients(); + + /* Allow clients to do their thing. */ + JXSync(display, True); + JXUngrabServer(display); + + StartupSwallow(); + + /* Send expose events. */ + ExposeCurrentDesktop(); + +} + +/**************************************************************************** + * This is called before the X connection is closed. + ****************************************************************************/ +void Shutdown() { + + /* This order is important. */ + + ShutdownSwallow(); + + ShutdownOutline(); + #ifndef DISABLE_CONFIRM + ShutdownDialogs(); + #endif + ShutdownPopup(); + ShutdownKeys(); + ShutdownPager(); + ShutdownRootMenu(); + ShutdownDock(); + ShutdownTray(); + ShutdownTrayButtons(); + ShutdownTaskBar(); + ShutdownClock(); + ShutdownBorders(); + ShutdownClients(); + ShutdownThemes(); + ShutdownIcons(); + ShutdownCursors(); + ShutdownFonts(); + ShutdownColors(); + ShutdownGroups(); + ShutdownDesktops(); + + ShutdownPlacement(); + ShutdownHints(); + ShutdownScreens(); + + ShutdownCommands(); + +} + +/**************************************************************************** + * This is called after the X connection is closed. + * Note that it is possible for this to be called more than once. + ****************************************************************************/ +void Destroy() { + DestroyBorders(); + DestroyClients(); + DestroyClock(); + DestroyColors(); + DestroyCommands(); + DestroyCursors(); + DestroyDesktops(); + #ifndef DISABLE_CONFIRM + DestroyDialogs(); + #endif + DestroyDock(); + DestroyFonts(); + DestroyGroups(); + DestroyHints(); + DestroyIcons(); + DestroyKeys(); + DestroyOutline(); + DestroyPager(); + DestroyPlacement(); + DestroyPopup(); + DestroyRootMenu(); + DestroyScreens(); + DestroySwallow(); + DestroyTaskBar(); + DestroyThemes(); + DestroyTray(); + DestroyTrayButtons(); +} + +/**************************************************************************** + * Send _JWM_RESTART to the root window. + ****************************************************************************/ +void SendRestart() { + + XEvent event; + + OpenConnection(); + + memset(&event, 0, sizeof(event)); + event.xclient.type = ClientMessage; + event.xclient.window = rootWindow; + event.xclient.message_type = JXInternAtom(display, "_JWM_RESTART", False); + event.xclient.format = 32; + + JXSendEvent(display, rootWindow, False, SubstructureRedirectMask, &event); + + CloseConnection(); + +} + +/**************************************************************************** + * Send _JWM_EXIT to the root window. + ****************************************************************************/ +void SendExit() { + + XEvent event; + + OpenConnection(); + + memset(&event, 0, sizeof(event)); + event.xclient.type = ClientMessage; + event.xclient.window = rootWindow; + event.xclient.message_type = JXInternAtom(display, "_JWM_EXIT", False); + event.xclient.format = 32; + + JXSendEvent(display, rootWindow, False, SubstructureRedirectMask, &event); + + CloseConnection(); +} + -- cgit v1.2.3