MainWindow.cpp 29.4 KB
Newer Older
Ludovic Fauvet's avatar
Ludovic Fauvet committed
1
/*****************************************************************************
2
 * MainWindow.cpp: VLMC MainWindow
Ludovic Fauvet's avatar
Ludovic Fauvet committed
3
 *****************************************************************************
Ludovic Fauvet's avatar
Ludovic Fauvet committed
4
 * Copyright (C) 2008-2010 VideoLAN
Ludovic Fauvet's avatar
Ludovic Fauvet committed
5 6
 *
 * Authors: Ludovic Fauvet <etix@l0cal.com>
7
 *          Hugo Beauzée-Luyssen <beauze.h@gmail.com>
Ludovic Fauvet's avatar
Ludovic Fauvet committed
8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
 *****************************************************************************/

24
#include <QSizePolicy>
Christophe Courtaut's avatar
Christophe Courtaut committed
25
#include <QDockWidget>
26
#include <QFileDialog>
27
#include <QSlider>
28
#include <QMessageBox>
29 30
#include <QDesktopServices>
#include <QUrl>
31
#include <QSettings>
32 33
#include <QDebug>
#include <QTemporaryFile>
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
34

Ludovic Fauvet's avatar
Ludovic Fauvet committed
35
#include "MainWindow.h"
36
#include "config.h"
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
37
#include "Library.h"
Ludovic Fauvet's avatar
Ludovic Fauvet committed
38
#include "About.h"
39 40
#include "VlmcDebug.h"

Ludovic Fauvet's avatar
Ludovic Fauvet committed
41
#include "MainWorkflow.h"
42
#include "export/RendererSettings.h"
43
#include "export/ShareOnYoutube.h"
Ludovic Fauvet's avatar
Ludovic Fauvet committed
44
#include "WorkflowFileRenderer.h"
45
#include "WorkflowRenderer.h"
46
#include "ClipRenderer.h"
47 48 49

/* Widgets */
#include "DockWidgetManager.h"
50
#include "ImportController.h"
51
#include "MediaLibrary.h"
52
#include "PreviewWidget.h"
53 54
#include "timeline/Timeline.h"
#include "timeline/TracksView.h"
55
#include "UndoStack.h"
56 57

/* Settings / Preferences */
58
#include "project/GuiProjectManager.h"
Ludovic Fauvet's avatar
Ludovic Fauvet committed
59 60
#include "ProjectWizard.h"
#include "Settings.h"
61
#include "SettingsManager.h"
62
#include "LanguageHelper.h"
Ludovic Fauvet's avatar
Ludovic Fauvet committed
63

64 65 66
/* VLCpp */
#include "VLCInstance.h"

Ludovic Fauvet's avatar
Ludovic Fauvet committed
67
MainWindow::MainWindow( QWidget *parent ) :
68
    QMainWindow( parent ), m_fileRenderer( NULL )
