File indexing completed on 2024-04-28 04:38:52

0001 /*
0002     SPDX-FileCopyrightText: 2020 Jonathan L. Verner <jonathan.verner@matfyz.cz>
0003 
0004     SPDX-License-Identifier: LGPL-2.0-or-later
0005 */
0006 
0007 #include "simplecommitform.h"
0008 
0009 #include <KColorScheme>
0010 #include <KLocalizedString>
0011 #include <KMessageWidget>
0012 
0013 #include <QAction>
0014 #include <QFontDatabase>
0015 #include <QGuiApplication>
0016 #include <QHBoxLayout>
0017 #include <QLabel>
0018 #include <QLineEdit>
0019 #include <QPainter>
0020 #include <QPushButton>
0021 #include <QTextEdit>
0022 #include <QToolButton>
0023 #include <QVBoxLayout>
0024 
0025 QPixmap textIcon(const QString& str, const QColor& fg = Qt::black, const QColor& bg = Qt::white)
0026 {
0027     QPixmap ret(40, 40);
0028     QPainter p(&ret);
0029     QFont font = p.font();
0030     font.setPixelSize(0.625 * 40);
0031     p.setFont(font);
0032     ret.fill(bg);
0033     p.setPen(fg);
0034     p.drawText(ret.rect(), Qt::AlignCenter, str);
0035     return ret;
0036 }
0037 
0038 SimpleCommitForm::SimpleCommitForm(QWidget* parent)
0039     : QWidget(parent)
0040     , m_commitBtn(new QPushButton(i18n("Commit")))
0041     , m_summaryEdit(new QLineEdit)
0042     , m_messageEdit(new QTextEdit)
0043     , m_inlineError(new KMessageWidget)
0044     , m_disabled(false)
0045 {
0046     QHBoxLayout* _hlayout = new QHBoxLayout();
0047     _hlayout->setSpacing(0);
0048     _hlayout->addWidget(m_summaryEdit);
0049     _hlayout->addWidget(m_commitBtn);
0050 
0051     QVBoxLayout* _vlayout = new QVBoxLayout(this);
0052     _vlayout->setSpacing(2);
0053     _vlayout->setContentsMargins(0, 0, 0, 0);
0054     _vlayout->addWidget(m_inlineError);
0055     _vlayout->addLayout(_hlayout);
0056     _vlayout->addWidget(m_messageEdit);
0057 
0058     m_inlineError->setHidden(true);
0059     m_inlineError->setMessageType(KMessageWidget::Error);
0060     m_inlineError->setCloseButtonVisible(true);
0061     m_inlineError->setWordWrap(true);
0062 
0063     auto monospace = QFontDatabase::systemFont(QFontDatabase::FixedFont);
0064     monospace.setStyleHint(QFont::TypeWriter);
0065     m_messageEdit->setPlaceholderText(i18n("Extended commit description"));
0066     m_messageEdit->setMinimumHeight(30);
0067     m_messageEdit->setFont(monospace);
0068     m_messageEdit->setWordWrapMode(QTextOption::WordWrap);
0069     m_messageEdit->setLineWrapMode(QTextEdit::FixedColumnWidth);
0070     m_messageEdit->setLineWrapColumnOrWidth(80);
0071 
0072     QAction* summaryLen = new QAction(this);
0073     m_summaryEdit->setPlaceholderText(i18n("Commit summary"));
0074     m_summaryEdit->addAction(summaryLen, QLineEdit::TrailingPosition);
0075     m_summaryEdit->setFont(monospace);
0076 
0077     auto colors = KColorScheme();
0078 
0079     summaryLen->setIcon(textIcon(QString::number(0), colors.foreground(KColorScheme::NormalText).color(),
0080                                  colors.background(KColorScheme::NormalBackground).color()));
0081     connect(m_summaryEdit, &QLineEdit::textChanged, this, [=] {
0082         int sz = m_summaryEdit->text().size();
0083 
0084         // Disable the commit button if the message is empty
0085         if (sz == 0) {
0086             m_commitBtn->setDisabled(true);
0087             if (!m_disabled)
0088                 m_commitBtn->setToolTip(i18n("To commit changes, please write a commit message first"));
0089         } else if (!m_disabled) {
0090             m_commitBtn->setToolTip(
0091                 i18n("Commit changes to <b>%1</b> on branch <b>%2</b>", m_projectName, m_branchName));
0092             m_commitBtn->setDisabled(false);
0093         }
0094 
0095         // Determine the summary background color based on the length
0096         QBrush fg, bg;
0097 
0098         if (sz < 65) {
0099             bg = colors.background(KColorScheme::NormalBackground);
0100             fg = colors.foreground(KColorScheme::NormalText);
0101         } else if (sz < 73) {
0102            bg = colors.background(KColorScheme::NormalBackground);
0103            fg = colors.foreground(KColorScheme::NormalText);
0104         } else if (sz < 79) {
0105             bg = colors.background(KColorScheme::NeutralBackground);
0106             fg = colors.foreground(KColorScheme::NeutralText);
0107         } else {
0108             bg = colors.background(KColorScheme::NegativeBackground);
0109             fg = colors.foreground(KColorScheme::NegativeText);
0110         }
0111 
0112         QPalette palette = QGuiApplication::palette();
0113         palette.setBrush(QPalette::Base, bg);
0114         palette.setBrush(QPalette::Text, fg);
0115         m_summaryEdit->setPalette(palette);
0116         summaryLen->setIcon(textIcon(QString::number(sz), fg.color(), bg.color()));
0117     });
0118 
0119     connect(m_commitBtn, &QPushButton::clicked, this, &SimpleCommitForm::committed);
0120     setLayout(_vlayout);
0121 
0122     m_commitBtn->setToolTip(i18n("To commit changes, please select a project first"));
0123     disable();
0124 }
0125 
0126 QString SimpleCommitForm::extendedDescription(int wrapAtColumn) const
0127 {
0128     if (wrapAtColumn <= 0)
0129         return m_messageEdit->toPlainText();
0130     int currentLineLen = 0;
0131     QString ret;
0132     for(const auto c: m_messageEdit->toPlainText()) {
0133         if (c == QLatin1Char('\n')) {
0134             ret += QLatin1Char('\n');
0135             currentLineLen = 0;
0136         } else if (currentLineLen > wrapAtColumn && c.isSpace()) {
0137             ret += QLatin1Char('\n');
0138             currentLineLen = 0;
0139         } else {
0140             ret += c;
0141             currentLineLen++;
0142         }
0143     }
0144     return ret;
0145 }
0146 
0147 void SimpleCommitForm::setExtendedDescription(const QString& txt)
0148 {
0149     m_messageEdit->setText(txt);
0150 }
0151 QString SimpleCommitForm::summary() const
0152 {
0153     return m_summaryEdit->text();
0154 }
0155 void SimpleCommitForm::setSummary(const QString& txt)
0156 {
0157     m_summaryEdit->setText(txt);
0158 }
0159 void SimpleCommitForm::disableCommitButton()
0160 {
0161     m_disabled = true;
0162     m_commitBtn->setDisabled(true);
0163     m_commitBtn->setToolTip(i18n("Please stage some changes before committing."));
0164 }
0165 void SimpleCommitForm::enableCommitButton()
0166 {
0167     m_disabled = false;
0168     if (m_summaryEdit->text().size() > 0) {
0169         m_commitBtn->setToolTip(i18n("Commit changes to <b>%1</b> on branch <b>%2</b>", m_projectName, m_branchName));
0170         m_commitBtn->setDisabled(false);
0171     } else {
0172         m_commitBtn->setToolTip(i18n("To commit changes, please write a commit message first"));
0173     }
0174 }
0175 
0176 void SimpleCommitForm::disable()
0177 {
0178     m_commitBtn->setDisabled(true);
0179     m_summaryEdit->setDisabled(true);
0180     m_messageEdit->setDisabled(true);
0181 }
0182 
0183 void SimpleCommitForm::enable()
0184 {
0185     if (! m_disabled)
0186         enableCommitButton();
0187     m_summaryEdit->setDisabled(false);
0188     m_messageEdit->setDisabled(false);
0189 }
0190 
0191 
0192 
0193 void SimpleCommitForm::clear()
0194 {
0195     m_summaryEdit->clear();
0196     m_messageEdit->clear();
0197     clearError();
0198 }
0199 
0200 
0201 void SimpleCommitForm::setBranchName(const QString& branchName)
0202 {
0203     m_branchName = branchName;
0204 }
0205 
0206 void SimpleCommitForm::setProjectName(const QString& projName)
0207 {
0208     m_projectName = projName;
0209 }
0210 
0211 void SimpleCommitForm::showError(const QString& error)
0212 {
0213     m_inlineError->setText(error);
0214     m_inlineError->animatedShow();
0215 }
0216 
0217 void SimpleCommitForm::clearError()
0218 {
0219     if (!m_inlineError->isHidden() && !m_inlineError->isHideAnimationRunning()) {
0220         m_inlineError->animatedHide();
0221     }
0222 }
0223 
0224 #include "moc_simplecommitform.cpp"