c#RTB - 粘贴没有颜色/字体的纯文本?

问题描述 投票:5回答:9

我在C#应用程序中使用Rich Text对象。我遇到的唯一问题是,当用户从另一个应用程序粘贴格式化文本时,它仍然是我不能拥有的格式。有没有办法如何只粘贴字符串并忽略格式?谢谢!

c# winforms richtextbox
9个回答
9
投票

假设WinForms:尝试这个:使用KeyDown事件处理程序定义一个RichTextBox,如下所示:

仅附加示例:

    private void richTextBox1_KeyDown(object sender, KeyEventArgs e)
    {
        if (e.Control && e.KeyCode == Keys.V) 
        {
            richTextBox1.Text += (string)Clipboard.GetData("Text"); 
            e.Handled = true; 
        }
    }

[编辑]

在当前插入点(选择开始)示例中将剪贴板RTF添加到RichTextBox:

private void richTextBox1_KeyDown(object sender, KeyEventArgs e) 
{ 
    if (e.Control && e.KeyCode == Keys.V)  
    { 
            // suspend layout to avoid blinking
            richTextBox2.SuspendLayout();

            // get insertion point
            int insPt = richTextBox2.SelectionStart;

            // preserve text from after insertion pont to end of RTF content
            string postRTFContent = richTextBox2.Text.Substring(insPt);

            // remove the content after the insertion point
            richTextBox2.Text = richTextBox2.Text.Substring(0, insPt);

            // add the clipboard content and then the preserved postRTF content
            richTextBox2.Text += (string)Clipboard.GetData("Text") + postRTFContent;

            // adjust the insertion point to just after the inserted text
            richTextBox2.SelectionStart = richTextBox2.TextLength - postRTFContent.Length;

            // restore layout
            richTextBox2.ResumeLayout();

            // cancel the paste
            e.Handled = true;
    } 
} 

[结束编辑]

注意0:粘贴的文本将假设当前样式设置对RichTextBox有效:如果您将'ForeGround颜色设置为'蓝色:粘贴的文本将为蓝色。

注1:这是我快速拼凑的东西,并且通过使用写字板为剪贴板创建一些多色和奇怪格式的RTF进行了几次测试:然后在运行时粘贴到RichTextBox1中:它确实剥离了所有的颜色,缩进等

由于未经过全面测试,请谨慎使用。

注2:显然,这不会处理“插入”或“通过上下文菜单粘贴”的情况。

欢迎对这个答案的所有批评,如果它不是“标记”,将立即将其删除。


29
投票

KeyDown事件添加处理程序以拦截标准粘贴并手动仅插入纯文本:

private void rtb_KeyDown(object sender, KeyEventArgs e)
{
    if (e.Control && e.KeyCode == Keys.V)
    {
        ((RichTextBox)sender).Paste(DataFormats.GetFormat("Text"));
            e.Handled = true;
    }
}

4
投票

我正在寻找一个纯文本richtextbox但没有在网上找到解决方案。

为什么纯文本只有RichTextBox而不是TextBox?例如,因为RichTextBox具有可用的撤消/重做功能等等。

最后我通过挖掘richedit控件的C头文件找到了一个完美的解决方案:一个RichTextBox可以切换到明文模式,之后它不接受格式化的文本和图像以及来自剪贴板的类似的东西,行为就像一个普通的TextBox formattingwise。无法粘贴图像等奇特的东西,并通过删除格式来粘贴格式化文本。

class PlainRichTextBox : RichTextBox
{
    const int WM_USER = 0x400;
    const int EM_SETTEXTMODE = WM_USER + 89;
    const int EM_GETTEXTMODE = WM_USER + 90;

    // EM_SETTEXTMODE/EM_GETTEXTMODE flags
    const int TM_PLAINTEXT = 1;
    const int TM_RICHTEXT = 2;          // Default behavior 
    const int TM_SINGLELEVELUNDO = 4;
    const int TM_MULTILEVELUNDO = 8;    // Default behavior 
    const int TM_SINGLECODEPAGE = 16;
    const int TM_MULTICODEPAGE = 32;    // Default behavior 

    [DllImport("user32.dll")]
    static extern IntPtr SendMessage(IntPtr hWnd, int wMsg, IntPtr wParam, IntPtr lParam);

    bool m_PlainTextMode;

    // If this property doesn't work for you from the designer for some reason
    // (for example framework version...) then set this property from outside
    // the designer then uncomment the Browsable and DesignerSerializationVisibility
    // attributes and set the Property from your component initializer code
    // that runs after the designer's code.
    [DefaultValue(false)]
    //[Browsable(false)]
    //[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
    public bool PlainTextMode
    {
        get
        {
            return m_PlainTextMode;
        }
        set
        {
            m_PlainTextMode = value;
            if (IsHandleCreated)
            {
                IntPtr mode = value ? (IntPtr)TM_PLAINTEXT : (IntPtr)TM_RICHTEXT;
                SendMessage(Handle, EM_SETTEXTMODE, mode, IntPtr.Zero);
            }
        }
    }

