DAVEGA X Updates

Nice! Will try it tomorrow

I was dreaming of how to make a better travel build potentially for next year’s Carve PDX, and I might have the opposite problem – would it be possible to have the Davega iterate between multiple smart BMSes in the same board? :grinning_face_with_smiling_eyes:

Just get some more DAVEGAs. :slight_smile:

4 Likes

I’m currently quarantined, so that’s an ideal opportunity to work on the firmware and I’ve managed to get quite a bit done this week.

v5.03 is now available as a release candidate.

There 3 new features:

Pause lifespan tracking for a part

Thanks to @ShutterShock for the idea. This is handy for tracking the lifespan of a part that’s not installed permanently. Maybe you have two sets of tires that you toggle. Maybe you have an external battery that you only use for weekend trips but not for your daily commute.

Here’s how you pause the tracking. It’s completely straightforward:

Restore backup over WiFi

This goes in line with the transition to the DAVEGA v1.2 hardware that no longer has the USB port.

Before, it was only possible to upload data directly from the DAVEGA to the cloud. To restore the backup, you would need to download it to your computer and then copy to the DAVEGA over the USB cable.

Now this can be done directly from the DAVEGA:

WebREPL mode

Another update that allows doing more over the air. This is quite a big thing. I’ll do a separate post on it.

5 Likes

Woohooo! This is awesome, I mentioned this in my last video as something that would make the parts lifespan even more great! This will be perfect for me to use both my street tires and offroad tires in succession.

2 Likes

WebREPL mode

As you may know, DAVEGA firmware is written in micropython. Micropython is very cool and the WebREPL is one of the builtin features that allows you to connect to the device and get an interactive prompt.

With v5.03, DAVEGA will boot into the WebREPL mode if you hold the up and down buttons simultaneously at start up (using the :metal: grip).

Here’s how it looks:

DAVEGA will tell you the name of the WiFi access point it has created. Note that once you connect you’ll no longer have Internet so before you do that, you’ll want to open the WebREPL client in your browser, which is available at http://micropython.org/webrepl/.

You’ll want to make sure you have http:// and NOT https:// since the connection won’t work over SSL (we won’t be transferring credit card numbers or bitcoin wallet private keys so don’t worry). Though this may be counter-intuitive, the “Not Secure” warning is actually what you want here.

Now you’re ready to connect to the DAVEGA WiFi:

Then you can hit the “Connect” button in the WebREPL client and it should connect to the DAVEGA. You’ll be asked for a password, which is agevad (I had to put something; it doesn’t work without a password).

Then you should get the Python command prompt and you’re ready to run Python on your DAVEGA. How cool is that?!

For example, here’s one toy thing you can try. Type:

from frozen.display import DISPLAY
DISPLAY.print("hi mum!")

And it will get printed on the DAVEGA display:

There’s also stuff you can do that’s actually useful. In particular the frozen.commands module contains functions for archiving/restoring the DAVEGA data. On the right hand side of the WebREPL client there are widgets for transferring files to/from the DAVEGA.

If you combine this, here’s how you can get a data backup. Type:

from frozen.commands import backup
backup()

This will archive all the DAVEGA data into a single filed called /backup.dfs. If you then type /backup.dfs into the “Get a file” text field and click on “Get from device”, the file gets transferred to your computer.

The other direction is also possible. Say that you have a backup file called backup_from_another_davega.dfs that you either downloaded from https://davega.eu/backups or created using WebREPL the way I just showed.

In the “Send a file” widget, look up the file on your disk and click “Send to device”. The file name will be retained and it will be put in the root directory, so in this particular case the file path will be:

/backup_from_another_davega.dfs

Now we can go ahead and restore that backup as follows:

from frozen.commands import restore
restore('/backup_from_another_davega.dfs')

Last, the .dfs files are now stored in the DAVEGA flash memory. We may want to clean it up. Here’s one way of listing the files in the root directory:

import os
os.listdir('/')

Here’s how to remove the files:

os.remove('/backup.dfs')
os.remove('/backup_from_another_davega.dfs')

(The leading slash is not strictly necessary since we’re working from the root directory.)

Being able to run custom code on DAVEGA opens the door for tinkering if you know what you’re doing. Some other things one could potentially do include:

  • accessing VESC data programmatically
  • changing VESC settings
  • accessing smart BMS data programmatically
  • changing smart BMS settings
  • changing DAVEGA settings (including hidden settings)
  • adjusting DAVEGA odometers
  • writing DAVEGA plug-ins

Obviously none of this is straightforward and it’s not for everyone. It’s also riding completely without seatbelts and you can easily mess things up if you’re not careful. (Still if you backup everything first, there’s not a lot to worry about.)

