swift
dbstashcomponent.cpp
1 // SPDX-FileCopyrightText: Copyright (C) 2013 swift Project Community / Contributors
2 // SPDX-License-Identifier: GPL-3.0-or-later OR LicenseRef-swift-pilot-client-1
3 
5 
6 #include <iterator>
7 
8 #include <QCheckBox>
9 #include <QMessageBox>
10 #include <QPushButton>
11 #include <QStringBuilder>
12 #include <QWidget>
13 #include <Qt>
14 #include <QtGlobal>
15 
16 #include "ui_dbstashcomponent.h"
17 
18 #include "core/application.h"
19 #include "core/db/databaseutils.h"
20 #include "core/db/databasewriter.h"
21 #include "core/webdataservices.h"
23 #include "gui/guiapplication.h"
26 #include "gui/views/viewbase.h"
28 #include "misc/aviation/livery.h"
29 #include "misc/logcategories.h"
30 #include "misc/sequence.h"
33 #include "misc/verify.h"
34 
35 using namespace swift::core;
36 using namespace swift::core::db;
37 using namespace swift::misc;
38 using namespace swift::misc::simulation;
39 using namespace swift::misc::aviation;
40 using namespace swift::misc::network;
41 using namespace swift::gui;
42 using namespace swift::gui::models;
43 using namespace swift::gui::views;
44 
45 namespace swift::gui::components
46 {
47  CDbStashComponent::CDbStashComponent(QWidget *parent)
48  : QFrame(parent), CDbMappingComponentAware(parent), ui(new Ui::CDbStashComponent)
49  {
50  ui->setupUi(this);
51 
52  connect(ui->pb_Unstash, &QPushButton::pressed, this, &CDbStashComponent::onUnstashPressed);
53  connect(ui->pb_Validate, &QPushButton::pressed, this, &CDbStashComponent::onValidatePressed);
54  connect(ui->pb_RemoveInvalid, &QPushButton::pressed, this, &CDbStashComponent::onRemoveInvalidPressed);
55  connect(ui->pb_Publish, &QPushButton::pressed, this, &CDbStashComponent::onPublishPressed);
56  connect(ui->tvp_StashAircraftModels, &CAircraftModelView::modelChanged, this,
58  connect(ui->tvp_StashAircraftModels, &CAircraftModelView::modelDataChanged, this,
59  &CDbStashComponent::onRowCountChanged);
60 
61  // copy over buttons
62  connect(ui->pb_AircraftIcao, &QPushButton::pressed, this, &CDbStashComponent::copyOverValuesToSelectedModels);
63  connect(ui->pb_AirlineIcao, &QPushButton::pressed, this, &CDbStashComponent::copyOverValuesToSelectedModels);
64  connect(ui->pb_Livery, &QPushButton::pressed, this, &CDbStashComponent::copyOverValuesToSelectedModels);
65  connect(ui->pb_Distributor, &QPushButton::pressed, this, &CDbStashComponent::copyOverValuesToSelectedModels);
66  connect(ui->pb_Model, &QPushButton::pressed, this, &CDbStashComponent::modifyModelDialog);
67 
68  ui->tvp_StashAircraftModels->setAircraftModelMode(CAircraftModelListModel::StashModel);
69  ui->tvp_StashAircraftModels->allowDragDrop(false, true, true);
70  ui->tvp_StashAircraftModels->setAcceptedMetaTypeIds();
71  ui->tvp_StashAircraftModels->menuAddItems(CAircraftModelView::MenuLoadAndSave);
72  ui->tvp_StashAircraftModels->menuAddItems(CAircraftModelView::MenuRemoveSelectedRows);
73  ui->tvp_StashAircraftModels->setHighlight(true);
74  ui->tvp_StashAircraftModels->setHighlightColor(Qt::red);
75  ui->tvp_StashAircraftModels->setSettingsDirectoryIndex(CDirectories::IndexDirLastModelStashJsonOrDefault);
76  this->enableButtonRow();
77 
78  connect(sApp->getWebDataServices()->getDatabaseWriter(), &CDatabaseWriter::publishedModels, this,
79  &CDbStashComponent::onPublishedModelsResponse, Qt::QueuedConnection);
80  this->onUserChanged();
81  }
82 
84 
86  {
87  if (!allowReplace && ui->tvp_StashAircraftModels->container().containsModelStringOrDbKey(model))
88  {
89  const QString msg("Model '%1' already stashed");
90  return CStatusMessage(validationCategories(), CStatusMessage::SeverityError,
91  msg.arg(model.getModelString()));
92  }
93  return CStatusMessage();
94  }
95 
96  CStatusMessage CDbStashComponent::stashModel(const CAircraftModel &model, bool replace, bool consolidateWithDbData,
97  bool clearHighlighting)
98  {
99  const CAircraftModel stashModel(consolidateWithDbData ? this->consolidateModel(model) : model);
100  const CStatusMessage m(this->validateStashModel(stashModel, replace));
101  if (!m.isWarningOrAbove())
102  {
103  if (clearHighlighting) { this->clearValidationHighlighting(); }
104  if (replace)
105  {
106  ui->tvp_StashAircraftModels->replaceOrAdd(&CAircraftModel::getModelString, stashModel.getModelString(),
107  stashModel);
108  }
109  else { ui->tvp_StashAircraftModels->insert(stashModel); }
110  }
111  return m;
112  }
113 
115  bool consolidateWithDbData, bool clearHighlighting)
116  {
117  if (models.isEmpty()) { return CStatusMessageList(); }
118  CStatusMessageList msgs;
119  int successfullyAdded = 0;
120  for (const CAircraftModel &model : models)
121  {
122  const CStatusMessage m(this->stashModel(model, replace, consolidateWithDbData, false));
123  if (m.isWarningOrAbove()) { msgs.push_back(m); }
124  else { successfullyAdded++; }
125  }
126  if (successfullyAdded > 0 && clearHighlighting) { this->clearValidationHighlighting(); }
127  return msgs;
128  }
129 
131  {
132  ui->tvp_StashAircraftModels->updateContainerMaybeAsync(models);
133  }
134 
135  int CDbStashComponent::unstashModels(const QSet<int> &keys)
136  {
137  if (keys.isEmpty()) { return 0; }
138  return ui->tvp_StashAircraftModels->removeDbKeys(keys);
139  }
140 
141  int CDbStashComponent::unstashModels(const QStringList &modelStrings)
142  {
143  if (modelStrings.isEmpty()) { return 0; }
144  return ui->tvp_StashAircraftModels->removeModelsWithModelString(modelStrings);
145  }
146 
148  {
149  if (models.isEmpty()) { return 0; }
150  return ui->tvp_StashAircraftModels->removeModelsWithModelString(models);
151  }
152 
153  CAircraftModelView *CDbStashComponent::view() const { return ui->tvp_StashAircraftModels; }
154 
155  bool CDbStashComponent::hasStashedModels() const { return !ui->tvp_StashAircraftModels->isEmpty(); }
156 
157  int CDbStashComponent::getStashedModelsCount() const { return ui->tvp_StashAircraftModels->rowCount(); }
158 
160  {
161  return ui->tvp_StashAircraftModels->derivedModel()->getModelStrings(false);
162  }
163 
165  {
166  return ui->tvp_StashAircraftModels->derivedModel()->container();
167  }
168 
169  CAircraftModel CDbStashComponent::getStashedModel(const QString &modelString) const
170  {
171  if (modelString.isEmpty() || ui->tvp_StashAircraftModels->isEmpty()) { return CAircraftModel(); }
172  return ui->tvp_StashAircraftModels->container().findFirstByModelStringOrDefault(modelString);
173  }
174 
175  void CDbStashComponent::applyToSelected(const CLivery &livery, bool acceptWarnings)
176  {
177  if (!ui->tvp_StashAircraftModels->hasSelection()) { return; }
178  CStatusMessageList msgs(livery.validate());
179  if (this->showOverlayMessages(msgs, acceptWarnings)) { return; }
180  ui->tvp_StashAircraftModels->applyToSelected(livery);
181  }
182 
183  void CDbStashComponent::applyToSelected(const CAircraftIcaoCode &icao, bool acceptWarnings)
184  {
185  if (!ui->tvp_StashAircraftModels->hasSelection()) { return; }
186  CStatusMessageList msgs(icao.validate());
187  if (this->showOverlayMessages(msgs, acceptWarnings)) { return; }
188  ui->tvp_StashAircraftModels->applyToSelected(icao);
189  }
190 
191  void CDbStashComponent::applyToSelected(const CAirlineIcaoCode &icao, bool acceptWarnings)
192  {
193  if (!icao.hasValidDesignator())
194  {
195  static const CStatusMessage msg(CStatusMessage::SeverityError, u"No valid designator");
196  this->showOverlayMessage(msg);
197  return;
198  }
199 
200  // retrieve the std livery
201  const CLivery stdLivery(sApp->getWebDataServices()->getStdLiveryForAirlineCode(icao));
202  if (!stdLivery.hasValidDbKey())
203  {
204  static const CStatusMessage msg(CStatusMessage::SeverityError,
205  u"No valid standard livery for " % icao.getDesignator());
206  this->showOverlayMessage(msg);
207  return;
208  }
209 
210  applyToSelected(stdLivery, acceptWarnings);
211  }
212 
213  void CDbStashComponent::applyToSelected(const CDistributor &distributor, bool acceptWarnings)
214  {
215  if (!ui->tvp_StashAircraftModels->hasSelection()) { return; }
216  CStatusMessageList msgs(distributor.validate());
217  if (this->showOverlayMessages(msgs, acceptWarnings)) { return; }
218  ui->tvp_StashAircraftModels->applyToSelected(distributor);
219  }
220 
222  {
223  if (vm.isEmpty()) { return; }
224  if (!ui->tvp_StashAircraftModels->hasSelection()) { return; }
225  ui->tvp_StashAircraftModels->applyToSelected(vm);
226  }
227 
228  void CDbStashComponent::onUnstashPressed() { ui->tvp_StashAircraftModels->removeSelectedRows(); }
229 
230  void CDbStashComponent::onValidatePressed()
231  {
232  if (ui->tvp_StashAircraftModels->isEmpty()) { return; }
233  CAircraftModelList validModels;
234  CAircraftModelList invalidModels;
235  this->validateAndDisplay(validModels, invalidModels, true);
236  }
237 
238  void CDbStashComponent::onRemoveInvalidPressed()
239  {
240  if (ui->tvp_StashAircraftModels->isEmpty()) { return; }
241  CAircraftModelList validModels;
242  CAircraftModelList invalidModels;
243  this->validate(validModels, invalidModels);
244  this->unstashModels(invalidModels);
245  }
246 
247  void CDbStashComponent::onPublishPressed()
248  {
249  if (!sGui || sGui->isShuttingDown() || !sGui->hasWebDataServices()) { return; }
250  if (ui->tvp_StashAircraftModels->isEmpty()) { return; }
251  if (!sGui->hasMinimumMappingVersion()) { return; }
252 
253  // get models right here, because later steps might affect selection
254  const CAircraftModelList models(getSelectedOrAllModels());
255  if (models.isEmpty()) { return; }
256 
257  // validate
258  CAircraftModelList validModels;
259  CAircraftModelList invalidModels;
260  if (!this->validateAndDisplay(validModels, invalidModels)) { return; }
261  CStatusMessageList msgs;
262  if (validModels.size() > MaxModelPublished)
263  {
264  validModels.truncate(MaxModelPublished);
265  msgs.push_back(CStatusMessage(validationCategories(), CStatusMessage::SeverityWarning,
266  u"More than %1 values, values skipped")
267  << MaxModelPublished);
268  }
269 
270  msgs.push_back(sGui->getWebDataServices()->asyncPublishModels(validModels));
271  if (msgs.hasWarningOrErrorMessages()) { this->showOverlayMessages(msgs); }
272  else { ui->tvp_StashAircraftModels->showLoadIndicator(); }
273  }
274 
275  void CDbStashComponent::onPublishedModelsResponse(const CAircraftModelList &publishedModels,
276  const CAircraftModelList &skippedModels,
277  const CStatusMessageList &msgs, bool sendingSuccesful,
278  bool directWrite)
279  {
280  Q_UNUSED(skippedModels);
281  ui->tvp_StashAircraftModels->hideLoadIndicator();
282  if (!publishedModels.isEmpty() && sendingSuccesful)
283  {
284  emit this->modelsSuccessfullyPublished(publishedModels, directWrite);
285  }
286 
287  if (!msgs.isEmpty())
288  {
289  if (publishedModels.isEmpty()) { this->showOverlayMessages(msgs, false, false); }
290  else
291  {
292  QPointer<CDbStashComponent> myself(this);
293  const QString confirm("Remove %1 published models from stash?");
294  auto lambda = [=]() {
295  if (!myself) { return; }
296  myself->unstashModels(publishedModels.getModelStringList(false));
297  };
298  this->showOverlayMessagesWithConfirmation(msgs, false, confirm.arg(publishedModels.size()), lambda,
299  QMessageBox::Ok);
300  }
301  }
302  }
303 
304  CStatusMessageList CDbStashComponent::validate(CAircraftModelList &validModels,
305  CAircraftModelList &invalidModels) const
306  {
307  if (ui->tvp_StashAircraftModels->isEmpty()) { return CStatusMessageList(); }
308  Q_ASSERT_X(sGui->getWebDataServices(), Q_FUNC_INFO, "No web services");
309  const CAircraftModelList models(getSelectedOrAllModels());
310  if (models.isEmpty()) { return CStatusMessageList(); }
311  const bool ignoreEqual = ui->cb_ChangedOnly->isChecked();
312  const CStatusMessageList msgs(
313  sGui->getWebDataServices()->validateForPublishing(models, ignoreEqual, validModels, invalidModels));
314 
315  // OK?
316  if (msgs.isEmpty())
317  {
318  return CStatusMessageList(
319  { CStatusMessage(validationCategories(), CStatusMessage::SeverityInfo, u"No errors in %1 model(s)")
320  << models.size() });
321  }
322  else { return msgs; }
323  }
324 
325  bool CDbStashComponent::validateAndDisplay(CAircraftModelList &validModels, CAircraftModelList &invalidModels,
326  bool displayInfo)
327  {
328  const CStatusMessageList msgs(this->validate(validModels, invalidModels));
329  if (msgs.hasWarningOrErrorMessages())
330  {
331  this->showOverlayMessages(msgs);
332  ui->tvp_StashAircraftModels->setHighlightModelStrings(invalidModels.getModelStringList(false));
333  }
334  else
335  {
336  // delete highlighting because no errors
337  ui->tvp_StashAircraftModels->clearHighlighting();
338  if (displayInfo)
339  {
340  const QString no = QString::number(this->getStashedModelsCount());
341  const CStatusMessage msg(validationCategories(), CStatusMessage::SeverityInfo,
342  "Validation passed for " + no + " models");
343  this->showOverlayMessage(msg);
344  }
345  }
346  return !validModels.isEmpty(); // at least some valid objects
347  }
348 
349  void CDbStashComponent::enableButtonRow()
350  {
351  const bool e = !ui->tvp_StashAircraftModels->isEmpty();
352  ui->pb_AircraftIcao->setEnabled(e);
353  ui->pb_AirlineIcao->setEnabled(e);
354  ui->pb_Distributor->setEnabled(e);
355  ui->pb_Livery->setEnabled(e);
356  ui->pb_Unstash->setEnabled(e);
357  ui->pb_Validate->setEnabled(e);
358  ui->pb_RemoveInvalid->setEnabled(e);
359  ui->pb_Model->setEnabled(e);
360  ui->pb_Publish->setEnabled(e);
361  this->onUserChanged();
362  }
363 
364  const CLogCategoryList &CDbStashComponent::validationCategories() const
365  {
366  static const CLogCategoryList cats(CLogCategoryList(this).withValidation());
367  return cats;
368  }
369 
370  CAircraftModelList CDbStashComponent::getSelectedOrAllModels() const
371  {
372  const bool selectedOnly = ui->cb_SelectedOnly->isChecked();
373  const CAircraftModelList models(selectedOnly ? ui->tvp_StashAircraftModels->selectedObjects() :
374  ui->tvp_StashAircraftModels->containerOrFilteredContainer());
375  return models;
376  }
377 
378  CAircraftModel CDbStashComponent::consolidateWithDbData(const CAircraftModel &model, bool forced) const
379  {
380  const CAircraftModel consolidatedModel = CDatabaseUtils::consolidateModelWithDbData(model, forced);
381  return consolidatedModel;
382  }
383 
384  CAircraftModel CDbStashComponent::consolidateWithOwnModels(const CAircraftModel &model) const
385  {
386  if (!model.hasModelString()) { return model; }
387  if (model.getModelType() == CAircraftModel::TypeOwnSimulatorModel) { return model; }
388  CAircraftModel ownModel(this->getMappingComponent()->getOwnModelForModelString(model.getModelString()));
389  if (!ownModel.hasModelString()) { return model; }
390  ownModel.updateMissingParts(model);
391  return ownModel;
392  }
393 
394  CAuthenticatedUser CDbStashComponent::getSwiftDbUser() const { return m_swiftDbUser.get(); }
395 
397  {
398  CAircraftModel stashModel(model);
399  const bool ownModel = stashModel.getModelType() == CAircraftModel::TypeOwnSimulatorModel;
400 
401  // merge/update with DB data if any
402  // this is a forced update with DB data, as DB data can change
403  stashModel = this->consolidateWithDbData(stashModel, true);
404 
405  // merge with own models if any
406  if (!ownModel) { stashModel = this->consolidateWithOwnModels(stashModel); }
407 
408  return stashModel;
409  }
410 
412  {
413  if (!sGui || !sGui->hasWebDataServices()) { return; }
414  if (sGui->isShuttingDown()) { return; }
415  const CAircraftModelList models = ui->tvp_StashAircraftModels->selectedObjects();
416  if (models.isEmpty()) { return; }
417 
418  CStatusMessageList msgs;
419  for (const CAircraftModel &model : models)
420  {
421  CStatusMessageList modelMsgs;
422  const bool equal = sGui->getWebDataServices()->isDbModelEqualForPublishing(model, &modelMsgs);
423  if (equal)
424  {
425  msgs.push_back(CStatusMessage(this).info(u"Model '%1' has no change values")
426  << model.getModelStringAndDbKey());
427  }
428  else { msgs.push_back(modelMsgs); }
429  }
430  this->showOverlayMessages(msgs);
431  }
432 
433  void CDbStashComponent::clearValidationHighlighting() { ui->tvp_StashAircraftModels->clearHighlighting(); }
434 
435  void CDbStashComponent::copyOverValuesToSelectedModels()
436  {
437  const QObject *sender = QObject::sender();
438  SWIFT_VERIFY_X(this->getMappingComponent(), Q_FUNC_INFO, "Missing mapping component");
439  if (!this->getMappingComponent()) { return; }
440  if (!ui->tvp_StashAircraftModels->hasSelection()) { return; }
441 
442  const CAircraftModel model(this->getMappingComponent()->getEditorAircraftModel());
443  if (sender == ui->pb_AircraftIcao) { this->applyToSelected(model.getAircraftIcaoCode()); }
444  else if (sender == ui->pb_AirlineIcao) { this->applyToSelected(model.getAirlineIcaoCode()); }
445  else if (sender == ui->pb_Distributor) { this->applyToSelected(model.getDistributor()); }
446  else if (sender == ui->pb_Livery) { this->applyToSelected(model.getLivery()); }
447  }
448 
449  void CDbStashComponent::modifyModelDialog()
450  {
451  if (this->getMappingComponent()) { this->getMappingComponent()->modifyModelDialog(); }
452  }
453 
454  void CDbStashComponent::onRowCountChanged(int number, bool filter)
455  {
456  Q_UNUSED(number);
457  Q_UNUSED(filter);
458  this->enableButtonRow();
459  }
460 
461  void CDbStashComponent::onUserChanged()
462  {
463  const CAuthenticatedUser user(this->getSwiftDbUser());
464  if (!user.isAuthenticated())
465  {
466  ui->pb_Publish->setText(" Publish (login) ");
467  ui->pb_Publish->setToolTip("Login first");
468  ui->pb_Publish->setEnabled(false);
469  }
470  else if (user.canDirectlyWriteModels())
471  {
472  ui->pb_Publish->setText(" Publish (dir.) ");
473  ui->pb_Publish->setToolTip("Models directly released");
474  ui->pb_Publish->setEnabled(true);
475  }
476  else
477  {
478  ui->pb_Publish->setText(" Publish (CR) ");
479  ui->pb_Publish->setToolTip("Models published as change request");
480  ui->pb_Publish->setEnabled(true);
481  }
482  }
483 
484  bool CDbStashComponent::showOverlayMessages(const CStatusMessageList &msgs, bool onlyErrors, bool appendOldMessages,
485  std::chrono::milliseconds timeout)
486  {
487  if (msgs.isEmpty()) { return false; }
488  if (!msgs.hasErrorMessages() && onlyErrors) { return false; }
489  SWIFT_VERIFY_X(this->getMappingComponent(), Q_FUNC_INFO, "missing mapping component");
490  if (!this->getMappingComponent()) { return false; }
491 
492  this->getMappingComponent()->showOverlayMessages(msgs, appendOldMessages, timeout);
493  return true;
494  }
495 
496  bool CDbStashComponent::showOverlayMessagesWithConfirmation(const CStatusMessageList &msgs, bool appendOldMessages,
497  const QString &confirmation,
498  std::function<void()> okLambda,
499  QMessageBox::StandardButton defaultButton,
500  bool onlyErrors, std::chrono::milliseconds timeout)
501  {
502  if (msgs.isEmpty()) { return false; }
503  if (!msgs.hasErrorMessages() && onlyErrors) { return false; }
504  SWIFT_VERIFY_X(this->getMappingComponent(), Q_FUNC_INFO, "missing mapping component");
505  if (!this->getMappingComponent()) { return false; }
506  this->getMappingComponent()->showOverlayMessagesWithConfirmation(msgs, appendOldMessages, confirmation,
507  okLambda, defaultButton, timeout);
508  return true;
509  }
510 
511  bool CDbStashComponent::showOverlayMessage(const CStatusMessage &msg, std::chrono::milliseconds timeout)
512  {
513  if (msg.isEmpty()) { return false; }
514  SWIFT_VERIFY_X(this->getMappingComponent(), Q_FUNC_INFO, "missing mapping component");
515  if (!this->getMappingComponent()) { return false; }
516  this->getMappingComponent()->showOverlayMessage(msg, timeout);
517  return true;
518  }
519 
520  void CDbStashComponent::clearOverlayMessages()
521  {
522  SWIFT_VERIFY_X(this->getMappingComponent(), Q_FUNC_INFO, "missing mapping component");
523  if (!this->getMappingComponent()) { return; }
525  }
526 } // namespace swift::gui::components
SWIFT_CORE_EXPORT swift::core::CApplication * sApp
Single instance of application object.
Definition: application.cpp:71
bool hasWebDataServices() const
Web data services available?
bool isShuttingDown() const
Is application shutting down?
CWebDataServices * getWebDataServices() const
Get the web data services.
swift::misc::CStatusMessageList asyncPublishModels(const swift::misc::simulation::CAircraftModelList &modelsToBePublished) const
Publish models to database.
db::CDatabaseWriter * getDatabaseWriter() const
DB writer class.
swift::misc::aviation::CLivery getStdLiveryForAirlineCode(const swift::misc::aviation::CAirlineIcaoCode &icao) const
Standard livery for airline code.
bool isDbModelEqualForPublishing(const swift::misc::simulation::CAircraftModel &modelToBeChecked, swift::misc::CStatusMessageList *details=nullptr) const
Considered equal for publishing, compares if livery etc. are the same DB values.
swift::misc::CStatusMessageList validateForPublishing(const swift::misc::simulation::CAircraftModelList &modelsToBePublished, bool ignoreEqual, swift::misc::simulation::CAircraftModelList &validModels, swift::misc::simulation::CAircraftModelList &invalidModels) const
Validate for publishing.
bool hasMinimumMappingVersion() const
Minimum mapping version check.
void clearOverlayMessages()
Clear the overlay messages.
bool showOverlayMessage(const swift::misc::CStatusMessage &message, std::chrono::milliseconds timeout=std::chrono::milliseconds(0))
Show single message.
void showOverlayMessages(const swift::misc::CStatusMessageList &messages, bool appendOldMessages=false, std::chrono::milliseconds timeout=std::chrono::milliseconds(0))
Show multiple messages.
void showOverlayMessagesWithConfirmation(const swift::misc::CStatusMessageList &messages, bool appendOldMessages, const QString &confirmationMessage, std::function< void()> okLambda, QMessageBox::StandardButton defaultButton=QMessageBox::Cancel, std::chrono::milliseconds timeout=std::chrono::milliseconds(0))
Show multiple messages with confirmation bar.
Allows subcomponents to gain access to model component.
CDbMappingComponent * getMappingComponent() const
Get the mapping component.
void modifyModelDialog()
Open model modify dialog.
static constexpr int MaxModelPublished
Number of models which can be published at once.
void stashedModelsChanged()
Stashed models have been changed.
void showChangedAttributes()
Show changed attributes of selected models.
int unstashModels(const QSet< int > &keys)
Unstash given models with keys.
int getStashedModelsCount() const
Number of models.
swift::misc::simulation::CAircraftModel getStashedModel(const QString &modelString) const
Model for model string.
swift::gui::views::CAircraftModelView * view() const
The embedded view.
void applyToSelected(const swift::misc::aviation::CLivery &livery, bool acceptWarnings=true)
Apply livery to selected objects.
bool hasStashedModels() const
Has stashed models.
swift::misc::CStatusMessage stashModel(const swift::misc::simulation::CAircraftModel &model, bool replace=false, bool consolidateWithDbData=true, bool clearHighlighting=true)
Stash given model (includes validation and consolidation with DB data)
swift::misc::CStatusMessage validateStashModel(const swift::misc::simulation::CAircraftModel &model, bool allowReplace) const
Test the given model if it can be stashed.
swift::misc::simulation::CAircraftModel consolidateModel(const swift::misc::simulation::CAircraftModel &model) const
Consolidate with other available data.
const swift::misc::simulation::CAircraftModelList & getStashedModels() const
The stashed models.
void modelsSuccessfullyPublished(const swift::misc::simulation::CAircraftModelList &publishedModels, bool directWrite)
Models succesfully published.
swift::misc::CStatusMessageList stashModels(const swift::misc::simulation::CAircraftModelList &models, bool replace=false, bool consolidateWithDbData=true, bool clearHighlighting=true)
Stash given models (includes validation and consolidation with DB data)
void clearValidationHighlighting()
Clear highlighting set by validations.
void replaceModelsUnvalidated(const swift::misc::simulation::CAircraftModelList &models)
Replace models, no validation.
QStringList getStashedModelStrings() const
Stashed model strings.
T get() const
Get a copy of the current value.
Definition: valuecache.h:408
A sequence of log categories.
bool isEmpty() const
Message empty.
Specialized value object compliant map for variants, based on indexes.
size_type size() const
Returns number of elements in the sequence.
Definition: sequence.h:273
void truncate(size_type maxSize)
Changes the size of the sequence, if it is bigger than the given size.
Definition: sequence.h:291
void push_back(const T &value)
Appends an element at the end of the sequence.
Definition: sequence.h:305
bool isEmpty() const
Synonym for empty.
Definition: sequence.h:285
Streamable status message, e.g.
bool isWarningOrAbove() const
Warning or above.
Status messages, e.g. from Core -> GUI.
bool hasWarningOrErrorMessages() const
Warning or error messages.
bool hasErrorMessages() const
Error messages.
Value object for ICAO classification.
CStatusMessageList validate() const
Validate data.
Value object for ICAO classification.
const QString & getDesignator() const
Get airline, e.g. "DLH".
bool hasValidDesignator() const
Airline designator available?
Value object encapsulating information about an airpot.
Definition: livery.h:29
CStatusMessageList validate() const
Validate data.
Definition: livery.cpp:128
bool hasValidDbKey() const
Has valid DB key.
Definition: datastore.h:102
Value object encapsulating information of an authentiated user.
Aircraft model (used by another pilot, my models on disk)
Definition: aircraftmodel.h:71
const aviation::CAirlineIcaoCode & getAirlineIcaoCode() const
Airline ICAO code.
const aviation::CLivery & getLivery() const
Get livery.
const QString & getModelString() const
Model key, either queried or loaded from simulator model.
const CDistributor & getDistributor() const
Get distributor.
const aviation::CAircraftIcaoCode & getAircraftIcaoCode() const
Aircraft ICAO code.
ModelType getModelType() const
Model type.
QString getModelStringAndDbKey() const
Model string and DB key (if available)
bool hasModelString() const
Non empty model string?
void updateMissingParts(const CAircraftModel &otherModel, bool dbModelPriority=true)
Update missing parts from another model.
Value object encapsulating a list of aircraft models.
QStringList getModelStringList(bool sort=true) const
Model strings.
Value object encapsulating information of software distributor.
Definition: distributor.h:33
swift::misc::CStatusMessageList validate() const
Validate data.
SWIFT_GUI_EXPORT swift::gui::CGuiApplication * sGui
Single instance of GUI application object.
Classes interacting with the swift database (aka "datastore").
Backend services of the swift project, like dealing with the network or the simulators.
Definition: actionbind.cpp:7
High level reusable GUI components.
Definition: aboutdialog.cpp:13
Models to be used with views, mainly QTableView.
Views, mainly QTableView.
GUI related classes.
Free functions in swift::misc.
#define SWIFT_VERIFY_X(COND, WHERE, WHAT)
A weaker kind of assert.
Definition: verify.h:26