cm_eeg_topoplot_20140226.m 8.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233
  1. function [handle,Zi,grid,Xi,Yi] = cm_eeg_topoplot_20140226(Values,loc_file,MAPLIMITS)
  2. %% functions needed:
  3. % - THG_eeg_readlocs
  4. % - THG_eeg_finputcheck
  5. %%%%%%%%%%%%%%%%%%%%%%%% Set defaults %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
  6. % whitebk = 'on'; % by default, make gridplot background color = EEGLAB screen background color
  7. rmax = 0.5; % actual head radius - Don't change this!
  8. GRID_SCALE = 57; % plot map on a n x n grid
  9. CIRCGRID = 201; % number of angles to use in drawing circles
  10. AXHEADFAC = 1.3; % head to axes scaling factor
  11. CONTOURNUM = 6; % number of contour levels to plot
  12. STYLE = 'both'; % default 'style': both,straight,fill,contour,blank
  13. HEADCOLOR = [0 0 0]; % default head color (black = [0 0 0])
  14. BACKCOLOR = [1 1 1];
  15. ELECTRODES = 'on'; % default 'electrodes': on|off|label - set below
  16. EMARKER = '.'; % mark electrode locations with small disks
  17. EMARKERSIZE = 6;
  18. ECOLOR = [0 0 0]; % default electrode color = black
  19. EMARKERLINEWIDTH = 1; % default edge linewidth for emarkers
  20. HLINEWIDTH = 1; % default linewidth for head, nose, ears
  21. BLANKINGRINGWIDTH = .05; % width of the blanking ring
  22. HEADRINGWIDTH = .01; % width of the cartoon head ring
  23. % SHADING = 'flat'; % default 'shading': flat|interp
  24. cmap = colormap;
  25. cmaplen = size(cmap,1);
  26. %% Read the channel location information
  27. [tmpeloc labels Th Rd indices] = cm_eeg_readlocs_20140226( loc_file );
  28. Th = pi/180*Th;
  29. allchansind = 1:length(Th);
  30. %% Channels to plot
  31. plotchans = indices;
  32. [x,y] = pol2cart(Th,Rd); % transform electrode locations from polar to cartesian coordinates
  33. plotchans = abs(plotchans); % reverse indicated channel polarities
  34. allchansind = allchansind(plotchans);
  35. Th = Th(plotchans);
  36. Rd = Rd(plotchans);
  37. x = x(plotchans);
  38. y = y(plotchans);
  39. labels = labels(plotchans); % remove labels for electrodes without locations
  40. labels = strvcat(labels); % make a label string matrix
  41. Values = Values(plotchans);
  42. %% Read plotting radius from chanlocs
  43. plotrad = min(1.0,max(Rd)*1.02); % default: just outside the outermost electrode location
  44. plotrad = max(plotrad,0.5); % default: plot out to the 0.5 head boundary
  45. default_intrad = 1; % indicator for (no) specified intrad
  46. intrad = min(1.0,max(Rd)*1.02); % default: just outside the outermost electrode location
  47. %% Set radius of head cartoon
  48. headrad = rmax; % (anatomically correct)
  49. %% Find plotting channels
  50. pltchans = find(Rd <= plotrad); % plot channels inside plotting circle
  51. intchans = find(x <= intrad & y <= intrad); % interpolate and plot channels inside interpolation square
  52. %% Eliminate channels not plotted
  53. allx = x;
  54. ally = y;
  55. intchans; % interpolate using only the 'intchans' channels
  56. pltchans; % plot using only indicated 'plotchans' channels
  57. intValues = Values(intchans);
  58. Values = Values(pltchans);
  59. % now channel parameters and values all refer to plotting channels only
  60. allchansind = allchansind(pltchans);
  61. intTh = Th(intchans); % eliminate channels outside the interpolation area
  62. intRd = Rd(intchans);
  63. intx = x(intchans);
  64. inty = y(intchans);
  65. Th = Th(pltchans); % eliminate channels outside the plotting area
  66. Rd = Rd(pltchans);
  67. x = x(pltchans);
  68. y = y(pltchans);
  69. labels = labels(pltchans,:);
  70. %% Squeeze channel locations to <= rmax
  71. squeezefac = rmax/plotrad;
  72. intRd = intRd*squeezefac; % squeeze electrode arc_lengths towards the vertex
  73. Rd = Rd*squeezefac; % squeeze electrode arc_lengths towards the vertex
  74. % to plot all inside the head cartoon
  75. intx = intx*squeezefac;
  76. inty = inty*squeezefac;
  77. x = x*squeezefac;
  78. y = y*squeezefac;
  79. allx = allx*squeezefac;
  80. ally = ally*squeezefac;
  81. % Note: Now outermost channel will be plotted just inside rmax
  82. % rotate channels based on chaninfo %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
  83. rotate = 0;
  84. %% Make the plot
  85. xmin = min(-rmax,min(intx)); xmax = max(rmax,max(intx));
  86. ymin = min(-rmax,min(inty)); ymax = max(rmax,max(inty));
  87. % Interpolate scalp map data
  88. xi = linspace(xmin,xmax,GRID_SCALE); % x-axis description (row vector)
  89. yi = linspace(ymin,ymax,GRID_SCALE); % y-axis description (row vector)
  90. [Xi,Yi,Zi] = griddata(inty,intx,intValues,yi',xi,'cubic'); % interpolate data ('invdist' replaced by)
  91. % Mask out data outside the head
  92. mask = (sqrt(Xi.^2 + Yi.^2) <= rmax); % mask outside the plotting circle
  93. ii = find(mask == 0);
  94. Zi(ii) = NaN; % mask non-plotting voxels with NaNs
  95. grid = plotrad; % unless 'noplot', then 3rd output arg is plotrad
  96. % Colormap limits
  97. amin = MAPLIMITS(1);
  98. amax = MAPLIMITS(2);
  99. delta = xi(2)-xi(1); % length of grid entry
  100. % Scale the axes
  101. cla % clear current axis
  102. hold on
  103. h = gca; % uses current axes
  104. set(gca,'Xlim',[-rmax rmax]*AXHEADFAC,'Ylim',[-rmax rmax]*AXHEADFAC,'color','w','xcolor','w','ycolor','w','zcolor','w','xtick',[],'ytick',[]);
  105. %% plot
  106. tmph = surface(Xi-delta/2,Yi-delta/2,zeros(size(Zi)),Zi,'EdgeColor','none','FaceColor','flat'); % 'FaceColor','interp' or 'flat'
  107. colormap jet
  108. %% Set color axis
  109. caxis([amin amax]) % set coloraxis
  110. handle = gca;
  111. %% Plot filled ring to mask jagged grid boundary
  112. hwidth = HEADRINGWIDTH; % width of head ring
  113. hin = squeezefac*headrad*(1- hwidth/2); % inner head ring radius
  114. rwidth = BLANKINGRINGWIDTH; % width of blanking outer ring
  115. rin = rmax*(1-rwidth/2); % inner ring radius
  116. if hin>rin
  117. rin = hin; % don't blank inside the head ring
  118. end
  119. %% mask the jagged border around rmax
  120. circ = linspace(0,2*pi,CIRCGRID);
  121. rx = sin(circ);
  122. ry = cos(circ);
  123. ringx = [[rx(:)' rx(1) ]*(rin+rwidth) [rx(:)' rx(1)]*rin];
  124. ringy = [[ry(:)' ry(1) ]*(rin+rwidth) [ry(:)' ry(1)]*rin];
  125. ringh = patch(ringx,ringy,0.01*ones(size(ringx)),BACKCOLOR,'edgecolor','none'); hold on
  126. %% Plot head outline
  127. headx = [[rx(:)' rx(1) ]*(hin+hwidth) [rx(:)' rx(1)]*hin];
  128. heady = [[ry(:)' ry(1) ]*(hin+hwidth) [ry(:)' ry(1)]*hin];
  129. ringh = patch(headx,heady,ones(size(headx)),'k','edgecolor','none'); hold on
  130. %% Plot ears and nose
  131. base = rmax-.0046;
  132. basex = 0.18*rmax; % nose width
  133. tip = 1.15*rmax;
  134. tiphw = .04*rmax; % nose tip half width
  135. tipr = .01*rmax; % nose tip rounding
  136. q = .04; % ear lengthening
  137. EarX = [.497-.005 .510 .518 .5299 .5419 .54 .547 .532 .510 .489-.005]; % rmax = 0.5
  138. EarY = [q+.0555 q+.0775 q+.0783 q+.0746 q+.0555 -.0055 -.0932 -.1313 -.1384 -.1199];
  139. sf = headrad/plotrad; % squeeze the model ears and nose
  140. % by this factor
  141. plot3([basex;tiphw;0;-tiphw;-basex]*sf,[base;tip-tipr;tip;tip-tipr;base]*sf,...
  142. 2*ones(size([basex;tiphw;0;-tiphw;-basex])),...
  143. 'Color',HEADCOLOR,'LineWidth',HLINEWIDTH); % plot nose
  144. plot3(EarX*sf,EarY*sf,2*ones(size(EarX)),'color',HEADCOLOR,'LineWidth',HLINEWIDTH) % plot left ear
  145. plot3(-EarX*sf,EarY*sf,2*ones(size(EarY)),'color',HEADCOLOR,'LineWidth',HLINEWIDTH) % plot right ear
  146. %% Show electrode information
  147. plotax = gca;
  148. axis square
  149. axis off
  150. pos = get(gca,'position');
  151. xlm = get(gca,'xlim');
  152. ylm = get(gca,'ylim');
  153. axis square % make textax square
  154. pos = get(gca,'position');
  155. set(plotax,'position',pos);
  156. xlm = get(gca,'xlim');
  157. set(plotax,'xlim',xlm);
  158. ylm = get(gca,'ylim');
  159. set(plotax,'ylim',ylm); % copy position and axis limits again
  160. %% Mark electrode locations only
  161. ELECTRODE_HEIGHT = 2.1; % z value for plotting electrode information (above the surf)
  162. hp2 = plot3(y*.95,x*.95,ones(size(x))*ELECTRODE_HEIGHT,...
  163. EMARKER,'Color',ECOLOR,'markersize',EMARKERSIZE,'linewidth',EMARKERLINEWIDTH);
  164. %%%%%%%%%%%%% Set EEGLAB background color to match head border %%%%%%%%%%%%%%%%%%%%%%%%
  165. hold off
  166. axis off
  167. return