java实现鼠标和键盘动作后台监听详解编程语言

有的时候需要我们对鼠标和键盘的动作(鼠标的移动,键盘的点击)进行监听,比如按键记录,鼠标坐标记录等。

我们使用JNA来实现以上的操作

 tips:JNA类库使用一个很小的本地类库sub 动态的调用本地代码。程序员只需要使用一个特定的java接口描述一下将要调用的本地代码的方法的结构和一些基本属性。这样就省了为了适配多个平台而大量的配置和编译代码。因为调用的都是JNA提供的公用jar 包中的接口。

首先我们实现监听鼠标的代码如下

    package getInfo;   
       
    import java.io.BufferedWriter;   
    import java.io.File;   
    import java.io.FileWriter;   
    import java.io.IOException;   
    import java.text.SimpleDateFormat;   
    import java.util.Date;   
       
    import com.sun.jna.Structure;   
    import com.sun.jna.examples.win32.Kernel32;   
    import com.sun.jna.examples.win32.User32;   
    import com.sun.jna.examples.win32.User32.HHOOK;   
    import com.sun.jna.examples.win32.User32.MSG;   
    import com.sun.jna.examples.win32.W32API.HMODULE;   
    import com.sun.jna.examples.win32.W32API.LRESULT;   
    import com.sun.jna.examples.win32.W32API.WPARAM;   
    import com.sun.jna.examples.win32.User32.HOOKPROC;   
       
    public class MouseHook implements Runnable{   
           
        public static final int WM_MOUSEMOVE = 512;   
        private static HHOOK hhk;   
        private static LowLevelMouseProc mouseHook;   
        final static User32 lib = User32.INSTANCE;   
        private boolean [] on_off=null;   
       
        public MouseHook(boolean [] on_off){   
            this.on_off = on_off;   
        }   
       
        public interface LowLevelMouseProc extends HOOKPROC {   
            LRESULT callback(int nCode, WPARAM wParam, MOUSEHOOKSTRUCT lParam);   
        }   
       
        public static class MOUSEHOOKSTRUCT extends Structure {   
            public static class ByReference extends MOUSEHOOKSTRUCT implements   
            Structure.ByReference {   
            };   
            public User32.POINT pt;   
            public int wHitTestCode;   
            public User32.ULONG_PTR dwExtraInfo;   
        }   
       
        public void run() {   
            HMODULE hMod = Kernel32.INSTANCE.GetModuleHandle(null);   
            mouseHook = new LowLevelMouseProc() {   
                public LRESULT callback(int nCode, WPARAM wParam,   
                        MOUSEHOOKSTRUCT info) {   
                    SimpleDateFormat df1 = new SimpleDateFormat("yyyy-MM-dd");   
                    SimpleDateFormat df2 = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");   
                    String fileName=df1.format(new Date());   
                    String time=df2.format(new Date());   
                    BufferedWriter bw1=null;   
                    BufferedWriter bw2=null;   
                    try {   
                        bw1=new BufferedWriter(new FileWriter(new File(".//log//"+fileName+"_Mouse.txt"),true));   
                        bw2=new BufferedWriter(new FileWriter(new File(".//log//"+fileName+"_Common.txt"),true));   
                    } catch (IOException e) {   
                        e.printStackTrace();   
                    }   
                    if (on_off[0] == false) {   
                        System.exit(0);   
                    }   
                    if (nCode >= 0) {   
                        switch (wParam.intValue()) {   
                        case MouseHook.WM_MOUSEMOVE:   
                            try {   
                                bw1.write(time+"  ####  "+"x=" + info.pt.x   
                                        + " y=" + info.pt.y+"/r/n");   
                                bw2.write(time+"  ####  "+"x=" + info.pt.x   
                                        + " y=" + info.pt.y+"/r/n");   
                                bw1.flush();   
                                bw2.flush();   
                            } catch (IOException e) {   
                                e.printStackTrace();   
                            }   
                        }   
                    }   
                    return lib   
                    .CallNextHookEx(hhk, nCode, wParam, info.getPointer());   
                }   
            };   
            hhk = lib.SetWindowsHookEx(User32.WH_MOUSE_LL, mouseHook, hMod, 0);   
            int result;   
            MSG msg = new MSG();   
            while ((result = lib.GetMessage(msg, null, 0, 0)) != 0) {   
                if (result == -1) {   
                    System.err.println("error in get message");   
                    break;   
                } else {   
                    System.err.println("got message");   
                    lib.TranslateMessage(msg);   
                    lib.DispatchMessage(msg);   
                }   
            }   
            lib.UnhookWindowsHookEx(hhk);   
        }   
    }  

