Arduino Virtual Flywheel Throttle controller


100 W
Jan 27, 2020
I have another thread discussing Moto e-Trials design that's been going a few years.
One of the key things that's been discussed at length there is that ICE trials bikes rely heavily on flywheel inertia and torque delivery characteristics for their performance.

To date (Feb 2024) there have been no electric trials bikes that have been able to perform at the level of current stock ICE trials bikes. (The EM Factor-e prototype has just been publicly shown for the first time. It looks very promising.).
My belief is that a large part of the reason for their under-performance is lack of effective flywheel and sub-optimal torque / throttle response.

This project effectively has two parts:
  1. to investigate how effective electronic "virtual flywheel" can be to modify response.
  2. to experiment with modifying torque delivery to more closely mimic the useful characteristics of ICE engines.
I fully expect there to be people who would argue the value of these two proposals.
This isn't the place to discuss if this is useful or not. Only how best to implement it.
Unfortunately developing the software to handle this within a controller is just not viable for a variety of reasons. Also not really open for discussion as it will only detract from getting an initial prototype device up and running.

So the plan is to build an intermediate controller (similar concept to Cycle Analyst) that will manipulate throttle signal to get the desired motor response. This should be largely independent of the controller so it's easy to try it on different controllers to find which ones respond best.

I fully intend to retain a "real" flywheel and clutch on the bike until the electronic analogy proves to be really viable.
Frankly I'm not expecting the electronic alternative to be able to fully replace the mechanical systems, I hope that it can improve power delivery and control and provide greater adjust-ability to the overall response - effectively a somewhat 'tuneable' flywheel and torque output.

The basic functions are:
  • Apply an RPM dependent variable throttle response (emulating ICE RPM/torque relationship).
  • On acceleration apply smoothing to the throttle response (the controller will be set for maximum fast response).
  • On deceleration apply an algorithm to emulate the decay of flywheel RPM. Initially this will disregard actual load on the drive system, so it will be fairly approximate.
  • Secondary Development: Experiment with electronic clutch emulation
I've selected the Arduino UNO R4 as the platform - it's native 5V, has the ability to directly output analog voltage (not just PWM) which might make it compatible with more controllers, is fast (48 MHz) so my poor coding shouldn't make it run too slowly to be useful, it's got plenty of peripherals, it has CAN Bus onboard which might add to flexibility with various controllers (Nucular springs to mind because I have one) and it's pretty common.
There are some issues with that choice, but I think it's a reasonable compromise. Fingers crossed.

My coding skills are starting from very close to nothing and my electronics skills also. I've got a grasp of some of the fundamental concepts in both, but no practical skills or knowledge to talk of.

If anyone is interested in getting involved with this I'd be more than grateful.
I've started a GitHub project, e-trials_throttle
There's a Dev branch that I hope I can work out how to open up to collaborators. I know less about GitHub than I do writing C++ !
Below is a photo of my throttle signal intercept module:77241A0A-8389-4BFD-8252-6BDD52726C77.jpeg

The module was bench tested using USB output: 5V & 2V.
Upon pushing the black button one could add from 0.0V to 1.5V ( c cell battery output adjustable with pot) to the current throttle signal. In the photo below 0.1V is added to throttle signal line.View attachment 347019

The working module input side was plugged into the three throttle wires and the output side forwarded to the controller.

An Arduino SPDT relay was used to perform the circuit switching from pass thru (NC) mode to the add voltage (NO)mode. This switching to the NO side takes place by doing a push/pulse to the thumb button.

Results when tested on the ebike:

1. The throttle worked as normal when in pass thru mode.

2. Attempts to add 1.0 volt to the throttle signal, they were as fast as the relay switched circuits, failed because of controller interrupt.

3. Attempts were made to add 0.1v to the throttle signal but these failed to move the wheel due to Controller interupt.

Either one of two possibilities caused the controller to interrupt:

1. The change in voltage was too fast of a change (kind of a step function) as measured by the controller.

2. The relays time to swap circuits was too slow and the controller measured this time gap? as a faulty throttle signal.

The Arduino relay is not a SSR but a low voltage electromechanical rely that may be too slow and opens the throttle signal long enough for the controller to require a new try on the throttle from 0.0 volts.

More experimentation……

I have not come across a SSR that is SPDT yet. It could swap circuits much faster than this Arduino relay.

If the added voltage burst rise is too quick for the controller I may have to make the waveform into a steep ramp.

Lastly, some setting in my controller program may accommodate this rise if the parameters were appropriately changed.
Last edited:
I finished an alpha version of Arduino code to apply dynamic throttle smoothing proportional to RPM today. It needs a fair bit of polishing but at least on the simulator it gave vaguely sensible output finally.
It's a mystery what it will actually be like to ride with - kind of does my head in trying to imagine how it will react as you accelerate down a straight, that could be really strange, or good. No clue.
In the Dev branch in GitHub.
More time on the basic throttle smoothing in order to produce a more ICE type torque response.
I'm considering throttle output to being analogous to torque.
My previous version was modifying the response rate, which wasn't actually what's needed. I think it needs to modify the maximum torque available according to RPM.
I've now adopted a sigmoidal logistic function to calculate the maximum throttle output at any RPM.
I can tweak this to change the min & max, slope and the point in the rev range where that slope occurs. This graph is what I came up with as a first guess approximation.
At very low RPM (the X scale is time between hall pulses, so larger = lower RPM) there is very little maximum torque. As RPM rises the max possible torque increases rapidly until we get a fairly wide rev range with maximum torque available. I think this is a reasonable rough approximation of an ICE engine torque curve, but gaining benefit from the flat electric curve in the mid-high rpm.

The code then does linear interpretation of the throttle input to the available output range, with output Max limited according to the logistic function.

