34using System.Collections.Generic;
35using System.Runtime.InteropServices;
297 [StructLayout(LayoutKind.Sequential)]
306 [StructLayout(LayoutKind.Sequential)]
317 return "(" +
x +
", " +
y +
")";
322 [StructLayout(LayoutKind.Sequential)]
333 [StructLayout(LayoutKind.Sequential)]
338 public RECT(
int left,
int top,
int right,
int bottom)
351 public delegate IntPtr
HookProc(
int code, IntPtr wParam, ref
MSG lParam);
354#if UNITY_STANDALONE_WIN || UNITY_EDITOR_WIN
356 public static class Window
358 [DllImport(
"user32.dll")]
359 public static extern bool EnumThreadWindows(uint dwThreadId,
EnumThreadDelegate lpfn, IntPtr lParam);
361 [DllImport(
"user32.dll", SetLastError =
true)]
362 public static extern bool GetWindowRect(IntPtr hwnd, out
RECT lpRect);
364 [DllImport(
"user32.dll")]
365 public static extern bool IsWindowVisible(IntPtr hWnd);
367 [DllImport(
"user32.dll", SetLastError =
true, CharSet = CharSet.Auto)]
368 static extern int GetClassName(IntPtr hWnd, System.Text.StringBuilder lpClassName,
int nMaxCount);
369 public static string GetClassName(IntPtr hWnd)
371 var sb =
new System.Text.StringBuilder(256);
372 int count = GetClassName(hWnd, sb, 256);
373 return sb.ToString(0, count);
376 [DllImport(
"user32.dll", SetLastError =
true, CharSet = CharSet.Auto)]
377 static extern int GetWindowTextLength(IntPtr hWnd);
378 [DllImport(
"user32.dll", CharSet = CharSet.Unicode, SetLastError =
true)]
379 static extern int GetWindowText(IntPtr hWnd, System.Text.StringBuilder lpString,
int nMaxCount);
380 public static string GetWindowText(IntPtr hWnd)
382 int length = GetWindowTextLength(hWnd) + 2;
383 var sb =
new System.Text.StringBuilder(length);
384 int count = GetWindowText(hWnd, sb, length);
385 return sb.ToString(0, count);
389 public static class WinAPI
391 [DllImport(
"kernel32.dll", CharSet = CharSet.Auto)]
392 public static extern IntPtr GetModuleHandle(
string lpModuleName);
393 [DllImport(
"kernel32.dll")]
394 public static extern uint GetCurrentThreadId();
396 [DllImport(
"user32.dll", SetLastError =
true)]
397 public static extern IntPtr SetWindowsHookEx(
HookType hookType,
HookProc lpfn, IntPtr hMod, uint dwThreadId);
398 [DllImport(
"user32.dll", SetLastError =
true)]
399 public static extern bool UnhookWindowsHookEx(IntPtr hhk);
400 [DllImport(
"user32.dll")]
401 public static extern IntPtr CallNextHookEx(IntPtr hhk,
int nCode, IntPtr wParam, ref MSG lParam);
403 [DllImport(
"shell32.dll")]
404 public static extern void DragAcceptFiles(IntPtr hwnd,
bool fAccept);
405 [DllImport(
"shell32.dll", CharSet = CharSet.Unicode)]
406 public static extern uint DragQueryFile(IntPtr hDrop, uint iFile, System.Text.StringBuilder lpszFile, uint cch);
407 [DllImport(
"shell32.dll")]
408 public static extern void DragFinish(IntPtr hDrop);
410 [DllImport(
"shell32.dll")]
411 public static extern void DragQueryPoint(IntPtr hDrop, out POINT pos);
416 public static class UnityDragAndDropHook
418 public delegate
void DroppedFilesEvent(List<string> aPathNames, POINT aDropPoint);
419 public static event DroppedFilesEvent OnDroppedFiles;
421#if UNITY_STANDALONE_WIN && !UNITY_EDITOR_WIN
423 private static uint threadId;
424 private static IntPtr mainWindow = IntPtr.Zero;
425 private static IntPtr m_Hook;
426 private static string m_ClassName =
"UnityWndClass";
430 private static bool EnumCallback(IntPtr W, IntPtr _)
432 if (Window.IsWindowVisible(W) && (mainWindow == IntPtr.Zero || (m_ClassName !=
null && Window.GetClassName(W) == m_ClassName)))
439 public static void InstallHook()
441 threadId = WinAPI.GetCurrentThreadId();
443 Window.EnumThreadWindows(threadId, EnumCallback, IntPtr.Zero);
445 var hModule = WinAPI.GetModuleHandle(
null);
446 m_Hook = WinAPI.SetWindowsHookEx(
HookType.WH_GETMESSAGE,
Callback, hModule, threadId);
448 WinAPI.DragAcceptFiles(mainWindow,
true);
450 public static void UninstallHook()
452 WinAPI.UnhookWindowsHookEx(m_Hook);
453 WinAPI.DragAcceptFiles(mainWindow,
false);
454 m_Hook = IntPtr.Zero;
458 [AOT.MonoPInvokeCallback(typeof(
HookProc))]
459 private static IntPtr
Callback(
int code, IntPtr wParam, ref MSG lParam)
461 if (code == 0 && lParam.message ==
WM.DROPFILES)
464 WinAPI.DragQueryPoint(lParam.wParam, out pos);
467 uint n = WinAPI.DragQueryFile(lParam.wParam, 0xFFFFFFFF,
null, 0);
468 var sb =
new System.Text.StringBuilder(1024);
470 List<string> result =
new List<string>();
471 for (uint i = 0; i < n; i++)
473 int len = (int)WinAPI.DragQueryFile(lParam.wParam, i, sb, 1024);
474 result.Add(sb.ToString(0, len));
477 WinAPI.DragFinish(lParam.wParam);
478 if (OnDroppedFiles !=
null)
479 OnDroppedFiles(result, pos);
481 return WinAPI.CallNextHookEx(m_Hook, code, wParam, ref lParam);
484 public static void InstallHook()
487 public static void UninstallHook()
@ DWMWINDOWMAXIMIZEDCHANGE
@ DWMCOLORIZATIONCOLORCHANGED
delegate IntPtr HookProc(int code, IntPtr wParam, ref MSG lParam)
delegate bool EnumThreadDelegate(IntPtr Hwnd, IntPtr lParam)
override string ToString()
RECT(int left, int top, int right, int bottom)
override string ToString()