Forum Replies Created
- 
		AuthorPosts
- 
		
			
				
 btaParticipant btaParticipantI have figured out a solution, which I’m sharing below (I’ve put this code in a .js file that I added under “modules”). I use it in my Sequence()as inSequence( sepChunkWithChunk("theSeparator", 1, "theStimuli", 2) ), which does what I described in my previous post (*except that it doesn’t add a separator after the final stimulus, which I did on purpose*).// this code below lets you put something like sepChunkWithChunk("separators", 1, "stimuli", 2) into the Sequence // this works so that, if you have a Trial (in a Template) named "separators" and a Trial (in a Template) named "stimuli", … // …it will present trials from the "stimuli" in chunks of 2, with each chunk separated by 1 trial from "separators" // (NOTE: there will be a "separators" chunk between chunks of "stimuli" — meaning if there are 4 chunks of "stimuli", only 3 "separators" chunks will be alreadyUsed) function SepChunkWithChunk(sep, nSep, main, nMain) { assert(typeof(nSep)=="number" && nSep>0, "nSep should be a number greater than 0"); assert(typeof(nMain)=="number" && nMain>0, "nMain should be a number greater than 0"); this.args = [sep, main]; this.run = function(arrays) { var alreadyUsedSep = []; var alreadyUsedMain = []; let sep = arrays[0]; let main = arrays[1]; var numChunksForMain = Math.ceil(main.length / nMain); // calculates the number of chunks of 'main' are necessary to show all items from 'main' var totalNumUsedFromMain = 0; // counter for tallying number of items used from 'main' var chunkedAndSeparatedArray = []; // this array will house the order of all trials, randomized into chunks of 'main' separated by chunks of 'sep' for (let i = 1; i <= numChunksForMain; ++i) { // run this loop as many times as there are chunks of 'main' counterMain = 0; counterSep = 0; // create a chunk with 'nMain' elements by looping 'nMain' times // STOP LOOPING if it's already pulled out all trials from 'main' // (this will happen if, e.g., you have 8 trials in 'main' and 'nMain' is set to something like 5 — two chunks are needed, but the second chunk should only have 3 elements) while (counterMain < nMain && totalNumUsedFromMain < main.length) { // generate a random number between 0 and (main.length-1): r = Math.floor(Math.random()*main.length); // keep generating a new random number until the random number generated hasn't been used before // (this has the effect of blocking the repetition of items from 'main' that have already been added to 'chunkedAndSeparatedArray') while (alreadyUsedMain.includes(r)) { r = Math.floor(Math.random()*main.length); } // now that a unique random number has been generated, add it to the array of random numbers that have been used alreadyUsedMain.push(r); // add the rTH trial from 'main' to 'chunkedAndSeparatedArray' chunkedAndSeparatedArray.push(main[r]); // increase counters ++counterMain; ++totalNumUsedFromMain; } // create a chunk with 'nSep' elements by looping 'nSep' times // DON'T RUN THIS LOOP if the last chunk of 'main' has just been added to 'chunkedAndSeparatedArray' if (i != (numChunksForMain)){ while (counterSep < nSep) { // generate a random number between 0 and (sep.length-1): r = Math.floor(Math.random()*sep.length); // keep generating a new random number until the random number generated hasn't been used before // UNLESS all the trials from 'sep' have already been used // (this has the effect of allowing separator trials to be re-used just in case the number of separators needed is greater than the number of unique trials in 'sep') while (alreadyUsedSep.includes(r) && sep.length > alreadyUsedSep.length ) { r = Math.floor(Math.random()*sep.length); } // now that a unique random number has been generated, add it to the array of random numbers that have been used alreadyUsedSep.push(r); // add the rTH trial from 'sep' to 'chunkedAndSeparatedArray' chunkedAndSeparatedArray.push(sep[r]); // increase counter ++counterSep; } } } // return the finalized Array, which will have all the trials of 'main' in a raondomized order // moreover, between every chunk of 'nMain' trials, there is a chunk of random 'nSep' trials from 'sep' return chunkedAndSeparatedArray; } } function sepChunkWithChunk(sep, nSep, main, nMain) { return new SepChunkWithChunk(sep, nSep, main, nMain); } btaParticipant btaParticipantGreat that worked perfectly!  btaParticipant btaParticipantThank you, this worked great!  btaParticipant btaParticipantThank you so much, this is so helpful! I find it challenging to think this way, but I’m starting to get used to it.  btaParticipant btaParticipantOh great, thanks! This is very helpful. I did not know that all JS functions are run from the start, even when the calls to those functions are made within instances of PennController test.is.The one thing that I didn’t mention before is that I did want to reuse the image multiple times, which I think would just mean using the series of test.isstatements every time I reuse the image. Is that right?
 (i.e., it seems to me that all of thesenewImages cannot have the same name —something like testerImage— because every timenewImageis called it needs to have a unique identifier; and because of that, there’s no way to use a single line of code likegetImage("testerImage")to call back that same image.) btaParticipant btaParticipantGreat, yes, that worked! Thank you! 
- 
		AuthorPosts