Jump to content

Python Visualizations: Difference between revisions

From BCI2000 Wiki
Redirect to VisualizeBCI2000, the new documentation
Tag: New redirect
 
(One intermediate revision by the same user not shown)
Line 1: Line 1:
[[Image:CCEP gif.gif |616px|right|thumb|frame| An example video showing one channel of the CCEP filter.]]
#REDIRECT [[VisualizeBCI2000]]
[[File:PAC Demo.gif|thumb|568px|A demo of the Phase-Amplitude Coupling visualization with Python]]
 
=Synopsis=
Visualize your BCI2000 signals real-time with python! This integration allows for you to combine complex Signal Processing pipelines in C++ with beautiful, interactive visualizations in Python.
 
There are currently two prepared visualizations: [[Contributions:CCEPFilter|Cortico-cortical evoked potentials (CCEPs)]] and [[Contributions:PAC|phase-amplitude coupling (PAC)]]. However, the pipeline is adaptable, allowing you to visualize whatever you want!
 
=Installation=
#Python 3.7+ needs to be installed. [https://www.python.org/downloads/| You can download the lastest version here].
#A couple additional packages are used in this visualization. Run the following segments using <code>pip</code> in the command line.
#*Numpy: <code>pip install numpy</code>
#*PyQt5: <code>pip install PyQt5</code>
#*PyQtGraph 0.13.3+: <code>pip install pyqtgraph</code>
#*SciPy: <code>pip install scipy</code> (only the stats package is required)
 
=Demo Use=
Configure (BCI2000/build/Configure.sh.cmd) and build BCI2000 (Visual Studio), making sure to build Contributions (enable BUILD_CONTRIB flag, then build in Visual Studio). After this is done, navigate to <code>BCI2000 &rarr; python &rarr; visualizations</code>. Here you will find demo python files you can run out of the box!
 
=Configuration=
Below is an example runnable script that will start BCI2000, along with the PAC visualization. This replaces the need for batch files, and allows you to easily run BCI2000 programmatically. Additional commands are available at [[Programming Reference:BCI2000Remote Class]]. <i>Make sure to run this file in the correct location (<b>BCI2000 &rarr; python &rarr; visualizations</b>)</i>!
 
<syntaxhighlight lang="python">
from scripts.main import main
 
#configure to customize your BCI2000 instance
def initBCI2000(bci):
    bci.WindowTitle = 'BCI2000: Phase-Amplitude coupling'
    bci.Execute('cd ${BCI2000LAUNCHDIR}')
 
    #FilePlayback is helpful if you already have the data file
    bci.StartupModules(('FilePlayback --PlaybackFileName=..\data\samplefiles\eeg3_1.dat',
                        'PAC',
                        'DummyApplication'))
 
    bci.SubjectID = 'pacDemo'
    bci.LoadParametersRemote('../parms/PAC/pac_pipeline.prm')
 
    #due to signal's low sampling rate
    bci.Execute('SET PARAMETER Amplitude/IIRBandpass/LowPassCorner 120Hz')
    bci.Execute('SET PARAMETER SourceDecimationFilter/LowPassCorner 120Hz')
 
if __name__ == '__main__':
    main(initBCI2000)
</syntaxhighlight>
There are additional parameters you can pass <code>main()</code> (or don't pass it anything to be able to start your own batch file).
 
Full definition: <syntaxhighlight lang="python" inline>def main(bciConfig = defaultBCI, path="../../prog", address = ("localhost", 1879), winSize = (1600, 1200), timerUpdate=30 )</syntaxhighlight>
* <b><i>bciConfig</b></i>: the BCI2000 configuration (initBCI2000 function)
* <b><i>path</b></i>: the path to your BCI2000 prog directory. If this is configured, the python files can be run anywhere (as long as they keep their underlying architecture)
* <b><i>address</b></i>: the address that is used to communicate between BCI2000 and Python
* <b><i>winSize</b></i>: Default window size when it is opened
* <b><i>timerUpdate</b></i>: The minimum amount of time between each update of the Python GUI (milliseconds). This is really the frequency that the visualization checks if it should update, but only updates if there is new data. It has an upper bound of the BCI2000 block size, as that is how often data is updated. If the CPU load is large, increasing this number will help.
 
=Architecture=
Once BCI2000 is configured and built, these files are used to visualize your signal in BCI2000 in real-time with Python:
 
* BCI2000
**python
***visualizations - ''contains "batch" files that you can run to start BCI2000 and the python visualization''
****connect_batch.py - ''run this to connect to a batch file you have started''
****pacDemo.py
****ccepDemo.py
****scripts
*****main.py - ''starts the 2 secondary threads: data collection thread and BCI2000 connection thread''
*****AcquireDataThread.py - ''thread that handles the data collection from the shared memory''
*****BCI2000Connection.py - ''thread that handles the communication with the BCI2000 instance''
*****CCEPVisualization.py - ''specifies how to handle the incoming data into the CCEP visualization''
*****PACVisualization.py: - ''specifies how to do the same for the PAC visualization''
*****DefaultVisualization.py: - ''a default visualization''
*****SharedVisualization.py: - ''the abstract class which needs to be implemented for all visualizations''
 
These files can be moved around (if the path to BCI2000 is correctly specified), however <u>make sure to always keep the architecture under ''visualizations'' the same</u>.
 
=Known Issues=
*If the signal fails to send from BCI2000 (indicated by a warning message in the BCI2000 Command Log: <code>Could not send signal. Giving up</code>), BCI2000 must be restarted to be able to connect to Python again.
*Every once in a while (only seen with the CCEP visualization), BCI2000 thinks they are connected, but the Python side is not connected (still says <code>Attempting to connect to BCI2000...</code>). This can be fixed by simply pressing SetConfig again, as long as a run wasn't started (if it was, it brings us to the previous problem because the signal failed to send).
 
==Python==
3 threads are running within the Python scripts.
#'''Data acquisition:''' Connects to the shared memory address and continually updates the local data when there is new data to be acquired.
#'''BCI2000 Connection:''' Using [[Programming Reference:BCI2000Remote Class|BCI2000Remote]], we have a two-way connection between Python and BCI2000. This is used for updating and acquiring states and parameters. This can also be used to start a BCI2000 instance, instead of the common practice of using a batch file.
#'''Visualization:''' The main thread of the Python script creates an interactive visualization with PyQtGraph. When the visualization is interacted with, BCI2000 states are updated accordingly.
 
[[Category:User_Interface]]

Latest revision as of 14:52, 29 April 2025

Redirect to: