Instrument Neutral Distributed Interface INDI  2.0.2
roll_off.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 
20 #include "roll_off.h"
21 
22 #include "indicom.h"
23 
24 #include <cmath>
25 #include <cstring>
26 #include <ctime>
27 #include <memory>
28 
29 // We declare an auto pointer to RollOff.
30 std::unique_ptr<RollOff> rollOff(new RollOff());
31 
32 #define ROLLOFF_DURATION 10 // 10 seconds until roof is fully opened or closed
33 
35 {
37 }
38 
39 /************************************************************************************
40  *
41 * ***********************************************************************************/
43 {
45 
47 
49 
50  return true;
51 }
52 
54 {
55  return INDI::Dome::ISSnoopDevice(root);
56 }
57 
58 bool RollOff::SetupParms()
59 {
60  // If we have parking data
61  if (InitPark())
62  {
63  if (isParked())
64  {
65  fullOpenLimitSwitch = ISS_OFF;
66  fullClosedLimitSwitch = ISS_ON;
67  }
68  else
69  {
70  fullOpenLimitSwitch = ISS_ON;
71  fullClosedLimitSwitch = ISS_OFF;
72  }
73  }
74  // If we don't have parking data
75  else
76  {
77  fullOpenLimitSwitch = ISS_OFF;
78  fullClosedLimitSwitch = ISS_OFF;
79  }
80 
81  return true;
82 }
83 
85 {
86  SetTimer(1000); // start the timer
87  return true;
88 }
89 
91 {
92  return true;
93 }
94 
96 {
97  return (const char *)"RollOff Simulator";
98 }
99 
100 bool RollOff::ISNewSwitch(const char *dev, const char *name, ISState *states, char *names[], int n)
101 {
102  return INDI::Dome::ISNewSwitch(dev, name, states, names, n);
103 }
104 
106 {
108 
109  if (isConnected())
110  {
111  SetupParms();
112  }
113 
114  return true;
115 }
116 
118 {
119  if (!isConnected())
120  return; // No need to reset timer if we are not connected anymore
121 
122  if (DomeMotionSP.s == IPS_BUSY)
123  {
124  // Abort called
125  if (MotionRequest < 0)
126  {
127  LOG_INFO("Roof motion is stopped.");
129  SetTimer(1000);
130  return;
131  }
132 
133  // Roll off is opening
134  if (DomeMotionS[DOME_CW].s == ISS_ON)
135  {
137  {
138  LOG_INFO("Roof is open.");
139  SetParked(false);
140  return;
141  }
142  }
143  // Roll Off is closing
144  else if (DomeMotionS[DOME_CCW].s == ISS_ON)
145  {
147  {
148  LOG_INFO("Roof is closed.");
149  SetParked(true);
150  return;
151  }
152  }
153 
154  SetTimer(1000);
155  }
156 
157  //SetTimer(1000);
158 }
159 
161 {
162  return INDI::Dome::saveConfigItems(fp);
163 }
164 
166 {
167  if (operation == MOTION_START)
168  {
169  // DOME_CW --> OPEN. If can we are ask to "open" while we are fully opened as the limit switch indicates, then we simply return false.
170  if (dir == DOME_CW && fullOpenLimitSwitch == ISS_ON)
171  {
172  LOG_WARN("Roof is already fully opened.");
173  return IPS_ALERT;
174  }
175  // else if (dir == DOME_CW && getWeatherState() == IPS_ALERT)
176  // {
177  // LOG_WARN("Weather conditions are in the danger zone. Cannot open roof.");
178  // return IPS_ALERT;
179  // }
180  else if (dir == DOME_CCW && fullClosedLimitSwitch == ISS_ON)
181  {
182  LOG_WARN("Roof is already fully closed.");
183  return IPS_ALERT;
184  }
185  else if (dir == DOME_CCW && INDI::Dome::isLocked())
186  {
188  "Cannot close dome when mount is locking. See: Telescope parking policy, in options tab");
189  return IPS_ALERT;
190  }
191 
192  fullOpenLimitSwitch = ISS_OFF;
193  fullClosedLimitSwitch = ISS_OFF;
194  MotionRequest = ROLLOFF_DURATION;
195  gettimeofday(&MotionStart, nullptr);
196  SetTimer(1000);
197  return IPS_BUSY;
198  }
199 
200  return (Dome::Abort() ? IPS_OK : IPS_ALERT);
201 }
202 
204 {
206  if (rc == IPS_BUSY)
207  {
208  LOG_INFO("Roll off is parking...");
209  return IPS_BUSY;
210  }
211  else
212  return IPS_ALERT;
213 }
214 
216 {
218  if (rc == IPS_BUSY)
219  {
220  LOG_INFO("Roll off is unparking...");
221  return IPS_BUSY;
222  }
223  else
224  return IPS_ALERT;
225 }
226 
228 {
229  MotionRequest = -1;
230 
231  // If both limit switches are off, then we're neither parked nor unparked.
232  if (fullOpenLimitSwitch == ISS_OFF && fullClosedLimitSwitch == ISS_OFF)
233  {
235  ParkSP.s = IPS_IDLE;
236  IDSetSwitch(&ParkSP, nullptr);
237  }
238 
239  return true;
240 }
241 
242 float RollOff::CalcTimeLeft(timeval start)
243 {
244  double timesince;
245  double timeleft;
246  struct timeval now
247  {
248  0, 0
249  };
250  gettimeofday(&now, nullptr);
251 
252  timesince =
253  (double)(now.tv_sec * 1000.0 + now.tv_usec / 1000) - (double)(start.tv_sec * 1000.0 + start.tv_usec / 1000);
254  timesince = timesince / 1000;
255  timeleft = MotionRequest - timesince;
256  return timeleft;
257 }
258 
260 {
261  double timeleft = CalcTimeLeft(MotionStart);
262 
263  if (timeleft <= 0)
264  {
265  fullOpenLimitSwitch = ISS_ON;
266  return true;
267  }
268  else
269  return false;
270 }
271 
273 {
274  double timeleft = CalcTimeLeft(MotionStart);
275 
276  if (timeleft <= 0)
277  {
278  fullClosedLimitSwitch = ISS_ON;
279  return true;
280  }
281  else
282  return false;
283 }
bool isConnected() const
Definition: basedevice.cpp:520
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.
@ DOME_CAN_PARK
Definition: indidome.h:159
@ DOME_CAN_ABORT
Definition: indidome.h:156
ISwitch DomeMotionS[2]
Definition: indidome.h:531
void SetParked(bool isparked)
SetParked Change the mount parking status. The data park file (stored in ~/.indi/ParkData....
Definition: indidome.cpp:1633
void SetDomeCapability(uint32_t cap)
SetDomeCapability set the dome capabilities. All capabilities must be initialized.
Definition: indidome.cpp:1561
bool isParked()
isParked is dome currently parked?
Definition: indidome.cpp:1639
DomeMotionCommand
Definition: indidome.h:97
@ MOTION_START
Definition: indidome.h:98
virtual bool initProperties() override
Initilize properties initial state and value. The child class must implement this function.
Definition: indidome.cpp:93
@ DOME_CCW
Definition: indidome.h:94
bool isLocked()
isLocked, is the dome currently locked?
Definition: indidome.cpp:1077
ISwitchVectorProperty ParkSP
Definition: indidome.h:551
virtual bool updateProperties() override
updateProperties is called whenever there is a change in the CONNECTION status of the driver....
Definition: indidome.cpp:279
virtual bool ISNewSwitch(const char *dev, const char *name, ISState *states, char *names[], int n) override
Process the client newSwitch command.
Definition: indidome.cpp:492
virtual bool ISSnoopDevice(XMLEle *root) override
Process a snoop event from INDI server. This function is called when a snooped property is updated in...
Definition: indidome.cpp:822
ISwitchVectorProperty DomeMotionSP
Definition: indidome.h:530
virtual bool saveConfigItems(FILE *fp) override
saveConfigItems Saves the Device Port and Dome Presets in the configuration file
Definition: indidome.cpp:1043
void setDomeState(const DomeState &value)
Definition: indidome.cpp:1156
bool InitPark()
InitPark Loads parking data (stored in ~/.indi/ParkData.xml) that contains parking status and parking...
Definition: indidome.cpp:1644
void SetParkDataType(DomeParkData type)
setParkDataType Sets the type of parking data stored in the park data file and presented to the user.
Definition: indidome.cpp:1587
virtual IPState Move(DomeDirection dir, DomeMotionCommand operation)
Move the Dome in a particular direction.
Definition: indidome.cpp:1873
virtual bool ISNewSwitch(const char *dev, const char *name, ISState *states, char *names[], int n) override
Process the client newSwitch command.
Definition: roll_off.cpp:100
RollOff()
Definition: roll_off.cpp:34
virtual bool getFullOpenedLimitSwitch()
Definition: roll_off.cpp:259
bool Connect() override
Connect to the device. INDI::DefaultDevice implementation connects to appropriate connection interfac...
Definition: roll_off.cpp:84
virtual IPState Move(DomeDirection dir, DomeMotionCommand operation) override
Move the Dome in a particular direction.
Definition: roll_off.cpp:165
virtual bool saveConfigItems(FILE *fp) override
saveConfigItems Saves the Device Port and Dome Presets in the configuration file
Definition: roll_off.cpp:160
virtual bool ISSnoopDevice(XMLEle *root) override
Process a snoop event from INDI server. This function is called when a snooped property is updated in...
Definition: roll_off.cpp:53
virtual bool initProperties() override
Initilize properties initial state and value. The child class must implement this function.
Definition: roll_off.cpp:42
bool Disconnect() override
Disconnect from device.
Definition: roll_off.cpp:90
virtual IPState UnPark() override
UnPark dome. The action of the Unpark command is dome specific, but it may include opening the shutte...
Definition: roll_off.cpp:215
virtual bool Abort() override
Abort all dome motion.
Definition: roll_off.cpp:227
virtual IPState Park() override
Goto Park Position. The park position is an absolute azimuth value.
Definition: roll_off.cpp:203
void TimerHit() override
Callback function to be called once SetTimer duration elapses.
Definition: roll_off.cpp:117
const char * getDefaultName() override
Definition: roll_off.cpp:95
virtual bool getFullClosedLimitSwitch()
Definition: roll_off.cpp:272
bool updateProperties() override
updateProperties is called whenever there is a change in the CONNECTION status of the driver....
Definition: roll_off.cpp:105
ISState
Switch state.
Definition: indiapi.h:150
@ ISS_OFF
Definition: indiapi.h:151
@ ISS_ON
Definition: indiapi.h:152
IPState
Property state.
Definition: indiapi.h:160
@ IPS_BUSY
Definition: indiapi.h:163
@ IPS_ALERT
Definition: indiapi.h:164
@ IPS_IDLE
Definition: indiapi.h:161
@ IPS_OK
Definition: indiapi.h:162
Implementations for common driver routines.
void IUResetSwitch(ISwitchVectorProperty *svp)
Reset all switches in a switch vector property to OFF.
Definition: indidevapi.c:148
void IDSetSwitch(const ISwitchVectorProperty *svp, const char *fmt,...)
Definition: indidriver.c:1231
#define DEBUG(priority, msg)
Macro to print log messages. Example of usage of the Logger: DEBUG(DBG_DEBUG, "hello " << "world");.
Definition: indilogger.h:56
#define LOG_WARN(txt)
Definition: indilogger.h:73
#define LOG_INFO(txt)
Definition: indilogger.h:74
#define ROLLOFF_DURATION
Definition: roll_off.cpp:32
std::unique_ptr< RollOff > rollOff(new RollOff())