Получение handle в JAVA

В своем прокте мне необходимо было получить handle компонета.

1. Включаем в проект какой-нибудь класс, который будет реализовывать вызов метода.

public class GAccess {
 static native int getHWND(Component target, String bootpath);
}

2. Компилируем его, и получаем файл .class
В моем случае получился файл  project_folder/build/classes/PNAME/GAccess.class
PNAME - package name.

3. С помошью javah мы можем сгенерировать заголовочный файл для будущей билиотеки. Откроем командную строку и перейдем в католог project_folder/build/classes. Выполним  javah PNAME.GAccess.class, в текущем каталоге получим заголовочный файл GAccess.h вида

 
#ifndef _Included_win32_Win32 
#define _Included_win32_Win32 
#ifdef __cplusplus 
extern "C" { 
#endif 

JNIEXPORT jint JNICALL GAccess_getHWND 
(JNIEnv *env, jclass, jobject comp, jstring jrePath) 
#ifdef __cplusplus 
} 
#endif 
#endif



4. Напишем реализацию  GAccess.c. Можно было бы определять handle не по заголовку, но у меня не было желания ставить например windows SDK чтобы скомпилировать код.


 
#include "jni.h" 
#include "GAccess.h" 
#include "jawt.h" 
#include "jawt_md.h" 

JNIEXPORT jint JNICALL Java_gis1_GAccess_getHWND 
(JNIEnv *env, jclass c, jobject comp, jstring jreTitle) 
{ 
 HWND hwnd = NULL; 
 const char *str = NULL; 
 str = (*env)->GetStringUTFChars(env,  jreTitle, 0); 
 hwnd = FindWindow(NULL,str); 
 (*env)->ReleaseStringUTFChars(env, jreTitle, str); 
 return (jint) hwnd; 
}

jawt.h и jawt_md.h можно взять здесь

5. Создаем объектный файл
    gcc - c GAccess.c

 Создаем библиотеку
 gcc -shared -o gaccess.dll GAccess.o -Wl,--kill-at

-Wl,--kill-at  - эти параметры мне пригодились, чтобы оставить имя метода в библиотеки неизменным, без mangling.

6. Теперь осталось загрузить библиотеку, и использовать ее.
 Скопирем ее в WINDOWS\systems32 :
 System.loadLibrary("gaccess");
//либо вызовем, используя путь :
 System.loadLibrary("C:\\...\\gaccess");

И наконец получаем handle:
int hwnd = GAccess.getHWND(this, this.getTitle());

Comments