PIC Mixer

A word of caution. I don't advocate building this like this now. With the evolution of hobbyist microcontrollers, I'd now do this in a higher-level language - and did exactly that for Mark 2D

In order to control the fans and thrust reversers of the Mark 2B, I have built and programmed an on-board mixer for the radio control, using a microcontroller programmed in assembly. Conceptually, it's similar to a V-tail or delta mixer, but while they have two inputs and two outputs, mine has four inputs and four outputs, various configuration options set by switches on the mixer, and some status lights.


There were two ideas feeding into the concept.

Firstly, I preferred the use of fairly small diameter thrust fans (as on Mk 1 and Mk 2A hovercraft). With two fans, it's possible to steer by controlling the balance of propulsion. That is, you can turn right by generating more thrust on the left side, much like a tank or bulldozer steers by driving one track faster then the other.

This steering is easily achieved in radio control by means of a v-tail or delta mixer. Many transmitters have such a mix built-in, or you can buy cheap, small modules to do it on-board. They have two inputs and two outputs. If you call the inputs A and B, one output is A+B, and one is A-B. For the steering set up, you connect the speed channel to A, and the steering to B. This is how Mark 1 and Mark 2A worked, and you can see the mixer resting on the battery in the picture to the right.

You can add gyro stabilisation to this simply by putting a gyro on the steering channel between the receiver and the V-tail mixer.

The second idea is derived from the observation that it's generally accepted that hovercraft don't have brakes, and don't reverse.

In theory, you can get some degree of braking or reverse by running the thrust propeller backwards. However, this is difficult to achieve and inefficient. Most engines either only run in one direction. Even if you have a reversing engine, propellers are generally more efficient running in the direction they are intended for. I don't have figures, but I'd guess 4 or 5 times the thrust when running 'correctly'. (One of the tricks for test flights of a free-flight engine model is after the first test glides, to fit the propeller backwards so you get some thrust, but only a little.) Therefore, generally you don't bother with the complexity of reversing gearboxes or electrics when all you're going to get is 20% power. There are a few hovercraft that do have thrust propellers that will reverse - the US marines LCAC being one, but I only found out about that after I had built the Mk2B.

It would be nice to have a hovercraft that did have brakes and reverse, at near full power. Such a propulsion system would also make the steering method described above sharper.

Design Goals

The primary ones, arising from the discussion above:

Secondary ones, from other considerations:


From the concept set out above, my solution was to use fans running forwards only, with a mechanical arrangement of deflectors and ducts to redirect the thrust to achieve reversing. Simple!


The detail is not quite so simple. The logic goes like this:

Two propulsion units, each of which has variable speed fan (but always forwards) and variable deflector/duct arrangements. The deflector need not actually be proportional - it could simply switch from one limit to the other, but it's easiest to use a standard servo as an actuator, so it may as well be proportional.

Therefore, I need at least four outputs from the mixer - two speed controls, and two deflector servos.

The maths behind the mixing is as follows:

As an example:

The gates on the thrust reversers would therefore look like this:

Some added complexity is that I didn't want the gates slamming back and forth when the thrust is very small (that is, suppose you go from 1% forwards to 1% backwards - I don't want that to need the deflector to travel from one limit to the other. Therefore, the deflector moves across smoothly over a third of the thrust values. That is, at +33% thrust the deflector is full forwards, at -33% it's full reverse, and in between it's linear.

Combined with that, I thought it would be better if the fans never stopped entirely while the hovercraft is flying. Therefore, if the thrust calculations comes out at less than some critical (but low) value the fans actually sit at a minimum speed where they're spinning but not generating much thrust. This is mainly cosmetic (and for the entertainment of coding it). Theoretically, it might help brushless motors, which (theoretically) can pause before starting up from rest, but I don't know how significant that really is.

As described in the hardware discussion (below) I had some spare inputs available, so I added a couple of features. The mixer monitors (but does not alter) the lift fan channel. When the lift motor is below about half the speed needed to lift off, the mixer centres the deflectors and switches the fans off. This means that if you want to stop fast, you can cut the lift and although momentum drags the hovercraft along the ground, at least the fans aren't making it worse. I also thought it would look good for the fans to spin up automatically as the hovercraft lifts off into the hover. Finally, it is also a safety measure, since otherwise the fans would never stop.

The fourth available input has been used for various things in the evolution of the code. Originally, I had the idle setting (now hard-coded into the software) set by this input, so you could change the idle speed of the fans from the transmitter. However, that's not actually very useful. In the second version, I tried adjusting the gyro influence by controlling the gain channel from the mixer on the basis of the speed and a gain channel sent from the transmitter, so the input was the gain channel from the receiver and there was a fifth output which was gain channel to the gyro. However, that doesn't actually give the effect I wanted - I wanted the gyro not to interfere at low speeds but this arrangement just means you don't get any steering at low speeds! Now, the gyro contribution is adjusted by having both the 'raw' steering from the transmitter and the modified steering from the gyro fed to the mixer, and it uses one or other (or some combination) as appropriate.

In the final implementation, the fourth input is the output from the gyro, and (depending upon various configuration switch settings) the mixer uses one of 5 different combinations of inputs 1 and 4. In order of increasing thrust:


Hardware was bound to be a PIC microcontroller from Microchip, since that's the only microcontroller I had any experience with. They give away an IDE and lots of technical literature from their web site, and they're readily available (Maplin, Farnell) which is the reason I chose PIC when I first wanted to dabble with microcontrollers.

The selection of the particular PIC to use was governed by:

From that set of requirements, I chose a PIC16F870:

The hardware is set up with i/o arranged as described in the source code:
; uses 16F870 PIC
; timing requires a 4 MHz instruction cycle, so must be 16 MHz crystal
; Has four inputs and four outputs which work on standard
; radio control PWM servo instructions, ie a pulse of
; 1 to 2 mS at a  rate of 50 Hz.
; note that my futaba T6EXA and R136F seem to use pulses
; with absolute range 1.0-2.1 mS,
; with untrimmed sticks 1.14-1.96, centred 1.55
; ie, centred is 1.55 and full through 0.41 either way
; repeat rate is 54.3 Hz
; (all values determined with uncalibrated oscilloscope - may be a bit iffy)
; PWM IO are on portb
; The inputs use interrupt-on-change
; function for timing purposes, so bits 0-3 are output,
; bits 4-7 inputs.
; RB7   steering input (RC channel 1)
; RB6   speed input (RC channel 2)
; RB5   lift fan speed (RC channel 3)
; RB4   gyro output (ie, RC channel 1 fed through gyro)
; RB3   first fan speed
; RB2   first gate
; RB1   second fan speed
; RB0   second gate
; Status indicators show for speed and turn inputs when at
; extremes of travel (red or green LED respectively) and when
; centred (both LEDs lit).  These are on RA0 - RA3
; RA0 = red, RA1 = green ; RA2 = red, RA3 = green
; RC6 and RC7 are left spare on the off-chance that they
; might be used for serial comms in future.
; At this time they are connected to test pins, so can
; be used for diagnostic outputs
; All other ports used for on-board configuration by dip switch:
; 1 - RC4 - 1=gyro switching suppressed (so either always on or always off)
; 2 - RC5 - 1=gyro off when speed stick is centred
; 3 - RA5 - 1=suppress idle control (0=motors limited to idle setting minimum)
; 4 - RA4 - 1=suppress lift fan over-ride (0= cutting lift fan cuts propulsion)
; 5 - RC3 - 1=no gates - fans only, so no reverse / braking (implies suppress idle)
; 6 - RC2 - 1=reverse steering input
; 7 - RC1 - 1=reverse gate servo on output 2
; 8 - RC0 - 1=reverse gate servo on output 4
; The settings of switches 1 and 2 and most easily understood in combination:
; 1=off, 2=off - normal operation, gyro progressively mixed in at increasing speed
; 1=off, 2=on  - gyro fully off when thrust near centred, fully on otherwise
; 1=on,  2=off - gyro always fully on
; 1=on,  2=on  - gyro always fully off


If you're very interested in the actual coding, you can download the assembly code.

An outline of some key points in the code:

The 16MHz clock was chosen because servos are controlled by a pulse with duration between 1.0 and 2.0 mS. That is, the pulse is +/- 0.5 mS from a central value. At 16MHz clock, the PIC has a 4MHz, 250nS instruction cycle. Therefore, the 0.5mS is 2000 cycles, which if I use a prescaler of 32 on a timer, becomes +- 62.5. 32 is good because because the prescaler needs to be a power of 2 (which 32 is). This is convenient because if I store the pulse duration (in units of 32 instruction cycles) as a signed 8-bit value, I can simply do eight-bit addition and subtraction, since the range after addition is +- 124, which is just within what can be stored in the register. A slower clock would give me less resolution, a higher clock would need 16 bit (or at least higher than 8 bit) arithmetic.

The input channels are timed by means of an interrupt-driven routine. The interrupt service routine has a theoretical range of 51 to 82 clock cycles to complete. As a worst case, therefore, the resolution of the input is 48 steps within the 1mS pulse variation (1mS/(82*250nS)). In reality, my receiver ripples the pulses, so channel 1 goes high then low, then channel 2 goes high then low, and so on. When this happens, the resolution is actually very high, because each change occurs in a separate pass through the ISR, and the variation in run time from start of ISR to the point where the time is recorded is no more than 3 cycles, so input resolution is 1333 steps.

Output channels are driven by a timer with postscaler 32, so they have a resolution of 124 steps from limit to limit. I consider this sufficient resolution for the control I want.

There's a watchdog timer, so if the code gets stuck for more than about half a second the unit resets.

On power-up the three critical channels (RB7, RB6 and RB4) are sampled 8 times and averaged to define what the timing of a zero point pulse is.

The main activity loop counts timer overflows such that it repeats at a rate of 48.8 Hz, so that's the frequency of the output pulses sent to the servos (for comparison, my radio gear, a Futaba 6EXA and R136F receiver, generates pulses at 54.3Hz).

back to the Mark 2B page
back to the top hovercraft page
back to Ian's contents page
back to www.astounding.org.uk top contents page

To comment on anything (please do) email ian@astounding.org.uk