Arduinoon perustuva ohjelmoitava kantoraketti

Ajattelin tuossa rakentaa kantoraketin, joka toimii kiinteällä polttoaineella (alumiini jauheen, ammonium perkloraatin ja polyesterihartsin seos), ja jota voisi ohjata servoilla.

Olen opetellut arduinon ohjelmointia noin puoli vuotta ja laitoin itselleni vähän isomman haasteen, joten kirjoitin tuossa ohjelman joka lukee serial portista tietoja, ja laittaa ne muuttujina EEPROM:iin, josta ne haetaan taas servojen ohjausta varten.
Muuttujilla ohjataan kantoraketin neljää servoa, jotka ovat kiinni kantoraketin neljässä ohjaussiivekkeessä.
Raketissa olisi elektroniikkana arduino duemilanove, yhdensuuntainen kiihtyvyysanturi, kolmiakselinen gyroskooppi, korkeusmittari ja mahdollisesti SD kortti, johon nämä tiedot voi halutessaan tallentaa.

En ole vielä tehnyt tälle muuta kuin arduino koodin, mutta varmasti on lisää tulossa…

Sanokaa sitten pliis, jos huomaatte koodissa virheitä, kun oon vaan 14 vuotias…

Tässä koodia:

#include <SD.h>
#include <EEPROM.h>
#include <Servo.h>

Servo servo1;
Servo servo2;
Servo servo3;
Servo servo4;

//SPI SD Kortin Pinnejä
//MOSI = Pin 11
//MISO = Pin 12
//SCLK = PIN 13
int CS_pin = 10;
int pow_pin = 8;
// Kiihtyvyys pinni
int acceleration_pin = 4;
int recovery_pin = 13;
//Korkeus pinni
int altitude_pin = 3;
//Gyro pinnit
int gyro1_pin = 0;
int gyro2_pin = 1;
int gyro3_pin = 2;

//Servo pinnit
int servo1_pin = 11;
int servo2_pin = 10;
int servo3_pin = 9;
int servo4_pin = 6;

//EEPROM osoitteet
int servo_address1 = 3;
int servo_address2 = 4;
int servo_address3 = 5;
int servo_address4 = 6;
int gyro_address1 = 7;
int gyro_address2 = 8;
int gyro_address3 = 9;
//Sytytys pinni
int ignition_pin = 2;

//Servojen kulmat EEPROM:ista
float servo1_position = EEPROM.read(servo_address1);
float servo2_position = EEPROM.read(servo_address2);
float servo3_position = EEPROM.read(servo_address3);
float servo4_position = EEPROM.read(servo_address4);
//Gyroskooppien odotetut kulmat EEPROM:ista
float gyro_angle1 = EEPROM.read(gyro_address1);
float gyro_angle2 = EEPROM.read(gyro_address2);
float gyro_angle3 = EEPROM.read(gyro_address3);

long id = 1; //Tämä antaa SD kortille tallennettaville tiedoille numeron
//*********************************************************************************************
void setup()
{

Serial.begin(9600);
Serial.println(“Valmistellaan korttia…”);
//CS Pin on output
pinMode(CS_pin, OUTPUT);
pinMode(altitude_pin, INPUT);
pinMode(gyro1_pin, INPUT);
pinMode(gyro2_pin, INPUT);
pinMode(gyro3_pin, INPUT);
pinMode(ignition_pin, OUTPUT);
pinMode(recovery_pin, OUTPUT);

//SD kortti ottaa virtaa pinnistä 8, joten kirjoita se 1:si
pinMode(pow_pin, OUTPUT);
digitalWrite(pow_pin, HIGH);

//Valmistellaan korttia
if (!SD.begin(CS_pin))
{
Serial.println(“Kortti ei toimi!”);//Korttia ei välttämättä tarvitse olla, joten jatketaan //ohjelmassa.
}
Serial.println(“Card Ready”);

//Kirjoitetaan tiedostoon otsikko:
File logFile = SD.open(“LOG.csv”, FILE_WRITE);
if (logFile)
{
logFile.println(", , , ,"); //Vedetään tällainen viiva, jotta erotetaan edellinen data uudesta, jos kortilla oli jotain.
String header = “ID, Kiihtyvyys, Korkeus, Gyro1, Gyro2, Gyro3”;
logFile.println(header);
logFile.close();
}
//Määritetään servot joko vaaka tai pystysuora ohjaaviksi antamalla serialin kautta 1, 2, 3 tai4.
Serial.println(“Anna 1, 2, 3 tai 4 määrätäksesi lähtösuunnan”);
while (Serial.available() == 0);
int val = Serial.read() - ‘0’;

if (val == 1)
{//servot 1 ja 2 ohjaavat aina pystysuunnassa:
servo1.attach(servo1_pin);
servo2.attach(servo3_pin);
servo3.attach(servo2_pin);
servo4.attach(servo4_pin);
Serial.flush();
delay(5);}

if (val == 2)
{//servot 3 ja 4 ohjaavat aina vaakasuunnassa
servo1.attach(servo2_pin);
servo2.attach(servo4_pin);
servo3.attach(servo3_pin);
servo4.attach(servo1_pin);
Serial.flush();
delay(5);
}
if (val == 3)
{
servo1.attach(servo3_pin);
servo2.attach(servo1_pin);
servo3.attach(servo4_pin);
servo4.attach(servo2_pin);
}
if (val == 4)
{
servo1.attach(servo4_pin);
servo2.attach(servo2_pin);
servo3.attach(servo1_pin);
servo4.attach(servo3_pin);
}
else
{Serial.println(“Ei tunnisteta!”);
return;
}

Serial.println(“Anna haluttu 1:gyroskoopin asento”);
while (Serial.available() == 0);//Odottaa dataa serialilta.
int gyro_angle1 = Serial.read() - ‘0’;//Asetta saadun arvon muuttujaan gyro_angle1.
EEPROM.write(gyro_address1, gyro_angle1);//Kirjoittaa muuttujan gyro_angle1 osoitteeseen gyro_address1 EEPROM:illa
Serial.flush();//Tyhjentää sarjaportin puskurin
delay(5);//Odottaa 5 ms

{
//Tekee saman kahdelle muulle gyroskoopin akselille
Serial.println(“Anna haluttu 2:gyroskoopin asento”);
while (Serial.available() == 0);
int gyro_angle2 = Serial.read() - ‘0’;
EEPROM.write(gyro_address2, gyro_angle2);
Serial.flush();
delay(5);
}
{
Serial.println(“Anna haluttu 3:gyroskoopin asento”);
while (Serial.available() == 0);
int gyro_angle3 = Serial.read() - ‘0’;
EEPROM.write(gyro_address3, gyro_angle3);
Serial.flush();
delay(5);
}
{//Laitetaan servojen halutut asennot muistiin samalla tavalla, kuin gyroskooppejenkin…
Serial.println(“Anna pystysuunnan ohjaavien siivekkeiden asento (2 kpl) sitten paina enter, ja muista että 90 astetta on 0…”);
while (Serial.available() == 0);//Odottaa dataa serialilta.
int servo1_position = Serial.read() - ‘0’;//Asettaa saadun arvon muuttujaan servo1ja2_position.
EEPROM.write(servo_address1, servo1_position);//Kirjoittaa EEPROM:ille
Serial.flush();//Tyhjentää puskurin
//Tehdään sama kaikille servoille.
delay(5);
while (Serial.available() == 0);
int servo2_position = Serial.read() - ‘0’;
EEPROM.write(servo_address2, servo2_position);
Serial.flush();
delay(5);

Serial.println(“Anna vaakasuunnan ohjaavien siivekkeiden asento”);
while (Serial.available() == 0);
int servo3_position = Serial.read() - ‘0’;
EEPROM.write(servo_address3, servo3_position);
Serial.flush();
delay(5);

while (Serial.available() == 0);
int servo4_position = Serial.read() - ‘0’;
EEPROM.write(servo_address4, servo4_position);
Serial.flush();
delay(5);

}
servo1.write(90);
servo3.write(90);
servo2.write(90);
servo4.write(90);
delay(2000);

digitalWrite(ignition_pin, HIGH); //Odota pari sekuntia, että raketti on kerennyt nousta vähänmatkaa:
delay(2000);
servo1.write(92);
servo2.write(88);
delay(500);
servo3.write(servo3_position);
servo4.write(servo4_position);
delay(500);
servo1.write(servo1_position);
servo2.write(servo2_position);

}
//***********************************************************************************************
void loop()
{
//Tarkistaa asentoaan lennon aikana
int angle1 = analogRead(gyro1_pin);
int angle2 = analogRead(gyro2_pin);
int angle3 = analogRead(gyro3_pin);

// Haluttu arvo - oikea arvo
if (gyro_angle1 > angle1)
{
servo1.write(89);
servo2.write(91);
delay(7);

}

else if (gyro_angle1 < angle1)
{servo1.write(91);
servo2.write(89);
delay(7);}

//Ei tee mitään, kuin asettaa siivekkeet nolla asentoon
if (gyro_angle1 == angle1)
{
servo1.write(90);
servo2.write(90);
delay(3);}
//’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’
{
int altitude = analogRead(altitude_pin);
}
if (gyro_angle2 > angle2)
{
servo3.write(89);
servo4.write(91);
delay(7);

}

else if (gyro_angle2 < angle2)
{servo3.write(91);
servo4.write(89);
delay(7);}
//Ei tee mitään, kuin asettaa siivekkeet nolla asentoon
if (gyro_angle2 == angle2)
{
servo3.write(90);
servo4.write(90);
delay(3);
//’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’
}
if (gyro_angle3 > angle3)
{
servo1.write(89);
servo2.write(89);
servo3.write(89);
servo4.write(89);
delay(2);

}

else if (gyro_angle3 < angle3)
{servo1.write(91);
servo2.write(91);
delay(2);}
//Ei tee mitään, kuin asettaa siivekkeet nolla asentoon
if (gyro_angle3 == angle3)
{
servo1.write(90);
servo2.write(90);
delay(3);}
//’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’
int acceleration_level = analogRead(acceleration_pin);
int G_force = (acceleration_level * 1000 / 512);

if (G_force == 0)
{
delay(3000);
digitalWrite(recovery_pin, HIGH);//Avaa laskuvarjon.
while (Serial.available() == 0);}//Jää tähän jumiin eikä tee enää muuta.
//’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’’
//Käytän CSV Formaattia
int altitude = analogRead(altitude_pin);
String dataString = String(id) + ", " + String(G_force) + ", " + String(altitude) + ", " + String(angle1) + ", " + String(angle2) + “,” + String(angle3);

//Avaa sd kortin kirjoittamista varten
File logFile = SD.open(“LOG.csv”, FILE_WRITE);
if (logFile)
{
logFile.println(dataString);
logFile.close();
//Nosta ID numeroa
id++;
}
delay(5);// Odotetaan 5ms ja ajetaan uudestaan
}

Johan olet koodin kirjoittanut, muuta ite en sano koodiin mitään. Mutta kai olet tutustunut pienoismallirakettien rakenteluun ja niiden käyttöön. Kato vaikka täältä: http://pollux.ayy.fi/rakettiforum/index.php?sid=981b2f3d7f3d41769548ccf4967eb790

Onnea hienosta projektista.

Koodia en uskalla katsoa, mutta toivottavasti toimii. Sellainen softa kuin VMLab. Sillä voi simuloida Atmelia ja ehkä Arduinojakin.

Raketeista…

Raketin polttoaine on räjähdysainetta (siinä on hapetin) ja sen hankkimiseen ja hallussapitoon tarvitaan lupia. Luvat vaativa täysi-ikäisyyttä. Laukaisu on myös luvanvaraista ja lennonjohdot yms. pahastuvat jne. Laukaisuun tarvitset käytännössä vakuutuksen. Maksat itsesi kipeäksi jos tiputat värkin jonkun sata amppeerisen Datsunin päälle. Kalliimpi auto niin lapsenlapsesikin maksavat sitä velkaa.

Mikäli rikokseen yllyttäminen ei olisi rangaistavaa niin neuvoisin seuraavasti:

Nyt kun tiedät reaaliteetit niin tee tämä sitten oikein. Ole neuvokas, kehitä tekniikkaa, testaa, dokumentoi, laukaise korvessa, dokumentoi laukaisu, tule vasta sitten julkisuuteen ja huuda suureen ääneen, että yhteiskunta olet paha, kun estät nuoria ihmisiä toteuttamasta itseään ja haistakaa pitkät. Alan sosiaalipummiksi moisten kieltojen takia, Mutta silti tein sen BUAHAHAHA.

Tee itse mahdollisimman paljon ja kysy fiksummilta neuvoa vain turvallisuuden suhteen. Pääasia, että voit sanoa itse tehneesi.

Mutta noin en voi neuvoa, koska se on väärin. Tutustu rakettiharrastukseen. Jos olet TRE:n lähellä niin kysele TTY:ltä Castorin ihmisiä. Yhdessä se on kivempaa ja porukalla tehtäessä vastuujutut on yleensä kunnossa.

Ai niin. Hapettimet ovat vaarallisia. Omakin elämä muuttui ehkä paremmaksi, kun pääsin yhdyttämään sitä määrissä kuusi vuotta sitten.

Juu… Ajattelin että tohon tulee laskuvarjo, jonka se avaa kun kiihtyvyys tippuu alle yhteen G:hen…

Muista kuitenki varjon aukeminen ei ole 100% tai sitten vaikka aukeekin niin saattaa sorkeutuu narut. Kannattaa lisäksi olla ehkä vara-varjo joka aukeaa jonku ajan kuluttuu kun pää varjon pitäs olla auveta.

Mutta suosittelisin enemmä jotain valmista isohkoa ruutimoottoria mikä on tarkotettu pienoismalliraketteihin ja itse rakentaisi kaiken muun mootorin ympärille. Niitä saa ostettuu kun on hommannut rakettikortin ja tälläin ampumiseen ei tarvita erillisiä lupia, täälä enemmä raketti kortista http://pollux.ayy.fi/raketit.html

Hei!

Koodista pieni kysymys. Minkätakia ohjaat muuttujat EEPROMiin? Eikös se ole aika hidasta?