当前位置: 首页 > ops >正文

【Unity知识分享】Unity实现全局监听键鼠调用

1、实现该功能前,优先学习Unity接入dll调用Window系统接口教程

【Unity知识分享】Unity接入dll调用Window系统接口

2、初始化动态连接库后,进行脚本功能实现

2.1 创建脚本KeyBoardHook.h和KeyBoardHook.cpp,实现功能如下

KeyBoardHook.h

#pragma once
#include <windows.h>#ifdef MYNATIVE_EXPORTS
#define MY_API __declspec(dllexport)
#else
#define MY_API __declspec(dllimport)
#endif // MYNATIVE_EXPORTSextern "C" {//定义一个回调的函数指针typedef void(__stdcall* KeyCallback)(int vkCode);MY_API bool InstallHook(HWND hWnd, KeyCallback callback);MY_API void UninstallHook();
}LRESULT CALLBACK KeyboardProc(int nCode, WPARAM wParam, LPARAM lParam);
LRESULT CALLBACK MouseProc(int nCode, WPARAM wParam, LPARAM lParam);

KeyBoardHook.cpp

#include "KeyBoardHook.h"
//#include <Windows.h>HHOOK g_hHook = NULL;
HHOOK g_hMouseHook = NULL;
HWND g_hwnd = NULL;
KeyCallback g_callback = nullptr;extern "C" {MY_API bool InstallHook(HWND hwnd, KeyCallback callback){g_hwnd = hwnd;g_callback = callback;g_hHook = SetWindowsHookEx(WH_KEYBOARD_LL, KeyboardProc, GetModuleHandle(NULL), 0);g_hMouseHook = SetWindowsHookEx(WH_MOUSE_LL, MouseProc, GetModuleHandle(NULL), 0);return g_hHook != NULL;}MY_API void UninstallHook() {if (g_hHook) {UnhookWindowsHookEx(g_hHook);UnhookWindowsHookEx(g_hMouseHook);g_hHook = NULL;g_hMouseHook = NULL;g_callback = nullptr;}}
}LRESULT CALLBACK KeyboardProc(int nCode, WPARAM wParam, LPARAM lParam) 
{if (nCode == HC_ACTION && (wParam == WM_KEYDOWN || wParam == WM_SYSKEYDOWN)){KBDLLHOOKSTRUCT* kb = (KBDLLHOOKSTRUCT*)lParam;OutputDebugStringA("keyboardProc triggered\n");if (g_hwnd && g_callback){OutputDebugStringA("Calling Unity callback\n");g_callback((int)kb->vkCode);}else{OutputDebugStringA("g_callback is null\n");}}return CallNextHookEx(g_hHook, nCode, wParam, lParam);
}LRESULT CALLBACK MouseProc(int nCode, WPARAM wParam, LPARAM lParam)
{if (nCode == HC_ACTION){int vkCode = 0;MSLLHOOKSTRUCT* ms = (MSLLHOOKSTRUCT*)lParam;switch (wParam){case WM_LBUTTONDOWN:vkCode = VK_LBUTTON;break;case WM_RBUTTONDOWN:vkCode = VK_RBUTTON;break;case WM_MBUTTONDOWN:vkCode = VK_MBUTTON;break;default:return CallNextHookEx(g_hMouseHook, nCode, wParam, lParam);}OutputDebugStringA("MouseProc triggered\n");if (g_hwnd && g_callback) {OutputDebugStringA("Calling Unity mouse callback\n");g_callback(vkCode);}else{OutputDebugStringA("g_callback is null\n");}}return CallNextHookEx(g_hMouseHook, nCode, wParam, lParam);
}

2.2 生成dll包

3、将dll包导入Unity,并实现dll包实现功能

3.1 创建Plugins文件夹,将dll包复制到该文件夹下面

3.2 将dll设置为PC的x64

3.3 创建脚本KeyboardHook,实现具体功能逻辑,代码如下

KeyboardHook

