Recevoir une donnée

Dependencies:   mbed

Files at this revision

API Documentation at this revision

Comitter:
MoussOudj
Date:
Thu Jun 14 07:04:14 2018 +0000
Commit message:
Recevoir une seule donn?e

Changed in this revision

PCA9685.cpp Show annotated file Show diff for this revision Revisions of this file
PCA9685.h Show annotated file Show diff for this revision Revisions of this file
definitions.h Show annotated file Show diff for this revision Revisions of this file
main.cpp Show annotated file Show diff for this revision Revisions of this file
mbed.bld Show annotated file Show diff for this revision Revisions of this file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/PCA9685.cpp	Thu Jun 14 07:04:14 2018 +0000
@@ -0,0 +1,167 @@
+#ifndef PCA9685_LIBRARY_CPP
+#define PCA9685_LIBRARY_CPP
+
+
+#include "mbed.h"
+#include "PCA9685.h"
+#include "definitions.h"
+
+
+PCA9685::PCA9685(uint8_t i2c_address, I2C i2c_object, float frequency) :
+
+    i2c_addr(i2c_address),
+    freq(frequency),
+    i2c(i2c_object)
+
+{
+
+}
+
+void PCA9685::init(void)
+{
+
+    reset();
+
+    uint8_t prescale = (uint8_t) (OSC_CLOCK / (4096 * PWM_SCALER * freq)) - 1;
+
+    write_8(MODE1, 0x21); //0010 0001 : AI ENABLED
+    write_8(MODE2, 0x07); //0000 0111 : NOT INVRT, CHANGE ON STOP, TOTEM POLE, \OE = 1, LEDn = HIGH IMP
+
+    set_prescale(prescale);
+
+}
+
+void PCA9685::reset(void)
+{
+
+    write_8(MODE1,0x00);
+
+}
+
+void PCA9685::set_prescale(uint8_t prescale)
+{
+
+    uint8_t oldmode = read_8(MODE1);
+    uint8_t newmode = (oldmode&0x7F) | 0x10; // set the sleep bit
+
+    write_8(MODE1, newmode); // send the device to sleep
+    wait_ms(5);
+    write_8(PRESCALE, prescale); // set the prescaler
+    write_8(MODE1, oldmode);
+    wait_ms(5);
+    write_8(MODE1, oldmode | 0xa1); // wake up the device
+
+}
+
+
+//NB REQUIRES AUTO-INCREMENT MODE ENABLED
+//0 <= pwm_output <= 15
+//0 <= (count_on || count_off) <= 4095
+void PCA9685::set_pwm_output(int pwm_output, uint16_t count_on, uint16_t count_off)
+{
+
+    char msg[5];
+
+    msg[0] = LED0_ON_L + (4 * pwm_output);
+    msg[1] = count_on;
+    msg[2] = count_on >> 8;
+    msg[3] = count_off;
+    msg[4] = count_off >> 8;
+
+    i2c.write(i2c_addr, msg, 5);
+
+}
+
+void PCA9685::set_pwm_output_on_0(int pwm_output, uint16_t count_off)
+{
+
+    char msg[3];
+
+    msg[0] = LED0_ON_L + 2 + (4 * pwm_output);
+    msg[1] = count_off;
+    msg[2] = count_off >> 8;
+
+    i2c.write(i2c_addr,msg,3);
+
+}
+
+
+//NB REQUIRES AUTO-INCREMENT MODE ENABLED
+//0 <= pwm_output <= 15
+void PCA9685::set_pwm_duty(int pwm_output, float duty_cycle)
+{
+
+    if (duty_cycle > 1.0) {
+        duty_cycle = 1.0;
+    }
+    if (duty_cycle < 0.0) {
+        duty_cycle = 0.0;
+    }
+
+    uint16_t count_off = (uint16_t) (duty_cycle * 4095);
+    uint16_t count_on = 0x0000;
+
+    set_pwm_output(pwm_output, count_on, count_off);
+
+}
+
+
+//NB REQUIRES AUTO-INCREMENT MODE ENABLED
+//0 <= pwm_output <= 15
+void PCA9685::set_pwm_pw(int pwm_output, float pulse_width_us)
+{
+
+    float period_us = (1e6/freq);
+
+    float duty = pulse_width_us/period_us;
+
+    set_pwm_duty(pwm_output, duty);
+
+}
+
+
+void PCA9685::update(void)
+{
+
+    i2c.stop();
+
+}
+
+
+
+void PCA9685::write_8(uint8_t reg, uint8_t msg)
+{
+
+    char send[2]; //Store the address and data in an array
+    send[0] = reg;
+    send[1] = msg;
+    i2c.write(i2c_addr, send, 2);
+
+}
+
+uint8_t PCA9685::read_8(uint8_t reg)
+{
+
+    char send[1] ;
+    send[0] = reg;
+    i2c.write(i2c_addr, send, 1);
+    char recieve[1];
+    i2c.read(i2c_addr, recieve, 1);
+    return recieve[0];
+
+}
+
+int PCA9685::convert_pwm_value(float pulse_width_us, float period_us)
+{
+
+    int result;
+    float interim;
+
+    interim = ((pulse_width_us / period_us) * 4095); //scale the pulse width to a 12-bit scale
+    result = (int) interim; //round the value to the nearest integer
+
+    return result;
+
+}
+
+#endif
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/PCA9685.h	Thu Jun 14 07:04:14 2018 +0000
@@ -0,0 +1,32 @@
+#ifndef PCA9685_LIBRARY_H
+#define PCA9685_LIBRARY_H
+
+#include "mbed.h"
+#include "definitions.h"
+
+
+class PCA9685 {
+    
+    public:
+        PCA9685(uint8_t i2c_addr, I2C i2c_object, float frequency);
+        void init(void);
+        void set_pwm_output(int pwm_output, uint16_t count_on, uint16_t count_off);
+        void set_pwm_output_on_0(int pwm_output, uint16_t count_off);
+        void set_pwm_duty(int pwm_output, float duty_cycle);
+        void set_pwm_pw(int pwm_output, float pulse_width_us);
+        void update(void);
+        
+    private: 
+        void reset(void);
+        void write_8(uint8_t reg, uint8_t msg);
+        uint8_t read_8(uint8_t reg);
+        void set_prescale(uint8_t prescale);
+        int convert_pwm_value(float pulse_width_us, float period_us);
+    
+    private:
+        int i2c_addr;
+        float freq;
+        I2C i2c;
+};        
+
+#endif
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/definitions.h	Thu Jun 14 07:04:14 2018 +0000
@@ -0,0 +1,24 @@
+#ifndef PCA9685_LIBRARY_DEFINITIONS_H
+#define PCA9685_LIBRARY_DEFINITIONS_H
+
+#define ADDR 0x80
+
+#define MODE1 0x0
+#define MODE2 0x1
+#define PRESCALE 0xFE
+
+#define LED0_ON_L 0x6
+#define LED0_ON_H 0x7
+#define LED0_OFF_L 0x8
+#define LED0_OFF_H 0x9
+
+#define ALLLED_ON_L 0xFA
+#define ALLLED_ON_H 0xFB
+#define ALLLED_OFF_L 0xFC
+#define ALLLED_OFF_H 0xFD
+
+#define OSC_CLOCK 25e6
+
+#define PWM_SCALER 0.90425 //set by manual calibration - ratio of FREQUENCY_SET:ACTUAL_OUTPUT
+
+#endif
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Thu Jun 14 07:04:14 2018 +0000
@@ -0,0 +1,148 @@
+#include "mbed.h"
+#include "PCA9685.h"
+
+
+Serial xbee(PA_9, PA_10);
+DigitalOut myled(LED1);
+Serial pc(USBTX,USBRX);
+I2C i2c_PCA(PB_9, PB_8); // Utilisation et déclaration d'un port I2C pour communiquer avec la carte PWM Adafruit
+PCA9685 PCA_SERVO(ADDR, i2c_PCA, 50); 
+
+uint8_t text_xbee[21];
+uint8_t idx_carac_xbee_in = 0;
+uint8_t send_measure = 0;
+
+
+/*
+void irq_xbee(void){ // Fonction d'interruption qui agit dès qu'une mesure est arrivée
+    text_xbee[idx_carac_xbee_in] = xbee.getc();
+    send_measure = 1; // Une mesure est reçu, on met donc le flag à 1
+    idx_carac_xbee_in =  (idx_carac_xbee_in+1) % 5;
+    
+}*/
+
+
+//Phalanges doigt 0 // Définitions de chaque servomoteur sur chaque doigt. Le doigt 0 correspond à l'index, et les servos se suivent de haut en bas. M0 est donc le servo de la base du doigt, et M3 le servomoteur le plus haut
+#define D0M1 0x00 // On attribue à chaque servomoteur une adresse sur laquelle on enverra l'ordre d'angle
+#define D0M2 0x01 // Ces adresses correspondent à des ports de la carte PWM Adafruit
+#define D0M3 0x02
+#define D0M0 0x03
+
+//Phalanges doigt 1 // Définitions de chaque servomoteur du doigt majeur
+#define D1M1 0x04
+#define D1M2 0x05
+#define D1M3 0x06
+#define D1M0 0x07
+
+//Phalanges doigt 2 // Définitions de chaque servcomoteur de l'annulaire
+#define D2M1 0x08
+#define D2M2 0x09
+#define D2M3 0x0A
+#define D2M0 0x0B
+
+//Phalanges doigt 3 // Définitions de chaque servomoteur de l'auriculaire
+#define D3M1 0x0C
+#define D3M2 0x0D
+#define D3M3 0x0E
+#define D3M0 0x0F
+
+int i = 0;
+
+
+
+void angle(int moteur, int valeur){ // Fonction qui envoie les données au servomoteur correspondant
+        
+    valeur = valeur * 10;// Mise en forme correspondant
+    valeur = valeur + 1100;//  Ajout de l'offset
+    
+    if(valeur >= 2400) // On borne les données reçues
+    {
+        valeur = 2400;
+    }
+    if(valeur <= 1100)
+    {
+        valeur = 1100;
+    }
+    
+    PCA_SERVO.set_pwm_pw(moteur, valeur); // Puis on envoie au moteur
+}
+
+
+
+
+
+
+
+
+
+
+int main() {
+    
+    int i = 0;
+    
+    pc.baud(115200);
+    xbee.baud(9600);
+     //xbee.attach(&irq_xbee);
+     
+     
+     
+     
+     PCA_SERVO.init(); //Initialisation des servomoteurs
+    for(i=0;i<=15;i++){ // On met tous les servomoteurs dans une position qui équivaut à la position de repos
+        PCA_SERVO.set_pwm_output_on_0(i, 0);
+    }
+    
+    
+    
+    /*angle(D1M1, ); // Les valeurs sont différentes les unes des autres car les servomoteurs ne sont pas tous identiques et ils prennent de la place, ils se décalent donc un peu
+    angle(D1M2, 35);
+    angle(D1M3, 35);*/
+     
+    /* for(i;i<10;i++){
+     
+     angle(4,80);
+     
+     wait(2);
+     
+      angle(4,20);
+      }*/
+  
+    int test;
+    
+    /*
+         for(i = 0 ;i<10;i++){
+     
+     angle(4,120);
+     
+     wait_ms(100);
+     
+      angle(4,30);
+      }*/
+    
+    while(1) {
+        
+      
+      
+      
+            
+        
+        test = xbee.getc();
+        //pc.printf("%d \r\n",test);
+        
+    
+       
+       /*angle(D1M1, text_xbee[1]); 
+       angle(D1M2, text_xbee[1]); 
+       angle(D1M3, text_xbee[1]);*/
+       
+       angle(4, test);
+       /*angle(D1M2, test);
+       angle(D1M3, test);*/
+       
+       /*PCA_SERVO.set_pwm_duty(4, 0.5);
+       
+        wait_ms(20);
+        
+       PCA_SERVO.set_pwm_duty(4, 0.1);*/
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mbed.bld	Thu Jun 14 07:04:14 2018 +0000
@@ -0,0 +1,1 @@
+https://os.mbed.com/users/mbed_official/code/mbed/builds/5aab5a7997ee
\ No newline at end of file