Instrument Neutral Distributed Interface INDI 2.2.5
dome_simulator.cpp
Go to the documentation of this file.
1/*******************************************************************************
2 Dome Simulator
3 Copyright(c) 2014 Jasem Mutlaq. All rights reserved.
4
5 This library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Library General Public
7 License version 2 as published by the Free Software Foundation.
8 .
9 This library is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 Library General Public License for more details.
13 .
14 You should have received a copy of the GNU Library General Public License
15 along with this library; see the file COPYING.LIB. If not, write to
16 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 Boston, MA 02110-1301, USA.
18*******************************************************************************/
19#include "dome_simulator.h"
20
21#include "indicom.h"
22
23#include <cmath>
24#include <memory>
25#include <unistd.h>
26
27// We declare an auto pointer to domeSim.
28static std::unique_ptr<DomeSim> domeSim(new DomeSim());
29
41
46{
48
49 SpeedNP[Dome].fill("DOME", "Dome (deg/s)", "%.2f", 0.1, 10, 1, 5);
50 SpeedNP[Shutter].fill("SHUTTER", "Shutter (m/s)", "%.2f", 0.01, 1, 0.1, 0.1);
51 SpeedNP.fill(getDeviceName(), "SPEEDS", "Speeds", MAIN_CONTROL_TAB, IP_RW, 60, IPS_IDLE);
52
54
56
57 return true;
58}
59
63bool DomeSim::SetupParms()
64{
65 targetAz = 0;
66 DomeAbsPosNP[0].setValue(0);
68
69 if (InitPark())
70 {
71 // If loading parking data is successful, we just set the default parking values.
73 }
74 else
75 {
76 // Otherwise, we set all parking data to default in case no parking data is found.
77 SetAxis1Park(90);
79 }
80
81 return true;
82}
83
88{
89 return "Dome Simulator";
90}
91
96{
98
99 if (isConnected())
100 {
101 defineProperty(SpeedNP);
102 SetupParms();
103 }
104 else
105 {
106 deleteProperty(SpeedNP);
107 }
108
109 return true;
110}
111
116{
117 SetTimer(1000);
118 return true;
119}
120
125{
126 return true;
127}
128
132bool DomeSim::ISNewNumber(const char * dev, const char * name, double values[], char * names[], int n)
133{
134 if (dev != nullptr && strcmp(dev, getDeviceName()) == 0)
135 {
136 if (SpeedNP.isNameMatch(name))
137 {
138 SpeedNP.update(values, names, n);
139 SpeedNP.setState(IPS_OK);
140 SpeedNP.apply();
141 saveConfig(SpeedNP);
142 return true;
143 }
144 }
145
146 return INDI::Dome::ISNewNumber(dev, name, values, names, n);
147}
148
153{
154 if (!isConnected())
155 return;
156
157 auto domeSpeed = SpeedNP[Dome].getValue();
158 auto shutterSpeed = SpeedNP[Shutter].getValue();
159
161 {
162 double b = DomeAbsPosNP[0].getValue();
163
164 if (m_MoveDirection != 0)
165 {
166 // Continuous jog: DOME_CW increases azimuth, DOME_CCW decreases it.
167 DomeAbsPosNP[0].setValue(range360(b + domeSpeed * m_MoveDirection));
168 }
169 else
170 {
171 // Find shortest distance given target degree
172 double a = targetAz;
173 int sign = (a - b >= 0 && a - b <= 180) || (a - b <= -180 && a - b >= -360) ? 1 : -1;
174 DomeAbsPosNP[0].setValue(range360(b + domeSpeed * sign));
175
176 if (std::abs(targetAz - DomeAbsPosNP[0].getValue()) <= domeSpeed)
177 {
178 DomeAbsPosNP[0].setValue(targetAz);
179 LOG_INFO("Dome reached requested azimuth angle.");
180
181 if (getDomeState() == DOME_PARKING)
182 SetParked(true);
183 else if (getDomeState() == DOME_UNPARKING)
184 SetParked(false);
185 else
187 }
188 }
189
191 }
192
193 // Dome shutter, we decrease by shutter speed in meters/second
195 {
196 m_ShutterDistance -= shutterSpeed;
197
198 if (m_ShutterDistance <= 0)
199 {
200 m_ShutterDistance = 0;
202 LOGF_INFO("Shutter is %s.", (DomeShutterSP[0].getState() == ISS_ON ? "open" : "closed"));
204
206 SetParked(false);
207 }
208 }
209
211}
212
217{
218 if (operation == MOTION_START)
219 {
220 // DOME_CW increases the azimuth, DOME_CCW decreases it (see INDI::Dome convention).
221 m_MoveDirection = (dir == DOME_CW) ? 1 : -1;
223 }
224 else
225 {
226 m_MoveDirection = 0;
227 targetAz = DomeAbsPosNP[0].getValue();
229 }
230
232 return ((operation == MOTION_START) ? IPS_BUSY : IPS_OK);
233}
234
239{
240 m_MoveDirection = 0;
241 targetAz = az;
242
243 // Requested position is within one cycle, let's declare it done
244 if (std::abs(az - DomeAbsPosNP[0].getValue()) < SpeedNP[Dome].getValue())
245 return IPS_OK;
246
247 // It will take a few cycles to reach final position
248 return IPS_BUSY;
249}
250
255{
256 m_MoveDirection = 0;
257 targetAz = range360(DomeAbsPosNP[0].getValue() + azDiff);
258
259 // Requested position is within one cycle, let's declare it done
260 if (std::abs(targetAz - DomeAbsPosNP[0].value) < SpeedNP[Dome].getValue())
261 return IPS_OK;
262
263 // It will take a few cycles to reach final position
264 return IPS_BUSY;
265}
266
271{
272 targetAz = DomeParamNP[0].getValue();
273 Dome::ControlShutter(SHUTTER_CLOSE);
274 Dome::MoveAbs(GetAxis1Park());
275
276 return IPS_BUSY;
277}
278
283{
284 return Dome::ControlShutter(SHUTTER_OPEN);
285}
286
291{
292 INDI_UNUSED(operation);
293 // If shutter width = 1 meter, then we only need to open half of that since we presume
294 // two sides are moving at the same speed closing or opening.
295 m_ShutterDistance = DomeMeasurementsNP[DM_SHUTTER_WIDTH].getValue() / 2;
296 return IPS_BUSY;
297}
298
303{
304 // If we abort while in the middle of opening/closing shutter, alert.
306 {
308 LOG_ERROR("Shutter operation aborted. Status: unknown.");
310 return false;
311 }
312
313 return true;
314}
315
320{
321 SetAxis1Park(DomeAbsPosNP[0].getValue());
322 return true;
323}
324
329{
330 // By default set position to 90
331 SetAxis1Park(90);
332 return true;
333}
334
339{
341 SpeedNP.save(fp);
342 return true;
343}
The DomeSim class provides an absolute position dome that supports parking, unparking,...
virtual bool Abort() override
Abort all dome motion.
virtual bool SetCurrentPark() override
SetCurrentPark Set current coordinates/encoders value as the desired parking position.
virtual bool ISNewNumber(const char *dev, const char *name, double values[], char *names[], int n) override
Process the client newNumber command.
virtual IPState Park() override
Goto Park Position. The park position is an absolute azimuth value.
virtual const char * getDefaultName() override
virtual bool SetDefaultPark() override
SetDefaultPark Set default coordinates/encoders value as the desired parking position.
bool Disconnect() override
Disconnect from device.
void TimerHit() override
Callback function to be called once SetTimer duration elapses.
virtual IPState UnPark() override
UnPark dome. The action of the Unpark command is dome specific, but it may include opening the shutte...
virtual bool saveConfigItems(FILE *fp) override
saveConfigItems Saves the Device Port and Dome Presets in the configuration file
virtual bool initProperties() override
Initialize properties initial state and value. The child class must implement this function.
virtual bool updateProperties() override
updateProperties is called whenever there is a change in the CONNECTION status of the driver....
virtual IPState MoveAbs(double az) override
Move the Dome to an absolute azimuth.
virtual IPState MoveRel(double azDiff) override
Move the Dome to an relative position.
bool Connect() override
Connect to the device. INDI::DefaultDevice implementation connects to appropriate connection interfac...
virtual IPState ControlShutter(ShutterOperation operation) override
Open or Close shutter.
virtual IPState Move(DomeDirection dir, DomeMotionCommand operation) override
Move the Dome in a particular direction.
Definition dome.h:33
bool isConnected() const
virtual bool saveConfig(bool silent=false, const char *property=nullptr)
Save the current properties in a configuration file.
virtual bool deleteProperty(const char *propertyName)
Delete a property and unregister it. It will also be deleted from all clients.
uint32_t getPollingPeriod() const
getPollingPeriod Return the polling period.
void defineProperty(INumberVectorProperty *property)
virtual bool saveConfigItems(FILE *fp)
saveConfigItems Save specific properties in the provide config file handler. Child class usually over...
void addAuxControls()
Add Debug, Simulation, and Configuration options to the driver.
int SetTimer(uint32_t ms)
Set a timer to call the function TimerHit after ms milliseconds.
double prev_alt
Definition indidome.h:602
void SetParked(bool isparked)
SetParked Change the mount parking status. The data park file (stored in ~/.indi/ParkData....
void SetDomeCapability(uint32_t cap)
SetDomeCapability set the dome capabilities. All capabilities must be initialized.
INDI::PropertyNumber DomeParamNP
Definition indidome.h:542
@ DOME_UNPARKING
Definition indidome.h:135
void SetAxis1Park(double value)
SetRAPark Set current AZ parking position. The data park file (stored in ~/.indi/ParkData....
void SetAxis1ParkDefault(double steps)
SetAxis1Park Set default AZ parking position.
ShutterOperation
Shutter operation command.
Definition indidome.h:114
@ SHUTTER_CLOSE
Definition indidome.h:116
DomeMotionCommand
Definition indidome.h:97
@ MOTION_START
Definition indidome.h:98
virtual bool initProperties() override
Initialize properties initial state and value. The child class must implement this function.
Definition indidome.cpp:105
double prev_az
Definition indidome.h:602
INDI::PropertyNumber DomeMeasurementsNP
Definition indidome.h:576
@ DOME_CAN_PARK
Definition indidome.h:159
@ DOME_CAN_ABS_MOVE
Definition indidome.h:157
@ DOME_HAS_SHUTTER
Definition indidome.h:161
@ DOME_CAN_REL_MOVE
Definition indidome.h:158
@ DOME_CAN_ABORT
Definition indidome.h:156
double GetAxis1Park()
virtual bool updateProperties() override
updateProperties is called whenever there is a change in the CONNECTION status of the driver....
Definition indidome.cpp:284
INDI::PropertyNumber DomeAbsPosNP
Definition indidome.h:536
void setDomeState(const DomeState &value)
bool InitPark()
InitPark Loads parking data (stored in ~/.indi/ParkData.xml) that contains parking status and parking...
void SetParkDataType(DomeParkData type)
setParkDataType Sets the type of parking data stored in the park data file and presented to the user.
INDI::PropertySwitch DomeShutterSP
Definition indidome.h:546
@ DM_SHUTTER_WIDTH
Definition indidome.h:84
virtual bool ISNewNumber(const char *dev, const char *name, double values[], char *names[], int n) override
Process the client newNumber command.
Definition indidome.cpp:394
DomeState getDomeState() const
Definition indidome.h:285
void setState(IPState state)
void apply(const char *format,...) const ATTRIBUTE_FORMAT_PRINTF(2
void save(FILE *f) const
save Save property to configuration file.
bool isNameMatch(const char *otherName) const
bool update(const double values[], const char *const names[], int n)
void fill(const char *device, const char *name, const char *label, const char *group, IPerm permission, double timeout, IPState state)
const char * MAIN_CONTROL_TAB
MAIN_CONTROL_TAB Where all the primary controls for the device are located.
@ ISS_ON
Definition indiapi.h:150
@ IP_RW
Definition indiapi.h:184
IPState
Property state.
Definition indiapi.h:158
@ IPS_BUSY
Definition indiapi.h:161
@ IPS_ALERT
Definition indiapi.h:162
@ IPS_IDLE
Definition indiapi.h:159
@ IPS_OK
Definition indiapi.h:160
double range360(double r)
range360 Limits an angle to be between 0-360 degrees.
Definition indicom.c:1321
Implementations for common driver routines.
#define INDI_UNUSED(x)
Definition indidevapi.h:132
#define LOGF_INFO(fmt,...)
Definition indilogger.h:82
#define LOG_ERROR(txt)
Shorter logging macros. In order to use these macros, the function (or method) "getDeviceName()" must...
Definition indilogger.h:72
#define LOG_INFO(txt)
Definition indilogger.h:74
#define getDeviceName