##// END OF EJS Templates
Variable update signal forwards variable ID...
jeandet -
r32:6b6270b07547
parent child
Show More
@@ -1,112 +1,113
1 1 #ifndef SCIQLOP_VARIABLE_H
2 2 #define SCIQLOP_VARIABLE_H
3 3
4 4 #include <optional>
5 5
6 6 #include <QLoggingCategory>
7 7 #include <QObject>
8 8 #include <QUuid>
9 9 #include <QReadWriteLock>
10 10 #include <QDataStream>
11 11
12 12 #include "CoreGlobal.h"
13 13 #include <Data/DataSeriesIterator.h>
14 14 #include <Data/DataSeriesType.h>
15 15 #include <Data/DateTimeRange.h>
16 16
17 17
18 18 #include <Common/deprecate.h>
19 19 #include <Common/MetaTypes.h>
20 20 #include <Common/spimpl.h>
21 21
22 22 Q_DECLARE_LOGGING_CATEGORY(LOG_Variable)
23 23
24 24 class IDataSeries;
25 25 class QString;
26 26
27 27 /**
28 28 * @brief The Variable class represents a variable in SciQlop.
29 29 */
30 30 class SCIQLOP_CORE_EXPORT Variable : public QObject {
31 31
32 32 Q_OBJECT
33 33
34 34 public:
35 35 explicit Variable(const QString &name, const QVariantHash &metadata = {});
36 36
37 37 /// Copy ctor
38 38 explicit Variable(const Variable &other);
39 39
40 40 std::shared_ptr<Variable> clone() const;
41 41
42 42 QString name() const noexcept;
43 43 void setName(const QString &name) noexcept;
44 44 DateTimeRange range() const noexcept;
45 45 void setRange(const DateTimeRange &range, bool notify=false) noexcept;
46 46 DateTimeRange cacheRange() const noexcept;
47 47 void setCacheRange(const DateTimeRange &cacheRange) noexcept;
48 48
49 49 /// @return the number of points hold by the variable. The number of points is updated each time
50 50 /// the data series changes
51 51 unsigned int nbPoints() const noexcept;
52 52
53 53 /// Returns the real range of the variable, i.e. the min and max x-axis values of the data
54 54 /// series between the range of the variable. The real range is updated each time the variable
55 55 /// range or the data series changed
56 56 /// @return the real range, invalid range if the data series is null or empty
57 57 /// @sa setDataSeries()
58 58 /// @sa setRange()
59 59 std::optional<DateTimeRange> realRange() const noexcept;
60 60
61 61 /// @return the data of the variable, nullptr if there is no data
62 62 std::shared_ptr<IDataSeries> dataSeries() const noexcept;
63 63
64 64 /// @return the type of data that the variable holds
65 65 DataSeriesType type() const noexcept;
66 66
67 67 QVariantHash metadata() const noexcept;
68 68
69 69 void updateData(const std::vector<IDataSeries*>& dataSeries,
70 70 const DateTimeRange& newRange, const DateTimeRange& newCacheRange,
71 71 bool notify=true);
72 72
73 73 static QByteArray mimeData(const std::vector<std::shared_ptr<Variable> > &variables)
74 74 {
75 75 auto encodedData = QByteArray{};
76 76 QDataStream stream{&encodedData, QIODevice::WriteOnly};
77 77 for (auto &var : variables) {
78 78 stream << var->ID().toByteArray();
79 79 }
80 80 return encodedData;
81 81 }
82 82
83 83 static std::vector<QUuid> variablesIDs(QByteArray mimeData)
84 84 {
85 85 std::vector<QUuid> variables;
86 86 QDataStream stream{mimeData};
87 87
88 88 QVariantList ids;
89 89 stream >> ids;
90 90
91 91 for (const auto& id : ids) {
92 92 variables.emplace_back (id.toByteArray());
93 93 }
94 94 return variables;
95 95 }
96 96
97 97 operator QUuid() {return _uuid;}
98 98 QUuid ID(){return _uuid;}
99 99 signals:
100 void updated();
101 private:
102 class VariablePrivate;
100 void updated(QUuid ID);
101
102 private:
103 class VariablePrivate;
103 104 spimpl::unique_impl_ptr<VariablePrivate> impl;
104 105 QUuid _uuid;
105 106 QReadWriteLock m_lock;
106 107 };
107 108
108 109 // Required for using shared_ptr in signals/slots
109 110 SCIQLOP_REGISTER_META_TYPE(VARIABLE_PTR_REGISTRY, std::shared_ptr<Variable>)
110 111 SCIQLOP_REGISTER_META_TYPE(VARIABLE_PTR_VECTOR_REGISTRY, QVector<std::shared_ptr<Variable> >)
111 112
112 113 #endif // SCIQLOP_VARIABLE_H
@@ -1,68 +1,68
1 1 #ifndef SCIQLOP_VARIABLEMODEL2_H
2 2 #define SCIQLOP_VARIABLEMODEL2_H
3 3
4 4 #include "CoreGlobal.h"
5 5
6 6 #include <Data/DateTimeRange.h>
7 7
8 8 #include <QAbstractTableModel>
9 9 #include <QLoggingCategory>
10 10
11 11 #include <Common/MetaTypes.h>
12 12 #include <Common/spimpl.h>
13 13
14 14
15 15
16 16 class IDataSeries;
17 17 class Variable;
18 18 class VariableController2;
19 19
20 20 enum VariableRoles { ProgressRole = Qt::UserRole };
21 21
22 22 /**
23 23 * @brief The VariableModel class aims to hold the variables that have been created in SciQlop
24 24 */
25 25 class SCIQLOP_CORE_EXPORT VariableModel2 : public QAbstractTableModel {
26 26 Q_OBJECT
27 27 // read only mirror of VariableController2 content
28 28 std::vector<std::shared_ptr<Variable>> _variables;
29 29 public:
30 30 explicit VariableModel2(QObject *parent = nullptr);
31 31
32 32 // /////////////////////////// //
33 33 // QAbstractTableModel methods //
34 34 // /////////////////////////// //
35 35
36 36 virtual int columnCount(const QModelIndex &parent = QModelIndex{}) const override;
37 37 virtual int rowCount(const QModelIndex &parent = QModelIndex{}) const override;
38 38 virtual QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
39 39 virtual QVariant headerData(int section, Qt::Orientation orientation,
40 40 int role = Qt::DisplayRole) const override;
41 41 virtual Qt::ItemFlags flags(const QModelIndex &index) const override;
42 42
43 43 // ///////////////// //
44 44 // Drag&Drop methods //
45 45 // ///////////////// //
46 46
47 47 virtual Qt::DropActions supportedDropActions() const override;
48 48 virtual Qt::DropActions supportedDragActions() const override;
49 49 virtual QStringList mimeTypes() const override;
50 50 virtual QMimeData *mimeData(const QModelIndexList &indexes) const override;
51 51 virtual bool canDropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column,
52 52 const QModelIndex &parent) const override;
53 53 virtual bool dropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column,
54 54 const QModelIndex &parent) override;
55 55 const std::vector<std::shared_ptr<Variable>>& variables() const
56 56 {return _variables;}
57 57
58 58 signals:
59 59 void createVariable(const QVariantHash &productData);
60 60 void asyncChangeRange(const std::shared_ptr<Variable>& variable, const DateTimeRange& r);
61 61 public slots:
62 62 /// Slot called when data of a variable has been updated
63 void variableUpdated() noexcept;
63 void variableUpdated(QUuid id) noexcept;
64 64 void variableAdded(const std::shared_ptr<Variable>&);
65 65 void variableDeleted(const std::shared_ptr<Variable>&);
66 66 };
67 67
68 68 #endif // SCIQLOP_VARIABLEMODEL2_H
@@ -1,214 +1,212
1 1 #include <optional>
2 2 #include <QMutex>
3 3 #include <QReadWriteLock>
4 4 #include <QThread>
5 5
6 6 #include "Variable/Variable.h"
7 7
8 8 #include <Data/IDataSeries.h>
9 9 #include <Data/DateTimeRange.h>
10 10
11 11 #include <Common/debug.h>
12 12
13 13 Q_LOGGING_CATEGORY(LOG_Variable, "Variable")
14 14
15 15
16 16 /**
17 17 * Searches in metadata for a value that can be converted to DataSeriesType
18 18 * @param metadata the metadata where to search
19 19 * @return the value converted to a DataSeriesType if it was found, UNKNOWN type otherwise
20 20 * @sa DataSeriesType
21 21 */
22 22 static DataSeriesType findDataSeriesType(const QVariantHash &metadata)
23 23 {
24 24 auto dataSeriesType = DataSeriesType::UNKNOWN;
25 25
26 26 // Go through the metadata and stop at the first value that could be converted to DataSeriesType
27 27 for (auto it = metadata.cbegin(), end = metadata.cend();
28 28 it != end && dataSeriesType == DataSeriesType::UNKNOWN; ++it) {
29 29 dataSeriesType = DataSeriesTypeUtils::fromString(it.value().toString());
30 30 }
31 31
32 32 return dataSeriesType;
33 33 }
34 34
35 35
36 36 #define VP_PROPERTY(property,getter,setter,type) \
37 37 type getter() noexcept\
38 38 {\
39 39 QReadLocker lock{&m_Lock};\
40 40 return property;\
41 41 }\
42 42 void setter(const type& getter) noexcept\
43 43 {\
44 44 QWriteLocker lock{&m_Lock};\
45 45 property = getter;\
46 46 }\
47 47 type property;\
48 48
49 49 #define V_FW_GETTER_SETTER(getter,setter, type)\
50 50 type Variable::getter() const noexcept \
51 51 {\
52 52 return impl->getter();\
53 53 }\
54 54 void Variable::setter(const type& getter) noexcept \
55 55 {\
56 56 impl->setter(getter);\
57 emit updated();\
57 emit updated(this->ID());\
58 58 }\
59 59
60 60 struct Variable::VariablePrivate {
61 61 explicit VariablePrivate(const QString &name, const QVariantHash &metadata)
62 62 : m_Name{name},
63 63 m_Range{INVALID_RANGE},
64 64 m_CacheRange{INVALID_RANGE},
65 65 m_Metadata{metadata},
66 66 m_DataSeries{nullptr},
67 67 m_RealRange{INVALID_RANGE},
68 68 m_NbPoints{0},
69 69 m_Type{findDataSeriesType(m_Metadata)}
70 70 {
71 71 }
72 72
73 73 VariablePrivate(const VariablePrivate &other)
74 74 : m_Name{other.m_Name},
75 75 m_Range{other.m_Range},
76 76 m_CacheRange{other.m_CacheRange},
77 77 m_Metadata{other.m_Metadata},
78 78 m_DataSeries{other.m_DataSeries != nullptr ? other.m_DataSeries->clone() : nullptr},
79 79 m_RealRange{other.m_RealRange},
80 80 m_NbPoints{other.m_NbPoints},
81 81 m_Type{findDataSeriesType(m_Metadata)}
82 82 {
83 83 }
84 84
85 85 void lockRead() { m_Lock.lockForRead(); }
86 86 void lockWrite() { m_Lock.lockForWrite(); }
87 87 void unlock() { m_Lock.unlock(); }
88 88
89 89 void purgeDataSeries()
90 90 {
91 91 if (m_DataSeries) {
92 92 m_DataSeries->purge(m_CacheRange.m_TStart, m_CacheRange.m_TEnd);
93 93 }
94 94 updateRealRange();
95 95 updateNbPoints();
96 96 }
97 97 void mergeDataSeries(const std::vector<IDataSeries*>& dataseries)
98 98 {
99 99 QWriteLocker lock{&m_Lock};
100 100 for(auto ds:dataseries)
101 101 {
102 102 if(m_DataSeries)
103 103 m_DataSeries->merge(ds);
104 104 else
105 105 m_DataSeries = ds->clone();
106 106 }
107 107 }
108 108 void updateNbPoints() { m_NbPoints = m_DataSeries ? m_DataSeries->nbPoints() : 0; }
109 109
110 110 /// Updates real range according to current variable range and data series
111 111 void updateRealRange()
112 112 {
113 113 if (m_DataSeries) {
114 114 auto lock = m_DataSeries->getReadLock();
115 115 auto end = m_DataSeries->cend();
116 116 auto minXAxisIt = m_DataSeries->minXAxisData(m_Range.m_TStart);
117 117 auto maxXAxisIt = m_DataSeries->maxXAxisData(m_Range.m_TEnd);
118 118 if(minXAxisIt != end && maxXAxisIt != end && minXAxisIt->x() <= maxXAxisIt->x())
119 119 m_RealRange = DateTimeRange{minXAxisIt->x(), maxXAxisIt->x()};
120 120 else
121 121 m_RealRange = std::nullopt;
122 122 }
123 123 else {
124 124 m_RealRange = std::nullopt;
125 125 }
126 126 }
127 127
128 128 VP_PROPERTY(m_Name, name, setName, QString)
129 129 VP_PROPERTY(m_Range, range, setRange, DateTimeRange)
130 130 VP_PROPERTY(m_CacheRange, cacheRange, setCacheRange, DateTimeRange)
131 131 VP_PROPERTY(m_Metadata, metadata, setMetadata, QVariantHash)
132 132 VP_PROPERTY(m_DataSeries, dataSeries, setDataSeries, std::shared_ptr<IDataSeries>)
133 133 VP_PROPERTY(m_RealRange, realRange, setRealRange, std::optional<DateTimeRange>)
134 134 unsigned int m_NbPoints;
135 135 VP_PROPERTY(m_Type, type, setType, DataSeriesType)
136 136 QReadWriteLock m_Lock;
137 137 };
138 138
139 139 Variable::Variable(const QString &name, const QVariantHash &metadata)
140 140 : impl{spimpl::make_unique_impl<VariablePrivate>(name, metadata)},
141 141 _uuid{QUuid::createUuid()}
142 142 {
143 143 }
144 144
145 145 Variable::Variable(const Variable &other)
146 146 : impl{spimpl::make_unique_impl<VariablePrivate>(*other.impl)},
147 147 _uuid{QUuid::createUuid()} //is a clone but must have a != uuid
148 148 {
149 149 }
150 150
151 151 std::shared_ptr<Variable> Variable::clone() const
152 152 {
153 153 return std::make_shared<Variable>(*this);
154 154 }
155 155
156 156 V_FW_GETTER_SETTER(name,setName,QString)
157 157
158 158 DateTimeRange Variable::range() const noexcept
159 159 {
160 160 return impl->range();
161 161 }
162 162
163 163 void Variable::setRange(const DateTimeRange &range, bool notify) noexcept
164 164 {
165 165 impl->setRange(range);
166 166 impl->updateRealRange();
167 167 if(notify)
168 emit this->updated();
168 emit this->updated(this->ID());
169 169 }
170 170
171 171 V_FW_GETTER_SETTER(cacheRange, setCacheRange, DateTimeRange)
172 172
173 173 unsigned int Variable::nbPoints() const noexcept
174 174 {
175 175 return impl->m_NbPoints;
176 176 }
177 177
178 178 std::optional<DateTimeRange> Variable::realRange() const noexcept
179 179 {
180 180 return impl->realRange();
181 181 }
182 182
183 183 void Variable::updateData(const std::vector<IDataSeries *> &dataSeries, const DateTimeRange &newRange, const DateTimeRange &newCacheRange, bool notify)
184 184 {
185 185 {
186 186 QWriteLocker lock{&m_lock};
187 187 impl->mergeDataSeries(dataSeries);
188 188 impl->setRange(newRange);
189 189 impl->setCacheRange(newCacheRange);
190 190 impl->purgeDataSeries();
191 191 }
192 192 if(notify)
193 emit updated();
193 emit updated(this->ID());
194 194 }
195 195
196
197 196 std::shared_ptr<IDataSeries> Variable::dataSeries() const noexcept
198 197 {
199 198 return impl->dataSeries();
200 199 }
201 200
202 201 DataSeriesType Variable::type() const noexcept
203 202 {
204 203 return impl->type();
205 204 }
206 205
207 206 QVariantHash Variable::metadata() const noexcept
208 207 {
209 208 impl->lockRead();
210 209 auto metadata = impl->m_Metadata;
211 210 impl->unlock();
212 211 return metadata;
213 212 }
214
@@ -1,270 +1,270
1 1 #include <QMimeData>
2 2 #include <QSize>
3 3 #include <QTimer>
4 4 #include <unordered_map>
5 5
6 6 #include <Variable/Variable.h>
7 7 #include <Variable/VariableController2.h>
8 8 #include <Variable/VariableModel2.h>
9 9
10 10 #include <Common/DateUtils.h>
11 11 #include <Common/MimeTypesDef.h>
12 12 #include <Common/StringUtils.h>
13 13 #include <Common/containers.h>
14 14
15 15 #include <Data/IDataSeries.h>
16 16
17 17 #include <DataSource/DataSourceController.h>
18 18 #include <Time/TimeController.h>
19 19
20 20 namespace {
21 21
22 22 // Column indexes
23 23 const auto NAME_COLUMN = 0;
24 24 const auto TSTART_COLUMN = 1;
25 25 const auto TEND_COLUMN = 2;
26 26 const auto NBPOINTS_COLUMN = 3;
27 27 const auto UNIT_COLUMN = 4;
28 28 const auto MISSION_COLUMN = 5;
29 29 const auto PLUGIN_COLUMN = 6;
30 30 const auto NB_COLUMNS = 7;
31 31
32 32 // Column properties
33 33 const auto DEFAULT_HEIGHT = 25;
34 34 const auto DEFAULT_WIDTH = 100;
35 35
36 36 struct ColumnProperties {
37 37 ColumnProperties(const QString &name = {}, int width = DEFAULT_WIDTH,
38 38 int height = DEFAULT_HEIGHT)
39 39 : m_Name{name}, m_Width{width}, m_Height{height}
40 40 {
41 41 }
42 42
43 43 QString m_Name;
44 44 int m_Width;
45 45 int m_Height;
46 46 };
47 47
48 48 const auto COLUMN_PROPERTIES = QHash<int, ColumnProperties>{
49 49 {NAME_COLUMN, {QObject::tr("Name")}}, {TSTART_COLUMN, {QObject::tr("tStart"), 180}},
50 50 {TEND_COLUMN, {QObject::tr("tEnd"), 180}}, {NBPOINTS_COLUMN, {QObject::tr("Nb points")}},
51 51 {UNIT_COLUMN, {QObject::tr("Unit")}}, {MISSION_COLUMN, {QObject::tr("Mission")}},
52 52 {PLUGIN_COLUMN, {QObject::tr("Plugin")}}};
53 53
54 54 QString uniqueName(const QString &defaultName,
55 55 const std::vector<std::shared_ptr<Variable> > &variables)
56 56 {
57 57 auto forbiddenNames = std::vector<QString>(variables.size());
58 58 std::transform(variables.cbegin(), variables.cend(), forbiddenNames.begin(),
59 59 [](const auto &variable) { return variable->name(); });
60 60 auto uniqueName = StringUtils::uniqueName(defaultName, forbiddenNames);
61 61 Q_ASSERT(!uniqueName.isEmpty());
62 62
63 63 return uniqueName;
64 64 }
65 65
66 66 } // namespace
67 67
68 68
69 69
70 70 VariableModel2::VariableModel2(QObject *parent)
71 71 : QAbstractTableModel{parent}
72 72 {
73 73 }
74 74
75 75
76 76 int VariableModel2::columnCount(const QModelIndex &parent) const
77 77 {
78 78 Q_UNUSED(parent);
79 79
80 80 return NB_COLUMNS;
81 81 }
82 82
83 83 int VariableModel2::rowCount(const QModelIndex &parent) const
84 84 {
85 85 Q_UNUSED(parent);
86 86 return _variables.size();
87 87 }
88 88
89 89 QVariant VariableModel2::data(const QModelIndex &index, int role) const
90 90 {
91 91 if (!index.isValid()) {
92 92 return QVariant{};
93 93 }
94 94
95 95 if (index.row() < 0 || index.row() >= rowCount()) {
96 96 return QVariant{};
97 97 }
98 98
99 99 if (role == Qt::DisplayRole) {
100 100 if (auto variable = _variables[index.row()]) {
101 101 switch (index.column()) {
102 102 case NAME_COLUMN:
103 103 return variable->name();
104 104 case TSTART_COLUMN: {
105 105 if(auto range = variable->realRange(); range.has_value())
106 106 return DateUtils::dateTime(range.value().m_TStart).toString(DATETIME_FORMAT);
107 107 return QVariant{};
108 108 }
109 109 case TEND_COLUMN: {
110 110 if(auto range = variable->realRange(); range.has_value())
111 111 return DateUtils::dateTime(range.value().m_TEnd).toString(DATETIME_FORMAT);
112 112 return QVariant{};
113 113 }
114 114 case NBPOINTS_COLUMN:
115 115 return variable->nbPoints();
116 116 case UNIT_COLUMN:
117 117 return variable->metadata().value(QStringLiteral("units"));
118 118 case MISSION_COLUMN:
119 119 return variable->metadata().value(QStringLiteral("mission"));
120 120 case PLUGIN_COLUMN:
121 121 return variable->metadata().value(QStringLiteral("plugin"));
122 122 default:
123 123 // No action
124 124 break;
125 125 }
126 126 }
127 127 }
128 128 else if (role == VariableRoles::ProgressRole) {
129 129 return QVariant{};
130 130 }
131 131
132 132 return QVariant{};
133 133 }
134 134
135 135 QVariant VariableModel2::headerData(int section, Qt::Orientation orientation, int role) const
136 136 {
137 137 if (role != Qt::DisplayRole && role != Qt::SizeHintRole) {
138 138 return QVariant{};
139 139 }
140 140
141 141 if (orientation == Qt::Horizontal) {
142 142 auto propertiesIt = COLUMN_PROPERTIES.find(section);
143 143 if (propertiesIt != COLUMN_PROPERTIES.cend()) {
144 144 // Role is either DisplayRole or SizeHintRole
145 145 return (role == Qt::DisplayRole)
146 146 ? QVariant{propertiesIt->m_Name}
147 147 : QVariant{QSize{propertiesIt->m_Width, propertiesIt->m_Height}};
148 148 }
149 149 }
150 150
151 151 return QVariant{};
152 152 }
153 153
154 154 Qt::ItemFlags VariableModel2::flags(const QModelIndex &index) const
155 155 {
156 156 return QAbstractTableModel::flags(index) | Qt::ItemIsDragEnabled | Qt::ItemIsDropEnabled;
157 157 }
158 158
159 159 Qt::DropActions VariableModel2::supportedDropActions() const
160 160 {
161 161 return Qt::CopyAction | Qt::MoveAction;
162 162 }
163 163
164 164 Qt::DropActions VariableModel2::supportedDragActions() const
165 165 {
166 166 return Qt::CopyAction | Qt::MoveAction;
167 167 }
168 168
169 169 QStringList VariableModel2::mimeTypes() const
170 170 {
171 171 return {MIME_TYPE_VARIABLE_LIST, MIME_TYPE_TIME_RANGE};
172 172 }
173 173
174 174 QMimeData *VariableModel2::mimeData(const QModelIndexList &indexes) const
175 175 {
176 176 auto mimeData = new QMimeData;
177 177 std::vector<std::shared_ptr<Variable> > variables;
178 178
179 179 DateTimeRange firstTimeRange;
180 180 for (const auto &index : indexes) {
181 181 if (index.column() == 0) { // only the first column
182 182 auto variable = _variables[index.row()];
183 183 if (variable.get() && index.isValid()) {
184 184
185 185 if (variables.size()==0) {
186 186 // Gets the range of the first variable
187 187 firstTimeRange = variable->range();
188 188 }
189 189 variables.push_back(variable);
190 190 }
191 191 }
192 192 }
193 193
194 194 auto variablesEncodedData = Variable::mimeData(variables);
195 195 mimeData->setData(MIME_TYPE_VARIABLE_LIST, variablesEncodedData);
196 196
197 197 if (variables.size() == 1) {
198 198 // No time range MIME data if multiple variables are dragged
199 199 auto timeEncodedData = TimeController::mimeDataForTimeRange(firstTimeRange);
200 200 mimeData->setData(MIME_TYPE_TIME_RANGE, timeEncodedData);
201 201 }
202 202
203 203 return mimeData;
204 204 }
205 205
206 206 bool VariableModel2::canDropMimeData(const QMimeData *data, Qt::DropAction action, int row,
207 207 int column, const QModelIndex &parent) const
208 208 {
209 209 Q_UNUSED(column);
210 210 // drop of a product
211 211 return data->hasFormat(MIME_TYPE_PRODUCT_LIST)
212 212 || (data->hasFormat(MIME_TYPE_TIME_RANGE) && parent.isValid()
213 213 && !data->hasFormat(MIME_TYPE_VARIABLE_LIST));
214 214 }
215 215
216 216 bool VariableModel2::dropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column,
217 217 const QModelIndex &parent)
218 218 {
219 219 auto dropDone = false;
220 220
221 221 if (data->hasFormat(MIME_TYPE_PRODUCT_LIST)) {
222 222 auto productList
223 223 = DataSourceController::productsDataForMimeData(data->data(MIME_TYPE_PRODUCT_LIST));
224 224
225 225 for (auto metaData : productList) {
226 226 emit createVariable(metaData.toHash());
227 227 }
228 228
229 229 dropDone = true;
230 230 }
231 231 else if (data->hasFormat(MIME_TYPE_TIME_RANGE) && parent.isValid()) {
232 232 auto variable = _variables[parent.row()];
233 233 auto range = TimeController::timeRangeForMimeData(data->data(MIME_TYPE_TIME_RANGE));
234 234
235 235 emit asyncChangeRange(variable, range);
236 236
237 237 dropDone = true;
238 238 }
239 239
240 240 return dropDone;
241 241 }
242 242
243 void VariableModel2::variableUpdated() noexcept
243 void VariableModel2::variableUpdated(QUuid id) noexcept
244 244 {
245 245 emit dataChanged(QModelIndex(),QModelIndex());
246 246 }
247 247
248 248 void VariableModel2::variableAdded(const std::shared_ptr<Variable> & variable)
249 249 {
250 250 if(!SciQLop::containers::contains(_variables,variable))
251 251 {
252 252 beginInsertRows(QModelIndex(), this->_variables.size(), this->_variables.size());
253 253 this->_variables.push_back(variable);
254 254 endInsertRows();
255 255 connect(variable.get(),&Variable::updated,this,&VariableModel2::variableUpdated);
256 256 }
257 257 }
258 258
259 259 void VariableModel2::variableDeleted(const std::shared_ptr<Variable> &variable)
260 260 {
261 261 auto it = std::find(_variables.begin(), _variables.end(), variable);
262 262 if (it != _variables.end())
263 263 {
264 264 auto index = std::distance(_variables.begin(), it);
265 265 beginRemoveRows(QModelIndex(), index, index);
266 266 _variables.erase(it);
267 267 endRemoveRows();
268 268 }
269 269 }
270 270
General Comments 0
You need to be logged in to leave comments. Login now