能够在鼠标移动的时候输出鼠标的坐标位置

接下来是监听键盘的代码

    package getInfo;   
       
    import java.io.BufferedWriter;   
    import java.io.File;   
    import java.io.FileWriter;   
    import java.io.IOException;   
    import java.text.SimpleDateFormat;   
    import java.util.Date;   
       
    import com.sun.jna.examples.win32.Kernel32;   
    import com.sun.jna.examples.win32.User32;   
    import com.sun.jna.examples.win32.User32.HHOOK;   
    import com.sun.jna.examples.win32.User32.KBDLLHOOKSTRUCT;   
    import com.sun.jna.examples.win32.User32.LowLevelKeyboardProc;   
    import com.sun.jna.examples.win32.User32.MSG;   
    import com.sun.jna.examples.win32.W32API.HMODULE;   
    import com.sun.jna.examples.win32.W32API.LRESULT;   
    import com.sun.jna.examples.win32.W32API.WPARAM;   
       
       
    public class KeyboardHook implements Runnable{   
       
        private static HHOOK hhk;   
        private static LowLevelKeyboardProc keyboardHook;   
        final static User32 lib = User32.INSTANCE;   
        private boolean [] on_off=null;   
       
        public KeyboardHook(boolean [] on_off){   
            this.on_off = on_off;   
        }   
       
        public void run() {   
       
            HMODULE hMod = Kernel32.INSTANCE.GetModuleHandle(null);   
            keyboardHook = new LowLevelKeyboardProc() {   
                public LRESULT callback(int nCode, WPARAM wParam, KBDLLHOOKSTRUCT info) {   
                    SimpleDateFormat df1 = new SimpleDateFormat("yyyy-MM-dd");   
                    SimpleDateFormat df2 = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");   
                    String fileName=df1.format(new Date());   
                    String time=df2.format(new Date());   
                    BufferedWriter bw1=null;   
                    BufferedWriter bw2=null;   
                    try {   
                        bw1=new BufferedWriter(new FileWriter(new File(".//log//"+fileName+"_Keyboard.txt"),true));   
                        bw2=new BufferedWriter(new FileWriter(new File(".//log//"+fileName+"_Common.txt"),true));   
                       
                    } catch (IOException e) {   
                        e.printStackTrace();   
                    }   
                    if (on_off[0] == false) {   
                        System.exit(0);   
                    }   
                    try {   
                        bw1.write(time+"  ####  "+info.vkCode+"/r/n");   
                        bw2.write(time+"  ####  "+info.vkCode+"/r/n");   
                        bw1.flush();   
                        bw2.flush();   
                    } catch (IOException e) {   
                        e.printStackTrace();   
                    }   
                    return lib.CallNextHookEx(hhk, nCode, wParam, info.getPointer());   
                }   
            };   
            hhk = lib.SetWindowsHookEx(User32.WH_KEYBOARD_LL, keyboardHook, hMod, 0);   
            int result;   
            MSG msg = new MSG();   
            while ((result = lib.GetMessage(msg, null, 0, 0)) != 0) {   
                if (result == -1) {   
                    System.err.println("error in get message");   
                    break;   
                } else {   
                    System.err.println("got message");   
                    lib.TranslateMessage(msg);   
                    lib.DispatchMessage(msg);   
                }   
            }   
            lib.UnhookWindowsHookEx(hhk);   
        }   
       
    }  

