Moved JNA specific utilities to their own project
This commit is contained in:
parent
3eff10fca1
commit
07d2cc2fa4
@ -1,121 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util;
|
|
||||||
|
|
||||||
import java.lang.reflect.Method;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
import com.sun.jna.JNIEnv;
|
|
||||||
import com.sun.jna.Library;
|
|
||||||
import com.sun.jna.Native;
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
import com.sun.jna.win32.StdCallFunctionMapper;
|
|
||||||
|
|
||||||
// http://hg.openjdk.java.net/jdk/jdk10/file/b09e56145e11/src/java.base/share/native/libjava/ClassLoader.c
|
|
||||||
// http://hg.openjdk.java.net/jdk10/jdk10/jdk/file/777356696811/src/java.base/share/native/libjava/ClassLoader.c
|
|
||||||
// http://hg.openjdk.java.net/jdk9/jdk9/jdk/file/65464a307408/src/java.base/share/native/libjava/ClassLoader.c
|
|
||||||
// http://hg.openjdk.java.net/jdk8u/jdk8u/jdk/file/be698ac28848/src/share/native/java/lang/ClassLoader.c
|
|
||||||
// http://hg.openjdk.java.net/jdk7/jdk7/hotspot/file/tip/src/share/vm/prims/jvm.cpp
|
|
||||||
|
|
||||||
// objdump -T <file> | grep foo
|
|
||||||
// otool -T <file> | grep foo
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gives us the ability to inject bytes into the "normal" classloader, or directly into java's bootstrap classloader.
|
|
||||||
* <p>
|
|
||||||
* When injecting into the bootstrap classloader, this COMPLETELY bypass all security checks, as it calls native methods directly via JNA.
|
|
||||||
*/
|
|
||||||
@SuppressWarnings("WeakerAccess")
|
|
||||||
public class ClassLoaderUtil {
|
|
||||||
private static JVM libjvm;
|
|
||||||
|
|
||||||
// Note: this does not work in java8 x86 *on windows XP windows7, etc. It only works on x64
|
|
||||||
@SuppressWarnings("UnusedReturnValue")
|
|
||||||
public
|
|
||||||
interface JVM extends com.sun.jna.Library {
|
|
||||||
void JVM_DefineClass(JNIEnv env, String name, Object classLoader, byte[] buffer, int length, Object protectionDomain);
|
|
||||||
// Class JVM_FindLoadedClass(JNIEnv env, Object classLoader, JString name);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static final String libName;
|
|
||||||
static {
|
|
||||||
if (OS.isMacOsX()) {
|
|
||||||
if (OS.javaVersion < 7) {
|
|
||||||
libName = "JavaVM";
|
|
||||||
} else {
|
|
||||||
String javaLocation = System.getProperty("java.home");
|
|
||||||
|
|
||||||
// have to explicitly specify the JVM library via full path
|
|
||||||
// this is OK, because for java on MacOSX, this is the only location it can exist
|
|
||||||
libName = javaLocation + "/lib/server/libjvm.dylib";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
libName = "jvm";
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// function name is SLIGHTLY different on windows x32 java builds.
|
|
||||||
// For actual name use: http://www.nirsoft.net/utils/dll_export_viewer.html
|
|
||||||
Map options = new HashMap();
|
|
||||||
options.put(Library.OPTION_ALLOW_OBJECTS, Boolean.TRUE);
|
|
||||||
|
|
||||||
if (OS.isWindows() && OS.is32bit()) {
|
|
||||||
options.put(Library.OPTION_FUNCTION_MAPPER, new StdCallFunctionMapper() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
String getFunctionName(NativeLibrary library, Method method) {
|
|
||||||
String methodName = method.getName();
|
|
||||||
if (methodName.equals("JVM_DefineClass")) {
|
|
||||||
// specifically Oracle Java 32bit builds. Tested on XP and Win7
|
|
||||||
return "_JVM_DefineClass@24";
|
|
||||||
}
|
|
||||||
return methodName;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
libjvm = Native.load(libName, JVM.class, options);
|
|
||||||
} else {
|
|
||||||
libjvm = Native.load(libName, JVM.class, options);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Defines a class in the current threads class-loader
|
|
||||||
*
|
|
||||||
* @param classBytes the bytes of the class to define
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
void defineClass(final byte[] classBytes) throws Exception {
|
|
||||||
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
|
|
||||||
defineClass(classLoader, classBytes);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Inject class bytes directly into the bootstrap classloader.
|
|
||||||
* <p>
|
|
||||||
* This is a VERY DANGEROUS method to use!
|
|
||||||
*
|
|
||||||
* @param classLoader the classLoader to use. null will use the BOOTSTRAP classloader
|
|
||||||
* @param classBytes the bytes to inject
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
void defineClass(ClassLoader classLoader, byte[] classBytes) throws Exception {
|
|
||||||
// inject into the FIRST JVM that are started by us (is USUALLY 1, but not always)
|
|
||||||
libjvm.JVM_DefineClass(JNIEnv.CURRENT, null, classLoader, classBytes, classBytes.length, null);
|
|
||||||
}
|
|
||||||
}
|
|
@ -25,9 +25,9 @@ import java.net.URI;
|
|||||||
import java.net.URISyntaxException;
|
import java.net.URISyntaxException;
|
||||||
|
|
||||||
import dorkbox.executor.ShellExecutor;
|
import dorkbox.executor.ShellExecutor;
|
||||||
import dorkbox.util.jna.linux.GnomeVFS;
|
import dorkbox.jna.linux.GnomeVFS;
|
||||||
import dorkbox.util.jna.linux.GtkCheck;
|
import dorkbox.jna.linux.GtkCheck;
|
||||||
import dorkbox.util.jna.linux.GtkEventDispatch;
|
import dorkbox.jna.linux.GtkEventDispatch;
|
||||||
|
|
||||||
@SuppressWarnings({"WeakerAccess", "Convert2Lambda", "Duplicates"})
|
@SuppressWarnings({"WeakerAccess", "Convert2Lambda", "Duplicates"})
|
||||||
public
|
public
|
||||||
|
@ -58,8 +58,6 @@ public class FastThreadLocal<T> {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the current thread's "initial value" for this thread-local variable.
|
* Returns the current thread's "initial value" for this thread-local variable.
|
||||||
*
|
|
||||||
* @see ThreadLocal#initialValue()
|
|
||||||
*/
|
*/
|
||||||
public T initialValue() {
|
public T initialValue() {
|
||||||
return null;
|
return null;
|
||||||
|
@ -22,7 +22,6 @@ import java.security.PrivilegedAction;
|
|||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
import dorkbox.util.ClassLoaderUtil;
|
|
||||||
import dorkbox.util.OS;
|
import dorkbox.util.OS;
|
||||||
import dorkbox.util.swt.Swt;
|
import dorkbox.util.swt.Swt;
|
||||||
|
|
||||||
|
@ -1,55 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna;
|
|
||||||
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
|
||||||
import java.util.Set;
|
|
||||||
|
|
||||||
import com.sun.jna.Library;
|
|
||||||
import com.sun.jna.Native;
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
import com.sun.jna.win32.W32APIOptions;
|
|
||||||
|
|
||||||
import dorkbox.util.OS;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Helper method to get the library info from JNA when registering via direct map
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class JnaHelper {
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
public static
|
|
||||||
NativeLibrary register(final String libraryName, final Class<?> clazz) throws IllegalArgumentException {
|
|
||||||
final Map<String, Object> options = new HashMap<String, Object>();
|
|
||||||
options.put(Library.OPTION_CLASSLOADER, clazz.getClassLoader());
|
|
||||||
|
|
||||||
if (OS.isWindows()) {
|
|
||||||
Set<Map.Entry<String, Object>> entries = W32APIOptions.DEFAULT_OPTIONS.entrySet();
|
|
||||||
for (Map.Entry<String, Object> entry : entries) {
|
|
||||||
options.put(entry.getKey(), entry.getValue());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
final NativeLibrary library = NativeLibrary.getInstance(libraryName, options);
|
|
||||||
if (library == null) {
|
|
||||||
throw new IllegalArgumentException(libraryName + " doesn't exist or cannot be loaded.");
|
|
||||||
}
|
|
||||||
|
|
||||||
Native.register(clazz, library);
|
|
||||||
return library;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,191 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.OS;
|
|
||||||
import dorkbox.util.OSUtil;
|
|
||||||
import dorkbox.util.OSUtil.Linux.PackageManager;
|
|
||||||
import dorkbox.util.OSUtil.Linux.PackageManager.Type;
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
import dorkbox.util.jna.linux.structs.AppIndicatorInstanceStruct;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* bindings for libappindicator
|
|
||||||
*
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
@SuppressWarnings({"Duplicates", "SameParameterValue", "DanglingJavadoc"})
|
|
||||||
public
|
|
||||||
class AppIndicator {
|
|
||||||
public static final boolean isLoaded;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Loader for AppIndicator, because it is absolutely mindboggling how those whom maintain the standard, can't agree to what that
|
|
||||||
* standard library naming convention or features/API set is. We just try until we find one that works, and are able to map the
|
|
||||||
* symbols we need. There are bash commands that will tell us the linked library name, however - I'd rather not run bash commands
|
|
||||||
* to determine this.
|
|
||||||
*
|
|
||||||
* This is so hacky it makes me sick.
|
|
||||||
*/
|
|
||||||
static {
|
|
||||||
boolean _isLoaded = false;
|
|
||||||
|
|
||||||
boolean shouldLoadAppIndicator = !(OS.isWindows() || OS.isMacOsX());
|
|
||||||
if (!shouldLoadAppIndicator) {
|
|
||||||
_isLoaded = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// GTK must be loaded!!
|
|
||||||
if (!Gtk.isLoaded) {
|
|
||||||
shouldLoadAppIndicator = false;
|
|
||||||
_isLoaded = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libappindicator.so.1 | grep foo
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libappindicator3.so.1 | grep foo
|
|
||||||
|
|
||||||
// NOTE:
|
|
||||||
// ALSO WHAT VERSION OF GTK to use? appindiactor1 -> GTK2, appindicator3 -> GTK3.
|
|
||||||
// appindiactor1 is GKT2 only (can't use GTK3 bindings with it)
|
|
||||||
// appindicator3 doesn't support menu icons via GTK2!!
|
|
||||||
|
|
||||||
// appindicator3 doesn't support menu icons via GTK2!! *but it can work* -- we ignore this use-case, because it's so buggy
|
|
||||||
// We want to load the matching appindicator library to the loaded GTK version
|
|
||||||
|
|
||||||
String[] GTK2 = new String[] {"appindicator", "appindicator1", "appindicator-gtk"};
|
|
||||||
String[] GTK3 = new String[] {"appindicator3", "appindicator3-1", "appindicator-gtk3", "appindicator-gtk3-1"};
|
|
||||||
|
|
||||||
// NOTE: appindicator1 -> GTk2, appindicator3 -> GTK3.
|
|
||||||
// Note: appindicator-gtk3 is Fedora...
|
|
||||||
|
|
||||||
|
|
||||||
if (Gtk.isGtk2) {
|
|
||||||
for (String libraryName : GTK2) {
|
|
||||||
if (!_isLoaded) {
|
|
||||||
try {
|
|
||||||
final NativeLibrary library = JnaHelper.register(libraryName, AppIndicator.class);
|
|
||||||
if (library != null) {
|
|
||||||
_isLoaded = true;
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(AppIndicator.class).debug("Error loading GTK2 library name '{}'. {}", libraryName, e.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Gtk.isGtk3) {
|
|
||||||
for (String libraryName : GTK3) {
|
|
||||||
if (!_isLoaded) {
|
|
||||||
try {
|
|
||||||
final NativeLibrary library = JnaHelper.register(libraryName, AppIndicator.class);
|
|
||||||
if (library != null) {
|
|
||||||
_isLoaded = true;
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(AppIndicator.class).debug("Error loading GTK3 library name '{}'. {}", libraryName, e.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// We can fall back to GtkStatusIndicator or Swing if this cannot load
|
|
||||||
if (shouldLoadAppIndicator && _isLoaded) {
|
|
||||||
isLoaded = true;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
isLoaded = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Note: AppIndicators DO NOT support tooltips, as per mark shuttleworth. Rather stupid IMHO.
|
|
||||||
// See: https://bugs.launchpad.net/indicator-application/+bug/527458/comments/12
|
|
||||||
|
|
||||||
|
|
||||||
public static
|
|
||||||
String getInstallString(boolean isGtk2) {
|
|
||||||
Type packageManager = PackageManager.get();
|
|
||||||
|
|
||||||
// ARCH
|
|
||||||
// requires the install of libappindicator which is GTK2 (as of 25DEC2016)
|
|
||||||
// requires the install of libappindicator3 which is GTK3 (as of 25DEC2016)
|
|
||||||
|
|
||||||
// FEDORA
|
|
||||||
// appindicator-gtk
|
|
||||||
// appindicator-gtk3
|
|
||||||
|
|
||||||
// Debian based
|
|
||||||
// libappindicator
|
|
||||||
// libappindicator3 (or 3-1)
|
|
||||||
|
|
||||||
|
|
||||||
String packageName;
|
|
||||||
|
|
||||||
|
|
||||||
if (isGtk2) {
|
|
||||||
packageName = "libappindicator";
|
|
||||||
|
|
||||||
if (OSUtil.Linux.isFedora()) {
|
|
||||||
packageName = "libappindicator-gtk";
|
|
||||||
}
|
|
||||||
else if (OSUtil.Linux.isDebian()) {
|
|
||||||
// proper debian is slightly different
|
|
||||||
packageName = "libappindicator1";
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
packageName = "libappindicator3";
|
|
||||||
|
|
||||||
if (OSUtil.Linux.isFedora()) {
|
|
||||||
packageName = "libappindicator-gtk3";
|
|
||||||
}
|
|
||||||
else if (OSUtil.Linux.isDebian()) {
|
|
||||||
// proper debian is slightly different
|
|
||||||
packageName = "libappindicator3-1";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return "Please install " + packageName + ", for example: '" + packageManager.installString() + " " + packageName + "'.";
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public static final int CATEGORY_APPLICATION_STATUS = 0;
|
|
||||||
// public static final int CATEGORY_COMMUNICATIONS = 1;
|
|
||||||
// public static final int CATEGORY_SYSTEM_SERVICES = 2;
|
|
||||||
// public static final int CATEGORY_HARDWARE = 3;
|
|
||||||
// public static final int CATEGORY_OTHER = 4;
|
|
||||||
|
|
||||||
public static final int STATUS_PASSIVE = 0;
|
|
||||||
public static final int STATUS_ACTIVE = 1;
|
|
||||||
// public static final int STATUS_ATTENTION = 2;
|
|
||||||
|
|
||||||
|
|
||||||
public static native
|
|
||||||
AppIndicatorInstanceStruct app_indicator_new(String id, String icon_name, int category);
|
|
||||||
|
|
||||||
public static native void app_indicator_set_title(Pointer indicator, String title);
|
|
||||||
public static native void app_indicator_set_status(Pointer indicator, int status);
|
|
||||||
public static native void app_indicator_set_menu(Pointer indicator, Pointer menu);
|
|
||||||
public static native void app_indicator_set_icon(Pointer indicator, String icon_name);
|
|
||||||
}
|
|
@ -1,65 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2010 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import java.nio.ByteBuffer;
|
|
||||||
|
|
||||||
import com.sun.jna.Native;
|
|
||||||
import com.sun.jna.ptr.IntByReference;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.linux.structs.Termios;
|
|
||||||
|
|
||||||
@SuppressWarnings("ALL")
|
|
||||||
public
|
|
||||||
class CLibraryPosix {
|
|
||||||
static {
|
|
||||||
Native.register("c");
|
|
||||||
}
|
|
||||||
|
|
||||||
// MAGIC!
|
|
||||||
public static final int TIOCGWINSZ = System.getProperty("os.name").equalsIgnoreCase("linux") ? 0x5413 : 1074295912;
|
|
||||||
|
|
||||||
|
|
||||||
public static native
|
|
||||||
int isatty(int fd);
|
|
||||||
|
|
||||||
public static native
|
|
||||||
int read(int fd, IntByReference c, int count);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Original signature : <code>int ioctl(int, int, char*)</code><br>
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int ioctl(int d, int request, ByteBuffer data);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Put the state of FD into *TERMIOS_P.<br>
|
|
||||||
* <p>
|
|
||||||
* Original signature : <code>int tcgetattr(int, char*)</code><br>
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int tcgetattr(int fd, Termios termios_p);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Set the state of FD to *TERMIOS_P.<br>
|
|
||||||
* <p>
|
|
||||||
* Values for OPTIONAL_ACTIONS (TCSA*) are in <bits/termios.h>.<br>
|
|
||||||
* <p>
|
|
||||||
* Original signature : <code>int tcsetattr(int, int, char*)</code><br>
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int tcsetattr(int fd, int optional_actions, Termios termios_p);
|
|
||||||
}
|
|
@ -1,30 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
interface FuncCallback extends Callback {
|
|
||||||
/**
|
|
||||||
* @return Gtk.FALSE if it will be automatically removed from the stack once it's handled
|
|
||||||
*/
|
|
||||||
int callback(Pointer data);
|
|
||||||
}
|
|
@ -1,30 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
interface GCallback extends Callback {
|
|
||||||
/**
|
|
||||||
* @return Gtk.TRUE if we handled this event
|
|
||||||
*/
|
|
||||||
int callback(Pointer instance, Pointer data);
|
|
||||||
}
|
|
@ -1,28 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
import dorkbox.util.jna.linux.structs.GdkEventButton;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
interface GEventCallback extends Callback {
|
|
||||||
void callback(Pointer instance, GdkEventButton event);
|
|
||||||
}
|
|
@ -1,30 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
public
|
|
||||||
class GMainContext extends GObjectType {
|
|
||||||
public
|
|
||||||
GMainContext() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
GMainContext(Pointer p) {
|
|
||||||
super(p);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,30 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
public
|
|
||||||
class GMainLoop extends GObjectType {
|
|
||||||
public
|
|
||||||
GMainLoop() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
GMainLoop(Pointer p) {
|
|
||||||
super(p);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,77 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* bindings for libgobject-2.0
|
|
||||||
*
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class GObject {
|
|
||||||
|
|
||||||
static {
|
|
||||||
try {
|
|
||||||
NativeLibrary library = JnaHelper.register("gobject-2.0", GObject.class);
|
|
||||||
if (library == null) {
|
|
||||||
LoggerFactory.getLogger(GObject.class).error("Error loading GObject library, it failed to load.");
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
LoggerFactory.getLogger(GObject.class).error("Error loading GObject library, it failed to load {}", e.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgobject-2.0.so.0 | grep block
|
|
||||||
|
|
||||||
public static native void g_object_ref(Pointer object);
|
|
||||||
public static native void g_object_unref(Pointer object);
|
|
||||||
|
|
||||||
public static native void g_object_force_floating(Pointer object);
|
|
||||||
public static native void g_object_ref_sink(Pointer object);
|
|
||||||
|
|
||||||
// note: the return type here MUST be long to avoid issues on freeBSD. NativeLong (previously used) worked on everything except BSD.
|
|
||||||
public static native long g_signal_connect_object(Pointer instance, String detailed_signal, Callback c_handler, Pointer object, int connect_flags);
|
|
||||||
|
|
||||||
public static native void g_signal_handler_block(Pointer instance, long handlerId);
|
|
||||||
public static native void g_signal_handler_unblock(Pointer instance, long handlerId);
|
|
||||||
|
|
||||||
public static native void g_object_get(Pointer instance, String property_name, Pointer value, Pointer terminator);
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// Types are here https://developer.gnome.org/gobject/stable/gobject-Type-Information.html
|
|
||||||
public static native void g_value_init(Pointer gvalue, double type);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Clears the current value in value (if any) and "unsets" the type, this releases all resources associated with this GValue.
|
|
||||||
* An unset value is the same as an uninitialized (zero-filled) GValue structure.
|
|
||||||
*/
|
|
||||||
public static native void g_value_unset(Pointer gvalue);
|
|
||||||
|
|
||||||
public static native String g_value_get_string(Pointer gvalue);
|
|
||||||
public static native int g_value_get_int(Pointer gvalue);
|
|
||||||
|
|
||||||
public static native Pointer g_type_class_ref(Pointer widgetType);
|
|
||||||
public static native void g_type_class_unref(Pointer widgetClass);
|
|
||||||
}
|
|
@ -1,47 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.PointerType;
|
|
||||||
|
|
||||||
public
|
|
||||||
class GObjectType extends PointerType {
|
|
||||||
public
|
|
||||||
GObjectType() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
GObjectType(Pointer p) {
|
|
||||||
super(p);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
void finalize() throws Throwable {
|
|
||||||
super.finalize();
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void ref() {
|
|
||||||
GObject.g_object_ref(getPointer());
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void unref() {
|
|
||||||
GObject.g_object_unref(getPointer());
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,73 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* bindings for glib-2.0
|
|
||||||
*
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class Glib {
|
|
||||||
static {
|
|
||||||
try {
|
|
||||||
NativeLibrary library = JnaHelper.register("glib-2.0", Glib.class);
|
|
||||||
if (library == null) {
|
|
||||||
LoggerFactory.getLogger(Glib.class).error("Error loading Glib library, it failed to load.");
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
LoggerFactory.getLogger(Glib.class).error("Error loading Glib library, it failed to load {}", e.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public interface GLogLevelFlags {
|
|
||||||
public static final int RECURSION = 1 << 0;
|
|
||||||
public static final int FATAL = 1 << 1;
|
|
||||||
/* GLib log levels */
|
|
||||||
public static final int ERROR = 1 << 2; /* always fatal */
|
|
||||||
public static final int CRITICAL = 1 << 3;
|
|
||||||
public static final int WARNING = 1 << 4;
|
|
||||||
public static final int MESSAGE = 1 << 5;
|
|
||||||
public static final int INFO = 1 << 6;
|
|
||||||
public static final int DEBUG = 1 << 7;
|
|
||||||
public static final int MASK = ~(RECURSION | FATAL);
|
|
||||||
}
|
|
||||||
|
|
||||||
public interface GLogFunc extends Callback {
|
|
||||||
void callback (String log_domain, int log_level, String message, Pointer data);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final Glib.GLogFunc nullLogFunc = new Glib.GLogFunc() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void callback(final String log_domain, final int log_level, final String message, final Pointer data) {
|
|
||||||
// do nothing
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
public static native int g_log_set_handler(String log_domain, int levels, GLogFunc handler, Pointer user_data);
|
|
||||||
public static native void g_log_default_handler (String log_domain, int log_level, String message, Pointer unused_data);
|
|
||||||
public static native GLogFunc g_log_set_default_handler(GLogFunc log_func, Pointer user_data);
|
|
||||||
public static native void g_log_remove_handler (String log_domain, int handler_id);
|
|
||||||
}
|
|
@ -1,83 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* bindings for gnome
|
|
||||||
* <p>
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
* <p>
|
|
||||||
* https://github.com/GNOME/libgnome/blob/master/libgnome/gnome-url.c
|
|
||||||
*
|
|
||||||
* NOTE: This is used to open URL/file/email/etc from java. In different places, they recommend using gtk_show_uri() -- we support that,
|
|
||||||
* NOTE: HOWEVER there are problems where GTK warnings/errors will STILL SHOW on the console for whatever target application is opened,
|
|
||||||
* NOTE: and because of these errors, it looks like crap. gnome_vfs_url_show_with_env() solves this problem.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class GnomeVFS {
|
|
||||||
public final static boolean isInited;
|
|
||||||
|
|
||||||
static {
|
|
||||||
boolean init = false;
|
|
||||||
try {
|
|
||||||
NativeLibrary library = JnaHelper.register("libgnomevfs-2", GnomeVFS.class);
|
|
||||||
if (library == null) {
|
|
||||||
// try with no version
|
|
||||||
library = JnaHelper.register("libgnomevfs", GnomeVFS.class);
|
|
||||||
}
|
|
||||||
if (library == null) {
|
|
||||||
// try v3 (maybe this happened? Not likely, but who knows)
|
|
||||||
library = JnaHelper.register("libgnomevfs-3", GnomeVFS.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
//noinspection StatementWithEmptyBody
|
|
||||||
if (library == null) {
|
|
||||||
// not loading :/
|
|
||||||
// fail silently, because we only use this for loading URLs, and have fallbacks in place
|
|
||||||
// LoggerFactory.getLogger(GnomeVFS.class).error("Error loading GnomeVFS library, it failed to load.");
|
|
||||||
} else {
|
|
||||||
// must call call gnome_vfs_init()
|
|
||||||
GnomeVFS.gnome_vfs_init();
|
|
||||||
init = true;
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
// fail silently, because we only use this for loading URLs, and have fallbacks in place
|
|
||||||
// LoggerFactory.getLogger(GnomeVFS.class).error("Error loading GnomeVFS library, it failed to load {}", e.getMessage());
|
|
||||||
}
|
|
||||||
|
|
||||||
isInited = init;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static native
|
|
||||||
void gnome_vfs_init();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Open a URL or path to display using the default/registered handlers.
|
|
||||||
*
|
|
||||||
* @param url The url or path to display. The path can be relative to the current working
|
|
||||||
* directory or the user's home directory. This function will convert it into a fully
|
|
||||||
* qualified url using the gnome_url_get_from_input function.
|
|
||||||
*
|
|
||||||
* @return 0 if successful, non-0 if there were issues.
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int gnome_vfs_url_show_with_env(String url, Pointer shouldbeNull);
|
|
||||||
}
|
|
@ -1,407 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Function;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.linux.structs.GtkStyle;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Bindings for GTK+ 2. Bindings that are exclusively for GTK+ 3 are in that respective class
|
|
||||||
* <p>
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
@SuppressWarnings({"Duplicates", "SameParameterValue", "DeprecatedIsStillUsed", "WeakerAccess", "UnusedReturnValue"})
|
|
||||||
public
|
|
||||||
interface Gtk {
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgtk-x11-2.0.so.0 | grep gtk
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgtk-3.so.0 | grep gtk
|
|
||||||
// objdump -T /usr/local/lib/libgtk-3.so.0 | grep gtk
|
|
||||||
|
|
||||||
// For funsies to look at, SyncThing did a LOT of work on compatibility in python (unfortunate for us, but interesting).
|
|
||||||
// https://github.com/syncthing/syncthing-gtk/blob/b7a3bc00e3bb6d62365ae62b5395370f3dcc7f55/syncthing_gtk/statusicon.py
|
|
||||||
|
|
||||||
int FALSE = 0;
|
|
||||||
int TRUE = 1;
|
|
||||||
|
|
||||||
// use GtkCheck for a safe accessor of these
|
|
||||||
int MAJOR = GtkLoader.MAJOR;
|
|
||||||
int MINOR = GtkLoader.MINOR;
|
|
||||||
int MICRO = GtkLoader.MICRO;
|
|
||||||
|
|
||||||
// make specific versions of GTK2 vs GTK3 APIs
|
|
||||||
// ALSO, GTK must be loaded via .init()
|
|
||||||
Gtk Gtk2 = GtkLoader.isGtk2 ? new Gtk2() : new Gtk3();
|
|
||||||
Gtk3 Gtk3 = GtkLoader.isGtk2 ? null : (Gtk3) Gtk2;
|
|
||||||
|
|
||||||
// use GtkCheck for a safe accessor of these
|
|
||||||
boolean isGtk2 = GtkLoader.isGtk2;
|
|
||||||
boolean isGtk3 = GtkLoader.isGtk3;
|
|
||||||
boolean isLoaded = GtkLoader.isLoaded;
|
|
||||||
|
|
||||||
boolean alreadyRunningGTK = GtkLoader.alreadyRunningGTK;
|
|
||||||
|
|
||||||
Function gtk_status_icon_position_menu = GtkLoader.gtk_status_icon_position_menu;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This would NORMALLY have a 2nd argument that is a String[] -- however JNA direct-mapping DOES NOT support this. We are lucky
|
|
||||||
* enough that we just pass 'null' as the second argument, therefore, we don't have to define that parameter here.
|
|
||||||
*/
|
|
||||||
boolean gtk_init_check(int argc);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new GMainLoop structure.
|
|
||||||
*/
|
|
||||||
GMainLoop g_main_loop_new(Pointer context, boolean is_running);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Runs a main loop until g_main_loop_quit() is called on the loop. If this is called for the thread of the loop's GMainContext,
|
|
||||||
* it will process events from the loop, otherwise it will simply wait.
|
|
||||||
*/
|
|
||||||
void g_main_loop_run(GMainLoop loop);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Stops a GMainLoop from running. Any calls to g_main_loop_run() for the loop will return.
|
|
||||||
* Note that sources that have already been dispatched when g_main_loop_quit() is called will still be executed.
|
|
||||||
*/
|
|
||||||
void g_main_loop_quit(GMainLoop loop);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the GMainContext of loop .
|
|
||||||
*/
|
|
||||||
GMainContext g_main_loop_get_context(GMainLoop loop);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Invokes a function in such a way that context is owned during the invocation of function .
|
|
||||||
*/
|
|
||||||
void g_main_context_invoke(GMainContext c, FuncCallback func, Pointer data);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new GtkMenu
|
|
||||||
*/
|
|
||||||
Pointer gtk_menu_new();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets or replaces the menu item’s submenu, or removes it when a NULL submenu is passed.
|
|
||||||
*/
|
|
||||||
void gtk_menu_item_set_submenu(Pointer menuEntry, Pointer menu);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new GtkSeparatorMenuItem.
|
|
||||||
*/
|
|
||||||
Pointer gtk_separator_menu_item_new();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new GtkImage displaying the file filename . If the file isn’t found or can’t be loaded, the resulting GtkImage will
|
|
||||||
* display a “broken image” icon. This function never returns NULL, it always returns a valid GtkImage widget.
|
|
||||||
* <p>
|
|
||||||
* If the file contains an animation, the image will contain an animation.
|
|
||||||
*/
|
|
||||||
Pointer gtk_image_new_from_file(String iconPath);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the active state of the menu item’s check box.
|
|
||||||
*/
|
|
||||||
void gtk_check_menu_item_set_active(Pointer check_menu_item, boolean isChecked);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new GtkImageMenuItem containing a label. The label will be created using gtk_label_new_with_mnemonic(), so underscores
|
|
||||||
* in label indicate the mnemonic for the menu item.
|
|
||||||
* <p>
|
|
||||||
* uses '_' to define which key is the mnemonic
|
|
||||||
* <p>
|
|
||||||
* gtk_image_menu_item_new_with_mnemonic has been deprecated since version 3.10 and should not be used in newly-written code.
|
|
||||||
* NOTE: Use gtk_menu_item_new_with_mnemonic() instead.
|
|
||||||
*/
|
|
||||||
Pointer gtk_image_menu_item_new_with_mnemonic(String label);
|
|
||||||
|
|
||||||
Pointer gtk_check_menu_item_new_with_mnemonic(String label);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the image of image_menu_item to the given widget. Note that it depends on the show-menu-images setting whether the image
|
|
||||||
* will be displayed or not.
|
|
||||||
* <p>
|
|
||||||
* gtk_image_menu_item_set_image has been deprecated since version 3.10 and should not be used in newly-written code.
|
|
||||||
*/
|
|
||||||
void gtk_image_menu_item_set_image(Pointer image_menu_item, Pointer image);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* If TRUE, the menu item will ignore the “gtk-menu-images” setting and always show the image, if available.
|
|
||||||
* Use this property if the menuitem would be useless or hard to use without the image
|
|
||||||
* <p>
|
|
||||||
* gtk_image_menu_item_set_always_show_image has been deprecated since version 3.10 and should not be used in newly-written code.
|
|
||||||
*/
|
|
||||||
void gtk_image_menu_item_set_always_show_image(Pointer menu_item, boolean forceShow);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates an empty status icon object.
|
|
||||||
* <p>
|
|
||||||
* gtk_status_icon_new has been deprecated since version 3.14 and should not be used in newly-written code.
|
|
||||||
* Use notifications
|
|
||||||
*/
|
|
||||||
Pointer gtk_status_icon_new();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Obtains the root window (parent all other windows are inside) for the default display and screen.
|
|
||||||
*
|
|
||||||
* @return the default root window
|
|
||||||
*/
|
|
||||||
Pointer gdk_get_default_root_window();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the default screen for the default display. (See gdk_display_get_default()).
|
|
||||||
*
|
|
||||||
* @return a GdkScreen, or NULL if there is no default display.
|
|
||||||
*
|
|
||||||
* @since 2.2
|
|
||||||
*/
|
|
||||||
Pointer gdk_screen_get_default();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the resolution for font handling on the screen; see gdk_screen_set_resolution() for full details.
|
|
||||||
*
|
|
||||||
* IE:
|
|
||||||
*
|
|
||||||
* The resolution for font handling on the screen. This is a scale factor between points specified in a PangoFontDescription and
|
|
||||||
* cairo units. The default value is 96, meaning that a 10 point font will be 13 units high. (10 * 96. / 72. = 13.3).
|
|
||||||
*
|
|
||||||
* @return the current resolution, or -1 if no resolution has been set.
|
|
||||||
*
|
|
||||||
* @since Since: 2.10
|
|
||||||
*/
|
|
||||||
double gdk_screen_get_resolution(Pointer screen);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Makes status_icon display the file filename . See gtk_status_icon_new_from_file() for details.
|
|
||||||
* <p>
|
|
||||||
* gtk_status_icon_set_from_file has been deprecated since version 3.14 and should not be used in newly-written code.
|
|
||||||
* Use notifications
|
|
||||||
*/
|
|
||||||
void gtk_status_icon_set_from_file(Pointer widget, String label);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Shows or hides a status icon.
|
|
||||||
* <p>
|
|
||||||
* gtk_status_icon_set_visible has been deprecated since version 3.14 and should not be used in newly-written code.
|
|
||||||
* Use notifications
|
|
||||||
*/
|
|
||||||
void gtk_status_icon_set_visible(Pointer widget, boolean visible);
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets text as the contents of the tooltip.
|
|
||||||
* This function will take care of setting “has-tooltip” to TRUE and of the default handler for the “query-tooltip” signal.
|
|
||||||
*
|
|
||||||
* app indicators don't support this
|
|
||||||
*
|
|
||||||
* gtk_status_icon_set_tooltip_text has been deprecated since version 3.14 and should not be used in newly-written code.
|
|
||||||
* Use notifications
|
|
||||||
*/
|
|
||||||
void gtk_status_icon_set_tooltip_text(Pointer widget, String tooltipText);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the title of this tray icon. This should be a short, human-readable, localized string describing the tray icon. It may be used
|
|
||||||
* by tools like screen readers to render the tray icon.
|
|
||||||
* <p>
|
|
||||||
* gtk_status_icon_set_title has been deprecated since version 3.14 and should not be used in newly-written code.
|
|
||||||
* Use notifications
|
|
||||||
*/
|
|
||||||
void gtk_status_icon_set_title(Pointer widget, String titleText);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the name of this tray icon. This should be a string identifying this icon. It is may be used for sorting the icons in the
|
|
||||||
* tray and will not be shown to the user.
|
|
||||||
* <p>
|
|
||||||
* gtk_status_icon_set_name has been deprecated since version 3.14 and should not be used in newly-written code.
|
|
||||||
* Use notifications
|
|
||||||
*/
|
|
||||||
void gtk_status_icon_set_name(Pointer widget, String name);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Displays a menu and makes it available for selection.
|
|
||||||
* <p>
|
|
||||||
* gtk_menu_popup has been deprecated since version 3.22 and should not be used in newly-written code.
|
|
||||||
* NOTE: Please use gtk_menu_popup_at_widget(), gtk_menu_popup_at_pointer(). or gtk_menu_popup_at_rect() instead
|
|
||||||
*/
|
|
||||||
void gtk_menu_popup(Pointer menu, Pointer widget, Pointer bla, Function func, Pointer data, int button, int time);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets text on the menu_item label
|
|
||||||
*/
|
|
||||||
void gtk_menu_item_set_label(Pointer menu_item, String label);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds a new GtkMenuItem to the end of the menu shell's item list.
|
|
||||||
*/
|
|
||||||
void gtk_menu_shell_append(Pointer menu_shell, Pointer child);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the sensitivity of a widget. A widget is sensitive if the user can interact with it. Insensitive widgets are “grayed out”
|
|
||||||
* and the user can’t interact with them. Insensitive widgets are known as “inactive”, “disabled”, or “ghosted” in some other toolkits.
|
|
||||||
*/
|
|
||||||
void gtk_widget_set_sensitive(Pointer widget, boolean sensitive);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Recursively shows a widget, and any child widgets (if the widget is a container)
|
|
||||||
*/
|
|
||||||
void gtk_widget_show_all(Pointer widget);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Removes widget from container . widget must be inside container . Note that container will own a reference to widget , and that
|
|
||||||
* this may be the last reference held; so removing a widget from its container can destroy that widget.
|
|
||||||
* <p>
|
|
||||||
* If you want to use widget again, you need to add a reference to it before removing it from a container, using g_object_ref().
|
|
||||||
* If you don’t want to use widget again it’s usually more efficient to simply destroy it directly using gtk_widget_destroy()
|
|
||||||
* since this will remove it from the container and help break any circular reference count cycles.
|
|
||||||
*/
|
|
||||||
void gtk_container_remove(Pointer parentWidget, Pointer widget);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Destroys a widget.
|
|
||||||
* When a widget is destroyed all references it holds on other objects will be released:
|
|
||||||
* - if the widget is inside a container, it will be removed from its parent
|
|
||||||
* - if the widget is a container, all its children will be destroyed, recursively
|
|
||||||
* - if the widget is a top level, it will be removed from the list of top level widgets that GTK+ maintains internally
|
|
||||||
* <p>
|
|
||||||
* It's expected that all references held on the widget will also be released; you should connect to the “destroy” signal if you
|
|
||||||
* hold a reference to widget and you wish to remove it when this function is called. It is not necessary to do so if you are
|
|
||||||
* implementing a GtkContainer, as you'll be able to use the GtkContainerClass.remove() virtual function for that.
|
|
||||||
* <p>
|
|
||||||
* It's important to notice that gtk_widget_destroy() will only cause the widget to be finalized if no additional references,
|
|
||||||
* acquired using g_object_ref(), are held on it. In case additional references are in place, the widget will be in an "inert" state
|
|
||||||
* after calling this function; widget will still point to valid memory, allowing you to release the references you hold, but you
|
|
||||||
* may not query the widget's own state.
|
|
||||||
* <p>
|
|
||||||
* NOTE You should typically call this function on top level widgets, and rarely on child widgets.
|
|
||||||
*/
|
|
||||||
void gtk_widget_destroy(Pointer widget);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the GtkSettings object for screen , creating it if necessary.
|
|
||||||
*
|
|
||||||
* @since 2.2
|
|
||||||
*/
|
|
||||||
Pointer gtk_settings_get_for_screen(Pointer screen);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Finds all matching RC styles for a given widget, composites them together, and then creates a GtkStyle representing the composite
|
|
||||||
* appearance. (GTK+ actually keeps a cache of previously created styles, so a new style may not be created.)
|
|
||||||
*/
|
|
||||||
GtkStyle gtk_rc_get_style(Pointer widget);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds widget to container . Typically used for simple containers such as GtkWindow, GtkFrame, or GtkButton; for more complicated
|
|
||||||
* layout containers such as GtkBox or GtkTable, this function will pick default packing parameters that may not be correct. So
|
|
||||||
* consider functions such as gtk_box_pack_start() and gtk_table_attach() as an alternative to gtk_container_add() in those cases.
|
|
||||||
* A widget may be added to only one container at a time; you can't place the same widget inside two different containers.
|
|
||||||
*/
|
|
||||||
void gtk_container_add(Pointer offscreen, Pointer widget);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Get's the child from a GTK Bin object
|
|
||||||
*/
|
|
||||||
Pointer gtk_bin_get_child(Pointer bin);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the PangoLayout used to display the label. The layout is useful to e.g. convert text positions to pixel positions, in
|
|
||||||
* combination with gtk_label_get_layout_offsets(). The returned layout is owned by the label so need not be freed by the caller.
|
|
||||||
*
|
|
||||||
* The label is free to recreate its layout at any time, so it should be considered read-only.
|
|
||||||
*/
|
|
||||||
Pointer gtk_label_get_layout(Pointer label);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Computes the logical and ink extents of layout in device units. This function just calls pango_layout_get_extents() followed
|
|
||||||
* by two pango_extents_to_pixels() calls, rounding ink_rect and logical_rect such that the rounded rectangles fully contain the
|
|
||||||
* unrounded one (that is, passes them as first argument to pango_extents_to_pixels()).
|
|
||||||
*
|
|
||||||
* @param layout a PangoLayout
|
|
||||||
* @param ink_rect rectangle used to store the extents of the layout as drawn or NULL to indicate that the result is not needed.
|
|
||||||
* @param logical_rect rectangle used to store the logical extents of the layout or NULL to indicate that the result is not needed.
|
|
||||||
*/
|
|
||||||
void pango_layout_get_pixel_extents(Pointer layout, Pointer ink_rect, Pointer logical_rect);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates the GDK (windowing system) resources associated with a widget. For example, widget->window will be created when a widget
|
|
||||||
* is realized. Normally realization happens implicitly; if you show a widget and all its parent containers, then the widget will
|
|
||||||
* be realized and mapped automatically.
|
|
||||||
*
|
|
||||||
* Realizing a widget requires all the widget’s parent widgets to be realized; calling gtk_widget_realize() realizes the widget’s
|
|
||||||
* parents in addition to widget itself. If a widget is not yet inside a toplevel window when you realize it, bad things will happen.
|
|
||||||
*
|
|
||||||
* This function is primarily used in widget implementations, and isn’t very useful otherwise. Many times when you think you might
|
|
||||||
* need it, a better approach is to connect to a signal that will be called after the widget is realized automatically, such as
|
|
||||||
* “draw”. Or simply g_signal_connect() to the “realize” signal.
|
|
||||||
*/
|
|
||||||
void gtk_widget_realize(Pointer widget);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a toplevel container widget that is used to retrieve snapshots of widgets without showing them on the screen.
|
|
||||||
*
|
|
||||||
* @since 2.20
|
|
||||||
*/
|
|
||||||
Pointer gtk_offscreen_window_new();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This function is typically used when implementing a GtkContainer subclass. Obtains the preferred size of a widget. The
|
|
||||||
* container uses this information to arrange its child widgets and decide what size allocations to give them with
|
|
||||||
* gtk_widget_size_allocate().
|
|
||||||
*
|
|
||||||
* You can also call this function from an application, with some caveats. Most notably, getting a size request requires the
|
|
||||||
* widget to be associated with a screen, because font information may be needed. Multihead-aware applications should keep this in mind.
|
|
||||||
*
|
|
||||||
* Also remember that the size request is not necessarily the size a widget will actually be allocated.
|
|
||||||
*/
|
|
||||||
void gtk_widget_size_request(final Pointer widget, final Pointer requisition);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new GtkImageMenuItem containing the image and text from a stock item. Some stock ids have preprocessor macros
|
|
||||||
* like GTK_STOCK_OK and GTK_STOCK_APPLY.
|
|
||||||
*
|
|
||||||
* @param stock_id the name of the stock item.
|
|
||||||
* @param accel_group the GtkAccelGroup to add the menu items accelerator to, or NULL.
|
|
||||||
*
|
|
||||||
* @return a new GtkImageMenuItem.
|
|
||||||
*/
|
|
||||||
Pointer gtk_image_menu_item_new_from_stock(String stock_id, Pointer accel_group);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A convenience function for launching the default application to show the uri. Like gtk_show_uri_on_window(), but takes a screen
|
|
||||||
* as transient parent instead of a window.
|
|
||||||
*
|
|
||||||
* @param timestamp GDK_CURRENT_TIME = 0 (this is what you should use)
|
|
||||||
* @since 2.14
|
|
||||||
*/
|
|
||||||
@Deprecated
|
|
||||||
boolean gtk_show_uri(Pointer screen, String uri, int timestamp, Pointer error);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets text as the contents of the tooltip. This function will take care of setting “has-tooltip” to TRUE and of the default
|
|
||||||
* handler for the “query-tooltip” signal. Null text will remove the tooltip
|
|
||||||
*
|
|
||||||
* @since 2.12
|
|
||||||
*/
|
|
||||||
void gtk_widget_set_tooltip_text(Pointer widget, String text);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the default GdkDisplay. This is a convenience function for gdk_display_manager_get_default_display (gdk_display_manager_get()).
|
|
||||||
*
|
|
||||||
* @since: 2.2
|
|
||||||
*/
|
|
||||||
Pointer gdk_display_get_default();
|
|
||||||
}
|
|
||||||
|
|
@ -1,213 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Function;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.linux.structs.GtkStyle;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Bindings for GTK+ 2. Bindings that are exclusively for GTK+ 3 are in that respective class
|
|
||||||
* <p>
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class Gtk2 implements Gtk {
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgtk-x11-2.0.so.0 | grep gtk
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean gtk_init_check(final int argc);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
GMainLoop g_main_loop_new(Pointer context, boolean is_running);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
GMainContext g_main_loop_get_context(GMainLoop loop);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void g_main_loop_run(GMainLoop loop);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void g_main_context_invoke(GMainContext c, FuncCallback func, Pointer data);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void g_main_loop_quit(GMainLoop loop);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_menu_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_item_set_submenu(final Pointer menuEntry, final Pointer menu);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_separator_menu_item_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_image_new_from_file(final String iconPath);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_check_menu_item_set_active(final Pointer check_menu_item, final boolean isChecked);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_image_menu_item_new_with_mnemonic(final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_check_menu_item_new_with_mnemonic(final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_image_menu_item_set_image(final Pointer image_menu_item, final Pointer image);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_image_menu_item_set_always_show_image(final Pointer menu_item, final boolean forceShow);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_status_icon_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gdk_get_default_root_window();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gdk_screen_get_default();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
double gdk_screen_get_resolution(final Pointer screen);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_from_file(final Pointer widget, final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_visible(final Pointer widget, final boolean visible);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_tooltip_text(final Pointer widget, final String tooltipText);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_title(final Pointer widget, final String titleText);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_name(final Pointer widget, final String name);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_popup(final Pointer menu,
|
|
||||||
final Pointer widget,
|
|
||||||
final Pointer bla,
|
|
||||||
final Function func,
|
|
||||||
final Pointer data,
|
|
||||||
final int button,
|
|
||||||
final int time);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_item_set_label(final Pointer menu_item, final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_shell_append(final Pointer menu_shell, final Pointer child);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_set_sensitive(final Pointer widget, final boolean sensitive);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_show_all(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_container_remove(final Pointer parentWidget, final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_destroy(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_settings_get_for_screen(final Pointer screen);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
GtkStyle gtk_rc_get_style(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_container_add(final Pointer offscreen, final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_bin_get_child(final Pointer bin);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_label_get_layout(final Pointer label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void pango_layout_get_pixel_extents(final Pointer layout, final Pointer ink_rect, final Pointer logical_rect);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_realize(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_offscreen_window_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_size_request(final Pointer widget, final Pointer requisition);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_image_menu_item_new_from_stock(final String stock_id, final Pointer accel_group);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean gtk_show_uri(final Pointer screen, final String uri, final int timestamp, final Pointer error);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_set_tooltip_text(final Pointer widget, final String text);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gdk_display_get_default();
|
|
||||||
}
|
|
@ -1,308 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import com.sun.jna.Function;
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.linux.structs.GtkStyle;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* bindings for GTK+ 3.
|
|
||||||
* <p>
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
@SuppressWarnings("WeakerAccess")
|
|
||||||
public
|
|
||||||
class Gtk3 implements Gtk {
|
|
||||||
private static Function gdk_window_get_scale_factor = null;
|
|
||||||
private static Function gtk_show_uri_on_window = null;
|
|
||||||
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgtk-3.so.0 | grep gtk
|
|
||||||
// objdump -T /usr/local/lib/libgtk-3.so.0 | grep gtk
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Loads version specific methods
|
|
||||||
*/
|
|
||||||
static
|
|
||||||
void loadMethods(final NativeLibrary library) {
|
|
||||||
// Abusing static fields this way is not proper, but it gets the job done nicely.
|
|
||||||
|
|
||||||
if (GtkCheck.gtkIsGreaterOrEqual(3, 10, 0)) {
|
|
||||||
gdk_window_get_scale_factor = library.getFunction("gdk_window_get_scale_factor");
|
|
||||||
}
|
|
||||||
|
|
||||||
if (GtkCheck.gtkIsGreaterOrEqual(3, 22, 0)) {
|
|
||||||
gtk_show_uri_on_window = library.getFunction("gtk_show_uri_on_window");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Retrieves the minimum and natural size of a widget, taking into account the widget’s preference for height-for-width management.
|
|
||||||
* <p>
|
|
||||||
* This is used to retrieve a suitable size by container widgets which do not impose any restrictions on the child placement.
|
|
||||||
* It can be used to deduce toplevel window and menu sizes as well as child widgets in free-form containers such as GtkLayout.
|
|
||||||
* <p>
|
|
||||||
* Handle with care. Note that the natural height of a height-for-width widget will generally be a smaller size than the minimum
|
|
||||||
* height, since the required height for the natural width is generally smaller than the required height for the minimum width.
|
|
||||||
* <p>
|
|
||||||
* Use gtk_widget_get_preferred_height_and_baseline_for_width() if you want to support baseline alignment.
|
|
||||||
*
|
|
||||||
* @param widget a GtkWidget instance
|
|
||||||
* @param minimum_size location for storing the minimum size, or NULL.
|
|
||||||
* @param natural_size location for storing the natural size, or NULL.
|
|
||||||
*/
|
|
||||||
public native
|
|
||||||
void gtk_widget_get_preferred_size(final Pointer widget, final Pointer minimum_size, final Pointer natural_size);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the internal scale factor that maps from window coordinates to the actual device pixels. On traditional systems this is 1,
|
|
||||||
* but on very high density outputs this can be a higher value (often 2).
|
|
||||||
* <p>
|
|
||||||
* A higher value means that drawing is automatically scaled up to a higher resolution, so any code doing drawing will automatically
|
|
||||||
* look nicer. However, if you are supplying pixel-based data the scale value can be used to determine whether to use a pixel
|
|
||||||
* resource with higher resolution data.
|
|
||||||
* <p>
|
|
||||||
* The scale of a window may change during runtime, if this happens a configure event will be sent to the toplevel window.
|
|
||||||
*
|
|
||||||
* @return the scale factor
|
|
||||||
*
|
|
||||||
* @since 3.10
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
int gdk_window_get_scale_factor(Pointer window) {
|
|
||||||
if (gdk_window_get_scale_factor != null) {
|
|
||||||
return gdk_window_get_scale_factor.invokeInt(new Object[]{window});
|
|
||||||
} else {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return TRUE on success, FALSE on error
|
|
||||||
*
|
|
||||||
* @since: 3.22
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
boolean gtk_show_uri_on_window(final Pointer parent, final String uri, final int timestamp, final Pointer error) {
|
|
||||||
if (gtk_show_uri_on_window != null) {
|
|
||||||
return (Boolean) gtk_show_uri_on_window.invoke(Boolean.class, new Object[] {parent, uri, timestamp, error});
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
///////////////////////////
|
|
||||||
//// GTK2 methods
|
|
||||||
///////////////////////////
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This function is typically used when implementing a GtkContainer subclass. Obtains the preferred size of a widget. The
|
|
||||||
* container uses this information to arrange its child widgets and decide what size allocations to give them with
|
|
||||||
* gtk_widget_size_allocate().
|
|
||||||
*
|
|
||||||
* You can also call this function from an application, with some caveats. Most notably, getting a size request requires the
|
|
||||||
* widget to be associated with a screen, because font information may be needed. Multihead-aware applications should keep this in mind.
|
|
||||||
*
|
|
||||||
* Also remember that the size request is not necessarily the size a widget will actually be allocated.
|
|
||||||
*/
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void gtk_widget_size_request(final Pointer widget, final Pointer requisition) {
|
|
||||||
this.gtk_widget_get_preferred_size(widget, requisition, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean gtk_init_check(final int argc);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
GMainLoop g_main_loop_new(Pointer context, boolean is_running);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
GMainContext g_main_loop_get_context(GMainLoop loop);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void g_main_loop_run(GMainLoop loop);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void g_main_context_invoke(GMainContext c, FuncCallback func, Pointer data);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void g_main_loop_quit(GMainLoop loop);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_menu_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_item_set_submenu(final Pointer menuEntry, final Pointer menu);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_separator_menu_item_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_image_new_from_file(final String iconPath);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_check_menu_item_set_active(final Pointer check_menu_item, final boolean isChecked);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_image_menu_item_new_with_mnemonic(final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_check_menu_item_new_with_mnemonic(final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_image_menu_item_set_image(final Pointer image_menu_item, final Pointer image);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_image_menu_item_set_always_show_image(final Pointer menu_item, final boolean forceShow);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_status_icon_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gdk_get_default_root_window();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gdk_screen_get_default();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
double gdk_screen_get_resolution(final Pointer screen);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_from_file(final Pointer widget, final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_visible(final Pointer widget, final boolean visible);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_tooltip_text(final Pointer widget, final String tooltipText);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_title(final Pointer widget, final String titleText);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_status_icon_set_name(final Pointer widget, final String name);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_popup(final Pointer menu,
|
|
||||||
final Pointer widget,
|
|
||||||
final Pointer bla,
|
|
||||||
final Function func,
|
|
||||||
final Pointer data,
|
|
||||||
final int button,
|
|
||||||
final int time);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_item_set_label(final Pointer menu_item, final String label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_menu_shell_append(final Pointer menu_shell, final Pointer child);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_set_sensitive(final Pointer widget, final boolean sensitive);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_show_all(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_container_remove(final Pointer parentWidget, final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_destroy(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_settings_get_for_screen(final Pointer screen);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
GtkStyle gtk_rc_get_style(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_container_add(final Pointer offscreen, final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_bin_get_child(final Pointer bin);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_label_get_layout(final Pointer label);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void pango_layout_get_pixel_extents(final Pointer layout, final Pointer ink_rect, final Pointer logical_rect);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_realize(final Pointer widget);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_offscreen_window_new();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gtk_image_menu_item_new_from_stock(final String stock_id, final Pointer accel_group);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean gtk_show_uri(final Pointer screen, final String uri, final int timestamp, final Pointer error);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void gtk_widget_set_tooltip_text(final Pointer widget, final String text);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
Pointer gdk_display_get_default();
|
|
||||||
}
|
|
@ -1,36 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* bindings for GTK+ 3 version info.
|
|
||||||
* <p>
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class Gtk3VersionInfo {
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgtk-3.so.0 | grep gtk
|
|
||||||
// objdump -T /usr/local/lib/libgtk-3.so.0 | grep gtk
|
|
||||||
|
|
||||||
public native
|
|
||||||
int gtk_get_major_version();
|
|
||||||
|
|
||||||
public native
|
|
||||||
int gtk_get_minor_version();
|
|
||||||
|
|
||||||
public native
|
|
||||||
int gtk_get_micro_version();
|
|
||||||
}
|
|
@ -1,126 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import dorkbox.util.javaFx.JavaFX;
|
|
||||||
import dorkbox.util.SwingUtil;
|
|
||||||
import dorkbox.util.swt.Swt;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Accessor methods/logic for determining if GTK is already loaded by the Swing/JavaFX/SWT, or if GTK has been manually loaded via
|
|
||||||
* GtkEventDispatch.startGui().
|
|
||||||
*/
|
|
||||||
@SuppressWarnings("WeakerAccess")
|
|
||||||
public
|
|
||||||
class GtkCheck {
|
|
||||||
/**
|
|
||||||
* Only valid if `isGtkLoaded=true`. Determine if the application is running via GTK2.
|
|
||||||
* <p>
|
|
||||||
* This does not cause GTK to load, where calls to Gtk.isGtk2 will
|
|
||||||
*/
|
|
||||||
public static volatile boolean isGtk2 = false;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Only valid if `isGtkLoaded=true`. Determine if the application is running via GTK3.
|
|
||||||
* <p>
|
|
||||||
* This does not cause GTK to load, where calls to Gtk.isGtk2 will
|
|
||||||
*/
|
|
||||||
public static volatile boolean isGtk3 = false;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Determine if the application has *MANUALLY* loaded GTK yet or not. This does not cause GTK to load, where calls to Gtk.isLoaded will
|
|
||||||
*/
|
|
||||||
public static volatile boolean isGtkLoaded = false;
|
|
||||||
|
|
||||||
|
|
||||||
/** If GTK is loaded, this is the GTK MAJOR version */
|
|
||||||
public static volatile int MAJOR = 0;
|
|
||||||
|
|
||||||
/** If GTK is loaded, this is the GTK MINOR version */
|
|
||||||
public static volatile int MINOR = 0;
|
|
||||||
|
|
||||||
/** If GTK is loaded, this is the GTK MICRO version */
|
|
||||||
public static volatile int MICRO = 0;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return true if the currently loaded GTK version is greater to or equal to the passed-in major.minor.mico
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
boolean gtkIsGreaterOrEqual(final int major, final int minor, final int micro) {
|
|
||||||
if (MAJOR > major) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (MAJOR < major) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (MINOR > minor) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (MINOR < minor) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (MICRO > micro) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (MICRO < micro) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// same exact version
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This method is agnostic w.r.t. how GTK is loaded, which can be manually loaded or loaded via JavaFX/SWT/Swing.
|
|
||||||
*
|
|
||||||
* @return the version of GTK loaded. 0=no GTK loaded, 2=GTK2, 3=GTK3
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
int getLoadedGtkVersion() {
|
|
||||||
// if we have ALREADY loaded GTK, then return that information.
|
|
||||||
if (isGtkLoaded) {
|
|
||||||
if (isGtk3) {
|
|
||||||
return 3;
|
|
||||||
} else {
|
|
||||||
return 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Swt.isLoaded) {
|
|
||||||
if (Swt.isGtk3) {
|
|
||||||
return 3;
|
|
||||||
} else {
|
|
||||||
return 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (JavaFX.isLoaded) {
|
|
||||||
if (JavaFX.isGtk3) {
|
|
||||||
return 3;
|
|
||||||
} else {
|
|
||||||
return 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// now check if swing has loaded GTK from the Look and Feel
|
|
||||||
return SwingUtil.getLoadedGtkVersion();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
@ -1,362 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import static dorkbox.util.jna.linux.Gtk.Gtk2;
|
|
||||||
|
|
||||||
import java.awt.event.ActionListener;
|
|
||||||
import java.util.LinkedList;
|
|
||||||
import java.util.concurrent.CountDownLatch;
|
|
||||||
import java.util.concurrent.TimeUnit;
|
|
||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.javaFx.JavaFX;
|
|
||||||
import dorkbox.util.swt.Swt;
|
|
||||||
|
|
||||||
public
|
|
||||||
class GtkEventDispatch {
|
|
||||||
static boolean FORCE_GTK2 = false;
|
|
||||||
static boolean PREFER_GTK3 = false;
|
|
||||||
static boolean DEBUG = false;
|
|
||||||
|
|
||||||
// have to save these in a field to prevent GC on the objects (since they go out-of-scope from java)
|
|
||||||
private static final LinkedList<FuncCallback> gtkCallbacks = new LinkedList<FuncCallback>();
|
|
||||||
|
|
||||||
// This is required because the EDT needs to have it's own value for this boolean, that is a different value than the main thread
|
|
||||||
private static ThreadLocal<Boolean> isDispatch = new ThreadLocal<Boolean>() {
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
Boolean initialValue() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
private static boolean started = false;
|
|
||||||
|
|
||||||
@SuppressWarnings("FieldCanBeLocal")
|
|
||||||
private static Thread gtkUpdateThread = null;
|
|
||||||
|
|
||||||
private static GMainLoop mainloop;
|
|
||||||
private static GMainContext context;
|
|
||||||
|
|
||||||
// when debugging the EDT, we need a longer timeout.
|
|
||||||
private static final boolean debugEDT = false;
|
|
||||||
|
|
||||||
// timeout is in seconds
|
|
||||||
private static final int TIMEOUT = debugEDT ? 10000000 : 2;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This will load and start GTK
|
|
||||||
*/
|
|
||||||
public static synchronized
|
|
||||||
void startGui(final boolean forceGtk2, final boolean preferGkt3, final boolean debug) {
|
|
||||||
// only permit one startup per JVM instance
|
|
||||||
if (!started) {
|
|
||||||
started = true;
|
|
||||||
|
|
||||||
GtkEventDispatch.FORCE_GTK2 = forceGtk2;
|
|
||||||
GtkEventDispatch.PREFER_GTK3 = preferGkt3;
|
|
||||||
GtkEventDispatch.DEBUG = debug;
|
|
||||||
|
|
||||||
// startup the GTK GUI event loop. There can be multiple/nested loops.
|
|
||||||
if (!GtkLoader.alreadyRunningGTK) {
|
|
||||||
// If JavaFX/SWT is used, this is UNNECESSARY (we can detect if the GTK main_loop is running)
|
|
||||||
|
|
||||||
gtkUpdateThread = new Thread() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
Glib.GLogFunc orig = null;
|
|
||||||
if (debug) {
|
|
||||||
// don't suppress GTK warnings in debug mode
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class).debug("Running GTK Native Event Loop");
|
|
||||||
} else {
|
|
||||||
// NOTE: This can output warnings, so we suppress them. Additionally, setting System.err to null, or trying
|
|
||||||
// to filter it, will not suppress these errors/warnings
|
|
||||||
orig = Glib.g_log_set_default_handler(Glib.nullLogFunc, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
if (!Gtk2.gtk_init_check(0)) {
|
|
||||||
throw new RuntimeException("Error starting GTK");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// create the main-loop
|
|
||||||
mainloop = Gtk2.g_main_loop_new(null, false);
|
|
||||||
context = Gtk2.g_main_loop_get_context(mainloop);
|
|
||||||
|
|
||||||
// blocks until we quit the main loop
|
|
||||||
Gtk2.g_main_loop_run(mainloop);
|
|
||||||
|
|
||||||
|
|
||||||
if (orig != null) {
|
|
||||||
Glib.g_log_set_default_handler(orig, null);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
gtkUpdateThread.setDaemon(false); // explicitly NOT daemon so that this will hold the JVM open as necessary
|
|
||||||
gtkUpdateThread.setName("GTK Native Event Loop");
|
|
||||||
gtkUpdateThread.start();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Waits for the all posted events to GTK to finish loading
|
|
||||||
*/
|
|
||||||
@SuppressWarnings("Duplicates")
|
|
||||||
public static synchronized
|
|
||||||
void waitForEventsToComplete() {
|
|
||||||
final CountDownLatch blockUntilStarted = new CountDownLatch(1);
|
|
||||||
|
|
||||||
dispatch(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
blockUntilStarted.countDown();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
if (JavaFX.isLoaded) {
|
|
||||||
if (!JavaFX.isEventThread()) {
|
|
||||||
try {
|
|
||||||
if (!blockUntilStarted.await(10, TimeUnit.SECONDS)) {
|
|
||||||
if (DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class)
|
|
||||||
.error("Something is very wrong. The waitForEventsToComplete took longer than expected.",
|
|
||||||
new Exception(""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// we have to WAIT until all events are done processing, OTHERWISE we have initialization issues
|
|
||||||
while (true) {
|
|
||||||
Thread.sleep(100);
|
|
||||||
|
|
||||||
synchronized (gtkCallbacks) {
|
|
||||||
if (gtkCallbacks.isEmpty()) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (InterruptedException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (Swt.isLoaded) {
|
|
||||||
if (!Swt.isEventThread()) {
|
|
||||||
// we have to WAIT until all events are done processing, OTHERWISE we have initialization issues
|
|
||||||
try {
|
|
||||||
if (!blockUntilStarted.await(10, TimeUnit.SECONDS)) {
|
|
||||||
if (DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class)
|
|
||||||
.error("Something is very wrong. The waitForEventsToComplete took longer than expected.",
|
|
||||||
new Exception(""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
while (true) {
|
|
||||||
Thread.sleep(100);
|
|
||||||
|
|
||||||
synchronized (gtkCallbacks) {
|
|
||||||
if (gtkCallbacks.isEmpty()) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (InterruptedException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
try {
|
|
||||||
if (!blockUntilStarted.await(10, TimeUnit.SECONDS)) {
|
|
||||||
if (DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class)
|
|
||||||
.error("Something is very wrong. The waitForEventsToComplete took longer than expected.",
|
|
||||||
new Exception(""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// we have to WAIT until all events are done processing, OTHERWISE we have initialization issues
|
|
||||||
while (true) {
|
|
||||||
Thread.sleep(100);
|
|
||||||
|
|
||||||
synchronized (gtkCallbacks) {
|
|
||||||
if (gtkCallbacks.isEmpty()) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (InterruptedException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Dispatch the runnable to GTK and wait until it has finished executing. If this is called while on the GTK dispatch thread, it will
|
|
||||||
* immediately execute the task, otherwise it will submit the task to run on the FIFO queue.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
void dispatchAndWait(final Runnable runnable) {
|
|
||||||
// if we are on the dispatch queue, do not block
|
|
||||||
Boolean isDispatch = GtkEventDispatch.isDispatch.get();
|
|
||||||
if (isDispatch) {
|
|
||||||
// don't block. The ORIGINAL call (before items were queued) will still be blocking. If the original call was a "normal"
|
|
||||||
// dispatch, then subsequent dispatchAndWait calls are irrelevant (as they happen in the GTK thread, and not the main thread).
|
|
||||||
runnable.run();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
final CountDownLatch countDownLatch = new CountDownLatch(1);
|
|
||||||
dispatch(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
try {
|
|
||||||
runnable.run();
|
|
||||||
} catch (Exception e) {
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class).error("Error during GTK run loop: ", e);
|
|
||||||
} finally {
|
|
||||||
countDownLatch.countDown();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// this is slightly different than how swing does it. We have a timeout here so that we can make sure that updates on the GUI
|
|
||||||
// thread occur in REASONABLE time-frames, and alert the user if not.
|
|
||||||
try {
|
|
||||||
if (!countDownLatch.await(TIMEOUT, TimeUnit.SECONDS)) {
|
|
||||||
if (DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class).error(
|
|
||||||
"Something is very wrong. The Event Dispatch Queue took longer than " + TIMEOUT + " seconds " +
|
|
||||||
"to complete.", new Exception(""));
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
throw new RuntimeException("Something is very wrong. The Event Dispatch Queue took longer than " + TIMEOUT +
|
|
||||||
" seconds " + "to complete.");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (InterruptedException e) {
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class).error("Error waiting for dispatch to complete.", new Exception(""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Best practices for GTK, is to call everything for it on the GTK THREAD. If we are currently on the dispatch thread, then this
|
|
||||||
* task will execute immediately.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
void dispatch(final Runnable runnable) {
|
|
||||||
if (GtkLoader.alreadyRunningGTK) {
|
|
||||||
if (JavaFX.isLoaded) {
|
|
||||||
// JavaFX only
|
|
||||||
if (JavaFX.isEventThread()) {
|
|
||||||
// Run directly on the JavaFX event thread
|
|
||||||
runnable.run();
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
JavaFX.dispatch(runnable);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Swt.isLoaded && Swt.isEventThread()) {
|
|
||||||
// Run directly on the SWT event thread. If it's not on the dispatch thread, we will use GTK to put it there
|
|
||||||
runnable.run();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// not javafx
|
|
||||||
// gtk/swt are **mostly** the same in how events are dispatched, so we can use "raw" gtk methods for SWT
|
|
||||||
if (isDispatch.get()) {
|
|
||||||
// Run directly on the dispatch thread. This will be false unless we are running the dispatch queue.
|
|
||||||
runnable.run();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
final FuncCallback callback = new FuncCallback() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
int callback(final Pointer data) {
|
|
||||||
isDispatch.set(true);
|
|
||||||
|
|
||||||
try {
|
|
||||||
runnable.run();
|
|
||||||
} finally {
|
|
||||||
isDispatch.set(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
synchronized (gtkCallbacks) {
|
|
||||||
gtkCallbacks.removeFirst(); // now that we've 'handled' it, we can remove it from our callback list
|
|
||||||
}
|
|
||||||
|
|
||||||
return Gtk2.FALSE; // don't want to call this again
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
synchronized (gtkCallbacks) {
|
|
||||||
gtkCallbacks.offer(callback); // prevent GC from collecting this object before it can be called
|
|
||||||
}
|
|
||||||
|
|
||||||
// explicitly invoke on our new GTK main loop context
|
|
||||||
Gtk2.g_main_context_invoke(context, callback, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* required to properly setup the dispatch flag when using native menus
|
|
||||||
*
|
|
||||||
* @param callback will never be null.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
void proxyClick(final ActionListener callback) {
|
|
||||||
isDispatch.set(true);
|
|
||||||
|
|
||||||
try {
|
|
||||||
callback.actionPerformed(null);
|
|
||||||
} catch (Throwable t) {
|
|
||||||
LoggerFactory.getLogger(GtkEventDispatch.class)
|
|
||||||
.error("Error during GTK click callback: ", t);
|
|
||||||
}
|
|
||||||
|
|
||||||
isDispatch.set(false);
|
|
||||||
}
|
|
||||||
public static synchronized
|
|
||||||
void shutdownGui() {
|
|
||||||
dispatchAndWait(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
// If JavaFX/SWT is used, this is UNNECESSARY (and will break SWT/JavaFX shutdown)
|
|
||||||
if (!GtkLoader.alreadyRunningGTK) {
|
|
||||||
Gtk2.g_main_loop_quit(mainloop);
|
|
||||||
// Gtk2.gtk_main_quit();
|
|
||||||
}
|
|
||||||
|
|
||||||
started = false;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,253 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.Function;
|
|
||||||
import com.sun.jna.NativeLibrary;
|
|
||||||
|
|
||||||
import dorkbox.util.OS;
|
|
||||||
import dorkbox.util.swt.Swt;
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Bindings for GTK+ 2. Bindings that are exclusively for GTK+ 3 are in that respective class
|
|
||||||
* <p>
|
|
||||||
* Direct-mapping, See: https://github.com/java-native-access/jna/blob/master/www/DirectMapping.md
|
|
||||||
*/
|
|
||||||
@SuppressWarnings({"Duplicates", "SameParameterValue", "DeprecatedIsStillUsed", "WeakerAccess"})
|
|
||||||
public
|
|
||||||
class GtkLoader {
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgtk-x11-2.0.so.0 | grep gtk
|
|
||||||
// objdump -T /usr/lib/x86_64-linux-gnu/libgtk-3.so.0 | grep gtk
|
|
||||||
// objdump -T /usr/local/lib/libgtk-3.so.0 | grep gtk
|
|
||||||
|
|
||||||
// For funsies to look at, SyncThing did a LOT of work on compatibility in python (unfortunate for us, but interesting).
|
|
||||||
// https://github.com/syncthing/syncthing-gtk/blob/b7a3bc00e3bb6d62365ae62b5395370f3dcc7f55/syncthing_gtk/statusicon.py
|
|
||||||
|
|
||||||
// NOTE: AppIndicator uses this info to figure out WHAT VERSION OF appindicator to use: GTK2 -> appindicator1, GTK3 -> appindicator3
|
|
||||||
static boolean isGtk2;
|
|
||||||
static boolean isGtk3;
|
|
||||||
static boolean isLoaded;
|
|
||||||
|
|
||||||
|
|
||||||
static boolean alreadyRunningGTK;
|
|
||||||
|
|
||||||
static Function gtk_status_icon_position_menu = null;
|
|
||||||
|
|
||||||
// use GtkCheck for a safe accessor of these
|
|
||||||
static int MAJOR;
|
|
||||||
static int MINOR;
|
|
||||||
static int MICRO;
|
|
||||||
|
|
||||||
|
|
||||||
private static final NativeLibrary libraryReference;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* We can have GTK v3 or v2.
|
|
||||||
*
|
|
||||||
* Observations:
|
|
||||||
* JavaFX (java8) uses GTK2, and we can't load GTK3 if GTK2 symbols are loaded
|
|
||||||
* SWT uses GTK2 or GTK3. We do not work with the GTK3 version of SWT.
|
|
||||||
*/
|
|
||||||
static {
|
|
||||||
boolean forceGtk2 = GtkEventDispatch.FORCE_GTK2;
|
|
||||||
// prefer GTK3 and force GTK2 are mutually exclusive
|
|
||||||
boolean preferGtk3 = !forceGtk2 && GtkEventDispatch.PREFER_GTK3;
|
|
||||||
|
|
||||||
boolean _isGtk2 = false;
|
|
||||||
boolean _isLoaded = false;
|
|
||||||
boolean _alreadyRunningGTK = false;
|
|
||||||
int major = 0;
|
|
||||||
int minor = 0;
|
|
||||||
int micro = 0;
|
|
||||||
|
|
||||||
boolean shouldLoadGtk = !(OS.isWindows() || OS.isMacOsX());
|
|
||||||
if (!shouldLoadGtk) {
|
|
||||||
_isLoaded = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// we can force the system to use the swing indicator, which WORKS, but doesn't support transparency in the icon. However, there
|
|
||||||
// are certain GTK functions we might want to use (even if we are Swing or AWT), so we load GTK anyways...
|
|
||||||
|
|
||||||
// in some cases, we ALWAYS want to try GTK2 first
|
|
||||||
String gtk2LibName = "gtk-x11-2.0";
|
|
||||||
String gtk3LibName = "libgtk-3.so.0";
|
|
||||||
|
|
||||||
NativeLibrary library = null;
|
|
||||||
|
|
||||||
if (!_isLoaded && (forceGtk2 || !preferGtk3)) {
|
|
||||||
try {
|
|
||||||
library = JnaHelper.register(gtk2LibName, Gtk2.class);
|
|
||||||
|
|
||||||
_isGtk2 = true;
|
|
||||||
|
|
||||||
major = library.getGlobalVariableAddress("gtk_major_version").getInt(0);
|
|
||||||
minor = library.getGlobalVariableAddress("gtk_minor_version").getInt(0);
|
|
||||||
micro = library.getGlobalVariableAddress("gtk_micro_version").getInt(0);
|
|
||||||
|
|
||||||
gtk_status_icon_position_menu = library.getFunction( "gtk_status_icon_position_menu");
|
|
||||||
Function gtk_main_level = library.getFunction("gtk_main_level");
|
|
||||||
|
|
||||||
// when running inside of JavaFX, this will be '1'. All other times this should be '0'
|
|
||||||
// when it's '1', it means that someone else has started GTK -- so we DO NOT NEED TO.
|
|
||||||
_alreadyRunningGTK = gtk_main_level.invokeInt(null) != 0;
|
|
||||||
_isLoaded = true;
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkLoader.class).debug("GTK: {}", gtk2LibName);
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
if (library != null) {
|
|
||||||
library.dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkLoader.class).debug("Error loading library", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (forceGtk2) {
|
|
||||||
// don't try anything else if we forced GTK2
|
|
||||||
_isLoaded = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// now for the defaults...
|
|
||||||
|
|
||||||
// start with version 3
|
|
||||||
if (!_isLoaded) {
|
|
||||||
try {
|
|
||||||
// have to get the version information FIRST, because there are some really old GTK3 libraries out there.
|
|
||||||
library = JnaHelper.register(gtk3LibName, Gtk3VersionInfo.class);
|
|
||||||
|
|
||||||
Gtk3VersionInfo version = new Gtk3VersionInfo();
|
|
||||||
major = version.gtk_get_major_version();
|
|
||||||
minor = version.gtk_get_minor_version();
|
|
||||||
micro = version.gtk_get_micro_version();
|
|
||||||
|
|
||||||
library.dispose();
|
|
||||||
library = null;
|
|
||||||
|
|
||||||
library = JnaHelper.register(gtk3LibName, Gtk3.class);
|
|
||||||
|
|
||||||
gtk_status_icon_position_menu = library.getFunction( "gtk_status_icon_position_menu");
|
|
||||||
Function gtk_main_level = library.getFunction("gtk_main_level");
|
|
||||||
|
|
||||||
// when running inside of JavaFX, this will be '1'. All other times this should be '0'
|
|
||||||
// when it's '1', it means that someone else has started GTK -- so we DO NOT NEED TO.
|
|
||||||
_alreadyRunningGTK = gtk_main_level.invokeInt(null) != 0;
|
|
||||||
_isLoaded = true;
|
|
||||||
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkLoader.class).debug("GTK: {}", gtk3LibName);
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
if (library != null) {
|
|
||||||
library.dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkLoader.class).debug("Error loading library.", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// now version 2
|
|
||||||
if (!_isLoaded) {
|
|
||||||
try {
|
|
||||||
library = JnaHelper.register(gtk2LibName, Gtk2.class);
|
|
||||||
|
|
||||||
_isGtk2 = true;
|
|
||||||
major = library.getGlobalVariableAddress("gtk_major_version").getInt(0);
|
|
||||||
minor = library.getGlobalVariableAddress("gtk_minor_version").getInt(0);
|
|
||||||
micro = library.getGlobalVariableAddress("gtk_micro_version").getInt(0);
|
|
||||||
|
|
||||||
gtk_status_icon_position_menu = Function.getFunction(gtk2LibName, "gtk_status_icon_position_menu");
|
|
||||||
Function gtk_main_level = library.getFunction("gtk_main_level");
|
|
||||||
|
|
||||||
// when running inside of JavaFX, this will be '1'. All other times this should be '0'
|
|
||||||
// when it's '1', it means that someone else has started GTK -- so we DO NOT NEED TO.
|
|
||||||
_alreadyRunningGTK = gtk_main_level.invokeInt(null) != 0;
|
|
||||||
_isLoaded = true;
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkLoader.class).debug("GTK: {}", gtk2LibName);
|
|
||||||
}
|
|
||||||
} catch (Throwable e) {
|
|
||||||
if (library != null) {
|
|
||||||
library.dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (GtkEventDispatch.DEBUG) {
|
|
||||||
LoggerFactory.getLogger(GtkLoader.class).debug("Error loading library", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (shouldLoadGtk && _isLoaded) {
|
|
||||||
isLoaded = true;
|
|
||||||
|
|
||||||
// depending on how the system is initialized, SWT may, or may not, have the gtk_main loop running. It will EVENTUALLY run, so we
|
|
||||||
// do not want to run our own GTK event loop.
|
|
||||||
_alreadyRunningGTK |= Swt.isLoaded;
|
|
||||||
|
|
||||||
alreadyRunningGTK = _alreadyRunningGTK;
|
|
||||||
isGtk2 = _isGtk2;
|
|
||||||
isGtk3 = !_isGtk2;
|
|
||||||
|
|
||||||
MAJOR = major;
|
|
||||||
MINOR = minor;
|
|
||||||
MICRO = micro;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
isLoaded = false;
|
|
||||||
|
|
||||||
alreadyRunningGTK = false;
|
|
||||||
isGtk2 = false;
|
|
||||||
isGtk3 = false;
|
|
||||||
|
|
||||||
MAJOR = 0;
|
|
||||||
MINOR = 0;
|
|
||||||
MICRO = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
// This is so that queries for the GTK version DO NOT try to load GTK
|
|
||||||
GtkCheck.isGtk2 = isGtk2;
|
|
||||||
GtkCheck.isGtk3 = isGtk3;
|
|
||||||
GtkCheck.isGtkLoaded = isLoaded;
|
|
||||||
|
|
||||||
GtkCheck.MAJOR = MAJOR;
|
|
||||||
GtkCheck.MINOR = MINOR;
|
|
||||||
GtkCheck.MICRO = MICRO;
|
|
||||||
|
|
||||||
|
|
||||||
// load any GTK version specific methods
|
|
||||||
if (isGtk3) {
|
|
||||||
Gtk3.loadMethods(library);
|
|
||||||
}
|
|
||||||
|
|
||||||
libraryReference = library;
|
|
||||||
|
|
||||||
if (shouldLoadGtk) {
|
|
||||||
if (!_isLoaded) {
|
|
||||||
throw new RuntimeException("We apologize for this, but we are unable to determine the GTK library is in use, " +
|
|
||||||
"or even if it is in use... Please create an issue for this and include your OS type and configuration.");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,23 +0,0 @@
|
|||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
@SuppressWarnings({"unused", "PointlessBitwiseExpression"})
|
|
||||||
public
|
|
||||||
class GtkState {
|
|
||||||
public static final int NORMAL = 0x0; // normal state.
|
|
||||||
public static final int ACTIVE = 0x1; // pressed-in or activated; e.g. buttons while the mouse button is held down.
|
|
||||||
public static final int PRELIGHT = 0x2; // color when the mouse is over an activatable widget.
|
|
||||||
public static final int SELECTED = 0x3; // color when something is selected, e.g. when selecting some text to cut/copy.
|
|
||||||
public static final int INSENSITIVE = 0x4; // color when the mouse is over an activatable widget.
|
|
||||||
|
|
||||||
public static final int FLAG_NORMAL = 0;
|
|
||||||
public static final int FLAG_ACTIVE = 1 << 0;
|
|
||||||
public static final int FLAG_PRELIGHT = 1 << 1;
|
|
||||||
public static final int FLAG_SELECTED = 1 << 2;
|
|
||||||
public static final int FLAG_INSENSITIVE = 1 << 3;
|
|
||||||
public static final int FLAG_INCONSISTENT = 1 << 4;
|
|
||||||
public static final int FLAG_FOCUSED = 1 << 5;
|
|
||||||
public static final int FLAG_BACKDROP = 1 << 6;
|
|
||||||
}
|
|
@ -1,520 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux;
|
|
||||||
|
|
||||||
import static dorkbox.util.jna.linux.Gtk.Gtk2;
|
|
||||||
import static dorkbox.util.jna.linux.Gtk.Gtk3;
|
|
||||||
|
|
||||||
import java.awt.Color;
|
|
||||||
import java.awt.Rectangle;
|
|
||||||
import java.awt.Toolkit;
|
|
||||||
import java.io.File;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.concurrent.atomic.AtomicInteger;
|
|
||||||
import java.util.concurrent.atomic.AtomicReference;
|
|
||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.ptr.PointerByReference;
|
|
||||||
|
|
||||||
import dorkbox.executor.ShellExecutor;
|
|
||||||
import dorkbox.util.FileUtil;
|
|
||||||
import dorkbox.util.MathUtil;
|
|
||||||
import dorkbox.util.OS;
|
|
||||||
import dorkbox.util.OSUtil;
|
|
||||||
import dorkbox.util.jna.linux.structs.GtkRequisition;
|
|
||||||
import dorkbox.util.jna.linux.structs.GtkStyle;
|
|
||||||
import dorkbox.util.jna.linux.structs.PangoRectangle;
|
|
||||||
import dorkbox.util.swt.Swt;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Class to contain all of the various methods needed to get information set by a GTK theme.
|
|
||||||
*/
|
|
||||||
@SuppressWarnings({"deprecation", "WeakerAccess"})
|
|
||||||
public
|
|
||||||
class GtkTheme {
|
|
||||||
public static
|
|
||||||
Rectangle getPixelTextHeight(String text) {
|
|
||||||
// the following method requires an offscreen widget to get the size of text (for the checkmark size) via pango
|
|
||||||
// don't forget to destroy everything!
|
|
||||||
Pointer menu = null;
|
|
||||||
Pointer item = null;
|
|
||||||
|
|
||||||
try {
|
|
||||||
menu = Gtk2.gtk_menu_new();
|
|
||||||
item = Gtk2.gtk_image_menu_item_new_with_mnemonic(text);
|
|
||||||
|
|
||||||
Gtk2.gtk_container_add(menu, item);
|
|
||||||
|
|
||||||
Gtk2.gtk_widget_realize(menu);
|
|
||||||
Gtk2.gtk_widget_realize(item);
|
|
||||||
Gtk2.gtk_widget_show_all(menu);
|
|
||||||
|
|
||||||
// get the text widget (GtkAccelLabel/GtkLabel) from inside the GtkMenuItem
|
|
||||||
Pointer textLabel = Gtk2.gtk_bin_get_child(item);
|
|
||||||
Pointer pangoLayout = Gtk2.gtk_label_get_layout(textLabel);
|
|
||||||
|
|
||||||
// ink pixel size is how much exact space it takes on the screen
|
|
||||||
PangoRectangle ink = new PangoRectangle();
|
|
||||||
|
|
||||||
Gtk2.pango_layout_get_pixel_extents(pangoLayout, ink.getPointer(), null);
|
|
||||||
ink.read();
|
|
||||||
|
|
||||||
return new Rectangle(ink.width, ink.height);
|
|
||||||
} finally {
|
|
||||||
Gtk2.gtk_widget_destroy(item);
|
|
||||||
Gtk2.gtk_widget_destroy(menu);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return the size of the GTK menu entry's IMAGE, as best as we can tell, for determining how large of icons to use for the menu entry
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
int getMenuEntryImageSize() {
|
|
||||||
final AtomicReference<Integer> imageHeight = new AtomicReference<Integer>();
|
|
||||||
|
|
||||||
GtkEventDispatch.dispatchAndWait(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
Pointer offscreen = Gtk2.gtk_offscreen_window_new();
|
|
||||||
|
|
||||||
// get the default icon size for the "paste" icon.
|
|
||||||
Pointer item = Gtk2.gtk_image_menu_item_new_from_stock("gtk-paste", null);
|
|
||||||
|
|
||||||
Gtk2.gtk_container_add(offscreen, item);
|
|
||||||
|
|
||||||
PointerByReference r = new PointerByReference();
|
|
||||||
GObject.g_object_get(item, "image", r.getPointer(), null);
|
|
||||||
|
|
||||||
Pointer imageWidget = r.getValue();
|
|
||||||
GtkRequisition gtkRequisition = new GtkRequisition();
|
|
||||||
Gtk2.gtk_widget_size_request(imageWidget, gtkRequisition.getPointer());
|
|
||||||
gtkRequisition.read();
|
|
||||||
|
|
||||||
imageHeight.set(gtkRequisition.height);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
int height = imageHeight.get();
|
|
||||||
if (height > 0) {
|
|
||||||
return height;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
LoggerFactory.getLogger(GtkTheme.class).warn("Unable to get tray menu image size. Using default.");
|
|
||||||
return 16;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the system tray indicator size.
|
|
||||||
* - AppIndicator: will properly scale the image if it's not the correct size
|
|
||||||
* - GtkStatusIndicator: ??
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
int getIndicatorSize() {
|
|
||||||
// Linux is similar enough, that it just uses this method
|
|
||||||
// https://wiki.archlinux.org/index.php/HiDPI
|
|
||||||
|
|
||||||
// 96 DPI is the default
|
|
||||||
final double defaultDPI = 96.0;
|
|
||||||
|
|
||||||
final AtomicReference<Double> screenScale = new AtomicReference<Double>();
|
|
||||||
final AtomicInteger screenDPI = new AtomicInteger();
|
|
||||||
screenScale.set(0D);
|
|
||||||
screenDPI.set(0);
|
|
||||||
|
|
||||||
GtkEventDispatch.dispatchAndWait(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
// screen DPI
|
|
||||||
Pointer screen = Gtk2.gdk_screen_get_default();
|
|
||||||
if (screen != null) {
|
|
||||||
// this call makes NO SENSE, but reading the documentation shows it is the CORRECT call.
|
|
||||||
screenDPI.set((int) Gtk2.gdk_screen_get_resolution(screen));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Gtk2.isGtk3) {
|
|
||||||
Pointer window = Gtk2.gdk_get_default_root_window();
|
|
||||||
if (window != null) {
|
|
||||||
double scale = Gtk3.gdk_window_get_scale_factor(window);
|
|
||||||
screenScale.set(scale);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
// fallback
|
|
||||||
if (screenDPI.get() <= 0) {
|
|
||||||
// GET THE DPI IN LINUX
|
|
||||||
// https://wiki.archlinux.org/index.php/Talk:GNOME
|
|
||||||
Object detectedValue = Toolkit.getDefaultToolkit().getDesktopProperty("gnome.Xft/DPI");
|
|
||||||
if (detectedValue instanceof Integer) {
|
|
||||||
Integer asInteger = (Integer) detectedValue;
|
|
||||||
// reasonably safe check
|
|
||||||
if (asInteger > 1024) {
|
|
||||||
int dpi = asInteger / 1024;
|
|
||||||
screenDPI.set(dpi);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// 50 dpi is the minimum value gnome allows, and assume something screwed up. We apply this for ALL environments!
|
|
||||||
if (screenDPI.get() < 50) {
|
|
||||||
screenDPI.set((int) defaultDPI);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// check system ENV variables.
|
|
||||||
if (screenScale.get() == 0) {
|
|
||||||
String envVar = System.getenv("QT_AUTO_SCREEN_SCALE_FACTOR");
|
|
||||||
if (envVar != null) {
|
|
||||||
try {
|
|
||||||
screenScale.set(Double.parseDouble(envVar));
|
|
||||||
} catch (Exception ignored) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// check system ENV variables.
|
|
||||||
if (screenScale.get() == 0) {
|
|
||||||
String envVar = System.getenv("QT_SCALE_FACTOR");
|
|
||||||
if (envVar != null) {
|
|
||||||
try {
|
|
||||||
screenScale.set(Double.parseDouble(envVar));
|
|
||||||
} catch (Exception ignored) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// check system ENV variables.
|
|
||||||
if (screenScale.get() == 0) {
|
|
||||||
String envVar = System.getenv("GDK_SCALE");
|
|
||||||
if (envVar != null) {
|
|
||||||
try {
|
|
||||||
screenScale.set(Double.parseDouble(envVar));
|
|
||||||
} catch (Exception ignored) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// check system ENV variables.
|
|
||||||
if (screenScale.get() == 0) {
|
|
||||||
String envVar = System.getenv("ELM_SCALE");
|
|
||||||
if (envVar != null) {
|
|
||||||
try {
|
|
||||||
screenScale.set(Double.parseDouble(envVar));
|
|
||||||
} catch (Exception ignored) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
OSUtil.DesktopEnv.Env env = OSUtil.DesktopEnv.get();
|
|
||||||
// sometimes the scaling-factor is set. If we have gsettings, great! otherwise try KDE
|
|
||||||
try {
|
|
||||||
// gsettings get org.gnome.desktop.interface scaling-factor
|
|
||||||
final ShellExecutor shellVersion = new ShellExecutor();
|
|
||||||
shellVersion.setExecutable("gsettings");
|
|
||||||
shellVersion.addArgument("get");
|
|
||||||
shellVersion.addArgument("org.gnome.desktop.interface");
|
|
||||||
shellVersion.addArgument("scaling-factor");
|
|
||||||
shellVersion.start();
|
|
||||||
|
|
||||||
String output = shellVersion.getOutput();
|
|
||||||
|
|
||||||
if (!output.isEmpty()) {
|
|
||||||
// DEFAULT icon size is 16. HiDpi changes this scale, so we should use it as well.
|
|
||||||
// should be: uint32 0 or something
|
|
||||||
if (output.contains("uint32")) {
|
|
||||||
String value = output.substring(output.indexOf("uint") + 7);
|
|
||||||
|
|
||||||
// 0 is disabled (no scaling)
|
|
||||||
// 1 is enabled (default scale)
|
|
||||||
// 2 is 2x scale
|
|
||||||
// 3 is 3x scale
|
|
||||||
// etc
|
|
||||||
|
|
||||||
double scalingFactor = Double.parseDouble(value);
|
|
||||||
if (scalingFactor >= 1) {
|
|
||||||
screenScale.set(scalingFactor);
|
|
||||||
}
|
|
||||||
|
|
||||||
// A setting of 2, 3, etc, which is all you can do with scaling-factor
|
|
||||||
// To enable HiDPI, use gsettings:
|
|
||||||
// gsettings set org.gnome.desktop.interface scaling-factor 2
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (Throwable ignore) {
|
|
||||||
}
|
|
||||||
|
|
||||||
if (OSUtil.DesktopEnv.isKDE()) {
|
|
||||||
// check the custom KDE override file
|
|
||||||
try {
|
|
||||||
File customSettings = new File("/usr/bin/startkde-custom");
|
|
||||||
if (customSettings.canRead()) {
|
|
||||||
List<String> lines = FileUtil.readLines(customSettings);
|
|
||||||
for (String line : lines) {
|
|
||||||
String str = "export GDK_SCALE=";
|
|
||||||
int i = line.indexOf(str);
|
|
||||||
if (i > -1) {
|
|
||||||
String scale = line.substring(i + str.length());
|
|
||||||
double scalingFactor = Double.parseDouble(scale);
|
|
||||||
if (scalingFactor >= 1) {
|
|
||||||
screenScale.set(scalingFactor);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (Exception ignored) {
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// System.err.println("screen scale: " + screenScale.get());
|
|
||||||
// System.err.println("screen DPI: " + screenDPI.get());
|
|
||||||
|
|
||||||
if (screenScale.get() == 0) {
|
|
||||||
/*
|
|
||||||
*
|
|
||||||
* Looking in plasma-framework/src/declarativeimports/core/units.cpp:
|
|
||||||
// Scale the icon sizes up using the devicePixelRatio
|
|
||||||
// This function returns the next stepping icon size
|
|
||||||
// and multiplies the global settings with the dpi ratio.
|
|
||||||
const qreal ratio = devicePixelRatio();
|
|
||||||
|
|
||||||
if (ratio < 1.5) {
|
|
||||||
return size;
|
|
||||||
} else if (ratio < 2.0) {
|
|
||||||
return size * 1.5;
|
|
||||||
} else if (ratio < 2.5) {
|
|
||||||
return size * 2.0;
|
|
||||||
} else if (ratio < 3.0) {
|
|
||||||
return size * 2.5;
|
|
||||||
} else if (ratio < 3.5) {
|
|
||||||
return size * 3.0;
|
|
||||||
} else {
|
|
||||||
return size * ratio;
|
|
||||||
}
|
|
||||||
My ratio is 1.47674, that means I have no scaling at all when there is a 1.5 factor existing. Is it reasonable? Wouldn't it make more sense to use the factor the closest to the ratio rather than what is done here?
|
|
||||||
*/
|
|
||||||
|
|
||||||
File mainFile = new File("/usr/share/plasma/plasmoids/org.kde.plasma.private.systemtray/contents/config/main.xml");
|
|
||||||
if (mainFile.canRead()) {
|
|
||||||
List<String> lines = FileUtil.readLines(mainFile);
|
|
||||||
boolean found = false;
|
|
||||||
int index;
|
|
||||||
for (final String line : lines) {
|
|
||||||
if (line.contains("<entry name=\"iconSize\" type=\"Int\">")) {
|
|
||||||
found = true;
|
|
||||||
// have to get the "default" line value
|
|
||||||
}
|
|
||||||
|
|
||||||
String str = "<default>";
|
|
||||||
if (found && (index = line.indexOf(str)) > -1) {
|
|
||||||
// this is our line. now get the value.
|
|
||||||
String substring = line.substring(index + str.length(), line.indexOf("</default>", index));
|
|
||||||
|
|
||||||
if (MathUtil.isInteger(substring)) {
|
|
||||||
// Default icon size for the systray icons, it's an enum which values mean,
|
|
||||||
// Small, SmallMedium, Medium, Large, Huge, Enormous respectively.
|
|
||||||
// On low DPI systems they correspond to :
|
|
||||||
// 16, 22, 32, 48, 64, 128 pixels.
|
|
||||||
// On high DPI systems those values would be scaled up, depending on the DPI.
|
|
||||||
int imageSize = 0;
|
|
||||||
int imageSizeEnum = Integer.parseInt(substring);
|
|
||||||
switch (imageSizeEnum) {
|
|
||||||
case 0:
|
|
||||||
imageSize = 16;
|
|
||||||
break;
|
|
||||||
case 1:
|
|
||||||
imageSize = 22;
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
imageSize = 32;
|
|
||||||
break;
|
|
||||||
case 3:
|
|
||||||
imageSize = 48;
|
|
||||||
break;
|
|
||||||
case 4:
|
|
||||||
imageSize = 64;
|
|
||||||
break;
|
|
||||||
case 5:
|
|
||||||
imageSize = 128;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (imageSize > 0) {
|
|
||||||
double scaleRatio = screenDPI.get() / defaultDPI;
|
|
||||||
|
|
||||||
return (int) (scaleRatio * imageSize);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
if (OSUtil.Linux.isUbuntu() && OSUtil.DesktopEnv.isUnity(env)) {
|
|
||||||
// if we measure on ubuntu unity using a screen shot (using swing, so....) , the max size was 24, HOWEVER this goes from
|
|
||||||
// the top->bottom of the indicator bar -- and since it was swing, it uses a different rendering method and it (honestly)
|
|
||||||
// looks weird, because there is no padding for the icon. The official AppIndicator size is hardcoded...
|
|
||||||
// http://bazaar.launchpad.net/~indicator-applet-developers/libindicator/trunk.16.10/view/head:/libindicator/indicator-image-helper.c
|
|
||||||
|
|
||||||
return 22;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
// xfce is easy, because it's not a GTK setting for the size (xfce notification area maximum icon size)
|
|
||||||
if (env == OSUtil.DesktopEnv.Env.XFCE) {
|
|
||||||
String properties = OSUtil.DesktopEnv.queryXfce("xfce4-panel", null);
|
|
||||||
String[] propertiesAsList = properties.split(OS.LINE_SEPARATOR);
|
|
||||||
for (String prop : propertiesAsList) {
|
|
||||||
if (prop.startsWith("/plugins/") && prop.endsWith("/size-max")) {
|
|
||||||
// this is the property we are looking for (we just don't know which panel it's on)
|
|
||||||
|
|
||||||
String size = OSUtil.DesktopEnv.queryXfce("xfce4-panel", prop);
|
|
||||||
try {
|
|
||||||
return Integer.parseInt(size);
|
|
||||||
} catch (Exception e) {
|
|
||||||
LoggerFactory.getLogger(GtkTheme.class)
|
|
||||||
.error("Unable to get XFCE notification panel size for channel '{}', property '{}'",
|
|
||||||
"xfce4-panel", prop, e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// default...
|
|
||||||
return 22;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// try to use GTK to get the tray icon size
|
|
||||||
final AtomicInteger traySize = new AtomicInteger();
|
|
||||||
|
|
||||||
|
|
||||||
if (Swt.isLoaded) {
|
|
||||||
} else {
|
|
||||||
GtkEventDispatch.dispatchAndWait(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
Pointer screen = Gtk2.gdk_screen_get_default();
|
|
||||||
Pointer settings = null;
|
|
||||||
|
|
||||||
if (screen != null) {
|
|
||||||
settings = Gtk2.gtk_settings_get_for_screen(screen);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (settings != null) {
|
|
||||||
PointerByReference pointer = new PointerByReference();
|
|
||||||
|
|
||||||
// https://wiki.archlinux.org/index.php/GTK%2B
|
|
||||||
// To use smaller icons, use a line like this:
|
|
||||||
// gtk-icon-sizes = "panel-menu=16,16:panel=16,16:gtk-menu=16,16:gtk-large-toolbar=16,16:gtk-small-toolbar=16,16:gtk-button=16,16"
|
|
||||||
|
|
||||||
// this gets icon sizes. On XFCE, ubuntu, it returns "panel-menu-bar=24,24"
|
|
||||||
// NOTE: gtk-icon-sizes is deprecated and ignored since GTK+ 3.10.
|
|
||||||
|
|
||||||
// A list of icon sizes. The list is separated by colons, and item has the form: size-name = width , height
|
|
||||||
GObject.g_object_get(settings, "gtk-icon-sizes", pointer.getPointer(), null);
|
|
||||||
|
|
||||||
Pointer value = pointer.getValue();
|
|
||||||
if (value != null) {
|
|
||||||
String iconSizes = value.getString(0);
|
|
||||||
String[] strings = new String[] {"panel-menu-bar=", "panel=", "gtk-large-toolbar=", "gtk-small-toolbar="};
|
|
||||||
for (String var : strings) {
|
|
||||||
int i = iconSizes.indexOf(var);
|
|
||||||
if (i >= 0) {
|
|
||||||
String size = iconSizes.substring(i + var.length(), iconSizes.indexOf(",", i));
|
|
||||||
|
|
||||||
if (MathUtil.isInteger(size)) {
|
|
||||||
traySize.set(Integer.parseInt(size));
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
int i = traySize.get();
|
|
||||||
if (i != 0) {
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// sane default
|
|
||||||
LoggerFactory.getLogger(GtkTheme.class).warn("Unable to get tray image size. Using default.");
|
|
||||||
|
|
||||||
return 24;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return the widget color of text for the current theme, or black. It is important that this is called AFTER GTK has been initialized.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
Color getTextColor() {
|
|
||||||
final AtomicReference<Color> color = new AtomicReference<Color>(null);
|
|
||||||
GtkEventDispatch.dispatchAndWait(new Runnable() {
|
|
||||||
@SuppressWarnings("UnusedAssignment")
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
Color c = null;
|
|
||||||
|
|
||||||
// the following method requires an offscreen widget to get the style information from.
|
|
||||||
// don't forget to destroy everything!
|
|
||||||
Pointer menu = null;
|
|
||||||
Pointer item = null;
|
|
||||||
|
|
||||||
try {
|
|
||||||
menu = Gtk2.gtk_menu_new();
|
|
||||||
item = Gtk2.gtk_image_menu_item_new_with_mnemonic("a");
|
|
||||||
|
|
||||||
Gtk2.gtk_container_add(menu, item);
|
|
||||||
|
|
||||||
Gtk2.gtk_widget_realize(menu);
|
|
||||||
Gtk2.gtk_widget_realize(item);
|
|
||||||
Gtk2.gtk_widget_show_all(menu);
|
|
||||||
|
|
||||||
GtkStyle style = Gtk2.gtk_rc_get_style(item);
|
|
||||||
style.read();
|
|
||||||
|
|
||||||
// this is the same color chromium uses (fg)
|
|
||||||
// https://chromium.googlesource.com/chromium/src/+/b3ca230ddd7d1238ee96ed26ea23e369f10dd655/chrome/browser/ui/libgtk2ui/gtk2_ui.cc#873
|
|
||||||
c = style.fg[GtkState.NORMAL].getColor();
|
|
||||||
|
|
||||||
color.set(c);
|
|
||||||
} finally {
|
|
||||||
Gtk2.gtk_widget_destroy(item);
|
|
||||||
Gtk2.gtk_widget_destroy(menu);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
return color.get();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,58 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
import dorkbox.util.jna.linux.AppIndicator;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
class AppIndicatorInstanceStruct extends Structure {
|
|
||||||
public GObjectStruct parent;
|
|
||||||
public Pointer priv;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("parent", "priv");
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void app_indicator_set_title(String title) {
|
|
||||||
AppIndicator.app_indicator_set_title(getPointer(), title);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void app_indicator_set_status(int status) {
|
|
||||||
AppIndicator.app_indicator_set_status(getPointer(), status);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void app_indicator_set_menu(Pointer menu) {
|
|
||||||
AppIndicator.app_indicator_set_menu(getPointer(), menu);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void app_indicator_set_icon(String icon_name) {
|
|
||||||
AppIndicator.app_indicator_set_icon(getPointer(), icon_name);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,46 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
class GObjectStruct extends Structure {
|
|
||||||
public
|
|
||||||
class ByValue extends GObjectStruct implements Structure.ByValue {}
|
|
||||||
|
|
||||||
|
|
||||||
public
|
|
||||||
class ByReference extends GObjectStruct implements Structure.ByReference {}
|
|
||||||
|
|
||||||
|
|
||||||
public GTypeInstanceStruct g_type_instance;
|
|
||||||
public int ref_count;
|
|
||||||
public Pointer qdata;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("g_type_instance", "ref_count", "qdata");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,44 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
class GTypeInstanceStruct extends Structure {
|
|
||||||
public
|
|
||||||
class ByValue extends GTypeInstanceStruct implements Structure.ByValue {}
|
|
||||||
|
|
||||||
|
|
||||||
public
|
|
||||||
class ByReference extends GTypeInstanceStruct implements Structure.ByReference {}
|
|
||||||
|
|
||||||
|
|
||||||
public Pointer g_class;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("g_class");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,88 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.awt.Color;
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.gnome.org/gdk3/stable/gdk3-Colors.html
|
|
||||||
*
|
|
||||||
* GdkColor has been deprecated since version 3.14 and should not be used in newly-written code.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class GdkColor extends Structure {
|
|
||||||
|
|
||||||
/* The color type.
|
|
||||||
* A color consists of red, green and blue values in the
|
|
||||||
* range 0-65535 and a pixel value. The pixel value is highly
|
|
||||||
* dependent on the depth and colormap which this color will
|
|
||||||
* be used to draw into. Therefore, sharing colors between
|
|
||||||
* colormaps is a bad idea.
|
|
||||||
*/
|
|
||||||
public int pixel;
|
|
||||||
public short red;
|
|
||||||
public short green;
|
|
||||||
public short blue;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Convert from positive int (value between 0 and 65535, these are 16 bits per pixel) to values from 0-255
|
|
||||||
*/
|
|
||||||
private static int convert(int inputColor) {
|
|
||||||
return (inputColor & 0x0000FFFF >> 8) & 0xFF;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int red() {
|
|
||||||
return convert(red);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int green() {
|
|
||||||
return convert(green);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int blue() {
|
|
||||||
return convert(blue);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
Color getColor() {
|
|
||||||
read(); // have to read the struct members first!
|
|
||||||
return new Color(red(), green(), blue());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
String toString() {
|
|
||||||
return "[r=" + red() + ",g=" + green() + ",b=" + blue() + "]";
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("pixel", "red", "green", "blue");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public
|
|
||||||
class ByValue extends GdkColor implements Structure.ByValue {}
|
|
||||||
|
|
||||||
|
|
||||||
public static
|
|
||||||
class ByReference extends GdkColor implements Structure.ByReference {}
|
|
||||||
}
|
|
@ -1,47 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
class GdkEventButton extends Structure {
|
|
||||||
public int type;
|
|
||||||
public Pointer window;
|
|
||||||
public int send_event;
|
|
||||||
public int time;
|
|
||||||
public double x;
|
|
||||||
public double y;
|
|
||||||
public Pointer axes;
|
|
||||||
public int state;
|
|
||||||
public int button;
|
|
||||||
public Pointer device;
|
|
||||||
public double x_root;
|
|
||||||
public double y_root;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("type", "window", "send_event", "time", "x", "y", "axes", "state", "button", "device", "x_root", "y_root");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,37 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.gimp.org/api/2.0/gtk/GtkWidget.html#GtkRequisition
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class GtkRequisition extends Structure {
|
|
||||||
|
|
||||||
public int width;
|
|
||||||
public int height;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("width", "height");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,116 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
class GtkStyle extends Structure {
|
|
||||||
/*
|
|
||||||
* There are several 'directives' to change the attributes of a widget.
|
|
||||||
* fg - Sets the foreground color of a widget.
|
|
||||||
* bg - Sets the background color of a widget.
|
|
||||||
* text - Sets the foreground color for widgets that have editable text.
|
|
||||||
* base - Sets the background color for widgets that have editable text.
|
|
||||||
* bg_pixmap - Sets the background of a widget to a tiled pixmap.
|
|
||||||
* font_name - Sets the font to be used with the given widget.
|
|
||||||
* xthickness - Sets the left and right border width. This is not what you might think; it sets the borders of children(?)
|
|
||||||
* ythickness - similar to above but for the top and bottom.
|
|
||||||
*
|
|
||||||
* There are several states a widget can be in, and you can set different colors, pixmaps and fonts for each state. These states are:
|
|
||||||
* NORMAL - The normal state of a widget. Ie the mouse is not over it, and it is not being pressed, etc.
|
|
||||||
* PRELIGHT - When the mouse is over top of the widget, colors defined using this state will be in effect.
|
|
||||||
* ACTIVE - When the widget is pressed or clicked it will be active, and the attributes assigned by this tag will be in effect.
|
|
||||||
* INSENSITIVE - This is the state when a widget is 'greyed out'. It is not active, and cannot be clicked on.
|
|
||||||
* SELECTED - When an object is selected, it takes these attributes.
|
|
||||||
*/
|
|
||||||
|
|
||||||
public static
|
|
||||||
class ByReference extends GtkStyle implements Structure.ByReference {
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
class ByValue extends GtkStyle implements Structure.ByValue {
|
|
||||||
}
|
|
||||||
|
|
||||||
// required, even though it's "private" in the corresponding C code. OTHERWISE the memory offsets are INCORRECT.
|
|
||||||
public GObjectStruct parent_instance;
|
|
||||||
|
|
||||||
/** fg: foreground for drawing GtkLabel */
|
|
||||||
public GdkColor fg[] = new GdkColor[5];
|
|
||||||
|
|
||||||
/** bg: the usual background color, gray by default */
|
|
||||||
public GdkColor bg[] = new GdkColor[5];
|
|
||||||
|
|
||||||
public GdkColor light[] = new GdkColor[5];
|
|
||||||
public GdkColor dark[] = new GdkColor[5];
|
|
||||||
public GdkColor mid[] = new GdkColor[5];
|
|
||||||
|
|
||||||
/**
|
|
||||||
* text: text for entries and text widgets (although in GTK 1.2 sometimes fg gets used, this is more or less a bug and fixed in GTK 2.0).
|
|
||||||
*/
|
|
||||||
public GdkColor text[] = new GdkColor[5];
|
|
||||||
|
|
||||||
/** base: background when using text, colored white in the default theme. */
|
|
||||||
public GdkColor base[] = new GdkColor[5];
|
|
||||||
|
|
||||||
/** Halfway between text/base */
|
|
||||||
public GdkColor text_aa[] = new GdkColor[5];
|
|
||||||
|
|
||||||
public GdkColor black;
|
|
||||||
public GdkColor white;
|
|
||||||
public Pointer /*PangoFontDescription*/ font_desc;
|
|
||||||
public int xthickness;
|
|
||||||
public int ythickness;
|
|
||||||
public Pointer /*cairo_pattern_t*/ background[] = new Pointer[5];
|
|
||||||
|
|
||||||
public
|
|
||||||
void debug(final int gtkState) {
|
|
||||||
System.err.println("base " + base[gtkState].getColor());
|
|
||||||
System.err.println("text " + text[gtkState].getColor());
|
|
||||||
System.err.println("text_aa " + text_aa[gtkState].getColor());
|
|
||||||
System.err.println("bg " + bg[gtkState].getColor());
|
|
||||||
System.err.println("fg " + fg[gtkState].getColor());
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("parent_instance",
|
|
||||||
"fg",
|
|
||||||
"bg",
|
|
||||||
"light",
|
|
||||||
"dark",
|
|
||||||
"mid",
|
|
||||||
"text",
|
|
||||||
"base",
|
|
||||||
"text_aa",
|
|
||||||
"black",
|
|
||||||
"white",
|
|
||||||
"font_desc",
|
|
||||||
"xthickness",
|
|
||||||
"ythickness",
|
|
||||||
"background");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,39 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.gnome.org/pango/stable/pango-Glyph-Storage.html#PangoRectangle
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class PangoRectangle extends Structure {
|
|
||||||
|
|
||||||
public int x;
|
|
||||||
public int y;
|
|
||||||
public int width;
|
|
||||||
public int height;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("x", "y", "width", "height");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,184 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2010 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.linux.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
@SuppressWarnings("ALL")
|
|
||||||
public
|
|
||||||
class Termios extends Structure {
|
|
||||||
// NOTE: MUST BE BITS!! from: /usr/include/x86_64-linux-gnu/bits/termios.h
|
|
||||||
// the one in octal WILL NOT WORK!! (you have been warned)
|
|
||||||
|
|
||||||
// Definitions at: http://linux.die.net/man/3/termios
|
|
||||||
|
|
||||||
// Input flags - software input processing
|
|
||||||
public static class Input {
|
|
||||||
public static final int IGNBRK = 0000001; // ignore BREAK condition
|
|
||||||
public static final int BRKINT = 0000002; // map BREAK to SIGINTR
|
|
||||||
public static final int IGNPAR = 0000004; // ignore (discard) parity errors
|
|
||||||
public static final int PARMRK = 0000010; // mark parity and framing errors
|
|
||||||
public static final int INPCK = 0000020; // enable checking of parity errors
|
|
||||||
public static final int ISTRIP = 0000040; // strip 8th bit off chars
|
|
||||||
public static final int INLCR = 0000100; // map NL into CR
|
|
||||||
public static final int IGNCR = 0000200; // ignore CR
|
|
||||||
public static final int ICRNL = 0000400; // map CR to NL (ala CRMOD)
|
|
||||||
// public static final int IUCLC = 0001000; // (not in POSIX) Map uppercase characters to lowercase on input.
|
|
||||||
public static final int IXON = 0002000; // enable output flow control
|
|
||||||
public static final int IXANY = 0004000; // any char will restart after stop
|
|
||||||
public static final int IXOFF = 0010000; // enable input flow control
|
|
||||||
public static final int IMAXBEL = 0020000; // ring bell on input queue full
|
|
||||||
// public static final int IUTF8 = 0040000; // (since Linux 2.6.4) (not in POSIX) Input is UTF8; this allows character-erase to be correctly performed in cooked mode.
|
|
||||||
}
|
|
||||||
|
|
||||||
public static class Output {
|
|
||||||
// Output flags - software output processing
|
|
||||||
public static final int OPOST = 0000001; // enable following output processing (not set = raw output)
|
|
||||||
// public static final int OLCUC = 0000002; // (not in POSIX) Map lowercase characters to uppercase on output.
|
|
||||||
public static final int ONLCR = 0000004; // map NL to CR-NL (ala CRMOD)
|
|
||||||
public static final int OCRNL = 0000010; // map CR to NL on output
|
|
||||||
public static final int ONOCR = 0000020; // no CR output at column 0
|
|
||||||
public static final int ONLRET = 0000040; // NL performs CR function
|
|
||||||
public static final int OFILL = 0000100; // Send fill characters for a delay, rather than using a timed delay.
|
|
||||||
public static final int OFDEL = 0000200; // Fill character is ASCII DEL (0177). If unset, fill character is ASCII NUL ('\0'). (Not implemented on Linux.)
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public static class Control {
|
|
||||||
// Control flags - hardware control of terminal
|
|
||||||
public static final int CSIZE = 0000060; // character size mask
|
|
||||||
public static final int CS5 = 0000000; // 5 bits (pseudo)
|
|
||||||
public static final int CS6 = 0000020; // 6 bits
|
|
||||||
public static final int CS7 = 0000040; // 7 bits
|
|
||||||
public static final int CS8 = 0000060; // 8 bits
|
|
||||||
public static final int CSTOPB = 0000100; // send 2 stop bits
|
|
||||||
public static final int CREAD = 0000200; // enable receiver
|
|
||||||
public static final int PARENB = 0000400; // parity enable
|
|
||||||
public static final int PARODD = 0001000; // odd parity, else even
|
|
||||||
public static final int HUPCL = 0002000; // hang up on last close
|
|
||||||
public static final int CLOCAL = 0004000; // ignore modem status lines
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public static class Local {
|
|
||||||
// "Local" flags - dumping ground for other state
|
|
||||||
// Warning: some flags in this structure begin with the letter "I" and look like they belong in the input flag.
|
|
||||||
public static final int ISIG = 0000001; // enable signals INTR, QUIT, [D]SUSP
|
|
||||||
public static final int ICANON = 0000002; // canonicalize input lines
|
|
||||||
//public static final int XCASE = 0000004; // (not in POSIX; not supported under Linux)
|
|
||||||
public static final int ECHO = 0000010; // enable echoing
|
|
||||||
public static final int ECHOE = 0000020; // visually erase chars
|
|
||||||
public static final int ECHOK = 0000040; // echo NL after line kill
|
|
||||||
public static final int ECHONL = 0000100; // echo NL even if ECHO is off
|
|
||||||
public static final int NOFLSH = 0000200; // don't flush after interrupt
|
|
||||||
public static final int TOSTOP = 0000400; // stop background jobs from output
|
|
||||||
public static final int ECHOCTL = 0001000; // echo control chars as ^(Char)
|
|
||||||
public static final int ECHOPRT = 0002000; // visual erase mode for hardcopy
|
|
||||||
public static final int ECHOKE = 0004000; // visual erase for line kill
|
|
||||||
public static final int FLUSHO = 0001000; // output being flushed (state)
|
|
||||||
public static final int PENDIN = 0004000; // XXX retype pending input (state)
|
|
||||||
public static final int IEXTEN = 0100000; // enable DISCARD and LNEXT
|
|
||||||
public static final int EXTPROC = 0200000; // external processing
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public static class ControlChars {
|
|
||||||
// Special Control Characters
|
|
||||||
//
|
|
||||||
// the value is the index into c_cc[] character array.
|
|
||||||
public static final int VINTR = 0; // ISIG
|
|
||||||
public static final int VQUIT = 1; // ISIG
|
|
||||||
public static final int VERASE = 2; // ICANON
|
|
||||||
public static final int VKILL = 3; // ICANON
|
|
||||||
public static final int VEOF = 4; // ICANON
|
|
||||||
public static final int VTIME = 5; // !ICANON
|
|
||||||
public static final int VMIN = 6; // !ICANON
|
|
||||||
public static final int VSWTC = 7;
|
|
||||||
public static final int VSTART = 8; // IXON, IXOFF
|
|
||||||
public static final int VSTOP = 9; // IXON, IXOFF
|
|
||||||
public static final int VSUSP = 10;// ISIG
|
|
||||||
public static final int VEOL = 11;// ICANON
|
|
||||||
public static final int VREPRINT = 12;// ICANON together with IEXTEN
|
|
||||||
public static final int VDISCARD = 13;
|
|
||||||
public static final int VWERASE = 14;// ICANON together with IEXTEN
|
|
||||||
public static final int VLNEXT = 15;// IEXTEN
|
|
||||||
public static final int VEOL2 = 16;// ICANON together with IEXTEN
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public static final int TCSANOW = 0;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* input mode flags
|
|
||||||
*/
|
|
||||||
public int inputFlags;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* output mode flags
|
|
||||||
*/
|
|
||||||
public int outputFlags;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* control mode flags
|
|
||||||
*/
|
|
||||||
public int controlFlags;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* local mode flags
|
|
||||||
*/
|
|
||||||
public int localFlags;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* line discipline
|
|
||||||
*/
|
|
||||||
public char lineDiscipline;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* control characters
|
|
||||||
*/
|
|
||||||
public byte[] controlChars = new byte[32];
|
|
||||||
|
|
||||||
/**
|
|
||||||
* input speed
|
|
||||||
*/
|
|
||||||
public int inputSpeed;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* output speed
|
|
||||||
*/
|
|
||||||
public int outputSpeed;
|
|
||||||
|
|
||||||
public
|
|
||||||
Termios() {}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("inputFlags",
|
|
||||||
"outputFlags",
|
|
||||||
"controlFlags",
|
|
||||||
"localFlags",
|
|
||||||
"lineDiscipline",
|
|
||||||
"controlChars",
|
|
||||||
"inputSpeed",
|
|
||||||
"outputSpeed");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,26 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/appkit/nscell?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
interface NSCellStateValue {
|
|
||||||
int NSMixedState = -1;
|
|
||||||
int NSOffState = 0;
|
|
||||||
int NSOnState = 1;
|
|
||||||
}
|
|
@ -1,36 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/foundation/nsdata?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSData extends NSObject {
|
|
||||||
|
|
||||||
private static final Pointer objectClass = ObjectiveC.objc_lookUpClass("NSData");
|
|
||||||
|
|
||||||
private static final Pointer dataWithBytesLength = ObjectiveC.sel_getUid("dataWithBytes:length:");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSData(byte[] data) {
|
|
||||||
super(ObjectiveC.objc_msgSend(objectClass, dataWithBytesLength, data, data.length));
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,60 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.ImageUtil;
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/appkit/nsimage?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSImage extends NSObject {
|
|
||||||
|
|
||||||
private static final Pointer objectClass = ObjectiveC.objc_lookUpClass("NSImage");
|
|
||||||
|
|
||||||
private static final Pointer initWithContentsOfFile = ObjectiveC.sel_getUid("initWithContentsOfFile:");
|
|
||||||
private static final Pointer initWithData = ObjectiveC.sel_getUid("initWithData:");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSImage(NSData data) {
|
|
||||||
super(ObjectiveC.class_createInstance(objectClass, 0));
|
|
||||||
ObjectiveC.objc_msgSend(this, initWithData, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSImage(BufferedImage image) throws IOException {
|
|
||||||
this(ImageUtil.toBytes(image));
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSImage(byte[] imageBytes) {
|
|
||||||
this(new NSData(imageBytes));
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSImage(final File file) {
|
|
||||||
super(ObjectiveC.class_createInstance(objectClass, 0));
|
|
||||||
ObjectiveC.objc_msgSend(this, initWithContentsOfFile, new NSString(file.getAbsolutePath()));
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,34 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import com.sun.jna.NativeLong;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/foundation/nsnumber?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSInteger extends NativeLong {
|
|
||||||
|
|
||||||
public
|
|
||||||
NSInteger() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSInteger(long value) {
|
|
||||||
super(value);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,114 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/appkit/nsmenu?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSMenu extends NSObject {
|
|
||||||
|
|
||||||
private static final Pointer objectClass = ObjectiveC.objc_lookUpClass("NSMenu");
|
|
||||||
|
|
||||||
private static final Pointer addItem = ObjectiveC.sel_getUid("addItem:");
|
|
||||||
private static final Pointer removeItem = ObjectiveC.sel_getUid("removeItem:");
|
|
||||||
private static final Pointer setAutoenablesItems = ObjectiveC.sel_getUid("setAutoenablesItems:");
|
|
||||||
private static final Pointer itemAtIndex = ObjectiveC.sel_getUid("itemAtIndex:");
|
|
||||||
private static final Pointer insertItemAtIndex = ObjectiveC.sel_getUid("insertItem:atIndex:");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSMenu() {
|
|
||||||
super(ObjectiveC.class_createInstance(objectClass, 0));
|
|
||||||
|
|
||||||
// make this part of the constructor. By default, we want to have items automatically enabled
|
|
||||||
setAutoEnablesItems(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds a menu item to the end of the menu.
|
|
||||||
* <p>
|
|
||||||
* NOTE: This method invokes insertItem(_:at:). Thus, the menu does not accept the
|
|
||||||
* menu item if it already belongs to another menu. After adding the menu item, the menu updates itself.
|
|
||||||
*
|
|
||||||
* @param newItem The menu item (an object conforming to the NSMenuItem protocol) to add to the menu.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void addItem(NSMenuItem newItem) {
|
|
||||||
ObjectiveC.objc_msgSend(this, addItem, newItem);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Inserts a menu item into the menu at a specific location.
|
|
||||||
* <p>
|
|
||||||
* NOTE: This method posts an NSMenuDidAddItemNotification, allowing
|
|
||||||
* interested observers to update as appropriate. This method is a primitive
|
|
||||||
* method. All item-addition methods end up calling this method, so this is
|
|
||||||
* where you should implement custom behavior on adding new items to a menu
|
|
||||||
* in a custom subclass. If the menu item already exists in another menu, it
|
|
||||||
* is not inserted and the method raises an exception of type
|
|
||||||
* NSInternalInconsistencyException.
|
|
||||||
*
|
|
||||||
* @param newItem An object conforming to the NSMenuItem protocol that represents a menu item.
|
|
||||||
* @param index An integer index identifying the location of the menu item in the menu.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void insertItemAtIndex(NSMenuItem newItem, int index) {
|
|
||||||
ObjectiveC.objc_msgSend(this, insertItemAtIndex, newItem, index);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the menu item at a specific location of the menu.
|
|
||||||
*
|
|
||||||
* @param index An integer index locating a menu item in a menu.
|
|
||||||
*
|
|
||||||
* @return The found menu item (an object conforming to the NSMenuItem protocol) or nil if the object couldn't be found.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
NSMenuItem itemAtIndex(int index) {
|
|
||||||
return new NSMenuItem(ObjectiveC.objc_msgSend(this, itemAtIndex, index));
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Indicates whether the menu automatically enables and disables its menu items.
|
|
||||||
* <p>
|
|
||||||
* This property contains a Boolean value, indicating whether the menu automatically
|
|
||||||
* enables and disables its menu items. If set to true, menu items of the menu are automatically
|
|
||||||
* enabled and disabled according to rules computed by the NSMenuValidation informal protocol.
|
|
||||||
* By default, NSMenu objects autoenable their menu items.
|
|
||||||
*
|
|
||||||
* @param enable true to enable the items by default, false to disable items by default
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setAutoEnablesItems(boolean enable) {
|
|
||||||
// WEIRDLY enough, the logic is backwards...
|
|
||||||
ObjectiveC.objc_msgSend(this, setAutoenablesItems, !enable);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Removes a menu item from the menu.
|
|
||||||
*
|
|
||||||
* @param anItem The menu item to remove.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void removeItem(final NSMenuItem anItem) {
|
|
||||||
ObjectiveC.objc_msgSend(this, removeItem, anItem);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,163 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/appkit/nsmenuitem?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSMenuItem extends NSObject {
|
|
||||||
|
|
||||||
private static final Pointer objectClass = ObjectiveC.objc_lookUpClass("NSMenuItem");
|
|
||||||
|
|
||||||
private static final Pointer setTitle = ObjectiveC.sel_getUid("setTitle:");
|
|
||||||
private static final Pointer toolTip = ObjectiveC.sel_getUid("toolTip");
|
|
||||||
private static final Pointer setKeyEquivalent = ObjectiveC.sel_getUid("setKeyEquivalent:");
|
|
||||||
|
|
||||||
private static final Pointer setIndentationLevel = ObjectiveC.sel_getUid("setIndentationLevel:");
|
|
||||||
|
|
||||||
private static final Pointer setImage = ObjectiveC.sel_getUid("setImage:");
|
|
||||||
private static final Pointer setOnStateImage = ObjectiveC.sel_getUid("setOnStateImage:");
|
|
||||||
private static final Pointer setEnabled = ObjectiveC.sel_getUid("setEnabled:");
|
|
||||||
private static final Pointer separatorItem = ObjectiveC.sel_getUid("separatorItem");
|
|
||||||
|
|
||||||
private static final Pointer setSubmenu = ObjectiveC.sel_getUid("setSubmenu:");
|
|
||||||
|
|
||||||
private static final Pointer setState = ObjectiveC.sel_getUid("setState:");
|
|
||||||
private static final Pointer setTarget = ObjectiveC.sel_getUid("setTarget:");
|
|
||||||
private static final Pointer setAction = ObjectiveC.sel_getUid("setAction:");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSMenuItem() {
|
|
||||||
super(ObjectiveC.class_createInstance(objectClass, 0));
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSMenuItem(long peer) {
|
|
||||||
super(peer);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A menu item that is used to separate logical groups of menu commands.
|
|
||||||
* <p>
|
|
||||||
* NOTE: This menu item is disabled. The default separator item is blank space.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
NSMenuItem separatorItem() {
|
|
||||||
return new NSMenuItem(ObjectiveC.objc_msgSend(objectClass, separatorItem));
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The menu item's title.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setTitle(NSString title) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setTitle, title);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return the menu item's title.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
NSString setToolTip(NSString tooltip) {
|
|
||||||
return new NSString(ObjectiveC.objc_msgSend(this, toolTip, tooltip));
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the menu item indentation level for the menu item.
|
|
||||||
*
|
|
||||||
* @param indentationLevel Value is from 0 to 15. The default indentation level is 0.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setIndentationLevel(NSInteger indentationLevel) {
|
|
||||||
ObjectiveC.objc_msgSend(this, NSMenuItem.setIndentationLevel, indentationLevel);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The menu item's shortcut key, if it's a capital letter, then it's a capital letter required for the shortcut
|
|
||||||
* <p>
|
|
||||||
* https://developer.apple.com/library/archive/documentation/Cocoa/Conceptual/Button/Tasks/SettingButtonKeyEquiv.html
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setKeyEquivalent(NSString characters) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setKeyEquivalent, characters);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The menu item’s image.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setImage(NSImage image) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setImage, image);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The menu item’s image.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setOnStateImage(NSImage image) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setOnStateImage, image);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A Boolean value that indicates whether the menu item is enabled.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setEnabled(boolean enabled) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setEnabled, enabled);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The submenu of the menu item.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setSubmenu(NSMenu submenu) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setSubmenu, submenu);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The state of the menu item.
|
|
||||||
* <p>
|
|
||||||
* NOTE: The image associated with the new state is displayed to the left of the menu item.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setState(int state) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setState, state);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The menu item's target.
|
|
||||||
* <p>
|
|
||||||
* NOTE: To ensure that a menu item’s target can receive commands while a
|
|
||||||
* modal dialog is open, the target object should return YES in worksWhenModal.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setTarget(NSObject target) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setTarget, target);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The menu item's action-method selector.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
void setAction(Pointer pointer) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setAction, pointer);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,73 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/objectivec/nsobject?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSObject extends Pointer {
|
|
||||||
public static final Pointer objectClass = ObjectiveC.objc_lookUpClass("NSObject");
|
|
||||||
|
|
||||||
private static final Pointer alloc = ObjectiveC.sel_getUid("alloc");
|
|
||||||
private static final Pointer retain = ObjectiveC.sel_getUid("retain");
|
|
||||||
private static final Pointer release = ObjectiveC.sel_getUid("release");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSObject(long peer) {
|
|
||||||
super(peer);
|
|
||||||
|
|
||||||
retain();
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSObject(Pointer pointer) {
|
|
||||||
this(Pointer.nativeValue(pointer));
|
|
||||||
}
|
|
||||||
|
|
||||||
protected
|
|
||||||
void finalize() throws Throwable {
|
|
||||||
release();
|
|
||||||
|
|
||||||
super.finalize();
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void alloc() {
|
|
||||||
ObjectiveC.objc_msgSend(this, alloc);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public
|
|
||||||
void retain() {
|
|
||||||
ObjectiveC.objc_msgSend(this, retain);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void release() {
|
|
||||||
ObjectiveC.objc_msgSend(this, release);
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressWarnings("WeakerAccess")
|
|
||||||
public
|
|
||||||
long asPointer() {
|
|
||||||
return Pointer.nativeValue(this);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,56 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/appkit/nsstatusbar?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSStatusBar extends NSObject {
|
|
||||||
|
|
||||||
public final static double NSVariableStatusItemLength = -1; // can specify exactly how wide to make the space
|
|
||||||
public final static double NSSquareStatusItemLength = -2; // the space will be a square
|
|
||||||
|
|
||||||
static Pointer objectClass = ObjectiveC.objc_lookUpClass("NSStatusBar");
|
|
||||||
|
|
||||||
static Pointer systemStatusBar = ObjectiveC.sel_getUid("systemStatusBar");
|
|
||||||
static Pointer statusItemWithLength = ObjectiveC.sel_getUid("statusItemWithLength:");
|
|
||||||
static Pointer removeStatusItem = ObjectiveC.sel_getUid("removeStatusItem:");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSStatusBar(long peer) {
|
|
||||||
super(peer);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static
|
|
||||||
NSStatusBar systemStatusBar() {
|
|
||||||
return new NSStatusBar(ObjectiveC.objc_msgSend(objectClass, systemStatusBar));
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSStatusItem newStatusItem() {
|
|
||||||
return new NSStatusItem(ObjectiveC.objc_msgSend(this, statusItemWithLength, NSStatusBar.NSSquareStatusItemLength));
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void removeStatusItem(NSStatusItem statusItem) {
|
|
||||||
ObjectiveC.objc_msgSend(this, removeStatusItem, statusItem);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,57 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/appkit/nsstatusitem?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSStatusItem extends NSObject {
|
|
||||||
|
|
||||||
private static final Pointer setHighlightMode = ObjectiveC.sel_getUid("setHighlightMode:");
|
|
||||||
private static final Pointer setToolTip = ObjectiveC.sel_getUid("setToolTip:");
|
|
||||||
private static final Pointer setMenu = ObjectiveC.sel_getUid("setMenu:");
|
|
||||||
private static final Pointer setImage = ObjectiveC.sel_getUid("setImage:");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSStatusItem(long peer) {
|
|
||||||
super(peer);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void setHighlightMode(boolean highlight) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setHighlightMode, highlight);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void setImage(NSImage image) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setImage, image);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void setMenu(NSMenu menu) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setMenu, menu);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void setToolTip(NSString tooltip) {
|
|
||||||
ObjectiveC.objc_msgSend(this, setToolTip, tooltip);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,57 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import java.nio.charset.Charset;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.macos.foundation.ObjectiveC;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://developer.apple.com/documentation/foundation/nsstring?language=objc
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class NSString extends NSObject {
|
|
||||||
private static final Charset UTF8 = Charset.forName("UTF-8");
|
|
||||||
|
|
||||||
static
|
|
||||||
Object asBytes(String string) {
|
|
||||||
return (string + "\0").getBytes(UTF8);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
private static final Pointer objectClass = ObjectiveC.objc_lookUpClass("NSString");
|
|
||||||
|
|
||||||
private static final Pointer stringWithUTF8String = ObjectiveC.sel_getUid("stringWithUTF8String:");
|
|
||||||
private static final Pointer UTF8String = ObjectiveC.sel_getUid("UTF8String");
|
|
||||||
|
|
||||||
public
|
|
||||||
NSString(long peer) {
|
|
||||||
super(peer);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
NSString(String string) {
|
|
||||||
this(ObjectiveC.objc_msgSend(objectClass, stringWithUTF8String, asBytes(string)));
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
String toString() {
|
|
||||||
long pointerReference = ObjectiveC.objc_msgSend(this, UTF8String);
|
|
||||||
return new Pointer(pointerReference).getString(0);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,24 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.cocoa;
|
|
||||||
|
|
||||||
import dorkbox.util.Keep;
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
public
|
|
||||||
interface OsxClickCallback {
|
|
||||||
void click();
|
|
||||||
}
|
|
@ -1,157 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2018 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.macos.foundation;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.Library;
|
|
||||||
import com.sun.jna.Native;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* "how to" from: https://gist.github.com/3974488
|
|
||||||
* <p>
|
|
||||||
* https://developer.apple.com/documentation/objectivec/objective-c_runtime
|
|
||||||
* <p>
|
|
||||||
* We cannot use JNA "direct mapping", because direct mapping DOES NOT support var-args (which `objc_msgSend` requires)
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class ObjectiveC {
|
|
||||||
interface Objc extends Library {
|
|
||||||
Pointer objc_lookUpClass(String name);
|
|
||||||
|
|
||||||
long objc_msgSend(Pointer theReceiver, Pointer theSelector, Object... string);
|
|
||||||
|
|
||||||
Pointer objc_allocateClassPair(Pointer superClass, String name, long extraBytes);
|
|
||||||
|
|
||||||
void objc_registerClassPair(Pointer clazz);
|
|
||||||
|
|
||||||
Pointer class_createInstance(Pointer clazz, int extraBytes);
|
|
||||||
|
|
||||||
boolean class_addMethod(Pointer clazz, Pointer selector, Callback callback, String types);
|
|
||||||
|
|
||||||
Pointer sel_getUid(String name);
|
|
||||||
|
|
||||||
Pointer sel_registerName(String name);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static final Objc INSTANCE = Native.loadLibrary("objc", Objc.class);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the class definition of a specified class.
|
|
||||||
*
|
|
||||||
* @param name The name of the class to look up.
|
|
||||||
*
|
|
||||||
* @return The Class object for the named class, or nil if the class is not registered with the Objective-C runtime.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
Pointer objc_lookUpClass(String name) {
|
|
||||||
return INSTANCE.objc_lookUpClass(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sends a message with a simple return value to an instance of a class.
|
|
||||||
*
|
|
||||||
* @param self A pointer that points to the instance of the class that is to receive the message.
|
|
||||||
* @param op The selector of the method that handles the message.
|
|
||||||
* @param args A variable argument list containing the arguments to the method.
|
|
||||||
*
|
|
||||||
* @return The return value of the method.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
long objc_msgSend(Pointer self, Pointer op, Object... args) {
|
|
||||||
return INSTANCE.objc_msgSend(self, op, args);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new class and metaclass.
|
|
||||||
*
|
|
||||||
* @param superClass The class to use as the new class's superclass, or Nil to create a new root class.
|
|
||||||
* @param name The string to use as the new class's name. The string will be copied.
|
|
||||||
* @param extraBytes The number of bytes to allocate for indexed ivars at the end of the class and metaclass objects. This should usually be 0.
|
|
||||||
*
|
|
||||||
* @return The new class, or Nil if the class could not be created (for example, the desired name is already in use).
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
Pointer objc_allocateClassPair(Pointer superClass, String name, long extraBytes) {
|
|
||||||
return INSTANCE.objc_allocateClassPair(superClass, name, extraBytes);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Registers a class that was allocated using objc_allocateClassPair.
|
|
||||||
*
|
|
||||||
* @param cls The class you want to register.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
void objc_registerClassPair(Pointer cls) {
|
|
||||||
INSTANCE.objc_registerClassPair(cls);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates an instance of a class, allocating memory for the class in the default malloc memory zone.
|
|
||||||
*
|
|
||||||
* @param cls The class that you want to allocate an instance of.
|
|
||||||
* @param extraBytes An integer indicating the number of extra bytes to allocate. The additional bytes can be used to store additional instance variables beyond those defined in the class definition.
|
|
||||||
*
|
|
||||||
* @return An instance of the class cls.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
Pointer class_createInstance(Pointer cls, int extraBytes) {
|
|
||||||
return INSTANCE.class_createInstance(cls, extraBytes);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds a new method to a class with a given name and implementation.
|
|
||||||
* NOTE: class_addMethod will add an override of a superclass's implementation, but will not replace an existing implementation in this class. To change an existing implementation, use method_setImplementation.
|
|
||||||
*
|
|
||||||
* @param cls The class to which to add a method.
|
|
||||||
* @param name A selector that specifies the name of the method being added.
|
|
||||||
* @param imp A function which is the implementation of the new method. The function must take at least two arguments—self and _cmd.
|
|
||||||
* @param types An array of characters that describe the types of the arguments to the method. For possible values, see Objective-C Runtime Programming Guide > Type Encodings. Since the function must take at least two arguments—self and _cmd, the second and third characters must be “@:” (the first character is the return type).
|
|
||||||
*
|
|
||||||
* @return YES if the method was added successfully, otherwise NO (for example, the class already contains a method implementation with that name).
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
boolean class_addMethod(Pointer cls, Pointer name, Callback imp, String types) {
|
|
||||||
return INSTANCE.class_addMethod(cls, name, imp, types);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Registers a method name with the Objective-C runtime system.
|
|
||||||
* NOTE: The implementation of this method is identical to the implementation of sel_registerName.
|
|
||||||
*
|
|
||||||
* @param str A pointer to a C string. Pass the name of the method you wish to register.
|
|
||||||
*
|
|
||||||
* @return A pointer of type SEL specifying the selector for the named method.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
Pointer sel_getUid(String str) {
|
|
||||||
return INSTANCE.sel_getUid(str);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Registers a method with the Objective-C runtime system, maps the method name to a selector, and returns the selector value.
|
|
||||||
* NOTE: You must register a method name with the Objective-C runtime system to obtain the method’s selector before you can add the method to a class definition. If the method name has already been registered, this function simply returns the selector.
|
|
||||||
*
|
|
||||||
* @param str A pointer to a C string. Pass the name of the method you wish to register.
|
|
||||||
*
|
|
||||||
* @return A pointer of type SEL specifying the selector for the named method.
|
|
||||||
*/
|
|
||||||
public static
|
|
||||||
Pointer sel_registerName(String str) {
|
|
||||||
return INSTANCE.sel_registerName(str);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,95 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HBITMAP;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HDC;
|
|
||||||
import static com.sun.jna.platform.win32.WinGDI.BITMAPINFO;
|
|
||||||
import static com.sun.jna.platform.win32.WinNT.HANDLE;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.ptr.PointerByReference;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
|
|
||||||
public
|
|
||||||
class GDI32 {
|
|
||||||
static {
|
|
||||||
JnaHelper.register("GDI32", GDI32.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The CreateCompatibleDC function creates a memory device context (DC) compatible with the specified device.
|
|
||||||
*
|
|
||||||
* @param hDC Handle to an existing DC. If this handle is NULL, the function creates a memory DC compatible with the
|
|
||||||
* application's current screen.
|
|
||||||
*
|
|
||||||
* @return If the function succeeds, the return value is the handle to a memory DC.
|
|
||||||
* If the function fails, the return value is NULL.
|
|
||||||
* To get extended error information, call GetLastError.
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
HDC CreateCompatibleDC(HDC hDC);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The DeleteDC function deletes the specified device context (DC).
|
|
||||||
*
|
|
||||||
* @param hDC Handle to the device context.
|
|
||||||
*
|
|
||||||
* @return If the function succeeds, the return value is nonzero.
|
|
||||||
* If the function fails, the return value is zero.
|
|
||||||
* To get extended error information, call GetLastError.
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
boolean DeleteDC(HDC hDC);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The DeleteObject function deletes a logical pen, brush, font, bitmap, region, or palette,
|
|
||||||
* freeing all system resources associated with the object. After the object is deleted, the
|
|
||||||
* specified handle is no longer valid.
|
|
||||||
*
|
|
||||||
* @param hObject Handle to a logical pen, brush, font, bitmap, region, or palette.
|
|
||||||
*
|
|
||||||
* @return If the function succeeds, the return value is nonzero.
|
|
||||||
* If the specified handle is not valid or is currently selected into a DC, the return value is zero.
|
|
||||||
* To get extended error information, call GetLastError.
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
boolean DeleteObject(HANDLE hObject);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The CreateDIBSection function creates a DIB that applications can write to directly.
|
|
||||||
* The function gives you a pointer to the location of the bitmap bit values. You can supply
|
|
||||||
* a handle to a file-mapping object that the function will use to create the bitmap, or you
|
|
||||||
* can let the system allocate the memory for the bitmap.
|
|
||||||
*
|
|
||||||
* @param hDC Handle to a device context. If the value of iUsage is DIB_PAL_COLORS, the function uses this
|
|
||||||
* device context's logical palette to initialize the DIB colors.
|
|
||||||
* @param pbmi Pointer to a BITMAPINFO structure that specifies various attributes of the DIB, including
|
|
||||||
* the bitmap dimensions and colors.
|
|
||||||
* @param iUsage Specifies the type of data contained in the bmiColors array member of the BITMAPINFO structure
|
|
||||||
* pointed to by pbmi (either logical palette indexes or literal RGB values).
|
|
||||||
* @param ppvBits Pointer to a variable that receives a pointer to the location of the DIB bit values.
|
|
||||||
* @param hSection Handle to a file-mapping object that the function will use to create the DIB. This parameter can be NULL.
|
|
||||||
* @param dwOffset Specifies the offset from the beginning of the file-mapping object referenced by hSection where storage
|
|
||||||
* for the bitmap bit values is to begin.
|
|
||||||
*
|
|
||||||
* @return Specifies the offset from the beginning of the file-mapping object referenced by hSection where storage
|
|
||||||
* for the bitmap bit values is to begin.
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
HBITMAP CreateDIBSection(HDC hDC, BITMAPINFO pbmi, int iUsage, PointerByReference ppvBits, Pointer hSection, int dwOffset);
|
|
||||||
}
|
|
@ -1,35 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import com.sun.jna.platform.win32.Kernel32Util;
|
|
||||||
|
|
||||||
public
|
|
||||||
class GetLastErrorException extends RuntimeException {
|
|
||||||
private static final long serialVersionUID = 3980497906900380359L;
|
|
||||||
|
|
||||||
private String message;
|
|
||||||
|
|
||||||
public
|
|
||||||
GetLastErrorException() {
|
|
||||||
message = Kernel32Util.getLastErrorMessage();
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
String toString() {
|
|
||||||
return message;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,122 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HBITMAP;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HDC;
|
|
||||||
import static dorkbox.util.jna.windows.User32.User32;
|
|
||||||
|
|
||||||
import java.awt.AlphaComposite;
|
|
||||||
import java.awt.Graphics2D;
|
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
import java.awt.image.Raster;
|
|
||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.Memory;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.platform.win32.Kernel32Util;
|
|
||||||
import com.sun.jna.platform.win32.WinGDI;
|
|
||||||
import com.sun.jna.ptr.PointerByReference;
|
|
||||||
|
|
||||||
public class HBITMAPWrap extends HBITMAP {
|
|
||||||
|
|
||||||
// NOTE: This is a field (instead of private) so that GC does not try to collect this object
|
|
||||||
private HBITMAP bitmap;
|
|
||||||
|
|
||||||
// https://github.com/twall/jna/blob/master/contrib/alphamaskdemo/com/sun/jna/contrib/demo/AlphaMaskDemo.java
|
|
||||||
private static
|
|
||||||
HBITMAP createBitmap(BufferedImage image) {
|
|
||||||
int w = image.getWidth(null);
|
|
||||||
int h = image.getHeight(null);
|
|
||||||
HDC screenDC = User32.GetDC(null);
|
|
||||||
HDC memDC = GDI32.CreateCompatibleDC(screenDC);
|
|
||||||
HBITMAP hBitmap = null;
|
|
||||||
|
|
||||||
try {
|
|
||||||
BufferedImage buf = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB_PRE);
|
|
||||||
Graphics2D g = (Graphics2D) buf.getGraphics();
|
|
||||||
g.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
|
|
||||||
g.drawImage(image, 0, 0, w, h, null);
|
|
||||||
|
|
||||||
WinGDI.BITMAPINFO bmi = new WinGDI.BITMAPINFO();
|
|
||||||
bmi.bmiHeader.biWidth = w;
|
|
||||||
bmi.bmiHeader.biHeight = h;
|
|
||||||
bmi.bmiHeader.biPlanes = 1;
|
|
||||||
bmi.bmiHeader.biBitCount = 32;
|
|
||||||
bmi.bmiHeader.biCompression = WinGDI.BI_RGB;
|
|
||||||
bmi.bmiHeader.biSizeImage = w * h * 4;
|
|
||||||
|
|
||||||
Memory memory = new Memory(w*h*32*4);
|
|
||||||
PointerByReference pointerRef = new PointerByReference(memory);
|
|
||||||
hBitmap = GDI32.CreateDIBSection(memDC, bmi, WinGDI.DIB_RGB_COLORS, pointerRef, null, 0);
|
|
||||||
Pointer pointerToBits = pointerRef.getValue();
|
|
||||||
|
|
||||||
if (pointerToBits == null) {
|
|
||||||
// the bitmap was invalid
|
|
||||||
LoggerFactory.getLogger(HBITMAPWrap.class).error("The image was invalid", Kernel32Util.getLastErrorMessage());
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
Raster raster = buf.getData();
|
|
||||||
int[] pixel = new int[4];
|
|
||||||
int[] bits = new int[w * h];
|
|
||||||
for (int y = 0; y < h; y++) {
|
|
||||||
for (int x = 0; x < w; x++) {
|
|
||||||
raster.getPixel(x, h - y - 1, pixel);
|
|
||||||
int red = (pixel[2] & 0xFF) << 0;
|
|
||||||
int green = (pixel[1] & 0xFF) << 8;
|
|
||||||
int blue = (pixel[0] & 0xFF) << 16;
|
|
||||||
int alpha = (pixel[3] & 0xFF) << 24;
|
|
||||||
bits[x + y * w] = alpha | red | green | blue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
pointerToBits.write(0, bits, 0, bits.length);
|
|
||||||
}
|
|
||||||
|
|
||||||
return hBitmap;
|
|
||||||
} finally {
|
|
||||||
User32.ReleaseDC(null, screenDC);
|
|
||||||
GDI32.DeleteDC(memDC);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
BufferedImage img;
|
|
||||||
|
|
||||||
public HBITMAPWrap(BufferedImage img) {
|
|
||||||
bitmap = createBitmap(img);
|
|
||||||
setPointer(bitmap.getPointer());
|
|
||||||
|
|
||||||
this.img = img;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void finalize() throws Throwable {
|
|
||||||
close();
|
|
||||||
super.finalize();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() {
|
|
||||||
if (Pointer.nativeValue(getPointer()) != 0) {
|
|
||||||
GDI32.DeleteObject(this);
|
|
||||||
setPointer(new Pointer(0));
|
|
||||||
bitmap = null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public BufferedImage getImage() {
|
|
||||||
return img;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,73 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HBITMAP;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HICON;
|
|
||||||
import static dorkbox.util.jna.windows.User32.User32;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.windows.structs.ICONINFO;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://www.pinvoke.net/default.aspx/user32.createiconindirect
|
|
||||||
*/
|
|
||||||
public class HICONWrap extends HICON {
|
|
||||||
|
|
||||||
static HICON createIconIndirect(HBITMAP bm) {
|
|
||||||
ICONINFO info = new ICONINFO();
|
|
||||||
info.IsIcon = true;
|
|
||||||
info.MaskBitmap = bm;
|
|
||||||
info.ColorBitmap = bm;
|
|
||||||
|
|
||||||
HICON hicon = User32.CreateIconIndirect(info);
|
|
||||||
if (hicon == null) {
|
|
||||||
throw new GetLastErrorException();
|
|
||||||
}
|
|
||||||
|
|
||||||
return hicon;
|
|
||||||
}
|
|
||||||
|
|
||||||
private HBITMAPWrap bm;
|
|
||||||
|
|
||||||
public HICONWrap() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public HICONWrap(Pointer p) {
|
|
||||||
super(p);
|
|
||||||
}
|
|
||||||
|
|
||||||
public HICONWrap(HBITMAPWrap bm) {
|
|
||||||
this.bm = bm;
|
|
||||||
setPointer(createIconIndirect(bm).getPointer());
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() {
|
|
||||||
bm.close();
|
|
||||||
|
|
||||||
if (Pointer.nativeValue(getPointer()) != 0) {
|
|
||||||
GDI32.DeleteObject(this);
|
|
||||||
setPointer(new Pointer(0));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void finalize() throws Throwable {
|
|
||||||
close();
|
|
||||||
super.finalize();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,137 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinNT.HANDLE;
|
|
||||||
|
|
||||||
import com.sun.jna.platform.win32.Kernel32Util;
|
|
||||||
import com.sun.jna.ptr.IntByReference;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
import dorkbox.util.jna.windows.structs.CONSOLE_SCREEN_BUFFER_INFO;
|
|
||||||
import dorkbox.util.jna.windows.structs.COORD;
|
|
||||||
import dorkbox.util.jna.windows.structs.INPUT_RECORD;
|
|
||||||
import dorkbox.util.jna.windows.structs.SMALL_RECT;
|
|
||||||
|
|
||||||
public
|
|
||||||
class Kernel32 {
|
|
||||||
static {
|
|
||||||
JnaHelper.register("kernel32", Kernel32.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
// see: http://msdn.microsoft.com/en-us/library/ms682013%28VS.85%29.aspx
|
|
||||||
public static final short FOREGROUND_BLACK = (short) 0x0000;
|
|
||||||
public static final short FOREGROUND_BLUE = (short) 0x0001;
|
|
||||||
public static final short FOREGROUND_GREEN = (short) 0x0002;
|
|
||||||
public static final short FOREGROUND_CYAN = (short) 0x0003;
|
|
||||||
public static final short FOREGROUND_RED = (short) 0x0004;
|
|
||||||
public static final short FOREGROUND_MAGENTA = (short) 0x0005;
|
|
||||||
public static final short FOREGROUND_YELLOW = (short) 0x0006;
|
|
||||||
public static final short FOREGROUND_GREY = (short) 0x0007;
|
|
||||||
public static final short FOREGROUND_INTENSITY = (short) 0x0008; // foreground color is intensified.
|
|
||||||
|
|
||||||
public static final short BACKGROUND_BLACK = (short) 0x0000;
|
|
||||||
public static final short BACKGROUND_BLUE = (short) 0x0010;
|
|
||||||
public static final short BACKGROUND_GREEN = (short) 0x0020;
|
|
||||||
public static final short BACKGROUND_CYAN = (short) 0x0030;
|
|
||||||
public static final short BACKGROUND_RED = (short) 0x0040;
|
|
||||||
public static final short BACKGROUND_MAGENTA = (short) 0x0050;
|
|
||||||
public static final short BACKGROUND_YELLOW = (short) 0x0060;
|
|
||||||
public static final short BACKGROUND_GREY = (short) 0x0070;
|
|
||||||
public static final short BACKGROUND_INTENSITY = (short) 0x0080; // background color is intensified.
|
|
||||||
|
|
||||||
|
|
||||||
public static final short COMMON_LVB_LEADING_BYTE = (short) 0x0100;
|
|
||||||
public static final short COMMON_LVB_TRAILING_BYTE = (short) 0x0200;
|
|
||||||
public static final short COMMON_LVB_GRID_HORIZONTAL = (short) 0x0400;
|
|
||||||
public static final short COMMON_LVB_GRID_LVERTICAL = (short) 0x0800;
|
|
||||||
public static final short COMMON_LVB_GRID_RVERTICAL = (short) 0x1000;
|
|
||||||
public static final short COMMON_LVB_REVERSE_VIDEO = (short) 0x4000;
|
|
||||||
public static final short COMMON_LVB_UNDERSCORE = (short) 0x8000;
|
|
||||||
|
|
||||||
public static final int FORMAT_MESSAGE_FROM_SYSTEM = 0x1000;
|
|
||||||
|
|
||||||
public static void ASSERT(final int returnValue, final String message) {
|
|
||||||
// if returnValue == 0, throw assertion error
|
|
||||||
assert returnValue != 0 : message + " : " + Kernel32Util.getLastErrorMessage();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms683231%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
HANDLE GetStdHandle(int stdHandle);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms724211%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int CloseHandle(HANDLE handle);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms686047%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int SetConsoleTextAttribute(HANDLE consoleOutput, short attributes);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms683171%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int GetConsoleScreenBufferInfo(HANDLE consoleOutput, CONSOLE_SCREEN_BUFFER_INFO consoleScreenBufferInfo);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/windows/desktop/ms686025(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int SetConsoleCursorPosition(HANDLE consoleOutput, COORD.ByValue cursorPosition);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/windows/desktop/ms685107(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int ScrollConsoleScreenBuffer(HANDLE consoleOutput, SMALL_RECT.ByReference scrollRect, SMALL_RECT.ByReference clipRect, COORD.ByValue destinationOrigin, IntByReference fillAttributes);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms682662%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int FillConsoleOutputAttribute(HANDLE consoleOutput, short attribute, int length, COORD.ByValue writeCoord, IntByReference numberOfAttrsWritten);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms682663%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int FillConsoleOutputCharacter(HANDLE consoleOutput, char character, int length, COORD.ByValue writeCoord, IntByReference numberOfCharsWritten);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms683167%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int GetConsoleMode(HANDLE handle, IntByReference mode);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms686033%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int SetConsoleMode(HANDLE handle, int mode);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms684961(v=VS.85).aspx
|
|
||||||
*/
|
|
||||||
public static native
|
|
||||||
int ReadConsoleInput(HANDLE handle, INPUT_RECORD.ByReference inputRecords, int length, IntByReference eventsCount);
|
|
||||||
}
|
|
@ -1,28 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HWND;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LPARAM;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.WPARAM;
|
|
||||||
|
|
||||||
public
|
|
||||||
class Listener {
|
|
||||||
public
|
|
||||||
void run(HWND hWnd, WPARAM wParam, LPARAM lParam) {
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,39 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
public
|
|
||||||
class MSG extends Structure {
|
|
||||||
public Pointer hWnd;
|
|
||||||
public int message;
|
|
||||||
public Parameter wParam;
|
|
||||||
public Parameter lParam;
|
|
||||||
public int time;
|
|
||||||
public int x;
|
|
||||||
public int y;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("hWnd", "message", "wParam", "lParam", "time", "x", "y");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,17 +0,0 @@
|
|||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import com.sun.jna.IntegerType;
|
|
||||||
import com.sun.jna.Native;
|
|
||||||
|
|
||||||
public
|
|
||||||
class Parameter extends IntegerType {
|
|
||||||
public
|
|
||||||
Parameter() {
|
|
||||||
this(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
Parameter(long value) {
|
|
||||||
super(Native.POINTER_SIZE, value);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,33 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
import dorkbox.util.jna.windows.structs.NOTIFYICONDATA;
|
|
||||||
|
|
||||||
public
|
|
||||||
class Shell32 {
|
|
||||||
static {
|
|
||||||
JnaHelper.register("shell32", Shell32.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
static public final int NIM_ADD = 0x0;
|
|
||||||
static public final int NIM_MODIFY = 0x1;
|
|
||||||
static public final int NIM_DELETE = 0x2;
|
|
||||||
|
|
||||||
public static native
|
|
||||||
boolean Shell_NotifyIcon(int dwMessage, NOTIFYICONDATA lpdata);
|
|
||||||
}
|
|
@ -1,168 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2015 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HDC;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HICON;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HINSTANCE;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HMENU;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HWND;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LPARAM;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LRESULT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.POINT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.WPARAM;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.WString;
|
|
||||||
import com.sun.jna.platform.win32.WinNT;
|
|
||||||
|
|
||||||
import dorkbox.util.OS;
|
|
||||||
import dorkbox.util.jna.windows.structs.ICONINFO;
|
|
||||||
|
|
||||||
@SuppressWarnings("WeakerAccess")
|
|
||||||
public
|
|
||||||
interface User32 {
|
|
||||||
User32 User32 = OS.is64bit() ? new User32_64() : new User32_32();
|
|
||||||
|
|
||||||
int GWL_WNDPROC = -4;
|
|
||||||
|
|
||||||
int WM_LBUTTONUP = 0x202;
|
|
||||||
int WM_RBUTTONUP = 0x205;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This is overridden by the 64-bit version to be SetWindowLongPtr instead.
|
|
||||||
*/
|
|
||||||
int SetWindowLong(HWND hWnd, int nIndex, Callback procedure);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The GetSystemMetrics function retrieves various system metrics (widths
|
|
||||||
* and heights of display elements) and system configuration settings. All
|
|
||||||
* dimensions retrieved by GetSystemMetrics are in pixels.
|
|
||||||
*
|
|
||||||
* @param nIndex System metric or configuration setting to retrieve. This
|
|
||||||
* parameter can be one of the following values. Note that all
|
|
||||||
* SM_CX* values are widths and all SM_CY* values are heights.
|
|
||||||
* Also note that all settings designed to return Boolean data
|
|
||||||
* represent TRUE as any nonzero value, and FALSE as a zero
|
|
||||||
* value.
|
|
||||||
*
|
|
||||||
* @return If the function succeeds, the return value is the requested
|
|
||||||
* system metric or configuration setting. If the function fails,
|
|
||||||
* the return value is zero. GetLastError does not provide extended
|
|
||||||
* error information.
|
|
||||||
*/
|
|
||||||
int GetSystemMetrics(int nIndex);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/ms644950(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
LRESULT SendMessage(HWND hWnd, int Msg, WPARAM wParam, LPARAM lParam);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/ms648062(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
HICON CreateIconIndirect(ICONINFO piconinfo);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/ms632682(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
boolean DestroyWindow(HWND hWnd);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This function places a message in the message queue associated with the
|
|
||||||
* thread that created the specified window and then returns without waiting
|
|
||||||
* for the thread to process the message. Messages in a message queue are
|
|
||||||
* retrieved by calls to the GetMessage or PeekMessage function.
|
|
||||||
*
|
|
||||||
* @param hWnd Handle to the window whose window procedure is to receive the
|
|
||||||
* message.
|
|
||||||
* @param msg Specifies the message to be posted.
|
|
||||||
* @param wParam Specifies additional message-specific information.
|
|
||||||
* @param lParam Specifies additional message-specific information.
|
|
||||||
*/
|
|
||||||
void PostMessage(HWND hWnd, int msg, WPARAM wParam, LPARAM lParam);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/ms632680(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
HWND CreateWindowEx(int dwExStyle,
|
|
||||||
String lpClassName,
|
|
||||||
String lpWindowName,
|
|
||||||
int dwStyle,
|
|
||||||
int x,
|
|
||||||
int y,
|
|
||||||
int nWidth,
|
|
||||||
int nHeight,
|
|
||||||
HWND hWndParent,
|
|
||||||
HMENU hMenu,
|
|
||||||
HINSTANCE hInstance,
|
|
||||||
WinNT.HANDLE lpParam);
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/ms644947(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
LRESULT DefWindowProc(HWND hWnd, int Msg, WPARAM wParam, LPARAM lParam);
|
|
||||||
|
|
||||||
boolean GetMessage(MSG lpMsg, Pointer hWnd, int wMsgFilterMin, int wMsgFilterMax);
|
|
||||||
|
|
||||||
boolean TranslateMessage(MSG lpMsg);
|
|
||||||
|
|
||||||
boolean DispatchMessage(MSG lpMsg);
|
|
||||||
|
|
||||||
int RegisterWindowMessage(WString lpString);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/windows/desktop/dd144871(v=vs.85).aspx
|
|
||||||
*
|
|
||||||
* This function retrieves a handle to a display device context (DC) for the
|
|
||||||
* client area of the specified window. The display device context can be
|
|
||||||
* used in subsequent graphics display interface (GDI) functions to draw in
|
|
||||||
* the client area of the window.
|
|
||||||
*
|
|
||||||
* @param hWnd Handle to the window whose device context is to be retrieved.
|
|
||||||
* If this value is NULL, GetDC retrieves the device context for
|
|
||||||
* the entire screen.
|
|
||||||
*
|
|
||||||
* @return The handle the device context for the specified window's client
|
|
||||||
* area indicates success. NULL indicates failure. To get extended
|
|
||||||
* error information, call GetLastError.
|
|
||||||
*/
|
|
||||||
HDC GetDC(HWND hWnd);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/windows/desktop/dd162920(v=vs.85).aspx
|
|
||||||
*
|
|
||||||
* This function releases a device context (DC), freeing it for use by other
|
|
||||||
* applications. The effect of ReleaseDC depends on the type of device
|
|
||||||
* context.
|
|
||||||
*
|
|
||||||
* @param hWnd Handle to the window whose device context is to be released.
|
|
||||||
* @param hDC Handle to the device context to be released.
|
|
||||||
*
|
|
||||||
* @return The return value specifies whether the device context is
|
|
||||||
* released. 1 indicates that the device context is released. Zero
|
|
||||||
* indicates that the device context is not released.
|
|
||||||
*/
|
|
||||||
int ReleaseDC(HWND hWnd, HDC hDC);
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/windows/desktop/ms648390(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
boolean GetCursorPos(POINT point);
|
|
||||||
}
|
|
@ -1,120 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HDC;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HICON;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HINSTANCE;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HMENU;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HWND;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LPARAM;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LRESULT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.POINT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.WPARAM;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.WString;
|
|
||||||
import com.sun.jna.platform.win32.WinNT;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
import dorkbox.util.jna.windows.structs.ICONINFO;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* On first glance, this appears to be unnecessary to have a DirectMapping class implement an interface - however this is so different
|
|
||||||
* methods can be overridden by the correct 64bit versions, otherwise multiple copies of this library would have to be loaded (one for
|
|
||||||
* "normal", and another for the "special case").
|
|
||||||
*
|
|
||||||
* Doing it this way greatly simplifies the API while maintaining Direct Mapping, at the cost of a slightly more complex code hierarchy.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class User32_32 implements User32 {
|
|
||||||
static {
|
|
||||||
JnaHelper.register("user32", User32_32.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
// is replaced by the 64bit version
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
int SetWindowLong(HWND hWnd, int nIndex, Callback procedure);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
int GetSystemMetrics(final int nIndex);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
LRESULT SendMessage(final HWND hWnd, final int Msg, final WPARAM wParam, final LPARAM lParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
HICON CreateIconIndirect(final ICONINFO piconinfo);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean DestroyWindow(final HWND hWnd);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void PostMessage(final HWND hWnd, final int msg, final WPARAM wParam, final LPARAM lParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
HWND CreateWindowEx(final int dwExStyle,
|
|
||||||
final String lpClassName,
|
|
||||||
final String lpWindowName,
|
|
||||||
final int dwStyle,
|
|
||||||
final int x,
|
|
||||||
final int y,
|
|
||||||
final int nWidth,
|
|
||||||
final int nHeight,
|
|
||||||
final HWND hWndParent,
|
|
||||||
final HMENU hMenu,
|
|
||||||
final HINSTANCE hInstance,
|
|
||||||
final WinNT.HANDLE lpParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
LRESULT DefWindowProc(final HWND hWnd, final int Msg, final WPARAM wParam, final LPARAM lParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean GetMessage(final MSG lpMsg, final Pointer hWnd, final int wMsgFilterMin, final int wMsgFilterMax);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean TranslateMessage(final MSG lpMsg);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean DispatchMessage(final MSG lpMsg);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
int RegisterWindowMessage(final WString lpString);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
HDC GetDC(final HWND hWnd);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
int ReleaseDC(final HWND hWnd, final HDC hDC);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean GetCursorPos(final POINT point);
|
|
||||||
}
|
|
@ -1,125 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HDC;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HICON;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HINSTANCE;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HMENU;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HWND;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LPARAM;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LRESULT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.POINT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.WPARAM;
|
|
||||||
|
|
||||||
import com.sun.jna.Callback;
|
|
||||||
import com.sun.jna.Pointer;
|
|
||||||
import com.sun.jna.WString;
|
|
||||||
import com.sun.jna.platform.win32.WinNT;
|
|
||||||
|
|
||||||
import dorkbox.util.jna.JnaHelper;
|
|
||||||
import dorkbox.util.jna.windows.structs.ICONINFO;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* On first glance, this appears to be unnecessary to have a DirectMapping class implement an interface - however this is so different
|
|
||||||
* methods can be overridden by the correct 64bit versions, otherwise multiple copies of this library would have to be loaded (one for
|
|
||||||
* "normal", and another for the "special case").
|
|
||||||
*
|
|
||||||
* Doing it this way greatly simplifies the API while maintaining Direct Mapping, at the cost of a slightly more complex code hierarchy.
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class User32_64 implements User32 {
|
|
||||||
static {
|
|
||||||
JnaHelper.register("user32", User32_64.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
int SetWindowLong(HWND hWnd, int nIndex, Callback procedure) {
|
|
||||||
return SetWindowLongPtr(hWnd, nIndex, procedure);
|
|
||||||
}
|
|
||||||
|
|
||||||
// should be used instead of SetWindowLong for 64 versions
|
|
||||||
public native
|
|
||||||
int SetWindowLongPtr(HWND hWnd, int nIndex, Callback procedure);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
int GetSystemMetrics(final int nIndex);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
LRESULT SendMessage(final HWND hWnd, final int Msg, final WPARAM wParam, final LPARAM lParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
HICON CreateIconIndirect(final ICONINFO piconinfo);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean DestroyWindow(final HWND hWnd);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
void PostMessage(final HWND hWnd, final int msg, final WPARAM wParam, final LPARAM lParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
HWND CreateWindowEx(final int dwExStyle,
|
|
||||||
final String lpClassName,
|
|
||||||
final String lpWindowName,
|
|
||||||
final int dwStyle,
|
|
||||||
final int x,
|
|
||||||
final int y,
|
|
||||||
final int nWidth,
|
|
||||||
final int nHeight,
|
|
||||||
final HWND hWndParent,
|
|
||||||
final HMENU hMenu,
|
|
||||||
final HINSTANCE hInstance,
|
|
||||||
final WinNT.HANDLE lpParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
LRESULT DefWindowProc(final HWND hWnd, final int Msg, final WPARAM wParam, final LPARAM lParam);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean GetMessage(final MSG lpMsg, final Pointer hWnd, final int wMsgFilterMin, final int wMsgFilterMax);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean TranslateMessage(final MSG lpMsg);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean DispatchMessage(final MSG lpMsg);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
int RegisterWindowMessage(final WString lpString);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
HDC GetDC(final HWND hWnd);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
int ReleaseDC(final HWND hWnd, final HDC hDC);
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public native
|
|
||||||
boolean GetCursorPos(final POINT point);
|
|
||||||
}
|
|
@ -1,28 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HWND;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LPARAM;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LRESULT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.WPARAM;
|
|
||||||
|
|
||||||
import com.sun.jna.win32.StdCallLibrary;
|
|
||||||
|
|
||||||
public
|
|
||||||
interface WNDPROC extends StdCallLibrary.StdCallCallback {
|
|
||||||
LRESULT callback(HWND hWnd, int uMsg, WPARAM uParam, LPARAM lParam);
|
|
||||||
}
|
|
@ -1,208 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HWND;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LPARAM;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.LRESULT;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.WPARAM;
|
|
||||||
import static com.sun.jna.platform.win32.WinUser.WM_QUIT;
|
|
||||||
import static dorkbox.util.jna.windows.User32.User32;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
import org.slf4j.Logger;
|
|
||||||
import org.slf4j.LoggerFactory;
|
|
||||||
|
|
||||||
import com.sun.jna.WString;
|
|
||||||
import com.sun.jna.platform.win32.WinUser;
|
|
||||||
|
|
||||||
@SuppressWarnings({"Convert2Lambda", "UnusedAssignment", "Convert2Diamond", "FieldCanBeLocal"})
|
|
||||||
public
|
|
||||||
class WindowsEventDispatch implements Runnable {
|
|
||||||
private static final Logger logger = LoggerFactory.getLogger(WindowsEventDispatch.class);
|
|
||||||
|
|
||||||
private static final String NAME = "WindowsEventDispatch";
|
|
||||||
|
|
||||||
public static final int WM_TASKBARCREATED = User32.RegisterWindowMessage(new WString("TaskbarCreated"));
|
|
||||||
public static final int WM_COMMAND = 0x0111;
|
|
||||||
public static final int WM_SHELLNOTIFY = WinUser.WM_USER + 1;
|
|
||||||
public static final int WM_MEASUREITEM = 44;
|
|
||||||
public static final int WM_DRAWITEM = 43;
|
|
||||||
|
|
||||||
public static final int MF_POPUP = 0x00000010;
|
|
||||||
|
|
||||||
|
|
||||||
private static final WindowsEventDispatch edt = new WindowsEventDispatch();
|
|
||||||
private final static Map<Integer, List<Listener>> messageIDs = new HashMap<Integer, List<Listener>>();
|
|
||||||
|
|
||||||
private static final Object lock = new Object();
|
|
||||||
private static int referenceCount = 0;
|
|
||||||
|
|
||||||
|
|
||||||
private Thread dispatchThread;
|
|
||||||
|
|
||||||
// keep these around to prevent GC
|
|
||||||
private WNDPROC WndProc;
|
|
||||||
|
|
||||||
// used to dispatch messages
|
|
||||||
private volatile HWND hWnd;
|
|
||||||
|
|
||||||
|
|
||||||
private
|
|
||||||
WindowsEventDispatch() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public static
|
|
||||||
void start() {
|
|
||||||
synchronized (lock) {
|
|
||||||
int ref = referenceCount++;
|
|
||||||
|
|
||||||
if (ref == 0) {
|
|
||||||
edt.start_();
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
|
||||||
// wait for the dispatch thread to start
|
|
||||||
lock.wait();
|
|
||||||
} catch (InterruptedException e) {
|
|
||||||
Thread.currentThread().interrupt();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static
|
|
||||||
void stop() {
|
|
||||||
synchronized (lock) {
|
|
||||||
if (--referenceCount == 0) {
|
|
||||||
edt.stop_();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static
|
|
||||||
HWND get() {
|
|
||||||
return edt.hWnd;
|
|
||||||
}
|
|
||||||
|
|
||||||
// always from inside lock!
|
|
||||||
private
|
|
||||||
void start_() {
|
|
||||||
dispatchThread = new Thread(this, NAME);
|
|
||||||
dispatchThread.start();
|
|
||||||
}
|
|
||||||
|
|
||||||
// always from inside lock!
|
|
||||||
private void
|
|
||||||
stop_() {
|
|
||||||
User32.SendMessage(hWnd, WM_QUIT, new WPARAM(0), new LPARAM(0));
|
|
||||||
|
|
||||||
try {
|
|
||||||
// wait for the dispatch thread to quit (but only if we are not on the dispatch thread)
|
|
||||||
if (!Thread.currentThread().equals(dispatchThread)) {
|
|
||||||
dispatchThread.join();
|
|
||||||
}
|
|
||||||
} catch (InterruptedException e) {
|
|
||||||
Thread.currentThread().interrupt();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressWarnings("Java8MapApi")
|
|
||||||
public static
|
|
||||||
void addListener(final int messageId, final Listener listener) {
|
|
||||||
synchronized (messageIDs) {
|
|
||||||
List<Listener> listeners = messageIDs.get(messageId);
|
|
||||||
if (listeners == null) {
|
|
||||||
listeners = new ArrayList<Listener>();
|
|
||||||
messageIDs.put(messageId, listeners);
|
|
||||||
}
|
|
||||||
|
|
||||||
listeners.add(listener);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
public static
|
|
||||||
void removeListener(final Listener listener) {
|
|
||||||
synchronized (messageIDs) {
|
|
||||||
for (Map.Entry<Integer, List<Listener>> entry : messageIDs.entrySet()) {
|
|
||||||
List<Listener> value = entry.getValue();
|
|
||||||
if (value.remove(listener)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void run() {
|
|
||||||
WndProc = new WNDPROC() {
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
LRESULT callback(HWND hWnd, int msg, WPARAM wParam, LPARAM lParam) {
|
|
||||||
List<Listener> listeners = null;
|
|
||||||
synchronized (messageIDs) {
|
|
||||||
listeners = messageIDs.get(msg);
|
|
||||||
if (listeners != null) {
|
|
||||||
// make a copy, in case a listener action modifies the message listener
|
|
||||||
listeners = new ArrayList<Listener>(listeners);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (listeners != null) {
|
|
||||||
for (final Listener listener : listeners) {
|
|
||||||
if (listener != null) {
|
|
||||||
try {
|
|
||||||
listener.run(hWnd, wParam, lParam);
|
|
||||||
} catch (Exception e) {
|
|
||||||
logger.error("Error during listener execution.", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return User32.DefWindowProc(hWnd, msg, wParam, lParam);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
hWnd = User32.CreateWindowEx(0, "STATIC", NAME, 0, 0, 0, 0, 0, null, null, null,
|
|
||||||
null);
|
|
||||||
if (hWnd == null) {
|
|
||||||
throw new GetLastErrorException();
|
|
||||||
}
|
|
||||||
|
|
||||||
User32.SetWindowLong(hWnd, User32.GWL_WNDPROC, WndProc);
|
|
||||||
|
|
||||||
synchronized (lock) {
|
|
||||||
lock.notifyAll();
|
|
||||||
}
|
|
||||||
|
|
||||||
MSG msg = new MSG();
|
|
||||||
while (User32.GetMessage(msg, null, 0, 0)) {
|
|
||||||
User32.TranslateMessage(msg);
|
|
||||||
User32.DispatchMessage(msg);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (hWnd != null) {
|
|
||||||
if (!User32.DestroyWindow(hWnd)) {
|
|
||||||
throw new GetLastErrorException();
|
|
||||||
}
|
|
||||||
hWnd = null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,47 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms682093%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class CONSOLE_SCREEN_BUFFER_INFO extends Structure {
|
|
||||||
|
|
||||||
public COORD size = new COORD();
|
|
||||||
public COORD cursorPosition = new COORD();
|
|
||||||
public short attributes = (short) 0;
|
|
||||||
public SMALL_RECT window = new SMALL_RECT();
|
|
||||||
public COORD maximumWindowSize = new COORD();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("size", "cursorPosition", "attributes", "window", "maximumWindowSize");
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
String toString() {
|
|
||||||
return "Size: " + size + " CursorPos: " + cursorPosition + " Attribs: " + attributes + " Window: " + window + " MaxWindowSize: " +
|
|
||||||
maximumWindowSize;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,54 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms682119(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class COORD extends Structure {
|
|
||||||
public short x;
|
|
||||||
public short y;
|
|
||||||
|
|
||||||
public
|
|
||||||
COORD.ByValue asValue() {
|
|
||||||
COORD.ByValue copy = new COORD.ByValue();
|
|
||||||
copy.x = this.x;
|
|
||||||
copy.y = this.y;
|
|
||||||
return copy;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("x", "y");
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
String toString() {
|
|
||||||
return x + ":" + y;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static public
|
|
||||||
class ByValue extends COORD implements Structure.ByValue {}
|
|
||||||
}
|
|
@ -1,52 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import com.sun.jna.Union;
|
|
||||||
|
|
||||||
public
|
|
||||||
class CharUnion extends Union {
|
|
||||||
public char unicodeChar;
|
|
||||||
public byte asciiChar;
|
|
||||||
|
|
||||||
public
|
|
||||||
CharUnion() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
CharUnion(char c) {
|
|
||||||
setType(char.class);
|
|
||||||
unicodeChar = c;
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
CharUnion(byte c) {
|
|
||||||
setType(byte.class);
|
|
||||||
asciiChar = c;
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void set(char c) {
|
|
||||||
setType(char.class);
|
|
||||||
unicodeChar = c;
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void set(byte c) {
|
|
||||||
setType(byte.class);
|
|
||||||
asciiChar = c;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,50 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.DWORD;
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HBITMAP;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/ms648052(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class ICONINFO extends Structure {
|
|
||||||
public boolean IsIcon;
|
|
||||||
public DWORD xHotspot;
|
|
||||||
public DWORD yHotspot;
|
|
||||||
public HBITMAP MaskBitmap;
|
|
||||||
public HBITMAP ColorBitmap;
|
|
||||||
|
|
||||||
|
|
||||||
public
|
|
||||||
ICONINFO() {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("IsIcon", "xHotspot", "yHotspot", "MaskBitmap", "ColorBitmap");
|
|
||||||
}
|
|
||||||
|
|
||||||
public static
|
|
||||||
class ByValue extends ICONINFO implements Structure.ByValue {}
|
|
||||||
}
|
|
@ -1,65 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
import com.sun.jna.Union;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms683499(v=VS.85).aspx
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class INPUT_RECORD extends Structure {
|
|
||||||
public static final short KEY_EVENT = 0x0001;
|
|
||||||
public static final short MOUSE_EVENT = 0x0002;
|
|
||||||
public short EventType;
|
|
||||||
public EventUnion Event;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
void read() {
|
|
||||||
readField("EventType");
|
|
||||||
switch (EventType) {
|
|
||||||
case KEY_EVENT:
|
|
||||||
Event.setType(KEY_EVENT_RECORD.class);
|
|
||||||
break;
|
|
||||||
case MOUSE_EVENT:
|
|
||||||
Event.setType(MOUSE_EVENT_RECORD.class);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
super.read();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("EventType", "Event");
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static public
|
|
||||||
class ByReference extends INPUT_RECORD implements Structure.ByReference {}
|
|
||||||
|
|
||||||
|
|
||||||
public static
|
|
||||||
class EventUnion extends Union {
|
|
||||||
public KEY_EVENT_RECORD KeyEvent;
|
|
||||||
public MOUSE_EVENT_RECORD MouseEvent;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,40 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms684166(v=VS.85).aspx
|
|
||||||
*/
|
|
||||||
public
|
|
||||||
class KEY_EVENT_RECORD extends Structure {
|
|
||||||
public boolean keyDown;
|
|
||||||
public short repeatCount;
|
|
||||||
public short virtualKeyCode;
|
|
||||||
public short virtualScanCode;
|
|
||||||
public CharUnion uChar;
|
|
||||||
public int controlKeyState;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("keyDown", "repeatCount", "virtualKeyCode", "virtualScanCode", "uChar", "controlKeyState");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,35 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
public
|
|
||||||
class MOUSE_EVENT_RECORD extends Structure {
|
|
||||||
public COORD mousePosition;
|
|
||||||
public int buttonState;
|
|
||||||
public int controlKeyState;
|
|
||||||
public int eventFlags;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("mousePosition", "buttonState", "controlKeyState", "eventFlags");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,116 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2017 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import static com.sun.jna.platform.win32.WinDef.HWND;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
import com.sun.jna.platform.win32.WinDef;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* http://msdn.microsoft.com/en-us/library/windows/desktop/bb773352(v=vs.85).aspx
|
|
||||||
*/
|
|
||||||
public class NOTIFYICONDATA extends Structure {
|
|
||||||
static public final int NIF_MESSAGE = 0x1;
|
|
||||||
static public final int NIF_ICON = 0x2;
|
|
||||||
static public final int NIF_TIP = 0x4;
|
|
||||||
static public final int NIF_STATE = 0x8;
|
|
||||||
|
|
||||||
static public final int NIF_INFO = 0x10;
|
|
||||||
|
|
||||||
static public final int NIIF_NONE = 0x0;
|
|
||||||
static public final int NIIF_INFO = 0x1;
|
|
||||||
static public final int NIIF_WARNING = 0x2;
|
|
||||||
static public final int NIIF_ERROR = 0x3;
|
|
||||||
static public final int NIIF_USER = 0x4;
|
|
||||||
|
|
||||||
public int cbSize;
|
|
||||||
public HWND hWnd;
|
|
||||||
public int uID;
|
|
||||||
public int uFlags;
|
|
||||||
public int uCallbackMessage;
|
|
||||||
public WinDef.HICON hIcon;
|
|
||||||
|
|
||||||
public char[] szTip = new char[128];
|
|
||||||
|
|
||||||
public int dwState;
|
|
||||||
public int dwStateMask;
|
|
||||||
|
|
||||||
public char[] szInfo = new char[256];
|
|
||||||
public int uTimeoutOrVersion; // {UINT uTimeout; UINT uVersion;};
|
|
||||||
|
|
||||||
public char[] szInfoTitle = new char[64];
|
|
||||||
public int dwInfoFlags;
|
|
||||||
|
|
||||||
public
|
|
||||||
NOTIFYICONDATA() {
|
|
||||||
cbSize = size();
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void setTooltip(String s) {
|
|
||||||
uFlags |= NIF_TIP;
|
|
||||||
|
|
||||||
System.arraycopy(s.toCharArray(), 0, szTip, 0, Math.min(s.length(), szTip.length));
|
|
||||||
szTip[s.length()] = '\0';
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void setBalloon(String title, String message, int millis, int niif) {
|
|
||||||
uFlags |= NIF_INFO;
|
|
||||||
|
|
||||||
System.arraycopy(message.toCharArray(), 0, szInfo, 0, Math.min(message.length(), szInfo.length));
|
|
||||||
szInfo[message.length()] = '\0';
|
|
||||||
|
|
||||||
uTimeoutOrVersion = millis;
|
|
||||||
|
|
||||||
System.arraycopy(title.toCharArray(), 0, szInfoTitle, 0, Math.min(title.length(), szInfoTitle.length));
|
|
||||||
szInfoTitle[title.length()] = '\0';
|
|
||||||
|
|
||||||
dwInfoFlags = niif;
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
void setIcon(WinDef.HICON hIcon) {
|
|
||||||
uFlags |= NIF_ICON;
|
|
||||||
this.hIcon = hIcon;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setCallback(int callback) {
|
|
||||||
uFlags |= NIF_MESSAGE;
|
|
||||||
uCallbackMessage = callback;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected List<String> getFieldOrder () {
|
|
||||||
return Arrays.asList("cbSize",
|
|
||||||
"hWnd",
|
|
||||||
"uID",
|
|
||||||
"uFlags",
|
|
||||||
"uCallbackMessage",
|
|
||||||
"hIcon",
|
|
||||||
"szTip",
|
|
||||||
"dwState",
|
|
||||||
"dwStateMask",
|
|
||||||
"szInfo",
|
|
||||||
"uTimeoutOrVersion",
|
|
||||||
"szInfoTitle",
|
|
||||||
"dwInfoFlags");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,59 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2016 dorkbox, llc
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package dorkbox.util.jna.windows.structs;
|
|
||||||
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.sun.jna.Structure;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* https://msdn.microsoft.com/en-us/library/ms686311%28VS.85%29.aspx
|
|
||||||
*/
|
|
||||||
@SuppressWarnings("NumericCastThatLosesPrecision")
|
|
||||||
public
|
|
||||||
class SMALL_RECT extends Structure {
|
|
||||||
public short left;
|
|
||||||
public short top;
|
|
||||||
public short right;
|
|
||||||
public short bottom;
|
|
||||||
|
|
||||||
public
|
|
||||||
short width() {
|
|
||||||
return (short) (this.right - this.left);
|
|
||||||
}
|
|
||||||
|
|
||||||
public
|
|
||||||
short height() {
|
|
||||||
return (short) (this.bottom - this.top);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected
|
|
||||||
List<String> getFieldOrder() {
|
|
||||||
return Arrays.asList("left", "top", "right", "bottom");
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public
|
|
||||||
String toString() {
|
|
||||||
return "LTRB: " + left + "," + top + "," + right + "," + bottom;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static public
|
|
||||||
class ByReference extends SMALL_RECT implements Structure.ByReference {}
|
|
||||||
}
|
|
@ -21,7 +21,7 @@ import java.security.PrivilegedAction;
|
|||||||
|
|
||||||
import org.slf4j.LoggerFactory;
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
import dorkbox.util.ClassLoaderUtil;
|
import dorkbox.jna.JnaClassUtils;
|
||||||
import dorkbox.util.OS;
|
import dorkbox.util.OS;
|
||||||
import javassist.ClassPool;
|
import javassist.ClassPool;
|
||||||
import javassist.CtClass;
|
import javassist.CtClass;
|
||||||
@ -118,7 +118,7 @@ class Swt {
|
|||||||
"}", listener);
|
"}", listener);
|
||||||
listener.addMethod(method);
|
listener.addMethod(method);
|
||||||
bytes = listener.toBytecode();
|
bytes = listener.toBytecode();
|
||||||
ClassLoaderUtil.defineClass(bytes);
|
JnaClassUtils.defineClass(bytes);
|
||||||
}
|
}
|
||||||
|
|
||||||
method = swtOverriedClass.getDeclaredMethod("onShutdown");
|
method = swtOverriedClass.getDeclaredMethod("onShutdown");
|
||||||
@ -136,7 +136,7 @@ class Swt {
|
|||||||
bytes = swtOverriedClass.toBytecode();
|
bytes = swtOverriedClass.toBytecode();
|
||||||
|
|
||||||
// define this new class in our current classloader
|
// define this new class in our current classloader
|
||||||
ClassLoaderUtil.defineClass(bytes);
|
JnaClassUtils.defineClass(bytes);
|
||||||
} catch (Throwable e) {
|
} catch (Throwable e) {
|
||||||
LoggerFactory.getLogger(Swt.class).error("Cannot initialize SWT", e);
|
LoggerFactory.getLogger(Swt.class).error("Cannot initialize SWT", e);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user