• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

mcallegari / qlcplus / 7252848206

18 Dec 2023 07:26PM UTC coverage: 32.067% (+0.001%) from 32.066%
7252848206

push

github

mcallegari
Code style review #1427

199 of 628 new or added lines in 101 files covered. (31.69%)

8 existing lines in 2 files now uncovered.

15169 of 47304 relevant lines covered (32.07%)

23733.74 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

44.77
/ui/src/virtualconsole/virtualconsole.cpp
1
/*
2
  Q Light Controller Plus
3
  virtualconsole.cpp
4

5
  Copyright (c) Heikki Junnila
6
                Massimo Callegari
7

8
  Licensed under the Apache License, Version 2.0 (the "License");
9
  you may not use this file except in compliance with the License.
10
  You may obtain a copy of the License at
11

12
      http://www.apache.org/licenses/LICENSE-2.0.txt
13

14
  Unless required by applicable law or agreed to in writing, software
15
  distributed under the License is distributed on an "AS IS" BASIS,
16
  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17
  See the License for the specific language governing permissions and
18
  limitations under the License.
19
*/
20

21
#include <QXmlStreamReader>
22
#include <QXmlStreamWriter>
23
#include <QApplication>
24
#include <QInputDialog>
25
#include <QColorDialog>
26
#include <QActionGroup>
27
#include <QHBoxLayout>
28
#include <QVBoxLayout>
29
#include <QMessageBox>
30
#include <QFileDialog>
31
#include <QFontDialog>
32
#include <QScrollArea>
33
#include <QSettings>
34
#include <QKeyEvent>
35
#include <QMenuBar>
36
#include <QToolBar>
37
#include <QString>
38
#include <QDebug>
39
#include <QMenu>
40
#include <QList>
41

42
#include "vcpropertieseditor.h"
43
#include "addvcbuttonmatrix.h"
44
#include "addvcslidermatrix.h"
45
#include "vcaudiotriggers.h"
46
#include "virtualconsole.h"
47
#include "vcproperties.h"
48
#include "vcspeeddial.h"
49
#include "vcsoloframe.h"
50
#include "vcdockarea.h"
51
#include "vccuelist.h"
52
#include "vcbutton.h"
53
#include "vcslider.h"
54
#include "vcmatrix.h"
55
#include "vcframe.h"
56
#include "vclabel.h"
57
#include "vcxypad.h"
58
#include "vcclock.h"
59
#include "doc.h"
60

61
#define SETTINGS_VC_SIZE "virtualconsole/size"
62

63
VirtualConsole* VirtualConsole::s_instance = NULL;
64

65
/****************************************************************************
66
 * Initialization
67
 ****************************************************************************/
68

69
VirtualConsole::VirtualConsole(QWidget* parent, Doc* doc)
76✔
70
    : QWidget(parent)
71
    , m_doc(doc)
72
    , m_latestWidgetId(0)
73

74
    , m_editAction(EditNone)
75
    , m_toolbar(NULL)
76

77
    , m_addActionGroup(NULL)
78
    , m_editActionGroup(NULL)
79
    , m_bgActionGroup(NULL)
80
    , m_fgActionGroup(NULL)
81
    , m_fontActionGroup(NULL)
82
    , m_frameActionGroup(NULL)
83
    , m_stackingActionGroup(NULL)
84

85
    , m_addButtonAction(NULL)
86
    , m_addButtonMatrixAction(NULL)
87
    , m_addSliderAction(NULL)
88
    , m_addSliderMatrixAction(NULL)
89
    , m_addKnobAction(NULL)
90
    , m_addSpeedDialAction(NULL)
91
    , m_addXYPadAction(NULL)
92
    , m_addCueListAction(NULL)
93
    , m_addFrameAction(NULL)
94
    , m_addSoloFrameAction(NULL)
95
    , m_addLabelAction(NULL)
96
    , m_addAudioTriggersAction(NULL)
97
    , m_addClockAction(NULL)
98
    , m_addAnimationAction(NULL)
99

100
    , m_toolsSettingsAction(NULL)
101

102
    , m_editCutAction(NULL)
103
    , m_editCopyAction(NULL)
104
    , m_editPasteAction(NULL)
105
    , m_editDeleteAction(NULL)
106
    , m_editPropertiesAction(NULL)
107
    , m_editRenameAction(NULL)
108

109
    , m_bgColorAction(NULL)
110
    , m_bgImageAction(NULL)
111
    , m_bgDefaultAction(NULL)
112

113
    , m_fgColorAction(NULL)
114
    , m_fgDefaultAction(NULL)
115

116
    , m_fontAction(NULL)
117
    , m_resetFontAction(NULL)
118

119
    , m_frameSunkenAction(NULL)
120
    , m_frameRaisedAction(NULL)
121
    , m_frameNoneAction(NULL)
122

123
    , m_stackingRaiseAction(NULL)
124
    , m_stackingLowerAction(NULL)
125

126
    , m_customMenu(NULL)
127
    , m_editMenu(NULL)
128
    , m_addMenu(NULL)
129

130
    , m_dockArea(NULL)
131
    , m_contentsLayout(NULL)
132
    , m_scrollArea(NULL)
133
    , m_contents(NULL)
134

135
    , m_liveEdit(false)
76✔
136
{
137
    Q_ASSERT(s_instance == NULL);
76✔
138
    s_instance = this;
76✔
139

140
    Q_ASSERT(doc != NULL);
76✔
141

142
    /* Main layout */
143
    new QHBoxLayout(this);
76✔
144
    layout()->setContentsMargins(1, 1, 1, 1);
76✔
145
    layout()->setSpacing(1);
76✔
146

147
    initActions();
76✔
148
    initDockArea();
76✔
149
    m_contentsLayout = new QVBoxLayout;
76✔
150
    layout()->addItem(m_contentsLayout);
76✔
151
    initMenuBar();
76✔
152
    initContents();
76✔
153

154
    // Propagate mode changes to all widgets
155
    connect(m_doc, SIGNAL(modeChanged(Doc::Mode)),
76✔
156
            this, SLOT(slotModeChanged(Doc::Mode)));
157

158
    // Use the initial mode
159
    slotModeChanged(m_doc->mode());
76✔
160

161
    // Nothing is selected
162
    updateActions();
76✔
163
}
76✔
164

165
VirtualConsole::~VirtualConsole()
152✔
166
{
167
    s_instance = NULL;
76✔
168
}
152✔
169

170
VirtualConsole* VirtualConsole::instance()
822✔
171
{
172
    return s_instance;
822✔
173
}
174

175
Doc *VirtualConsole::getDoc()
×
176
{
177
    return m_doc;
×
178
}
179

180
quint32 VirtualConsole::newWidgetId()
1✔
181
{
182
    /* This results in an endless loop if there are UINT_MAX-1 widgets. That,
183
       however, seems a bit unlikely. */
184
    while (m_widgetsMap.contains(m_latestWidgetId) ||
2✔
185
           m_latestWidgetId == VCWidget::invalidId())
1✔
186
    {
187
        m_latestWidgetId++;
×
188
    }
189

190
    return m_latestWidgetId;
1✔
191
}
192

193
/*****************************************************************************
194
 * Properties
195
 *****************************************************************************/
196

197
VCProperties VirtualConsole::properties() const
154✔
198
{
199
    return m_properties;
154✔
200
}
201

202
/*****************************************************************************
203
 * Selected widget
204
 *****************************************************************************/
205

206
void VirtualConsole::setEditAction(VirtualConsole::EditAction action)
×
207
{
208
    m_editAction = action;
×
209
}
×
210

211
VirtualConsole::EditAction VirtualConsole::editAction() const
×
212
{
213
    return m_editAction;
×
214
}
215

216
const QList <VCWidget*> VirtualConsole::selectedWidgets() const
5✔
217
{
218
    return m_selectedWidgets;
5✔
219
}
220

221
void VirtualConsole::setWidgetSelected(VCWidget* widget, bool select)
4✔
222
{
223
    Q_ASSERT(widget != NULL);
4✔
224

225
    if (select == false)
4✔
226
    {
227
        m_selectedWidgets.removeAll(widget);
×
228
        widget->update();
×
229
    }
230
    else if (select == true && m_selectedWidgets.indexOf(widget) == -1)
4✔
231
    {
232
        m_selectedWidgets.append(widget);
4✔
233
        widget->update();
4✔
234
    }
235

236
    /* Change the custom menu to the latest-selected widget's menu */
237
    updateCustomMenu();
4✔
238

239
    /* Enable or disable actions */
240
    updateActions();
4✔
241
}
4✔
242

243
bool VirtualConsole::isWidgetSelected(VCWidget* widget) const
31✔
244
{
245
    if (widget == NULL || m_selectedWidgets.indexOf(widget) == -1)
31✔
246
        return false;
27✔
247
    else
248
        return true;
4✔
249
}
250

251
void VirtualConsole::clearWidgetSelection()
6✔
252
{
253
    /* Get a copy of selected widget list */
254
    QList <VCWidget*> widgets(m_selectedWidgets);
12✔
255

256
    /* Clear the list so isWidgetSelected() returns false for all widgets */
257
    m_selectedWidgets.clear();
6✔
258

259
    /* Update all widgets to clear the selection frame around them */
260
    QListIterator <VCWidget*> it(widgets);
12✔
261
    while (it.hasNext() == true)
7✔
262
        it.next()->update();
1✔
263

264
    /* Change the custom menu to the latest-selected widget's menu */
265
    updateCustomMenu();
6✔
266

267
    /* Enable or disable actions */
268
    updateActions();
6✔
269
}
6✔
270

271
void VirtualConsole::reselectWidgets()
×
272
{
273
    QList <VCWidget*> widgets(m_selectedWidgets);
×
274
    clearWidgetSelection();
×
275
    foreach (VCWidget* w, widgets)
×
276
        setWidgetSelected(w, true);
×
277
}
×
278

279
/*****************************************************************************
280
 * Actions, menu- and toolbar
281
 *****************************************************************************/
282

283
QMenu* VirtualConsole::customMenu() const
×
284
{
285
    return m_customMenu;
×
286
}
287

288
QMenu* VirtualConsole::editMenu() const
×
289
{
290
    return m_editMenu;
×
291
}
292

293
QMenu* VirtualConsole::addMenu() const
8✔
294
{
295
    return m_addMenu;
8✔
296
}
297

