This class library has been created for use with the Apeiros Robot by Abe Howell's Robotics.

/media/uploads/abotics/apeiros_gripper_10-04-2014.jpg

Apeiros is a low cost, flexible and entirely open source, educational mobile robot that has been designed for everyone by Abe Howell's Robotics, http://www.abotics.com. With an optional gripper mechanism Apeiros can manipulate objects and perform more advanced robotic tasks and experiments. Sensory expansion has been designed into this robot, so that you can add sensors as they are needed. I created Apeiros so that you can get hit the ground running in the wonderful world of robotics!

My Apeiros class library is released as open source under General Public License (GPL) Version 3, http://www.gnu.org/licenses/gpl-3.0.html, so please feel free to use and modify however you see fit.

Check out my Apeiros page for more information.

Below is an example main.cpp file that uses the Apeiros class library.

The Apeiros constructor passes a Serial transmit, tx, and receive, rx, PinName along with left and right motor PWM offsets. I am designing my wireless shield to use PA_9 for tx and PA_10 for rx. For now simply use the built-in USB serial connection by specifying SERIAL_TX & SERIAL_RX. No two gear motors will begin to rotate at the same PWM level, so I have allowed for the specification of a leftMotorPwmOffset and a rightMotorPwmOffset parameter. These values correspond to the PWM level that starts the respective motor rotating. You can determine these values by simply passing zero for the left and right PWM offsets. Then connect with Tera Term and issue the open-loop move command, MOxxx,yyy\r, where xxx is left motor speed and yyy is right motor speed (MO120,115\r). Simply vary the left and right motor speeds until you find the level at which each motor begins to rotate.These values will be the PWM motor offsets that need to be passed to the Apeiros constructor.

main.cpp

#include "mbed.h"
#include "Apeiros.h"

Apeiros apeiros(SERIAL_TX, SERIAL_RX,120,115);

int main() {
    
    apeiros.Begin();
    
    while(1) {
        
        if (apeiros.IsSerialDataAvailable()) apeiros.ParseUartData();
        
        // Add your custom code below//
                
    }
}

Below is a simple obstacle avoidance program that uses sensory input from a front left and front right IR sensor. The front left sensor's OUT pin must be connected to PC_15 and the front right sensor's OUT pin to PC_13 on the Nucleo F401RE's Morpho header.

main.cpp

#include "mbed.h"
#include "Apeiros.h"

Apeiros apeiros(SERIAL_TX, SERIAL_RX,100,100);

int main() {    
    apeiros.Begin();
    while(1) {
        int sensorState = 2*apeiros.leftFrontIR.read();
        sensorState += apeiros.rightFrontIR.read();
        
        switch (sensorState) {
            case 0:
              apeiros.SetMotorSpeed(-65,-65);
              apeiros.SetBuzzerTone(5);
              break;              
            case 1:
              apeiros.SetMotorSpeed(65,-65);
              apeiros.SetBuzzerTone(50);
              break;
            case 2:
              apeiros.SetMotorSpeed(-65,65);
              apeiros.SetBuzzerTone(30);
              break;              
            case 3:
              apeiros.SetMotorSpeed(65,65);
              apeiros.SetBuzzerTone(0);
              break;             
            default:
              apeiros.SetMotorSpeed(0,0);
              break;
        }        
        wait_ms(100);
    }

Apeiros.h

Committer:
abotics
Date:
2014-12-16
Revision:
2:71ede4f26f71
Parent:
1:8edccfd4646a
Child:
3:c61c3feb0729

File content as of revision 2:71ede4f26f71:

/** Apeiros Robot class.
 *  Used for developing programs for the Apeiros Robot by Abe Howell's Robotics.
 *
 * Example:
 * @code
 * #include "mbed.h"
 * #include "Apeiros.h"
 *
 * Apeiros apeiros(SERIAL_TX, SERIAL_RX, 120, 120);
 * 
 * int main() {
 *     apeiros.Begin();
 *      while(1)
 *     {
 *        if (apeiros.IsSerialDataAvailable()) apeiros.ParseUartData();
 *     }
 * }
 * @endcode
 */

#ifndef MBED_APEIROS_H
#define MBED_APEIROS_H
 
#include "mbed.h"
 
#define Dwh 2.621       // wheel diameter
#define PI 3.14159      // PI
#define Cwh (Dwh * PI)  // wheel circumference
#define TSCALE 10       // convert to 10ths of an inch
#define INVTICK 4883    // this is 1 / 204.8 us, to avoid using floating point math
#define NCLKS 128       // number of encoder clocks per wheel rotation
#define Ktps ((Cwh * TSCALE * INVTICK) / NCLKS)
#define MaxMotorSpeed 255

#define MIN_GRIPPER_PULSE 1000
#define MAX_GRIPPER_PULSE 2300

#define MAX_BUZZER_PWM 100

/** Create Apeiros class
     *
     * @param Apeiros class
     *
     */
 
class Apeiros : public Serial{

public:

    /** Create Apeiros instance
    *
    * @param tx specified as PinName of UART Tx pin. Use SERIAL_TX as default.
    * @param rx specified as PinName of UART Rx pin. Use SERIAL_RX as deafult.
    * @param leftMotorPwmOffset specified as integer value from 0-150. Use 120 as default.
    * @param rightMotorPwmOffset specified as integer value from 0-150. Use 120 as default.
    */
    Apeiros(PinName tx, PinName rx, int leftMotorPwmOffset, int rightMotorPwmOffset);
    
    /** Begin using Apeiros class. Must be called before using class functions.
     *
     */
    void Begin(void);
    
    /** Is Serial data available to be parsed.
     *
     * @returns
     *   1 if serial data is available,
     *   0 if no serial data has been received
     */
    bool IsSerialDataAvailable(void);
    
    /** Parse available serial UART data.
     *
     */
    void ParseUartData(void);
    
    /** Set piezo buzzer tone.
     *
     * @param buzzerTone specified as an integer value(int) from 0-100.
     */
    void SetBuzzerTone(int buzzerTone);
    
    /** Set left and roght motor speeds.
     *
     * @param leftMotorSpeed specified as an integer value(int) from 0-150, rightMotorSpeed specified as an integer value(int) from 0-150.
     */
    void SetMotorSpeed(int leftMotorSpeed, int rightMotorSpeed);
    
    /** Set servo gripper position.
     *
     * @param pulseWidth_us specified as an integer value(int) from MIN_GRIPPER_PULSE(1000) to MAX_GRIPPER_PULSE(2300).
     */
    void SetGripperPosition(int pulseWidth_us);
    
    /** Return integer count for left wheel encoder.
     *
     * @returns
     *   Integer value for left wheel encoder count.
     */
    int GetLeftEncoder(void);
    
    /** Return integer count for right wheel encoder.
     *
     * @returns
     *   Integer value for right wheel encoder count.
     */
    int GetRightEncoder(void);
    
    /** Reset both left & right wheel encoder counts.
     *
     */
    void ResetWheelEncoders(void);
    
    DigitalIn leftFrontIR;
    DigitalIn centerFrontIR;
    DigitalIn rightFrontIR;
    
    AnalogIn ad_0;
    AnalogIn ad_1;
    AnalogIn ad_2;
    AnalogIn ad_3;
    AnalogIn ad_4;
    AnalogIn ad_5;
    

    
private:

    DigitalOut _buzzerOut;

    DigitalOut _SN_3A;
    DigitalOut _SN_4A;

    DigitalOut _SN_2A;
    DigitalOut _SN_1A;

    DigitalIn _leftEncoderDirPin;
    DigitalIn _rightEncoderDirPin;
    
    InterruptIn _leftEncoderClk;
    InterruptIn _rightEncoderClk;
    
    PwmOut _rightMotorPWM;
    PwmOut _leftMotorPWM;
    PwmOut _gripperPWM;
    
    Ticker _motorControl;
    
    volatile char rxBuff[16];
    volatile char rxBuffIndx;
    volatile char tmpRxBuff[16];
    volatile bool uartDataRdy;
    
    volatile int motorUpdateTickCount;
    volatile int motionLoopCount;
    
    volatile int leftEncoderCount;
    volatile int rightEncoderCount;
    volatile bool leftEncoderDir;
    volatile bool rightEncoderDir;
    volatile int leftMotorOffset;
    volatile int rightMotorOffset;
    
    volatile unsigned short analogIndex;
    volatile float adSensors[6];
    volatile int analogUpdateCount;
    
    volatile char encoderArrayIndex_L, encoderArrayIndex_R;
    volatile int encoderPeriodArray_L[4], encoderPeriodArray_R[4];
    volatile int encoderPeriod_L, encoderPeriod_R, encoderPeriodSum_L, encoderPeriodSum_R;
    volatile int prevT3Count_L, prevT3Count_R;
    volatile bool encoderUpdated_L, encoderUpdated_R;
    volatile int encoderSpeed_L, encoderSpeed_R;
    
    // Buzzer Variables //
    volatile int buzzerPeriod;
    volatile int buzzerDuty;
    volatile int buzzerTick;
    volatile bool enableBuzzer;

    void getUartData(void);
    void motorControlISR(void);
    void leftEncoderTick(void);
    void rightEncoderTick(void);
    
    void ParseMotorCommand(void);
    void ParseBuzzerCommand(void);
    void ParseGripperCommand(void);
    void CalculateWheelSpeed(void);
    void Initialize(void);

};
 
#endif