Kstars

align.h
1/*
2 SPDX-FileCopyrightText: 2013 Jasem Mutlaq <mutlaqja@ikarustech.com>
3 SPDX-FileCopyrightText: 2013-2021 Jasem Mutlaq <mutlaqja@ikarustech.com>
4 SPDX-FileCopyrightText: 2018-2020 Robert Lancaster <rlancaste@gmail.com>
5 SPDX-FileCopyrightText: 2019-2021 Hy Murveit <hy@murveit.com>
6
7 SPDX-License-Identifier: GPL-2.0-or-later
8*/
9
10#pragma once
11
12#include "ui_align.h"
13#include "ekos/ekos.h"
14#include "indi/indicamera.h"
15#include "indi/indistd.h"
16#include "indi/indimount.h"
17#include "skypoint.h"
18
19#include <QTime>
20#include <QTimer>
21#include <QElapsedTimer>
22#include <KConfigDialog>
23
24#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0)
25#include <QtDBus/qtdbusglobal.h>
26#elif QT_VERSION >= QT_VERSION_CHECK(5, 8, 0)
27#include <qtdbusglobal.h>
28#else
29#include <qdbusmacros.h>
30#endif
31
32#include <stellarsolver.h>
33#include <memory>
34
36
37class AlignView;
38class FITSViewer;
39class FOV;
40class StarObject;
41class ProfileInfo;
42class RotatorSettings;
43
44namespace Ekos
45{
46class AstrometryParser;
47class DarkProcessor;
48class FilterManager;
49class RemoteAstrometryParser;
50class OpsAstrometry;
51class OpsAlign;
52class StellarSolverProfileEditor;
53class OpsPrograms;
54class OpsASTAP;
55class OpsAstrometryIndexFiles;
56class MountModel;
57class PolarAlignmentAssistant;
58class ManualRotator;
59
60/**
61 *@class Align
62 *@short Align class handles plate-solving and polar alignment measurement and correction using astrometry.net
63 * The align class employs StellarSolver library for local solvers and supports remote INDI-based solver.
64 * StellarSolver supports internal and external solvers (Astrometry.net, ASTAP, Online Astrometry).
65 * If an image is solved successfully, the image central J2000 RA & DE coordinates along with pixel scale, rotation, and partiy are
66 * reported back.
67 * Index files management is supported with ability to download astrometry.net files. The user may select and edit different solver
68 * profiles that provide settings to control both extraction and solving profiles in detail. Manual and automatic field rotation
69 * is supported in order to align the solved images to a particular orientation in the sky. The manual rotation assistant is an interactive
70 * tool that helps the user to arrive at the desired framing.
71 * Align module provide Polar Align Helper tool which enables easy-to-follow polar alignment procedure given wide FOVs (> 1.5 degrees)
72 * Legacy polar aligment is deprecated.
73 *@author Jasem Mutlaq
74 *@version 2.0
75 */
76class Align : public QWidget, public Ui::Align
77{
79 Q_CLASSINFO("D-Bus Interface", "org.kde.kstars.Ekos.Align")
80 Q_PROPERTY(Ekos::AlignState status READ status NOTIFY newStatus)
81 Q_PROPERTY(QStringList logText READ logText NOTIFY newLog)
82 Q_PROPERTY(QString opticalTrain READ opticalTrain WRITE setOpticalTrain)
83 Q_PROPERTY(QString camera READ camera)
84 Q_PROPERTY(QString filterWheel READ filterWheel)
85 Q_PROPERTY(QString filter READ filter WRITE setFilter)
86 Q_PROPERTY(double exposure READ exposure WRITE setExposure)
87 Q_PROPERTY(QList<double> fov READ fov)
88 Q_PROPERTY(QList<double> cameraInfo READ cameraInfo)
89 Q_PROPERTY(QList<double> telescopeInfo READ telescopeInfo)
90 //Q_PROPERTY(QString solverArguments READ solverArguments WRITE setSolverArguments)
91
92 public:
93 explicit Align(const QSharedPointer<ProfileInfo> &activeProfile);
94 virtual ~Align() override;
95
96 typedef enum { GOTO_SYNC, GOTO_SLEW, GOTO_NOTHING } GotoMode;
97 typedef enum { SOLVER_LOCAL, SOLVER_REMOTE } SolverMode;
98 typedef enum
99 {
100 ALIGN_RESULT_SUCCESS,
101 ALIGN_RESULT_WARNING,
102 ALIGN_RESULT_FAILED
103 } AlignResult;
104
105 typedef enum
106 {
107 BLIND_IDLE,
108 BLIND_ENGAGNED,
109 BLIND_USED
110 } BlindState;
111
112 /** @defgroup AlignDBusInterface Ekos DBus Interface - Align Module
113 * Ekos::Align interface provides advanced scripting capabilities to solve images using online or offline astrometry.net
114 */
115
116 /*@{*/
117
118 /** DBUS interface function.
119 * Select CCD
120 * @param device CCD device name
121 * @return Returns true if device if found and selected, false otherwise.
122 */
123 Q_SCRIPTABLE QString camera();
124
125 /** DBUS interface function.
126 * select the filter device from the available filter drivers. The filter device can be the same as the CCD driver if the filter functionality was embedded within the driver.
127 * @param device The filter device name
128 * @return Returns true if filter device is found and set, false otherwise.
129 */
130 Q_SCRIPTABLE QString filterWheel();
131
132 /** DBUS interface function.
133 * select the filter from the available filters.
134 * @param filter The filter name
135 * @return Returns true if filter is found and set, false otherwise.
136 */
137 Q_SCRIPTABLE bool setFilter(const QString &filter);
138 Q_SCRIPTABLE QString filter();
139
140 /** DBUS interface function.
141 * Start the plate-solving process given the passed image file.
142 * @param filename Name of image file to solve. FITS and JPG/JPG/TIFF formats are accepted.
143 * @param isGenerated Set to true if filename is generated from a CCD capture operation. If the file is loaded from any storage or network media, pass false.
144 * @return Returns true if device if found and selected, false otherwise.
145 */
146 Q_SCRIPTABLE Q_NOREPLY void startSolving();
147
148 /** DBUS interface function.
149 * Select Solver Action after successfully solving an image.
150 * @param mode 0 for Sync, 1 for Slew To Target, 2 for Nothing (just display solution results)
151 */
152 Q_SCRIPTABLE Q_NOREPLY void setSolverAction(int mode);
153
154 /** DBUS interface function.
155 * Returns the solver's solution results
156 * @return Returns array of doubles. First item is RA in degrees. Second item is DEC in degrees.
157 */
158 Q_SCRIPTABLE QList<double> getSolutionResult();
159
160 /** DBUS interface function.
161 * Returns the solver's current status
162 * @return Returns solver status (Ekos::AlignState)
163 */
165 {
166 return state;
167 }
168
169 /** DBUS interface function.
170 * @return Returns State of load slew procedure. Idle if not started. Busy if in progress. Ok if complete. Alert if procedure failed.
171 */
172 Q_SCRIPTABLE int getLoadAndSlewStatus()
173 {
174 return m_SolveFromFile;
175 }
176
177 /** DBUS interface function.
178 * Sets the exposure of the selected CCD device.
179 * @param value Exposure value in seconds
180 */
181 Q_SCRIPTABLE Q_NOREPLY void setExposure(double value);
182 Q_SCRIPTABLE double exposure()
183 {
184 return alignExposure->value();
185 }
186
187 /** DBUS interface function.
188 * Get currently active camera info in this order:
189 * width, height, pixel_size_x, pixel_size_y
190 */
191 Q_SCRIPTABLE QList<double> cameraInfo();
192
193 /** DBUS interface function.
194 * Get current active telescope info in this order:
195 * focal length, aperture
196 */
198
199 /** @}*/
200
201 /**
202 * @brief Add Camera to the list of available Cameras.
203 * @param device pointer to camera device.
204 * @return True if added successfully, false if duplicate or failed to add.
205 */
206 bool setCamera(ISD::Camera *device);
207
208 /**
209 * @brief addFilterWheel Add new filter wheel filter device.
210 * @param device pointer to filter device.
211 * @return True if added successfully, false if duplicate or failed to add.
212 */
213 bool setFilterWheel(ISD::FilterWheel *device);
214
215 /**
216 * @brief Add new mount
217 * @param device pointer to mount device.
218 * @return True if added successfully, false if duplicate or failed to add.
219 */
220 bool setMount(ISD::Mount *device);
221
222 /**
223 * @brief Add new Dome
224 * @param device pointer to dome device.
225 * @return True if added successfully, false if duplicate or failed to add.
226 */
227 bool setDome(ISD::Dome *device);
228
229 /**
230 * @brief Add new Rotator
231 * @param device pointer to rotator device.
232 */
233 void setRotator(ISD::Rotator *device);
234
235 void removeDevice(const QSharedPointer<ISD::GenericDevice> &device);
236
237 /**
238 * @brief setAstrometryDevice
239 * @param newAstrometry
240 */
242
243 /**
244 * @brief CCD information is updated, sync them.
245 */
246 void syncCameraInfo();
247
248 /**
249 * @brief syncCCDControls Update camera controls like gain, offset, ISO..etc.
250 */
251 void syncCameraControls();
252
253 /**
254 * @brief Generate arguments we pass to the remote solver.
255 */
257
258 /**
259 * @brief Does our parser exist in the system?
260 */
261 bool isParserOK();
262
263 // Log
264 QStringList logText()
265 {
266 return m_LogText;
267 }
268 QString getLogText()
269 {
270 return m_LogText.join("\n");
271 }
272 Q_SCRIPTABLE void clearLog();
273
274 /**
275 * @brief getFOVScale Returns calculated FOV values
276 * @param fov_w FOV width in arcmins
277 * @param fov_h FOV height in arcmins
278 * @param fov_scale FOV scale in arcsec per pixel
279 */
280 void getFOVScale(double &fov_w, double &fov_h, double &fov_scale);
281 QList<double> fov();
282
283 /**
284 * @brief getCalculatedFOVScale Get calculated FOV scales from the current CCD+Telescope combination.
285 * @param fov_w return calculated fov width in arcminutes
286 * @param fov_h return calculated fov height in arcminutes
287 * @param fov_scale return calculated fov pixcale in arcsecs per pixel.
288 * @note This is NOT the same as effective FOV which is the measured FOV from astrometry. It is the
289 * theoretical FOV from calculated values.
290 */
291 void getCalculatedFOVScale(double &fov_w, double &fov_h, double &fov_scale);
292
293 void setupFilterManager();
294 void setupPlot();
295 void setupSolutionTable();
296 void setupOptions();
297
298 /**
299 * @brief Sync the telescope to the solved alignment coordinate.
300 */
301 void Sync();
302
303 /**
304 * @brief Slew the telescope to the solved alignment coordinate.
305 */
306 void Slew();
307
308 /**
309 * @brief Sync the telescope to the solved alignment coordinate, and then slew to the target coordinate.
310 */
311 void SlewToTarget();
312
313 /**
314 * @brief getStellarSolverProfiles
315 * @return list of StellarSolver profile names
316 */
318
319 GotoMode currentGOTOMode() const
320 {
321 return m_CurrentGotoMode;
322 }
323
324 /**
325 * @brief generateOptions Generate astrometry.net option given the supplied map
326 * @param optionsMap List of key=value pairs for all astrometry.net options
327 * @return String List of valid astrometry.net options
328 */
329 static QStringList generateRemoteOptions(const QVariantMap &optionsMap);
330 static void generateFOVBounds(double fov_h, QString &fov_low, QString &fov_high, double tolerance = 0.05);
331
332 // access to the mount model UI, required for testing
333 MountModel * mountModel() const
334 {
335 return m_MountModel;
336 }
337
338 PolarAlignmentAssistant *polarAlignmentAssistant() const
339 {
340 return m_PolarAlignmentAssistant;
341 }
342
343 bool wcsSynced() const
344 {
345 return m_wcsSynced;
346 }
347
348 /**
349 * @brief Process updated device properties
350 * @param prop INDI Property
351 */
352 void updateProperty(INDI::Property prop);
353
354
355 /**
356 * @brief Check CCD and make sure information is updated and FOV is re-calculated.
357 * @param CCDNum By default, we check the already selected CCD in the dropdown menu. If CCDNum is specified, the check is made against this specific CCD in the dropdown menu. CCDNum is the index of the CCD in the dropdown menu.
358 */
359 void checkCamera();
360
361 /**
362 * @brief Check Filter and make sure information is updated accordingly.
363 * @param filterNum By default, we check the already selected filter in the dropdown menu. If filterNum is specified, the check is made against this specific filter in the dropdown menu.
364 * filterNum is the index of the filter in the dropdown menu.
365 */
366 void checkFilter();
367
368 /**
369 * @brief checkCameraExposureProgress Track the progress of CCD exposure
370 * @param targetChip Target chip under exposure
371 * @param remaining how many seconds remaining
372 * @param state status of exposure
373 */
374 void checkCameraExposureProgress(ISD::CameraChip *targetChip, double remaining, IPState state);
375 /**
376 * @brief Process new FITS received from CCD.
377 * @param bp pointer to blob property
378 */
379 void processData(const QSharedPointer<FITSData> &data);
380
381 /** DBUS interface function.
382 * Loads an image (FITS, RAW, or JPG/PNG) and solve its coordinates, then it slews to the solved coordinates and an image is captured and solved to ensure
383 * the telescope is pointing to the same coordinates of the image.
384 * @param image buffer to image data.
385 * @param extension image extension (e.g. cr2, jpg, fits,..etc).
386 */
387 bool loadAndSlew(const QByteArray &image, const QString &extension);
388
389 /** \addtogroup AlignDBusInterface
390 * @{
391 */
392
393 /**
394 * @brief Stop aligning
395 * @param mode stop mode (abort or suspend)
396 */
397 void stop(Ekos::AlignState mode);
398
399 /** DBUS interface function.
400 * Aborts the solving operation, handle outside of the align module.
401 */
402 Q_SCRIPTABLE Q_NOREPLY void abort()
403 {
405 }
406
407 /**
408 * @brief Suspend aligning, recovery handled by the align module itself.
409 */
410 void suspend()
411 {
413 }
414
415 /** DBUS interface function.
416 * Select the solver mode
417 * @param type Set solver type. 0 LOCAL, 1 REMOTE (requires remote astrometry driver to be activated)
418 */
419 Q_SCRIPTABLE Q_NOREPLY void setSolverMode(int mode);
420
421 /** DBUS interface function.
422 * Capture and solve an image using the astrometry.net engine
423 * @return Returns true if the procedure started successful, false otherwise (return true, not false, when retrying!)
424 */
425 Q_SCRIPTABLE bool captureAndSolve(bool initialCall = true);
426
427 /** DBUS interface function.
428 * Loads an image (FITS, RAW, or JPG/PNG) and solve its coordinates, then it slews to the solved coordinates and an image is captured and solved to ensure
429 * the telescope is pointing to the same coordinates of the image.
430 * @param fileURL URL to the image to solve
431 */
432 Q_SCRIPTABLE bool loadAndSlew(QString fileURL = QString());
433
434 /** DBUS interface function.
435 * Sets the target coordinates that the solver compares the solution coordinates to.
436 * By default, the target coordinates are those of the current mount when the capture and
437 * solve operation is started. In case of SYNC, only the error between the solution and target
438 * coordinates is calculated. When Slew to Target is selected, the mount would be slewed afterwards to
439 * this target coordinate.
440 * @param ra0 J2000 Right Ascension in hours.
441 * @param de0 J2000 Declination in degrees.
442 */
443 Q_SCRIPTABLE Q_NOREPLY void setTargetCoords(double ra0, double de0);
444
445 /**
446 * @brief getTargetCoords QList of target coordinates.
447 * @return First value is J2000 RA in hours. Second value is J2000 DE in degrees.
448 */
449 Q_SCRIPTABLE QList<double> getTargetCoords();
450
451
452 /**
453 * @brief Set the alignment target where the mount is expected to point at.
454 * @param targetCoord exact coordinates of the target position.
455 */
456 void setTarget(const SkyPoint &targetCoord);
457
458 /**
459 * @brief Set the coordinates that the mount reports as its position
460 * @param position current mount position
461 */
462 void setTelescopeCoordinates(const SkyPoint &position)
463 {
464 m_TelescopeCoord = position;
465 }
466
467 Q_SCRIPTABLE Q_NOREPLY void setTargetPositionAngle(double value);
468
469 /** DBUS interface function.
470 * Sets the binning of the selected CCD device.
471 * @param binIndex Index of binning value. Default values range from 0 (binning 1x1) to 3 (binning 4x4)
472 */
473 Q_SCRIPTABLE Q_NOREPLY void setBinningIndex(int binIndex);
474
475 /** @}*/
476
477 /**
478 * @brief Solver finished successfully, process the data and execute the required actions depending on the mode.
479 * @param orientation Orientation of image in degrees (East of North)
480 * @param ra Center RA in solved image, degrees.
481 * @param dec Center DEC in solved image, degrees.
482 * @param pixscale Image scale is arcsec/pixel
483 * @param eastToTheRight When the image is rotated, so that North is up, East would be to the right.
484 */
485 void solverFinished(double orientation, double ra, double dec, double pixscale, bool eastToTheRight);
486
487 void solverComplete();
488
489 /**
490 * @brief Process solver failure.
491 */
492 void solverFailed();
493
494 /**
495 * @brief We received new telescope info, process them and update FOV.
496 */
497 bool syncTelescopeInfo();
498
499 void setFocusStatus(Ekos::FocusState state);
500
501 // Log
502 void appendLogText(const QString &);
503
504 // Capture
505 void setCaptureComplete();
506
507 // Update Capture Module status
508 void setCaptureStatus(Ekos::CaptureState newState);
509 // Update Mount module status
510 void setMountStatus(ISD::Mount::Status newState);
511
512 void zoomAlignView();
513 void setAlignZoom(double scale);
514
515 // Manual Rotator Dialog
516 void toggleManualRotator(bool toggled);
517
518 /**
519 * @brief checkIfRotationRequired Check whether we need to perform an ALIGN_ROTATING action, whether manual or automatic.
520 * @return True if rotation is required as per the settings, false is not required.
521 */
523
524 // Settings
525 QVariantMap getAllSettings() const;
526 void setAllSettings(const QVariantMap &settings);
527
528 /**
529 * @brief settleSettings Run this function after timeout from debounce timer to update database
530 * and emit settingsChanged signal. This is required so we don't overload output.
531 */
532 void settleSettings();
533
534 // Trains
535 QString opticalTrain() const
536 {
537 return opticalTrainCombo->currentText();
538 }
539 void setOpticalTrain(const QString &value)
540 {
541 opticalTrainCombo->setCurrentText(value);
542 }
543
544 Ekos::OpsAlign *getAlignOptionsModule()
545 {
546 return opsAlign;
547 }
548
549 private slots:
550 // Solver timeout
551 void checkAlignmentTimeout();
552 void setAlignTableResult(AlignResult result);
553
554 // External View
555 void showFITSViewer();
556 void toggleAlignWidgetFullScreen();
557
558 /**
559 * @brief prepareCapture Set common settings for capture for align module
560 * @param targetChip target Chip
561 */
562 void prepareCapture(ISD::CameraChip *targetChip);
563
564 //Solutions Display slots
565 void buildTarget();
566 void handlePointTooltip(QMouseEvent *event);
567 void handleVerticalPlotSizeChange();
568 void handleHorizontalPlotSizeChange();
569 void selectSolutionTableRow(int row, int column);
570 void slotClearAllSolutionPoints();
571 void slotRemoveSolutionPoint();
572 void slotAutoScaleGraph();
573
574 // Model
575 void slotMountModel();
576
577 // Capture Timeout
578 void processCaptureTimeout();
579
580 protected slots:
581 /**
582 * @brief After a solver process is completed successfully, sync, slew to target, or do nothing as set by the user.
583 */
584 void executeGOTO();
585
586 /**
587 * @brief refreshAlignOptions is called when settings are updated in OpsAlign.
588 */
589 void refreshAlignOptions();
590
591 void processPAHStage(int stage);
592
593 signals:
594 void newLog(const QString &text);
595 void newStatus(Ekos::AlignState state);
596 void newPAAStage(int stage);
597 void newSolution(const QVariantMap &solution);
598
599 // This is sent when we load an image in the view
600 void newImage(const QSharedPointer<FITSView> &view);
601 // This is sent when the pixmap is updated within the view
602 void newFrame(const QSharedPointer<FITSView> &view);
603 // Send new solver results
604 void newSolverResults(double orientation, double ra, double dec, double pixscale);
605
606 // Train changed
607 void trainChanged();
608
609 // Settings
610 void settingsUpdated(const QVariantMap &settings);
611
612 // Manual Rotator
613 void manualRotatorChanged(double currentPA, double targetPA, double pixscale);
614
615 private:
616
617 void setupOpticalTrainManager();
618 void refreshOpticalTrain();
619
620 ////////////////////////////////////////////////////////////////////
621 /// Settings
622 ////////////////////////////////////////////////////////////////////
623
624 /**
625 * @brief Connect GUI elements to sync settings once updated.
626 */
627 void connectSettings();
628 /**
629 * @brief Stop updating settings when GUI elements are updated.
630 */
631 void disconnectSettings();
632 /**
633 * @brief loadSettings Load setting from Options and set them accordingly.
634 */
635 void loadGlobalSettings();
636
637 /**
638 * @brief syncSettings When checkboxes, comboboxes, or spin boxes are updated, save their values in the
639 * global and per-train settings.
640 */
641 void syncSettings();
642
643 /**
644 * @brief syncControl Sync setting to widget. The value depends on the widget type.
645 * @param settings Map of all settings
646 * @param key name of widget to sync
647 * @param widget pointer of widget to set
648 * @return True if sync successful, false otherwise
649 */
650 bool syncControl(const QVariantMap &settings, const QString &key, QWidget * widget);
651
652 void setState (AlignState value);
653 /**
654 * @brief Retrieve the align status indicator
655 */
656 QProgressIndicator *getProgressStatus();
657
658 /**
659 * @brief Stop the progress animation in the solution table
660 */
661 void stopProgressAnimation();
662
663 void exportSolutionPoints();
664
665 /**
666 * @brief Calculate Field of View of CCD+Telescope combination that we need to pass to astrometry.net solver.
667 */
668 void calculateFOV();
669
670 /**
671 * @brief calculateEffectiveFocalLength Calculate Focal Length purely form astrometric data.
672 */
673 void calculateEffectiveFocalLength(double newFOVW);
674
675 /**
676 * @brief calculateAlignTargetDiff Find the difference between aligned vs. target coordinates and update
677 * the GUI accordingly.
678 */
679 void calculateAlignTargetDiff();
680
681 /**
682 * @brief Get formatted RA & DEC coordinates compatible with astrometry.net format.
683 * @param ra Right ascension
684 * @param dec Declination
685 * @param ra_str will contain the formatted RA string
686 * @param dec_str will contain the formatted DEC string
687 */
688 void getFormattedCoords(double ra, double dec, QString &ra_str, QString &dec_str);
689
690 uint8_t getSolverDownsample(uint16_t binnedW);
691
692 /**
693 * @brief setWCSEnabled enables/disables World Coordinate System settings in the CCD driver.
694 * @param enable true to enable WCS, false to disable.
695 */
696 void setWCSEnabled(bool enable);
697
698 void resizeEvent(QResizeEvent *event) override;
699
700 KPageWidgetItem *m_IndexFilesPage;
701 QString savedOptionsProfiles;
702
703 /**
704 * @brief React when a mount motion has been detected
705 */
706 void handleMountMotion();
707
708 /**
709 * @brief Continue aligning according to the current mount status
710 */
711 void handleMountStatus();
712
713 /**
714 * @brief initPolarAlignmentAssistant Initialize Polar Alignment Asssistant Tool
715 */
716 void setupPolarAlignmentAssistant();
717
718 void setupRotatorControl();
719
720 /**
721 * @brief initManualRotator Initialize Manual Rotator Tool
722 */
723 void setupManualRotator();
724
725 /**
726 * @brief initDarkProcessor Initialize Dark Processor
727 */
728 void setuptDarkProcessor();
729
730 bool matchPAHStage(uint32_t stage);
731
732
733 // Effective FOV
734
735 /**
736 * @brief getEffectiveFOV Search database for effective FOV that matches the current profile and settings
737 * @return Variant Map containing effect FOV data or empty variant map if none found
738 */
739 QVariantMap getEffectiveFOV();
740 void saveNewEffectiveFOV(double newFOVW, double newFOVH);
741 QList<QVariantMap> effectiveFOVs;
742 void syncFOV();
743
744 // We are using calculated FOV now until a more accurate effective FOV is found.
745 bool m_EffectiveFOVPending { false };
746 /// Which chip should we invoke in the current CCD?
747 bool useGuideHead { false };
748 /// Can the mount sync its coordinates to those set by Ekos?
749 bool canSync { false };
750 // m_SolveFromFile is true we load an image and solve it, no capture is done.
751 bool m_SolveFromFile { false };
752 // Target Position Angle of solver Load&Slew image to be used for rotator if necessary
753 double m_TargetPositionAngle { std::numeric_limits<double>::quiet_NaN() };
754 // Target Pierside of solver Load&Slew image to be used
755 ISD::Mount::PierSide m_TargetPierside = ISD::Mount::PIER_UNKNOWN;
756 double currentRotatorPA { -1 };
757 /// Solver iterations count
758 uint8_t solverIterations { 0 };
759 /// Was solving with scale off used?
760 BlindState useBlindScale {BLIND_IDLE};
761 /// Was solving with position off used?
762 BlindState useBlindPosition {BLIND_IDLE};
763
764 // FOV
765 double m_CameraPixelWidth { -1 };
766 double m_CameraPixelHeight { -1 };
767 uint16_t m_CameraWidth { 0 };
768 uint16_t m_CameraHeight { 0 };
769
770 double m_FocalLength {-1};
771 double m_Aperture {-1};
772 double m_FocalRatio {-1};
773 double m_Reducer = {-1};
774
775 double m_FOVWidth { 0 };
776 double m_FOVHeight { 0 };
777 double m_FOVPixelScale { 0 };
778
779 // Keep raw rotator angle
780 double sRawAngle { INVALID_VALUE };
781 // Keep track of solver results
782 double sOrientation { INVALID_VALUE };
783 double sRA { INVALID_VALUE };
784 double sDEC { INVALID_VALUE };
785
786 /// Solver alignment coordinates
787 SkyPoint m_AlignCoord;
788 /// Target coordinates the mount will slew to
789 SkyPoint m_TargetCoord;
790 /// Final coordinates we want to reach in case of differential align
791 SkyPoint m_DestinationCoord;
792 /// Current telescope coordinates
793 SkyPoint m_TelescopeCoord;
794 /// Difference between solution and target coordinate
795 double m_TargetDiffTotal { 1e6 };
796 double m_TargetDiffRA { 1e6 };
797 double m_TargetDiffDE { 1e6 };
798
799 /// Progress icon if the solver is running
800 std::unique_ptr<QProgressIndicator> pi;
801
802 /// Keep track of how long the solver is running
803 QElapsedTimer solverTimer;
804
805 // The StellarSolver
806 std::unique_ptr<StellarSolver> m_StellarSolver;
807 // StellarSolver Profiles
808 QList<SSolver::Parameters> m_StellarSolverProfiles;
809
810 /// Have we slewed?
811 bool m_wasSlewStarted { false };
812 // Above flag only stays false for 10s after slew start.
813 QElapsedTimer slewStartTimer;
814 bool didSlewStart();
815 // Only wait this many milliseconds for slew to start.
816 // Otherwise assume it has begun.
817 static constexpr int MAX_WAIT_FOR_SLEW_START_MSEC = 10000;
818
819 // Online and Offline parsers
820 AstrometryParser* parser { nullptr };
821 std::unique_ptr<RemoteAstrometryParser> remoteParser;
822 QSharedPointer<ISD::GenericDevice> m_RemoteParserDevice;
823
824 // Pointers to our devices
825 ISD::Mount *m_Mount { nullptr };
826 ISD::Dome *m_Dome { nullptr };
827 ISD::Camera *m_Camera { nullptr };
828 ISD::Rotator *m_Rotator { nullptr };
829 ISD::FilterWheel *m_FilterWheel { nullptr };
830
831 int currentFilterPosition { -1 };
832 /// True if we need to change filter position and wait for result before continuing capture
833 bool filterPositionPending { false };
834
835 /// Keep track of solver FOV to be plotted in the skymap after each successful solve operation
836 std::shared_ptr<FOV> solverFOV;
837 std::shared_ptr<FOV> sensorFOV;
838
839 /// WCS
840 bool m_wcsSynced { false };
841
842 /// Log
843 QStringList m_LogText;
844
845 /// Issue counters
846 uint8_t m_CaptureTimeoutCounter { 0 };
847 uint8_t m_CaptureErrorCounter { 0 };
848 uint8_t m_SlewErrorCounter { 0 };
849 bool m_resetCaptureTimeoutCounter = false;
850
851 QTimer m_CaptureTimer;
852
853 // State
854 AlignState state { ALIGN_IDLE };
855 FocusState m_FocusState { FOCUS_IDLE };
856 CaptureState m_CaptureState { CAPTURE_IDLE };
857
858 // Track which upload mode the CCD is set to. If set to UPLOAD_LOCAL, then we need to switch it to UPLOAD_CLIENT in order to do focusing, and then switch it back to UPLOAD_LOCAL
859 ISD::Camera::UploadMode rememberUploadMode { ISD::Camera::UPLOAD_CLIENT };
860
861 GotoMode m_CurrentGotoMode;
862
863 QString dirPath;
864
865 // Timer
866 QTimer m_AlignTimer;
867 QTimer m_DebounceTimer;
868
869 // Align Frame
870 QSharedPointer<AlignView> m_AlignView;
871
872 // FITS Viewer in case user want to display in it instead of internal view
874
875 QUrl alignURL;
876 QUrl alignURLPath;
877
878 // keep track of autoWSC
879 bool rememberAutoWCS { false };
880 bool rememberSolverWCS { false };
881
882 // move rotator
883 bool RotatorGOTO { false };
884
885 // Align slew
886 bool targetAccuracyNotMet { false };
887
888 // Astrometry Options
889 OpsAstrometry *opsAstrometry { nullptr };
890 OpsAlign *opsAlign { nullptr };
891 OpsPrograms *opsPrograms { nullptr };
892 OpsAstrometryIndexFiles *opsAstrometryIndexFiles { nullptr };
893 OpsASTAP *opsASTAP { nullptr };
894 StellarSolverProfileEditor *optionsProfileEditor { nullptr };
895
896 // Drawing
897 QCPCurve *centralTarget { nullptr };
898 QCPCurve *yellowTarget { nullptr };
899 QCPCurve *redTarget { nullptr };
900 QCPCurve *concentricRings { nullptr };
901
902 // Telescope Settings
903 double m_EffectiveFocalLength = -1;
904 bool m_isRateSynced = false;
905 bool domeReady = true;
906
907 // CCD Exposure Looping
908 bool m_RememberCameraFastExposure = { false };
909
910 // Controls
911 double alignGainSpecialValue {INVALID_VALUE};
912 double TargetCustomGainValue {-1};
913
914 // Data
915 QSharedPointer<FITSData> m_ImageData;
916
917 // Active Profile
918 QSharedPointer<ProfileInfo> m_ActiveProfile;
919
920 // Threshold to notify settle time is 3 seconds
921 static constexpr uint16_t DELAY_THRESHOLD_NOTIFY { 3000 };
922
923 // Mount Model
924 // N.B. We do not need to use "smart pointer" here as the object memroy
925 // is taken care of by the Qt framework.
926 MountModel *m_MountModel {nullptr};
927 PolarAlignmentAssistant *m_PolarAlignmentAssistant {nullptr};
928 ManualRotator *m_ManualRotator {nullptr};
929
930 // Dark Processor
931 QPointer<DarkProcessor> m_DarkProcessor;
932
933 // Filter Manager
934 QSharedPointer<FilterManager> m_FilterManager;
935
936 // Rotator Control
937 QSharedPointer<RotatorSettings> m_RotatorControlPanel;
938 int m_RotatorTimeFrame = 0;
939 bool m_estimateRotatorTimeFrame = false;
940
941 // Settings
942 QVariantMap m_Settings;
943 QVariantMap m_GlobalSettings;
944
945 bool m_UsedScale = false;
946 bool m_UsedPosition = false;
947 double m_ScaleUsed = 0;
948 double m_RAUsed = 0;
949 double m_DECUsed = 0;
950};
951}
Align class handles plate-solving and polar alignment measurement and correction using astrometry....
Definition align.h:77
void Slew()
Slew the telescope to the solved alignment coordinate.
Definition align.cpp:2964
static QStringList generateRemoteOptions(const QVariantMap &optionsMap)
generateOptions Generate astrometry.net option given the supplied map
Definition align.cpp:1193
void checkCameraExposureProgress(ISD::CameraChip *targetChip, double remaining, IPState state)
checkCameraExposureProgress Track the progress of CCD exposure
Definition align.cpp:3297
QStringList generateRemoteArgs(const QSharedPointer< FITSData > &imageData)
Generate arguments we pass to the remote solver.
Definition align.cpp:1283
Q_SCRIPTABLE bool setFilter(const QString &filter)
DBUS interface function.
Definition align.cpp:3182
void syncCameraInfo()
CCD information is updated, sync them.
Definition align.cpp:861
bool setCamera(ISD::Camera *device)
Add Camera to the list of available Cameras.
Definition align.cpp:642
Q_SCRIPTABLE QList< double > cameraInfo()
DBUS interface function.
bool setDome(ISD::Dome *device)
Add new Dome.
Definition align.cpp:749
bool setMount(ISD::Mount *device)
Add new mount.
Definition align.cpp:692
Q_SCRIPTABLE int getLoadAndSlewStatus()
DBUS interface function.
Definition align.h:172
void syncCameraControls()
syncCCDControls Update camera controls like gain, offset, ISO..etc.
Definition align.cpp:912
void checkCamera()
Check CCD and make sure information is updated and FOV is re-calculated.
Definition align.cpp:604
Q_SCRIPTABLE Ekos::AlignState status()
DBUS interface function.
Definition align.h:164
bool isParserOK()
Does our parser exist in the system?
Definition align.cpp:530
Q_SCRIPTABLE QList< double > getSolutionResult()
DBUS interface function.
Definition align.cpp:2612
Q_SCRIPTABLE QList< double > telescopeInfo()
DBUS interface function.
QStringList getStellarSolverProfiles()
getStellarSolverProfiles
Definition align.cpp:3934
Q_SCRIPTABLE Q_NOREPLY void startSolving()
DBUS interface function.
Definition align.cpp:1823
void refreshAlignOptions()
refreshAlignOptions is called when settings are updated in OpsAlign.
Definition align.cpp:3494
void getFOVScale(double &fov_w, double &fov_h, double &fov_scale)
getFOVScale Returns calculated FOV values
Definition align.cpp:971
void executeGOTO()
After a solver process is completed successfully, sync, slew to target, or do nothing as set by the u...
Definition align.cpp:2924
bool loadAndSlew(const QByteArray &image, const QString &extension)
DBUS interface function.
Definition align.cpp:3095
void setAstrometryDevice(const QSharedPointer< ISD::GenericDevice > &device)
setAstrometryDevice
Definition align.cpp:3481
void solverFinished(double orientation, double ra, double dec, double pixscale, bool eastToTheRight)
Solver finished successfully, process the data and execute the required actions depending on the mode...
Definition align.cpp:2086
bool checkIfRotationRequired()
checkIfRotationRequired Check whether we need to perform an ALIGN_ROTATING action,...
Definition align.cpp:2447
Q_SCRIPTABLE QString camera()
DBUS interface function.
bool setFilterWheel(ISD::FilterWheel *device)
addFilterWheel Add new filter wheel filter device.
Definition align.cpp:3139
void Sync()
Sync the telescope to the solved alignment coordinate.
Definition align.cpp:2946
void checkFilter()
Check Filter and make sure information is updated accordingly.
Definition align.cpp:3199
void setRotator(ISD::Rotator *device)
Add new Rotator.
Definition align.cpp:3233
Q_SCRIPTABLE QString filterWheel()
DBUS interface function.
void processData(const QSharedPointer< FITSData > &data)
Process new FITS received from CCD.
Definition align.cpp:1702
void getCalculatedFOVScale(double &fov_w, double &fov_h, double &fov_scale)
getCalculatedFOVScale Get calculated FOV scales from the current CCD+Telescope combination.
Definition align.cpp:1005
Q_SCRIPTABLE Q_NOREPLY void setExposure(double value)
DBUS interface function.
Definition align.cpp:3119
void settleSettings()
settleSettings Run this function after timeout from debounce timer to update database and emit settin...
Definition align.cpp:4280
Q_SCRIPTABLE Q_NOREPLY void setSolverAction(int mode)
DBUS interface function.
Definition align.cpp:1817
bool syncTelescopeInfo()
We received new telescope info, process them and update FOV.
Definition align.cpp:818
void updateProperty(INDI::Property prop)
Process updated device properties.
Definition align.cpp:2637
void solverFailed()
Process solver failure.
Definition align.cpp:2366
void SlewToTarget()
Sync the telescope to the solved alignment coordinate, and then slew to the target coordinate.
Definition align.cpp:2993
Primary window to view monochrome and color FITS images.
Definition fitsviewer.h:54
A simple class encapsulating a Field-of-View symbol.
Definition fov.h:28
CameraChip class controls a particular chip in camera.
Camera class controls an INDI Camera device.
Definition indicamera.h:45
Class handles control of INDI dome devices.
Definition indidome.h:25
device handle controlling Mounts.
Definition indimount.h:29
Rotator class handles control of INDI Rotator devices.
Definition indirotator.h:20
A plottable representing a parametric curve in a plot.
The QProgressIndicator class lets an application display a progress indicator to show that a long tas...
The sky coordinates of a point in the sky.
Definition skypoint.h:45
This is a subclass of SkyObject.
Definition starobject.h:33
void setTarget(const SkyPoint &targetCoord)
Set the alignment target where the mount is expected to point at.
Definition align.cpp:3827
Q_SCRIPTABLE Q_NOREPLY void setSolverMode(int mode)
DBUS interface function.
Definition align.cpp:561
void stop(Ekos::AlignState mode)
Stop aligning.
Definition align.cpp:2526
void setTelescopeCoordinates(const SkyPoint &position)
Set the coordinates that the mount reports as its position.
Definition align.h:462
Q_SCRIPTABLE Q_NOREPLY void setTargetCoords(double ra0, double de0)
DBUS interface function.
Definition align.cpp:3818
Q_SCRIPTABLE Q_NOREPLY void setBinningIndex(int binIndex)
DBUS interface function.
Definition align.cpp:3124
Q_SCRIPTABLE bool captureAndSolve(bool initialCall=true)
DBUS interface function.
Definition align.cpp:1416
void suspend()
Suspend aligning, recovery handled by the align module itself.
Definition align.h:410
Q_SCRIPTABLE QList< double > getTargetCoords()
getTargetCoords QList of target coordinates.
Definition align.cpp:3834
Q_SCRIPTABLE Q_NOREPLY void abort()
DBUS interface function.
Definition align.h:402
Ekos is an advanced Astrophotography tool for Linux.
Definition align.cpp:83
AlignState
Definition ekos.h:145
@ ALIGN_ABORTED
Alignment aborted by user or agent.
Definition ekos.h:149
@ ALIGN_IDLE
No ongoing operations.
Definition ekos.h:146
@ ALIGN_SUSPENDED
Alignment operations suspended.
Definition ekos.h:155
CaptureState
Capture states.
Definition ekos.h:92
@ CAPTURE_IDLE
Definition ekos.h:93
Q_CLASSINFO(Name, Value)
Q_OBJECTQ_OBJECT
Q_PROPERTY(...)
QString join(QChar separator) const const
virtual bool event(QEvent *event) override
This file is part of the KDE documentation.
Documentation copyright © 1996-2024 The KDE developers.
Generated on Fri Oct 11 2024 12:15:11 by doxygen 1.12.0 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.