298
void VirtualConsole::initActions()
76✔
299
{
300
    /* Add menu actions */
301
    m_addButtonAction = new QAction(QIcon(":/button.png"), tr("New Button"), this);
76✔
302
    connect(m_addButtonAction, SIGNAL(triggered(bool)), this, SLOT(slotAddButton()), Qt::QueuedConnection);
76✔
303

304
    m_addButtonMatrixAction = new QAction(QIcon(":/buttonmatrix.png"), tr("New Button Matrix"), this);
76✔
305
    connect(m_addButtonMatrixAction, SIGNAL(triggered(bool)), this, SLOT(slotAddButtonMatrix()), Qt::QueuedConnection);
76✔
306

307
    m_addSliderAction = new QAction(QIcon(":/slider.png"), tr("New Slider"), this);
76✔
308
    connect(m_addSliderAction, SIGNAL(triggered(bool)), this, SLOT(slotAddSlider()), Qt::QueuedConnection);
76✔
309

310
    m_addSliderMatrixAction = new QAction(QIcon(":/slidermatrix.png"), tr("New Slider Matrix"), this);
76✔
311
    connect(m_addSliderMatrixAction, SIGNAL(triggered(bool)), this, SLOT(slotAddSliderMatrix()), Qt::QueuedConnection);
76✔
312

313
    m_addKnobAction = new QAction(QIcon(":/knob.png"), tr("New Knob"), this);
76✔
314
    connect(m_addKnobAction, SIGNAL(triggered(bool)), this, SLOT(slotAddKnob()), Qt::QueuedConnection);
76✔
315

316
    m_addSpeedDialAction = new QAction(QIcon(":/speed.png"), tr("New Speed Dial"), this);
76✔
317
    connect(m_addSpeedDialAction, SIGNAL(triggered(bool)), this, SLOT(slotAddSpeedDial()), Qt::QueuedConnection);
76✔
318

319
    m_addXYPadAction = new QAction(QIcon(":/xypad.png"), tr("New XY pad"), this);
76✔
320
    connect(m_addXYPadAction, SIGNAL(triggered(bool)), this, SLOT(slotAddXYPad()), Qt::QueuedConnection);
76✔
321

322
    m_addCueListAction = new QAction(QIcon(":/cuelist.png"), tr("New Cue list"), this);
76✔
323
    connect(m_addCueListAction, SIGNAL(triggered(bool)), this, SLOT(slotAddCueList()), Qt::QueuedConnection);
76✔
324

325
    m_addFrameAction = new QAction(QIcon(":/frame.png"), tr("New Frame"), this);
76✔
326
    connect(m_addFrameAction, SIGNAL(triggered(bool)), this, SLOT(slotAddFrame()), Qt::QueuedConnection);
76✔
327

328
    m_addSoloFrameAction = new QAction(QIcon(":/soloframe.png"), tr("New Solo frame"), this);
76✔
329
    connect(m_addSoloFrameAction, SIGNAL(triggered(bool)), this, SLOT(slotAddSoloFrame()), Qt::QueuedConnection);
76✔
330

331
    m_addLabelAction = new QAction(QIcon(":/label.png"), tr("New Label"), this);
76✔
332
    connect(m_addLabelAction, SIGNAL(triggered(bool)), this, SLOT(slotAddLabel()), Qt::QueuedConnection);
76✔
333

334
    m_addAudioTriggersAction = new QAction(QIcon(":/audioinput.png"), tr("New Audio Triggers"), this);
76✔
335
    connect(m_addAudioTriggersAction, SIGNAL(triggered(bool)), this, SLOT(slotAddAudioTriggers()), Qt::QueuedConnection);
76✔
336

337
    m_addClockAction = new QAction(QIcon(":/clock.png"), tr("New Clock"), this);
76✔
338
    connect(m_addClockAction, SIGNAL(triggered(bool)), this, SLOT(slotAddClock()), Qt::QueuedConnection);
76✔
339

340
    m_addAnimationAction = new QAction(QIcon(":/animation.png"), tr("New Animation"), this);
76✔
341
    connect(m_addAnimationAction, SIGNAL(triggered(bool)), this, SLOT(slotAddAnimation()), Qt::QueuedConnection);
76✔
342

343
    /* Put add actions under the same group */
344
    m_addActionGroup = new QActionGroup(this);
76✔
345
    m_addActionGroup->setExclusive(false);
76✔
346
    m_addActionGroup->addAction(m_addButtonAction);
76✔
347
    m_addActionGroup->addAction(m_addButtonMatrixAction);
76✔
348
    m_addActionGroup->addAction(m_addSliderAction);
76✔
349
    m_addActionGroup->addAction(m_addSliderMatrixAction);
76✔
350
    m_addActionGroup->addAction(m_addKnobAction);
76✔
351
    m_addActionGroup->addAction(m_addSpeedDialAction);
76✔
352
    m_addActionGroup->addAction(m_addXYPadAction);
76✔
353
    m_addActionGroup->addAction(m_addCueListAction);
76✔
354
    m_addActionGroup->addAction(m_addFrameAction);
76✔
355
    m_addActionGroup->addAction(m_addSoloFrameAction);
76✔
356
    m_addActionGroup->addAction(m_addLabelAction);
76✔
357
    m_addActionGroup->addAction(m_addAudioTriggersAction);
76✔
358
    m_addActionGroup->addAction(m_addClockAction);
76✔
359
    m_addActionGroup->addAction(m_addAnimationAction);
76✔
360

361
    /* Tools menu actions */
362
    m_toolsSettingsAction = new QAction(QIcon(":/configure.png"), tr("Virtual Console Settings"), this);
76✔
363
    connect(m_toolsSettingsAction, SIGNAL(triggered(bool)), this, SLOT(slotToolsSettings()));
76✔
364
    // Prevent this action from ending up to the application menu on OSX
365
    // and crashing the app after VC window is closed.
366
    m_toolsSettingsAction->setMenuRole(QAction::NoRole);
76✔
367

368
    /* Edit menu actions */
369
    m_editCutAction = new QAction(QIcon(":/editcut.png"), tr("Cut"), this);
76✔
370
    connect(m_editCutAction, SIGNAL(triggered(bool)), this, SLOT(slotEditCut()));
76✔
371

372
    m_editCopyAction = new QAction(QIcon(":/editcopy.png"), tr("Copy"), this);
76✔
373
    connect(m_editCopyAction, SIGNAL(triggered(bool)), this, SLOT(slotEditCopy()));
76✔
374

375
    m_editPasteAction = new QAction(QIcon(":/editpaste.png"), tr("Paste"), this);
76✔
376
    m_editPasteAction->setEnabled(false);
76✔
377
    connect(m_editPasteAction, SIGNAL(triggered(bool)), this, SLOT(slotEditPaste()));
76✔
378

379
    m_editDeleteAction = new QAction(QIcon(":/editdelete.png"), tr("Delete"), this);
76✔
380
    connect(m_editDeleteAction, SIGNAL(triggered(bool)), this, SLOT(slotEditDelete()));
76✔
381

382
    m_editPropertiesAction = new QAction(QIcon(":/edit.png"), tr("Widget Properties"), this);
76✔
383
    connect(m_editPropertiesAction, SIGNAL(triggered(bool)), this, SLOT(slotEditProperties()));
76✔
384

385
    m_editRenameAction = new QAction(QIcon(":/editclear.png"), tr("Rename Widget"), this);
76✔
386
    connect(m_editRenameAction, SIGNAL(triggered(bool)), this, SLOT(slotEditRename()));
76✔
387

388
    /* Put edit actions under the same group */
389
    m_editActionGroup = new QActionGroup(this);
76✔
390
    m_editActionGroup->setExclusive(false);
76✔
391
    m_editActionGroup->addAction(m_editCutAction);
76✔
392
    m_editActionGroup->addAction(m_editCopyAction);
76✔
393
    m_editActionGroup->addAction(m_editPasteAction);
76✔
394
    m_editActionGroup->addAction(m_editDeleteAction);
76✔
395
    m_editActionGroup->addAction(m_editPropertiesAction);
76✔
396
    m_editActionGroup->addAction(m_editRenameAction);
76✔
397

398
    /* Background menu actions */
399
    m_bgColorAction = new QAction(QIcon(":/color.png"), tr("Background Color"), this);
76✔
400
    connect(m_bgColorAction, SIGNAL(triggered(bool)), this, SLOT(slotBackgroundColor()));
76✔
401

402
    m_bgImageAction = new QAction(QIcon(":/image.png"), tr("Background Image"), this);
76✔
403
    connect(m_bgImageAction, SIGNAL(triggered(bool)), this, SLOT(slotBackgroundImage()));
76✔
404

405
    m_bgDefaultAction = new QAction(QIcon(":/undo.png"), tr("Default"), this);
76✔
406
    connect(m_bgDefaultAction, SIGNAL(triggered(bool)), this, SLOT(slotBackgroundNone()));
76✔
407

408
    /* Put BG actions under the same group */
409
    m_bgActionGroup = new QActionGroup(this);
76✔
410
    m_bgActionGroup->setExclusive(false);
76✔
411
    m_bgActionGroup->addAction(m_bgColorAction);
76✔
412
    m_bgActionGroup->addAction(m_bgImageAction);
76✔
413
    m_bgActionGroup->addAction(m_bgDefaultAction);
76✔
414

415
    /* Foreground menu actions */
416
    m_fgColorAction = new QAction(QIcon(":/fontcolor.png"), tr("Font Colour"), this);
76✔
417
    connect(m_fgColorAction, SIGNAL(triggered(bool)), this, SLOT(slotForegroundColor()));
76✔
418

419
    m_fgDefaultAction = new QAction(QIcon(":/undo.png"), tr("Default"), this);
76✔
420
    connect(m_fgDefaultAction, SIGNAL(triggered(bool)), this, SLOT(slotForegroundNone()));
76✔
421

422
    /* Put FG actions under the same group */
423
    m_fgActionGroup = new QActionGroup(this);
76✔
424
    m_fgActionGroup->setExclusive(false);
76✔
425
    m_fgActionGroup->addAction(m_fgColorAction);
76✔
426
    m_fgActionGroup->addAction(m_fgDefaultAction);
76✔
427

428
    /* Font menu actions */
429
    m_fontAction = new QAction(QIcon(":/fonts.png"), tr("Font"), this);
76✔
430
    connect(m_fontAction, SIGNAL(triggered(bool)), this, SLOT(slotFont()));
76✔
431

432
    m_resetFontAction = new QAction(QIcon(":/undo.png"), tr("Default"), this);
76✔
433
    connect(m_resetFontAction, SIGNAL(triggered(bool)), this, SLOT(slotResetFont()));
76✔
434

435
    /* Put font actions under the same group */
436
    m_fontActionGroup = new QActionGroup(this);
76✔
437
    m_fontActionGroup->setExclusive(false);
76✔
438
    m_fontActionGroup->addAction(m_fontAction);
76✔
439
    m_fontActionGroup->addAction(m_resetFontAction);
76✔
440

441
    /* Frame menu actions */
442
    m_frameSunkenAction = new QAction(QIcon(":/framesunken.png"), tr("Sunken"), this);
76✔
443
    connect(m_frameSunkenAction, SIGNAL(triggered(bool)), this, SLOT(slotFrameSunken()));
76✔
444

445
    m_frameRaisedAction = new QAction(QIcon(":/frameraised.png"), tr("Raised"), this);
76✔
446
    connect(m_frameRaisedAction, SIGNAL(triggered(bool)), this, SLOT(slotFrameRaised()));
76✔
447

448
    m_frameNoneAction = new QAction(QIcon(":/framenone.png"), tr("None"), this);
76✔
449
    connect(m_frameNoneAction, SIGNAL(triggered(bool)), this, SLOT(slotFrameNone()));
76✔
450

451
    /* Put frame actions under the same group */
452
    m_frameActionGroup = new QActionGroup(this);
76✔
453
    m_frameActionGroup->setExclusive(false);
76✔
454
    m_frameActionGroup->addAction(m_frameRaisedAction);
76✔
455
    m_frameActionGroup->addAction(m_frameSunkenAction);
76✔
456
    m_frameActionGroup->addAction(m_frameNoneAction);
76✔
457

458
    /* Stacking menu actions */
459
    m_stackingRaiseAction = new QAction(QIcon(":/up.png"), tr("Bring to front"), this);
76✔
460
    connect(m_stackingRaiseAction, SIGNAL(triggered(bool)), this, SLOT(slotStackingRaise()));
76✔
461

462
    m_stackingLowerAction = new QAction(QIcon(":/down.png"), tr("Send to back"), this);
76✔
463
    connect(m_stackingLowerAction, SIGNAL(triggered(bool)), this, SLOT(slotStackingLower()));
76✔
464

465
    /* Put stacking actions under the same group */
466
    m_stackingActionGroup = new QActionGroup(this);
76✔
467
    m_stackingActionGroup->setExclusive(false);
76✔
468
    m_stackingActionGroup->addAction(m_stackingRaiseAction);
76✔
469
    m_stackingActionGroup->addAction(m_stackingLowerAction);
76✔
470
}
76✔
471

