Skip to content
Snippets Groups Projects
Commit 14263cf9 authored by dawehr's avatar dawehr
Browse files

Added Data Analysis tool files from May 16-30's repository

parent b26afcdf
No related branches found
No related tags found
No related merge requests found
Showing
with 4673 additions and 0 deletions
File added
File added
function [] = cam_sys_data_load( varargin )
%cam_sys_data_load(...)
%
% USE:
%
% Produces a structure containing the time data, x axis position, y axis
% position, z axis position, roll Euler angle, pitch Euler angle, and yaw
% Euler angle for each CSV file produced by Optitrack Tracking Tools
% contained in a given directory.
%
% SYNTAX:
%
% cam_sys_data_load( path )
%
% Optional Inputs:
%
% path is a string containing the name of the directory containing the
% CSV files to be read in. If this argument is not included, the user
% will be prompted to choose a director through a GUI menu.
%
% Outputs:
%
% One or more instances of a structure containing vectors for time,
% position and orientation. For an output structure called data:
% data.t (time stamp vector)
% data.x (x axis position vector)
% data.y (y axis position vector)
% data.z (z axis position vector)
% data.phi (roll Euler angle vector)
% data.theta (pitch Euler angle vector)
% data.psi (yaw Euler angle vector)
%
% ***The structure names will generally be the same as the CSV file
% names, unless the file name is not a valid MATLAB variable name in
% which case it will be renamed data#, where # will be the index
% where the file would appear in the result of a dir or ls command.
%
% AUTHOR(s):
%
% Matt Rich
% Graduate Student
% Electrical and Computer Engineering Department
% Iowa State University
% m87rich@iastate.edu
%
% LAST MODIFIED:
%
% 13-Mar-2012 (Matt Rich) : initial creation
%
%
if isempty(varargin)
path = uigetdir('.','Choose a directory containing the Optitrack CSV files you want to load.');
else
path = varargin{end};
end
files = dir(path);
fileIndex = find(~[files.isdir]);
for k = 1:length(fileIndex)
fileName = files(fileIndex(k)).name;
if strcmpi('.csv',fileName(end-3:end))
if isvarname(fileName(1:end-4))
assignin('base',fileName(1:end-4),cam_sys_data_read([path,'\',fileName]));
else
assignin('base',['data',num2str(k)],cam_sys_data_read([path,'\',fileName]));
disp([fileName(1:end-4),' has been renamed data',num2str(k),...
' in order to be a valid MATLAB variable name.']);
end
else
disp([fileName,' not loaded since it is not a CSV file.']);
end
end
end
function data = cam_sys_data_read(filename)
%cam_sys_data_read(...)
%
% USE:
%
% Produces a structure containing the time data, x axis position, y axis
% position, z axis position, roll Euler angle, pitch Euler angle, and yaw
% Euler angle from a CSV file produced by Optitrack Tracking Tools.
%
% SYNTAX:
%
% data = cam_sys_data_read(filename)
%
% Inputs:
%
% filename is a string containing the name of the CSV file to be read in
%
% Outputs:
%
% data is a structure containing vectors for time, position and
% orientation:
% data.t (time stamp)
% data.x (x axis position)
% data.y (y axis position)
% data.z (z axis position)
% data.phi (roll Euler angle *(as reported by Tracking Tools))
% data.theta (pitch Euler angle *(as reported by Tracking Tools))
% data.psi (yaw Euler angle *(as reported by Tracking Tools))
% data.qx = 1st quaternion component
% data.qy = 1st quaternion component
% data.qz = 1st quaternion component
% data.qw = 1st quaternion component
%
% *The Euler Angles reported by Tracking Tools may be incorrect
% depending on the setup of the axes. As of 3-14-13, they are
% incorrect since the axes are set up to provide the correct
% information for the VRPN decoding of the MicroCART base station
% software, which assumes a Yaw-Pitch-Roll sequence of rotations.
% The quaternions can be used to obtain the correct Euler angles if
% the rotation sequence is known.
%
%
% AUTHOR(s):
%
% Matt Rich
% Graduate Student
% Electrical and Computer Engineering Department
% Iowa State University
% m87rich@iastate.edu
%
% LAST MODIFIED:
%
% 13-Mar-2012 (Matt Rich) : initial creation
% 14-Mar-2013 (Matt Rich) : added quaternion extraction
%
%
[num,txt,raw] = xlsread(filename);
data.t = raw(45:end,3); data.t = [data.t{1:2:end}];
data.x = raw(45:end,6); data.x = [data.x{1:2:end}];
data.y = raw(45:end,7); data.y = [data.y{1:2:end}];
data.z = raw(45:end,8); data.z = [data.z{1:2:end}];
data.psi = raw(45:end,13); data.psi = [data.psi{1:2:end}];
data.theta = raw(45:end,14); data.theta = [data.theta{1:2:end}];
data.phi = raw(45:end,15); data.phi = [data.phi{1:2:end}];
data.qx = raw(45:end,9); data.qx = [data.qx{1:2:end}];
data.qy = raw(45:end,10); data.qy = [data.qy{1:2:end}];
data.qz = raw(45:end,11); data.qz = [data.qz{1:2:end}];
data.qw = raw(45:end,12); data.qw = [data.qw{1:2:end}];
end
This diff is collapsed.
#
#**********************************************
#Custom Header:::::
#Settings: x y z
#Constants: 1 2 3
#Contents will be printed to MATLAB terminal
#**********************************************
#
#▼▼▼▼ - Time must be included for parser to work properly needs to be exactly the following string: 'Time'
%Time Header1 Header2 Header3 Header4 b
&sec Unit1 Unit2 Unit3 Unit4 b
1 1 1 100 0 0
2 1 2 80 .5 -1
3 1 3 60 1 1
4 1 4 40 .5 -.5
5 1 5 20 0 0
Source diff could not be displayed: it is too large. Options to address this: view the blob.
This diff is collapsed.
%% ANALYSIS CONFIGURATION OPTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Modify your analysis configuration options here
% FNAME %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% if you know the name of the log file that you want to parse, set the it
% here only if it is in the working directory. Otherwise, you may leave it
% blank. You will be able to choose the file to parse through an explorer
% window.
%
%fname = 'sampleLogFileWithMarker.txt';
fname = 'testies_v2.txt';
% PLOTTING SWITCHES - set them to 0 or 1 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
plot = 1; % to choose plotting
separatePlot = 1; % to generate separatePlots
multiPlot = 1; % to generate multiPlot
subPlot = 0; % to generate subPlots
clearFigs = 0; % to close all the plots (needed only by the GUI)
% DATA TO PLOT %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% SEPARATEDATA
% write names of the data headers that you want to plot using
% seperatePlots. If this is empty but "plot" switch is 1, all the columns
% will be plotted using seperatePlots.
%
separateData = {'PID_roll_vel'};
% MULTIDATA
% write names of the data headers that you want to plot using multiPlots.
% If this is empty but "plot" switch is 1, the data headers in separateData
% will be plotted using multiPlots.
%
multiData = {};
% SUBDATA
% write names of the data headers that you want to plot using subPlots.
% If this is empty but "plot" switch is 1, the data headers in multiData
% will be plotted using subPlots.
%
subData = {};
% COLOR FOR PLOTTING %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
color = 'r'; % one character for color of the plotting line
marker = ''; % one character for the marker of the plotting line
style = ':'; % one character for the style of the plotting line
backgnd = [1 1 1]; % rgb array for background color of the plot
%% DO NOT MODIFY %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
fpath = '';
if(isempty(fname))
[fname, fpath] = uigetfile('.txt','Select log file');
end
% storing file options in the structure
params.file.name = fname; % file name only
params.file.path = fpath; % file path only
params.file.pathName = [fpath fname]; % file path with file name
% storing plotting parameters in the structure
params.plotting.plot = plot;
params.plotting.separatePlot = separatePlot;
params.plotting.multiPlot = multiPlot;
params.plotting.subPlot = subPlot;
params.plotting.clearFigs = clearFigs;
% storing plotting data in the structure
params.plotting.separateData = separateData;
params.plotting.multiData = multiData;
params.plotting.subData = subData;
% storing colors for plotting in the struture
params.plotting.color = color;
params.plotting.marker = marker;
params.plotting.style = style;
params.plotting.backgnd = backgnd;
% saving params into a file
%save params params;
% DO NOT MODIFY - END
%% parsing the log file specified %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% parse the log and instantiate the data structure, expData
%
expData = parse_log(params.file.pathName, params);
%save expData expData;
%% plotting routines %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% plot the data accoriding to the plotting parameters set
%
plot_data(expData, params.plotting);
%% creating the main structure to be stored in the workspace %%%%%%%%%%%%%
%
main.params = params;
main.expData = expData;
clearvars -except main;
save main main;
\ No newline at end of file
File added
This diff is collapsed.
function plotCharStr = buildPlotCharString(plotParams)
%buildPlotCharString builds a character string for plotting using the
%plotParams input structure
% plotParams : structure that contains the plotting style parameters.
% fields of plotParams:
% plotParams.plot
% plotParams.style
% plotParams.color
% plotParams.marker
% plotParams.backgnd
%
% keeps track of the index in the string
i = 1;
% color
if(~isempty(plotParams.color))
plotCharStr(i) = plotParams.color;
i = i + 1;
end
% marker
if(~isempty(plotParams.marker))
plotCharStr(i) = plotParams.marker;
i = i + 1;
end
% style
if(~isempty(plotParams.style))
plotCharStr(i) = plotParams.style;
i = i + 1;
end
% sanity check for the string
if(~isPlotCharString(plotCharStr))
error('Wrong plot style formatting options, please use allowed values only');
end
end
function y = haveDiffPlotStyles(data,headers)
% haveDiffPlotStyles checks to see if the headers in the data structure
% have different plotting parameters
%
% This function ONLY compares the color, marker and style fields of the
% params structure.
% initialize to true
y = 1;
% return 1 if only one
if(length(headers) == 1)
y = 1;
return
end
% obtaining the plotting params structure from each header
j = 0;
for i = 1:length(headers)
entity = headers{i};
headerPlotParams(i) = eval(['data.' entity '.params']);
end
% check if there are more than two defaults
numOfDefaults = 0;
for i = 1:length(headerPlotParams)
if(isDefaultPlotCharString(headerPlotParams(i)))
numOfDefaults = numOfDefaults + 1;
if(numOfDefaults >= 2)
y = 0;
return
end
else
end
end
% checking for equality between the plotting parameters
colorEqual = 0;
markerEqual = 0;
styleEqual = 0;
for i = 1:length(headerPlotParams)
for j = 1:length(headerPlotParams)
if(i == j)
continue;
else
if(strcmp(headerPlotParams(i).color, headerPlotParams(j).color) == 1)
colorEqual = 1;
end
if(strcmp(headerPlotParams(i).marker, headerPlotParams(j).marker) == 1)
markerEqual = 1;
end
if(strcmp(headerPlotParams(i).marker, headerPlotParams(j).marker) == 1)
styleEqual = 1;
end
if(colorEqual && markerEqual && styleEqual)
y = 0;
return;
end
colorEqual = 0;
markerEqual = 0;
styleEqual = 0;
end
end
end
end
function y = isDefaultPlotCharString(plotParams)
%isDefaultPlotCharString Compares the input plotParams structure to the
%default plotting format:
% color b
% marker (none)
% style -
% Return 1 if it is the default plotting style. Returns 0 otherwise
defaultColor = 0;
defaultMarker = 0;
defaultStyle = 0;
% checking plotting color
if(plotParams.color == 'b' || isempty(plotParams.color))
defaultColor = 1;
end
% checking plotting marker
if(isempty(plotParams.marker))
defaultMarker = 1;
end
% checking plotting style
if(plotParams.style == '-' || isempty(plotParams.style))
defaultStyle = 1;
end
% final check
if(defaultColor && defaultMarker && defaultStyle)
y = 1;
else
y = 0;
end
end
function y = isPlotCharString(str)
% isPlotCharString sees if the str is composed of characeters that are used
% in making up a plot formatting string.
% str - string to check
if (length(str) <= 4)
% if the input string is empty, it is a valid plot formatting character
% string
if(length(str) == 0)
y = 1;
return
end
% list of possible characters allowed in the string
plotTypeChars = ['bgrcmykw.ox+*sdv^<>ph-:.'];
for i = 1:length(str)
if (ismember(str(i),plotTypeChars))
y = 1;
continue
else
y = 0;
break;
end
end
else
y = 0;
end
end
\ No newline at end of file
File added
function trackableData = parse_camera_log(filepath)
%loads position, quaternion orientation and euler angles from rigidbody
%trajectories exported to csv in Motive 1.5.1 and returns them in the
%array of structs
%tested for one and three rigid bodies
%license: GPL, author Frieder Wittmann, email frieder.wittmann@gmail.com
openedFile = fopen(filepath,'r');
currentLineNo = 0;
%go through the first lines which dont contain data of interest
for lineIndex = 1:41 % edited by RZ: to match the OptiTrack Tools software used by the Controls Lab at Iowa State University
readNextLine(openedFile);
currentLineNo = currentLineNo +1;
end
commaSeperatedValues = csvStringFromOpenedFile(openedFile);
numberOfFrames = str2num(commaSeperatedValues{3})
commaSeperatedValues = csvStringFromOpenedFile(openedFile);
numberOfRidgidBodies = str2num(commaSeperatedValues{3})
%create container of size numberOfRidgidBodies for the output data
RigidBodies = repmat(struct(...
'Name', 'empty_name', ... % added by RZ: name of the trackable
'T', NaN(numberOfFrames,1), ...
'P', NaN(numberOfFrames,3), ...
'Q', NaN(numberOfFrames,4), ...
'Euler', NaN(numberOfFrames,3)),numberOfRidgidBodies,1);
%the next lines contain information about the markerpositions on the ridigd bodies. we ignore this infrmation
for i = 1:numberOfRidgidBodies
commaSeparatedValues = csvStringFromOpenedFile(openedFile);
name = commaSeparatedValues{2};
if(isequal(name(1),'"')) % taking care of this issue. Occurs sometimes only.
name(1) = '';
name(end) = '';
end
RigidBodies(i).Name = name;
end
frameIndex = 0; %every nth (numberOfRidgidBodies+1) contains the ridgidbody information of a frame/timestamp
numberOfLinesUntilNextFrameLine = numberOfRidgidBodies+1;
for lineIndex = 1:numberOfFrames*numberOfLinesUntilNextFrameLine
%there is always a frame line and then one line per rigid body with details which are not of interest to us here
currentLineContent = readNextLine(openedFile);
%if current line is a line with frame information
if( mod(lineIndex,numberOfLinesUntilNextFrameLine) == 1)
frameIndex = frameIndex+1; %we're at the next frame
frameLine = currentLineContent;
commaSeperatedValues = regexp(frameLine, ',', 'split');
frameIndexFromFile = str2num(commaSeperatedValues{2});
timestamp = str2num(commaSeperatedValues{3});
%check how many ridig bodies were tracked, sometimes so are out of
%sight and hence not tracked
numberOFTrackedRidigdBodiesInThisFrame = str2num(commaSeperatedValues{4});
currentCSVIndex = 4;
if (numberOFTrackedRidigdBodiesInThisFrame > 0)
currentCSVIndex = currentCSVIndex+1;
currentRidgidBodyID = str2num(commaSeperatedValues{currentCSVIndex});
for(expectedRidigbBodyID = 1:numberOfRidgidBodies + 1)
if (expectedRidigbBodyID ~= currentRidgidBodyID)
break %go to next
end
currentCSVIndex = currentCSVIndex+1;
[p, q, euler ] = readPQEulerStartingAtIndex(currentCSVIndex, commaSeperatedValues);
RigidBodies(currentRidgidBodyID).T(frameIndex,:) = timestamp;
RigidBodies(currentRidgidBodyID).P(frameIndex,:) = p;
RigidBodies(currentRidgidBodyID).Q(frameIndex,:) = q;
RigidBodies(currentRidgidBodyID).Euler(frameIndex,:) = euler;
currentCSVIndex = currentCSVIndex+10; %the ten values are p(3),q(4)euler(3)=10
if (currentCSVIndex + 11 < length(commaSeperatedValues))
currentRidgidBodyID = str2num(commaSeperatedValues{currentCSVIndex}); %get next ridgid body id
else
break;
end
end
end
end
end
% added by RZ: to output the structure in readable format
trackableData.numOfTrackables = length(RigidBodies);
for i=1:trackableData.numOfTrackables
eval(['trackableData.' RigidBodies(i).Name ' = RigidBodies(i);']);
end
end
function lineContent = readNextLine(openedFile)
lineContent = fgetl(openedFile);
end
function csvString = csvStringFromOpenedFile(openedFile)
lineContent = readNextLine(openedFile);
csvString = regexp(lineContent, ',', 'split');
end
function [p, q, euler] = readPQEulerStartingAtIndex(index, commaSeperatedValues)
positionX = str2double(commaSeperatedValues{index});
positionY = str2double(commaSeperatedValues{index+1});
positionZ = str2double(commaSeperatedValues{index+2});
p = [positionX, positionY, positionZ];
QuaternionX = str2double(commaSeperatedValues{index+3});
QuaternionY = str2double(commaSeperatedValues{index+4});
QuaternionZ = str2double(commaSeperatedValues{index+5});
QuaternionW = str2double(commaSeperatedValues{index+6});
q = [QuaternionX, QuaternionY, QuaternionZ, QuaternionW];
EulerX = str2double(commaSeperatedValues{index+7});
EulerY = str2double(commaSeperatedValues{index+8});
EulerZ = str2double(commaSeperatedValues{index+9});
euler = [EulerX, EulerY, EulerZ];
end
\ No newline at end of file
function [loggedData] = parse_log(filename, params, expData)
%parse_log This independent function parses the data stored in the file and
%returns a structure containing the data
% filename - this is the complete path of the file with the filename
% params - this is the params structure which holds the analysis
% configuration options
% Check if file exists
if (~exist(filename,'file'))
error(strcat(filename, ' does not exist'));
end
% Open file
FileID = fopen(filename, 'r');
% Gets the first line of the file
string = fgetl(FileID);
% Test first line, if not formatted correctly, reject
if(size(regexp(string, '^#')) == 0)
error(strcat(filename, ' is not properly formatted, and does not contain "#" headers'));
end
% Loop through header lines
while( regexp(string, '^#') == 1 )
%Print out string and move on
disp(string)
old = string;
string = fgetl(FileID);
end
% Two possibilities for the next two lines:
% 1) line of headers
% 2) line of units
foundHeaders = 0;
foundUnits = 0;
% Checking current line's type:
identifier = string(1);
if (regexp(identifier,'%'))
foundHeaders = 1;
% this is a line of headers; extract headers:
headers = strsplit(string);
headers{1} = strrep(headers{1},'%', '');
numOfHeaders = length(headers);
else
if (regexp(identifier,'&'))
foundUnits = 1;
% this is a line of units; extract units:
units = strsplit(string);
units{1} = strrep(units{1},'&','');
else
error(strcat(filename, ' is not properly formatted, contains undefined line identifier.'));
end
end
% Obtaining the next line
string = fgetl(FileID);
identifier = string(1);
if(foundHeaders)
if(regexp(identifier,'&'))
foundUnits = 1;
% this is a line of units; extract units:
units = strsplit(string);
units{1} = strrep(units{1},'&','');
else
error(strcat(filename, ' is not properly formatted, contains or undefined/excessive line identifiers.'));
end
else
if(foundUnits)
if(regexp(identifier,'%'))
% this is a line of headers; extract headers:
headers = strsplit(string);
headers{1} = strrep(headers{1},'%', '');
numOfHeaders = length(headers);
end
else
error('Should never be able to get here');
end
end
% sanity check and clean up
if(numOfHeaders ~= length(units))
error(strcat(filename, ' is not properly formatted, contains unmatched number of units and headers'));
end
clear foundHeaders foundUnits;
% Get all data into a single matrix called "log"
log = [];
line = zeros(1,numOfHeaders);
while ~feof(FileID)
line = textscan(FileID, '%f', numOfHeaders);
line = transpose(cell2mat(line));
log = [log;line];
end
% Converting the log matrix into a expData structure.
for i = 1:numOfHeaders
eval(['loggedData.' headers{i} '.data = log(:,i);']); % adding data
eval(['loggedData.' headers{i} '.unit = cell2mat(units(i));']); % adding unit
eval(['loggedData.' headers{i} '.params.plot = 0;']); % adding params.plot
eval(['loggedData.' headers{i} '.params.style = ''-'';']); % adding params.style
eval(['loggedData.' headers{i} '.params.color = ''b'';']); % adding params.color
eval(['loggedData.' headers{i} '.params.marker = '''';']); % adding params.marker
eval(['loggedData.' headers{i} '.params.backgnd = [1 1 1];']); % adding params.backgnd
end
% data types are set
if exist('params', 'var')
% setting the value of <header-name>.params.plot value
if(params.plotting.plot == 1)
if(params.plotting.subPlot == 1)
if(isempty(params.plotting.subData))
if(isempty(params.plotting.multiData))
if(isempty(params.plotting.separateData))
for i = 1:numOfHeaders
eval(['loggedData.' headers{i} '.params.plot = 1;']);
end
else
for i = 1:length(params.plotting.separateData)
eval(['loggedData.' params.plotting.separateData{i} '.params.plot = 1;']);
end
end
else
for i = 1:length(params.plotting.multiData)
eval(['loggedData.' params.plotting.multiData{i} '.params.plot = 1;']);
end
end
else
for i = 1:length(params.plotting.subData)
eval(['loggedData.' params.plotting.subData{i} '.params.plot = 1;']);
end
end
end
if(params.plotting.multiPlot == 1)
if(isempty(params.plotting.multiData))
if(isempty(params.plotting.separateData))
for i = 1:numOfHeaders
eval(['loggedData.' headers{i} '.params.plot = 1;']);
end
else
for i = 1:length(params.plotting.separateData)
eval(['loggedData.' params.plotting.separateData{i} '.params.plot = 1;']);
end
end
else
for i = 1:length(params.plotting.multiData)
eval(['loggedData.' params.plotting.multiData{i} '.params.plot = 1;']);
end
end
end
if(params.plotting.separatePlot == 1)
if(isempty(params.plotting.separateData))
for i = 1:numOfHeaders
eval(['loggedData.' headers{i} '.params.plot = 1;']);
end
else
for i = 1:length(params.plotting.separateData)
eval(['loggedData.' params.plotting.separateData{i} '.params.plot = 1;']);
end
end
end
else
% nothing really needed to do here since the default value of
% <header-name>.params.plot is 0
end
% setting the following values to those set in DataAnalysis.m
% 1) <header-name>.params.style
% 2) <header-name>.params.color
% 3) <header-name>.params.marker
% 4) <header-name>.params.backgnd
for i = 1:numOfHeaders
eval(['loggedData.' headers{i} '.params.style = params.plotting.style;']);
eval(['loggedData.' headers{i} '.params.color = params.plotting.color;']);
eval(['loggedData.' headers{i} '.params.marker = params.plotting.marker;']);
eval(['loggedData.' headers{i} '.params.backgnd = params.plotting.backgnd;']);
end
end
% converting time to relative time
loggedData.Time.data = loggedData.Time.data - loggedData.Time.data(1);
% this is to parse the Marker field, if it exists
if (isfield(loggedData,'Marker'))
c = zeros(numel(loggedData.Marker.data),1);
for i = 2: numel(loggedData.Marker.data)
if (loggedData.Marker.data(i)>loggedData.Marker.data(i-1))
c(i) = loggedData.Marker.data(i);
end
end
loggedData.Marker.data = c;
end
% if expData was sent in as a variable, then update the plotting parameters
% of loggedData to be the same as that in the existing data structure
if (exist('expData','var'))
if(isempty(setdiff(headers,expData.datafields)))
for i = 1:numOfHeaders
eval(['loggedData.' headers{i} '.params.style = expData.' headers{i} '.params.style;']);
eval(['loggedData.' headers{i} '.params.color = expData.' headers{i} '.params.color;']);
eval(['loggedData.' headers{i} '.params.marker = expData.' headers{i} '.params.marker;']);
eval(['loggedData.' headers{i} '.params.backgnd = expData.' headers{i} '.params.backgnd;']);
end
end
end
end
function plot_data(expData, plotParams)
%PLOT_DATA This function plots the data according to the parameters mentioned in params
% expData - structure that contains the data to be plotted
% plotParams - structure that contains the plotting options
% check plotting switch
if (~plotParams.plot)
disp('No plotting');
else
%% check separate plotting switch
if(plotParams.separatePlot)
% bulding the plot_separate statement that will be executed
plot_separateString = 'plot_separate(expData,0,''';
% extracting data headers to plot
if(isempty(plotParams.separateData))
headers = fieldnames(expData); % if none mentioned, use all of the headers
headers = headers(2:end); % except Time :)
else
headers = plotParams.separateData;
end
% adding the headers to the plot_separate statement
for i = 1:length(headers)
if(i==length(headers))
plot_separateString = strcat(plot_separateString,headers{i},''');');
else
plot_separateString = strcat(plot_separateString,headers{i},''',''');
end
end
% executing the plot_separate statement
eval(plot_separateString);
end
%% check multi plotting switch
if(plotParams.multiPlot)
% building the plot_multi statement that will be executed
plot_multiString = 'plot_multi(expData,0,''';
% extracting data headers to plot
if(isempty(plotParams.multiData)) % if none mentioned, use headers for separate plotting
if(isempty(plotParams.separateData))
headers = fieldnames(expData); % if no headers mentioned for separate plotting, use all of the headers
else
headers = plotParams.separateData;
end
else
headers = plotParams.multiData;
end
% adding the headers to the plot_multi statement
for i = 1:length(headers)
if(i==length(headers))
plot_multiString = strcat(plot_multiString,headers{i},''');');
else
plot_multiString = strcat(plot_multiString,headers{i},''',''');
end
end
% executing the plot_multi statement
eval(plot_multiString);
end
%% check sub plotting switch
if(plotParams.subPlot)
% building the plot_sub statement that will be executed
plot_subString = 'plot_sub(expData,0,''';
% extracting data headers to plot
if(isempty(plotParams.subData)) % if none mentioned, use headers mentioned for multi plotting
if(isempty(plotParams.multiData)) % if no headers mentioned for multi plotting, use headers mentioned for separate plotting
if(isempty(plotParams.separateData)) % if no headers mentioned for separate plotting, use all of the headers
headers = fieldNames(expData);
else
headers = plotParams.separateData;
end
else
headers = plotParams.multiData;
end
else
headers = plotParams.subData;
end
% adding the headers to the plot_sub statement
for i = 1:length(headers)
if(i==length(headers))
plot_subString = strcat(plot_subString,headers{i},''');');
else
plot_subString = strcat(plot_subString,headers{i},''',''');
end
end
% executing the plot_sub statement
eval(plot_subString);
end
end
end
function plot_multi(expData, useMarker, varargin)
%PLOT_MULTI This function is used to plot multiple headers on the same plot
% expData - structure that stores all of the data
% useMarker - flag to indicated whether or not to plot vertical lines
% at the marker locations
% varargin - the header names and corresponding plotting parameters
%
% Example of varargin: 'Pitch','r-','Roll','Yaw','go'
% This means that Pitch will be plotted in red solids, Roll with no
% special formatting and Yaw in green circles.
% calculating number of headers
numOfHeaders = 0;
headers = {};
for i = 1:length(varargin)
if(~isPlotCharString(varargin{i}))
numOfHeaders = numOfHeaders + 1;
headers{numOfHeaders} = varargin{i};
end
end
% checking to see validity of varargin
if (length(varargin) > (numOfHeaders*2))
error('Too many arguments entered');
end
% if the plotting style params for each header are different, diffPlotStyles = 1
diffPlotStyles = haveDiffPlotStyles(expData,headers);
% extracting time structure
time = expData.Time;
% extract markerlocations, if any
markerLocations = [];
if(useMarker)
if(~isfield(expData,'Marker'))
error('Error! Attempting to plot markers without Marker field');
else
markerLocations = find(expData.Marker.data);
end
end
% initiliazing final plot statement to be executed
plotString = ['plot(time.data,expData.'];
% building the plot statement to be executed
for i = 1:length(varargin)
entity = varargin{i};
plotString = strcat(plotString,entity);
if (i~=length(varargin))
% adding plot style character string
if (isPlotCharString(entity))
% entity is a plot character string here
plotString = strcat(plotString,''',time.data,expData.');
else
% entity is a header here
plotString = strcat(plotString,'.data,');
% extracting next entity
nextEntity = varargin{i+1};
% checking to see if next entity is a plot character string
if (isPlotCharString(nextEntity))
% if yes, add the required inverted commas
plotString = strcat(plotString,'''');
else
% if not, add the plot character string from header's params
if(diffPlotStyles)
% if the headers have different plotting style params
if(isDefaultPlotCharString(eval(['expData.' entity '.params'])))
% if the plotting params are default, don't bother
plotString = strcat(plotString,'time.data,expData.');
else
% else, construct a plot char string and append
plotCharString = buildPlotCharString(eval(['expData.' entity '.params']));
plotString = strcat(plotString,'''');
plotString = strcat(plotString,plotCharString);
plotString = strcat(plotString,''',');
plotString = strcat(plotString,'time.data,expData.');
end
else
% if two or more headers have the same plotting style
% params, don't construct their plot char strings
plotString = strcat(plotString,'time.data,expData.');
end
end
end
else
% this is the last entity in the varargin cell array
if(isPlotCharString(entity))
% if a plot character string, add the ending inverted comma
plotString = strcat(plotString,''');');
else
% if not, add the header's data to the plotString
plotString = strcat(plotString,'.data');
% and also add the plot character string from its params
if(diffPlotStyles)
% if the headers have different plotting style params
if (isDefaultPlotCharString(eval(['expData.' entity '.params'])))
% if the plotting params are default, don't worry
plotString = strcat(plotString,');');
else
% else, construct a plot char string and append
plotCharString = buildPlotCharString(eval(['expData.' entity '.params']));
plotString = strcat(plotString,',''');
plotString = strcat(plotString,plotCharString);
plotString = strcat(plotString,''');');
end
else
% if two or more headers have the same plotting style
% params, don't construct their plot char strings
plotString = strcat(plotString,');');
end
end
end
end
%% plotting stuff
figure; % opening a new figure
whitebg(gcf,[1 1 1]); % making sure the background is set to white
eval(plotString); % plotting
grid ON; % plotting grid lines
xlim([0,time.data(end)]); % setting x-axis limits
xlabel(['Time (' time.unit ')']); % setting x-axis label
%constructing yAxisLabel
yAxisLabel = [];
for i = 1:numOfHeaders
if i == numOfHeaders
yAxisLabel = strcat(yAxisLabel,headers{i});
if(eval(['isempty(expData.' headers{1} '.unit)']))
break;
else
yAxisLabel = strcat(yAxisLabel,'(', eval(['expData.' headers{1} '.unit']),')');
end
else
yAxisLabel = strcat(yAxisLabel,headers{i},',');
end
end
ylabel(yAxisLabel);
% constructing statement for inserting the legend
legendString = ['legend('''];
for i = 1:numOfHeaders
if(i == numOfHeaders)
legendString = strcat(legendString,headers{i},''',''Location'',''NorthWest'');');
else
legendString = strcat(legendString,headers{i},''',''');
end
end
eval(legendString);
% plotting markers, if any
for i = 1:numel(markerLocations)
%hx = graph2d.constantline(time.data(markerLocations(i)),'Linestyle','--', 'Color', [0.7 0.7 0.7]);
%changedependvar(hx,'x');
text(time.data(markerLocations(i)),(min(ylim)+max(ylim))/2,num2str(i));
end
end
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment