Quick GUI: Hide entries and their children when deleted
This commit is contained in:
parent
55eddd3fed
commit
316f1ee2a7
|
@ -11,7 +11,7 @@ Kirigami.ScrollablePage {
|
|||
property alias rootIndex: delegateModel.rootIndex
|
||||
|
||||
Layout.fillWidth: true
|
||||
title: "?"
|
||||
title: entryModel.data(rootIndex)
|
||||
actions {
|
||||
main: Kirigami.Action {
|
||||
iconName: "list-add"
|
||||
|
|
40
qml/main.qml
40
qml/main.qml
|
@ -7,6 +7,8 @@ import org.kde.kirigami 2.4 as Kirigami
|
|||
Kirigami.ApplicationWindow {
|
||||
id: root
|
||||
property alias showPasswordsOnFocus: showPasswordsOnFocusSwitch.checked
|
||||
property var fieldsPage: undefined
|
||||
property var lastEntriesPage: undefined
|
||||
|
||||
header: Kirigami.ApplicationHeader {
|
||||
backButtonEnabled: false
|
||||
|
@ -220,6 +222,25 @@ Kirigami.ApplicationWindow {
|
|||
onNewNotification: {
|
||||
showPassiveNotification(message)
|
||||
}
|
||||
onCurrentAccountChanged: {
|
||||
// remove the fields page if the current account has been removed
|
||||
if (!nativeInterface.hasCurrentAccount) {
|
||||
pageStack.pop(lastEntriesPage)
|
||||
}
|
||||
}
|
||||
onEntryAboutToBeRemoved: {
|
||||
// remove all possibly open stack pages of the removed entry and its children
|
||||
for (var i = pageStack.depth - 1; i >= 0; --i) {
|
||||
var stackPage = pageStack.get(i)
|
||||
if (!stackPage) {
|
||||
continue
|
||||
}
|
||||
if (stackPage.rootIndex === removedIndex) {
|
||||
pageStack.pop(lastEntriesPage = pageStack.get(i - 1))
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Component {
|
||||
|
@ -251,20 +272,27 @@ Kirigami.ApplicationWindow {
|
|||
}
|
||||
|
||||
function clearStack() {
|
||||
pageStack.pop(root.pageStack.initialPage, Controls.StackView.Immediate)
|
||||
pageStack.pop(lastEntriesPage = root.pageStack.initialPage,
|
||||
Controls.StackView.Immediate)
|
||||
}
|
||||
|
||||
function pushStackEntry(entryModel, rootIndex) {
|
||||
pageStack.push(entriesComponent.createObject(root, {
|
||||
pageStack.push(lastEntriesPage = entriesComponent.createObject(root, {
|
||||
"entryModel": entryModel,
|
||||
"rootIndex": rootIndex,
|
||||
"title": entryModel.data(
|
||||
rootIndex)
|
||||
"rootIndex": rootIndex
|
||||
}))
|
||||
}
|
||||
|
||||
function pushAccountEdit() {
|
||||
pageStack.push(fieldsComponent.createObject(root))
|
||||
// lazy-initialize fieldsPage
|
||||
if (!fieldsPage) {
|
||||
fieldsPage = fieldsComponent.createObject(root)
|
||||
}
|
||||
// remove fieldsPage if already shown to prevent warning
|
||||
if (pageStack.get(pageStack.depth - 1) === fieldsPage) {
|
||||
pageStack.pop(lastEntriesPage)
|
||||
}
|
||||
pageStack.push(fieldsPage)
|
||||
}
|
||||
|
||||
function createFileActions(files) {
|
||||
|
|
|
@ -23,6 +23,7 @@
|
|||
#include <QSettings>
|
||||
#include <QStringBuilder>
|
||||
|
||||
#include <cassert>
|
||||
#include <stdexcept>
|
||||
|
||||
using namespace std;
|
||||
|
@ -40,6 +41,7 @@ Controller::Controller(QSettings &settings, const QString &filePath, QObject *pa
|
|||
, m_useNativeFileDialog(false)
|
||||
{
|
||||
m_entryFilterModel.setSourceModel(&m_entryModel);
|
||||
connect(&m_entryModel, &QAbstractItemModel::rowsAboutToBeRemoved, this, &Controller::handleEntriesRemoved);
|
||||
|
||||
// share settings with main window
|
||||
m_settings.beginGroup(QStringLiteral("mainwindow"));
|
||||
|
@ -258,6 +260,50 @@ void Controller::handleFileSelectionCanceled()
|
|||
emit newNotification(tr("Canceled file selection"));
|
||||
}
|
||||
|
||||
void Controller::handleEntriesRemoved(const QModelIndex &parentIndex, int first, int last)
|
||||
{
|
||||
// handle deletion of root (currently the view doesn't allow this)
|
||||
const auto *const parentEntry = m_entryModel.entry(parentIndex);
|
||||
if (!parentEntry) {
|
||||
emit entryAboutToBeRemoved(m_entryModel.index(0, 0, QModelIndex()));
|
||||
setCurrentAccount(nullptr);
|
||||
return;
|
||||
}
|
||||
|
||||
// assert arguments
|
||||
assert(parentEntry->type() == EntryType::Node);
|
||||
const auto &childEntries = static_cast<const NodeEntry *>(parentEntry)->children();
|
||||
assert(first >= 0 && static_cast<size_t>(first) < childEntries.size());
|
||||
assert(last >= 0 && static_cast<size_t>(last) < childEntries.size());
|
||||
|
||||
// iterate from first to last of the deleted entries
|
||||
const auto *const currentAccount = this->currentAccount();
|
||||
for (; first <= last; ++first) {
|
||||
// inform view about deletion
|
||||
emit entryAboutToBeRemoved(m_entryModel.index(first, 0, parentIndex));
|
||||
|
||||
// unset current account if it is under the deleted node
|
||||
if (!currentAccount) {
|
||||
continue;
|
||||
}
|
||||
const auto *const childEntry = childEntries[static_cast<size_t>(first)];
|
||||
switch (childEntry->type()) {
|
||||
case EntryType::Account:
|
||||
if (currentAccount == static_cast<const AccountEntry *>(childEntry)) {
|
||||
setCurrentAccount(nullptr);
|
||||
}
|
||||
break;
|
||||
case EntryType::Node:
|
||||
// FIXME: remove const_cast in passwordfile v4
|
||||
if (currentAccount->isIndirectChildOf(static_cast<NodeEntry *>(const_cast<Entry *>(childEntry)))) {
|
||||
setCurrentAccount(nullptr);
|
||||
}
|
||||
break;
|
||||
default:;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
QStringList Controller::pasteEntries(const QModelIndex &destinationParent, int row)
|
||||
{
|
||||
if (m_cutEntries.isEmpty() || !m_entryModel.isNode(destinationParent)) {
|
||||
|
|
|
@ -25,8 +25,10 @@ class Controller : public QObject {
|
|||
Q_PROPERTY(EntryModel *entryModel READ entryModel NOTIFY entryModelChanged)
|
||||
Q_PROPERTY(EntryFilterModel *entryFilterModel READ entryFilterModel NOTIFY entryFilterModelChanged)
|
||||
Q_PROPERTY(FieldModel *fieldModel READ fieldModel NOTIFY fieldModelChanged)
|
||||
Q_PROPERTY(Io::AccountEntry *currentAccount READ currentAccount WRITE setCurrentAccount NOTIFY currentAccountChanged)
|
||||
Q_PROPERTY(QModelIndex currentAccountIndex READ currentAccountIndex WRITE setCurrentAccountIndex NOTIFY currentAccountChanged)
|
||||
Q_PROPERTY(QString currentAccountName READ currentAccountName NOTIFY currentAccountChanged)
|
||||
Q_PROPERTY(bool hasCurrentAccount READ hasCurrentAccount NOTIFY currentAccountChanged)
|
||||
Q_PROPERTY(QList<QPersistentModelIndex> cutEntries READ cutEntries WRITE setCutEntries NOTIFY cutEntriesChanged)
|
||||
Q_PROPERTY(bool canPaste READ canPaste NOTIFY cutEntriesChanged)
|
||||
Q_PROPERTY(QStringList recentFiles READ recentFiles NOTIFY recentFilesChanged)
|
||||
|
@ -48,8 +50,11 @@ public:
|
|||
EntryModel *entryModel();
|
||||
EntryFilterModel *entryFilterModel();
|
||||
FieldModel *fieldModel();
|
||||
Io::AccountEntry *currentAccount();
|
||||
void setCurrentAccount(Io::AccountEntry *entry);
|
||||
QModelIndex currentAccountIndex() const;
|
||||
void setCurrentAccountIndex(const QModelIndex &accountIndex);
|
||||
bool hasCurrentAccount() const;
|
||||
const QList<QPersistentModelIndex> &cutEntries() const;
|
||||
void setCutEntries(const QList<QPersistentModelIndex> &cutEntries);
|
||||
QString currentAccountName() const;
|
||||
|
@ -92,6 +97,10 @@ signals:
|
|||
void newNotification(const QString &message);
|
||||
void useNativeFileDialogChanged(bool useNativeFileDialog);
|
||||
void supportsNativeFileDialogChanged();
|
||||
void entryAboutToBeRemoved(const QModelIndex &removedIndex);
|
||||
|
||||
private slots:
|
||||
void handleEntriesRemoved(const QModelIndex &parentIndex, int first, int last);
|
||||
|
||||
private:
|
||||
void resetFileStatus();
|
||||
|
@ -166,6 +175,17 @@ inline FieldModel *Controller::fieldModel()
|
|||
return &m_fieldModel;
|
||||
}
|
||||
|
||||
inline Io::AccountEntry *Controller::currentAccount()
|
||||
{
|
||||
return m_fieldModel.accountEntry();
|
||||
}
|
||||
|
||||
inline void Controller::setCurrentAccount(Io::AccountEntry *entry)
|
||||
{
|
||||
m_fieldModel.setAccountEntry(entry);
|
||||
emit currentAccountChanged();
|
||||
}
|
||||
|
||||
inline QModelIndex Controller::currentAccountIndex() const
|
||||
{
|
||||
return m_fieldModel.accountEntry() ? m_entryModel.index(const_cast<Io::AccountEntry *>(m_fieldModel.accountEntry())) : QModelIndex();
|
||||
|
@ -177,6 +197,11 @@ inline void Controller::setCurrentAccountIndex(const QModelIndex &accountIndex)
|
|||
emit currentAccountChanged();
|
||||
}
|
||||
|
||||
inline bool Controller::hasCurrentAccount() const
|
||||
{
|
||||
return m_fieldModel.accountEntry() != nullptr;
|
||||
}
|
||||
|
||||
inline const QList<QPersistentModelIndex> &Controller::cutEntries() const
|
||||
{
|
||||
return m_cutEntries;
|
||||
|
|
Loading…
Reference in New Issue