472
void VirtualConsole::initMenuBar()
76✔
473
{
474
    /* Add menu */
475
    m_addMenu = new QMenu(this);
76✔
476
    m_addMenu->setTitle(tr("&Add"));
76✔
477
    m_addMenu->addAction(m_addButtonAction);
76✔
478
    m_addMenu->addAction(m_addButtonMatrixAction);
76✔
479
    m_addMenu->addSeparator();
76✔
480
    m_addMenu->addAction(m_addSliderAction);
76✔
481
    m_addMenu->addAction(m_addSliderMatrixAction);
76✔
482
    m_addMenu->addAction(m_addKnobAction);
76✔
483
    m_addMenu->addAction(m_addSpeedDialAction);
76✔
484
    m_addMenu->addSeparator();
76✔
485
    m_addMenu->addAction(m_addXYPadAction);
76✔
486
    m_addMenu->addAction(m_addCueListAction);
76✔
487
    m_addMenu->addAction(m_addAnimationAction);
76✔
488
    m_addMenu->addAction(m_addAudioTriggersAction);
76✔
489
    m_addMenu->addSeparator();
76✔
490
    m_addMenu->addAction(m_addFrameAction);
76✔
491
    m_addMenu->addAction(m_addSoloFrameAction);
76✔
492
    m_addMenu->addAction(m_addLabelAction);
76✔
493
    m_addMenu->addAction(m_addClockAction);
76✔
494

495
    /* Edit menu */
496
    m_editMenu = new QMenu(this);
76✔
497
    m_editMenu->setTitle(tr("&Edit"));
76✔
498
    m_editMenu->addAction(m_editCutAction);
76✔
499
    m_editMenu->addAction(m_editCopyAction);
76✔
500
    m_editMenu->addAction(m_editPasteAction);
76✔
501
    m_editMenu->addAction(m_editDeleteAction);
76✔
502
    m_editMenu->addSeparator();
76✔
503
    m_editMenu->addAction(m_editPropertiesAction);
76✔
504
    m_editMenu->addAction(m_editRenameAction);
76✔
505
    m_editMenu->addSeparator();
76✔
506

507
    /* Background Menu */
508
    QMenu* bgMenu = new QMenu(m_editMenu);
76✔
509
    bgMenu->setTitle(tr("&Background"));
76✔
510
    m_editMenu->addMenu(bgMenu);
76✔
511
    bgMenu->addAction(m_bgColorAction);
76✔
512
    bgMenu->addAction(m_bgImageAction);
76✔
513
    bgMenu->addAction(m_bgDefaultAction);
76✔
514

515
    /* Foreground menu */
516
    QMenu* fgMenu = new QMenu(m_editMenu);
76✔
517
    fgMenu->setTitle(tr("&Foreground"));
76✔
518
    m_editMenu->addMenu(fgMenu);
76✔
519
    fgMenu->addAction(m_fgColorAction);
76✔
520
    fgMenu->addAction(m_fgDefaultAction);
76✔
521

522
    /* Font menu */
523
    QMenu* fontMenu = new QMenu(m_editMenu);
76✔
524
    fontMenu->setTitle(tr("F&ont"));
76✔
525
    m_editMenu->addMenu(fontMenu);
76✔
526
    fontMenu->addAction(m_fontAction);
76✔
527
    fontMenu->addAction(m_resetFontAction);
76✔
528

529
    /* Frame menu */
530
    QMenu* frameMenu = new QMenu(m_editMenu);
76✔
531
    frameMenu->setTitle(tr("F&rame"));
76✔
532
    m_editMenu->addMenu(frameMenu);
76✔
533
    frameMenu->addAction(m_frameSunkenAction);
76✔
534
    frameMenu->addAction(m_frameRaisedAction);
76✔
535
    frameMenu->addAction(m_frameNoneAction);
76✔
536

537
    /* Stacking order menu */
538
    QMenu* stackMenu = new QMenu(m_editMenu);
76✔
539
    stackMenu->setTitle(tr("Stacking &order"));
76✔
540
    m_editMenu->addMenu(stackMenu);
76✔
541
    stackMenu->addAction(m_stackingRaiseAction);
76✔
542
    stackMenu->addAction(m_stackingLowerAction);
76✔
543

544
    /* Add a separator that separates the common edit items from a custom
545
       widget menu that gets appended to the edit menu when a selected
546
       widget provides one. */
547
    m_editMenu->addSeparator();
76✔
548

549
    /* Toolbar */
550
    m_toolbar = new QToolBar(this);
76✔
551
    m_toolbar->setIconSize(QSize(26,26));
76✔
552
    m_contentsLayout->addWidget(m_toolbar);
76✔
553

554
    m_toolbar->addAction(m_addButtonAction);
76✔
555
    m_toolbar->addAction(m_addButtonMatrixAction);
76✔
556
    m_toolbar->addAction(m_addSliderAction);
76✔
557
    m_toolbar->addAction(m_addSliderMatrixAction);
76✔
558
    m_toolbar->addAction(m_addKnobAction);
76✔
559
    m_toolbar->addAction(m_addSpeedDialAction);
76✔
560
    m_toolbar->addAction(m_addXYPadAction);
76✔
561
    m_toolbar->addAction(m_addCueListAction);
76✔
562
    m_toolbar->addAction(m_addAnimationAction);
76✔
563
    m_toolbar->addAction(m_addFrameAction);
76✔
564
    m_toolbar->addAction(m_addSoloFrameAction);
76✔
565
    m_toolbar->addAction(m_addLabelAction);
76✔
566
    m_toolbar->addAction(m_addAudioTriggersAction);
76✔
567
    m_toolbar->addAction(m_addClockAction);
76✔
568
    m_toolbar->addSeparator();
76✔
569
    m_toolbar->addAction(m_editCutAction);
76✔
570
    m_toolbar->addAction(m_editCopyAction);
76✔
571
    m_toolbar->addAction(m_editPasteAction);
76✔
572
    m_toolbar->addSeparator();
76✔
573
    m_toolbar->addAction(m_editDeleteAction);
76✔
574
    m_toolbar->addSeparator();
76✔
575
    m_toolbar->addAction(m_editPropertiesAction);
76✔
576
    m_toolbar->addAction(m_editRenameAction);
76✔
577
    m_toolbar->addSeparator();
76✔
578
    m_toolbar->addAction(m_stackingRaiseAction);
76✔
579
    m_toolbar->addAction(m_stackingLowerAction);
76✔
580
    m_toolbar->addSeparator();
76✔
581
    m_toolbar->addAction(m_bgColorAction);
76✔
582
    m_toolbar->addAction(m_bgImageAction);
76✔
583
    m_toolbar->addAction(m_fgColorAction);
76✔
584
    m_toolbar->addAction(m_fontAction);
76✔
585
    m_toolbar->addSeparator();
76✔
586
    m_toolbar->addAction(m_toolsSettingsAction);
76✔
587
}
76✔
588

589
void VirtualConsole::updateCustomMenu()
10✔
590
{
591
    /* Get rid of the custom menu, but delete it later because this might
592
       be called from the very menu that is being deleted. */
593
    if (m_customMenu != NULL)
10✔
594
    {
595
        delete m_customMenu;
6✔
596
        m_customMenu = NULL;
6✔
597
    }
598

599
    if (m_selectedWidgets.size() > 0)
10✔
600
    {
601
        /* Change the custom menu to the last selected widget's menu */
602
        VCWidget* latestWidget = m_selectedWidgets.last();
4✔
603
        m_customMenu = latestWidget->customMenu(m_editMenu);
4✔
604
        if (m_customMenu != NULL)
4✔
605
            m_editMenu->addMenu(m_customMenu);
2✔
606
    }
607
    else
608
    {
609
        /* Change the custom menu to the bottom frame's menu */
610
        Q_ASSERT(contents() != NULL);
6✔
611
        m_customMenu = contents()->customMenu(m_editMenu);
6✔
612
        if (m_customMenu != NULL)
6✔
613
            m_editMenu->addMenu(m_customMenu);
6✔
614
    }
615
}
10✔
616

617
void VirtualConsole::updateActions()
162✔
618
{
619
    /* When selected widgets is empty, all actions go to main draw area. */
620
    if (m_selectedWidgets.isEmpty() == true)
162✔
621
    {
622
        /* Enable widget additions to draw area */
623
        m_addActionGroup->setEnabled(true);
158✔
624

625
        /* Disable edit actions that can't be allowed for draw area */
626
        m_editCutAction->setEnabled(false);
158✔
627
        m_editCopyAction->setEnabled(false);
158✔
628
        m_editDeleteAction->setEnabled(false);
158✔
629
        m_editRenameAction->setEnabled(false);
158✔
630
        m_editPropertiesAction->setEnabled(false);
158✔
631

632
        /* All the rest are disabled for draw area, except BG & font */
633
        m_frameActionGroup->setEnabled(false);
158✔
634
        m_stackingActionGroup->setEnabled(false);
158✔
635

636
        /* Enable paste to draw area if there's something to paste */
637
        if (m_clipboard.isEmpty() == true)
158✔
638
            m_editPasteAction->setEnabled(false);
158✔
639
        else
640
            m_editPasteAction->setEnabled(true);
×
641
    }
642
    else
643
    {
644
        /* Enable edit actions for other widgets */
645
        m_editCutAction->setEnabled(true);
4✔
646
        m_editCopyAction->setEnabled(true);
4✔
647
        m_editDeleteAction->setEnabled(true);
4✔
648
        m_editRenameAction->setEnabled(true);
4✔
649
        m_editPropertiesAction->setEnabled(true);
4✔
650

651
        /* Enable all common properties */
652
        m_bgActionGroup->setEnabled(true);
4✔
653
        m_fgActionGroup->setEnabled(true);
4✔
654
        m_fontActionGroup->setEnabled(true);
4✔
655
        m_frameActionGroup->setEnabled(true);
4✔
656
        m_stackingActionGroup->setEnabled(true);
4✔
657

658
        /* Check, whether the last selected widget can hold children */
659
        if (m_selectedWidgets.last()->allowChildren() == true)
4✔
660
        {
661
            /* Enable paste for widgets that can hold children */
662
            if (m_clipboard.isEmpty() == true)
1✔
663
                m_editPasteAction->setEnabled(false);
1✔
664
            else
665
                m_editPasteAction->setEnabled(true);
×
666

667
            /* Enable also new additions */
668
            m_addActionGroup->setEnabled(true);
1✔
669
        }
670
        else
671
        {
672
            /* No pasted children possible */
673
            m_editPasteAction->setEnabled(false);
3✔
674
        }
675
    }
676

677
    if (contents()->children().count() == 0)
162✔
678
        m_latestWidgetId = 0;
156✔
679
}
162✔
680

681
/*****************************************************************************
682
 * Add menu callbacks
683
 *****************************************************************************/
684

685
VCWidget* VirtualConsole::closestParent() const
×
686
{
687
    /* If nothing is selected, return the bottom-most contents frame */
688
    if (m_selectedWidgets.isEmpty() == true)
×
689
        return contents();
×
690

691
    /* Find the next VCWidget in the hierarchy that accepts children */
692
    VCWidget* widget = m_selectedWidgets.last();
×
693
    while (widget != NULL)
×
694
    {
695
        if (widget->allowChildren() == true)
×
696
            return widget;
×
697
        else
698
            widget = qobject_cast<VCWidget*> (widget->parentWidget());
×
699
    }
700

701
    return NULL;
×
702
}
703

704
void VirtualConsole::connectWidgetToParent(VCWidget *widget, VCWidget *parent)
×
705
{
706
    if (parent->type() == VCWidget::FrameWidget
×
707
            || parent->type() == VCWidget::SoloFrameWidget)
×
708
    {
709
        VCFrame *frame = qobject_cast<VCFrame *>(parent);
×
710
        if (frame != NULL)
×
711
        {
712
            widget->setPage(frame->currentPage());
×
713
            frame->addWidgetToPageMap(widget);
×
714
        }
715
    }
716
    else
717
        widget->setPage(0);
×
718

719
    if (widget->type() == VCWidget::SliderWidget)
×
720
    {
721
        VCSlider *slider = qobject_cast<VCSlider *>(widget);
×
722
        if (slider != NULL)
×
723
        {
724
            connect(slider, SIGNAL(submasterValueChanged(qreal)),
×
725
                    parent, SLOT(slotSubmasterValueChanged(qreal)));
726
        }
727
    }
728
}
×
729

730
void VirtualConsole::disconnectWidgetFromParent(VCWidget *widget, VCWidget *parent)
×
731
{
732
    if (parent->type() == VCWidget::FrameWidget
×
733
            || parent->type() == VCWidget::SoloFrameWidget)
×
734
    {
735
        VCFrame *frame = qobject_cast<VCFrame *>(parent);
×
736
        if (frame != NULL)
×
737
            frame->removeWidgetFromPageMap(widget);
×
738
    }
739

740
    if (widget->type() == VCWidget::SliderWidget)
×
741
    {
742
        VCSlider *slider = qobject_cast<VCSlider *>(widget);
×
743
        if (slider != NULL)
×
744
        {
745
            disconnect(slider, SIGNAL(submasterValueChanged(qreal)),
×
746
                       parent, SLOT(slotSubmasterValueChanged(qreal)));
747
        }
748
    }
749
}
×
750

751
void VirtualConsole::slotAddButton()
×
752
{
753
    VCWidget* parent(closestParent());
×
754
    if (parent == NULL)
×
755
        return;
×
756

757
    VCButton* button = new VCButton(parent, m_doc);
×
758
    setupWidget(button, parent);
×
759
    m_doc->setModified();
×
760
}
761

762
void VirtualConsole::slotAddButtonMatrix()
×
763
{
764
    VCWidget* parent(closestParent());
×
765
    if (parent == NULL)
×
766
        return;
×
767

768
    AddVCButtonMatrix abm(this, m_doc);
×
769
    if (abm.exec() == QDialog::Rejected)
×
770
        return;
×
771

772
    int h = abm.horizontalCount();
×
773
    int v = abm.verticalCount();
×
774
    int sz = abm.buttonSize();
×
775

776
    VCFrame* frame = NULL;
×
777
    if (abm.frameStyle() == AddVCButtonMatrix::NormalFrame)
×
778
        frame = new VCFrame(parent, m_doc);
×
779
    else
780
        frame = new VCSoloFrame(parent, m_doc);
×
781
    Q_ASSERT(frame != NULL);
×
782
    addWidgetInMap(frame);
×
783
    frame->setHeaderVisible(false);
×
784
    connectWidgetToParent(frame, parent);
×
785

786
    // Resize the parent frame to fit the buttons nicely and toggle resizing off
787
    frame->resize(QSize((h * sz) + 20, (v * sz) + 20));
×
788
    frame->setAllowResize(false);
×
789

790
    for (int y = 0; y < v; y++)
×
791
    {
792
        for (int x = 0; x < h; x++)
×
793
        {
794
            VCButton* button = new VCButton(frame, m_doc);
×
795
            Q_ASSERT(button != NULL);
×
796
            addWidgetInMap(button);
×
797
            connectWidgetToParent(button, frame);
×
798
            button->move(QPoint(10 + (x * sz), 10 + (y * sz)));
×
799
            button->resize(QSize(sz, sz));
×
800
            button->show();
×
801

802
            int index = (y * h) + x;
×
803
            if (index < abm.functions().size())
×
804
            {
805
                quint32 fid = abm.functions().at(index);
×
806
                Function* function = m_doc->function(fid);
×
807
                if (function != NULL)
×
808
                {
809
                    button->setFunction(fid);
×
810
                    button->setCaption(function->name());
×
811
                }
812
            }
813
        }
814
    }
815

816
    // Show the frame after adding buttons to prevent flickering
817
    frame->show();
×
818
    frame->move(parent->lastClickPoint());
×
819
    frame->setAllowChildren(false); // Don't allow more children
×
820
    clearWidgetSelection();
×
821
    setWidgetSelected(frame, true);
×
822
    m_doc->setModified();
×
823
}
824

825
void VirtualConsole::slotAddSlider()
×
826
{
827
    VCWidget* parent(closestParent());
×
828
    if (parent == NULL)
×
829
        return;
×
830

831
    VCSlider* slider = new VCSlider(parent, m_doc);
×
832
    setupWidget(slider, parent);
×
833
    m_doc->setModified();
×
834
}
835

836
void VirtualConsole::slotAddSliderMatrix()
×
837
{
838
    VCWidget* parent(closestParent());
×
839
    if (parent == NULL)
×
840
        return;
×
841

842
    AddVCSliderMatrix avsm(this);
×
843
    if (avsm.exec() == QDialog::Rejected)
×
844
        return;
×
845

846
    int width = avsm.width();
×
847
    int height = avsm.height();
×
848
    int count = avsm.amount();
×
849

850
    VCFrame* frame = new VCFrame(parent, m_doc);
×
851
    Q_ASSERT(frame != NULL);
×
852
    addWidgetInMap(frame);
×
853
    frame->setHeaderVisible(false);
×
854
    connectWidgetToParent(frame, parent);
×
855

856
    // Resize the parent frame to fit the sliders nicely
857
    frame->resize(QSize((count * width) + 20, height + 20));
×
858
    frame->setAllowResize(false);
×
859

860
    for (int i = 0; i < count; i++)
×
861
    {
862
        VCSlider* slider = new VCSlider(frame, m_doc);
×
863
        Q_ASSERT(slider != NULL);
×
864
        addWidgetInMap(slider);
×
865
        connectWidgetToParent(slider, frame);
×
866
        slider->move(QPoint(10 + (width * i), 10));
×
867
        slider->resize(QSize(width, height));
×
868
        slider->show();
×
869
    }
870

871
    // Show the frame after adding buttons to prevent flickering
872
    frame->show();
×
873
    frame->move(parent->lastClickPoint());
×
874
    frame->setAllowChildren(false); // Don't allow more children
×
875
    clearWidgetSelection();
×
876
    setWidgetSelected(frame, true);
×
877
    m_doc->setModified();
×
878
}
879

880
void VirtualConsole::slotAddKnob()
×
881
{
882
    VCWidget* parent(closestParent());
×
883
    if (parent == NULL)
×
884
        return;
×
885

886
    VCSlider* knob = new VCSlider(parent, m_doc);
×
887
    setupWidget(knob, parent);
×
888
    knob->resize(QSize(60, 90));
×
889
    knob->setWidgetStyle(VCSlider::WKnob);
×
890
    knob->setCaption(tr("Knob %1").arg(knob->id()));
×
891
    m_doc->setModified();
×
892
}
893

894
void VirtualConsole::slotAddSpeedDial()
×
895
{
896
    VCWidget* parent(closestParent());
×
897
    if (parent == NULL)
×
898
        return;
×
899

900
    VCSpeedDial* dial = new VCSpeedDial(parent, m_doc);
×
901
    setupWidget(dial, parent);
×
902
    m_doc->setModified();
×
903
}
904

905
void VirtualConsole::slotAddXYPad()
×
906
{
907
    VCWidget* parent(closestParent());
×
908
    if (parent == NULL)
×
909
        return;
×
910

911
    VCXYPad* xypad = new VCXYPad(parent, m_doc);
×
912
    setupWidget(xypad, parent);
×
913
    m_doc->setModified();
×
914
}
915

916
void VirtualConsole::slotAddCueList()
×
917
{
918
    VCWidget* parent(closestParent());
×
919
    if (parent == NULL)
×
920
        return;
×
921

922
    VCCueList* cuelist = new VCCueList(parent, m_doc);
×
923
    setupWidget(cuelist, parent);
×
924
    m_doc->setModified();
×
925
}
926

927
void VirtualConsole::slotAddFrame()
×
928
{
929
    VCWidget* parent(closestParent());
×
930
    if (parent == NULL)
×
931
        return;
×
932

933
    VCFrame* frame = new VCFrame(parent, m_doc, true);
×
934
    setupWidget(frame, parent);
×
935
    m_doc->setModified();
×
936
}
937

938
void VirtualConsole::slotAddSoloFrame()
×
939
{
940
    VCWidget* parent(closestParent());
×
941
    if (parent == NULL)
×
942
        return;
×
943

944
    VCSoloFrame* soloframe = new VCSoloFrame(parent, m_doc, true);
×
945
    setupWidget(soloframe, parent);
×
946
    m_doc->setModified();
×
947
}
948

949
void VirtualConsole::slotAddLabel()
×
950
{
951
    VCWidget* parent(closestParent());
×
952
    if (parent == NULL)
×
953
        return;
×
954

955
    VCLabel* label = new VCLabel(parent, m_doc);
×
956
    setupWidget(label, parent);
×
957
    m_doc->setModified();
×
958
}
959

960
void VirtualConsole::slotAddAudioTriggers()
×
961
{
962
    VCWidget* parent(closestParent());
×
963
    if (parent == NULL)
×
964
        return;
×
965

966
    VCAudioTriggers* triggers = new VCAudioTriggers(parent, m_doc);
×
967
    setupWidget(triggers, parent);
×
968
    m_doc->setModified();
×
969
}
970

971
void VirtualConsole::slotAddClock()
×
972
{
973
    VCWidget* parent(closestParent());
×
974
    if (parent == NULL)
×
975
        return;
×
976

977
    VCClock* clock = new VCClock(parent, m_doc);
×
978
    setupWidget(clock, parent);
×
979
    m_doc->setModified();
×
980
}
981

982
void VirtualConsole::slotAddAnimation()
×
983
{
984
    VCWidget* parent(closestParent());
×
985
    if (parent == NULL)
×
986
        return;
×
987

988
    VCMatrix* matrix = new VCMatrix(parent, m_doc);
×
989
    setupWidget(matrix, parent);
×
990
    m_doc->setModified();
×
991
}
992

993
/*****************************************************************************
994
 * Tools menu callbacks
995
 *****************************************************************************/
996

997
void VirtualConsole::slotToolsSettings()
×
998
{
999
    VCPropertiesEditor vcpe(this, m_properties, m_doc->inputOutputMap());
×
1000
    if (vcpe.exec() == QDialog::Accepted)
×
1001
    {
1002
        m_properties = vcpe.properties();
×
1003
        contents()->resize(m_properties.size());
×
1004
        m_doc->inputOutputMap()->setGrandMasterChannelMode(m_properties.grandMasterChannelMode());
×
1005
        m_doc->inputOutputMap()->setGrandMasterValueMode(m_properties.grandMasterValueMode());
×
1006
        if (m_dockArea != NULL)
×
1007
            m_dockArea->setGrandMasterInvertedAppearance(m_properties.grandMasterSlideMode());
×
1008

1009
        QSettings settings;
×
1010
        settings.setValue(SETTINGS_BUTTON_SIZE, vcpe.buttonSize());
×
1011
        settings.setValue(SETTINGS_BUTTON_STATUSLED, vcpe.buttonStatusLED());
×
1012
        settings.setValue(SETTINGS_SLIDER_SIZE, vcpe.sliderSize());
×
1013
        settings.setValue(SETTINGS_SPEEDDIAL_SIZE, vcpe.speedDialSize());
×
1014
        settings.setValue(SETTINGS_SPEEDDIAL_VALUE, vcpe.speedDialValue());
×
1015
        settings.setValue(SETTINGS_XYPAD_SIZE, vcpe.xypadSize());
×
1016
        settings.setValue(SETTINGS_CUELIST_SIZE, vcpe.cuelistSize());
×
1017
        settings.setValue(SETTINGS_FRAME_SIZE, vcpe.frameSize());
×
1018
        settings.setValue(SETTINGS_SOLOFRAME_SIZE, vcpe.soloFrameSize());
×
1019
        settings.setValue(SETTINGS_AUDIOTRIGGERS_SIZE, vcpe.audioTriggersSize());
×
1020
        settings.setValue(SETTINGS_RGBMATRIX_SIZE, vcpe.rgbMatrixSize());
×
1021

1022
        m_doc->setModified();
×
1023
    }
1024
}
×
1025

1026
/*****************************************************************************
1027
 * Edit menu callbacks
1028
 *****************************************************************************/
1029

1030
void VirtualConsole::slotEditCut()
×
1031
{
1032
    /* No need to delete widgets in clipboard because they are actually just
1033
       MOVED to another parent during Paste when m_editAction == EditCut.
1034
       Cutting the widgets does nothing to them unless Paste is invoked. */
1035

1036
    /* Make the edit action valid only if there's something to cut */
1037
    if (m_selectedWidgets.size() == 0)
×
1038
    {
1039
        m_editAction = EditNone;
×
1040
        m_clipboard.clear();
×
1041
        m_editPasteAction->setEnabled(false);
×
1042
    }
1043
    else
1044
    {
1045
        m_editAction = EditCut;
×
1046
        m_clipboard = m_selectedWidgets;
×
1047
        m_editPasteAction->setEnabled(true);
×
1048
    }
1049

1050
    updateActions();
×
1051
}
×
1052

1053
void VirtualConsole::slotEditCopy()
×
1054
{
1055
    /* Make the edit action valid only if there's something to copy */
1056
    if (m_selectedWidgets.size() == 0)
×
1057
    {
1058
        m_editAction = EditNone;
×
1059
        m_clipboard.clear();
×
1060
        m_editPasteAction->setEnabled(false);
×
1061
    }
1062
    else
1063
    {
1064
        m_editAction = EditCopy;
×
1065
        m_clipboard = m_selectedWidgets;
×
1066
        m_editPasteAction->setEnabled(true);
×
1067
    }
1068
}
×
1069

1070
void VirtualConsole::slotEditPaste()
×
1071
{
1072
    if (m_clipboard.size() == 0)
×
1073
    {
1074
        /* Invalidate the edit action if there's nothing to paste */
1075
        m_editAction = EditNone;
×
1076
        m_editPasteAction->setEnabled(false);
×
1077
        return;
×
1078
    }
1079

1080
    VCWidget* parent;
1081
    VCWidget* widget;
1082
    QRect bounds;
×
1083

1084
    Q_ASSERT(contents() != NULL);
×
1085

1086
    /* Select the parent that gets the cut clipboard contents */
1087
    parent = closestParent();
×
1088

1089
    /* Get the bounding rect for all selected widgets */
1090
    QListIterator <VCWidget*> it(m_clipboard);
×
1091
    while (it.hasNext() == true)
×
1092
    {
1093
        widget = it.next();
×
1094
        Q_ASSERT(widget != NULL);
×
1095
        bounds = bounds.united(widget->geometry());
×
1096
    }
1097

1098
    /* Get the upcoming parent's last mouse click point */
1099
    QPoint cp(parent->lastClickPoint());
×
1100

1101
    if (m_editAction == EditCut)
×
1102
    {
1103
        it.toFront();
×
1104
        while (it.hasNext() == true)
×
1105
        {
1106
            widget = it.next();
×
1107
            Q_ASSERT(widget != NULL);
×
1108
            if (widget == parent)
×
1109
                continue;
×
1110

1111
            VCWidget* prevParent = qobject_cast<VCWidget*> (widget->parentWidget());
×
1112
            if (prevParent != NULL)
×
1113
                disconnectWidgetFromParent(widget, prevParent);
×
1114

1115
            /* Get widget's relative pos to the bounding rect */
1116
            QPoint p(widget->x() - bounds.x() + cp.x(),
×
1117
                     widget->y() - bounds.y() + cp.y());
×
1118

1119
            /* Reparent and move to the correct place */
1120
            widget->setParent(parent);
×
1121
            connectWidgetToParent(widget, parent);
×
1122
            widget->move(p);
×
1123
            widget->show();
×
1124
        }
1125

1126
        /* Clear clipboard after pasting stuff that was CUT */
1127
        m_clipboard.clear();
×
1128
        m_editPasteAction->setEnabled(false);
×
1129
    }
1130
    else if (m_editAction == EditCopy)
×
1131
    {
1132
        it.toFront();
×
1133
        while (it.hasNext() == true)
×
1134
        {
1135
            widget = it.next();
×
1136
            Q_ASSERT(widget != NULL);
×
1137
            if (widget == parent)
×
1138
                continue;
×
1139

1140
            /* Get widget's relative pos to the bounding rect */
1141
            QPoint p(widget->x() - bounds.x() + cp.x(),
×
1142
                     widget->y() - bounds.y() + cp.y());
×
1143

1144
            /* Create a copy and move to correct place */
1145
            VCWidget* copy = widget->createCopy(parent);
×
1146
            Q_ASSERT(copy != NULL);
×
1147
            addWidgetInMap(copy);
×
1148
            connectWidgetToParent(copy, parent);
×
1149
            copy->move(p);
×
1150
            copy->show();
×
1151
        }
1152
    }
1153

1154
    updateActions();
×
1155
}
1156

