├── .github └── workflows │ └── continuous-integration.yml ├── .gitignore ├── .gitmodules ├── AUTHORS ├── CMakeLists.txt ├── COPYING.LESSER.md ├── COPYING.md ├── ChangeLog.md ├── README.md ├── doc ├── Compiling.md ├── ConsoleOutput.md ├── ConsumingEvents.md ├── Keyboard.md ├── LibraryLoading.md ├── Mouse.md ├── MouseWheel.md └── Swing.md ├── pom.xml └── src ├── main ├── java │ ├── com │ │ └── github │ │ │ └── kwhat │ │ │ └── jnativehook │ │ │ ├── AbstractSwingInputAdapter.java │ │ │ ├── DefaultLibraryLocator.java │ │ │ ├── GlobalScreen.java │ │ │ ├── NativeHookException.java │ │ │ ├── NativeInputEvent.java │ │ │ ├── NativeLibraryLocator.java │ │ │ ├── NativeMonitorInfo.java │ │ │ ├── NativeSystem.java │ │ │ ├── dispatcher │ │ │ ├── DefaultDispatchService.java │ │ │ ├── SwingDispatchService.java │ │ │ ├── VoidDispatchService.java │ │ │ └── package-info.java │ │ │ ├── example │ │ │ ├── NativeHookDemo.java │ │ │ └── package-info.java │ │ │ ├── keyboard │ │ │ ├── NativeKeyAdapter.java │ │ │ ├── NativeKeyEvent.java │ │ │ ├── NativeKeyListener.java │ │ │ ├── SwingKeyAdapter.java │ │ │ └── package-info.java │ │ │ └── mouse │ │ │ ├── NativeMouseAdapter.java │ │ │ ├── NativeMouseEvent.java │ │ │ ├── NativeMouseInputAdapter.java │ │ │ ├── NativeMouseInputListener.java │ │ │ ├── NativeMouseListener.java │ │ │ ├── NativeMouseMotionAdapter.java │ │ │ ├── NativeMouseMotionListener.java │ │ │ ├── NativeMouseWheelAdapter.java │ │ │ ├── NativeMouseWheelEvent.java │ │ │ ├── NativeMouseWheelListener.java │ │ │ ├── SwingMouseAdapter.java │ │ │ ├── SwingMouseWheelAdapter.java │ │ │ └── package-info.java │ └── module-info.java └── jni │ ├── com_github_kwhat_jnativehook_GlobalScreen.c │ ├── include │ ├── com_github_kwhat_jnativehook_NativeInputEvent.h │ ├── com_github_kwhat_jnativehook_keyboard_NativeKeyEvent.h │ ├── com_github_kwhat_jnativehook_mouse_NativeMouseEvent.h │ └── com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent.h │ ├── jni_Converter.c │ ├── jni_Converter.h │ ├── jni_Errors.c │ ├── jni_Errors.h │ ├── jni_EventDispatcher.c │ ├── jni_EventDispathcer.h │ ├── jni_Globals.c │ ├── jni_Globals.h │ ├── jni_Load.c │ ├── jni_Logger.c │ └── jni_Logger.h └── test └── java └── com └── github └── kwhat └── jnativehook ├── NativeHookExceptionTest.java ├── NativeInputEventTest.java ├── NativeMonitorInfoTest.java ├── NativeSystemTest.java ├── dispatcher └── VoidDispatchServiceTest.java ├── keyboard ├── NativeKeyEventTest.java ├── NativeKeyListenerTest.java └── listeners │ └── NativeKeyListenerTest.java └── mouse ├── NativeMouseEventTest.java ├── NativeMouseListenerTest.java ├── NativeMouseMotionListenerTest.java ├── NativeMouseWheelEventTest.java ├── NativeMouseWheelListenerTest.java ├── SwingMouseAdapterTest.java └── listeners ├── NativeMouseInputListenerTest.java └── NativeMouseWheelListenerTest.java /.gitignore: -------------------------------------------------------------------------------- 1 | /.idea/ 2 | /.vs/ 3 | /src/main/resources 4 | /target/ 5 | *.iml 6 | *build.properties 7 | *.project 8 | *.classpath 9 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "libuiohook"] 2 | path = src/external/libuiohook 3 | url = git@github.com:kwhat/libuiohook.git 4 | branch = 1.2 5 | -------------------------------------------------------------------------------- /AUTHORS: -------------------------------------------------------------------------------- 1 | Alexander Barker 2 | 3 | Aidas Adomkus 4 | NativeLibraryLocator interface and locator override concept 5 | 6 | Johannes Boczek 7 | Input adapter classes 8 | 9 | Amir Sangi 10 | JavaFX Key Adapter class 11 | -------------------------------------------------------------------------------- /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # JNativeHook: Global keyboard and mouse listeners for Java. 2 | # Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | # https://github.com/kwhat/jnativehook/ 4 | 5 | # JNativeHook is free software: you can redistribute it and/or modify 6 | # it under the terms of the GNU Lesser General Public License as published 7 | # by the Free Software Foundation, either version 3 of the License, or 8 | # (at your option) any later version. 9 | # 10 | # JNativeHook is distributed in the hope that it will be useful, 11 | # but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | # GNU General Public License for more details. 14 | # 15 | # You should have received a copy of the GNU Lesser General Public License 16 | # along with this program. If not, see . 17 | 18 | cmake_minimum_required(VERSION 3.10) 19 | 20 | project(JNativeHook VERSION 2.2.0 LANGUAGES C) 21 | 22 | if(NOT CMAKE_SYSTEM_NAME STREQUAL "") 23 | string(TOLOWER ${CMAKE_SYSTEM_NAME} TARGET_OS) 24 | set(CMAKE_INSTALL_PREFIX "${PROJECT_SOURCE_DIR}/src/main/resources/com/github/kwhat/jnativehook/lib/${TARGET_OS}" CACHE PATH "Internal var" FORCE) 25 | else() 26 | message(FATAL_ERROR "Could not determine target system. Please set CMAKE_SYSTEM_NAME to the desired resource folder.") 27 | endif() 28 | 29 | 30 | string(TOLOWER ${CMAKE_SYSTEM_PROCESSOR} TARGET_PROCESSOR) 31 | if(TARGET_PROCESSOR STREQUAL x86_64 OR TARGET_PROCESSOR STREQUAL amd64) 32 | set(CMAKE_INSTALL_LIBDIR "x86_64" CACHE PATH "Internal var" FORCE) 33 | elseif(TARGET_PROCESSOR STREQUAL x86 OR TARGET_PROCESSOR MATCHES "i.86") 34 | set(CMAKE_INSTALL_LIBDIR "x86" CACHE PATH "Internal var" FORCE) 35 | elseif(TARGET_PROCESSOR MATCHES "^arm" OR TARGET_PROCESSOR MATCHES "^aarch") 36 | if(TARGET_PROCESSOR MATCHES "64$") 37 | set(CMAKE_INSTALL_LIBDIR "arm64" CACHE PATH "Internal var" FORCE) 38 | else() 39 | set(CMAKE_INSTALL_LIBDIR "arm" CACHE PATH "Internal var" FORCE) 40 | endif() 41 | elseif(TARGET_PROCESSOR MATCHES "^ppc" OR TARGET_PROCESSOR MATCHES "^power") 42 | if(TARGET_PROCESSOR MATCHES "64$") 43 | set(CMAKE_INSTALL_LIBDIR "ppc64" CACHE PATH "Internal var" FORCE) 44 | else() 45 | set(CMAKE_INSTALL_LIBDIR "ppc" CACHE PATH "Internal var" FORCE) 46 | endif() 47 | elseif(NOT CMAKE_SYSTEM_NAME STREQUAL "") 48 | message(FATAL_ERROR "Unsupported target architecture \"${CMAKE_SYSTEM_PROCESSOR}\".") 49 | else() 50 | message(FATAL_ERROR "Could not determine target architecture. Please set CMAKE_SYSTEM_PROCESSOR to the desired resource folder.") 51 | endif() 52 | 53 | if(APPLE) 54 | set(CMAKE_MACOSX_RPATH 1) 55 | set(CMAKE_OSX_DEPLOYMENT_TARGET "10.5") 56 | endif() 57 | 58 | 59 | find_package(JNI) 60 | if(NOT JNI_FOUND) 61 | message(FATAL_ERROR "Could not determine Java include path. Please set your JAVA_HOME environment variable to the location of the desired JDK.") 62 | endif() 63 | 64 | add_library(jnativehook SHARED 65 | "./src/main/jni/jni_Converter.c" 66 | "./src/main/jni/jni_Errors.c" 67 | "./src/main/jni/jni_EventDispatcher.c" 68 | "./src/main/jni/jni_Globals.c" 69 | "./src/main/jni/jni_Load.c" 70 | "./src/main/jni/jni_Logger.c" 71 | "./src/main/jni/com_github_kwhat_jnativehook_GlobalScreen.c" 72 | ) 73 | 74 | set_target_properties(jnativehook PROPERTIES 75 | PROPERTY C_STANDARD 99 76 | PROPERTY C_STANDARD_REQUIRED ON 77 | OUTPUT_NAME ${CMAKE_PROJECT_NAME} 78 | ) 79 | 80 | find_package(uiohook REQUIRED) 81 | target_link_libraries(jnativehook uiohook) 82 | 83 | target_include_directories(jnativehook 84 | PUBLIC 85 | $ 86 | 87 | PRIVATE 88 | ${CMAKE_CURRENT_SOURCE_DIR}/src/main/jni 89 | ${CMAKE_CURRENT_SOURCE_DIR}/src/main/jni/include 90 | ) 91 | 92 | if(UNIX) 93 | find_package(Threads REQUIRED) 94 | target_link_libraries(jnativehook "${CMAKE_THREAD_LIBS_INIT}") 95 | endif() 96 | 97 | install(TARGETS jnativehook RUNTIME DESTINATION ${CMAKE_INSTALL_LIBDIR}) 98 | -------------------------------------------------------------------------------- /COPYING.LESSER.md: -------------------------------------------------------------------------------- 1 | GNU Lesser General Public License 2 | ================================= 3 | 4 | Version 3, 29 June 2007 5 | 6 | Copyright © 2007 Free Software Foundation, Inc. <> 7 | 8 | Everyone is permitted to copy and distribute verbatim copies 9 | of this license document, but changing it is not allowed. 10 | 11 | 12 | This version of the GNU Lesser General Public License incorporates 13 | the terms and conditions of version 3 of the GNU General Public 14 | License, supplemented by the additional permissions listed below. 15 | 16 | ### 0. Additional Definitions. 17 | 18 | As used herein, “this License” refers to version 3 of the GNU Lesser 19 | General Public License, and the “GNU GPL” refers to version 3 of the GNU 20 | General Public License. 21 | 22 | “The Library” refers to a covered work governed by this License, 23 | other than an Application or a Combined Work as defined below. 24 | 25 | An “Application” is any work that makes use of an interface provided 26 | by the Library, but which is not otherwise based on the Library. 27 | Defining a subclass of a class defined by the Library is deemed a mode 28 | of using an interface provided by the Library. 29 | 30 | A “Combined Work” is a work produced by combining or linking an 31 | Application with the Library. The particular version of the Library 32 | with which the Combined Work was made is also called the “Linked 33 | Version”. 34 | 35 | The “Minimal Corresponding Source” for a Combined Work means the 36 | Corresponding Source for the Combined Work, excluding any source code 37 | for portions of the Combined Work that, considered in isolation, are 38 | based on the Application, and not on the Linked Version. 39 | 40 | The “Corresponding Application Code” for a Combined Work means the 41 | object code and/or source code for the Application, including any data 42 | and utility programs needed for reproducing the Combined Work from the 43 | Application, but excluding the System Libraries of the Combined Work. 44 | 45 | ### 1. Exception to Section 3 of the GNU GPL. 46 | 47 | You may convey a covered work under sections 3 and 4 of this License 48 | without being bound by section 3 of the GNU GPL. 49 | 50 | ### 2. Conveying Modified Versions. 51 | 52 | If you modify a copy of the Library, and, in your modifications, a 53 | facility refers to a function or data to be supplied by an Application 54 | that uses the facility (other than as an argument passed when the 55 | facility is invoked), then you may convey a copy of the modified 56 | version: 57 | 58 | * a) under this License, provided that you make a good faith effort to 59 | ensure that, in the event an Application does not supply the 60 | function or data, the facility still operates, and performs 61 | whatever part of its purpose remains meaningful, or 62 | 63 | * b) under the GNU GPL, with none of the additional permissions of 64 | this License applicable to that copy. 65 | 66 | ### 3. Object Code Incorporating Material from Library Header Files. 67 | 68 | The object code form of an Application may incorporate material from 69 | a header file that is part of the Library. You may convey such object 70 | code under terms of your choice, provided that, if the incorporated 71 | material is not limited to numerical parameters, data structure 72 | layouts and accessors, or small macros, inline functions and templates 73 | (ten or fewer lines in length), you do both of the following: 74 | 75 | * a) Give prominent notice with each copy of the object code that the 76 | Library is used in it and that the Library and its use are 77 | covered by this License. 78 | * b) Accompany the object code with a copy of the GNU GPL and this license 79 | document. 80 | 81 | ### 4. Combined Works. 82 | 83 | You may convey a Combined Work under terms of your choice that, 84 | taken together, effectively do not restrict modification of the 85 | portions of the Library contained in the Combined Work and reverse 86 | engineering for debugging such modifications, if you also do each of 87 | the following: 88 | 89 | * a) Give prominent notice with each copy of the Combined Work that 90 | the Library is used in it and that the Library and its use are 91 | covered by this License. 92 | 93 | * b) Accompany the Combined Work with a copy of the GNU GPL and this license 94 | document. 95 | 96 | * c) For a Combined Work that displays copyright notices during 97 | execution, include the copyright notice for the Library among 98 | these notices, as well as a reference directing the user to the 99 | copies of the GNU GPL and this license document. 100 | 101 | * d) Do one of the following: 102 | - 0) Convey the Minimal Corresponding Source under the terms of this 103 | License, and the Corresponding Application Code in a form 104 | suitable for, and under terms that permit, the user to 105 | recombine or relink the Application with a modified version of 106 | the Linked Version to produce a modified Combined Work, in the 107 | manner specified by section 6 of the GNU GPL for conveying 108 | Corresponding Source. 109 | - 1) Use a suitable shared library mechanism for linking with the 110 | Library. A suitable mechanism is one that (a) uses at run time 111 | a copy of the Library already present on the user's computer 112 | system, and (b) will operate properly with a modified version 113 | of the Library that is interface-compatible with the Linked 114 | Version. 115 | 116 | * e) Provide Installation Information, but only if you would otherwise 117 | be required to provide such information under section 6 of the 118 | GNU GPL, and only to the extent that such information is 119 | necessary to install and execute a modified version of the 120 | Combined Work produced by recombining or relinking the 121 | Application with a modified version of the Linked Version. (If 122 | you use option 4d0, the Installation Information must accompany 123 | the Minimal Corresponding Source and Corresponding Application 124 | Code. If you use option 4d1, you must provide the Installation 125 | Information in the manner specified by section 6 of the GNU GPL 126 | for conveying Corresponding Source.) 127 | 128 | ### 5. Combined Libraries. 129 | 130 | You may place library facilities that are a work based on the 131 | Library side by side in a single library together with other library 132 | facilities that are not Applications and are not covered by this 133 | License, and convey such a combined library under terms of your 134 | choice, if you do both of the following: 135 | 136 | * a) Accompany the combined library with a copy of the same work based 137 | on the Library, uncombined with any other library facilities, 138 | conveyed under the terms of this License. 139 | * b) Give prominent notice with the combined library that part of it 140 | is a work based on the Library, and explaining where to find the 141 | accompanying uncombined form of the same work. 142 | 143 | ### 6. Revised Versions of the GNU Lesser General Public License. 144 | 145 | The Free Software Foundation may publish revised and/or new versions 146 | of the GNU Lesser General Public License from time to time. Such new 147 | versions will be similar in spirit to the present version, but may 148 | differ in detail to address new problems or concerns. 149 | 150 | Each version is given a distinguishing version number. If the 151 | Library as you received it specifies that a certain numbered version 152 | of the GNU Lesser General Public License “or any later version” 153 | applies to it, you have the option of following the terms and 154 | conditions either of that published version or of any later version 155 | published by the Free Software Foundation. If the Library as you 156 | received it does not specify a version number of the GNU Lesser 157 | General Public License, you may choose any version of the GNU Lesser 158 | General Public License ever published by the Free Software Foundation. 159 | 160 | If the Library as you received it specifies that a proxy can decide 161 | whether future versions of the GNU Lesser General Public License shall 162 | apply, that proxy's public statement of acceptance of any version is 163 | permanent authorization for you to choose that version for the 164 | Library. 165 | -------------------------------------------------------------------------------- /ChangeLog.md: -------------------------------------------------------------------------------- 1 | ## ChangeLog 2 | 3 | **JNativeHook 2.2.2 (Mar 18, 2022)** 4 | * Fixed Java module issue. 5 | * Fixed crash when using getNativeMonitors on Windows. 6 | * Fixed deadlock issue on Windows. 7 | * Fixed deadlock issue on OS X. 8 | * Fixed event posting issues on all platforms. 9 | * Fixed mouse button issues on Linux. 10 | * Fixed mouse horizontal scroll direction on Windows. 11 | * Fixed key character issues on Linux. 12 | * Fixed key typed event issues on Windows. 13 | * Fixed invalid system properties on OS X. 14 | * Updating system property sources on OS X. 15 | * Updated compile documentation. 16 | 17 | **JNativeHook 2.2.1 (Nov 19, 2021)** 18 | * Added support for Java 17 19 | * Fixed crash on Linux with xkb-file and pc105. 20 | * Fixed crash on OSX with capslock and media keys. 21 | * Fixed pom versioning issue with revision property. 22 | * Fixed library location issues with folders that contain spaces. 23 | 24 | **JNativeHook 2.2.0 (Sep 27, 2021)** 25 | * Complete CI/CD overhaul using GitHub Actions. 26 | * Dropping Ant support in favor of CMake and Maven. 27 | * Changed Maven group id to com.github.kwhat. 28 | * Namespace migration due to Maven group id change. 29 | * Added support for Arm on Windows. 30 | * Added support for Arm 64 on OS X and Linux. 31 | * Added support for multi-release jars. 32 | * Added wiki docs to the project. 33 | * Added VoidDispatcher class. 34 | * Fixed logging to be less verbose by default. 35 | * Fixed native library extraction location. 36 | * Fixed issue with unregistering the hook. 37 | * Fixed could not find keyboard map for locale on Windows. 38 | * Fixed issue with setEventDispatcher being overridden on hook registration. 39 | * Fixed issue with dead keys not working in some situations. 40 | * Deprecated all adaptor classes. 41 | * Deprecated NativeInputEvent.setModifiers() and NativeInputEvent.setReserved(). 42 | * Removed support for Java 1.5. 43 | 44 | **JNativeHook 2.1.0 (Jan 25, 2015)** 45 | * All events now use the native time source instead of the Unix epoch. 46 | * Added adapter classes. 47 | * Added native monitor properties. 48 | * Added method calls for global properties. 49 | * Added support for keyboard lock masks. 50 | * Added support for Swing event conversion. 51 | * Relaxed GlobalScreen scope restrictions. 52 | * Fixed a major issue with UTF-16 support on Linux. 53 | * Fixed key mapping for the number pad on Linux. 54 | * Fixed language support on X11 platforms. 55 | * Code refactoring and organization. 56 | 57 | **JNativeHook 2.0.3 (Nov 02, 2015)** 58 | * Added support for media keys on OS X. 59 | * Added wiki pages to the project. 60 | * Fixed caps-lock key release on OS X. 61 | * Fixed posting mouse coordinates on Windows and Linux. 62 | * Fixed posting number keys on Windows. 63 | * Fixed segfault with multiple instances on Linux. 64 | * Fixed SetWindowsHookEx failed with 0X7E error on Windows. 65 | * Fixed the coordinates of posted mouse events for Windows. 66 | * Small documentation updates. 67 | 68 | **JNativeHook 2.0.2 (Jun 28, 2015)** 69 | * Added support for Maven central repository. 70 | * Added modifier polling to hook start procedure. 71 | * Fixed a bug on OS X where the hook would always succeed. 72 | * Fixed event timing issues for all platforms. 73 | * Fixed issue with build.property file included in the release package. 74 | * Various cleanups throughout the code base. 75 | 76 | **JNativeHook 2.0.1 (Mar 21, 2015)** 77 | * Added support for dispatch_sync_f when available on OS X. 78 | * Added libuiohook as a git submodule. 79 | * Changed hard coded dlsym() paths to RTLD_DEFAULT on OS X. 80 | * Fixed a memory leak in event posting on OS X. 81 | * Fixed an LTO related crash on Linux. 82 | * Fixed missing button number of mouse pressed events on Windows. 83 | 84 | **JNativeHook 2.0.0 (Jan 27, 2015)** 85 | * Total rewrite and fork of the native code to its own [standalone project](https://github.com/kwhat/libuiohook). 86 | * Transitioned to virtual keycodes backed by scancode set 1. 87 | * Added Java's ExecutorService support for event delivery. 88 | * Added the ability to post NativeInputEvent's back to the Operating System. 89 | * Added support for multi-head hosts. 90 | * Countless bug fixes and performance improvements. 91 | * Fixed a long-standing RDP capture issue. 92 | * More flexible library loading. 93 | * More accurate event timestamps. 94 | * Removed the vestigial singleton API. 95 | * Vastly improved the build process. 96 | 97 | **JNativeHook 1.1.4 (Mar 17, 2013)** 98 | * Added no-strict-aliasing compiler option that is enabled by default for all platforms. 99 | * Fixed 100% CPU utilization on Linux when using asynchronous XRecord API. 100 | * Fixed a crash when re-registering the native hook on all platforms. 101 | * Fixed the dead key interpretation for key typed events on Windows. 102 | * Improved language support for multiple locales on Windows. 103 | * Improved the memory utilization for the demo application. 104 | * Updated the demo application to allow unregistering and re-registering of the global hook. 105 | * Various cleanups throughout the native code base. 106 | 107 | **JNativeHook 1.1.3 (Jan 2, 2013)** 108 | * Fixed a JVM memory leak due to NativeInputEvent objects not being garbage collected. 109 | * Fixed exception for assistive devices on OS X. 110 | * Fixed JNLP and custom class loading issues in native code. 111 | * Fixed mouse click events on Windows. 112 | * Fixed key typed events for OS X, again. This should prevent the TSMProcessRawKeyCode failed (-192) errors from popping up. 113 | * Fixed key typed events for tab, enter and number pad keys on X11 platforms. 114 | * Improved key char lookup for OSX. 115 | * Updated the author and license of the code used in WinUnicodeHelper. 116 | 117 | **JNativeHook 1.1.2 (Nov 5, 2012)** 118 | * Added asynchronous XRecord build option and enabled it by default for Unix. 119 | * Fixed the click count for OS X. 120 | * Fixed key character lookup including support for dead keys on OS X. 121 | * Improved stability for synchronous XRecord on Unix. 122 | * Improved thread startup and shutdown across all platforms. 123 | * Improved thread safety for Unix and OS X. 124 | * Various cleanups throughout the native code base. 125 | 126 | **JNativeHook 1.1.1 (Oct 17, 2012)** 127 | * Added an explicit exception if the native library not found. 128 | * Added safety checks to the Windows unicode helper function. 129 | * Changed to listen only tap for OS X. 130 | * Fixed a few small memory leaks for OS X. 131 | * Fixed click count for OS X. 132 | * Fixed free() on static memory pointer for Unix and OS X. 133 | * Fixed potential sscanf overflow on Unix. 134 | * Fixed potential use of a null pointer in rare circumstances for Unix and OS X. 135 | * Fixed several unicode conversions for Unix. 136 | * Fixed ant run target java library path. 137 | * Improved ant platform compatibility. 138 | * Removed unneeded ActionListener from the NativeHookDemo. 139 | * Various cleanups throughout the native code base. 140 | 141 | **JNativeHook 1.1.0 (Sep 10, 2012)** 142 | * Total rewrite and restructuring of the native code base. 143 | * Added support for key typed events. 144 | * Added support for action key checks. 145 | * Added support for mouse click events. 146 | * Added support for mouse drag events. 147 | * Added support for mouse wheel events. 148 | * Improved both native and Java thread safety. 149 | * Improved unpacking of the native library from the Jar. 150 | * Improved operating system compatibility. 151 | * Optimized native code for all platforms. 152 | * Removed Make dependency. 153 | * Workaround for Java web start shortfalls. 154 | 155 | **JNativeHook 1.0.2288 (Sep 23, 2011)** 156 | * Added button masks to all platforms for consistency. 157 | * Added checks for null on GlobalScreen listener addition and removal. 158 | * Added WM_QUIT exit listener instead of isRunning boolean for Windows message loop. 159 | * Changed Carbon constant for the Context Menu to a user defined value in OSXKeyCodes.h. 160 | * Enabled sun.awt.enableExtraMouseButtons by default. 161 | * Fixed an issue with Linux mouse buttons 4 and 5. Switched to using the standard virtual button codes for events. 162 | * Fixed various typos. 163 | * Fixed the termination order for Unix/Linux XRecord connection. 164 | * Fixed an issue with the MouseEvent constructor id for all platforms. Used a separate id for mouse button and motion events. 165 | * Fixed the double event registration issue with the demo. 166 | * Fixed issue with Makefile error message not displaying if run outside of ant. 167 | * Fixed issues with null pointer VM crashes due to garbage collection for all platforms. 168 | * Fixed RunLoop termination on OS X. 169 | * Fixed issues with the OS X button modifiers. 170 | * Improved MinGW compatibility Windows. 171 | * Improved event delivery performance for all platforms. 172 | * Removed Carbon code from the keyboard rate and delay functions on OS X. 173 | * Removed the Carbon HIToolbox requirement for key constants on OS X. 174 | * Switch to async XRecord connection. 175 | * Switch from Carbon to ApplicationServices framework for key hooking on OS X. 176 | 177 | **JNativeHook 1.0.1950 (Aug 30, 2011)** 178 | * Fixed a problem with the 32-bit OS X binary. 179 | * Fixed various typos. 180 | * Removed unneeded `-framework JavaVM` for OS X targets. 181 | * Improved build file. 182 | 183 | **JNativeHook 1.0.1840 (May 11, 2011)** 184 | * Initial Release. 185 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | JNativeHook: Global keyboard and mouse listeners for Java. 2 | ========================================================== 3 | 4 | [![Maven Central](https://maven-badges.herokuapp.com/maven-central/com.github.kwhat/jnativehook/badge.svg)](https://maven-badges.herokuapp.com/maven-central/com.github.kwhat/jnativehook) 5 | ![Nightly Build](https://github.com/kwhat/jnativehook/workflows/Nightly%20Build/badge.svg) 6 | 7 | ## About 8 | JNativeHook is a library to provide global keyboard and mouse listeners for Java. This will allow you to listen for 9 | global shortcuts or mouse motion that would otherwise be impossible using pure Java. To accomplish this task, 10 | JNativeHook leverages platform-dependent native code through Java's native interface to create low-level system-wide 11 | hooks and deliver those events to your application. 12 | 13 | The following events are available via their respective listeners. 14 | * Key Press Events 15 | * Key Release Events 16 | * Key Typed Events 17 | * Mouse Down Events 18 | * Mouse Up Events 19 | * Mouse Click Events 20 | * Mouse Move Events 21 | * Mouse Drag Events 22 | * Mouse Wheel Events 23 | 24 | In addition to global event listeners, this library has the ability to post native events back to the native operating 25 | system. 26 | 27 | ## Licensing 28 | JNativeHook is covered under the [GNU Lesser General Public License](COPYING.LESSER.md) which is an extension of the 29 | [GNU General Public License](COPYING.md) that grants you additional distribution rights. As I understand it, you may 30 | use this library in proprietary (closed source) projects so long as it remains an external library with the same binary 31 | interface. You may modify the source code of this library to fulfill any proprietary need, as long as those 32 | modifications are made available under the terms and conditions of the LGPL. Please consult with a licenced attorney 33 | if you have additional licence compatibility questions or concerns. 34 | 35 | ## Download 36 | Binary distribution for JNativeHook can be found at the 37 | [releases](https://github.com/kwhat/jnativehook/releases) section of the 38 | [project page](https://github.com/kwhat/jnativehook). Maven users can 39 | use the `com.github.kwhat` and `jnativehook` 40 | to include this library automatically. The nightly builds can be found at the maven 41 | [snapshot repository](https://oss.sonatype.org/content/repositories/snapshots/com/github/kwhat/jnativehook/2.2-SNAPSHOT). 42 | 43 | ## Software and Hardware Requirements 44 | * Java 1.8 - 17 45 | * 256 MB of RAM 46 | * Apple OS X 10.5 - 10.15 47 | * amd64, aarch64 48 | * Enable Access for Assistive Devices 49 | * Windows 2000 - 10 50 | * i586, amd64, arm7 51 | * X11 Linux 52 | * i586, amd64, arm7, aarch64 53 | * libxkbfile.so.1 54 | * libxkbcommon-x11.so.0 55 | * libxkbcommon.so.0 56 | * libX11-xcb.so.1 57 | * libX11.so.6 58 | * libxcb.so.1 59 | * libXinerama.so.1 60 | * libXt.so.6 61 | * libXtst.so.6 62 | * libc.so.6 63 | * libxcb-xkb.so.1 64 | * libdl.so.2 65 | * libXau.so.6 66 | * libXdmcp.so.6 67 | * libXext.so.6 68 | * libSM.so.6 69 | * libICE.so.6 70 | * libbsd.so.0 71 | * libuuid.so.1 72 | * librt.so.1 73 | * libpthread.so.0 74 | 75 | ## Donate 76 | If you have found this library useful, please consider making a donation. 77 | [![Donate](https://www.paypalobjects.com/en_US/i/btn/btn_donate_LG.gif)](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=UPMHT4ZFBTCBL) 78 | 79 | ## Documentation 80 | * [Global Keyboard Listener](doc/Keyboard.md) 81 | * [Global Mouse Listener](doc/Mouse.md) 82 | * [Global Mouse Wheel Listener](doc/MouseWheel.md) 83 | * [Thread Safety for AWT, Swing and JavaFX](doc/Swing.md) 84 | * [Logging and Console Output](doc/ConsoleOutput.md) 85 | * [Advanced Library Loading](doc/LibraryLoading.md) 86 | * [Consuming Events (Unsupported)](doc/ConsumingEvents.md) 87 | 88 | ## Demo Application 89 | The graphical example application exists to provide a real-time demonstration of raw output for all available native 90 | events. To run the application simply execute the jar file provided. Source code available at 91 | [src/main/java/com/github/kwhat/jnativehook/example/NativeHookDemo.java](src/main/java/com/github/kwhat/jnativehook/example/NativeHookDemo.java). 92 | 93 | ## Additional Information 94 | Up-to-date source code and documentation available at: 95 | [https://github.com/kwhat/jnativehook/](https://github.com/kwhat/jnativehook/) 96 | -------------------------------------------------------------------------------- /doc/Compiling.md: -------------------------------------------------------------------------------- 1 | ## Introduction 2 | JNativeHook should compile on all operating systems that support Java. Unix and Linux based systems will require the 3 | X Window System for compilation and execution. This is not an easy library to build from source. It requires the 4 | compilation of both Java class files and native C code that must be compiled separately for each target platform. If 5 | you do not have experience building software from source, you may find it easier to simply fork this repository and 6 | use the [GitHub actions](../.github/workflows/continuous-integration.yml) provided to automatically build your changes 7 | on all supported platforms. 8 | 9 | ## Dependencies 10 | * [Oracle's JDK](http://www.oracle.com/technetwork/java/javase/downloads/index.html) or [OpenJDK](https://jdk.java.net/) 11 | * [Maven](https://maven.apache.org/download.cgi) 12 | * [CMake](https://cmake.org) 13 | * GCC, CLang or MSVC 14 | * Unix / Linux dependencies: 15 | * libx11-dev 16 | * libxtst-dev 17 | * libxt-dev 18 | * libxinerama-dev 19 | * libx11-xcb-dev 20 | * libxkbcommon-dev 21 | * libxkbcommon-x11-dev 22 | * libxkbfile-dev 23 | 24 | ## Building 25 | Building this library is a multistep process. All native code will need to be compiled for the target system 26 | individually. All JNI libraries should be installed in the [resources](../src/main/resources) folder under the target 27 | operating system and architecture automatically. 28 | 29 | If you are building for multiple targets consecutively, remember to remove the 30 | [build](../target/build) directory before starting on the next target. 31 | 32 | ### Compile Java 33 | Java class files need to be compiled first to generate the JNI headers. Maven will build all supported Java targets 34 | up and including the JDK version currently being used. 35 | ``` 36 | mvn compile 37 | ``` 38 | 39 | ### Compile Native Libraries 40 | You only need to build native libraries if you plan on modify the external sources. You can skip this step by 41 | downloading the [library-resources](https://github.com/kwhat/jnativehook/actions?query=event%3Arelease) artifact 42 | produced by GitHub actions and extracting them to the [resources](../src/main/resources) folder. These prebuilt 43 | resources can be mixed with the precompiled resources if you are only making changes to specific platforms. Platforms 44 | can also be omitted if they are not required for your build. Only 1 native library is required for this library to 45 | function, but it will only function on platforms that have native libraries available. 46 | 47 | #### Compile Apple ARM64 48 | ``` 49 | mkdir -p target/build/libuiohook/ 50 | cmake -B target/build/libuiohook/ -S src/external/libuiohook/ \ 51 | -G "Unix Makefiles" \ 52 | -D CMAKE_INSTALL_PREFIX=target/ \ 53 | -D CMAKE_VERBOSE_MAKEFILE=ON \ 54 | -D BUILD_SHARED_LIBS=OFF \ 55 | -D USE_EPOCH_TIME=ON 56 | 57 | cmake --build target/build/libuiohook/ \ 58 | --parallel 2 \ 59 | --clean-first 60 | 61 | cmake --install target/build/libuiohook/ 62 | ``` 63 | 64 | ``` 65 | mkdir -p target/build/jni/ 66 | cmake -B target/build/jni/ \ 67 | -G "Unix Makefiles" \ 68 | -D CMAKE_PREFIX_PATH=target/ \ 69 | -D CMAKE_SYSTEM_NAME=darwin \ 70 | -D CMAKE_SYSTEM_PROCESSOR=arm64 \ 71 | -D CMAKE_VERBOSE_MAKEFILE=ON 72 | 73 | cmake --build target/build/jni/ \ 74 | --parallel 2 \ 75 | --clean-first 76 | 77 | cmake --install target/build/jni/ 78 | ``` 79 | 80 | #### Compile Apple x86_64 81 | ``` 82 | mkdir -p target/build/libuiohook/ 83 | cmake -B target/build/libuiohook/ -S src/external/libuiohook/ \ 84 | -G "Unix Makefiles" \ 85 | -D CMAKE_INSTALL_PREFIX=target/ \ 86 | -D CMAKE_VERBOSE_MAKEFILE=ON \ 87 | -D BUILD_SHARED_LIBS=OFF \ 88 | -D USE_EPOCH_TIME=ON 89 | 90 | cmake --build target/build/libuiohook/ \ 91 | --parallel 2 \ 92 | --clean-first 93 | 94 | cmake --install target/build/libuiohook/ 95 | ``` 96 | 97 | ``` 98 | mkdir -p target/build/jni/ 99 | cmake -B target/build/jni/ \ 100 | -G "Unix Makefiles" \ 101 | -D CMAKE_PREFIX_PATH=target/ \ 102 | -D CMAKE_SYSTEM_NAME=darwin \ 103 | -D CMAKE_SYSTEM_PROCESSOR=x86_64 \ 104 | -D CMAKE_VERBOSE_MAKEFILE=ON 105 | 106 | cmake --build target/build/jni/ \ 107 | --parallel 2 \ 108 | --clean-first 109 | 110 | cmake --install target/build/jni/ 111 | ``` 112 | 113 | #### Compile Linux ARM 114 | ``` 115 | mkdir -p target/build/libuiohook/ 116 | cmake -B target/build/libuiohook/ -S src/external/libuiohook/ \ 117 | -G "Unix Makefiles" \ 118 | -D CMAKE_INSTALL_PREFIX=target/ \ 119 | -D CMAKE_VERBOSE_MAKEFILE=ON \ 120 | -D BUILD_SHARED_LIBS=OFF \ 121 | -D USE_EPOCH_TIME=ON 122 | 123 | cmake --build target/build/libuiohook/ \ 124 | --parallel 2 \ 125 | --clean-first 126 | 127 | cmake --install target/build/libuiohook/ 128 | ``` 129 | 130 | ``` 131 | mkdir -p target/build/jni/ 132 | cmake -B target/build/jni/ \ 133 | -G "Unix Makefiles" \ 134 | -D CMAKE_PREFIX_PATH=target/ \ 135 | -D CMAKE_SYSTEM_NAME=linux \ 136 | -D CMAKE_SYSTEM_PROCESSOR=arm \ 137 | -D CMAKE_VERBOSE_MAKEFILE=ON 138 | 139 | cmake --build target/build/jni/ \ 140 | --parallel 2 \ 141 | --clean-first 142 | 143 | cmake --install target/build/jni/ 144 | ``` 145 | 146 | #### Compile Linux ARM64 147 | ``` 148 | mkdir -p target/build/libuiohook/ 149 | cmake -B target/build/libuiohook/ -S src/external/libuiohook/ \ 150 | -G "Unix Makefiles" \ 151 | -D CMAKE_INSTALL_PREFIX=target/ \ 152 | -D CMAKE_VERBOSE_MAKEFILE=ON \ 153 | -D BUILD_SHARED_LIBS=OFF \ 154 | -D USE_EPOCH_TIME=ON 155 | 156 | cmake --build target/build/libuiohook/ \ 157 | --parallel 2 \ 158 | --clean-first 159 | 160 | cmake --install target/build/libuiohook/ 161 | ``` 162 | 163 | ``` 164 | mkdir -p target/build/jni/ 165 | cmake -B target/build/jni/ \ 166 | -G "Unix Makefiles" \ 167 | -D CMAKE_PREFIX_PATH=target/ \ 168 | -D CMAKE_SYSTEM_NAME=linux \ 169 | -D CMAKE_SYSTEM_PROCESSOR=arm64 \ 170 | -D CMAKE_VERBOSE_MAKEFILE=ON 171 | 172 | cmake --build target/build/jni/ \ 173 | --parallel 2 \ 174 | --clean-first 175 | 176 | cmake --install target/build/jni/ 177 | ``` 178 | 179 | #### Compile Linux x86 180 | ``` 181 | mkdir -p target/build/libuiohook/ 182 | cmake -B target/build/libuiohook/ -S src/external/libuiohook/ \ 183 | -G "Unix Makefiles" \ 184 | -D CMAKE_INSTALL_PREFIX=target/ \ 185 | -D CMAKE_VERBOSE_MAKEFILE=ON \ 186 | -D BUILD_SHARED_LIBS=OFF \ 187 | -D USE_EPOCH_TIME=ON 188 | 189 | cmake --build target/build/libuiohook/ \ 190 | --parallel 2 \ 191 | --clean-first 192 | 193 | cmake --install target/build/libuiohook/ 194 | ``` 195 | 196 | ``` 197 | mkdir -p target/build/jni/ 198 | cmake -B target/build/jni/ \ 199 | -G "Unix Makefiles" \ 200 | -D CMAKE_PREFIX_PATH=target/ \ 201 | -D CMAKE_SYSTEM_NAME=linux \ 202 | -D CMAKE_SYSTEM_PROCESSOR=x86 \ 203 | -D CMAKE_VERBOSE_MAKEFILE=ON 204 | 205 | cmake --build target/build/jni/ \ 206 | --parallel 2 \ 207 | --clean-first 208 | 209 | cmake --install target/build/jni/ 210 | ``` 211 | 212 | #### Compile Linux x86_64 213 | ``` 214 | mkdir -p target/build/libuiohook/ 215 | cmake -B target/build/libuiohook/ -S src/external/libuiohook/ \ 216 | -G "Unix Makefiles" \ 217 | -D CMAKE_INSTALL_PREFIX=target/ \ 218 | -D CMAKE_VERBOSE_MAKEFILE=ON \ 219 | -D BUILD_SHARED_LIBS=OFF \ 220 | -D USE_EPOCH_TIME=ON 221 | 222 | cmake --build target/build/libuiohook/ \ 223 | --parallel 2 \ 224 | --clean-first 225 | 226 | cmake --install target/build/libuiohook/ 227 | ``` 228 | 229 | ``` 230 | mkdir -p target/build/jni/ 231 | cmake -B target/build/jni/ \ 232 | -G "Unix Makefiles" \ 233 | -D CMAKE_PREFIX_PATH=target/ \ 234 | -D CMAKE_SYSTEM_NAME=linux \ 235 | -D CMAKE_SYSTEM_PROCESSOR=x86_64 \ 236 | -D CMAKE_VERBOSE_MAKEFILE=ON 237 | 238 | cmake --build target/build/jni/ \ 239 | --parallel 2 \ 240 | --clean-first 241 | 242 | cmake --install target/build/jni/ 243 | ``` 244 | 245 | #### Compile Windows ARM 246 | ``` 247 | md target\build\libuiohook\ 248 | cmake -B target\build\libuiohook\ -S src\external\libuiohook\ ^ 249 | -G "Visual Studio 17 2022" -A ARM ^ 250 | -D CMAKE_INSTALL_PREFIX=target\ ^ 251 | -D CMAKE_VERBOSE_MAKEFILE=ON ^ 252 | -D BUILD_SHARED_LIBS=OFF ^ 253 | -D USE_EPOCH_TIME=ON 254 | 255 | cmake --build target\build\libuiohook\ ^ 256 | --parallel 2 ^ 257 | --config RelWithDebInfo ^ 258 | --clean-first 259 | 260 | cmake --install target\build\libuiohook\ ^ 261 | --config RelWithDebInfo 262 | ``` 263 | 264 | ``` 265 | md target\build\jni\ 266 | cmake -B target\build\jni\ ^ 267 | -G "Visual Studio 17 2022" -A ARM ^ 268 | -D CMAKE_PREFIX_PATH=target\ ^ 269 | -D CMAKE_SYSTEM_NAME=windows ^ 270 | -D CMAKE_SYSTEM_PROCESSOR=arm ^ 271 | -D CMAKE_VERBOSE_MAKEFILE=ON 272 | 273 | cmake --build target\build\jni\ ^ 274 | --parallel 2 ^ 275 | --config RelWithDebInfo ^ 276 | --clean-first 277 | 278 | cmake --install target\build\jni\ ^ 279 | --config RelWithDebInfo 280 | ``` 281 | 282 | #### Compile Windows x86 283 | ``` 284 | md target\build\libuiohook\ 285 | cmake -B target\build\libuiohook\ -S src\external\libuiohook\ ^ 286 | -G "Visual Studio 17 2022" -A Win32 ^ 287 | -D CMAKE_INSTALL_PREFIX=target\ ^ 288 | -D CMAKE_VERBOSE_MAKEFILE=ON ^ 289 | -D BUILD_SHARED_LIBS=OFF ^ 290 | -D USE_EPOCH_TIME=ON 291 | 292 | cmake --build target\build\libuiohook\ ^ 293 | --parallel 2 ^ 294 | --config RelWithDebInfo ^ 295 | --clean-first 296 | 297 | cmake --install target\build\libuiohook\ ^ 298 | --config RelWithDebInfo 299 | ``` 300 | 301 | ``` 302 | md target\build\jni\ 303 | cmake -B target\build\jni\ ^ 304 | -G "Visual Studio 17 2022" -A Win32 ^ 305 | -D CMAKE_PREFIX_PATH=target\ ^ 306 | -D CMAKE_SYSTEM_NAME=windows ^ 307 | -D CMAKE_SYSTEM_PROCESSOR=x86 ^ 308 | -D CMAKE_VERBOSE_MAKEFILE=ON 309 | 310 | cmake --build target\build\jni\ ^ 311 | --parallel 2 ^ 312 | --config RelWithDebInfo ^ 313 | --clean-first 314 | 315 | cmake --install target\build\jni\ ^ 316 | --config RelWithDebInfo 317 | ``` 318 | 319 | #### Compile Windows x86_64 320 | ``` 321 | md target\build\libuiohook\ 322 | cmake -B target\build\libuiohook\ -S src\external\libuiohook\ ^ 323 | -G "Visual Studio 17 2022" -A x64 ^ 324 | -D CMAKE_INSTALL_PREFIX=target\ ^ 325 | -D CMAKE_VERBOSE_MAKEFILE=ON ^ 326 | -D BUILD_SHARED_LIBS=OFF ^ 327 | -D USE_EPOCH_TIME=ON 328 | 329 | cmake --build target\build\libuiohook\ ^ 330 | --parallel 2 ^ 331 | --config RelWithDebInfo ^ 332 | --clean-first 333 | 334 | cmake --install target\build\libuiohook\ ^ 335 | --config RelWithDebInfo 336 | ``` 337 | 338 | ``` 339 | md target\build\jni\ 340 | cmake -B target\build\jni\ ^ 341 | -G "Visual Studio 17 2022" -A x64 ^ 342 | -D CMAKE_PREFIX_PATH=target\ ^ 343 | -D CMAKE_SYSTEM_NAME=windows ^ 344 | -D CMAKE_SYSTEM_PROCESSOR=x86_64 ^ 345 | -D CMAKE_VERBOSE_MAKEFILE=ON 346 | 347 | cmake --build target\build\jni\ ^ 348 | --parallel 2 ^ 349 | --config RelWithDebInfo ^ 350 | --clean-first 351 | 352 | cmake --install target\build\jni\ ^ 353 | --config RelWithDebInfo 354 | ``` 355 | 356 | ### Create JAR Files 357 | Create source, javadoc and multi-release JAR files. 358 | ``` 359 | mvn package 360 | ``` 361 | -------------------------------------------------------------------------------- /doc/ConsoleOutput.md: -------------------------------------------------------------------------------- 1 | ### Logging and Console Output 2 | As of version 2.0, JNativeHook includes an internal [Logger](http://docs.oracle.com/javase/1.5.0/docs/api/java/util/logging/Logger.html) 3 | to handle nearly all console output. By default, JNativeHook will use the default Logger 4 | configured by the JVM. 5 | 6 | **Set the log level to only display warnings and errors.** 7 | ```java 8 | // Get the logger for "com.github.kwhat.jnativehook" and set the level to warning. 9 | Logger logger = Logger.getLogger(GlobalScreen.class.getPackage().getName()); 10 | logger.setLevel(Level.WARNING); 11 | 12 | // Don't forget to disable the parent handlers. 13 | logger.setUseParentHandlers(false); 14 | ``` 15 | 16 | **Disable all console output.** 17 | ```java 18 | // Get the logger for "com.github.kwhat.jnativehook" and set the level to off. 19 | Logger logger = Logger.getLogger(GlobalScreen.class.getPackage().getName()); 20 | logger.setLevel(Level.OFF); 21 | 22 | // Don't forget to disable the parent handlers. 23 | logger.setUseParentHandlers(false); 24 | ``` 25 | 26 | **Set the log level to display everything.** 27 | ```java 28 | // Get the "com.github.kwhat.jnativehook" logger and set the level 29 | Logger logger = Logger.getLogger(GlobalScreen.class.getPackage().getName()); 30 | logger.setLevel(Level.ALL); 31 | 32 | // Don't forget to disable the parent handlers. 33 | logger.setUseParentHandlers(false); 34 | ``` 35 | -------------------------------------------------------------------------------- /doc/ConsumingEvents.md: -------------------------------------------------------------------------------- 1 | ### Consuming Events (Unsupported) 2 | Starting with version 2.0 it is now possible to prevent event propagation by consuming native events from Java. This behavior is currently unsupported because it is impossible to implement on X11 platforms like Unix, Linux and Solaris. This may change in the future as Wayland begins to replace X11 as the default windowing server on these platforms. 3 | 4 | ```java 5 | import com.github.kwhat.jnativehook.GlobalScreen; 6 | import com.github.kwhat.jnativehook.NativeHookException; 7 | import com.github.kwhat.jnativehook.NativeInputEvent; 8 | import com.github.kwhat.jnativehook.dispatcher.VoidDispatchService; 9 | import com.github.kwhat.jnativehook.keyboard.NativeKeyEvent; 10 | import com.github.kwhat.jnativehook.keyboard.NativeKeyListener; 11 | import java.lang.reflect.Field; 12 | import java.util.ArrayList; 13 | import java.util.List; 14 | import java.util.concurrent.AbstractExecutorService; 15 | import java.util.concurrent.TimeUnit; 16 | import java.util.logging.Level; 17 | import java.util.logging.Logger; 18 | 19 | public class ConsumeEvent implements NativeKeyListener { 20 | public ConsumeEvent() throws NativeHookException { 21 | // Create custom logger and level. 22 | Logger logger = Logger.getLogger(GlobalScreen.class.getPackage().getName()); 23 | logger.setLevel(Level.WARNING); 24 | 25 | GlobalScreen.setEventDispatcher(new VoidDispatchService()); 26 | GlobalScreen.registerNativeHook(); 27 | 28 | GlobalScreen.addNativeKeyListener(this); 29 | } 30 | 31 | public void nativeKeyPressed(NativeKeyEvent e) { 32 | if (e.getKeyCode() == NativeKeyEvent.VC_B) { 33 | System.out.print("Attempting to consume B event...\t"); 34 | try { 35 | Field f = NativeInputEvent.class.getDeclaredField("reserved"); 36 | f.setAccessible(true); 37 | f.setShort(e, (short) 0x01); 38 | 39 | System.out.print("[ OK ]\n"); 40 | } 41 | catch (Exception ex) { 42 | System.out.print("[ !! ]\n"); 43 | ex.printStackTrace(); 44 | } 45 | } 46 | } 47 | 48 | public void nativeKeyReleased(NativeKeyEvent e) { 49 | if (e.getKeyCode() == NativeKeyEvent.VC_B) { 50 | System.out.print("Attempting to consume B event...\t"); 51 | try { 52 | Field f = NativeInputEvent.class.getDeclaredField("reserved"); 53 | f.setAccessible(true); 54 | f.setShort(e, (short) 0x01); 55 | 56 | System.out.print("[ OK ]\n"); 57 | } 58 | catch (Exception ex) { 59 | System.out.print("[ !! ]\n"); 60 | ex.printStackTrace(); 61 | } 62 | } 63 | } 64 | 65 | public void nativeKeyTyped(NativeKeyEvent e) { /* Unimplemented */ } 66 | 67 | public static void main(String [] args) throws NativeHookException { 68 | new ConsumeEvent(); 69 | } 70 | } 71 | ``` 72 | -------------------------------------------------------------------------------- /doc/Keyboard.md: -------------------------------------------------------------------------------- 1 | ### Global Keyboard Listener 2 | ```java 3 | import com.github.kwhat.jnativehook.GlobalScreen; 4 | import com.github.kwhat.jnativehook.NativeHookException; 5 | import com.github.kwhat.jnativehook.keyboard.NativeKeyEvent; 6 | import com.github.kwhat.jnativehook.keyboard.NativeKeyListener; 7 | 8 | public class GlobalKeyListenerExample implements NativeKeyListener { 9 | public void nativeKeyPressed(NativeKeyEvent e) { 10 | System.out.println("Key Pressed: " + NativeKeyEvent.getKeyText(e.getKeyCode())); 11 | 12 | if (e.getKeyCode() == NativeKeyEvent.VC_ESCAPE) { 13 | try { 14 | GlobalScreen.unregisterNativeHook(); 15 | } catch (NativeHookException nativeHookException) { 16 | nativeHookException.printStackTrace(); 17 | } 18 | } 19 | } 20 | 21 | public void nativeKeyReleased(NativeKeyEvent e) { 22 | System.out.println("Key Released: " + NativeKeyEvent.getKeyText(e.getKeyCode())); 23 | } 24 | 25 | public void nativeKeyTyped(NativeKeyEvent e) { 26 | System.out.println("Key Typed: " + e.getKeyText(e.getKeyCode())); 27 | } 28 | 29 | public static void main(String[] args) { 30 | try { 31 | GlobalScreen.registerNativeHook(); 32 | } 33 | catch (NativeHookException ex) { 34 | System.err.println("There was a problem registering the native hook."); 35 | System.err.println(ex.getMessage()); 36 | 37 | System.exit(1); 38 | } 39 | 40 | GlobalScreen.addNativeKeyListener(new GlobalKeyListenerExample()); 41 | } 42 | } 43 | ``` 44 | -------------------------------------------------------------------------------- /doc/LibraryLoading.md: -------------------------------------------------------------------------------- 1 | ### Advanced Library Loading 2 | As of version 2.0, JNativeHook includes a native library loading interface called [NativeLibraryLocator](https://github.com/kwhat/jnativehook/tree/master/src/java/com/github/kwhat/jnativehook/NativeLibraryLocator.java). 3 | You can implement this interface to customize what libraries are loaded, as well as where they are loaded from. 4 | 5 | ```java 6 | public class UrlLibraryLocator implements NativeLibraryLocator { 7 | public Iterator getLibraries() { 8 | String libName = "MyLibrary"; 9 | 10 | // Get what the system "thinks" the library name should be. 11 | String libNativeName = System.mapLibraryName(libName); 12 | 13 | // Hack for OS X JRE 1.6 and earlier. 14 | libNativeName = libNativeName.replaceAll("\\.jnilib$", "\\.dylib"); 15 | 16 | String libExt = libNativeName.substring(libNativeName.lastIndexOf('.')); 17 | 18 | URL libUrl = new URL("http://www.mydomain.tld/pathToFile/" + libNativeName); 19 | File libFile = File.createTempFile(tempFile, libExt); 20 | 21 | libFile.deleteOnExit(); 22 | 23 | FileUtils.copyURLToFile(libUrl, libFile); 24 | 25 | ArrayList list = new ArrayList(1); 26 | list.add(file); 27 | 28 | return list; 29 | } 30 | } 31 | ``` 32 | -------------------------------------------------------------------------------- /doc/Mouse.md: -------------------------------------------------------------------------------- 1 | ### Global Mouse Listener 2 | ```java 3 | import GlobalScreen; 4 | import NativeHookException; 5 | import NativeMouseEvent; 6 | import NativeMouseInputListener; 7 | 8 | public class GlobalMouseListenerExample implements NativeMouseInputListener { 9 | public void nativeMouseClicked(NativeMouseEvent e) { 10 | System.out.println("Mouse Clicked: " + e.getClickCount()); 11 | } 12 | 13 | public void nativeMousePressed(NativeMouseEvent e) { 14 | System.out.println("Mouse Pressed: " + e.getButton()); 15 | } 16 | 17 | public void nativeMouseReleased(NativeMouseEvent e) { 18 | System.out.println("Mouse Released: " + e.getButton()); 19 | } 20 | 21 | public void nativeMouseMoved(NativeMouseEvent e) { 22 | System.out.println("Mouse Moved: " + e.getX() + ", " + e.getY()); 23 | } 24 | 25 | public void nativeMouseDragged(NativeMouseEvent e) { 26 | System.out.println("Mouse Dragged: " + e.getX() + ", " + e.getY()); 27 | } 28 | 29 | public static void main(String[] args) { 30 | try { 31 | GlobalScreen.registerNativeHook(); 32 | } 33 | catch (NativeHookException ex) { 34 | System.err.println("There was a problem registering the native hook."); 35 | System.err.println(ex.getMessage()); 36 | 37 | System.exit(1); 38 | } 39 | 40 | // Construct the example object. 41 | GlobalMouseListenerExample example = new GlobalMouseListenerExample(); 42 | 43 | // Add the appropriate listeners. 44 | GlobalScreen.addNativeMouseListener(example); 45 | GlobalScreen.addNativeMouseMotionListener(example); 46 | } 47 | } 48 | ``` 49 | -------------------------------------------------------------------------------- /doc/MouseWheel.md: -------------------------------------------------------------------------------- 1 | ### Global Mouse Wheel Listener 2 | ```java 3 | import GlobalScreen; 4 | import NativeHookException; 5 | import NativeMouseWheelEvent; 6 | import NativeMouseWheelListener; 7 | 8 | public class GlobalMouseWheelListenerExample implements NativeMouseWheelListener { 9 | public void nativeMouseWheelMoved(NativeMouseWheelEvent e) { 10 | System.out.println("Mosue Wheel Moved: " + e.getWheelRotation()); 11 | } 12 | 13 | public static void main(String[] args) { 14 | try { 15 | GlobalScreen.registerNativeHook(); 16 | } 17 | catch (NativeHookException ex) { 18 | System.err.println("There was a problem registering the native hook."); 19 | System.err.println(ex.getMessage()); 20 | ex.printStackTrace(); 21 | 22 | System.exit(1); 23 | } 24 | 25 | GlobalScreen.addNativeMouseWheelListener(new GlobalMouseWheelListenerExample()); 26 | } 27 | } 28 | ``` 29 | -------------------------------------------------------------------------------- /doc/Swing.md: -------------------------------------------------------------------------------- 1 | ### Working with Swing 2 | JNativeHook does *NOT* operate on the event dispatch thread. Because Swing components are not thread safe, you *MUST* 3 | wrap access to Swing components using the 4 | [SwingUtilities.invokeLater()](https://docs.oracle.com/javase/8/docs/api/javax/swing/SwingUtilities.html#invokeLater-java.lang.Runnable-) 5 | or [EventQueue.invokeLater()](https://docs.oracle.com/javase/8/docs/api/java/awt/EventQueue.html#invokeLater-java.lang.Runnable-) 6 | methods. As of version 2.0, the `SwingDispatchService` class maybe used to automatically use Swing's event dispatch 7 | thread for all native event delivery. 8 | 9 | ```java 10 | import java.awt.event.WindowEvent; 11 | import java.awt.event.WindowListener; 12 | import javax.swing.JFrame; 13 | import javax.swing.JOptionPane; 14 | import javax.swing.SwingUtilities; 15 | import javax.swing.WindowConstants; 16 | import com.github.kwhat.jnativehook.GlobalScreen; 17 | import com.github.kwhat.jnativehook.NativeHookException; 18 | import com.github.kwhat.jnativehook.dispatcher.SwingDispatchService; 19 | import com.github.kwhat.jnativehook.keyboard.NativeKeyEvent; 20 | import com.github.kwhat.jnativehook.keyboard.NativeKeyListener; 21 | 22 | public class SwingExample extends JFrame implements NativeKeyListener, WindowListener { 23 | public SwingExample() { 24 | // Set the event dispatcher to a swing safe executor service. 25 | GlobalScreen.setEventDispatcher(new SwingDispatchService()); 26 | 27 | setTitle("JNativeHook Swing Example"); 28 | setSize(300, 150); 29 | setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE); 30 | addWindowListener(this); 31 | setVisible(true); 32 | } 33 | 34 | public void windowOpened(WindowEvent e) { 35 | // Initialze native hook. 36 | try { 37 | GlobalScreen.registerNativeHook(); 38 | } 39 | catch (NativeHookException ex) { 40 | System.err.println("There was a problem registering the native hook."); 41 | System.err.println(ex.getMessage()); 42 | ex.printStackTrace(); 43 | 44 | System.exit(1); 45 | } 46 | 47 | GlobalScreen.addNativeKeyListener(this); 48 | } 49 | 50 | public void windowClosed(WindowEvent e) { 51 | //Clean up the native hook. 52 | GlobalScreen.unregisterNativeHook(); 53 | System.runFinalization(); 54 | System.exit(0); 55 | } 56 | 57 | public void windowClosing(WindowEvent e) { /* Unimplemented */ } 58 | public void windowIconified(WindowEvent e) { /* Unimplemented */ } 59 | public void windowDeiconified(WindowEvent e) { /* Unimplemented */ } 60 | public void windowActivated(WindowEvent e) { /* Unimplemented */ } 61 | public void windowDeactivated(WindowEvent e) { /* Unimplemented */ } 62 | 63 | public void nativeKeyReleased(NativeKeyEvent e) { 64 | if (e.getKeyCode() == NativeKeyEvent.VC_SPACE) { 65 | JOptionPane.showMessageDialog(null, "This will run on Swing's Event Dispatch Thread."); 66 | } 67 | } 68 | 69 | public void nativeKeyPressed(NativeKeyEvent e) { /* Unimplemented */ } 70 | public void nativeKeyTyped(NativeKeyEvent e) { /* Unimplemented */ } 71 | 72 | public static void main(String[] args) { 73 | SwingUtilities.invokeLater(new Runnable() { 74 | public void run() { 75 | new SwingExample(); 76 | } 77 | }); 78 | } 79 | } 80 | ``` 81 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/AbstractSwingInputAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import java.awt.Component; 21 | import java.awt.event.KeyEvent; 22 | 23 | /** 24 | * Adapter to convert native modifiers to java modifiers and to provide an anchor point for 25 | * native events. The methods are empty so the super call is obsolete. 26 | * 27 | * @since 2.1 28 | */ 29 | public abstract class AbstractSwingInputAdapter extends Component { 30 | @SuppressWarnings("deprecation") 31 | protected int getJavaModifiers(int nativeModifiers) { 32 | int modifiers = 0x00; 33 | if ((nativeModifiers & NativeInputEvent.SHIFT_MASK) != 0) { 34 | modifiers |= KeyEvent.SHIFT_MASK; 35 | modifiers |= KeyEvent.SHIFT_DOWN_MASK; 36 | } 37 | if ((nativeModifiers & NativeInputEvent.META_MASK) != 0) { 38 | modifiers |= KeyEvent.META_MASK; 39 | modifiers |= KeyEvent.META_DOWN_MASK; 40 | } 41 | if ((nativeModifiers & NativeInputEvent.CTRL_MASK) != 0) { 42 | modifiers |= KeyEvent.CTRL_MASK; 43 | modifiers |= KeyEvent.CTRL_DOWN_MASK; 44 | } 45 | if ((nativeModifiers & NativeInputEvent.ALT_MASK) != 0) { 46 | modifiers |= KeyEvent.ALT_MASK; 47 | modifiers |= KeyEvent.ALT_DOWN_MASK; 48 | } 49 | if ((nativeModifiers & NativeInputEvent.BUTTON1_MASK) != 0) { 50 | modifiers |= KeyEvent.BUTTON1_MASK; 51 | modifiers |= KeyEvent.BUTTON1_DOWN_MASK; 52 | } 53 | if ((nativeModifiers & NativeInputEvent.BUTTON2_MASK) != 0) { 54 | modifiers |= KeyEvent.BUTTON2_MASK; 55 | modifiers |= KeyEvent.BUTTON2_DOWN_MASK; 56 | } 57 | if ((nativeModifiers & NativeInputEvent.BUTTON3_MASK) != 0) { 58 | modifiers |= KeyEvent.BUTTON3_MASK; 59 | modifiers |= KeyEvent.BUTTON3_DOWN_MASK; 60 | } 61 | 62 | return modifiers; 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/DefaultLibraryLocator.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import java.io.File; 21 | import java.io.FileOutputStream; 22 | import java.io.IOException; 23 | import java.io.InputStream; 24 | import java.net.URISyntaxException; 25 | import java.net.URL; 26 | import java.nio.file.Paths; 27 | import java.util.ArrayList; 28 | import java.util.Iterator; 29 | import java.util.List; 30 | import java.util.logging.Logger; 31 | 32 | /** 33 | * Default implementation of the NativeLibraryLocator interface. This will first 34 | * attempt to load the native library from the java.library.path property. If that fails, it will 35 | * attempt to extract a library from the jar based on the host operating system and architecture. 36 | * 37 | * @author Alexander Barker (alex@1stleg.com) 38 | * @version 2.0 39 | * @since 2.0 40 | * @see NativeLibraryLocator 41 | */ 42 | public class DefaultLibraryLocator implements NativeLibraryLocator { 43 | private static final Logger log = Logger.getLogger(GlobalScreen.class.getPackage().getName()); 44 | 45 | /** 46 | * Perform default procedures to interface with the native library. These procedures include 47 | * unpacking and loading the library into the Java Virtual Machine. 48 | */ 49 | public Iterator getLibraries() { 50 | List libraries = new ArrayList(1); 51 | 52 | String libName = System.getProperty("jnativehook.lib.name", "JNativeHook"); 53 | 54 | // Get the package name for the GlobalScreen. 55 | String basePackage = GlobalScreen.class.getPackage().getName().replace('.', '/'); 56 | 57 | String libNativeArch = NativeSystem.getArchitecture().toString().toLowerCase(); 58 | String libNativeName = System 59 | .mapLibraryName(libName) // Get what the system "thinks" the library name should be. 60 | .replaceAll("\\.jnilib$", "\\.dylib"); // Hack for OS X JRE 1.6 and earlier. 61 | 62 | // Resource path for the native library. 63 | String libResourcePath = "/" + basePackage + "/lib/" + 64 | NativeSystem.getFamily().toString().toLowerCase() + 65 | '/' + libNativeArch + '/' + libNativeName; 66 | 67 | URL classLocation = GlobalScreen.class.getProtectionDomain().getCodeSource().getLocation(); 68 | 69 | File classFile = null; 70 | try { 71 | classFile = new File(classLocation.toURI()); 72 | } 73 | catch (URISyntaxException e) { 74 | log.warning(e.getMessage()); 75 | classFile = new File(classLocation.getPath()); 76 | } 77 | 78 | File libFile = null; 79 | if (classFile.isFile()) { 80 | // Jar Archive 81 | String libPath = System.getProperty("jnativehook.lib.path", classFile.getParentFile().getPath()); 82 | 83 | InputStream resourceInputStream = GlobalScreen.class.getResourceAsStream(libResourcePath); 84 | if (resourceInputStream == null) { 85 | throw new RuntimeException("Unable to extract the native library " + libResourcePath + "!\n"); 86 | } 87 | 88 | String version = GlobalScreen.class.getPackage().getImplementationVersion(); 89 | if (version != null) { 90 | version = '-' + version; 91 | } else { 92 | version = ""; 93 | } 94 | 95 | libFile = new File( 96 | libPath, 97 | libNativeName.replaceAll("^(.*)\\.(.*)$", "$1" + version + '.' + libNativeArch + ".$2") 98 | ); 99 | if (!libFile.exists()) { 100 | try { 101 | // Check and see if a copy of the native lib already exists. 102 | FileOutputStream libOutputStream = new FileOutputStream(libFile); 103 | 104 | // Read from the digest stream and write to the file steam. 105 | int size; 106 | byte[] buffer = new byte[4 * 1024]; 107 | while ((size = resourceInputStream.read(buffer)) != -1) { 108 | libOutputStream.write(buffer, 0, size); 109 | } 110 | 111 | // Close all the streams. 112 | resourceInputStream.close(); 113 | libOutputStream.close(); 114 | } 115 | catch (IOException e) { 116 | throw new RuntimeException(e.getMessage(), e); 117 | } 118 | 119 | log.fine("Extracted library: " + libFile.getPath() + ".\n"); 120 | } 121 | } else { 122 | // Loose Classes 123 | libFile = Paths.get(classFile.getAbsolutePath(), libResourcePath.toString()).toFile(); 124 | } 125 | 126 | if (!libFile.exists()) { 127 | throw new RuntimeException("Unable to locate JNI library at " + libFile.getPath() + "!\n"); 128 | } 129 | 130 | log.fine("Loading library: " + libFile.getPath() + ".\n"); 131 | libraries.add(libFile); 132 | 133 | return libraries.iterator(); 134 | } 135 | } 136 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/NativeHookException.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * http://code.google.com/p/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | /** 21 | * Signals that a Native Hook Exception has occurred. 22 | * 23 | * @author Alexander Barker (alex@1stleg.com) 24 | * @version 2.0 25 | * @since 1.0 26 | */ 27 | public class NativeHookException extends Exception { 28 | /** The Constant serialVersionUID. */ 29 | private static final long serialVersionUID = 8952825837670265527L; 30 | 31 | /** The error code associated with this exception. */ 32 | private int code = NativeHookException.UNSPECIFIED_FAILURE; 33 | 34 | /** 35 | * Unspecified failure error code. 36 | * 37 | * @since 2.0 38 | */ 39 | public static final int UNSPECIFIED_FAILURE = 0x00; 40 | 41 | /** 42 | * General failure error code. 43 | * 44 | * @since 2.0 45 | */ 46 | @SuppressWarnings("unused") 47 | public static final int HOOK_FAILURE = 0x01; 48 | 49 | /** 50 | * X11 open display error code. 51 | * 52 | * @since 2.0 53 | */ 54 | @SuppressWarnings("unused") 55 | public static final int X11_OPEN_DISPLAY = 0x20; 56 | 57 | /** 58 | * X11 extension XRecord was not found. 59 | * 60 | * @since 2.0 61 | */ 62 | @SuppressWarnings("unused") 63 | public static final int X11_RECORD_NOT_FOUND = 0x21; 64 | 65 | /** 66 | * X11 extension XRecord could not allocate range. 67 | * 68 | * @since 2.0 69 | */ 70 | @SuppressWarnings("unused") 71 | public static final int X11_RECORD_ALLOC_RANGE = 0x22; 72 | 73 | /** 74 | * X11 extension XRecord could not create a context. 75 | * 76 | * @since 2.0 77 | */ 78 | @SuppressWarnings("unused") 79 | public static final int X11_RECORD_CREATE_CONTEXT = 0x23; 80 | 81 | 82 | /** 83 | * X11 extension XRecord could not enable the context. 84 | */ 85 | @SuppressWarnings("unused") 86 | public static final int X11_RECORD_ENABLE_CONTEXT = 0x24; 87 | 88 | /** 89 | * X11 extension XRecord could not enable the context. 90 | */ 91 | @SuppressWarnings("unused") 92 | public static final int X11_RECORD_GET_CONTEXT = 0x25; 93 | 94 | /** 95 | * Windows SetWindowsHookEx function failed to register the low level hook. See log level debug for details. 96 | * 97 | * @since 2.0 98 | */ 99 | @SuppressWarnings("unused") 100 | public static final int WIN_SET_HOOK = 0x30; 101 | 102 | 103 | /** 104 | * Apple access for assistive devices is disabled. 105 | */ 106 | @SuppressWarnings("unused") 107 | public static final int DARWIN_AXAPI_DISABLED = 0x40; 108 | 109 | /** 110 | * Apple could not create an event port. 111 | */ 112 | @SuppressWarnings("unused") 113 | public static final int DARWIN_CREATE_EVENT_PORT = 0x41; 114 | 115 | /** 116 | * Apple could not create a run loop source. 117 | */ 118 | @SuppressWarnings("unused") 119 | public static final int DARWIN_CREATE_RUN_LOOP_SOURCE = 0x42; 120 | 121 | /** 122 | * Apple could not acquire the current run loop. 123 | */ 124 | @SuppressWarnings("unused") 125 | public static final int DARWIN_GET_RUNLOOP = 0x43; 126 | 127 | /** 128 | * Apple could not create an observer. 129 | */ 130 | @SuppressWarnings("unused") 131 | public static final int DARWIN_CREATE_OBSERVER = 0x44; 132 | 133 | 134 | /** 135 | * Instantiates a new NativeHookException with UNKNOWN_FAILURE as its error code and null as its 136 | * detail message. 137 | */ 138 | public NativeHookException() { 139 | super(); 140 | } 141 | 142 | 143 | /** 144 | * Instantiates a new NativeHookException with a specified error code and null as its detail message. 145 | * 146 | * @since 2.0 147 | * 148 | * @param code The native error code. 149 | */ 150 | public NativeHookException(int code) { 151 | super(); 152 | 153 | this.code = code; 154 | } 155 | 156 | /** 157 | * Instantiates a new NativeHookException with UNKNOWN_FAILURE as its error code and a specified 158 | * detail message. 159 | * 160 | * @param message The detail message. 161 | */ 162 | public NativeHookException(String message) { 163 | super(message); 164 | } 165 | 166 | /** 167 | * Instantiates a new NativeHookException with a specified code and detail message. 168 | * 169 | * @since 2.0 170 | * 171 | * @param code The native error code. 172 | * @param message The detail message. 173 | */ 174 | public NativeHookException(int code, String message) { 175 | super(message); 176 | 177 | this.code = code; 178 | } 179 | 180 | /** 181 | * Instantiates a new NativeHookException with a specified detail message and cause. 182 | * 183 | * @param message The detail message. 184 | * @param cause The cause of the exception. A null value is permitted, and indicates that the cause is unknown. 185 | */ 186 | public NativeHookException(String message, Throwable cause) { 187 | super(message, cause); 188 | } 189 | 190 | /** 191 | * Instantiates a new NativeHookException with a specified error code, detail message and cause. 192 | * 193 | * @since 2.0 194 | * 195 | * @param code The native error code. 196 | * @param message The detail message. 197 | * @param cause The cause of the exception. A null value is permitted, and indicates that the cause is unknown. 198 | */ 199 | public NativeHookException(int code, String message, Throwable cause) { 200 | super(message, cause); 201 | 202 | this.code = code; 203 | } 204 | 205 | /** 206 | * Instantiates a new NativeHookException with a specified cause. 207 | * 208 | * @param cause The cause of the exception. A null value is permitted, and indicates that the cause is unknown. 209 | */ 210 | public NativeHookException(Throwable cause) { 211 | super(cause); 212 | } 213 | 214 | /** 215 | * Instantiates a new NativeHookException with a specified error code and cause. 216 | * 217 | * @param code The native error code. 218 | * @param cause The cause of the exception. A null value is permitted, and indicates that the cause is unknown. 219 | */ 220 | public NativeHookException(int code, Throwable cause) { 221 | super(cause); 222 | 223 | this.code = code; 224 | } 225 | 226 | /** 227 | * Get the native error code associated with this exception. 228 | * 229 | * @since 2.0 230 | * 231 | * @return The native error code 232 | */ 233 | public int getCode() { 234 | return this.code; 235 | } 236 | } 237 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/NativeInputEvent.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import com.github.kwhat.jnativehook.keyboard.NativeKeyListener; 21 | import com.github.kwhat.jnativehook.mouse.NativeMouseListener; 22 | import com.github.kwhat.jnativehook.mouse.NativeMouseMotionListener; 23 | import com.github.kwhat.jnativehook.mouse.NativeMouseWheelListener; 24 | import java.awt.Toolkit; 25 | import java.util.EventObject; 26 | 27 | /** 28 | * The root event class for all native-level input events. Input events are 29 | * delivered to listeners as they are received by the native source. There is 30 | * no method for listeners or subclasses to prevent delivery of the event to 31 | * the native system. There is no guarantee that the events will be received by 32 | * Java before they are delivered natively. 33 | *

