OSDN Git Service

[denncoCreator] implemented the feature to launch dennco engine from creator.
[dennco/denncoCreator.git] / Source / mainwindow.cpp
1 //  Copyright (c) 2012 Dennco Project
2 //
3 // This program is free software: you can redistribute it and/or modify
4 // it under the terms of the GNU General Public License as published by
5 // the Free Software Foundation, either version 3 of the License, or
6 // (at your option) any later version.
7 //
8 // This program is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 // GNU General Public License for more details.
12 //
13 // You should have received a copy of the GNU General Public License
14 // along with this program.  If not, see <http://www.gnu.org/licenses/>.
15
16 //
17 //  Created by tkawata on Sep-30, 2012.
18 //
19 #include "TKLog.h"
20
21 #include "mainwindow.h"
22 #include "ui_mainwindow.h"
23
24 #include "dccreator.h"
25 #include "dccontent.h"
26 #include "dcglvisualizerwidget.h"
27 #include "dctreeviewwidget.h"
28 #include "TKConsole.h"
29 #include "utils/dcresources.h"
30 #include "utils/dcskeltoncreatorutil.h"
31
32 #include <QCloseEvent>
33 #include <QFileDialog>
34 #include <QMessageBox>
35 #include <QSettings>
36 #include <QLocalSocket>
37
38 #ifdef Q_WS_WIN
39     const QString DENNCO_ENGINE = "QtDennco.exe";
40 #elif Q_WS_MACX
41
42 #elif Q_OS_UNIX
43
44 #endif
45
46 class SleeperThread : public QThread
47 {
48 public:
49     static void msleep(unsigned long msecs)
50     {
51         QThread::msleep(msecs);
52     }
53 };
54
55 MainWindow::MainWindow(QWidget *parent) :
56     QMainWindow(parent),
57     ui(new Ui::MainWindow)
58 {
59     ui->setupUi(this);
60
61     DCResources::initResources();
62
63     createActions();
64     createMenus();
65     createToolBars();
66     createStatusBar();
67
68     readSettings();
69
70     TKLog::setDestination(new TKConsole);
71
72     d_IPCServerName = "denncoCreator_";
73     QTextStream s(&d_IPCServerName);
74     s.setIntegerBase(16);
75     s << qrand();
76
77     d_creator = new DCCreator(this);
78     d_visualizerWidget = new DCGLVisualizerWidget(d_creator, this) ;
79     setCentralWidget(d_visualizerWidget);
80
81     d_treeViewWidget = new DCTreeViewWidget(this, d_creator);
82     ui->treeViewDock->layout()->addWidget(d_treeViewWidget);
83
84     setCurrentContent("");
85     setUnifiedTitleAndToolBarOnMac(true);
86 }
87
88 MainWindow::~MainWindow()
89 {
90     delete ui;
91     if (d_creator)
92         delete d_creator;
93 }
94
95
96 //! [3]
97 void MainWindow::closeEvent(QCloseEvent *event)
98 //! [3] //! [4]
99 {
100     if (maybeSave()) {
101         writeSettings();
102         event->accept();
103     } else {
104         event->ignore();
105     }
106 }
107
108 void MainWindow::newFile()
109 {
110     QString dirName = QFileDialog::getSaveFileName(this, tr("Create new content"));
111     if (!dirName.isEmpty() && DCSkeltonCreatorUtil::createNewContent(dirName))
112     {
113         loadContent(dirName);
114     }
115 }
116
117 void MainWindow::open()
118 {
119     if (maybeSave()) {
120         QString dirName = QFileDialog::getExistingDirectory(this, tr("Open a content"));
121         if (!dirName.isEmpty())
122             loadContent(dirName);
123     }
124 }
125 //! [8]
126
127 //! [9]
128 bool MainWindow::save()
129 {
130     return saveContent();
131 }
132
133 bool MainWindow::saveAs()
134 {
135     //TODO
136     return false;
137 }
138
139 void MainWindow::about()
140 {
141    QMessageBox::about(this, tr("About Application"),
142             tr("TODO: exampalin\81@about <b>dennco creator</b>  "
143                "TODO: exampalin\81@about <b>dennco creator</b> "
144                "TODO: exampalin\81@about <b>dennco creator</b>"));
145 }
146
147 void MainWindow::documentWasModified()
148 //! [15] //! [16]
149 {
150 //    setWindowModified(textEdit->document()->isModified());
151 }
152 //! [16]
153
154 //! [17]
155 void MainWindow::createActions()
156 //! [17] //! [18]
157 {
158     newAct = new QAction(QIcon(":/images/new.png"), tr("&New"), this);
159     newAct->setShortcuts(QKeySequence::New);
160     newAct->setStatusTip(tr("Create a new file"));
161     connect(newAct, SIGNAL(triggered()), this, SLOT(newFile()));
162
163 //! [19]
164     openAct = new QAction(QIcon(":/images/open.png"), tr("&Open..."), this);
165     openAct->setShortcuts(QKeySequence::Open);
166     openAct->setStatusTip(tr("Open an existing file"));
167     connect(openAct, SIGNAL(triggered()), this, SLOT(open()));
168 //! [18] //! [19]
169
170     saveAct = new QAction(QIcon(":/images/save.png"), tr("&Save"), this);
171     saveAct->setShortcuts(QKeySequence::Save);
172     saveAct->setStatusTip(tr("Save the document to disk"));
173     connect(saveAct, SIGNAL(triggered()), this, SLOT(save()));
174
175     saveAsAct = new QAction(tr("Save &As..."), this);
176     saveAsAct->setShortcuts(QKeySequence::SaveAs);
177     saveAsAct->setStatusTip(tr("Save the document under a new name"));
178     connect(saveAsAct, SIGNAL(triggered()), this, SLOT(saveAs()));
179
180 //! [20]
181     exitAct = new QAction(tr("E&xit"), this);
182     exitAct->setShortcuts(QKeySequence::Quit);
183 //! [20]
184     exitAct->setStatusTip(tr("Exit the application"));
185     connect(exitAct, SIGNAL(triggered()), this, SLOT(close()));
186
187 //! [21]
188     cutAct = new QAction(QIcon(":/images/cut.png"), tr("Cu&t"), this);
189 //! [21]
190     cutAct->setShortcuts(QKeySequence::Cut);
191     cutAct->setStatusTip(tr("Cut the current selection's contents to the "
192                             "clipboard"));
193 //    connect(cutAct, SIGNAL(triggered()), textEdit, SLOT(cut()));
194
195     copyAct = new QAction(QIcon(":/images/copy.png"), tr("&Copy"), this);
196     copyAct->setShortcuts(QKeySequence::Copy);
197     copyAct->setStatusTip(tr("Copy the current selection's contents to the "
198                              "clipboard"));
199 //    connect(copyAct, SIGNAL(triggered()), textEdit, SLOT(copy()));
200
201     pasteAct = new QAction(QIcon(":/images/paste.png"), tr("&Paste"), this);
202     pasteAct->setShortcuts(QKeySequence::Paste);
203     pasteAct->setStatusTip(tr("Paste the clipboard's contents into the current "
204                               "selection"));
205
206     //    connect(pasteAct, SIGNAL(triggered()), textEdit, SLOT(paste()));
207
208     playAct = new QAction(QIcon(":/images/playbutton.png"), tr("Play"), this);
209     playAct->setStatusTip(tr("Play the editing content"));
210
211     connect(playAct, SIGNAL(triggered()), this, SLOT(playContent()));
212
213     aboutAct = new QAction(tr("&About"), this);
214     aboutAct->setStatusTip(tr("Show the application's About box"));
215     connect(aboutAct, SIGNAL(triggered()), this, SLOT(about()));
216
217     cutAct->setEnabled(false);
218     copyAct->setEnabled(false);
219     playAct->setEnabled(false);
220 //    connect(textEdit, SIGNAL(copyAvailable(bool)),
221 //            cutAct, SLOT(setEnabled(bool)));
222 //    connect(textEdit, SIGNAL(copyAvailable(bool)),
223 //            copyAct, SLOT(setEnabled(bool)));
224 }
225 //! [24]
226
227 //! [25] //! [26]
228 void MainWindow::createMenus()
229 //! [25] //! [27]
230 {
231     fileMenu = menuBar()->addMenu(tr("&File"));
232     fileMenu->addAction(newAct);
233 //! [28]
234     fileMenu->addAction(openAct);
235 //! [28]
236     fileMenu->addAction(saveAct);
237 //! [26]
238     fileMenu->addAction(saveAsAct);
239     fileMenu->addSeparator();
240     fileMenu->addAction(exitAct);
241
242     editMenu = menuBar()->addMenu(tr("&Edit"));
243     editMenu->addAction(cutAct);
244     editMenu->addAction(copyAct);
245     editMenu->addAction(pasteAct);
246
247     menuBar()->addSeparator();
248
249     editMenu = menuBar()->addMenu(tr("&Play"));
250     editMenu->addAction(playAct);
251
252     menuBar()->addSeparator();
253
254     helpMenu = menuBar()->addMenu(tr("&Help"));
255     helpMenu->addAction(aboutAct);
256 }
257
258 void MainWindow::createToolBars()
259 {
260     fileToolBar = addToolBar(tr("File"));
261     fileToolBar->addAction(newAct);
262     fileToolBar->addAction(openAct);
263     fileToolBar->addAction(saveAct);
264
265     editToolBar = addToolBar(tr("Edit"));
266     editToolBar->addAction(cutAct);
267     editToolBar->addAction(copyAct);
268     editToolBar->addAction(pasteAct);
269
270     playToolBar = addToolBar(tr("Play"));
271     playToolBar->addAction(playAct);
272 }
273
274 void MainWindow::createStatusBar()
275 //! [32] //! [33]
276 {
277     statusBar()->showMessage(tr("Ready"));
278 }
279 //! [33]
280
281 //! [34] //! [35]
282 void MainWindow::readSettings()
283 //! [34] //! [36]
284 {
285     QSettings settings("dennco project", "dennco creator");
286     QPoint pos = settings.value("pos", QPoint(200, 200)).toPoint();
287     QSize size = settings.value("size", QSize(400, 400)).toSize();
288     resize(size);
289     move(pos);
290 }
291 //! [35] //! [36]
292
293 //! [37] //! [38]
294 void MainWindow::writeSettings()
295 //! [37] //! [39]
296 {
297     QSettings settings("dennco project", "dennco creator");
298     settings.setValue("pos", pos());
299     settings.setValue("size", size());
300 }
301 //! [38] //! [39]
302
303 //! [40]
304 bool MainWindow::maybeSave()
305 //! [40] //! [41]
306 {
307 //    if (textEdit->document()->isModified()) {
308  //       QMessageBox::StandardButton ret;
309  //       ret = QMessageBox::warning(this, tr("Application"),
310  //                    tr("The document has been modified.\n"
311 //                        "Do you want to save your changes?"),
312 //                     QMessageBox::Save | QMessageBox::Discard | QMessageBox::Cancel);
313 //        if (ret == QMessageBox::Save)
314 //            return save();
315 //        else if (ret == QMessageBox::Cancel)
316 //            return false;
317 //    }
318     return true;
319 }
320 //! [41]
321
322 //! [42]
323 void MainWindow::loadContent(const QString &contentDirectory)
324 {
325     if (!d_creator)
326         return;
327
328     if (d_creator->loadContent(contentDirectory))
329     {
330         playAct->setEnabled(true);
331     }
332     else
333     {
334         playAct->setEnabled(false);
335     }
336
337     setCurrentContent(contentDirectory);
338 }
339
340 bool MainWindow::saveContent()
341 {
342     if (!d_creator)
343         return false;
344
345     if (d_creator->getCurrentContainer())
346     {
347         d_creator->saveAll(true);
348     }
349
350     return true;
351 }
352
353 void MainWindow::setCurrentContent(const QString &contentDirectory)
354 {
355     curContent = contentDirectory;
356 //    textEdit->document()->setModified(false);
357     setWindowModified(false);
358
359     QString shownName = curContent;
360     if (curContent.isEmpty())
361         shownName = "untitled.txt";
362     setWindowFilePath(shownName);
363 }
364
365 QString MainWindow::strippedName(const QString &fullFileName)
366 {
367     return QFileInfo(fullFileName).fileName();
368 }
369
370 void MainWindow::playContent()
371 {
372     if (!d_creator || !d_creator->getCurrentContent())
373         return;
374
375     if (d_player.state() != QProcess::NotRunning)
376     {
377         QLocalSocket *socket = new QLocalSocket(this);
378         connect(socket, SIGNAL(disconnected()), socket,SLOT(deleteLater()));
379
380         for (int retry = 0; retry < 10; retry++)
381         {
382             socket->connectToServer(d_IPCServerName);
383             if (socket->waitForConnected())
384             {
385                 break;
386             }
387             SleeperThread::msleep(500);
388         }
389         QString requestData = "close,";
390         socket->write(requestData.toLocal8Bit());
391         socket->flush();
392         socket->close();
393     }
394
395     if (!d_player.waitForFinished(5000))
396         d_player.kill();
397
398     if (d_player.state() == QProcess::NotRunning)
399     {
400         QStringList args;
401         args << "-creatorControlled";
402         args << d_IPCServerName;
403
404         d_player.start(DENNCO_ENGINE, args);
405         d_player.waitForStarted(5000);
406     }
407
408     if (d_player.state() == QProcess::Running)
409     {
410         QLocalSocket *socket = new QLocalSocket(this);
411         connect(socket, SIGNAL(disconnected()), socket,SLOT(deleteLater()));
412         for (int retry = 0; retry < 10; retry++)
413         {
414             socket->connectToServer(d_IPCServerName);
415             if (socket->waitForConnected())
416             {
417                 break;
418             }
419             SleeperThread::msleep(500);
420         }
421         QString requestData = "load,";
422         requestData.append(d_creator->getCurrentContent()->getContentRootPath());
423         socket->write(requestData.toLocal8Bit());
424         socket->flush();
425         socket->close();
426     }
427 }