"""Helpers for chat-friendly workspace shell output rendering."""

from __future__ import annotations


def _apply_csi(
    final: str,
    parameters: str,
    line: list[str],
    cursor: int,
    lines: list[str],
) -> tuple[list[str], int, list[str]]:
    if final == "K":
        mode = parameters or "0"
        if mode in {"0", ""}:
            del line[cursor:]
        elif mode == "1":
            for index in range(min(cursor, len(line))):
                line[index] = " "
        elif mode == "2":
            line.clear()
            cursor = 0
    elif final == "J":
        mode = parameters or "0"
        if mode in {"2", "3"}:
            lines.clear()
            line.clear()
            cursor = 0
    return line, cursor, lines


def _consume_escape_sequence(
    text: str,
    index: int,
    line: list[str],
    cursor: int,
    lines: list[str],
) -> tuple[int, list[str], int, list[str]]:
    if index + 1 >= len(text):
        return len(text), line, cursor, lines
    leader = text[index + 1]
    if leader == "[":
        cursor_index = index + 2
        while cursor_index < len(text):
            char = text[cursor_index]
            if "\x40" <= char <= "\x7e":
                parameters = text[index + 2 : cursor_index]
                line, cursor, lines = _apply_csi(char, parameters, line, cursor, lines)
                return cursor_index + 1, line, cursor, lines
            cursor_index += 1
        return len(text), line, cursor, lines
    if leader in {"]", "P", "_", "^"}:
        cursor_index = index + 2
        while cursor_index < len(text):
            char = text[cursor_index]
            if char == "\x07":
                return cursor_index + 1, line, cursor, lines
            if char == "\x1b" and cursor_index + 1 < len(text) and text[cursor_index + 1] == "\\":
                return cursor_index + 2, line, cursor, lines
            cursor_index += 1
        return len(text), line, cursor, lines
    if leader == "O":
        return min(index + 3, len(text)), line, cursor, lines
    return min(index + 2, len(text)), line, cursor, lines


def render_plain_shell_output(raw_text: str) -> str:
    """Render PTY output into chat-friendly plain text."""
    lines: list[str] = []
    line: list[str] = []
    cursor = 0
    ended_with_newline = False
    index = 0
    while index < len(raw_text):
        char = raw_text[index]
        if char == "\x1b":
            index, line, cursor, lines = _consume_escape_sequence(
                raw_text,
                index,
                line,
                cursor,
                lines,
            )
            ended_with_newline = False
            continue
        if char == "\r":
            cursor = 0
            ended_with_newline = False
            index += 1
            continue
        if char == "\n":
            lines.append("".join(line))
            line = []
            cursor = 0
            ended_with_newline = True
            index += 1
            continue
        if char == "\b":
            if cursor > 0:
                cursor -= 1
                if cursor < len(line):
                    del line[cursor]
            ended_with_newline = False
            index += 1
            continue
        if char == "\t" or (ord(char) >= 32 and ord(char) != 127):
            if cursor < len(line):
                line[cursor] = char
            else:
                line.append(char)
            cursor += 1
        ended_with_newline = False
        index += 1
    if line or ended_with_newline:
        lines.append("".join(line))
    return "\n".join(lines)
