Windows.Forms RichTextBox控件 - 避免插入大数据

时间:2010-04-15 12:43:07

标签: winforms richtextbox maxlength

我有一个带有RichTextBox的Windows窗体。 RichTextBox的内容将写入数据库字段,该字段仅限于64k数据。 为了我的目的,这是足够的文本存储。

我已设置MaxLength属性以避免插入比允许的数据更多的数据。

rtcControl.MaxLength = 65536

但是,这仅限制允许放入文本的字符数量。 但是由于Rtf的格式化开销,我可以输入比我应该允许的文本更多的文本。如果我插入一个大图像,它甚至会变得更糟,它不会增加TextLength,但Rtf长度会增长很多。

目前,我在FormClosing事件中检查richttextboxes的Rtf属性的长度,并向用户显示一条消息,如果它是大的话。 然而,这只是一种解决方法,因为我想禁止将更多数据放入控件中(例如,如果超过MaxLength属性,则在文本框中没有任何内容插入到控件中,您会听到默认的哔声()。

任何想法如何实现这个?

我已经尝试过:

  • 使用自定义控件扩展richtextbox并遮蔽Rtf属性以拦截插入。但是如果我添加文字似乎没有执行。

  • 如果输入smth,即使TextChanged事件也不会触发。在控制中。

2 个答案:

答案 0 :(得分:1)

这样做:

处理TextChanged事件并在每次更改时进行比较。它解雇了文本输入和图像拖放。

private void richTextBox1_TextChanged(object sender, EventArgs e)
{
   if (richTextBox1.Rtf.Length > richTextBox1.MaxLength)
   {
      // do something here - I displayed a label for
      // my example 
      label1.Text = "Text exceeds maximum size";
      label1.ForeColor = Color.Red;
   }
   else
   {
      label1.Text = richTextBox1.Rtf.Length.ToString();
      label1.ForeColor = Color.Red;
   }
}

这似乎有效,尽管我并没有花很多时间在这上面。我怀疑如果超出最大尺寸,你可能会截断内容。


编辑:我更多地考虑了这一点,我怀疑你每次都可以利用StringBuilder存储richtextbox的内容,如果有人试图超过该长度,请将数据恢复到以前的状态。我承认这有点hacky但似乎有效。像这样:

StringBuild sb = new StringBuilder();

private void richTextBox1_TextChanged(object sender, EventArgs e)
{
   if (richTextBox1.Rtf.Length > richTextBox1.MaxLength)
   {
      richTextBox1.Rtf = sb.ToString();
   }
   else
   {
      sb.Insert(0,richTextBox1.Rtf);
   }
}

这看起来效果很好。可能有更优雅的解决方案。

答案 1 :(得分:0)

回应其意见:

这是有效的,除了TextChanged事件似乎不会在我的环境中触发(不知道为什么)。但是因为我有自己的usercontrol,它是从RichTextBox中插入的,所以我能够覆盖被调用的OnTextChanged()方法。 但代码变得有点复杂,因为如果你更改OnTextChanged()方法中的文本,它会再次被调用,这会导致StackOverflowException。 我还想要一个Beep(),并且应该记住光标位置/选择。

使用此代码,文字>有点慢30000但这对我来说已经足够了。用户不应该在其中存储如此多的数据。

    private string lastText;
    private string lastRtf;
    private int lastSelectionStart;
    private int lastSelectionLength;

    private bool skipLengthCheck;
    protected override void OnTextChanged(EventArgs e)
    {
        if (Rtf.Length > MaxLength && !skipLengthCheck)
        {
            skipLengthCheck = true;
            Console.WriteLine("MaxLength exceeded");
            System.Media.SystemSounds.Beep.Play();
            int start = lastSelectionStart;
            int length = lastSelectionLength;
            base.Text = lastText;
            base.Rtf = lastRtf;
            SelectionStart = start > 0 ? start - 1 : 0;
            SelectionLength = length;
            skipLengthCheck = false;               
        }
        else
        {
            lastText = Text;
            lastRtf = Rtf;

            base.OnTextChanged(e);
        }

    }

    protected override void OnSelectionChanged(EventArgs e)
    {
        lastSelectionStart = SelectionStart;
        lastSelectionLength = SelectionLength;

        base.OnSelectionChanged(e);
    }