Pisząc w skrócie: masz jakąś funkcję systemową-weźmy <ort>najprostrzą</ort>, a mianowicie przydzielanie uchwytów do odpalanej aplikacji desktopowej. Jest jakaś sobie biblioteka w windowsie którą się wykorzystuje do przydzielania uchytów. Czasami istnieje konieczność wysyłania komunikatów do naszej aplikacji(okna) więc aby to zrobić musimy mieć uchwyt prawda?:)
Jest taka biblioteka user32.dll (inna przydatna do kernel32.dll albo spools.dll), która posiada wiele różnych przydatnych metod i między innymi metodę EnumWindows ... i tu chwila przerwy bo odpowiem na pytanie skąd brać wiedzę i szukać odpowiednich metod i jak je definiować: tylko i zawsze MSDN:)
http://msdn.microsoft.com/en-us/library/ms633497(VS.85).aspx
MAsz napisane co to do czego co trzeba dać a co wyciągnąć. I tak nasza metoda wygląda tak:
Kopiuj
BOOL WINAPI EnumWindows(
__in WNDENUMPROC lpEnumFunc,
__in LPARAM lParam
);
Celowo wybrałem tą która jest również często wybraana w przykładach ponieważ (bardzo często) wynik operacji dostaniesz w tzw. callback'u.I tu pojawia konieczność poznania C++. W javie oczywisćie callback jest ale służy przede wszystkim do "chwytania" zdarzeń. w WINAPI nawet <ort>najprostrzego</ort> stringa dostaniesz bezpośrednio z systemu do wcześniej zdefiniowanego kodu (to własnie callback). Również jak już pewnie zauważyłeś w Javie nie ma typów LPARAM, LPRESULT czy HWND.
I tu są dwa wyjścia: JNI-musisz napisać własną przejściową bibliotekę dll w cpp która będzie w sobie udostępniała mapowanie z natywnego na jave lub JNA który moim zdaniem jest już o wiele lepszym rozwiazaniem: mapujesz w samym programie Javy.
Z tabelki na stronie JNA:
Native Type Size Java Type Common Windows Types
char 8-bit integer byte BYTE, TCHAR
i juz wiesz co pisać w programie.
Poza tym teraz jest jeszcze wygodniej bo np kiedyś było tak że zamiast np hwnd dawałeś Pointer-to samo w winapi i javie a teraz importujesz
import com.sun.jna.platform.win32.W32API
i masz wszystkie typy same w sobie-bez Twojej ingerencji JNA zapewnia kompatybilnośc typów.
OK to do konkluzji:
Aby wykorzystać metodę EnumWindows:
- Tworzysz interfejs User32 w którym dasz metodę EnumWindows:
Kopiuj
import com.sun.jna.win32.StdCallLibrary;
import com.sun.jna.Pointer;
import com.sun.jna.platform.win32.W32API.HWND;
public interface User32 extends StdCallLibrary {
boolean EnumWindows(WndEnumProc wndenumproc, Pointer lParam);
}
Co wchodzi i wychodzi z tej metody wiesz z MSDN.
2 Teraz definiujesz WndEnumProc w której bedzie zwracany wynik za pomocą callbacka:
Kopiuj
import com.sun.jna.win32.StdCallLibrary;
import com.sun.jna.platform.win32.W32API.HWND;
public interface WndEnumProc extends StdCallLibrary.StdCallCallback
{
boolean callback (HWND hWnd, int lParam);
}
- A teraz już wczytujesz bibliotekę user32.ddl , definiujesz kod programu callback w którym ma system zwrócić wynik i masz:)
Kopiuj
import com.sun.jna.Native;
import com.sun.jna.platform.win32.W32API.HWND;
public class UchwytOknaCallback {
private User32 user32Lib;
private WndEnumProc wndenumproc;
private byte[] title = new byte[256];
public UchwytOknaCallback() {
user32Lib = (User32) Native.loadLibrary("user32", User32.class);
wndenumproc = new WndEnumProc() {
public boolean callback(HWND hWnd, int lParam) {
System.out.println(hwnd);
}
return true;
}
};
public boolean enumWindows() {
return user32Lib.EnumWindows(wndenumproc, null);
}
Teraz już tylko wywołanie: tworzysz obiekt klasy UchwytOknaCallback i wywołujesz mtodę enumWindows;
W sumie to tylko wypisuje liste wskaźników do okna uruchomionych na systemie ale spróbuj sam dodać metodę GetWindowTextA - otrzymasz nazwę okna dla danego hwnd - już nie trzeba callbacku:)
PS: w CPP czy siszarpie czy dotnecie aby mieć kontrolę nad natywnymi możliwościami windows i tak będziesz musiał się zagłębić-mocno.
PPS: Jak CIę zaciekawiłem to musisz pamiętac że takie aplikacje się inaczej pisze niż standardowe Javowe - musisz zrobić pętlę komunikatów i to będzie serce programu - jak będziesz chciał to Ci pomoge pozdro
btw nie ma żadnych problemów z przenoszeniem - musi być windows chyba minimum 2000 i tyle. bez różnicy czy 64 bity czy 32.