Also adds the non-functional view mode selector.
return texts_->front();
}
+bool Annotation::visible() const
+{
+ const Row* row = data_->row();
+
+ return (row->visible() && row->class_is_visible(ann_class_id_));
+}
+
const QColor Annotation::color() const
{
return data_->row()->get_class_color(ann_class_id_);
const vector<QString>* annotations() const;
const QString longest_annotation() const;
+ bool visible() const;
+
const QColor color() const;
const QColor bright_color() const;
const QColor dark_color() const;
return false;
}
+bool Row::class_is_visible(uint32_t ann_class_id) const
+{
+ return decoder_->get_ann_class_by_id(ann_class_id)->visible;
+}
+
bool Row::operator<(const Row& other) const
{
return (decoder_ < other.decoder_) ||
const QColor get_dark_class_color(uint32_t ann_class_id) const;
bool has_hidden_classes() const;
+ bool class_is_visible(uint32_t ann_class_id) const;
bool operator<(const Row& other) const;
bool operator==(const Row& other) const;
AnnotationCollectionModel::AnnotationCollectionModel(QObject* parent) :
QAbstractTableModel(parent),
all_annotations_(nullptr),
+ dataset_(nullptr),
signal_(nullptr),
prev_segment_(0),
- prev_last_row_(0)
+ prev_last_row_(0),
+ hide_hidden_(false)
{
GlobalSettings::add_change_handler(this);
theme_is_dark_ = GlobalSettings::current_theme_is_dark();
assert(row >= 0);
assert(column >= 0);
- if (!all_annotations_)
+ if (!dataset_)
return QModelIndex();
- if ((size_t)row > all_annotations_->size())
- return QModelIndex();
+ QModelIndex idx;
+
+ if ((size_t)row < dataset_->size())
+ idx = createIndex(row, column, (void*)dataset_->at(row));
- return createIndex(row, column, (void*)(all_annotations_->at(row)));
+ return idx;
}
QModelIndex AnnotationCollectionModel::parent(const QModelIndex& index) const
{
(void)parent_idx;
- if (!all_annotations_)
+ if (!dataset_)
return 0;
- return all_annotations_->size();
+ return dataset_->size();
}
int AnnotationCollectionModel::columnCount(const QModelIndex& parent_idx) const
{
if (!signal) {
all_annotations_ = nullptr;
+ dataset_ = nullptr;
signal_ = nullptr;
+
dataChanged(QModelIndex(), QModelIndex());
layoutChanged();
return;
all_annotations_ = signal->get_all_annotations_by_segment(current_segment);
signal_ = signal;
- if (!all_annotations_ || all_annotations_->empty()) {
+ if (hide_hidden_)
+ update_annotations_without_hidden();
+ else
+ dataset_ = all_annotations_;
+
+ if (!dataset_ || dataset_->empty()) {
prev_segment_ = current_segment;
return;
}
- const size_t new_row_count = all_annotations_->size() - 1;
+ const size_t new_row_count = dataset_->size() - 1;
// Force the view associated with this model to update when the segment changes
if (prev_segment_ != current_segment) {
prev_last_row_ = new_row_count;
}
+void AnnotationCollectionModel::set_hide_hidden(bool hide_hidden)
+{
+ hide_hidden_ = hide_hidden;
+
+ if (hide_hidden_) {
+ dataset_ = &all_annotations_without_hidden_;
+ update_annotations_without_hidden();
+ } else {
+ dataset_ = all_annotations_;
+ all_annotations_without_hidden_.clear(); // To conserve memory
+ }
+}
+
+void AnnotationCollectionModel::update_annotations_without_hidden()
+{
+ uint64_t count = 0;
+
+ if (!all_annotations_ || all_annotations_->empty()) {
+ all_annotations_without_hidden_.clear();
+ return;
+ }
+
+ for (const Annotation* ann : *all_annotations_) {
+ if (!ann->visible())
+ continue;
+
+ if (all_annotations_without_hidden_.size() < (count + 100))
+ all_annotations_without_hidden_.resize(count + 100);
+
+ all_annotations_without_hidden_[count++] = ann;
+ }
+
+ all_annotations_without_hidden_.resize(count);
+
+ dataChanged(index(0, 0, QModelIndex()), index(count, 0, QModelIndex()));
+ layoutChanged();
+}
+
void AnnotationCollectionModel::on_setting_changed(const QString &key, const QVariant &value)
{
(void)key;
"CSV, fields quoted"
};
+const char* ViewModeNames[ViewModeCount] = {
+ "Show all",
+ "Show all and focus on newest",
+ "Show visible in main view"
+};
+
QSize QCustomTableView::minimumSizeHint() const
{
QSize size(QTableView::sizeHint());
// Note: Place defaults in View::reset_view_state(), not here
parent_(parent),
decoder_selector_(new QComboBox()),
+ hide_hidden_cb_(new QCheckBox()),
+ view_mode_selector_(new QComboBox()),
save_button_(new QToolButton()),
save_action_(new QAction(this)),
table_view_(new QCustomTableView()),
toolbar->addWidget(decoder_selector_);
toolbar->addSeparator();
toolbar->addWidget(save_button_);
+ toolbar->addSeparator();
+ toolbar->addWidget(view_mode_selector_);
+ toolbar->addSeparator();
+ toolbar->addWidget(hide_hidden_cb_);
connect(decoder_selector_, SIGNAL(currentIndexChanged(int)),
this, SLOT(on_selected_decoder_changed(int)));
+ connect(view_mode_selector_, SIGNAL(currentIndexChanged(int)),
+ this, SLOT(on_view_mode_changed(int)));
+ connect(hide_hidden_cb_, SIGNAL(toggled(bool)),
+ this, SLOT(on_hide_hidden_changed(bool)));
// Configure widgets
decoder_selector_->setSizeAdjustPolicy(QComboBox::AdjustToContents);
+ for (int i = 0; i < ViewModeCount; i++)
+ view_mode_selector_->addItem(ViewModeNames[i], QVariant::fromValue(i));
+
+ hide_hidden_cb_->setText(tr("Hide Hidden Rows/Classes"));
+ hide_hidden_cb_->setChecked(true);
+
// Configure actions
save_action_->setText(tr("&Save..."));
save_action_->setIcon(QIcon::fromTheme("document-save-as",
void View::save_settings(QSettings &settings) const
{
ViewBase::save_settings(settings);
+
+ settings.setValue("view_mode", view_mode_selector_->currentIndex());
+ settings.setValue("hide_hidden", hide_hidden_cb_->isChecked());
}
void View::restore_settings(QSettings &settings)
{
- // Note: It is assumed that this function is only called once,
- // immediately after restoring a previous session.
ViewBase::restore_settings(settings);
+
+ if (settings.contains("view_mode"))
+ view_mode_selector_->setCurrentIndex(settings.value("view_mode").toInt());
+
+ if (settings.contains("hide_hidden"))
+ hide_hidden_cb_->setChecked(settings.value("hide_hidden").toBool());
}
void View::reset_data()
update_data();
}
+void View::on_hide_hidden_changed(bool checked)
+{
+ model_->set_hide_hidden(checked);
+
+ // Force repaint, otherwise the new selection isn't shown for some reason
+ table_view_->viewport()->update();
+}
+
+void View::on_view_mode_changed(int index)
+{
+ (void)index;
+}
+
void View::on_signal_name_changed(const QString &name)
{
(void)name;
#define PULSEVIEW_PV_VIEWS_TABULARDECODER_VIEW_HPP
#include <QAction>
+#include <QCheckBox>
#include <QComboBox>
#include <QTableView>
#include <QToolButton>
SaveTypeCount // Indicates how many save types there are, must always be last
};
+// When adding an entry here, don't forget to update ViewModeNames as well
+enum ViewModeType {
+ ViewModeAll,
+ ViewModeLatest,
+ ViewModeVisible,
+ ViewModeCount // Indicates how many save types there are, must always be last
+};
+
extern const char* SaveTypeNames[SaveTypeCount];
+extern const char* ViewModeNames[ViewModeCount];
class AnnotationCollectionModel : public QAbstractTableModel, public GlobalSettingsInterface
int columnCount(const QModelIndex& parent_idx = QModelIndex()) const override;
void set_signal_and_segment(data::DecodeSignal* signal, uint32_t current_segment);
+ void set_hide_hidden(bool hide_hidden);
+
+ void update_annotations_without_hidden();
void on_setting_changed(const QString &key, const QVariant &value) override;
private:
vector<QVariant> header_data_;
const deque<const Annotation*>* all_annotations_;
+ deque<const Annotation*> all_annotations_without_hidden_;
+ const deque<const Annotation*>* dataset_;
data::DecodeSignal* signal_;
uint32_t prev_segment_;
uint64_t prev_last_row_;
+ bool hide_hidden_;
bool theme_is_dark_;
};
private Q_SLOTS:
void on_selected_decoder_changed(int index);
+ void on_hide_hidden_changed(bool checked);
+ void on_view_mode_changed(int index);
+
void on_signal_name_changed(const QString &name);
void on_signal_color_changed(const QColor &color);
void on_new_annotations();
QWidget* parent_;
QComboBox* decoder_selector_;
+ QCheckBox* hide_hidden_cb_;
+ QComboBox* view_mode_selector_;
QToolButton* save_button_;
QAction* save_action_;