File indexing completed on 2024-04-28 05:11:34
0001 /* 0002 SPDX-FileCopyrightText: 2010 Bertjan Broeksema <broeksema@kde.org> 0003 SPDX-FileCopyrightText: 2010 Klarälvdalens Datakonsult AB, a KDAB Group company <info@kdab.com> 0004 0005 SPDX-License-Identifier: LGPL-2.0-or-later 0006 */ 0007 0008 #include "incidencedescription.h" 0009 #include "ui_dialogdesktop.h" 0010 #include <KPIMTextEdit/RichTextComposer> 0011 0012 #include "incidenceeditor_debug.h" 0013 #include <KActionCollection> 0014 #include <KLocalizedString> 0015 #include <KToolBar> 0016 0017 using namespace IncidenceEditorNG; 0018 0019 namespace IncidenceEditorNG 0020 { 0021 class IncidenceDescriptionPrivate 0022 { 0023 public: 0024 IncidenceDescriptionPrivate() = default; 0025 0026 QString mRealOriginalDescriptionEditContents; 0027 bool mRichTextEnabled = false; 0028 }; 0029 } 0030 0031 IncidenceDescription::IncidenceDescription(Ui::EventOrTodoDesktop *ui) 0032 : IncidenceEditor(nullptr) 0033 , mUi(ui) 0034 , d(new IncidenceDescriptionPrivate()) 0035 { 0036 setObjectName(QLatin1StringView("IncidenceDescription")); 0037 mUi->mRichTextLabel->setContextMenuPolicy(Qt::NoContextMenu); 0038 setupToolBar(); 0039 connect(mUi->mRichTextLabel, &QLabel::linkActivated, this, &IncidenceDescription::toggleRichTextDescription); 0040 connect(mUi->mDescriptionEdit->richTextComposer(), &KPIMTextEdit::RichTextComposer::textChanged, this, &IncidenceDescription::checkDirtyStatus); 0041 } 0042 0043 IncidenceDescription::~IncidenceDescription() = default; 0044 0045 void IncidenceDescription::load(const KCalendarCore::Incidence::Ptr &incidence) 0046 { 0047 mLoadedIncidence = incidence; 0048 0049 d->mRealOriginalDescriptionEditContents.clear(); 0050 0051 if (incidence) { 0052 enableRichTextDescription(incidence->descriptionIsRich()); 0053 if (incidence->descriptionIsRich()) { 0054 mUi->mDescriptionEdit->richTextComposer()->setHtml(incidence->richDescription()); 0055 d->mRealOriginalDescriptionEditContents = mUi->mDescriptionEdit->richTextComposer()->toHtml(); 0056 } else { 0057 mUi->mDescriptionEdit->richTextComposer()->setPlainText(incidence->description()); 0058 d->mRealOriginalDescriptionEditContents = mUi->mDescriptionEdit->richTextComposer()->toPlainText(); 0059 } 0060 } else { 0061 enableRichTextDescription(false); 0062 mUi->mDescriptionEdit->richTextComposer()->clear(); 0063 } 0064 0065 mWasDirty = false; 0066 } 0067 0068 void IncidenceDescription::save(const KCalendarCore::Incidence::Ptr &incidence) 0069 { 0070 if (d->mRichTextEnabled) { 0071 incidence->setDescription(mUi->mDescriptionEdit->richTextComposer()->toHtml(), true); 0072 } else { 0073 incidence->setDescription(mUi->mDescriptionEdit->richTextComposer()->toPlainText(), false); 0074 } 0075 } 0076 0077 bool IncidenceDescription::isDirty() const 0078 { 0079 /* Sometimes, what you put in a KRichTextWidget isn't the same as what you get out. 0080 Line terminators (cr,lf) for example can be converted. 0081 0082 So, to see if the user changed something, we can't compare the original incidence 0083 with the new editor content. 0084 0085 Instead we compare the new editor content, with the original editor content, this way 0086 any transformation regarding non-printable chars will be irrelevant. 0087 */ 0088 if (d->mRichTextEnabled) { 0089 return !mLoadedIncidence->descriptionIsRich() || d->mRealOriginalDescriptionEditContents != mUi->mDescriptionEdit->richTextComposer()->toHtml(); 0090 } else { 0091 return mLoadedIncidence->descriptionIsRich() || d->mRealOriginalDescriptionEditContents != mUi->mDescriptionEdit->richTextComposer()->toPlainText(); 0092 } 0093 } 0094 0095 void IncidenceDescription::enableRichTextDescription(bool enable) 0096 { 0097 d->mRichTextEnabled = enable; 0098 0099 QString rt(i18nc("@action Enable or disable rich text editing", "Enable rich text")); 0100 QString placeholder(QStringLiteral("<a href=\"show\">%1 >></a>")); 0101 0102 if (enable) { 0103 rt = i18nc("@action Enable or disable rich text editing", "Disable rich text"); 0104 placeholder = QStringLiteral("<a href=\"show\"><< %1</a>"); 0105 mUi->mDescriptionEdit->richTextComposer()->activateRichText(); 0106 d->mRealOriginalDescriptionEditContents = mUi->mDescriptionEdit->richTextComposer()->toHtml(); 0107 } else { 0108 mUi->mDescriptionEdit->richTextComposer()->switchToPlainText(); 0109 d->mRealOriginalDescriptionEditContents = mUi->mDescriptionEdit->richTextComposer()->toPlainText(); 0110 } 0111 0112 placeholder = placeholder.arg(rt); 0113 mUi->mRichTextLabel->setText(placeholder); 0114 mUi->mDescriptionEdit->richTextComposer()->setEnableActions(enable); 0115 mUi->mEditToolBarPlaceHolder->setVisible(enable); 0116 checkDirtyStatus(); 0117 } 0118 0119 void IncidenceDescription::toggleRichTextDescription() 0120 { 0121 enableRichTextDescription(!d->mRichTextEnabled); 0122 } 0123 0124 void IncidenceDescription::setupToolBar() 0125 { 0126 #ifndef QT_NO_TOOLBAR 0127 auto collection = new KActionCollection(this); 0128 mUi->mDescriptionEdit->richTextComposer()->createActions(collection); 0129 0130 auto mEditToolBar = new KToolBar(mUi->mEditToolBarPlaceHolder); 0131 mEditToolBar->setToolButtonStyle(Qt::ToolButtonIconOnly); 0132 mEditToolBar->addAction(collection->action(QStringLiteral("format_text_bold"))); 0133 mEditToolBar->addAction(collection->action(QStringLiteral("format_text_italic"))); 0134 mEditToolBar->addAction(collection->action(QStringLiteral("format_text_underline"))); 0135 mEditToolBar->addAction(collection->action(QStringLiteral("format_text_strikeout"))); 0136 mEditToolBar->addSeparator(); 0137 0138 mEditToolBar->addAction(collection->action(QStringLiteral("format_font_family"))); 0139 mEditToolBar->addAction(collection->action(QStringLiteral("format_font_size"))); 0140 mEditToolBar->addSeparator(); 0141 0142 mEditToolBar->addAction(collection->action(QStringLiteral("format_text_foreground_color"))); 0143 mEditToolBar->addAction(collection->action(QStringLiteral("format_text_background_color"))); 0144 mEditToolBar->addSeparator(); 0145 0146 mEditToolBar->addAction(collection->action(QStringLiteral("format_list_style"))); 0147 mEditToolBar->addSeparator(); 0148 0149 mEditToolBar->addAction(collection->action(QStringLiteral("format_align_left"))); 0150 mEditToolBar->addAction(collection->action(QStringLiteral("format_align_center"))); 0151 mEditToolBar->addAction(collection->action(QStringLiteral("format_align_right"))); 0152 mEditToolBar->addAction(collection->action(QStringLiteral("format_align_justify"))); 0153 mEditToolBar->addSeparator(); 0154 0155 mEditToolBar->addAction(collection->action(QStringLiteral("format_painter"))); 0156 mEditToolBar->addSeparator(); 0157 mEditToolBar->addAction(collection->action(QStringLiteral("manage_link"))); 0158 mUi->mDescriptionEdit->richTextComposer()->setEnableActions(false); 0159 0160 auto layout = new QGridLayout(mUi->mEditToolBarPlaceHolder); 0161 layout->addWidget(mEditToolBar); 0162 #endif 0163 0164 // By default we don't show the rich text toolbar. 0165 mUi->mEditToolBarPlaceHolder->setVisible(false); 0166 d->mRichTextEnabled = false; 0167 } 0168 0169 void IncidenceDescription::printDebugInfo() const 0170 { 0171 // We're going to crash 0172 qCDebug(INCIDENCEEDITOR_LOG) << "RichText enabled " << d->mRichTextEnabled; 0173 0174 if (mLoadedIncidence) { 0175 qCDebug(INCIDENCEEDITOR_LOG) << "Incidence description is rich " << mLoadedIncidence->descriptionIsRich(); 0176 0177 if (mLoadedIncidence->descriptionIsRich()) { 0178 qCDebug(INCIDENCEEDITOR_LOG) << "desc is rich, and it is <desc>" << mLoadedIncidence->richDescription() << "</desc>; " 0179 << "widget has <desc>" << mUi->mDescriptionEdit->richTextComposer()->toHtml() << "</desc>; " 0180 << "expr mLoadedIncidence->richDescription() != mUi->mDescriptionEdit->toHtml() is " 0181 << (mLoadedIncidence->richDescription() != mUi->mDescriptionEdit->richTextComposer()->toHtml()); 0182 } else { 0183 qCDebug(INCIDENCEEDITOR_LOG) << "desc is not rich, and it is <desc>" << mLoadedIncidence->description() << "</desc>; " 0184 << "widget has <desc>" << mUi->mDescriptionEdit->richTextComposer()->toPlainText() << "</desc>; " 0185 << "expr mLoadedIncidence->description() != mUi->mDescriptionEdit->toPlainText() is " 0186 << (mLoadedIncidence->description() != mUi->mDescriptionEdit->richTextComposer()->toPlainText()); 0187 } 0188 } else { 0189 qCDebug(INCIDENCEEDITOR_LOG) << "Incidence is invalid"; 0190 } 0191 } 0192 0193 #include "moc_incidencedescription.cpp"