34 | * 35 | * @author Alexander Barker (alex@1stleg.com) 36 | * @version 2.1 37 | * @since 1.0 38 | * 39 | * @see NativeKeyListener 40 | * @see NativeMouseListener 41 | * @see NativeMouseMotionListener 42 | * @see NativeMouseWheelListener 43 | */ 44 | public class NativeInputEvent extends EventObject { 45 | /** The Constant serialVersionUID. */ 46 | private static final long serialVersionUID = 2306729722565226621L; 47 | 48 | /** The type of event. */ 49 | private final int id; 50 | 51 | /** The platform dependent time the event occured at. */ 52 | private final long when; 53 | 54 | /** The modifier keys down during event. */ 55 | private int modifiers; 56 | 57 | /** Mask for undocumented behavior. 58 | * More information available at: 59 | * doc/ConsumingEvents.md 60 | * @since 2.0 61 | */ 62 | @SuppressWarnings("unused") 63 | private short reserved; 64 | 65 | /** The left shift key modifier constant. 66 | * @since 2.0 67 | */ 68 | public static final int SHIFT_L_MASK = 1 << 0; 69 | 70 | /** The left ctrl key modifier constant. 71 | * @since 2.0 72 | */ 73 | public static final int CTRL_L_MASK = 1 << 1; 74 | 75 | /** The left meta key modifier constant. 76 | * @since 2.0 77 | */ 78 | public static final int META_L_MASK = 1 << 2; 79 | 80 | /** The left alt key modifier constant. 81 | * @since 2.0 82 | */ 83 | public static final int ALT_L_MASK = 1 << 3; 84 | 85 | /** The right shift key modifier constant. 86 | * @since 2.0 87 | */ 88 | public static final int SHIFT_R_MASK = 1 << 4; 89 | 90 | /** The right ctrl key modifier constant. 91 | * @since 2.0 92 | */ 93 | public static final int CTRL_R_MASK = 1 << 5; 94 | 95 | /** The right meta key modifier constant. 96 | * @since 2.0 97 | */ 98 | public static final int META_R_MASK = 1 << 6; 99 | 100 | /** The right alt key modifier constant. 101 | * @since 2.0 102 | */ 103 | public static final int ALT_R_MASK = 1 << 7; 104 | 105 | /** Either the right or left shift key modifier constant. */ 106 | public static final int SHIFT_MASK = SHIFT_L_MASK | SHIFT_R_MASK; 107 | 108 | /** Either the right or left ctrl key modifier constant. */ 109 | public static final int CTRL_MASK = CTRL_L_MASK | CTRL_R_MASK; 110 | 111 | /** Either the right or left meta key modifier constant. */ 112 | public static final int META_MASK = META_L_MASK | META_R_MASK; 113 | 114 | /** Either the right or left alt key modifier constant. */ 115 | public static final int ALT_MASK = ALT_L_MASK | ALT_R_MASK; 116 | 117 | /** The Button1 modifier constant. */ 118 | public static final int BUTTON1_MASK = 1 << 8; 119 | 120 | /** The Button2 modifier constant. */ 121 | public static final int BUTTON2_MASK = 1 << 9; 122 | 123 | /** The Button3 modifier constant. */ 124 | public static final int BUTTON3_MASK = 1 << 10; 125 | 126 | /** The Button4 modifier constant. */ 127 | public static final int BUTTON4_MASK = 1 << 11; 128 | 129 | /** The Button5 modifier constant. */ 130 | public static final int BUTTON5_MASK = 1 << 12; 131 | 132 | /** The Number Lock modifier constant. */ 133 | public static final int NUM_LOCK_MASK = 1 << 13; 134 | 135 | /** The Caps Lock modifier constant. */ 136 | public static final int CAPS_LOCK_MASK = 1 << 14; 137 | 138 | /** The Scroll Lock modifier constant. */ 139 | public static final int SCROLL_LOCK_MASK = 1 << 15; 140 | 141 | 142 | /** 143 | * Instantiates a new native input event. 144 | * 145 | * @param source The source of the event. 146 | * @param id The type of event. 147 | * @param modifiers the modifier keys down during event. 148 | * NativeInputEvent _MASK modifiers should be used as they are 149 | * not compatible with the extended _DOWN_MASK or the old _MASK 150 | * InputEvent modifiers. 151 | */ 152 | public NativeInputEvent(Class source, int id, int modifiers) { 153 | super(source); 154 | 155 | this.id = id; 156 | this.when = 0; 157 | this.modifiers = modifiers; 158 | this.reserved = 0x00; 159 | } 160 | 161 | /** 162 | * Gets the event type. 163 | * 164 | * @return the event type 165 | */ 166 | public int getID() { 167 | return id; 168 | } 169 | 170 | /** 171 | * Gets the platform dependent native interval for chronological event sequencing. 172 | * 173 | * @return the native timestamp 174 | */ 175 | public long getWhen() { 176 | return when; 177 | } 178 | 179 | /** 180 | * Gets the modifier flags for this event. 181 | * 182 | * @return the modifier flags 183 | */ 184 | public int getModifiers() { 185 | return this.modifiers; 186 | } 187 | 188 | /** 189 | * Sets the modifier flags for this event. 190 | * 191 | * @param modifiers the new modifier flags 192 | * @deprecated 193 | */ 194 | public void setModifiers(int modifiers) { 195 | this.modifiers = modifiers; 196 | } 197 | 198 | /** 199 | * Sets the reserved flags for this event. 200 | *

201 | * 202 | * Note the use of this method may not be supported by all native platforms. 203 | *

204 | * 205 | * Event propagation support for X11 cannot be provided due to an oversight 206 | * in the way that XRecord currently operates. No public method will be 207 | * available until a working cross-platform solution can be provided. 208 | * 209 | * @param reserved Non-portable flags for unsupported functionality. 210 | * 211 | * @since 1.1 212 | * @deprecated 213 | */ 214 | @SuppressWarnings("unused") 215 | private void setReserved(short reserved) { 216 | this.reserved = reserved; 217 | } 218 | 219 | /** 220 | * Gets a String describing the modifier flags, such as 221 | * "Button1", or "Ctrl+Alt". These strings can be localized by changing the 222 | * awt.properties file. 223 | * 224 | * @param modifiers a modifier mask describing the modifier keys and mouse 225 | * buttons of an event. 226 | * @return the modifier mask's textual representation. 227 | */ 228 | public static String getModifiersText(int modifiers) { 229 | StringBuilder param = new StringBuilder(255); 230 | 231 | if ((modifiers & NativeInputEvent.SHIFT_MASK) != 0) { 232 | param.append(Toolkit.getProperty("AWT.shift", "Shift")); 233 | param.append('+'); 234 | } 235 | 236 | if ((modifiers & NativeInputEvent.CTRL_MASK) != 0) { 237 | param.append(Toolkit.getProperty("AWT.control", "Ctrl")); 238 | param.append('+'); 239 | } 240 | 241 | if ((modifiers & NativeInputEvent.META_MASK) != 0) { 242 | param.append(Toolkit.getProperty("AWT.meta", "Meta")); 243 | param.append('+'); 244 | } 245 | 246 | if ((modifiers & NativeInputEvent.ALT_MASK) != 0) { 247 | param.append(Toolkit.getProperty("AWT.alt", "Alt")); 248 | param.append('+'); 249 | } 250 | 251 | 252 | if ((modifiers & NativeInputEvent.BUTTON1_MASK) != 0) { 253 | param.append(Toolkit.getProperty("AWT.button1", "Button1")); 254 | param.append('+'); 255 | } 256 | 257 | if ((modifiers & NativeInputEvent.BUTTON2_MASK) != 0) { 258 | param.append(Toolkit.getProperty("AWT.button2", "Button2")); 259 | param.append('+'); 260 | } 261 | 262 | if ((modifiers & NativeInputEvent.BUTTON3_MASK) != 0) { 263 | param.append(Toolkit.getProperty("AWT.button3", "Button3")); 264 | param.append('+'); 265 | } 266 | 267 | if ((modifiers & NativeInputEvent.BUTTON4_MASK) != 0) { 268 | param.append(Toolkit.getProperty("AWT.button4", "Button4")); 269 | param.append('+'); 270 | } 271 | 272 | if ((modifiers & NativeInputEvent.BUTTON5_MASK) != 0) { 273 | param.append(Toolkit.getProperty("AWT.button5", "Button5")); 274 | param.append('+'); 275 | } 276 | 277 | 278 | if ((modifiers & NativeInputEvent.NUM_LOCK_MASK) != 0) { 279 | param.append(Toolkit.getProperty("AWT.numLock", "Num Lock")); 280 | param.append('+'); 281 | } 282 | 283 | if ((modifiers & NativeInputEvent.CAPS_LOCK_MASK) != 0) { 284 | param.append(Toolkit.getProperty("AWT.capsLock", "Caps Lock")); 285 | param.append('+'); 286 | } 287 | 288 | if ((modifiers & NativeInputEvent.SCROLL_LOCK_MASK) != 0) { 289 | param.append(Toolkit.getProperty("AWT.scrollLock", "Scroll Lock")); 290 | param.append('+'); 291 | } 292 | 293 | if (param.length() > 0) { 294 | // Remove the trailing '+'. 295 | param.deleteCharAt(param.length() - 1); 296 | } 297 | 298 | return param.toString(); 299 | } 300 | 301 | /** 302 | * Gets a String representation of this event. This method is 303 | * useful for event-logging and debugging. 304 | * 305 | * @return a string identifying the event and its attributes 306 | */ 307 | public String paramString() { 308 | 309 | String param = "id=" + getID() + ',' 310 | + "when=" + getWhen() + ',' 311 | + "mask=" + Integer.toBinaryString(getModifiers()) + ',' 312 | + "modifiers=" + getModifiersText(getModifiers()); 313 | 314 | return param; 315 | } 316 | } 317 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/NativeLibraryLocator.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import java.io.File; 21 | import java.util.Iterator; 22 | 23 | /** 24 | * Interface used for native library loading. This interface should be implemented to alter what libraries are loaded, 25 | * and where they are loaded from. The jnativehook.lib.locator property should be set to the implementing 26 | * class prior to loading the GlobalScreen class. If no property is specified, 27 | * DefaultLibraryLocator will be used. 28 | *

29 | * 30 | * @author Aidas Adomkus (vasiukai@gmail.com) 31 | * @version 2.0 32 | * @since 2.0 33 | * 34 | * @see DefaultLibraryLocator 35 | */ 36 | public interface NativeLibraryLocator { 37 | /** 38 | * Perform procedures to interface with the native library. These procedures may include acquiring, unpacking and 39 | * loading the library into the Java Virtual Machine. 40 | * 41 | * @return Iterator of type file, where each file points to a native library to load. 42 | */ 43 | public Iterator getLibraries(); 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/NativeMonitorInfo.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | /** 21 | * Object representation of a native monitor layout. 22 | *

23 | * 24 | * The primary display is guaranteed to be at number zero. No other grantee is made about monitor number for subsequent 25 | * displays. All logical displays are guaranteed to have x and y coordinates relative to the primary display. 26 | * 27 | * @author Alexander Barker (alex@1stleg.com) 28 | * @version 2.1 29 | * @since 2.1 30 | * 31 | * @see java.util.concurrent.ExecutorService 32 | * @see GlobalScreen#setEventDispatcher 33 | */ 34 | public class NativeMonitorInfo { 35 | /** 36 | * Display number. The primary display is always zero. 37 | */ 38 | private short number; 39 | 40 | /** 41 | * Pixel distance relative to the primary display in the x direction. 42 | */ 43 | private int x; 44 | 45 | /** 46 | * Pixel distance relative to the primary display in the y direction. 47 | */ 48 | private int y; 49 | 50 | /** 51 | * The horizontal size of the current display. 52 | */ 53 | private short width; 54 | 55 | /** 56 | * The vertical size of the current display. 57 | */ 58 | private short height; 59 | 60 | /** 61 | * Instantiates a new monitor info class. 62 | *

63 | * Note that passing in an invalid ID results in unspecified behavior. 64 | * 65 | * @param number an integer that identifies the display. 66 | * @param x the x coordate of this display. 67 | * @param y the y coordate of this display. 68 | * @param width the width coordate of this display. 69 | * @param height the height coordate of this display. 70 | */ 71 | public NativeMonitorInfo(short number, int x, int y, short width, short height) { 72 | this.number = number; 73 | this.x = x; 74 | this.y = y; 75 | this.width = width; 76 | this.height = height; 77 | } 78 | 79 | /** 80 | * Get the logical number of this display. The primary display will always be zero. 81 | * 82 | * @return the logical number of this display. 83 | */ 84 | public short getNumber() { 85 | return number; 86 | } 87 | 88 | /** 89 | * Set the logical number for this display. 90 | * 91 | * @param number the logical number of this display. 92 | */ 93 | public void setNumber(short number) { 94 | this.number = number; 95 | } 96 | 97 | /** 98 | * Returns the x offset of this display. 99 | * 100 | * @return the x offset in pixels of this display. 101 | */ 102 | public int getX() { 103 | return x; 104 | } 105 | 106 | /** 107 | * Set the x offset of this display. 108 | * 109 | * @param x the x location of this display. 110 | */ 111 | public void setX(int x) { 112 | this.x = x; 113 | } 114 | 115 | /** 116 | * Returns the y offset of this display. 117 | * 118 | * @return the y offset in pixels of this display. 119 | */ 120 | public int getY() { 121 | return y; 122 | } 123 | 124 | /** 125 | * Set the y offset of this display. 126 | * 127 | * @param y the y location of this display. 128 | */ 129 | public void setY(int y) { 130 | this.y = y; 131 | } 132 | 133 | /** 134 | * Returns the width of this native display. 135 | * 136 | * @return the width in pixels of this display. 137 | */ 138 | public short getWidth() { 139 | return width; 140 | } 141 | 142 | /** 143 | * Set the width in pixel value for this display. 144 | * 145 | * @param width the pixel width of this monitor. 146 | */ 147 | public void setWidth(short width) { 148 | this.width = width; 149 | } 150 | 151 | /** 152 | * Returns the hight of this naitve monitor. 153 | * 154 | * @return the hight in pixels of this display. 155 | */ 156 | public short getHeight() { 157 | return height; 158 | } 159 | 160 | /** 161 | * Set the height in pixel value for this display. 162 | * 163 | * @param height the pixel height of this display. 164 | */ 165 | public void setHeight(short height) { 166 | this.height = height; 167 | } 168 | } 169 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/NativeSystem.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import java.util.Locale; 21 | 22 | /** 23 | * A small class to determine the native system's operating system family and architecture. The 24 | * class is only used to determine which native library to unpack and load at runtime. This class is 25 | * never used if the native library is loaded using the java.library.path property. 26 | * 27 | * @author Alexander Barker (alex@1stleg.com) 28 | * @version 2.2 29 | * @since 1.0 30 | */ 31 | public class NativeSystem { 32 | /** 33 | * The operating system family enum. 34 | * 35 | * @see NativeSystem 36 | */ 37 | public enum Family { 38 | FREEBSD, 39 | OPENBSD, 40 | DARWIN, 41 | SOLARIS, 42 | LINUX, 43 | WINDOWS, 44 | 45 | UNSUPPORTED; 46 | 47 | @Override 48 | public String toString() { 49 | return super.toString().toLowerCase(Locale.ROOT); 50 | } 51 | } 52 | 53 | /** 54 | * The system architecture enum. 55 | * 56 | * @see NativeSystem 57 | */ 58 | public enum Arch { 59 | ARM, 60 | ARM64, 61 | SPARC, 62 | SPARC64, 63 | PPC, 64 | PPC64, 65 | x86, 66 | x86_64, 67 | 68 | UNSUPPORTED; 69 | 70 | @Override 71 | public String toString() { 72 | return super.toString().toLowerCase(Locale.ROOT); 73 | } 74 | } 75 | 76 | /** 77 | * Determines the current operating system family. 78 | * 79 | * @return The current operating system family enum item. 80 | */ 81 | public static Family getFamily() { 82 | final String osName = System.getProperty("os.name").toLowerCase(Locale.ROOT); 83 | Family family = Family.UNSUPPORTED; 84 | 85 | if (osName.equals("freebsd")) { 86 | family = Family.FREEBSD; 87 | } else if (osName.equals("openbsd")) { 88 | family = Family.OPENBSD; 89 | } else if (osName.equals("mac os x")) { 90 | family = Family.DARWIN; 91 | } else if (osName.equals("solaris") 92 | || osName.equals("sunos")) { 93 | family = Family.SOLARIS; 94 | } else if (osName.equals("linux")) { 95 | family = Family.LINUX; 96 | } else if (osName.startsWith("windows")) { 97 | family = Family.WINDOWS; 98 | } 99 | 100 | return family; 101 | } 102 | 103 | /** 104 | * Determines the current system architecture. 105 | * 106 | * @return The current system architecture. 107 | */ 108 | public static Arch getArchitecture() { 109 | final String osArch = System.getProperty("os.arch").toLowerCase(Locale.ROOT); 110 | Arch arch = Arch.UNSUPPORTED; 111 | 112 | if (osArch.startsWith("arm")) { 113 | arch = Arch.ARM; 114 | } else if (osArch.equals("aarch64")) { 115 | arch = Arch.ARM64; 116 | } else if (osArch.equals("sparc")) { 117 | arch = Arch.SPARC; 118 | } else if (osArch.equals("sparc64")) { 119 | arch = Arch.SPARC64; 120 | } else if (osArch.equals("ppc") 121 | || osArch.equals("powerpc")) { 122 | arch = Arch.PPC; 123 | } else if (osArch.equals("ppc64") 124 | || osArch.equals("powerpc64")) { 125 | arch = Arch.PPC64; 126 | } else if (osArch.equals("x86") 127 | || osArch.equals("i386") 128 | || osArch.equals("i486") 129 | || osArch.equals("i586") 130 | || osArch.equals("i686")) { 131 | arch = Arch.x86; 132 | } else if (osArch.equals("x86_64") 133 | || osArch.equals("amd64") 134 | || osArch.equals("k8")) { 135 | arch = Arch.x86_64; 136 | } 137 | 138 | return arch; 139 | } 140 | } 141 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/dispatcher/DefaultDispatchService.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.dispatcher; 19 | 20 | import com.github.kwhat.jnativehook.GlobalScreen; 21 | import java.util.concurrent.LinkedBlockingQueue; 22 | import java.util.concurrent.ThreadFactory; 23 | import java.util.concurrent.ThreadPoolExecutor; 24 | import java.util.concurrent.TimeUnit; 25 | 26 | /** 27 | * Default implementation of the ExecutorService used to dispatch native events. This 28 | * is effectively the same as calling {@link java.util.concurrent.Executors#newSingleThreadExecutor}. 29 | *

30 | * 31 | * @author Alexander Barker (alex@1stleg.com) 32 | * @version 2.0 33 | * @since 2.0 34 | * @see java.util.concurrent.ExecutorService 35 | * @see GlobalScreen#setEventDispatcher 36 | */ 37 | public class DefaultDispatchService extends ThreadPoolExecutor { 38 | /** 39 | * Instantiates a new default dispatch service using a single thread. 40 | */ 41 | public DefaultDispatchService() { 42 | super( 43 | 1, 1, 0L, 44 | TimeUnit.MILLISECONDS, new LinkedBlockingQueue<>(), 45 | new ThreadFactory() { 46 | public Thread newThread(Runnable r) { 47 | Thread t = new Thread(r); 48 | t.setName("JNativeHook Dispatch Thread"); 49 | t.setDaemon(true); 50 | 51 | return t; 52 | } 53 | } 54 | ); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/dispatcher/SwingDispatchService.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.dispatcher; 19 | 20 | import com.github.kwhat.jnativehook.GlobalScreen; 21 | import java.util.ArrayList; 22 | import java.util.List; 23 | import java.util.concurrent.AbstractExecutorService; 24 | import java.util.concurrent.TimeUnit; 25 | import javax.swing.SwingUtilities; 26 | 27 | /** 28 | * Swing compatible implementation of the ExecutorService used to dispatch native 29 | * events. This wraps event dispatching with {@link java.awt.EventQueue#invokeLater}. 30 | * 31 | * @author Alexander Barker (alex@1stleg.com) 32 | * @version 2.0 33 | * @since 2.0 34 | * @see java.util.concurrent.ExecutorService 35 | * @see GlobalScreen#setEventDispatcher 36 | */ 37 | public class SwingDispatchService extends AbstractExecutorService { 38 | private boolean running; 39 | 40 | public SwingDispatchService() { 41 | running = true; 42 | } 43 | 44 | public void shutdown() { 45 | running = false; 46 | } 47 | 48 | public List shutdownNow() { 49 | running = false; 50 | return new ArrayList<>(0); 51 | } 52 | 53 | public boolean isShutdown() { 54 | return !running; 55 | } 56 | 57 | public boolean isTerminated() { 58 | return !running; 59 | } 60 | 61 | public boolean awaitTermination(long timeout, TimeUnit unit) { 62 | return true; 63 | } 64 | 65 | public void execute(Runnable r) { 66 | SwingUtilities.invokeLater(r); 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/dispatcher/VoidDispatchService.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.dispatcher; 19 | 20 | import com.github.kwhat.jnativehook.GlobalScreen; 21 | import java.util.ArrayList; 22 | import java.util.List; 23 | import java.util.concurrent.AbstractExecutorService; 24 | import java.util.concurrent.TimeUnit; 25 | 26 | /** 27 | * Void implementation of the ExecutorService used to dispatch native events directly on the operating 28 | * system's event delivery thread. Because this queue does not hand off events to a different thread, it is important 29 | * that you do not block on native event callback functions as it will delay or prevent subsequent events from being 30 | * delivered by the operating system. This dispatcher should only be used by those attempting to consume native events. 31 | * 32 | * @author Alexander Barker (alex@1stleg.com) 33 | * @version 2.2 34 | * @see java.util.concurrent.ExecutorService 35 | * @see GlobalScreen#setEventDispatcher 36 | * @since 2.2 37 | */ 38 | public class VoidDispatchService extends AbstractExecutorService { 39 | private boolean running = false; 40 | 41 | public VoidDispatchService() { 42 | running = true; 43 | } 44 | 45 | public void shutdown() { 46 | running = false; 47 | } 48 | 49 | public List shutdownNow() { 50 | running = false; 51 | return new ArrayList(0); 52 | } 53 | 54 | public boolean isShutdown() { 55 | return !running; 56 | } 57 | 58 | public boolean isTerminated() { 59 | return !running; 60 | } 61 | 62 | public boolean awaitTermination(long timeout, TimeUnit unit) { 63 | return true; 64 | } 65 | 66 | public void execute(Runnable r) { 67 | r.run(); 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/dispatcher/package-info.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | /** 20 | * ExecutorService implementations for native event dispatch. 21 | * 22 | * @version 2.0 23 | * @since 2.0 24 | */ 25 | package com.github.kwhat.jnativehook.dispatcher; 26 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/example/package-info.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | /** 20 | * ExecutorService implementations for native event dispatch. 21 | * 22 | * @version 2.0 23 | * @since 2.0 24 | */ 25 | package com.github.kwhat.jnativehook.example; 26 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/keyboard/NativeKeyAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.keyboard; 19 | 20 | /** 21 | * Adapter implementation of the NativeKeyListener interface. The methods are empty so the super 22 | * call is obsolete. 23 | * 24 | * @deprecated No need to extend this class, implement the {@code NativeKeyListener} interface instead 25 | * @author Johannes Boczek 26 | * @since 2.1 27 | */ 28 | @Deprecated 29 | public class NativeKeyAdapter implements NativeKeyListener {} 30 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/keyboard/NativeKeyListener.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.keyboard; 19 | 20 | import com.github.kwhat.jnativehook.GlobalScreen; 21 | import java.util.EventListener; 22 | 23 | /** 24 | * The listener interface for receiving global NativeKeyEvents. 25 | *

26 | * 27 | * The class that is interested in processing a NativeKeyEvent implements this 28 | * interface, and the object created with that class is registered with the 29 | * GlobalScreen using the {@link GlobalScreen#addNativeKeyListener(NativeKeyListener)} 30 | * method. When the 31 | * NativeKeyEvent occurs, that object's appropriate method is 32 | * invoked. 33 | * 34 | * @author Alexander Barker (alex@1stleg.com) 35 | * @version 2.0 36 | * @since 1.0 37 | * @see NativeKeyEvent 38 | */ 39 | public interface NativeKeyListener extends EventListener { 40 | 41 | /** 42 | * Invoked when a key has been typed. 43 | * 44 | * @param nativeEvent the native key event. 45 | * @since 1.1 46 | */ 47 | default void nativeKeyTyped(NativeKeyEvent nativeEvent) {} 48 | 49 | /** 50 | * Invoked when a key has been pressed. 51 | * 52 | * @param nativeEvent the native key event. 53 | */ 54 | default void nativeKeyPressed(NativeKeyEvent nativeEvent) {} 55 | 56 | /** 57 | * Invoked when a key has been released. 58 | * 59 | * @param nativeEvent the native key event. 60 | */ 61 | default void nativeKeyReleased(NativeKeyEvent nativeEvent) {} 62 | } 63 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/keyboard/package-info.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | /** 20 | * Classes used for native keyboard events. 21 | * 22 | * @version 2.0 23 | * @since 1.0 24 | */ 25 | package com.github.kwhat.jnativehook.keyboard; 26 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | /** 21 | * Adapter implementation of the NativeMouseListener interface. The methods are empty so the super 22 | * call is obsolete. 23 | * 24 | * @deprecated No need to extend this class, implement the {@code NativeMouseListener} interface instead 25 | * @author Johannes Boczek 26 | */ 27 | @Deprecated 28 | public class NativeMouseAdapter implements NativeMouseListener {} 29 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseInputAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | /** 21 | * Adapter implementation of the NativeMouseInputListener interface. The methods are empty so the 22 | * super call is obsolete. 23 | * 24 | * @deprecated No need to extend this class, implement the {@code NativeMouseInputListener} interface instead 25 | * @author Johannes Boczek 26 | * @since 2.1 27 | */ 28 | @Deprecated 29 | public class NativeMouseInputAdapter implements NativeMouseInputListener {} 30 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseInputListener.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | /** 21 | * A listener implementing all the methods in both the NativeMouseListener and 22 | * NativeMouseMotionListener interfaces. 23 | * 24 | * @author Alexander Barker (alex@1stleg.com) 25 | * @version 2.0 26 | * @since 1.0 27 | * @see NativeMouseEvent 28 | */ 29 | public interface NativeMouseInputListener extends NativeMouseListener, NativeMouseMotionListener {} 30 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseListener.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import com.github.kwhat.jnativehook.GlobalScreen; 21 | import java.util.EventListener; 22 | 23 | /** 24 | * The listener interface for receiving systemwide NativeMouseEvents. (To track native 25 | * mouse moves, use the NativeMouseMotionListener.) 26 | *

27 | * 28 | * The class that is interested in processing a NativeMouseEvent implements this 29 | * interface, and the object created with that class is registered with the 30 | * GlobalScreen using the {@link GlobalScreen#addNativeMouseListener} method. When the 31 | * NativeMouseMotion event occurs, that object's appropriate 32 | * method is invoked. 33 | * 34 | * @author Alexander Barker (alex@1stleg.com) 35 | * @version 2.0 36 | * @since 1.0 37 | * @see NativeMouseEvent 38 | */ 39 | public interface NativeMouseListener extends EventListener { 40 | /** 41 | * Invoked when a mouse button has been clicked (pressed and released) without being moved. 42 | * 43 | * @param nativeEvent the native mouse event. 44 | */ 45 | default void nativeMouseClicked(NativeMouseEvent nativeEvent) {} 46 | 47 | /** 48 | * Invoked when a mouse button has been pressed 49 | * 50 | * @param nativeEvent the native mouse event. 51 | */ 52 | default void nativeMousePressed(NativeMouseEvent nativeEvent) {} 53 | 54 | /** 55 | * Invoked when a mouse button has been released 56 | * 57 | * @param nativeEvent the native mouse event. 58 | */ 59 | default void nativeMouseReleased(NativeMouseEvent nativeEvent) {} 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseMotionAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | /** 21 | * Adapter implementation of the NativeMouseMotionListener interface. The methods are empty so the 22 | * super call is obsolete. 23 | * 24 | * @deprecated No need to extend this class, implement the {@code NativeMouseMotionListener} interface instead 25 | * @author Johannes Boczek 26 | */ 27 | @Deprecated 28 | public class NativeMouseMotionAdapter implements NativeMouseMotionListener {} 29 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseMotionListener.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import com.github.kwhat.jnativehook.GlobalScreen; 21 | import java.util.EventListener; 22 | 23 | /** 24 | * The listener interface for receiving native mouse motion events. (For clicks and other mouse 25 | * events, use the NativeMouseListener.) 26 | *

27 | * 28 | * The class that is interested in processing a NativeMouseMotionEvent implements this 29 | * interface, and the object created with that class is registered with the 30 | * GlobalScreen using the {@link GlobalScreen#addNativeMouseMotionListener} method. 31 | * When the NativeMouseMotion event occurs, that object's appropriate method is invoked. 32 | * 33 | * @author Alexander Barker (alex@1stleg.com) 34 | * @version 2.0 35 | * @since 1.0 36 | * @see NativeMouseEvent 37 | */ 38 | public interface NativeMouseMotionListener extends EventListener { 39 | 40 | /** 41 | * Invoked when the mouse has been moved. 42 | * 43 | * @param nativeEvent the native mouse event. 44 | */ 45 | default void nativeMouseMoved(NativeMouseEvent nativeEvent) {} 46 | 47 | /** 48 | * Invoked when the mouse has been moved while a button is depressed. 49 | * 50 | * @param nativeEvent the native mouse event 51 | * @since 1.1 52 | */ 53 | default void nativeMouseDragged(NativeMouseEvent nativeEvent) {} 54 | } 55 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseWheelAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | /** 21 | * @deprecated No need to extend this class, implement the {@code NativeMouseWheelListener} interface instead 22 | */ 23 | @Deprecated 24 | public class NativeMouseWheelAdapter implements NativeMouseWheelListener {} 25 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/NativeMouseWheelListener.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import com.github.kwhat.jnativehook.GlobalScreen; 21 | import java.util.EventListener; 22 | 23 | /** 24 | * The listener interface for receiving native mouse wheel events. (For clicks and other mouse 25 | * events, use the NativeMouseListener.) 26 | *

27 | * The class that is interested in processing a NativeMouseWheelEvent implements this 28 | * interface, and the object created with that class is registered with the 29 | * GlobalScreen using the {@link GlobalScreen#addNativeMouseWheelListener(NativeMouseWheelListener)} 30 | * method. When the NativeMouseWheelEvent occurs, that object's appropriate method is invoked. 31 | * 32 | * @author Alexander Barker (alex@1stleg.com) 33 | * @version 2.0 34 | * @since 1.1 35 | * @see NativeMouseWheelEvent 36 | */ 37 | public interface NativeMouseWheelListener extends EventListener { 38 | 39 | /** 40 | * Invoked when the mouse wheel is rotated. 41 | * 42 | * @param nativeEvent the native mouse wheel event. 43 | */ 44 | default void nativeMouseWheelMoved(NativeMouseWheelEvent nativeEvent) {} 45 | } 46 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/SwingMouseAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import com.github.kwhat.jnativehook.AbstractSwingInputAdapter; 21 | import java.awt.event.MouseEvent; 22 | import java.awt.event.MouseListener; 23 | 24 | /** 25 | * Adapter to convert NativeKeyEvents to Java KeyEvents. The methods are empty so the super call is 26 | * obsolete. 27 | * 28 | * @since 2.1 29 | */ 30 | public class SwingMouseAdapter extends AbstractSwingInputAdapter implements NativeMouseListener, MouseListener { 31 | 32 | @Override 33 | public void nativeMouseClicked(NativeMouseEvent nativeEvent) { 34 | this.mouseClicked(this.getJavaKeyEvent(nativeEvent)); 35 | } 36 | 37 | @Override 38 | public void nativeMousePressed(NativeMouseEvent nativeEvent) { 39 | this.mousePressed(this.getJavaKeyEvent(nativeEvent)); 40 | } 41 | 42 | @Override 43 | public void nativeMouseReleased(NativeMouseEvent nativeEvent) { 44 | this.mouseReleased(this.getJavaKeyEvent(nativeEvent)); 45 | } 46 | 47 | @Override 48 | public void mouseClicked(MouseEvent mouseEvent) {} 49 | 50 | @Override 51 | public void mousePressed(MouseEvent mouseEvent) {} 52 | 53 | @Override 54 | public void mouseReleased(MouseEvent mouseEvent) {} 55 | 56 | @Override 57 | public void mouseEntered(MouseEvent mouseEvent) {} 58 | 59 | @Override 60 | public void mouseExited(MouseEvent mouseEvent) {} 61 | 62 | protected MouseEvent getJavaKeyEvent(NativeMouseEvent nativeEvent) { 63 | return new MouseEvent( 64 | this, 65 | nativeEvent.getID() - (NativeMouseEvent.NATIVE_MOUSE_FIRST 66 | - MouseEvent.MOUSE_FIRST), 67 | System.currentTimeMillis(), 68 | this.getJavaModifiers(nativeEvent.getModifiers()), 69 | nativeEvent.getX(), 70 | nativeEvent.getY(), 71 | nativeEvent.getClickCount(), 72 | false, 73 | nativeEvent.getButton()); 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/SwingMouseWheelAdapter.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import java.awt.event.MouseEvent; 21 | import java.awt.event.MouseWheelEvent; 22 | import java.awt.event.MouseWheelListener; 23 | 24 | /** 25 | * Adapter to convert NativeKeyEvents to Java KeyEvents. The methods are empty so the super call is 26 | * obsolete. 27 | * 28 | * @since 2.1 29 | */ 30 | public class SwingMouseWheelAdapter extends SwingMouseAdapter implements NativeMouseWheelListener, 31 | MouseWheelListener { 32 | 33 | @Override 34 | public void nativeMouseWheelMoved(NativeMouseWheelEvent nativeEvent) { 35 | this.mouseWheelMoved(this.getJavaMouseWheelEvent(nativeEvent)); 36 | } 37 | 38 | @Override 39 | public void mouseWheelMoved(MouseWheelEvent mouseWheelEvent) {} 40 | 41 | protected MouseWheelEvent getJavaMouseWheelEvent(NativeMouseWheelEvent nativeEvent) { 42 | int scrollType = MouseWheelEvent.WHEEL_UNIT_SCROLL; 43 | if (nativeEvent.getScrollType() == NativeMouseWheelEvent.WHEEL_BLOCK_SCROLL) { 44 | scrollType = MouseWheelEvent.WHEEL_BLOCK_SCROLL; 45 | } 46 | 47 | return new MouseWheelEvent( 48 | this, 49 | nativeEvent.getID() - (NativeMouseWheelEvent.NATIVE_MOUSE_FIRST 50 | - MouseWheelEvent.MOUSE_FIRST), 51 | System.currentTimeMillis(), 52 | this.getJavaModifiers(nativeEvent.getModifiers()), 53 | nativeEvent.getX(), 54 | nativeEvent.getY(), 55 | nativeEvent.getClickCount(), 56 | false, 57 | scrollType, 58 | nativeEvent.getScrollAmount(), 59 | nativeEvent.getWheelRotation()); 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/main/java/com/github/kwhat/jnativehook/mouse/package-info.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | /** 20 | * Classes used for native mouse events. 21 | * 22 | * @version 2.0 23 | * @since 1.0 24 | */ 25 | package com.github.kwhat.jnativehook.mouse; 26 | -------------------------------------------------------------------------------- /src/main/java/module-info.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | module com.github.kwhat.jnativehook { 20 | exports com.github.kwhat.jnativehook; 21 | exports com.github.kwhat.jnativehook.dispatcher; 22 | exports com.github.kwhat.jnativehook.keyboard; 23 | exports com.github.kwhat.jnativehook.mouse; 24 | 25 | requires transitive java.desktop; 26 | requires transitive java.logging; 27 | } 28 | -------------------------------------------------------------------------------- /src/main/jni/include/com_github_kwhat_jnativehook_NativeInputEvent.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | /* Redefined virtual constants for native use. This file should be machine 20 | * generated however no tool exists for doing so. 21 | * Reference: com/github/kwhat/jnativehook/NativeInputEvent.java 22 | */ 23 | 24 | #ifndef _Included_com_github_kwhat_jnativehook_NativeInputEvent 25 | #define _Included_com_github_kwhat_jnativehook_NativeInputEvent 26 | 27 | #define com_github_kwhat_jnativehook_NativeInputEvent_SHIFT_L_MASK 1 << 0 28 | #define com_github_kwhat_jnativehook_NativeInputEvent_CTRL_L_MASK 1 << 1 29 | #define com_github_kwhat_jnativehook_NativeInputEvent_META_L_MASK 1 << 2 30 | #define com_github_kwhat_jnativehook_NativeInputEvent_ALT_L_MASK 1 << 3 31 | 32 | #define com_github_kwhat_jnativehook_NativeInputEvent_SHIFT_R_MASK 1 << 4 33 | #define com_github_kwhat_jnativehook_NativeInputEvent_CTRL_R_MASK 1 << 5 34 | #define com_github_kwhat_jnativehook_NativeInputEvent_META_R_MASK 1 << 6 35 | #define com_github_kwhat_jnativehook_NativeInputEvent_ALT_R_MASK 1 << 7 36 | 37 | #define com_github_kwhat_jnativehook_NativeInputEvent_BUTTON1_MASK 1 << 8 38 | #define com_github_kwhat_jnativehook_NativeInputEvent_BUTTON2_MASK 1 << 9 39 | #define com_github_kwhat_jnativehook_NativeInputEvent_BUTTON3_MASK 1 << 10 40 | #define com_github_kwhat_jnativehook_NativeInputEvent_BUTTON4_MASK 1 << 11 41 | #define com_github_kwhat_jnativehook_NativeInputEvent_BUTTON5_MASK 1 << 12 42 | 43 | #endif 44 | -------------------------------------------------------------------------------- /src/main/jni/include/com_github_kwhat_jnativehook_mouse_NativeMouseEvent.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | /* Redefined virtual constants for native use. This file should be machine 20 | * generated however no tool exists for doing so. 21 | * Reference: com/github/kwhat/jnativehook/mouse/NativeMouseEvent.java 22 | */ 23 | 24 | #ifndef _Included_com_github_kwhat_jnativehook_mouse_NativeMouseEvent 25 | #define _Included_com_github_kwhat_jnativehook_mouse_NativeMouseEvent 26 | 27 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST 2500 28 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_LAST 2505 29 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_CLICKED com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST 30 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_PRESSED 1 + com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST 31 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_RELEASED 2 + com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST 32 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_MOVED 3 + com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST 33 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_DRAGGED 4 + com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST 34 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_WHEEL 5 + com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST 35 | 36 | 37 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NOBUTTON 0 // AnyButton 38 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_BUTTON1 1 39 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_BUTTON2 2 40 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_BUTTON3 3 41 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_BUTTON4 4 // Extra Mouse Button 42 | #define com_github_kwhat_jnativehook_mouse_NativeMouseEvent_BUTTON5 5 // Extra Mouse Button 43 | 44 | #endif 45 | -------------------------------------------------------------------------------- /src/main/jni/include/com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | /* Redefined virtual constants for native use. This file should be machine 20 | * generated however no tool exists for doing so. 21 | * Reference: com/github/kwhat/jnativehook/mouse/NativeMouseWheelEvent.java 22 | */ 23 | 24 | #ifndef _Included_com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent 25 | #define _Included_com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent 26 | 27 | #define com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent_WHEEL_UNIT_SCROLL 0 28 | #define com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent_WHEEL_BLOCK_SCROLL 1 29 | 30 | #endif 31 | -------------------------------------------------------------------------------- /src/main/jni/jni_Converter.c: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #include 20 | #include 21 | 22 | #include "jni_Converter.h" 23 | #include "com_github_kwhat_jnativehook_NativeInputEvent.h" 24 | #include "com_github_kwhat_jnativehook_keyboard_NativeKeyEvent.h" 25 | #include "com_github_kwhat_jnativehook_mouse_NativeMouseEvent.h" 26 | #include "com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent.h" 27 | 28 | 29 | jint jni_ConvertToJavaType(event_type nativeType, jint *javaType) { 30 | jint status = JNI_ERR; 31 | 32 | if (javaType != NULL) { 33 | switch (nativeType) { 34 | case EVENT_KEY_TYPED: 35 | case EVENT_KEY_PRESSED: 36 | case EVENT_KEY_RELEASED: 37 | // 3 = EVENT_HOOK_ENABLED + EVENT_HOOK_DISABLED + UNDEFINED. 38 | *javaType = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_FIRST + (nativeType - 3); 39 | status = JNI_OK; 40 | break; 41 | 42 | case EVENT_MOUSE_CLICKED: 43 | case EVENT_MOUSE_PRESSED: 44 | case EVENT_MOUSE_RELEASED: 45 | case EVENT_MOUSE_MOVED: 46 | case EVENT_MOUSE_DRAGGED: 47 | case EVENT_MOUSE_WHEEL: 48 | // 6 = (NATIVE_KEY_LAST - NATIVE_KEY_FIRST) + EVENT_HOOK_ENABLED + EVENT_HOOK_DISABLED + UNDEFINED. 49 | *javaType = com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST + (nativeType - 6); 50 | status = JNI_OK; 51 | break; 52 | 53 | default: 54 | *javaType = 0; 55 | break; 56 | } 57 | } 58 | 59 | return status; 60 | } 61 | 62 | 63 | jint jni_ConvertToNativeType(jint javaType, event_type *nativeType) { 64 | jint status = JNI_ERR; 65 | 66 | if (nativeType != NULL) { 67 | switch (javaType) { 68 | case com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_TYPED: 69 | case com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_PRESSED: 70 | case com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_RELEASED: 71 | *nativeType = (javaType + 3) - com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_FIRST; 72 | status = JNI_OK; 73 | break; 74 | 75 | case com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_CLICKED: 76 | case com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_PRESSED: 77 | case com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_RELEASED: 78 | case com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_MOVED: 79 | case com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_DRAGGED: 80 | case com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_WHEEL: 81 | *nativeType = (javaType + 6) - com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_FIRST; 82 | status = JNI_OK; 83 | break; 84 | 85 | default: 86 | *nativeType = 0; 87 | break; 88 | } 89 | } 90 | 91 | return status; 92 | } 93 | 94 | jint jni_ConvertToJavaLocation(unsigned short int *nativeKeyCode, jint *javaKeyLocation) { 95 | jint status = JNI_ERR; 96 | 97 | if (nativeKeyCode != NULL && javaKeyLocation != NULL) { 98 | switch (*nativeKeyCode) { 99 | case VC_SHIFT_L: 100 | case VC_CONTROL_L: 101 | case VC_ALT_L: 102 | case VC_META_L: 103 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_LEFT; 104 | break; 105 | 106 | case VC_SHIFT_R: 107 | case VC_CONTROL_R: 108 | case VC_ALT_R: 109 | *nativeKeyCode ^= 0x0E00; 110 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_RIGHT; 111 | break; 112 | 113 | case VC_META_R: 114 | *nativeKeyCode -= 1; 115 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_RIGHT; 116 | break; 117 | 118 | case VC_KP_COMMA: 119 | *nativeKeyCode = VC_COMMA; 120 | /* fall-thru */ 121 | 122 | case VC_NUM_LOCK: 123 | case VC_KP_SEPARATOR: 124 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_NUMPAD; 125 | break; 126 | 127 | case VC_KP_ENTER: 128 | case VC_KP_MULTIPLY: 129 | case VC_KP_ADD: 130 | case VC_KP_SUBTRACT: 131 | case VC_KP_DIVIDE: 132 | 133 | case VC_KP_DOWN: 134 | case VC_KP_LEFT: 135 | case VC_KP_CLEAR: 136 | case VC_KP_RIGHT: 137 | case VC_KP_UP: 138 | *nativeKeyCode ^= 0x0E00; 139 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_NUMPAD; 140 | break; 141 | 142 | case VC_KP_0: 143 | *nativeKeyCode = VC_0; 144 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_NUMPAD; 145 | break; 146 | 147 | case VC_KP_1: 148 | case VC_KP_2: 149 | case VC_KP_3: 150 | *nativeKeyCode -= ((VC_KP_1 - VC_1) - (VC_KP_4 - VC_4) ); // 0x4D - 0x46 151 | // FIXME Should this fall though? 152 | /* fall-thru */ 153 | 154 | case VC_KP_4: 155 | case VC_KP_5: 156 | case VC_KP_6: 157 | *nativeKeyCode -= ((VC_KP_4 - VC_4) - (VC_KP_7 - VC_7) ); // 0x46 - 0x3F 158 | // FIXME Should this fall though? 159 | /* fall-thru */ 160 | 161 | case VC_KP_7: 162 | case VC_KP_8: 163 | case VC_KP_9: 164 | *nativeKeyCode -= (VC_KP_7 - VC_7); // 0x3F 165 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_NUMPAD; 166 | break; 167 | 168 | case VC_KP_END: 169 | case VC_KP_PAGE_DOWN: 170 | case VC_KP_HOME: 171 | case VC_KP_PAGE_UP: 172 | case VC_KP_INSERT: 173 | case VC_KP_DELETE: 174 | *nativeKeyCode ^= 0xE000; 175 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_NUMPAD; 176 | break; 177 | 178 | default: 179 | *javaKeyLocation = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_STANDARD; 180 | break; 181 | } 182 | 183 | status = JNI_OK; 184 | } 185 | 186 | return status; 187 | } 188 | -------------------------------------------------------------------------------- /src/main/jni/jni_Converter.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #ifndef _Included_jni_Converter_h 20 | #define _Included_jni_Converter_h 21 | 22 | #include 23 | #include 24 | 25 | extern jint jni_ConvertToJavaType(event_type nativeType, jint *javaType); 26 | 27 | extern jint jni_ConvertToNativeType(jint javaType, event_type *nativeType); 28 | 29 | extern jint jni_ConvertToJavaLocation(unsigned short int *nativeKeyCode, jint *javaKeyLocation); 30 | 31 | #endif 32 | -------------------------------------------------------------------------------- /src/main/jni/jni_Errors.c: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #include 20 | #include 21 | 22 | #include "jni_Errors.h" 23 | #include "jni_Globals.h" 24 | #include "jni_Logger.h" 25 | 26 | void jni_ThrowFatalError(JNIEnv *env, const char *message) { 27 | // Throw a fatal error to the JVM. 28 | (*env)->FatalError(env, message); 29 | 30 | exit(EXIT_FAILURE); 31 | } 32 | 33 | void jni_ThrowException(JNIEnv *env, const char *classname, const char *message) { 34 | // Locate our exception class. 35 | jclass Exception_class = (*env)->FindClass(env, classname); 36 | if (Exception_class != NULL) { 37 | (*env)->ThrowNew(env, Exception_class, message); 38 | (*env)->DeleteLocalRef(env, Exception_class); 39 | } else { 40 | // Throw a ClassNotFoundException if we could not locate the exception class above. 41 | Exception_class = (*env)->FindClass(env, "java/lang/ClassNotFoundException"); 42 | if (Exception_class != NULL) { 43 | (*env)->ThrowNew(env, Exception_class, classname); 44 | (*env)->DeleteLocalRef(env, Exception_class); 45 | } else { 46 | jni_ThrowFatalError(env, "Failed to locate core class: java.lang.ClassNotFoundException"); 47 | } 48 | } 49 | } 50 | 51 | void jni_ThrowNativeHookException(JNIEnv *env, short code, const char *message) { 52 | jobject Exception_object = (*env)->NewObject(env, com_github_kwhat_jnativehook_NativeHookException->cls, 53 | com_github_kwhat_jnativehook_NativeHookException->init, (jint) code, (*env)->NewStringUTF(env, message)); 54 | (*env)->Throw(env, (jthrowable) Exception_object); 55 | (*env)->DeleteLocalRef(env, Exception_object); 56 | } 57 | -------------------------------------------------------------------------------- /src/main/jni/jni_Errors.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #ifndef _Included_jni_Errors_h 20 | #define _Included_jni_Errors_h 21 | 22 | /* Produces a fatal error in the virtual machine. This error is unrecoverable 23 | * and program execution will terminate immediately. 24 | */ 25 | extern void jni_ThrowFatalError(JNIEnv *env, const char *message); 26 | 27 | /* Produces and throw a general exception to the virtual machine. This error may or may 28 | * not be recoverable outside of the native library. 29 | */ 30 | extern void jni_ThrowException(JNIEnv *env, const char *classname, const char *message); 31 | 32 | /* Produces a specific NativeHookException containing an error code indicating what might 33 | * have gone wrong. 34 | */ 35 | extern void jni_ThrowNativeHookException(JNIEnv *env, short code, const char *message); 36 | 37 | #endif 38 | -------------------------------------------------------------------------------- /src/main/jni/jni_EventDispatcher.c: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #include 20 | #include 21 | #include 22 | 23 | #include "jni_Converter.h" 24 | #include "jni_Errors.h" 25 | #include "jni_Globals.h" 26 | #include "jni_Logger.h" 27 | #include "com_github_kwhat_jnativehook_NativeInputEvent.h" 28 | #include "com_github_kwhat_jnativehook_keyboard_NativeKeyEvent.h" 29 | #include "com_github_kwhat_jnativehook_mouse_NativeMouseEvent.h" 30 | #include "com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent.h" 31 | 32 | // Simple function to notify() the hook thread. 33 | static inline void notifyHookThread(JNIEnv *env) { 34 | jobject hookThread_obj = (*env)->GetStaticObjectField( 35 | env, 36 | java_lang_Object->cls, 37 | com_github_kwhat_jnativehook_GlobalScreen->hookThread); 38 | 39 | if (hookThread_obj != NULL) { 40 | (*env)->MonitorEnter(env, hookThread_obj); 41 | (*env)->CallVoidMethod( 42 | env, 43 | hookThread_obj, 44 | java_lang_Object->notify); 45 | (*env)->MonitorExit(env, hookThread_obj); 46 | } 47 | } 48 | 49 | // NOTE: This function executes on the hook thread! If you need to block 50 | // please do so on another thread via your own event dispatcher. 51 | void jni_EventDispatcher(uiohook_event * const event) { 52 | JNIEnv *env; 53 | if ((*jvm)->GetEnv(jvm, (void **)(&env), jvm_attach_args.version) == JNI_OK) { 54 | jobject NativeInputEvent_obj = NULL; 55 | jint location = com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_LOCATION_UNKNOWN; 56 | switch (event->type) { 57 | case EVENT_HOOK_DISABLED: 58 | case EVENT_HOOK_ENABLED: 59 | notifyHookThread(env); 60 | return; 61 | 62 | 63 | case EVENT_KEY_PRESSED: 64 | // FIXME We really shouldnt be wrighting to that memory. 65 | if (jni_ConvertToJavaLocation(&(event->data.keyboard.keycode), &location) == JNI_OK) { 66 | NativeInputEvent_obj = (*env)->NewObject( 67 | env, 68 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent->cls, 69 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent->init, 70 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_PRESSED, 71 | (jint) event->mask, 72 | (jint) event->data.keyboard.rawcode, 73 | (jint) event->data.keyboard.keycode, 74 | (jchar) com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_CHAR_UNDEFINED, 75 | location); 76 | } 77 | break; 78 | 79 | case EVENT_KEY_RELEASED: 80 | // FIXME We really shouldnt be wrighting to that memory. 81 | if (jni_ConvertToJavaLocation(&(event->data.keyboard.keycode), &location) == JNI_OK) { 82 | NativeInputEvent_obj = (*env)->NewObject( 83 | env, 84 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent->cls, 85 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent->init, 86 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_RELEASED, 87 | (jint) event->mask, 88 | (jint) event->data.keyboard.rawcode, 89 | (jint) event->data.keyboard.keycode, 90 | (jchar) com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_CHAR_UNDEFINED, 91 | location); 92 | } 93 | break; 94 | 95 | case EVENT_KEY_TYPED: 96 | NativeInputEvent_obj = (*env)->NewObject( 97 | env, 98 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent->cls, 99 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent->init, 100 | com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_NATIVE_KEY_TYPED, 101 | (jint) event->mask, 102 | (jint) event->data.keyboard.rawcode, 103 | (jint) com_github_kwhat_jnativehook_keyboard_NativeKeyEvent_VC_UNDEFINED, 104 | (jchar) event->data.keyboard.keychar, 105 | location); 106 | break; 107 | 108 | 109 | case EVENT_MOUSE_PRESSED: 110 | NativeInputEvent_obj = (*env)->NewObject( 111 | env, 112 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->cls, 113 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->init, 114 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_PRESSED, 115 | (jint) event->mask, 116 | (jint) event->data.mouse.x, 117 | (jint) event->data.mouse.y, 118 | (jint) event->data.mouse.clicks, 119 | (jint) event->data.mouse.button); 120 | break; 121 | 122 | case EVENT_MOUSE_RELEASED: 123 | NativeInputEvent_obj = (*env)->NewObject( 124 | env, 125 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->cls, 126 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->init, 127 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_RELEASED, 128 | (jint) event->mask, 129 | (jint) event->data.mouse.x, 130 | (jint) event->data.mouse.y, 131 | (jint) event->data.mouse.clicks, 132 | (jint) event->data.mouse.button); 133 | break; 134 | 135 | case EVENT_MOUSE_CLICKED: 136 | NativeInputEvent_obj = (*env)->NewObject( 137 | env, 138 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->cls, 139 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->init, 140 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_CLICKED, 141 | (jint) event->mask, 142 | (jint) event->data.mouse.x, 143 | (jint) event->data.mouse.y, 144 | (jint) event->data.mouse.clicks, 145 | (jint) event->data.mouse.button); 146 | break; 147 | 148 | case EVENT_MOUSE_MOVED: 149 | NativeInputEvent_obj = (*env)->NewObject( 150 | env, 151 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->cls, 152 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->init, 153 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_MOVED, 154 | (jint) event->mask, 155 | (jint) event->data.mouse.x, 156 | (jint) event->data.mouse.y, 157 | (jint) event->data.mouse.clicks, 158 | (jint) event->data.mouse.button); 159 | break; 160 | 161 | case EVENT_MOUSE_DRAGGED: 162 | NativeInputEvent_obj = (*env)->NewObject( 163 | env, 164 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->cls, 165 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent->init, 166 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_DRAGGED, 167 | (jint) event->mask, 168 | (jint) event->data.mouse.x, 169 | (jint) event->data.mouse.y, 170 | (jint) event->data.mouse.clicks, 171 | (jint) event->data.mouse.button); 172 | break; 173 | 174 | case EVENT_MOUSE_WHEEL: 175 | NativeInputEvent_obj = (*env)->NewObject( 176 | env, 177 | com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent->cls, 178 | com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent->init, 179 | com_github_kwhat_jnativehook_mouse_NativeMouseEvent_NATIVE_MOUSE_WHEEL, 180 | (jint) event->mask, 181 | (jint) event->data.wheel.x, 182 | (jint) event->data.wheel.y, 183 | (jint) event->data.wheel.clicks, 184 | (jint) event->data.wheel.type, 185 | (jint) event->data.wheel.amount, 186 | (jint) event->data.wheel.rotation, 187 | (jint) event->data.wheel.direction); 188 | break; 189 | 190 | default: 191 | jni_Logger(LOG_LEVEL_INFO, "%s [%u]: Unknown native event type: %#X.\n", 192 | __FUNCTION__, __LINE__, event->type); 193 | break; 194 | } 195 | 196 | if (NativeInputEvent_obj != NULL) { 197 | // Set the private when field to the native event time. 198 | (*env)->SetLongField( 199 | env, 200 | NativeInputEvent_obj, 201 | com_github_kwhat_jnativehook_NativeInputEvent->when, 202 | (jlong) event->time); 203 | 204 | // Dispatch the event. 205 | (*env)->CallStaticVoidMethod( 206 | env, 207 | com_github_kwhat_jnativehook_GlobalScreen$NativeHookThread->cls, 208 | com_github_kwhat_jnativehook_GlobalScreen$NativeHookThread->dispatchEvent, 209 | NativeInputEvent_obj); 210 | 211 | // Set the propagate flag from java. 212 | event->reserved = (unsigned short) (*env)->GetShortField( 213 | env, 214 | NativeInputEvent_obj, 215 | com_github_kwhat_jnativehook_NativeInputEvent->reserved); 216 | 217 | // Make sure our object is garbage collected. 218 | (*env)->DeleteLocalRef(env, NativeInputEvent_obj); 219 | } 220 | } 221 | } 222 | -------------------------------------------------------------------------------- /src/main/jni/jni_EventDispathcer.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #ifndef _Included_jni_EventDispathcer_h 20 | #define _Included_jni_EventDispathcer_h 21 | 22 | #include 23 | 24 | // This is a simple forwarding function to the Java event dispatcher. 25 | extern void jni_EventDispatcher(uiohook_event * const event); 26 | 27 | #endif 28 | -------------------------------------------------------------------------------- /src/main/jni/jni_Globals.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #ifndef _Included_jni_Globals_h 20 | #define _Included_jni_Globals_h 21 | 22 | #include 23 | 24 | // Globals for the jvm and jni version, this is set in JNILoad.c 25 | extern JavaVM *jvm; 26 | extern JavaVMAttachArgs jvm_attach_args; 27 | 28 | /* JNI requires that all calls to FindClass be made during JNI_OnLoad to 29 | * prevent NoClassDefError from popping up when various Java security models 30 | * are used. The following structures are used to better organize the data 31 | * associated with each class. Note that these structs do not cover all of the 32 | * available methods for each class; only methods used in native code are 33 | * included. 34 | */ 35 | typedef struct _com_github_kwhat_jnativehook_GlobalScreen { 36 | jclass cls; 37 | jfieldID hookThread; 38 | } GlobalScreen; 39 | 40 | typedef struct com_github_kwhat_jnativehook_GlobalScreen$NativeHookThread { 41 | jclass cls; 42 | jmethodID dispatchEvent; 43 | } NativeHookThread; 44 | 45 | typedef struct _com_github_kwhat_jnativehook_NativeHookException { 46 | jclass cls; 47 | jmethodID init; 48 | } NativeHookException; 49 | 50 | typedef struct _com_github_kwhat_jnativehook_NativeMonitorInfo { 51 | jclass cls; 52 | jmethodID init; 53 | } NativeMonitorInfo; 54 | 55 | typedef struct _com_github_kwhat_jnativehook_NativeInputEvent { 56 | jclass cls; 57 | jfieldID when; 58 | jfieldID reserved; 59 | jmethodID init; 60 | jmethodID getID; 61 | jmethodID getModifiers; 62 | } NativeInputEvent; 63 | 64 | typedef struct _com_github_kwhat_jnativehook_keyboard_NativeKeyEvent { 65 | jclass cls; 66 | jmethodID init; 67 | NativeInputEvent *parent; 68 | jmethodID getKeyCode; 69 | jmethodID getKeyLocation; 70 | jmethodID getKeyChar; 71 | } NativeKeyEvent; 72 | 73 | typedef struct _com_github_kwhat_jnativehook_mouse_NativeMouseEvent { 74 | jclass cls; 75 | jmethodID init; 76 | NativeInputEvent *parent; 77 | jmethodID getButton; 78 | jmethodID getClickCount; 79 | jmethodID getX; 80 | jmethodID getY; 81 | } NativeMouseEvent; 82 | 83 | typedef struct _com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent { 84 | jclass cls; 85 | jmethodID init; 86 | NativeMouseEvent *parent; 87 | jmethodID getScrollAmount; 88 | jmethodID getScrollType; 89 | jmethodID getWheelRotation; 90 | } NativeMouseWheelEvent; 91 | 92 | typedef struct _java_lang_Object { 93 | jclass cls; 94 | jmethodID notify; 95 | } Object; 96 | 97 | typedef struct _java_lang_Integer { 98 | jclass cls; 99 | jmethodID init; 100 | } Integer; 101 | 102 | typedef struct _java_lang_System { 103 | jclass cls; 104 | jmethodID setProperty; 105 | jmethodID clearProperty; 106 | } System; 107 | 108 | typedef struct _java_util_logging_Logger { 109 | jclass cls; 110 | jmethodID getLogger; 111 | jmethodID fine; 112 | jmethodID info; 113 | jmethodID warning; 114 | jmethodID severe; 115 | } Logger; 116 | 117 | // Global variables for Java object struct representation. 118 | extern GlobalScreen *com_github_kwhat_jnativehook_GlobalScreen; 119 | extern NativeHookThread *com_github_kwhat_jnativehook_GlobalScreen$NativeHookThread; 120 | extern NativeHookException *com_github_kwhat_jnativehook_NativeHookException; 121 | extern NativeMonitorInfo *com_github_kwhat_jnativehook_NativeMonitorInfo; 122 | extern NativeInputEvent *com_github_kwhat_jnativehook_NativeInputEvent; 123 | extern NativeKeyEvent *com_github_kwhat_jnativehook_keyboard_NativeKeyEvent; 124 | extern NativeMouseEvent *com_github_kwhat_jnativehook_mouse_NativeMouseEvent; 125 | extern NativeMouseWheelEvent *com_github_kwhat_jnativehook_mouse_NativeMouseWheelEvent; 126 | extern Object *java_lang_Object; 127 | extern Integer *java_lang_Integer; 128 | extern System *java_lang_System; 129 | extern Logger *java_util_logging_Logger; 130 | 131 | // Create all of the JNI global references used throughout the native library. 132 | extern int jni_CreateGlobals(JNIEnv *env); 133 | 134 | // Free all of the JNI globals created by the CreateJNIGlobals() function. 135 | extern int jni_DestroyGlobals(JNIEnv *env); 136 | 137 | #endif 138 | -------------------------------------------------------------------------------- /src/main/jni/jni_Load.c: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #include 20 | #include 21 | 22 | #include "jni_Errors.h" 23 | #include "jni_EventDispathcer.h" 24 | #include "jni_Globals.h" 25 | #include "jni_Logger.h" 26 | 27 | // JNI Related global references. 28 | JavaVM *jvm; 29 | JavaVMAttachArgs jvm_attach_args = { 30 | .version = JNI_VERSION_1_4, 31 | .name = "JNativeHook Library", 32 | .group = NULL 33 | }; 34 | 35 | // JNI entry point, This is executed when the Java virtual machine attaches to the native library. 36 | JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *reserved) { 37 | // Grab the currently running virtual machine so we can attach to it in 38 | // functions that are not called from java. 39 | jvm = vm; 40 | JNIEnv *env = NULL; 41 | if ((*jvm)->GetEnv(jvm, (void **)(&env), jvm_attach_args.version) == JNI_OK) { 42 | // Create all the global class references onload to prevent class loader 43 | // issues with JNLP and some IDE's. 44 | if (jni_CreateGlobals(env) == JNI_OK) { 45 | // Set Java logger for native code messages. 46 | hook_set_logger_proc(&jni_Logger); 47 | 48 | // Set the hook callback function to dispatch events. 49 | hook_set_dispatch_proc(&jni_EventDispatcher); 50 | } 51 | } else { 52 | jni_ThrowFatalError(env, "Failed to acquire JNI interface pointer"); 53 | } 54 | 55 | return jvm_attach_args.version; 56 | } 57 | 58 | // JNI exit point, This is executed when the Java virtual machine detaches from the native library. 59 | JNIEXPORT void JNICALL JNI_OnUnload(JavaVM *vm, void *reserved) { 60 | // Unset the hook callback function to dispatch events. 61 | hook_set_dispatch_proc(NULL); 62 | 63 | // Unset Java logger for native code messages. 64 | hook_set_logger_proc(NULL); 65 | 66 | // Grab the currently JNI interface pointer so we can cleanup the 67 | // system properties set on load. 68 | JNIEnv *env = NULL; 69 | if ((*jvm)->GetEnv(jvm, (void **)(&env), jvm_attach_args.version) == JNI_OK) { 70 | // It is not critical that these values are cleared so no exception 71 | // will be thrown if this does not succeed. 72 | 73 | // Cleanup JNI global memory. 74 | jni_DestroyGlobals(env); 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /src/main/jni/jni_Logger.c: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #include 20 | #include 21 | #include 22 | #include 23 | #include 24 | 25 | #include "jni_Errors.h" 26 | #include "jni_Globals.h" 27 | 28 | static char buffer[1024]; 29 | 30 | bool jni_Logger(unsigned int level, const char *format, ...) { 31 | bool status = false; 32 | 33 | JNIEnv *env = NULL; 34 | if ((*jvm)->GetEnv(jvm, (void **)(&env), jvm_attach_args.version) == JNI_OK) { 35 | 36 | va_list args; 37 | va_start(args, format); 38 | int size = vsnprintf(buffer, sizeof(buffer), format, args); 39 | va_end(args); 40 | 41 | if (size >= 0) { 42 | jstring name = (*env)->NewStringUTF(env, "com.github.kwhat.jnativehook"); 43 | jstring message = (*env)->NewStringUTF(env, buffer); 44 | 45 | jobject object = (*env)->CallStaticObjectMethod( 46 | env, 47 | java_util_logging_Logger->cls, 48 | java_util_logging_Logger->getLogger, 49 | name); 50 | 51 | switch (level) { 52 | case LOG_LEVEL_DEBUG: 53 | (*env)->CallVoidMethod( 54 | env, 55 | object, 56 | java_util_logging_Logger->fine, 57 | message); 58 | break; 59 | 60 | case LOG_LEVEL_INFO: 61 | (*env)->CallVoidMethod( 62 | env, 63 | object, 64 | java_util_logging_Logger->info, 65 | message); 66 | break; 67 | 68 | case LOG_LEVEL_WARN: 69 | (*env)->CallVoidMethod( 70 | env, 71 | object, 72 | java_util_logging_Logger->warning, 73 | message); 74 | break; 75 | 76 | case LOG_LEVEL_ERROR: 77 | (*env)->CallVoidMethod( 78 | env, 79 | object, 80 | java_util_logging_Logger->severe, 81 | message); 82 | break; 83 | } 84 | 85 | (*env)->DeleteLocalRef(env, name); 86 | (*env)->DeleteLocalRef(env, message); 87 | (*env)->DeleteLocalRef(env, object); 88 | 89 | status = true; 90 | } 91 | } 92 | 93 | return status; 94 | } 95 | -------------------------------------------------------------------------------- /src/main/jni/jni_Logger.h: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | 19 | #ifndef _Included_jni_Logger_h 20 | #define _Included_jni_Logger_h 21 | 22 | #include 23 | #include 24 | #include 25 | 26 | extern bool jni_Logger(unsigned int level, const char *format, ...); 27 | 28 | #endif 29 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/NativeHookExceptionTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import org.junit.jupiter.api.Test; 21 | import static org.junit.jupiter.api.Assertions.assertEquals; 22 | import static org.junit.jupiter.api.Assertions.fail; 23 | 24 | public class NativeHookExceptionTest { 25 | @Test 26 | public void testCode() { 27 | int code = NativeHookException.HOOK_FAILURE; 28 | 29 | try { 30 | throw new NativeHookException(code); 31 | } 32 | catch (NativeHookException e) { 33 | assertEquals(code, e.getCode()); 34 | } 35 | catch (Exception e) { 36 | fail("Invalid exception type: " + e.getClass()); 37 | } 38 | } 39 | 40 | @Test 41 | public void testMessage() { 42 | String message = "Test NativeHookException"; 43 | 44 | try { 45 | throw new NativeHookException(message); 46 | } 47 | catch (NativeHookException e) { 48 | assertEquals(message, e.getMessage()); 49 | } 50 | catch (Exception e) { 51 | fail("Invalid exception type: " + e.getClass()); 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/NativeInputEventTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import com.github.kwhat.jnativehook.keyboard.NativeKeyEvent; 21 | import org.junit.jupiter.api.Test; 22 | import static org.junit.jupiter.api.Assertions.assertEquals; 23 | import static org.junit.jupiter.api.Assertions.assertNotEquals; 24 | 25 | public class NativeInputEventTest { 26 | @Test 27 | public void testGetID() { 28 | NativeInputEvent event = new NativeInputEvent( 29 | GlobalScreen.class, 30 | NativeKeyEvent.NATIVE_KEY_PRESSED, 31 | 0x00); 32 | 33 | assertEquals(event.getID(), NativeKeyEvent.NATIVE_KEY_PRESSED); 34 | } 35 | 36 | @Test 37 | public void testGetWhen() { 38 | long when = 0; 39 | 40 | NativeInputEvent event = new NativeInputEvent( 41 | GlobalScreen.class, 42 | NativeKeyEvent.NATIVE_KEY_PRESSED, 43 | 0x00); 44 | 45 | assertEquals(event.getWhen(), when); 46 | } 47 | 48 | @Test 49 | public void testGetModifiers() { 50 | int mask = NativeInputEvent.ALT_MASK 51 | | NativeInputEvent.CTRL_MASK 52 | | NativeInputEvent.META_MASK 53 | | NativeInputEvent.SHIFT_MASK; 54 | 55 | NativeInputEvent event = new NativeInputEvent( 56 | GlobalScreen.class, 57 | NativeKeyEvent.NATIVE_KEY_PRESSED, 58 | mask); 59 | 60 | assertEquals(event.getModifiers(), mask); 61 | } 62 | 63 | @Test 64 | public void testSetModifiers() { 65 | int mask = NativeInputEvent.BUTTON1_MASK 66 | | NativeInputEvent.BUTTON2_MASK 67 | | NativeInputEvent.BUTTON3_MASK 68 | | NativeInputEvent.BUTTON4_MASK 69 | | NativeInputEvent.BUTTON5_MASK; 70 | 71 | NativeInputEvent event = new NativeInputEvent( 72 | GlobalScreen.class, 73 | NativeKeyEvent.NATIVE_KEY_PRESSED, 74 | 0x00); 75 | 76 | event.setModifiers(mask); 77 | assertEquals(event.getModifiers(), mask); 78 | } 79 | 80 | @Test 81 | public void testGetModifiersText() { 82 | int mask = NativeInputEvent.ALT_MASK 83 | | NativeInputEvent.BUTTON1_MASK; 84 | 85 | assertNotEquals("", NativeInputEvent.getModifiersText(mask)); 86 | } 87 | 88 | @Test 89 | public void testParamString() { 90 | NativeInputEvent event = new NativeInputEvent( 91 | GlobalScreen.class, 92 | NativeKeyEvent.NATIVE_KEY_PRESSED, 93 | NativeInputEvent.SHIFT_MASK 94 | | NativeInputEvent.BUTTON5_MASK); 95 | 96 | assertNotEquals("", event.paramString()); 97 | } 98 | } 99 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/NativeMonitorInfoTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import org.junit.jupiter.api.BeforeEach; 21 | import org.junit.jupiter.api.Test; 22 | import static org.junit.jupiter.api.Assertions.assertEquals; 23 | 24 | public class NativeMonitorInfoTest { 25 | private short number; 26 | private short x; 27 | private short y; 28 | private short width; 29 | private short height; 30 | 31 | private NativeMonitorInfo subject; 32 | 33 | @BeforeEach 34 | public void initialize() { 35 | number = 2; 36 | x = 100; 37 | y = 200; 38 | width = 1024; 39 | height = 768; 40 | 41 | subject = new NativeMonitorInfo(number, x, y, width, height); 42 | } 43 | 44 | @Test 45 | public void testConstructor() { 46 | assertEquals(number, subject.getNumber()); 47 | assertEquals(x, subject.getX()); 48 | assertEquals(y, subject.getY()); 49 | assertEquals(width, subject.getWidth()); 50 | assertEquals(height, subject.getHeight()); 51 | } 52 | 53 | @Test 54 | public void testNumber() { 55 | number = 1; 56 | subject.setNumber(number); 57 | 58 | assertEquals(number, subject.getNumber()); 59 | } 60 | 61 | @Test 62 | public void testX() { 63 | short x = 500; 64 | subject.setX(x); 65 | 66 | assertEquals(x, subject.getX()); 67 | } 68 | 69 | @Test 70 | public void testY() { 71 | y = 500; 72 | subject.setY(y); 73 | 74 | assertEquals(y, subject.getY()); 75 | } 76 | 77 | @Test 78 | public void testWidth() { 79 | width = 1280; 80 | subject.setWidth(width); 81 | 82 | assertEquals(width, subject.getWidth()); 83 | } 84 | 85 | @Test 86 | public void testHeight() { 87 | height = 1280; 88 | subject.setHeight(height); 89 | 90 | assertEquals(height, subject.getHeight()); 91 | } 92 | } 93 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/NativeSystemTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook; 19 | 20 | import org.junit.jupiter.api.Test; 21 | import static org.junit.jupiter.api.Assertions.assertEquals; 22 | 23 | public class NativeSystemTest { 24 | @Test 25 | public void testGetFamily() { 26 | System.setProperty("os.name", "FreeBSD"); 27 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.FREEBSD); 28 | 29 | System.setProperty("os.name", "OpenBSD"); 30 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.OPENBSD); 31 | 32 | System.setProperty("os.name", "Mac OS X"); 33 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.DARWIN); 34 | 35 | System.setProperty("os.name", "SunOS"); 36 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.SOLARIS); 37 | 38 | System.setProperty("os.name", "Solaris"); 39 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.SOLARIS); 40 | 41 | System.setProperty("os.name", "Linux"); 42 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.LINUX); 43 | 44 | System.setProperty("os.name", "Windows 2000"); 45 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 46 | 47 | System.setProperty("os.name", "Windows 2003"); 48 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 49 | 50 | System.setProperty("os.name", "Windows 2008"); 51 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 52 | 53 | System.setProperty("os.name", "Windows 2008 R2"); 54 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 55 | 56 | System.setProperty("os.name", "Windows 2012"); 57 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 58 | 59 | System.setProperty("os.name", "Windows 2012 R2"); 60 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 61 | 62 | System.setProperty("os.name", "Windows 2016"); 63 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 64 | 65 | System.setProperty("os.name", "Windows 2019"); 66 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 67 | 68 | System.setProperty("os.name", "Windows XP"); 69 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 70 | 71 | System.setProperty("os.name", "Windows 7"); 72 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 73 | 74 | System.setProperty("os.name", "Windows 8"); 75 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 76 | 77 | System.setProperty("os.name", "Windows 8.1"); 78 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.WINDOWS); 79 | 80 | System.setProperty("os.name", "Something Else"); 81 | assertEquals(NativeSystem.getFamily(), NativeSystem.Family.UNSUPPORTED); 82 | } 83 | 84 | @Test 85 | public void testGetArchitecture() { 86 | System.setProperty("os.arch", "arm"); 87 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.ARM); 88 | 89 | System.setProperty("os.arch", "arm7a"); 90 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.ARM); 91 | 92 | System.setProperty("os.arch", "aarch64"); 93 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.ARM64); 94 | 95 | System.setProperty("os.arch", "sparc"); 96 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.SPARC); 97 | 98 | System.setProperty("os.arch", "sparc64"); 99 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.SPARC64); 100 | 101 | System.setProperty("os.arch", "ppc"); 102 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.PPC); 103 | 104 | System.setProperty("os.arch", "powerpc"); 105 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.PPC); 106 | 107 | System.setProperty("os.arch", "ppc64"); 108 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.PPC64); 109 | 110 | System.setProperty("os.arch", "powerpc64"); 111 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.PPC64); 112 | 113 | System.setProperty("os.arch", "x86"); 114 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86); 115 | 116 | System.setProperty("os.arch", "i386"); 117 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86); 118 | 119 | System.setProperty("os.arch", "i486"); 120 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86); 121 | 122 | System.setProperty("os.arch", "i586"); 123 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86); 124 | 125 | System.setProperty("os.arch", "i686"); 126 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86); 127 | 128 | System.setProperty("os.arch", "x86_64"); 129 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86_64); 130 | 131 | System.setProperty("os.arch", "amd64"); 132 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86_64); 133 | 134 | System.setProperty("os.arch", "k8"); 135 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.x86_64); 136 | 137 | System.setProperty("os.arch", "Something Else"); 138 | assertEquals(NativeSystem.getArchitecture(), NativeSystem.Arch.UNSUPPORTED); 139 | } 140 | } 141 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/dispatcher/VoidDispatchServiceTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.dispatcher; 19 | 20 | import org.junit.jupiter.api.Test; 21 | import java.util.List; 22 | import java.util.concurrent.TimeUnit; 23 | import static org.junit.jupiter.api.Assertions.assertEquals; 24 | import static org.junit.jupiter.api.Assertions.assertFalse; 25 | import static org.junit.jupiter.api.Assertions.assertTrue; 26 | 27 | public class VoidDispatchServiceTest { 28 | @Test 29 | public void testConstructor() { 30 | VoidDispatchService service = new VoidDispatchService(); 31 | 32 | assertFalse(service.isShutdown()); 33 | assertFalse(service.isTerminated()); 34 | } 35 | 36 | @Test 37 | public void testShutdown() { 38 | VoidDispatchService service = new VoidDispatchService(); 39 | service.shutdown(); 40 | 41 | assertTrue(service.isShutdown()); 42 | assertTrue(service.isTerminated()); 43 | } 44 | 45 | @Test 46 | public void testShutdownNow() { 47 | VoidDispatchService service = new VoidDispatchService(); 48 | List tasks = service.shutdownNow(); 49 | 50 | assertEquals(0, tasks.size()); 51 | assertTrue(service.isShutdown()); 52 | assertTrue(service.isTerminated()); 53 | } 54 | 55 | @Test 56 | public void testAwaitTermination() { 57 | VoidDispatchService service = new VoidDispatchService(); 58 | 59 | assertTrue(service.awaitTermination(1L, TimeUnit.SECONDS)); 60 | } 61 | 62 | @Test 63 | public void testExecute() { 64 | VoidDispatchService service = new VoidDispatchService(); 65 | 66 | final boolean[] hasRun = {false}; 67 | service.execute(new Runnable() { 68 | @Override 69 | public void run() { 70 | hasRun[0] = true; 71 | } 72 | }); 73 | 74 | assertTrue(hasRun[0]); 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/keyboard/NativeKeyListenerTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.keyboard; 19 | 20 | import org.junit.jupiter.api.Test; 21 | import static org.junit.jupiter.api.Assertions.assertEquals; 22 | 23 | public class NativeKeyListenerTest { 24 | @Test 25 | public void testNativeKeyPressed() { 26 | NativeKeyEvent event = new NativeKeyEvent( 27 | NativeKeyEvent.NATIVE_KEY_PRESSED, 28 | NativeKeyEvent.SHIFT_MASK, 29 | 0x41, 30 | NativeKeyEvent.VC_A, 31 | NativeKeyEvent.CHAR_UNDEFINED, 32 | NativeKeyEvent.KEY_LOCATION_STANDARD); 33 | 34 | com.github.kwhat.jnativehook.keyboard.listeners.NativeKeyListenerTest listener = new com.github.kwhat.jnativehook.keyboard.listeners.NativeKeyListenerTest(); 35 | listener.nativeKeyPressed(event); 36 | 37 | assertEquals(event, listener.getLastEvent()); 38 | } 39 | 40 | @Test 41 | public void testNativeKeyReleased() { 42 | NativeKeyEvent event = new NativeKeyEvent( 43 | NativeKeyEvent.NATIVE_KEY_RELEASED, 44 | NativeKeyEvent.SHIFT_MASK, 45 | 0x41, 46 | NativeKeyEvent.VC_A, 47 | NativeKeyEvent.CHAR_UNDEFINED, 48 | NativeKeyEvent.KEY_LOCATION_STANDARD); 49 | 50 | com.github.kwhat.jnativehook.keyboard.listeners.NativeKeyListenerTest listener = new com.github.kwhat.jnativehook.keyboard.listeners.NativeKeyListenerTest(); 51 | listener.nativeKeyReleased(event); 52 | 53 | assertEquals(event, listener.getLastEvent()); 54 | } 55 | 56 | @Test 57 | public void testNativeKeyTyped() { 58 | NativeKeyEvent event = new NativeKeyEvent( 59 | NativeKeyEvent.NATIVE_KEY_TYPED, 60 | NativeKeyEvent.SHIFT_MASK, 61 | 0x41, 62 | NativeKeyEvent.VC_UNDEFINED, 63 | 'A', 64 | NativeKeyEvent.KEY_LOCATION_STANDARD); 65 | 66 | com.github.kwhat.jnativehook.keyboard.listeners.NativeKeyListenerTest listener = new com.github.kwhat.jnativehook.keyboard.listeners.NativeKeyListenerTest(); 67 | listener.nativeKeyTyped(event); 68 | 69 | assertEquals(event, listener.getLastEvent()); 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/keyboard/listeners/NativeKeyListenerTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.keyboard.listeners; 19 | 20 | import com.github.kwhat.jnativehook.NativeInputEvent; 21 | import com.github.kwhat.jnativehook.keyboard.NativeKeyEvent; 22 | import com.github.kwhat.jnativehook.keyboard.NativeKeyListener; 23 | import java.lang.reflect.Field; 24 | import static org.junit.jupiter.api.Assertions.fail; 25 | 26 | public class NativeKeyListenerTest implements NativeKeyListener { 27 | private NativeKeyEvent lastEvent; 28 | 29 | public void nativeKeyPressed(NativeKeyEvent e) { 30 | if (e.getID() != NativeKeyEvent.NATIVE_KEY_PRESSED) { 31 | fail("Invalid event type received for nativeKeyPressed!"); 32 | } 33 | 34 | lastEvent = e; 35 | 36 | synchronized (this) { 37 | this.notifyAll(); 38 | } 39 | 40 | try { 41 | Field f = NativeInputEvent.class.getDeclaredField("reserved"); 42 | f.setAccessible(true); 43 | f.setShort(e, (short) 0x01); 44 | } 45 | catch (Exception e1) { 46 | e1.printStackTrace(); 47 | } 48 | } 49 | 50 | public void nativeKeyReleased(NativeKeyEvent e) { 51 | if (e.getID() != NativeKeyEvent.NATIVE_KEY_RELEASED) { 52 | fail("Invalid event type received for nativeKeyPressed!"); 53 | } 54 | 55 | lastEvent = e; 56 | 57 | synchronized (this) { 58 | this.notifyAll(); 59 | } 60 | 61 | try { 62 | Field f = NativeInputEvent.class.getDeclaredField("reserved"); 63 | f.setAccessible(true); 64 | f.setShort(e, (short) 0x01); 65 | } 66 | catch (Exception e1) { 67 | e1.printStackTrace(); 68 | } 69 | } 70 | 71 | public void nativeKeyTyped(NativeKeyEvent e) { 72 | if (e.getID() != NativeKeyEvent.NATIVE_KEY_TYPED) { 73 | fail("Invalid event type received for nativeKeyPressed!"); 74 | } 75 | 76 | lastEvent = e; 77 | 78 | synchronized (this) { 79 | this.notifyAll(); 80 | } 81 | 82 | try { 83 | Field f = NativeInputEvent.class.getDeclaredField("reserved"); 84 | f.setAccessible(true); 85 | f.setShort(e, (short) 0x01); 86 | } 87 | catch (Exception e1) { 88 | e1.printStackTrace(); 89 | } 90 | } 91 | 92 | public NativeKeyEvent getLastEvent() { 93 | return lastEvent; 94 | } 95 | } 96 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/NativeMouseEventTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import org.junit.jupiter.api.Test; 21 | import java.awt.Point; 22 | import static org.junit.jupiter.api.Assertions.assertEquals; 23 | import static org.junit.jupiter.api.Assertions.assertNotEquals; 24 | 25 | public class NativeMouseEventTest { 26 | @Test 27 | public void testGetButton() { 28 | NativeMouseEvent event = new NativeMouseEvent( 29 | NativeMouseEvent.NATIVE_MOUSE_PRESSED, 30 | 0x00, 31 | 50, 32 | 75, 33 | 1, 34 | NativeMouseEvent.BUTTON1); 35 | 36 | assertEquals(NativeMouseEvent.BUTTON1, event.getButton()); 37 | } 38 | 39 | @Test 40 | public void testGetClickCount() { 41 | NativeMouseEvent event = new NativeMouseEvent( 42 | NativeMouseEvent.NATIVE_MOUSE_PRESSED, 43 | 0x00, 44 | 50, 45 | 75, 46 | 1, 47 | NativeMouseEvent.BUTTON1); 48 | 49 | assertEquals(1, event.getClickCount()); 50 | } 51 | 52 | @Test 53 | public void testGetPoint() { 54 | NativeMouseEvent event = new NativeMouseEvent( 55 | NativeMouseEvent.NATIVE_MOUSE_PRESSED, 56 | 0x00, 57 | 50, 58 | 75, 59 | 1, 60 | NativeMouseEvent.BUTTON1); 61 | 62 | assertEquals(new Point(50, 75), event.getPoint()); 63 | } 64 | 65 | @Test 66 | public void testGetX() { 67 | NativeMouseEvent event = new NativeMouseEvent( 68 | NativeMouseEvent.NATIVE_MOUSE_PRESSED, 69 | 0x00, 70 | 50, 71 | 75, 72 | 1, 73 | NativeMouseEvent.BUTTON1); 74 | 75 | assertEquals(50, event.getX()); 76 | } 77 | 78 | @Test 79 | public void testGetY() { 80 | NativeMouseEvent event = new NativeMouseEvent( 81 | NativeMouseEvent.NATIVE_MOUSE_PRESSED, 82 | 0x00, 83 | 50, 84 | 75, 85 | 1, 86 | NativeMouseEvent.BUTTON1); 87 | 88 | assertEquals(75, event.getY()); 89 | } 90 | 91 | @Test 92 | public void testParamString() { 93 | NativeMouseEvent event = new NativeMouseEvent( 94 | NativeMouseEvent.NATIVE_MOUSE_PRESSED, 95 | 0x00, 96 | 50, 97 | 75, 98 | 1, 99 | NativeMouseEvent.BUTTON1); 100 | 101 | assertNotEquals("", event.paramString()); 102 | } 103 | } 104 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/NativeMouseListenerTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import com.github.kwhat.jnativehook.mouse.listeners.NativeMouseInputListenerTest; 21 | import org.junit.jupiter.api.Test; 22 | import static org.junit.jupiter.api.Assertions.assertEquals; 23 | 24 | public class NativeMouseListenerTest { 25 | @Test 26 | public void testNativeMouseClicked() { 27 | NativeMouseEvent event = new NativeMouseEvent( 28 | NativeMouseEvent.NATIVE_MOUSE_CLICKED, 29 | 0x00, 30 | 50, 31 | 75, 32 | 1, 33 | NativeMouseEvent.BUTTON1); 34 | 35 | NativeMouseInputListenerTest listener = new NativeMouseInputListenerTest(); 36 | listener.nativeMouseClicked(event); 37 | 38 | assertEquals(event, listener.getLastEvent()); 39 | } 40 | 41 | @Test 42 | public void testNativeMousePressed() { 43 | System.out.println("nativeMousePressed"); 44 | 45 | NativeMouseEvent event = new NativeMouseEvent( 46 | NativeMouseEvent.NATIVE_MOUSE_PRESSED, 47 | 0x00, 48 | 50, 49 | 75, 50 | 1, 51 | NativeMouseEvent.BUTTON1); 52 | 53 | NativeMouseInputListenerTest listener = new NativeMouseInputListenerTest(); 54 | listener.nativeMousePressed(event); 55 | 56 | assertEquals(event, listener.getLastEvent()); 57 | } 58 | 59 | @Test 60 | public void testNativeMouseReleased() { 61 | NativeMouseEvent event = new NativeMouseEvent( 62 | NativeMouseEvent.NATIVE_MOUSE_RELEASED, 63 | 0x00, 64 | 50, 65 | 75, 66 | 1, 67 | NativeMouseEvent.BUTTON1); 68 | 69 | NativeMouseInputListenerTest listener = new NativeMouseInputListenerTest(); 70 | listener.nativeMouseReleased(event); 71 | 72 | assertEquals(event, listener.getLastEvent()); 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/NativeMouseMotionListenerTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import com.github.kwhat.jnativehook.mouse.listeners.NativeMouseInputListenerTest; 21 | import org.junit.jupiter.api.Test; 22 | import static org.junit.jupiter.api.Assertions.assertEquals; 23 | 24 | public class NativeMouseMotionListenerTest { 25 | @Test 26 | public void testNativeMouseMoved() { 27 | NativeMouseEvent event = new NativeMouseEvent( 28 | NativeMouseEvent.NATIVE_MOUSE_MOVED, 29 | 0x00, 30 | 50, 31 | 75, 32 | 0, 33 | NativeMouseEvent.NOBUTTON); 34 | 35 | NativeMouseInputListenerTest listener = new NativeMouseInputListenerTest(); 36 | listener.nativeMouseMoved(event); 37 | 38 | assertEquals(event, listener.getLastEvent()); 39 | } 40 | 41 | /** 42 | * Test of nativeMouseDragged method, of class NativeMouseMotionListener. 43 | */ 44 | @Test 45 | public void testNativeMouseDragged() { 46 | NativeMouseEvent event = new NativeMouseEvent( 47 | NativeMouseEvent.NATIVE_MOUSE_DRAGGED, 48 | NativeMouseEvent.BUTTON1_MASK, 49 | 50, 50 | 75, 51 | 0, 52 | NativeMouseEvent.NOBUTTON); 53 | 54 | NativeMouseInputListenerTest listener = new NativeMouseInputListenerTest(); 55 | listener.nativeMouseDragged(event); 56 | 57 | assertEquals(event, listener.getLastEvent()); 58 | } 59 | } 60 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/NativeMouseWheelEventTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import org.junit.jupiter.api.Test; 21 | import static org.junit.jupiter.api.Assertions.assertEquals; 22 | import static org.junit.jupiter.api.Assertions.assertNotEquals; 23 | 24 | public class NativeMouseWheelEventTest { 25 | @Test 26 | public void testGetScrollAmount() { 27 | NativeMouseWheelEvent event = new NativeMouseWheelEvent( 28 | NativeMouseEvent.NATIVE_MOUSE_WHEEL, 29 | 0x00, 30 | 50, 31 | 75, 32 | 1, 33 | NativeMouseWheelEvent.WHEEL_UNIT_SCROLL, 34 | 3, 35 | -1); 36 | 37 | assertEquals(3, event.getScrollAmount()); 38 | } 39 | 40 | @Test 41 | public void testGetScrollType() { 42 | NativeMouseWheelEvent event = new NativeMouseWheelEvent( 43 | NativeMouseEvent.NATIVE_MOUSE_WHEEL, 44 | 0x00, 45 | 50, 46 | 75, 47 | 1, 48 | NativeMouseWheelEvent.WHEEL_UNIT_SCROLL, 49 | 3, 50 | -1); 51 | 52 | assertEquals(NativeMouseWheelEvent.WHEEL_UNIT_SCROLL, event.getScrollType()); 53 | } 54 | 55 | @Test 56 | public void testGetWheelRotation() { 57 | NativeMouseWheelEvent event = new NativeMouseWheelEvent( 58 | NativeMouseEvent.NATIVE_MOUSE_WHEEL, 59 | 0x00, 60 | 50, 61 | 75, 62 | 1, 63 | NativeMouseWheelEvent.WHEEL_UNIT_SCROLL, 64 | 3, 65 | -1); 66 | 67 | assertEquals(-1, event.getWheelRotation()); 68 | } 69 | 70 | @Test 71 | public void testParamString() { 72 | NativeMouseWheelEvent event = new NativeMouseWheelEvent( 73 | NativeMouseEvent.NATIVE_MOUSE_WHEEL, 74 | 0x00, 75 | 50, 76 | 75, 77 | 1, 78 | NativeMouseWheelEvent.WHEEL_UNIT_SCROLL, 79 | 3, 80 | -1); 81 | 82 | assertNotEquals("", event.paramString()); 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/NativeMouseWheelListenerTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse; 19 | 20 | import org.junit.jupiter.api.Test; 21 | import static org.junit.jupiter.api.Assertions.assertEquals; 22 | 23 | public class NativeMouseWheelListenerTest { 24 | @Test 25 | public void testNativeMouseWheelMoved() { 26 | NativeMouseWheelEvent event = new NativeMouseWheelEvent( 27 | NativeMouseEvent.NATIVE_MOUSE_WHEEL, 28 | 0x00, 29 | 50, 30 | 75, 31 | 1, 32 | NativeMouseWheelEvent.WHEEL_UNIT_SCROLL, 33 | 3, 34 | -1); 35 | 36 | com.github.kwhat.jnativehook.mouse.listeners.NativeMouseWheelListenerTest listener = new com.github.kwhat.jnativehook.mouse.listeners.NativeMouseWheelListenerTest(); 37 | listener.nativeMouseWheelMoved(event); 38 | 39 | assertEquals(event, listener.getLastEvent()); 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/SwingMouseAdapterTest.java: -------------------------------------------------------------------------------- 1 | package com.github.kwhat.jnativehook.mouse; 2 | 3 | import org.junit.jupiter.api.Test; 4 | 5 | import java.awt.event.MouseEvent; 6 | 7 | import static org.junit.jupiter.api.Assertions.assertEquals; 8 | 9 | public class SwingMouseAdapterTest { 10 | @Test 11 | public void testGetJavaKeyEvent() { 12 | SwingMouseAdapter adapter = new SwingMouseAdapter(); 13 | NativeMouseEvent nativeEvent = new NativeMouseEvent( 14 | NativeMouseEvent.NATIVE_MOUSE_MOVED, 15 | 0x00, 16 | 666, 17 | 666, 18 | 0); 19 | MouseEvent event = adapter.getJavaKeyEvent(nativeEvent); 20 | assertEquals(event.getID(), MouseEvent.MOUSE_MOVED); 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/listeners/NativeMouseInputListenerTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse.listeners; 19 | 20 | import com.github.kwhat.jnativehook.mouse.NativeMouseEvent; 21 | import com.github.kwhat.jnativehook.mouse.NativeMouseInputListener; 22 | 23 | public class NativeMouseInputListenerTest implements NativeMouseInputListener { 24 | private NativeMouseEvent lastEvent; 25 | 26 | public void nativeMouseClicked(NativeMouseEvent e) { 27 | System.out.println("Received " + e.paramString()); 28 | 29 | if (e.getID() != NativeMouseEvent.NATIVE_MOUSE_CLICKED) { 30 | throw new IllegalArgumentException("Invalid event type received for nativeMouseClicked!"); 31 | } 32 | 33 | lastEvent = e; 34 | 35 | synchronized(this) { 36 | this.notifyAll(); 37 | } 38 | } 39 | 40 | public void nativeMousePressed(NativeMouseEvent e) { 41 | System.out.println("Received " + e.paramString()); 42 | 43 | if (e.getID() != NativeMouseEvent.NATIVE_MOUSE_PRESSED) { 44 | throw new IllegalArgumentException("Invalid event type received for nativeKeyPressed!"); 45 | } 46 | 47 | lastEvent = e; 48 | 49 | synchronized(this) { 50 | this.notifyAll(); 51 | } 52 | } 53 | 54 | public void nativeMouseReleased(NativeMouseEvent e) { 55 | System.out.println("Received " + e.paramString()); 56 | 57 | if (e.getID() != NativeMouseEvent.NATIVE_MOUSE_RELEASED) { 58 | throw new IllegalArgumentException("Invalid event type received for nativeMouseReleased!"); 59 | } 60 | 61 | lastEvent = e; 62 | 63 | synchronized(this) { 64 | this.notifyAll(); 65 | } 66 | } 67 | 68 | public void nativeMouseMoved(NativeMouseEvent e) { 69 | System.out.println("Received " + e.paramString()); 70 | 71 | if (e.getID() != NativeMouseEvent.NATIVE_MOUSE_MOVED) { 72 | throw new IllegalArgumentException("Invalid event type received for nativeMouseMoved!"); 73 | } 74 | 75 | lastEvent = e; 76 | 77 | synchronized(this) { 78 | this.notifyAll(); 79 | } 80 | } 81 | 82 | public void nativeMouseDragged(NativeMouseEvent e) { 83 | System.out.println("Received " + e.paramString()); 84 | 85 | if (e.getID() != NativeMouseEvent.NATIVE_MOUSE_DRAGGED) { 86 | throw new IllegalArgumentException("Invalid event type received" + 87 | "" + 88 | " for nativeMouseDragged!"); 89 | } 90 | 91 | lastEvent = e; 92 | 93 | synchronized(this) { 94 | this.notifyAll(); 95 | } 96 | } 97 | 98 | public NativeMouseEvent getLastEvent() { 99 | return lastEvent; 100 | } 101 | } 102 | -------------------------------------------------------------------------------- /src/test/java/com/github/kwhat/jnativehook/mouse/listeners/NativeMouseWheelListenerTest.java: -------------------------------------------------------------------------------- 1 | /* JNativeHook: Global keyboard and mouse listeners for Java. 2 | * Copyright (C) 2006-2021 Alexander Barker. All Rights Reserved. 3 | * https://github.com/kwhat/jnativehook/ 4 | * 5 | * JNativeHook is free software: you can redistribute it and/or modify 6 | * it under the terms of the GNU Lesser General Public License as published 7 | * by the Free Software Foundation, either version 3 of the License, or 8 | * (at your option) any later version. 9 | * 10 | * JNativeHook is distributed in the hope that it will be useful, 11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 | * GNU General Public License for more details. 14 | * 15 | * You should have received a copy of the GNU Lesser General Public License 16 | * along with this program. If not, see . 17 | */ 18 | package com.github.kwhat.jnativehook.mouse.listeners; 19 | 20 | import com.github.kwhat.jnativehook.mouse.NativeMouseWheelEvent; 21 | import com.github.kwhat.jnativehook.mouse.NativeMouseWheelListener; 22 | 23 | public class NativeMouseWheelListenerTest implements NativeMouseWheelListener { 24 | private NativeMouseWheelEvent lastEvent; 25 | 26 | public void nativeMouseWheelMoved(NativeMouseWheelEvent e) { 27 | if (e.getID() != NativeMouseWheelEvent.NATIVE_MOUSE_WHEEL) { 28 | throw new IllegalArgumentException("Invalid event type received for nativeMouseWheelMoved!"); 29 | } 30 | 31 | lastEvent = e; 32 | 33 | synchronized (this) { 34 | this.notifyAll(); 35 | } 36 | } 37 | 38 | public NativeMouseWheelEvent getLastEvent() { 39 | return lastEvent; 40 | } 41 | } 42 | --------------------------------------------------------------------------------