Ludovic Fauvet's avatar
Ludovic Fauvet committed
69 70
{
    m_ui.setupUi( this );
71

72
    qRegisterMetaType<MainWorkflow::TrackType>( "MainWorkflow::TrackType" );
73
    qRegisterMetaType<MainWorkflow::FrameChangedReason>( "MainWorkflow::FrameChangedReason" );
74
    qRegisterMetaType<QVariant>( "QVariant" );
75

Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
76
    //We only install message handler here cause it uses configuration.
77
//    VlmcDebug::getInstance()->setup();
78

79
    //VLC Instance:
80
    LibVLCpp::Instance::getInstance();
81

82
    //Creating the project manager first (so it can create all the project variables)
83
    GUIProjectManager::getInstance();
84

85 86 87
    //Preferences
    initVlmcPreferences();

88
    // GUI
89
    DockWidgetManager::getInstance( this )->setMainWindow( this );
90
    createGlobalPreferences();
91
    createProjectPreferences();
92 93
    initializeDockWidgets();
    createStatusBar();
Ludovic Fauvet's avatar
Ludovic Fauvet committed
94
#ifdef WITH_CRASHBUTTON
95 96
    setupCrashTester();
#endif
97

Ludovic Fauvet's avatar
Ludovic Fauvet committed
98
    // Zoom
99 100
    connect( m_zoomSlider, SIGNAL( valueChanged( int ) ),
             m_timeline, SLOT( changeZoom( int ) ) );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
101 102 103 104
    connect( m_timeline->tracksView(), SIGNAL( zoomIn() ),
             this, SLOT( zoomIn() ) );
    connect( m_timeline->tracksView(), SIGNAL( zoomOut() ),
             this, SLOT( zoomOut() ) );
105 106
    connect( this, SIGNAL( toolChanged( ToolButtons ) ),
             m_timeline, SLOT( setTool( ToolButtons ) ) );
107

108
    connect( GUIProjectManager::getInstance(), SIGNAL( projectUpdated( const QString&, bool ) ),
109
             this, SLOT( projectUpdated( const QString&, bool ) ) );
110

111 112 113 114 115 116 117 118 119
    // Undo/Redo
    connect( UndoStack::getInstance( this ), SIGNAL( canRedoChanged( bool ) ),
             this, SLOT( canRedoChanged( bool ) ) );
    connect( UndoStack::getInstance( this ), SIGNAL( canUndoChanged( bool ) ),
             this, SLOT( canUndoChanged( bool ) ) );
    canRedoChanged( UndoStack::getInstance( this )->canRedo() );
    canUndoChanged( UndoStack::getInstance( this )->canUndo() );


Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
120 121 122 123
    // Wizard
    m_pWizard = new ProjectWizard( this );
    m_pWizard->setModal( true );

124

125
#ifdef WITH_CRASHHANDLER
126
    if ( restoreSession() == true )
127 128
        return ;
#endif
129
    QSettings s;
130

131
    if ( s.value( "ShowWizardStartup", true ).toBool() )
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
132
    {
133
        //If a project was opened from the command line: don't show the wizard.
134 135
        if ( qApp->arguments().size() == 1 )
            m_pWizard->show();
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
136
    }
Ludovic Fauvet's avatar
Ludovic Fauvet committed
137 138
}

139 140
MainWindow::~MainWindow()
{
141 142 143 144 145
    QSettings s;
    // Save the current geometry
    s.setValue( "MainWindowGeometry", saveGeometry() );
    // Save the current layout
    s.setValue( "MainWindowState", saveState() );
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
146
    s.setValue( "CleanQuit", true );
147 148
    s.sync();

149 150
    if ( m_fileRenderer )
        delete m_fileRenderer;
151
    delete m_importController;
152
    LibVLCpp::Instance::destroyInstance();
153 154
}

155 156
void 
MainWindow::changeEvent( QEvent *e )
Ludovic Fauvet's avatar
Ludovic Fauvet committed
157 158 159 160 161
{
    switch ( e->type() )
    {
    case QEvent::LanguageChange:
        m_ui.retranslateUi( this );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
162
        DockWidgetManager::getInstance()->retranslateUi();
Ludovic Fauvet's avatar
Ludovic Fauvet committed
163 164 165 166 167 168
        break;
    default:
        break;
    }
}

Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
169
//use this helper when the shortcut is binded to a menu action
170 171 172
#define CREATE_MENU_SHORTCUT( key, defaultValue, name, desc, actionInstance  )      \
        VLMC_CREATE_PREFERENCE_KEYBOARD( key, defaultValue, name, desc );           \
        new KeyboardShortcutHelper( key, m_ui.actionInstance, this );
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
173

174 175 176
void
MainWindow::initVlmcPreferences()
{
177
    //Setup VLMC Keyboard Preference...
178 179 180
    VLMC_CREATE_PREFERENCE_KEYBOARD( "keyboard/defaultmode", "n",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Select mode" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Select the selection tool in the timeline" ) );
181

182 183 184
    VLMC_CREATE_PREFERENCE_KEYBOARD( "keyboard/cutmode", "x",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Cut mode" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Select the cut/razor tool in the timeline" ) );
185

186 187 188
    VLMC_CREATE_PREFERENCE_KEYBOARD( "keyboard/mediapreview", "Ctrl+Return",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Media preview" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Preview the selected media, or pause the current preview" ) );
189

190 191 192
    VLMC_CREATE_PREFERENCE_KEYBOARD( "keyboard/renderpreview", "Space",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Render preview" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Preview the project, or pause the current preview" ) );
193

194
    //A bit nasty, but we better use what Qt's providing as default shortcut
195 196 197 198
    CREATE_MENU_SHORTCUT( "keyboard/undo",
                          QKeySequence( QKeySequence::Undo ).toString().toLocal8Bit(),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Undo" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Undo the last action" ), actionUndo );
199