1157
void VirtualConsole::slotEditDelete()
×
1158
{
1159
    QString msg(tr("Do you wish to delete the selected widgets?"));
×
1160
    QString title(tr("Delete widgets"));
×
1161
    int result = QMessageBox::question(this, title, msg,
×
1162
                                       QMessageBox::Yes,
1163
                                       QMessageBox::No);
1164
    if (result == QMessageBox::Yes)
×
1165
    {
1166
        while (m_selectedWidgets.isEmpty() == false)
×
1167
        {
1168
            /* Consume the selected list until it is empty and
1169
               delete each widget. */
1170
            VCWidget* widget = m_selectedWidgets.takeFirst();
×
1171
            m_widgetsMap.remove(widget->id());
×
1172
            foreach (VCWidget* child, getChildren(widget))
×
1173
                m_widgetsMap.remove(child->id());
×
1174
            VCWidget* parent = qobject_cast<VCWidget*> (widget->parentWidget());
×
1175
            widget->deleteLater();
×
1176

1177
            if (parent != NULL)
×
1178
                disconnectWidgetFromParent(widget, parent);
×
1179

1180
            /* Remove the widget from clipboard as well so that
1181
               deleted widgets won't be pasted anymore anywhere */
1182
            m_clipboard.removeAll(widget);
×
1183
            m_editPasteAction->setEnabled(false);
×
1184
        }
1185

1186
        updateActions();
×
1187
    }
1188
    m_doc->setModified();
×
1189
}
×
1190

1191
void VirtualConsole::slotEditProperties()
×
1192
{
1193
    VCWidget* widget;
1194

1195
    Q_ASSERT(contents() != NULL);
×
1196

1197
    if (m_selectedWidgets.isEmpty() == true)
×
1198
        widget = contents();
×
1199
    else
1200
        widget = m_selectedWidgets.last();
×
1201

1202
    if (widget != NULL)
×
1203
        widget->editProperties();
×
1204
}
×
1205

1206
void VirtualConsole::slotEditRename()
×
1207
{
1208
    if (m_selectedWidgets.isEmpty() == true)
×
1209
        return;
×
1210

1211
    bool ok = false;
×
1212
    QString text(m_selectedWidgets.last()->caption());
×
1213
    text = QInputDialog::getText(this, tr("Rename widgets"), tr("Caption:"),
×
1214
                                 QLineEdit::Normal, text, &ok);
×
1215
    if (ok == true)
×
1216
    {
1217
        VCWidget* widget;
NEW
1218
        foreach (widget, m_selectedWidgets)
×
1219
            widget->setCaption(text);
×
1220
    }
1221
}
1222

1223
/*****************************************************************************
1224
 * Background menu callbacks
1225
 *****************************************************************************/
1226

1227
void VirtualConsole::slotBackgroundColor()
×
1228
{
1229
    QColor color;
×
1230

1231
    Q_ASSERT(contents() != NULL);
×
1232

1233
    if (m_selectedWidgets.isEmpty() == true)
×
1234
        color = contents()->backgroundColor();
×
1235
    else
1236
        color = m_selectedWidgets.last()->backgroundColor();
×
1237

1238
    color = QColorDialog::getColor(color);
×
1239
    if (color.isValid() == true)
×
1240
    {
1241
        if (m_selectedWidgets.isEmpty() == true)
×
1242
        {
1243
            contents()->setBackgroundColor(color);
×
1244
        }
1245
        else
1246
        {
1247
            VCWidget* widget;
NEW
1248
            foreach (widget, m_selectedWidgets)
×
1249
                widget->setBackgroundColor(color);
×
1250
        }
1251
    }
1252
}
×
1253

1254
void VirtualConsole::slotBackgroundImage()
×
1255
{
1256
    QString path;
×
1257

1258
    Q_ASSERT(contents() != NULL);
×
1259

1260
    if (m_selectedWidgets.isEmpty() == true)
×
1261
        path = contents()->backgroundImage();
×
1262
    else
1263
        path = m_selectedWidgets.last()->backgroundImage();
×
1264

1265
    path = QFileDialog::getOpenFileName(this,
×
1266
                                        tr("Select background image"),
×
1267
                                        path,
1268
                                        QString("%1 (*.png *.bmp *.jpg *.jpeg *.gif)").arg(tr("Images")));
×
1269
    if (path.isEmpty() == false)
×
1270
    {
1271
        if (m_selectedWidgets.isEmpty() == true)
×
1272
        {
1273
            contents()->setBackgroundImage(path);
×
1274
        }
1275
        else
1276
        {
1277
            VCWidget* widget;
NEW
1278
            foreach (widget, m_selectedWidgets)
×
1279
                widget->setBackgroundImage(path);
×
1280
        }
1281
    }
1282
}
×
1283

1284
void VirtualConsole::slotBackgroundNone()
×
1285
{
1286
    Q_ASSERT(contents() != NULL);
×
1287

1288
    if (m_selectedWidgets.isEmpty() == true)
×
1289
    {
1290
        contents()->resetBackgroundColor();
×
1291
    }
1292
    else
1293
    {
1294
        VCWidget* widget;
NEW
1295
        foreach (widget, m_selectedWidgets)
×
1296
            widget->resetBackgroundColor();
×
1297
    }
1298
}
×
1299

1300
/*****************************************************************************
1301
 * Foreground menu callbacks
1302
 *****************************************************************************/
1303

1304
void VirtualConsole::slotForegroundColor()
×
1305
{
1306
    Q_ASSERT(contents() != NULL);
×
1307

1308
    if (m_selectedWidgets.isEmpty() == true)
×
1309
        return;
×
1310

1311
    QColor color(m_selectedWidgets.last()->foregroundColor());
×
1312
    color = QColorDialog::getColor(color);
×
1313
    if (color.isValid() == true)
×
1314
    {
1315
        VCWidget* widget;
NEW
1316
        foreach (widget, m_selectedWidgets)
×
1317
            widget->setForegroundColor(color);
×
1318
    }
1319
}
1320

1321
void VirtualConsole::slotForegroundNone()
×
1322
{
1323
    Q_ASSERT(contents() != NULL);
×
1324

1325
    if (m_selectedWidgets.isEmpty() == true)
×
1326
        return;
×
1327

1328
    VCWidget* widget;
NEW
1329
    foreach (widget, m_selectedWidgets)
×
1330
        widget->resetForegroundColor();
×
1331
}
1332

1333
/*****************************************************************************
1334
 * Font menu callbacks
1335
 *****************************************************************************/
1336

1337
void VirtualConsole::slotFont()
×
1338
{
1339
    bool ok = false;
×
1340
    QFont font;
×
1341

1342
    Q_ASSERT(contents() != NULL);
×
1343

1344
    if (m_selectedWidgets.isEmpty() == true)
×
1345
        font = contents()->font();
×
1346
    else
1347
        font = m_selectedWidgets.last()->font();
×
1348

1349
    /* This crashes with Qt 4.6.x on OSX. Upgrade to 4.7.x. */
1350
    font = QFontDialog::getFont(&ok, font);
×
1351
    if (ok == true)
×
1352
    {
1353
        if (m_selectedWidgets.isEmpty() == true)
×
1354
        {
1355
            contents()->setFont(font);
×
1356
        }
1357
        else
1358
        {
1359
            VCWidget* widget;
NEW
1360
            foreach (widget, m_selectedWidgets)
×
1361
                widget->setFont(font);
×
1362
        }
1363
    }
1364
}
×
1365

1366
void VirtualConsole::slotResetFont()
×
1367
{
1368
    Q_ASSERT(contents() != NULL);
×
1369

1370
    if (m_selectedWidgets.isEmpty() == true)
×
1371
    {
1372
        contents()->resetFont();
×
1373
    }
1374
    else
1375
    {
1376
        VCWidget* widget;
NEW
1377
        foreach (widget, m_selectedWidgets)
×
1378
            widget->resetFont();
×
1379
    }
1380
}
×
1381

1382
/*****************************************************************************
1383
 * Stacking menu callbacks
1384
 *****************************************************************************/
1385

1386
void VirtualConsole::slotStackingRaise()
×
1387
{
1388
    Q_ASSERT(contents() != NULL);
×
1389

1390
    if (m_selectedWidgets.isEmpty() == true)
×
1391
        return;
×
1392

1393
    VCWidget* widget;
NEW
1394
    foreach (widget, m_selectedWidgets)
×
1395
        widget->raise();
×
1396

1397
    m_doc->setModified();
×
1398
}
1399

1400
void VirtualConsole::slotStackingLower()
×
1401
{
1402
    Q_ASSERT(contents() != NULL);
×
1403

1404
    if (m_selectedWidgets.isEmpty() == true)
×
1405
        return;
×
1406

1407
    VCWidget* widget;
NEW
1408
    foreach (widget, m_selectedWidgets)
×
1409
        widget->lower();
×
1410

1411
    m_doc->setModified();
×
1412
}
1413

1414
/*****************************************************************************
1415
 * Frame menu callbacks
1416
 *****************************************************************************/
1417

1418
void VirtualConsole::slotFrameSunken()
×
1419
{
1420
    Q_ASSERT(contents() != NULL);
×
1421

1422
    if (m_selectedWidgets.isEmpty() == true)
×
1423
        return;
×
1424

1425
    VCWidget* widget;
NEW
1426
    foreach (widget, m_selectedWidgets)
×
1427
        widget->setFrameStyle(KVCFrameStyleSunken);
×
1428
}
1429

1430
void VirtualConsole::slotFrameRaised()
×
1431
{
1432
    Q_ASSERT(contents() != NULL);
×
1433

1434
    if (m_selectedWidgets.isEmpty() == true)
×
1435
        return;
×
1436

1437
    VCWidget* widget;
NEW
1438
    foreach (widget, m_selectedWidgets)
×
1439
        widget->setFrameStyle(KVCFrameStyleRaised);
×
1440
}
1441

1442
void VirtualConsole::slotFrameNone()
×
1443
{
1444
    Q_ASSERT(contents() != NULL);
×
1445

1446
    if (m_selectedWidgets.isEmpty() == true)
×
1447
        return;
×
1448

1449
    VCWidget* widget;
NEW
1450
    foreach (widget, m_selectedWidgets)
×
1451
        widget->setFrameStyle(KVCFrameStyleNone);
×
1452
}
1453

1454
/*****************************************************************************
1455
 * Dock area
1456
 *****************************************************************************/
1457

1458
VCDockArea* VirtualConsole::dockArea() const
×
1459
{
1460
    return m_dockArea;
×
1461
}
1462

