Clipboard.GetText覆盖剪贴板? [英] Clipboard.GetText overrides clipboard?
问题描述
下面是我尝试做的事:
有一些游戏,当我按下Ctrl-C光标下写一些信息有关的项目到剪贴板。我试着去抓住这些信息,并选择一些东西,我从它的需要。
Im做这样的:
Here is what im trying to do: There is some game which writes some info about item under mouse cursor into clipboard when i press Ctrl-C. Im trying to grab that info and select some stuff i need from it. Im doing it like this:
//at form load
RegisterHotKey(this.Handle, 0, 0x002, (int)Keys.C);
protected override void WndProc(ref Message m)
{
if (m.Msg == 0x0312)
{
int id = m.WParam.ToInt32();
if (id == 0)
{
System.Threading.Thread.Sleep(155); //ive thought if i add some delay it would help but it doesnt...
string textFromClipboard = Clipboard.GetText();
if (textFromClipboard.Contains("Itemlevel: "))
{
// do some stuff with data IF it exists in clipboard, doesnt important what i do - i never get here
}
}
}
base.WndProc(ref m);
}
所以基本上,当我按下Ctrl-C在游戏中没有这个项目上 - 一切工作正常,信息剪贴板复制。当我打开程序 - 剪贴板保持相同的,因为这是我以前在游戏中按下Ctrl-C。我如何防止?我如何正确地得到剪贴板中的文本?也许我得到这个文本的方式是错误的? ?或者,也许已注册热键与游戏热键干扰所以它不工作了。
So basically, when i press Ctrl-C in-game without this program on - all works fine, info copied in clipboard. When i turn program on - clipboard stays same as it was before i press Ctrl-C in-game. How do i prevent this? How do i get text from clipboard correctly? Maybe the way i get this text is wrong? Or maybe that registered hotkey interferes with game hotkey so it doesn't work anymore?
更新:
伊夫想通了一些简单的解决方案,但是非常粗糙和野蛮。但它工作正常。
update: Ive figured out some simple solution, but very rough and barbaric. But it works fine.
public static void KeyDown(System.Windows.Forms.Keys key)
{
keybd_event((byte)key, 0x45, 0x0001 | 0, 0);
}
public static void KeyUp(System.Windows.Forms.Keys key)
{
keybd_event((byte)key, 0x45, 0x0001 | 0x0002, 0);
}
protected override void WndProc(ref Message m)
{
if (m.Msg == 0x0312)
{
int id = m.WParam.ToInt32();
if (id == 0)
{
ToggleHotkeys(false);
KeyDown(Keys.Control);
KeyDown(Keys.C);
KeyUp(Keys.C);
KeyUp(Keys.Control);
System.Threading.Thread.Sleep(155);
//if i comment this sleep - code executes too fast, making first Ctrl-C press
//capture nothing, second press outputs results for first item
//third press - for second item, ...
string textFromClipboard = Clipboard.GetText();
if (textFromClipboard.Contains("Itemlevel: "))
{
//do stuff with data
}
ToggleHotkeys(true);
}
}
base.WndProc(ref m);
}
也许有解决这个问题更聪明的方式?
Maybe there is more clever way to solve this problem?
推荐答案
我会用剪贴板监视,所以你可以得到通知,每当剪贴板的变化:
I would use a ClipBoard monitor so you can get notified whenever the ClipBoard changes:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace WindowsFormsApplication1
{
public partial class Form1 : Form
{
private ClipBoardMonitor cbm = null;
public Form1()
{
InitializeComponent();
cbm = new ClipBoardMonitor();
cbm.NewText += cbm_NewText;
}
private void cbm_NewText(string txt)
{
Console.WriteLine(txt);
}
}
public class ClipBoardMonitor : NativeWindow
{
private const int WM_DESTROY = 0x2;
private const int WM_DRAWCLIPBOARD = 0x308;
private const int WM_CHANGECBCHAIN = 0x30d;
[DllImport("user32.dll")]
static extern IntPtr SetClipboardViewer(IntPtr hWndNewViewer);
[DllImport("user32.dll")]
static extern bool ChangeClipboardChain(IntPtr hWndRemove, IntPtr hWndNewNext);
[DllImport("user32.dll", CharSet = CharSet.Auto)]
private static extern IntPtr SendMessage(IntPtr hWnd, int Msg, IntPtr wParam, IntPtr lParam);
public event NewTextEventHandler NewText;
public delegate void NewTextEventHandler(string txt);
private IntPtr NextClipBoardViewerHandle;
public ClipBoardMonitor()
{
this.CreateHandle(new CreateParams());
NextClipBoardViewerHandle = SetClipboardViewer(this.Handle);
}
protected override void WndProc(ref Message m)
{
switch (m.Msg)
{
case WM_DRAWCLIPBOARD:
if (Clipboard.ContainsText())
{
if (NewText != null)
{
NewText(Clipboard.GetText());
}
}
SendMessage(NextClipBoardViewerHandle, m.Msg, m.WParam, m.LParam);
break;
case WM_CHANGECBCHAIN:
if (m.WParam.Equals(NextClipBoardViewerHandle))
{
NextClipBoardViewerHandle = m.LParam;
}
else if (!NextClipBoardViewerHandle.Equals(IntPtr.Zero))
{
SendMessage(NextClipBoardViewerHandle, m.Msg, m.WParam, m.LParam);
}
break;
case WM_DESTROY:
ChangeClipboardChain(this.Handle, NextClipBoardViewerHandle);
break;
}
base.WndProc(ref m);
}
}
}
这篇关于Clipboard.GetText覆盖剪贴板?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!