Skip to content

Conhost color selection doesn't work correctly with wrapping and DBCS #8572

@j4james

Description

@j4james

Environment

Windows build number: Version 10.0.18363.1198
Windows Terminal version (if applicable):

Steps to reproduce

  1. Open a cmd shell in conhost.
  2. Open the Properties dialog and make sure Enable line wrapping selection is turned on.
  3. Select a range of text wrapped across multiple lines.
  4. Press Ctrl+4 to highlight the selected text in green.
  5. Output some text from double byte character set.
  6. Select a range of those characters starting and ending halfway through a double width character.
  7. Again press Ctrl+4 to highlight the selected text in green.

Expected behavior

When the selection wraps across multiple lines, the green highlighting should also wrap in exactly the same way. When selecting halfway through a double width character, the selection always covers the full width, so I'd expect the green highlighting to work in the same way.

image

Actual behavior

The wrapped selection changes to a block selection when painting the green background. And only half of the start and end characters in the DBCS range are painted green (I should note that this renders differently in the current openconsole build, but is still doesn't match the initial selection).

image

The reason for this behaviour is that the color selection code just uses a simple rect spanning the start and end points of the selection, where typically a selection operation should be using the Selection::GetSelectionRects method to obtain the affected range (which automatically handles the line wrapping option, and makes sure double width characters are fully covered).

The code I'm referring to is here:

ColorSelection(_srSelectionRect, selectionAttr);

And my recommendation would be to change the line above to use the GetSelectionRects method like this:

const auto selectionRects = GetSelectionRects();
for (const auto& selectionRect : selectionRects)
{
    ColorSelection(selectionRect, selectionAttr);
}

I suppose it's possible the current behaviour is deliberate, but I think it's more likely it was just an oversight when conhost was updated to support wrapped selections.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Needs-Tag-FixDoesn't match tag requirementsNeeds-TriageIt's a new issue that the core contributor team needs to triage at the next triage meetingResolution-Fix-CommittedFix is checked in, but it might be 3-4 weeks until a release.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions