RIT VEXU Core API
Toggle main menu visibility
Loading...
Searching...
No Matches
lift.h
1
#pragma once
2
3
#include "core/utils/controls/pid.h"
4
#include "vex.h"
5
#include <atomic>
6
#include <iostream>
7
#include <map>
8
#include <vector>
9
10
using namespace
std;
11
19
template
<
typename
T>
class
Lift
{
20
public
:
27
struct
lift_cfg_t
{
28
double
up_speed, down_speed;
29
double
softstop_up, softstop_down;
30
31
PID::pid_config_t
lift_pid_cfg;
32
};
33
55
Lift
(vex::motor_group &lift_motors,
lift_cfg_t
&lift_cfg, map<T, double> &setpoint_map, vex::limit *homing_switch = NULL)
56
: lift_motors(lift_motors), cfg(lift_cfg), lift_pid(cfg.lift_pid_cfg), setpoint_map(setpoint_map),
57
homing_switch(homing_switch) {
58
59
is_async =
true
;
60
setpoint = 0;
61
62
// Create a background task that is constantly updating the lift PID, if requested.
63
// Set once, and forget.
64
vex::task t(
65
[](
void
*ptr) {
66
Lift
&lift = *((
Lift
*)ptr);
67
68
while
(
true
) {
69
if
(lift.
get_async
())
70
lift.
hold
();
71
72
vexDelay(50);
73
}
74
75
return
0;
76
},
77
this
);
78
}
79
88
void
control_continuous
(
bool
up_ctrl,
bool
down_ctrl) {
89
static
vex::timer tmr;
90
91
double
cur_pos = 0;
92
93
// Check if there's a hook for a custom sensor. If not, use the motors.
94
if
(get_sensor == NULL)
95
cur_pos = lift_motors.position(vex::rev);
96
else
97
cur_pos = get_sensor();
98
99
if
(up_ctrl && cur_pos < cfg.softstop_up) {
100
lift_motors.spin(vex::directionType::fwd, cfg.up_speed, vex::volt);
101
setpoint = cur_pos + .3;
102
103
// std::cout << "DEBUG OUT: UP " << setpoint << ", " << tmr.time(sec) << ", " << cfg.down_speed << "\n";
104
105
// Disable the PID while going UP.
106
is_async =
false
;
107
}
else
if
(down_ctrl && cur_pos > cfg.softstop_down) {
108
// Lower the lift slowly, at a rate defined by down_speed
109
if
(setpoint > cfg.softstop_down)
110
setpoint = setpoint - (tmr.time(vex::sec) * cfg.down_speed);
111
// std::cout << "DEBUG OUT: DOWN " << setpoint << ", " << tmr.time(sec) << ", " << cfg.down_speed << "\n";
112
is_async =
true
;
113
}
else
{
114
// Hold the lift at the last setpoint
115
is_async =
true
;
116
}
117
118
tmr.reset();
119
}
120
129
void
control_manual
(
bool
up_btn,
bool
down_btn,
int
volt_up,
int
volt_down) {
130
static
bool
down_hold =
false
;
131
static
bool
init =
true
;
132
133
// Allow for setting position while still calling this function
134
if
(init || up_btn || down_btn) {
135
init =
false
;
136
is_async =
false
;
137
}
138
139
double
rev = lift_motors.position(vex::rotationUnits::rev);
140
141
if
(rev < cfg.softstop_down && down_btn)
142
down_hold =
true
;
143
else
if
(!down_btn)
144
down_hold =
false
;
145
146
if
(up_btn && rev < cfg.softstop_up)
147
lift_motors.spin(vex::directionType::fwd, volt_up, vex::voltageUnits::volt);
148
else
if
(down_btn && rev > cfg.softstop_down && !down_hold)
149
lift_motors.spin(vex::directionType::rev, volt_down, vex::voltageUnits::volt);
150
else
151
lift_motors.spin(vex::directionType::fwd, 0, vex::voltageUnits::volt);
152
}
153
165
void
control_setpoints
(
bool
up_step,
bool
down_step, vector<T> pos_list) {
166
// Make sure inputs are only processed on the rising edge of the button
167
static
bool
up_last = up_step, down_last = down_step;
168
169
bool
up_rising = up_step && !up_last;
170
bool
down_rising = down_step && !down_last;
171
172
up_last = up_step;
173
down_last = down_step;
174
175
static
int
cur_index = 0;
176
177
// Avoid an index overflow. Shouldn't happen unless the user changes pos_list between calls.
178
if
(cur_index >= pos_list.size())
179
cur_index = pos_list.size() - 1;
180
181
// Increment or decrement the index of the list, bringing it up or down.
182
if
(up_rising && cur_index < (pos_list.size() - 1))
183
cur_index++;
184
else
if
(down_rising && cur_index > 0)
185
cur_index--;
186
187
// Set the lift to hold the position in the background with the PID loop
188
set_position
(pos_list[cur_index]);
189
is_async =
true
;
190
}
191
200
bool
set_position
(T pos) {
201
this->setpoint = setpoint_map[pos];
202
is_async =
true
;
203
204
return
(lift_pid.get_target() == this->setpoint) && lift_pid.is_on_target();
205
}
206
213
bool
set_setpoint
(
double
val) {
214
this->setpoint = val;
215
return
(lift_pid.get_target() == this->setpoint) && lift_pid.is_on_target();
216
}
217
221
double
get_setpoint
() {
return
this->setpoint; }
222
227
void
hold
() {
228
lift_pid.set_target(setpoint);
229
// std::cout << "DEBUG OUT: SETPOINT " << setpoint << "\n";
230
231
if
(get_sensor != NULL)
232
lift_pid.update(get_sensor());
233
else
234
lift_pid.update(lift_motors.position(vex::rev));
235
236
// std::cout << "DEBUG OUT: ROTATION " << lift_motors.rotation(rev) << "\n\n";
237
238
lift_motors.spin(vex::fwd, lift_pid.get(), vex::volt);
239
}
240
245
void
home
() {
246
static
vex::timer tmr;
247
tmr.reset();
248
249
while
(tmr.time(vex::sec) < 3) {
250
lift_motors.spin(vex::directionType::rev, 6, vex::volt);
251
252
if
(homing_switch == NULL && lift_motors.current(vex::currentUnits::amp) > 1.5)
253
break
;
254
else
if
(homing_switch != NULL && homing_switch->pressing())
255
break
;
256
}
257
258
if
(reset_sensor != NULL)
259
reset_sensor();
260
261
lift_motors.resetPosition();
262
lift_motors.stop();
263
}
264
268
bool
get_async
() {
return
is_async; }
269
275
void
set_async
(
bool
val) { this->is_async = val; }
276
286
void
set_sensor_function
(
double
(*fn_ptr)(
void
)) { this->get_sensor = fn_ptr; }
287
294
void
set_sensor_reset
(
void
(*fn_ptr)(
void
)) { this->reset_sensor = fn_ptr; }
295
296
private
:
297
vex::motor_group &lift_motors;
298
lift_cfg_t &cfg;
299
PID
lift_pid;
300
map<T, double> &setpoint_map;
301
vex::limit *homing_switch;
302
303
atomic<double> setpoint;
304
atomic<bool> is_async;
305
306
double (*get_sensor)(void) = NULL;
307
void (*reset_sensor)(void) = NULL;
308
};
Lift::set_sensor_function
void set_sensor_function(double(*fn_ptr)(void))
Definition
lift.h:286
Lift::set_setpoint
bool set_setpoint(double val)
Definition
lift.h:213
Lift::get_async
bool get_async()
Definition
lift.h:268
Lift::set_sensor_reset
void set_sensor_reset(void(*fn_ptr)(void))
Definition
lift.h:294
Lift::control_setpoints
void control_setpoints(bool up_step, bool down_step, vector< T > pos_list)
Definition
lift.h:165
Lift::set_async
void set_async(bool val)
Definition
lift.h:275
Lift::hold
void hold()
Definition
lift.h:227
Lift::set_position
bool set_position(T pos)
Definition
lift.h:200
Lift::home
void home()
Definition
lift.h:245
Lift::Lift
Lift(vex::motor_group &lift_motors, lift_cfg_t &lift_cfg, map< T, double > &setpoint_map, vex::limit *homing_switch=NULL)
Definition
lift.h:55
Lift::control_manual
void control_manual(bool up_btn, bool down_btn, int volt_up, int volt_down)
Definition
lift.h:129
Lift::get_setpoint
double get_setpoint()
Definition
lift.h:221
Lift::control_continuous
void control_continuous(bool up_ctrl, bool down_ctrl)
Definition
lift.h:88
PID
Definition
pid.h:21
Lift::lift_cfg_t
Definition
lift.h:27
PID::pid_config_t
Definition
pid.h:41
include
core
subsystems
lift.h
Generated by
1.17.0