1 #include "argumentseditor.h"
3 #include "apitracecall.h"
6 #include <QDoubleSpinBox>
7 #include <QItemEditorFactory>
15 isVariantEditable(const QVariant &var)
17 switch (var.userType()) {
21 case QVariant::LongLong:
22 case QVariant::ULongLong:
23 case QVariant::Double:
31 ArgumentsItemEditorFactory::ArgumentsItemEditorFactory()
32 : QItemEditorFactory()
36 QWidget * ArgumentsItemEditorFactory::createEditor(QVariant::Type type,
37 QWidget *parent) const
40 case QVariant::Bool: {
41 BooleanComboBox *cb = new BooleanComboBox(parent);
45 case QVariant::UInt: {
46 QSpinBox *sb = new QSpinBox(parent);
48 sb->setMaximum(INT_MAX);
51 QSpinBox *sb = new QSpinBox(parent);
53 sb->setMinimum(INT_MIN);
54 sb->setMaximum(INT_MAX);
57 case QVariant::ULongLong: {
58 QSpinBox *sb = new QSpinBox(parent);
60 sb->setMaximum(INT_MAX);
62 case QVariant::LongLong: {
63 QSpinBox *sb = new QSpinBox(parent);
65 sb->setMinimum(INT_MIN);
66 sb->setMaximum(INT_MAX);
69 case QVariant::Pixmap:
70 return new QLabel(parent);
71 case QVariant::Double: {
72 QDoubleSpinBox *sb = new QDoubleSpinBox(parent);
74 sb->setMinimum(-DBL_MAX);
75 sb->setMaximum(DBL_MAX);
86 ArgumentsItemEditorFactory::valuePropertyName(QVariant::Type type) const
90 return "currentIndex";
93 case QVariant::LongLong:
94 case QVariant::ULongLong:
95 case QVariant::Double:
98 case QVariant::String:
105 BooleanComboBox::BooleanComboBox(QWidget *parent)
108 addItem(tr("False"));
112 void BooleanComboBox::setValue(bool value)
114 setCurrentIndex(value ? 1 : 0);
117 bool BooleanComboBox::value() const
119 return (currentIndex() == 1);
122 ArgumentsEditor::ArgumentsEditor(QWidget *parent)
124 m_model(new QStandardItemModel()),
130 ArgumentsEditor::~ArgumentsEditor()
134 void ArgumentsEditor::setCall(ApiTraceCall *call)
136 if (m_call != call) {
142 ApiTraceCall * ArgumentsEditor::call() const
147 void ArgumentsEditor::init()
151 connect(m_ui.selectStringCB, SIGNAL(currentIndexChanged(int)),
152 SLOT(currentSourceChanged(int)));
153 connect(m_ui.glslEdit, SIGNAL(textChanged()),
154 SLOT(sourceChanged()));
156 m_ui.argsTree->setModel(m_model);
157 QItemEditorFactory *factory =
158 new ArgumentsItemEditorFactory();
160 QItemEditorFactory::setDefaultFactory(factory);
163 void ArgumentsEditor::setupCall()
168 headers.append(tr("Argument"));
169 headers.append(tr("Value"));
170 m_model->setColumnCount(2);
171 m_model->setHorizontalHeaderLabels(headers);
172 m_ui.argsTabWidget->removeTab(
173 m_ui.argsTabWidget->indexOf(m_ui.shaderTab));
178 m_ui.callLabel->setText(m_call->name());
179 QStandardItem *rootItem = m_model->invisibleRootItem();
180 for (int i = 0; i < m_call->argNames().count(); ++i) {
181 QString argName = m_call->argNames()[i];
182 QVariant val = m_call->arguments()[i];
183 QStandardItem *nameItem = new QStandardItem(argName);
184 nameItem->setFlags(nameItem->flags() ^ Qt::ItemIsEditable);
185 QList<QStandardItem*> topRow;
186 topRow.append(nameItem);
188 if (val.canConvert<ApiArray>()) {
189 ApiArray array = val.value<ApiArray>();
190 QList<QVariant> vals = array.values();
192 QVariant firstVal = vals.value(0);
193 if (firstVal.userType() == QVariant::String) {
194 m_ui.argsTabWidget->addTab(
195 m_ui.shaderTab, argName);
196 setupShaderEditor(vals);
199 } else if (isVariantEditable(firstVal)) {
200 for (int i = 0; i < vals.count(); ++i) {
201 QList<QStandardItem*> row;
203 QStandardItem *idx = new QStandardItem();
204 idx->setFlags(idx->flags() ^ Qt::ItemIsEditable);
205 idx->setText(tr("%1)").arg(i));
207 QStandardItem *col = new QStandardItem();
208 col->setFlags(col->flags() | Qt::ItemIsEditable);
209 col->setData(vals[i], Qt::DisplayRole);
212 nameItem->appendRow(row);
215 qDebug()<<"\tUnsupported array = "<<firstVal;
219 } else if (val.canConvert<ApiPointer>()) {
220 ApiPointer ptr = val.value<ApiPointer>();
221 QStandardItem *item = new QStandardItem();
222 item->setFlags(item->flags() ^ Qt::ItemIsEditable);
223 item->setText(ptr.toString());
224 QIcon icon(":/resources/emblem-locked.png");
226 item->setToolTip(tr("Argument is read-only"));
228 } else if (val.canConvert<ApiBitmask>()) {
229 ApiBitmask mask = val.value<ApiBitmask>();
230 QStandardItem *item = new QStandardItem();
231 item->setFlags(item->flags() ^ Qt::ItemIsEditable);
232 item->setText(mask.toString());
233 QIcon icon(":/resources/emblem-locked.png");
235 item->setToolTip(tr("Argument is read-only"));
237 } else if (val.canConvert<ApiStruct>()) {
238 ApiStruct str = val.value<ApiStruct>();
239 QStandardItem *item = new QStandardItem();
240 item->setFlags(item->flags() ^ Qt::ItemIsEditable);
241 item->setText(str.toString());
242 QIcon icon(":/resources/emblem-locked.png");
244 item->setToolTip(tr("Argument is read-only"));
246 } else if (val.userType() == QVariant::ByteArray) {
247 QByteArray ba = val.value<QByteArray>();
248 QStandardItem *item = new QStandardItem();
249 item->setFlags(item->flags() ^ Qt::ItemIsEditable);
251 tr("<binary data, size = %1 bytes>").arg(ba.size()));
252 QIcon icon(":/resources/emblem-locked.png");
254 item->setToolTip(tr("Argument is read-only"));
258 = new QStandardItem();
260 if (isVariantEditable(val)) {
261 item->setFlags(item->flags() | Qt::ItemIsEditable);
263 QIcon icon(":/resources/emblem-locked.png");
265 item->setFlags(item->flags() ^ Qt::ItemIsEditable);
266 item->setToolTip(tr("Argument is read-only"));
268 item->setData(val, Qt::DisplayRole);
271 rootItem->appendRow(topRow);
275 void ArgumentsEditor::setupShaderEditor(const QList<QVariant> &sources)
277 m_ui.selectStringCB->clear();
278 m_ui.glslEdit->clear();
279 for (int i = 0; i < sources.count(); ++i) {
280 m_ui.selectStringCB->addItem(
281 tr("Shader string: %1").arg(i),
284 m_ui.selectStringCB->setCurrentIndex(0);
287 void ArgumentsEditor::currentSourceChanged(int idx)
289 QVariant source = m_ui.selectStringCB->itemData(idx);
290 QString str = source.toString();
291 m_ui.glslEdit->setPlainText(source.toString());
292 m_ui.lengthLabel->setText(
293 tr("%1").arg(str.length()));
296 void ArgumentsEditor::sourceChanged()
298 QString str = m_ui.glslEdit->toPlainText();
299 m_ui.lengthLabel->setText(
300 tr("%1").arg(str.length()));
303 void ArgumentsEditor::accept()
305 QStringList argNames = m_call->argNames();
306 QList<QVariant> originalValues = m_call->arguments();
307 for (int i = 0; i < argNames.count(); ++i) {
308 QString argName = argNames[i];
309 QVariant argValue = originalValues[i];
310 QVariant editorValue = valueForName(argName, argValue);
311 qDebug()<<"Arg = "<<argName;
312 qDebug()<<"\toriginal = "<<argValue;
313 qDebug()<<"\teditor = "<<editorValue;
319 QVariant ArgumentsEditor::valueForName(const QString &name,
320 const QVariant &originalValue) const
323 for (int topRow = 0; topRow < m_model->rowCount(); ++topRow) {
324 QModelIndex nameIdx = m_model->index(topRow, 0, QModelIndex());
325 QString argName = nameIdx.data().toString();
326 /* we display shaders in a separate widget so
327 * the ordering might be different */
328 if (argName == name) {
329 if (originalValue.userType() == QMetaType::type("ApiArray")) {
330 ApiArray array = originalValue.value<ApiArray>();
331 val = arrayFromIndex(nameIdx, array);
333 QModelIndex valIdx = m_model->index(topRow, 1, QModelIndex());
341 QVariant ArgumentsEditor::arrayFromIndex(const QModelIndex &parentIndex,
342 const ApiArray &origArray) const
344 QList<QVariant> origValues = origArray.values();
346 if (origValues.isEmpty())
347 return QVariant::fromValue(ApiArray());
349 if (origValues.first().userType() == QVariant::String) {
354 for (int i = 0; i < origValues.count(); ++i) {
355 QModelIndex valIdx = m_model->index(i, 1, parentIndex);
356 QVariant var = valIdx.data();
357 //qDebug()<<"\t\tarray "<<i<<") "<<var;
360 newValue = QVariant::fromValue(ApiArray(lst));
365 #include "argumentseditor.moc"