using System;
using System.Collections;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using UnityEngine;
using UnityEngine.UI;public class KeyboardHook : MonoBehaviour
{[UnmanagedFunctionPointer(CallingConvention.StdCall)]public delegate void KeyCallback(int vkCode);[DllImport("UnityDll.dll")]private static extern bool InstallHook(IntPtr hwnd, KeyCallback callback);[DllImport("UnityDll.dll")]private static extern void UninstallHook();private static KeyCallback callbackDelegate;private IntPtr _hwnd;public Text txt_NumberText;public Text txt_vkText;private int num = 0;private Dictionary<int, string> keyCodeToStringDic = new Dictionary<int, string>{// 字母键 (A-Z){ 65, "A" }, { 66, "B" }, { 67, "C" }, { 68, "D" }, { 69, "E" },{ 70, "F" }, { 71, "G" }, { 72, "H" }, { 73, "I" }, { 74, "J" },{ 75, "K" }, { 76, "L" }, { 77, "M" }, { 78, "N" }, { 79, "O" },{ 80, "P" }, { 81, "Q" }, { 82, "R" }, { 83, "S" }, { 84, "T" },{ 85, "U" }, { 86, "V" }, { 87, "W" }, { 88, "X" }, { 89, "Y" },{ 90, "Z" },// 数字键 (0-9){ 48, "0" }, { 49, "1" }, { 50, "2" }, { 51, "3" }, { 52, "4" },{ 53, "5" }, { 54, "6" }, { 55, "7" }, { 56, "8" }, { 57, "9" },// 数字小键盘 (NumPad 0-9){ 96, "NumPad 0" }, { 97, "NumPad 1" }, { 98, "NumPad 2" },{ 99, "NumPad 3" }, { 100, "NumPad 4" }, { 101, "NumPad 5" },{ 102, "NumPad 6" }, { 103, "NumPad 7" }, { 104, "NumPad 8" },{ 105, "NumPad 9" },// 功能键 (F1-F12){ 112, "F1" }, { 113, "F2" }, { 114, "F3" }, { 115, "F4" },{ 116, "F5" }, { 117, "F6" }, { 118, "F7" }, { 119, "F8" },{ 120, "F9" }, { 121, "F10" }, { 122, "F11" }, { 123, "F12" },// 方向键{ 38, "Up Arrow" }, { 40, "Down Arrow" },{ 37, "Left Arrow" }, { 39, "Right Arrow" },// 特殊键{ 27, "Escape" }, { 9, "Tab" }, { 20, "Caps Lock" },{ 16, "Shift" }, { 17, "Control" }, { 18, "Alt" },{ 91, "Left Windows" }, { 92, "Right Windows" },{ 93, "Application" }, { 32, "Space" }, { 13, "Enter" },{ 8, "Backspace" }, { 46, "Delete" }, { 45, "Insert" },{ 36, "Home" }, { 35, "End" }, { 33, "Page Up" },{ 34, "Page Down" }, { 44, "Print Screen" }, { 145, "Scroll Lock" },{ 19, "Pause" }, { 144, "Num Lock" },// 小键盘操作符{ 107, "NumPad +" }, { 109, "NumPad -" }, { 106, "NumPad *" },{ 111, "NumPad /" }, { 110, "NumPad ." },// 标点符号(美式键盘){ 186, ";:" }, { 187, "=+" }, { 188, ",<" },{ 189, "-_" }, { 190, ".>" }, { 191, "/?" },{ 192, "~`" }, { 219, "[{" }, { 220, "\\|" },{ 221, "]}" }, { 222, "'\"" },//鼠标按键{1, "Left Mouse Key" },{2, "Right Mouse Key" },{4, "Middle Mouse Key" },};private void Awake(){_hwnd = System.Diagnostics.Process.GetCurrentProcess().MainWindowHandle;callbackDelegate = OnKeyPressed;bool res = InstallHook(_hwnd, callbackDelegate);if(!res){Debug.LogError("钩子安装失败!");}else{Debug.Log("钩子安装成功!");}}private void OnDestroy(){UninstallHook();}private string GetKeyName(int vkCode){if(keyCodeToStringDic.ContainsKey(vkCode))return keyCodeToStringDic[vkCode];return "Null";}private void OnKeyPressed(int vkCode){string keyName = GetKeyName(vkCode);Debug.Log(vkCode);Debug.Log(KeyCode.W);Debug.Log((int)KeyCode.W);//设置Text文字内容if (txt_NumberText){txt_NumberText.text = (num++).ToString();}if(txt_vkText){txt_vkText.text = keyName;}}}

3.4 创建两个Text,一个记录点击键鼠次数,一个用于显示当前按下键鼠键位,创建空物体拖拽脚本,并将Text拖拽到脚本中

http://www.xdnf.cn/news/19869.html

相关文章:

  • ZooKeeper核心ZAB选举核心逻辑(大白话版)
  • Anaconda3 2025软件下载及安装教程
  • LangGraph(一):入门从0到1(零基础)
  • 使用Qt Charts实现高效多系列数据可视化
  • RabbitMQ模型详解与常见问题
  • 大数据开发/工程核心目标
  • 文心iRAG - 百度推出的检索增强的文生图技术,支持生成超真实图片
  • “AI 正回应时,也可随时打断?”揭秘 GPT Realtime × Gemini 的“全双工魔力”,都离不开它!
  • Python快速入门专业版(一):Windows/macOS/Linux 系统环境搭建(附常见报错解决)
  • postgresql9.2.4 跨版本升级14.6
  • 25高教社杯数模国赛【B题超高质量思路+问题分析】
  • 渲染是否伤电脑?从根源减少损伤的技巧
  • 字符串(1)
  • Bug 排查日记:一次曲折的技术解谜之旅
  • matlab 数据分析教程
  • 科学研究系统性思维的方法体系:质量控制
  • Redis C++ 实现笔记(F篇)
  • C/C++关键字——union
  • Python开篇撬动未来的万能钥匙 从入门到架构的全链路指南
  • 《IC验证必看|semaphore与mailbox的核心区别》
  • [从零开始面试算法] (11/100) LeetCode 226. 反转二叉树:递归的“镜像”魔法
  • RabbitMQ学习笔记
  • 找活招工系统源码 雇员雇主小程序 后端JAVA前端uniapp
  • 《云原生深坑实录:让团队卡壳的不是配置,是底层逻辑盲区》
  • 基于扣子平台构造AutoGen框架的多智能体使用-----封装成FastAPI接口供调用
  • JVM:程序计数器
  • 基于Matlab狭窄空间环境中多无人机自重构V字队形方法研究
  • 《清远市市级政务信息化服务项目立项审批细则(试行)》标准解读
  • Jenkins调用Ansible构建LNMP平台
  • 深入探索 WebSocket:构建实时应用的核心技术