diff --git a/kstars/ekos/capture/capture.h b/kstars/ekos/capture/capture.h --- a/kstars/ekos/capture/capture.h +++ b/kstars/ekos/capture/capture.h @@ -540,6 +540,7 @@ // Jobs void resetJobs(); + void selectJob(QModelIndex i); void editJob(QModelIndex i); void resetJobEdit(); void executeJob(); @@ -646,6 +647,9 @@ // If exposure timed out, let's handle it. void processCaptureTimeout(); + // selection of a job + void selectedJobCanged(QModelIndex current, QModelIndex previous); + /* Capture */ /** diff --git a/kstars/ekos/capture/capture.cpp b/kstars/ekos/capture/capture.cpp --- a/kstars/ekos/capture/capture.cpp +++ b/kstars/ekos/capture/capture.cpp @@ -138,6 +138,7 @@ connect(queueSaveAsB, &QPushButton::clicked, this, &Ekos::Capture::saveSequenceQueueAs); connect(queueLoadB, &QPushButton::clicked, this, static_cast(&Ekos::Capture::loadSequenceQueue)); connect(resetB, &QPushButton::clicked, this, &Ekos::Capture::resetJobs); + connect(queueTable->selectionModel(), &QItemSelectionModel::currentRowChanged, this, &Ekos::Capture::selectedJobCanged); connect(queueTable, &QAbstractItemView::doubleClicked, this, &Ekos::Capture::editJob); connect(queueTable, &QTableWidget::itemSelectionChanged, this, &Ekos::Capture::resetJobEdit); connect(setTemperatureB, &QPushButton::clicked, [&]() @@ -3978,15 +3979,29 @@ emit settingsUpdated(settings); } -void Capture::editJob(QModelIndex i) +void Capture::selectedJobCanged(QModelIndex current, QModelIndex previous) +{ + Q_UNUSED(previous); + selectJob(current); +} + +void Capture::selectJob(QModelIndex i) { + if (i.row() < 0 || (i.row()+1) > jobs.size()) + return; + SequenceJob * job = jobs.at(i.row()); if (job == nullptr) return; syncGUIToJob(job); +} + +void Capture::editJob(QModelIndex i) +{ + selectJob(i); appendLogText(i18n("Editing job #%1...", i.row() + 1)); addToQueueB->setIcon(QIcon::fromTheme("dialog-ok-apply")); @@ -4199,10 +4214,10 @@ activeJob = nullptr; //m_TargetName.clear(); //stop(); - qDeleteAll(jobs); - jobs.clear(); while (queueTable->rowCount() > 0) queueTable->removeRow(0); + qDeleteAll(jobs); + jobs.clear(); } QString Capture::getSequenceQueueStatus() diff --git a/kstars/ekos/ekos.h b/kstars/ekos/ekos.h --- a/kstars/ekos/ekos.h +++ b/kstars/ekos/ekos.h @@ -158,7 +158,7 @@ typedef enum { SCHEDULER_IDLE, /*< Scheduler is stopped. */ SCHEDULER_STARTUP, /*< Scheduler is starting the observatory up. */ - SCHEDULER_RUNNIG, /*< Scheduler is running. */ + SCHEDULER_RUNNING, /*< Scheduler is running. */ SCHEDULER_PAUSED, /*< Scheduler is paused by the end-user. */ SCHEDULER_SHUTDOWN, /*< Scheduler is shutting the observatory down. */ SCHEDULER_ABORTED, /*< Scheduler is stopped in error. */ diff --git a/kstars/ekos/scheduler/scheduler.h b/kstars/ekos/scheduler/scheduler.h --- a/kstars/ekos/scheduler/scheduler.h +++ b/kstars/ekos/scheduler/scheduler.h @@ -324,11 +324,23 @@ void setJobManipulation(bool can_reorder, bool can_delete); /** + * @brief set all GUI fields to the values of the given scheduler job + */ + void syncGUIToJob(SchedulerJob *job); + + /** * @brief jobSelectionChanged Update UI state when the job list is clicked once. */ void clickQueueTable(QModelIndex index); /** + * @brief Update scheduler parameters to the currently selected scheduler job + * @param current table position + * @param previous table position + */ + void queueTableSelectionChanged(QModelIndex current, QModelIndex previous); + + /** * @brief reorderJobs Change the order of jobs in the UI based on a subset of its jobs. */ bool reorderJobs(QList reordered_sublist); @@ -783,6 +795,5 @@ static const uint32_t FOCUS_INACTIVITY_TIMEOUT = 120000; static const uint32_t CAPTURE_INACTIVITY_TIMEOUT = 120000; static const uint16_t GUIDE_INACTIVITY_TIMEOUT = 60000; - }; } diff --git a/kstars/ekos/scheduler/scheduler.cpp b/kstars/ekos/scheduler/scheduler.cpp --- a/kstars/ekos/scheduler/scheduler.cpp +++ b/kstars/ekos/scheduler/scheduler.cpp @@ -172,6 +172,7 @@ connect(queueDownB, &QPushButton::clicked, this, &Scheduler::moveJobDown); connect(evaluateOnlyB, &QPushButton::clicked, this, &Scheduler::startJobEvaluation); connect(sortJobsB, &QPushButton::clicked, this, &Scheduler::sortJobsPerAltitude); + connect(queueTable->selectionModel(), &QItemSelectionModel::currentRowChanged, this, &Scheduler::queueTableSelectionChanged); connect(queueTable, &QAbstractItemView::clicked, this, &Scheduler::clickQueueTable); connect(queueTable, &QAbstractItemView::doubleClicked, this, &Scheduler::loadJob); @@ -457,7 +458,7 @@ void Scheduler::saveJob() { - if (state == SCHEDULER_RUNNIG) + if (state == SCHEDULER_RUNNING) { appendLogText(i18n("Warning: You cannot add or modify a job while the scheduler is running.")); return; @@ -729,47 +730,21 @@ } } -void Scheduler::loadJob(QModelIndex i) +void Scheduler::syncGUIToJob(SchedulerJob *job) { - if (jobUnderEdit == i.row()) - return; - - if (state == SCHEDULER_RUNNIG) - { - appendLogText(i18n("Warning: you cannot add or modify a job while the scheduler is running.")); - return; - } - - SchedulerJob * const job = jobs.at(i.row()); - - if (job == nullptr) - return; - - watchJobChanges(false); - - //job->setState(SchedulerJob::JOB_IDLE); - //job->setStage(SchedulerJob::STAGE_IDLE); - nameEdit->setText(job->getName()); prioritySpin->setValue(job->getPriority()); raBox->showInHours(job->getTargetCoords().ra0()); decBox->showInDegrees(job->getTargetCoords().dec0()); if (job->getFITSFile().isEmpty() == false) - { fitsEdit->setText(job->getFITSFile().toLocalFile()); - fitsURL = job->getFITSFile(); - } else - { fitsEdit->clear(); - fitsURL = QUrl(); - } sequenceEdit->setText(job->getSequenceFile().toLocalFile()); - sequenceURL = job->getSequenceFile(); trackStepCheck->setChecked(job->getStepPipeline() & SchedulerJob::USE_TRACK); focusStepCheck->setChecked(job->getStepPipeline() & SchedulerJob::USE_FOCUS); @@ -844,6 +819,37 @@ break; } +} + +void Scheduler::loadJob(QModelIndex i) +{ + if (jobUnderEdit == i.row()) + return; + + if (state == SCHEDULER_RUNNING) + { + appendLogText(i18n("Warning: you cannot add or modify a job while the scheduler is running.")); + return; + } + + SchedulerJob * const job = jobs.at(i.row()); + + if (job == nullptr) + return; + + watchJobChanges(false); + + //job->setState(SchedulerJob::JOB_IDLE); + //job->setStage(SchedulerJob::STAGE_IDLE); + syncGUIToJob(job); + + if (job->getFITSFile().isEmpty() == false) + fitsURL = job->getFITSFile(); + else + fitsURL = QUrl(); + + sequenceURL = job->getSequenceFile(); + /* Turn the add button into an apply button */ setJobAddApply(false); @@ -860,6 +866,22 @@ watchJobChanges(true); } +void Scheduler::queueTableSelectionChanged(QModelIndex current, QModelIndex previous) +{ + Q_UNUSED(previous); + + if (current.row() < 0 || (current.row()+1) > jobs.size()) + return; + + SchedulerJob * const job = jobs.at(current.row()); + + if (job == nullptr) + return; + + resetJobEdit(); + syncGUIToJob(job); +} + void Scheduler::clickQueueTable(QModelIndex index) { setJobManipulation(!Options::sortSchedulerJobs() && index.isValid(), index.isValid()); @@ -1088,7 +1110,7 @@ void Scheduler::toggleScheduler() { - if (state == SCHEDULER_RUNNIG) + if (state == SCHEDULER_RUNNING) { preemptiveShutdown = false; stop(); @@ -1099,7 +1121,7 @@ void Scheduler::stop() { - if (state != SCHEDULER_RUNNIG) + if (state != SCHEDULER_RUNNING) return; qCInfo(KSTARS_EKOS_SCHEDULER) << "Scheduler is stopping..."; @@ -1254,7 +1276,7 @@ /* Reset and re-evaluate all scheduler jobs, then start the Scheduler */ startJobEvaluation(); - state = SCHEDULER_RUNNIG; + state = SCHEDULER_RUNNING; emit newStatus(state); schedulerTimer.start(); @@ -1269,7 +1291,7 @@ /* Edit-related buttons are still disabled */ /* The end-user cannot update the schedule, don't re-evaluate jobs. Timer schedulerTimer is already running. */ - state = SCHEDULER_RUNNIG; + state = SCHEDULER_RUNNING; emit newStatus(state); qCDebug(KSTARS_EKOS_SCHEDULER) << "Scheduler paused."; @@ -1917,7 +1939,7 @@ /* Apply sorting to queue table, and mark it for saving if it changes */ mDirty = reorderJobs(sortedJobs); - if (jobEvaluationOnly || state != SCHEDULER_RUNNIG) + if (jobEvaluationOnly || state != SCHEDULER_RUNNING) { qCInfo(KSTARS_EKOS_SCHEDULER) << "Ekos finished evaluating jobs, no job selection required."; jobEvaluationOnly = false; @@ -1967,7 +1989,7 @@ } else { - if (state == SCHEDULER_RUNNIG) + if (state == SCHEDULER_RUNNING) appendLogText(i18n("Scheduler is awake. Jobs shall be started when ready...")); else appendLogText(i18n("Scheduler is awake. Jobs shall be started when scheduler is resumed.")); @@ -2931,7 +2953,7 @@ setCurrentJob(nullptr); - if (state == SCHEDULER_RUNNIG) + if (state == SCHEDULER_RUNNING) schedulerTimer.start(); if (preemptiveShutdown == false) @@ -3901,7 +3923,7 @@ bool Scheduler::manageConnectionLoss() { - if (SCHEDULER_RUNNIG != state) + if (SCHEDULER_RUNNING != state) return false; // Don't manage loss if Ekos is actually down in the state machine @@ -3995,11 +4017,12 @@ if (jobUnderEdit >= 0) resetJobEdit(); - qDeleteAll(jobs); - jobs.clear(); while (queueTable->rowCount() > 0) queueTable->removeRow(0); + qDeleteAll(jobs); + jobs.clear(); + LilXML *xmlParser = newLilXML(); char errmsg[MAXRBUF]; XMLEle *root = nullptr; @@ -4900,7 +4923,7 @@ if (sender() == startupProcedureButtonGroup || sender() == shutdownProcedureGroup) return; - if (0 <= jobUnderEdit && state != SCHEDULER_RUNNIG && 0 <= queueTable->currentRow()) + if (0 <= jobUnderEdit && state != SCHEDULER_RUNNING && 0 <= queueTable->currentRow()) { // Now that jobs are sorted, reset jobs that are later than the edited one for re-evaluation for (int row = jobUnderEdit; row < jobs.size(); row++) @@ -6161,7 +6184,7 @@ void Scheduler::resetAllJobs() { - if (state == SCHEDULER_RUNNIG) + if (state == SCHEDULER_RUNNING) return; // Reset capture count of all jobs before re-evaluating