Messagelib

templatesconfiguration.cpp
1/*
2 * SPDX-FileCopyrightText: 2006 Dmitry Morozhnikov <dmiceman@mail.ru>
3 * SPDX-FileCopyrightText: 2012-2024 Laurent Montel <montel@kde.org>
4 *
5 * SPDX-License-Identifier: GPL-2.0-or-later
6 */
7
8#include "templatesconfiguration.h"
9#include "globalsettings_templateparser.h"
10#include "templatesconfiguration_kfg.h"
11#include <TextCustomEditor/PlainTextEditor>
12
13#include "templateparser_debug.h"
14#include <KLocalizedString>
15#include <KMessageBox>
16
17#include <QWhatsThis>
18
19using namespace TemplateParser;
20class TemplateParser::TemplatesConfigurationPrivate
21{
22public:
23 TemplatesConfigurationPrivate() = default;
24
25 QString mHelpString;
26};
27
28TemplatesConfiguration::TemplatesConfiguration(QWidget *parent, const QString &name)
29 : QWidget(parent)
30 , d(new TemplateParser::TemplatesConfigurationPrivate)
31{
32 setupUi(this);
33 setObjectName(name);
34
36 sizeHint();
37
38 connect(textEdit_new->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
39 connect(textEdit_reply->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
40 connect(textEdit_reply_all->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
41 connect(textEdit_forward->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
42 connect(lineEdit_quote, &QLineEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
43
44 connect(mInsertCommand,
45 qOverload<const QString &, int>(&TemplateParser::TemplatesInsertCommandPushButton::insertCommand),
46 this,
47 &TemplatesConfiguration::slotInsertCommand);
48
49 d->mHelpString = i18n(
50 "<p>Here you can create and manage templates to use when "
51 "composing new messages, replies or forwarded messages.</p>"
52 "<p>The message templates support substitution commands, "
53 "either simply type them or select them from "
54 "the <i>Insert command</i> menu.</p>");
55 const QString templateConfigurationName(name);
56 if (templateConfigurationName == QLatin1StringView("folder-templates")) {
57 d->mHelpString += i18n(
58 "<p>Templates specified here are folder-specific. "
59 "They override both global templates and per-identity "
60 "templates.</p>");
61 } else if (templateConfigurationName == QLatin1StringView("identity-templates")) {
62 d->mHelpString += i18n(
63 "<p>Templates specified here are identity-specific. "
64 "They override global templates, but can be overridden by "
65 "per-folder templates if they are specified.</p>");
66 } else {
67 d->mHelpString += i18n(
68 "<p>These are global (default) templates. They can be overridden "
69 "by per-identity templates or per-folder templates "
70 "if they are specified.</p>");
71 }
72
73 mHelp->setText(i18n("<a href=\"whatsthis\">How does this work?</a>"));
74 connect(mHelp, &QLabel::linkActivated, this, &TemplatesConfiguration::slotHelpLinkClicked);
75 mHelp->setContextMenuPolicy(Qt::NoContextMenu);
76}
77
78TemplatesConfiguration::~TemplatesConfiguration()
79{
80 disconnect(textEdit_new->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
81 disconnect(textEdit_reply->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
82 disconnect(textEdit_reply_all->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
83 disconnect(textEdit_forward->editor(), &QPlainTextEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
84 disconnect(lineEdit_quote, &QLineEdit::textChanged, this, &TemplatesConfiguration::slotTextChanged);
85}
86
87void TemplatesConfiguration::slotHelpLinkClicked(const QString &)
88{
89 QWhatsThis::showText(QCursor::pos(), d->mHelpString);
90}
91
92void TemplatesConfiguration::slotTextChanged()
93{
94 Q_EMIT changed();
95}
96
97void TemplatesConfiguration::resetToDefault()
98{
100 i18n("Do you want to reset current template or all templates to default?"),
101 i18nc("@title:window", "Reset to default"),
102 KGuiItem(i18n("Reset Current Template")),
103 KGuiItem(i18n("Reset All Templates")),
105
107 return;
108 } else if (choice == KMessageBox::ButtonCode::PrimaryAction) {
109 const int toolboxCurrentIndex(toolBox1->currentIndex());
110 if (toolBox1->widget(toolboxCurrentIndex) == page_new) {
111 textEdit_new->setPlainText(DefaultTemplates::defaultNewMessage());
112 } else if (toolBox1->widget(toolboxCurrentIndex) == page_reply) {
113 textEdit_reply->setPlainText(DefaultTemplates::defaultReply());
114 } else if (toolBox1->widget(toolboxCurrentIndex) == page_reply_all) {
115 textEdit_reply_all->setPlainText(DefaultTemplates::defaultReplyAll());
116 } else if (toolBox1->widget(toolboxCurrentIndex) == page_forward) {
117 textEdit_forward->setPlainText(DefaultTemplates::defaultForward());
118 } else {
119 qCDebug(TEMPLATEPARSER_LOG) << "Unknown current page in TemplatesConfiguration!";
120 }
121 } else {
122 textEdit_new->setPlainText(DefaultTemplates::defaultNewMessage());
123 textEdit_reply->setPlainText(DefaultTemplates::defaultReply());
124 textEdit_reply_all->setPlainText(DefaultTemplates::defaultReplyAll());
125 textEdit_forward->setPlainText(DefaultTemplates::defaultForward());
126 }
127 lineEdit_quote->setText(DefaultTemplates::defaultQuoteString());
128}
129
130QLabel *TemplatesConfiguration::helpLabel() const
131{
132 return mHelp;
133}
134
135void TemplatesConfiguration::loadFromGlobal()
136{
137 QString str;
138 str = TemplateParserSettings::self()->templateNewMessage();
139 if (str.isEmpty()) {
140 textEdit_new->setPlainText(DefaultTemplates::defaultNewMessage());
141 } else {
142 textEdit_new->setPlainText(str);
143 }
144 str = TemplateParserSettings::self()->templateReply();
145 if (str.isEmpty()) {
146 textEdit_reply->setPlainText(DefaultTemplates::defaultReply());
147 } else {
148 textEdit_reply->setPlainText(str);
149 }
150 str = TemplateParserSettings::self()->templateReplyAll();
151 if (str.isEmpty()) {
152 textEdit_reply_all->setPlainText(DefaultTemplates::defaultReplyAll());
153 } else {
154 textEdit_reply_all->setPlainText(str);
155 }
156 str = TemplateParserSettings::self()->templateForward();
157 if (str.isEmpty()) {
158 textEdit_forward->setPlainText(DefaultTemplates::defaultForward());
159 } else {
160 textEdit_forward->setPlainText(str);
161 }
162 str = TemplateParserSettings::self()->quoteString();
163 if (str.isEmpty()) {
164 lineEdit_quote->setText(DefaultTemplates::defaultQuoteString());
165 } else {
166 lineEdit_quote->setText(str);
167 }
168}
169
170void TemplatesConfiguration::saveToGlobal()
171{
172 TemplateParserSettings::self()->setTemplateNewMessage(strOrBlank(textEdit_new->toPlainText()));
173 TemplateParserSettings::self()->setTemplateReply(strOrBlank(textEdit_reply->toPlainText()));
174 TemplateParserSettings::self()->setTemplateReplyAll(strOrBlank(textEdit_reply_all->toPlainText()));
175 TemplateParserSettings::self()->setTemplateForward(strOrBlank(textEdit_forward->toPlainText()));
176 TemplateParserSettings::self()->setQuoteString(lineEdit_quote->text());
177 TemplateParserSettings::self()->save();
178}
179
180void TemplatesConfiguration::loadFromIdentity(uint id)
181{
182 Templates t(configIdString(id));
183
184 QString str;
185
186 str = t.templateNewMessage();
187 if (str.isEmpty()) {
188 str = TemplateParserSettings::self()->templateNewMessage();
189 }
190 if (str.isEmpty()) {
191 str = DefaultTemplates::defaultNewMessage();
192 }
193 textEdit_new->setPlainText(str);
194
195 str = t.templateReply();
196 if (str.isEmpty()) {
197 str = TemplateParserSettings::self()->templateReply();
198 }
199 if (str.isEmpty()) {
200 str = DefaultTemplates::defaultReply();
201 }
202 textEdit_reply->setPlainText(str);
203
204 str = t.templateReplyAll();
205 if (str.isEmpty()) {
206 str = TemplateParserSettings::self()->templateReplyAll();
207 }
208 if (str.isEmpty()) {
209 str = DefaultTemplates::defaultReplyAll();
210 }
211 textEdit_reply_all->setPlainText(str);
212
213 str = t.templateForward();
214 if (str.isEmpty()) {
215 str = TemplateParserSettings::self()->templateForward();
216 }
217 if (str.isEmpty()) {
218 str = DefaultTemplates::defaultForward();
219 }
220 textEdit_forward->setPlainText(str);
221
222 str = t.quoteString();
223 if (str.isEmpty()) {
224 str = TemplateParserSettings::self()->quoteString();
225 }
226 if (str.isEmpty()) {
227 str = DefaultTemplates::defaultQuoteString();
228 }
229 lineEdit_quote->setText(str);
230}
231
232void TemplatesConfiguration::saveToIdentity(uint id)
233{
234 Templates t(configIdString(id));
235 t.setTemplateNewMessage(strOrBlank(textEdit_new->toPlainText()));
236 t.setTemplateReply(strOrBlank(textEdit_reply->toPlainText()));
237 t.setTemplateReplyAll(strOrBlank(textEdit_reply_all->toPlainText()));
238 t.setTemplateForward(strOrBlank(textEdit_forward->toPlainText()));
239 t.setQuoteString(lineEdit_quote->text());
240 t.save();
241}
242
243void TemplatesConfiguration::loadFromFolder(const QString &id, uint identity)
244{
245 Templates t(id);
246 Templates *tid = nullptr;
247
248 if (identity) {
249 tid = new Templates(configIdString(identity));
250 }
251
252 QString str;
253
254 str = t.templateNewMessage();
255 if (str.isEmpty() && tid) {
256 str = tid->templateNewMessage();
257 }
258 if (str.isEmpty()) {
259 str = TemplateParserSettings::self()->templateNewMessage();
260 if (str.isEmpty()) {
261 str = DefaultTemplates::defaultNewMessage();
262 }
263 }
264 textEdit_new->setPlainText(str);
265
266 str = t.templateReply();
267 if (str.isEmpty() && tid) {
268 str = tid->templateReply();
269 }
270 if (str.isEmpty()) {
271 str = TemplateParserSettings::self()->templateReply();
272 if (str.isEmpty()) {
273 str = DefaultTemplates::defaultReply();
274 }
275 }
276 textEdit_reply->setPlainText(str);
277
278 str = t.templateReplyAll();
279 if (str.isEmpty() && tid) {
280 str = tid->templateReplyAll();
281 if (str.isEmpty()) {
282 str = TemplateParserSettings::self()->templateReplyAll();
283 }
284 }
285 if (str.isEmpty()) {
286 str = DefaultTemplates::defaultReplyAll();
287 }
288 textEdit_reply_all->setPlainText(str);
289
290 str = t.templateForward();
291 if (str.isEmpty() && tid) {
292 str = tid->templateForward();
293 if (str.isEmpty()) {
294 str = TemplateParserSettings::self()->templateForward();
295 }
296 }
297 if (str.isEmpty()) {
298 str = DefaultTemplates::defaultForward();
299 }
300 textEdit_forward->setPlainText(str);
301
302 str = t.quoteString();
303 if (str.isEmpty() && tid) {
304 str = tid->quoteString();
305 }
306 if (str.isEmpty()) {
307 str = TemplateParserSettings::self()->quoteString();
308 if (str.isEmpty()) {
309 str = DefaultTemplates::defaultQuoteString();
310 }
311 }
312 lineEdit_quote->setText(str);
313
314 delete (tid);
315}
316
317void TemplatesConfiguration::saveToFolder(const QString &id)
318{
319 Templates t(id);
320
321 t.setTemplateNewMessage(strOrBlank(textEdit_new->toPlainText()));
322 t.setTemplateReply(strOrBlank(textEdit_reply->toPlainText()));
323 t.setTemplateReplyAll(strOrBlank(textEdit_reply_all->toPlainText()));
324 t.setTemplateForward(strOrBlank(textEdit_forward->toPlainText()));
325 t.setQuoteString(lineEdit_quote->text());
326 t.save();
327}
328
329QPlainTextEdit *TemplatesConfiguration::currentTextEdit() const
330{
331 QPlainTextEdit *edit = nullptr;
332
333 const int toolboxCurrentIndex(toolBox1->currentIndex());
334 if (toolBox1->widget(toolboxCurrentIndex) == page_new) {
335 edit = textEdit_new->editor();
336 } else if (toolBox1->widget(toolboxCurrentIndex) == page_reply) {
337 edit = textEdit_reply->editor();
338 } else if (toolBox1->widget(toolboxCurrentIndex) == page_reply_all) {
339 edit = textEdit_reply_all->editor();
340 } else if (toolBox1->widget(toolboxCurrentIndex) == page_forward) {
341 edit = textEdit_forward->editor();
342 } else {
343 qCDebug(TEMPLATEPARSER_LOG) << "Unknown current page in TemplatesConfiguration!";
344 edit = nullptr;
345 }
346 return edit;
347}
348
349void TemplatesConfiguration::slotInsertCommand(const QString &cmd, int adjustCursor)
350{
351 QPlainTextEdit *edit = currentTextEdit();
352 if (!edit) {
353 return;
354 }
355
356 // qCDebug(TEMPLATEPARSER_LOG) << "Insert command:" << cmd;
357 const QString editText(edit->toPlainText());
358 if ((editText.contains(QLatin1StringView("%FORCEDPLAIN")) && (cmd == QLatin1StringView("%FORCEDHTML")))
359 || (editText.contains(QLatin1StringView("%FORCEDHTML")) && (cmd == QLatin1StringView("%FORCEDPLAIN")))) {
361 i18n("Use of \"Reply using plain text\" and \"Reply using HTML text\" in pairs"
362 " is not correct. Use only one of the aforementioned commands with \" Reply as"
363 " Quoted Message command\" as per your need\n"
364 "(a)Reply using plain text for quotes to be strictly in plain text\n"
365 "(b)Reply using HTML text for quotes being in HTML format if present"));
366 } else {
367 QTextCursor cursor = edit->textCursor();
369 cursor.setPosition(cursor.position() + adjustCursor);
370 edit->setTextCursor(cursor);
371 edit->setFocus();
372 }
373}
374
375QString TemplatesConfiguration::strOrBlank(const QString &str)
376{
377 if (str.trimmed().isEmpty()) {
378 return QStringLiteral("%BLANK");
379 }
380 return str;
381}
382
384{
385 return QStringLiteral("IDENTITY_%1").arg(id);
386}
387
388#include "moc_templatesconfiguration.cpp"
static QString configIdString(uint id)
Returns the template configuration identifier string for a given identity.
QString i18nc(const char *context, const char *text, const TYPE &arg...)
QString i18n(const char *text, const TYPE &arg...)
void error(QWidget *parent, const QString &text, const QString &title, const KGuiItem &buttonOk, Options options=Notify)
ButtonCode questionTwoActionsCancel(QWidget *parent, const QString &text, const QString &title, const KGuiItem &primaryAction, const KGuiItem &secondaryAction, const KGuiItem &cancelAction=KStandardGuiItem::cancel(), const QString &dontAskAgainName=QString(), Options options=Notify)
KGuiItem cancel()
QPoint pos()
void linkActivated(const QString &link)
void textChanged(const QString &text)
Q_EMITQ_EMIT
bool disconnect(const QMetaObject::Connection &connection)
T qobject_cast(QObject *object)
void setTextCursor(const QTextCursor &cursor)
void textChanged()
QTextCursor textCursor() const const
QString toPlainText() const const
QString arg(Args &&... args) const const
NoContextMenu
void insertText(const QString &text)
QFuture< ArgsType< Signal > > connect(Sender *sender, Signal signal)
void showText(const QPoint &pos, const QString &text, QWidget *w)
void setFocus()
This file is part of the KDE documentation.
Documentation copyright © 1996-2024 The KDE developers.
Generated on Tue Mar 26 2024 11:12:44 by doxygen 1.10.0 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.