runstim_RF_barsweep_stimcondition1.m 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362
  1. function runstim_RF_barsweep(T_Trl)
  2. global Par %global parameters
  3. % global LPStat %das status values
  4. %Size of fixation window
  5. FixWinSizex = 1.3;
  6. FixWinSizey = 1.3;
  7. %Plot marker at RF loc
  8. % RFon = 0;
  9. rand('state',sum(clock))
  10. %Global properties -assumes Tracker opened at 85Hz
  11. frame = 1/60;
  12. %Dot sizes (physical)
  13. FixDotSize = 0.1;%0.3
  14. FixPix = round(Par.PixPerDeg.*FixDotSize);
  15. TargSz = 0.5*FixDotSize;%0.3.*Par.PixPerDeg;
  16. %Fixation coordinates
  17. Px = 0;
  18. Py = 0;
  19. fixcol =[0.6,0,0];%[1 0 0]
  20. fixcol2 = [0,0,1];
  21. %Receptive field guesses in pixels, the bar sweep will be centred on this
  22. %point
  23. RFx = 30;
  24. RFy = -30;
  25. % RFxa = [-50 -70 -50 -80 -100]; % Darwin, guess based on flash map
  26. % RFya = [-50 -50 -100 -70 -60]; % Darwin
  27. %Tracker times
  28. FIXT = 200; %time to fix before stim onset
  29. STIMT = 1000; %duration of bar sweep, should be 1000ms
  30. PREFIXT = 2000; %Time ot enter fix window
  31. %Timing properties
  32. BarDur = STIMT./1000; %in seconds
  33. BarDurFrame = round(BarDur./frame);
  34. %This is speed in degrees per second
  35. BarSpeed = 4.*Par.PixPerDeg;
  36. %actual distance covered by bar in stimulus time
  37. BarDist = BarSpeed.*BarDur;
  38. %Bar properties
  39. BarCol = [1 1 1];
  40. BarThick = 1;%0.33.*Par.PixPerDeg; %in degrees
  41. BarLength = BarDist/2; %This is half the bar length (in pixels)
  42. %0 = left to right, 90 = down-to-up, 180 = right to left, 270 = up to down
  43. Ang = [0 90 180 270];
  44. Times = Par.Times; %copy timing structure
  45. BG = [0.5 0.5 0.5]; %background Color
  46. %Create log file
  47. LOG.fn = 'runstim_RF_barsweep';
  48. LOG.BG = BG;
  49. LOG.Par = Par;
  50. LOG.Ang = Ang;
  51. LOG.Times = Times;
  52. LOG.BarDur = BarDur;
  53. LOG.BarSpeed = BarSpeed;
  54. LOG.BarCol = BarCol;
  55. LOG.BarThick = BarThick;
  56. LOG.BarLength = BarLength;
  57. LOG.BarDist = BarDist;
  58. LOG.Frame = frame;
  59. LOG.FIXT = FIXT;
  60. LOG.STIMT = STIMT;
  61. LOG.RFx = RFx;
  62. LOG.RFy = RFy;
  63. LOG.ScreenX = 1024;
  64. LOG.Screeny = 768;
  65. currentDir=cd;
  66. mydir = [currentDir,'\RF_mapping_logs\'];
  67. fn = input('Enter LOG file name (e.g. 20110413_B1), blank = no file\n','s');
  68. if isempty(fn)
  69. logon = 0;
  70. else
  71. logon = 1;
  72. fn = [mydir,'RF_barsweep_',fn];
  73. save(fn,'LOG')
  74. end
  75. % for i = 1:10
  76. % uS(i)= cgflip(BG(1), BG(2), BG(3));
  77. % end
  78. %Copy the run stim, it will have the same name as the LOG and go in the
  79. %same directory
  80. fnrs = [fn,'_','runstim.m'];
  81. cfn = [mfilename('fullpath') '.m'];
  82. copyfile(cfn,fnrs)
  83. %Randomly permute the four directions
  84. RANDTAB = randperm(4);
  85. %////YOUR STIMULATION CONTROL LOOP /////////////////////////////////
  86. Hit = 2;
  87. TZ = 0;
  88. %Windows (fix only)
  89. WIN = [0 0 Par.PixPerDeg.*FixWinSizex Par.PixPerDeg.*FixWinSizey 0];
  90. Par.WIN = WIN';
  91. Par.ESC = false; %escape has not been pressed
  92. while ~Par.ESC
  93. %Pretrial
  94. %REad in the sweep direction fo rthis trial
  95. I = RANDTAB(1);
  96. %Word bit = direction
  97. % dasword(I);
  98. %Spatial properties - start and end of sweep
  99. BarStartx = RFx-(cosd(Ang(I)).*(BarDist./2));
  100. BarStarty = RFy-(sind(Ang(I)).*(BarDist./2));
  101. BarEndx = RFx+(cosd(Ang(I)).*(BarDist./2));
  102. BarEndy = RFy+(sind(Ang(I)).*(BarDist./2));
  103. %Speed
  104. BarSpeedx = (BarEndx-BarStartx)./BarDurFrame;
  105. BarSpeedy = (BarEndy-BarStarty)./BarDurFrame;
  106. %/////////////////////////////////////////////////////////////////////
  107. %START THE TRIAL
  108. %set control window positions and dimensions
  109. refreshtracker(1) %for your control display
  110. SetWindowDas %for the dascard
  111. Abort = false; %whether subject has aborted before end of trial
  112. %///////// EVENT 0 START FIXATING //////////////////////////////////////
  113. Par.Updatxy = 1;
  114. cgellipse(Px,Py,FixPix,FixPix,fixcol,'f') %the red fixation dot on the screen
  115. cgflip(BG(1), BG(2), BG(3))
  116. dasreset(0)
  117. %subject has to start fixating central dot
  118. Par.SetZero = false; %set key to false to remove previous presses
  119. Par.Updatxy = 1; %centering key is enabled
  120. Time = 1;
  121. Hit = 0;
  122. while Time < PREFIXT && Hit == 0
  123. dasrun(5)
  124. [Hit Time] = DasCheck; %retrieve position values and plot on Control display
  125. end
  126. %///////// EVENT 1 KEEP FIXATING or REDO ////////////////////////////////////
  127. Par.Updatxy = 1;
  128. if Hit ~= 0 %subjects eyes are in fixation window keep fixating for FIX time
  129. dasreset(1); %test for exiting fix window
  130. Time = 1;
  131. Hit = 0;
  132. while Time < FIXT && Hit == 0
  133. %Check for 5 ms
  134. dasrun(5)
  135. %or just pause for 5ms?
  136. [Hit Time] = DasCheck;
  137. end
  138. if Hit ~= 0 %eye has left fixation to early
  139. %possibly due to eye overshoot, give another chance
  140. dasreset(0);
  141. Time = 1;
  142. Hit = 0;
  143. while Time < PREFIXT && Hit == 0
  144. dasrun(5)
  145. [Hit Time] = DasCheck; %retrieve position values and plot on Control display
  146. end
  147. if Hit ~= 0 %subjects eyes are in fixation window keep fixating for FIX time
  148. dasreset(1); %test for exiting fix window
  149. Time = 1;
  150. Hit = 0;
  151. while Time < FIXT && Hit == 0
  152. %Check for 5 ms
  153. dasrun(5)
  154. % dasrun(5)
  155. [Hit Time] = DasCheck;
  156. end
  157. else
  158. Hit = -1; %the subject did not fixate
  159. end
  160. end
  161. else
  162. Hit = -1; %the subject did not fixate
  163. end
  164. %///////// EVENT 2 DISPLAY STIMULUS //////////////////////////////////////
  165. if Hit == 0 %subject kept fixation, display stimulus
  166. Par.Updatxy = 1;
  167. dasreset(1); %test for exiting fix window
  168. Time = 0;
  169. % StimFlg = true;
  170. stimbitdone = 0;
  171. cgpenwid(BarThick)
  172. fp=0;
  173. % clear uS
  174. while Time < STIMT && Hit == 0 %Keep fixating till target onset
  175. cgellipse(Px,Py,FixPix,FixPix,fixcol,'f') %the red fixation dot on the screen
  176. %Centre of Bar, update x and y position
  177. if ~stimbitdone
  178. Barx = BarStartx;
  179. Bary = BarStarty;
  180. else
  181. Barx = Barx+BarSpeedx;
  182. Bary = Bary+BarSpeedy;
  183. end
  184. %Bar begin and end
  185. BarAng = Ang(I)+90;
  186. x1 = round(Barx-(cosd(BarAng).*(BarLength)));
  187. x2 = round(Barx+(cosd(BarAng).*(BarLength)));
  188. y1 = round(Bary-(sind(BarAng).*(BarLength)));
  189. y2 = round(Bary+(sind(BarAng).*(BarLength)));
  190. cgdraw(x1,y1,x2,y2,BarCol)
  191. % if RFon
  192. % for r = 1:length(RFxa)
  193. % cgellipse(RFxa(r),RFya(r),20,20,[1,0,1],'f')
  194. % end
  195. % end
  196. % cgflip('V')
  197. fp = fp+1;
  198. uS(fp) = cgflip(BG(1), BG(2), BG(3));
  199. % pause
  200. if ~stimbitdone
  201. % dasbit(Par.StimB, 1);
  202. dasbit(1, 1);%first input arg- 1: stim on
  203. stimbitdone = 1;
  204. end
  205. %..............................................................
  206. % if Time > STIMT && StimFlg %present stim no longer than stim time
  207. % StimFlg = false;
  208. % end
  209. % %Check for 1 ms
  210. dasrun(1)%check whether fixation is maintained
  211. Hit = LPStat(1); %LPStat reads out results from dasrun (buffer)
  212. Time = LPStat(0); %time
  213. %[Hit,Time] = DasCheck;
  214. end
  215. % dasreset( 0 ) %test enter fix window
  216. % 0 enter fix window
  217. % 1 leave fix window
  218. % 2 enter target window
  219. %LPStat(0) = time (ms) passed since last reset
  220. %LPStat(1) = control window hit (1 : in or out (depending on input arg to dasreset), 2 : in correct
  221. % target window
  222. %LPStat.(2) = hit position x
  223. %LPStat(3) = hit postion y
  224. %LPStat(4) = reaction time(saccade onset)
  225. %LPStat(5) = time saccade length (exiting fix win and entering target
  226. %win)
  227. %///////// EVENT 3 TARGET ONSET, REACTION TIME //////////////////////////////////////
  228. Par.Updatxy = 1;
  229. if Hit == 0 %subject kept fixation
  230. cgellipse(0,0,TargSz,TargSz,fixcol2,'f') %the red fixation dot on the screen
  231. cgflip(BG(1), BG(2), BG(3))
  232. % dasbit(Par.TargetB, 1);
  233. %EXTRACT USING THE TARGETB as we only want completed trials
  234. %Update counter
  235. TZ = TZ+1;
  236. MAT(TZ,:) = [I,Ang(I),1];
  237. Hit = 2;
  238. else
  239. Abort = true;
  240. end
  241. %END EVENT 3
  242. else
  243. Abort = true;
  244. end
  245. %END EVENT 2
  246. %///////// POSTTRIAL AND REWARD //////////////////////////////////////
  247. if Hit ~= 0 && ~Abort %has entered a target window (false or correct)
  248. % if Par.Mouserun
  249. % HP = line('XData', Par.ZOOM * (LPStat(3) + Par.MOff(1)), 'YData', Par.ZOOM * (LPStat(4) + Par.MOff(2)), 'EraseMode','none');
  250. % else
  251. % HP = line('XData', Par.ZOOM * LPStat(3), 'YData', Par.ZOOM * LPStat(4), 'EraseMode','none');
  252. % end
  253. % set(HP, 'Marker', '+', 'MarkerSize', 20, 'MarkerEdgeColor', 'm')
  254. if Hit == 2
  255. % dasbit(Par.MicroB, 1);
  256. % dasbit(Par.CorrectB, 1);
  257. dasbit(2, 1);%first input arg- 2: correct trial
  258. pause(0.1);%add a time buffer between sending of dasbits
  259. dasbit(2+I, 1);%first input arg- 3 to 6: stimulus condition
  260. % dasbit(Par.RewardB, 1);
  261. dasjuice(5.1);
  262. Par.Corrcount = Par.Corrcount + 1;
  263. pause(Par.RewardTime) %RewardTime is in seconds
  264. dasjuice(0.0);
  265. % dasbit(Par.RewardB, 0);
  266. %Remove trial
  267. RANDTAB(1) = [];
  268. if ~length(RANDTAB)
  269. RANDTAB = randperm(4);
  270. end
  271. else
  272. Hit = 0;
  273. end
  274. %keep following eye motion
  275. dasrun(5)
  276. DasCheck; %keep following eye motion
  277. end
  278. %///////////////////////INTERTRIAL AND CLEANUP
  279. % display([ num2str(Hit) ' ' num2str(LPStat(6)) ' ' num2str(LPStat(7)) ' ' num2str(Time - LPStat(7)) ]);
  280. %reset all bits to null
  281. for i = [0 1 2 3 4 5 6 7] %Error, Stim, Saccade, Trial, Correct,
  282. dasbit(i, 0);
  283. end
  284. dasclearword
  285. %Par.Trlcount = Par.Trlcount + 1; %counts total number of trials for this session
  286. %tracker('update_trials', gcbo, [], guidata(gcbo)) %displays number of trials, corrects and errors
  287. Par.Trlcount = Par.Trlcount + 1; %counts total number of trials for this session
  288. SCNT = {'TRIALS'};
  289. SCNT(2) = { ['N: ' num2str(Par.Trlcount) ]};
  290. SCNT(3) = { ['C: ' num2str(Par.Corrcount) ] };
  291. SCNT(4) = { ['E: ' num2str(Par.Errcount) ] };
  292. set(T_Trl, 'String', SCNT ) %display updated numbers in GUI
  293. [Hit T] = DasCheck;
  294. % cgrect(465,-370,50,50,[1,1,1])
  295. cgflip(BG(1), BG(2), BG(3))
  296. % pause( Times.InterTrial/1000 ) %pause is called with seconds
  297. %Times.InterTrial is in ms
  298. if TZ > 0
  299. save(fn,'LOG','MAT')
  300. end
  301. end %WHILE_NOT_ESCAPED%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%