File: AbstractLogWindow.cpp

package info (click to toggle)
wsjtx 2.3.0%2Brepack-2
  • links: PTS, VCS
  • area: main
  • in suites: bullseye
  • size: 63,524 kB
  • sloc: cpp: 59,051; f90: 34,130; python: 27,241; ansic: 11,205; fortran: 2,051; sh: 132; makefile: 109
file content (157 lines) | stat: -rw-r--r-- 5,610 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
#include "AbstractLogWindow.hpp"

#include <algorithm>
#include <QSettings>
#include <QObject>
#include <QString>
#include <QTableView>
#include <QHeaderView>
#include <QAction>
#include <QSqlTableModel>
#include <QItemSelectionModel>
#include <QItemSelection>
#include "Configuration.hpp"
#include "SettingsGroup.hpp"
#include "MessageBox.hpp"
#include "models/FontOverrideModel.hpp"
#include "pimpl_impl.hpp"

class AbstractLogWindow::impl final
  : public QObject
{
  Q_OBJECT

public:
  impl (AbstractLogWindow * self, QString const& settings_key, QSettings * settings
        , Configuration const * configuration)
    : self_ {self}
    , settings_key_ {settings_key}
    , settings_ {settings}
    , configuration_ {configuration}
    , log_view_ {nullptr}
  {
  }

  void delete_QSOs ();

  AbstractLogWindow * self_;
  QString settings_key_;
  QSettings * settings_;
  Configuration const * configuration_;
  QTableView * log_view_;
  FontOverrideModel model_;
};

#include "moc_AbstractLogWindow.cpp"
#include "AbstractLogWindow.moc"

namespace
{
  bool row_is_higher (QModelIndex const& lhs, QModelIndex const& rhs)
  {
    return lhs.row () > rhs.row ();
  }
}

void AbstractLogWindow::impl::delete_QSOs ()
{
  auto selection_model = log_view_->selectionModel ();
  selection_model->select (selection_model->selection (), QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
  auto row_indexes = selection_model->selectedRows ();

  if (row_indexes.size ()
      && MessageBox::Yes == MessageBox::query_message (self_
                                                       , tr ("Confirm Delete")
                                                       , tr ("Are you sure you want to delete the %n "
                                                             "selected QSO(s) from the log?", ""
                                                             , row_indexes.size ())))
    {
      // We must work with source model indexes because we don't want row
      // removes to invalidate model indexes we haven't yet processed. We
      // achieve that by processing them in decending row order.
      for (auto& row_index : row_indexes)
        {
          row_index = model_.mapToSource (row_index);
        }

      // reverse sort by row
      std::sort (row_indexes.begin (), row_indexes.end (), row_is_higher);
      for (auto index : row_indexes)
        {
          auto row = model_.mapFromSource (index).row ();
          model_.removeRow (row);
          self_->log_model_changed ();
        }
    }
}

AbstractLogWindow::AbstractLogWindow (QString const& settings_key, QSettings * settings
                                      , Configuration const * configuration
                                      , QWidget * parent)
  : QWidget {parent}
  , m_ {this, settings_key, settings, configuration}
{
  // this attempt to scroll to the last new record doesn't work, some
  // sort of issue with model indexes and optimized DB fetches. For
  // now sorting by the same column and direction as the underlying DB
  // select and that DB select being in descending order so new rows
  // at the end appear at view row 0 gets the job done

  // // ensure view scrolls to latest new row
  // connect (&m_->model_, &QAbstractItemModel::rowsInserted, this, [this] (QModelIndex const& parent, int first, int last) {
  //     // note col 0 is hidden so use col 1
  //     // queued connection required otherwise row may not be available
  //     // in time
  //     auto index = m_->model_.index (last, 1, parent);
  //     if (m_->log_view_)
  //       {
  //         m_->log_view_->scrollTo (index);
  //       }
  //   }, Qt::QueuedConnection);
}

AbstractLogWindow::~AbstractLogWindow ()
{
  SettingsGroup g {m_->settings_, m_->settings_key_};
  m_->settings_->setValue ("window/geometry", saveGeometry ());
}

void AbstractLogWindow::set_log_view (QTableView * log_view)
{
  // do this here because we know the UI must be setup before this
  SettingsGroup g {m_->settings_, m_->settings_key_};
  restoreGeometry (m_->settings_->value ("window/geometry").toByteArray ());
  m_->log_view_ = log_view;
  set_log_view_font (m_->configuration_->decoded_text_font ());
  log_view->setSortingEnabled (true);
  log_view->setContextMenuPolicy (Qt::ActionsContextMenu);
  log_view->setAlternatingRowColors (true);
  log_view->setSelectionBehavior (QAbstractItemView::SelectRows);
  log_view->setSelectionMode (QAbstractItemView::ExtendedSelection);
  log_view->setVerticalScrollMode (QAbstractItemView::ScrollPerPixel);
  m_->model_.setSourceModel (log_view->model ());
  log_view->setModel (&m_->model_);
  log_view->setColumnHidden (0, true);
  auto horizontal_header = log_view->horizontalHeader ();
  horizontal_header->setResizeContentsPrecision (0); // visible region only
  horizontal_header->setSectionResizeMode (QHeaderView::ResizeToContents);
  horizontal_header->setSectionsMovable (true);
  auto vertical_header = log_view->horizontalHeader ();
  vertical_header->setResizeContentsPrecision (0); // visible region only
  vertical_header->setSectionResizeMode (QHeaderView::ResizeToContents);

  // actions
  auto delete_action = new QAction {tr ("&Delete ..."), log_view};
  log_view->insertAction (nullptr, delete_action);
  connect (delete_action, &QAction::triggered, [this] (bool /*checked*/) {
      m_->delete_QSOs ();
    });
}

void AbstractLogWindow::set_log_view_font (QFont const& font)
{
  m_->log_view_->setFont (font);
  m_->log_view_->horizontalHeader ()->setFont (font);
  m_->log_view_->verticalHeader ()->setFont (font);
  m_->model_.set_font (font);
}