ClearCore Library
Loading...
Searching...
No Matches
Move2IncrementsHomeToSwitch.cpp

Return to SDK Examples for Microchip Studio

1/*
2 * Title: 2IncrementsHomeToSwitch
3 *
4 * Objective:
5 * This example demonstrates control of the ClearPath-MCPV operational mode
6 * Move Incremental Distance, 2 Increments (Home to Switch).
7 *
8 * Description:
9 * This example enables a ClearPath motor and executes a repeating pattern of
10 * incremental moves. During operation, various move statuses are written to
11 * the USB serial port.
12 *
13 * Requirements:
14 * 1. A ClearPath motor must be connected to Connector M-0.
15 * 2. The connected ClearPath motor must be configured through the MSP software
16 * for Move Incremental Distance, 2 Increments (Home to Switch) mode (In MSP
17 * select Mode>>Position>>Move Incremental Distance, then with "2 Increments
18 * (Home to Switch)" selected hit the OK button).
19 * 3. The ClearPath motor must be set to use the HLFB mode "ASG-Position
20 * w/Measured Torque" with a PWM carrier frequency of 482 Hz through the MSP
21 * software (select Advanced>>High Level Feedback [Mode]... then choose
22 * "ASG-Position w/Measured Torque" from the dropdown, make sure that 482 Hz
23 * is selected in the "PWM Carrier Frequency" dropdown, and hit the OK
24 * button).
25 * 4. If the ClearPath is configured for sensor-based homing, ensure that the
26 * homing sensor is wired to Connector DI-6 (homing is optional, not required
27 * in this operational mode or in this example).
28 * 5. The ClearPath must have defined Position Increments through the MSP
29 * software which match the #define values below (On the main MSP window
30 * check the "Position Increment Setup (cnts)" box and fill in the two text
31 * boxes labeled "A off" and "A on").
32 * 6. Ensure the Trigger Pulse Time in MSP is set to 20ms. To configure, click
33 * the "Setup..." button found under the "Trigger Pulse" label on the MSP's
34 * main window, fill in the text box, and hit the OK button. Setting this to
35 * 20ms allows trigger pulses to be as long as 60ms, which will accommodate
36 * our 25ms pulses used later.
37 * 7. Ensure the Input A & B filters in MSP are both set to 20ms (In MSP
38 * select Advanced>>Input A, B Filtering... then in the Settings box fill in
39 * the textboxes labeled "Input A Filter Time Constant (msec)" and "Input B
40 * Filter Time Constant (msec)" then hit the OK button).
41 *
42 * ** Note: Homing is optional, and not required in this operational mode or in
43 * this example. This example makes its first move in the positive direction,
44 * assuming any homing move occurs in the negative direction or there are no
45 * end of travel limits
46 *
47 * Links:
48 * ** ClearCore Documentation: https://teknic-inc.github.io/ClearCore-library/
49 * ** ClearCore Manual: https://www.teknic.com/files/downloads/clearcore_user_manual.pdf
50 * ** ClearPath Manual (DC Power): https://www.teknic.com/files/downloads/clearpath_user_manual.pdf
51 * ** ClearPath Manual (AC Power): https://www.teknic.com/files/downloads/ac_clearpath-mc-sd_manual.pdf
52 * ** ClearPath Mode Informational Video: https://www.teknic.com/watch-video/#OpMode4
53 *
54 *
55 * Copyright (c) 2020 Teknic Inc. This work is free to use, copy and distribute under the terms of
56 * the standard MIT permissive software license which can be found at https://opensource.org/licenses/MIT
57 */
58
59#include "ClearCore.h"
60
61// Define the motor's connector as ConnectorM0
62#define motor ConnectorM0
63
64// The TRIGGER_PULSE_TIME is set to 25ms to ensure it is within the
65// Trigger Pulse Range defined in the MSP software (Default is 20-60ms)
66#define TRIGGER_PULSE_TIME 25
67
68// The INPUT_A_B_FILTER must match the Input A, B filter setting in
69// MSP (Advanced >> Input A, B Filtering...)
70#define INPUT_A_B_FILTER 20
71
72// Increments defined below must be set identically to the position increments
73// set in MSP
74#define POSITION_INCREMENT_1 1000 // Input A "off" setup selection, 1000 counts (CCW)
75#define POSITION_INCREMENT_2 -1000 // Input A "on" setup selection, -1000 counts (CW)
76
77// Specify the home sensor connector
78#define HomingSensor ConnectorDI6
79
80// Select the baud rate to match the target device.
81#define baudRate 9600
82
83// Specify which serial to use: ConnectorUsb, ConnectorCOM0, or ConnectorCOM1.
84#define SerialPort ConnectorUsb
85
86// This example has built-in functionality to automatically clear motor faults.
87// Any uncleared fault will cancel and disallow motion.
88// WARNING: enabling automatic fault handling will clear faults immediately when
89// encountered and return a motor to a state in which motion is allowed. Before
90// enabling this functionality, be sure to understand this behavior and ensure
91// your system will not enter an unsafe state.
92// To enable automatic fault handling, #define HANDLE_MOTOR_FAULTS (1)
93// To disable automatic fault handling, #define HANDLE_MOTOR_FAULTS (0)
94#define HANDLE_MOTOR_FAULTS (0)
95
96// Declares user-defined helper functions.
97// The definition/implementations of these functions are at the bottom of the sketch.
98void HomingSensorCallback();
99bool MoveIncrements(uint32_t numberOfIncrements, int32_t positionIncrement);
100void HandleMotorFaults();
101
102int main()
103{
104 // Sets all motor connectors to the correct mode for Incremental Distance
105 // mode.
106 MotorMgr.MotorModeSet(MotorManager::MOTOR_ALL,
107 Connector::CPM_MODE_A_DIRECT_B_DIRECT);
108
109 // Set the motor's HLFB mode to bipolar PWM
110 motor.HlfbMode(MotorDriver::HLFB_MODE_HAS_BIPOLAR_PWM);
111 // Set the HFLB carrier frequency to 482 Hz
112 motor.HlfbCarrier(MotorDriver::HLFB_CARRIER_482_HZ);
113
114 // Enforces the state of the motor's A and B inputs before enabling
115 motor.MotorInAState(false);
116 motor.MotorInBState(false);
117
118 // This section attaches the interrupt callback to the homing sensor pin,
119 // set to trigger on any change of sensor state.
120 HomingSensor.Mode(Connector::INPUT_DIGITAL);
121 HomingSensor.InterruptHandlerSet(HomingSensorCallback, InputManager::CHANGE);
122 // Set input B to match the initial state of the sensor.
123 motor.MotorInBState(HomingSensor.State());
124
125 // Sets up serial communication and waits up to 5 seconds for a port to open.
126 // Serial communication is not required for this example to run.
127 SerialPort.Mode(Connector::USB_CDC);
128 SerialPort.Speed(baudRate);
129 uint32_t timeout = 5000;
130 uint32_t startTime = Milliseconds();
131 SerialPort.PortOpen();
132 while (!SerialPort && Milliseconds() - startTime < timeout)
133 {
134 continue;
135 }
136
137 // Enables the motor; homing will begin automatically if homing is enabled
138 // in MSP.
139 motor.EnableRequest(true);
140 SerialPort.SendLine("Motor Enabled");
141
142 // Waits for HLFB to assert (waits for homing to complete if applicable)
143 SerialPort.SendLine("Waiting for HLFB...");
144 while (motor.HlfbState() != MotorDriver::HLFB_ASSERTED &&
145 !motor.StatusReg().bit.MotorInFault)
146 {
147 continue;
148 }
149 // Check if a motor faulted during enabling
150 // Clear fault if configured to do so
151 if (motor.StatusReg().bit.MotorInFault)
152 {
153 SerialPort.SendLine("Motor fault detected.");
154 if (HANDLE_MOTOR_FAULTS)
155 {
156 HandleMotorFaults();
157 }
158 else
159 {
160 SerialPort.SendLine("Enable automatic fault handling by setting HANDLE_MOTOR_FAULTS to 1.");
161 }
162 SerialPort.SendLine("Enabling may not have completed as expected. Proceed with caution.");
163 SerialPort.SendLine();
164 }
165 else
166 {
167 SerialPort.SendLine("Motor Ready");
168 }
169
170 while (true)
171 {
172 // Move a distance equal to 1 * POSITION_INCREMENT_1 = 1000 counts.
173 // See below for the detailed function definition.
174 MoveIncrements(1, POSITION_INCREMENT_1);
175 // Stay settled for 1 second before moving again.
176 Delay_ms(1000);
177
178 // Move a distance equal to 1 * POSITION_INCREMENT_2 = -1000 counts.
179 MoveIncrements(1, POSITION_INCREMENT_2);
180 Delay_ms(1000);
181
182 // Note: If another incremental move is triggered in the same direction as
183 // an active move before deceleration begins, then the moves will be
184 // seamlessly combined into one continuous move
185
186 // Move a distance equal to 4 * POSITION_INCREMENT_1 = 4000 counts.
187 MoveIncrements(4, POSITION_INCREMENT_1);
188 Delay_ms(1000);
189
190 // Move a distance equal to 4 * POSITION_INCREMENT_2 = -4000 counts.
191 MoveIncrements(4, POSITION_INCREMENT_2);
192 Delay_ms(1000);
193 }
194}
195
196/*------------------------------------------------------------------------------
197 * MoveIncrements
198 *
199 * Triggers an incremental move of length numberOfIncrements *
200 * positionIncrement.
201 * Prints the distance and move status to the USB serial port.
202 * Returns when HLFB asserts (indicating move has successfully completed).
203 *
204 * Parameters:
205 * int numberOfIncrements - The number of increments to command
206 * int positionIncrement - The position increment commanded
207 *
208 * Returns: True/False depending on whether the move was successfully triggered.
209 */
210bool MoveIncrements(uint32_t numberOfIncrements, int32_t positionIncrement)
211{
212 // Check if a motor fault is currently preventing motion
213 // Clear fault if configured to do so
214 if (motor.StatusReg().bit.MotorInFault)
215 {
216 if (HANDLE_MOTOR_FAULTS)
217 {
218 SerialPort.SendLine("Motor fault detected. Move canceled.");
219 HandleMotorFaults();
220 }
221 else
222 {
223 SerialPort.SendLine("Motor fault detected. Move canceled. Enable automatic fault handling by setting HANDLE_MOTOR_FAULTS to 1.");
224 }
225 return false;
226 }
227
228 SerialPort.Send("Moving ");
229 SerialPort.Send(numberOfIncrements);
230 SerialPort.Send(" * ");
231
232 switch (positionIncrement)
233 {
234 case POSITION_INCREMENT_1:
235 // Sets Input A to position increment 1
236 SerialPort.SendLine(POSITION_INCREMENT_1);
237 motor.MotorInAState(false);
238 break;
239 case POSITION_INCREMENT_2:
240 // Sets Input A to position increment 2
241 SerialPort.SendLine(POSITION_INCREMENT_2);
242 motor.MotorInAState(true);
243 break;
244 default:
245 // If this case is reached then an incorrect positionIncrement was
246 // entered
247 return false;
248 }
249
250 // Delays for 20ms longer than the Input A, B filter setting in MSP
251 Delay_ms(20 + INPUT_A_B_FILTER);
252
253 // Sends trigger pulses to the motor
254 motor.EnableTriggerPulse(numberOfIncrements, TRIGGER_PULSE_TIME, true);
255
256 SerialPort.SendLine("Moving.. Waiting for HLFB");
257 while (motor.HlfbState() != MotorDriver::HLFB_ASSERTED &&
258 !motor.StatusReg().bit.MotorInFault)
259 {
260 continue;
261 }
262 // Check if a motor faulted during move
263 // Clear fault if configured to do so
264 if (motor.StatusReg().bit.MotorInFault)
265 {
266 SerialPort.SendLine("Motor fault detected.");
267 if (HANDLE_MOTOR_FAULTS)
268 {
269 HandleMotorFaults();
270 }
271 else
272 {
273 SerialPort.SendLine("Enable automatic fault handling by setting HANDLE_MOTOR_FAULTS to 1.");
274 }
275 SerialPort.SendLine("Motion may not have completed as expected. Proceed with caution.");
276 SerialPort.SendLine();
277 return false;
278 }
279 else
280 {
281 SerialPort.SendLine("Move Done");
282 return true;
283 }
284
285 SerialPort.SendLine("Move Done");
286 return true;
287}
288//------------------------------------------------------------------------------
289
290/*------------------------------------------------------------------------------
291 * HomingSensorCallback
292 *
293 * Reads the state of the homing sensor and passes the state to the motor.
294 */
295void HomingSensorCallback()
296{
297 // A 1 ms delay is required in order to pass the correct filtered sensor
298 // state.
299 Delay_ms(1);
300 motor.MotorInBState(HomingSensor.State());
301}
302//------------------------------------------------------------------------------
303
304/*------------------------------------------------------------------------------
305 * HandleMotorFaults
306 *
307 * Clears motor faults by cycling enable to the motor.
308 * Assumes motor is in fault
309 * (this function is called when motor.StatusReg.MotorInFault == true)
310 *
311 * Parameters:
312 * requires "motor" to be defined as a ClearCore motor connector
313 *
314 * Returns:
315 * none
316 */
317void HandleMotorFaults()
318{
319 SerialPort.SendLine("Handling fault: clearing faults by cycling enable signal to motor.");
320 motor.EnableRequest(false);
321 Delay_ms(3 * TRIGGER_PULSE_TIME);
322 motor.EnableRequest(true);
323 Delay_ms(100);
324}
325//------------------------------------------------------------------------------
void Delay_ms(uint32_t ms)
Blocks operations for ms milliseconds.
Definition SysTiming.h:287
uint32_t Milliseconds(void)
Number of milliseconds since the ClearCore was initialized.
bool MotorModeSet(MotorPair motorPair, Connector::ConnectorModes newMode)
Sets the operational mode for the specified MotorDriver connectors.