mirror of
https://github.com/keepassxreboot/keepassxc.git
synced 2024-12-28 00:39:43 -05:00
parent
8117809901
commit
e166722026
BIN
share/icons/application/16x16/actions/document-encrypt.png
Normal file
BIN
share/icons/application/16x16/actions/document-encrypt.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 452 B |
@ -82,6 +82,7 @@ set(keepassx_SOURCES
|
||||
gui/MainWindow.cpp
|
||||
gui/SettingsWidget.cpp
|
||||
gui/SortFilterHideProxyModel.cpp
|
||||
gui/UnlockDatabaseWidget.cpp
|
||||
gui/WelcomeWidget.cpp
|
||||
gui/entry/AutoTypeAssociationsModel.cpp
|
||||
gui/entry/EditEntryWidget.cpp
|
||||
@ -137,6 +138,7 @@ set(keepassx_MOC
|
||||
gui/MainWindow.h
|
||||
gui/SettingsWidget.h
|
||||
gui/SortFilterHideProxyModel.h
|
||||
gui/UnlockDatabaseWidget.h
|
||||
gui/WelcomeWidget.h
|
||||
gui/entry/AutoTypeAssociationsModel.h
|
||||
gui/entry/EditEntryWidget.h
|
||||
|
@ -94,31 +94,11 @@ void DatabaseOpenWidget::enterKey(const QString& pw, const QString& keyFile)
|
||||
void DatabaseOpenWidget::openDatabase()
|
||||
{
|
||||
KeePass2Reader reader;
|
||||
CompositeKey masterKey;
|
||||
|
||||
if (m_ui->checkPassword->isChecked()) {
|
||||
masterKey.addKey(PasswordKey(m_ui->editPassword->text()));
|
||||
CompositeKey masterKey = databaseKey();
|
||||
if (masterKey.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
QHash<QString, QVariant> lastKeyFiles = config()->get("LastKeyFiles").toHash();
|
||||
|
||||
if (m_ui->checkKeyFile->isChecked()) {
|
||||
FileKey key;
|
||||
QString keyFilename = m_ui->comboKeyFile->currentText();
|
||||
QString errorMsg;
|
||||
if (!key.load(keyFilename, &errorMsg)) {
|
||||
QMessageBox::warning(this, tr("Error"), tr("Can't open key file:\n%1").arg(errorMsg));
|
||||
return;
|
||||
}
|
||||
masterKey.addKey(key);
|
||||
lastKeyFiles[m_filename] = keyFilename;
|
||||
}
|
||||
else {
|
||||
lastKeyFiles.remove(m_filename);
|
||||
}
|
||||
|
||||
config()->set("LastKeyFiles", lastKeyFiles);
|
||||
|
||||
QFile file(m_filename);
|
||||
if (!file.open(QIODevice::ReadOnly)) {
|
||||
// TODO: error message
|
||||
@ -141,6 +121,36 @@ void DatabaseOpenWidget::openDatabase()
|
||||
}
|
||||
}
|
||||
|
||||
CompositeKey DatabaseOpenWidget::databaseKey()
|
||||
{
|
||||
CompositeKey masterKey;
|
||||
|
||||
if (m_ui->checkPassword->isChecked()) {
|
||||
masterKey.addKey(PasswordKey(m_ui->editPassword->text()));
|
||||
}
|
||||
|
||||
QHash<QString, QVariant> lastKeyFiles = config()->get("LastKeyFiles").toHash();
|
||||
|
||||
if (m_ui->checkKeyFile->isChecked()) {
|
||||
FileKey key;
|
||||
QString keyFilename = m_ui->comboKeyFile->currentText();
|
||||
QString errorMsg;
|
||||
if (!key.load(keyFilename, &errorMsg)) {
|
||||
QMessageBox::warning(this, tr("Error"), tr("Can't open key file:\n%1").arg(errorMsg));
|
||||
return CompositeKey();
|
||||
}
|
||||
masterKey.addKey(key);
|
||||
lastKeyFiles[m_filename] = keyFilename;
|
||||
}
|
||||
else {
|
||||
lastKeyFiles.remove(m_filename);
|
||||
}
|
||||
|
||||
config()->set("LastKeyFiles", lastKeyFiles);
|
||||
|
||||
return masterKey;
|
||||
}
|
||||
|
||||
void DatabaseOpenWidget::reject()
|
||||
{
|
||||
Q_EMIT editFinished(false);
|
||||
|
@ -21,6 +21,7 @@
|
||||
#include <QtCore/QScopedPointer>
|
||||
|
||||
#include "gui/DialogyWidget.h"
|
||||
#include "keys/CompositeKey.h"
|
||||
|
||||
class Database;
|
||||
class QFile;
|
||||
@ -43,6 +44,9 @@ public:
|
||||
Q_SIGNALS:
|
||||
void editFinished(bool accepted);
|
||||
|
||||
protected:
|
||||
CompositeKey databaseKey();
|
||||
|
||||
protected Q_SLOTS:
|
||||
virtual void openDatabase();
|
||||
void reject();
|
||||
|
@ -297,6 +297,7 @@ void DatabaseTabWidget::saveDatabaseAs(Database* db)
|
||||
dbStruct.filePath = fileInfo.absoluteFilePath();
|
||||
dbStruct.canonicalFilePath = fileInfo.canonicalFilePath();
|
||||
dbStruct.fileName = fileInfo.fileName();
|
||||
dbStruct.dbWidget->updateFilename(dbStruct.filePath);
|
||||
updateTabName(db);
|
||||
updateLastDatabases(dbStruct.filePath);
|
||||
}
|
||||
@ -391,20 +392,35 @@ void DatabaseTabWidget::updateTabName(Database* db)
|
||||
tabName = QString("%1 [%2]").arg(db->metadata()->name(), tr("New database"));
|
||||
}
|
||||
}
|
||||
|
||||
if (dbStruct.dbWidget->currentMode() == DatabaseWidget::LockedMode) {
|
||||
tabName.append(QString(" [%1]").arg(tr("locked")));
|
||||
}
|
||||
|
||||
if (dbStruct.modified) {
|
||||
tabName.append("*");
|
||||
}
|
||||
|
||||
setTabText(index, tabName);
|
||||
Q_EMIT tabNameChanged();
|
||||
}
|
||||
|
||||
void DatabaseTabWidget::updateTabNameFromSender()
|
||||
void DatabaseTabWidget::updateTabNameFromDbSender()
|
||||
{
|
||||
Q_ASSERT(qobject_cast<Database*>(sender()));
|
||||
|
||||
updateTabName(static_cast<Database*>(sender()));
|
||||
}
|
||||
|
||||
void DatabaseTabWidget::updateTabNameFromDbWidgetSender()
|
||||
{
|
||||
Q_ASSERT(qobject_cast<DatabaseWidget*>(sender()));
|
||||
Q_ASSERT(databaseFromDatabaseWidget(qobject_cast<DatabaseWidget*>(sender())));
|
||||
|
||||
DatabaseWidget* dbWidget = static_cast<DatabaseWidget*>(sender());
|
||||
updateTabName(databaseFromDatabaseWidget(dbWidget));
|
||||
}
|
||||
|
||||
int DatabaseTabWidget::databaseIndex(Database* db)
|
||||
{
|
||||
QWidget* dbWidget = m_dbList.value(db).dbWidget;
|
||||
@ -466,6 +482,7 @@ void DatabaseTabWidget::insertDatabase(Database* db, const DatabaseManagerStruct
|
||||
connectDatabase(db);
|
||||
connect(dbStruct.dbWidget, SIGNAL(closeRequest()), SLOT(closeDatabaseFromSender()));
|
||||
connect(dbStruct.dbWidget, SIGNAL(databaseChanged(Database*)), SLOT(changeDatabase(Database*)));
|
||||
connect(dbStruct.dbWidget, SIGNAL(unlockedDatabase()), SLOT(updateTabNameFromDbWidgetSender()));
|
||||
}
|
||||
|
||||
DatabaseWidget* DatabaseTabWidget::currentDatabaseWidget()
|
||||
@ -479,6 +496,37 @@ DatabaseWidget* DatabaseTabWidget::currentDatabaseWidget()
|
||||
}
|
||||
}
|
||||
|
||||
bool DatabaseTabWidget::hasLockableDatabases()
|
||||
{
|
||||
QHashIterator<Database*, DatabaseManagerStruct> i(m_dbList);
|
||||
while (i.hasNext()) {
|
||||
i.next();
|
||||
DatabaseWidget::Mode mode = i.value().dbWidget->currentMode();
|
||||
|
||||
if ((mode == DatabaseWidget::ViewMode || mode == DatabaseWidget::EditMode)
|
||||
&& i.value().dbWidget->dbHasKey()) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void DatabaseTabWidget::lockDatabases()
|
||||
{
|
||||
QHashIterator<Database*, DatabaseManagerStruct> i(m_dbList);
|
||||
while (i.hasNext()) {
|
||||
i.next();
|
||||
DatabaseWidget::Mode mode = i.value().dbWidget->currentMode();
|
||||
|
||||
if ((mode == DatabaseWidget::ViewMode || mode == DatabaseWidget::EditMode)
|
||||
&& i.value().dbWidget->dbHasKey()) {
|
||||
i.value().dbWidget->lock();
|
||||
updateTabName(i.key());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void DatabaseTabWidget::modified()
|
||||
{
|
||||
Q_ASSERT(qobject_cast<Database*>(sender()));
|
||||
@ -535,7 +583,7 @@ void DatabaseTabWidget::connectDatabase(Database* newDb, Database* oldDb)
|
||||
oldDb->disconnect(this);
|
||||
}
|
||||
|
||||
connect(newDb, SIGNAL(nameTextChanged()), SLOT(updateTabNameFromSender()));
|
||||
connect(newDb, SIGNAL(nameTextChanged()), SLOT(updateTabNameFromDbSender()));
|
||||
connect(newDb, SIGNAL(modified()), SLOT(modified()));
|
||||
newDb->setEmitModified(true);
|
||||
}
|
||||
|
@ -53,6 +53,7 @@ public:
|
||||
void openDatabase(const QString& fileName, const QString& pw = QString(),
|
||||
const QString& keyFile = QString());
|
||||
DatabaseWidget* currentDatabaseWidget();
|
||||
bool hasLockableDatabases();
|
||||
|
||||
static const int LastDatabasesCount;
|
||||
|
||||
@ -69,13 +70,15 @@ public Q_SLOTS:
|
||||
void changeDatabaseSettings();
|
||||
bool readOnly(int index = -1);
|
||||
void performGlobalAutoType();
|
||||
void lockDatabases();
|
||||
|
||||
Q_SIGNALS:
|
||||
void tabNameChanged();
|
||||
|
||||
private Q_SLOTS:
|
||||
void updateTabName(Database* db);
|
||||
void updateTabNameFromSender();
|
||||
void updateTabNameFromDbSender();
|
||||
void updateTabNameFromDbWidgetSender();
|
||||
void modified();
|
||||
void toggleTabbar();
|
||||
void changeDatabase(Database* newDb);
|
||||
|
@ -36,6 +36,7 @@
|
||||
#include "gui/DatabaseOpenWidget.h"
|
||||
#include "gui/DatabaseSettingsWidget.h"
|
||||
#include "gui/KeePass1OpenWidget.h"
|
||||
#include "gui/UnlockDatabaseWidget.h"
|
||||
#include "gui/entry/EditEntryWidget.h"
|
||||
#include "gui/entry/EntryView.h"
|
||||
#include "gui/group/EditGroupWidget.h"
|
||||
@ -121,6 +122,8 @@ DatabaseWidget::DatabaseWidget(Database* db, QWidget* parent)
|
||||
m_databaseOpenWidget->setObjectName("databaseOpenWidget");
|
||||
m_keepass1OpenWidget = new KeePass1OpenWidget();
|
||||
m_keepass1OpenWidget->setObjectName("keepass1OpenWidget");
|
||||
m_unlockDatabaseWidget = new UnlockDatabaseWidget();
|
||||
m_unlockDatabaseWidget->setObjectName("unlockDatabaseWidget");
|
||||
addWidget(m_mainWidget);
|
||||
addWidget(m_editEntryWidget);
|
||||
addWidget(m_editGroupWidget);
|
||||
@ -129,6 +132,7 @@ DatabaseWidget::DatabaseWidget(Database* db, QWidget* parent)
|
||||
addWidget(m_historyEditEntryWidget);
|
||||
addWidget(m_databaseOpenWidget);
|
||||
addWidget(m_keepass1OpenWidget);
|
||||
addWidget(m_unlockDatabaseWidget);
|
||||
|
||||
connect(m_groupView, SIGNAL(groupChanged(Group*)), this, SLOT(clearLastGroup(Group*)));
|
||||
connect(m_groupView, SIGNAL(groupChanged(Group*)), SIGNAL(groupChanged()));
|
||||
@ -143,6 +147,7 @@ DatabaseWidget::DatabaseWidget(Database* db, QWidget* parent)
|
||||
connect(m_databaseSettingsWidget, SIGNAL(editFinished(bool)), SLOT(switchToView(bool)));
|
||||
connect(m_databaseOpenWidget, SIGNAL(editFinished(bool)), SLOT(openDatabase(bool)));
|
||||
connect(m_keepass1OpenWidget, SIGNAL(editFinished(bool)), SLOT(openDatabase(bool)));
|
||||
connect(m_unlockDatabaseWidget, SIGNAL(editFinished(bool)), SLOT(unlockDatabase(bool)));
|
||||
connect(this, SIGNAL(currentChanged(int)), this, SLOT(emitCurrentModeChanged()));
|
||||
connect(m_searchUi->searchEdit, SIGNAL(textChanged(QString)), this, SLOT(startSearchTimer()));
|
||||
connect(m_searchUi->caseSensitiveCheckBox, SIGNAL(toggled(bool)), this, SLOT(startSearch()));
|
||||
@ -151,7 +156,7 @@ DatabaseWidget::DatabaseWidget(Database* db, QWidget* parent)
|
||||
connect(m_searchTimer, SIGNAL(timeout()), this, SLOT(search()));
|
||||
connect(closeAction, SIGNAL(triggered()), this, SLOT(closeSearch()));
|
||||
|
||||
setCurrentIndex(0);
|
||||
setCurrentWidget(m_mainWidget);
|
||||
}
|
||||
|
||||
DatabaseWidget::~DatabaseWidget()
|
||||
@ -160,22 +165,17 @@ DatabaseWidget::~DatabaseWidget()
|
||||
|
||||
DatabaseWidget::Mode DatabaseWidget::currentMode()
|
||||
{
|
||||
switch (currentIndex()) {
|
||||
case -1:
|
||||
if (currentWidget() == Q_NULLPTR) {
|
||||
return DatabaseWidget::None;
|
||||
case 0:
|
||||
}
|
||||
else if (currentWidget() == m_mainWidget) {
|
||||
return DatabaseWidget::ViewMode;
|
||||
case 1: // entry edit
|
||||
case 2: // group edit
|
||||
case 3: // change master key
|
||||
case 4: // database settings
|
||||
case 5: // entry history
|
||||
case 6: // open database
|
||||
case 7: // keepass 1 import
|
||||
}
|
||||
else if (currentWidget() == m_unlockDatabaseWidget) {
|
||||
return DatabaseWidget::LockedMode;
|
||||
}
|
||||
else {
|
||||
return DatabaseWidget::EditMode;
|
||||
default:
|
||||
Q_ASSERT(false);
|
||||
return DatabaseWidget::None;
|
||||
}
|
||||
}
|
||||
|
||||
@ -347,12 +347,20 @@ int DatabaseWidget::addWidget(QWidget* w)
|
||||
}
|
||||
|
||||
void DatabaseWidget::setCurrentIndex(int index)
|
||||
{
|
||||
// use setCurrentWidget() instead
|
||||
// index is not reliable
|
||||
Q_UNUSED(index);
|
||||
Q_ASSERT(false);
|
||||
}
|
||||
|
||||
void DatabaseWidget::setCurrentWidget(QWidget* widget)
|
||||
{
|
||||
if (currentWidget()) {
|
||||
currentWidget()->setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Ignored);
|
||||
}
|
||||
|
||||
QStackedWidget::setCurrentIndex(index);
|
||||
QStackedWidget::setCurrentWidget(widget);
|
||||
|
||||
if (currentWidget()) {
|
||||
currentWidget()->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred);
|
||||
@ -390,18 +398,18 @@ void DatabaseWidget::switchToView(bool accepted)
|
||||
m_newParent = Q_NULLPTR;
|
||||
}
|
||||
|
||||
setCurrentIndex(0);
|
||||
setCurrentWidget(m_mainWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToHistoryView(Entry* entry)
|
||||
{
|
||||
m_historyEditEntryWidget->loadEntry(entry, false, true, "", m_db);
|
||||
setCurrentIndex(5);
|
||||
setCurrentWidget(m_historyEditEntryWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchBackToEntryEdit()
|
||||
{
|
||||
setCurrentIndex(1);
|
||||
setCurrentWidget(m_editEntryWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToEntryEdit(Entry* entry)
|
||||
@ -419,13 +427,13 @@ void DatabaseWidget::switchToEntryEdit(Entry* entry, bool create)
|
||||
Q_ASSERT(group);
|
||||
|
||||
m_editEntryWidget->loadEntry(entry, create, false, group->name(), m_db);
|
||||
setCurrentIndex(1);
|
||||
setCurrentWidget(m_editEntryWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToGroupEdit(Group* group, bool create)
|
||||
{
|
||||
m_editGroupWidget->loadGroup(group, create, m_db);
|
||||
setCurrentIndex(2);
|
||||
setCurrentWidget(m_editGroupWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::updateMasterKey(bool accepted)
|
||||
@ -440,7 +448,7 @@ void DatabaseWidget::updateMasterKey(bool accepted)
|
||||
return;
|
||||
}
|
||||
|
||||
setCurrentIndex(0);
|
||||
setCurrentWidget(m_mainWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::openDatabase(bool accepted)
|
||||
@ -451,7 +459,7 @@ void DatabaseWidget::openDatabase(bool accepted)
|
||||
m_groupView->changeDatabase(m_db);
|
||||
Q_EMIT databaseChanged(m_db);
|
||||
delete oldDb;
|
||||
setCurrentIndex(0);
|
||||
setCurrentWidget(m_mainWidget);
|
||||
|
||||
// We won't need those anymore and KeePass1OpenWidget closes
|
||||
// the file in its dtor.
|
||||
@ -468,6 +476,15 @@ void DatabaseWidget::openDatabase(bool accepted)
|
||||
}
|
||||
}
|
||||
|
||||
void DatabaseWidget::unlockDatabase(bool accepted)
|
||||
{
|
||||
// cancel button is disabled
|
||||
Q_ASSERT(accepted);
|
||||
|
||||
setCurrentWidget(widgetBeforeLock);
|
||||
Q_EMIT unlockedDatabase();
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToEntryEdit()
|
||||
{
|
||||
switchToEntryEdit(m_entryView->currentEntry(), false);
|
||||
@ -481,32 +498,35 @@ void DatabaseWidget::switchToGroupEdit()
|
||||
void DatabaseWidget::switchToMasterKeyChange()
|
||||
{
|
||||
m_changeMasterKeyWidget->clearForms();
|
||||
setCurrentIndex(3);
|
||||
setCurrentWidget(m_changeMasterKeyWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToDatabaseSettings()
|
||||
{
|
||||
m_databaseSettingsWidget->load(m_db);
|
||||
setCurrentIndex(4);
|
||||
setCurrentWidget(m_databaseSettingsWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToOpenDatabase(const QString& fileName)
|
||||
{
|
||||
updateFilename(fileName);
|
||||
m_databaseOpenWidget->load(fileName);
|
||||
setCurrentIndex(6);
|
||||
setCurrentWidget(m_databaseOpenWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToOpenDatabase(const QString& fileName, const QString& password,
|
||||
const QString& keyFile)
|
||||
{
|
||||
updateFilename(fileName);
|
||||
switchToOpenDatabase(fileName);
|
||||
m_databaseOpenWidget->enterKey(password, keyFile);
|
||||
}
|
||||
|
||||
void DatabaseWidget::switchToImportKeepass1(const QString& fileName)
|
||||
{
|
||||
updateFilename(fileName);
|
||||
m_keepass1OpenWidget->load(fileName);
|
||||
setCurrentIndex(7);
|
||||
setCurrentWidget(m_keepass1OpenWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::toggleSearch()
|
||||
@ -641,3 +661,17 @@ void DatabaseWidget::clearLastGroup(Group* group)
|
||||
m_searchWidget->hide();
|
||||
}
|
||||
}
|
||||
|
||||
void DatabaseWidget::lock()
|
||||
{
|
||||
Q_ASSERT(currentMode() != DatabaseWidget::LockedMode);
|
||||
|
||||
widgetBeforeLock = currentWidget();
|
||||
m_unlockDatabaseWidget->load(m_filename, m_db);
|
||||
setCurrentWidget(m_unlockDatabaseWidget);
|
||||
}
|
||||
|
||||
void DatabaseWidget::updateFilename(const QString& fileName)
|
||||
{
|
||||
m_filename = fileName;
|
||||
}
|
||||
|
@ -36,6 +36,7 @@ class GroupView;
|
||||
class KeePass1OpenWidget;
|
||||
class QFile;
|
||||
class QMenu;
|
||||
class UnlockDatabaseWidget;
|
||||
|
||||
namespace Ui {
|
||||
class SearchWidget;
|
||||
@ -50,7 +51,8 @@ public:
|
||||
{
|
||||
None,
|
||||
ViewMode,
|
||||
EditMode
|
||||
EditMode,
|
||||
LockedMode
|
||||
};
|
||||
|
||||
explicit DatabaseWidget(Database* db, QWidget* parent = Q_NULLPTR);
|
||||
@ -63,7 +65,10 @@ public:
|
||||
bool isInSearchMode();
|
||||
int addWidget(QWidget* w);
|
||||
void setCurrentIndex(int index);
|
||||
void setCurrentWidget(QWidget* widget);
|
||||
DatabaseWidget::Mode currentMode();
|
||||
void lock();
|
||||
void updateFilename(const QString& filename);
|
||||
|
||||
Q_SIGNALS:
|
||||
void closeRequest();
|
||||
@ -73,6 +78,7 @@ Q_SIGNALS:
|
||||
void databaseChanged(Database* newDb);
|
||||
void groupContextMenuRequested(const QPoint& globalPos);
|
||||
void entryContextMenuRequested(const QPoint& globalPos);
|
||||
void unlockedDatabase();
|
||||
|
||||
public Q_SLOTS:
|
||||
void createEntry();
|
||||
@ -104,6 +110,7 @@ private Q_SLOTS:
|
||||
void switchToGroupEdit(Group* entry, bool create);
|
||||
void updateMasterKey(bool accepted);
|
||||
void openDatabase(bool accepted);
|
||||
void unlockDatabase(bool accepted);
|
||||
void emitCurrentModeChanged();
|
||||
void clearLastGroup(Group* group);
|
||||
void search();
|
||||
@ -124,6 +131,7 @@ private:
|
||||
DatabaseSettingsWidget* m_databaseSettingsWidget;
|
||||
DatabaseOpenWidget* m_databaseOpenWidget;
|
||||
KeePass1OpenWidget* m_keepass1OpenWidget;
|
||||
UnlockDatabaseWidget* m_unlockDatabaseWidget;
|
||||
GroupView* m_groupView;
|
||||
EntryView* m_entryView;
|
||||
Group* m_newGroup;
|
||||
@ -131,6 +139,8 @@ private:
|
||||
Group* m_newParent;
|
||||
Group* m_lastGroup;
|
||||
QTimer* m_searchTimer;
|
||||
QWidget* widgetBeforeLock;
|
||||
QString m_filename;
|
||||
};
|
||||
|
||||
#endif // KEEPASSX_DATABASEWIDGET_H
|
||||
|
@ -29,7 +29,7 @@
|
||||
KeePass1OpenWidget::KeePass1OpenWidget(QWidget* parent)
|
||||
: DatabaseOpenWidget(parent)
|
||||
{
|
||||
setWindowTitle(tr("Import KeePass1 database"));
|
||||
m_ui->labelHeadline->setText(tr("Import KeePass1 database"));
|
||||
}
|
||||
|
||||
void KeePass1OpenWidget::openDatabase()
|
||||
|
@ -63,6 +63,7 @@ MainWindow::MainWindow()
|
||||
setShortcut(m_ui->actionDatabaseSave, QKeySequence::Save, Qt::CTRL + Qt::Key_S);
|
||||
setShortcut(m_ui->actionDatabaseSaveAs, QKeySequence::SaveAs);
|
||||
setShortcut(m_ui->actionDatabaseClose, QKeySequence::Close, Qt::CTRL + Qt::Key_W);
|
||||
m_ui->actionLockDatabases->setShortcut(Qt::CTRL + Qt::Key_L);
|
||||
setShortcut(m_ui->actionQuit, QKeySequence::Quit, Qt::CTRL + Qt::Key_Q);
|
||||
setShortcut(m_ui->actionSearch, QKeySequence::Find, Qt::CTRL + Qt::Key_F);
|
||||
m_ui->actionEntryNew->setShortcut(Qt::CTRL + Qt::Key_N);
|
||||
@ -85,6 +86,7 @@ MainWindow::MainWindow()
|
||||
m_ui->actionDatabaseClose->setIcon(filePath()->icon("actions", "document-close"));
|
||||
m_ui->actionChangeDatabaseSettings->setIcon(filePath()->icon("actions", "document-edit"));
|
||||
m_ui->actionChangeMasterKey->setIcon(filePath()->icon("actions", "database-change-key", false));
|
||||
m_ui->actionLockDatabases->setIcon(filePath()->icon("actions", "document-encrypt", false));
|
||||
m_ui->actionQuit->setIcon(filePath()->icon("actions", "application-exit"));
|
||||
|
||||
m_ui->actionEntryNew->setIcon(filePath()->icon("actions", "entry-new", false));
|
||||
@ -140,6 +142,8 @@ MainWindow::MainWindow()
|
||||
SLOT(changeDatabaseSettings()));
|
||||
connect(m_ui->actionImportKeePass1, SIGNAL(triggered()), m_ui->tabWidget,
|
||||
SLOT(importKeePass1Database()));
|
||||
connect(m_ui->actionLockDatabases, SIGNAL(triggered()), m_ui->tabWidget,
|
||||
SLOT(lockDatabases()));
|
||||
connect(m_ui->actionQuit, SIGNAL(triggered()), SLOT(close()));
|
||||
|
||||
m_actionMultiplexer.connect(m_ui->actionEntryNew, SIGNAL(triggered()),
|
||||
@ -246,6 +250,7 @@ void MainWindow::setMenuActionState(DatabaseWidget::Mode mode)
|
||||
break;
|
||||
}
|
||||
case DatabaseWidget::EditMode:
|
||||
case DatabaseWidget::LockedMode:
|
||||
Q_FOREACH (QAction* action, m_ui->menuEntries->actions()) {
|
||||
action->setEnabled(false);
|
||||
}
|
||||
@ -290,6 +295,8 @@ void MainWindow::setMenuActionState(DatabaseWidget::Mode mode)
|
||||
m_ui->actionDatabaseOpen->setEnabled(inDatabaseTabWidgetOrWelcomeWidget);
|
||||
m_ui->menuRecentDatabases->setEnabled(inDatabaseTabWidgetOrWelcomeWidget);
|
||||
m_ui->actionImportKeePass1->setEnabled(inDatabaseTabWidgetOrWelcomeWidget);
|
||||
|
||||
m_ui->actionLockDatabases->setEnabled(m_ui->tabWidget->hasLockableDatabases());
|
||||
}
|
||||
|
||||
void MainWindow::updateWindowTitle()
|
||||
|
@ -94,6 +94,7 @@
|
||||
<addaction name="separator"/>
|
||||
<addaction name="actionImportKeePass1"/>
|
||||
<addaction name="separator"/>
|
||||
<addaction name="actionLockDatabases"/>
|
||||
<addaction name="actionQuit"/>
|
||||
</widget>
|
||||
<widget class="QMenu" name="menuHelp">
|
||||
@ -328,6 +329,14 @@
|
||||
<string>Open URL</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="actionLockDatabases">
|
||||
<property name="enabled">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Lock databases</string>
|
||||
</property>
|
||||
</action>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
|
64
src/gui/UnlockDatabaseWidget.cpp
Normal file
64
src/gui/UnlockDatabaseWidget.cpp
Normal file
@ -0,0 +1,64 @@
|
||||
/*
|
||||
* Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 2 or (at your option)
|
||||
* version 3 of the License.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "UnlockDatabaseWidget.h"
|
||||
|
||||
#include <QtGui/QMessageBox>
|
||||
|
||||
#include "ui_DatabaseOpenWidget.h"
|
||||
#include "core/Database.h"
|
||||
|
||||
UnlockDatabaseWidget::UnlockDatabaseWidget(QWidget* parent)
|
||||
: DatabaseOpenWidget(parent)
|
||||
{
|
||||
m_ui->labelHeadline->setText(tr("Unlock database"));
|
||||
|
||||
m_ui->buttonBox->removeButton(m_ui->buttonBox->button(QDialogButtonBox::Cancel));
|
||||
connect(this, SIGNAL(editFinished(bool)), SLOT(clearForms()));
|
||||
}
|
||||
|
||||
void UnlockDatabaseWidget::load(const QString& filename, Database* db)
|
||||
{
|
||||
Q_ASSERT(db);
|
||||
|
||||
DatabaseOpenWidget::load(filename);
|
||||
m_db = db;
|
||||
}
|
||||
|
||||
void UnlockDatabaseWidget::openDatabase()
|
||||
{
|
||||
CompositeKey masterKey = databaseKey();
|
||||
if (masterKey.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_db->verifyKey(masterKey)) {
|
||||
Q_EMIT editFinished(true);
|
||||
}
|
||||
else {
|
||||
QMessageBox::warning(this, tr("Error"), tr("Wrong key."));
|
||||
m_ui->editPassword->clear();
|
||||
}
|
||||
}
|
||||
|
||||
void UnlockDatabaseWidget::clearForms()
|
||||
{
|
||||
m_ui->editPassword->clear();
|
||||
m_ui->comboKeyFile->clear();
|
||||
m_ui->checkPassword->setChecked(false);
|
||||
m_ui->checkKeyFile->setChecked(false);
|
||||
}
|
33
src/gui/UnlockDatabaseWidget.h
Normal file
33
src/gui/UnlockDatabaseWidget.h
Normal file
@ -0,0 +1,33 @@
|
||||
/*
|
||||
* Copyright (C) 2012 Felix Geyer <debfx@fobos.de>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 2 or (at your option)
|
||||
* version 3 of the License.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "gui/DatabaseOpenWidget.h"
|
||||
|
||||
class UnlockDatabaseWidget : public DatabaseOpenWidget
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit UnlockDatabaseWidget(QWidget* parent = Q_NULLPTR);
|
||||
void load(const QString& filename, Database* db);
|
||||
|
||||
protected:
|
||||
void openDatabase() Q_DECL_OVERRIDE;
|
||||
|
||||
private Q_SLOTS:
|
||||
void clearForms();
|
||||
};
|
@ -336,6 +336,24 @@ void TestGui::testKeePass1Import()
|
||||
QCOMPARE(m_tabWidget->tabText(m_tabWidget->currentIndex()), QString("basic [New database]*"));
|
||||
}
|
||||
|
||||
void TestGui::testDatabaseLocking()
|
||||
{
|
||||
triggerAction("actionLockDatabases");
|
||||
|
||||
QCOMPARE(m_tabWidget->tabText(0), QString("Save [locked]"));
|
||||
QCOMPARE(m_tabWidget->tabText(1), QString("basic [New database] [locked]*"));
|
||||
|
||||
QWidget* dbWidget = m_tabWidget->currentDatabaseWidget();
|
||||
QWidget* unlockDatabaseWidget = dbWidget->findChild<QWidget*>("unlockDatabaseWidget");
|
||||
QWidget* editPassword = unlockDatabaseWidget->findChild<QLineEdit*>("editPassword");
|
||||
QVERIFY(editPassword);
|
||||
|
||||
QTest::keyClicks(editPassword, "masterpw");
|
||||
QTest::keyClick(editPassword, Qt::Key_Enter);
|
||||
|
||||
QCOMPARE(m_tabWidget->tabText(m_tabWidget->currentIndex()), QString("basic [New database]*"));
|
||||
}
|
||||
|
||||
void TestGui::cleanupTestCase()
|
||||
{
|
||||
delete m_mainWindow;
|
||||
|
@ -45,6 +45,7 @@ private Q_SLOTS:
|
||||
void testSave();
|
||||
void testDatabaseSettings();
|
||||
void testKeePass1Import();
|
||||
void testDatabaseLocking();
|
||||
void cleanupTestCase();
|
||||
|
||||
private:
|
||||
|
Loading…
Reference in New Issue
Block a user