mirror of
https://github.com/ClassiCube/ClassiCube.git
synced 2025-09-24 05:10:42 -04:00
Ungroup multiple instances from taskbar, use native pinvoke for clipboard.
This commit is contained in:
parent
ad7c213630
commit
bf19bae85a
@ -57,13 +57,13 @@ namespace ClassicalSharp {
|
||||
// TODO: retry when clipboard returns null.
|
||||
public string ClipboardText {
|
||||
get {
|
||||
if (OpenTK.Configuration.RunningOnMacOS)
|
||||
if (!OpenTK.Configuration.RunningOnLinux)
|
||||
return GetClipboardText();
|
||||
else
|
||||
return Clipboard.GetText();
|
||||
}
|
||||
set {
|
||||
if (OpenTK.Configuration.RunningOnMacOS)
|
||||
if (!OpenTK.Configuration.RunningOnLinux)
|
||||
SetClipboardText(value);
|
||||
else
|
||||
Clipboard.SetText(value);
|
||||
|
@ -3,7 +3,7 @@
|
||||
* Contributions from Erik Ylvisaker
|
||||
* See license.txt for license info
|
||||
*/
|
||||
#endregion
|
||||
#endregion
|
||||
|
||||
using System;
|
||||
using System.Drawing;
|
||||
@ -16,6 +16,9 @@ namespace OpenTK.Platform.Windows {
|
||||
|
||||
internal static class API {
|
||||
|
||||
[DllImport("shell32.dll")]
|
||||
public static extern int SetCurrentProcessExplicitAppUserModelID([MarshalAs(UnmanagedType.LPWStr)] string AppID);
|
||||
|
||||
[DllImport("user32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern bool SetWindowPos(IntPtr handle, IntPtr insertAfter, int x, int y, int cx, int cy, SetWindowPosFlags flags);
|
||||
|
||||
@ -27,10 +30,10 @@ namespace OpenTK.Platform.Windows {
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern IntPtr CreateWindowEx(ExtendedWindowStyle ExStyle, IntPtr ClassAtom, IntPtr WindowName, WindowStyle Style,
|
||||
int X, int Y, int Width, int Height, IntPtr HandleToParentWindow, IntPtr Menu, IntPtr Instance, IntPtr Param);
|
||||
int X, int Y, int Width, int Height, IntPtr HandleToParentWindow, IntPtr Menu, IntPtr Instance, IntPtr Param);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern bool DestroyWindow(IntPtr windowHandle);
|
||||
internal static extern bool DestroyWindow(IntPtr windowHandle);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern ushort RegisterClassEx(ref ExtendedWindowClass window_class);
|
||||
@ -80,6 +83,7 @@ namespace OpenTK.Platform.Windows {
|
||||
[DllImport("User32.dll", CharSet = CharSet.Auto), SuppressUnmanagedCodeSecurity]
|
||||
public extern static IntPtr DefWindowProc(IntPtr hWnd, WindowMessage msg, IntPtr wParam, IntPtr lParam);
|
||||
|
||||
|
||||
[DllImport("user32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern IntPtr GetDC(IntPtr hwnd);
|
||||
|
||||
@ -97,6 +101,7 @@ namespace OpenTK.Platform.Windows {
|
||||
|
||||
[DllImport("gdi32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern bool SwapBuffers(IntPtr dc);
|
||||
|
||||
|
||||
[DllImport("kernel32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern IntPtr LoadLibrary(string dllName);
|
||||
@ -104,9 +109,6 @@ namespace OpenTK.Platform.Windows {
|
||||
[DllImport("kernel32", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern IntPtr GetProcAddress(IntPtr hModule, string procName);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern uint MapVirtualKey(VirtualKeys vkey, MapVirtualKeyType uMapType);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern bool ShowWindow(IntPtr hWnd, ShowWindowCommand nCmdShow);
|
||||
|
||||
@ -120,9 +122,6 @@ namespace OpenTK.Platform.Windows {
|
||||
[DllImport("user32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
public static extern bool IsWindowVisible(IntPtr intPtr);
|
||||
|
||||
[DllImport("user32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
public static extern IntPtr LoadCursor(IntPtr hInstance, IntPtr lpCursorName);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
public static extern bool SetForegroundWindow(IntPtr hWnd);
|
||||
|
||||
@ -137,6 +136,38 @@ namespace OpenTK.Platform.Windows {
|
||||
internal static extern bool EnumDisplaySettings([MarshalAs(UnmanagedType.LPTStr)] string device_name,
|
||||
int graphics_mode, [In, Out] DeviceMode device_mode);
|
||||
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
public static extern bool OpenClipboard(IntPtr hWndNewOwner);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
public static extern bool EmptyClipboard();
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
public static extern bool CloseClipboard();
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
public static extern IntPtr GetClipboardData(uint uFormat);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
public static extern IntPtr SetClipboardData(uint uFormat, IntPtr hMem);
|
||||
|
||||
[DllImport("kernel32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
public static extern IntPtr GlobalAlloc(uint uFlags, UIntPtr dwBytes);
|
||||
|
||||
[DllImport("kernel32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
public static extern IntPtr GlobalFree(IntPtr hMem);
|
||||
|
||||
[DllImport("kernel32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
public static extern IntPtr GlobalLock(IntPtr hMem);
|
||||
|
||||
[DllImport("kernel32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
public static extern bool GlobalUnlock(IntPtr hMem);
|
||||
|
||||
|
||||
[DllImport("user32.dll"), SuppressUnmanagedCodeSecurity]
|
||||
public static extern IntPtr LoadCursor(IntPtr hInstance, IntPtr lpCursorName);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
public static extern bool TrackMouseEvent(ref TrackMouseEventStructure lpEventTrack);
|
||||
|
||||
@ -151,6 +182,9 @@ namespace OpenTK.Platform.Windows {
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern ushort GetKeyState( int code );
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true), SuppressUnmanagedCodeSecurity]
|
||||
internal static extern uint MapVirtualKey(VirtualKeys vkey, MapVirtualKeyType uMapType);
|
||||
}
|
||||
|
||||
internal struct Constants {
|
||||
@ -302,7 +336,7 @@ namespace OpenTK.Platform.Windows {
|
||||
|
||||
internal static int SizeInBytes = Marshal.SizeOf(default(WindowClass));
|
||||
}
|
||||
|
||||
|
||||
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
|
||||
struct ExtendedWindowClass
|
||||
{
|
||||
@ -507,7 +541,7 @@ namespace OpenTK.Platform.Windows {
|
||||
DRAW_TO_WINDOW = 0x04,
|
||||
SUPPORT_OPENGL = 0x20,
|
||||
DEPTH_DONTCARE = 0x20000000,
|
||||
}
|
||||
}
|
||||
|
||||
internal enum PixelType : byte {
|
||||
RGBA = 0,
|
||||
@ -623,11 +657,11 @@ namespace OpenTK.Platform.Windows {
|
||||
}
|
||||
|
||||
enum MouseKeys {
|
||||
None = 0x00, //No mouse button was pressed.
|
||||
Left = 0x01, // The left mouse button was pressed.
|
||||
Right = 0x02, // The right mouse button was pressed.
|
||||
Middle = 0x10, // The middle mouse button was pressed.
|
||||
XButton1 = 0x20, // The first XButton was pressed.
|
||||
None = 0x00, //No mouse button was pressed.
|
||||
Left = 0x01, // The left mouse button was pressed.
|
||||
Right = 0x02, // The right mouse button was pressed.
|
||||
Middle = 0x10, // The middle mouse button was pressed.
|
||||
XButton1 = 0x20, // The first XButton was pressed.
|
||||
XButton2 = 0x40, // The second XButton was pressed.
|
||||
}
|
||||
|
||||
|
@ -29,6 +29,7 @@ using System;
|
||||
using System.Drawing;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using OpenTK.Input;
|
||||
|
||||
namespace OpenTK.Platform.Windows
|
||||
@ -64,9 +65,17 @@ namespace OpenTK.Platform.Windows
|
||||
|
||||
public WinGLNative(int x, int y, int width, int height, string title, DisplayDevice device) {
|
||||
WindowProcedureDelegate = WindowProcedure;
|
||||
UngroupFromTaskbar();
|
||||
window = new WinWindowInfo(CreateWindow(x, y, width, height, title, device));
|
||||
exists = true;
|
||||
}
|
||||
|
||||
void UngroupFromTaskbar() {
|
||||
Version version = Environment.OSVersion.Version;
|
||||
if ((version.Major > 6) || (version.Major == 6 && version.Minor >= 1)) {
|
||||
API.SetCurrentProcessExplicitAppUserModelID("ClassicalSharp_" + new Random().Next());
|
||||
}
|
||||
}
|
||||
|
||||
unsafe IntPtr WindowProcedure(IntPtr handle, WindowMessage message, IntPtr wParam, IntPtr lParam) {
|
||||
switch (message) {
|
||||
@ -438,9 +447,55 @@ namespace OpenTK.Platform.Windows
|
||||
suppress_resize--;
|
||||
}
|
||||
|
||||
public string GetClipboardText() { return ""; }
|
||||
const uint GMEM_MOVEABLE = 2;
|
||||
const uint CF_UNICODETEXT = 13;
|
||||
public unsafe string GetClipboardText() {
|
||||
// retry up to 10 times
|
||||
for (int i = 0; i < 10; i++) {
|
||||
if (API.OpenClipboard(window.WindowHandle)) {
|
||||
IntPtr hGlobal = API.GetClipboardData(CF_UNICODETEXT);
|
||||
if (hGlobal == IntPtr.Zero) { API.CloseClipboard(); return ""; }
|
||||
|
||||
IntPtr src = API.GlobalLock(hGlobal);
|
||||
string value = new String((char*)src);
|
||||
API.GlobalUnlock(hGlobal);
|
||||
|
||||
API.CloseClipboard();
|
||||
return value;
|
||||
}
|
||||
Thread.Sleep(100);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
public void SetClipboardText( string value ) { }
|
||||
public unsafe void SetClipboardText( string value ) {
|
||||
UIntPtr dstSize = (UIntPtr)((value.Length + 1) * Marshal.SystemDefaultCharSize);
|
||||
// retry up to 10 times
|
||||
for (int i = 0; i < 10; i++) {
|
||||
if (API.OpenClipboard(window.WindowHandle)) {
|
||||
IntPtr hGlobal = API.GlobalAlloc(GMEM_MOVEABLE, dstSize);
|
||||
if (hGlobal == IntPtr.Zero) { API.CloseClipboard(); return; }
|
||||
|
||||
IntPtr dst = API.GlobalLock(hGlobal);
|
||||
fixed (char* src = value) {
|
||||
CopyString((IntPtr)src, dst, value.Length);
|
||||
}
|
||||
API.GlobalUnlock(hGlobal);
|
||||
|
||||
API.EmptyClipboard();
|
||||
API.SetClipboardData(CF_UNICODETEXT, hGlobal);
|
||||
API.CloseClipboard();
|
||||
return;
|
||||
}
|
||||
Thread.Sleep(100);
|
||||
}
|
||||
}
|
||||
|
||||
unsafe static void CopyString(IntPtr src, IntPtr dst, int numChars) {
|
||||
char* src2 = (char*)src, dst2 = (char*)dst;
|
||||
for (int i = 0; i < numChars; i++) { dst2[i] = src2[i]; }
|
||||
dst2[numChars] = '\0';
|
||||
}
|
||||
|
||||
public Rectangle Bounds {
|
||||
get { return bounds; }
|
||||
|
Loading…
x
Reference in New Issue
Block a user