1463
void VirtualConsole::initDockArea()
76✔
1464
{
1465
    if (m_dockArea != NULL)
76✔
1466
        delete m_dockArea;
×
1467

1468
    m_dockArea = new VCDockArea(this, m_doc->inputOutputMap());
76✔
1469
    m_dockArea->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Expanding);
76✔
1470

1471
    // Add the dock area into the master horizontal layout
1472
    layout()->addWidget(m_dockArea);
76✔
1473

1474
    /* Show the dock area by default */
1475
    m_dockArea->show();
76✔
1476
}
76✔
1477

1478
/*****************************************************************************
1479
 * Contents
1480
 *****************************************************************************/
1481

1482
VCFrame* VirtualConsole::contents() const
787✔
1483
{
1484
    return m_contents;
787✔
1485
}
1486

1487
void VirtualConsole::resetContents()
76✔
1488
{
1489
    if (m_contents != NULL)
76✔
1490
        delete m_contents;
×
1491

1492
    Q_ASSERT(m_scrollArea != NULL);
76✔
1493
    m_contents = new VCFrame(m_scrollArea, m_doc);
76✔
1494
    m_contents->setFrameStyle(0);
76✔
1495

1496
    // Get virtual console size from properties
1497
    QSize size(m_properties.size());
76✔
1498
    contents()->resize(size);
76✔
1499
    contents()->setSizePolicy(QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed));
76✔
1500
    m_scrollArea->setWidget(contents());
76✔
1501

1502
    /* Disconnect old key handlers to prevent duplicates */
1503
    disconnect(this, SIGNAL(keyPressed(const QKeySequence&)),
152✔
1504
               contents(), SLOT(slotKeyPressed(const QKeySequence&)));
76✔
1505
    disconnect(this, SIGNAL(keyReleased(const QKeySequence&)),
152✔
1506
               contents(), SLOT(slotKeyReleased(const QKeySequence&)));
76✔
1507

1508
    /* Connect new key handlers */
1509
    connect(this, SIGNAL(keyPressed(const QKeySequence&)),
152✔
1510
            contents(), SLOT(slotKeyPressed(const QKeySequence&)));
76✔
1511
    connect(this, SIGNAL(keyReleased(const QKeySequence&)),
152✔
1512
            contents(), SLOT(slotKeyReleased(const QKeySequence&)));
76✔
1513

1514
    /* Make the contents area take up all available space */
1515
    contents()->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
76✔
1516

1517
    m_clipboard.clear();
76✔
1518
    m_selectedWidgets.clear();
76✔
1519
    m_latestWidgetId = 0;
76✔
1520
    m_widgetsMap.clear();
76✔
1521

1522
    /* Update actions' enabled status */
1523
    updateActions();
76✔
1524

1525
    /* Reset all properties but size */
1526
    m_properties.setGrandMasterChannelMode(GrandMaster::Intensity);
76✔
1527
    m_properties.setGrandMasterValueMode(GrandMaster::Reduce);
76✔
1528
    m_properties.setGrandMasterInputSource(InputOutputMap::invalidUniverse(), QLCChannel::invalid());
76✔
1529
}
76✔
1530

1531
void VirtualConsole::addWidgetInMap(VCWidget* widget)
1✔
1532
{
1533
    // Valid ID ?
1534
    if (widget->id() != VCWidget::invalidId())
1✔
1535
    {
1536
        // Maybe we don't know this widget yet
1537
        if (!m_widgetsMap.contains(widget->id()))
×
1538
        {
1539
            m_widgetsMap.insert(widget->id(), widget);
×
1540
            return;
×
1541
        }
1542

1543
        // Maybe we already know this widget
1544
        if (m_widgetsMap[widget->id()] == widget)
×
1545
        {
1546
            qDebug() << Q_FUNC_INFO << "widget" << widget->id() << "already in map";
×
1547
            return;
×
1548
        }
1549

1550
        // This widget id conflicts with another one we have to change it.
1551
        qDebug() << Q_FUNC_INFO << "widget id" << widget->id() << "conflicts, creating a new ID";
×
1552
    }
1553

1554
    quint32 wid = newWidgetId();
1✔
1555
    Q_ASSERT(!m_widgetsMap.contains(wid));
1✔
1556
    qDebug() << Q_FUNC_INFO << "id=" << wid;
1✔
1557
    widget->setID(wid);
1✔
1558
    m_widgetsMap.insert(wid, widget);
1✔
1559
}
1560

1561
void VirtualConsole::setupWidget(VCWidget *widget, VCWidget *parent)
×
1562
{
1563
    Q_ASSERT(widget != NULL);
×
1564
    Q_ASSERT(parent != NULL);
×
1565

1566
    addWidgetInMap(widget);
×
1567
    connectWidgetToParent(widget, parent);
×
1568
    widget->show();
×
1569
    widget->move(parent->lastClickPoint());
×
1570
    clearWidgetSelection();
×
1571
    setWidgetSelected(widget, true);
×
1572
}
×
1573

1574
VCWidget *VirtualConsole::widget(quint32 id)
×
1575
{
1576
    if (id == VCWidget::invalidId())
×
1577
        return NULL;
×
1578

1579
    return m_widgetsMap.value(id, NULL);
×
1580
}
1581

1582
void VirtualConsole::initContents()
76✔
1583
{
1584
    Q_ASSERT(layout() != NULL);
76✔
1585

1586
    m_scrollArea = new QScrollArea(this);
76✔
1587
    m_contentsLayout->addWidget(m_scrollArea);
76✔
1588
    m_scrollArea->setAlignment(Qt::AlignCenter);
76✔
1589
    m_scrollArea->setWidgetResizable(false);
76✔
1590

1591
    resetContents();
76✔
1592
}
76✔
1593

1594
/*****************************************************************************
1595
 * Key press handler
1596
 *****************************************************************************/
1597

1598
void VirtualConsole::keyPressEvent(QKeyEvent* event)
×
1599
{
1600
    if (event->isAutoRepeat() == true)
×
1601
    {
1602
        event->ignore();
×
1603
        return;
×
1604
    }
1605

1606
    QKeySequence seq(event->key() | (event->modifiers() & ~Qt::ControlModifier));
×
1607
    emit keyPressed(seq);
×
1608

1609
    event->accept();
×
1610
}
1611

1612
void VirtualConsole::keyReleaseEvent(QKeyEvent* event)
×
1613
{
1614
    if (event->isAutoRepeat() == true)
×
1615
    {
1616
        event->ignore();
×
1617
        return;
×
1618
    }
1619

1620
    QKeySequence seq(event->key() | event->modifiers());
×
1621
    emit keyReleased(seq);
×
1622

1623
    event->accept();
×
1624
}
1625

1626
/*****************************************************************************
1627
 * Main application mode
1628
 *****************************************************************************/
1629

1630
void VirtualConsole::toggleLiveEdit()
×
1631
{
1632
    // No live edit in Design Mode
1633
    Q_ASSERT(m_doc->mode() == Doc::Operate);
×
1634

1635
    if (m_liveEdit)
×
1636
    { // live edit was on, disable live edit
1637
        m_liveEdit = false;
×
1638
        disableEdit();
×
1639
    }
1640
    else
1641
    { // live edit was off, enable live edit
1642
        m_liveEdit = true;
×
1643
        enableEdit();
×
1644
    }
1645

1646
    // inform the widgets of the live edit status
1647
    QHash<quint32, VCWidget*>::iterator widgetIt = m_widgetsMap.begin();
×
1648
    while (widgetIt != m_widgetsMap.end())
×
1649
    {
1650
        VCWidget* widget = widgetIt.value();
×
1651
        widget->setLiveEdit(m_liveEdit);
×
1652
        ++widgetIt;
×
1653
    }
1654
    m_contents->setLiveEdit(m_liveEdit);
×
1655
}
×
1656

1657
bool VirtualConsole::liveEdit() const
177✔
1658
{
1659
    return m_liveEdit;
177✔
1660
}
1661

1662
void VirtualConsole::enableEdit()
80✔
1663
{
1664
    // Allow editing and adding in design mode
1665
    m_toolsSettingsAction->setEnabled(true);
80✔
1666
    m_editActionGroup->setEnabled(true);
80✔
1667
    m_addActionGroup->setEnabled(true);
80✔
1668
    m_bgActionGroup->setEnabled(true);
80✔
1669
    m_fgActionGroup->setEnabled(true);
80✔
1670
    m_fontActionGroup->setEnabled(true);
80✔
1671
    m_frameActionGroup->setEnabled(true);
80✔
1672
    m_stackingActionGroup->setEnabled(true);
80✔
1673

1674
    // Set action shortcuts for design mode
1675
    m_addButtonAction->setShortcut(QKeySequence("CTRL+SHIFT+B"));
80✔
1676
    m_addButtonMatrixAction->setShortcut(QKeySequence("CTRL+SHIFT+M"));
80✔
1677
    m_addSliderAction->setShortcut(QKeySequence("CTRL+SHIFT+S"));
80✔
1678
    m_addSliderMatrixAction->setShortcut(QKeySequence("CTRL+SHIFT+I"));
80✔
1679
    m_addKnobAction->setShortcut(QKeySequence("CTRL+SHIFT+K"));
80✔
1680
    m_addSpeedDialAction->setShortcut(QKeySequence("CTRL+SHIFT+D"));
80✔
1681
    m_addXYPadAction->setShortcut(QKeySequence("CTRL+SHIFT+X"));
80✔
1682
    m_addCueListAction->setShortcut(QKeySequence("CTRL+SHIFT+C"));
80✔
1683
    m_addFrameAction->setShortcut(QKeySequence("CTRL+SHIFT+F"));
80✔
1684
    m_addSoloFrameAction->setShortcut(QKeySequence("CTRL+SHIFT+O"));
80✔
1685
    m_addLabelAction->setShortcut(QKeySequence("CTRL+SHIFT+L"));
80✔
1686
    m_addAudioTriggersAction->setShortcut(QKeySequence("CTRL+SHIFT+A"));
80✔
1687
    m_addClockAction->setShortcut(QKeySequence("CTRL+SHIFT+T"));
80✔
1688
    m_addAnimationAction->setShortcut(QKeySequence("CTRL+SHIFT+R"));
80✔
1689

1690
    m_editCutAction->setShortcut(QKeySequence("CTRL+X"));
80✔
1691
    m_editCopyAction->setShortcut(QKeySequence("CTRL+C"));
80✔
1692
    m_editPasteAction->setShortcut(QKeySequence("CTRL+V"));
80✔
1693
    m_editDeleteAction->setShortcut(QKeySequence("Delete"));
80✔
1694
    m_editPropertiesAction->setShortcut(QKeySequence("CTRL+E"));
80✔
1695

1696
    m_bgColorAction->setShortcut(QKeySequence("SHIFT+B"));
80✔
1697
    m_bgImageAction->setShortcut(QKeySequence("SHIFT+I"));
80✔
1698
    m_bgDefaultAction->setShortcut(QKeySequence("SHIFT+ALT+B"));
80✔
1699
    m_fgColorAction->setShortcut(QKeySequence("SHIFT+F"));
80✔
1700
    m_fgDefaultAction->setShortcut(QKeySequence("SHIFT+ALT+F"));
80✔
1701
    m_fontAction->setShortcut(QKeySequence("SHIFT+O"));
80✔
1702
    m_resetFontAction->setShortcut(QKeySequence("SHIFT+ALT+O"));
80✔
1703
    m_frameSunkenAction->setShortcut(QKeySequence("SHIFT+S"));
80✔
1704
    m_frameRaisedAction->setShortcut(QKeySequence("SHIFT+R"));
80✔
1705
    m_frameNoneAction->setShortcut(QKeySequence("SHIFT+ALT+S"));
80✔
1706

1707
    m_stackingRaiseAction->setShortcut(QKeySequence("SHIFT+UP"));
80✔
1708
    m_stackingLowerAction->setShortcut(QKeySequence("SHIFT+DOWN"));
80✔
1709

1710
    // Show toolbar
1711
    m_toolbar->show();
80✔
1712
}
80✔
1713