Currently there’s no documentation for the DAVEGA APIs and I don’t intend to write and maintain complete documentation. However, if people come up with interesting use cases I’m happy to document relevant parts of the APIs and/or write up guidelines/tutorials.

12 Likes

The stuff you’re making is genius!

2 Likes

Successfully updated the HW1.2 to FW5.03 over wifi, through the usplit!

So much easier than last time i played with davega! Nice work Jan!

Quick little update… i noticed that the little receiver blips at the top were getting a red blip every 3-5 secs while davega was connected through usplit.

I connected directly to the vesc and got hardly any red blips at all. It would seem as if the usplit is losing some stuff in translation. I’m wondering how this will now affect my robogotchi logs… if at all.


6 Likes

v5.03rc3 is out and it brings a very basic support for plug-ins. You can now upload a custom micropython file called start.py (using the method described here) and it gets executed upon start-up.

Here’s an example of such file:

from frozen.display import DISPLAY
DISPLAY.print("Hi mum!")

And then DAVEGA will say “Hi mum!” any time it starts up.

Exciting, right?! :nerd_face:

The real importance of this feature is to be illustrated on my next post though. Stay tuned.

6 Likes

I feel like you’re a bit bored. :smiley: But thats giving me cool new features, so I’m very cool with it. :smiley:

2 Likes

Up to this day, the esk8 world suffered from a major shortcoming, which is: You can’t play snake on your electric skateboard. Well, not anymore.

Introducing… :drum: :drum: :drum: The DAVEGA sn8ke!

sn8ke_demo

Despite the obvious importance of this feature, I decided not to include it in the firmware by default. Instead, it’s a plug-in.

To install it, you first need the latest DAVEGA firmware v5.03rc3. Then download the sn8ke.zip (10.2 KB) file, extract and upload all three extracted files (start.py, sn8ke.py, sn8ke.pic) to your DAVEGA using the method described here. The sn8ke.pic is a bit large and it will work without it. You just don’t get the sn8ke splashscreen, which I think is pretty much mandatory, but you can still leave it out.

To run the sn8ke, hold the left (down) button while booting up.

And the best part is that sn8ke.py, for the most part, is just Python with some simple DAVEGA/micropython APIs, so you can customize it.

The first to post a picture/video of a working sn8ke on their DAVEGA is to be titled The DAVEGA Hacker. :nerd_face:

I have no idea what you’re talking about!

22 Likes

This MAN!!! Just keeps bringing it!!! :flushed::partying_face::partying_face::partying_face::partying_face::partying_face::partying_face::partying_face:

6 Likes

Oooh this is awesome!

I have an idea for a startup plugin, but no programming experience :sweat_smile:

I’ve just built a parallel battery for my board, but I won’t be using it every ride. Would be awesome to have a startup feature that gave me the option of choos8ng just my board battery or board + parallel… if said feature could log the lifetime use of my parallel battery too, that would be amazing! Maybe by triggering the super cool pause/unpause feature!

8 Likes

I thought this was a troll but it’s legit guys!

14 Likes

@janpom this is amazing, I’ll never be bored waiting for the group ride to start anymore!

6 Likes

tbh this is just such a neat party trick to bring to a group ride :rofl:

3 Likes

That reaction made my day! :laughing: Well worth the time spent on this.

@jamie, can we please give @Dunkan a title? :slight_smile:

3 Likes

Great idea and this would indeed be possible to do as a plug-in, at least in some simple form.

One way would be to toggle the setup by holding a button (or a button pattern) at startup. In the simplest form this would just modify the battery capacity setting. A more advanced version could also tinker with part lifespan and pause/unpause the tracking for the external battery. I’ll prepare some example code later on today.

3 Likes

@glyphiks: This should do the trick. Just change the BUILTIN_BATTERY_MAH and EXTENDED_BATTERY_MAH as appropriate (the latter is the total capacity after adding the extended battery). Then save everything to a file called start.py, upload that one to your DAVEGA and you’re good to go.

import utime

from frozen.buttons import BUTTON_DOWN
from frozen.config import load_config, save_config
from frozen.display import DISPLAY

BUILTIN_BATTERY_MAH = 20000
EXTENDED_BATTERY_MAH = 30000

# trigger by holding the down button at start-up
if not BUTTON_DOWN.value():
    config = load_config()
    if config.battery_mah == BUILTIN_BATTERY_MAH:
        config.battery_mah = EXTENDED_BATTERY_MAH
        DISPLAY.print("extended battery ENABLED")
    else:
        config.battery_mah = BUILTIN_BATTERY_MAH
        DISPLAY.print("extended battery DISABLED")
    save_config(config)

    # short delay so that the message can be easily noted
    utime.sleep_ms(1000)
8 Likes

Thanks heaps Jan! I’m working on the board today so I’ll give it a crack!

5 Likes