获取当前活动窗口';Java中的标题

获取当前活动窗口';Java中的标题,java,user-interface,active-window,Java,User Interface,Active Window,我正在尝试编写一个Java程序,每5秒记录我正在使用的应用程序(这是一个时间跟踪器应用程序)。我需要一些方法来找出当前活动窗口是什么。我找到了KeyboardFocusManager.getGlobalActivieWindow(),但我无法让它正常工作。跨平台解决方案更可取,但如果不存在,那么我将使用X.Org为linux开发。谢谢。要在java swing应用程序中查找活动窗口(无论是框架还是对话框),可以使用以下递归方法: Window getSelectedWindow(Window[]

我正在尝试编写一个Java程序,每5秒记录我正在使用的应用程序(这是一个时间跟踪器应用程序)。我需要一些方法来找出当前活动窗口是什么。我找到了KeyboardFocusManager.getGlobalActivieWindow(),但我无法让它正常工作。跨平台解决方案更可取,但如果不存在,那么我将使用X.Org为linux开发。谢谢。

要在java swing应用程序中查找活动窗口(无论是框架还是对话框),可以使用以下递归方法:

Window getSelectedWindow(Window[] windows) {
    Window result = null;
    for (int i = 0; i < windows.length; i++) {
        Window window = windows[i];
        if (window.isActive()) {
            result = window;
        } else {
            Window[] ownedWindows = window.getOwnedWindows();
            if (ownedWindows != null) {
                result = getSelectedWindow(ownedWindows);
            }
        }
    }
    return result;
}
windowgetselectedwindow(Window[]windows){
窗口结果=空;
对于(int i=0;i
这是从
关于窗口状态的更多线索。

我很确定,您将发现没有办法用纯Java枚举活动窗口(我以前很难找到),因此您需要为您想要针对的平台编写代码

  • 在Mac OS X上,您可以使用“osascript”启动一个脚本

  • 在X11上,您可以使用

  • 在Windows上,您可能可以启动一些VBScript(例如,看起来很有希望)


如果您正在使用SWT,您可能会在SWT库中找到一些未记录的非公共方法,因为SWT为许多操作系统API提供了包装(例如,Cocoa上的SWT具有可用于访问操作系统的
org.eclipse.SWT.internal.cococoa.OS#objc_msgSend()
方法)。Windows和X11上的等效“OS”类可能有您可以使用的API。

我编写了一个bash脚本,记录当前活动窗口: 它使用了wmctrl的修补版本,但提供了以下内容的详细信息: 使用xprop和xwininfo的替代(较慢)方法

指向wmctrl修补程序和源代码以及脚本的链接可以是
我已经用user361601的脚本编写了一个java程序。我希望这能帮助其他人

import java.io.BufferedReader;
import java.io.InputStreamReader;

public class WindowAndProcessInfo4Linux {

public static final String WIN_ID_CMD = "xprop -root | grep " + "\"_NET_ACTIVE_WINDOW(WINDOW)\"" + "|cut -d ' ' -f 5";
public static final String WIN_INFO_CMD_PREFIX = "xwininfo -id ";
public static final String WIN_INFO_CMD_MID = " |awk \'BEGIN {FS=\"\\\"\"}/xwininfo: Window id/{print $2}\' | sed \'s/-[^-]*$//g\'";

public String execShellCmd(String cmd){
    try {  

        Runtime runtime = Runtime.getRuntime();  
        Process process = runtime.exec(new String[] { "/bin/bash", "-c", cmd });  
        int exitValue = process.waitFor();  
        System.out.println("exit value: " + exitValue);  
        BufferedReader buf = new BufferedReader(new InputStreamReader(process.getInputStream()));  
        String line = "";  
        String output = "";
        while ((line = buf.readLine()) != null) {
            output = line;
        }
        return output;
    } catch (Exception e) {  
        System.out.println(e);
        return null;
    }  
}

public String windowInfoCmd(String winId){
    if(null!=winId && !"".equalsIgnoreCase(winId)){
        return WIN_INFO_CMD_PREFIX+winId +WIN_INFO_CMD_MID;
    }
    return null;
}

public static void main (String [] args){
    WindowAndProcessInfo4Linux windowAndProcessInfo4Linux = new WindowAndProcessInfo4Linux();
    try {
        Thread.sleep(4000);
    } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    String winId = windowAndProcessInfo4Linux.execShellCmd(WIN_ID_CMD);
    String winInfoMcd = windowAndProcessInfo4Linux.windowInfoCmd(winId);
    String windowTitle = windowAndProcessInfo4Linux.execShellCmd(winInfoMcd);
    System.out.println("window title is: "+ windowTitle);

}
}
//thread.sleep在那里,这样您就有时间切换到其他窗口:)
另外,您可以使用spring中的quartz来调度它。

我在研究类似主题时创建了此applescript-此主题获得特定的窗口大小

全局边界
告诉应用程序“系统事件”
将此_info设置为{}
将边界设置为{}
对进程中的进程重复此操作
如果不只是进程的背景,那么
告诉这个过程
将processName设置为name
将windows设置为windows
结束语
将windowsCount设置为Windows的计数
如果processName包含“xxxxxxxx”,则
将此\u info设置为此\u info&processName
否则,如果processName不是“Finder”,则
如果windowsCount大于0,则
对窗口中的窗口重复此操作
告诉这个过程
告诉窗户
如果(属性“AXTitle”的值)包含“供个人使用的Genymotion-”,则
--将此\u info设置为此\u info&(属性“AXTitle”的值)
设置道具以获取窗口的属性
将边界设置为支柱的{size,position}
将此信息设置为此信息(&U)
如果结束
结束语
结束语
结束重复
如果结束
如果结束
如果结束
结束重复
结束语

返回边界
使用SWT内部构件,我能够将其组合在一起,它似乎工作得很好:

/**@返回当前活动窗口的标题*/
公共静态最终字符串getActiveWindowText(){
long/*int*/handle=OS.getForeGroundIndow();
int length=OS.GetWindowTextLength(句柄);
如果(长度==0)返回“”;
/*使用默认区域设置的字符编码*/
TCHAR缓冲区=新的TCHAR(0,长度+1);
GetWindowText(句柄、缓冲区、长度+1);
返回buffer.toString(0,长度);
}
publicstaticfinalvoidmain(字符串[]args){
试一试{
睡眠(1000L);
}捕捉(中断异常e){
Thread.currentThread().interrupt();
}
System.out.println(getActiveWindowText());
}

打印:
用户界面-在Java中获取当前活动窗口的标题-堆栈溢出-Google Chrome

,但它只考虑Java窗口,而我认为Steven希望获得全局活动窗口,无论它是否是Java程序。哎呀!我误解了这个问题!David是对的,我想知道全局活动窗口的名称。这样我就可以自动跟踪我何时使用firefox,何时使用Eclipse。你使用的是KDE或Gnome之类的窗口系统吗?可能需要知道的是,由于此类任务通常需要使用系统特定的代码来完成。非常感谢此脚本。还请提供代码说明,而不是将其粘贴到此处。