Akonadi

collectionpropertiesdialog.cpp
1 /*
2  SPDX-FileCopyrightText: 2008 Volker Krause <[email protected]>
3 
4  SPDX-License-Identifier: LGPL-2.0-or-later
5 */
6 
7 #include "collectionpropertiesdialog.h"
8 
9 #include "cachepolicy.h"
10 #include "cachepolicypage.h"
11 #include "collection.h"
12 #include "collectiongeneralpropertiespage_p.h"
13 #include "collectionmodifyjob.h"
14 
15 #include "akonadiwidgets_debug.h"
16 
17 #include <KConfigGroup>
18 #include <KSharedConfig>
19 #include <QTabWidget>
20 
21 #include <QDialogButtonBox>
22 
23 using namespace Akonadi;
24 
25 /**
26  * @internal
27  */
28 class Akonadi::CollectionPropertiesDialogPrivate
29 {
30 public:
31  CollectionPropertiesDialogPrivate(CollectionPropertiesDialog *parent, const Akonadi::Collection &collection, const QStringList &pageNames);
32 
33  void init();
34 
35  static void registerBuiltinPages();
36 
37  void save()
38  {
39  const int numberOfTab(mTabWidget->count());
40  for (int i = 0; i < numberOfTab; ++i) {
41  auto page = static_cast<CollectionPropertiesPage *>(mTabWidget->widget(i));
42  page->save(mCollection);
43  }
44 
45  // We use WA_DeleteOnClose => Don't use dialog as parent otherwise we can't save modified collection.
46  auto job = new CollectionModifyJob(mCollection);
47  QObject::connect(job, &CollectionModifyJob::result, q, [this](KJob *job) {
48  saveResult(job);
49  });
50  Q_EMIT q->settingsSaved();
51  }
52 
53  void saveResult(KJob *job)
54  {
55  if (job->error()) {
56  // TODO
57  qCWarning(AKONADIWIDGETS_LOG) << job->errorString();
58  }
59  }
60 
61  void setCurrentPage(const QString &name)
62  {
63  const int numberOfTab(mTabWidget->count());
64  for (int i = 0; i < numberOfTab; ++i) {
65  QWidget *w = mTabWidget->widget(i);
66  if (w->objectName() == name) {
67  mTabWidget->setCurrentIndex(i);
68  break;
69  }
70  }
71  }
72 
74  Collection mCollection;
75  QStringList mPageNames;
76  QTabWidget *mTabWidget = nullptr;
77 };
78 
79 class CollectionPropertiesPageFactoryList : public QList<CollectionPropertiesPageFactory *>
80 {
81 public:
82  explicit CollectionPropertiesPageFactoryList() = default;
83  CollectionPropertiesPageFactoryList(const CollectionPropertiesPageFactoryList &) = delete;
84  CollectionPropertiesPageFactoryList &operator=(const CollectionPropertiesPageFactoryList &) = delete;
85  ~CollectionPropertiesPageFactoryList()
86  {
87  qDeleteAll(*this);
88  }
89 };
90 
91 Q_GLOBAL_STATIC(CollectionPropertiesPageFactoryList, s_pages) // NOLINT(readability-redundant-member-init)
92 
93 static bool s_defaultPage = true;
94 
95 CollectionPropertiesDialogPrivate::CollectionPropertiesDialogPrivate(CollectionPropertiesDialog *qq,
96  const Akonadi::Collection &collection,
97  const QStringList &pageNames)
98  : q(qq)
99  , mCollection(collection)
100  , mPageNames(pageNames)
101 {
102  if (s_defaultPage) {
103  registerBuiltinPages();
104  }
105 }
106 
107 void CollectionPropertiesDialogPrivate::registerBuiltinPages()
108 {
109  static bool registered = false;
110 
111  if (registered) {
112  return;
113  }
114 
115  s_pages->append(new CollectionGeneralPropertiesPageFactory());
116  s_pages->append(new CachePolicyPageFactory());
117 
118  registered = true;
119 }
120 
121 void CollectionPropertiesDialogPrivate::init()
122 {
123  auto mainLayout = new QVBoxLayout(q);
124  q->setAttribute(Qt::WA_DeleteOnClose);
125  mTabWidget = new QTabWidget(q);
126  mainLayout->addWidget(mTabWidget);
127 
129  QPushButton *okButton = buttonBox->button(QDialogButtonBox::Ok);
130  okButton->setDefault(true);
131  okButton->setShortcut(Qt::CTRL | Qt::Key_Return); // NOLINT(bugprone-suspicious-enum-usage)
132  q->connect(buttonBox, &QDialogButtonBox::accepted, q, &QDialog::accept);
133  q->connect(buttonBox, &QDialogButtonBox::rejected, q, &QDialog::reject);
134  mainLayout->addWidget(buttonBox);
135 
136  if (mPageNames.isEmpty()) { // default loading
137  for (CollectionPropertiesPageFactory *factory : std::as_const(*s_pages)) {
138  CollectionPropertiesPage *page = factory->createWidget(mTabWidget);
139  if (page->canHandle(mCollection)) {
140  mTabWidget->addTab(page, page->pageTitle());
141  page->load(mCollection);
142  } else {
143  delete page;
144  }
145  }
146  } else { // custom loading
148 
149  for (CollectionPropertiesPageFactory *factory : std::as_const(*s_pages)) {
150  CollectionPropertiesPage *page = factory->createWidget(mTabWidget);
151  const QString pageName = page->objectName();
152 
153  if (page->canHandle(mCollection) && mPageNames.contains(pageName) && !pages.contains(pageName)) {
154  pages.insert(page->objectName(), page);
155  } else {
156  delete page;
157  }
158  }
159 
160  for (const QString &pageName : std::as_const(mPageNames)) {
161  CollectionPropertiesPage *page = pages.value(pageName);
162  if (page) {
163  mTabWidget->addTab(page, page->pageTitle());
164  page->load(mCollection);
165  }
166  }
167  }
168 
169  q->connect(buttonBox->button(QDialogButtonBox::Ok), &QPushButton::clicked, q, [this]() {
170  save();
171  });
172  q->connect(buttonBox->button(QDialogButtonBox::Cancel), &QAbstractButton::clicked, q, &QObject::deleteLater);
173 
174  KConfigGroup group(KSharedConfig::openStateConfig(), "CollectionPropertiesDialog");
175  const QSize size = group.readEntry("Size", QSize());
176  if (size.isValid()) {
177  q->resize(size);
178  } else {
179  q->resize(q->sizeHint().width(), q->sizeHint().height());
180  }
181 }
182 
184  : QDialog(parent)
185  , d(new CollectionPropertiesDialogPrivate(this, collection, QStringList()))
186 {
187  d->init();
188 }
189 
191  : QDialog(parent)
192  , d(new CollectionPropertiesDialogPrivate(this, collection, pages))
193 {
194  d->init();
195 }
196 
198 {
199  KConfigGroup group(KSharedConfig::openStateConfig(), "CollectionPropertiesDialog");
200  group.writeEntry("Size", size());
201 }
202 
204 {
205  if (s_pages->isEmpty() && s_defaultPage) {
206  CollectionPropertiesDialogPrivate::registerBuiltinPages();
207  }
208  s_pages->append(factory);
209 }
210 
212 {
213  s_defaultPage = defaultPage;
214 }
215 
217 {
218  switch (page) {
219  case GeneralPage:
220  return QStringLiteral("Akonadi::CollectionGeneralPropertiesPage");
221  case CachePage:
222  return QStringLiteral("Akonadi::CachePolicyPage");
223  }
224 
225  return QString();
226 }
227 
229 {
230  d->setCurrentPage(name);
231 }
232 
233 #include "moc_collectionpropertiesdialog.cpp"
void writeEntry(const char *key, const char *value, WriteConfigFlags pFlags=Normal)
const T value(const Key &key) const const
static void registerPage(CollectionPropertiesPageFactory *factory)
Register custom pages for the collection properties dialog.
virtual void save(Collection &collection)=0
Saves page content to the given collection.
bool isValid() const const
Job that modifies a collection in the Akonadi storage.
virtual void reject()
void setShortcut(const QKeySequence &key)
void result(KJob *job)
A generic and extensible dialog for collection properties.
QCA_EXPORT void init()
static QString defaultPageObjectName(DefaultPage page)
Returns the object name of one of the dialog's registered default pages.
void clicked(bool checked)
virtual void load(const Collection &collection)=0
Loads the page content from the given collection.
Represents a collection of PIM items.
Definition: collection.h:61
QString pageTitle() const
Returns the page title.
Definition: item.h:32
QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
QHash::iterator insert(const Key &key, const T &value)
Q_GLOBAL_STATIC(Internal::StaticControl, s_instance) class ControlPrivate
Definition: control.cpp:28
void deleteLater()
~CollectionPropertiesDialog() override
Destroys the collection properties dialog.
static KSharedConfig::Ptr openStateConfig(const QString &fileName=QString())
DefaultPage
Enumerates the registered default pages which can be displayed.
virtual void accept()
CollectionPropertiesDialog(const Collection &collection, QWidget *parent=nullptr)
Creates a new collection properties dialog.
Key_Return
static void useDefaultPage(bool use)
Sets whether to use default page or not.
void setCurrentPage(const QString &name)
Sets the page to be shown in the tab widget.
const QList< QKeySequence > & save()
void setDefault(bool)
virtual QString errorString() const
int error() const
bool contains(const Key &key) const const
A single page in a collection properties dialog.
A factory class for collection properties dialog pages.
WA_DeleteOnClose
Helper integration between Akonadi and Qt.
virtual bool canHandle(const Collection &collection) const
Checks if this page can actually handle the given collection.
This file is part of the KDE documentation.
Documentation copyright © 1996-2022 The KDE developers.
Generated on Sat Jun 25 2022 06:00:31 by doxygen 1.8.17 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.