StateParameterEditor.cpp
Go to the documentation of this file.
1 /*
2  * This file is part of ArmarX.
3  *
4  * Copyright (C) 2011-2016, High Performance Humanoid Technologies (H2T), Karlsruhe Institute of Technology (KIT), all rights reserved.
5  *
6  * ArmarX is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 as
8  * published by the Free Software Foundation.
9  *
10  * ArmarX is distributed in the hope that it will be useful, but
11  * WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program. If not, see <http://www.gnu.org/licenses/>.
17  *
18  * @package
19  * @author
20  * @date
21  * @copyright http://www.gnu.org/licenses/gpl-2.0.txt
22  * GNU General Public License
23  */
24 #include "StateParameterEditor.h"
25 
26 #include <QComboBox>
27 #include <QCompleter>
28 #include <QDialog>
29 #include <QDialogButtonBox>
30 #include <QInputDialog>
31 #include <QLabel>
32 #include <QLineEdit>
33 #include <QMessageBox>
34 #include <QPushButton>
35 #include <QStyledItemDelegate>
36 #include <QTextEdit>
37 #include <QToolButton>
38 #include <QVBoxLayout>
39 
40 #include <Ice/ObjectFactory.h>
41 
45 
47 
48 using namespace armarx;
49 
51  QTableWidget(parent), defaultValueState(Qt::Unchecked)
52 {
53  // For jsonobject double/float serilization on german/spanish pcs....
54  setlocale(LC_ALL, "C");
55 
56  setColumnCount(6);
57  qRegisterMetaType<StateParameterMap>("StateParameterMap");
58  qRegisterMetaType<std::map<QString, std::pair<QString, QString>>>(
59  "std::map<QString,std::pair<QString,QString> >");
60  connect(
61  this,
62  SIGNAL(buildRequested(StateParameterMap, std::map<QString, std::pair<QString, QString>>)),
63  this,
64  SLOT(__buildFromMap(StateParameterMap, std::map<QString, std::pair<QString, QString>>)),
65  Qt::QueuedConnection);
66  setHeaders();
67 
68  if (params.size() == 0)
69  {
71  }
72  else
73  {
74  buildFromMap(params);
75  }
76 
77 
78  setItemDelegateForColumn(eKey, &delegate);
79 }
80 
81 void
82 StateParameterEditor::setKeyBlackList(const QSet<QString>& keyBlackList)
83 {
84  this->keyBlackList = keyBlackList;
85 }
86 
87 QSet<QString>
89 {
90  QSet<QString> result;
91 
92  for (int row = 0; row < rowCount(); row++)
93  {
94  if (item(row, eKey) && !item(row, eKey)->text().isEmpty())
95  {
96  result.insert(item(row, eKey)->text());
97  }
98  }
99 
100  return result;
101 }
102 
103 StateParameterIceBasePtr
105 {
106  if (getKey(row).isEmpty())
107  {
108  return NULL;
109  }
110 
111  StateParameterIceBasePtr param = StateParameter::create();
112  param->defaultValue = getVariantContainer(row);
113  param->optionalParam = getIsOptional(row);
114  param->set = false;
115  return param;
116 }
117 
120 {
121  StateParameterMap result;
122 
123  for (int row = 0; row < rowCount(); ++row)
124  {
125  auto param = getStateParameter(row);
126 
127  if (param)
128  {
129  result[getKey(row).toStdString()] = param;
130  }
131  }
132 
133  return result;
134 }
135 
136 //StateParameterMap StateParameterEditor::getStateParametersWithoutValue()
137 //{
138 // StateParameterMap result;
139 // for (int row = 0; row < rowCount(); ++row) {
140 // StateParameterIceBasePtr param = new StateParameterIceBase();
141 //if(getKey(row).length() == 0)
142 // continue;
143 
144 // }
145 //}
146 
147 StringVariantContainerBaseMap
149 {
150  StringVariantContainerBaseMap result;
151 
152  for (int row = 0; row < rowCount(); ++row)
153  {
154  // StateParameterIceBasePtr param = new StateParameter();
155  if (getKey(row).length() == 0)
156  {
157  continue;
158  }
159 
160  VariantContainerBasePtr con = getVariantContainer(row);
161  result[getKey(row).toStdString()] = con;
162  }
163 
164  return result;
165 }
166 
167 QString
169 {
170  if (row >= rowCount())
171  {
172  throw LocalException("row index out of range: ") << row;
173  }
174 
175  QLineEdit* valueEdit = qobject_cast<QLineEdit*>(cellWidget(row, eValue));
176 
177  if (!valueEdit)
178  {
179  throw LocalException("value edit ptr is NULL");
180  }
181 
182  return valueEdit->text();
183 }
184 
185 QString
187 {
188  int row = -1;
189 
190  for (int i = 0; i < rowCount(); i++)
191  {
192  if (getKey(i) == key)
193  {
194  row = i;
195  break;
196  }
197  }
198 
199  if (row == -1)
200  {
201  throw LocalException("row index out of range: ") << row;
202  }
203 
204  if (row >= rowCount())
205  {
206  throw LocalException("row index out of range: ") << row;
207  }
208 
209  VariantContainerBasePtr container;
210 
211  QString type = getType(row);
212  QLineEdit* valueEdit = qobject_cast<QLineEdit*>(cellWidget(row, eValue));
213  QPushButton* editButton = qobject_cast<QPushButton*>(cellWidget(row, eValue));
214 
215 
216  JSONObjectPtr jsonObject = new JSONObject(communicator);
217 
218  if (valueEdit && valueEdit->isEnabled())
219  {
220  int typeId = Variant::hashTypeName(type.toStdString());
221  Variant variant;
222 
223  if (typeId == VariantType::Int)
224  {
225  variant.setInt(valueEdit->text().toInt());
226  }
227  else if (typeId == VariantType::Long)
228  {
229  variant.setLong(valueEdit->text().toLong());
230  }
231 
232  else if (typeId == VariantType::Bool)
233  if (valueEdit->text() == "true" || valueEdit->text() == "1")
234  {
235  variant.setBool(true);
236  }
237  else
238  {
239  variant.setBool(false);
240  }
241 
242  else if (typeId == VariantType::Float)
243  {
244  variant.setFloat(valueEdit->text().toFloat());
245  }
246  else if (typeId == VariantType::Double)
247  {
248  variant.setDouble(valueEdit->text().toDouble());
249  }
250 
251  else if (typeId == VariantType::String)
252  {
253  variant.setString(valueEdit->text().trimmed().toStdString());
254  }
255 
256  container = new SingleVariant(variant);
257  jsonObject->serializeIceObject(container);
258  return QString::fromUtf8(jsonObject->toString().c_str());
259  }
260  else if (editButton && editButton->isEnabled())
261  {
262  QString jsonValue = editButton->property("JsonValue").toString();
263  return jsonValue;
264  }
265 
266  // else
267  // throw LocalException("Neither QLineEdit nor QPushButton found!");
268  return "";
269 }
270 
271 VariantContainerBasePtr
273 {
274  if (row >= rowCount())
275  {
276  throw LocalException("row index out of range: ") << row;
277  }
278 
279  VariantContainerBasePtr result;
280 
281  QString type = getType(row);
282  QLineEdit* valueEdit = qobject_cast<QLineEdit*>(cellWidget(row, eValue));
283  QPushButton* editButton = qobject_cast<QPushButton*>(cellWidget(row, eValue));
284 
285  if ((valueEdit && valueEdit->isEnabled()) || item(row, eValue))
286  {
287  int typeId = Variant::hashTypeName(type.toStdString());
288  Variant variant;
289  QString valueStr = valueEdit ? valueEdit->text() : item(row, eValue)->text();
290 
291  if (typeId == VariantType::Int)
292  {
293  variant.setInt(valueStr.toInt());
294  }
295  else if (typeId == VariantType::Long)
296  {
297  variant.setLong(valueStr.toLong());
298  }
299 
300  else if (typeId == VariantType::Bool)
301  if (valueStr.compare("true", Qt::CaseInsensitive) == 0 || valueStr == "1")
302  {
303  variant.setBool(true);
304  }
305  else
306  {
307  variant.setBool(false);
308  }
309 
310  else if (typeId == VariantType::Float)
311  {
312  variant.setFloat(valueStr.toFloat());
313  }
314  else if (typeId == VariantType::Double)
315  {
316  variant.setDouble(valueStr.toDouble());
317  }
318 
319  else if (typeId == VariantType::String)
320  {
321  variant.setString(valueStr.trimmed().toStdString());
322  }
323 
324  result = new SingleVariant(variant);
325  }
326  else if (editButton && editButton->isEnabled())
327  {
328  QString jsonValue = editButton->property("JsonValue").toString();
329 
330  if (jsonValue.isEmpty())
331  {
332  return result;
333  }
334 
335  JSONObjectPtr jsonObject = new JSONObject(communicator);
336  // ARMARX_INFO_S << VAROUT(jsonValue.toUtf8().data());
337  jsonObject->fromString(jsonValue.toUtf8().data());
338 
339  try
340  {
341  SerializablePtr obj = jsonObject->deserializeIceObject();
342  result = VariantContainerBasePtr::dynamicCast(obj);
343 
344  if (!result)
345  {
346  // must be simple variant
347  result = new SingleVariant(Variant(VariantDataPtr::dynamicCast(obj)));
348  }
349  }
350  catch (std::exception& e)
351  {
352  ARMARX_WARNING_S << "JSON string for type " << type.toStdString()
353  << " could not be deserialized: " << e.what();
354  return result;
355  }
356  }
357 
358  return result;
359 }
360 
361 QString
363 {
364  if (row >= rowCount())
365  {
366  throw LocalException("row index out of range: ") << row;
367  }
368 
369  if (!item(row, eKey))
370  {
371  return "";
372  }
373 
374  return item(row, eKey)->text();
375 }
376 
377 QString
379 {
380  if (row >= rowCount())
381  {
382  throw LocalException("row index out of range: ") << row;
383  }
384 
385  QComboBox* CBvalueType = qobject_cast<QComboBox*>(cellWidget(row, 1));
386 
387  if (!CBvalueType)
388  {
389  return "";
390  }
391 
392  QString type = getBaseNameFromHumanName(CBvalueType->currentText()); //@@@
393  return type;
394 }
395 
396 QString
398 {
399  int row = getRow(key);
400  return getType(row);
401 }
402 
403 int
404 StateParameterEditor::getRow(const QString& key) const
405 {
406  int row = -1;
407 
408  for (int i = 0; i < rowCount(); i++)
409  {
410  if (getKey(i) == key)
411  {
412  row = i;
413  break;
414  }
415  }
416 
417  if (row == -1)
418  {
419  throw LocalException("could not find key ") << key.toStdString();
420  }
421 
422  return row;
423 }
424 
425 bool
427 {
428  if (row >= rowCount())
429  {
430  throw LocalException("row index out of range: ") << row;
431  }
432 
433  QComboBox* cbOptional = qobject_cast<QComboBox*>(cellWidget(row, eOptional));
434  return cbOptional->currentText() == "true";
435 }
436 
437 int
439 {
440  // ARMARX_IMPORTANT_S << "Adding row";
441  int row = rowCount();
442  insertRow(row);
443  setItem(row, eKey, new QTableWidgetItem());
444 
445  setItem(row, eProvideDefaultValue, new QTableWidgetItem());
446  item(row, eProvideDefaultValue)->setFlags(Qt::ItemIsEnabled | Qt::ItemIsUserCheckable);
447  item(row, eProvideDefaultValue)->setCheckState(defaultValueState);
448 
449  QComboBox* valueTypebox = new QComboBox;
450  valueTypebox->setEditable(true);
451  // valueTypebox->setInsertPolicy(QComboBox::InsertAlphabetically);
452  // valueTypebox->setValidator(new QIntValidator(this));
453  setCellWidget(row, eType, valueTypebox);
454  addVariantTypesToComboBox(valueTypebox);
455  QCompleter* fullCompleter = new QCompleter(valueTypebox->model(), this);
456  fullCompleter->setCompletionMode(QCompleter::PopupCompletion);
457  fullCompleter->setCaseSensitivity(Qt::CaseSensitive);
458  valueTypebox->setCompleter(fullCompleter);
459  valueTypebox->setEditText("string");
460  connect(valueTypebox, SIGNAL(editTextChanged(QString)), this, SLOT(typeCbChanged(QString)));
461  //valueTypebox->model()->sort(0);
462  QComboBox* cbOptional;
463  cbOptional = new QComboBox();
464  cbOptional->addItems(QString("true;false").split(";"));
465  cbOptional->setCurrentIndex(1);
466  setCellWidget(row, eOptional, cbOptional);
467 
468 
469  QIcon icon;
470  icon.addFile(QString::fromUtf8(":/icons/dialog-close.ico"), QSize(), QIcon::Normal, QIcon::Off);
471  QToolButton* deleteButton = new QToolButton(this);
472  deleteButton->setIcon(icon);
473  deleteButton->setToolTip("Delete this row");
474  setCellWidget(row, eDeleteButton, deleteButton);
475  connect(deleteButton, SIGNAL(clicked()), this, SLOT(deleteRow()));
476  emit rowAdded(row);
477  return row;
478 }
479 
480 void
482  QString variantIdStr,
483  QString value,
484  bool optional)
485 {
486  int row = addParameterRow();
487 
488  item(row, eKey)->setText(key);
489 
490  QComboBox* valueTypeBox = qobject_cast<QComboBox*>(cellWidget(row, eType));
491  // ARMARX_INFO_S << "type id: " << variantIdStr.toStdString() << " size: " << valueTypeBox->count();
492  valueTypeBox->setEditText(getHumanNameFromBaseName(variantIdStr));
493 
494  QComboBox* optionalBox = qobject_cast<QComboBox*>(cellWidget(row, eOptional));
495 
496  if (optional)
497  {
498  optionalBox->setCurrentIndex(0);
499  }
500  else
501  {
502  optionalBox->setCurrentIndex(1);
503  }
504 
505  if (!value.isEmpty())
506  {
507  item(row, eProvideDefaultValue)->setCheckState(Qt::Checked);
508  }
509 
510  int variantId = Variant::hashTypeName(variantIdStr.toStdString());
511 
512  if (variantId == VariantType::String || variantId == VariantType::Int ||
513  variantId == VariantType::Long || variantId == VariantType::Bool ||
514  variantId == VariantType::Float || variantId == VariantType::Double)
515  {
516  QLineEdit* valueEdit = new QLineEdit;
517 
518  if (item(row, eProvideDefaultValue)->checkState() == Qt::Unchecked)
519  {
520  valueEdit->setEnabled(false);
521  }
522 
523  setCellWidget(row, eValue, valueEdit);
524 
525  if (variantId == VariantType::String)
526  {
527  if (value.at(0) == '\"')
528  {
529  value.remove(0, 1);
530  }
531 
532  if (value.at(value.length() - 1) == '\"')
533  {
534  value.remove(value.length() - 1, 1);
535  }
536 
537  value = value.replace("\\\"", "\"").replace("\\\\", "\\");
538  }
539 
540  valueEdit->setText(value);
541  }
542  else
543  {
544  createValueButton(row, value);
545  }
546 
547  emit rowFilled(row, key);
548 }
549 
550 void
551 StateParameterEditor::createValueButton(int row, const QString& jsonValue)
552 {
553  // ARMARX_INFO_S << VAROUT(row) << VAROUT(jsonValue.toStdString());
554  QComboBox* typeBox = qobject_cast<QComboBox*>(cellWidget(row, eType));
555 
556  QString typeString = getBaseNameFromHumanName(typeBox->currentText()); //@@@
557  QWidget* oldWidget = qobject_cast<QWidget*>(cellWidget(row, eValue));
558 
559  if (oldWidget)
560  {
561  oldWidget->hide();
562  }
563 
564  QPushButton* editValueButton = new QPushButton("Edit");
565 
566  if (item(row, eProvideDefaultValue)->checkState() == Qt::Unchecked)
567  {
568  editValueButton->setEnabled(false);
569  }
570 
571  setCellWidget(row, eValue, editValueButton);
572 
573  try
574  {
575  if (jsonValue.isEmpty())
576  {
577  auto variantContainerType = VariantContainerType::FromString(typeString.toStdString());
578  JSONObjectPtr jsonObject = new JSONObject(communicator);
579 
580  // ARMARX_INFO_S << VAROUT(variantContainerType->typeId);
581 
582  Ice::ValueFactoryPtr factory =
583  communicator->getValueFactoryManager()->find(variantContainerType->typeId);
584 
585  if (factory)
586  {
587  Ice::ValuePtr objectPtr = factory->create(variantContainerType->typeId);
588 
589  VariantDataPtr var = VariantDataPtr::dynamicCast(objectPtr);
590 
591  if (!var)
592  {
593  // TODO: make better with dummy element function for all containers/variants?!
594  // ARMARX_INFO_S << VAROUT(variantContainerType->subType->typeId);
595  Ice::ValueFactoryPtr subfactory = communicator->getValueFactoryManager()->find(
596  variantContainerType->subType->typeId);
597 
598  if (!subfactory)
599  {
600  // ARMARX_INFO_S << " no factory";
601  subfactory = IceInternal::factoryTable->getValueFactory(
602  variantContainerType->subType->typeId);
603  }
604 
605  if (subfactory)
606  {
607  Ice::ValuePtr subObj =
608  subfactory->create(variantContainerType->subType->typeId);
609  VariantDataPtr var = VariantDataPtr::dynamicCast(subObj);
610 
611  if (!var)
612  {
613  }
614 
616  SingleTypeVariantListPtr::dynamicCast(objectPtr);
617 
618  if (var && list)
619  {
620  list->addVariant(Variant(var));
621  }
622 
623  StringValueMapPtr map = StringValueMapPtr::dynamicCast(objectPtr);
624 
625  if (var && map)
626  {
627  map->addVariant("mykey", Variant(var));
628  }
629  }
630  else
631  {
632  ARMARX_INFO_S << " no base factory";
633  }
634  }
635 
636  jsonObject->serializeIceObject(SerializablePtr::dynamicCast(objectPtr));
637  }
638 
639  editValueButton->setProperty("JsonValue",
640  QString::fromStdString(jsonObject->asString(true)));
641  }
642  else
643  {
644  editValueButton->setProperty("JsonValue", jsonValue);
645  }
646 
647  connect(editValueButton, SIGNAL(clicked()), this, SLOT(editDefaultButtonClicked()));
648  }
649  catch (...)
650  {
652  editValueButton->setEnabled(false);
653  }
654 }
655 
656 void
657 StateParameterEditor::typeCbChanged(const QString& /*text*/)
658 {
659  QWidget* wid = qobject_cast<QWidget*>(sender());
660 
661  /*QModelIndex mIndex =*/indexAt(
662  wid->pos()); // Some strange bug happens here: If this is used, it will deliver on table creation zero
663  // If indexAt is not called, wid->pos() delivers a 0,0 Point and then rowAt() also return wrong index
664  // ARMARX_INFO_S << VAROUT(wid->pos()) << VAROUT(rowAt(wid->pos().y()));
665 
666  int row = rowAt(wid->pos().y());
667 
668  QWidget* valueWidget = cellWidget(row, eValue);
669 
670  QComboBox* typeBox = qobject_cast<QComboBox*>(cellWidget(row, eType));
671  std::string typeStr = getBaseNameFromHumanName(typeBox->currentText()).toStdString(); //@@@
672  int typeId = Variant::hashTypeName(typeStr);
673 
674  if (typeId == VariantType::String || typeId == VariantType::Int ||
675  typeId == VariantType::Long || typeId == VariantType::Bool ||
676  typeId == VariantType::Float || typeId == VariantType::Double)
677  {
678  QLineEdit* valueLineEdit = qobject_cast<QLineEdit*>(valueWidget);
679 
680  if (!valueLineEdit)
681  {
682  valueLineEdit = new QLineEdit;
683  setCellWidget(row, eValue, valueLineEdit);
684  }
685 
686  if (item(row, eProvideDefaultValue)->checkState() == Qt::Unchecked)
687  {
688  valueLineEdit->setEnabled(false);
689  }
690 
691  if (typeId == VariantType::String)
692  {
693  valueLineEdit->setValidator(NULL);
694  }
695  else if (typeId == VariantType::Int || typeId == VariantType::Long)
696  {
697  valueLineEdit->setValidator(new QIntValidator(this));
698  }
699  else if (typeId == VariantType::Bool)
700  {
701  QRegExp rx("((1|0)|(true|false))");
702  QValidator* validator = new QRegExpValidator(rx, this);
703  valueLineEdit->setValidator(validator);
704  }
705  else if (typeId == VariantType::Float || typeId == VariantType::Double)
706  {
707  valueLineEdit->setValidator(new QDoubleValidator(this));
708  }
709 
710  QString value = valueLineEdit->text();
711  int pos;
712 
713  if (valueLineEdit->validator() &&
714  valueLineEdit->validator()->validate(value, pos) != QValidator::Acceptable)
715  {
716  valueLineEdit->setText("");
717  }
718  }
719  else
720  {
721  createValueButton(row, "");
722  }
723 }
724 
725 void
727 {
728  int row;
729  QWidget* wid = qobject_cast<QWidget*>(sender());
730  QModelIndex mIndex = indexAt(wid->pos());
731  row = mIndex.row();
732 
733  disconnect(this);
734  removeRow(row);
735 
736  if (rowCount() == 0)
737  {
738  addParameterRow();
739  }
740 
741  connectUserEditSlots();
742 }
743 
744 void
746 {
747  // ARMARX_IMPORTANT_S << "checking row: " << row << ", " << column;
748 
749  if (column == eProvideDefaultValue)
750  {
751  if (item(row, eProvideDefaultValue)->checkState() == Qt::Unchecked)
752  {
753  QWidget* valueWidget = cellWidget(row, eValue);
754  QWidget* valueLineEdit = qobject_cast<QWidget*>(valueWidget);
755 
756  if (valueLineEdit)
757  {
758  valueLineEdit->setEnabled(false);
759  }
760  }
761  else
762  {
763  QWidget* valueWidget = cellWidget(row, eValue);
764  QWidget* valueLineEdit = qobject_cast<QWidget*>(valueWidget);
765 
766  if (valueLineEdit)
767  {
768  valueLineEdit->setEnabled(true);
769  }
770  }
771  }
772  else if (column == eKey)
773  {
774  auto keyitem = item(row, eKey);
775 
776  if (keyitem)
777  {
778  if ((keyBlackList.find(keyitem->text()) != keyBlackList.end() ||
779  findItems(keyitem->text(), Qt::MatchExactly).size() > 1))
780  {
781  keyitem->setText(item(row, eKey)->text() + "_2");
783  << "Keys must be unique (input and local parameters share the same key pool)";
784  }
785  }
786  }
787 
788  if (row >= rowCount() - 1 && item(rowCount() - 1, 0) &&
789  !item(rowCount() - 1, 0)->text().isEmpty())
790  {
791  addParameterRow();
792  }
793 }
794 
795 void
797 {
798  for (int row = 0; row < rowCount(); row++)
799  {
800  QComboBox* valueTypeBox = qobject_cast<QComboBox*>(cellWidget(row, eType));
801  addVariantTypesToComboBox(valueTypeBox);
802  // valueTypeBox->model()->sort(0);
803  }
804 }
805 
806 void
808 {
809  QDialog editDefaultDialog;
810  editDefaultDialog.setWindowTitle("Statechart Parameter Complex Value Editor");
811  editDefaultDialog.resize(QSize(600, 400));
812  QTextEdit* dialogTextEdit = new QTextEdit();
813  dialogTextEdit->setAcceptRichText(false);
814  dialogTextEdit->setPlainText(sender()->property("JsonValue").toString());
815 
816  QVBoxLayout* layout = new QVBoxLayout;
817  layout->addWidget(dialogTextEdit);
818  QDialogButtonBox* buttonBox = new QDialogButtonBox(dialogTextEdit);
819  buttonBox->setOrientation(Qt::Horizontal);
820  buttonBox->setStandardButtons(QDialogButtonBox::Cancel | QDialogButtonBox::Ok);
821  layout->addWidget(buttonBox);
822  editDefaultDialog.setLayout(layout);
823 
824  connect(buttonBox, SIGNAL(accepted()), &editDefaultDialog, SLOT(accept()));
825  connect(buttonBox, SIGNAL(rejected()), &editDefaultDialog, SLOT(reject()));
826 
827  if (editDefaultDialog.exec() == QDialog::Accepted)
828  {
829  sender()->setProperty("JsonValue", dialogTextEdit->toPlainText());
830  }
831 }
832 
833 void
834 StateParameterEditor::connectUserEditSlots()
835 {
836  connect(this,
837  SIGNAL(cellEntered(int, int)),
838  this,
839  SLOT(checkAndUpdateRowCount(int, int)),
840  Qt::UniqueConnection);
841  connect(this,
842  SIGNAL(cellPressed(int, int)),
843  this,
844  SLOT(checkAndUpdateRowCount(int, int)),
845  Qt::UniqueConnection);
846  connect(this,
847  SIGNAL(cellChanged(int, int)),
848  this,
849  SLOT(checkAndUpdateRowCount(int, int)),
850  Qt::UniqueConnection);
851 }
852 
853 void
854 StateParameterEditor::addVariantTypesToComboBox(QComboBox* combo)
855 {
856  if (!combo)
857  {
858  return;
859  }
860 
861  combo->clear();
862 
863  QList<QString> list;
864 
865  for (std::pair<VariantTypeId, std::string> pair : Variant::getTypes())
866  {
867  QString typeName = tr(pair.second.c_str());
868  //QString humanName = tr(Variant::getHumanName(pair->first).c_str());
869 
870  if (typeName.contains("Invalid"))
871  {
872  continue;
873  }
874 
875  list.append(getHumanNameFromBaseName(typeName));
876  /*if(combo->findText(typeName) == -1)
877  {
878  combo->addItem(getHumanNameFromBaseName(typeName));
879  }*/
880  }
881 
882  std::vector<VariantContainerType> containers;
883  containers.push_back(VariantType::List);
884  containers.push_back(VariantType::Map);
885 
886  for (VariantContainerType c : containers)
887  {
888  for (auto it : Variant::getTypes())
889  {
890  QString typeName = tr(it.second.c_str());
891 
892 
893  if (typeName.contains("Invalid"))
894  {
895  continue;
896  }
897 
898  std::string typeStr = VariantContainerType::allTypesToString(c(it.first).clone());
899  typeName = QString::fromStdString(typeStr);
900  list.append(getHumanNameFromBaseName(typeName));
901  /*if(combo->findText(typeName) == -1)
902  {
903  combo->addItem(getHumanNameFromBaseName(typeName));
904  }*/
905  }
906  }
907 
908  qSort(list.begin(), list.end(), compareVariantNames);
909  combo->addItems(list);
910 }
911 
912 QString
913 StateParameterEditor::getHumanNameFromBaseName(QString variantBaseTypeName) const
914 {
915  if (!variantInfo)
916  {
917  return variantBaseTypeName;
918  }
919 
920  std::string humanName =
921  variantInfo->getNestedHumanNameFromBaseName(variantBaseTypeName.toUtf8().data());
922 
923  if (humanName.empty())
924  {
925  return variantBaseTypeName;
926  }
927 
928  return QString::fromUtf8(humanName.c_str());
929 }
930 
931 QString
932 StateParameterEditor::getBaseNameFromHumanName(QString humanName) const
933 {
934  if (!variantInfo)
935  {
936  return humanName;
937  }
938 
939  std::string variantBaseTypeName =
940  variantInfo->getNestedBaseNameFromHumanName(humanName.toUtf8().data());
941 
942  if (variantBaseTypeName.empty())
943  {
944  return humanName;
945  }
946 
947  return QString::fromUtf8(variantBaseTypeName.c_str());
948 }
949 
950 bool
951 StateParameterEditor::compareVariantNames(const QString& a, const QString& b)
952 {
953  bool pa, pb;
954 
955  // list nested types after basic ones
956  pa = a.contains("(");
957  pb = b.contains("(");
958 
959  if (pa != pb)
960  {
961  return pb;
962  }
963 
964  // list human types before non resolved ones
965  pa = a.contains(":");
966  pb = b.contains(":");
967 
968  if (pa != pb)
969  {
970  return pb;
971  }
972 
973  // lower case (basic types) first
974  pa = a.count() > 0 && a[0].isLower();
975  pb = b.count() > 0 && b[0].isLower();
976 
977  if (pa != pb)
978  {
979  return pa;
980  }
981 
982  return a.compare(b) < 0;
983 }
984 
985 Qt::CheckState
987 {
988  return defaultValueState;
989 }
990 
991 void
993 {
994  defaultValueState = value;
995 }
996 
997 void
999 {
1000  setHorizontalHeaderLabels(QString("Key;Type;Optional;Def;Value;Del").split(";"));
1001  setColumnWidth(eKey, 180);
1002  setColumnWidth(eType, 225);
1003  setColumnWidth(eOptional, 70);
1004  setColumnWidth(eProvideDefaultValue, 29);
1005  setColumnWidth(eValue, 200);
1006  setColumnWidth(eDeleteButton, 25);
1007 }
1008 
1009 void
1011  const StateParameterMap& map,
1012  const std::map<QString, std::pair<QString, QString>>& jsonStringMap)
1013 {
1014  emit buildRequested(map, jsonStringMap);
1015 }
1016 
1017 void
1018 StateParameterEditor::__buildFromMap(
1019  const StateParameterMap& map,
1020  const std::map<QString, std::pair<QString, QString>>& jsonStringMap)
1021 {
1022  clearContents();
1023  QWidget* tempW = new QLabel("mylabel", this);
1024  tempW->deleteLater();
1025  setRowCount(0);
1026  // disconnect(this);
1027  disconnect(this, SIGNAL(cellEntered(int, int)));
1028  disconnect(this, SIGNAL(cellPressed(int, int)));
1029  disconnect(this, SIGNAL(cellChanged(int, int)));
1030  StateParameterMap::const_iterator it = map.begin();
1031 
1032  for (; it != map.end(); it++)
1033  {
1034  StateParameterIceBasePtr p = it->second;
1035  JSONObjectPtr json = new JSONObject(communicator);
1036  QString typeStr;
1037  QString jsonStr;
1038 
1039  if (p->defaultValue)
1040  {
1041  json->serializeIceObject(p->defaultValue);
1042  typeStr = QString::fromStdString(
1043  VariantContainerType::allTypesToString(p->defaultValue->getContainerType()));
1044 
1045  // ARMARX_INFO_S << VAROUT(typeStr.toStdString());
1046  // ARMARX_INFO_S << VAROUT(json->asString(true));
1047  if (VariantType::IsBasicType(Variant::hashTypeName(typeStr.toStdString())))
1048  {
1049  jsonStr = QString::fromUtf8(
1050  json->getElement("variant")->getElement("value")->toString().c_str());
1051  }
1052  else
1053  {
1054  jsonStr = QString::fromUtf8(json->asString(true).c_str());
1055  }
1056 
1057  // ARMARX_INFO_S << VAROUT(jsonStr.toStdString());
1058  }
1059  else if (jsonStringMap.find(QString::fromStdString(it->first)) != jsonStringMap.end())
1060  {
1061  typeStr = jsonStringMap.at(QString::fromStdString(it->first)).first;
1062  jsonStr = jsonStringMap.at(QString::fromStdString(it->first)).second;
1063  }
1064 
1065  addParameterRow(QString::fromStdString(it->first), typeStr, jsonStr, p->optionalParam);
1066  }
1067 
1068  addParameterRow();
1069  connectUserEditSlots();
1070  // setHeaders();
1071 }
1072 
1073 QWidget*
1074 StateParameterEditor::LineEditDelegate::createEditor(QWidget* parent,
1075  const QStyleOptionViewItem& option,
1076  const QModelIndex& index) const
1077 {
1078  QLineEdit* lineEdit = new QLineEdit(parent);
1079  QString regExpStr("(|([a-z_]{1})([a-z_0-9]*))");
1080  QRegExp reg(regExpStr, Qt::CaseInsensitive);
1081  lineEdit->setValidator(new QRegExpValidator(reg, lineEdit));
1082  return lineEdit;
1083 }
armarx::Variant
The Variant class is described here: Variants.
Definition: Variant.h:223
armarx::StateParameterEditor::eOptional
@ eOptional
Definition: StateParameterEditor.h:46
armarx::StateParameterEditor::eType
@ eType
Definition: StateParameterEditor.h:45
armarx::StateParameterEditor::getKeys
QSet< QString > getKeys() const
Definition: StateParameterEditor.cpp:88
armarx::StateParameterEditor::eKey
@ eKey
Definition: StateParameterEditor.h:44
armarx::VariantType::Float
const VariantTypeId Float
Definition: Variant.h:919
armarx::StateParameterEditor::getDefaultValueState
Qt::CheckState getDefaultValueState() const
Definition: StateParameterEditor.cpp:986
armarx::VariantType::List
const VariantContainerType List
Definition: SingleTypeVariantList.h:204
armarx::Variant::setLong
void setLong(long n, const Ice::Current &c=Ice::emptyCurrent) override
Sets the Variant's value to n.
Definition: Variant.cpp:372
armarx::StateParameterEditor::buildFromMap
void buildFromMap(const StateParameterMap &map, const std::map< QString, std::pair< QString, QString >> &jsonStringMap=std::map< QString, std::pair< QString, QString >>())
Definition: StateParameterEditor.cpp:1010
armarx::StateParameterEditor::getStringValueMap
StringVariantContainerBaseMap getStringValueMap() const
Definition: StateParameterEditor.cpp:148
JSONObject.h
index
uint8_t index
Definition: EtherCATFrame.h:59
armarx::StateParameterEditor::setDefaultValueState
void setDefaultValueState(const Qt::CheckState &value)
Definition: StateParameterEditor.cpp:992
armarx::StateParameterEditor::buildRequested
void buildRequested(const StateParameterMap &map, const std::map< QString, std::pair< QString, QString >> &jsonStringMap)
list
list(APPEND SOURCES ${QT_RESOURCES}) set(COMPONENT_LIBS ArmarXGui ArmarXCoreObservers ArmarXCoreEigen3Variants PlotterController $
Definition: CMakeLists.txt:49
armarx::JSONObject
The JSONObject class is used to represent and (de)serialize JSON objects.
Definition: JSONObject.h:43
armarx::VariantType::Map
const VariantContainerType Map
Definition: StringValueMap.h:263
armarx::Variant::setString
void setString(const std::string &s, const Ice::Current &c=Ice::emptyCurrent) override
Sets the Variant's value to s.
Definition: Variant.cpp:428
c
constexpr T c
Definition: UnscentedKalmanFilterTest.cpp:46
armarx::Variant::getTypes
static const std::map< VariantTypeId, std::string > & getTypes()
Returns the mapping of currently registered types.
Definition: Variant.cpp:863
armarx::VariantType::Bool
const VariantTypeId Bool
Definition: Variant.h:916
armarx::StateParameterEditor::getStateParameters
StateParameterMap getStateParameters() const
Definition: StateParameterEditor.cpp:119
armarx::StateParameterEditor::addParameterRow
int addParameterRow()
Definition: StateParameterEditor.cpp:438
GfxTL::Off
OnOff< false > Off
Definition: OnOff.h:13
armarx::StateParameterEditor::createValueButton
void createValueButton(int row, const QString &jsonValue)
Definition: StateParameterEditor.cpp:551
StateParameter.h
armarx::Variant::setInt
void setInt(int n, const Ice::Current &c=Ice::emptyCurrent) override
Sets the Variant's value to n.
Definition: Variant.cpp:355
armarx::StateParameterEditor::getType
QString getType(int row) const
Definition: StateParameterEditor.cpp:378
armarx::StateParameterEditor::editDefaultButtonClicked
void editDefaultButtonClicked()
Definition: StateParameterEditor.cpp:807
IceInternal::Handle< JSONObject >
armarx::StateParameterEditor::getStateParameter
StateParameterIceBasePtr getStateParameter(int row) const
Definition: StateParameterEditor.cpp:104
armarx::StateParameterEditor::getValueAsString
QString getValueAsString(int row) const
Definition: StateParameterEditor.cpp:168
armarx::StateParameterEditor::getKey
QString getKey(int row) const
Definition: StateParameterEditor.cpp:362
armarx::VariantType::Double
const VariantTypeId Double
Definition: Variant.h:920
armarx::Variant::setDouble
void setDouble(double d, const Ice::Current &c=Ice::emptyCurrent) override
Sets the Variant's value to d.
Definition: Variant.cpp:409
armarx::StateParameterEditor::eDeleteButton
@ eDeleteButton
Definition: StateParameterEditor.h:49
armarx::StateParameterEditor::setKeyBlackList
void setKeyBlackList(const QSet< QString > &keyBlackList)
Definition: StateParameterEditor.cpp:82
armarx::ctrlutil::a
double a(double t, double a0, double j)
Definition: CtrlUtil.h:45
cxxopts::value
std::shared_ptr< Value > value()
Definition: cxxopts.hpp:855
armarx::Variant::setBool
void setBool(bool b, const Ice::Current &c=Ice::emptyCurrent) override
Sets the Variant's value to b.
Definition: Variant.cpp:447
armarx::SingleVariant
The SingleVariant class is required to store single Variant instances in VariantContainer subclasses.
Definition: VariantContainer.h:107
armarx::StateParameterEditor::getVariantContainer
VariantContainerBasePtr getVariantContainer(int row) const
Definition: StateParameterEditor.cpp:272
armarx::statechartmodel::StateParameterMap
QMap< QString, StateParameterPtr > StateParameterMap
Definition: StateParameter.h:46
armarx::StateParameterEditor::getJson
QString getJson(QString key) const
Definition: StateParameterEditor.cpp:186
armarx::StateParameterEditor::refreshVariantTypes
void refreshVariantTypes()
Definition: StateParameterEditor.cpp:796
armarx::Variant::setFloat
void setFloat(float f, const Ice::Current &c=Ice::emptyCurrent) override
Sets the Variant's value to f.
Definition: Variant.cpp:390
armarx::StateParameterEditor::getIsOptional
bool getIsOptional(int row) const
Definition: StateParameterEditor.cpp:426
armarx::StateParameterEditor::getRow
int getRow(const QString &key) const
Definition: StateParameterEditor.cpp:404
armarx::VariantType::Long
const VariantTypeId Long
Definition: Variant.h:918
armarx::StateParameterEditor::setHeaders
void setHeaders()
Definition: StateParameterEditor.cpp:998
armarx::VariantType::IsBasicType
bool IsBasicType(VariantTypeId id)
Definition: Variant.cpp:893
ARMARX_WARNING_S
#define ARMARX_WARNING_S
Definition: Logging.h:213
armarx::StateParameterEditor::eProvideDefaultValue
@ eProvideDefaultValue
Definition: StateParameterEditor.h:47
armarx::StateParameterEditor::rowFilled
void rowFilled(int rowId, const QString &key)
armarx::VariantContainerType
Definition: VariantContainer.h:213
option
#define option(type, fn)
ArmarXWidgetController.h
armarx::viz::toString
const char * toString(InteractionFeedbackType type)
Definition: Interaction.h:28
StateParameterEditor.h
armarx::VariantType::Int
const VariantTypeId Int
Definition: Variant.h:917
armarx::StateParameterEditor::checkAndUpdateRowCount
void checkAndUpdateRowCount(int row, int column)
Definition: StateParameterEditor.cpp:745
armarx::Variant::hashTypeName
static int hashTypeName(const std::string &typeName)
Compute and return a hash value for a given type name.
Definition: Variant.cpp:813
armarx::StateParameter::create
static StateParameterPtr create()
Definition: StateParameter.cpp:59
armarx::StateParameterEditor::StateParameterEditor
StateParameterEditor(QWidget *parent=0, const StateParameterMap &params=StateParameterMap())
Definition: StateParameterEditor.cpp:50
ARMARX_INFO_S
#define ARMARX_INFO_S
Definition: Logging.h:202
armarx::handleExceptions
void handleExceptions()
Definition: Exception.cpp:157
armarx::VariantType::String
const VariantTypeId String
Definition: Variant.h:921
armarx::StateParameterEditor::deleteRow
void deleteRow()
Definition: StateParameterEditor.cpp:726
armarx::StateParameterEditor::eValue
@ eValue
Definition: StateParameterEditor.h:48
armarx::StateParameterEditor::rowAdded
void rowAdded(int rowId)
Variant.h
armarx::VariantContainerType::FromString
static ContainerTypePtr FromString(const std::string &typeStr)
Definition: VariantContainer.cpp:281
armarx
This file offers overloads of toIce() and fromIce() functions for STL container types.
Definition: ArmarXTimeserver.cpp:27
armarx::StateParameterEditor::typeCbChanged
void typeCbChanged(const QString &text)
Definition: StateParameterEditor.cpp:657
armarx::VariantContainerType::allTypesToString
static std::string allTypesToString(const ContainerTypePtr &type)
Definition: VariantContainer.cpp:250
armarx::split
std::vector< std::string > split(const std::string &source, const std::string &splitBy, bool trimElements=false, bool removeEmptyElements=false)
Definition: StringHelpers.cpp:38