State Query Service

    The IStateQueryService interface exposes read-only queries about the current caret position, active HTML element, and formatting state in a WinFormHtmlEditor control. The service is reached through the StateQuery property on the editor (for example htmlEditor1.StateQuery.IsBold()) and is the read-only mirror of the Formatting Service. Host applications use it to drive toolbar enabled/checked state, status-bar indicators, context-menu visibility, and event-driven UI such as the 2-Way Table Dialog.

    Methods that ask about the active element walk up the DOM from the caret. For example IsTable() returns true only when the active element itself is a <table>, while IsActiveOrAncestorElementTable() also returns true when the caret is inside any descendant of the table. Pick the variant that matches the question you are asking. The three QueryCommand* methods are thin wrappers over MSHTML's queryCommandEnabled, queryCommandState, and queryCommandValue; use them for commands the strongly-typed helpers above do not cover.

    Namespace: SpiceLogic.HtmlEditor.Abstractions.Services
    Assembly: SpiceLogic.HtmlEditor.Abstractions
    Inheritance: IStateQueryService : IDisposable. The runtime implementation holds references to the underlying MSHTML document and command target; the editor disposes it when the control is disposed, so application code never needs to call Dispose directly.

    In every example below, htmlEditor1 is a WinFormHtmlEditor instance dropped onto a WinForms designer (namespace SpiceLogic.HtmlEditor.WinForms).

    GetActiveHtmlElement()

    Returns the MSHTML element that contains the caret, or the element currently selected. This is the same element targeted by the Formatting Service when it applies styles, and the natural starting point for any DOM-level inspection the strongly-typed helpers do not cover.

    Syntax
    IHTMLElement GetActiveHtmlElement();
    Parameters

    None.

    Returns

    The active mshtml.IHTMLElement, or null when the document is empty or not ready.

    Example
    var element = htmlEditor1.StateQuery.GetActiveHtmlElement();
    if (element != null)
    {
        System.Diagnostics.Debug.WriteLine($"Caret tag: {element.tagName}");
    }
    Dim element = htmlEditor1.StateQuery.GetActiveHtmlElement()
    
    If element IsNot Nothing Then
        System.Diagnostics.Debug.WriteLine($"Caret tag: {element.tagName}")
    End If

    IsImage()

    Indicates whether the active HTML element is an image (<img>).

    Syntax
    bool IsImage();
    Parameters

    None.

    Returns

    true when the active element is an image; otherwise false.

    Example
    // Show an "Image Properties..." menu only when the caret targets an image.
    
    imagePropsToolStripMenuItem.Visible = htmlEditor1.StateQuery.IsImage();

    IsHyperLink()

    Indicates whether the active HTML element is itself an anchor (<a>). This method does not walk up the DOM - use IsActiveOrAncestorElementHyperLink() when the caret may sit inside text wrapped by a link.

    Syntax
    bool IsHyperLink();
    Parameters

    None.

    Returns

    true when the active element is an anchor; otherwise false.

    Example
    if (htmlEditor1.StateQuery.IsHyperLink())
    {
        statusLabel.Text = "Anchor selected";
    }
    If htmlEditor1.StateQuery.IsHyperLink() Then
        statusLabel.Text = "Anchor selected"
    End If

    IsTable()

    Indicates whether the active HTML element is itself a <table>. Does not climb ancestors.

    Syntax
    bool IsTable();
    Parameters

    None.

    Returns

    true when the active element is a table; otherwise false.

    Remarks

    To detect a caret anywhere inside a table (cells, paragraphs, spans nested in cells), call IsActiveOrAncestorElementTable() instead.

    Example
    tableBordersButton.Enabled = htmlEditor1.StateQuery.IsTable();

    IsActiveOrAncestorElementTable()

    Indicates whether the active element or any of its ancestors is a <table>. Unlike IsTable(), this returns true when the caret sits inside a nested element (<span>, <p>, <td>, etc.) within a table. Designed for the 2-Way Table Dialog entry check.

    Syntax
    bool IsActiveOrAncestorElementTable();
    Parameters

    None.

    Returns

    true when the caret sits inside any table; otherwise false.

    Example
    // Enable the "Edit Table..." menu only when the caret is inside a table.
    
    editTableMenuItem.Enabled = htmlEditor1.StateQuery.IsActiveOrAncestorElementTable();

    GetCurrentTable()

    Returns a populated TableElement describing the nearest enclosing <table> ancestor of the current caret, or null when the caret is not inside any table. Intended for the 2-Way Table Dialog: host code calls this, passes the result to a custom edit dialog, and after the dialog is confirmed calls TableElement.UpdateTheActiveHtmlElement() to write changes back.

    Syntax
    TableElement GetCurrentTable();
    Parameters

    None.

    Returns

    A TableElement with HTML attribute and inline style values populated for the nearest enclosing table, or null when there is no enclosing table.

    Remarks

    CSS round-trip caveat: getters fall back to computed style when an HTML attribute is missing, so the dialog reflects what the user sees. Setters write only to HTML attributes and inline style - they never edit external stylesheets. For fully CSS-driven tables, prefer editing the stylesheet directly.

    Example
    var table = htmlEditor1.StateQuery.GetCurrentTable();
    if (table != null)
    {
        table.BorderWidth = 1;
        table.UpdateTheActiveHtmlElement();
    }
    Dim table = htmlEditor1.StateQuery.GetCurrentTable()
    
    If table IsNot Nothing Then
        table.BorderWidth = 1
        table.UpdateTheActiveHtmlElement()
    End If

    IsTableCell()

    Indicates whether the active HTML element is a table cell (<td> or <th>).

    Syntax
    bool IsTableCell();
    Parameters

    None.

    Returns

    true when the active element is a table cell; otherwise false.

    Example
    cellPropertiesMenuItem.Visible = htmlEditor1.StateQuery.IsTableCell();

    CanMergeTableCells()

    Indicates whether the current selection spans two or more adjacent cells in a way that allows a merge operation. Suitable for enabling a "Merge Cells" toolbar button or context-menu item.

    Syntax
    bool CanMergeTableCells();
    Parameters

    None.

    Returns

    true when the selection covers mergeable cells; otherwise false.

    Example
    mergeCellsToolStripButton.Enabled = htmlEditor1.StateQuery.CanMergeTableCells();

    IsJustifyLeft()

    Indicates whether the active paragraph is left-justified.

    Syntax
    bool IsJustifyLeft();
    Parameters

    None.

    Returns

    true when the paragraph is left-aligned; otherwise false.

    Example
    justifyLeftButton.Checked = htmlEditor1.StateQuery.IsJustifyLeft();

    IsJustifyRight()

    Indicates whether the active paragraph is right-justified.

    Syntax
    bool IsJustifyRight();
    Parameters

    None.

    Returns

    true when the paragraph is right-aligned; otherwise false.

    Example
    justifyRightButton.Checked = htmlEditor1.StateQuery.IsJustifyRight();

    IsJustifyCenter()

    Indicates whether the active paragraph is center-justified.

    Syntax
    bool IsJustifyCenter();
    Parameters

    None.

    Returns

    true when the paragraph is center-aligned; otherwise false.

    Example
    justifyCenterButton.Checked = htmlEditor1.StateQuery.IsJustifyCenter();

    IsOverWriteMode()

    Indicates whether the editor is in overwrite (Insert key) mode, where typing replaces the character at the caret instead of inserting before it.

    Syntax
    bool IsOverWriteMode();
    Parameters

    None.

    Returns

    true when overwrite mode is active; otherwise false.

    Example
    // Drive a status-bar "OVR" indicator from the caret state.
    
    overwriteStatusLabel.Text = htmlEditor1.StateQuery.IsOverWriteMode() ? "OVR" : "INS";

    IsOrderedList()

    Indicates whether the active element is inside an ordered list (<ol>).

    Syntax
    bool IsOrderedList();
    Parameters

    None.

    Returns

    true when the caret sits inside an ordered list; otherwise false.

    Example
    orderedListButton.Checked = htmlEditor1.StateQuery.IsOrderedList();

    IsUnorderedList()

    Indicates whether the active element is inside an unordered list (<ul>).

    Syntax
    bool IsUnorderedList();
    Parameters

    None.

    Returns

    true when the caret sits inside an unordered list; otherwise false.

    Example
    unorderedListButton.Checked = htmlEditor1.StateQuery.IsUnorderedList();

    IsStrikeThrough()

    Indicates whether the active element is strike-through.

    Syntax
    bool IsStrikeThrough();
    Parameters

    None.

    Returns

    true when strike-through is in effect; otherwise false.

    Example
    strikeThroughButton.Checked = htmlEditor1.StateQuery.IsStrikeThrough();

    IsSuperscript()

    Indicates whether the active element is rendered as superscript.

    Syntax
    bool IsSuperscript();
    Parameters

    None.

    Returns

    true when superscript is in effect; otherwise false.

    Example
    superscriptButton.Checked = htmlEditor1.StateQuery.IsSuperscript();

    IsSubscript()

    Indicates whether the active element is rendered as subscript.

    Syntax
    bool IsSubscript();
    Parameters

    None.

    Returns

    true when subscript is in effect; otherwise false.

    Example
    subscriptButton.Checked = htmlEditor1.StateQuery.IsSubscript();

    IsUnderline()

    Indicates whether the active element is underlined.

    Syntax
    bool IsUnderline();
    Parameters

    None.

    Returns

    true when underline is in effect; otherwise false.

    Example
    underlineButton.Checked = htmlEditor1.StateQuery.IsUnderline();

    IsItalic()

    Indicates whether the active element is italic.

    Syntax
    bool IsItalic();
    Parameters

    None.

    Returns

    true when italic is in effect; otherwise false.

    Example
    italicButton.Checked = htmlEditor1.StateQuery.IsItalic();

    IsBold()

    Indicates whether the active element is bold.

    Syntax
    bool IsBold();
    Parameters

    None.

    Returns

    true when bold is in effect; otherwise false.

    Example
    // Sync a toolbar Bold button with the caret state.
    
    boldToolStripButton.Checked = htmlEditor1.StateQuery.IsBold();

    GetActiveFontFamilyName()

    Returns the CSS font-family name applied to the active element.

    Syntax
    string GetActiveFontFamilyName();
    Parameters

    None.

    Returns

    The CSS font family name as a string. Empty when no font is explicitly applied.

    Example
    fontFamilyComboBox.Text = htmlEditor1.StateQuery.GetActiveFontFamilyName();

    GetActiveFontSize()

    Returns the font size applied to the active element. The result may be an HTML legacy size (1-7) or a CSS size with unit (for example 14pt), depending on how the content was authored.

    Syntax
    string GetActiveFontSize();
    Parameters

    None.

    Returns

    The font size as a string.

    Example
    fontSizeComboBox.Text = htmlEditor1.StateQuery.GetActiveFontSize();

    GetFontSizeFromElement(IHTMLElement element)

    Returns the font size applied to a specific HTML element, independent of the current caret position. Useful when iterating DOM elements during validation or export, or when you have an element reference from GetElementFromPoint().

    Syntax
    string GetFontSizeFromElement(IHTMLElement element);
    Parameters
    NameTypeDescription
    elementmshtml.IHTMLElementThe element whose font size should be read.
    Returns

    The font size as a string. Empty when none is set.

    Example
    var body = htmlEditor1.Document.Body as IHTMLElement;
    string size = htmlEditor1.StateQuery.GetFontSizeFromElement(body);
    System.Diagnostics.Debug.WriteLine($"Body font-size: {size}");
    Dim body = TryCast(htmlEditor1.Document.Body, IHTMLElement)
    Dim size As String = htmlEditor1.StateQuery.GetFontSizeFromElement(body)
    System.Diagnostics.Debug.WriteLine($"Body font-size: {size}")

    GetActiveForeColor()

    Returns the foreground (text) color of the active element.

    Syntax
    Color GetActiveForeColor();
    Parameters

    None.

    Returns

    A System.Drawing.Color value.

    Example
    foreColorButton.BackColor = htmlEditor1.StateQuery.GetActiveForeColor();

    GetActiveHighlightColor()

    Returns the highlight (background) color of the active element.

    Syntax
    Color GetActiveHighlightColor();
    Parameters

    None.

    Returns

    A System.Drawing.Color value.

    Example
    highlightColorButton.BackColor = htmlEditor1.StateQuery.GetActiveHighlightColor();

    IsYouTubeVideo()

    Indicates whether the active element is an embedded YouTube video frame produced by the editor's YouTube insertion command.

    Syntax
    bool IsYouTubeVideo();
    Parameters

    None.

    Returns

    true when the active element is a YouTube embed; otherwise false.

    Example
    editVideoMenuItem.Visible = htmlEditor1.StateQuery.IsYouTubeVideo();

    QueryCommandEnabled(string commandName)

    Queries the underlying MSHTML command target to determine whether a named command is currently enabled for execution. Thin wrapper over document.queryCommandEnabled. Use for advanced scenarios where the public formatting API does not cover the command you need.

    Syntax
    bool QueryCommandEnabled(string commandName);
    Parameters
    NameTypeDescription
    commandNamestringMSHTML command identifier (e.g. "Bold", "JustifyLeft", "InsertOrderedList").
    Returns

    true when the command is enabled; otherwise false.

    Example
    bool canBold = htmlEditor1.StateQuery.QueryCommandEnabled("Bold");
    boldToolStripButton.Enabled = canBold;
    Dim canBold As Boolean = htmlEditor1.StateQuery.QueryCommandEnabled("Bold")
    boldToolStripButton.Enabled = canBold

    QueryCommandState(string commandName)

    Queries the underlying MSHTML command target to determine whether a named command is currently in effect at the caret position. Thin wrapper over document.queryCommandState. For toggleable commands such as Bold, the result mirrors the toolbar "checked" state.

    Syntax
    bool QueryCommandState(string commandName);
    Parameters
    NameTypeDescription
    commandNamestringMSHTML command identifier.
    Returns

    true when the command state is active; otherwise false.

    Example
    italicToolStripButton.Checked = htmlEditor1.StateQuery.QueryCommandState("Italic");

    QueryCommandValue(string commandName)

    Queries the value currently associated with a named MSHTML command (for example the current font name for FontName). Thin wrapper over document.queryCommandValue.

    Syntax
    object QueryCommandValue(string commandName);
    Parameters
    NameTypeDescription
    commandNamestringMSHTML command identifier.
    Returns

    The command value as object. The runtime type depends on the command - cast accordingly.

    Example
    var fontName = htmlEditor1.StateQuery.QueryCommandValue("FontName") as string;
    fontFamilyComboBox.Text = fontName ?? string.Empty;
    Dim fontName = TryCast(htmlEditor1.StateQuery.QueryCommandValue("FontName"), String)
    fontFamilyComboBox.Text = If(fontName, String.Empty)

    CanUndo()

    Indicates whether the editor has an entry on its undo stack that can be reverted.

    Syntax
    bool CanUndo();
    Parameters

    None.

    Returns

    true when an undo is available; otherwise false.

    Example
    undoToolStripButton.Enabled = htmlEditor1.StateQuery.CanUndo();

    CanRedo()

    Indicates whether the editor has an entry on its redo stack that can be replayed.

    Syntax
    bool CanRedo();
    Parameters

    None.

    Returns

    true when a redo is available; otherwise false.

    Example
    redoToolStripButton.Enabled = htmlEditor1.StateQuery.CanRedo();

    CanCut()

    Indicates whether the current selection can be cut to the clipboard. Returns false when nothing is selected or when the content is read-only.

    Syntax
    bool CanCut();
    Parameters

    None.

    Returns

    true when Cut is allowed; otherwise false.

    Example
    cutToolStripButton.Enabled = htmlEditor1.StateQuery.CanCut();

    CanCopy()

    Indicates whether the current selection can be copied to the clipboard.

    Syntax
    bool CanCopy();
    Parameters

    None.

    Returns

    true when Copy is allowed; otherwise false.

    Example
    copyToolStripButton.Enabled = htmlEditor1.StateQuery.CanCopy();

    CanPaste()

    Indicates whether the clipboard currently holds content that can be pasted into the editor.

    Syntax
    bool CanPaste();
    Parameters

    None.

    Returns

    true when Paste is allowed; otherwise false.

    Example
    pasteToolStripButton.Enabled = htmlEditor1.StateQuery.CanPaste();

    CanDelete()

    Indicates whether pressing Delete would remove content at the current selection.

    Syntax
    bool CanDelete();
    Parameters

    None.

    Returns

    true when Delete is allowed; otherwise false.

    Example
    deleteToolStripButton.Enabled = htmlEditor1.StateQuery.CanDelete();

    IsActiveElementHeaderTitle()

    Indicates whether the active element is one of the heading tags <h1> through <h6>.

    Syntax
    bool IsActiveElementHeaderTitle();
    Parameters

    None.

    Returns

    true when the active element is a heading; otherwise false.

    Example
    headingComboBox.Visible = htmlEditor1.StateQuery.IsActiveElementHeaderTitle();

    GetActiveHeaderTitleNumber()

    Returns the heading level (1 through 6) of the active heading element. Returns 0 when the active element is not a heading.

    Syntax
    int GetActiveHeaderTitleNumber();
    Parameters

    None.

    Returns

    Heading level 1-6, or 0 when no heading is active.

    Example
    int level = htmlEditor1.StateQuery.GetActiveHeaderTitleNumber();
    headingComboBox.Text = level == 0 ? "Normal" : $"Heading {level}";
    Dim level As Integer = htmlEditor1.StateQuery.GetActiveHeaderTitleNumber()
    headingComboBox.Text = If(level Is 0, "Normal", $"Heading {level}")

    GetElementFromPoint(Point pt)

    Returns the WinForms HtmlElement at the given client-coordinate point inside the editor. Use this from mouse-event handlers (for example MouseClick) to discover which DOM element the user pointed at, for hit-testing in context-menu and drag-and-drop scenarios.

    Syntax
    HtmlElement GetElementFromPoint(Point pt);
    Parameters
    NameTypeDescription
    ptSystem.Drawing.PointPoint in editor client coordinates.
    Returns

    A System.Windows.Forms.HtmlElement at the point, or null when there is no element at that location.

    Example
    private void htmlEditor1_MouseClick(object sender, MouseEventArgs e)
    {
        var element = htmlEditor1.StateQuery.GetElementFromPoint(e.Location);
        if (element != null)
            statusLabel.Text = $"Clicked on <{element.TagName.ToLower()}>";
    }
    Private Sub htmlEditor1_MouseClick(sender As Object, e As MouseEventArgs)
        Dim element = htmlEditor1.StateQuery.GetElementFromPoint(e.Location)
        If element IsNot Nothing Then statusLabel.Text = $"Clicked on <{element.TagName.ToLower()}>"
    End Sub

    SetTableManipulator(ITableManipulator tableManipulator)

    Associates an ITableManipulator instance with this state-query service so that table-specific queries (such as CanMergeTableCells()) can delegate to the manipulator. Called by the editor during initialization; application code does not normally invoke this method.

    Syntax
    void SetTableManipulator(ITableManipulator tableManipulator);
    Parameters
    NameTypeDescription
    tableManipulatorITableManipulatorThe table-manipulation service to associate with this state-query service.
    Returns

    None.

    Example
    // Advanced: inject a custom table manipulator before the editor wires its default.
    htmlEditor1.StateQuery.SetTableManipulator(new MyCustomTableManipulator());
    ' Advanced: inject a custom table manipulator before the editor wires its default.
    htmlEditor1.StateQuery.SetTableManipulator(New MyCustomTableManipulator())

    IsActiveOrAncestorElementHyperLink()

    Indicates whether the active HTML element or any of its ancestors is a hyperlink (<a>). Use this in preference to IsHyperLink() when the caret may sit inside text wrapped by a link (for example inside a <span> or <b> nested in an <a>).

    Syntax
    bool IsActiveOrAncestorElementHyperLink();
    Parameters

    None.

    Returns

    true when the caret is inside a hyperlink; otherwise false.

    Example
    // Enable an "Edit Link..." menu item whenever the caret is inside an anchor.
    
    editLinkMenuItem.Enabled = htmlEditor1.StateQuery.IsActiveOrAncestorElementHyperLink();

    Dispose()

    Inherited from IDisposable. The editor control calls this during teardown to release the underlying MSHTML command target. Host applications normally do not invoke this directly.

    Syntax
    void Dispose();
    Parameters

    None.

    Returns

    None.

    Example
    // The editor disposes its StateQuery when the control itself is disposed,
    
    // so host code typically does not call Dispose() directly:
    
    htmlEditor1.Dispose(); // disposes htmlEditor1.StateQuery as a side effect.

    Last updated on May 14, 2026