⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 gui_topo_animate.m

📁 Matlab下的EEG处理程序库
💻 M
📖 第 1 页 / 共 2 页
字号:
function [p] = gui_topo_animate(command,p)

% GUI_TOPO_ANIMATE - GUI controls for animating topography
%
% Useage:   p = gui_topo_animate(command,[p])
%
% command   - either 'init' or 'animate'
%
% p is the eeg_toolbox struct
%
% This function adds controls to the current figure.
% It assumes this figure has been created with a topographic
% map patch and the userdata contains the p struct for the
% data of the patch.
% 

% $Revision: 1.5 $ $Date: 2003/04/08 01:42:38 $

% Licence:  GNU GPL, no express or implied warranties
% History:  05/2002, Darren.Weber@flinders.edu.au
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

if ~exist('command','var'), command = 'init'; end

switch command,
    
	case 'init',
        
        if exist('p','var'),
            if ~isempty(p),
                ANIM = INIT(p);
            end
        else
            ANIM = INIT;
        end
        
	case 'animate',
	    
        ANIM = get(gcbf,'Userdata');
        if isempty(ANIM),
            ANIM = get(gcf,'Userdata');
        end
        
        % Obtain the current view from mouse_rotate, which
        % can be used in eeg_save_graphics
        views = get(ANIM.View,'String');
        ANIM.p.topoView = lower(char(views(get(ANIM.View,'Value'))));
        
        
        
        % ---  First get patch handle (Hp)  ---
        
        axsibs = get(ANIM.axis,'Children');
        for i=1:length(axsibs),
            type = get(axsibs(i),'Type');
            if isequal(type,'patch'),
                ANIM.Hp = axsibs(i);
            end
        end
        
        
      	% Animation setup
        ANIM = toggle_visible(ANIM);
        set(ANIM.Hp,'EraseMode','normal');
        figure(ANIM.gui);
        
        
        % ---  Get the animation parameters (msec)  ---
        
        start_msec  = str2num(get(ANIM.Start,'string'));
        finish_msec = str2num(get(ANIM.Finish,'string'));
        step_msec   = str2num(get(ANIM.Step,'string'));
        
        
        % --- get data from p struct ---
        
        [ SampleRate, timeArray ] = extract_data(ANIM);
        
        
        % ---  Check step parameter  ---
        
        step = step_msec/SampleRate;
        stepREM = step - fix(step);
        if stepREM,
            nointerp = 0;
            % have not yet implemented interpolation
            warning('GUI_TOPO_ANIMATE: Cannot interpolate for steps ~= sample rate\n');
            step = 1;
            set(ANIM.Step,'string',sprintf('%7.2f',SampleRate));
        else
            nointerp = 1;
        end
        
        
        
        % ---  Convert start/finish to data rows  ---
        
        [ index, point ] = NearestXYArrayPoint( timeArray, start_msec, 'exact' );
        if isempty(index),
            [ index, point ] = NearestXYArrayPoint( timeArray, start_msec );
        end
        start_index = index;
        start_point = point;
        
        [ index, point ] = NearestXYArrayPoint( timeArray, finish_msec, 'exact' );
        if isempty(index),
            [ index, point ] = NearestXYArrayPoint( timeArray, finish_msec );
        end
        finish_index = index;
        finish_point = point;
        
        set(ANIM.Start,'value',start_point);
        set(ANIM.Start,'string',sprintf('%7.2f',start_point));
        set(ANIM.Finish,'value',finish_point);
        set(ANIM.Finish,'string',sprintf('%7.2f',finish_point));
        
        
        % ---  Verify start/finish values  ---
        
        if isequal(start_index,finish_index),
            
            % Given start == finish, update topo for that time
            
            % set voltage scale limits
            ANIM = voltage_scale(ANIM,start_index,finish_index);
            caxis([ANIM.p.minimumIntensity ANIM.p.maximumIntensity]);
            colorbar
            
            t = start_index;
            
            ANIM = update_topo(ANIM,t,step);
            
            ANIM = toggle_visible(ANIM);
            p = ANIM.p;
            return;
            
        elseif start_index > finish_index,
            ANIM = toggle_visible(ANIM);
            error('GUI_TOPO_ANIMATE: Finish < Start!\n');
        end
        
        
        
        % Define movie region as figure size
        if get(ANIM.Movie,'value'),
            rect = get(ANIM.gui,'Position');
            rect(1:2) = [0 0];
        end
        
        
        
        % ---  Run the animation  ---
        
        % Update voltage scale limits
        ANIM = voltage_scale(ANIM,start_index,finish_index);
        caxis([ANIM.p.minimumIntensity ANIM.p.maximumIntensity]);
        colorbar
        
        for t=start_index : step : finish_index,
            
            ANIM = update_topo(ANIM,t,step);
            
            % Capture movie frame
            if get(ANIM.Movie,'value'),
                M(t-(start_index-1)) = getframe(ANIM.gui,rect);
            end
		end
        ANIM = toggle_visible(ANIM);
        
        
        if get(ANIM.Movie,'value'),
            % Play movie in another figure
            playtimes = 10;  fps = 10;
            
            figure('NumberTitle','off','Name','Movie Playback (10 FPS, 10 LOOPS)',...
                'PaperType','A4','PaperUnits','centimeters');
            
            axis off; movie(gcf,M,playtimes,fps,rect);
            
            % Save movie to AVI file
            
            movie2avi(M,'topo_movie.avi','quality',100);
            filename = strcat(pwd,filesep,'topo_movie.avi');
            fprintf('Saved movie to %s\n',filename);
        end
        
        p = ANIM.p;
        
        
    otherwise,
        
end

return






%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function [ SampleRate, timeArray, Cdata ] = extract_data(ANIM),
    
    % Unlike most of the eeg_toolbox, this function requires
    % the potential data to be electrodes in rows, voltage in columns;
    % this is especially so for using this data as Cdata in the patch
    % function and facilitates storage and handling of very large
    % patch Cdata, such as cortical patches
    
    if ANIM.p.mesh.current & ~isempty(ANIM.p.mesh.data),
        
        if ANIM.p.mesh.current > length(ANIM.p.mesh.data.meshtype),
            % assume we are plotting the p.volt.data with the electrodes
            SampleRate = ANIM.p.volt.sampleMsec;
            timeArray  = ANIM.p.volt.timeArray(:,1);
            Cdata      = ANIM.p.volt.data';
            return
        end
        
        meshtype = lower(ANIM.p.mesh.data.meshtype{ANIM.p.mesh.current});
        switch meshtype,
        case 'elec',
            % assume we are plotting the p.volt.data with the electrodes
            SampleRate = ANIM.p.volt.sampleMsec;
            timeArray  = ANIM.p.volt.timeArray(:,1);
            Cdata      = ANIM.p.volt.data';
        case 'scalp',
            % assume we are plotting the p.volt.data on the scalp
            SampleRate = ANIM.p.volt.sampleMsec;
            timeArray  = ANIM.p.volt.timeArray(:,1);
            % check for vertices in rows (default) or columns
            nvert = size(ANIM.p.mesh.data.vertices{ANIM.p.mesh.current},1);
            [s1,s2] = size(ANIM.p.mesh.data.Cdata{ANIM.p.mesh.current});
            if isequal(nvert,s1), % vertices in rows, timepoints in columns
                Cdata = ANIM.p.mesh.data.Cdata{ANIM.p.mesh.current};
            else,                 % vertices in columns, timeseries in rows
                % try to rotate it, but it may exceed memory for detailed surfaces
                Cdata = ANIM.p.mesh.data.Cdata{ANIM.p.mesh.current}';
            end
        otherwise
            % assume the data is in p.mesh.data.Cdata, with a 
            % timeseries in p.mesh.data.timeseries
            SampleRate = ANIM.p.mesh.data.timeseries{ANIM.p.mesh.current}(2) - ANIM.p.mesh.data.timeseries{ANIM.p.mesh.current}(1);
            timeArray  = ANIM.p.mesh.data.timeseries{ANIM.p.mesh.current};
            % get number of vertices
            nvert = size(ANIM.p.mesh.data.vertices{ANIM.p.mesh.current},1);
            % Assume more vertices than time points
            [s1,s2] = size(ANIM.p.mesh.data.Cdata{ANIM.p.mesh.current});
            if isequal(nvert,s1), % vertices in rows, timepoints in columns
                Cdata = ANIM.p.mesh.data.Cdata{ANIM.p.mesh.current};
            else,                 % vertices in columns, timeseries in rows
                % try to rotate it, but it may exceed memory
                Cdata = ANIM.p.mesh.data.Cdata{ANIM.p.mesh.current}';
            end
        end
    else
        % assume we are plotting the p.volt.data with the electrodes
        SampleRate = ANIM.p.volt.sampleMsec;
        timeArray  = ANIM.p.volt.timeArray(:,1);
        Cdata      = ANIM.p.volt.data';
    end
    
return


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function [ ANIM ] = update_topo(ANIM,t,step),
	
	[ SampleRate, timeArray, Cdata ] = extract_data(ANIM);
    
    
    % Do we need to average?
    if step > 1,
        Cdata = Cdata(:,t-(step-1):t);
        V = mean(Cdata,2);
    else
        V = Cdata(:,t);
    end
    clear Tmp;
    
    set(ANIM.Hp,'FaceVertexCdata',V);
    
    %ANIM.p.timePoint = t;
    switch ANIM.p.mesh.data.meshtype{ANIM.p.mesh.current},
    case {'scalp','elec'},
        ANIM.p.volt.samplePoint = t;
    otherwise
        ANIM.p.mesh.samplePoint = t;
    end
    
    if (ANIM.p.contour.plot3D == 1),
        ANIM.p = eeg_plot_surf_contours(ANIM.p);
    end
    
    drawnow;
    
    % Update the figure name (title)
    ANIM.p.volt.sampleTime = timeArray(t);
    name = sprintf('Surface: %s @ %8.2f msec',ANIM.p.volt.file, ANIM.p.volt.sampleTime);
    set(ANIM.gui,'Name',name);
    
    % Save the new figure to a graphics file
    if get(ANIM.Save,'Value'),
        types = get(ANIM.Type,'String');
        type = char(types(get(ANIM.Type,'Value')));
        eeg_save_graphics(ANIM.gui,type,ANIM.p,0);
    end
    
    set(ANIM.gui,'Userdata',ANIM);
    
return
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function [ ANIM ] = voltage_scale(ANIM,start,finish),
    
    [ SampleRate, timeArray, Cdata ] = extract_data(ANIM);
    
    yset = 0;
    if isfield(ANIM,'Yset'),
        if get(ANIM.Yset,'value'),
            ANIM.p.minimumIntensity = get(ANIM.Ymin,'value');
            ANIM.p.maximumIntensity = get(ANIM.Ymax,'value');
            yset = 1;
        end
    end
    if ~yset,
        
        % For very large Cdata matrices, it is more memory
        % efficient to use max(Cdata) that first use abs(Cdata)
        Cmax = max(max(Cdata(:,start:finish)));
        Cmin = min(min(Cdata(:,start:finish)));
        absmax = max([Cmax abs(Cmin)]);
        
        ANIM.p.minimumIntensity = -absmax;
        ANIM.p.maximumIntensity =  absmax;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -