function [kSpace, evalMask] = extractKSpace_main(dData, iLC, iEvalInfoMask, measPara)
% extract kSpace data
%
% (c) Thomas Kuestner
% ---------------------------------------------------------------------

% set repetitions
if(measPara.LCall(4) ~= 1)
    iRepetitions = 1:measPara.LCall(4);
else
    iRepetitions = 1;
end

% set averages
if(measPara.LCall(2) ~= 1)
    iAverages = 1:measPara.LCall(2);
else
    iAverages = 1;
end

nSeg = double(max(iLC(:,11)) - min(iLC(:,11)) + 1);

fprintf(1, 'Preprocessing Channels\n');
if(strcmp(measPara.dimension,'2D'))
    % cell: slice - cha
    % in cell: k_y - k_x - (t)
    if(measPara.LCall(1) == 1)
        % one 2D slice was acquired
        iSlices = 1;
    else
        % several 2D slices were acquired
        iSlices = 1:measPara.LCall(1);
    end

    kSpace = cell(length(iSlices),measPara.dim(5),length(iRepetitions),length(iAverages));
    evalMask = cell(length(iSlices),measPara.dim(5),length(iRepetitions),length(iAverages));

    % extract phase correction data
    if(~isempty(iEvalInfoMask))
        lPhaseCorr = false(size(iLC,1),1);
        for iPhaseCorr=1:length(lPhaseCorr)
            lPhaseCorr(iPhaseCorr) = bitget(iEvalInfoMask(iPhaseCorr,1),22);
        end
        iLC = iLC(~lPhaseCorr,:);
        dData = dData(~lPhaseCorr,:);
        if(~isempty(iEvalInfoMask))
            iEvalInfoMask = iEvalInfoMask(~lPhaseCorr,:);
        end
    end

    totalCount = length(iRepetitions)*length(iAverages)*measPara.dim(5)*length(iSlices)*measPara.dim(4)*nSeg;
    dispProgress('Extracting K-Space', 0, totalCount);
    for iRep=1:length(iRepetitions)
        dDataRep = dData(iLC(:,9) == iRepetitions(iRep)-1, :);
        iLCRep = iLC(iLC(:,9) == iRepetitions(iRep)-1, :);
        if(~isempty(iEvalInfoMask))
            iEvalInfoMaskRepLC = iEvalInfoMask(iLC(:,9) == iRepetitions(iRep)-1, :);
        end
        for iAvg=1:length(iAverages)
            dDataAvg = dDataRep(iLCRep(:,4) == iAverages(iAvg)-1, :);
            iLCAvg = iLCRep(iLCRep(:,4) == iAverages(iAvg)-1, :);
            if(~isempty(iEvalInfoMask))
                iEvalInfoMaskAvgLC = iEvalInfoMaskRepLC(iLCRep(:,4) == iAverages(iAvg)-1, :);
            end
            for iSli=1:length(iSlices)
                dDataSli = dDataAvg(iLCAvg(:,5) == iSlices(iSli)-1, :);
                iLCSli = iLCAvg(iLCAvg(:,5) == iSlices(iSli)-1, :);
                if(~isempty(iEvalInfoMask))
                    iEvalInfoMaskSliLC = iEvalInfoMaskAvgLC(iLCAvg(:,5) == iSlices(iSli)-1, :);
                else
                    iEvalInfoMaskSliLC = [];
                end

                [kSpace(iSli,:,iRep,iAvg), evalMask(iSli,:,iRep,iAvg)] = extractKSpace2D(dDataSli, iLCSli, iEvalInfoMaskSliLC, measPara.dim, [iRep, iAvg, iSli, totalCount, length(iAverages), length(iSlices)]);
                dispProgress('Extracting K-Space', ((iRep-1)*length(iAverages)*measPara.dim(5)*length(iSlices)*measPara.dim(4)*nSeg + (iAvg-1)*measPara.dim(5)*length(iSlices)*measPara.dim(4)*nSeg + iSli*measPara.dim(5)*measPara.dim(4)*nSeg)/totalCount);
            end
            dispProgress('Extracting K-Space', ((iRep-1)*length(iAverages)*measPara.dim(5)*length(iSlices)*measPara.dim(4)*nSeg + iAvg*measPara.dim(5)*length(iSlices)*measPara.dim(4)*nSeg)/totalCount);
        end
        dispProgress('Extracting K-Space', iRep/length(iRepetitions));
    end
    dispProgress('Extracting K-Space', 'Close');

elseif(strcmp(measPara.dimension,'3D'))
    % cell: 1 - cha
    % in cell: k_y - k_x - k_z

    kSpace = cell(1,measPara.dim(5),length(iRepetitions),length(iAverages));
    evalMask = cell(1,measPara.dim(5),length(iRepetitions),length(iAverages));
    totalCount = length(iRepetitions)*measPara.dim(5)*measPara.dim(3)*nSeg;
    dispProgress('Extracting K-Space', 0, totalCount);
    for iRep=1:length(iRepetitions)
        dDataRep = dData(iLC(:,9) == iRepetitions(iRep)-1, :);
        iLCRep = iLC(iLC(:,9) == iRepetitions(iRep)-1, :);
        if(~isempty(iEvalInfoMask))
            iEvalInfoMaskRepLC = iEvalInfoMask(iLC(:,9) == iRepetitions(iRep)-1, :);
        end
        for iAvg=1:length(iAverages)
            dDataAvg = dDataRep(iLCRep(:,4) == iAverages(iAvg)-1, :);
            iLCAvg = iLCRep(iLCRep(:,4) == iAverages(iAvg)-1, :);
            if(~isempty(iEvalInfoMask))
                iEvalInfoMaskAvgLC = iEvalInfoMaskRepLC(iLCRep(:,4) == iAverages(iAvg)-1, :);
            else
                iEvalInfoMaskAvgLC = [];
            end
            [kSpace(1,:,iRep,iAvg), evalMask(1,:,iRep,iAvg)] = extractKSpace3D(dDataAvg, iLCAvg, iEvalInfoMaskAvgLC, measPara.dim, [iRep,iAvg,totalCount]);
            dispProgress('Extracting K-Space', ((iRep-1)*length(iAverages) + iAvg)/(length(iRepetitions)*length(iAverages)));
        end
        dispProgress('Extracting K-Space', iRep/length(iRepetitions));
    end
    dispProgress('Extracting K-Space', 'Close');

elseif(strcmp(measPara.dimension,'4D'))
    % cell: 1 - cha
    % in cell: k_y - k_x - k_z - t

    % extract prescans/Navi for CS_Trufi
    if(max(iLC(:,1)) ~= min(iLC(:,1)))
        dData = dData(iLC(:,1) == measPara.dim(2),:);
        iLC = iLC(iLC(:,1) == measPara.dim(2),:);
        if(~isempty(iEvalInfoMask))
            iEvalInfoMask = iEvalInfoMask(iLC(:,1) == measPara.dim(2),:);
        end
    end
    if(strcmp(measPara.sequenceName,'CS_Trufi'))
        phaseLCcol = 10;
    else
        phaseLCcol = 8;
    end
    kSpace = cell(1,measPara.dim(5),length(iRepetitions),length(iAverages));
    evalMask = cell(1,measPara.dim(5),length(iRepetitions),length(iAverages));
    totalCount = length(iRepetitions)*measPara.dim(5)*measPara.dim(3)*nSeg*measPara.dim(4);
    dispProgress('Extracting K-Space', 0, totalCount);
    for iRep=1:length(iRepetitions)
        dDataRep = dData(iLC(:,9) == iRepetitions(iRep)-1, :);
        iLCRep = iLC(iLC(:,9) == iRepetitions(iRep)-1, :);
        if(~isempty(iEvalInfoMask))
            iEvalInfoMaskRepLC = iEvalInfoMask(iLC(:,9) == iRepetitions(iRep)-1, :);
        end
        for iAvg=1:length(iAverages)
            dDataAvg = dDataRep(iLCRep(:,4) == iAverages(iAvg)-1, :);
            iLCAvg = iLCRep(iLCRep(:,4) == iAverages(iAvg)-1, :);
            if(~isempty(iEvalInfoMask))
                iEvalInfoMaskAvgLC = iEvalInfoMaskRepLC(iLCRep(:,4) == iAverages(iAvg)-1, :);
            else
                iEvalInfoMaskAvgLC = [];
            end
            [kSpace(1,:,iRep,iAvg), evalMask(1,:,iRep,iAvg)] = extractKSpace4D(dDataAvg, iLCAvg, iEvalInfoMaskAvgLC, measPara.dim, [iRep,iAvg,totalCount], phaseLCcol);
            dispProgress('Extracting K-Space', ((iRep-1)*length(iAverages) + iAvg)/(length(iRepetitions)*length(iAverages)));
        end
        dispProgress('Extracting K-Space', iRep/length(iRepetitions));
    end
    dispProgress('Extracting K-Space', 'Close');

end

end


function figOffscreenCheck(fig);
% figOffscreenCheck([fig]): check that a figure
% doesn't get moved off the edges of the screen.
%
% This function checks the figure fig [default gcf]
% and, if it's running off the edge of the screen, moves / reshapes
% it to fit within the screen.
%
% ras, 07/05/05.
if ~exist('fig','var') | isempty(fig), fig = gcf;     end

% record the existing units of the figure, then set to normalized
% for now:
exUnits = get(fig,'Units');
set(fig,'Units','normalized');
pos = get(fig,'Position');

% first, check if either size argument is larger
% than the screen size (normalized value > 1):
if pos(3)>1, pos(3)=1; end
if pos(4)>1, pos(4)=1; end

% check if right edge out of bounds
if pos(1)+pos(3)>1,  pos(1) = 1-pos(3);    end

% check if left edge out of bounds
if pos(1)<0,    pos(1) = 0;    end

% check if upper edge out of bounds
% (allow extra 0.05 for toolbars which matlab sometimes adds)
if pos(2)+pos(4)>0.95,  pos(2) = 0.95-pos(4);    end

% check if lower edge out of bounds
if pos(2)<0,    pos(2) = 0;    end

% set new position
set(fig,'Position',pos);

% restore old unit convention
set(fig,'Units',exUnits);

return


% STD_ERPIMAGEPLOT - Commandline function to plot cluster ERPimage or channel erpimage.
%
% Usage:
%   >> [STUDY] = std_erpimageplot(STUDY, ALLEEG, key1, val1, key2, val2);
%   >> [STUDY data times freqs pgroup pcond pinter] = ...
%                std_erpimageplot(STUDY, ALLEEG ...);
% Inputs:
%   STUDY      - EEGLAB STUDY set comprising some or all of the EEG datasets in ALLEEG.
%   ALLEEG     - global EEGLAB vector of EEG structures for the datasets in the STUDY.
%                Note: ALLEEG for a STUDY set is typically created using LOAD_ALLEEG.
%
% Additional help:
% Inputs and output of this function are strictly identical to the STD_ERSPPLOT.
% See the help message of this function for more information.
%
% See also: STD_ERSPPLOT
%
% Authors: Arnaud Delorme, UCSD/CERCO, August, 2011-

% Copyright (C) Arnaud Delorme, arno@ucsd.edu
%
% This file is part of EEGLAB, see http://www.eeglab.org
% for the documentation and details.
%
% Redistribution and use in source and binary forms, with or without
% modification, are permitted provided that the following conditions are met:
%
% 1. Redistributions of source code must retain the above copyright notice,
% this list of conditions and the following disclaimer.
%
% 2. Redistributions in binary form must reproduce the above copyright notice,
% this list of conditions and the following disclaimer in the documentation
% and/or other materials provided with the distribution.
%
% THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
% AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
% IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
% ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
% LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
% CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
% SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
% INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
% CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
% ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
% THE POSSIBILITY OF SUCH DAMAGE.

function [STUDY, allitc, alltimes, allfreqs, pgroup, pcond, pinter, events] = std_erpimageplot(STUDY, ALLEEG, varargin)

if nargin < 2
    help std_erpimageplot;
    return;
end

events = [];
STUDY = pop_erpimparams(STUDY, 'default');
if strcmpi(STUDY.etc.erpimparams.concatenate, 'off')

    % use std_erspplot for stats when concatenate is off
    [STUDY allitc alltimes allfreqs pgroup pcond pinter events] = std_erspplot(STUDY, ALLEEG, 'datatype', 'erpim', varargin{:});

else
    params = STUDY.etc.erpimparams;
    [ opt moreparams ] = finputcheck( varargin, { ...
        'design'      'integer' [] STUDY.currentdesign;
        'topotime'    'real'    [] params.topotime;
        'topotrial'  'real'     [] params.topotrial;
        'timerange'   'real'    [] params.timerange;
        'trialrange'  'real'    [] params.trialrange;
        'colorlimits' 'real'    [] params.colorlimits; % ERPimage
        'statistics'  'string'  [] params.statistics;
        'groupstats'  'string'  [] params.groupstats;
        'condstats'   'string'  [] params.condstats;
        'threshold'   'real'    [] params.threshold;
        'naccu'       'integer' [] params.naccu;
        'mcorrect'    'string'  [] params.mcorrect;
        'erpimageopt' 'cell'    [] params.erpimageopt;
        'concatenate'  'string' { 'on','off' }  params.concatenate;
        'channels'    'cell'    []              {};
        'clusters'    'integer' []              [];
        'comps'       {'integer','string'}  []              []; % for backward compatibility
        'plotsubjects' 'string' { 'on','off' }  'off';
        'plotmode'    'string' { 'normal','condensed','none' }  'normal';
        'subject'     'string'  []              '' }, 'std_erpimageplot', 'ignore');

    if ~isempty(opt.topotime) && ~isempty(opt.topotrial)
        error('Cannot plot topography when ERP-image is in trial concatenation mode');
    end
    if ~isempty(opt.trialrange)
        error('Cannot select trial range when ERP-image is in trial concatenation mode');
    end
    if strcmpi(opt.groupstats, 'on') || strcmpi(opt.condstats, 'on')
        disp('Warning: cannot perform statistics when ERP-image is in trial concatenation mode');
    end

    % options
    if ~isempty(opt.colorlimits), options = { 'caxis' opt.colorlimits opt.erpimageopt{:} };
    else                          options = { 'cbar' 'on' opt.erpimageopt{:}  };
    end

    if ~isempty(opt.channels)
        [STUDY allerpimage alltimes alltrials tmp events] = std_readersp(STUDY, ALLEEG, 'channels', opt.channels, 'infotype', 'erpim', 'subject', opt.subject, ...
            'concatenate', 'on', 'timerange', opt.timerange, 'design', opt.design);

        % get figure title
        % ----------------
        locs = eeg_mergelocs(ALLEEG.chanlocs);
        locs = locs(std_chaninds(STUDY, opt.channels));
        allconditions = STUDY.design(opt.design).variable(1).value;
        allgroups     = STUDY.design(opt.design).variable(2).value;
        alltitles = std_figtitle('condnames', allconditions, 'cond2names', allgroups, 'chanlabels', { locs.labels }, ...
            'subject', opt.subject, 'valsunit', 'ms', 'datatype', 'ERPIM');

        figure;
        for iCond = 1:length(allconditions)
            for iGroup = 1:length(allgroups)
                tmpevents = events{iCond, iGroup};
                if isempty(tmpevents), tmpevents = zeros(1, size(allerpimage{iCond, iGroup},2)); end
                subplot(length(allconditions), length(allgroups), (iCond-1)*length(allgroups) + iGroup);

                % use color scale for last plot
                if ~isempty(opt.colorlimits) && iCond == length(allconditions) && iGroup == length(allgroups)
                    options = { options{:} 'cbar' 'on' };
                end
                erpimage(allerpimage{iCond, iGroup}, tmpevents, alltimes, alltitles{iCond, iGroup}, params.smoothing, params.nlines, options{:});
            end
        end

    else
        for cInd = 1:length(opt.clusters)
            [STUDY allerpimage alltimes alltrials tmp events] = std_readersp(STUDY, ALLEEG, 'clusters', opt.clusters(cInd), 'infotype', 'erpim', 'subject', opt.subject, ...
                'concatenate', 'on', 'timerange', opt.timerange, 'design', opt.design);
            % get figure title
            % ----------------
            locs = eeg_mergelocs(ALLEEG.chanlocs);
            locs = locs(std_chaninds(STUDY, opt.channels));
            allconditions = STUDY.design(opt.design).variable(1).value;
            allgroups     = STUDY.design(opt.design).variable(2).value;
            alltitles = std_figtitle('condnames', allconditions, 'cond2names', allgroups, 'clustname', STUDY.cluster(opt.clusters(cInd)).name, ...
                'subject', opt.subject, 'valsunit', 'ms', 'datatype', 'ERPIM');

            figure;
            for iCond = 1:length(allconditions)
                for iGroup = 1:length(allgroups)
                    tmpevents = events{iCond, iGroup};
                    if isempty(tmpevents), tmpevents = zeros(1, size(allerpimage{iCond, iGroup},2)); end
                    subplot(length(allconditions), length(allgroups), (iCond-1)*length(allgroups) + iGroup);

                    % use color scale for last plot
                    if ~isempty(opt.colorlimits) && iCond == length(allconditions) && iGroup == length(allgroups)
                        options = { options{:} 'cbar' 'on' };
                    end
                    erpimage(allerpimage{iCond, iGroup}, tmpevents, alltimes, alltitles{iCond, iGroup}, params.smoothing, params.nlines, options{:});
                end
            end
        end
    end
end


function [curCosts] = scaleCosts(curCosts, counts)
  curCosts.total = curCosts.total/counts.total;
  curCosts.word = curCosts.word/counts.word;
end


hydro = struct();

hydro = readNEMOH(hydro,'../Cylinder/');
% hydro = readWAMIT(hydro,'../../WAMIT/Cylinder/cyl.out',[]);
% hydro = combineBEM(hydro);   % Compare to WAMIT
hydro = radiationIRF(hydro,5,[],[],[],[]);
hydro = radiationIRFSS(hydro,[],[]);
hydro = excitationIRF(hydro,5,[],[],[],[]);
% writeBEMIOH5(hydro)
plotBEMIO(hydro)


% run sequence similarity

% whether to run the network to extract feature vectors of the objects
EXTRACT_FEATURES = true;

% whether to calculate the similarity matrix of the objects across frames
CALC_SIMILARITY = false;

CALC_DEEP_MATCH = false;

im_name = ['MOT-09/000001.jpg'];
img = imread(im_name);
[im_H,im_W,im_C] = size(img);
GT = csvread('MOT-09-gt/gt.txt');
W = load('net_weights.mat');
cls_ind = 16; % 1 background, 3 bike, 16 human
%frames = [110,115,120];
%ids = [7,22,44];
frames = [21];
ids = [19];

%{
GET FT VECTORS OF EACH BBOX:

  for each image:
    1. get rois, process it to be in original image pixel unit
    2. keep track of (object index, roi index) pairs
    3. do forward and backward pass of network
    4. extract feature vector (pool_5, contrib_img), save to dictionary
%}

% preprocess gt
gt = GT(:,1:6);
gt(:,5) = gt(:,5) + gt(:,3);
gt(:,6) = gt(:,6) + gt(:,4);
gt_ind = find_gt_idx_frame_obj(gt, frames, ids);
gt = gt(gt_ind,:);
for r=1:size(gt,1)
    if gt(r,3)>im_W
        gt(r,3) = im_W;
    end
    if gt(r,4)>im_H
        gt(r,4) = im_H;
    end
    if gt(r,5)>im_W
        gt(r,5) = im_W;
    end
    if gt(r,6)>im_H
        gt(r,6) = im_H;
    end
end

% resize img
for frame = frames
    im_name = ['MOT-09/' sprintf('%06d',frame) '.jpg'];
    img = imread(im_name);
    resized(frame).img = resize_img(img);
end

% get feature vector per frame
% FT_VEC is a matrix of struct
if EXTRACT_FEATURES

    for frame = frames
        gt_ind = find(gt(:,1) == frame);
        rois = gt(gt_ind, 2:6);
        rois(1,2:5) = [1200,300,1920,780];
        obj_ids = gt(gt_ind, 2);

        % setup
        im_name = ['MOT-09/' sprintf('%06d',frame) '.jpg'];
        img = imread(im_name);

        %forward & backward pass the network
        tic;
        res = net_forward_pass(img, W, rois, true);toc
        tic;
        contrib = net_reverse_contrib(res, W, cls_ind, 'img');toc
        contrib2 = net_reverse_contrib(res, W, 1, 'img');
        for roi_ind = 1:size(rois, 1)
            obj_id = obj_ids(roi_ind);
            FT_VEC(frame, obj_id).img = img;
            FT_VEC(frame, obj_id).roipool = squeeze(res.pool_5(:,:,:,roi_ind));
            FT_VEC(frame, obj_id).contrib_roipool = squeeze(contrib.roipool(roi_ind,:,:,:));
            FT_VEC(frame, obj_id).contrib_conv1_1 = squeeze(contrib.conv1_1(roi_ind,:,:,:));
            FT_VEC(frame, obj_id).contrib_img = squeeze(contrib.img(roi_ind,:,:,:));
        end
    end

end

% get cropped img of rois
for frame=frames
    for id=ids
        % get cropped matrix of rois
        im_name = ['MOT-09/' sprintf('%06d',frame) '.jpg'];
        img = imread(im_name);
        gt_ind = find_gt_idx_frame_obj(gt, [frame], [id]);
        roi = gt(gt_ind, 3:6);
        roi = ceil(roi);
        mat = img(roi(2):roi(4), roi(1):roi(3), :);
        im_name = ['output/' sprintf('%03d',id) '_' sprintf('%03d',frame) '.jpg'];
        imwrite(mat,im_name);
        cropped(frame,id).mat = mat;
    end
end

% generate similarity matrix:
frs = frames;
num_obj = length(frs)*length(ids);
SIM_roipool = zeros(num_obj,num_obj);
SIM_DM = SIM_roipool;
SIM_contrib_roipool = SIM_DM;

if CALC_SIMILARITY
    count = 0;
    for A_idx = 1:num_obj % A_idx and B_idx are index in the similarity matrix
        for B_idx = A_idx:num_obj
            count = count + 1;
            disp(count);

            A_id = ids( floor((A_idx-1)/length(ids)) + 1 ); % the actual frame number
            A_fr = frs( mod((A_idx-1), length(ids)) + 1 ); % the actual id number of the object
            B_id = ids( floor((B_idx-1)/length(ids)) + 1 );
            B_fr = frs( mod((B_idx-1), length(ids)) + 1 );

            A_mat = cropped(A_fr,A_id).mat;
            B_mat = cropped(B_fr,B_id).mat;

            A = FT_VEC(A_fr,A_id);
            B = FT_VEC(B_fr,B_id);
            SIM_roipool(A_idx,B_idx) = mat_sim(A, B,'roipool');
            SIM_contrib_roipool(A_idx,B_idx) = mat_sim(A, B,'contrib_roipool');

            A_chist = my_color_hist(A_mat);
            B_chist = my_color_hist(B_mat);
            SIM_color_hist(A_idx,B_idx) = mat_sim(A_chist,B_chist,'color_hist');

            A_chist = my_color_hist_weight(resized(A_fr).img,sum(A.contrib_conv1_1,3));
            B_chist = my_color_hist_weight(resized(B_fr).img,sum(B.contrib_conv1_1,3));
            SIM_color_hist_conv1_contrib(A_idx,B_idx) = mat_sim(A_chist,B_chist,'color_hist');
            if CALC_DEEP_MATCH
                 matches = my_deepmatch(A_mat, B_mat);
                 SIM_DM(A_idx,B_idx) = size(matches, 1)/sqrt(length(A_mat(:))*length(B_mat(:)));
            end

        end
    end

end

% post processing
SIM_roipool = matrix_max_percent(SIM_roipool);
SIM_DM = matrix_max_percent(SIM_DM);
SIM_color_hist = matrix_max_percent(SIM_color_hist);
SIM_color_hist_conv1_contrib = matrix_max_percent(SIM_color_hist_conv1_contrib);
SIM_contrib_roipool = matrix_max_percent(SIM_contrib_roipool);

%for roi_ind = 1:size(rois,1)
%    box = squeeze(rois(roi_ind,:));
%    rectangle('Position',[box(2),box(3),box(4)-box(2),box(5)-box(3)]);
%end


classdef TestScharr
    %TestScharr

    properties (Constant)
        im = fullfile(mexopencv.root(),'test','blox.jpg');
    end

    methods (Static)
        function test_1
            img = imread(TestScharr.im);
            result = cv.Scharr(img);
            validateattributes(result, {class(img)}, {'size',size(img)});
        end

        function test_2
            img = imread(TestScharr.im);
            result = cv.Scharr(img, ...
                'XOrder',0, 'YOrder',1, 'Scale',1, 'Delta',0, ...
                'BorderType','Default', 'DDepth','double');
            validateattributes(result, {'double'}, {'size',size(img)});
        end

        function test_3
            img = imread(fullfile(mexopencv.root(),'test','fruits.jpg'));
            result = cv.Scharr(img);
            validateattributes(result, {class(img)}, {'size',size(img)});
        end

        function test_error_argnum
            try
                cv.Scharr();
                throw('UnitTest:Fail');
            catch e
                assert(strcmp(e.identifier,'mexopencv:error'));
            end
        end
    end

end


function r = lt(p,q)
% this function compares the less than condition of x, y, and z values of the structures that I use in
% the FVtool.
%
% SYNOPSIS:
%
%
% PARAMETERS:
%
%
% RETURNS:
%
%
% EXAMPLE:
%
% SEE ALSO:
%

% Copyright (c) 2012-2016 Ali Akbar Eftekhari
% See the license file

if (isa(p, 'FaceVariable')&&isa(q, 'FaceVariable'))
    r=p;
    r.xvalue = p.xvalue<q.xvalue;
    r.yvalue = p.yvalue<q.yvalue;
    r.zvalue = p.zvalue<q.zvalue;
elseif isa(p, 'FaceVariable')
    r=p;
    r.xvalue = p.xvalue<q;
    r.yvalue = p.yvalue<q;
    r.zvalue = p.zvalue<q;
else
    r=q;
    r.xvalue = p<q.xvalue;
    r.yvalue = p<q.yvalue;
    r.zvalue = p<q.zvalue;
end


%% Example of using KST class for interfacing with KUKA iiwa robots
% This example script is used to show how to utilise the networking
% functions integrated into the class KST of the KUKA Sunrise Toolbox

% Before using the script:
% 1- You need to establish a network between the PC and the robot
%       controller
% 2- Synchronise the application "MatlabToolboxServer" into the robot
%       controller using the SunriseWorkbench, from more info consult the
%       document "Import KST to SunriseWorkbench.pdf"
% 3- Run the application "MatlabToolboxServer" from the teach pendant of
%       the robot.
% 4- Run the following script from MATLAB on a PC that is paired to the
%       controller of the robot using an ethernet cable connected to the
%       X66 connector.

% Note: When you run the "MatlabToolboxServer" app, you have 60 seconds to
% connect to the robot from MATLAB, if the limit time is exceeded without
% establishing a connection from MATLAB, the "MatlabToolboxServer" app
% turns off automatically. You have to manyally restart the
% "MatlabToolboxServer" app before connecting to the robot again.

% Exceptions, to use the instruction "net_pingIIWA", or the general porpuse
% functions it is not required to run the "MatlabToolboxServer" app.
% Yet a pairing the PC and the controller on ethernet is still important to
% run the function "net_pingIIWA".

% Copyright Mohammad SAFEEA, 30th-June-2018

close all;clear;clc;
warning('off')

%% Create the robot object
ip='172.31.1.147'; % The IP of the controller
arg1=KST.LBR7R800; % choose the robot iiwa7R800 or iiwa14R820
arg2=KST.Medien_Flansch_elektrisch; % choose the type of flange
Tef_flange=eye(4); % transofrm matrix of EEF with respect to flange
iiwa=KST(ip,arg1,arg2,Tef_flange); % create the object
%% Check if the robot is reachable
rep=iiwa.net_pingIIWA();
disp(rep);

%% Start a connection with the server
flag=iiwa.net_establishConnection();
if flag==0
  return;
end
pause(1);
disp('This script demonstrates the networking functions of KST')

%% Read EEF position from the controller
Pos=iiwa.getEEFPos();
disp('EEF position and orientation is:')
disp(Pos)

%% turn off the server
iiwa.net_turnOffServer();
warning('on')


function out = get(f, prop)
%GET   GET method for the TRIGTECH class
%   P = GET(F, PROP) returns the property P specified in the string PROP from
%   the TRIGTECH F.  The string PROP may be the name of a TRIGTECH property (see
%   the TRIGTECH classdef files for lists) or any of the following strings:
%       'POINTS'          - Equally spaced points where F is sampled.
%       'VALUES'          - Values of F at trig points.
%       'LVAL'            - Value of F at -1.
%       'RVAL'            - Value of F at +1.
%       'TECH'            - Handle to the TRIGTECH constructor. *
%
% See also CHEBTECH, CHEBTECH2.

% Copyright 2017 by The University of Oxford and The Chebfun Developers.
% See http://www.chebfun.org/ for Chebfun information.

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% DEVELOPER NOTE:
%  * Currently get(f, 'tech') returns a function handle to the tech constructor.
%    This may change in future to return instead an empty instance of the tech.
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

switch prop
    case fieldnames(f)
        % Allow access to any of the properties of F via GET:
        out = f.(prop);
    case 'vscale'
        % Get the vscale:
        out = vscale(f);
    case 'points'
        % Get the trigier grid corresponding to the VALUES:
        out = f.points();
    case 'lval'
        % The value at -1:
        out = feval(f, -1);
    case 'rval'
        % The value at 1:
        out = feval(f, 1);
    case 'tech'
        % TODO: Return function handle, or empty instance of the tech?
        out = @trigtech;
    otherwise
        error('CHEBFUN:TRIGTECH:GET:proname', ...
            'Unknown property name ''%s'' for object of type trigtech.', prop);
end

end


function [datatypesout]=any2byte(datatypes)

% ANY2BYTE - Mask Initialization function for UDP Byte Packing Block
% Derived from The MathWorks, Inc. MXPCANY2BYTE
% $Revision: 1 $ $Date: 2008/03/07  $

if ~isa(datatypes,'cell')
  error('datatypes argument must be a cell array');
end

datatypesout=[];
for i=1:length(datatypes)
  datatype=datatypes{i};
  if ~isa(datatype,'char')
    error('datatypes elements must be char arrays');
  end
  if strcmp(datatype,'double')
     dtypeout=0;
  elseif strcmp(datatype,'single')
    dtypeout=1;
  elseif strcmp(datatype,'int8')
    dtypeout=2;
  elseif strcmp(datatype,'uint8')
    dtypeout=3;
  elseif strcmp(datatype,'int16')
    dtypeout=4;
  elseif strcmp(datatype,'uint16')
    dtypeout=5;
  elseif strcmp(datatype,'int32')
    dtypeout=6;
  elseif strcmp(datatype,'uint32')
    dtypeout=7;
  elseif strcmp(datatype,'boolean')
    dtypeout=8;
  else
    error('the supported data types are: double, single, int, uint8, int16, uint16, int32, uint32, boolean');
  end
  datatypesout=[datatypesout,dtypeout];
end


function C = mrdivide(A, B)
%/    CHEBOP right division.
%   C = A/B, where ones of a A is a CHEBOP and is B a scalar is equivalent
%   to A*(1/B), repectively.
%
%   All other instances returns an error.
%
% See also CHEBOP/MTIMES, CHEBOP/RDIVIDE.

% Copyright 2017 by The University of Oxford and The Chebfun Developers.
% See http://www.chebfun.org/ for Chebfun information.

if ( isnumeric(B) )
    C = mtimes(A, 1./B);
else
    error('CHEBOP:MRDIVIDE:NotSupported', '%s/%s is not supported.', ...
        class(A), class(B));
end

end


clc; clear;

% Name of the video
videoString = "01";

% Define path of background image. Can be empty.
backgroundImagePath = sprintf('data/%s_highway.jpg', videoString);
% backgroundImagePath = "";

% Read tracks by using tracks file and static tracks file.
tracksFilename = sprintf('data/%s_tracks.csv', videoString);
tracksStaticFilename = sprintf('data/%s_tracksMeta.csv', videoString);
tracks = readInTracksCsv(tracksFilename, tracksStaticFilename);
% Read video meta data from video meta file
videoMetaFilename = sprintf('data/%s_recordingMeta.csv', videoString);
videoMeta = readInVideoCsv(videoMetaFilename);

% The visualization needs the tracks, the videoMeta data and the
% backgroundImagePath (which can be empty).
argumentsInput.tracks = tracks;
argumentsInput.videoMeta = videoMeta;
argumentsInput.backgroundImagePath = backgroundImagePath;

% Plot variables initialization. These are the default values. Please use
% them or modify them for your own purpose.
argumentsInput.removingList = [];
argumentsInput.trackWidth = 408; % Width of the video frame
argumentsInput.laneThickness = 0.3; % thickness of the lane markings
argumentsInput.laneColor = [1 1 1]; % color of the lane markings (white)
argumentsInput.currentFrame = 1; % Starting frame
argumentsInput.minimumFrame = 1; % Minimum frame that exists (1)
argumentsInput.maximumFrame = tracks(end).finalFrame-1; % Maximum frame
argumentsInput.playRate = 1; % The play rate (going "playRate" steps forward)
argumentsInput.stop = false; % Boolean for
argumentsInput.streetColor = [0.6 0.6 0.6]; % The street color
argumentsInput.boundingBoxColor = [1 0 0]; % The color of the bounding box
argumentsInput.plotTextAnnotation = true; % Whether the text annotations shall be plotted
argumentsInput.plotTrackingLine = true; % Whether the tracking line shall be plotted

argumentsInput.geoParams.meterPerPixel = 0.10106;
argumentsInput.geoParams.kmhPerPixelFrame = 9.0954;

% Start the visualization
trackVisualization(argumentsInput);


function checkEnvironment(param,num_arg)
% checkEnvironment checks if the required tools are present in the host system.

%   This file is part of the LIONSIMBA Toolbox
%
%	Official web-site: 	http://sisdin.unipv.it/labsisdin/lionsimba.php
% 	Official GitHUB: 	https://github.com/lionsimbatoolbox/LIONSIMBA
%
%   LIONSIMBA: A Matlab framework based on a finite volume model suitable for Li-ion battery design, simulation, and control
%   Copyright (C) 2016-2018 :Marcello Torchio, Lalo Magni, Davide Raimondo,
%                            University of Pavia, 27100, Pavia, Italy
%                            Bhushan Gopaluni, Univ. of British Columbia,
%                            Vancouver, BC V6T 1Z3, Canada
%                            Richard D. Braatz,
%                            Massachusetts Institute of Technology,
%                            Cambridge, Massachusetts 02142, USA
%
%   Main code contributors to LIONSIMBA 2.0:
%                           Ian Campbell, Krishnakumar Gopalakrishnan,
%                           Imperial college London, London, UK
%
%   LIONSIMBA is a free Matlab-based software distributed with an MIT
%   license.

% Check for input arguments
if(num_arg==0)
    error('Type help startSimulation')
end

if(num_arg == 3 && param{1}.OperatingMode == 1)
    error('For constant input currents, please provide the current density as a parameter to startSimulation')
end

% Check if SUNDIALS is installed correctly
disp('Checking for SUNDIALS availability...');
result = exist('IDAFree');
if(result~=2)
    error('The SUNDIALS software does not seem to be present in the search path or installed on your system.\nPlease go to:\nhttps://computation.llnl.gov/casc/sundials/main.html\nand follow the instruction for installing SUNDIALS in MATLAB.');
else
    disp('SUNDIALS Package FOUND!');
end

%Check for CasADi
disp('Checking for CasADi availability...');

try
    import casadi.*
catch e
    error('The CasADi package does not seem to be present in the search path or installed on your system.\nPlease go to:\nhttps://github.com/casadi/casadi/wiki/InstallationInstructions\nand follow the instruction for installing CasADi in MATLAB.');
end

disp('CasADi Package FOUND!');

% For each parameter structure, check if all the fields are set.
for i=1:length(param)
    %Check if the parameters have been set correctly
    [result, missing] = checkBatteryParameters(param{i});
    if(result==0)
        disp('Warning, there are missing parameters in the param array.')
        disp('Please find below, the list of missing parameters:')
        for jj=1:length(missing)
            disp(missing{jj});
        end
        error('Please fix the problem and restart the script')
    end
end

end


function headmodel = ft_headmodel_infinite(varargin)

% FT_HEADMODEL_INFINITE returns an infinitely large homogenous
% volume conduction model. For EEG the volume conductor can be used
% to compute the leadfield of electric current dipoles, for MEG it
% can be used for computing the leadfield of magnetic dipoles.
%
% Use as
%   headmodel = ft_headmodel_infinite;
%
% See also FT_PREPARE_VOL_SENS, FT_COMPUTE_LEADFIELD

% Copyright (C) 2012, Donders Centre for Cognitive Neuroimaging, Nijmegen, NL
%
% This file is part of FieldTrip, see http://www.fieldtriptoolbox.org
% for the documentation and details.
%
%    FieldTrip is free software: you can redistribute it and/or modify
%    it under the terms of the GNU General Public License as published by
%    the Free Software Foundation, either version 3 of the License, or
%    (at your option) any later version.
%
%    FieldTrip is distributed in the hope that it will be useful,
%    but WITHOUT ANY WARRANTY; without even the implied warranty of
%    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
%    GNU General Public License for more details.
%
%    You should have received a copy of the GNU General Public License
%    along with FieldTrip. If not, see <http://www.gnu.org/licenses/>.
%
% $Id$

sourcemodel = ft_getopt(varargin, 'sourcemodel', 'default');

% this is an easy one
headmodel = [];

switch sourcemodel
  case 'monopole'
    headmodel.type = 'infinite_monopole';
  case 'magneticdipole'
    headmodel.type = 'infinite_magneticdipole';
  case 'currentdipole'
    headmodel.type = 'infinite_currentdipole';
  case 'default'
    % let the EEG or MEG leadfield code decide
    headmodel.type = 'infinite';
end % switch


%%% void show_4dvideo(4dmatrix)
%
function show_4dvideo(video)
  for i = 1 : size(video,4)
    frame = video(:,:,:,i);
    imshow(frame,[],'InitialMagnification','fit');
    disp(i);
    pause(0.01);
  end
end


% example_meshscript:
%
% quick script to collect a bunch of mesh images automagically, and save in
% the 'Images/' folder. This loops across different data types (which in
% this case represent different population receptive field models), and
% loops across maps produced by each pRF model (the variance explained, the
% polar angle, eccentricity, and pRF size), THEN loops across different
% view angles for each hemisphere, taking a snapshot and saving it as an
% PNG image with a stereotyped name. The images should then be easy to sort
% through. The final line calls a separate function (also included as an
% example) which then loads these images, and compsites the results across
% hemispheres into a PowerPoint file.
%
%
% ras, 080408.
rois = {'aFus_faces' 'pFus_faces' 'FBA_event' 'aEBA' ...
		'sEBA'  'TOS_event' 'PPA' ...
		'MT.mat' 'STS_faces_event'};
meshes = {'s3_left_new_football' 's3_right_new_football'};
dtNames = {'CheckerboardAverages' 'HouseAverages' 'FaceAverages' 'Averages' ...
		   'Odd' 'Even' 'FaceOdd' 'FaceEven' 'HouseOdd' 'HouseEven' ...
		   'CheckerboardOdd' 'CheckerboardEven'};
meshViews = { {'VentralZoom' 'Medial' 'LateralOccipital'} ...
			  {'VentralZoom' 'Medial' 'LateralOccipital'} };
fields = {'co' 'map' 'ph' 'amp'};
fieldNames = {'Variance Explained' 'Eccentricity' 'Polar Angle' 'pRF Diameter'};
lr = 'LR';  leftright = {'Left' 'Right'};  rightleft = {'right' 'left'};

%% open the view
mrvCleanWorkspace;
mrVista 3
% VOLUME{1} = prfLoadROIs(VOLUME{1}, rois);
for h = 1:2
	meshPath = fullfile('3DAnatomy', leftright{h}, '3DMeshes', meshes{h});
	VOLUME{1} = meshLoad(VOLUME{1}, meshPath, 1);
end

%% loop across data types, pRF models
for dt = dtNames
	VOLUME{1} = selectDataType(VOLUME{1}, dt{1});

	%% load the model / maps
	% (the 'prfLoadModel' function is a personal function: this calls the
	% 'rmSelect' function to load the most recent pRF model.)
% 	VOLUME{1} = prfLoadModel(VOLUME{1});
	VOLUME{1} = rmSelect(VOLUME{1}, 'mostrecent');

	%% loop across view fields
	for f = 1:length(fields)
		VOLUME{1} = setDisplayMode(VOLUME{1}, fields{f});

		% set viewing parameters appropriate to the field
		if isequal(fields{f}, 'co')
			VOLUME{1} = setCothresh(VOLUME{1}, 0.01); % minimal thresholding
			VOLUME{1}.ui.coMode.clipMode = [0 .6];
		else
			VOLUME{1} = setCothresh(VOLUME{1}, 0.1);
			VOLUME{1}.ui.coMode.clipMode = [0 .5];
		end

		%% loop across meshes (hemispheres)
		for h = 1:2
			if isequal(fields{f}, 'ph')
% 				VOLUME{1}.ui.phMode.cmap(129:end,:) = circshift(hsv(128), 32);
				VOLUME{1} = cmapPolarAngleRGB(VOLUME{1}, rightleft{h});
			else
				VOLUME{1} = setPhWindow(VOLUME{1}, [0 2*pi]);
			end
			VOLUME{1}.meshNum3d = h;
			meshColorOverlay(VOLUME{1});

			%% loop across mesh view settings
			for j = 1:3
				meshRetrieveSettings(VOLUME{1}.mesh{h}, meshViews{h}{j});
				img = mrmGet(VOLUME{1}.mesh{h}, 'screenshot') ./ 255;
				saveName = sprintf('%s %sH %s %s.png',  meshViews{h}{j}, ...
									 lr(h), fieldNames{f}, dt{1});
				savePath = fullfile(pwd, 'Images', saveName);
				imwrite(img, savePath, 'png');
				fprintf('Saved %s.\n', savePath);
			end
		end
	end
end

example_prfMakePPTFromImages;


function SleepState = SleepScoreMaster(basePath,varargin)
%SleepScoreMaster(basePath,<options>)
%This is the master function for sleep state scoring.
%
%It's strongly recommended that you
%   1) indicate bad (noisy) channels using bz_getSessionInfo(basePath,'editGUI',true)
%      before running SleepScoreMaster.
%   2) use the 'ignoretime' input to exclude time windows with opto
%       stimulation or behavior with electrical noise
%   3) check the scoring quality using TheStateEditor after running SleepScoreMaster.
%      Use the 'A' key in TheStateEditory to further refine thresholds as
%      needed, and implement sticky thresholds.
%
%INPUT
%   basePath        folder containing .xml and .lfp files.
%                   basePath and files should be of the form:
%                   'whateverfolder/recordingName/recordingName'
%   (optional)      If no inputs included, select folder(s) containing .lfp
%                   and .xml file in prompt.
%   (optional)      if no .lfp in basePath, option to select multiple
%                   lfp-containing subfolders
%
%   OPTIONS
%   'savedir'       Default: basePath
%   'overwrite'     Overwrite all processing steps (Default: false)
%   'ignoreManual'  Default: false. Overwrite manual scoring from TheStateEditor
%   'savebool'      Default: true. Save anything.
%   'scoretime'     Window of time to score. Default: [0 Inf]
%                   NOTE: must be continous interval
%   'ignoretime'    Time intervals winthin scoretime to ignore
%                   (for example, opto stimulation or behavior with artifacts)
%   'winparms'      [FFT window , smooth window] (Default: [2 15])
%                   (Note: updated from [10 10] based on bimodaility optimization, 6/17/19)
%   'SWWeightsName' Name of file in path (in Dependencies folder)
%                   containing the weights for the various frequencies to
%                   be used for SWS detection.
%                   Default is to use Power Spectrum Slope ('PSS'),
%                   If this doesn't work, try 'SWweights.mat'
%                   or 'SWweightsHPC.mat' for HPC recording.
%   'Notch60Hz'     Boolean 0 or 1.  Value of 1 will notch out the 57.5-62.5 Hz
%                   band, default is 0, no notch.  This can be necessary if
%                   electrical noise.
%   'NotchUnder3Hz' Boolean 0 or 1.  Value of 1 will notch out the 0-3 Hz
%                   band, default is 0, no notch.  This can be necessary
%                   due to poor grounding and low freq movement transients
%   'NotchHVS'      Boolean 0 or 1.  Value of 1 will notch the 4-10 and
%                   12-18 Hz bands for SW detection, default is 0, no
%                   notch.  This can be useful in
%                   recordings with prominent high voltage spindles which
%                   have prominent ~16hz harmonics
%   'NotchTheta'    Boolean 0 or 1.  Value of 1 will notch the 4-10 Hz
%                   band for SW detection, default is 0, no notch.  This
%                   can be useful to
%                   transform the cortical spectrum to approximately
%                   hippocampal, may also be necessary with High Voltage
%                   Spindles
%   'stickytrigger' Implements a "sticky" trigger for SW/EMG threshold
%                   crossings: metrics must reach halfway between threshold
%                   and opposite peak to count as crossing (reduces
%                   flickering) (default:true)
%   'SWChannels'    A vector list of channels that may be chosen for SW
%                   signal
%   'ThetaChannels' A vector list of channels that may be chosen for Theta
%                   signal
%   'rejectChannels' A vector of channels to exclude from the analysis
%   'saveLFP'       (default:true) to save SleepScoreLFP.lfp.mat file
%   'noPrompts'     (default:false) an option to not prompt user of things
%
%OUTPUT
%   !THIS IS OUT OF DATE - UPDATE!
%   StateIntervals  structure containing start/end times (seconds) of
%                   NREM, REM, WAKE states and episodes. states is the
%                   "raw" state scoring. episodes are joined episodes of
%                   extended (40s) time in a given states, allowing for
%                   brief interruptions. also contains NREM packets,
%                   unitary epochs of NREM as described in Watson et al 2016.
%                   saved in a .mat file:
%                   recordingname_SleepScore.mat
%
%
% DLevenstein and BWatson 2015/16
%% Recording Selection
%if recname is 'select' or something
%use uigetfile to pick and get list of filenames
%if recname is 'all', get all recordings in a folder and
%then run SleepScoreMaster on each of the filenames'
%if no input arguements... select uigetfile

%Select from no input
if ~exist('basePath','var')
    basePath = uigetdir(cd,...
        'Which recording(s) would you like to state score?');
    if isequal(basePath,0);return;end
end

%Separate datasetfolder and recordingname
[datasetfolder,recordingname,extension] = fileparts(basePath);
recordingname = [recordingname,extension]; % fileparts parses '.' into extension

%% If there is no .lfp in basePath, choose (multiple?) folders within basePath.
%Select from dataset folder - need to check if .xml/lfp exist
if ~exist(fullfile(datasetfolder,recordingname,[recordingname,'.lfp']),'file') && ...
    ~exist(fullfile(datasetfolder,recordingname,[recordingname,'.eeg']),'file')
    display(['no .lfp file in basePath, pick a selection of session folders',...
             'containing .lfp files'])
         %Find all basePaths within the topPath
        [basePaths,recordingname] = bz_FindBasePaths(basePath,'select',true);
end

%If multiple recordings, loop calling SleepScoreMaster with each
numrecs = length(recordingname);
if numrecs > 1 & iscell(recordingname)
    display(['Multiple Recordings (',num2str(numrecs),')'])
    for rr = 1:numrecs
        multibasepath = basePaths{rr};
        SleepScoreMaster(multibasepath,varargin{:})
        close all
    end
    return
elseif numrecs == 1 & iscell(recordingname)
        recordingname = recordingname{1};
end

display(['Scoring Recording: ',recordingname]);

%% inputParse for Optional Inputs and Defaults
p = inputParser;

addParameter(p,'overwrite',false)
addParameter(p,'savebool',true,@islogical)
addParameter(p,'savedir',datasetfolder)
addParameter(p,'scoretime',[0 Inf])
addParameter(p,'ignoretime',[])
addParameter(p,'SWWeightsName','PSS')
addParameter(p,'Notch60Hz',0)
addParameter(p,'NotchUnder3Hz',0)
addParameter(p,'NotchHVS',0)
addParameter(p,'NotchTheta',0)
addParameter(p,'SWChannels',0)
addParameter(p,'ThetaChannels',0)
addParameter(p,'rejectChannels',[]);
addParameter(p,'noPrompts',true);
addParameter(p,'stickytrigger',false);
addParameter(p,'saveLFP',true);
addParameter(p,'winparms',[2 15]);
addParameter(p,'ignoreManual',false)

parse(p,varargin{:})
%Clean up this junk...
overwrite = p.Results.overwrite;
savedir = p.Results.savedir;
savebool = p.Results.savebool;
scoretime = p.Results.scoretime;
ignoretime = p.Results.ignoretime;
SWWeightsName = p.Results.SWWeightsName;
Notch60Hz = p.Results.Notch60Hz;
NotchUnder3Hz = p.Results.NotchUnder3Hz;
NotchHVS = p.Results.NotchHVS;
NotchTheta = p.Results.NotchTheta;
SWChannels = p.Results.SWChannels;
ThetaChannels = p.Results.ThetaChannels;
rejectChannels = p.Results.rejectChannels;
noPrompts = p.Results.noPrompts;
stickytrigger = p.Results.stickytrigger;
saveLFP = p.Results.saveLFP;
winparms = p.Results.winparms;
ignoreManual = p.Results.ignoreManual;

%% Database File Management
savefolder = fullfile(savedir,recordingname);
if ~exist(savefolder,'dir')
    mkdir(savefolder)
end

%Filenames of metadata and SleepState.states.mat file to save
sessionmetadatapath = fullfile(savefolder,[recordingname,'.SessionMetadata.mat']);
%Buzcode outputs
bz_sleepstatepath = fullfile(savefolder,[recordingname,'.SleepState.states.mat']);

%% Check for existing Manual Scoring
if exist(bz_sleepstatepath,'file') && ~overwrite && ~ignoreManual
   SleepState_old = load(bz_sleepstatepath);
   if isfield(SleepState_old.SleepState.detectorinfo,'LastManualUpdate')
       display(['Manual scoring detected... will update the SleepScoreMetrics and AutoScoreInts, ',...
        'but keep previous (manual) scoring.'])
       display(['To overwrite manual scoring use ''ignoreManual'',true ',...
           'or ''overwrite'',true to overwrite all metrics.'])
       ManScore.ints = SleepState_old.SleepState.ints;
       ManScore.idx = SleepState_old.SleepState.idx;
       ManScore.LastManualUpdate = SleepState_old.SleepState.detectorinfo.LastManualUpdate;
   end
end

%% Get channels not to use
sessionInfo = bz_getSessionInfo(basePath,'noPrompts',noPrompts);
% check that SW/Theta channels exist in rec..
if length(SWChannels) > 1
    if sum(ismember(SWChannels,sessionInfo.channels)) ~= length(SWChannels)
        error('some of the SW input channels dont exist in this recording...?')
    end
end
if length(ThetaChannels) > 1
    if sum(ismember(ThetaChannels,sessionInfo.channels)) ~= length(ThetaChannels)
        error('some of the theta input channels dont exist in this recording...?')
    end
end

%Is this still needed?/Depreciated?
% if exist(sessionmetadatapath,'file')%bad channels is an ascii/text file where all lines below the last blank line are assumed to each have a single entry of a number of a bad channel (base 0)
%     load(sessionmetadatapath)
%     rejectChannels = [rejectChannels SessionMetadata.ExtracellEphys.BadChannels];
% elseif isfield(sessionInfo,'badchannels')
if isfield(sessionInfo,'badchannels')
    rejectChannels = [rejectChannels sessionInfo.badchannels]; %get badchannels from the .xml

end

if isempty(rejectChannels)
    display('No rejected channels - it''s recommended you identify noisy channels to ignore')
end

%% CALCULATE EMG FROM HIGH-FREQUENCY COHERENCE
% Load/Calculate EMG based on cross-shank correlations
% (high frequency correlation signal = high EMG).
% Schomburg E.W. Neuron 84, 470?485. 2014)
EMGFromLFP = bz_EMGFromLFP(basePath,'overwrite',overwrite,...
                                     'rejectChannels',rejectChannels,'noPrompts',noPrompts,...
                                     'saveMat',savebool);

%% DETERMINE BEST SLOW WAVE AND THETA CHANNELS
%Determine the best channels for Slow Wave and Theta separation.
%Described in Watson et al 2016, with modifications
SleepScoreLFP = PickSWTHChannel(basePath,...
                            scoretime,SWWeightsName,...
                            Notch60Hz,NotchUnder3Hz,NotchHVS,NotchTheta,...
                            SWChannels,ThetaChannels,rejectChannels,...
                            overwrite,'ignoretime',ignoretime,...
                            'noPrompts',noPrompts,'saveFiles',saveLFP&savebool,...
                            'window',winparms(1),'smoothfact',winparms(2),'IRASA',true);

%% CLUSTER STATES BASED ON SLOW WAVE, THETA, EMG

%Calculate the scoring metrics: broadbandLFP, theta, EMG
display('Quantifying metrics for state scoring')
[SleepScoreMetrics,StatePlotMaterials] = ClusterStates_GetMetrics(...
                                           basePath,SleepScoreLFP,EMGFromLFP,overwrite,...
                                           'onSticky',stickytrigger,'ignoretime',ignoretime,...
                                           'window',winparms(1),'smoothfact',winparms(2),...
                                           'IRASA',true,'ThIRASA',true);

%Use the calculated scoring metrics to divide time into states
display('Clustering States Based on EMG, SW, and TH LFP channels')
[ints,idx,MinTimeWindowParms] = ClusterStates_DetermineStates(SleepScoreMetrics);

%% RECORD PARAMETERS from scoring
detectionparms.userinputs = p.Results;
detectionparms.MinTimeWindowParms = MinTimeWindowParms;
detectionparms.SleepScoreMetrics = SleepScoreMetrics;

% note and keep special version of original hists and threshs

SleepState.ints = ints;
SleepState.idx = idx;
SleepState.detectorinfo.detectorname = 'SleepScoreMaster';
SleepState.detectorinfo.detectionparms = detectionparms;
SleepState.detectorinfo.detectionparms.histsandthreshs_orig = detectionparms.SleepScoreMetrics.histsandthreshs;
SleepState.detectorinfo.detectiondate = datestr(now,'yyyy-mm-dd');
SleepState.detectorinfo.StatePlotMaterials = StatePlotMaterials;

%Put old manual scoring back in
if exist('ManScore','var')
    SleepState.AutoScoreInts = SleepState.ints;
    SleepState.ints = ManScore.ints;
    SleepState.idx = ManScore.idx;
    SleepState.detectorinfo.LastManualUpdate = ManScore.LastManualUpdate;
end

%Saving SleepStates
save(bz_sleepstatepath,'SleepState');

%% MAKE THE STATE SCORE OUTPUT FIGURE
%ClusterStates_MakeFigure(stateintervals,stateIDX,figloc,SleepScoreMetrics,StatePlotMaterials);
try
    ClusterStates_MakeFigure(SleepState,basePath,noPrompts);
    disp('Figures Saved to StateScoreFigures')
catch
    disp('Figure making error')
end

%% JOIN STATES INTO EPISODES

% Extract states, Episodes, properly organize params etc, prep for final saving
display('Calculating/Saving Episodes')
StatesToEpisodes(SleepState,basePath);

display(['Sleep Score ',recordingname,': Complete!']);

%% PROMPT USER TO MANUALLY CHECK DETECTION WITH THESTATEEDITOR
if ~noPrompts
    str = input('Would you like to check detection with TheStateEditor? [Y/N] ','s');
    switch str
        case {'Y','y',''}
            TheStateEditor([basePath,filesep,recordingname])
        case {'N','n'}
        otherwise
            display('Unknown input..... you''ll have to load TheStateEditor on your own')
    end
end

end


function returnPathway = colorPathway(pathway, reactionIDs, fluxes, referenceFluxes, ...
    cutOff, defaultColor, upColor, downColor)
% colorPathway
%	Calculates the color for those reactions that should be marked in the
%	map and returns an updated pathway structure.
%
%   pathway         pathway structure of the metabolic network
%   reactionsIDs    cell array with the names of the reactions in the model
%   fluxes          vector with flux values from the simulation
%   referenceFluxes vector with fluxes for the reference simulation
%   cutOff          a reaction is only colored if the absolute value of
%                   at least one of the fluxes is above the cutoff value
%                   (opt, default 0)
%   defaultColor    a color in Matlab format to be used if there are no
%                   changes between the fluxes. This color is also used to
%                   calculate the transition between the colors for up and
%                   down regulated fluxes (opt, default [1 1 1])
%   upColor         a color in Matlab format to be used if the flux is
%                   larger than the reference flux (opt, default [0 1 0])
%   downColor       a color in Matlab format to be used if the flux is
%                   smaller than the reference flux (opt, default [1 0 0])
%
%   returnPathway   updated pathway structure which contains coloring data
%       color       array indicating the coloring of the enzyme
%       signChange  true if the reaction has changed direction
%
%	Usage: returnPathway = colorPathway(pathway, reactionIDs, fluxes, referenceFluxes, ...
%           cutOff, defaultColor, upColor, downColor)

if nargin<8
    downColor=[1 0 0];
end
if nargin<7
    upColor=[0 1 0];
end
if nargin<6
    defaultColor=[1 1 1];
end
if nargin<5
    cutOff=0;
end

%Loop through the components in the pathway. Check if any component has a
%note and then check for the corresponding reaction id
returnPathway=pathway;

for i=1:length(pathway.listOfSpecies)
    if strcmpi(pathway.listOfSpecies(i).type,'PROTEIN')
        if isfield(pathway.listOfSpecies(i),'note')
            if ~isempty(pathway.listOfSpecies(i).note)
                %If there is a note check if there is a corresponding
                %reaction id
                correspondingReaction=find(strcmpi(reactionIDs,pathway.listOfSpecies(i).note));
                if correspondingReaction>0
                    %Check if either flux is above the cutoff value
                    if abs(referenceFluxes(correspondingReaction))>=cutOff ||...
                            abs(fluxes(correspondingReaction))>=cutOff
                        %Calculate the corresponding color
                        [color, signChange]=getColorCodes(referenceFluxes(correspondingReaction)...
                            ,fluxes(correspondingReaction),1 , defaultColor, upColor, downColor);
                        if ~isempty(color)
                            returnPathway.listOfSpecies(i).color=color{1,1};
                            returnPathway.listOfSpecies(i).signChange=signChange{1,1};
                        end
                    end
                end
            end
        end
    end
end
end


function P3 = reslice_seg_anatomy()

disp(['This script reslices all segmented n*het1*img anatomicals into space of functionals.'])
disp(['Output images are thresholded (1 or 0) to be mask images.'])

mdir = spm_get(-1,'*','Enter Main Directory for Study',pwd);
mypwd = pwd;
eval(['cd ' mdir])

!ls
dwcard = input('Enter wildcard for all individual subjects:','s');

P = get_filename(dwcard,['anatomy' filesep 'n*het1*img']);
disp(['reslicing these images:']), P

d = dir(dwcard);
P2 = get_filename([d(1).name '*'],'scan1/sn*ra*0001.img');
Pt = P2(1,:);

disp(['Reslicing to space of: ' Pt])

reslice_imgs(Pt,P,1);

P3 = get_filename(dwcard,['anatomy' filesep 'rn*het1*img']);

disp('Output in:')
P3

return


function drawRawPnts(SenFig,Raw)

% DRAWRAWPNTS  Draw raw points.
%   DRAWRAWPNTS(SENFIG,RAW)  redraws the 2D points in RAW on figure SenFig.

%   Copyright 2008-2009 Joan Sola @ LAAS-CNRS.

if ~isempty(Raw.data.points.coord)
    set(SenFig.raw.points,...
        'xdata',Raw.data.points.coord(1,:),...
        'ydata',Raw.data.points.coord(2,:))
end

% ========== End of function - Start GPL license ==========

%   # START GPL LICENSE

%---------------------------------------------------------------------
%
%   This file is part of SLAMTB, a SLAM toolbox for Matlab.
%
%   SLAMTB is free software: you can redistribute it and/or modify
%   it under the terms of the GNU General Public License as published by
%   the Free Software Foundation, either version 3 of the License, or
%   (at your option) any later version.
%
%   SLAMTB is distributed in the hope that it will be useful,
%   but WITHOUT ANY WARRANTY; without even the implied warranty of
%   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
%   GNU General Public License for more details.
%
%   You should have received a copy of the GNU General Public License
%   along with SLAMTB.  If not, see <http://www.gnu.org/licenses/>.
%
%---------------------------------------------------------------------

%   SLAMTB is Copyright:
%   Copyright (c) 2008-2010, Joan Sola @ LAAS-CNRS,
%   Copyright (c) 2010-2013, Joan Sola,
%   Copyright (c) 2014-2015, Joan Sola @ IRI-UPC-CSIC,
%   SLAMTB is Copyright 2009
%   by Joan Sola, Teresa Vidal-Calleja, David Marquez and Jean Marie Codol
%   @ LAAS-CNRS.
%   See on top of this file for its particular copyright.

%   # END GPL LICENSE


function e = end(X,k,n)
%END Last index of indexing expression for ktensor.
%
%   The expression X(end,:,:) will call END(X,1,3) to determine
%   the value of the first index.
%
%   See also KTENSOR, KTENSOR/SUBSREF, END.
%
%MATLAB Tensor Toolbox.
%Copyright 2015, Sandia Corporation.

% This is the MATLAB Tensor Toolbox by T. Kolda, B. Bader, and others.
% http://www.sandia.gov/~tgkolda/TensorToolbox.
% Copyright (2015) Sandia Corporation. Under the terms of Contract
% DE-AC04-94AL85000, there is a non-exclusive license for use of this
% work by or on behalf of the U.S. Government. Export of this data may
% require a license from the United States Government.
% The full license terms can be found in the file LICENSE.txt

%TODO (after 2.0 release): Resolve ambiguity w.r.t X{end}and X(end,1,1)
%for 1st-order tensors.

if n > ndims(X)
  error('Subscript out of range.');
end

if (n ~= 1)
  e = size(X,k);
else
  e = ndims(X);
end


function bezier_surface_rectangle_write ( rectangle_file_name, ...
  rectangle_num, rectangle_node )

%*****************************************************************************80
%
%% BEZIER_SURFACE_RECTANGLE_WRITE writes rectangle to a rectangle file.
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    19 June 2006
%
%  Author:
%
%    John Burkardt
%
%  Parameters:
%
%    Input, string RECTANGLE_FILE_NAME, the name of the
%    rectangle file.
%
%    Input, integer RECTANGLE_NUM, the number of rectangle.
%
%    Input, integer RECTANGLE_NODE(16,RECTANGLE_NUM), the nodes that
%    make up each rectangle.
%
  dim_num = 16;
  header = 1;

  i4mat_write ( rectangle_file_name, dim_num, rectangle_num, ...
    rectangle_node, header );

  return
end


function p25_p_set ( p )

%*****************************************************************************80
%
%% P25_P_SET sets the value of a parameter for problem 25.
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    22 January 2001
%
%  Author:
%
%    John Burkardt
%
%  Parameters:
%
%    Input, real P, the value of the parameter that multiplies the
%    Gaussian noise.
%
  p25_p_val ( 'SET', p );

  return
end


function O = GetOPTI(B,opts)
%Build OPTI Object from SymBuilder Object
%
%   Called By SYMBUILDER Class

%   Copyright (C) 2012-2013 Jonathan Currie (IPL)

if(nargin < 2 || isempty(opts)), opts = symbset; else, opts = symbset(opts); end

%Check object is built
if(~IsBuilt(B))
    error('Please build the object using Draft() or Build()');
end

%Check we have an objective (no good without!)
if(B.noObjs == 0)
    error('You can only construct an OPTI object when you have specified an objective!');
elseif(B.noObjs > 1)
    error('You can only construct an OPTI object with a single objective');
end

%Clear existing callback function from memory
clear symb_cb symb_ccb

%Separate objective and constraint indices
olin = B.objlin(B.indobj);
clin = B.conlin; clin(B.indobj) = [];

%Default options
if(~isempty(opts.optiOpts))
    Oopts = optiset(opts.optiOpts,'warnings','off'); %overrides solver and display settings
    %check if user has specified a solver/display
    if(~strcmpi(opts.solver,'auto'))
        optiwarn('OPTI:SymBSolver','As you have supplied optiOpts to symbset, your solver selection within symbset has been overwritten by the solver specified in optiOpts.');
    end
    if(~strcmpi(opts.display,'off'))
        optiwarn('OPTI:SymBDisplay','As you have supplied optiOpts to symbset, your display setting within symbset has been overwritten by the display setting specified in optiOpts.');
    end
else
    Oopts = optiset(opts.optiOpts,'warnings','off','solver',opts.solver,'display',opts.display);
end

%Check for Linear Problem
if(olin == 1 && all(clin == 1))
    %Build OPTI object
    O = opti(GetLinProb(B),'options',Oopts);
%Check for Quadratic Pprogram
elseif(olin == 2 && all(clin == 1))
    %Build OPTI object
    O = opti(GetQuadProb(B),'options',Oopts);
%Check for QCQP/QCLP
elseif(olin <= 2 && all(clin <= 2))
    %Build OPTI object
    O = opti(GetQuadProb(B),'options',Oopts);
%Check for NLP
elseif(olin <= 3 && all(clin <= 3))
    %If we are building an MINLP, add BONMIN linear information
    if(any(B.xtype ~= 'C'))
        %Constraint Linearity
        cons_lin = clin;
        cons_lin(clin > 1) = 0;
        %Variable linearity
        varlin = ones(size(B.jac,2),1);
        nlvars = symvar(B.jac); %Variables in the jacobian are nonlinear WHAT ABOUT GRADIENT?
        for i = 1:length(nlvars)
            varlin(logical(nlvars(i) == B.vars)) = 0;
        end
        if(~isempty(Oopts.solverOpts))
            Oopts = optiset(Oopts,'warnings','off','solverOpts',bonminset(Oopts.solverOpts,'cons_lin',cons_lin,'var_lin',varlin));
        else
            Oopts = optiset(Oopts,'warnings','off','solverOpts',bonminset('cons_lin',cons_lin,'var_lin',varlin));
        end
    end
    %Build OPTI object
    O = opti(GetNLProb(B,opts),'options',Oopts);
else
    error('problem type not yet supported');
end


function [f, h] = plotBrainGrid(brainGridData, ax, brain_figure, black_brain)
% function plotBrainGrid([brainGridData], [ax])
%
% To plot the wire mesh data loaded from brainGridData.npy.

if nargin<1 || isempty(brainGridData)
    mf = mfilename('fullpath');
    brainGridData = readNPY(fullfile(fileparts(mf), 'brainGridData.npy'));
end

bp = double(brainGridData);
bp(sum(bp,2)==0,:) = NaN; % when saved to uint16, NaN's become zeros. There aren't any real vertices at (0,0,0) and it shouldn't look much different if there were

if nargin<2||isempty(ax)
    if nargin<3||isempty(brain_figure)
        brain_figure = figure('Name','Brain View');
    end

    ax = axes('Parent', brain_figure);
end

if nargin<4||~black_brain
    h = plot3(ax, bp(:,1), bp(:,2), bp(:,3), 'Color', [0 0 0 0.3]);
else
    h = plot3(ax, bp(:,1), bp(:,2), bp(:,3), 'Color', [.7 .7 .7 0.3]);
    set(get(ax, 'Parent'),'color','k')
end

set(ax, 'ZDir', 'reverse')
axis(ax, 'equal');
axis(ax, 'vis3d');
axis(ax, 'off');
f = get(ax, 'Parent');


%%
example = qMRusage(qMT_bSSFP,'fit');

% Duplicate %
prctpos=strfind(example,'%');
for ia = 1:length(prctpos)
    example=[example(1:((prctpos(ia)+ia-1)-1)) '%' example((prctpos(ia)+ia-1):end)];
end

fid = fopen('bSSFP_batch.m','w');
fprintf(fid,example);
fclose(fid);


%kDeconvAxial 'Deconvolution using ML/EM algorithm '
% This MatLab function was automatically generated by a converter (KhorosToMatLab) from the Khoros DeconvAxial.pane file
%
% Parameters:
% Integer: n 'Iterations', default: 60: 'Number of iterations until algorythm stops'
% Integer: rW 'Border (Pixels)', default: 4: 'a gaussian Window will be applied'
% Toggle: norichardson 'No Richardson', default: 0: 'do not use the richardson iteration, but the stadard ML-correction method instead'
% Toggle: noPSFnorm 'Do not normalize PSFs', default: 0: 'The integral intensity of the PSFs will then not be normalized'
% Double: mf 'Maximal Rel. Frequency X/Y', default: 0.8: 'Higher frequencies are suppressed in X/Y direction'
% Double: mzf 'Z', default: 0.4: 'Higher frequencies are suppressed in Z-direction'
% InputFile: i 'Measured Image', required: 'Measured confocal image'
% InputFile: p 'PSF', required: 'PSF needed for ML algorithm (same size as measured data)'
% InputFile: s 'Start File', optional: 'file to start iteration with'
% InputFile: Over 'Overrelaxation Table', optional: 'Table for Overrelaxation Factors'
% InputFile: patterns 'Pattern File', optional: 'File containing the different patterns (along elements)'
% Toggle: patsep 'Separable Patterns', default: 0: 'If selected, it is assumed, that the pattern can be described as a sum of separable components. In this case, the pattern-file has to consist of N planes (stacked along depth) for each element. The PSF elements are then assumed to contain the Z-modified PSFs.'
% Toggle: HolmesLiu 'Holmes & Liu', default: 0: 'If selected, the overrelaxation is choosen according to the Holmes&Liu paper. This specific implementation is however rather slow.'
% OutputFile: o 'Recon. Image', required: 'Resulting output data object'
% OutputFile: c 'Correction Image', required: 'Correction Image'
% OutputFile: f 'Fwd Projected File', optional: 'forward proj. guess'
% OutputFile: hf 'HF Content Output', optional: 'energy of highest 10% frequences'
% Toggle: background 'Estimate Background', default: 0: 'For patterned excitation data, a background (out-of-focus, not deconvolved) can be estimated.'
% OutputFile: bgFile 'Background', optional: 'Only for patterned excitation data, Estimate Background active'
%
% Example: [o, c, f, hf, bgFile] = kDeconvAxial({i, p, s, Over, patterns}, {'n',60;'rW',4;'norichardson',0;'noPSFnorm',0;'mf',0.8;'mzf',0.4;'i','';'p','';'s','';'Over','';'patterns','';'patsep',0;'HolmesLiu',0;'o','';'c','';'f','';'hf','';'background',0;'bgFile',''})
%
% Khoros helpfile follows below:
%
%  PROGRAM
% DeconvAxial - Deconvolutes using many Psfs
%
%  DESCRIPTION
%
%
%
%  EXAMPLES
%
%  "SEE ALSO"
%
%  RESTRICTIONS
%
%  REFERENCES
%
%  COPYRIGHT
% Copyright (C) 1996-2003, Rainer Heintzmann,  All rights reserved.
%

function varargout = kDeconvAxial(varargin)
if nargin ==0
  Inputs={};arglist={'',''};
elseif nargin ==1
  Inputs=varargin{1};arglist={'',''};
elseif nargin ==2
  Inputs=varargin{1}; arglist=varargin{2};
else error('Usage: [out1,..] = kDeconvAxial(Inputs,arglist).');
end
if size(arglist,2)~=2
  error('arglist must be of form {''ParameterTag1'',value1;''ParameterTag2'',value2}')
 end
narglist={'n', 60;'rW', 4;'norichardson', 0;'noPSFnorm', 0;'mf', 0.8;'mzf', 0.4;'i', '__input';'p', '__input';'s', '__input';'Over', '__input';'patterns', '__input';'patsep', 0;'HolmesLiu', 0;'o', '__output';'c', '__output';'f', '__output';'hf', '__output';'background', 0;'bgFile', '__output'};
maxval={1000,2,0,0,2,2,0,0,1,1,1,0,0,0,0,1,1,0,1};
minval={1,2,0,0,0,0,0,0,1,1,1,0,0,0,0,1,1,0,1};
istoggle=[0,1,1,1,1,1,0,0,1,1,1,1,1,0,0,1,1,1,1];
was_set=istoggle * 0;
paramtype={'Integer','Integer','Toggle','Toggle','Double','Double','InputFile','InputFile','InputFile','InputFile','InputFile','Toggle','Toggle','OutputFile','OutputFile','OutputFile','OutputFile','Toggle','OutputFile'};
% identify the input arrays and assign them to the arguments as stated by the user
if ~iscell(Inputs)
Inputs = {Inputs};
end
NumReqOutputs=2; nextinput=1; nextoutput=1;
  for ii=1:size(arglist,1)
  wasmatched=0;
  for jj=1:size(narglist,1)
   if strcmp(arglist{ii,1},narglist{jj,1})  % a given argument was matched to the possible arguments
     wasmatched = 1;
     was_set(jj) = 1;
     if strcmp(narglist{jj,2}, '__input')
      if (nextinput > length(Inputs))
        error(['Input ' narglist{jj,1} ' has no corresponding input!']);
      end
      narglist{jj,2} = 'OK_in';
      nextinput = nextinput + 1;
     elseif strcmp(narglist{jj,2}, '__output')
      if (nextoutput > nargout)
        error(['Output nr. ' narglist{jj,1} ' is not present in the assignment list of outputs !']);
      end
      if (isempty(arglist{ii,2}))
        narglist{jj,2} = 'OK_out';
      else
        narglist{jj,2} = arglist{ii,2};
      end

      nextoutput = nextoutput + 1;
      if (minval{jj} == 0)
         NumReqOutputs = NumReqOutputs - 1;
      end
     elseif isstr(arglist{ii,2})
      narglist{jj,2} = arglist{ii,2};
     else
        if strcmp(paramtype{jj}, 'Integer') & (round(arglist{ii,2}) ~= arglist{ii,2})
            error(['Argument ' arglist{ii,1} ' is of integer type but non-integer number ' arglist{ii,2} ' was supplied']);
        end
        if (minval{jj} ~= 0 | maxval{jj} ~= 0)
          if (minval{jj} == 1 & maxval{jj} == 1 & arglist{ii,2} < 0)
            error(['Argument ' arglist{ii,1} ' must be bigger or equal to zero!']);
          elseif (minval{jj} == -1 & maxval{jj} == -1 & arglist{ii,2} > 0)
            error(['Argument ' arglist{ii,1} ' must be smaller or equal to zero!']);
          elseif (minval{jj} == 2 & maxval{jj} == 2 & arglist{ii,2} <= 0)
            error(['Argument ' arglist{ii,1} ' must be bigger than zero!']);
          elseif (minval{jj} == -2 & maxval{jj} == -2 & arglist{ii,2} >= 0)
            error(['Argument ' arglist{ii,1} ' must be smaller than zero!']);
          elseif (minval{jj} ~= maxval{jj} & arglist{ii,2} < minval{jj})
            error(['Argument ' arglist{ii,1} ' must be bigger than ' num2str(minval{jj})]);
          elseif (minval{jj} ~= maxval{jj} & arglist{ii,2} > maxval{jj})
            error(['Argument ' arglist{ii,1} ' must be smaller than ' num2str(maxval{jj})]);
          end
        end
     end
     if ~strcmp(narglist{jj,2},'OK_out') &  ~strcmp(narglist{jj,2},'OK_in')
       narglist{jj,2} = arglist{ii,2};
     end
   end
   end
   if (wasmatched == 0 & ~strcmp(arglist{ii,1},''))
        error(['Argument ' arglist{ii,1} ' is not a valid argument for this function']);
   end
end
% match the remaining inputs/outputs to the unused arguments and test for missing required inputs
 for jj=1:size(narglist,1)
     if  strcmp(paramtype{jj}, 'Toggle')
        if (narglist{jj,2} ==0)
          narglist{jj,1} = '';
        end;
        narglist{jj,2} = '';
     end;
     if  ~strcmp(narglist{jj,2},'__input') && ~strcmp(narglist{jj,2},'__output') && istoggle(jj) && ~ was_set(jj)
          narglist{jj,1} = '';
          narglist{jj,2} = '';
     end;
     if strcmp(narglist{jj,2}, '__input')
      if (minval{jj} == 0)  % meaning this input is required
        if (nextinput > size(Inputs))
           error(['Required input ' narglist{jj,1} ' has no corresponding input in the list!']);
        else
          narglist{jj,2} = 'OK_in';
          nextinput = nextinput + 1;
        end
      else  % this is an optional input
        if (nextinput <= length(Inputs))
          narglist{jj,2} = 'OK_in';
          nextinput = nextinput + 1;
        else
          narglist{jj,1} = '';
          narglist{jj,2} = '';
        end;
      end;
     else
     if strcmp(narglist{jj,2}, '__output')
      if (minval{jj} == 0) % this is a required output
        if (nextoutput > nargout & nargout > 1)
           error(['Required output ' narglist{jj,1} ' is not stated in the assignment list!']);
        else
          narglist{jj,2} = 'OK_out';
          nextoutput = nextoutput + 1;
          NumReqOutputs = NumReqOutputs-1;
        end
      else % this is an optional output
        if (nargout - nextoutput >= NumReqOutputs)
          narglist{jj,2} = 'OK_out';
          nextoutput = nextoutput + 1;
        else
          narglist{jj,1} = '';
          narglist{jj,2} = '';
        end;
      end
     end
  end
end
if nargout
   varargout = cell(1,nargout);
else
  varargout = cell(1,1);
end
global KhorosRoot
if exist('KhorosRoot') && ~isempty(KhorosRoot)
w=['"' KhorosRoot];
else
if ispc
  w='"C:\Program Files\dip\khorosBin\';
else
[s,w] = system('which cantata');
w=['"' w(1:end-8)];
end
end
[varargout{:}]=callKhoros([w 'axialrec"  -k'],Inputs,narglist);


function ShuZiZiMu = DuQuSZZM(s1,s2,s3,s4,s5,s6,s7,s8,s9,s10,...
                              s11,s12,s13,s14,s15,s16,s17,s18,s19,s20,...
                              s21,s22,s23,s24,s25,s26,s27,s28,s29,s30,...
                              s31,s32,s33,s34)
%0-9
%10-14 ABCDE 15-19FGHJK 20-24 LMNPQ 25-29 RSTUV 30-33 WXYZ
ShuZiZiMu(:,:,1)   =imresize(im2bw(s1, graythresh(rgb2gray(s1))), [110 55],'bilinear');
ShuZiZiMu(:,:,2)   =imresize(im2bw(s2, graythresh(rgb2gray(s2))), [110 55],'bilinear');
ShuZiZiMu(:,:,3)   =imresize(im2bw(s3, graythresh(rgb2gray(s3))), [110 55],'bilinear');
ShuZiZiMu(:,:,4)   =imresize(im2bw(s4, graythresh(rgb2gray(s4))), [110 55],'bilinear');
ShuZiZiMu(:,:,5)   =imresize(im2bw(s5, graythresh(rgb2gray(s5))), [110 55],'bilinear');
ShuZiZiMu(:,:,6)   =imresize(im2bw(s6, graythresh(rgb2gray(s6))), [110 55],'bilinear');
ShuZiZiMu(:,:,7)   =imresize(im2bw(s7, graythresh(rgb2gray(s7))), [110 55],'bilinear');
ShuZiZiMu(:,:,8)   =imresize(im2bw(s8, graythresh(rgb2gray(s8))), [110 55],'bilinear');
ShuZiZiMu(:,:,9)   =imresize(im2bw(s9, graythresh(rgb2gray(s9))), [110 55],'bilinear');
ShuZiZiMu(:,:,10)  =imresize(im2bw(s10,graythresh(rgb2gray(s10))),[110 55],'bilinear');
ShuZiZiMu(:,:,11)  =imresize(im2bw(s11,graythresh(rgb2gray(s11))),[110 55],'bilinear');
ShuZiZiMu(:,:,12)  =imresize(im2bw(s12,graythresh(rgb2gray(s12))),[110 55],'bilinear');
ShuZiZiMu(:,:,13)  =imresize(im2bw(s13,graythresh(rgb2gray(s13))),[110 55],'bilinear');
ShuZiZiMu(:,:,14)  =imresize(im2bw(s14,graythresh(rgb2gray(s14))),[110 55],'bilinear');
ShuZiZiMu(:,:,15)  =imresize(im2bw(s15,graythresh(rgb2gray(s15))),[110 55],'bilinear');
ShuZiZiMu(:,:,16)  =imresize(im2bw(s16,graythresh(rgb2gray(s16))),[110 55],'bilinear');
ShuZiZiMu(:,:,17)  =imresize(im2bw(s17,graythresh(rgb2gray(s17))),[110 55],'bilinear');
ShuZiZiMu(:,:,18)  =imresize(im2bw(s18,graythresh(rgb2gray(s18))),[110 55],'bilinear');
ShuZiZiMu(:,:,19)  =imresize(im2bw(s19,graythresh(rgb2gray(s19))),[110 55],'bilinear');
ShuZiZiMu(:,:,20)  =imresize(im2bw(s20,graythresh(rgb2gray(s20))),[110 55],'bilinear');
ShuZiZiMu(:,:,21)  =imresize(im2bw(s21,graythresh(rgb2gray(s21))),[110 55],'bilinear');
ShuZiZiMu(:,:,22)  =imresize(im2bw(s22,graythresh(rgb2gray(s22))),[110 55],'bilinear');
ShuZiZiMu(:,:,23)  =imresize(im2bw(s23,graythresh(rgb2gray(s23))),[110 55],'bilinear');
ShuZiZiMu(:,:,24)  =imresize(im2bw(s24,graythresh(rgb2gray(s24))),[110 55],'bilinear');
ShuZiZiMu(:,:,25)  =imresize(im2bw(s25,graythresh(rgb2gray(s25))),[110 55],'bilinear');
ShuZiZiMu(:,:,26)  =imresize(im2bw(s26,graythresh(rgb2gray(s26))),[110 55],'bilinear');
ShuZiZiMu(:,:,27)  =imresize(im2bw(s27,graythresh(rgb2gray(s27))),[110 55],'bilinear');
ShuZiZiMu(:,:,28)  =imresize(im2bw(s28,graythresh(rgb2gray(s28))),[110 55],'bilinear');
ShuZiZiMu(:,:,29)  =imresize(im2bw(s29,graythresh(rgb2gray(s29))),[110 55],'bilinear');
ShuZiZiMu(:,:,30)  =imresize(im2bw(s30,graythresh(rgb2gray(s30))),[110 55],'bilinear');
ShuZiZiMu(:,:,31)  =imresize(im2bw(s31,graythresh(rgb2gray(s31))),[110 55],'bilinear');
ShuZiZiMu(:,:,32)  =imresize(im2bw(s32,graythresh(rgb2gray(s32))),[110 55],'bilinear');
ShuZiZiMu(:,:,33)  =imresize(im2bw(s33,graythresh(rgb2gray(s33))),[110 55],'bilinear');
ShuZiZiMu(:,:,34)  =imresize(im2bw(s34,graythresh(rgb2gray(s34))),[110 55],'bilinear');


function pco_camera_create_deffile()
 wfid = fopen('pco_camera_def.txt','wt');
 if(wfid == -1 )
  error('Unable to create file: pco_camera_def.txt');
 end

 get_defines('PCO_err.h',wfid);
 get_defines('sc2_defs.h',wfid);
 get_defines('sc2_ml_sdkstructures.h',wfid);
 get_defines('PCO_Recorder_Defines.h',wfid);

 fclose(wfid);
end

function get_defines(hfile,wfid)
n = 0;
fid = fopen(hfile);
if( fid == -1 )
    error(['Unable to open file: ' hfile]);
end
while( true )
    tline = fgetl(fid);
    if( tline == -1 )
     break;
    end
    if(numel(tline)<2)
%     disp(['blank line ',tline]);
     continue;
    end
    if((tline(1)=='/')&&(tline(2)=='/'))
%     disp(['found comment ',tline]);
     continue;
    end
    d = strfind(tline,'#define ');
    if( ~isempty(d) )
        str = strtrim(tline(d(1)+8:end));
%        disp(['string is ',str]);
        s = strfind(str,' ');
        if( ~isempty(s) )
            p = strfind(str(1:s(1)-1),'(');
            if( isempty(p) )
             q = strfind(str,'0x');
             r = strfind(str,'/');
             if( isempty(q) )
              str(s(1)) = '=';
              if( ~isempty(r) )
               str=str(1:r-1);
              end
              s=strfind(str,'.');
              if( ~isempty(s) )
               str=str(1:end-1);
              end
               fprintf(wfid,'%s\n',str);
%              disp(['string is ',str]);
%              eval(str);
               n = n + 1;
             else
              hstr=str(1:q-1);
              hstr=strtrim(hstr);
              hstr=strcat(hstr,'=');
              if( ~isempty(r) )
               numstr=str(q+2:r-1);
              else
               numstr=str(q+2:end);
              end
              numstr=strtrim(numstr);
              num=hex2dec(numstr);
              str=strcat(hstr,num2str(num));
              fprintf(wfid,'%s\n',str);

%              disp(['string is ',hstr,' numstr is ',numstr,' num is ',num2str(num)]);
              n = n + 1;
             end
            end
        end
    end
end
disp(['Number of variables defined in ',hfile,' = ' num2str(n)]);
fclose(fid);

end


function myribbon = riverplot_draw_ribbon(topleft, topright, bottomleft, bottomright, varargin)

%
% This is a subfunction of the riverplot toolbox.
%  - Draws a ribbon given four [x y] coordinate pairs specifying the
%  corners of the ribbon in clockwise order.
%  - Used in riverplot_ribbon.m
%
% :Usage:
% ::
%
%     myribbon = riverplot_draw_ribbon((topleft, topright, bottomleft, bottomright, [optional inputs])
%
% ..
%     Author and copyright information:
%
%     Copyright (C) 2016  Tor Wager
%
%     This program is free software: you can redistribute it and/or modify
%     it under the terms of the GNU General Public License as published by
%     the Free Software Foundation, either version 3 of the License, or
%     (at your option) any later version.
%
%     This program is distributed in the hope that it will be useful,
%     but WITHOUT ANY WARRANTY; without even the implied warranty of
%     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
%     GNU General Public License for more details.
%
%     You should have received a copy of the GNU General Public License
%     along with this program.  If not, see <http://www.gnu.org/licenses/>.
% ..
%
% :Inputs:
%
%   **rect1:**
%        Structure with handles and decription of imrect class object,
%        created with riverplot_rect.m.  This is always the LEFTMOST
%        rect of the pair.
%
%   **rect2:**
%        Same as rect1, but this is the RIGHTMOST rect of the pair
%
% :Optional Inputs:
%   **coverage:**
%        'coverage' followed by 2-element vector for [rect1 rect2], where
%        each value is between 0 and 1 and specifies the percentage of the
%        plot the ribbon will cover.
%
%   **color:**
%        followed by [r g b] color spec for ribbon
%
%   **ax:**
%        followed by axis handle to plot
%
%   **from_bottom:**
%        align ribbon with bottom edges of rects
%
%   **steepness**
%        followed by value for sigmoid steepness, on [0 1] inteval
%
% :Outputs:
%
%   **myribbon:**
%        structure with handles and info for ribbon
%
%
% :Examples:
% ::
%
% rect1 = riverplot_rect('color', [.7 .3 .3], 'position', [1 2 1 3]);
% rect2 = riverplot_rect('color', [.3 .3 .6], 'position', [5 4 1 3]);
% newbr = rect2.topleft;
% newbr(2) = newbr(2) - 1.5;
% myribbon = riverplot_draw_ribbon(rect1.topright, rect2.topleft, rect1.bottomright, newbr, 'color', [.7 .3 .3]);
%
% :References:
%   CITATION(s) HERE
%
% :See also:
%   - list other functions related to this one, and alternatives*
%

% ..
%    Programmers' notes:
%    Created by Tor Wager, July 2, 2016
% ..

% ..
%    DEFAULTS AND INPUTS
% ..

ax = gca;
%myposition = [1 3 2 5];
mycolor = [.3 .3 .8];
steepness = .05;

% optional inputs with default values
for i = 1:length(varargin)
    if ischar(varargin{i})
        switch varargin{i}

            case 'ax', ax = varargin{i+1}; varargin{i+1} = [];
            %case 'position', myposition = varargin{i+1}; varargin{i+1} = [];
            case 'color', mycolor = varargin{i+1}; varargin{i+1} = [];

            case 'steepness', steepness = varargin{i+1}; varargin{i+1} = [];

            case {'coverage', 'from_bottom', 'y_offset'} % pass it on, irrelevant but passed from higher level calling fcn

            otherwise, warning(['Unknown input string option:' varargin{i}]);
        end
    end
end

axes(ax)

% each line coordinate is an [x,y] pair, e.g., topleft = [x,y] for top left
% point in absolute plot coordinates

line1 = riverplot_line(topleft, topright, 'w', 1, steepness);

line2 = riverplot_line(bottomleft, bottomright, 'w', 1, steepness);

ph = patch([line1.xcoords; line2.xcoords(end:-1:1)], [line1.ycoords; line2.ycoords(end:-1:1)], mycolor);

myribbon = struct('line1', line1, 'line2', line2, 'patchh', ph);

set(line1.h, 'Color', mycolor);
set(line2.h, 'Color', mycolor);
set(ph, 'FaceAlpha', .4);

end % function


function inplane = flat2ipAllROIs(flat,inplane,volume)
%
% inplane = flat2ipAllROIs(flat,inplane,[volume])
%
% Author: AAB/BW
%   Transform ROIs from flat view to inplane, going through the volume
%   representation.
%
% Examples:
%    INPLANE{1} = flat2ipAllROIs(FLAT{4},INPLANE{1});
%

if ieNotDefined('volume'), volume = initHiddenGray; end

[volume,volRoiIndexList] = flat2volAllROIs(flat,volume);
inplane = vol2ipAllROIs(volume,inplane);

return;


function write_neuralynx_nts(filename, nts)

% WRITE_NEURALYNX_NTS writes spike timestamps to a NTS file
%
% Use as
%   write_neuralynx_nts(filename, nts)
%
% See also READ_NEURALYNX_NTS

% Copyright (C) 2007, Robert Oostenveld
%
% This file is part of FieldTrip, see http://www.fieldtriptoolbox.org
% for the documentation and details.
%
%    FieldTrip is free software: you can redistribute it and/or modify
%    it under the terms of the GNU General Public License as published by
%    the Free Software Foundation, either version 3 of the License, or
%    (at your option) any later version.
%
%    FieldTrip is distributed in the hope that it will be useful,
%    but WITHOUT ANY WARRANTY; without even the implied warranty of
%    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
%    GNU General Public License for more details.
%
%    You should have received a copy of the GNU General Public License
%    along with FieldTrip. If not, see <http://www.gnu.org/licenses/>.
%
% $Id$

if ~isa(nts.TimeStamp, 'uint64')
  ft_error('timestamps should be uint64');
end

fid  = fopen_or_error(filename, 'wb', 'ieee-le');

% construct the header
buf  = [];
buf  = [buf sprintf('######## Neuralynx Data File Header\r\n')];
buf  = [buf sprintf('## File Name: %s\r\n', filename)];
buf  = [buf sprintf('## Time Opened: (m/d/y): %s  At Time: %s\r\n', datestr(clock, 'mm/dd/yy'), datestr(clock, 'HH:MM:SS'))];
f = fieldnames(nts.hdr);
for i=1:length(f)
  v = getfield(nts.hdr, f{i});
  switch class(v)
    case 'char'
      buf = [buf sprintf('-%s\t%s\r\n', f{i}, v)];
    case 'double'
      buf = [buf sprintf('-%s\t%g\r\n', f{i}, v)];
    otherwise
      ft_error('unknown class in writing header');
  end
end

% pad the rest of the header with zeros and write it to file
buf((end+1):16384) = 0;
fwrite(fid, buf);

% The format of a clustered electrode record is
%   int64 TimeStamp

fwrite(fid, nts.TimeStamp, 'uint64');

% close the file
fclose(fid);


% eeg_compare - compare EEG structures. Output are shown on the command
%               line regarding difference between the files.
% Usage:
%   eeg_compare(EEG1, EEG2);
%
% Input:
%  EEG1 - first EEGLAB structure
%  EEG2 - second EEGLAB structure

function eeg_compare(EEG, EEG2)

%% Assess difference between datasets
fields = fieldnames(EEG);
for iField = 1:length(fields)
    if ~isfield(EEG2, fields{iField})
        fprintf('Field %s missing in second dataset\n', fields{iField});
    else
        if ~isequal(EEG.(fields{iField}), EEG2.(fields{iField}))
            fprintf('Field %s differs\n', fields{iField});
        end
    end
end
if ~isequal(EEG.xmin, EEG2.xmin), fprintf('Difference between xmin is %1.6f sec\n', EEG.xmin-EEG2.xmin); end
if ~isequal(EEG.xmax, EEG2.xmax), fprintf('Difference between xmax is %1.6f sec\n', EEG.xmax-EEG2.xmax); end

% check chanlocs
[~,~,chanlocs1] = eeg_checkchanlocs( EEG.chanlocs, EEG.chaninfo);
[~,~,chanlocs2] = eeg_checkchanlocs( EEG2.chanlocs, EEG.chaninfo);
if length(chanlocs1) == length(chanlocs2)
    differ = 0;
    differLabel = 0;
    for iChan = 1:length(chanlocs1)
        if  sum(abs([ chanlocs1(iChan).X chanlocs1(iChan).Y chanlocs1(iChan).Z] - ...
                [ chanlocs2(iChan).X chanlocs2(iChan).Y chanlocs2(iChan).Z])) > 1e-12
            differ = differ+1;
        end
        if ~isequal(chanlocs1(iChan).labels, chanlocs2(iChan).labels)
            differLabel = differLabel+1;
        end
    end
    if differ
        fprintf('%d channel coordinates differ\n', differ);
    else
        disp('All channel coordinates are OK');
    end
    if differLabel
        fprintf('%d channel label(s) differ\n', differLabel);
    else
        disp('All channel labels are OK');
    end
else
    disp('Different numbers of channels');
end

% check events
if length(EEG.event) ~= length(EEG2.event)
    disp('Different numbers of events');
elseif isempty(EEG.event)
    disp('All events OK (empty)');
else
    fields1 = fieldnames(EEG.event);
    fields2 = fieldnames(EEG2.event);
    allFieldsOK = true;

    if ~isequal(sort(fields1), sort(fields2))
        disp('Not the same number of event fields');
        allFieldsOK = false;
    end

    for iField = 1:length(fields1)
        if isfield(EEG.event, fields1{iField}) && isfield(EEG2.event, fields1{iField})
            diffVal = zeros(1,length(EEG.event));
            if strcmpi(fields1{iField}, 'latency')
                for iEvent = 1:length(EEG.event)
                    diffVal(iEvent) = EEG.event(iEvent).(fields1{iField}) - EEG2.event(iEvent).(fields1{iField});
                end
            else
                for iEvent = 1:length(EEG.event)
                    diffVal(iEvent) = ~isequal(EEG.event(iEvent).(fields1{iField}), EEG2.event(iEvent).(fields1{iField}));
                end
            end
            if any(diffVal ~= 0)
                if strcmpi(fields1{iField}, 'latency')
                    fprintf('Event latency (%2.1f %%) are not OK (abs diff of these is %1.4f samples)\n', length(find(diffVal))/length(diffVal)*100, mean( abs(diffVal(diffVal ~=0 ))) );
                    fprintf(' ******** (see plot)\n');
                    figure; plot(diffVal);
                else
                    fprintf('Event fields "%s" are NOT OK (%2.1f %% of them)\n', fields1{iField}, length(find(diffVal))/length(diffVal)*100);
                end
                allFieldsOK = false;
            end
        end
    end
    disp('All other events OK (unless warning above)');
end

% check epochs
if length(EEG.epoch) == length(EEG2.epoch)
    if ~isempty(EEG.epoch)
        fields1 = fieldnames(EEG.epoch);
        fields2 = fieldnames(EEG2.epoch);
        allFieldsOK = true;
        if ~isequal(sort(fields1), sort(fields2))
            disp('Not the same number of event fields');
            allFieldsOK = false;
        else
            diffVal = [];
            for iField = 1:length(fields1)
                for iEpoch = 1:length(EEG.epoch)
                    diffVal(iEpoch) = ~isequal(EEG.epoch(iEpoch).(fields1{iField}), EEG2.epoch(iEpoch).(fields1{iField}));
                end
                if any(diffVal ~= 0)
                    fprintf('Epoch fields "%s" are NOT OK (%2.1f %% of them)\n', fields1{iField}, length(find(diffVal))/length(diffVal)*100);
                    allFieldsOK = false;
                end
            end
        end
        if allFieldsOK
            disp('All epoch and all epoch fields are OK');
        end
    end
elseif ~isempty(EEG.epoch)
    disp('Different numbers of epochs');
end


function [sourceout] = ft_source2sparse(sourcein)

% FT_SOURCE2SPARSE removes the grid locations outside the brain from the source
% reconstruction, thereby saving memory.
%
% This invalidates the fields that describe the grid, and also makes it
% more difficult to make a plot of each of the slices of the source volume.
% The original source structure can be recreated using FT_SOURCE2FULL.
%
% Use as
%   [source] = ft_source2sparse(source)
%
% See also FT_SOURCE2FULL

% Copyright (C) 2004-2021, Robert Oostenveld
%
% This file is part of FieldTrip, see http://www.fieldtriptoolbox.org
% for the documentation and details.
%
%    FieldTrip is free software: you can redistribute it and/or modify
%    it under the terms of the GNU General Public License as published by
%    the Free Software Foundation, either version 3 of the License, or
%    (at your option) any later version.
%
%    FieldTrip is distributed in the hope that it will be useful,
%    but WITHOUT ANY WARRANTY; without even the implied warranty of
%    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
%    GNU General Public License for more details.
%
%    You should have received a copy of the GNU General Public License
%    along with FieldTrip. If not, see <http://www.gnu.org/licenses/>.
%
% $Id$

% these are used by the ft_preamble/ft_postamble function and scripts
ft_revision = '$Id$';
ft_nargin   = nargin;
ft_nargout  = nargout;

% this function does not take a cfg as input
cfg = [];

% do the general setup of the function
ft_defaults
ft_preamble init
ft_preamble debug
ft_preamble provenance sourcein

% the ft_abort variable is set to true or false in ft_preamble_init
if ft_abort
  return
end

%%

sourcein = ft_checkdata(sourcein, 'datatype', 'source', 'insidestyle', 'logical');

inside  = find( sourcein.inside(:));
outside = find(~sourcein.inside(:));

fprintf('total number of dipoles        : %d\n', length(inside)+length(outside));
fprintf('number of dipoles inside  brain: %d\n', length(inside));
fprintf('number of dipoles outside brain: %d\n', length(outside));

%% construct the output data

% loop over parameters
fn = fieldnames(sourcein);
fn = setdiff(fn, {'dim', 'transform'});

% keep the descriptive fields that remain valid
sourceout = keepfields(sourcein, {'dim', 'transform', 'time', 'freq'});

for i=1:numel(fn)
  dimord = getdimord(sourcein, fn{i});

  clear tmp
  if startsWith(dimord, 'pos_pos') % this should go first
    tmp = sourcein.(fn{i});
    tmp = tmp(inside,inside,:,:,:,:,:);
    sourceout.(fn{i}) = tmp;
  elseif startsWith(dimord, 'pos')
    tmp = sourcein.(fn{i});
    tmp = tmp(inside,:,:,:,:,:,:);
    sourceout.(fn{i}) = tmp;
  elseif startsWith(dimord, '{pos}')
    tmp = sourcein.(fn{i});
    tmp = tmp(inside);
    sourceout.(fn{i}) = tmp;
  elseif startsWith(dimord, '{pos_pos}')
    tmp = sourcein.(fn{i});
    tmp = tmp(inside,inside);
    sourceout.(fn{i}) = tmp;
  else
    % skipping parameters with unknown dimord
  end

  if exist('tmp', 'var')
    ft_info('making "%s" with dimord "%s" sparse', fn{i}, dimord);
  else
    ft_info('skipping "%s" with dimord "%s"', fn{i}, dimord);
  end

end % for each field

%% do the general cleanup and bookkeeping at the end of the function
ft_postamble debug
ft_postamble previous   sourcein
ft_postamble provenance sourceout
ft_postamble history    sourceout


function s = y_to_s ( y )

%*****************************************************************************80
%
%% Y_TO_S writes a year into a string.
%
%  Licensing:
%
%    This code is distributed under the GNU LGPL license.
%
%  Modified:
%
%    16 April 2013
%
%  Author:
%
%    John Burkardt
%
%  Parameters:
%
%    Input, integer Y, the year.
%
%    Output, string S, a representation of the year.
%
  s = sprintf ( '%d', y );

  return
end


%DATGAUSS Apply Gaussian filter on images in a dataset
%
% This command is deprecated, use IM_GAUSS instead.

function a = datgauss(varargin)

  a = im_gauss(varargin{:});

return


classdef FixedPointInFrame < AbstractGeometricPoint
    %FixedPointInFrame Summary of this class goes here
    %   Detailed explanation goes here

    properties
        cartElem(1,1) CartesianElementSet

        name(1,:) char

        lvdData LvdData

        %marker
        markerColor(1,1) ColorSpecEnum = ColorSpecEnum.Red;
        markerShape(1,1) MarkerStyleEnum = MarkerStyleEnum.RightTriangle;

        %track line
        plotTrkLine(1,1) logical = true;
        trkLineColor(1,1) ColorSpecEnum = ColorSpecEnum.Black;
        trkLineSpec(1,1) LineSpecEnum = LineSpecEnum.DottedLine;
    end

    methods
        function obj = FixedPointInFrame(rVect, frame, name, lvdData)
            obj.cartElem = CartesianElementSet(0, rVect(:), [0;0;0], frame);
            obj.name = name;
            obj.lvdData = lvdData;
        end

        function newCartElem = getPositionAtTime(obj, time, ~, inFrame)
            newCartElem = repmat(CartesianElementSet.getDefaultElements(), [1 length(time)]);
            for(i=1:length(time))
                newCartElem(i) = copy(obj.cartElem);
                newCartElem(i).time = time(i);
            end
            newCartElem = convertToFrame(newCartElem, inFrame);
        end

        function name = getName(obj)
            name = obj.name;
        end

        function setName(obj, name)
            obj.name = name;
        end

        function listboxStr = getListboxStr(obj)
            listboxStr = sprintf('%s (Fixed in Frame: %s)', obj.getName(), obj.cartElem.frame.getNameStr());
        end

        function useTf = openEditDialog(obj, ~)
%             useTf = lvd_EditFixedInFramePointGUI(obj, obj.lvdData);

            output = AppDesignerGUIOutput({false});
            lvd_EditFixedInFramePointGUI_App(obj, obj.lvdData, output);
            useTf = output.output{1};
        end

        function tf = isVehDependent(obj)
            tf = false;
        end

        function tf = canBePlotted(obj)
            tf = true;
        end

        function bodyInfo = getOriginBody(obj)
            bodyInfo = obj.cartElem.frame.getOriginBody();
        end

        function tf = usesGroundObj(~, ~)
            tf = false;
        end

        function tf = usesGeometricPoint(~, ~)
            tf = false;
        end

        function tf = usesGeometricVector(~, ~)
            tf = false;
        end

        function tf = usesGeometricCoordSys(~, ~)
            tf = false;
        end

        function tf = usesGeometricRefFrame(~, ~)
            tf = false;
        end

        function tf = usesGeometricAngle(~, ~)
            tf = false;
        end

        function tf = usesGeometricPlane(~, ~)
            tf = false;
        end

        function tf = isInUse(obj, lvdData)
            tf = lvdData.usesGeometricPoint(obj);
        end

        function rVect = getRVect(obj)
            rVect = obj.cartElem.rVect;
        end

        function setRVect(obj, rVect)
            obj.cartElem.rVect = rVect;
        end

        function frame = getFrame(obj)
            frame = obj.cartElem.frame;
        end
    end
end


function tests = test_spm_cat_struct
% Unit Tests for spm_cat_struct
%__________________________________________________________________________
% Copyright (C) 2017 Wellcome Trust Centre for Neuroimaging

% $Id: test_spm_cat_struct.m 7074 2017-05-05 10:51:08Z guillaume $

tests = functiontests(localfunctions);

function test_spm_cat_struct_1(testCase)
s1 = struct('a',1,'b',2);
s2 = struct('a',3,'b',4);

exp = struct('a',{1,3},'b',{2,4});
act = spm_cat_struct(s1,s2);
testCase.verifyEqual(act, exp);

function test_spm_cat_struct_2(testCase)
s1 = struct('a',1);
s2 = struct('b',2);

exp = struct('a',{1,[]},'b',{[],2});
act = spm_cat_struct(s1,s2);
testCase.verifyEqual(act, exp);

function test_spm_cat_struct_3(testCase)
s1 = struct('a',{1,2});
s2 = struct('b',3);

exp = struct('a',{1,2,[]},'b',{[],[],3});
act = spm_cat_struct(s1,s2);
testCase.verifyEqual(act, exp);

exp = struct('a',{[],1,2},'b',{3,[],[]});
act = spm_cat_struct(s2,s1);
testCase.verifyEqual(act, exp);

function test_spm_cat_struct_4(testCase)
s1 = struct('a',{1;2});
s2 = struct('b',3);

exp = struct('a',{1;2;[]},'b',{[];[];3});
act = spm_cat_struct(s1,s2);
testCase.verifyEqual(act, exp);

exp = struct('a',{[],1,2},'b',{3,[],[]});
act = spm_cat_struct(s2,s1);
testCase.verifyEqual(act, exp);

function test_spm_cat_struct_5(testCase)
s1 = struct('a',{1,2});
s2 = struct('b',3);
s3 = struct('a',4,'c',5);

exp = struct('a',{1,2,[],4},'b',{[],[],3,[]},'c',{[],[],[],5});
act = spm_cat_struct(s1,s2,s3);
testCase.verifyEqual(act, exp);

function test_spm_cat_struct_6(testCase)
s1 = struct('a',{1,2;3 4},'b',{5,6;7,8});
s2 = struct('b',{0,1},'c',{3,2});

exp = struct('a',{1,3,2,4,[],[]},'b',{5,7,6,8,0,1},'c',{[],[],[],[],3,2})';
act = spm_cat_struct(s1,s2);
testCase.verifyEqual(act, exp);


%% Reads ECG header in AHA format
% Reads ECG annotations in AHA format. Implements the documentation
% available in the help of the application provided with the database.
%
% Reads ECG headers in AHA format. Implements the documentation
% available in the help of the application provided with the database.
%
% Arguments:
%   + filename: recording to extract header block.
%
% Output:
%   + heasig: header with the ECG properties.
%
%
% See also read_AHA_format, read_AHA_ann, read_ECG, ECGwrapper
%
% Author: Mariano Llamedo Soria
% <matlab:web('mailto:llamedom@electron.frba.utn.edu.ar','-browser') (email)>
% Version: 0.1 beta
% Birthdate: 17/12/2010
% Last update: 19/11/2014
% Copyright 2008-2015
%
function heasig = read_AHA_header(filename)

heasig = [];

%default settings for the whole DB
fidECG = fopen( filename, 'r');

if( fidECG > 0 )

    try
        fseek(fidECG, 0, 'eof');
        bytes_totales = ftell(fidECG);
        %esto es as� en la DB, si fuera necesario se podria cambiar.
        heasig.nsamp = (bytes_totales / 5);
        fclose(fidECG);
    catch ME
        fclose(fidECG);
        rethrow(ME)
    end

    heasig.nsig = 2;
    heasig.freq = 250;
    heasig.gain = repmat(400,1,heasig.nsig);
    heasig.adczero = zeros(1,heasig.nsig);
    % hardcoded fields
    [~, heasig.recname ] = fileparts(filename);
    heasig.btime = '00:00:00';
    heasig.bdate = '01/01/2000';
    heasig.desc = char(strcat(repmat({'ECG'}, heasig.nsig,1), cellstr(num2str(colvec(1:heasig.nsig))) ));

end


function q=transpose(q)
% transpose array of quaternions

q.a = q.a.';
q.b = q.b.';
q.c = q.c.';
q.d = q.d.';