RTIS Dev Remote MATLAB Wrapper

RTIS Dev Remote MATLAB Wrapper

MATLAB wrapper for using RTIS Dev remotely

This is a wrapper of the RTIS Dev Remote library to use RTIS Dev remotely over IP from MATLAB. Quickly develop with connected RTIS devices. Almost all RTIS Dev functions are available as well as automatic conversion of RTIS Dev custom class objects.

Unavailable RTIS Dev methods

Here is a short list of the current RTIS Dev methods that aren't available through this wrapper:

Usage

Configure Python for MATLAB

First you need to correctly link your installed Python installation to MATLAB, as by default this isn't always the latest version of Python 3 you installed. You can verify which Python is linked by running:

pe = pyenv;
pe.Version

If this is not a version that you which to use and does not match the dependencies you can alter this manually. Do note that you need to do this everytime before using the RTIS Dev Remote MATLAB wrapper! Once Python is loaded in matlab, you need to restart MATLAB first before changing it. Therefore, running the commands above will likely mean requiring a restart of MATLAB.

For Windows you can run:

pyenv('Version','your.version')

With your.version indicating the major.minor version number of you Python release, for example 3.6. On linux you need to refer to the path of your Python 3 installation:

pyenv('Version',"/usr/bin/python3")

You can also link to specific Python versions by altering the path. Some more information can be found here.

Initial setup

When starting with this wrapper, first try to make a connection the remote RTIS Device. This both tests the connection as makes sure that the RTIS Dev version used on the remote device is supported by the version of this wrapper. The only required argument is the IP of the remote RTIS Device. To learn more about how to find out the IP, please see this guide.

rtisdev = RTISDev("192.168.1.150");

Now the rtisdev object can be used to run RTIS Dev methods from.

Executing remote methods

After the connection is made and no errors were shown, you can now use all available RTIS Dev commands. Some don't work and are listed in the list above. Please use the RTIS Dev wiki to know which arguments to use. The commands should be called from the rtisdev objects. For example:

rtisdev.open_connection();

Arguments

There is a difference between using optional and required arguments. For example, a RTIS Dev method with a required argument needs to given explicitly:

rtisdev.set_settings_from_class(settings);

Whereas optional arguments should be given as name/value pairs:

rtisdev.set_recording_settings('callDuration', 4.4, 'callMinimumFrequency', int32(30000), 'callMaximumFrequency', int32(60000));

Please see the RTIS Dev wiki to know which arguments are optional and which are required.

Data types

As seen in the example below, place special attention to some data types as otherwise the argument parser will give an error. Integers should be actual integers and created with int32(). Similarly, strings need double quotations to be a true string.

rtisdev.set_recording_settings('callMinimumFrequency', int32(30000), 'configName',  "test");

Some methods return or require one of the RTIS Dev custom class object. The RTIS Dev MATLAB wrapper will automatically convert these to MATLAB struct objects. When these structs are provided as arguments, the wrapper will automatically convert them again so it should all work straight out of the box!

settings = rtisdev.get_current_settings();
rtisdev.set_settings_from_class(settings);

measurement_raw = rtisdev.get_raw_measurement('behaviour', true);
measurement_processed_from_raw = rtisdev.process_measurement(measurement_raw);

Example

A bigger example showing how to connect, record and process a measurement and plot the microphone signals and RTIS Energyscape.

%% Configure and run RTIS Dev

% Connect and verify matching versions of RTIS Dev
rtisdev = RTISDev("192.168.1.150");

% Connect to RTIS Device
rtisdev.open_connection();

% Configure the recording and processing settings
config_uuid = rtisdev.set_recording_settings('premade', "default_25_50");
rtisdev.set_processing_settings(config_uuid, 'premade', "2D_5m_181");
settings = rtisdev.get_current_settings();

% Get an ACTIVE measurement (protect your ears!) and process it
measurement_processed = rtisdev.get_processed_measurement('behaviour', true);

%% Plot raw microphone data

% Convert decimal data format to binary
data =  de2bi(measurement_processed.rawData, 32);

% Generate settings for converting to microphone signals. These have to match the recording settings!
fs_pdm = double(settings.pdmSampleFrequency); % PDM samplefrequency
fs_mic = double(settings.dacSampleFrequency); % Microphone samplefrequency

% PDM demodulation of binary data to the microphone signals
[b_pdm, a_pdm] = butter(6, 100e3 / ( fs_pdm / 2));
[b_bpf, a_bpf] = butter(6, [20e3 80e3] / (fs_mic / 2));
data_filtered = (filter(b_pdm, a_pdm, data));
data_filtered_dec = data_filtered(1:10:end, :);
data_mics = filter(b_bpf, a_bpf, data_filtered_dec);

% Plot the recording microphone signals
figure()
for plotcounter = 1 : 16
    subplot(4, 4, plotcounter);
    sig_out1 = data_mics(:, plotcounter) - mean(data_mics(:,plotcounter));
    plot(sig_out1 + 1);
    hold on;
    sig_out2 = data_mics(:, plotcounter + 16) - mean(data_mics(:, plotcounter + 16));
    plot(sig_out2  - 1);
    ylim([-1.5 1.5])
    hold off;
    plottitle = sprintf('Microphone %d and %d', plotcounter, plotcounter + 16);
    title(plottitle);
end 

%% Plot of processed data
figure()
imagesc(measurement_processed.processedData');
colormap hot
xlabel("Directions (degrees)")
ylabel("Range (meters)")
ax = gca;
set(gca,'Ydir','normal')
xt = get(gca, 'XTick');    
yt = get(gca, 'YTick');    
xt = 1 : 15 : length(settings.directions);
yt = 1 : 100 : length(settings.ranges);
xtlbl = rad2deg(settings.directions(xt));
ytlbl = settings.ranges(yt);
ytickformat('%.1f')
set(gca, 'XTick',xt, 'XTickLabel',xtlbl)
set(gca, 'YTick',yt, 'YTickLabel',ytlbl)
title('Energyscape');