TomS
TomS

Reputation: 511

Show HTML in DataGridView control cell in C# desktop app

I have a C# desktop app which connects to a database and populates a DataGridView from the database (using databinding). The values of one column are HTML-formatted values and should be shown as HTML in the DataGridView. Unfortunately, currently all the content (e. g. tags) are written in raw format (i.e. not HTML formatted).

I already found a site on the Internet where this question was already asked. Unfortunately, they didn't talk about bound data (or at least I do not understand what there would be left to do to make it work...)

Is there anyone who can give me some hints on this? I already used ILSpy to find out how to get this done, but this is more confusing for me than it was helpful.

Upvotes: 1

Views: 3059

Answers (1)

Karthik V
Karthik V

Reputation: 21

have derived a simplified solution for rendering html content in data grid view.

Solution uses WebBrowser to render html and converts the content into bitmap, then drawn into cell using graphics.

using System;
using System.Drawing;
using System.Windows.Forms;

namespace DataGridViewTest
{
internal class DataGridViewHtmlCell : DataGridViewTextBoxCell
{
    protected override void Paint(
        Graphics graphics,
        Rectangle clipBounds,
        Rectangle cellBounds,
        Int32 rowIndex,
        DataGridViewElementStates cellState,
        Object values,
        Object formattedValue,
        String errorText,
        System.Windows.Forms.DataGridViewCellStyle cellStyle,
        DataGridViewAdvancedBorderStyle advancedBorderStyle,
        DataGridViewPaintParts paintParts)
    {
        // add a condition here to check formattedValue is Html
        // you shall use HtmlAgilityPack to determine this.
        if(isHtml)
        {
            RenderHtmlValue(graphics, cellBounds, formattedValue, true);
        }
        else
        {
            base.Paint(graphics, clipBounds, cellBounds, rowIndex, cellState, values, formattedValue, errorText, cellStyle, advancedBorderStyle, paintParts);
        }
    }   

    private Size RenderHtmlValue(
        Graphics graphics,
        Rectangle cellBounds,
        string formattedValue,
        bool drawCell)
    {
        using (var webBrowser = new WebBrowser())
        {
            webBrowser.ScrollBarsEnabled = false;

            webBrowser.Navigate("about:blank");
            webBrowser.Document.Write(formattedValue);
            webBrowser.Size = Size;

            var rect = new Rectangle(
                webBrowser.Document.Body.ScrollRectangle.Location,
                webBrowser.Document.Body.ScrollRectangle.Size);

            rect.Width = Size.Width - cellBounds.X;
            webBrowser.Size = rect.Size;

            cellBounds = new Rectangle(cellBounds.X, cellBounds.Y, rect.Width, rect.Height);

            var htmlBodyElement = webBrowser.Document.Body.DomElement as mshtml.IHTMLBodyElement;
            htmlBodyElement.WhenNotNull(
                bodyElement =>
                {
                    cellBounds.Height += Convert.ToInt32(htmlBodyElement.bottomMargin);
                });

            if(drawCell)
            {
                using (var bitmap = new Bitmap(webBrowser.Width, webBrowser.Height))
                {
                    webBrowser.DrawToBitmap(bitmap, targetBounds);
                    graphics.DrawImage(bitmap, location);
                }
            }
        }

        return cellBounds.Size;
    }

    protected override Size GetPreferredSize(
        Graphics graphics,
        System.Windows.Forms.DataGridViewCellStyle cellStyle,
        Int32 rowIndex,
        Size constraintSize)
    {
        return RenderHtmlValue(graphics, cellBounds, formattedValue, false);
    }
}

}

Upvotes: 1

Related Questions