我希望将富文本放在HTML剪贴板上,这样当用户粘贴到Word中时,它将包括源HTML格式。
使用Clipboard.SetText
方法无法实现。
另外,如果用户将其粘贴到像Word这样的富文本编辑器中,它将粘贴格式化的文本,如果他们将其粘贴到像记事本这样的纯文本编辑器中,它将粘贴为纯文本。
我希望将富文本放在HTML剪贴板上,这样当用户粘贴到Word中时,它将包括源HTML格式。
使用Clipboard.SetText
方法无法实现。
另外,如果用户将其粘贴到像Word这样的富文本编辑器中,它将粘贴格式化的文本,如果他们将其粘贴到像记事本这样的纯文本编辑器中,它将粘贴为纯文本。
当设置HTML文本时,您需要提供一个标题,其中包含有关您要粘贴的html片段的附加信息,同时能够在其周围提供额外的样式:
Version:0.9
StartHTML:000125
EndHTML:000260
StartFragment:000209
EndFragment:000222
<HTML>
<head>
<title>HTML clipboard</title>
</head>
<body>
<!–StartFragment–><b>Hello!</b><!–EndFragment–>
</body>
</html>
使用正确的索引和标题,使用Clipboard.SetText
并指定TextDataFormat.Html
即可轻松处理HTML格式的复制粘贴。Clipboard.SetText
方法,因为每次调用该方法都会清除剪贴板。您需要创建一个DataObject
实例,并分别使用HTML和纯文本调用其SetData
方法一次,然后使用Clipboard.SetDataObject
将该对象设置到剪贴板中。
更新
了解更多详情和ClipboardHelper实现,请参见“重温设置HTML/Text到剪贴板”。这段代码解决了更新起始索引和结束索引的问题。
已转换为 C#:
public void AddHyperlinkToClipboard(string link, string description)
{
const string sContextStart = "<HTML><BODY><!--StartFragment -->";
const string sContextEnd = "<!--EndFragment --></BODY></HTML>";
const string m_sDescription = "Version:1.0" + Constants.vbCrLf + "StartHTML:aaaaaaaaaa" + Constants.vbCrLf + "EndHTML:bbbbbbbbbb" + Constants.vbCrLf + "StartFragment:cccccccccc" + Constants.vbCrLf + "EndFragment:dddddddddd" + Constants.vbCrLf;
string sHtmlFragment = "<A HREF=" + Strings.Chr(34) + link + Strings.Chr(34) + ">" + description + "</A>";
string sData = m_sDescription + sContextStart + sHtmlFragment + sContextEnd;
sData = sData.Replace("aaaaaaaaaa", m_sDescription.Length.ToString().PadLeft(10, '0'));
sData = sData.Replace("bbbbbbbbbb", sData.Length.ToString().PadLeft(10, '0'));
sData = sData.Replace("cccccccccc", (m_sDescription + sContextStart).Length.ToString().PadLeft(10, '0'));
sData = sData.Replace("dddddddddd", (m_sDescription + sContextStart + sHtmlFragment).Length.ToString().PadLeft(10, '0'));
sData.Dump();
Clipboard.SetDataObject(new DataObject(DataFormats.Html, sData), true );
}
让我分享一个设置剪贴板数据为HTML格式的助手,这是我为我的小项目#DevComrade刚刚想出来的:
var dataObject = new DataObject();
dataObject.SetData(DataFormats.Html, ClipboardFormats.ConvertHtmlToClipboardData(html);
Host.SetClipboardDataObject(dataObject);
internal static class ClipboardFormats
{
static readonly string HEADER =
"Version:0.9\r\n" +
"StartHTML:{0:0000000000}\r\n" +
"EndHTML:{1:0000000000}\r\n" +
"StartFragment:{2:0000000000}\r\n" +
"EndFragment:{3:0000000000}\r\n";
static readonly string HTML_START =
"<html>\r\n" +
"<body>\r\n" +
"<!--StartFragment-->";
static readonly string HTML_END =
"<!--EndFragment-->\r\n" +
"</body>\r\n" +
"</html>";
public static string ConvertHtmlToClipboardData(string html)
{
var encoding = new System.Text.UTF8Encoding(encoderShouldEmitUTF8Identifier: false);
var data = Array.Empty<byte>();
var header = encoding.GetBytes(String.Format(HEADER, 0, 1, 2, 3));
data = data.Concat(header).ToArray();
var startHtml = data.Length;
data = data.Concat(encoding.GetBytes(HTML_START)).ToArray();
var startFragment = data.Length;
data = data.Concat(encoding.GetBytes(html)).ToArray();
var endFragment = data.Length;
data = data.Concat(encoding.GetBytes(HTML_END)).ToArray();
var endHtml = data.Length;
var newHeader = encoding.GetBytes(
String.Format(HEADER, startHtml, endHtml, startFragment, endFragment));
if (newHeader.Length != startHtml)
{
throw new InvalidOperationException(nameof(ConvertHtmlToClipboardData));
}
Array.Copy(newHeader, data, length: startHtml);
return encoding.GetString(data);
}
}
Private Const Header As String = "Version:0.9" & vbCrLf & "StartHTML:<<<<<<<<1" & vbCrLf & "EndHTML:<<<<<<<<2" & vbCrLf & "StartFragment:<<<<<<<<3" & vbCrLf & "EndFragment:<<<<<<<<4" & vbCrLf & "StartSelection:<<<<<<<<3" & vbCrLf & "EndSelection:<<<<<<<<4"