Detect if a RichTextBox is empty

You could compare the pointers, which is not all too reliable:

var start = rtb.Document.ContentStart;
var end = rtb.Document.ContentEnd;
int difference = start.GetOffsetToPosition(end);

This evaluates to 2 if the RTB is loaded, and 4 if content has been entered and removed again.
If the RTB is completely cleared out e.g. via select all -> delete the value will be 0.


In the Silverlight reference on MSDN another method is found which can be adapted and improved to:

public bool IsRichTextBoxEmpty(RichTextBox rtb)
{
    if (rtb.Document.Blocks.Count == 0) return true;
    TextPointer startPointer = rtb.Document.ContentStart.GetNextInsertionPosition(LogicalDirection.Forward);
    TextPointer endPointer = rtb.Document.ContentEnd.GetNextInsertionPosition(LogicalDirection.Backward);
    return startPointer.CompareTo(endPointer) == 0;
}

The answer above works if you don't put anything into the RTB. However, if you simply delete the contents, the RTB tends to return a single, empty paragraph, not a completely empty string. So, this is more reliable in such cases:

string text = new TextRange(Document.ContentStart, Document.ContentEnd).Text;
return !String.IsNullOrWhiteSpace(text);

This only applies to textual contents, of course.


H.B.'s answer isn't useful if you need to distinguish between images and whitespace. You can use something like this answer to check for images.

bool IsEmpty(Document document)
{
    string text = new TextRange(Document.ContentStart, Document.ContentEnd).Text;
    if (string.IsNullOrWhiteSpace(text) == false)
        return false;
    else
    {
        if (document.Blocks.OfType<BlockUIContainer>()
            .Select(c => c.Child).OfType<Image>()
            .Any())
        return false;
    }
    return true;
}

This seems laborious, and still probably isn't correct for all scenarios. But I couldn't find any better way.