Modified phase table in stepper.cpp to enable stepping a bipolar motor using a twin H-bridge driver.

Fork of stepper by Kenji Arai

Corrected single-stepping, now walking up or down just one phase table. Compile-time options for driving bipolar motor in any of single-phase, two-phase, or half-stepping. Coils remain engaged at end of specifed movement command - de-energize coils by issuing a motor.move(0) while already stopped.

Committer:
gregeric
Date:
Wed Dec 31 17:36:36 2014 +0000
Revision:
8:75fcbd49d49f
Parent:
4:5b596b405573
Updates and fixes.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
kenjiArai 0:7b0c724fa658 1 /*
kenjiArai 0:7b0c724fa658 2 * mbed library program
kenjiArai 0:7b0c724fa658 3 * Stepping Motor
kenjiArai 0:7b0c724fa658 4 *
kenjiArai 0:7b0c724fa658 5 * Copyright (c) 2014 Kenji Arai / JH1PJL
kenjiArai 0:7b0c724fa658 6 * http://www.page.sannet.ne.jp/kenjia/index.html
kenjiArai 0:7b0c724fa658 7 * http://mbed.org/users/kenjiArai/
kenjiArai 0:7b0c724fa658 8 * Created: August 20th, 2014
kenjiArai 0:7b0c724fa658 9 * Revised: August 23rd, 2014
kenjiArai 0:7b0c724fa658 10 *
kenjiArai 0:7b0c724fa658 11 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
kenjiArai 0:7b0c724fa658 12 * INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE
kenjiArai 0:7b0c724fa658 13 * AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
kenjiArai 0:7b0c724fa658 14 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
kenjiArai 0:7b0c724fa658 15 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
kenjiArai 0:7b0c724fa658 16 */
kenjiArai 0:7b0c724fa658 17
kenjiArai 0:7b0c724fa658 18 #ifndef MBED_STEPPER
kenjiArai 0:7b0c724fa658 19 #define MBED_STEPPER
kenjiArai 0:7b0c724fa658 20
kenjiArai 0:7b0c724fa658 21 #include "mbed.h"
kenjiArai 0:7b0c724fa658 22
kenjiArai 0:7b0c724fa658 23 #define MT_SLOP_STEP 10
kenjiArai 0:7b0c724fa658 24 #define MT_MIN_STEP (MT_SLOP_STEP+MT_SLOP_STEP)
kenjiArai 0:7b0c724fa658 25 #define MT_PLS_WIDTH_MIN 2 // 2mS
kenjiArai 0:7b0c724fa658 26
kenjiArai 1:94f55ebfe2db 27 /** Unipolar Type Stepping Motor Driver using 4 Outputs(DigitalOut) with timer interrupt(Ticker)
kenjiArai 0:7b0c724fa658 28 *
kenjiArai 0:7b0c724fa658 29 * Driver circuit: Low side driver (4ch for one Stepper) e.g. TD62003AP
kenjiArai 0:7b0c724fa658 30 * CAUTION: This is only for Unipolar Type Stepping Motor!
kenjiArai 0:7b0c724fa658 31 * Cannot use for Bipolar Type
kenjiArai 0:7b0c724fa658 32 * Plese refer http://en.wikipedia.org/wiki/Stepper_motor
kenjiArai 0:7b0c724fa658 33 *
kenjiArai 0:7b0c724fa658 34 * @code
kenjiArai 0:7b0c724fa658 35 * #include "mbed.h"
kenjiArai 0:7b0c724fa658 36 * #include "stepper.h"
kenjiArai 0:7b0c724fa658 37 *
kenjiArai 0:7b0c724fa658 38 * #define TIMEBASE 15000 // 15mS
kenjiArai 0:7b0c724fa658 39 *
kenjiArai 0:7b0c724fa658 40 * STEPPER sm(D5, D4, D3, D2);
kenjiArai 0:7b0c724fa658 41 *
kenjiArai 0:7b0c724fa658 42 * uint8_t pls_width[10] = {5, 4, 3, 2, 1, 1, 1, 1, 1, 1 };
kenjiArai 0:7b0c724fa658 43 *
kenjiArai 0:7b0c724fa658 44 * int main() {
kenjiArai 0:7b0c724fa658 45 * sm_r.set_max_speed(TIMEBASE);
kenjiArai 0:7b0c724fa658 46 * sm.move(+100);
kenjiArai 0:7b0c724fa658 47 * while (sm.status){ ;}
kenjiArai 0:7b0c724fa658 48 * sm.move(-1000);
kenjiArai 0:7b0c724fa658 49 * wait(10);
kenjiArai 0:7b0c724fa658 50 * sm.move(0);
kenjiArai 0:7b0c724fa658 51 * while(true){;}
kenjiArai 0:7b0c724fa658 52 * }
kenjiArai 0:7b0c724fa658 53 * @endcode
kenjiArai 0:7b0c724fa658 54 */
kenjiArai 0:7b0c724fa658 55
kenjiArai 0:7b0c724fa658 56 class STEPPER {
kenjiArai 0:7b0c724fa658 57 public:
kenjiArai 1:94f55ebfe2db 58 // Please copy following pls_width[] part in to your main.cpp
kenjiArai 0:7b0c724fa658 59 /** pulse width definition -> Use for start and stop phase
kenjiArai 0:7b0c724fa658 60 * = data * TIMEBASE -> e.g following data = 5 then 5*15000/1000 = 75mS
kenjiArai 0:7b0c724fa658 61 */
kenjiArai 0:7b0c724fa658 62 //uint8_t pls_width[MT_SLOP_STEP] = {5, 4, 3, 2, 1, 1, 1, 1, 1, 1 };
kenjiArai 0:7b0c724fa658 63
kenjiArai 0:7b0c724fa658 64 /** Motor Status */
kenjiArai 0:7b0c724fa658 65 enum MOTOR_STATE { M_STOP = 0, M_UP, M_CONTINUE, M_DOWN, M_CHANGE, M_UNKOWN = 0xff};
kenjiArai 0:7b0c724fa658 66
kenjiArai 0:7b0c724fa658 67 /** Configure data pin
kenjiArai 0:7b0c724fa658 68 * @param data SDA and SCL pins
kenjiArai 0:7b0c724fa658 69 */
kenjiArai 0:7b0c724fa658 70 STEPPER (PinName xp, PinName xn, PinName yp, PinName yn);
kenjiArai 0:7b0c724fa658 71
kenjiArai 0:7b0c724fa658 72 /** Move steps
kenjiArai 0:7b0c724fa658 73 * @param number of steps
kenjiArai 0:7b0c724fa658 74 * @return none
kenjiArai 0:7b0c724fa658 75 */
kenjiArai 0:7b0c724fa658 76 void move (int32_t steps);
kenjiArai 0:7b0c724fa658 77
kenjiArai 0:7b0c724fa658 78 /** Set time period (max speed of stepper)
kenjiArai 0:7b0c724fa658 79 * @param time: e.g. 10mS(=10000) -> 100 PPS(Puls per Sec)
kenjiArai 0:7b0c724fa658 80 * @return none
kenjiArai 0:7b0c724fa658 81 */
kenjiArai 0:7b0c724fa658 82 void set_max_speed (uint32_t time_base_us);
kenjiArai 0:7b0c724fa658 83
kenjiArai 0:7b0c724fa658 84 /** Check status
kenjiArai 0:7b0c724fa658 85 * @param none
kenjiArai 0:7b0c724fa658 86 * @return running(= 1), stopped(= 0)
kenjiArai 0:7b0c724fa658 87 */
gregeric 8:75fcbd49d49f 88 //surely other states can be returned too eg UP, CONTINUE, CHANGE, DOWN?
kenjiArai 0:7b0c724fa658 89 uint8_t status (void);
gregeric 8:75fcbd49d49f 90
gregeric 8:75fcbd49d49f 91 /** De-energize coils
gregeric 8:75fcbd49d49f 92 * @param none
gregeric 8:75fcbd49d49f 93 * @return none
gregeric 8:75fcbd49d49f 94 */
gregeric 8:75fcbd49d49f 95 void stop();
gregeric 8:75fcbd49d49f 96
kenjiArai 0:7b0c724fa658 97
kenjiArai 0:7b0c724fa658 98 protected:
kenjiArai 0:7b0c724fa658 99 // Rotation Direction
kenjiArai 0:7b0c724fa658 100 enum { D_CCW = -1, D_UNKOWN = 0, D_CW = 1};
kenjiArai 0:7b0c724fa658 101
kenjiArai 0:7b0c724fa658 102 typedef struct{
kenjiArai 0:7b0c724fa658 103 int8_t direction;
kenjiArai 0:7b0c724fa658 104 uint32_t total_step;
kenjiArai 0:7b0c724fa658 105 } Motor_Inf;
kenjiArai 0:7b0c724fa658 106
kenjiArai 0:7b0c724fa658 107 typedef struct{
kenjiArai 0:7b0c724fa658 108 uint8_t state;
kenjiArai 0:7b0c724fa658 109 int8_t direction;
kenjiArai 0:7b0c724fa658 110 uint8_t up_cnt;
kenjiArai 0:7b0c724fa658 111 uint8_t up_cnt_keep;
kenjiArai 0:7b0c724fa658 112 uint8_t down_cnt;
kenjiArai 0:7b0c724fa658 113 uint8_t change_cnt;
kenjiArai 0:7b0c724fa658 114 uint8_t pls_width;
kenjiArai 0:7b0c724fa658 115 uint8_t ongoing;
kenjiArai 0:7b0c724fa658 116 uint32_t continue_cnt;
gregeric 4:5b596b405573 117 uint8_t motor_step; //keeps track of phase only, no need of uint32_t
kenjiArai 0:7b0c724fa658 118 } Motor_Control;
kenjiArai 0:7b0c724fa658 119
kenjiArai 0:7b0c724fa658 120 DigitalOut _xp, _xn, _yp, _yn;
kenjiArai 0:7b0c724fa658 121 Ticker _smdrv;
kenjiArai 0:7b0c724fa658 122
gregeric 8:75fcbd49d49f 123 void set4ports (void);
kenjiArai 0:7b0c724fa658 124 void setup_mtr_drv_dt(Motor_Inf *mi, Motor_Control *mt);
kenjiArai 0:7b0c724fa658 125 void millisec_inteval();
kenjiArai 0:7b0c724fa658 126
kenjiArai 0:7b0c724fa658 127 private:
kenjiArai 0:7b0c724fa658 128 uint8_t busy_sm_drv;
kenjiArai 0:7b0c724fa658 129 Motor_Inf inf;
kenjiArai 0:7b0c724fa658 130 Motor_Control cntl;
kenjiArai 0:7b0c724fa658 131
kenjiArai 0:7b0c724fa658 132 };
kenjiArai 0:7b0c724fa658 133
kenjiArai 0:7b0c724fa658 134 #endif // MBED_STEPPER