13 #include <KMessageBox>
14 #include <KPlotWidget>
15 #include <KPlotObject>
25 #include <basedevice.h>
27 #define MAXIMUM_ABS_ITERATIONS 30
36 currentFocuser = NULL;
48 connect(startFocusB, SIGNAL(clicked()),
this, SLOT(
startFocus()));
49 connect(stopFocusB, SIGNAL(clicked()),
this, SLOT(
stopFocus()));
51 connect(focusOutB, SIGNAL(clicked()),
this, SLOT(
FocusOut()));
52 connect(focusInB, SIGNAL(clicked()),
this, SLOT(
FocusIn()));
54 connect(captureB, SIGNAL(clicked()),
this, SLOT(
capture()));
56 connect(AutoModeR, SIGNAL(toggled(
bool)),
this, SLOT(
toggleAutofocus(
bool)));
58 connect(startLoopB, SIGNAL(clicked()),
this, SLOT(
startLooping()));
60 connect(CCDCaptureCombo, SIGNAL(activated(
int)),
this, SLOT(
checkCCD(
int)));
66 HFRPlot->axis( KPlotWidget::LeftAxis )->setLabel(
i18nc(
"Half Flux Radius",
"HFR") );
67 HFRPlot->axis( KPlotWidget::BottomAxis )->setLabel( i18n(
"Absolute Position") );
74 filterCombo->addItem(filter);
85 qDeleteAll(HFRPoints);
96 if (inFocusLoop || inAutoFocus)
104 if (ccdNum <= CCDs.count())
105 currentCCD = CCDs.at(ccdNum);
111 currentFocuser =
static_cast<ISD::Focuser *
> (newFocuser);
116 getAbsFocusPosition();
119 connect(currentFocuser, SIGNAL(numberUpdated(INumberVectorProperty*)),
this, SLOT(
processFocusProperties(INumberVectorProperty*)));
121 AutoModeR->setEnabled(
true);
130 CCDs.append(static_cast<ISD::CCD *>(newCCD));
134 CCDCaptureCombo->setCurrentIndex(0);
137 void Focus::getAbsFocusPosition()
141 INumberVectorProperty *absMove = currentFocuser->
getBaseDevice()->getNumber(
"ABS_FOCUS_POSITION");
144 pulseStep = absMove->np[0].value;
145 absMotionMax = absMove->np[0].max;
146 absMotionMin = absMove->np[0].min;
161 getAbsFocusPosition();
163 pulseDuration = stepIN->value();
177 qDeleteAll(HFRPoints);
193 currentCCD->disconnect(
this);
205 if (currentCCD == NULL)
210 double seqExpose = exposureIN->value();
222 connect(currentCCD, SIGNAL(BLOBUpdated(IBLOB*)),
this, SLOT(
newFITS(IBLOB*)));
226 targetChip->
capture(seqExpose);
228 if (inFocusLoop ==
false)
236 if (currentFocuser == NULL)
246 ms = stepIN->value();
267 if (currentFocuser == NULL)
279 ms = stepIN->value();
302 if (!strcmp(bp->name,
"CCD2"))
308 if (targetImage == NULL)
310 qDebug() <<
"Error: targetImage is NULL!" << endl;
316 currentCCD->disconnect(
this);
322 qDebug() <<
"curent HFR is " << currentHFR << endl;
324 if (currentHFR == -1)
326 currentHFR = image_data->
getHFR();
327 qDebug() <<
"and now hfr is " << currentHFR << endl;
330 HFRText = QString(
"%1").arg(currentHFR, 0,
'g', 3);
332 if (inFocusLoop ==
false && focusType ==
FOCUS_MANUAL && HFR == -1)
335 HFROut->setText(HFRText);
347 autoFocusAbs(currentHFR);
349 autoFocusRel(currentHFR);
354 void Focus::autoFocusAbs(
double currentHFR)
356 static int initHFRPos=0, lastHFRPos=0, minHFRPos=0, initSlopePos=0, initPulseDuration=0, focusOutLimit=0, focusInLimit=0, minPos=1e6, maxPos=0;
357 static double initHFR=0, minHFR=0, maxHFR=1,initSlopeHFR=0;
358 double targetPulse=0, delta=0;
360 QString deltaTxt = QString(
"%1").arg(fabs(currentHFR-minHFR)*100.0, 0,
'g', 2);
361 QString HFRText = QString(
"%1").arg(currentHFR, 0,
'g', 3);
368 appendLogText(i18n(
"FITS received. HFR %1 @ %2. Delta (%3%)", HFRText, pulseStep, deltaTxt));
370 appendLogText(i18n(
"FITS received. HFR %1 @ %2.", HFRText, pulseStep));
374 appendLogText(i18n(
"Autofocus failed to reach proper focus. Try increasing tolerance value."));
380 if (currentHFR == -1)
382 appendLogText(i18n(
"No stars detected, capturing again..."));
387 if (currentHFR > maxHFR || HFRPoints.empty())
391 if (HFRPoints.empty())
398 if (pulseStep > maxPos)
400 if (pulseStep < minPos)
403 HFRPoint *p =
new HFRPoint();
410 HFRPlot->removeAllPlotObjects();
413 HFRPlot->setLimits(minPos-pulseDuration, maxPos+pulseDuration, currentHFR/1.5, maxHFR );
415 KPlotObject *hfrObj =
new KPlotObject( Qt::red, KPlotObject::Points, 2 );
417 foreach(HFRPoint *p, HFRPoints)
418 hfrObj->addPoint(p->pos, p->HFR);
420 HFRPlot->addPlotObject(hfrObj);
424 switch (lastFocusDirection)
428 initHFRPos = pulseStep;
436 initPulseDuration=pulseDuration;
442 if (reverseDir && focusInLimit && focusOutLimit && fabs(currentHFR - minHFR) < (toleranceIN->value()/100.0) && HFRInc == 0 )
444 if (absIterations <= 2)
445 appendLogText(i18n(
"Change in HFR is too small. Try increasing the step size or decreasing the tolerance."));
451 else if (currentHFR < HFR)
456 if (initSlopeHFR == 0 && HFRInc == 0 && HFRDec >= 1)
459 initSlopePos = lastHFRPos;
463 if (lastFocusDirection ==
FOCUS_OUT && lastHFRPos < focusInLimit)
464 focusInLimit = lastHFRPos;
465 else if (lastFocusDirection ==
FOCUS_IN && lastHFRPos > focusOutLimit)
466 focusOutLimit = lastHFRPos;
471 slope = (currentHFR - initSlopeHFR) / (pulseStep - initSlopePos);
472 targetPulse = pulseStep + (currentHFR*0.5 - currentHFR)/slope;
478 targetPulse = pulseStep + pulseDuration;
480 targetPulse = pulseStep - pulseDuration;
490 minHFRPos = pulseStep;
493 lastHFRPos = pulseStep;
518 lastHFRPos = pulseStep;
524 focusInLimit = pulseStep;
526 focusOutLimit = pulseStep;
529 pulseDuration = pulseDuration * 0.75;
533 targetPulse = minHFRPos+pulseDuration/2;
535 targetPulse = minHFRPos-pulseDuration/2;
541 if (focusInLimit != 0 && lastFocusDirection ==
FOCUS_IN && targetPulse > focusInLimit)
542 targetPulse = focusInLimit;
543 else if (focusOutLimit != 0 && lastFocusDirection ==
FOCUS_OUT && targetPulse < focusOutLimit)
544 targetPulse = focusOutLimit;
547 if (targetPulse < absMotionMin)
548 targetPulse = absMotionMin;
549 else if (targetPulse > absMotionMax)
550 targetPulse = absMotionMax;
553 if (targetPulse == pulseStep)
561 if (focusOutLimit && focusOutLimit == focusInLimit)
563 appendLogText(i18n(
"Deadlock reached. Please try again with different settings."));
569 delta = (targetPulse - pulseStep);
584 void Focus::autoFocusRel(
double currentHFR)
586 QString deltaTxt = QString(
"%1").arg(fabs(currentHFR-HFR)*100.0, 0,
'g', 2);
587 QString HFRText = QString(
"%1").arg(currentHFR, 0,
'g', 3);
589 appendLogText(i18n(
"FITS received. HFR %1. Delta (%2%)", HFRText, deltaTxt));
591 if (pulseDuration <= 32)
593 appendLogText(i18n(
"Autofocus failed to reach proper focus. Try adjusting the tolerance value."));
598 if (currentHFR == -1)
600 appendLogText(i18n(
"No stars detected, capturing again..."));
605 switch (lastFocusDirection)
613 if (fabs(currentHFR - HFR) < (toleranceIN->value()/100.0) && HFRInc == 0)
619 else if (currentHFR < HFR)
663 if (fabs(currentHFR - HFR) < (toleranceIN->value()/100.0) && HFRInc == 0)
669 else if (currentHFR < HFR)
715 if (!strcmp(nvp->name,
"ABS_FOCUS_POSITION"))
717 INumber *pos = IUFindNumber(nvp,
"FOCUS_ABSOLUTE_POSITION");
719 pulseStep = pos->value;
721 if (canAbsMove && inAutoFocus)
723 if (nvp->s == IPS_OK)
725 else if (nvp->s == IPS_ALERT)
736 if (!strcmp(nvp->name,
"FOCUS_TIMER"))
739 if (canAbsMove ==
false && inAutoFocus)
741 if (nvp->s == IPS_OK)
743 else if (nvp->s == IPS_ALERT)
758 logText.insert(0,
i18nc(
"log entry; %1 is the date, %2 is the text",
"%1 %2", QDateTime::currentDateTime().toString(
"yyyy-MM-ddThh:mm:ss"), text));
782 void Focus::resetButtons()
787 startFocusB->setEnabled(
false);
788 startLoopB->setEnabled(
false);
789 stopFocusB->setEnabled(
true);
791 captureB->setEnabled(
false);
792 focusOutB->setEnabled(
false);
793 focusInB->setEnabled(
false);
800 stopFocusB->setEnabled(
true);
802 startFocusB->setEnabled(
false);
803 startLoopB->setEnabled(
false);
804 captureB->setEnabled(
false);
805 focusOutB->setEnabled(
false);
806 focusInB->setEnabled(
false);
811 if (focusType ==
FOCUS_AUTO && currentFocuser)
812 startFocusB->setEnabled(
true);
814 startFocusB->setEnabled(
false);
816 stopFocusB->setEnabled(
false);
817 startLoopB->setEnabled(
true);
824 focusOutB->setEnabled(
true);
825 focusInB->setEnabled(
true);
828 captureB->setEnabled(
true);
829 startLoopB->setEnabled(
true);
834 focusOutB->setEnabled(
false);
835 focusInB->setEnabled(
false);
FITSImage * getImageData()
CCDChip * getChip(CCDChip::ChipType cType)
void addCCD(ISD::GDInterface *newCCD)
void checkCCD(int CCDNum)
virtual const char * getDeviceName()=0
FITSView * getImage(FITSMode imageType)
void setFocuser(ISD::GDInterface *newFocuser)
bool absMoveFocuser(int steps)
static uint focusTicks()
Get Default Focuser step ticks.
static void setFocusTolerance(double v)
Set Default Focuser tolerance value.
bool capture(double exposure)
bool setFrameType(CCDFrameType fType)
void processFocusProperties(INumberVectorProperty *nvp)
i18nc("string from libindi, used in the config dialog","100x")
static double focusExposure()
Get Default Focuser exposure value.
static void setFocusTicks(uint v)
Set Default Focuser step ticks.
void appendLogText(const QString &)
void toggleAutofocus(bool enable)
void setCaptureFilter(FITSScale fType)
void setCaptureMode(FITSMode mode)
#define MAXIMUM_ABS_ITERATIONS
virtual bool isConnected()
double getHFR(HFRType type=HFR_AVERAGE)
virtual INDI::BaseDevice * getBaseDevice()
static double focusTolerance()
Get Default Focuser tolerance value.
static QStringList filterTypes
static void setFocusExposure(double v)
Set Default Focuser exposure value.
bool moveFocuser(int secs)