import logging

from PyQt6 import QtCore, QtGui, QtWidgets

logger = logging.getLogger("gotify-tray")


class PersistentNotification(QtWidgets.QWidget):
    close_all_requested = QtCore.pyqtSignal()

    def __init__(
        self,
        title: str,
        message: str,
        icon: QtGui.QIcon | QtWidgets.QSystemTrayIcon.MessageIcon,
        y_offset: int = 0,
        flash: bool = False,
        parent=None,
    ):
        super().__init__(parent)
        self.y_offset = y_offset
        self.flash = flash
        self.flash_state = False
        self.original_stylesheet = ""
        self.setWindowFlags(
            QtCore.Qt.WindowType.Window
            | QtCore.Qt.WindowType.FramelessWindowHint
            | QtCore.Qt.WindowType.WindowStaysOnTopHint
        )
        self.setAttribute(QtCore.Qt.WidgetAttribute.WA_OpaquePaintEvent, True)
        self.setAttribute(QtCore.Qt.WidgetAttribute.WA_ShowWithoutActivating)

        # Layout
        layout = QtWidgets.QHBoxLayout(self)
        layout.setContentsMargins(10, 10, 10, 10)
        layout.setSpacing(10)

        # Icon
        self.icon_label = QtWidgets.QLabel()
        if isinstance(icon, QtGui.QIcon):
            self.icon_label.setPixmap(icon.pixmap(32, 32))
        else:
            # For MessageIcon
            if icon == QtWidgets.QSystemTrayIcon.MessageIcon.Information:
                standard_icon = QtWidgets.QStyle.StandardPixmap.SP_MessageBoxInformation
            elif icon == QtWidgets.QSystemTrayIcon.MessageIcon.Warning:
                standard_icon = QtWidgets.QStyle.StandardPixmap.SP_MessageBoxWarning
            elif icon == QtWidgets.QSystemTrayIcon.MessageIcon.Critical:
                standard_icon = QtWidgets.QStyle.StandardPixmap.SP_MessageBoxCritical
            else:
                standard_icon = QtWidgets.QStyle.StandardPixmap.SP_MessageBoxInformation
            system_icon = self.style().standardIcon(standard_icon)
            self.icon_label.setPixmap(system_icon.pixmap(32, 32))
        layout.addWidget(self.icon_label)

        # Text
        text_layout = QtWidgets.QVBoxLayout()
        self.title_label = QtWidgets.QLabel(title)
        self.title_label.setStyleSheet("font-weight: bold;")
        text_layout.addWidget(self.title_label)

        self.message_label = QtWidgets.QLabel(message)
        self.message_label.setWordWrap(True)
        text_layout.addWidget(self.message_label)

        layout.addLayout(text_layout, 1)

        # Close button
        self.close_button = QtWidgets.QPushButton("×")
        self.close_button.setFixedSize(20, 20)
        self.close_button.clicked.connect(self._on_close)
        layout.addWidget(self.close_button)

        # Style
        self.setAutoFillBackground(True)
        self.setBackgroundRole(QtGui.QPalette.ColorRole.Window)
        palette = self.palette()
        palette.setColor(QtGui.QPalette.ColorRole.Window, QtGui.QColor("white"))
        palette.setColor(QtGui.QPalette.ColorRole.WindowText, QtGui.QColor("red"))
        self.setPalette(palette)

        self.setStyleSheet("""
            PersistentNotification {
                border-radius: 10px;
                border: 1px solid rgba(100, 100, 100, 200);
            }
            QPushButton {
                background-color: transparent;
                color: white;
                border: none;
                font-size: 16px;
            }
            QPushButton:hover {
                background-color: rgba(100, 100, 100, 100);
            }
        """)

        if self.flash:
            self.flash_timer = QtCore.QTimer(self)
            self.flash_timer.timeout.connect(self._toggle_flash)

        # Size and position
        self.adjustSize()
        self.setFixedWidth(300)
        self._position()

        # Timer for fade out if not clicked, but since persistent, maybe not needed
        # But to avoid staying forever if forgotten, perhaps auto-close after long time
        # But user wants until clicked, so no timer.

    def _position(self):
        screen = QtWidgets.QApplication.primaryScreen().availableGeometry()
        # Stack from bottom right
        self.move(
            screen.width() - self.width() - 10,
            screen.height() - self.height() - 50 - self.y_offset,
        )

    def _toggle_flash(self):
        self.flash_state = not self.flash_state
        palette = self.palette()
        if self.flash_state:
            palette.setColor(QtGui.QPalette.ColorRole.Window, QtGui.QColor("red"))
            palette.setColor(QtGui.QPalette.ColorRole.WindowText, QtGui.QColor("white"))
        else:
            palette.setColor(QtGui.QPalette.ColorRole.Window, QtGui.QColor("white"))
            palette.setColor(QtGui.QPalette.ColorRole.WindowText, QtGui.QColor("red"))
        self.setPalette(palette)
        self.update()
        self.repaint()

    def mousePressEvent(self, event):
        self._on_close()

    def _on_close(self):
        if self.flash:
            self.flash_timer.stop()
        self.close_all_requested.emit()
        self.close()

    def showEvent(self, event):
        super().showEvent(event)
        self.raise_()
        if self.flash:
            self.flash_timer.start(1000)
