I have the following code using the JNA library which outputs the active window's title.
private static final int MAX_TITLE_LENGTH = 1024;
public static void main(String[] args) throws Exception {
DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm:ss");
LocalDateTime now = LocalDateTime.now();
TimerTask task = new TimerTask() {
@Override
public void run() {
char[] buffer = new char[MAX_TITLE_LENGTH * 2];
HWND hwnd = User32.INSTANCE.GetForegroundWindow();
User32.INSTANCE.GetWindowText(hwnd, buffer, MAX_TITLE_LENGTH);
System.out.println("Active window title: " + Native.toString(buffer));
try {
BufferedWriter bw = new BufferedWriter(
new FileWriter(
new File("C:\\Users\\" + System.getProperty("user.name") + "\\AppData\\Roaming\\system\\useracivity.txt"),
true
)
);
bw.write(Native.toString(buffer) + " TIME WAS " + dtf.format(now));
bw.newLine();
bw.close();
} catch (Exception e) {
}
}
};
Timer timer = new Timer();
timer.schedule(task, new Date(), 5000);
}
But how do I get the name of the application, for example for Chrome "chrome.exe"?
Thanks in advance
I've found that GetWindowModuleFilename
doesn't really work most of the time. QueryFullProcessImageName
, however, works just fine. Note that you still do need to OpenProcess
the process to access the image file name.
Try this in a console application. It will print out the active window's image filename when you change the window.
import com.sun.jna.platform.win32.*;
import com.sun.jna.platform.win32.WinDef.HWND;
import com.sun.jna.platform.win32.WinNT.HANDLE;
import com.sun.jna.ptr.IntByReference;
public class Main {
public static void main(String[] args) throws Exception {
HWND prevFg = null;
while (true) {
Thread.sleep(200);
HWND fg = User32.INSTANCE.GetForegroundWindow();
// don't print the name if it's still the same window as previously
if (fg.equals(prevFg)) {
continue;
}
String fgImageName = getImageName(fg);
if (fgImageName == null) {
System.out.println("Failed to get the image name!");
} else {
System.out.println(fgImageName);
}
prevFg = fg;
}
}
private static String getImageName(HWND window) {
// Get the process ID of the window
IntByReference procId = new IntByReference();
User32.INSTANCE.GetWindowThreadProcessId(window, procId);
// Open the process to get permissions to the image name
HANDLE procHandle = Kernel32.INSTANCE.OpenProcess(
Kernel32.PROCESS_QUERY_LIMITED_INFORMATION,
false,
procId.getValue()
);
// Get the image name
char[] buffer = new char[4096];
IntByReference bufferSize = new IntByReference(buffer.length);
boolean success = Kernel32.INSTANCE.QueryFullProcessImageName(procHandle, 0, buffer, bufferSize);
// Clean up: close the opened process
Kernel32.INSTANCE.CloseHandle(procHandle);
return success ? new String(buffer, 0, bufferSize.getValue()) : null;
}
}
Clicking around my windows, the program prints out lines like these:
C:\Program Files\JetBrains\IntelliJ IDEA Community Edition 2017.3.5\bin\idea64.exe
C:\Program Files (x86)\Google\Chrome\Application\chrome.exe
C:\Program Files\JetBrains\IntelliJ IDEA Community Edition 2017.3.5\bin\idea64.exe