157 :numel(fn)
158 if ~matches(fn{j}, me.ignoreProperties)%create a temporary dynamic property
159 p = addprop(me, [fn{j} 'Out']);
160 if strcmp(fn{j},
'sf');p.SetMethod = @
set_sfOut;end
161 if strcmp(fn{j},
'tf');p.SetMethod = @
set_tfOut;end
163 if strcmp(fn{j},
'size');p.SetMethod = @
set_sizeOut;end
166 obj.([fn{j} 'Out']) = obj.(fn{j}); %copy our property value to our tempory copy
167 end
168 end
169
171
172 if isempty(obj.findprop('rotateMode'));p=obj.addprop('rotateMode');p.Transient=true;p.Hidden=true;end
173 if obj.rotationMethod==1
174 obj.rotateMode = kPsychUseTextureMatrixForRotation;
175 else
176 obj.rotateMode = [];
177 end
178
179 if isempty(obj.findprop('gratingSize'));p=obj.addprop('gratingSize');p.Transient=true;p.Hidden=true;end
180 obj.gratingSize = round(obj.ppd*obj.size);
181
182 if isempty(obj.findprop('phaseIncrement'));
183 p=obj.addprop('phaseIncrement');
184 end
185
186 if isempty(obj.findprop('driftPhase'));p=obj.addprop('driftPhase');p.Transient=true;end
187 if obj.correctPhase
188 ps=obj.calculatePhase;
189 obj.driftPhase=obj.phaseOut-ps;
190 else
191 obj.driftPhase=obj.phaseOut;
192 end
193
194 if isempty(obj.findprop('res'));p=obj.addprop('res');p.Transient=true;end
195 if obj.aspectRatio < 1
196 obj.res = round([obj.gratingSize*obj.aspectRatio obj.gratingSize]);
197 else
198 obj.res = round([obj.gratingSize*obj.aspectRatio obj.gratingSize]);
199 end
200
201 if obj.mask == true
202 obj.maskValue = floor((obj.ppd*obj.size)/2);
203 else
204 obj.maskValue = [];
205 end
206
207 if isempty(obj.findprop('texture'));p=obj.addprop('texture');p.Transient=true;end
208
209 if obj.phaseReverseTime > 0
210 obj.phaseCounter = round(obj.phaseReverseTime / obj.sM.screenVals.ifi);
211 end
212
213 if strcmpi(obj.type,'square')
215 obj.res(2), obj.colourOut, obj.mask, obj.contrastMult);
217 obj.res(2)*obj.inducerHeight, obj.colourOut, obj.mask, obj.contrastMult);
218 else
219 if obj.sigmaOut > 0
221 obj.res(2), obj.colourOut, obj.mask, obj.contrastMult, obj.sigmaOut, ...
222 obj.useAlpha, obj.smoothMethod);
224 obj.res(2)*obj.inducerHeight, obj.colourOut, obj.mask, obj.contrastMult, obj.sigmaOut, ...
225 obj.useAlpha, obj.smoothMethod);
226 else
227 obj.texture{1} = CreateProceduralSineGrating(obj.sM.win, obj.res(1),...
228 obj.res(2), obj.colourOut, obj.mask, obj.contrastMult);
229 obj.texture{2} = CreateProceduralSineGrating(obj.sM.win, obj.res(1),...
230 obj.res(2)*obj.inducerHeight, obj.colourOut, obj.mask, obj.contrastMult);
231 end
232 end
233
234 obj.inSetup = false;
235 obj.setRect();
236
238 if obj.sfRecurse == false
239 obj.sfCache = (value/obj.ppd);
240 obj.sfOut = obj.sfCache * obj.scale;
241 else
242 obj.sfOut = value;
243 obj.sfRecurse = false;
244 end
245 %fprintf('\nSET SFOut: %d | cachce: %d | in: %d\n', obj.sfOut, obj.sfCache, value);
246 end
248 obj.tfOut = value;
249 notify(obj,'changePhaseIncrement');
250 end
252 obj.driftDirectionOut = value;
253 notify(obj,'changePhaseIncrement');
254 end
256 obj.sizeOut = value*obj.ppd;
257 notify(obj,'changeScale');
258 end
260 obj.xPositionOut = value*obj.ppd;
261 if ~isempty(obj.texture);obj.setRect;end
262 end
264 obj.yPositionOut = value*obj.ppd;
265 if ~isempty(obj.texture);obj.setRect;end
266 end
267
268 end
269
270 % ===================================================================
271 %> @brief Update this stimulus object for display
272 %>
273 % ===================================================================
276 if obj.correctPhase
277 ps=obj.calculatePhase;
278 obj.driftPhase=obj.phaseOut-ps;
279 else
280 obj.driftPhase=obj.phaseOut;
281 end
282 obj.setRect();
283 end
284
285 % ===================================================================
286 %> @brief Draw this stimulus object for display
287 %>
288 %>
289 % ===================================================================
291 if obj.isVisible == true && obj.tick > obj.delayTicks
292
293 dstRect = Screen(
'Rect',obj.texture{2});
296
297 Screen('DrawTexture', obj.sM.win, obj.texture{1}, [], obj.mvRect,...
298 obj.angleOut, [], [], [], [], obj.rotateMode,...
299 [obj.driftPhase, obj.sfOut, obj.contrastOut, obj.sigmaOut]);
300 Screen(
'DrawTexture', obj.sM.win, obj.texture{2}, [],
dstRect,...
301 obj.angleOut, [], [], [], [], obj.rotateMode,...
302 [obj.driftPhase+obj.phaseOffset, obj.sfOut, obj.inducerContrastOut, obj.sigmaOut]);
303 obj.tick = obj.tick + 1;
304 end
305 end
306
307 % ===================================================================
309 %>
310 % ===================================================================
312 if obj.mouseOverride
314 if obj.mouseValid
315 obj.mvRect = CenterRectOnPointd(obj.mvRect, obj.mouseX, obj.mouseY);
316 end
317 end
318 if obj.doMotion == true
319 obj.mvRect=OffsetRect(obj.mvRect,obj.dX_,obj.dY_);
320 end
321 if obj.doDrift == true
322 obj.driftPhase = obj.driftPhase + obj.phaseIncrement;
323 end
324 if mod(obj.tick,obj.phaseCounter) == 0
325 obj.driftPhase = obj.driftPhase + obj.phaseOfReverse;
326 end
327 end
328
329 % ===================================================================
331 %>
333 %> @return stimulus structure.
334 % ===================================================================
337 obj.texture=[];
338 if obj.mask > 0
339 obj.mask = true;
340 end
341 obj.maskValue = [];
342 obj.removeTmpProperties;
343 end
344
345 % ===================================================================
346 %> @brief
sf Set method
347 %>
348 % ===================================================================
349 function set.sf(obj,value)
350 if value <= 0
351 value = 0.05;
352 end
353 obj.sf = value;
354 obj.salutation(['set sf: ' num2str(value)],'Custom set method')
355 end
356
357 % ===================================================================
358 %> @brief calculate
phase offset
359 %>
360 % ===================================================================
363 if obj.correctPhase > 0
365 size = (obj.sizeOut/2); %divide by 2 to get the 0 point
366 sfTmp = (obj.sfOut/obj.scale)*obj.ppd;
368 md=md-floor(md);
370 end
371 end
372
373 end %---END PUBLIC METHODS---%
374
375
376 %=======================================================================
377 methods ( Access = protected ) %-------PROTECTED METHODS-----%
378 %=======================================================================
379
380 % ===================================================================
382 %>
setRect makes the PsychRect based on the
texture and screen values
383 %> this is modified over parent method as gratings have slightly different
384 %> requirements.
385 % ===================================================================
387 if isempty(obj.findprop('directionOut'));
388 [sx sy]=pol2cart(obj.d2r(obj.direction),obj.startPosition);
389 else
390 [sx sy]=pol2cart(obj.d2r(obj.directionOut),obj.startPosition);
391 end
392 obj.dstRect=Screen('Rect',obj.texture{1});
393 obj.dstRect=ScaleRect(obj.dstRect,obj.scale,obj.scale);
394 obj.dstRect=CenterRectOnPointd(obj.dstRect,obj.sM.xCenter,obj.sM.yCenter);
395 if isempty(obj.findprop('xPositionOut'));
396 obj.dstRect=OffsetRect(obj.dstRect,(obj.xPosition)*obj.ppd,(obj.yPosition)*obj.ppd);
397 else
398 obj.dstRect=OffsetRect(obj.dstRect,obj.xPositionOut+(sx*obj.ppd),obj.yPositionOut+(sy*obj.ppd));
399 end
400 obj.mvRect=obj.dstRect;
401 obj.setAnimationDelta();
402 end
403
404 % ===================================================================
406 %> Use an
event to recalculate
scale as get method is slower (called
407 %> many more times), than an
event which is only called on
update
408 % ===================================================================
413 %fprintf('\nCalculate SFOut: %d | in: %d |
scale: %d\n', obj.sfOut, obj.
sfCache, obj.
scale);
414 end
415
416 % ===================================================================
418 %> Use an event to recalculate as get method is slower (called
419 %> many more times), than an event which is only called on
update
420 % ===================================================================
422 if ~isempty(obj.findprop('tfOut'))
424 if ~isempty(obj.findprop('driftDirectionOut'))
425 if obj.driftDirectionOut == false
427 end
428 end
429 end
430 end
431
432 end
433end
function CreateProceduralSineSmoothedGrating(in windowPtr, in width, in height, in backgroundColorOffset, in radius, in contrastPreMultiplicator, in sigma, in useAlpha, in method)
function CreateProceduralSineSquareGrating(in windowPtr, in width, in height, in backgroundColorOffset, in radius, in contrastPreMultiplicator)
Property size
Definition baseStimulus.m:46
function getMousePosition(in me)
get mouse position we make sure this is only called once per animation tick to improve performance an...
Property sM
our screen manager
Definition baseStimulus.m:165
Property ppd
pixels per degree (normally inhereted from screenManager)
Definition baseStimulus.m:139
function resetTicks(in me)
reset the various tick counters for our stimulus
Property texture
Our texture pointer for texture-based stimuli.
Definition baseStimulus.m:159
Property screenVals
screen settings generated by sM on setup
Definition baseStimulus.m:171
Property dstRect
initial screen rectangle position [LEFT TOP RIGHT BOTTOM]
Definition baseStimulus.m:184
function addRuntimeProperties(in me)
These are transient properties that specify actions during runtime.
The main experiment manager.
Definition runExperiment.m:3
function set_driftDirectionOut(in obj, in value)
function update(in obj)
Update this stimulus object for display.
function set_yPositionOut(in obj, in value)
function set_xPositionOut(in obj, in value)
function draw(in obj)
Draw this stimulus object for display.
Property scale
scale is used when changing size as an independent variable to keep sf accurate
Definition targetInducerStimulus.m:83
function setRect(in obj)
setRect setRect makes the PsychRect based on the texture and screen values this is modified over pare...
function calculatePhase(in obj)
calculate phase offset
Property sfCache
Definition targetInducerStimulus.m:98
Property sf
spatial frequency
Definition targetInducerStimulus.m:17
function animate(in obj)
Animate this object for runExperiment.
Property phase
phase of grating
Definition targetInducerStimulus.m:32
function set_tfOut(in obj, in value)
Property phaseIncrement
the phase amount we need to add for each frame of animation
Definition targetInducerStimulus.m:86
Property sfRecurse
to stop a loop between set method and an event
Definition targetInducerStimulus.m:101
function set_sfOut(in obj, in value)
function reset(in obj)
Reset an structure for runExperiment.
function calculatePhaseIncrement(in obj, in ignoredArg, in ignoredArg)
calculatePhaseIncrement Use an event to recalculate as get method is slower (called many more times),...
function calculateScale(in obj, in ignoredArg, in ignoredArg)
calculateScale Use an event to recalculate scale as get method is slower (called many more times),...
function set_sizeOut(in obj, in value)