1714
void VirtualConsole::disableEdit()
15✔
1715
{
1716
    // Don't allow editing or adding in operate mode
1717
    m_toolsSettingsAction->setEnabled(false);
15✔
1718
    m_editActionGroup->setEnabled(false);
15✔
1719
    m_addActionGroup->setEnabled(false);
15✔
1720
    m_bgActionGroup->setEnabled(false);
15✔
1721
    m_fgActionGroup->setEnabled(false);
15✔
1722
    m_fontActionGroup->setEnabled(false);
15✔
1723
    m_frameActionGroup->setEnabled(false);
15✔
1724
    m_stackingActionGroup->setEnabled(false);
15✔
1725

1726
    // Disable action shortcuts in operate mode
1727
    m_addButtonAction->setShortcut(QKeySequence());
15✔
1728
    m_addButtonMatrixAction->setShortcut(QKeySequence());
15✔
1729
    m_addSliderAction->setShortcut(QKeySequence());
15✔
1730
    m_addSliderMatrixAction->setShortcut(QKeySequence());
15✔
1731
    m_addKnobAction->setShortcut(QKeySequence());
15✔
1732
    m_addSpeedDialAction->setShortcut(QKeySequence());
15✔
1733
    m_addXYPadAction->setShortcut(QKeySequence());
15✔
1734
    m_addCueListAction->setShortcut(QKeySequence());
15✔
1735
    m_addFrameAction->setShortcut(QKeySequence());
15✔
1736
    m_addSoloFrameAction->setShortcut(QKeySequence());
15✔
1737
    m_addLabelAction->setShortcut(QKeySequence());
15✔
1738
    m_addAudioTriggersAction->setShortcut(QKeySequence());
15✔
1739
    m_addClockAction->setShortcut(QKeySequence());
15✔
1740
    m_addAnimationAction->setShortcut(QKeySequence());
15✔
1741

1742
    m_editCutAction->setShortcut(QKeySequence());
15✔
1743
    m_editCopyAction->setShortcut(QKeySequence());
15✔
1744
    m_editPasteAction->setShortcut(QKeySequence());
15✔
1745
    m_editDeleteAction->setShortcut(QKeySequence());
15✔
1746
    m_editPropertiesAction->setShortcut(QKeySequence());
15✔
1747

1748
    m_bgColorAction->setShortcut(QKeySequence());
15✔
1749
    m_bgImageAction->setShortcut(QKeySequence());
15✔
1750
    m_bgDefaultAction->setShortcut(QKeySequence());
15✔
1751
    m_fgColorAction->setShortcut(QKeySequence());
15✔
1752
    m_fgDefaultAction->setShortcut(QKeySequence());
15✔
1753
    m_fontAction->setShortcut(QKeySequence());
15✔
1754
    m_resetFontAction->setShortcut(QKeySequence());
15✔
1755
    m_frameSunkenAction->setShortcut(QKeySequence());
15✔
1756
    m_frameRaisedAction->setShortcut(QKeySequence());
15✔
1757
    m_frameNoneAction->setShortcut(QKeySequence());
15✔
1758

1759
    m_stackingRaiseAction->setShortcut(QKeySequence());
15✔
1760
    m_stackingLowerAction->setShortcut(QKeySequence());
15✔
1761

1762
    // Hide toolbar; there's nothing usable there in operate mode
1763
    m_toolbar->hide();
15✔
1764

1765
    // Make sure the virtual console contents has the focus.
1766
    // Without this, key combinations don't work unless
1767
    // the user clicks on some VC area
1768
    m_contents->setFocus();
15✔
1769
}
15✔
1770

1771
void VirtualConsole::slotModeChanged(Doc::Mode mode)
95✔
1772
{
1773
    if (mode == Doc::Operate)
95✔
1774
    { // Switch from Design mode to Operate mode
1775
        // Hide edit tools
1776
        disableEdit();
15✔
1777
    }
1778
    else
1779
    { // Switch from Operate mode to Design mode
1780
        if (m_liveEdit)
80✔
1781
        {
1782
            // Edit tools already shown,
1783
            // inform the widgets that we are out of live edit mode
1784
            m_liveEdit = false;
×
1785
            QHash<quint32, VCWidget*>::iterator widgetIt = m_widgetsMap.begin();
×
1786
            while (widgetIt != m_widgetsMap.end())
×
1787
            {
1788
                VCWidget* widget = widgetIt.value();
×
1789
                widget->cancelLiveEdit();
×
1790
                ++widgetIt;
×
1791
            }
1792
            m_contents->cancelLiveEdit();
×
1793
        }
1794
        else
1795
        {
1796
            // Show edit tools
1797
            enableEdit();
80✔
1798
        }
1799
    }
1800
}
95✔
1801

1802
/*****************************************************************************
1803
 * Load & Save
1804
 *****************************************************************************/
1805

1806
bool VirtualConsole::loadXML(QXmlStreamReader &root)
×
1807
{
1808
    if (root.name() != KXMLQLCVirtualConsole)
×
1809
    {
1810
        qWarning() << Q_FUNC_INFO << "Virtual Console node not found";
×
1811
        return false;
×
1812
    }
1813

1814
    while (root.readNextStartElement())
×
1815
    {
1816
        //qDebug() << "VC tag:" << root.name();
1817
        if (root.name() == KXMLQLCVCProperties)
×
1818
        {
1819
            /* Properties */
1820
            m_properties.loadXML(root);
×
1821
            QSize size(m_properties.size());
×
1822
            contents()->resize(size);
×
1823
            contents()->setSizePolicy(QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed));
×
1824
        }
1825
        else if (root.name() == KXMLQLCVCFrame)
×
1826
        {
1827
            /* Contents */
1828
            Q_ASSERT(m_contents != NULL);
×
1829
            m_contents->loadXML(root);
×
1830
        }
1831
        else
1832
        {
1833
            qWarning() << Q_FUNC_INFO << "Unknown Virtual Console tag"
×
1834
                       << root.name().toString();
×
1835
            root.skipCurrentElement();
×
1836
        }
1837
    }
1838

1839
    return true;
×
1840
}
1841

1842
bool VirtualConsole::saveXML(QXmlStreamWriter *doc)
×
1843
{
1844
    Q_ASSERT(doc != NULL);
×
1845

1846
    /* Virtual Console entry */
1847
    doc->writeStartElement(KXMLQLCVirtualConsole);
×
1848

1849
    /* Contents */
1850
    Q_ASSERT(m_contents != NULL);
×
1851
    m_contents->saveXML(doc);
×
1852

1853
    /* Properties */
1854
    m_properties.saveXML(doc);
×
1855

1856
    /* End the <VirtualConsole> tag */
1857
    doc->writeEndElement();
×
1858

1859
    return true;
×
1860
}
1861

1862
QList<VCWidget *> VirtualConsole::getChildren(VCWidget *obj)
×
1863
{
1864
    QList<VCWidget *> list;
×
1865
    if (obj == NULL)
×
1866
        return list;
×
1867
    QListIterator <VCWidget*> it(obj->findChildren<VCWidget*>());
×
1868
    while (it.hasNext() == true)
×
1869
    {
1870
        VCWidget* child = it.next();
×
1871
        list.append(child);
×
1872
        list.append(getChildren(child));
×
1873
    }
1874
    return list;
×
1875
}
1876

1877
void VirtualConsole::postLoad()
×
1878
{
1879
    m_contents->postLoad();
×
1880

1881
    /* apply GM values
1882
      this should probably be placed in another place, but at the moment m_properties
1883
      is just loaded in VirtualConsole */
1884
    m_doc->inputOutputMap()->setGrandMasterValue(255);
×
1885
    m_doc->inputOutputMap()->setGrandMasterValueMode(m_properties.grandMasterValueMode());
×
1886
    m_doc->inputOutputMap()->setGrandMasterChannelMode(m_properties.grandMasterChannelMode());
×
1887

1888
    /* Go through widgets, check IDs and register */
1889
    /* widgets to the map */
1890
    /* This code is the same as the one in addWidgetInMap() */
1891
    /* We have to repeat it to limit conflicts if */
1892
    /* one widget was not saved with a valid ID, */
1893
    /* as addWidgetInMap ensures the widget WILL be added */
1894
    QList<VCWidget *> widgetsList = getChildren(m_contents);
×
1895
    QList<VCWidget *> invalidWidgetsList;
×
1896
    foreach (VCWidget *widget, widgetsList)
×
1897
    {
1898
        quint32 wid = widget->id();
×
1899
        if (wid != VCWidget::invalidId())
×
1900
        {
1901
            if (!m_widgetsMap.contains(wid))
×
1902
                m_widgetsMap.insert(wid, widget);
×
1903
            else if (m_widgetsMap[wid] != widget)
×
1904
                invalidWidgetsList.append(widget);
×
1905
        }
1906
        else
1907
            invalidWidgetsList.append(widget);
×
1908
    }
1909
    foreach (VCWidget *widget, invalidWidgetsList)
×
1910
        addWidgetInMap(widget);
×
1911

1912
    m_contents->setFocus();
×
1913

1914
    emit loaded();
×
1915
}
×
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc