Python event driven interface: txOpenBCI

edited January 2015 in Software
(Continuation of discussion on Python brought up in another thread.)

For python, there's some code in the OpenBCI_Python repo here: 
https://github.com/OpenBCI/OpenBCI_Python

Over the weekend I started a new version from another angle, using an event-driven approach that will make it significantly easier to integrate with a web server and/or Kivy: 

I'd really hoped to put a web server on that before I had to go back to my day job, but it still needs more work. Maybe next weekend.

Current status of the event-driven version (txOpenBCI) is that it opens a connection to the device and sends the "reset" command. Which is not very impressive and why I was going to wait until it was a little further along before bringing it up, but you seem to be enthusiastic about Python now. :)

Comments

  • Yes I am! Thanks you for this and I'm looking forward to the next posting. Reading now and will probably have a question or two.
  • The python code, does this work with V3? I think I saw this before from back in 2013.
  • Progress update on txOpenBCI:

    Spent some more time on this over the weekend. Don't get too excited yet, there's still no web server.

    The most interesting thing I've encountered is that I am getting far more than 250 samples per second. About double that. This is using the 32-bit board's stock firmware and whatever settings it has after you send it the reset (v) code. I am not at all sure what to make of that.

    Other notes:
    • I found a bug in the dongle code.
    • It is often the case that things are in some unknown state when you open the serial port. I see why there have been so many folks struggling with this and needing to turn things off and on.
    I'll keep at it. Let me know if you have any questions; I'm often lurking in the #openbci channel on freenode.
  • wjcroftwjcroft Mount Shasta, CA
    Kevin,

    > The most interesting thing I've encountered is that I am getting far more than 250 samples per second.

    Check out this thread where @P300_MAN posted some graphs of his timings. At 250 packets per second, the nominal interpacket interval is 1/250 = .004 = 4 milliseconds. Which is what he was seeing.

    http://openbci.com/forum/index.php?p=/discussion/198/timing-marks-buffering-delays-etc

    Is it possible that your code is waking up more often as the bytes dribble in from the simulated serial port, running at 115200 bps = 115200 / 8  = 14400 bytes/sec. Do you delay your timing calculations until you get a full packet (frame termination character)?

    Another data point that I'm aware of is Brainbay, which displays a "samples per second" counter in the status area at the bottom of the screen while running. This is always in the range of 250 sps. + or - a couple samples.

    Regards, William

  • Hah! Turns out my timing function was looking at CPU-used-time, not wall-clock-time. When using the correct timer, I see everything's coming in at 250 samples per second, as expected.
  • Yeh!  Just Yeh.  This was going to be my next thread post re: upping the sample rate so, yeh that someone else is looking at this!  

    I noticed that data output files via the openbci gui program come out as data enumerated on the leftmost line as 1-255 and then resets back to 1 and continues incrementing.  Is the speed of the data coming somehow constrained by the bitdepth of the buffer?  I'm not able to understand/imagine why the data from all channels would come out that way for any other reason....
  • edited December 2014
    Okay, now txOpenBCI has a web server:
    image
    I guess the thing that isn't obvious from this un-moving picture is that those are live values that update as data comes in, not a single snapshot.

    and here's a typical terminal session:
    image

    As you can see, I pushed straight through to the web stuff without stopping to make it robust against protocol quirks, so do treat this very much as proof of concept. (It does parse the stream data okay, the error you see there is the one I mentioned earlier that happens when ending the stream.)

    I also haven't done any packaging yet to make it friendly to non-developers, but if you know how to set up a Python virtualenv and install the requirements, you should be able to give it a spin.
    You may need to change settings in the .tac file if your system uses different ports than mine.
  • Hi guys,

    Great work on the python code https://github.com/OpenBCI/OpenBCI_Python . Received my board just before Christmas and I'm happy there's a Python way. Can't wait to get started.
    I'm planning in creating an interface in Kivy if anyone wants to lend a hand. The main reason for choosing Kivy is that porting to IOS, Android, and OS X from the one kivy.app is straightforward.

  • edited December 2014
    @memebrain, integration with Kivy is one of my primary motivations for working on txOpenBCI. Kivy has documented support for integrating with Twisted. The main OpenBCI_Python implementation's use of blocking reads and time.sleep aren't well suited to an application that has to work with other user input events.

    I look forward to seeing what we can come up with Kivy. Let me know when you have thoughts about what the API should be like. I have my own ideas but I'm a ways from plugging it into an actual application yet.

    Regarding Kivy on IOS and Android: There are some caveats about connectivity directly from OpenBCI to mobile, as we talked about earlier, unless your mobile device has USB host mode and can plug the dongle in.
  • Speaking of txOpenBCI, since it's been a week since my last status post: I didn't work on it this week, but I did just make a list of tickets in the issue tracker that should provide a better idea of where things are at and where you might lend a hand, if you're so inclined.
  • Hi Keturn,

    Looking into Twisted integration in Kivy now. I like where this is headed.
  • biomurphbiomurph Brooklyn, NY
    This is pretty sweet!

    Just a couple of small notes:
    William, when converting baud to bytes per second, you need to divide by 10
    Start bit, 8 data bits, Stop bit 
    115200 is 11520 byres per second

    That first number in the data stream is only 1 byte wide. That's why it counts up to 255 and then rolls over to 0 again. 

    Cheers!
  • edited January 2015
    As python is concerned, I have played a bit with GNURadio interface today:
Sign In or Register to comment.