13 const QColor VuoInputEditorMovieFormat::darkModeEnabledLabelTextColor = QColor(207, 207, 207);
14 const QColor VuoInputEditorMovieFormat::darkModeDisabledLabelTextColor = QColor(127, 127, 127);
36 const int decimalPrecision = DBL_MAX_10_EXP + DBL_DIG;
38 suggestedMinImageQuality = 0;
39 suggestedMaxImageQuality = 1;
41 suggestedMinAudioQuality = 0;
42 suggestedMaxAudioQuality = 1;
44 double suggestedStepImageQuality = 0.1;
45 double suggestedStepAudioQuality = 0.1;
47 QDoubleValidator *validator =
new QDoubleValidator(
this);
48 validator->setDecimals(decimalPrecision);
51 tabCycleForward =
true;
57 if (json_object_object_get_ex(details,
"isDark", &darkMode))
58 isDark = json_object_get_boolean(darkMode);
61 if (json_object_object_get_ex(details,
"forwardTabTraversal", &forwardTabTraversal))
62 tabCycleForward = json_object_get_boolean(forwardTabTraversal);
66 if (json_object_object_get_ex(details,
"suggestedMin", &suggestedMinValue))
74 if (json_object_object_get_ex(details,
"suggestedMax", &suggestedMaxValue))
82 if (json_object_object_get_ex(details,
"suggestedStep", &suggestedStepValue))
95 comboBoxImageEncoding->setFont(font);
96 setUpComboBoxForType(comboBoxImageEncoding,
"VuoMovieImageEncoding", originalMovieImageEncodingAsString);
97 connect(comboBoxImageEncoding,
static_cast<void (QComboBox::*)(
int)
>(&QComboBox::currentIndexChanged),
this, &VuoInputEditorMovieFormat::updateQualitySliderEnabledStatusAndEmitValueChanged);
101 comboBoxAudioEncoding->setFont(font);
102 setUpComboBoxForType(comboBoxAudioEncoding,
"VuoAudioEncoding", originalAudioEncodingAsString);
103 connect(comboBoxAudioEncoding,
static_cast<void (QComboBox::*)(
int)
>(&QComboBox::currentIndexChanged),
this, &VuoInputEditorMovieFormat::updateQualitySliderEnabledStatusAndEmitValueChanged);
109 lineEditImageQuality =
new QLineEdit(&dialog);
110 lineEditImageQuality->setFont(font);
112 lineEditImageQuality->adjustSize();
114 lineEditImageQuality->setValidator(validator);
115 lineEditImageQuality->installEventFilter(
this);
117 sliderImageQuality =
new QSlider(&dialog);
118 sliderImageQuality->setOrientation(Qt::Horizontal);
119 sliderImageQuality->setFocusPolicy(Qt::NoFocus);
120 sliderImageQuality->setMinimum(0);
121 sliderImageQuality->setMaximum(sliderImageQuality->width());
122 sliderImageQuality->setSingleStep(fmax(1, suggestedStepImageQuality*(sliderImageQuality->maximum()-sliderImageQuality->minimum())/(suggestedMaxImageQuality-suggestedMinImageQuality)));
125 int sliderValueImageQuality = lineEditValueToScaledSliderValue(lineEditValueImageQuality, imageQuality);
126 sliderImageQuality->setValue(sliderValueImageQuality);
128 connect(sliderImageQuality, &QSlider::valueChanged,
this,
static_cast<void (
VuoInputEditorMovieFormat::*)(
int)
>(&VuoInputEditorMovieFormat::updateLineEditValue));
129 connect(lineEditImageQuality, &QLineEdit::textEdited,
this, &VuoInputEditorMovieFormat::updateSliderValue);
130 connect(lineEditImageQuality, &QLineEdit::editingFinished,
this, &VuoInputEditorMovieFormat::emitValueChanged);
133 lineEditAudioQuality =
new QLineEdit(&dialog);
134 lineEditAudioQuality->setFont(font);
136 lineEditAudioQuality->adjustSize();
138 lineEditAudioQuality->setValidator(validator);
139 lineEditAudioQuality->installEventFilter(
this);
141 sliderAudioQuality =
new QSlider(&dialog);
142 sliderAudioQuality->setOrientation(Qt::Horizontal);
143 sliderAudioQuality->setFocusPolicy(Qt::NoFocus);
144 sliderAudioQuality->setMinimum(0);
145 sliderAudioQuality->setMaximum(sliderAudioQuality->width());
146 sliderAudioQuality->setSingleStep(fmax(1, suggestedStepAudioQuality*(sliderAudioQuality->maximum()-sliderAudioQuality->minimum())/(suggestedMaxAudioQuality-suggestedMinAudioQuality)));
149 int sliderValueAudioQuality = lineEditValueToScaledSliderValue(lineEditValueAudioQuality, audioQuality);
150 sliderAudioQuality->setValue(sliderValueAudioQuality);
152 connect(sliderAudioQuality, &QSlider::valueChanged,
this,
static_cast<void (
VuoInputEditorMovieFormat::*)(
int)
>(&VuoInputEditorMovieFormat::updateLineEditValue));
153 connect(lineEditAudioQuality, &QLineEdit::textEdited,
this, &VuoInputEditorMovieFormat::updateSliderValue);
154 connect(lineEditAudioQuality, &QLineEdit::editingFinished,
this, &VuoInputEditorMovieFormat::emitValueChanged);
159 const int widgetVerticalSpacing = 4;
160 const int widgetHorizontalSpacing = 5;
163 const int comboLabelVerticalCorrection = 3;
164 const int lineEditLabelVerticalCorrection = 1;
166 QLabel *labelImageEncoding =
new QLabel(
"Image Encoding", &dialog);
167 QLabel *labelAudioEncoding =
new QLabel(
"Audio Encoding", &dialog);
168 labelImageQuality =
new QLabel(
"Image Quality", &dialog);
169 labelAudioQuality =
new QLabel(
"Audio Quality", &dialog);
174 updateQualitySliderEnabledStatus();
176 labelImageEncoding->move( labelImageEncoding->pos().x(),
177 labelImageEncoding->pos().y() + comboLabelVerticalCorrection);
178 comboBoxImageEncoding->move(labelImageEncoding->pos().x()+labelImageEncoding->width() + widgetHorizontalSpacing,
179 labelImageEncoding->pos().y() - comboLabelVerticalCorrection);
181 labelImageQuality->move( labelImageEncoding->pos().x(),
182 comboBoxImageEncoding->pos().y() + comboBoxImageEncoding->height() + widgetVerticalSpacing + lineEditLabelVerticalCorrection);
183 lineEditImageQuality->move( comboBoxImageEncoding->pos().x(),
184 labelImageQuality->pos().y() - lineEditLabelVerticalCorrection);
185 sliderImageQuality->move( lineEditImageQuality->pos().x(),
186 lineEditImageQuality->pos().y() + lineEditImageQuality->height() + widgetVerticalSpacing - lineEditLabelVerticalCorrection);
188 sliderImageQuality->resize(sliderImageQuality->width(), sliderImageQuality->height() - 10);
189 lineEditImageQuality->resize(sliderImageQuality->width(), lineEditImageQuality->height());
191 labelAudioEncoding->move( labelImageQuality->pos().x(),
192 sliderImageQuality->pos().y() + sliderImageQuality->height() + widgetVerticalSpacing + comboLabelVerticalCorrection);
193 comboBoxAudioEncoding->move(labelAudioEncoding->pos().x() + labelAudioEncoding->width() + widgetHorizontalSpacing,
194 labelAudioEncoding->pos().y() - comboLabelVerticalCorrection);
197 labelAudioQuality->move( labelAudioEncoding->pos().x(),
198 comboBoxAudioEncoding->pos().y() + comboBoxAudioEncoding->height() + widgetVerticalSpacing + lineEditLabelVerticalCorrection);
199 lineEditAudioQuality->move( comboBoxAudioEncoding->pos().x(),
200 labelAudioQuality->pos().y() - lineEditLabelVerticalCorrection);
201 sliderAudioQuality->move( lineEditAudioQuality->pos().x(),
202 lineEditAudioQuality->pos().y() + lineEditAudioQuality->height() + widgetVerticalSpacing - lineEditLabelVerticalCorrection);
204 sliderAudioQuality->resize(sliderAudioQuality->width(), sliderAudioQuality->height() - 10);
205 lineEditAudioQuality->resize(sliderAudioQuality->width(), lineEditAudioQuality->height());
207 labelImageEncoding->show();
208 comboBoxImageEncoding->show();
210 labelImageQuality->show();
211 sliderImageQuality->show();
213 labelAudioEncoding->show();
214 comboBoxAudioEncoding->show();
216 labelAudioQuality->show();
217 sliderAudioQuality->show();
229 lineEditImageQuality->text(),
230 comboBoxAudioEncoding->currentData(),
231 lineEditAudioQuality->text());
240 QString valueAsStringInUserLocale = QLocale().toString(realValue);
242 if (qAbs(realValue) >= 1000.0)
243 valueAsStringInUserLocale.remove(QLocale().groupSeparator());
245 return valueAsStringInUserLocale;
252 const QString &imageQualityAsString,
253 const QVariant &audioEncoding,
254 const QString &audioQualityAsString)
259 format.
imageQuality = QLocale().toDouble(imageQualityAsString);
260 format.
audioQuality = QLocale().toDouble(audioQualityAsString);
268 void VuoInputEditorMovieFormat::updateSliderValue(QString newLineEditText)
270 QObject *sender = QObject::sender();
271 qualityAttribute whichQualityAttribute = (sender == lineEditImageQuality? imageQuality : audioQuality);
273 double newLineEditValue = QLocale().toDouble(newLineEditText);
274 int newSliderValue = lineEditValueToScaledSliderValue(newLineEditValue, whichQualityAttribute);
276 QSlider *targetSlider = (whichQualityAttribute == imageQuality? sliderImageQuality : sliderAudioQuality);
278 disconnect(targetSlider, &QSlider::valueChanged,
this,
static_cast<void (
VuoInputEditorMovieFormat::*)(
int)
>(&VuoInputEditorMovieFormat::updateLineEditValue));
279 targetSlider->setValue(newSliderValue);
280 connect(targetSlider, &QSlider::valueChanged,
this,
static_cast<void (
VuoInputEditorMovieFormat::*)(
int)
>(&VuoInputEditorMovieFormat::updateLineEditValue));
289 void VuoInputEditorMovieFormat::updateLineEditValue()
291 QObject *sender = QObject::sender();
292 qualityAttribute whichQualityAttribute = (sender == sliderImageQuality? imageQuality: audioQuality);
293 updateLineEditValue(((QSlider *)sender)->value(), whichQualityAttribute);
296 void VuoInputEditorMovieFormat::updateLineEditValue(
int newSliderValue)
298 QObject *sender = QObject::sender();
299 qualityAttribute whichQualityAttribute = (sender == sliderImageQuality? imageQuality: audioQuality);
301 updateLineEditValue(newSliderValue, whichQualityAttribute);
313 void VuoInputEditorMovieFormat::updateLineEditValue(
int newSliderValue, qualityAttribute whichQualityAttribute)
315 double newLineEditValue = sliderValueToScaledLineEditValue(newSliderValue, whichQualityAttribute);
316 QLineEdit *targetLineEdit = (whichQualityAttribute == imageQuality? lineEditImageQuality : lineEditAudioQuality);
317 const QString originalLineEditText = targetLineEdit->text();
318 QString newLineEditText = QLocale().toString(newLineEditValue,
'g');
320 if (qAbs(newLineEditValue) >= 1000.0)
321 newLineEditText.remove(QLocale().groupSeparator());
323 if (originalLineEditText != newLineEditText)
325 targetLineEdit->setText(newLineEditText);
326 targetLineEdit->setFocus();
327 targetLineEdit->selectAll();
336 int VuoInputEditorMovieFormat::lineEditValueToScaledSliderValue(
double lineEditValue, qualityAttribute whichQualityAttribute)
338 QSlider *targetSlider = (whichQualityAttribute == imageQuality? sliderImageQuality : sliderAudioQuality);
339 double suggestedMin = (whichQualityAttribute == imageQuality? suggestedMinImageQuality : suggestedMinAudioQuality);
340 double suggestedMax = (whichQualityAttribute == imageQuality? suggestedMaxImageQuality : suggestedMaxAudioQuality);
341 const double lineEditRange = suggestedMax - suggestedMin;
343 const int sliderRange = targetSlider->maximum() - targetSlider->minimum();
344 int scaledSliderValue = targetSlider->minimum() + ((lineEditValue-suggestedMin)/(1.0*(lineEditRange)))*sliderRange;
346 return scaledSliderValue;
353 double VuoInputEditorMovieFormat::sliderValueToScaledLineEditValue(
int sliderValue, qualityAttribute whichQualityAttribute)
355 QSlider *targetSlider = (whichQualityAttribute == imageQuality? sliderImageQuality : sliderAudioQuality);
356 double suggestedMin = (whichQualityAttribute == imageQuality? suggestedMinImageQuality : suggestedMinAudioQuality);
357 double suggestedMax = (whichQualityAttribute == imageQuality? suggestedMaxImageQuality : suggestedMaxAudioQuality);
358 const double lineEditRange = suggestedMax - suggestedMin;
360 const int sliderRange = targetSlider->maximum() - targetSlider->minimum();
361 double scaledLineEditValue = suggestedMin + ((sliderValue-targetSlider->minimum())/(1.0*sliderRange))*lineEditRange;
363 return scaledLineEditValue;
366 void VuoInputEditorMovieFormat::updateQualitySliderEnabledStatusAndEmitValueChanged()
368 updateQualitySliderEnabledStatus();
375 void VuoInputEditorMovieFormat::updateQualitySliderEnabledStatus()
380 bool enableImageQualityWidgets = ((acceptedFormat.
imageEncoding == VuoMovieImageEncoding_JPEG) ||
381 (acceptedFormat.
imageEncoding == VuoMovieImageEncoding_H264) ||
382 (acceptedFormat.
imageEncoding == VuoMovieImageEncoding_HEVC) ||
383 (acceptedFormat.
imageEncoding == VuoMovieImageEncoding_HEVCAlpha));
385 labelImageQuality->setEnabled(enableImageQualityWidgets);
386 lineEditImageQuality->setEnabled(enableImageQualityWidgets);
387 sliderImageQuality->setEnabled(enableImageQualityWidgets);
389 if (!enableImageQualityWidgets)
391 int sliderValueImageQuality = lineEditValueToScaledSliderValue(1., imageQuality);
392 sliderImageQuality->setValue(sliderValueImageQuality);
396 bool enableAudioQualityWidgets = (acceptedFormat.
audioEncoding != VuoAudioEncoding_LinearPCM);
398 labelAudioQuality->setEnabled(enableAudioQualityWidgets);
399 lineEditAudioQuality->setEnabled(enableAudioQualityWidgets);
400 sliderAudioQuality->setEnabled(enableAudioQualityWidgets);
402 if (!enableAudioQualityWidgets)
404 int sliderValueAudioQuality = lineEditValueToScaledSliderValue(1., audioQuality);
405 sliderAudioQuality->setValue(sliderValueAudioQuality);
408 QLineEdit *firstEnabledLineEdit = (enableImageQualityWidgets? lineEditImageQuality :
409 (enableAudioQualityWidgets? lineEditAudioQuality :
412 QLineEdit *lastEnabledLineEdit = (enableAudioQualityWidgets? lineEditAudioQuality :
413 (enableImageQualityWidgets? lineEditImageQuality :
419 if (tabCycleForward && firstEnabledLineEdit)
421 firstEnabledLineEdit->setFocus();
422 firstEnabledLineEdit->selectAll();
424 else if (!tabCycleForward && lastEnabledLineEdit)
426 lastEnabledLineEdit->setFocus();
427 lastEnabledLineEdit->selectAll();
434 void VuoInputEditorMovieFormat::emitValueChanged()
444 QSlider *targetSlider = (
object==lineEditImageQuality? sliderImageQuality :
445 (
object==lineEditAudioQuality? sliderAudioQuality :
448 if (event->type()==QEvent::Wheel && targetSlider)
451 QApplication::sendEvent(targetSlider, event);
455 else if (event->type()==QEvent::KeyPress && targetSlider)
458 QKeyEvent *keyEvent = (QKeyEvent *)(event);
459 if ((keyEvent->key() == Qt::Key_Up) || (keyEvent->key() == Qt::Key_Down))
461 QApplication::sendEvent(targetSlider, event);
475 QComboBox * VuoInputEditorMovieFormat::setUpComboBoxForType(QComboBox *comboBox, QString type,
string originalValueAsString)
477 QString allowedValuesFunctionName = type +
"_getAllowedValues";
478 typedef void *(*allowedValuesFunctionType)(void);
479 allowedValuesFunctionType allowedValuesFunction = (allowedValuesFunctionType)dlsym(RTLD_SELF, allowedValuesFunctionName.toUtf8().constData());
481 QString summaryFunctionName = type +
"_getSummary";
482 typedef char *(*summaryFunctionType)(int);
483 summaryFunctionType summaryFunction = (summaryFunctionType)dlsym(RTLD_SELF, summaryFunctionName.toUtf8().constData());
485 QString jsonFunctionName = type +
"_getJson";
487 jsonFunctionType jsonFunction = (jsonFunctionType)dlsym(RTLD_SELF, jsonFunctionName.toUtf8().constData());
489 QString listCountFunctionName =
"VuoListGetCount_" + type;
490 typedef unsigned long (*listCountFunctionType)(
void *);
491 listCountFunctionType listCountFunction = (listCountFunctionType)dlsym(RTLD_SELF, listCountFunctionName.toUtf8().constData());
493 QString listValueFunctionName =
"VuoListGetValue_" + type;
494 typedef int (*listValueFunctionType)(
void *,
unsigned long);
495 listValueFunctionType listValueFunction = (listValueFunctionType)dlsym(RTLD_SELF, listValueFunctionName.toUtf8().constData());
497 if (allowedValuesFunction && summaryFunction && jsonFunction && listCountFunction && listValueFunction)
499 void *allowedValues = allowedValuesFunction();
500 unsigned long count = listCountFunction(allowedValues);
501 for (
unsigned long i=1; i<=count; ++i)
503 int value = listValueFunction(allowedValues, i);
504 char *summary = summaryFunction(value);
505 QVariant variantValue = QVariant::fromValue((
void *)jsonFunction(value));
508 if (type ==
"VuoMovieImageEncoding"
509 && value == VuoMovieImageEncoding_HEVC
510 && QSysInfo::macVersion() < Q_MV_OSX(10, 13))
515 if (type ==
"VuoMovieImageEncoding"
516 && (value == VuoMovieImageEncoding_HEVCAlpha
517 || value == VuoMovieImageEncoding_ProRes422HQ
518 || value == VuoMovieImageEncoding_ProRes422LT
519 || value == VuoMovieImageEncoding_ProRes422Proxy)
520 && QSysInfo::macVersion() < Q_MV_OSX(10, 15))
526 comboBox->addItem(summary, variantValue);
528 if (json_object_to_json_string_ext(jsonFunction(value), JSON_C_TO_STRING_PLAIN) == originalValueAsString)
529 comboBox->setCurrentText(summary);