200 201 202 203
    CREATE_MENU_SHORTCUT( "keyboard/redo",
                          QKeySequence( QKeySequence::Redo ).toString().toLocal8Bit(),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Redo" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Redo the last action" ), actionRedo );
204

205 206 207 208
    CREATE_MENU_SHORTCUT( "keyboard/help",
                          QKeySequence( QKeySequence::HelpContents ).toString().toLocal8Bit(),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Help" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Toggle the help page" ), actionHelp );
209

210 211 212
    CREATE_MENU_SHORTCUT( "keyboard/quit", "Ctrl+Q",
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Quit" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Quit VLMC" ), actionQuit );
213

214 215 216
    CREATE_MENU_SHORTCUT( "keyboard/preferences", "Alt+P",
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Preferences" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Open VLMC preferences" ), actionPreferences );
217

218 219 220
    CREATE_MENU_SHORTCUT( "keyboard/fullscreen", "F",
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Fullscreen" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Switch to fullscreen mode" ), actionFullscreen );
221

222 223 224
    CREATE_MENU_SHORTCUT( "keyboard/newproject",
                          QKeySequence( QKeySequence::New ).toString().toLocal8Bit(),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "New project" ),
225
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Open the new project wizard" ), actionNew_Project );
226

227 228 229 230
    CREATE_MENU_SHORTCUT( "keyboard/openproject",
                          QKeySequence( QKeySequence::Open ).toString().toLocal8Bit(),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Open a project" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Open an existing project" ), actionLoad_Project );
231

232 233 234 235
    CREATE_MENU_SHORTCUT( "keyboard/save",
                          QKeySequence( QKeySequence::Save ).toString().toLocal8Bit(),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Save" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Save the current project" ), actionSave );
236

237 238 239
    CREATE_MENU_SHORTCUT( "keyboard/saveas", "Ctrl+Shift+S",
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Save as" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Save the current project to a new file" ), actionSave_As );
240

241 242 243 244
    CREATE_MENU_SHORTCUT( "keyboard/closeproject",
                          QKeySequence( QKeySequence::Close ).toString().toLocal8Bit(),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Close the project" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Close the current project" ), actionClose_Project );
245

246 247 248
    CREATE_MENU_SHORTCUT( "keyboard/importmedia", "Ctrl+I",
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Import media" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Open the import window" ), actionImport );
249

250 251 252 253
    CREATE_MENU_SHORTCUT( "keyboard/renderproject", "Ctrl+R",
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Render the project" ),
                          QT_TRANSLATE_NOOP( "PreferenceWidget", "Render the project to a file" ), actionRender );

254
    //Setup VLMC Lang. Preferences...
255
    VLMC_CREATE_PREFERENCE_LANGUAGE( "general/VLMCLang", "default",
256
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Language" ),
257
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "The VLMC's UI language" ) );
258

259 260 261 262
    SettingsManager::getInstance()->watchValue( "general/VLMCLang",
                                                LanguageHelper::getInstance(),
                                                SLOT( languageChanged( const QVariant& ) ),
                                                SettingsManager::Vlmc );
263

264
    VLMC_CREATE_PREFERENCE_BOOL( "general/ConfirmDeletion", true,
265
                                 QT_TRANSLATE_NOOP( "PreferenceWidget", "Confirm clip deletion"),
266
                                 QT_TRANSLATE_NOOP( "PreferenceWidget", "Ask for confirmation before deleting a clip from the timeline" ) );
267

