1 /*****************************************************************************
2 * profile_selector.cpp : A small profile selector and editor
3 ****************************************************************************
4 * Copyright (C) 2009 the VideoLAN team
7 * Authors: Jean-Baptiste Kempf <jb@videolan.org>
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
22 *****************************************************************************/
25 #include "components/sout/profile_selector.hpp"
26 #include "components/sout/profiles.hpp"
27 #include "dialogs/sout.hpp"
29 #include <QHBoxLayout>
30 #include <QToolButton>
33 #include <QMessageBox>
34 #include <QRadioButton>
36 #include <QButtonGroup>
39 #include <QListWidgetItem>
42 #include <vlc_modules.h>
44 #define CATPROP2NAME( val ) QString("valueholder_%1").arg( val )
45 #define CATANDPROP( cat, prop ) QString("%1_%2").arg( cat ).arg( prop )
46 #define OLDFORMAT "^\\w+;\\d+;\\d+;\\d+;"
48 VLCProfileSelector::VLCProfileSelector( QWidget *_parent ): QWidget( _parent )
50 QHBoxLayout *layout = new QHBoxLayout( this );
52 QLabel *prLabel = new QLabel( qtr( "Profile"), this );
53 layout->addWidget( prLabel );
55 profileBox = new QComboBox( this );
56 layout->addWidget( profileBox );
58 QToolButton *editButton = new QToolButton( this );
59 editButton->setIcon( QIcon( ":/menu/preferences" ) );
60 editButton->setToolTip( qtr( "Edit selected profile" ) );
61 layout->addWidget( editButton );
63 QToolButton *deleteButton = new QToolButton( this );
64 deleteButton->setIcon( QIcon( ":/toolbar/clear" ) );
65 deleteButton->setToolTip( qtr( "Delete selected profile" ) );
66 layout->addWidget( deleteButton );
68 QToolButton *newButton = new QToolButton( this );
69 newButton->setIcon( QIcon( ":/new" ) );
70 newButton->setToolTip( qtr( "Create a new profile" ) );
71 layout->addWidget(newButton);
73 BUTTONACT( newButton, newProfile() );
74 BUTTONACT( editButton, editProfile() );
75 BUTTONACT( deleteButton, deleteProfile() );
78 CONNECT( profileBox, activated( int ),
79 this, updateOptions( int ) );
83 inline void VLCProfileSelector::fillProfilesCombo()
89 QSettings::NativeFormat,
91 QSettings::UserScope, "vlc", "vlc-qt-interface" );
93 int i_size = settings.beginReadArray( "codecs-profiles" );
95 for( int i = 0; i < i_size; i++ )
97 settings.setArrayIndex( i );
98 if( settings.value( "Profile-Name" ).toString().isEmpty() ) continue;
99 profileBox->addItem( settings.value( "Profile-Name" ).toString(),
100 settings.value( "Profile-Value" ) );
104 for( size_t i = 0; i < NB_PROFILE; i++ )
106 profileBox->addItem( video_profile_name_list[i],
107 video_profile_value_list[i] );
113 void VLCProfileSelector::newProfile()
115 editProfile( "", "" );
118 void VLCProfileSelector::editProfile()
120 editProfile( profileBox->currentText(),
121 profileBox->itemData( profileBox->currentIndex() ).toString() );
124 void VLCProfileSelector::editProfile( const QString& qs, const QString& value )
126 /* Create the Profile Editor */
127 VLCProfileEditor *editor = new VLCProfileEditor( qs, value, this );
130 if( QDialog::Accepted == editor->exec() )
134 profileBox->addItem( editor->name, QVariant( editor->transcodeValue() ) );
135 /* Update old profile */
138 /* Look for the profile */
139 int i_profile = profileBox->findText( qs );
140 assert( i_profile != -1 );
141 profileBox->setItemText( i_profile, editor->name );
142 profileBox->setItemData( i_profile, editor->transcodeValue() );
143 /* Force mrl recreation */
144 updateOptions( i_profile );
150 emit optionsChanged();
153 void VLCProfileSelector::deleteProfile()
155 profileBox->removeItem( profileBox->currentIndex() );
159 void VLCProfileSelector::saveProfiles()
163 QSettings::IniFormat,
165 QSettings::NativeFormat,
167 QSettings::UserScope, "vlc", "vlc-qt-interface" );
169 settings.remove( "codecs-profiles" ); /* Erase old profiles to be rewritten */
170 settings.beginWriteArray( "codecs-profiles" );
171 for( int i = 0; i < profileBox->count(); i++ )
173 settings.setArrayIndex( i );
174 settings.setValue( "Profile-Name", profileBox->itemText( i ) );
175 settings.setValue( "Profile-Value", profileBox->itemData( i ).toString() );
180 void VLCProfileSelector::updateOptions( int i )
182 QString options = profileBox->itemData( i ).toString();
183 QRegExp rx(OLDFORMAT);
184 if ( !options.contains( ";" ) ) return;
185 if ( rx.indexIn( options ) != -1 )
186 return updateOptionsOldFormat( i );
190 QStringList tuples = options.split( ";" );
191 typedef QHash<QString, QString> proptovalueHashType;
192 QHash<QString, proptovalueHashType *> categtopropHash;
193 proptovalueHashType *proptovalueHash;
196 /* Build a double hash structure because we need to make ordered lookups */
197 foreach ( const QString &tuple, tuples )
199 QStringList keyvalue = tuple.split( "=" );
200 if ( keyvalue.count() != 2 ) continue;
201 QString key = keyvalue[0];
203 keyvalue = key.split( "_" );
204 if ( keyvalue.count() != 2 ) continue;
205 QString categ = keyvalue[0];
206 QString prop = keyvalue[1];
208 if ( ! categtopropHash.contains( categ ) )
210 proptovalueHash = new proptovalueHashType();
211 categtopropHash.insert( categ, proptovalueHash );
213 proptovalueHash = categtopropHash.value( categ );
215 proptovalueHash->insert( prop, value );
218 /* Now we can build the/translate into MRL */
219 #define HASHPICK( categ, prop ) \
220 if ( categtopropHash.contains( categ ) ) \
222 proptovalueHash = categtopropHash.value( categ );\
223 value = proptovalueHash->take( prop );\
225 else value = QString()
228 smrl.begin( "transcode" );
230 /* First muxer options */
231 HASHPICK( "muxer", "mux" );
232 if ( value.isEmpty() ) goto cleanup;
235 HASHPICK( "video", "enable" );
236 if ( !value.isEmpty() )
238 HASHPICK( "video", "codec" );
240 if ( !value.isEmpty() )
242 smrl.option( "vcodec", value );
244 HASHPICK( "vcodec", "bitrate" );
245 if ( value.toInt() > 0 )
247 smrl.option( "vb", value.toInt() );
250 HASHPICK( "video", "filters" );
251 if ( !value.isEmpty() )
253 QStringList valuesList = QUrl::fromPercentEncoding( value.toAscii() ).split( ";" );
254 smrl.option( "vfilter", valuesList.join( ":" ) );
257 /*if ( codec is h264 )*/
259 /* special handling */
260 QStringList codecoptions;
262 HASHPICK( "vcodec", "qp" );
263 if( value.toInt() > 0 )
264 codecoptions << QString( "qp=%1" ).arg( value );
266 HASHPICK( "vcodec", "custom" );
267 if( !value.isEmpty() )
268 codecoptions << QUrl::fromPercentEncoding( value.toAscii() );
270 if ( codecoptions.count() )
272 QString("x264{%1}").arg( codecoptions.join(",") ) );
275 HASHPICK( "vcodec", "framerate" );
276 if ( !value.isEmpty() && value.toInt() > 0 )
277 smrl.option( "fps", value );
279 HASHPICK( "vcodec", "scale" );
280 if ( !value.isEmpty() )
281 smrl.option( "scale", value );
283 HASHPICK( "vcodec", "width" );
284 if ( !value.isEmpty() && value.toInt() > 0 )
285 smrl.option( "width", value );
287 HASHPICK( "vcodec", "height" );
288 if ( !value.isEmpty() && value.toInt() > 0 )
289 smrl.option( "height", value );
291 HASHPICK( "video", "copy" );
292 if ( ! value.isEmpty() )
293 smrl.option( "vcodec", "copy" );
296 smrl.option( "vcodec", "none" );
299 HASHPICK( "audio", "enable" );
300 if ( !value.isEmpty() )
302 HASHPICK( "audio", "codec" );
303 if ( !value.isEmpty() )
305 smrl.option( "acodec", value );
307 HASHPICK( "acodec", "bitrate" );
308 smrl.option( "ab", value.toInt() );
310 HASHPICK( "acodec", "channels" );
311 smrl.option( "channels", value.toInt() );
313 HASHPICK( "acodec", "samplerate" );
314 smrl.option( "samplerate", value.toInt() );
316 HASHPICK( "audio", "filters" );
317 if ( !value.isEmpty() )
319 QStringList valuesList = QUrl::fromPercentEncoding( value.toAscii() ).split( ";" );
320 smrl.option( "afilter", valuesList.join( ":" ) );
324 HASHPICK( "audio", "copy" );
325 if ( ! value.isEmpty() )
326 smrl.option( "acodec", "copy" );
329 smrl.option( "acodec", "none" );
332 HASHPICK( "subtitles", "enable" );
333 if( !value.isEmpty() )
335 HASHPICK( "subtitles", "codec" );
336 smrl.option( "scodec", value );
338 HASHPICK( "subtitles", "overlay" );
339 if ( !value.isEmpty() )
340 smrl.option( "soverlay" );
345 transcode = smrl.getMrl();
348 /* Temp hash tables cleanup */
349 foreach( proptovalueHashType *hash, categtopropHash )
352 emit optionsChanged();
355 void VLCProfileSelector::updateOptionsOldFormat( int i )
357 QStringList options = profileBox->itemData( i ).toString().split( ";" );
358 if( options.count() < 16 )
364 if( options[1].toInt() || options[2].toInt() || options[3].toInt() )
366 smrl.begin( "transcode" );
368 if( options[1].toInt() )
370 smrl.option( "vcodec", options[4] );
371 if( options[4] != "none" )
373 smrl.option( "vb", options[5].toInt() );
374 if( !options[7].isEmpty() && options[7].toInt() > 0 )
375 smrl.option( "fps", options[7] );
376 if( !options[6].isEmpty() )
377 smrl.option( "scale", options[6] );
378 if( !options[8].isEmpty() && options[8].toInt() > 0 )
379 smrl.option( "width", options[8].toInt() );
380 if( !options[9].isEmpty() && options[9].toInt() > 0 )
381 smrl.option( "height", options[9].toInt() );
385 if( options[2].toInt() )
387 smrl.option( "acodec", options[10] );
388 if( options[10] != "none" )
390 smrl.option( "ab", options[11].toInt() );
391 smrl.option( "channels", options[12].toInt() );
392 smrl.option( "samplerate", options[13].toInt() );
396 if( options[3].toInt() )
398 smrl.option( "scodec", options[14] );
399 if( options[15].toInt() )
400 smrl.option( "soverlay" );
405 transcode = smrl.getMrl();
409 emit optionsChanged();
416 VLCProfileEditor::VLCProfileEditor( const QString& qs_name, const QString& value,
418 : QVLCDialog( _parent, NULL )
421 ui.buttonGroup->setObjectName( CATPROP2NAME( CATANDPROP( "muxer", "mux" ) ) );
422 if( !qs_name.isEmpty() )
424 ui.profileLine->setText( qs_name );
425 ui.profileLine->setReadOnly( true );
431 QPushButton *saveButton = new QPushButton(
432 ( qs_name.isEmpty() ) ? qtr( "Create" ) : qtr( "Save" ) );
433 ui.buttonBox->addButton( saveButton, QDialogButtonBox::AcceptRole );
434 BUTTONACT( saveButton, close() );
435 QPushButton *cancelButton = new QPushButton( qtr( "Cancel" ) );
436 ui.buttonBox->addButton( cancelButton, QDialogButtonBox::RejectRole );
437 BUTTONACT( cancelButton, reject() );
439 CONNECT( ui.valueholder_video_copy, stateChanged( int ),
440 this, activatePanels() );
441 CONNECT( ui.valueholder_audio_copy, stateChanged( int ),
442 this, activatePanels() );
443 CONNECT( ui.valueholder_vcodec_bitrate, editingFinished( ),
444 this, fixBirateState() );
445 CONNECT( ui.valueholder_vcodec_qp, editingFinished( ),
446 this, fixQPState() );
447 CONNECT( ui.valueholder_video_codec, currentIndexChanged( int ),
448 this, codecSelected() );
451 fillProfile( value );
456 void VLCProfileEditor::loadCapabilities()
459 module_t **p_all = module_list_get (&count);
461 /* Parse the module list for capabilities and probe each of them */
462 for (size_t i = 0; i < count; i++)
464 module_t *p_module = p_all[i];
466 if( module_provides( p_module, "sout mux" ) )
467 caps["muxers"].insert( module_get_object( p_module ) );
468 // else if ( module_provides( p_module, "encoder" ) )
469 // caps["encoders"].insert( module_get_object( p_module ) );
471 module_list_free (p_all);
474 inline void VLCProfileEditor::registerFilters()
477 module_t **p_all = module_list_get (&count);
479 for (size_t i = 0; i < count; i++)
481 module_t *p_module = p_all[i];
482 if ( module_get_score( p_module ) > 0 ) continue;
484 QString capability = module_get_capability( p_module );
485 QListWidget *listWidget = NULL;
486 QListWidgetItem *item;
488 if ( capability == "video filter2" )
489 listWidget = ui.valueholder_video_filters;
490 else if ( capability == "audio filter" )
491 listWidget = ui.valueholder_audio_filters;
493 if ( !listWidget ) continue;
495 item = new QListWidgetItem( module_get_name( p_module, true ) );
496 item->setCheckState( Qt::Unchecked );
497 item->setToolTip( QString( module_get_help( p_module ) ) );
498 item->setData( Qt::UserRole, QString( module_get_object( p_module ) ) );
499 listWidget->addItem( item );
501 module_list_free (p_all);
503 ui.valueholder_video_filters->sortItems();
504 ui.valueholder_audio_filters->sortItems();
507 inline void VLCProfileEditor::registerCodecs()
509 #define SETMUX( button, val, vid, aud, men, sub, stream, chaps ) \
510 ui.button->setProperty( "sout", val );\
511 ui.button->setProperty( "capvideo", vid );\
512 ui.button->setProperty( "capaudio", aud );\
513 ui.button->setProperty( "capmenu", men );\
514 ui.button->setProperty( "capsubs", sub );\
515 ui.button->setProperty( "capstream", stream );\
516 ui.button->setProperty( "capchaps", chaps );\
517 CONNECT( ui.button, clicked(bool), this, muxSelected() );
518 SETMUX( PSMux, "ps", true, true, false, true, false, true )
519 SETMUX( TSMux, "ts", true, true, false, true, true, false )
520 SETMUX( WEBMux, "webm", true, true, false, false, true, false )
521 SETMUX( MPEG1Mux, "mpeg1", true, true, false, false, false, false )
522 SETMUX( OggMux, "ogg", true, true, false, false, true, true )
523 SETMUX( ASFMux, "asf", true, true, false, true, true, true )
524 SETMUX( MOVMux, "mp4", true, true, true, true, true, false )
525 SETMUX( WAVMux, "wav", false, true, false, false, false, false )
526 SETMUX( RAWMux, "raw", true, true, false, false, false, false )
527 SETMUX( FLVMux, "flv", true, true, false, false, true, false )
528 SETMUX( MKVMux, "mkv", true, true, true, true, true, true )
529 SETMUX( AVIMux, "avi", true, true, false, false, false, false )
530 SETMUX( MJPEGMux, "mpjpeg", true, false, false, false, false, false )
533 #define ADD_VCODEC( name, fourcc ) \
534 ui.valueholder_video_codec->addItem( name, QVariant( fourcc ) );
535 ADD_VCODEC( "MPEG-1", "mp1v" )
536 ADD_VCODEC( "MPEG-2", "mp2v" )
537 ADD_VCODEC( "MPEG-4", "mp4v" )
538 ADD_VCODEC( "DIVX 1" , "DIV1" )
539 ADD_VCODEC( "DIVX 2" , "DIV2" )
540 ADD_VCODEC( "DIVX 3" , "DIV3" )
541 ADD_VCODEC( "H-263", "H263" )
542 ADD_VCODEC( "H-264", "h264" )
543 ADD_VCODEC( "VP8", "VP80" )
544 ADD_VCODEC( "WMV1", "WMV1" )
545 ADD_VCODEC( "WMV2" , "WMV2" )
546 ADD_VCODEC( "M-JPEG", "MJPG" )
547 ADD_VCODEC( "Theora", "theo" )
548 ADD_VCODEC( "Dirac", "drac" )
551 qpcodecsList << "h264";
553 #define ADD_ACODEC( name, fourcc ) ui.valueholder_audio_codec->addItem( name, QVariant( fourcc ) );
554 ADD_ACODEC( "MPEG Audio", "mpga" )
555 ADD_ACODEC( "MP3", "mp3" )
556 ADD_ACODEC( "MPEG 4 Audio ( AAC )", "mp4a" )
557 ADD_ACODEC( "A52/AC-3", "a52" )
558 ADD_ACODEC( "Vorbis", "vorb" )
559 ADD_ACODEC( "Flac", "flac" )
560 ADD_ACODEC( "Speex", "spx" )
561 ADD_ACODEC( "WAV", "s16l" )
562 ADD_ACODEC( "WMA2", "wma2" )
565 #define ADD_SCALING( factor ) ui.valueholder_vcodec_scale->addItem( factor );
566 ADD_SCALING( qtr("Auto") );
568 ADD_SCALING( "0.25" )
570 ADD_SCALING( "0.75" )
571 ADD_SCALING( "1.25" )
573 ADD_SCALING( "1.75" )
577 #define ADD_SAMPLERATE( sample, val ) ui.valueholder_acodec_samplerate->addItem( sample, val );
578 ADD_SAMPLERATE( "8000 Hz", 8000 )
579 ADD_SAMPLERATE( "11025 Hz", 11025 )
580 ADD_SAMPLERATE( "22050 Hz", 22050 )
581 ADD_SAMPLERATE( "44100 Hz", 44100 )
582 ADD_SAMPLERATE( "48000 Hz", 48000 )
583 #undef ADD_SAMPLERATE
585 #define ADD_SCODEC( name, fourcc ) ui.valueholder_subtitles_codec->addItem( name, QVariant( fourcc ) );
586 ADD_SCODEC( "DVB subtitle", "dvbs" )
587 ADD_SCODEC( "T.140", "t140" )
591 void VLCProfileEditor::muxSelected()
593 QRadioButton *current =
594 qobject_cast<QRadioButton *>( ui.buttonGroup->checkedButton() );
596 #define SETYESNOSTATE( name, prop ) \
597 ui.name->setChecked( current->property( prop ).toBool() )
600 SETYESNOSTATE( capvideo, "capvideo" );
601 SETYESNOSTATE( capaudio, "capaudio" );
602 SETYESNOSTATE( capmenu, "capmenu" );
603 SETYESNOSTATE( capsubs, "capsubs" );
604 SETYESNOSTATE( capstream, "capstream" );
605 SETYESNOSTATE( capchaps, "capchaps" );
606 bool b = caps["muxers"].contains( "mux_" + current->property("sout").toString() );
608 ui.muxerwarning->setText(
609 QString( "<img src=\":/menu/info\"/> %1" )
610 .arg( qtr( "This muxer is not provided directly by VLC: It could be missing." ) )
613 ui.muxerwarning->setText("");
619 void VLCProfileEditor::codecSelected()
621 /* Enable quality preset */
622 QString currentcodec = ui.valueholder_video_codec->
623 itemData(ui.valueholder_video_codec->currentIndex() ).toString();
624 ui.valueholder_vcodec_qp->setEnabled( qpcodecsList.contains( currentcodec ) );
627 void VLCProfileEditor::fillProfile( const QString& qs )
629 QRegExp rx(OLDFORMAT);
630 if ( rx.indexIn( qs ) != -1 ) return fillProfileOldFormat( qs );
632 QStringList tuples = qs.split( ";" );
633 foreach ( const QString &tuple, tuples )
635 QStringList keyvalue = tuple.split( "=" );
636 if ( keyvalue.count() != 2 ) continue;
637 QString key = keyvalue[0];
638 QString value = keyvalue[1];
639 QObject *object = findChild<QObject *>( CATPROP2NAME( key ) );
642 if( object->inherits( "QButtonGroup" ) )
643 { /* Buttongroup for Radios */
644 const QButtonGroup *group = qobject_cast<const QButtonGroup *>( object );
645 foreach( QAbstractButton *button, group->buttons() )
647 if ( button->property("sout").toString() == value )
649 button->setChecked( true );
650 break;/* radios are exclusive */
654 else if( object->inherits( "QCheckBox" ) )
656 QCheckBox *box = qobject_cast<QCheckBox *>( object );
657 box->setChecked( ! value.isEmpty() );
659 else if( object->inherits( "QGroupBox" ) )
661 QGroupBox *box = qobject_cast<QGroupBox *>( object );
662 box->setChecked( ! value.isEmpty() );
664 else if( object->inherits( "QSpinBox" ) )
666 QSpinBox *box = qobject_cast<QSpinBox *>( object );
667 box->setValue( value.toInt() );
669 else if( object->inherits( "QDoubleSpinBox" ) )
671 QDoubleSpinBox *box = qobject_cast<QDoubleSpinBox *>( object );
672 box->setValue( value.toDouble() );
674 else if( object->inherits( "QComboBox" ) )
676 QComboBox *box = qobject_cast<QComboBox *>( object );
677 box->setCurrentIndex( box->findData( value ) );
679 else if( object->inherits( "QLineEdit" ) )
681 QLineEdit *box = qobject_cast<QLineEdit *>( object );
682 box->setText( QUrl::fromPercentEncoding( value.toAscii() ) );
684 else if ( object->inherits( "QListWidget" ) )
686 QStringList valuesList = QUrl::fromPercentEncoding( value.toAscii() ).split( ";" );
687 const QListWidget *list = qobject_cast<const QListWidget *>( object );
688 for( int i=0; i < list->count(); i++ )
690 QListWidgetItem *item = list->item( i );
691 if ( valuesList.contains( item->data( Qt::UserRole ).toString() ) )
692 item->setCheckState( Qt::Checked );
694 item->setCheckState( Qt::Unchecked );
701 void VLCProfileEditor::fillProfileOldFormat( const QString& qs )
703 QStringList options = qs.split( ";" );
704 if( options.count() < 16 )
707 const QString mux = options[0];
708 for ( int i=0; i< ui.muxer->layout()->count(); i++ )
710 QRadioButton *current =
711 qobject_cast<QRadioButton *>(ui.muxer->layout()->itemAt(i)->widget());
712 if ( unlikely( !current ) ) continue;/* someone is messing up with ui */
713 if ( current->property("sout").toString() == mux )
715 current->setChecked( true );
716 break;/* radios are exclusive */
720 ui.valueholder_video_copy->setChecked( !options[1].toInt() );
721 ui.valueholder_video_enable->setChecked( ( options[4] != "none" ) );
722 ui.valueholder_audio_copy->setChecked( !options[2].toInt() );
723 ui.valueholder_audio_enable->setChecked( ( options[10] != "none" ) );
724 ui.valueholder_subtitles_enable->setChecked( options[3].toInt() );
726 ui.valueholder_video_codec->setCurrentIndex( ui.valueholder_video_codec->findData( options[4] ) );
727 ui.valueholder_vcodec_bitrate->setValue( options[5].toInt() );
728 if ( options[6].toInt() > 0 )
729 ui.valueholder_vcodec_scale->setEditText( options[6] );
731 ui.valueholder_vcodec_scale->setCurrentIndex( 0 );
732 ui.valueholder_vcodec_framerate->setValue( options[7].toDouble() );
733 ui.valueholder_vcodec_width->setValue( options[8].toInt() );
734 ui.valueholder_vcodec_height->setValue( options[9].toInt() );
736 ui.valueholder_audio_codec->setCurrentIndex( ui.valueholder_audio_codec->findData( options[10] ) );
737 ui.valueholder_acodec_bitrate->setValue( options[11].toInt() );
738 ui.valueholder_acodec_channels->setValue( options[12].toInt() );
740 int index = ui.valueholder_acodec_samplerate->findData( options[13] );
741 if ( index == -1 ) index = ui.valueholder_acodec_samplerate->findData( 44100 );
742 ui.valueholder_acodec_samplerate->setCurrentIndex( index );
744 ui.valueholder_subtitles_codec->setCurrentIndex( ui.valueholder_subtitles_codec->findData( options[14] ) );
745 ui.valueholder_subtitles_overlay->setChecked( options[15].toInt() );
748 void VLCProfileEditor::close()
750 if( ui.profileLine->text().isEmpty() )
752 QMessageBox::warning( this, qtr(" Profile Name Missing" ),
753 qtr( "You must set a name for the profile." ) );
754 ui.profileLine->setFocus();
757 name = ui.profileLine->text();
762 #define currentData( box ) box->itemData( box->currentIndex() )
764 QString VLCProfileEditor::transcodeValue()
766 QList<QObject *> allwidgets = findChildren<QObject *>();
767 QStringList configuration;
769 foreach( const QObject *object, allwidgets )
771 if ( ! object->objectName().startsWith( CATPROP2NAME( "" ) ) )
773 if ( object->inherits( "QWidget" ) &&
774 ! qobject_cast<const QWidget *>(object)->isEnabled() ) continue;
776 QString name = object->objectName();
777 QStringList vals = object->objectName().split( "_" );
778 if ( vals.count() != 3 ) continue;
779 QString &categ = vals[1];
780 QString &prop = vals[2];
783 if( object->inherits( "QButtonGroup" ) )
785 const QButtonGroup *group = qobject_cast<const QButtonGroup *>( object );
786 value = group->checkedButton()->property( "sout" ).toString();
788 else if( object->inherits( "QCheckBox" ) )
790 const QCheckBox *box = qobject_cast<const QCheckBox *>( object );
791 value = box->isChecked() ? "yes" : "";
793 else if( object->inherits( "QGroupBox" ) )
795 const QGroupBox *box = qobject_cast<const QGroupBox *>( object );
796 value = box->isChecked() ? "yes" : "";
798 else if( object->inherits( "QSpinBox" ) )
800 const QSpinBox *box = qobject_cast<const QSpinBox *>( object );
801 value = QString::number( box->value() );
803 else if( object->inherits( "QDoubleSpinBox" ) )
805 const QDoubleSpinBox *box = qobject_cast<const QDoubleSpinBox *>( object );
806 value = QString::number( box->value() );
808 else if( object->inherits( "QComboBox" ) )
810 const QComboBox *box = qobject_cast<const QComboBox *>( object );
811 value = currentData( box ).toString();
813 else if( object->inherits( "QLineEdit" ) )
815 const QLineEdit *box = qobject_cast<const QLineEdit *>( object );
816 value = QUrl::toPercentEncoding( box->text(), "", "_;" );
818 else if ( object->inherits( "QListWidget" ) )
820 const QListWidget *list = qobject_cast<const QListWidget *>( object );
821 QStringList valuesList;
822 for( int i=0; i < list->count(); i++ )
824 const QListWidgetItem *item = list->item( i );
825 if ( item->checkState() == Qt::Checked )
826 valuesList.append( item->data( Qt::UserRole ).toString() );
828 value = QUrl::toPercentEncoding( valuesList.join( ";" ), "", "_;" );
831 if ( !value.isEmpty() )
832 configuration << QString( "%1_%2=%3" )
833 .arg( categ ).arg( prop ).arg( value );
836 return configuration.join( ";" );
839 void VLCProfileEditor::reset()
841 /* reset to default state as we can only check/enable existing values */
842 ui.valueholder_video_copy->setChecked( false );
843 ui.valueholder_audio_copy->setChecked( false );
845 fixBirateState(); /* defaults to bitrate, not qp */
846 /* end with top level ones for cascaded setEnabled() */
847 ui.valueholder_video_enable->setChecked( false );
848 ui.valueholder_audio_enable->setChecked( false );
849 ui.valueholder_subtitles_enable->setChecked( false );
852 void VLCProfileEditor::activatePanels()
854 ui.transcodevideo->setEnabled( ! ui.valueholder_video_copy->isChecked() );
855 ui.transcodeaudio->setEnabled( ! ui.valueholder_audio_copy->isChecked() );
858 void VLCProfileEditor::fixBirateState()
860 /* exclusive bitrate choice */
861 ui.valueholder_vcodec_qp->setValue( 0 );
864 void VLCProfileEditor::fixQPState()
866 /* exclusive bitrate choice */
867 ui.valueholder_vcodec_bitrate->setValue( 0 );