1 /*
2 SPDX-FileCopyrightText: 2008 Harald Hvaal <haraldhv@stud.ntnu.no>
3 SPDX-FileCopyrightText: 2009, 2011 Raphael Kubo da Costa <rakuco@FreeBSD.org>
4 SPDX-FileCopyrightText: 2015 Elvis Angelaccio <elvis.angelaccio@kde.org>
5 SPDX-FileCopyrightText: 2016 Ragnar Thomsen <rthomsen6@gmail.com>
6
7 SPDX-License-Identifier: BSD-2-Clause
8 */
9
10 #include "createdialog.h"
11 #include "archiveformat.h"
12 #include "ark_debug.h"
13 #include "ui_createdialog.h"
14 #include "mimetypes.h"
15
16 #include <KMessageBox>
17 #include <KSharedConfig>
18
19 #include <QMimeDatabase>
20 #include <QUrl>
21
22 namespace Kerfuffle
23 {
24 class CreateDialogUI: public QWidget, public Ui::CreateDialog
25 {
26 Q_OBJECT
27
28 public:
CreateDialogUI(QWidget * parent=nullptr)29 CreateDialogUI(QWidget *parent = nullptr)
30 : QWidget(parent) {
31 setupUi(this);
32 }
33 };
34
CreateDialog(QWidget * parent,const QString & caption,const QUrl & startDir)35 CreateDialog::CreateDialog(QWidget *parent,
36 const QString &caption,
37 const QUrl &startDir)
38 : QDialog(parent, Qt::Dialog)
39 {
40 setWindowTitle(caption);
41 setModal(true);
42
43 m_supportedMimeTypes = m_pluginManger.supportedWriteMimeTypes(PluginManager::SortByComment);
44
45 m_vlayout = new QVBoxLayout();
46 setLayout(m_vlayout);
47
48 m_ui = new CreateDialogUI(this);
49 m_ui->buttonBox->button(QDialogButtonBox::Ok)->setEnabled(false);
50
51 m_ui->destFolderUrlRequester->setMode(KFile::Directory);
52 if (startDir.isEmpty()) {
53 m_ui->destFolderUrlRequester->setUrl(QUrl::fromLocalFile(QDir::currentPath() + QLatin1Char('/')));
54 } else {
55 m_ui->destFolderUrlRequester->setUrl(startDir);
56 }
57
58 // Populate combobox with mimetypes.
59 for (const QString &type : std::as_const(m_supportedMimeTypes)) {
60 m_ui->mimeComboBox->addItem(QMimeDatabase().mimeTypeForName(type).comment());
61 }
62
63 connect(m_ui->filenameLineEdit, &QLineEdit::textChanged, this, &CreateDialog::slotFileNameEdited);
64 connect(m_ui->buttonBox, &QDialogButtonBox::accepted, this, &QDialog::accept);
65 connect(m_ui->buttonBox, &QDialogButtonBox::rejected, this, &QDialog::reject);
66 connect(this, &QDialog::accepted, this, &CreateDialog::slotUpdateDefaultMimeType);
67 connect(m_ui->mimeComboBox, QOverload<int>::of(&QComboBox::currentIndexChanged), this, &CreateDialog::slotUpdateWidgets);
68 connect(m_ui->mimeComboBox, QOverload<int>::of(&QComboBox::currentIndexChanged), this, &CreateDialog::slotUpdateFilenameExtension);
69
70 m_vlayout->addWidget(m_ui);
71
72 m_ui->optionsWidget->setMimeType(currentMimeType());
73
74 loadConfiguration();
75
76 layout()->setSizeConstraint(QLayout::SetFixedSize);
77 m_ui->filenameLineEdit->setFocus();
78 slotUpdateFilenameExtension(m_ui->mimeComboBox->currentIndex());
79 }
80
setFileName(const QString & fileName)81 void CreateDialog::setFileName(const QString &fileName)
82 {
83 m_ui->filenameLineEdit->setText(fileName);
84
85 const QString detectedSuffix = QMimeDatabase().suffixForFileName(fileName);
86 if (currentMimeType().suffixes().contains(detectedSuffix)) {
87 m_ui->filenameLineEdit->setSelection(0, fileName.length() - detectedSuffix.length() - 1);
88 } else {
89 m_ui->filenameLineEdit->selectAll();
90 }
91 }
92
slotFileNameEdited(const QString & fileName)93 void CreateDialog::slotFileNameEdited(const QString &fileName)
94 {
95 const QMimeType mimeFromFileName = QMimeDatabase().mimeTypeForFile(fileName, QMimeDatabase::MatchExtension);
96
97 if (m_supportedMimeTypes.contains(mimeFromFileName.name())) {
98 setMimeType(mimeFromFileName.name());
99 }
100
101 m_ui->buttonBox->button(QDialogButtonBox::Ok)->setEnabled(!fileName.isEmpty());
102 }
103
slotUpdateWidgets(int index)104 void CreateDialog::slotUpdateWidgets(int index)
105 {
106 m_ui->optionsWidget->setMimeType(QMimeDatabase().mimeTypeForName(m_supportedMimeTypes.at(index)));
107 }
108
slotUpdateFilenameExtension(int index)109 void CreateDialog::slotUpdateFilenameExtension(int index)
110 {
111 m_ui->chkAddExtension->setText(i18nc("the argument is a file extension (the period is not a typo)", "Automatically add .%1",
112 QMimeDatabase().mimeTypeForName(m_supportedMimeTypes.at(index)).preferredSuffix()));
113 }
114
selectedUrl() const115 QUrl CreateDialog::selectedUrl() const
116 {
117 QString fileName = m_ui->filenameLineEdit->text();
118 QString dir = m_ui->destFolderUrlRequester->url().toLocalFile();
119 if (dir.trimmed().endsWith(QLatin1Char('/'))) {
120 dir = dir.trimmed();
121 }
122
123 if (m_ui->chkAddExtension->isChecked()) {
124 QString detectedSuffix = QMimeDatabase().suffixForFileName(m_ui->filenameLineEdit->text().trimmed());
125
126 if (!currentMimeType().suffixes().contains(detectedSuffix)) {
127 if (!fileName.endsWith(QLatin1Char('.'))) {
128 fileName.append(QLatin1Char('.'));
129 }
130 fileName.append(currentMimeType().preferredSuffix());
131 }
132 }
133
134 if (!dir.endsWith(QLatin1Char('/'))) {
135 dir.append(QLatin1Char('/'));
136 }
137 return QUrl::fromLocalFile(dir + fileName);
138 }
139
compressionLevel() const140 int CreateDialog::compressionLevel() const
141 {
142 return m_ui->optionsWidget->compressionLevel();
143 }
144
compressionMethod() const145 QString CreateDialog::compressionMethod() const
146 {
147 return m_ui->optionsWidget->compressionMethod();
148 }
149
encryptionMethod() const150 QString CreateDialog::encryptionMethod() const
151 {
152 return m_ui->optionsWidget->encryptionMethod();
153 }
154
volumeSize() const155 ulong CreateDialog::volumeSize() const
156 {
157 return m_ui->optionsWidget->volumeSize();
158 }
159
password() const160 QString CreateDialog::password() const
161 {
162 return m_ui->optionsWidget->password();
163 }
164
isEncryptionAvailable() const165 bool CreateDialog::isEncryptionAvailable() const
166 {
167 return m_ui->optionsWidget->isEncryptionAvailable();
168 }
169
isEncryptionEnabled() const170 bool CreateDialog::isEncryptionEnabled() const
171 {
172 return m_ui->optionsWidget->isEncryptionEnabled();
173 }
174
isHeaderEncryptionAvailable() const175 bool CreateDialog::isHeaderEncryptionAvailable() const
176 {
177 return m_ui->optionsWidget->isHeaderEncryptionAvailable();
178 }
179
isHeaderEncryptionEnabled() const180 bool CreateDialog::isHeaderEncryptionEnabled() const
181 {
182 return m_ui->optionsWidget->isHeaderEncryptionEnabled();
183 }
184
accept()185 void CreateDialog::accept()
186 {
187 if (!isEncryptionEnabled()) {
188 QDialog::accept();
189 return;
190 }
191
192 switch (m_ui->optionsWidget->passwordStatus()) {
193 case KNewPasswordWidget::WeakPassword:
194 case KNewPasswordWidget::StrongPassword:
195 QDialog::accept();
196 break;
197 case KNewPasswordWidget::PasswordNotVerified:
198 KMessageBox::error(nullptr, i18n("The chosen password does not match the given verification password."));
199 break;
200 default:
201 break;
202 }
203 }
204
slotUpdateDefaultMimeType()205 void CreateDialog::slotUpdateDefaultMimeType()
206 {
207 m_config.writeEntry("LastMimeType", currentMimeType().name());
208 }
209
loadConfiguration()210 void CreateDialog::loadConfiguration()
211 {
212 m_config = KConfigGroup(KSharedConfig::openConfig()->group("CreateDialog"));
213 QMimeType lastUsedMime = QMimeDatabase().mimeTypeForName(m_config.readEntry("LastMimeType", QStringLiteral("application/x-compressed-tar")));
214 setMimeType(lastUsedMime.name());
215 }
216
currentMimeType() const217 QMimeType CreateDialog::currentMimeType() const
218 {
219 Q_ASSERT(m_supportedMimeTypes.size() > m_ui->mimeComboBox->currentIndex());
220 return QMimeDatabase().mimeTypeForName(m_supportedMimeTypes.at(m_ui->mimeComboBox->currentIndex()));
221 }
222
setMimeType(const QString & mimeTypeName)223 bool CreateDialog::setMimeType(const QString &mimeTypeName)
224 {
225 int index = m_supportedMimeTypes.indexOf(mimeTypeName);
226 if (index == -1) {
227 return false;
228 }
229 m_ui->mimeComboBox->setCurrentIndex(index);
230
231 // This is needed to make sure widgets get updated in case the mimetype is already selected.
232 slotUpdateWidgets(index);
233
234 return true;
235 }
236
237 }
238
239 #include "createdialog.moc"
240