Skip to content

Commit

Permalink
Merge pull request #32 from Andrey1994/eeg_descr
Browse files Browse the repository at this point in the history
Eeg descr
  • Loading branch information
Andrey1994 committed Apr 20, 2020
2 parents 70f921e + 90ea264 commit cb98655
Show file tree
Hide file tree
Showing 13 changed files with 188 additions and 43 deletions.
2 changes: 2 additions & 0 deletions brainflow_boards.json
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,7 @@
"battery_channel": 9,
"num_rows" : 11,
"eeg_channels" : [1, 2, 3, 4],
"eeg_names": "T3,T4,O1,O2",
"other_channels": [5, 6, 7, 8]
},
"8" : {
Expand All @@ -132,6 +133,7 @@
"battery_channel": 9,
"num_rows" : 18,
"eeg_channels" : [0, 1, 2, 3, 4, 5, 6, 7],
"eeg_names": "Fz,C3,Cz,C4,Pz,PO7,Oz,PO8",
"accel_channels": [8, 9, 10],
"gyro_channels": [11, 12, 13],
"other_channels": [16],
Expand Down
29 changes: 29 additions & 0 deletions cpp-package/src/board_shim.cpp
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
#include <algorithm>
#include <sstream>
#include <stdlib.h>
#include <string.h>
#include <string>
#include <vector>

#include "board_shim.h"

Expand Down Expand Up @@ -297,6 +300,32 @@ int BoardShim::get_num_rows (int board_id)
return num_rows;
}

std::string *BoardShim::get_eeg_names (int board_id, int *len)
{
char *eeg_names = new char[4096];
int string_len = 0;
int res = ::get_eeg_names (board_id, eeg_names, &string_len);
if (res != STATUS_OK)
{
throw BrainFlowException ("failed get board info", res);
}
std::string line (eeg_names, 0, string_len);
std::istringstream ss (line);
std::vector<std::string> out;
std::string single_name;
while (std::getline (ss, single_name, ','))
{
out.push_back (single_name);
}
delete[] eeg_names;

std::string *result = new std::string[out.size ()];
std::copy (out.begin (), out.end (), result);
*len = out.size ();

return result;
}

int *BoardShim::get_eeg_channels (int board_id, int *len)
{
int *eeg_channels = new int[MAX_CHANNELS];
Expand Down
38 changes: 22 additions & 16 deletions cpp-package/src/inc/board_shim.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,97 +51,103 @@ class BoardShim

/**
* get sampling rate for this board
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int get_sampling_rate (int board_id);
/**
* get row index which holds package nums
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int get_package_num_channel (int board_id);
/**
* get row index which holds timestamps
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int get_timestamp_channel (int board_id);
/**
* get row index which holds battery level info
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int get_battery_channel (int board_id);
/**
* get number of rows in returned from @ref get_board_data() 2d array
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int get_num_rows (int board_id);
/**
* get eeg channel names in 10-20 system for devices with fixed electrode locations
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static std::string *get_eeg_names (int board_id, int *len);
/**
* get row indices which hold EEG data, for some board we can not split EEG\EMG\...
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_eeg_channels (int board_id, int *len);
/**
* get row indices which hold EMG data, for some board we can not split EEG\EMG\...
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_emg_channels (int board_id, int *len);
/**
* get row indices which hold ECG data, for some board we can not split EEG\EMG\...
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_ecg_channels (int board_id, int *len);
/**
* get row indices which hold EOG data, for some board we can not split EEG\EMG\...
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_eog_channels (int board_id, int *len);
/**
* get row indices which hold PPG data
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_ppg_channels (int board_id, int *len);
/**
* get row indices which hold EDA data
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_eda_channels (int board_id, int *len);
/**
* get row indices which hold accel data
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_accel_channels (int board_id, int *len);
/**
* get row indices which hold analog data
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_analog_channels (int board_id, int *len);
/**
* get row indices which hold gyro data
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_gyro_channels (int board_id, int *len);
/**
* get row indices which hold other information
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_other_channels (int board_id, int *len);
/**
* get row indices which hold temperature data
* @param board_id board if for your board
* @param board_id board id of your device
* @throw BrainFlowException If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
*/
static int *get_temperature_channels (int board_id, int *len);
Expand Down
12 changes: 12 additions & 0 deletions csharp-package/brainflow/brainflow/board_controller_library.cs
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,8 @@ public static class BoardControllerLibrary64
public static extern int get_temperature_channels (int board_id, int[] channels, int[] len);
[DllImport("BoardController.dll", SetLastError = true, CallingConvention = CallingConvention.Cdecl)]
public static extern int is_prepared(int[] prepared, int board_id, string input_json);
[DllImport("BoardController.dll", SetLastError = true, CallingConvention = CallingConvention.Cdecl)]
public static extern int get_eeg_names(int board_id, byte[] eeg_names, int[] len);
}

public static class BoardControllerLibrary32
Expand Down Expand Up @@ -176,6 +178,8 @@ public static class BoardControllerLibrary32
public static extern int get_temperature_channels (int board_id, int[] channels, int[] len);
[DllImport("BoardController32.dll", SetLastError = true, CallingConvention = CallingConvention.Cdecl)]
public static extern int is_prepared(int[] prepared, int board_id, string input_json);
[DllImport("BoardController32.dll", SetLastError = true, CallingConvention = CallingConvention.Cdecl)]
public static extern int get_eeg_names(int board_id, byte[] eeg_names, int[] len);
}

public static class BoardControllerLibrary
Expand Down Expand Up @@ -316,6 +320,14 @@ public static int get_timestamp_channel (int board_id, int[] timestamp_channel)
return BoardControllerLibrary32.get_timestamp_channel (board_id, timestamp_channel);
}

public static int get_eeg_names(int board_id, byte[] names, int[] len)
{
if (System.Environment.Is64BitProcess)
return BoardControllerLibrary64.get_eeg_names(board_id, names, len);
else
return BoardControllerLibrary32.get_eeg_names(board_id, names, len);
}

public static int get_eeg_channels (int board_id, int[] channels, int[] len)
{
if (System.Environment.Is64BitProcess)
Expand Down
19 changes: 19 additions & 0 deletions csharp-package/brainflow/brainflow/board_shim.cs
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,25 @@ public static int get_num_rows (int board_id)
return val[0];
}

/// <summary>
/// get names of EEG channels in 10-20 system. Only if electrodes have fixed locations
/// </summary>
/// <param name="board_id"></param>
/// <returns>array of 10-20 locations</returns>
/// <exception cref="BrainFlowException">If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR</exception>
public static string[] get_eeg_names(int board_id)
{
int[] len = new int[1];
byte[] str = new byte[4096];
int res = BoardControllerLibrary.get_eeg_names(board_id, str, len);
if (res != (int)CustomExitCodes.STATUS_OK)
{
throw new BrainFlowException(res);
}
string eeg_str = System.Text.Encoding.UTF8.GetString (str, 0, len[0]);
return eeg_str.Split (new Char[] {','});
}

/// <summary>
/// get row indices of EEG channels for this board, for some board we can not split EMG\EEG\.. data and return the same array for all of them
/// </summary>
Expand Down
26 changes: 0 additions & 26 deletions docs/Gallery.rst

This file was deleted.

1 change: 0 additions & 1 deletion docs/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ It provides a **uniform data acquisition API for all supported boards**, it mean
UserAPI
DataFormatDesc
Examples
Gallery
BrainFlowDev
AskHelp
Partners
Expand Down
19 changes: 19 additions & 0 deletions java-package/brainflow/src/main/java/brainflow/BoardShim.java
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,8 @@ int get_current_board_data (int num_samples, double[] data_buf, int[] returned_s
int get_temperature_channels (int board_id, int[] temperature_channels, int[] len);

int is_prepared (int[] prepared, int board_id, String params);

int get_eeg_names (int board_id, byte[] names, int[] len);
}

private static DllInterface instance;
Expand Down Expand Up @@ -247,6 +249,23 @@ public static int get_battery_channel (int board_id) throws BrainFlowError
return res[0];
}

/**
* Get names of EEG electrodes in 10-20 system. Only if electrodes have freezed
* locations
*/
public static String[] get_eeg_names (int board_id) throws BrainFlowError
{
int[] len = new int[1];
byte[] str = new byte[4096];
int ec = instance.get_eeg_names (board_id, str, len);
if (ec != ExitCode.STATUS_OK.get_code ())
{
throw new BrainFlowError ("Error in board info getter", ec);
}
String eeg_names_string = new String (str, 0, len[0]);
return eeg_names_string.split (",");
}

/**
* get row indices in returned by get_board_data() 2d array which contains EEG
* data, for some boards we can not split EEG\EMG\... and return the same array
Expand Down
21 changes: 21 additions & 0 deletions julia-package/brainflow/src/board_shim.jl
Original file line number Diff line number Diff line change
Expand Up @@ -162,6 +162,27 @@ function get_num_rows(board_id)
end


function get_eeg_names(board_id)
names_string = Vector{Cuchar}(undef, 4096)
len = Vector{Cint}(undef, 1)
ec = STATUS_OK
# due to this bug https://github.com/JuliaLang/julia/issues/29602 libname should be hardcoded
if Sys.iswindows()
ec = ccall((:get_eeg_names, "BoardController.dll"), Cint, (Cint, Ptr{UInt8}, Ptr{Cint}), board_id, names_string, len)
elseif Sys.isapple()
ec = ccall((:get_eeg_names, "libBoardController.dylib"), Cint, (Cint, Ptr{UInt8}, Ptr{Cint}), board_id, names_string, len)
else
ec = ccall((:get_eeg_names, "libBoardController.so"), Cint, (Cint, Ptr{UInt8}, Ptr{Cint}), board_id, names_string, len)
end
if ec != Integer(STATUS_OK)
throw(BrainFlowError(string("Error in get board info ", ec), ec))
end
sub_string = String(names_string)[1:len[1]]
value = split(sub_string, ',')
value
end


function get_eeg_channels(board_id)
channels = Vector{Cint}(undef, 512)
len = Vector{Cint}(undef, 1)
Expand Down
10 changes: 10 additions & 0 deletions matlab-package/brainflow/BoardShim.m
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,16 @@ function log_message (log_level, message)
timestamp_channel = res.value + 1;
end

function eeg_names = get_eeg_names (board_id)
task_name = 'get_eeg_names';
lib_name = BoardShim.load_lib ();
% no way to understand how it works in matlab used this link
% https://nl.mathworks.com/matlabcentral/answers/131446-what-data-type-do-i-need-to-calllib-with-pointer-argument-char%
[exit_code, eeg_names] = calllib (lib_name, task_name, board_id, blanks(4096), 4096);
BoardShim.check_ec (exit_code, task_name);
eeg_names = split (eeg_names, ',');
end

function eeg_channels = get_eeg_channels (board_id)
task_name = 'get_eeg_channels';
num_channels = libpointer ('int32Ptr', 0);
Expand Down
25 changes: 25 additions & 0 deletions python-package/brainflow/board_shim.py
Original file line number Diff line number Diff line change
Expand Up @@ -257,6 +257,14 @@ def __init__ (self):
ndpointer (ctypes.c_int32)
]

self.get_eeg_names = self.lib.get_eeg_names
self.get_eeg_names.restype = ctypes.c_int
self.get_eeg_names.argtypes = [
ctypes.c_int,
ndpointer (ctypes.c_ubyte),
ndpointer (ctypes.c_int32)
]

self.get_eeg_channels = self.lib.get_eeg_channels
self.get_eeg_channels.restype = ctypes.c_int
self.get_eeg_channels.argtypes = [
Expand Down Expand Up @@ -512,6 +520,23 @@ def get_timestamp_channel (cls, board_id):
raise BrainFlowError ('unable to request info about this board', res)
return int (timestamp_channel[0])

@classmethod
def get_eeg_names (cls, board_id):
"""get names of EEG channels in 10-20 system if their location is fixed
:param board_id: Board Id
:type board_id: int
:return: EEG channels names
:rtype: list
:raises BrainFlowError: If this board has no such data exit code is UNSUPPORTED_BOARD_ERROR
"""
string = numpy.zeros (4096).astype (numpy.ubyte)
string_len = numpy.zeros (1).astype (numpy.int32)
res = BoardControllerDLL.get_instance ().get_eeg_names (board_id, string, string_len)
if res != BrainflowExitCodes.STATUS_OK.value:
raise BrainFlowError ('unable to request info about this board', res)
return string.tobytes ().decode ('utf-8')[0:string_len[0]].split (',')

@classmethod
def get_eeg_channels (cls, board_id):
"""get list of eeg channels in resulting data table for a board
Expand Down

0 comments on commit cb98655

Please sign in to comment.