|
@@ -8,6 +8,7 @@
|
|
|
#include <giomm/asyncresult.h>
|
|
#include <giomm/asyncresult.h>
|
|
|
#include <glibmm/main.h>
|
|
#include <glibmm/main.h>
|
|
|
#include <glibmm/markup.h>
|
|
#include <glibmm/markup.h>
|
|
|
|
|
+#include <gdk/gdkkeysyms.h>
|
|
|
|
|
|
|
|
#include <thread>
|
|
#include <thread>
|
|
|
#include <iostream>
|
|
#include <iostream>
|
|
@@ -148,6 +149,12 @@ BibliothecaWindow::BibliothecaWindow(DatabaseManager& db, BookList& bookList)
|
|
|
m_bookList.signalBookUpdated().connect([this](const Book&) { updateVisibleView(); });
|
|
m_bookList.signalBookUpdated().connect([this](const Book&) { updateVisibleView(); });
|
|
|
m_bookList.signalBookRemoved().connect([this](const std::string&) { updateVisibleView(); });
|
|
m_bookList.signalBookRemoved().connect([this](const std::string&) { updateVisibleView(); });
|
|
|
m_bookList.signalBulkChanged().connect([this] { updateVisibleView(); });
|
|
m_bookList.signalBulkChanged().connect([this] { updateVisibleView(); });
|
|
|
|
|
+
|
|
|
|
|
+ // Keyboard navigation
|
|
|
|
|
+ m_keyController = Gtk::EventControllerKey::create();
|
|
|
|
|
+ m_keyController->signal_key_pressed().connect(
|
|
|
|
|
+ sigc::mem_fun(*this, &BibliothecaWindow::onKeyPressed), false);
|
|
|
|
|
+ add_controller(m_keyController);
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
void BibliothecaWindow::buildHeaderBar() {
|
|
void BibliothecaWindow::buildHeaderBar() {
|
|
@@ -441,3 +448,57 @@ void BibliothecaWindow::onBookActivated(const Book& book) {
|
|
|
m_bookDetails->set_book(&book);
|
|
m_bookDetails->set_book(&book);
|
|
|
m_stack.set_visible_child("details");
|
|
m_stack.set_visible_child("details");
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
|
|
+bool BibliothecaWindow::onKeyPressed(guint keyval, guint /*keycode*/, Gdk::ModifierType /*state*/) {
|
|
|
|
|
+ const auto visible = m_stack.get_visible_child_name();
|
|
|
|
|
+
|
|
|
|
|
+ switch (keyval) {
|
|
|
|
|
+ case GDK_KEY_Escape:
|
|
|
|
|
+ if (visible == "details") {
|
|
|
|
|
+ // Go back to shelf from details
|
|
|
|
|
+ m_stack.set_visible_child("shelf");
|
|
|
|
|
+ if (!m_lastQuery.empty()) {
|
|
|
|
|
+ m_shelf->setFilter(m_lastQuery);
|
|
|
|
|
+ updateVisibleView();
|
|
|
|
|
+ }
|
|
|
|
|
+ return true;
|
|
|
|
|
+ } else if (m_searchBar.property_search_mode_enabled().get_value()) {
|
|
|
|
|
+ // Close search bar
|
|
|
|
|
+ m_searchBar.property_search_mode_enabled() = false;
|
|
|
|
|
+ return true;
|
|
|
|
|
+ } else if (m_shelf) {
|
|
|
|
|
+ // Clear selection
|
|
|
|
|
+ m_shelf->clearSelection();
|
|
|
|
|
+ return true;
|
|
|
|
|
+ }
|
|
|
|
|
+ break;
|
|
|
|
|
+
|
|
|
|
|
+ case GDK_KEY_Return:
|
|
|
|
|
+ case GDK_KEY_KP_Enter:
|
|
|
|
|
+ if (visible == "shelf" && m_shelf) {
|
|
|
|
|
+ // Activate selected book
|
|
|
|
|
+ if (auto book = m_shelf->getSelectedBook()) {
|
|
|
|
|
+ onBookActivated(*book);
|
|
|
|
|
+ return true;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ break;
|
|
|
|
|
+
|
|
|
|
|
+ case GDK_KEY_BackSpace:
|
|
|
|
|
+ if (visible == "details") {
|
|
|
|
|
+ // Go back to shelf from details
|
|
|
|
|
+ m_stack.set_visible_child("shelf");
|
|
|
|
|
+ if (!m_lastQuery.empty()) {
|
|
|
|
|
+ m_shelf->setFilter(m_lastQuery);
|
|
|
|
|
+ updateVisibleView();
|
|
|
|
|
+ }
|
|
|
|
|
+ return true;
|
|
|
|
|
+ }
|
|
|
|
|
+ break;
|
|
|
|
|
+
|
|
|
|
|
+ default:
|
|
|
|
|
+ break;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ return false; // Let other handlers process the key
|
|
|
|
|
+}
|