268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294
    //Setup VLMC Youtube Preference...
    VLMC_CREATE_PREFERENCE_STRING( "youtube/DeveloperKey", "AI39si7FOtp165Vq644xVkuka84TVQNbztQmQ1dC9stheBfh3-33RZaTu7eJkYJzvxp6XNbvlr4M6-ULjXDERFl62WIo6AQIEQ",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Youtube Developer Key" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "The Youtube Developer Key" ) );

    VLMC_CREATE_PREFERENCE_STRING( "youtube/Username", "username",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Youtube Username" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "VLMC won't store your passwords..." ) );

    //Setup VLMC Proxy Settings
    //FIXME: The widgets get sorted...
    VLMC_CREATE_PREFERENCE_STRING( "network/ProxyUrl", "",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Proxy" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "The HTTP Proxy " ) );

    VLMC_CREATE_PREFERENCE_STRING( "network/ProxyPort", "",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Proxy Port" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "The HTTP Proxy Port" ) );

    VLMC_CREATE_PREFERENCE_STRING( "network/ProxyUsername", "",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Proxy Username" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "The HTTP Proxy Username" ) );

    VLMC_CREATE_PREFERENCE_STRING( "network/ProxyPassword", "",
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "Proxy Password" ),
                                     QT_TRANSLATE_NOOP( "PreferenceWidget", "The HTTP Proxy Password" ) );

295
    //Load saved preferences :
296 297 298 299 300 301 302
    QSettings       s;
    if ( s.value( "VlmcVersion" ).toString() != PROJECT_VERSION )
        s.clear();
    else
    {
        loadVlmcPreferences( "keyboard" );
        loadVlmcPreferences( "general" );
303 304
        loadVlmcPreferences( "youtube" );
        loadVlmcPreferences( "network" );
305 306
    }
    s.setValue( "VlmcVersion", PROJECT_VERSION );
307 308 309 310 311 312 313 314 315 316 317 318
}

void
MainWindow::loadVlmcPreferences( const QString &subPart )
{
    QSettings       s;
    s.beginGroup( subPart );
    foreach ( QString key, s.allKeys() )
    {
        SettingsManager::getInstance()->setValue( subPart + "/" + key, s.value( key ),
                                                  SettingsManager::Vlmc );
    }
319 320
}

Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
321 322
#undef CREATE_MENU_SHORTCUT

323 324
void
MainWindow::setupLibrary()
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
325
{
326
    m_importController = new ImportController();
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
327 328
    const ClipRenderer* clipRenderer = qobject_cast<const ClipRenderer*>( m_clipPreview->getGenericRenderer() );
    Q_ASSERT( clipRenderer != NULL );
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
329

330 331 332
    MediaLibrary    *mediaLibrary = new MediaLibrary();

    DockWidgetManager::getInstance()->addDockedWidget( mediaLibrary, QT_TRANSLATE_NOOP( "DockWidgetManager", "Media Library" ),
333 334 335
                                                    Qt::AllDockWidgetAreas,
                                                    QDockWidget::AllDockWidgetFeatures,
                                                    Qt::LeftDockWidgetArea );
336
    connect( mediaLibrary, SIGNAL( clipSelected( Clip* ) ),
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
337
             clipRenderer, SLOT( setClip( Clip* ) ) );
338 339
    connect( mediaLibrary, SIGNAL( importRequired() ),
             this, SLOT( on_actionImport_triggered() ) );
340 341
    connect( Library::getInstance(), SIGNAL( clipRemoved( const QUuid& ) ),
             clipRenderer, SLOT( clipUnloaded( const QUuid& ) ) );
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
342 343
}

344 345
void
MainWindow::on_actionSave_triggered()
346
{
347
    GUIProjectManager::getInstance()->saveProject();
348 349
}

350 351
void    
MainWindow::on_actionSave_As_triggered()
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
352
{
353
    GUIProjectManager::getInstance()->saveProject( true );
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
354 355
}

356 357
void    
MainWindow::on_actionLoad_Project_triggered()
358
{
359 360
    GUIProjectManager* pm = GUIProjectManager::getInstance();
    pm->loadProject( pm->acquireProjectFileName() );
361 362
}

363 364
void 
MainWindow::createStatusBar()
365
{
366 367
    // Mouse (default) tool
    QToolButton* mouseTool = new QToolButton( this );
368
    mouseTool->setAutoRaise( true );
369 370
    mouseTool->setCheckable( true );
    mouseTool->setIcon( QIcon( ":/images/mouse" ) );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
371
    mouseTool->setStatusTip( tr( "Use the mouse tool to manipulate regions in the timeline" ) );
372 373 374 375
    m_ui.statusbar->addPermanentWidget( mouseTool );

    // Cut/Split tool
    QToolButton* splitTool = new QToolButton( this );
376
    splitTool->setAutoRaise( true );
377 378
    splitTool->setCheckable( true );
    splitTool->setIcon( QIcon( ":/images/editcut" ) );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
379
    splitTool->setStatusTip( tr( "Use the scissors to cut regions in the timeline" ) );
380 381 382 383 384 385 386 387 388
    m_ui.statusbar->addPermanentWidget( splitTool );

    // Group the two previous buttons
    QButtonGroup* toolButtonGroup = new QButtonGroup( this );
    toolButtonGroup->addButton( mouseTool, TOOL_DEFAULT);
    toolButtonGroup->addButton( splitTool, TOOL_CUT );
    toolButtonGroup->setExclusive( true );
    mouseTool->setChecked( true );

389
    //Shortcut part:
390 391
    KeyboardShortcutHelper* defaultModeShortcut = new KeyboardShortcutHelper( "keyboard/defaultmode", this );
    KeyboardShortcutHelper* cutModeShortcut = new KeyboardShortcutHelper( "keyboard/cutmode", this );
392 393 394
    connect( defaultModeShortcut, SIGNAL( activated() ), mouseTool, SLOT( click() ) );
    connect( cutModeShortcut, SIGNAL( activated() ), splitTool, SLOT( click() ) );

395 396 397 398 399 400 401 402
    connect( toolButtonGroup, SIGNAL( buttonClicked( int ) ),
             this, SLOT( toolButtonClicked( int ) ) );

    // Spacer
    QWidget* spacer = new QWidget( this );
    spacer->setFixedWidth( 20 );
    m_ui.statusbar->addPermanentWidget( spacer );

Ludovic Fauvet's avatar
Ludovic Fauvet committed
403 404 405
    // Zoom Out
    QToolButton* zoomOutButton = new QToolButton( this );
    zoomOutButton->setIcon( QIcon( ":/images/zoomout" ) );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
406
    zoomOutButton->setStatusTip( tr( "Zoom out" ) );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
407 408 409
    m_ui.statusbar->addPermanentWidget( zoomOutButton );
    connect( zoomOutButton, SIGNAL( clicked() ),
             this, SLOT( zoomOut() ) );
410 411

    // Zoom slider
412 413 414 415 416 417 418 419 420
    m_zoomSlider = new QSlider( this );
    m_zoomSlider->setOrientation( Qt::Horizontal );
    m_zoomSlider->setTickInterval( 1 );
    m_zoomSlider->setSingleStep( 1 );
    m_zoomSlider->setPageStep( 1 );
    m_zoomSlider->setMinimum( 0 );
    m_zoomSlider->setMaximum( 13 );
    m_zoomSlider->setValue( 10 );
    m_zoomSlider->setFixedWidth( 80 );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
421
    m_zoomSlider->setInvertedAppearance( true );
422
    m_ui.statusbar->addPermanentWidget( m_zoomSlider );
423

Ludovic Fauvet's avatar
Ludovic Fauvet committed
424 425 426
    // Zoom IN
    QToolButton* zoomInButton = new QToolButton( this );
    zoomInButton->setIcon( QIcon( ":/images/zoomin" ) );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
427
    zoomInButton->setStatusTip( tr( "Zoom in" ) );
Ludovic Fauvet's avatar
Ludovic Fauvet committed
428 429 430
    m_ui.statusbar->addPermanentWidget( zoomInButton );
    connect( zoomInButton, SIGNAL( clicked() ),
             this, SLOT( zoomIn() ) );
431 432
}

433 434
void 
MainWindow::initializeDockWidgets( void )
435
{
436 437 438
    m_renderer = new WorkflowRenderer();
    m_renderer->initializeRenderer();
    m_timeline = new Timeline( m_renderer, this );
439 440 441
    m_timeline->setSizePolicy( QSizePolicy::Expanding, QSizePolicy::Expanding );
    m_timeline->show();
    setCentralWidget( m_timeline );
442

443
    DockWidgetManager *dockManager = DockWidgetManager::getInstance();
444

445 446
    m_clipPreview = new PreviewWidget( new ClipRenderer, this );
    dockManager->addDockedWidget( m_clipPreview,
Ludovic Fauvet's avatar
Ludovic Fauvet committed
447
                                  QT_TRANSLATE_NOOP( "DockWidgetManager", "Clip Preview" ),
geoff's avatar
geoff committed
448 449 450
                                  Qt::AllDockWidgetAreas,
                                  QDockWidget::AllDockWidgetFeatures,
                                  Qt::TopDockWidgetArea );
451
    KeyboardShortcutHelper* clipShortcut = new KeyboardShortcutHelper( "keyboard/mediapreview", this );
452
    connect( clipShortcut, SIGNAL( activated() ), m_clipPreview, SLOT( on_pushButtonPlay_clicked() ) );
453

454
    m_projectPreview = new PreviewWidget( m_renderer, this );
455
    dockManager->addDockedWidget( m_projectPreview,
Ludovic Fauvet's avatar
Ludovic Fauvet committed
456
                                  QT_TRANSLATE_NOOP( "DockWidgetManager", "Project Preview" ),
457 458
                                  Qt::AllDockWidgetAreas,
                                  QDockWidget::AllDockWidgetFeatures,
459
                                  Qt::TopDockWidgetArea );
460
    KeyboardShortcutHelper* renderShortcut = new KeyboardShortcutHelper( "keyboard/renderpreview", this );
461
    connect( renderShortcut, SIGNAL( activated() ), m_projectPreview, SLOT( on_pushButtonPlay_clicked() ) );
462

463
    QDockWidget* dock = dockManager->addDockedWidget( UndoStack::getInstance( this ),
Ludovic Fauvet's avatar
Ludovic Fauvet committed
464
                                  QT_TRANSLATE_NOOP( "DockWidgetManager", "History" ),
465 466 467
                                  Qt::AllDockWidgetAreas,
                                  QDockWidget::AllDockWidgetFeatures,
                                  Qt::LeftDockWidgetArea );
468 469
    if ( dock != 0 )
        dock->hide();
470
    setupLibrary();
471 472
}

473 474
void
MainWindow::createGlobalPreferences()
475
{
476
    m_globalPreferences = new Settings( SettingsManager::Vlmc, this );
477
    m_globalPreferences->addCategory( QT_TRANSLATE_NOOP( "Settings", "general" ), SettingsManager::Vlmc,
478 479
                                     QIcon( ":/images/images/vlmc.png" ),
                                     tr ( "VLMC settings" ) );
480
    m_globalPreferences->addCategory( QT_TRANSLATE_NOOP( "Settings", "keyboard" ), SettingsManager::Vlmc,
481 482
                                     QIcon( ":/images/keyboard" ),
                                     tr( "Keyboard Settings" ) );
483 484 485 486 487 488
    m_globalPreferences->addCategory( QT_TRANSLATE_NOOP( "Settings", "youtube" ), SettingsManager::Vlmc,
                                     QIcon( ":/images/youtube" ),
                                     tr( "Youtube Settings" ) );
    m_globalPreferences->addCategory( QT_TRANSLATE_NOOP( "Settings", "network" ), SettingsManager::Vlmc,
                                     QIcon( ":/images/network" ),
                                     tr( "Network Settings" ) );
489 490
}

491 492
void
MainWindow::createProjectPreferences()
493
{
494
    m_projectPreferences = new Settings( SettingsManager::Project, this );
495
    m_projectPreferences->addCategory( QT_TRANSLATE_NOOP( "Settings", "general" ), SettingsManager::Project,
496 497
                                   QIcon( ":/images/images/vlmc.png" ),
                                   tr ( "Project settings" ) );
498
    m_projectPreferences->addCategory( QT_TRANSLATE_NOOP( "Settings", "video" ), SettingsManager::Project,
499 500
                                   QIcon( ":/images/images/video.png" ),
                                   tr ( "Video settings" ) );
501
    m_projectPreferences->addCategory( QT_TRANSLATE_NOOP( "Settings", "audio" ), SettingsManager::Project,
502 503
                                   QIcon( ":/images/images/audio.png" ),
                                   tr ( "Audio settings" ) );
504 505
}

506

507 508
//Private slots definition

509 510
void 
MainWindow::on_actionQuit_triggered()
Ludovic Fauvet's avatar
Ludovic Fauvet committed
511 512 513
{
    QApplication::quit();
}
514

515 516
void 
MainWindow::on_actionPreferences_triggered()
517
{
518
   m_globalPreferences->show();
519
}
Ludovic Fauvet's avatar
Ludovic Fauvet committed
520

521 522
void 
MainWindow::on_actionAbout_triggered()
Ludovic Fauvet's avatar
Ludovic Fauvet committed
523
{
524
    About::getInstance()->exec();
Ludovic Fauvet's avatar
Ludovic Fauvet committed
525
}
526

527 528
void 
MainWindow::on_actionTranscode_triggered()
529
{
530 531
    QMessageBox::information( this, tr( "Sorry" ),
                              tr( "This feature is currently disabled." ) );
532
    //Transcode::instance( this )->exec();
533
}
534

535 536
bool
MainWindow::checkVideoLength()
537
{
538
    if ( MainWorkflow::getInstance()->getLengthFrame() <= 0 )
539
    {
540
        QMessageBox::warning( NULL, tr ( "VLMC Renderer" ), tr( "There is nothing to render." ) );
541
        return false;
542
    }
543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566
    return true;
}

void 
MainWindow::renderVideo( const QString& outputFileName, quint32 width, quint32 height, double fps, quint32 vbitrate, quint32 abitrate )
{
    if ( m_fileRenderer )
        delete m_fileRenderer;
    m_fileRenderer = new WorkflowFileRenderer();
 
    WorkflowFileRendererDialog  *dialog = new WorkflowFileRendererDialog( m_fileRenderer, width, height );
    dialog->setModal( true );
    dialog->setOutputFileName( outputFileName );

    m_fileRenderer->initializeRenderer();
    m_fileRenderer->run( outputFileName, width, height, fps, vbitrate, abitrate );
    dialog->exec();
    delete dialog;
}

void 
MainWindow::on_actionRender_triggered()
{
    if ( checkVideoLength() )
567
    {
568
        m_renderer->killRenderer();
569 570 571 572 573 574 575 576
        //Setup dialog box for querying render parameters.
        RendererSettings    *settings = new RendererSettings;
        if ( settings->exec() == QDialog::Rejected )
        {
            delete settings;
            return ;
        }
        QString     outputFileName = settings->outputFileName();
577 578 579 580 581
        quint32     width          = settings->width();
        quint32     height         = settings->height();
        double      fps            = settings->fps();
        quint32     vbitrate       = settings->videoBitrate();
        quint32     abitrate       = settings->audioBitrate();
582
        delete settings;
583

584
        renderVideo( outputFileName, width, height, fps, vbitrate, abitrate );
585
    }
586 587
}

588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631
void 
MainWindow::on_actionShare_On_Youtube_triggered()
{
    if ( checkVideoLength() )
    {
        m_renderer->killRenderer();
        //Setup dialog box for querying youtube export parameters.
        ShareOnYoutube *exportToYoutube = new ShareOnYoutube;

        if ( exportToYoutube->exec() == QDialog::Rejected )
        {
            delete exportToYoutube;
            return ;
        }

        QString username     = exportToYoutube->username();
        QString password     = exportToYoutube->password();
        QString title        = exportToYoutube->title();
        QString category     = exportToYoutube->category();
        QString description  = exportToYoutube->description();
        QString tags         = exportToYoutube->tags();
        quint32 width        = exportToYoutube->width();
        quint32 height       = exportToYoutube->height();
        bool    videoPrivacy = exportToYoutube->videoPrivacy();

        delete exportToYoutube;

        qDebug()<< username << password << title << category << description << tags << width << height << videoPrivacy;

        //here add code to render video using WorkflowFileRenderer... to a temp folder, using QTemporaryFolder
        QTemporaryFile tmp( "vlmc-youtube.avi" );
        tmp.setAutoRemove( false );
        tmp.open();

        qDebug()<< tmp.fileTemplate() << tmp.fileName() << QDir::tempPath();

        renderVideo( tmp.fileName(), width, height, 30.0, 4000, 256 );

        //Add code here to init Youtube Uploader with the file, do stuff :D...
    }
}

void 
MainWindow::on_actionNew_Project_triggered()
632
{
633
    m_pWizard->restart();
634
    m_pWizard->show();
635 636
}

637 638
void    
MainWindow::on_actionHelp_triggered()
639 640
{
    QDesktopServices::openUrl( QUrl( "http://vlmc.org" ) );
641 642
}

643 644
void    
MainWindow::zoomIn()
Ludovic Fauvet's avatar
Ludovic Fauvet committed
645 646 647 648
{
    m_zoomSlider->setValue( m_zoomSlider->value() - 1 );
}

649 650
void    
MainWindow::zoomOut()
Ludovic Fauvet's avatar
Ludovic Fauvet committed
651 652 653
{
    m_zoomSlider->setValue( m_zoomSlider->value() + 1 );
}
Ludovic Fauvet's avatar
Ludovic Fauvet committed
654

655 656
void    
MainWindow::on_actionFullscreen_triggered( bool checked )
Ludovic Fauvet's avatar
Ludovic Fauvet committed
657 658 659 660 661 662
{
    if ( checked )
        showFullScreen();
    else
        showNormal();
}
663

664 665
void    
MainWindow::registerWidgetInWindowMenu( QDockWidget* widget )
666
{
667
    m_ui.menuWindow->addAction( widget->toggleViewAction() );
668
}
669

670 671
void    
MainWindow::toolButtonClicked( int id )
672 673 674
{
    emit toolChanged( (ToolButtons)id );
}
675

676 677
void 
MainWindow::on_actionBypass_effects_engine_toggled(bool)
678
{
679 680 681 682 683 684 685
//    EffectsEngine*  ee;
//
//    ee = MainWorkflow::getInstance()->getEffectsEngine();
//    if (toggled)
//        ee->enable();
//    else
//       ee->disable();
686 687
    return ;
}
688

689 690
void 
MainWindow::on_actionProject_Preferences_triggered()
691
{
692
  m_projectPreferences->show();
693
}
694

695 696
void    
MainWindow::closeEvent( QCloseEvent* e )
697
{
698 699
    GUIProjectManager   *pm = GUIProjectManager::getInstance();
    if ( pm->askForSaveIfModified() )
700
        e->accept();
701 702
    else
        e->ignore();
703
}
704

705 706
void   
MainWindow::projectUpdated( const QString& projectName, bool savedStatus )
707 708
{
    QString title = tr( "VideoLAN Movie Creator" );
709
    title += " - ";
710 711 712 713 714
    title += projectName;
    if ( savedStatus == false )
        title += " *";
    setWindowTitle( title );
}
715

716 717
void   
MainWindow::on_actionClose_Project_triggered()
718
{
719
    GUIProjectManager::getInstance()->closeProject();
720 721
}

722 723
void    
MainWindow::on_actionUndo_triggered()
724 725 726 727
{
    UndoStack::getInstance( this )->undo();
}

728 729
void    
MainWindow::on_actionRedo_triggered()
730 731 732 733
{
    UndoStack::getInstance( this )->redo();
}

734 735
void    
MainWindow::on_actionCrash_triggered()
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
736
{
737 738 739 740 741
    //WARNING: read this part at your own risk !!
    //I'm not responsible if you puke while reading this :D
    QString str;
    int test = 1 / str.length();
    Q_UNUSED( test );
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
742
}
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
743

744 745
bool    
MainWindow::restoreSession()
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
746 747
{
    QSettings   s;
748
    bool        fileCreated = false;
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
749 750
    bool        ret = false;

751 752
    fileCreated = s.contains( "VlmcVersion" );
    if ( fileCreated == true )
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
753
    {
754
        bool        cleanQuit = s.value( "CleanQuit", true ).toBool();
755 756 757 758 759 760 761

        // Restore the geometry
        restoreGeometry( s.value( "MainWindowGeometry" ).toByteArray() );
        // Restore the layout
        restoreState( s.value( "MainWindowState" ).toByteArray() );

        if ( cleanQuit == false )
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
762
        {
763
            QMessageBox::StandardButton res = QMessageBox::question( this, tr( "Crash recovery" ), tr( "VLMC didn't closed nicely. Do you wan't to recover your project?" ),
764 765 766
                                   QMessageBox::Yes | QMessageBox::No, QMessageBox::Yes );
            if ( res == QMessageBox::Yes )
            {
767
                if ( GUIProjectManager::getInstance()->loadEmergencyBackup() == true )
768 769
                    ret = true;
                else
770
                    QMessageBox::warning( this, tr( "Can't restore project" ), tr( "VLMC didn't manage to restore your project. We apology for the inconvenience" ) );
771
            }
Hugo Beauzee-Luyssen's avatar
Hugo Beauzee-Luyssen committed
772 773 774 775 776 777
        }
    }
    s.setValue( "CleanQuit", false );
    s.sync();
    return ret;
}
778

779 780
void    
MainWindow::on_actionImport_triggered()
781 782 783
{
    m_importController->exec();
}
784

785 786
void    
MainWindow::canUndoChanged( bool canUndo )
787 788 789 790
{
    m_ui.actionUndo->setEnabled( canUndo );
}

791 792
void    
MainWindow::canRedoChanged( bool canRedo )
793 794 795 796
{
    m_ui.actionRedo->setEnabled( canRedo );
}

Ludovic Fauvet's avatar
Ludovic Fauvet committed
797
#ifdef WITH_CRASHBUTTON
798 799
void
MainWindow::setupCrashTester()
800 801 802 803 804 805 806 807
{
    QAction* actionCrash = new QAction( this );
    actionCrash->setObjectName( QString::fromUtf8( "actionCrash" ) );
    m_ui.menuTools->addAction( actionCrash );
    actionCrash->setText( QApplication::translate( "MainWindow", "Crash", 0, QApplication::UnicodeUTF8 ) );
    connect( actionCrash, SIGNAL( triggered( bool ) ), this, SLOT( on_actionCrash_triggered() ) );
}
#endif
808