24 #include "evorobotviewer.h"
25 #include "abstracttest.h"
27 #include "total99resources.h"
28 #include <QGridLayout>
29 #include <QPushButton>
31 #include <QFileDialog>
32 #include <QVBoxLayout>
37 #include <QCoreApplication>
39 using namespace qglviewer;
46 #pragma warning(disable:4996)
54 ga = evorobot->
getGA();
62 connect( evorobot, SIGNAL(actionFinished()),
this, SLOT(onActionFinished()) );
72 actionsMenu->addAction(
"Evolve", evorobot, SLOT(evolve()) );
73 actionsMenu->addAction(
"Stop", evorobot, SLOT(stop()) );
77 QList<ParameterSettableUIViewer> viewsList;
78 viewsList.append( evogaControls( parent, flags ) );
80 viewsList.append( fitview( parent, flags ) );
81 viewsList.append( statview( parent, flags ) );
82 viewsList.append( renderWorld( parent, flags ) );
85 for (
int i = 0; i < testsList.size(); i++) {
87 if ( testIndividual ) {
88 viewsList.append( testIndividualUI( testIndividual, parent, flags ) );
95 QMenu* testMenu = menuBar->addMenu(
"Tests" );
97 for (
int i = 0; i < testsList.size(); i++) {
99 QAction* action = testMenu->addAction( test->
menuText(), evorobot, SLOT(runTestFromQAction()) );
100 action->setData( QVariant(testsList[i]) );
101 action->setToolTip( test->
tooltip() );
106 void EvoRobotViewer::resourceChanged(QString resourceName, ResourceChangeType changeType)
109 if ((resourceName ==
"world") && (changeType != Deleted)) {
110 World* world = getResource<World>();
112 connect( world, SIGNAL(advanced()),
this, SLOT(onWorldAdvance()), Qt::QueuedConnection );
116 ParameterSettableUIViewer EvoRobotViewer::renderWorld( QWidget* parent, Qt::WindowFlags flags )
119 renderworldwrapper =
new RenderWorldWrapperWidget(parent, flags);
122 return ParameterSettableUIViewer(renderworldwrapper,
"RenderWorld");
125 ParameterSettableUIViewer EvoRobotViewer::evogaControls( QWidget* parent, Qt::WindowFlags flags ) {
126 QWidget* widget =
new QWidget( parent, flags );
127 QGridLayout* lay =
new QGridLayout( widget );
131 infoEvoga =
new QLabel(
"Information", widget );
132 infoEvoga->setStyleSheet(
"QLabel { font: bold normal large \"Courier\" }" );
133 lay->addWidget( infoEvoga, 0, 0, 1, 2 );
135 QPushButton* bt =
new QPushButton(
"Do Step", widget );
136 bt->setAutoRepeat(
true);
137 bt->setEnabled(
false );
138 connect( bt, SIGNAL(clicked(
bool)), ga, SLOT(doNextStep()) );
140 QCheckBox* cb =
new QCheckBox(
"Step by Step Mode", widget );
141 connect( cb, SIGNAL(clicked(
bool)), ga, SLOT(enableStepByStep(
bool)) );
142 connect( cb, SIGNAL(clicked(
bool)), bt, SLOT(setEnabled(
bool)) );
144 lay->addWidget( cb, 1, 0 );
145 lay->addWidget( bt, 1, 1 );
147 bt =
new QPushButton(
"Next Trial", widget );
148 connect( bt, SIGNAL(clicked()),
this, SLOT(evogaNextTrial()) );
149 lay->addWidget( bt, 2, 0, 1, 2 );
153 return ParameterSettableUIViewer( widget,
"Evoga Controls" );
156 void EvoRobotViewer::evogaNextTrial() {
160 ParameterSettableUIViewer EvoRobotViewer::fitview( QWidget* parent, Qt::WindowFlags flags )
163 ftv =
new FitViewer(3,4000,parent,flags);
164 ftv->setChunkProperties(0,
"MaxFit", Qt::red,
true);
165 ftv->setChunkProperties(1,
"AverageFit", Qt::green,
true);
166 ftv->setChunkProperties(2,
"MinFit", Qt::blue,
true);
167 ftv->setLabels(QString(
"EvoICub Fitness Monitor"), QString(
"Generations"), QString(
"Fitness"));
168 ftv->setGeometry(50, 50, 500, 500);
169 ftv->setWindowTitle(
"Fitness Curves" );
170 connect( ga, SIGNAL(startingReplication(
int)),
171 this, SLOT(onEvogaStartingReplication(
int)), Qt::QueuedConnection );
172 connect( ga, SIGNAL(recoveredInterruptedEvolution(QString)),
173 this, SLOT(onEvogaRecoveredInterruptedEvolution(QString)), Qt::QueuedConnection );
174 connect( ga, SIGNAL(endGeneration(
int,
int,
int,
int)),
175 this, SLOT(onEvogaEndGeneration(
int,
int,
int,
int)), Qt::QueuedConnection );
176 return ParameterSettableUIViewer( ftv,
"Fitness monitor" );
188 ParameterSettableUIViewer EvoRobotViewer::statview( QWidget* parent, Qt::WindowFlags flags )
190 statViewer =
new QWidget( parent, flags );
191 statViewer->setWindowTitle(
"Statictis Viewer" );
192 QGridLayout* lay =
new QGridLayout( statViewer );
193 QPushButton* but =
new QPushButton(
"Load a Stat File", statViewer );
194 connect( but, SIGNAL(clicked()),
this, SLOT(loadStat()) );
195 lay->addWidget( but, 0, 0 );
196 but =
new QPushButton(
"Load All Stat", statViewer );
197 connect( but, SIGNAL(clicked()),
this, SLOT(loadAllStat()) );
198 lay->addWidget( but, 0, 1 );
199 return ParameterSettableUIViewer( statViewer,
"Statistic Viewer" );
202 void EvoRobotViewer::loadStat() {
203 QString filename = QFileDialog::getOpenFileName(statViewer, tr(
"Open Stat File"),
".", tr(
"Files with statistics (*.fit *.ini)"));
204 if (filename.isEmpty()) {
207 FitViewer* fitViewer = statViewer->findChild<FitViewer*>(
"statFitViewer" );
211 fitViewer =
new FitViewer(3, 4000, statViewer);
212 fitViewer->setObjectName(
"statFitViewer" );
213 fitViewer->setLabels(QString(
"Stat monitor. File: ").append(filename), QString(
"Generation"), QString(
"Fitnes"));
214 fitViewer->setChunkProperties(0,
"MaxFit", Qt::red,
true);
215 fitViewer->setChunkProperties(1,
"Average", Qt::green,
true);
216 fitViewer->setChunkProperties(2,
"Minimum", Qt::blue,
true);
217 fitViewer->loadRawData(0, filename, 0);
218 fitViewer->loadRawData(1, filename, 1);
219 fitViewer->loadRawData(2, filename, 2);
220 QGridLayout* lay = qobject_cast<QGridLayout*>( statViewer->layout() );
221 lay->addWidget( fitViewer, 1, 0, 1, 2 );
222 lay->setRowStretch( 1, 2 );
226 void EvoRobotViewer::loadAllStat()
228 FitViewer* fitViewer = statViewer->findChild<FitViewer*>(
"statFitViewer" );
234 QFileInfoList statFiles = currentDir.entryInfoList( QStringList() <<
"*.fit", QDir::Files, QDir::Name );
237 fitViewer->setObjectName(
"statFitViewer" );
238 QString title = QString(
"Stat monitor");
239 fitViewer->setLabels(title, QString(
"Generation"), QString(
"Fitness"));
241 QColor colors[10] = { QColor(Qt::red), QColor(Qt::green), QColor(Qt::blue), QColor(Qt::cyan),
242 QColor(Qt::magenta), QColor(Qt::darkYellow), QColor(Qt::gray), QColor(255, 140, 0, 255),
243 QColor(153, 50, 204, 255), QColor(Qt::black) };
244 for(
int i=0; i<statFiles.size(); i++ ) {
245 QFileInfo statFile = statFiles[i];
246 QColor col = colors[i%10];
247 fitViewer->setChunkProperties( i, QString(
"Seed:").append(statFile.baseName().split(
"S").last()), col,
true );
248 fitViewer->loadRawData( i, statFile.fileName(), 0 );
250 fitViewer->sortchunks();
251 QGridLayout* lay = qobject_cast<QGridLayout*>( statViewer->layout() );
252 lay->addWidget( fitViewer, 1, 0, 1, 2 );
253 lay->setRowStretch( 1, 2 );
257 ParameterSettableUIViewer EvoRobotViewer::testIndividualUI( TestIndividual* test, QWidget* parent, Qt::WindowFlags flags ) {
258 TestIndividualGUI* testIndUI =
new TestIndividualGUI( test, parent, flags );
259 testIndUI->setWindowTitle(
"Select the Individual to Test" );
260 return ParameterSettableUIViewer( testIndUI,
"Individual to Test", QString(),
"From this view you can select an individual to test using the \"TestIndividual\" from the \"Tests\" menu" );
263 void EvoRobotViewer::onWorldAdvance() {
266 EvoRobotExperiment* exp = getResource<EvoRobotExperiment>(
"experiment");
268 if ( exp->getActivityPhase() == EvoRobotExperiment::INTEST ) {
275 infoEvoga->setText( QString(
"Step %1 of %2 --- Trial %3 of %4" )
276 .arg( exp->getCurStep(), 5 ).arg( exp->getNSteps() )
277 .arg( exp->getCurTrial(), 5 ).arg( exp->getNTrials() ) );
280 void EvoRobotViewer::onEvogaStartingReplication(
int ) {
284 void EvoRobotViewer::onEvogaRecoveredInterruptedEvolution( QString statfile ) {
285 ftv->loadRawData(0,statfile,0);
286 ftv->loadRawData(1,statfile,1);
287 ftv->loadRawData(2,statfile,2);
290 void EvoRobotViewer::onEvogaEndGeneration(
int generation,
int fmax,
int faverage,
int fmin ) {
291 ftv->setChunkValue(0,generation,fmax);
292 ftv->setChunkValue(1,generation,faverage);
293 ftv->setChunkValue(2,generation,fmin);
294 ftv->diplayUntilStep(generation);
298 void EvoRobotViewer::onActionFinished() {
299 infoEvoga->setText( evorobot->
status() );
304 class ForceRenderWorldUpdateEvent :
public QEvent
307 ForceRenderWorldUpdateEvent() :
312 virtual ~ForceRenderWorldUpdateEvent()
319 QWidget(parent, flags),
322 m_layout(new QVBoxLayout(this)),
323 m_renderWorldStateRestored(false),
324 m_setCameraToLookAtRobot(false),
328 setWindowTitle(
"3D World");
329 m_layout->setContentsMargins(0, 0, 0, 0);
330 m_layout->addWidget(m_renderWorld);
331 const QString stateFileName =
".evolver.xml";
333 if (QFile::exists(stateFileName)) {
334 m_renderWorldStateRestored =
true;
349 if (m_setCameraToLookAtRobot) {
352 m_setCameraToLookAtRobot =
false;
354 m_renderWorldStateRestored =
true;
357 m_renderWorld->update();
369 void RenderWorldWrapperWidget::resourceChanged(QString resourceName, ResourceChangeType changeType)
371 if (resourceName ==
"robot") {
372 if ((changeType != Deleted) && (!m_renderWorldStateRestored)) {
374 m_robotTm = getResource<WObject>()->matrix();
375 }
catch (
const ResourceTypeMismatchException&) {
378 m_setCameraToLookAtRobot =
true;
381 Logger::info(
"Unknown resource " + resourceName +
" for RenderWorldWrapperWidget widget");
385 QCoreApplication::postEvent(
this,
new ForceRenderWorldUpdateEvent());
388 void RenderWorldWrapperWidget::customEvent(QEvent* event)
390 if (event->type() == QEvent::User) {
396 void RenderWorldWrapperWidget::lookAtRobot()
398 wVector cameraDefaultPosition = m_robotTm.
transformVector(wVector(-0.8f, 0.0f, +0.6f));
399 m_renderWorld->
camera()->setPosition(
Vec(cameraDefaultPosition[0], cameraDefaultPosition[1], cameraDefaultPosition[2]));
400 m_renderWorld->
camera()->setUpVector(
Vec(0.0f, 0.0f, 1.0f));
538 QWidget(parent, flags)
543 QGridLayout* mainLay =
new QGridLayout(
this );
546 QPushButton* bt =
new QPushButton(
"Refresh",
this );
547 connect( bt, SIGNAL(clicked()),
this, SLOT(populateCombo()) );
548 mainLay->addWidget(bt, 0, 0, 1, 2);
550 combo =
new QComboBox();
551 list =
new QListWidget();
552 mainLay->addWidget(
new QLabel(
"Select File to load:"), 1, 0);
553 mainLay->addWidget(combo, 1, 1);
554 mainLay->addWidget(list, 2, 0, 1, 2);
560 connect(combo, SIGNAL(activated(QString)),
this, SLOT(seedWasChosen()));
561 connect(list, SIGNAL(itemDoubleClicked(QListWidgetItem*)),
this, SLOT(agentClicked()));
564 void TestIndividualGUI::populateCombo()
569 QString bestF = test->component()->getGA()->bestsFilename();
570 QString genF = test->component()->getGA()->generationFilename();
573 QDir* dir =
new QDir();
574 QStringList expression = (QStringList() << bestF << genF);
575 fileList = dir->entryList(expression);
578 combo->addItems(fileList);
581 void TestIndividualGUI::seedWasChosen()
584 test->setPopulationToTest( combo->currentText(), false );
587 int loadindi = test->component()->getGA()->numLoadedGenotypes();
588 for(
int i=1; i<=loadindi; i++)
590 list->addItem(QString::number(i));
594 void TestIndividualGUI::agentClicked()
597 test->setIndividualToTest( list->currentRow() );
603 #if defined(_MSC_VER)