from qgis.PyQt.QtCore import Qt
from qgis.PyQt.QtGui import QColor, QPen


def color_to_dict(color: QColor) -> dict:
    """
    Convert QColor to dict for json export. Use default export of Qt.

    Args:
        color (QColor): input color

    """
    result = {}
    result["name"] = color.name()

    return result


def color_from_json(data: dict) -> QColor:
    """
    Define QColor from json data (see to_dict).

    Args:
        data: json data

    """
    result = QColor()
    result.setNamedColor(data["name"])
    return result


def pen_to_dict(pen: QPen) -> dict:
    """
    Convert QPen to dict for json export.

    Args:
        pen (QPen): input pen

    """
    result = {}
    result["color"] = color_to_dict(pen.color())
    result["width"] = pen.width()

    style = pen.style()
    if style == Qt.NoPen:
        style_str = "no-pen"
    elif style == Qt.SolidLine:
        style_str = "solid"
    elif style == Qt.DashLine:
        style_str = "dash"
    elif style == Qt.DotLine:
        style_str = "dot"
    elif style == Qt.DashDotLine:
        style_str = "dash-dot"
    elif style == Qt.DashDotDotLine:
        style_str = "dash-dot-dot"
    else:
        style_str = "solid"

    result["style"] = style_str

    return result


def pen_from_json(data: dict) -> QPen:
    """
    Define QPen from json data (see to_dict)

    Args:
        data: json data

    """
    result = QPen()

    result.setColor(color_from_json(data["color"]))
    result.setWidth(data["width"])

    style_str = data["style"]
    if style_str == "no-pen":
        style = Qt.NoPen
    elif style_str == "solid":
        style = Qt.SolidLine
    elif style_str == "dash":
        style = Qt.DashLine
    elif style_str == "dot":
        style = Qt.DotLine
    elif style_str == "dash-dot":
        style = Qt.DashDotLine
    elif style_str == "dash-dot-dot":
        style = Qt.DashDotDotLine
    else:
        style = Qt.SolidLine

    result.setStyle(style)

    # Pen always display with cosmetic or pyqtgraph result is not valid
    result.setCosmetic(True)

    return result
