#include "avatar-widget.h"

#include <QPainter>
#include <QPainterPath>
#include <QImage>
#include <QApplication>

AvatarWidget::AvatarWidget(QWidget* parent)
    : QWidget(parent)
{
    setAttribute(Qt::WA_TranslucentBackground, true);
    setFixedSize(m_diameter, m_diameter);
    setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
}

void AvatarWidget::setDisplayName(const QString& name)
{
    if (m_displayName == name)
        return;
    m_displayName = name;
    emit displayNameChanged(m_displayName);
    update();
}

void AvatarWidget::setDiameter(int d)
{
    if (d <= 0 || d == m_diameter)
        return;
    m_diameter = d;
    setFixedSize(m_diameter, m_diameter);
    emit diameterChanged(m_diameter);
    updateGeometry();
    update();
}

QPixmap AvatarWidget::fetchThemeAvatarPixmap(int base) const
{
    // Try common theme icon names
    QIcon icon = QIcon::fromTheme("avatar-default");
    if (icon.isNull()) icon = QIcon::fromTheme("user-identity");
    if (icon.isNull()) icon = QIcon::fromTheme("avatar-default-symbolic");
    if (icon.isNull()) icon = QIcon::fromTheme("contact-new");
    if (icon.isNull()) icon = QIcon::fromTheme("system-users");
    return icon.pixmap(base, base);
}

QPixmap AvatarWidget::cropTransparentMargins(const QPixmap& px)
{
    if (px.isNull()) return px;
    QImage img = px.toImage().convertToFormat(QImage::Format_ARGB32_Premultiplied);
    const int w = img.width(), h = img.height();
    int left = w, right = -1, top = h, bottom = -1;
    const int threshold = 8; // alpha threshold
    for (int y = 0; y < h; ++y) {
        const QRgb* line = reinterpret_cast<const QRgb*>(img.constScanLine(y));
        for (int x = 0; x < w; ++x) {
            if (qAlpha(line[x]) > threshold) {
                if (x < left) left = x;
                if (x > right) right = x;
                if (y < top) top = y;
                if (y > bottom) bottom = y;
            }
        }
    }
    if (right >= left && bottom >= top) {
        QRect r(left, top, right - left + 1, bottom - top + 1);
        return QPixmap::fromImage(img.copy(r));
    }
    return px;
}

QPixmap AvatarWidget::makePlaceholder(int base) const
{
    QPixmap placeholder(base, base);
    placeholder.fill(Qt::transparent);
    QPainter ph(&placeholder);
    ph.setRenderHint(QPainter::Antialiasing, true);
    ph.setRenderHint(QPainter::TextAntialiasing, true);
    // Circle background (slightly lighter than page bg)
    QColor bg(96, 99, 105);
    ph.setBrush(bg);
    ph.setPen(Qt::NoPen);
    ph.drawEllipse(QRect(0, 0, base, base));

    QString first;
    const QString t = m_displayName.trimmed();
    if (!t.isEmpty()) first = t.left(1).toUpper(); else first = QStringLiteral("U");

    QFont f = ph.font();
    f.setPointSizeF(base * 0.45);
    f.setBold(true);
    ph.setFont(f);
    ph.setPen(Qt::white);
    ph.drawText(QRect(0, 0, base, base), Qt::AlignCenter, first);
    ph.end();
    return placeholder;
}

void AvatarWidget::paintEvent(QPaintEvent*)
{
    const int size = m_diameter;
    const int base = size * 2; // draw with a larger source for better downscale

    QPixmap src = fetchThemeAvatarPixmap(base);
    if (src.isNull()) {
        src = makePlaceholder(base);
    }
    src = cropTransparentMargins(src);

    QPainter p(this);
    p.setRenderHint(QPainter::Antialiasing, true);
    p.setRenderHint(QPainter::SmoothPixmapTransform, true);

    // Clip to circle (AA can leave a subpixel seam with an outer border)
    QPainterPath path; path.addEllipse(rect());
    p.setClipPath(path);

    // Scale-and-crop to fill; slightly overdraw to hide any AA seam against a 1px border
    const QPixmap scaled = src.scaled(size, size, Qt::KeepAspectRatioByExpanding, Qt::SmoothTransformation);
    p.save();
    p.translate(-0.5, -0.5); // bleed under the border by half a pixel on each side
    p.drawPixmap(0, 0, scaled.width() + 1, scaled.height() + 1, scaled);
    p.restore();

    // Optional: border drawn via QSS (#avatarLabel) outside of paint
}
