The program is working at background and listening keyboard(like keylogger)
First I select a string on pdf or etc. Then I pressed the ctrl + rbutton the program must be pop up and it can be get my selected string.
For this;
[DllImport("User32.dll")]
private static extern short GetAsyncKeyState(System.Windows.Forms.Keys vKey);
[DllImport("User32.dll")]
private static extern short GetAsyncKeyState(System.Int32 vKey);
string key = "";
private void timer1_Tick(object sender, EventArgs e)
{
timer1.Interval = 5;
foreach (System.Int32 i in Enum.GetValues(typeof(Keys)))
{
int x = GetAsyncKeyState(i);
if ((x == 1) || (x == -32767))
{
keyBuffer += Enum.GetName(typeof(Keys), i);
}
}
if (keyBuffer != "")
{
keyBuffer = keyBuffer.ToLower();
if (keyBuffer.Contains("lcontrolkeyrbutton"))
{
// do somethings
keyBuffer = "";
}
}
}
But after first performing, ctrl + rbutton it doesn't work. What's the wrong? And how can i get the selected string into my program?
Sounds like you want a clipboard hook (in addition to your global key hook). Take a look here: Clipboard event C#
If you want to capture the string without the user copying it into the clipboard manually, you could send ctrl+c to the application yourself: http://msdn.microsoft.com/en-us/library/system.windows.forms.sendkeys.aspx
You need to SendKeyEvent(Ctrl+C) of MainWindowsHandle First, then Using Clipboard capture your text to your Project.
Here is the program funcional and tested
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace CtrLetterCopy
{
public partial class Form1 : Form
{
[DllImport("user32.dll")]
private static extern bool RegisterHotKey(IntPtr hWnd, int id, int fsModifiers, int vk);
[DllImport("user32.dll")]
private static extern bool UnregisterHotKey(IntPtr hWnd, int id);
const int WM_COMMAND = 0x111;
enum KeyModifier
{
None = 0,
Alt = 1,
Control = 2,
Shift = 4,
WinKey = 8
}
public Form1()
{
InitializeComponent();
this.ShowInTaskbar = false;
int id_Ctrl = 0; // The id of the hotkey.
RegisterHotKey(this.Handle, id_Ctrl, (int)KeyModifier.Control, Keys.R.GetHashCode());
}
protected override void WndProc(ref Message m)
{
//const int WM_HOTKEY = 0x0312;
if (m.Msg == 0x0312)
{
if (m.WParam.ToInt32() == 0)
{
//do what you want here
SendKeyEvent();
}
}
base.WndProc(ref m);
}
private void SendKeyEvent()
{
SendKeys.SendWait("^c");
Thread.Sleep(500);
string test3 = Clipboard.GetText();
MessageBox.Show(test3);
}
}
}
Download and check out this code here:
http://www.codeproject.com/KB/cs/globalhook.aspx
Pre-tested, well-written and fully functional.
Best of luck!
Related
I'm trying to make a program that opens a browser on each multi-display.
When I did it with a notepad, it worked. However, when it's a browser didn't work and showed the error "System.InvalidOperationException: Process must exit before requested information can be determined". I will appreciate your help with this situation.
This is my code:
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;
namespace WindowsFormsApp5
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern int MoveWindow(IntPtr hwnd, int x, int y,
int nWidth, int nHeight, int bRepaint);
private void Form1_Load(object sender, EventArgs e)
{
foreach (Screen item in Screen.AllScreens)
{
//Open a web browser
System.Diagnostics.Process process1 = System.Diagnostics.Process.Start("C:\\Program Files (x86)\\Microsoft\\Edge\\Application\\msedge.exe");
//System.Diagnostics.Process process2 = System.Diagnostics.Process.Start("notepad.exe");
process1.WaitForInputIdle();
//process2.WaitForInputIdle();
//Move the browser window
MoveWindow(process1.MainWindowHandle, item.Bounds.X, item.Bounds.Y, item.Bounds.Width, item.Bounds.Height, 1);
//MoveWindow(process2.MainWindowHandle, item.Bounds.X, item.Bounds.Y, item.Bounds.Width, item.Bounds.Height, 1);
}
}
}
}
It seems that msedge.exe use a host process to start different tabs, so we can't use the created process ID to handle it.
Compare created process ID with processes in the Task Manager, the
process 38756 is missing.
Another tool to browse edge relative processes is the built-in task manager of edge.
We can't find process 38756 as well.
So re-search the target edge process is necessary.
This repo https://github.com/alex-tomin/Tomin.Tools.KioskMode demostrate how to move chrome window into different monitors and set as full screen.
I tried to extract the necessary and modify your code like below, hope it helps:
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Runtime.InteropServices;
using System.Windows.Forms;
namespace TestWinFormsApp
{
// Get full definition of SetWindowPosFlags here:
// https://www.pinvoke.net/default.aspx/Enums/SetWindowPosFlags.html
[Flags]
public enum SetWindowPosFlags : uint
{
SWP_NOREDRAW = 0x0008,
SWP_NOZORDER = 0x0004
}
// Get full definition of ShowWindowCommands here:
// https://www.pinvoke.net/default.aspx/Enums/ShowWindowCommand.html
public enum ShowWindowCommands
{
Maximize = 3,
Restore = 9,
}
public static class WinApi
{
[DllImport("user32.dll", SetLastError = true)]
public static extern bool SetWindowPos(IntPtr hWnd, IntPtr hWndInsertAfter, int X, int Y, int cx, int cy, SetWindowPosFlags uFlags);
[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
public static extern bool ShowWindow(IntPtr hWnd, ShowWindowCommands nCmdShow);
}
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load_1(object sender, EventArgs e)
{
var ignoreHandles = new List<IntPtr>();
foreach (Screen item in Screen.AllScreens)
{
this.StartEdgeProcess();
var windowHandle = this.GetWindowHandle("msedge", ignoreHandles);
ignoreHandles.Add(windowHandle);
WinApi.ShowWindow(windowHandle, ShowWindowCommands.Restore);
WinApi.SetWindowPos(windowHandle, IntPtr.Zero, item.Bounds.Left, item.Bounds.Top, 800, 600, SetWindowPosFlags.SWP_NOZORDER | SetWindowPosFlags.SWP_NOREDRAW);
WinApi.ShowWindow(windowHandle, ShowWindowCommands.Maximize);
}
}
private void StartEdgeProcess()
{
var process = new Process();
process.StartInfo.FileName = "C:\\Program Files (x86)\\Microsoft\\Edge\\Application\\msedge.exe";
process.StartInfo.Arguments = "about:blank" + " --new-window -inprivate ";
process.Start();
process.WaitForInputIdle();
}
private IntPtr GetWindowHandle(string processName, List<IntPtr> ignoreHandlers)
{
IntPtr? windowHandle = null;
while (windowHandle == null)
{
windowHandle = Process.GetProcesses()
.FirstOrDefault(process => process.ProcessName == processName
&& process.MainWindowHandle != IntPtr.Zero
&& !string.IsNullOrWhiteSpace(process.MainWindowTitle)
&& !ignoreHandlers.Contains(process.MainWindowHandle))
?.MainWindowHandle;
}
return windowHandle.Value;
}
}
}
(I am an novice/beginner when it comes to C# and Winform)
I have a Windows Forms application with 2 forms. The first form is transparent and is just there to show and hide the second form. The second form is an "Overlay" with some buttons. I have a hotkey to open the second form but I can't get it to close the second form with a hotkey. I have tried some different things and googled a lot. The purpose with this application is to open the overlay menu and from that menu you can switch between applications.
Form1.cs
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;
using System.Diagnostics;
namespace WindowsFormsApp2
{
public partial class Form1 : Form
{
//Click thurgh
[DllImport("user32.dll")]
static extern int SetWindowLong(IntPtr Hwnd, int nIndex, int dwNewLong);
[DllImport("user32.dll")]
static extern int GetWindowLong(IntPtr hWnd, int nIndex);
//
//Hotkey
[DllImport("user32.dll")]
public static extern IntPtr FindWindow(String sClassName, String sAppName);
private IntPtr thisWindow;
private Hotkey hotkey;
//
FormOverlay frm = new FormOverlay();
public Form1()
{
InitializeComponent();
this.BackColor = Color.LimeGreen;
this.TransparencyKey = Color.LimeGreen;
this.TopMost = true;
this.FormBorderStyle = FormBorderStyle.None;
int initialStyle = GetWindowLong(this.Handle, -20);
SetWindowLong(this.Handle, -20, initialStyle | 0x80000 | 0x20);
}
private void Form1_Load(object sender, EventArgs e)
{
thisWindow = FindWindow(null, "Form1");
hotkey = new Hotkey(thisWindow);
hotkey.RegisterHotKeys();
}
private void Form1_FormClosed(object sender, FormClosedEventArgs e)
{
hotkey.UnRegisterHotKeys();
}
protected override void WndProc(ref Message keyPressed)
{
Process[] pname = Process.GetProcessesByName("FormOverlay");
if (keyPressed.Msg == 0x0312)
{
if (pname.Length > 0) //my latest try
{
frm.Hide();
MessageBox.Show("1");
}
else
{
frm.Show();
}
}
base.WndProc(ref keyPressed);
}
}
}
Hotkey.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;
using System.Windows.Forms;
namespace WindowsFormsApp2
{
class Hotkey
{
public enum fsModifiers
{
Alt = 0x0001,
Control = 0x0002,
Shift = 0x0004,
Window = 0x0008,
}
private IntPtr _hWnd;
public Hotkey(IntPtr hWnd)
{
this._hWnd = hWnd;
}
public void RegisterHotKeys()
{
RegisterHotKey(_hWnd, 1, (uint)fsModifiers.Control, (uint)Keys.G);
}
public void UnRegisterHotKeys()
{
UnregisterHotKey(_hWnd, 1);
UnregisterHotKey(_hWnd, 2);
}
#region WindowsAPI
[DllImport("user32.dll")]
private static extern bool RegisterHotKey(IntPtr hWnd, int id, uint fsModifiers, uint vk);
[DllImport("user32.dll")]
private static extern bool UnregisterHotKey(IntPtr hWnd, int id);
#endregion
}
}
If you have any documentation, article, video or tutorial that contains your answer please post it, too, so I don't ask too many questions in the comments.
I've been trying to figure this out for a very long time now; I've searched this several times and read more articles and questions on this than I can recall and I can't seem to figure out exactly what's going wrong. This is a small program that I've been trying to compile to test generating a hotkey to be used by an application.
The source for the test I've been trying to figure out is as follows:
using System;
using System.Windows.Forms;
using System.Drawing;
using System.Runtime.InteropServices;
namespace Prg
{
class MainClass
{
[DllImport("User32.dll")]
private static extern int RegisterHotKey(IntPtr hWnd, int id, int
fsModifiers, int vk);
[DllImport("User32.dll")]
private static extern int UnregisterHotKey(IntPtr hWnd, int id);
public static Form f1 = new Form();
public static int Register(Form f)
{
IntPtr ip = f.Handle;
return RegisterHotKey(ip, 1, 0, (int)Keys.Escape);
}
public static void b1_click(object sender, EventArgs e)
{
//Blah Blah stuff
}
protected override void WndProc(ref Message m)
{
if (m.Msg == 0x0312)
{
MessageBox.Show("wow");
}
base.WndProc(ref m);
}
public static void Main()
{
Button b1 = new Button();
b1.Location = new Point(10, 10);
b1.Text = "wow";
b1.Click += new EventHandler(b1_click);
f1.Width = 200;
f1.Height = 200;
f1.Controls.Add(b1);
f1.ShowDialog();
Register(f1);
}
}
}
I have been compiling with csc.exe using C# 4.0. Every time I try and compile this, or similar code, I keep getting this error:
Main.csx(37,27): error CS0115:
'Prg.MainClass.WndProc(System.Windows.Forms.Message)': no suitable method found to override
Every example of using User32.dll to register a hotkey has had the "protected override WndProc" method inside it and everyone has been saying it worked just fine for them, but I can't figure out why it won't work for the life of me. If someone could help me solve this problem it would be greatly appreciated. I'm using Windows 7 Professional 64-bit, and the path to csc.exe is C:\Windows\Microsoft.NET\Framework\v4.0.30319\csc.exe
Thanks :)
Edit
I've gotten it to compile now, However the issue now is that it doesn't seem to be registering and kind of hotkey or at least not picking up the KeyPress at all. Is there an error in my code?
using System;
using System.Windows.Forms;
using System.Drawing;
using System.Runtime.InteropServices;
namespace Prg
{
class MainClass : Form
{
[DllImport("User32.dll")]
private static extern int RegisterHotKey(IntPtr hWnd, int id, int
fsModifiers, int vk);
[DllImport("User32.dll")]
private static extern int UnregisterHotKey(IntPtr hWnd, int id);
public static Form f1 = new Form();
public static int Register(Form f)
{
IntPtr ip = f.Handle;
return RegisterHotKey(ip, 1, 0, (int)Keys.Escape);
}
public static void b1_click(object sender, EventArgs e)
{
//Blah Blah stuff
}
protected override void WndProc(ref Message m)
{
if (m.Msg == 0x0312)
{
MessageBox.Show("wow");
}
base.WndProc(ref m);
}
public static void Main()
{
Button b1 = new Button();
b1.Location = new Point(10, 10);
b1.Text = "wow";
b1.Click += new EventHandler(b1_click);
f1.Width = 200;
f1.Height = 200;
f1.Controls.Add(b1);
f1.ShowDialog();
Register(f1);
}
}
}
I've tried several different solutions but none of them have gotten the Hot Key to work at all. I've even tried re-writing the source to use Application.Run(new MainClass()); but it still didn't detect the Keypress even when the form was focused.
Edit
The Problem is solved thanks to zzxyz for helping get it to compile, and Antoine for helping me fix my mistakes in the code. Thanks guys. This is the code that compiles and works, for anyone who may have had the same problems or just prefers to learn by example. Thanks again.
using System;
using System.Windows.Forms;
using System.Drawing;
using System.Runtime.InteropServices;
namespace Prg
{
class MainClass : Form
{
[DllImport("User32.dll")]
private static extern int RegisterHotKey(IntPtr hWnd, int id, int
fsModifiers, int vk);
[DllImport("User32.dll")]
private static extern int UnregisterHotKey(IntPtr hWnd, int id);
public static MainClass f1 = new MainClass();
public static int Register(Form f)
{
IntPtr ip = f.Handle;
return RegisterHotKey(ip, 1, 0, (int)Keys.Escape);
}
public static void b1_click(object sender, EventArgs e)
{
//Blah Blah stuff
}
protected override void WndProc(ref Message m)
{
if (m.Msg == 0x0312)
{
MessageBox.Show("wow");
}
base.WndProc(ref m);
}
public static void Main()
{
Button b1 = new Button();
b1.Location = new Point(10, 10);
b1.Text = "wow";
b1.Click += new EventHandler(b1_click);
f1.Width = 200;
f1.Height = 200;
f1.Controls.Add(b1);
Register(f1);
f1.ShowDialog();
}
}
}
2 mistakes:
you must register the hotkeys before showing your f1. Swap the last 2 lines
currently, you override WndProc for MainClass, not for every form. So your form f1 inherits the base Form.WndProc, not your overriden one. So just declare f1 as MainClass, and it will work.
this is kinda strange for me. I made a dummy c# program in my house a while ago (PC) and it worked 100%, I mean the hotkeys. Numlock and Capslock worked perfectly fine. Now, I'm continuing my program here in my laptop, and apparently the RegisterHotKey function makes my capslock stuck. NUMLOCK in my laptop works so fine.
For instance, before I run my program, I check in my notepad if my capslock is on, so I'm gonna type a letter, say the capslock is confirmed to be ON. And then I'm going to run the program, I press the capslock and then type a letter in notepad. The result is that the last state of the capslock before I run the program REMAINS the same. Even if I press capslock many times again. Lastly, if I comment out the line RegisterHotKey(...., 0x14 for CAPSLOCK); and then turning off and on the capslock works fine. And if I stop the program, capslock works fine too.
take note that my laptop has no led indicator for the lock keys.
Whole codes:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Interop;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Windows.Threading;
namespace CapslockNotifier
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
DispatcherTimer timer;
[DllImport("user32.dll")]
private static extern bool RegisterHotKey(IntPtr hWnd, int id, uint fsModifiers, uint vk);
[DllImport("user32.dll")]
private static extern bool UnregisterHotKey(IntPtr hWnd, int id);
private const int HOTKEY_ID = 9000;
private const uint VK_NUMLOCK = 0x90;
private const uint MOD_CTRL = 0;
private const uint VK_CAPITAL = 0x14;
public MainWindow()
{
MouseDown += delegate { DragMove(); };
InitializeComponent();
}
private void mainForm_Loaded(object sender, RoutedEventArgs e)
{
timer = new DispatcherTimer();
timer.Interval = TimeSpan.FromMilliseconds(2000);
timer.Tick += timer_Tick;
}
private void timer_Tick(object sender, EventArgs e)
{
Popup1.IsOpen = false;
timer.Stop();
}
HwndSource source;
protected override void OnSourceInitialized(EventArgs e)
{
base.OnSourceInitialized(e);
IntPtr handle = new WindowInteropHelper(this).Handle;
source = HwndSource.FromHwnd(handle);
source.AddHook(HwndHook);
RegisterHotKey(handle, HOTKEY_ID, MOD_CTRL, VK_CAPITAL); //caps lock
RegisterHotKey(handle, HOTKEY_ID, MOD_CTRL, VK_NUMLOCK); //num lock
//
}
private IntPtr HwndHook(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handled)
{
const int WM_HOTKEY = 0x0312;
switch (msg)
{
case WM_HOTKEY:
switch (wParam.ToInt32())
{
case HOTKEY_ID:
int vkey = (((int)lParam >> 16) & 0xFFFF);
if (vkey == VK_CAPITAL)
{
if (Console.CapsLock == true)
{
McTextBlock.Text = "Capslock is ON";
Popup1.IsOpen = true;
timer.Start();
//MessageBox.Show("capslock is ON!!!");
}
if (Console.CapsLock == false)
{
McTextBlock.Text = "Capslock is OFF";
Popup1.IsOpen = true;
timer.Start();
//MessageBox.Show("capslock is ON!!!");
}
}
if (vkey == VK_NUMLOCK)
{
if (Console.NumberLock == true)
{
McTextBlock.Text = "NumLock is ON";
Popup1.IsOpen = true;
timer.Start();
}
if (Console.NumberLock == false)
{
McTextBlock.Text = "NumLock is OFF";
Popup1.IsOpen = true;
timer.Start();
}
}
handled = true;
break;
}
break;
}
return IntPtr.Zero;
}
protected override void OnClosed(EventArgs e)
{
source.RemoveHook(HwndHook);
source = null;
UnregisterHotKey(new WindowInteropHelper(this).Handle, HOTKEY_ID);
base.OnClosed(e);
}
}
}
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);
}
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);
}
}
}