SensorBil

Projekt av Borhan, Thai, Butrint, Karim

Sammanfattning

Detta projekt är baserat på konstruktionen av en C-kodad bil där funktionaliteten påverkas av en sensor. Arbetet har gått ut på att bygga en maskin med tillhandahållna komponenter där komponenterna som kodats för bilens önskade funktionalitet är hjulen, en servomotor och en ultrasonic sensor. Komponenterna är kodade i Atmel Studio 7 med processorn ATmega1284. Kodningen ser till att bilen fungerar enligt önskat, vilket är att den kör enligt bestämd hastighet och svänger när ett hinder finns framför den. Ultrasonic sensorn ser till att inget hinder finns framför den. Skulle det finnas så vänds sensorn med hjälp av servomotorn för att se åt vilket håll bilen ska svänga utan att träffa på ett nytt hinder. Resultatet av allt detta, är en miniatyr av en självkörande bil.

Resultat

Bilen fungerar som planerat och fungerar enkelt beskrivet, på så sätt att den kör rakt fram tills att ultrasonic sensorn utför sin uppgift av att känna av ett hinder eller vägg inom ett visst avstånd. När ett hinder dykt upp går servomotorn igång och styr ultrasonic sensorn så att den “kollar runt” för att se om den kan köra först till höger som är en programmerad prioritet. Skulle det däremot finnas ytterligare ett hinder till höger om bilen så kommer den att kolla till vänster för att se om rutten är mer optimal. Skulle det däremot ej fungera och den kommit till en återvändsgränd, så kommer bilen att vända sig helt och hållet. Själva körandet av bilen som vi kodade, fungerar som planerat, nämligen att vi ska kunna styra bland annat hastigheten och riktningen av de enskilda motorerna. Varje motor har två pins som input och genom att antingen sätta en till pwm och en till noll lyckades vi åstadkomma vad som syns på bild 6.

Kopplingsschema

Källkod

                    #include 
                    #include 
                    #include 
                    #define F_CPU 1000000UL
                    #include 
                    
                    
                    volatile uint8_t distance;
                    
                    #define SERVO_CONTROL 6
                    #define PWM_MOTOR_A1 7
                    #define PWM_MOTOR_A2 6
                    #define PWM_MOTOR_B1 3
                    #define PWM_MOTOR_B2 4
                    #define DISTANCE_SENSOR_PIN PA0
                    
                    
                    
                    void car_init(){
                        //DDRA = 0b00000000;
                    
                        DDRD |= (1 << PWM_MOTOR_A1) | (1 << PWM_MOTOR_A2);
                        DDRB |= (1 << PWM_MOTOR_B1) | (1 << PWM_MOTOR_B2) | (1 << SERVO_CONTROL);
                    }
                    
                    void rightWheel_pwm_init(){
                    
                    TCCR0A |= (1 << COM0A1) | (1 << WGM01) | (1 << WGM00); 
                    TCCR0B |= (1 << CS01);
                    }
                    void leftWheel_pwm_init(){
                        //DDRD = 0xff; //pd6 och pd7
                          TCCR2A |= (1 << COM2A1) | (1 << WGM21) | (1 << WGM20); // Set Fast PWM mode with TOP = 0xFF, and set OC2A on compare match
                          TCCR2B |= (1 << CS21);
                    }
                    void rightWheel_set_speed(int speed){
                     OCR0A = speed;
                    }
                    
                    void leftWheel_set_speed(int speed){
                        OCR2A = speed;// Set the top value (period) for Timer/Counter2 using OCR2A
                    }
                    
                    void drive_forward(int speed){
                        rightWheel_set_speed(speed);
                        leftWheel_set_speed(speed);
                    }
                    
                    
                    
                    void servoInit()
                    {
                        // Configure Timer/Counter3 (TCCR3) for Fast PWM mode
                        TCCR3A = (1 << COM3A1) | (1 << WGM31) | (1 << WGM30);
                        TCCR3B = (1 << WGM33) | (1 << WGM32) | (1 << CS31) | (1 << CS30); // Prescaler 64
                    
                        ICR3 = 39999;
                        DDRB |= (1 << PINB6);
                    }
                    
                    void setServoPosition(uint8_t angle)
                    {
                    
                        OCR3A = angle; 
                        _delay_ms(15); 
                    }
                    
                    
                    
                    
                    void ultrasonicInit() {
                        // Set trigger pin as output
                        DDRD |= (1 << PIND0);            // trig pin PD0
                    
                        // Set echo pin as input
                        DDRD &= ~(1 << PIND2);
                        // Enable external interrupt INT0
                        EIMSK |= (1 << INT0);
                        // Set INT0 to trigger on raising edge (Echo signal)
                        EICRA |= (1 << ISC00) | (1 << ISC01);
                    
                    }
                    
                     void  ultrasonicTrigger() {
                    
                        //// Send a 10us pulse on the trigger pin
                        PORTD |= (1 << PIND0);
                        _delay_us(10);
                        PORTD &= ~(1 << PIND0);
                        TCNT3 = 0;
                        TCCR3B |= (1 << CS32) |  (1 << CS30);
                    }
                    
                        //ISR(INT0_vect) {
                            //TCCR3B &= ~(1 << CS32) |  (1 << CS30);
                            //distance = TCNT3;
                            //TCNT3 = 0;
                            //ultrasonicTrigger();
                            //
                        //}
                    
                    
                    void carControl()
                    {
                        // Reduce speed
                        rightWheel_set_speed(50);
                        leftWheel_set_speed(50);
                        _delay_ms(2000);
                        //Turn left
                        rightWheel_set_speed(0);
                        leftWheel_set_speed(50);
                        _delay_ms(1000);
                        //Turn left
                        rightWheel_set_speed(50);
                        leftWheel_set_speed(0);
                        _delay_ms(1000);
                        //Stop
                        rightWheel_set_speed(0);
                        leftWheel_set_speed(0);
                        _delay_ms(2000);
                        // Reduce speed
                        rightWheel_set_speed(50);
                        leftWheel_set_speed(50);
                        _delay_ms(1000);
                        // high speed
                        rightWheel_set_speed(100);
                        leftWheel_set_speed(100);
                        _delay_ms(2500);
                    }
                    
                    
                    
                    int main() {
                        //Ultrasonic
                        //ultrasonicInit();
                        //sei();
                        //
                           car_init();
                           servoInit();
                    
                           rightWheel_pwm_init();
                           leftWheel_pwm_init();
                           drive_forward(130);
                           _delay_ms(500);
                    
                              
                        while (1) {
                            carControl();
                                //setServoPosition(0);
                                //_delay_ms(1000);
                                //
                                //// Move to 90 degrees
                                //setServoPosition(90);
                                //_delay_ms(1000);
                                //
                                //// Move to 180 degrees
                                //setServoPosition(180);
                                //_delay_ms(1000);
                        }
                        return 0;
                    }