From baf867eddd4efbc465f5a3490b1ea21dfe7ba597 Mon Sep 17 00:00:00 2001 From: Soeren Apel Date: Mon, 25 Nov 2019 21:46:27 +0100 Subject: [PATCH] Implement adding different view types --- pv/mainwindow.cpp | 34 +++++++++++++++++++--------------- pv/mainwindow.hpp | 8 +++----- pv/session.cpp | 2 +- pv/session.hpp | 3 +-- pv/toolbars/mainbar.cpp | 25 ++++++++++++++++++++++--- pv/toolbars/mainbar.hpp | 6 +++--- pv/views/viewbase.cpp | 7 +++++++ pv/views/viewbase.hpp | 7 ++++++- test/CMakeLists.txt | 2 ++ 9 files changed, 64 insertions(+), 30 deletions(-) diff --git a/pv/mainwindow.cpp b/pv/mainwindow.cpp index c652e3e8..51ebda83 100644 --- a/pv/mainwindow.cpp +++ b/pv/mainwindow.cpp @@ -128,8 +128,8 @@ shared_ptr MainWindow::get_active_view() const return nullptr; } -shared_ptr MainWindow::add_view(const QString &title, - views::ViewType type, Session &session) +shared_ptr MainWindow::add_view(views::ViewType type, + Session &session) { GlobalSettings settings; shared_ptr v; @@ -143,6 +143,13 @@ shared_ptr MainWindow::add_view(const QString &title, shared_ptr main_bar = session.main_bar(); + // Only use the view type in the name if it's not the main view + QString title; + if (main_bar) + title = QString("%1 (%2)").arg(session.name()).arg(views::ViewTypeNames[type]); + else + title = session.name(); + QDockWidget* dock = new QDockWidget(title, main_window); dock->setObjectName(title); main_window->addDockWidget(Qt::TopDockWidgetArea, dock); @@ -153,8 +160,7 @@ shared_ptr MainWindow::add_view(const QString &title, if (type == views::ViewTypeTrace) // This view will be the main view if there's no main bar yet - v = make_shared(session, - (main_bar ? false : true), dock_main); + v = make_shared(session, (main_bar ? false : true), dock_main); #ifdef ENABLE_DECODE if (type == views::ViewTypeDecoderOutput) v = make_shared(session, false, dock_main); @@ -194,8 +200,8 @@ shared_ptr MainWindow::add_view(const QString &title, dock_main->addToolBar(main_bar.get()); session.set_main_bar(main_bar); - connect(main_bar.get(), SIGNAL(new_view(Session*)), - this, SLOT(on_new_view(Session*))); + connect(main_bar.get(), SIGNAL(new_view(Session*, int)), + this, SLOT(on_new_view(Session*, int))); connect(main_bar.get(), SIGNAL(show_decoder_selector(Session*)), this, SLOT(on_show_decoder_selector(Session*))); @@ -319,8 +325,8 @@ shared_ptr MainWindow::add_session() shared_ptr session = make_shared(device_manager_, name); - connect(session.get(), SIGNAL(add_view(const QString&, views::ViewType, Session*)), - this, SLOT(on_add_view(const QString&, views::ViewType, Session*))); + connect(session.get(), SIGNAL(add_view(views::ViewType, Session*)), + this, SLOT(on_add_view(views::ViewType, Session*))); connect(session.get(), SIGNAL(name_changed()), this, SLOT(on_session_name_changed())); session_state_mapper_.setMapping(session.get(), session.get()); @@ -339,8 +345,7 @@ shared_ptr MainWindow::add_session() window->setDockNestingEnabled(true); - shared_ptr main_view = - add_view(name, views::ViewTypeTrace, *session); + shared_ptr main_view = add_view(views::ViewTypeTrace, *session); return session; } @@ -628,13 +633,12 @@ bool MainWindow::restoreState(const QByteArray &state, int version) return false; } -void MainWindow::on_add_view(const QString &title, views::ViewType type, - Session *session) +void MainWindow::on_add_view(views::ViewType type, Session *session) { // We get a pointer and need a reference for (shared_ptr& s : sessions_) if (s.get() == session) - add_view(title, type, *s); + add_view(type, *s); } void MainWindow::on_focus_changed() @@ -749,12 +753,12 @@ void MainWindow::on_capture_state_changed(QObject *obj) tr("Run") : tr("Stop")); } -void MainWindow::on_new_view(Session *session) +void MainWindow::on_new_view(Session *session, int view_type) { // We get a pointer and need a reference for (shared_ptr& s : sessions_) if (s.get() == session) - add_view(session->name(), views::ViewTypeTrace, *s); + add_view((views::ViewType)view_type, *s); } void MainWindow::on_view_close_clicked() diff --git a/pv/mainwindow.hpp b/pv/mainwindow.hpp index 6f3676c2..06eba40a 100644 --- a/pv/mainwindow.hpp +++ b/pv/mainwindow.hpp @@ -79,8 +79,7 @@ public: shared_ptr get_active_view() const; - shared_ptr add_view(const QString &title, - views::ViewType type, Session &session); + shared_ptr add_view(views::ViewType type, Session &session); void remove_view(shared_ptr view); @@ -114,8 +113,7 @@ private: virtual bool restoreState(const QByteArray &state, int version = 0); private Q_SLOTS: - void on_add_view(const QString &title, views::ViewType type, - Session *session); + void on_add_view(views::ViewType type, Session *session); void on_focus_changed(); void on_focused_session_changed(shared_ptr session); @@ -127,7 +125,7 @@ private Q_SLOTS: void on_session_name_changed(); void on_capture_state_changed(QObject *obj); - void on_new_view(Session *session); + void on_new_view(Session *session, int view_type); void on_view_close_clicked(); void on_tab_changed(int index); diff --git a/pv/session.cpp b/pv/session.cpp index 6d9ce830..39b1fb35 100644 --- a/pv/session.cpp +++ b/pv/session.cpp @@ -312,7 +312,7 @@ void Session::restore_setup(QSettings &settings) if (i > 0) { views::ViewType type = (views::ViewType)settings.value("type").toInt(); - add_view(name_, type, this); + add_view(type, this); views_.back()->restore_settings(settings); } else main_view_->restore_settings(settings); diff --git a/pv/session.hpp b/pv/session.hpp index a4aaf6aa..8d85996e 100644 --- a/pv/session.hpp +++ b/pv/session.hpp @@ -264,8 +264,7 @@ Q_SIGNALS: void data_received(); - void add_view(const QString &title, views::ViewType type, - Session *session); + void add_view(views::ViewType type, Session *session); public Q_SLOTS: void on_data_saved(); diff --git a/pv/toolbars/mainbar.cpp b/pv/toolbars/mainbar.cpp index 666c28d3..3836b09a 100644 --- a/pv/toolbars/mainbar.cpp +++ b/pv/toolbars/mainbar.cpp @@ -95,6 +95,7 @@ MainBar::MainBar(Session &session, QWidget *parent, pv::views::trace::View *view action_restore_setup_(new QAction(this)), action_save_setup_(new QAction(this)), action_connect_(new QAction(this)), + new_view_button_(new QToolButton()), open_button_(new QToolButton()), save_button_(new QToolButton()), device_selector_(parent, session.device_manager(), action_connect_), @@ -167,6 +168,20 @@ MainBar::MainBar(Session &session, QWidget *parent, pv::views::trace::View *view connect(action_connect_, SIGNAL(triggered(bool)), this, SLOT(on_actionConnect_triggered())); + // New view button + QMenu *menu_new_view = new QMenu(); + connect(menu_new_view, SIGNAL(triggered(QAction*)), + this, SLOT(on_actionNewView_triggered(QAction*))); + + for (int i = 0; i < views::ViewTypeCount; i++) { + QAction *const action = menu_new_view->addAction(tr(views::ViewTypeNames[i])); + action->setData(qVariantFromValue(i)); + } + + new_view_button_->setMenu(menu_new_view); + new_view_button_->setDefaultAction(action_new_view_); + new_view_button_->setPopupMode(QToolButton::MenuButtonPopup); + // Open button vector open_actions; open_actions.push_back(action_open_); @@ -754,9 +769,13 @@ void MainBar::on_config_changed() commit_sample_rate(); } -void MainBar::on_actionNewView_triggered() +void MainBar::on_actionNewView_triggered(QAction* action) { - new_view(&session_); + if (action) + new_view(&session_, action->data().toInt()); + else + // When the icon of the button is clicked, we create a trace view + new_view(&session_, views::ViewTypeTrace); } void MainBar::on_actionOpen_triggered() @@ -844,7 +863,7 @@ void MainBar::on_add_decoder_clicked() void MainBar::add_toolbar_widgets() { - addAction(action_new_view_); + addWidget(new_view_button_); addSeparator(); addWidget(open_button_); addWidget(save_button_); diff --git a/pv/toolbars/mainbar.hpp b/pv/toolbars/mainbar.hpp index bc0c2dfd..008ab628 100644 --- a/pv/toolbars/mainbar.hpp +++ b/pv/toolbars/mainbar.hpp @@ -139,7 +139,7 @@ private Q_SLOTS: void on_config_changed(); - void on_actionNewView_triggered(); + void on_actionNewView_triggered(QAction* action = nullptr); void on_actionOpen_triggered(); void on_actionSaveAs_triggered(); @@ -158,11 +158,11 @@ protected: bool eventFilter(QObject *watched, QEvent *event); Q_SIGNALS: - void new_view(Session *session); + void new_view(Session *session, int type); void show_decoder_selector(Session *session); private: - QToolButton *open_button_, *save_button_; + QToolButton *new_view_button_, *open_button_, *save_button_; pv::widgets::DeviceToolButton device_selector_; diff --git a/pv/views/viewbase.cpp b/pv/views/viewbase.cpp index 4449d190..a4dc5490 100644 --- a/pv/views/viewbase.cpp +++ b/pv/views/viewbase.cpp @@ -33,6 +33,13 @@ using std::shared_ptr; namespace pv { namespace views { +const char* ViewTypeNames[ViewTypeCount] = { + "Trace View", +#ifdef ENABLE_DECODE + "Decoder Output View" +#endif +}; + const int ViewBase::MaxViewAutoUpdateRate = 25; // No more than 25 Hz ViewBase::ViewBase(Session &session, bool is_main_view, QWidget *parent) : diff --git a/pv/views/viewbase.hpp b/pv/views/viewbase.hpp index 09c5716a..0c7b0463 100644 --- a/pv/views/viewbase.hpp +++ b/pv/views/viewbase.hpp @@ -50,12 +50,17 @@ class Signal; namespace views { +// When adding an entry here, don't forget to update ViewTypeNames as well enum ViewType { ViewTypeTrace, +#ifdef ENABLE_DECODE ViewTypeDecoderOutput, - ViewTypeTabularDecode +#endif + ViewTypeCount // Indicates how many view types there are, must always be last }; +extern const char* ViewTypeNames[ViewTypeCount]; + class ViewBase : public QWidget { Q_OBJECT diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index 6d4472a3..0f81a0e5 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -172,6 +172,7 @@ if(ENABLE_DECODE) ${PROJECT_SOURCE_DIR}/pv/subwindows/decoder_selector/item.cpp ${PROJECT_SOURCE_DIR}/pv/subwindows/decoder_selector/model.cpp ${PROJECT_SOURCE_DIR}/pv/subwindows/decoder_selector/subwindow.cpp + ${PROJECT_SOURCE_DIR}/pv/views/decoder_output/view.cpp ${PROJECT_SOURCE_DIR}/pv/views/trace/decodetrace.cpp ${PROJECT_SOURCE_DIR}/pv/widgets/decodergroupbox.cpp ${PROJECT_SOURCE_DIR}/pv/widgets/decodermenu.cpp @@ -180,6 +181,7 @@ if(ENABLE_DECODE) list(APPEND pulseview_TEST_HEADERS ${PROJECT_SOURCE_DIR}/pv/data/decodesignal.hpp ${PROJECT_SOURCE_DIR}/pv/subwindows/decoder_selector/subwindow.hpp + ${PROJECT_SOURCE_DIR}/pv/views/decoder_output/view.hpp ${PROJECT_SOURCE_DIR}/pv/views/trace/decodetrace.hpp ${PROJECT_SOURCE_DIR}/pv/widgets/decodergroupbox.hpp ${PROJECT_SOURCE_DIR}/pv/widgets/decodermenu.hpp -- 2.30.2