Introduction: Radio Controlled Electric Hovercraft

Picture of Radio Controlled Electric Hovercraft

This instructable is about the build of a Radio Controlled Electric Hovercraft.

I have been attempting to build model hovercraft since i was at school, and its only in the last few years that i have manged to get a really successful one running.

I know there are different approaches to making hovercraft and i will state right now that this model is definitely NOT the most simple model, but it is very successful and relatively quick. Another consideration to whether you attempt this model or not, is the electronic control of the Forward/Steering fans. I developed a mixer which takes in the two channel radio pulses and gives out the lift enable, and both forward fans which also control steering. I have used a Arduino Nano for this task, but if this is something you don't want to do then you could use a digital 6 channel radio and use a mix to control the two rear fans?

The Arduino Nano has turned out to be very useful and linked to a MPU-6050 very accurate. The options you could include are entirely up to your own imagination.

Step 1: The Hull. Cutting Out the Deck and Balsa Bulkheads.

Picture of The Hull. Cutting Out the Deck and Balsa Bulkheads.

The main part of this model is the hull. It is made from 3mm plywood and 3mm balsa.

Because i buy the wood in 2 by 1 foot sheets i use two sheets to make the top deck. Follow the plans and watch the video for instructions on how to make this model.

But to start with cut out then join the two half of the top deck giving a length of 600mm and width of 380mm. the corners are cut off at 45 degrees measuring in 111.3mm from both sides to make them the same length as the front and back, this means when you come to make the skirt you will only need to make two different sizes one pattern will cover the front back and corners and another pattern will cover the sides.

So before you get carried away with this model, now is the opportunity to take you time and mark out where all the bulkheads will go, again follow the drawing and accurately mark out the position of each bulkhead and once you are happy you can then add the inner frame work. When cutting out the inner frame you can cut out the bits in pairs, and before you separate the pairs check fit the ply goes nicely in the slots. Test fit the inner section and if happy it fits nicely over the hole then glue the bits together and glue down to the deck.

Now start the tedious part of cutting out all the bulkheads. you can see in the pictures that there are 5 different lengths and i use two different patterns. one pattern (called short) is used to make all the bulkhead which when fitted to the deck make a right angle to the edge. The "LONG" parts are used where the bulkheads are joined in the corners and hence at an angle of 67.5 because these bits are at an angle the length of the part increases and so does the length of the angle which is why i use two patterns. the patterns are made from 1/16 ply wood and i cut the balsa using a scalpel. in all cases the grain is longways.

Step 2: The Hull. Glueing the Bulkheads.

Picture of The Hull. Glueing the Bulkheads.

So by this stage you should have cut out all the bulkheads. i believe there are 32 in total.

next to cut out is the strips which go along the sides and on the top (bottom upside down). the bits which go along the side should be cut to match the pen marks on the deck. And the strips which go on top will be fitted in lastly after all other bits are in place.

So using the strips to hold the bulkheads in place (but don't glue the strips) glue the side and front and back bulkheads down to the deck. at this point i don't add the "LONG" corner bulkheads.

Once the sides and front and back have dried then you can add the corners again use the strips to hold the bulkheads in the correct place but don't glue the strips at this time.

Once you are happy with the corners you can then add the final "LONG" bulkheads into the corners.

Next you can add all the side strips which should fit nicely in the bulkhead slots and butt up in the corners.

At this stage i let everything set over night, before in the morning cutting the final top strips to size and glue them before i went to work.

Now you should have all bulkheads and strips in place.

Step 3: The Hull. Add the Side Sheeting.

Picture of The Hull. Add the Side Sheeting.

Before we add the side sheeting i like to reinforce the edge with 1/4" balsa, this is because the edge (below the air holes) takes a lot of punishment. So once the strips are glued in the next step is to carefully sand down all the sides so the sheeting will sit flush. I do the sanding with a "permaGrit" sanding block and a piece of sand paper glued to a long piece of wood. If you are two rough with the sanding you could end up breaking the bulkheads.

I start by adding the sides and front and back. I cut the balsa to overlap the edges and sand down once the glue has set.

Once the sides and front/back are done and sanded i then add the 4 corners.

When all off these have set i then spend a little time sanding all the sides and edges flush.

The next stage is crucial to getting the skirt correct. You need to mark out where a ply strip will be added to the top (bottom) to allow the skirt to be screwed to it.

To mark this out you need to make sure you measure from the edges of the deck and measure along the bulkheads 57.3mm in. this is where the ply strip will start and the 15mm width will go on the inside.

When you have accurately marked out the position of the strips then you can measure the length of the strips and cut them out. in my case the corners and front and back were 110mm long and the sides were 330mm.

Glue the strips into place and allow the glue to set. Once the glue has set, clean off any glue residue from the bulkheads and then fit all the remaining sheeting.

Step 4: The Hull. Final Sanding and Optional Fibreglass Covering.

Picture of The Hull. Final Sanding and Optional Fibreglass Covering.

Once all the glue has set you can then spend some time sanding all the edges.

In my case i have chosen to cover the hull with a light weight fiberglass cloth (180g per square meter). This is an extra stage and not necessary, but i mainly use my model on water and it tends to lead a hard life at the hands of my 6 year old son!

So to fiberglass, firstly cut out the required size of cloth making sure you leave a good over hang around all sides. Then mix up the resin approximately 1.5 times the weight of the cloth (it shouldn't need that much but its best to have spare then not enough)

Then paint the resin to the hull and lay the cloth on top then carefully go over the whole area to "wet" out the cloth adding more resin where needed.

Leave to go off and try and trim the extra off while the fiberglass is still green (not quite hard but gone off)

Then when finally set clean up all the edges.

And that is the hull complete!

Step 5: Lift Fan Build.

Picture of Lift Fan Build.

The lift fan was designed to slot into the front and then slide forward to latch into place. The design has been done with the consideration that you will you the same EDF as me. this 65mm EDF can be brought from BigDotUncle and comes complete with the brushless motor. you will need to find a 30A ESC

65mm EDF

There really isn't much to say about this part of the build! the front lift fan is a very simple part to make, just print out the drawings check the drawings have printed out the correct size, stick the drawings to 3mm ply and cut out the bits!

When you come to glue all the parts together test to check that the unit fits in the front hole before gluing. And when you do glue the bits together you should be able to locate the unit into the fan hole to hole all the parts correctly. Just make sure you don't stick the lift fan into the hole!

Finish the front fan by gluing balsa bits underneath the two horizontal bit and at the front as shown in the photos.

Step 6: The Skirt Design

Picture of The Skirt Design

This bit gets a tad complicated,

But hopefully with the drawings I should be able to make it clear. You can see from the section drawing that the skirt is based on ¾ (270°) of a 57.3mm radius circle, the skirt is attached as shown at the leading edge of the deck under the red ply strip and the bottom is sandwiched in between the hull and ply. These two points are 57.3mm down and in from each other, meaning the pivot for the skirt is easy to see. (A right angle) Firstly it’s easy to work out how deep each section needs to be. (The length around the skirt)

270°/360° * (2*57.3) * PI = 270mm

I choose 57.3mm radius because it makes the drawing out easy, 57.3mm radius will mean 5mm per 5° around the circumference.

So now you should work out the number of points around the edge you wish to draw, I choose to do a point every 5° for the above reason.

As an example take the measurement needed at 60mm down (or 60°), looking at the drawing the key dimension we need is dimension “B” if you want you can just draw it as I have and then measure it. The key thing to realise is that dimension happens at 60° from the top mount or if you wish 60mm down the circumference of the skirt..

Distance down skirt at 60° = 60°/360° * 2 * 57.3 * PI = 60.00mm

The measurement can be done mathematically in which case you need to know dimension “C” you can see that you have a right angle triangle with an angle of 60° and the hypotenuse is the radius I.E 57.3mm and the dimension “C” is opposite.

So opposite (C) = SIN 60° * 57.3 = 49.62mm.

Now you have dimension “C” you work out what "B" is. The angle is always going to be the same which is 22.5° (half the 45° corner angle).

So opposite (B) = TAN 22.5° * 49.62 = 20.55mm.

So just to clarify the two values you need (for each point) are the distance down from the top skirt mount which (due to the 57.3mm radius) is 40mm and the dimension “B”. I should point out that I did a spread sheet with all values ranging from 0° to 270° in steps of 5° which as explained means 5mm steps on a piece of graph paper.

Step 7: Superstructure

Picture of Superstructure

So this hovercraft was initially designed to seat a Action man, so the central structure is sized to fit one. The back of the seat forms part of the rear fan mounts, with a EDF mounted each side.

So once the bits were cut out, test fit them all to make sure they are not to tight, then mark out where the central unit should go at the front and rear of the central hole then glue the two sides and two parts of the rear fan mounts into place. you should be able to see i have added some spacers to keep everything aligned.

Once those are glued add the bottom of the seat the front and back also the tops of the fan mounts. All 3mm ply.

Then add the top of the back of the seat and doublers to the fan mounts, just 10mm deep to allow for where the screws will fit.

And the last bit of this part is to make up the small triangle sections to allow the lower halve of the EDF to screw down.

Have a look at all the pictures as i think i have covered most bits.

The last bit i made was the cover which fits over the batteries. there is nothing special about this bit, you should be able to print the side sections from the plan and then add the top and dash sections from 60mm wide ply. to make a lip for the top to fit i put strips of 1/16" ply on the sides of the central structure.

And as a finishing touch i have added a handle bar for the action man to hold, and this is made from a small length of 3/16" brake pipe and an M4 allen head bolt.

Step 8: Electronics

Picture of Electronics

This part of the project turned into a epic journey! I originally had the hovercraft working using a Microchip PIC and it worked very well, but i wanted to add more features and the pic only had 6 GPIO so i needed something bigger. So i decided to use an Arduino Nano.

So what does it do?

Firstly the Nano times the two pulses from the receiver, the first is the steering and the second is the throttle. both pulses should be set up to give 1.0ms at lowest throttle and left and should go up to 2.0ms for max throttle and right. the neutral should be 1.5ms.

Secondly the hover POT is checked, and formatted to give out a pulse to the lift fan ESC.

And lastly the main purpose is to sets the left and right fans depending on the steering and throttle.

I have however added more bits to the Nano, this includes another POT to change gyro settings, a row of LED's to allow the status to be displayed and finally and most importantly a MPU-6050 combined gyro and accelerometer which is used as a very effective gyro.

The program for this task grew and grew and will probably continue to grow and be improved, however at the moment i am pleased with what i have so will put the program on here and if anyone wants to change it and personalise it then it's up to them.

so i will now go through all parts of the program and try my best to explain them!

In the setup we do all the normal stuff, but importantly set up the MPU-6050, and then get average off-set value to use in the program.
  accelgyro.initialize();
  accelgyro.setDLPFMode(2);
  //0 = 256, 1 = 188, 2 = 98, 3 = 42, 4 = 20, 5 = 10, 6 = 5. in Hz so 5 is slowest.
  accelgyro.setFullScaleGyroRange(1);
  //0 = +/- 250 degs/sec | 1 = +/- 500 degs/sec | 2 = +/- 1000 degs/sec | 3 =  +/- 2000 degs/sec  
  Serial.begin(115200);
  Serial.println("Obtaining Gyro Offset in Z axis");
  for (int i = 1; i < 33; i = i + 1)
    {
      accelgyro.getRotation(&gx, &gy, &gz);
      sumgz = sumgz + gz;
      Serial.print(i);
      Serial.print("\t");
      Serial.print("GZ = ");
    }
  sumgz = sumgz>>5;
  Serial.print("Offset  GZ = ");
  Serial.println(sumgz);

Also in the setup i have set up the interrupt for the failsafe. This turned out to be pointless in most cases, as modern systems have failsafes built into the receivers.
  noInterrupts();           // disable all interrupts
  TCCR1A = 0;
  TCCR1B = 0;
  TCNT1 = FST;            // preload timer 65536-16MHz/256/2Hz
  TCCR1B |= (1 << CS11);
  TIMSK1 |= (1 << TOIE1);   // enable timer overflow interrupt
  interrupts();             // enable all interrupts
while i am on the failsafe, as you can see below the interrupt is short and basically toggles the LED13 and set the failsafe flag to "true"
ISR(TIMER1_OVF_vect)        // interrupt service routine that wraps a user defined function supplied by attachInterrupt
{
  TCNT1 = FST;            // preload timer with Fail Safe Time
  digitalWrite(FSLED, toggle);
  toggle = !toggle;
  failSafe = true;
}

I am not going to go through the whole program but i will have a look at the main bits. The start of the main program is to read the receiver pulses. and whilst this might seem easy, it took a while to get it right. It turns out that receivers from different manufacturers do things differently with regards to timing. The hobbyking wheel tx/receiver sends out the steering pulse then as soon as it ends sends the throttle straight after with no gap. so the program starts the second timer as soon as the steering pulse has finished, then checks if the throttle has actually gone high, or if its still low? This might seem strange but a different transmitter/receiver (my older Acoms 2.4Ghz set) has a gap in between the two pulses.

The other bits in this section allow for the gyro gain to be adjusted depending on the amount of steering. When you are not steering you want the maximum amount of gyro action, however when you are giving it max steering them you don't want the gyro to try and stop the spin!
void getReceiverInputs()
{
  while ((digitalRead(RxThro) == LOW)&&(failSafe == false))
  {
  }
  Time1 = micros();
  while ((digitalRead(RxThro) == HIGH)&&(failSafe == false))
  {
  }
  Time2 = micros();
  Time3 = micros();
  if (digitalRead(RxSter) == LOW)
  {
    while (digitalRead(RxSter) == LOW)
    {
    }
    Time3 = micros();
  }
  while ((digitalRead(RxSter) == HIGH)&&(failSafe == false))
  {
  }
  Time4 = micros();
  RxSterTime = Time2 - Time1; // should be a time 1000 - 2000ms
  RxThroTime = Time4 - Time3;
  totalTime = Time4 - Time1;
  cycleTime = Time1 - oldTime;
  oldTime = Time1;
  if (RxSterTime < centerSter - deadZone) // 1500 - 20 = 1480
  {
    if (RxSterTime < 1000)
    {
      RxSterTime = 1000;
    }
    RxSterTimeGyro = RxSterTime - 1000;// should be a number 0 - 500
    RxSterTimeGyro = RxSterTimeGyro >> 4;
  }
  else if (RxSterTime > centerSter + deadZone) // 1500 + 20 = 1520
  {
    if (RxSterTime > 2000)
    {
      RxSterTime = 2000;
    }
    RxSterTimeGyro = 2000 - RxSterTime;// should be a number 0 - 500
    RxSterTimeGyro = RxSterTimeGyro >> 4;
  }
  else
  {
    RxSterTimeGyro = 31;
  }
}

This next section is the part that has grown the most! it started simple then had to grow to accommodate all the options. This is mainly because the ESC's can go backwards. This means you have loads of possibilities. For example if the hovercraft is going forward, it could be going forward left, forward right or just forward straight! Then i had to do the same for backwards as initially when i tried just a left and right program it worked going forward but when i went backwards the steering was the wrong way around! And lastly i had to add a NOT going forward section because i have got use to controlling the original hovercraft slowly by just using the steering and no throttle.
void doCalcs()
{
  if (failSafe == false)//failsafe not activated, normal mode
  {
    strip.setPixelColor(3,0,20,0);//middle two leds to green
    strip.setPixelColor(4,0,20,0);
    strip.show();
    TCNT1 = FST; //reset the failsafe timer
    digitalWrite(FSLED, LOW);
    if (RxThroTime > 1520 || RxThroTime < 1480)
    {
      hoverTime = 0;
    }
    else
    {
      hoverTime = hoverTime + 1;
    }
    if (hoverTime > 1500)//time in normal mode to allow the hovering to stop on no throttle movement
    {
      liftESC = minVal;
      hoverTime = 1501;
      strip.setPixelColor(1,0,20,0);//not hovering
      strip.setPixelColor(6,0,20,0);
      strip.show();
    }
    else{
      liftESC = hoverHight + 1000; 
      strip.setPixelColor(1,0,0,0);
      strip.setPixelColor(6,0,0,0);
      strip.show();
    }
    if (RxThroTime > (centerThro + deadZone))// forwards, deadzone is 20 
    {
      RxSterTime = RxSterTime + gz;
      if (RxSterTime > (centerSter + deadZone))// create a dead zone around the steering
      {
        int temp = RxSterTime - centerSter;
        rightESC = RxThroTime - temp;
        leftESC = RxThroTime + temp;
      }  
      else if (RxSterTime < (centerSter - deadZone))
      {
        int temp = centerSter - RxSterTime;
        rightESC = RxThroTime + temp;
        leftESC = RxThroTime - temp;
      }
      else
      {
        leftESC = RxThroTime;
        rightESC = RxThroTime;
      }
    }
    else if (RxThroTime < (centerThro - deadZone))// backwards
    {
      RxSterTime = RxSterTime - gz;
      if (RxSterTime > (centerSter + deadZone))// backwards steer left?
      {
        int temp = RxSterTime - centerSter;
        rightESC = RxThroTime + temp;
        leftESC = RxThroTime - temp;
      }  
      else if (RxSterTime < (centerSter - deadZone))// backwards steer right?
      {
        int temp = centerSter - RxSterTime;
        rightESC = RxThroTime - temp;
        leftESC = RxThroTime + temp;
      }
      else// backwards straight
      {
        leftESC = RxThroTime;
        rightESC = RxThroTime;
      }
    }
    else// no throttle.
    {
      RxSterTime = RxSterTime + gz;
      if (RxSterTime > (centerSter + deadZone))
      {
        int temp = RxSterTime - centerSter;
        //rightESC = RxThroTime - temp;
        leftESC = RxThroTime + temp;
      }
      else if (RxSterTime < (centerSter - deadZone))
      {
        int temp = centerSter - RxSterTime;
        rightESC = RxThroTime + temp;
        //leftESC = RxThroTime - temp;
      }
      else
      {
        rightESC = 1500;
        leftESC = 1500;
      }
    }
    maxMin();
  }
  else
  {
    strip.setPixelColor(3,50,0,0);
    strip.setPixelColor(4,50,0,0);
    strip.show();
    digitalWrite(FSLED, HIGH);//failsafe activated use failsafe values
    liftESC = hoverHight + 1000;
    leftESC = 1500;
    rightESC = 1500;
    TCNT1 = FST;
  }
}

Step 9: The Whole Program.

Picture of The Whole Program.

/* latest

version started 15/01/2017

* this has the newest full scale code and filter code

* gyro code has been added and a no gyro option if pot = 0

* forward and reverse have been corrected.

* no gyro is included in the dead zone

* add gyro in neutral and steering

* change gyro sense in forward only

* added varible gyro gain depending on steering amount

* added no throttle steering but forward only and include gyro

*/

#include "Adafruit_NeoPixel.h"

#include "I2Cdev.h"

#include "MPU6050.h"

#if I2CDEV_IMPLEMENTATION == I2CDEV_ARDUINO_WIRE

#include "Wire.h"

#endif

MPU6050 accelgyro;

#define RxThro 2

#define RxSter 3

#define rightFan 7

#define leftFan 6

#define liftFan 5

#define FSLED 13

#define period 12

#define hoverPOT A1

#define gyroPOT A2

volatile boolean failSafe = false;

int RxThroTime;

int RxSterTime;

int RxSterTimeGyro;

int hoverHight;

int centerSter = 1500;

int centerThro = 1500;

int deadZone = 20;

int rightESC = 1000;

int leftESC = 1000;

int liftESC = 1000;

int minVal = 1000;

int maxVal = 2000;

int FST = 15000;

int maxMinValue = 1000;

int hoverTime = 0;

int gyroGain;

int i = 0;

int16_t gx, gy, gz;

int sumgz;

unsigned long Time1 = 0;

unsigned long Time2 = 0;

unsigned long Time3 = 0;

unsigned long Time4 = 0;

unsigned long totalTime =0;

unsigned long oldTime =0;

unsigned long cycleTime =0;

boolean toggle = false;

boolean toggle2 = false;

Adafruit_NeoPixel strip = Adafruit_NeoPixel(8 , 17, NEO_GRB + NEO_KHZ800);

void setup()

{

strip.begin();

stripColour(0,0,0,1);

stripColour(50,0,0,30);

stripColour(0,0,0,1);

stripColour(0,50,0,30);

stripColour(0,0,0,1);

stripColour(0,0,50,30);

stripColour(0,0,0,1);

#if I2CDEV_IMPLEMENTATION == I2CDEV_ARDUINO_WIRE

Wire.begin();

#elif I2CDEV_IMPLEMENTATION == I2CDEV_BUILTIN_FASTWIRE

Fastwire::setup(400, true);

#endif

#define OUTPUT_READABLE_ACCELGYRO

accelgyro.initialize();

accelgyro.setDLPFMode(2);

//0 = 256, 1 = 188, 2 = 98, 3 = 42, 4 = 20, 5 = 10, 6 = 5. in Hz so 5 is slowest.

accelgyro.setFullScaleGyroRange(1);

//0 = +/- 250 degrees/sec | 1 = +/- 500 degrees/sec | 2 = +/- 1000 degrees/sec | 3 = +/- 2000 degrees/sec

Serial.begin(115200);

pinMode(RxThro, INPUT);

pinMode(RxSter, INPUT);

pinMode(FSLED, OUTPUT);

pinMode(rightFan, OUTPUT);

pinMode(leftFan, OUTPUT);

pinMode(liftFan, OUTPUT);

Serial.println("Obtaining Gyro Offset in Z axis");

for (int i = 1; i < 33; i = i + 1)

{

accelgyro.getRotation(&gx, &gy, &gz);

sumgz = sumgz + gz;

Serial.print(i);

Serial.print("\t");

Serial.print("GZ = ");

Serial.print(gz);

Serial.print("\t");

Serial.print("GY = ");

Serial.print(gy);

Serial.print("\t");

Serial.print("GX = ");

Serial.println(gx);

}

sumgz = sumgz>>5;

Serial.print("Offset GZ = ");

Serial.println(sumgz);

noInterrupts(); // disable all interrupts

TCCR1A = 0;

TCCR1B = 0;

TCNT1 = FST; // preload timer 65536-16MHz/256/2Hz

TCCR1B |= (1 << CS11);

TIMSK1 |= (1 << TOIE1); // enable timer overflow interrupt

interrupts(); // enable all interrupts

}

ISR(TIMER1_OVF_vect) // interrupt service routine that wraps a user defined function supplied by attachInterrupt

{

TCNT1 = FST; // preload timer with Fail Safe Time

digitalWrite(FSLED, toggle);

toggle = !toggle;

failSafe = true;

}

void getReceiverInputs()

{

while ((digitalRead(RxThro) == LOW)&&(failSafe == false))

{

}

Time1 = micros();

while ((digitalRead(RxThro) == HIGH)&&(failSafe == false))

{

}

Time2 = micros();

Time3 = micros();

if (digitalRead(RxSter) == LOW)

{

while (digitalRead(RxSter) == LOW)

{

}

Time3 = micros();

}

while ((digitalRead(RxSter) == HIGH)&&(failSafe == false))

{

}

Time4 = micros();

RxSterTime = Time2 - Time1; // should be a time 1000 - 2000ms

RxThroTime = Time4 - Time3;

totalTime = Time4 - Time1;

cycleTime = Time1 - oldTime;

oldTime = Time1;

if (RxSterTime < centerSter - deadZone) // 1500 - 20 = 1480

{

if (RxSterTime < 1000)

{

RxSterTime = 1000;

}

RxSterTimeGyro = RxSterTime - 1000;// should be a number 0 - 500

RxSterTimeGyro = RxSterTimeGyro >> 4;

}

else if (RxSterTime > centerSter + deadZone) // 1500 + 20 = 1520

{

if (RxSterTime > 2000)

{

RxSterTime = 2000;

}

RxSterTimeGyro = 2000 - RxSterTime;// should be a number 0 - 500

RxSterTimeGyro = RxSterTimeGyro >> 4;

}

else

{

RxSterTimeGyro = 31;

}

}

void doCalcs()

{

if (failSafe == false)//failsafe not activated, normal mode

{

strip.setPixelColor(3,0,20,0);//middle two leds to green

strip.setPixelColor(4,0,20,0);

strip.show();

TCNT1 = FST; //reset the failsafe timer

digitalWrite(FSLED, LOW);

if (RxThroTime > 1520 || RxThroTime < 1480)

{

hoverTime = 0;

}

else

{

hoverTime = hoverTime + 1;

}

if (hoverTime > 1500)//time in normal mode to allow the hovering to stop on no throttle movement

{

liftESC = minVal;

hoverTime = 1501;

strip.setPixelColor(1,0,20,0);//not hovering

strip.setPixelColor(6,0,20,0);

strip.show();

}

else{

liftESC = hoverHight + 1000;

strip.setPixelColor(1,0,0,0);

strip.setPixelColor(6,0,0,0);

strip.show();

}

if (RxThroTime > (centerThro + deadZone))// forwards, deadzone is 20

{

RxSterTime = RxSterTime + gz;

if (RxSterTime > (centerSter + deadZone))// create a dead zone around the steering

{

int temp = RxSterTime - centerSter;

rightESC = RxThroTime - temp;

leftESC = RxThroTime + temp;

}

else if (RxSterTime < (centerSter - deadZone))

{

int temp = centerSter - RxSterTime;

rightESC = RxThroTime + temp;

leftESC = RxThroTime - temp;

}

else

{

leftESC = RxThroTime;

rightESC = RxThroTime;

}

}

else if (RxThroTime < (centerThro - deadZone))// backwards

{

RxSterTime = RxSterTime - gz;

if (RxSterTime > (centerSter + deadZone))// backwards steer left?

{

int temp = RxSterTime - centerSter;

rightESC = RxThroTime + temp;

leftESC = RxThroTime - temp;

}

else if (RxSterTime < (centerSter - deadZone))// backwards steer right?

{

int temp = centerSter - RxSterTime;

rightESC = RxThroTime - temp;

leftESC = RxThroTime + temp;

}

else// backwards straight

{

leftESC = RxThroTime;

rightESC = RxThroTime;

}

}

else// no throttle.

{

RxSterTime = RxSterTime + gz;

if (RxSterTime > (centerSter + deadZone))

{

int temp = RxSterTime - centerSter;

//rightESC = RxThroTime - temp;

leftESC = RxThroTime + temp;

}

else if (RxSterTime < (centerSter - deadZone))

{

int temp = centerSter - RxSterTime;

rightESC = RxThroTime + temp;

//leftESC = RxThroTime - temp;

}

else

{

rightESC = 1500;

leftESC = 1500;

}

}

maxMin();

}

else

{

strip.setPixelColor(3,50,0,0);

strip.setPixelColor(4,50,0,0);

strip.show();

digitalWrite(FSLED, HIGH);//failsafe activated use failsafe values

liftESC = hoverHight + 1000;

leftESC = 1500;

rightESC = 1500;

TCNT1 = FST;

}

}

void pixels()

{

if (leftESC > (1500 + deadZone))

{

int a = (leftESC - 1500 - deadZone)/2;

if (a>255){

a = 155;

}

strip.setPixelColor(2,0,0,a);

}

else if(leftESC < (1500 - deadZone))

{

int a = (1500 - leftESC + deadZone)/2;

if (a>255){

a = 155;

}

strip.setPixelColor(2,a,0,0);

}

else

{

strip.setPixelColor(2,0,10,0);

}

if (rightESC > (1500 + deadZone))

{

int a = (rightESC - 1500 - deadZone)/2;

if (a>255){

a = 155;

}

strip.setPixelColor(5,0,0,a);

}

else if(rightESC < (1500 - deadZone))

{

int a = (1500 - rightESC + deadZone)/2;

if (a>255){

a = 155;

}

strip.setPixelColor(5,a,0,0);

}

else

{

strip.setPixelColor(5,0,10,0);

}

strip.show();

}

void outputESC()

{

digitalWrite(rightFan, HIGH);

delayMicroseconds(rightESC);

digitalWrite(rightFan, LOW);

digitalWrite(leftFan, HIGH);

delayMicroseconds(leftESC);

digitalWrite(leftFan, LOW);

digitalWrite(liftFan, HIGH);

delayMicroseconds(liftESC);

digitalWrite(liftFan, LOW);

}

void getPOTs()

{

hoverHight = analogRead(hoverPOT);

gyroGain = analogRead(gyroPOT);

}

void getGyroValue()

{

accelgyro.getRotation(&gx, &gy, &gz);

}

void formatGyro()

{

gyroGain = gyroGain >> 5;

gz = gz - sumgz;

gz = (gz >> 5);

if (gyroGain > 0)//having zero allows you to turn off the gyro

{

gz = gz * RxSterTimeGyro; //varible depending on amount of steering

gz = gz >> 5;

}

else

{

gz = 0;

}

}

void MaxMin()

{

if (RxSterTime > 2000)

{

RxSterTime = 2000;

}

if (RxSterTime < 1000)

{

RxSterTime = 1000;

}

}

void maxMin()

{

if (leftESC > maxVal){

leftESC = maxVal;

}

if (leftESC < minVal){

leftESC = minVal;

}

if (rightESC > maxVal){

rightESC = maxVal;

}

if (rightESC < minVal){

rightESC = minVal;

}

}

void stripColour(int Red, int Green, int Blue, int A)

{

for(i=0; i

{

strip.setPixelColor(i,Red,Green,Blue);

delay(A);

strip.show();

}

delay(A*4);

}

void loop()

{

failSafe = false;

getReceiverInputs();

getPOTs();

getGyroValue();

formatGyro();

doCalcs();

pixels();

outputESC();

//serialOut();

digitalWrite(period, toggle2);

toggle2 = !toggle2;

TCNT1 = FST;

}

Comments

allangee (author)2017-11-20

Awesome job on the instructable. I especially appreciate the skirt instructions -- this has always been lacking in other projects that I've looked up, and the one thing that's kept me from trying a hovercraft.

This may be enough to finally get me started on one!

mr_fid (author)allangee2017-11-26

Thanks for your comment, I will try and find up my spreadsheet with the calculations. all you needed to do was put in the height and number of sides and it would calculate the sections. You still needed to plot out the numbers onto graph paper, and it was always based on 270degress, but was time saving.

KennyS65 (author)2017-11-21

While in highschool and college I actually asked my math teacher for real life senarios that someone would need to know pi and sin. He had no idea but you were able to describe your formulas and actually be interesting at the same time. Perfect. If I was to build it, I'd have a manual control option cause I hate relying on electronics while on the water.

mr_fid (author)KennyS652017-11-26

Glad you were able to understand the maths! it was a hard part to describe!

And for your information the first model i built (Before the electronics) was based on the two rear motors fitted on top of servos, it worked really well and gave maximum sideways action. going in a straight line was nearly impossible.

Swe_tloving (author)2017-11-21

Congratulations on a job well done! Selection of fabrics, patterns to distribute air flow and fans for the right air pressure is a challenging process. Even the method to connect it all together can take months just to find the right solution. If there is any area I would like to see you improve would be more control while operating the craft. I would love to see how fast it can go. Great job, I love it!!!

mr_fid (author)Swe_tloving2017-11-26

I will get a video together. Basically i mainly use it down a lake, but on a carpark it is very quick. The only issue i then had was it blowing over!

mr_fid (author)2017-11-26

Thanks for all the nice comments, Sorry for my delay in responding, i have been on 12 hour night shifts!

PaulA23 (author)2017-11-26

Wow. That's really the only word that didn't escape me while reading... Just WOW... :-)
You built a seaworthy vessel using "old-school" scratch-build aircraft techniques, and did an AMAZING job... Building ANY hovercraft from scratch is no easy task - no matter what method is used - due to the multiple required functions, since it's basically an aircraft on the ground, but you have made it look easy.
These are the kinds of posts that make me go pull out my RC projects & have fun again, because they're like a turbo boost to my imagination!!
Thank you for this VERY inspiring instructable, & I can't wait to see what upgrades & modifications you implement next! :-)

JohnC430 (author)2017-11-24

wonderful job. well done. congratulations and thanks for sharing

57thcork (author)2017-11-21

Hi. Fantastic project and very well described, however you refer to printing out drawings and I can't seem to find where they are. Otherwise a great instructible. Thanks.

inconceivable1 (author)2017-11-20

cool!

gm280 (author)2017-11-20

Nice combination of multiple skills. Great project. Thumbs Up!

sandilya.anisetty (author)2017-11-19

It's amazing. I'm gonna try this...

About This Instructable

6,811views

135favorites

License:

Bio: I love making things. I have for as long as I can remember liked to make stuff. Now days I have two kids (Thomas and ... More »
More by mr_fid:Radio Controlled Electric Hovercraft  Release Hook for Quadcopter (The Flying Beaver Called Pig!)Simple Quadcopter, Basic Tools Only.
Add instructable to: