balancing arenas can be started individually

This commit is contained in:
2026-05-03 20:33:33 +02:00
parent 426870158c
commit 55b42a03d9
6 changed files with 100 additions and 29 deletions

View File

@@ -14,6 +14,10 @@ BalancingWindow::BalancingWindow(const BalancingConfig& balancingConfig,
QVBoxLayout* mainLayout = new QVBoxLayout(this);
mainLayout->setContentsMargins(0, 0, 0, 0);
m_startAllButton = new QPushButton("Start All", this);
mainLayout->addWidget(m_startAllButton);
connect(m_startAllButton, &QPushButton::clicked, this, &BalancingWindow::startAll);
QScrollArea* scrollArea = new QScrollArea(this);
scrollArea->setWidgetResizable(true);
@@ -25,13 +29,18 @@ BalancingWindow::BalancingWindow(const BalancingConfig& balancingConfig,
unsigned int seed = 0;
for (const ArenaConfig& arenaConfig : balancingConfig.arenas)
{
int index = static_cast<int>(m_arenas.size());
ArenaEntry entry;
entry.simulation = std::make_unique<ArenaSimulation>(
gameConfig, arenaConfig, seed++);
entry.button = new ArenaButton(arenaConfig.name, scrollContent);
contentLayout->addWidget(entry.button);
entry.widget = new ArenaWidget(arenaConfig.name, scrollContent);
contentLayout->addWidget(entry.widget);
entry.button->updateStatus(entry.simulation->status());
entry.widget->updateStatus(entry.simulation->status());
connect(entry.widget, &ArenaWidget::startRequested,
this, [this, index]() { startArena(index); });
m_arenas.push_back(std::move(entry));
}
@@ -40,14 +49,6 @@ BalancingWindow::BalancingWindow(const BalancingConfig& balancingConfig,
scrollArea->setWidget(scrollContent);
mainLayout->addWidget(scrollArea);
// Start worker threads.
for (ArenaEntry& entry : m_arenas)
{
ArenaSimulation* sim = entry.simulation.get();
entry.worker = std::thread([sim]() { sim->run(); });
}
// Poll timer at ~10 Hz to update button statuses.
m_pollTimer = new QTimer(this);
connect(m_pollTimer, &QTimer::timeout, this, &BalancingWindow::pollStatuses);
m_pollTimer->start(100);
@@ -74,7 +75,45 @@ void BalancingWindow::pollStatuses()
{
for (ArenaEntry& entry : m_arenas)
{
const ArenaStatus status = entry.simulation->status();
entry.button->updateStatus(status);
if (entry.worker.joinable())
{
const ArenaStatus status = entry.simulation->status();
entry.widget->updateStatus(status);
}
}
updateStartAllButton();
}
void BalancingWindow::startAll()
{
for (int i = 0; i < static_cast<int>(m_arenas.size()); ++i)
{
startArena(i);
}
}
void BalancingWindow::startArena(int index)
{
ArenaEntry& entry = m_arenas[index];
if (entry.worker.joinable())
{
return;
}
entry.widget->startSimulation();
ArenaSimulation* sim = entry.simulation.get();
entry.worker = std::thread([sim]() { sim->run(); });
updateStartAllButton();
}
void BalancingWindow::updateStartAllButton()
{
for (ArenaEntry& entry : m_arenas)
{
if (!entry.worker.joinable())
{
m_startAllButton->setEnabled(true);
return;
}
}
m_startAllButton->setEnabled(false);
}