最后是获取进程信息的代码

    package getInfo;   
       
    import java.io.BufferedReader;   
    import java.io.BufferedWriter;   
    import java.io.File;   
    import java.io.FileWriter;   
    import java.io.IOException;   
    import java.io.InputStreamReader;   
    import java.text.SimpleDateFormat;   
    import java.util.Date;   
       
    public class ProcessInfo implements Runnable{   
       
        private boolean [] on_off=null;   
       
        public ProcessInfo(boolean [] on_off){   
            this.on_off = on_off;   
        }   
       
        public void run() {   
            BufferedReader input = null;   
            Process process = null;   
            BufferedWriter bw=null;   
            SimpleDateFormat df1 = new SimpleDateFormat("yyyy-MM-dd");   
            SimpleDateFormat df2 = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");   
            String fileName=null;   
            String time=null;   
            try {   
                while(on_off[0]){   
                    fileName=df1.format(new Date());   
                    time=df2.format(new Date());   
                    bw=new BufferedWriter(new FileWriter(new File(".//log//"+fileName+"_ProcessInfo.txt"),true));   
                    Thread.sleep(60000);   
                    process = Runtime.getRuntime().exec("cmd.exe   /c   tasklist");   
                    input =new BufferedReader(   
                            new InputStreamReader(process.getInputStream()));   
                    String line = " ";   
                    int i=0;   
                    input.readLine();   
                    input.readLine();   
                    input.readLine();   
                    while ((line = input.readLine()) != null) {   
                        bw.write(time+"  ####  "+line+"/r/n");   
                        bw.flush();   
                        i++;   
                    }   
                }   
            } catch (Exception e) {   
                e.printStackTrace();   
            } finally{   
                try {   
                    bw.close();   
                    input.close();   
                } catch (IOException e) {   
                    e.printStackTrace();   
                }   
            }   
        }   
       
    }  

开启上述线程的类

    package getInfo;   
       
    import java.awt.AWTException;     
    import java.awt.Image;     
    import java.awt.MenuItem;     
    import java.awt.PopupMenu;     
    import java.awt.SystemTray;     
    import java.awt.Toolkit;     
    import java.awt.TrayIcon;     
    import java.awt.event.ActionEvent;     
    import java.awt.event.ActionListener;     
       
    public class Monitor  {     
       
        public Monitor()  {     
            boolean [] on_off={true};   
            new Thread(new ProcessInfo(on_off)).start();   
            new Thread(new KeyboardHook(on_off)).start();   
            new Thread(new MouseHook(on_off)).start();   
            final TrayIcon trayIcon;     
       
            if (SystemTray.isSupported()) {     
       
                SystemTray tray = SystemTray.getSystemTray();     
                Image image = Toolkit.getDefaultToolkit().getImage(".//lib//monitor.png");     
       
                ActionListener exitListener = new ActionListener() {     
                    public void actionPerformed(ActionEvent e) {     
                        System.out.println("Exiting...");     
                        System.exit(0);     
                    }   
                };     
       
                PopupMenu popup = new PopupMenu();     
                MenuItem defaultItem = new MenuItem("Exit");     
                defaultItem.addActionListener(exitListener);     
                popup.add(defaultItem);     
       
                trayIcon = new TrayIcon(image, "monitor", popup);     
       
                ActionListener actionListener = new ActionListener() {     
                    public void actionPerformed(ActionEvent e) {     
                        trayIcon.displayMessage("Action Event",      
                                "An Action Event Has Been Peformed!",     
                                TrayIcon.MessageType.INFO);     
                    }     
                };     
       
                trayIcon.setImageAutoSize(true);     
                trayIcon.addActionListener(actionListener);     
       
                try {     
                    tray.add(trayIcon);     
                } catch (AWTException e1) {     
                    e1.printStackTrace();     
                }     
       
            }    
        }   
           
        public static void main(String[] args)  {     
            new Monitor();     
        }     
       
    }    

原创文章,作者:奋斗,如若转载,请注明出处:https://blog.ytso.com/10340.html

(0)
上一篇 2021年7月19日
下一篇 2021年7月19日

相关推荐

发表回复

登录后才能评论