    protected override void OnHandleCreated(EventArgs e)
    {
        // For some reason it worked for me only if I manipulated the created
        // handle before calling the base method.
        PlainTextMode = m_PlainTextMode;
        base.OnHandleCreated(e);
    }
}

1
投票

pasztorpisti的答案对我来说就像一个魅力。由于我正在使用vb.net,我以为我会为其他人发布我的翻译代码:

Imports System.Runtime.InteropServices
Imports System.ComponentModel

Public Class MyRichTextBox
    Inherits Windows.Forms.RichTextBox

    Public Const WM_USER As Integer = &H400
    Public Const EM_SETTEXTMODE As Integer = WM_USER + 89
    Public Const EM_GETTEXTMODE As Integer = WM_USER + 90

    'EM_SETTEXTMODE/EM_GETTEXTMODE flags
    Public Const TM_PLAINTEXT As Integer = 1
    Public Const TM_RICHTEXT As Integer = 2          ' Default behavior 
    Public Const TM_SINGLELEVELUNDO As Integer = 4
    Public Const TM_MULTILEVELUNDO As Integer = 8    ' Default behavior 
    Public Const TM_SINGLECODEPAGE As Integer = 16
    Public Const TM_MULTICODEPAGE As Integer = 32    ' Default behavior

    <DllImport("user32.dll", SetLastError:=True, CharSet:=CharSet.Auto)> _
    Private Shared Function SendMessage(ByVal hWnd As IntPtr, ByVal Msg As UInteger, ByVal wParam As IntPtr, ByVal lParam As IntPtr) As IntPtr
    End Function

    Private _plainTextMode As Boolean = False
    <DefaultValue(False),
      Browsable(True)>
    Public Property PlainTextMode As Boolean
        Get
            Return _plainTextMode
        End Get
        Set(value As Boolean)
            _plainTextMode = value

            If (Me.IsHandleCreated) Then
                Dim mode As IntPtr = If(value, TM_PLAINTEXT, TM_RICHTEXT)
                SendMessage(Handle, EM_SETTEXTMODE, mode, IntPtr.Zero)
            End If
        End Set
    End Property

    Protected Overrides Sub OnHandleCreated(e As EventArgs)
        'For some reason it worked for me only if I manipulated the created
        'handle before calling the base method.
        Me.PlainTextMode = _plainTextMode

        MyBase.OnHandleCreated(e)
    End Sub
End Class

0
投票

那么RichTextBox有一个SelectionFont属性,所以你可以做以下事情:

Font courier;
courier = new Font("Courier new", 10f, FontStyle.Regular);
myRtb.SelectionFont = courier;
myRtb.Font = courier; //So the typed text is also the same font

如果文本被粘贴,它将自动格式化。


0
投票

你也可以使用

private void richTextBox1_KeyDown(object sender, KeyEventArgs e)
{
    if (e.Control && e.KeyCode == Keys.V)
    {
        richTextBox1.SelectedText = (string)Clipboard.GetData("Text");
        e.Handled = true;
    }
}

0
投票

我通过在更改内容时修改整个RTB的字体和颜色来实现这一点。这对我来说很好,因为输入框不需要处理大量的文本。

public FormMain()
{
    InitializeComponent();
    txtRtb.TextChanged += txtRtb_TextChanged;
}

void txtRtb_TextChanged(object sender, EventArgs e)
{
    RichTextBox rtb = (RichTextBox)sender;
    rtb.SelectAll();
    rtb.SelectionFont = rtb.Font;
    rtb.SelectionColor = System.Drawing.SystemColors.WindowText;
    rtb.Select(rtb.TextLength,0);
}

0
投票

我的解决方案

private void OnCommandExecuting(object sender, Telerik.Windows.Documents.RichTextBoxCommands.CommandExecutingEventArgs e)
{
    if (e.Command is PasteCommand)
    {
        //override paste when clipboard comes from out of RichTextBox (plain text)
        var documentFromClipboard = ClipboardEx.GetDocumentFromClipboard("RadDocumentGUID");
        if (documentFromClipboard == null)
        {
            (sender as RichTextBox).Insert(Clipboard.GetText());
            e.Cancel = true;
        }
    }
}

-2
投票

很简单,但是当应用程序打开时,剪贴板中的所有内容都是纯文本。

private void timer2_Tick(object sender, EventArgs e)
        {
            string paste = Clipboard.GetText();
            Clipboard.SetText(paste);
        }
© www.soinside.com 2019 - 2024. All rights reserved.