# Application Entry Point and Initialization > **Relevant source files** > * [src/io/github/samera2022/mouse_macros/MouseMacro.java](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java) > * [src/io/github/samera2022/mouse_macros/constant/OtherConsts.java](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/constant/OtherConsts.java) ## Purpose and Scope This document describes the application bootstrap process in the MouseMacros system. The `MouseMacro` class serves as the application entry point, executing the minimal initialization sequence required before the main UI can launch. This includes configuring the JNativeHook native library path and delegating UI creation to the Swing Event Dispatch Thread (EDT). **Related Pages:** * For `MainFrame` singleton initialization and UI component setup, see [Main Window (MainFrame)](Main-Window-(MainFrame))) * For `ConfigManager.CONFIG_DIR` resolution and configuration loading, see [ConfigManager](ConfigManager) * For JNativeHook integration and event capture setup, see [Global Input Capture](Global-Input-Capture) ## System Context The `MouseMacro` entry point is the first code executed by the JVM and serves as the initialization coordinator for the entire application. From the high-level architecture (Diagram 1), the entry point's responsibilities are: 1. Configure JNativeHook library system properties before any hooks are registered 2. Launch the `MainFrame` singleton on the Swing EDT 3. Enable the `GlobalMouseListener` to access native libraries through proper path configuration ```mermaid flowchart TD JVM["JVM"] MouseMacro["MouseMacro.main()"] ConfigManagerStatic["ConfigManager.CONFIG_DIR
(static field)"] SystemProperties["System.setProperty()
jnativehook.lib.path"] SwingUtilities["SwingUtilities.invokeLater()"] MAIN_FRAME["MainFrame.MAIN_FRAME
(singleton)"] JVM --> MouseMacro MouseMacro --> ConfigManagerStatic MouseMacro --> SystemProperties MouseMacro --> SwingUtilities SwingUtilities --> MAIN_FRAME ``` **Diagram: Entry Point Position in Application Layer** **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L1-L18](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L1-L18) ## Main Class Structure The `MouseMacro` class defines the application entry point through its `main()` method. This class has no instance methods, fields, or constructors—it exists solely to bootstrap the application. | Property | Value | | --- | --- | | **Package** | `io.github.samera2022.mouse_macros` | | **Class Name** | `MouseMacro` | | **Entry Method** | `public static void main(String[] args)` | | **Source File** | [src/io/github/samera2022/mouse_macros/MouseMacro.java L9-L17](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L9-L17) | ### Import Dependencies ```mermaid flowchart TD MouseMacro["MouseMacro"] SystemUtil["io.github.samera2022.mouse_macros.util.SystemUtil"] SwingUtilities["javax.swing.SwingUtilities"] MAIN_FRAME_Import["static import:
io.github.samera2022.mouse_macros.ui.frame.MainFrame.MAIN_FRAME"] ConfigManager["io.github.samera2022.mouse_macros.manager.ConfigManager"] MouseMacro --> SystemUtil MouseMacro --> SwingUtilities MouseMacro --> MAIN_FRAME_Import MouseMacro --> ConfigManager ``` **Diagram: MouseMacro Import Structure** The class imports: * `SystemUtil` [src/io/github/samera2022/mouse_macros/MouseMacro.java L3](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L3-L3) - imported but not used in the current implementation * `javax.swing.SwingUtilities` [src/io/github/samera2022/mouse_macros/MouseMacro.java L5](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L5-L5) - for EDT thread delegation * Static import of `MAIN_FRAME` constant [src/io/github/samera2022/mouse_macros/MouseMacro.java L7](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L7-L7) - singleton instance reference * `ConfigManager.CONFIG_DIR` via fully qualified name [src/io/github/samera2022/mouse_macros/MouseMacro.java L12](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L12-L12) - configuration directory path **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L1-L7](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L1-L7) ## Bootstrap Sequence The `main()` method executes a two-phase initialization sequence: ```mermaid sequenceDiagram participant JVM participant MouseMacro["MouseMacro.main()"] participant ConfigManager["ConfigManager.CONFIG_DIR"] participant FileSystem["File System"] participant SystemProperties["System.setProperty()"] participant SwingUtilities["SwingUtilities"] participant EDT["Swing EDT"] participant MAIN_FRAME["MainFrame.MAIN_FRAME"] participant MouseMacro participant FileSystem participant ConfigManager participant SystemProperties participant MAIN_FRAME participant SwingUtilities participant EDT JVM->>MouseMacro: "invoke main()" note over MouseMacro,FileSystem: Phase 1: Native Library Configuration (Main Thread) MouseMacro->>MouseMacro: "dllName = 'JNativeHook.x86_64.dll'" MouseMacro->>ConfigManager: "access CONFIG_DIR" ConfigManager-->>MouseMacro: "config directory path" MouseMacro->>MouseMacro: "libDir = new File(configDir + '/libs/', dllName)" MouseMacro->>FileSystem: "libDir.exists()?" loop [Directory does not exist] FileSystem-->>MouseMacro: "false" MouseMacro->>FileSystem: "libDir.mkdirs()" end MouseMacro->>SystemProperties: "setProperty('jnativehook.lib.path', libDir.getAbsolutePath())" note over MouseMacro,MAIN_FRAME: Phase 2: UI Initialization (EDT) MouseMacro->>SwingUtilities: "invokeLater(() -> MAIN_FRAME.setVisible(true))" SwingUtilities->>EDT: "enqueue lambda" MouseMacro-->>JVM: "main() returns" EDT->>MAIN_FRAME: "setVisible(true)" note over MAIN_FRAME: Triggers MainFrame singleton initialization ``` **Diagram: Complete Bootstrap Execution Flow** ### Phase 1: Native Library Configuration Executed synchronously on the main thread [src/io/github/samera2022/mouse_macros/MouseMacro.java L11-L15](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L11-L15) This phase must complete before JNativeHook classes are loaded, otherwise the JVM will fail to find the native library. **Critical ordering:** System property `jnativehook.lib.path` must be set before any code references `org.jnativehook.*` classes. ### Phase 2: UI Thread Initialization Executed asynchronously on the EDT [src/io/github/samera2022/mouse_macros/MouseMacro.java L16](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L16-L16) The main thread enqueues the UI initialization task and terminates. All subsequent application logic runs on the EDT or background threads spawned by application components. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L10-L16](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L10-L16) ## Native Library Configuration The first critical operation is configuring the JNativeHook native library path before any UI code executes. ### Library Path Setup Logic ```mermaid flowchart TD start["main() execution"] dllName["Line 11:
dllName = 'JNativeHook.x86_64.dll'"] configDir["Line 12:
configDir = ConfigManager.CONFIG_DIR"] libDir["Line 13:
libDir = new File(configDir+'/libs/', dllName)"] existsCheck["Line 14:
libDir.exists()"] mkdirs["libDir.mkdirs()"] setProperty["Line 15:
System.setProperty('jnativehook.lib.path',
libDir.getAbsolutePath())"] start --> dllName start --> configDir dllName --> libDir configDir --> libDir libDir --> existsCheck existsCheck --> mkdirs existsCheck --> setProperty mkdirs --> setProperty ``` **Diagram: JNativeHook Native Library Path Configuration** The native library setup executes these operations: | Line | Operation | Description | | --- | --- | --- | | 11 | `dllName = "JNativeHook.x86_64.dll"` | Hardcoded Windows x64 library name | | 12 | `configDir = ConfigManager.CONFIG_DIR` | Reads static field containing platform-specific config directory path | | 13 | `new File(configDir+"/libs/", dllName)` | Constructs path: `{CONFIG_DIR}/libs/JNativeHook.x86_64.dll` | | 14 | `if (!libDir.exists()) libDir.mkdirs()` | Creates directory structure if missing | | 15 | `System.setProperty("jnativehook.lib.path", ...)` | Configures JVM system property for native library loading | **Important:** The `mkdirs()` call creates both the `libs/` directory and any missing parent directories. On first run, this ensures the entire directory structure exists. ### Resulting File System Layout After the first application launch, the directory structure is: ``` {CONFIG_DIR}/ ├── config.cfg (created by ConfigManager) ├── cache.json (created by CacheManager) └── libs/ └── JNativeHook.x86_64.dll (created by MouseMacro.main) ``` The `libs/` directory and parent directories are created by `mkdirs()` at [src/io/github/samera2022/mouse_macros/MouseMacro.java L14](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L14-L14) JNativeHook will later extract and load the native DLL from this location when `GlobalMouseListener` registers hooks. **Platform-specific paths for `CONFIG_DIR`:** * **Windows:** `%LOCALAPPDATA%\MouseMacros\` * **macOS:** `~/Library/Application Support/MouseMacros/` * **Linux:** `~/.local/share/MouseMacros/` See [File and Path Utilities](File-and-Path-Utilities) for `CONFIG_DIR` resolution logic. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L11-L14](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L11-L14) ## UI Thread Initialization After native library configuration, the main thread delegates UI creation to the Swing Event Dispatch Thread (EDT) using `SwingUtilities.invokeLater()` [src/io/github/samera2022/mouse_macros/MouseMacro.java L16](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L16-L16) ### Thread Handoff Mechanism ```mermaid flowchart TD MainThread["Main Thread
(MouseMacro.main)"] invokeLater["SwingUtilities.invokeLater()"] lambda["Lambda:
() -> MAIN_FRAME.setVisible(true)"] EDTQueue["EDT Event Queue"] EDT["Event Dispatch Thread"] setVisible["MAIN_FRAME.setVisible(true)"] MainFrameInit["MainFrame singleton initialization"] MainThreadEnd["Main thread terminates"] MainThread --> invokeLater invokeLater --> lambda lambda --> EDTQueue MainThread --> MainThreadEnd EDTQueue --> EDT EDT --> setVisible setVisible --> MainFrameInit ``` **Diagram: EDT Delegation via SwingUtilities.invokeLater()** ### Why EDT Delegation is Required Swing components are not thread-safe. All Swing operations (component creation, modification, event handling) must execute on a single thread: the EDT. Using `SwingUtilities.invokeLater()` ensures that: 1. UI initialization happens on the EDT 2. The main thread can terminate without blocking UI operations 3. Thread safety constraints are satisfied ### MAIN_FRAME Singleton Access The `MAIN_FRAME` constant is statically imported [src/io/github/samera2022/mouse_macros/MouseMacro.java L7](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L7-L7) : ```javascript import static io.github.samera2022.mouse_macros.ui.frame.MainFrame.MAIN_FRAME; ``` `MAIN_FRAME` is a `public static final MainFrame` field defined in the `MainFrame` class. When the lambda executes `MAIN_FRAME.setVisible(true)`, it triggers: 1. **Class Loading:** The `MainFrame` class is loaded by the JVM classloader 2. **Static Initialization:** The `MAIN_FRAME` singleton is constructed 3. **Constructor Execution:** Complete UI initialization occurs (see [Main Window (MainFrame)](Main-Window-(MainFrame)))) 4. **Window Display:** `setVisible(true)` displays the initialized window The entire application UI is initialized lazily when `MAIN_FRAME` is first accessed. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L7-L16](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L7-L16) ## Critical Ordering Constraints The bootstrap sequence has strict ordering requirements to prevent runtime failures: | Order | Operation | Thread | Line | Constraint | | --- | --- | --- | --- | --- | | 1 | Set `jnativehook.lib.path` system property | Main | 15 | **Must execute before** JNativeHook classes are loaded | | 2 | Enqueue UI initialization lambda | Main | 16 | **Must execute after** library path configuration | | 3 | Execute `MAIN_FRAME.setVisible(true)` | EDT | 16 | **Must execute on** EDT (Swing threading requirement) | ### Why Order Matters **Native Library Loading:** JNativeHook uses JNI (Java Native Interface) to load platform-specific DLLs. The JVM reads the `jnativehook.lib.path` system property when loading native code. If this property is not set before JNativeHook classes are accessed, the JVM will throw `UnsatisfiedLinkError`. **EDT Threading:** Swing enforces single-threaded access to UI components. Calling `setVisible()` from the main thread would violate this constraint and could cause race conditions or deadlocks. ### Dependency Chain ```mermaid flowchart TD JVM["JVM classloader"] main["MouseMacro.main(args)
Line 10"] configDir["ConfigManager.CONFIG_DIR
Line 12"] libDirConstruct["new File(...)
Line 13"] mkdirs["libDir.mkdirs()
Line 14"] setProperty["System.setProperty()
Line 15"] invokeLater["SwingUtilities.invokeLater()
Line 16"] EDT["EDT execution"] setVisible["MAIN_FRAME.setVisible(true)"] MainFrameClassLoad["MainFrame class load"] MainFrameSingleton["MAIN_FRAME field initialization"] JVM --> main main --> configDir main --> libDirConstruct libDirConstruct --> mkdirs mkdirs --> setProperty setProperty --> invokeLater invokeLater --> EDT EDT --> setVisible setVisible --> MainFrameClassLoad MainFrameClassLoad --> MainFrameSingleton ``` **Diagram: Complete Method Invocation and Dependency Chain** The entry point performs minimal work—only 7 lines of executable code—before transferring control to `MainFrame`. This design keeps the bootstrap logic simple and focused. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L10-L16](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L10-L16) ## Command-Line Arguments The `main()` method signature includes the standard `String[] args` parameter [src/io/github/samera2022/mouse_macros/MouseMacro.java L10](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L10-L10) but this parameter is currently unused. The application does not support any command-line arguments. All configuration is performed through: * The `config.cfg` file - managed by `ConfigManager` (see [Configuration Files and Settings](Configuration-Files-and-Settings)) * The settings dialogs - `SettingsDialog` and `MacroSettingsDialog` (see [Settings Dialog](Settings-Dialog) and [Macro Settings Dialog](Macro-Settings-Dialog)) ### Future Extension Point If command-line argument parsing is added in the future, it should be inserted between lines 15 and 16: ```sql System.setProperty("jnativehook.lib.path", libDir.getAbsolutePath()); // INSERT: parseCommandLineArgs(args) here SwingUtilities.invokeLater(() -> MAIN_FRAME.setVisible(true)); ``` This ensures arguments are processed after native library setup but before UI initialization. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L10](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L10-L10) ## Error Handling The `main()` method does not implement explicit error handling. All exceptions propagate to the JVM's default uncaught exception handler, which prints a stack trace to stderr and terminates the process. ### Potential Failure Modes | Operation | Line | Failure Scenario | Exception Type | Recovery | | --- | --- | --- | --- | --- | | `ConfigManager.CONFIG_DIR` access | 12 | Static initialization failure | Various | None - application cannot start | | `new File(...)` | 13 | Invalid path characters | None thrown | Constructor succeeds with invalid path | | `libDir.mkdirs()` | 14 | Insufficient permissions | None thrown | Returns `false`, continues execution | | `System.setProperty(...)` | 15 | Security manager denies access | `SecurityException` | JVM terminates | | `SwingUtilities.invokeLater(...)` | 16 | Null lambda (impossible here) | `NullPointerException` | JVM terminates | | `MAIN_FRAME` initialization | 16 (EDT) | UI construction failure | Various (e.g., `HeadlessException`) | EDT exception handler logs and terminates | ### No Graceful Degradation The application does not attempt graceful degradation on initialization failure. If the bootstrap sequence fails: 1. The exception propagates to the JVM 2. The JVM prints the stack trace 3. The process terminates with non-zero exit code **Design Rationale:** Bootstrap failures indicate severe environmental issues (missing directories, security restrictions, headless environment). Recovery is not practical, and early termination prevents the application from running in an invalid state. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L10-L16](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L10-L16) ## Platform Support ### Current Implementation: Windows x64 Only The native library name is hardcoded as `"JNativeHook.x86_64.dll"` [src/io/github/samera2022/mouse_macros/MouseMacro.java L11](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L11-L11) which restricts the application to 64-bit Windows systems. The application will fail to start on other platforms because: 1. JNativeHook cannot find the appropriately-named library file 2. The Windows DLL format is incompatible with Linux/macOS ### Multi-Platform Support Requirements To support additional platforms, the entry point would need OS and architecture detection logic: ``` String osName = System.getProperty("os.name").toLowerCase(); String osArch = System.getProperty("os.arch").toLowerCase(); String dllName; if (osName.contains("win")) { dllName = "JNativeHook.x86_64.dll"; } else if (osName.contains("mac")) { dllName = "libJNativeHook.x86_64.dylib"; } else if (osName.contains("nux")) { dllName = "libJNativeHook.x86_64.so"; } ``` **Required library files per platform:** | Platform | Architecture | Library File Name | Extension | | --- | --- | --- | --- | | Windows | x86_64 | `JNativeHook.x86_64.dll` | Windows PE DLL | | Linux | x86_64 | `libJNativeHook.x86_64.so` | ELF Shared Object | | macOS | x86_64 | `libJNativeHook.x86_64.dylib` | Mach-O Dynamic Library | | macOS | ARM64 (M1/M2) | `libJNativeHook.arm64.dylib` | Mach-O Dynamic Library | **Note:** `SystemUtil` is imported [src/io/github/samera2022/mouse_macros/MouseMacro.java L3](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L3-L3) but unused. This utility class could provide platform detection helpers for future multi-platform support. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L3-L11](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L3-L11) ## Integration Points The `MouseMacro` entry point integrates with: 1. **ConfigManager**: Retrieves `CONFIG_DIR` for library path construction [src/io/github/samera2022/mouse_macros/MouseMacro.java L10](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L10-L10) 2. **MainFrame**: Accesses singleton `MAIN_FRAME` instance [src/io/github/samera2022/mouse_macros/MouseMacro.java L15](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L15-L15) 3. **JVM System Properties**: Sets `jnativehook.lib.path` [src/io/github/samera2022/mouse_macros/MouseMacro.java L13](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L13-L13) 4. **Swing EDT**: Delegates UI work via `SwingUtilities.invokeLater()` [src/io/github/samera2022/mouse_macros/MouseMacro.java L15](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L15-L15) ```mermaid flowchart TD MouseMacro["MouseMacro.main()"] ConfigManager["ConfigManager"] MainFrame["MainFrame.MAIN_FRAME"] SystemProps["System Properties"] SwingEDT["Swing EDT"] MouseMacro --> ConfigManager MouseMacro --> SystemProps MouseMacro --> SwingEDT SwingEDT --> MainFrame ``` **Diagram: Entry Point Dependencies** After the entry point completes, control flow passes entirely to the Event Dispatch Thread and the event-driven Swing framework. The main thread terminates after enqueueing the UI initialization task. **Sources:** [src/io/github/samera2022/mouse_macros/MouseMacro.java L8-L16](https://github.com/Samera2022/MouseMacros/blob/1eb6620b/src/io/github/samera2022/mouse_macros/MouseMacro.java#L8-L16)