在 Windows 桌面应用开发中,剪贴板是一个非常有用的功能,它允许用户在不同应用程序之间复制和粘贴数据。在 WinForms 应用程序中,我们可以通过调用 Win32 API 来实现剪贴板操作。本文将详细介绍如何在 WinForms 中进行剪贴板操作,并提供一个完整的示例。
引入命名空间
在开始之前,我们需要引用一些必要的命名空间:
using System;
using System.Windows.Forms;
using System.Runtime.InteropServices;
Win32 API 声明
我们将使用一些 Win32 API 函数来访问剪贴板,这些函数包括:
- OpenClipboard
- CloseClipboard
- EmptyClipboard
- SetClipboardData
- GetClipboardData
- GlobalAlloc
- GlobalLock
- GlobalUnlock
在代码中声明这些 API 函数:
public class ClipboardAPI
{
    // 声明 Win32 API 函数
    [DllImport("user32.dll")]
    public static extern bool OpenClipboard(IntPtr hWnd);
    [DllImport("user32.dll")]
    public static extern bool CloseClipboard();
    [DllImport("user32.dll")]
    public static extern bool EmptyClipboard();
    [DllImport("user32.dll")]
    public static extern IntPtr SetClipboardData(uint uFormat, IntPtr hMem);
    [DllImport("user32.dll")]
    public static extern IntPtr GetClipboardData(uint uFormat);
    [DllImport("kernel32.dll")]
    public static extern IntPtr GlobalAlloc(uint uFlags, UIntPtr dwBytes);
    [DllImport("kernel32.dll")]
    public static extern IntPtr GlobalLock(IntPtr hMem);
    [DllImport("kernel32.dll")]
    public static extern bool GlobalUnlock(IntPtr hMem);
    // 定义数据格式
    publicconst uint CF_TEXT = 1;
}
复制文本到剪贴板
下面是一个将文本复制到剪贴板的方法:
public void CopyToClipboard(string text)
{
    // 打开剪贴板
    if (ClipboardAPI.OpenClipboard(IntPtr.Zero))
    {
        // 清空剪贴板
        ClipboardAPI.EmptyClipboard();
        IntPtr hGlobal = ClipboardAPI.GlobalAlloc(0, (UIntPtr)((text.Length + 1) * 2)); 
        if (hGlobal != IntPtr.Zero)
        {
            IntPtr pGlobal = ClipboardAPI.GlobalLock(hGlobal);
            Marshal.Copy(text.ToCharArray(), 0, pGlobal, text.Length);
            Marshal.WriteInt16(pGlobal, text.Length * 2, 0); 
            ClipboardAPI.GlobalUnlock(hGlobal);
            ClipboardAPI.SetClipboardData(13, hGlobal);
            ClipboardAPI.CloseClipboard();
        }
    }
}
从剪贴板读取文本
下面是一个从剪贴板读取文本的方法:
public static string PasteFromClipboard()
{
    string result = string.Empty;
    // 打开剪贴板
    if (OpenClipboard(IntPtr.Zero))
    {
        // 获取剪贴板数据
        IntPtr hGlobal = GetClipboardData(ClipboardAPI.CF_TEXT);
        if (hGlobal != IntPtr.Zero)
        {
            // 锁定全局内存
            IntPtr pGlobal = ClipboardAPI.GlobalLock(hGlobal);
            // 读取文本
            result = Marshal.PtrToStringAnsi(pGlobal);
            // 解锁全局内存
            ClipboardAPI.GlobalUnlock(hGlobal);
        }
        // 关闭剪贴板
        CloseClipboard();
    }
    return result;
}
完整示例
接下来,我们将创建一个简单的 WinForms 应用程序,包含一个文本框和两个按钮,分别用于复制和粘贴。
using System.Runtime.InteropServices;
namespace AppCopyToClipboardApi
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
        private void btnCopy_Click(object sender, EventArgs e)
        {
            CopyToClipboard(txt.Text);
        }
        private void btnPaste_Click(object sender, EventArgs e)
        {
            txt.Text = PasteFromClipboard();
        }
        public string PasteFromClipboard()
        {
            string result = string.Empty;
            // 打开剪贴板
            if (ClipboardAPI.OpenClipboard(IntPtr.Zero))
            {
                // 获取剪贴板数据
                IntPtr hGlobal = ClipboardAPI.GetClipboardData(ClipboardAPI.CF_TEXT);
                if (hGlobal != IntPtr.Zero)
                {
                    // 锁定全局内存
                    IntPtr pGlobal = ClipboardAPI.GlobalLock(hGlobal);
                    // 读取文本
                    result = Marshal.PtrToStringAnsi(pGlobal);
                    // 解锁全局内存
                    ClipboardAPI.GlobalUnlock(hGlobal);
                }
                // 关闭剪贴板
                ClipboardAPI.CloseClipboard();
            }
            return result;
        }
        public void CopyToClipboard(string text)
        {
            // 打开剪贴板
            if (ClipboardAPI.OpenClipboard(IntPtr.Zero))
            {
                // 清空剪贴板
                ClipboardAPI.EmptyClipboard();
                IntPtr hGlobal = ClipboardAPI.GlobalAlloc(0, (UIntPtr)((text.Length + 1) * 2)); 
                if (hGlobal != IntPtr.Zero)
                {
                    IntPtr pGlobal = ClipboardAPI.GlobalLock(hGlobal);
                    Marshal.Copy(text.ToCharArray(), 0, pGlobal, text.Length);
                    Marshal.WriteInt16(pGlobal, text.Length * 2, 0); 
                    ClipboardAPI.GlobalUnlock(hGlobal);
                    ClipboardAPI.SetClipboardData(13, hGlobal);
                    ClipboardAPI.CloseClipboard();
                }
            }
        }
    }
}
 
总结
通过调用 Win32 API,我们能够在 WinForms 应用程序中实现剪贴板的操作。本文提供了将文本复制和粘贴到剪贴板的完整示例,展示了如何使用 Windows API 来进行这些基本操作。这种方法可以为开发更复杂的剪贴板功能提供基础。
阅读原文:原文链接
该文章在 2025/6/2 13:02:11 编辑过