OSDN Git Service

It's 2011 now.
[qt-creator-jp/qt-creator-jp.git] / src / plugins / qmljsinspector / qmljsinspector.cpp
1 /**************************************************************************
2 **
3 ** This file is part of Qt Creator
4 **
5 ** Copyright (c) 2011 Nokia Corporation and/or its subsidiary(-ies).
6 **
7 ** Contact: Nokia Corporation (qt-info@nokia.com)
8 **
9 ** No Commercial Usage
10 **
11 ** This file contains pre-release code and may not be distributed.
12 ** You may use this file in accordance with the terms and conditions
13 ** contained in the Technology Preview License Agreement accompanying
14 ** this package.
15 **
16 ** GNU Lesser General Public License Usage
17 **
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 2.1 as published by the Free Software
20 ** Foundation and appearing in the file LICENSE.LGPL included in the
21 ** packaging of this file.  Please review the following information to
22 ** ensure the GNU Lesser General Public License version 2.1 requirements
23 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
24 **
25 ** In addition, as a special exception, Nokia gives you certain additional
26 ** rights.  These rights are described in the Nokia Qt LGPL Exception
27 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
28 **
29 ** If you have questions regarding the use of this file, please contact
30 ** Nokia at qt-info@nokia.com.
31 **
32 **************************************************************************/
33
34 #include "qmljsinspectorconstants.h"
35 #include "qmljsinspector.h"
36 #include "qmlinspectortoolbar.h"
37 #include "qmljsclientproxy.h"
38 #include "qmljslivetextpreview.h"
39 #include "qmljsprivateapi.h"
40 #include "qmljscontextcrumblepath.h"
41 #include "qmljsinspectorsettings.h"
42 #include "qmljsobjecttree.h"
43
44 #include <qmljs/qmljsmodelmanagerinterface.h>
45 #include <qmljs/qmljsdocument.h>
46 #include <qmljs/parser/qmljsast_p.h>
47 #include <qmljseditor/qmljseditorconstants.h>
48 #include <qmljseditor/qmljseditor.h>
49 #include <debugger/debuggerconstants.h>
50 #include <debugger/debuggermainwindow.h>
51 #include <debugger/debuggerplugin.h>
52
53 #include <utils/qtcassert.h>
54 #include <utils/styledbar.h>
55
56 #include <coreplugin/icontext.h>
57 #include <coreplugin/findplaceholder.h>
58 #include <coreplugin/minisplitter.h>
59 #include <coreplugin/outputpane.h>
60 #include <coreplugin/rightpane.h>
61 #include <coreplugin/navigationwidget.h>
62 #include <coreplugin/icore.h>
63 #include <coreplugin/coreconstants.h>
64 #include <coreplugin/uniqueidmanager.h>
65 #include <coreplugin/actionmanager/actioncontainer.h>
66 #include <coreplugin/actionmanager/actionmanager.h>
67 #include <coreplugin/actionmanager/command.h>
68 #include <coreplugin/editormanager/editormanager.h>
69
70 #include <texteditor/itexteditor.h>
71 #include <texteditor/basetexteditor.h>
72
73 #include <projectexplorer/runconfiguration.h>
74 #include <projectexplorer/buildconfiguration.h>
75 #include <projectexplorer/projectexplorer.h>
76 #include <projectexplorer/projectexplorerconstants.h>
77 #include <projectexplorer/project.h>
78 #include <projectexplorer/target.h>
79 #include <projectexplorer/applicationrunconfiguration.h>
80 #include <qmlprojectmanager/qmlprojectconstants.h>
81 #include <qmlprojectmanager/qmlprojectrunconfiguration.h>
82
83 #include <extensionsystem/pluginmanager.h>
84
85 #include <QtCore/QDebug>
86 #include <QtCore/QStringList>
87 #include <QtCore/QTimer>
88 #include <QtCore/QtPlugin>
89 #include <QtCore/QDateTime>
90
91 #include <QtGui/QLabel>
92 #include <QtGui/QDockWidget>
93 #include <QtGui/QVBoxLayout>
94 #include <QtGui/QAction>
95 #include <QtGui/QLineEdit>
96 #include <QtGui/QLabel>
97 #include <QtGui/QSpinBox>
98 #include <QtGui/QMessageBox>
99 #include <QtGui/QTextBlock>
100
101 #include <QtGui/QToolTip>
102 #include <QtGui/QCursor>
103 #include <QtNetwork/QHostAddress>
104
105 using namespace QmlJS;
106 using namespace QmlJS::AST;
107 using namespace QmlJSInspector::Internal;
108
109 enum {
110     MaxConnectionAttempts = 50,
111     ConnectionAttemptDefaultInterval = 75,
112
113     // used when debugging with c++ - connection can take a lot of time
114     ConnectionAttemptSimultaneousInterval = 500
115 };
116
117 InspectorUi *InspectorUi::m_instance = 0;
118
119 QmlJS::ModelManagerInterface *modelManager()
120 {
121     return ExtensionSystem::PluginManager::instance()->getObject<QmlJS::ModelManagerInterface>();
122 }
123
124 InspectorUi::InspectorUi(QObject *parent)
125     : QObject(parent)
126     , m_listeningToEditorManager(false)
127     , m_toolbar(0)
128     , m_crumblePath(0)
129     , m_objectTreeWidget(0)
130     , m_settings(new InspectorSettings(this))
131     , m_clientProxy(0)
132     , m_qmlEngine(0)
133     , m_debugQuery(0)
134     , m_lastSelectedDebugId(-1)
135     , m_debugProject(0)
136 {
137     m_instance = this;
138     m_toolbar = new QmlInspectorToolbar(this);
139 }
140
141 InspectorUi::~InspectorUi()
142 {
143 }
144
145 void InspectorUi::setupUi()
146 {
147     setupDockWidgets();
148     restoreSettings();
149 }
150
151 void InspectorUi::saveSettings() const
152 {
153     m_settings->saveSettings(Core::ICore::instance()->settings());
154 }
155
156 void InspectorUi::restoreSettings()
157 {
158     m_settings->restoreSettings(Core::ICore::instance()->settings());
159 }
160
161 void InspectorUi::setDebuggerEngine(QObject *qmlEngine)
162 {
163     if (m_qmlEngine && !qmlEngine) {
164         disconnect(m_qmlEngine,
165             SIGNAL(tooltipRequested(QPoint,TextEditor::ITextEditor*,int)),
166             this, SLOT(showDebuggerTooltip(QPoint,TextEditor::ITextEditor*,int)));
167     }
168
169     m_qmlEngine = qmlEngine;
170     if (m_qmlEngine) {
171         connect(m_qmlEngine,
172             SIGNAL(tooltipRequested(QPoint,TextEditor::ITextEditor*,int)),
173             this, SLOT(showDebuggerTooltip(QPoint,TextEditor::ITextEditor*,int)));
174     }
175 }
176
177 QObject *InspectorUi::debuggerEngine() const
178 {
179     return m_qmlEngine;
180 }
181
182 void InspectorUi::showDebuggerTooltip(const QPoint &mousePos, TextEditor::ITextEditor *editor,
183                                       int cursorPos)
184 {
185     Q_UNUSED(mousePos);
186     if (m_clientProxy && editor->id() == QmlJSEditor::Constants::C_QMLJSEDITOR_ID) {
187         QmlJSEditor::QmlJSTextEditor *qmlEditor =
188                 static_cast<QmlJSEditor::QmlJSTextEditor*>(editor->widget());
189
190         QTextCursor tc(qmlEditor->document());
191         tc.setPosition(cursorPos);
192         tc.movePosition(QTextCursor::StartOfWord);
193         tc.movePosition(QTextCursor::EndOfWord, QTextCursor::KeepAnchor);
194
195         QString wordAtCursor = tc.selectedText();
196         QString query;
197         QLatin1Char doubleQuote('"');
198
199         QmlJS::AST::Node *qmlNode = qmlEditor->semanticInfo().nodeUnderCursor(cursorPos);
200         if (!qmlNode)
201             return;
202
203         QDeclarativeDebugObjectReference ref;
204         if (QmlJS::AST::Node *node
205                 = qmlEditor->semanticInfo().declaringMemberNoProperties(cursorPos)) {
206             if (QmlJS::AST::UiObjectMember *objMember = node->uiObjectMemberCast()) {
207                 ref = m_clientProxy->objectReferenceForLocation(
208                             objMember->firstSourceLocation().startLine,
209                             objMember->firstSourceLocation().startColumn);
210             }
211         }
212
213         if (ref.debugId() == -1)
214             return;
215
216         if (wordAtCursor == QString("id")) {
217             query = QString("\"id:") + ref.idString() + doubleQuote;
218         } else {
219             if ((qmlNode->kind == QmlJS::AST::Node::Kind_IdentifierExpression) ||
220                     (qmlNode->kind == QmlJS::AST::Node::Kind_FieldMemberExpression)) {
221                 tc.setPosition(qmlNode->expressionCast()->firstSourceLocation().begin());
222                 tc.setPosition(qmlNode->expressionCast()->lastSourceLocation().end(),
223                                QTextCursor::KeepAnchor);
224                 QString refToLook = tc.selectedText();
225                 if ((qmlNode->kind == QmlJS::AST::Node::Kind_IdentifierExpression) &&
226                         (m_clientProxy->objectReferenceForId(refToLook).debugId() == -1)) {
227                     query = doubleQuote + QString("local: ") + refToLook + doubleQuote;
228                     foreach(QDeclarativeDebugPropertyReference property, ref.properties()) {
229                         if (property.name() == wordAtCursor
230                                 && !property.valueTypeName().isEmpty()) {
231                             query = doubleQuote + property.name() + QLatin1Char(':')
232                                     + doubleQuote + QLatin1Char('+') + property.name();
233                             break;
234                         }
235                     }
236                 }
237                 else
238                     query = doubleQuote + refToLook + QLatin1Char(':') + doubleQuote
239                             + QLatin1Char('+') + refToLook;
240             } else {
241                 // show properties
242                 foreach(QDeclarativeDebugPropertyReference property, ref.properties()) {
243                     if (property.name() == wordAtCursor && !property.valueTypeName().isEmpty()) {
244                         query = doubleQuote + property.name() + QLatin1Char(':')
245                                 + doubleQuote + QLatin1Char('+') + property.name();
246                         break;
247                     }
248                 }
249             }
250         }
251
252         if (!query.isEmpty()) {
253             m_debugQuery = m_clientProxy->queryExpressionResult(ref.debugId(),query);
254             connect(m_debugQuery, SIGNAL(stateChanged(QDeclarativeDebugQuery::State)),
255                     this, SLOT(debugQueryUpdated(QDeclarativeDebugQuery::State)));
256         }
257     }
258 }
259
260 void InspectorUi::debugQueryUpdated(QDeclarativeDebugQuery::State newState)
261 {
262     if (newState != QDeclarativeDebugExpressionQuery::Completed)
263         return;
264     if (!m_debugQuery)
265         return;
266
267     QString text = m_debugQuery->result().toString();
268     if (!text.isEmpty())
269         QToolTip::showText(QCursor::pos(), text);
270
271     disconnect(m_debugQuery, SIGNAL(stateChanged(QDeclarativeDebugQuery::State)),
272                this, SLOT(debugQueryUpdated(QDeclarativeDebugQuery::State)));
273 }
274
275 bool InspectorUi::isConnected() const
276 {
277     return m_clientProxy;
278 }
279
280 void InspectorUi::connected(ClientProxy *clientProxy)
281 {
282     m_clientProxy = clientProxy;
283
284     connect(m_clientProxy, SIGNAL(selectedItemsChanged(QList<QDeclarativeDebugObjectReference>)),
285             SLOT(gotoObjectReferenceDefinition(QList<QDeclarativeDebugObjectReference>)));
286
287     connect(m_clientProxy, SIGNAL(enginesChanged()), SLOT(updateEngineList()));
288     connect(m_clientProxy, SIGNAL(serverReloaded()), this, SLOT(serverReloaded()));
289     connect(m_clientProxy, SIGNAL(contextPathUpdated(QStringList)),
290             m_crumblePath, SLOT(updateContextPath(QStringList)));
291
292     m_debugProject = ProjectExplorer::ProjectExplorerPlugin::instance()->startupProject();
293     if (m_debugProject->activeTarget()
294             && m_debugProject->activeTarget()->activeBuildConfiguration())
295     {
296         ProjectExplorer::BuildConfiguration *bc
297                 = m_debugProject->activeTarget()->activeBuildConfiguration();
298         m_debugProjectBuildDir = bc->buildDirectory();
299     }
300
301     connect(m_debugProject, SIGNAL(destroyed()), SLOT(currentDebugProjectRemoved()));
302     m_projectFinder.setProjectDirectory(m_debugProject->projectDirectory());
303
304     setupToolbar(true);
305     resetViews();
306
307     initializeDocuments();
308
309     QHashIterator<QString, QmlJSLiveTextPreview *> iter(m_textPreviews);
310     while(iter.hasNext()) {
311         iter.next();
312         iter.value()->setClientProxy(m_clientProxy);
313         iter.value()->updateDebugIds();
314     }
315 }
316
317 void InspectorUi::disconnected()
318 {
319     disconnect(m_clientProxy, SIGNAL(selectedItemsChanged(QList<QDeclarativeDebugObjectReference>)),
320                this, SLOT(gotoObjectReferenceDefinition(QList<QDeclarativeDebugObjectReference>)));
321
322     disconnect(m_clientProxy, SIGNAL(enginesChanged()), this, SLOT(updateEngineList()));
323     disconnect(m_clientProxy, SIGNAL(serverReloaded()), this, SLOT(serverReloaded()));
324     disconnect(m_clientProxy, SIGNAL(contextPathUpdated(QStringList)),
325                m_crumblePath, SLOT(updateContextPath(QStringList)));
326
327     m_debugProject = 0;
328     m_qmlEngine = 0;
329     resetViews();
330
331     setupToolbar(false);
332     applyChangesToQmlObserverHelper(false);
333
334     QHashIterator<QString, QmlJSLiveTextPreview *> iter(m_textPreviews);
335     while(iter.hasNext()) {
336         iter.next();
337         iter.value()->setClientProxy(0);
338     }
339     m_clientProxy = 0;
340     m_objectTreeWidget->clear();
341     m_pendingPreviewDocumentNames.clear();
342 }
343
344 void InspectorUi::updateEngineList()
345 {
346     QList<QDeclarativeDebugEngineReference> engines = m_clientProxy->engines();
347
348 //#warning update the QML engines combo
349
350     if (engines.isEmpty())
351         qWarning("qmldebugger: no engines found!");
352     else {
353         const QDeclarativeDebugEngineReference engine = engines.first();
354         m_clientProxy->queryEngineContext(engine.debugId());
355     }
356 }
357
358 void InspectorUi::changeSelectedItems(const QList<QDeclarativeDebugObjectReference> &objects)
359 {
360     if (m_lastSelectedDebugId >= 0) {
361         foreach (const QDeclarativeDebugObjectReference &ref, objects) {
362             if (ref.debugId() == m_lastSelectedDebugId) {
363                 // this is only the 'call back' after we have programatically set a new cursor
364                 // position in
365                 m_lastSelectedDebugId = -1;
366                 return;
367             }
368         }
369         m_lastSelectedDebugId = -1;
370     }
371
372     m_clientProxy->setSelectedItemsByObjectId(objects);
373 }
374
375 void InspectorUi::initializeDocuments()
376 {
377     if (!modelManager() || !m_clientProxy)
378         return;
379
380     Core::EditorManager *em = Core::EditorManager::instance();
381     m_loadedSnapshot = modelManager()->snapshot();
382
383     if (!m_listeningToEditorManager) {
384         m_listeningToEditorManager = true;
385         connect(em, SIGNAL(editorAboutToClose(Core::IEditor*)),
386                 this, SLOT(removePreviewForEditor(Core::IEditor*)));
387         connect(em, SIGNAL(editorOpened(Core::IEditor*)),
388                 this, SLOT(createPreviewForEditor(Core::IEditor*)));
389         connect(modelManager(),
390                 SIGNAL(documentChangedOnDisk(QmlJS::Document::Ptr)),
391                 this, SLOT(updatePendingPreviewDocuments(QmlJS::Document::Ptr)));
392     }
393
394     // initial update
395     foreach (Core::IEditor *editor, em->openedEditors()) {
396         createPreviewForEditor(editor);
397     }
398
399     applyChangesToQmlObserverHelper(true);
400 }
401
402 void InspectorUi::serverReloaded()
403 {
404     QmlJS::Snapshot snapshot = modelManager()->snapshot();
405     m_loadedSnapshot = snapshot;
406     for (QHash<QString, QmlJSLiveTextPreview *>::const_iterator it = m_textPreviews.constBegin();
407          it != m_textPreviews.constEnd(); ++it) {
408         Document::Ptr doc = snapshot.document(it.key());
409         it.value()->resetInitialDoc(doc);
410     }
411     m_clientProxy->refreshObjectTree();
412 }
413
414
415 void InspectorUi::removePreviewForEditor(Core::IEditor *oldEditor)
416 {
417     if (QmlJSLiveTextPreview *preview = m_textPreviews.value(oldEditor->file()->fileName())) {
418         preview->unassociateEditor(oldEditor);
419     }
420 }
421
422 QmlJSLiveTextPreview *InspectorUi::createPreviewForEditor(Core::IEditor *newEditor)
423 {
424     QmlJSLiveTextPreview *preview = 0;
425
426     if (m_clientProxy
427             && m_clientProxy->isConnected()
428             && newEditor
429             && newEditor->id() == QmlJSEditor::Constants::C_QMLJSEDITOR_ID
430             )
431     {
432         QString filename = newEditor->file()->fileName();
433         QmlJS::Document::Ptr doc = modelManager()->snapshot().document(filename);
434         if (!doc) {
435             if (filename.endsWith(".qml")) {
436                 // add to list of docs that we have to update when
437                 // snapshot figures out that there's a new document
438                 m_pendingPreviewDocumentNames.append(filename);
439             }
440             return 0;
441         }
442         if (!doc->qmlProgram())
443             return 0;
444
445         QmlJS::Document::Ptr initdoc = m_loadedSnapshot.document(filename);
446         if (!initdoc)
447             initdoc = doc;
448
449         if (m_textPreviews.contains(filename)) {
450             preview = m_textPreviews.value(filename);
451             preview->associateEditor(newEditor);
452         } else {
453             preview = new QmlJSLiveTextPreview(doc, initdoc, m_clientProxy, this);
454             connect(preview,
455                     SIGNAL(selectedItemsChanged(QList<QDeclarativeDebugObjectReference>)),
456                     SLOT(changeSelectedItems(QList<QDeclarativeDebugObjectReference>)));
457             connect(preview, SIGNAL(reloadQmlViewerRequested()),
458                     m_clientProxy, SLOT(reloadQmlViewer()));
459             connect(preview, SIGNAL(disableLivePreviewRequested()), SLOT(disableLivePreview()));
460
461             m_textPreviews.insert(newEditor->file()->fileName(), preview);
462             preview->associateEditor(newEditor);
463             preview->updateDebugIds();
464         }
465     }
466
467     return preview;
468 }
469
470 void InspectorUi::currentDebugProjectRemoved()
471 {
472     m_debugProject = 0;
473 }
474
475 void InspectorUi::resetViews()
476 {
477     m_crumblePath->updateContextPath(QStringList());
478 }
479
480 void InspectorUi::reloadQmlViewer()
481 {
482     if (m_clientProxy)
483         m_clientProxy->reloadQmlViewer();
484 }
485
486 void InspectorUi::gotoObjectReferenceDefinition(QList<QDeclarativeDebugObjectReference>
487                                                 objectReferences)
488 {
489     if (objectReferences.length())
490         gotoObjectReferenceDefinition(objectReferences.first());
491 }
492
493 void InspectorUi::enable()
494 {
495     m_toolbar->enable();
496     m_crumblePath->setEnabled(true);
497     m_objectTreeWidget->setEnabled(true);
498 }
499
500 void InspectorUi::disable()
501 {
502     m_toolbar->disable();
503     m_crumblePath->setEnabled(false);
504     m_objectTreeWidget->setEnabled(false);
505 }
506
507 void InspectorUi::gotoObjectReferenceDefinition(const QDeclarativeDebugObjectReference &obj)
508 {
509     Q_UNUSED(obj);
510
511     QDeclarativeDebugFileReference source = obj.source();
512     QString fileName = source.url().toLocalFile();
513
514     if (source.lineNumber() < 0 || !QFile::exists(fileName))
515         return;
516
517     fileName = m_projectFinder.findFile(fileName);
518
519     Core::EditorManager *editorManager = Core::EditorManager::instance();
520     Core::IEditor *editor = editorManager->openEditor(fileName);
521     TextEditor::ITextEditor *textEditor = qobject_cast<TextEditor::ITextEditor*>(editor);
522
523     if (textEditor) {
524         m_lastSelectedDebugId = obj.debugId();
525
526         editorManager->addCurrentPositionToNavigationHistory();
527         textEditor->gotoLine(source.lineNumber());
528         textEditor->widget()->setFocus();
529     }
530 }
531
532 bool InspectorUi::addQuotesForData(const QVariant &value) const
533 {
534     switch (value.type()) {
535     case QVariant::String:
536     case QVariant::Color:
537     case QVariant::Date:
538         return true;
539     default:
540         break;
541     }
542
543     return false;
544 }
545
546 void InspectorUi::setupDockWidgets()
547 {
548     m_toolbar->createActions(Core::Context(Debugger::Constants::C_QMLDEBUGGER));
549     m_toolbar->setObjectName("QmlInspectorToolbar");
550
551     m_crumblePath = new ContextCrumblePath;
552     m_crumblePath->setObjectName("QmlContextPath");
553     m_crumblePath->setWindowTitle(tr("Context Path"));
554     connect(m_crumblePath, SIGNAL(elementClicked(int)), SLOT(crumblePathElementClicked(int)));
555
556     m_objectTreeWidget = new QmlJSObjectTree;
557
558     QWidget *observerWidget = new QWidget;
559     observerWidget->setWindowTitle(tr("QML Observer"));
560     observerWidget->setObjectName(Debugger::Constants::DOCKWIDGET_QML_INSPECTOR);
561
562     QVBoxLayout *wlay = new QVBoxLayout(observerWidget);
563     wlay->setMargin(0);
564     wlay->setSpacing(0);
565     observerWidget->setLayout(wlay);
566     wlay->addWidget(m_toolbar->widget());
567     wlay->addWidget(m_objectTreeWidget);
568     wlay->addWidget(m_crumblePath);
569
570     Debugger::DebuggerMainWindow *mw = Debugger::DebuggerPlugin::mainWindow();
571     QDockWidget *dock = mw->createDockWidget(Debugger::QmlLanguage, observerWidget);
572     dock->setAllowedAreas(Qt::TopDockWidgetArea | Qt::BottomDockWidgetArea);
573     dock->setTitleBarWidget(new QWidget(dock));
574 }
575
576 void InspectorUi::crumblePathElementClicked(int pathIndex)
577 {
578     if (m_clientProxy && m_clientProxy->isConnected() && !m_crumblePath->isEmpty()) {
579         m_clientProxy->setContextPathIndex(pathIndex);
580     }
581 }
582
583 bool InspectorUi::showExperimentalWarning()
584 {
585     return m_settings->showLivePreviewWarning();
586 }
587
588 void InspectorUi::setShowExperimentalWarning(bool value)
589 {
590     m_settings->setShowLivePreviewWarning(value);
591 }
592
593 InspectorUi *InspectorUi::instance()
594 {
595     return m_instance;
596 }
597
598 ProjectExplorer::Project *InspectorUi::debugProject() const
599 {
600     return m_debugProject;
601 }
602
603 bool InspectorUi::isShadowBuildProject() const
604 {
605     // for .qmlproject based stuff, build dir is empty
606     if (!debugProject() || debugProjectBuildDirectory().isEmpty())
607         return false;
608
609     return (debugProject()->projectDirectory() != debugProjectBuildDirectory());
610 }
611
612 QString InspectorUi::debugProjectBuildDirectory() const
613 {
614     return m_debugProjectBuildDir;
615 }
616
617 void InspectorUi::setApplyChangesToQmlObserver(bool applyChanges)
618 {
619     emit livePreviewActivated(applyChanges);
620     applyChangesToQmlObserverHelper(applyChanges);
621 }
622
623 void InspectorUi::applyChangesToQmlObserverHelper(bool applyChanges)
624 {
625     QHashIterator<QString, QmlJSLiveTextPreview *> iter(m_textPreviews);
626     while(iter.hasNext()) {
627         iter.next();
628         iter.value()->setApplyChangesToQmlObserver(applyChanges);
629     }
630 }
631
632 void InspectorUi::updatePendingPreviewDocuments(QmlJS::Document::Ptr doc)
633 {
634     int idx = -1;
635     idx = m_pendingPreviewDocumentNames.indexOf(doc->fileName());
636
637     if (idx == -1)
638         return;
639
640     QList<Core::IEditor *> editors
641             = Core::EditorManager::instance()->editorsForFileName(doc->fileName());
642
643     if (editors.isEmpty())
644         return;
645
646     m_pendingPreviewDocumentNames.removeAt(idx);
647
648     QmlJSLiveTextPreview *preview = createPreviewForEditor(editors.first());
649     editors.removeFirst();
650
651     foreach(Core::IEditor *editor, editors) {
652         preview->associateEditor(editor);
653     }
654 }
655
656 void InspectorUi::disableLivePreview()
657 {
658     setApplyChangesToQmlObserver(false);
659 }
660
661 void InspectorUi::setupToolbar(bool doConnect)
662 {
663     if (doConnect) {
664         connect(m_clientProxy, SIGNAL(connected()),
665                 this, SLOT(enable()));
666         connect(m_clientProxy, SIGNAL(disconnected()),
667                 this, SLOT(disable()));
668
669         connect(m_toolbar, SIGNAL(designModeSelected(bool)),
670                 m_clientProxy, SLOT(setDesignModeBehavior(bool)));
671         connect(m_toolbar, SIGNAL(reloadSelected()),
672                 m_clientProxy, SLOT(reloadQmlViewer()));
673         connect(m_toolbar, SIGNAL(animationSpeedChanged(qreal)),
674                 m_clientProxy, SLOT(setAnimationSpeed(qreal)));
675         connect(m_toolbar, SIGNAL(colorPickerSelected()),
676                 m_clientProxy, SLOT(changeToColorPickerTool()));
677         connect(m_toolbar, SIGNAL(zoomToolSelected()),
678                 m_clientProxy, SLOT(changeToZoomTool()));
679         connect(m_toolbar, SIGNAL(selectToolSelected()),
680                 m_clientProxy, SLOT(changeToSelectTool()));
681         connect(m_toolbar, SIGNAL(applyChangesFromQmlFileTriggered(bool)),
682                 this, SLOT(setApplyChangesToQmlObserver(bool)));
683         connect(m_toolbar, SIGNAL(showAppOnTopSelected(bool)),
684                 m_clientProxy, SLOT(showAppOnTop(bool)));
685
686         connect(m_clientProxy, SIGNAL(colorPickerActivated()),
687                 m_toolbar, SLOT(activateColorPicker()));
688         connect(m_clientProxy, SIGNAL(selectToolActivated()),
689                 m_toolbar, SLOT(activateSelectTool()));
690         connect(m_clientProxy, SIGNAL(zoomToolActivated()),
691                 m_toolbar, SLOT(activateZoomTool()));
692         connect(m_clientProxy, SIGNAL(designModeBehaviorChanged(bool)),
693                 m_toolbar, SLOT(setDesignModeBehavior(bool)));
694         connect(m_clientProxy, SIGNAL(showAppOnTopChanged(bool)),
695                 m_toolbar, SLOT(setShowAppOnTop(bool)));
696         connect(m_clientProxy, SIGNAL(selectedColorChanged(QColor)),
697                 m_toolbar, SLOT(setSelectedColor(QColor)));
698
699         connect(m_clientProxy, SIGNAL(animationSpeedChanged(qreal)),
700                 m_toolbar, SLOT(setAnimationSpeed(qreal)));
701
702         enable();
703     } else {
704         disconnect(m_clientProxy, SIGNAL(connected()), this, SLOT(enable()));
705         disconnect(m_clientProxy, SIGNAL(disconnected()), this, SLOT(disable()));
706
707         disconnect(m_toolbar, SIGNAL(designModeSelected(bool)),
708                    m_clientProxy, SLOT(setDesignModeBehavior(bool)));
709         disconnect(m_toolbar, SIGNAL(reloadSelected()),
710                    m_clientProxy, SLOT(reloadQmlViewer()));
711         disconnect(m_toolbar, SIGNAL(animationSpeedChanged(qreal)),
712                    m_clientProxy, SLOT(setAnimationSpeed(qreal)));
713         disconnect(m_toolbar, SIGNAL(colorPickerSelected()),
714                    m_clientProxy, SLOT(changeToColorPickerTool()));
715         disconnect(m_toolbar, SIGNAL(zoomToolSelected()),
716                    m_clientProxy, SLOT(changeToZoomTool()));
717         disconnect(m_toolbar, SIGNAL(selectToolSelected()),
718                    m_clientProxy, SLOT(changeToSelectTool()));
719         disconnect(m_toolbar, SIGNAL(applyChangesFromQmlFileTriggered(bool)),
720                    this, SLOT(setApplyChangesToQmlObserver(bool)));
721         disconnect(m_toolbar, SIGNAL(showAppOnTopSelected(bool)),
722                    m_clientProxy, SLOT(showAppOnTop(bool)));
723
724         disconnect(m_clientProxy, SIGNAL(colorPickerActivated()),
725                    m_toolbar, SLOT(activateColorPicker()));
726         disconnect(m_clientProxy, SIGNAL(selectToolActivated()),
727                    m_toolbar, SLOT(activateSelectTool()));
728         disconnect(m_clientProxy, SIGNAL(zoomToolActivated()),
729                    m_toolbar, SLOT(activateZoomTool()));
730         disconnect(m_clientProxy, SIGNAL(designModeBehaviorChanged(bool)),
731                    m_toolbar, SLOT(setDesignModeBehavior(bool)));
732         disconnect(m_clientProxy, SIGNAL(showAppOnTopChanged(bool)),
733                    m_toolbar, SLOT(setShowAppOnTop(bool)));
734         disconnect(m_clientProxy, SIGNAL(selectedColorChanged(QColor)),
735                    m_toolbar, SLOT(setSelectedColor(QColor)));
736
737         disconnect(m_clientProxy, SIGNAL(animationSpeedChanged(qreal)),
738                    m_toolbar, SLOT(setAnimationSpeed(qreal)));
739
740         disable();
741     }
742 }