This has made me think I might be able to apply the same idea to the flywheel effect.
A similar logistic function calculated against the difference between the defined rate of RPM drop and the actual drop.
At low deltas the curve would deliver fairly low response, which somewhat reflects a low RPM flywheel not being able to drop a lot of revs, hence not able to deliver a big surge in torque (not quite accurate, but maybe close enough). The response would fairly quickly increase as revs increase until again there's a wide RPM range with a very strong response to the RPM delta.

Any thoughts?

Pretty simple code that should run quite fast.
I've been a bit concerned that my rpm timing interrupt service routine could take up so much processor time that things get a bit sluggish in the rest of it, particularly if I ever drop this onto a high rpm motor - 17,000 rpm on a 5 pole motor would be 1,416 hz. I'm guessing that even by the time the ISR does some work that's pretty insignificant compared to a 48mHz processor clock.
My ISR is fairly minimal - just grab the microseconds, check if this is the first or second reading in the series, then store the value. If it's the second reading then subtract first from the second and store.
Still, I figure the simpler the processing the more scope there is for future developments without running into speed limits.
It's my first rodeo on micro's, so I really don't have a feel for what's reasonable and I'm spending so much time learning how to write code that there's none left for figuring how many clock cycles things take. And I'm sure my code is going to be pretty inefficient due to lack of knowledge.

@DanGT86 I'd be interested on your thoughts about this as you've got a much better understanding of ICE torque delivery than I do.
We have had big snow here so no road tests. But some indoor tests worth noting.

With the oscilloscope on the bike it was noted that likely the Arduino relays, when driven, often drew down the 5v throttle circuit below the active throttle threshold voltage making for a necessary throttle reset — no twist on it. I did get a few real module generated spikes to cause a spike in suspended wheel rpm. The fardriver controller permits for some form of a throttle spike.

The power needed for some Arduinos boards may sag throttle voltage to activate the throttle cutout threshold? My throttle circuitry was changed to have it not utilized by any other modules than what the controller sends/receives as throttle input voltage. I now power the intercept module circuitry with one cell of my LiPo battery set up — say average approx 3.9v.

The initial TSIM (throttle signal intercept module ) generated some near vertical spikes when viewed on an oscilloscope. I experimented to find capacitors (ranging from .3 micro-f to 3 micro-f) placed in parallel to the output of the TSIM to smooth the waveform.

Below is a photo of the Bench testing set-up for the TISM:
The signal is smoothed with a 3 micro-f capacitor.

Below is the signal spike with no capacitor in parallel:36084F49-B99D-4F81-9512-AAE515468ACE.jpeg

Below is a series of pulses using a 2 micro-f capacitor :EB260A2F-4D28-42B1-A402-4C176F4A7B92.jpeg
The amplitude of the signal can be changed by adjusting a potentiometer on the TISM.
Last edited:
@DingusMcGee what's the story with the signal going + & -?
I thought the idea was it just added V to the output signal?
Wouldn't the negative side cut power before the + added it?

Seems I might have misunderstood the system.

When batteries are hooked in series the voltage is the sum of each batteries voltage regardless of the voltage of each battery. So if you want to add volts, the additional (voltage source) connections have to be in series with the connections go from + TO - or - to + but never + to + or - to -. If you want to subtract some voltage, simply hook like polarities.

If you connect batteries in parallel, like jumping a dead car battery, the resultant voltage will be less than the voltage of the fully charged battery.

The oscilloscope signal goes towards zero because upon releasing the push button a connection is re-made to the pass thru line which has gone dead (in that short time) — zero voltage, unless voltage is added by a capacitor to that segment.

Coil relays, when switching, will have a time gap in which the arm is not touching either switch pole. SSR (relays) are so fast that a SPDT version can seeming have both circuits connected at the same — a no, no. It seems no one makes an SSR that is SPDT because of this problem. My circuit employs both coil relays and SSR’s. You can use a SSR SPST on the connection you want to be very fast.

Using Arduino you do not have this analog signal problem of dead upon switching.

The Fardriver controller permits a very steep throttle signal change. With the wheel off the ground, you can connect the throttle’s 5V wire red to the green throttle signal. The rear wheel accelerates like an explosion.
Last edited:
@DingusMcGee Maybe my question should have been, "Is this version working or is the controller still seeing a drop below active throttle threshold voltage?"
Maybe the blue trace is the threshold voltage?

Good to hear that the Fardriver seems to respond well to sudden throttle signal increases. That's encouraging. I assume you had the throttle smoothing dialled right down to get that kind of response when you put 5v straight across?

The current TSIM version works when the push button is depressed and held. But upon releasing the push button, voltage drops below throttle threshold and a restart is needed.

The display on the oscilloscope is upside down for positive and a triggered signal moves right to left. My set triggering is “rising edge”. The blue line is channel 2 at zero volts.

The current TSIM version has no coil relays. Since I could not find an Arduino SSR SPDT, I was able to make and employ an invert SSR en lieu of the unfindable SSR SPDT. The other 2 relays are normal 5V Omron SSRs. From the spec sheet the response time of the Omron SSR is 1.0 ms. I see an adjustment on the Fardriver, “curve time”. Is this time between samples?

A word about employing on board power for the module. Because DC circuits usually are based/biased on a common ground, the controller and it’s throttle circuit see zero volts on the black neg side of the lowest cell in the battery pack. If you connect elsewhere to the battery pack, the throttle circuit will see bias high voltage. In my case, hooking to 4v indiscriminately, put a high throttle signal to the controller which sent the rear wheel lurching out of rest state.

So presently the problem is how to boost the throttle signal above threshold when the push button is released.

Presently the maximum boost is about 1.2 volts.
Last edited: