00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038 #include "Component/ModelManager.H"
00039 #include "Image/Image.H"
00040 #include "Psycho/PsychoDisplay.H"
00041 #include "Psycho/EyeTrackerConfigurator.H"
00042 #include "Psycho/EyeTracker.H"
00043 #include "Psycho/PsychoOpts.H"
00044 #include "Component/EventLog.H"
00045 #include "Component/ComponentOpts.H"
00046 #include "Raster/Raster.H"
00047 #include "Util/MathFunctions.H"
00048 #include "Util/Types.H"
00049 #include "GameBoard/basic-graphics.H"
00050 #include <sys/types.h>
00051 #include <dirent.h>
00052 #include <errno.h>
00053 #include <vector>
00054 #include <string>
00055 #include <iostream>
00056 #include <SDL/SDL.h>
00057 #include <SDL/SDL_image.h>
00058 #include <SDL/SDL_mixer.h>
00059 #include <stdio.h>
00060 #include <stdlib.h>
00061 #include <sstream>
00062 #include <time.h>
00063 #include "Image/DrawOps.H"
00064 #include "GameBoard/resize.h"
00065 #include <iostream>
00066 #include <fstream>
00067 #include <set>
00068 #include <algorithm>
00069 #include <ctime>
00070
00071 #ifndef INVT_HAVE_LIBSDL_IMAGE
00072 #include <cstdio>
00073 int main()
00074 {
00075 fprintf(stderr, "The SDL_image library must be installed to use this program\n");
00076 return 1;
00077 }
00078
00079 #else
00080
00081
00082
00083 using namespace std;
00084
00085
00086
00087 ModelManager manager("Psycho-Spatial-Orientation");
00088 nub::soft_ref<PsychoDisplay> d(new PsychoDisplay(manager));
00089 map<uint,uint> testMap ;
00090 map<string,string> argMap ;
00091 map<string,vector<SDL_Rect*>*> clipsmap;
00092
00093
00094
00095
00096
00097 template <class T> std::string stringify(T i)
00098 {
00099 ostringstream o ;
00100 o << i ;
00101 return o.str();
00102 }
00103
00104
00105 double getAvarage(vector<long> v){
00106 double f = 0.0 ;
00107 for( uint i = 0 ; i < v.size() ; i++ ){
00108 f += v[i] ;
00109 }
00110 if (v.size()!=0) return f/v.size() ;
00111 return -1 ;
00112 }
00113
00114 double getVariance(vector<long> v){
00115 double m = getAvarage(v);
00116 double var = 0.0 ;
00117 for( uint i = 0 ; i < v.size(); i++ ){
00118 var += (v[i]-m)*(v[i]-m) ;
00119 }
00120 if (v.size()!=0) return var/v.size() ;
00121 return -1 ;
00122 }
00123
00124 bool itIsInThere(int x , vector<int> bag){
00125 for( uint i=0 ; i < bag.size(); i++ ){
00126 if(x == bag[i]) return true ;
00127 }
00128 return false ;
00129 }
00130
00131
00132
00133
00134
00135
00136 string ascSort(string st)
00137 {
00138 string res = "" ;
00139 vector<string> v = vector<string>();
00140 for(uint i = 0 ; i < st.size() ; i++) v.push_back(st.substr(i,1)) ;
00141
00142 std::sort(v.begin(), v.end());
00143
00144 for ( uint i = 0 ; i < v.size() ; i++ ){
00145 res += v[i] ;
00146 }
00147 return res;
00148 }
00149
00150
00151
00152
00153
00154
00155
00156 string desSort(string st)
00157 {
00158 string res = "" ;
00159 vector<string> v = vector<string>();
00160 for(uint i = 0 ; i < st.size() ; i++) v.push_back(st.substr(i,1)) ;
00161 std::sort(v.begin(), v.end());
00162 std::reverse(v.begin(), v.end());
00163 for ( uint i = 0 ; i < v.size() ; i++ ){
00164 res += v[i] ;
00165 }
00166 return res;
00167 }
00168
00169
00170
00171
00172
00173
00174 string getARandomString(uint l, string alphabet="0123456789" ){
00175
00176 string test = string("") ;
00177 string retString ;
00178 test = "" ;
00179 string tp = string("") ;
00180 vector<int> pickedones = vector<int>() ;
00181 for(uint i = 0 ; i < l ; i++){
00182 int nd;
00183 do{ nd= rand()% alphabet.size() ; }while(itIsInThere(nd,pickedones)) ;
00184 pickedones.push_back(nd);
00185 tp = alphabet.substr(nd,1) ;
00186 test += tp ;
00187 }
00188 retString = test ;
00189 return retString ;
00190 }
00191
00192
00193
00194
00195
00196
00197
00198 string digitMemorizationTask(uint l, string alphabet="0123456789" , int displayFrame = 10 ){
00199 d->clearScreen() ;
00200 vector<int> pickedones = vector<int>() ;
00201 string test = string("") ;
00202 string tp = string("") ;
00203 for(uint i = 0 ; i < l ; i++){
00204 int nd;
00205 do{ nd= rand()% alphabet.size() ; }while(itIsInThere(nd,pickedones) && pickedones.size() <= alphabet.size()) ;
00206 pickedones.push_back(nd);
00207 tp = alphabet.substr(nd,1) ;
00208 test += tp ;
00209 }
00210 d->displayText(test,true,0) ;
00211 d->waitFrames(displayFrame) ;
00212 d->clearScreen() ;
00213 return test ;
00214 }
00215
00216
00217
00218
00219
00220 void scramble(vector<string>& v){
00221 vector<string> tv = vector<string>() ;
00222 while(v.size()>0){
00223 tv.push_back(v[0]);
00224 v.erase(v.begin());
00225 }
00226 int i = 0 ;
00227 while(tv.size()>0){
00228 i = rand()%tv.size() ;
00229 v.push_back(tv[i]);
00230 tv.erase(tv.begin()+i);
00231 }
00232 }
00233
00234 void scramble(vector<int>& v){
00235 vector<int> tv = vector<int>() ;
00236 while(v.size()>0){
00237 tv.push_back(v[0]);
00238 v.erase(v.begin());
00239 }
00240 int i = 0 ;
00241 while(tv.size()>0){
00242 i = rand()%tv.size() ;
00243 v.push_back(tv[i]);
00244 tv.erase(tv.begin()+i);
00245 }
00246 }
00247
00248
00249
00250
00251 SDL_Surface* getButtonImage(string label , PixRGB<byte> txtcolor=PixRGB<byte>(0,0,0) , PixRGB<byte> bgcolor=PixRGB<byte>(255,255,255) ,Point2D<int> size = Point2D<int>(100,100) ,PixRGB<byte> bordercolor=PixRGB<byte>(0,0,0) , int border=3){
00252 Image<PixRGB<byte> > textIm(d->getWidth(),d->getHeight(),ZEROS);
00253 textIm.clear(bgcolor);
00254 writeText(textIm, Point2D<int>((size.i - label.length()*10)/2,(size.j-20) /2),label.c_str(),txtcolor,bgcolor);
00255 SDL_Surface *surf = d->makeBlittableSurface(textIm , true);
00256 Uint32 bc = d->getUint32color(bordercolor);
00257 drawRectangle(surf,bc,0,0,size.i -1,size.j -1 ,border);
00258 SDL_Surface* blank =getABlankSurface(size.i , size.j);
00259 SDL_Rect clip;
00260 clip.x = 0 ;
00261 clip.y = 0 ;
00262 clip.w = size.i ;
00263 clip.h = size.j ;
00264 apply_surface(0,0,*surf,*blank,clip);
00265 dumpSurface(surf) ;
00266 return blank ;
00267 }
00268
00269
00270
00271
00272
00273
00274 SDL_Surface* getKeyPad(string alphabet,map<string , SDL_Rect>& buttmap){
00275 SDL_Surface* pad= getABlankSurface(d->getWidth()/4,d->getHeight()/3);
00276 SDL_Rect clip;
00277 clip.x=0;
00278 clip.y=0;
00279 int numofrows = alphabet.size()/3 +1;
00280 if(alphabet.size()%3 != 0 ) numofrows++ ;
00281 int numofcolumns = 3 ;
00282 clip.w= pad->w / numofcolumns ;
00283 clip.h = pad->h / numofrows ;
00284
00285
00286 for( int i = 0 ; i < numofrows*3 ; i++){
00287 SDL_Surface* but ;
00288 if((uint)i < alphabet.size()){
00289 but = getButtonImage(alphabet.substr(i,1),PixRGB<byte>(0,0,0),PixRGB<byte>(255,255,255),Point2D<int>(pad->w / numofcolumns , pad->h / numofrows),PixRGB<byte>(255, 98 , 25),3);
00290 }else{
00291 but = getButtonImage(" ",PixRGB<byte>(0,0,0),PixRGB<byte>(255,255,255),Point2D<int>(pad->w / numofcolumns , pad->h / numofrows),PixRGB<byte>(255, 98 , 25),3);
00292 }
00293
00294 SDL_Rect cl ;
00295 cl.x = ((i)%numofcolumns)*(pad->w)/numofcolumns ; cl.y= ((i)/numofcolumns)*((pad->h)/numofrows) ;
00296 cl.w = clip.w ;
00297 cl.h = clip.h ;
00298 apply_surface( cl.x , cl.y ,*but,*pad,clip);
00299 if((uint)i < alphabet.size()) buttmap[alphabet.substr(i,1)] = cl ;
00300 dumpSurface(but);
00301 }
00302 SDL_Rect cl1 ;
00303 cl1.x = 0 ; cl1.y= (numofrows-1)*((pad->h)/numofrows) ;
00304 cl1.w = clip.w ;
00305 cl1.h = clip.h ;
00306 buttmap["!"] = cl1 ;
00307 SDL_Surface* but = getButtonImage(string("<-"),PixRGB<byte>(0,0,0),PixRGB<byte>(255,255,255),Point2D<int>(pad->w / numofcolumns , pad->h / numofrows),PixRGB<byte>(255, 98 , 25),3);
00308 apply_surface(0, (numofrows-1)*((pad->h)/numofrows),*but,*pad,clip);
00309 dumpSurface(but);
00310 SDL_Rect cl2 ;
00311 cl2.x = (pad->w)/numofcolumns ; cl2.y= (numofrows-1)*((pad->h)/numofrows) ;
00312 cl2.w = clip.w ;
00313 cl2.h = clip.h ;
00314 buttmap[" "] = cl2 ;
00315 but = getButtonImage(string("spc"),PixRGB<byte>(0,0,0),PixRGB<byte>(255,255,255),Point2D<int>(pad->w / numofcolumns , pad->h / numofrows),PixRGB<byte>(255, 98 , 25),3);
00316 apply_surface((pad->w)/numofcolumns, (numofrows-1)*((pad->h)/numofrows),*but,*pad,clip);
00317 dumpSurface(but);
00318 SDL_Rect cl3 ;
00319 cl3.x = 2*(pad->w)/numofcolumns ; cl3.y= (numofrows-1)*((pad->h)/numofrows) ;
00320 cl3.w = clip.w ;
00321 cl3.h = clip.h ;
00322 buttmap["*"] = cl3 ;
00323 but = getButtonImage(string("Ok"),PixRGB<byte>(0,0,0),PixRGB<byte>(255,255,255),Point2D<int>(pad->w / numofcolumns , pad->h / numofrows),PixRGB<byte>(255, 98 , 25),3);
00324 apply_surface(2*(pad->w)/numofcolumns, (numofrows-1)*((pad->h)/numofrows),*but,*pad,clip);
00325 dumpSurface(but);
00326 return pad ;
00327 }
00328
00329
00330
00331
00332
00333
00334
00335
00336
00337 string getPressedButtonCommand(map<string , SDL_Rect>& buttmap,Point2D<int> offset=Point2D<int>(0,0)){
00338 int quit = 0 ;
00339 string s ;
00340 SDL_Event event ;
00341 while( quit!=2 ){
00342 while( SDL_PollEvent( &event ) ) {
00343 if(event.type == SDL_MOUSEBUTTONDOWN && event.button.button == SDL_BUTTON_LEFT ){
00344 for( map<string , SDL_Rect>::iterator it = buttmap.begin() ; it!=buttmap.end() ; ++it){
00345 if(event.button.x >= (it->second).x + offset.i && event.button.x <= (it->second).x + (it->second).w + offset.i && event.button.y >= (it->second).y+ offset.j && event.button.y <= (it->second).y + (it->second).h + offset.j) {
00346 quit = 2 ;
00347 s = it->first ;
00348 break;
00349 }
00350
00351 }
00352 }
00353
00354 }
00355 }
00356 return s ;
00357
00358 }
00359
00360
00361
00362
00363
00364
00365
00366 string getDigitSequenceFromSubject(string alphabet="0123456789" , uint maxl = 7 , string message=""){
00367 d->showCursor(true) ;
00368
00369 map<string , SDL_Rect>* buttmap = new map<string , SDL_Rect>();
00370
00371 SDL_Surface * keypad = getKeyPad(alphabet,*buttmap);
00372
00373 SDL_Rect offset ;
00374 offset.x = (d->getWidth() - keypad->w) /2;
00375 offset.y = (d-> getHeight() - keypad->h) /2;
00376
00377 SDL_Surface* msgp = getButtonImage(message ,PixRGB<byte>(195,60,12) ,PixRGB<byte>(127,127,127) ,Point2D<int>(d->getWidth()/6,d->getHeight() /15) ,PixRGB<byte>(127,127,127) , 4) ;
00378 SDL_Rect msgoffs ; msgoffs.x = (d->getWidth() - msgp->w) /2 ; msgoffs.y = 2*d->getHeight()/9 ;
00379 d->displaySDLSurfacePatch(msgp , &msgoffs , NULL , -2 , false ,true ) ;
00380 dumpSurface(msgp) ;
00381
00382 d->displaySDLSurfacePatch(keypad , &offset,NULL , -2,false, true);
00383
00384 string p = string("") ;
00385
00386 string tp = string("");
00387
00388 while( tp.compare("*")!=0 ){
00389
00390 SDL_Surface* dp = getButtonImage(p ,PixRGB<byte>(195,60,12) ,PixRGB<byte>(255,255,255) ,Point2D<int>(d->getWidth()/6,d->getHeight() /15) ,PixRGB<byte>(0,25,180) , 4) ;
00391 SDL_Rect offs ; offs.x = (d->getWidth() - dp->w) /2 ; offs.y = d->getHeight()/6 ;
00392 d->displaySDLSurfacePatch(dp , &offs , NULL , -2 , false ,true ) ;
00393
00394 tp = getPressedButtonCommand(*buttmap,Point2D<int>(offset.x,offset.y)) ;
00395 dumpSurface(dp) ;
00396 if(tp.compare("!")==0 && p.size()>=0 ) {
00397 if (p.size()>0) p = p.substr(0,p.size()-1) ;
00398 }else{
00399 if(p.size() < maxl && tp.compare("*")!=0) {
00400 p +=tp ;
00401 }
00402
00403 }
00404
00405 }
00406
00407 buttmap = 0 ;
00408 dumpSurface(keypad) ;
00409 d->clearScreen() ;
00410 return p ;
00411
00412 }
00413
00414
00415
00416
00417
00418
00419
00420
00421
00422
00423
00424 bool isAnswerCorrect(string test , string answer , int mode){
00425
00426 if(mode == 0 && answer.compare(test)==0) return true ;
00427
00428 if(mode == 1 && answer.compare(ascSort(test))==0) return true ;
00429
00430 if(mode == 2 && answer.compare(desSort(test))==0) return true ;
00431
00432 return false;
00433 }
00434
00435
00436
00437 int addArgument(const string st,const string delim="="){
00438 int i = st.find(delim) ;
00439 argMap[st.substr(0,i)] = st.substr(i+1);
00440
00441 return 0 ;
00442 }
00443
00444 std::string getArgumentValue(string arg){
00445 return argMap[arg] ;
00446 }
00447
00448
00449 void displayWholeNumber(string s , int onsetTime , int wsd){
00450 int x = (d->getWidth()-s.size()*wsd)/2 ;
00451 int y = (d->getHeight())/2 -10;
00452 Image<PixRGB<byte> > textIm(d->getWidth(),d->getHeight(),ZEROS);
00453 textIm.clear(PixRGB<byte>(128,128,128));
00454 for( uint k = 0 ; k < s.size() ; k++ ){
00455
00456 writeText(textIm, Point2D<int>(x+k*wsd,y),s.substr(k,1).c_str(),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128));
00457 }
00458 SDL_Surface *surf = d->makeBlittableSurface(textIm , true);
00459 SDL_Rect offs ; offs.x = 0 ; offs.y = 0 ;
00460 d->displaySDLSurfacePatch(surf , &offs , NULL , -2 , false ,true ) ;
00461 dumpSurface(surf);
00462 d->waitFrames(onsetTime);
00463 d->clearScreen() ;
00464 }
00465
00466 void displayWholeNumberVertically(string s , int onsetTime , int wsd){
00467 int x = (d->getWidth())/2 ;
00468 int y = (d->getHeight()-s.size()*wsd)/2 ;
00469 Image<PixRGB<byte> > textIm(d->getWidth(),d->getHeight(),ZEROS);
00470 textIm.clear(PixRGB<byte>(128,128,128));
00471 for( uint k = 0 ; k < s.size() ; k++ ){
00472
00473 writeText(textIm, Point2D<int>(x,y+k*wsd),s.substr(k,1).c_str(),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128));
00474 }
00475 SDL_Surface *surf = d->makeBlittableSurface(textIm , true);
00476 SDL_Rect offs ; offs.x = 0 ; offs.y = 0 ;
00477 d->displaySDLSurfacePatch(surf , &offs , NULL , -2 , false ,true ) ;
00478 dumpSurface(surf);
00479 d->waitFrames(onsetTime);
00480 d->clearScreen() ;
00481 }
00482
00483 void displayRandom(string s , int onsetTime){
00484 for( uint k = 0 ; k < s.size() ; k++ ){
00485 int x = 9*d->getWidth()/20 + rand()%(d->getWidth()/10);
00486 int y = 9*d->getHeight()/20 + rand()%(d->getHeight()/10) ;
00487 d->displayText(s.substr(k,1),Point2D<int>(x,y),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128),true) ;
00488 d->waitFrames(onsetTime);
00489 d->clearScreen() ;
00490 }
00491 }
00492
00493 void displayLinear(string s , int onsetTime){
00494 int x = (d->getWidth()-s.size()*40)/2 ;
00495 int y = d->getHeight()/2 - 10;
00496 for( uint k = 0 ; k < s.size() ; k++ ){
00497 d->displayText(s.substr(k,1),Point2D<int>(x+k*40,y),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128),true) ;
00498 d->waitFrames(onsetTime);
00499 d->clearScreen() ;
00500 }
00501 }
00502
00503 void displayLinearReverse(string s , int onsetTime){
00504 int x = (d->getWidth()-s.size()*10)/2 ;
00505 int y = d->getHeight()/2 - 10;
00506 for( uint k = 0 ; k < s.size() ; k++ ){
00507 d->displayText(s.substr(k,1),Point2D<int>(x+(s.size()-k)*10,y),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128),true) ;
00508 d->waitFrames(onsetTime);
00509 d->clearScreen() ;
00510 }
00511 }
00512 void displayLinearRandom(string s , int onsetTime){
00513 int x = (d->getWidth()-s.size()*10)/2 ;
00514 int y = d->getHeight()/2 - 10;
00515 for( uint k = 0 ; k < s.size() ; k++ ){
00516 d->displayText(s.substr(k,1),Point2D<int>(x+ (random()%s.size())*10,y),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128),true) ;
00517 d->waitFrames(onsetTime);
00518 d->clearScreen() ;
00519 }
00520 }
00521
00522 void displayLinearRandomVertically(string s , int onsetTime){
00523 int x = (d->getWidth())/2 ;
00524 int y = (d->getHeight()-s.size()*10)/2 - 10;
00525 for( uint k = 0 ; k < s.size() ; k++ ){
00526 d->displayText(s.substr(k,1),Point2D<int>(x, (random()%s.size())*10+y),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128),true) ;
00527 d->waitFrames(onsetTime);
00528 d->clearScreen() ;
00529 }
00530 }
00531
00532 void displayLinearRandomNoRepeating(string s , int onsetTime){
00533 int x = (d->getWidth()-s.size()*10)/2 ;
00534 int y = d->getHeight()/2 - 10;
00535 for( uint k = 0 ; k < s.size() ; k++ ){
00536 d->displayText(s.substr(k,1),Point2D<int>(x+ (random()%s.size())*10,y),PixRGB<byte>(0,0,0),PixRGB<byte>(128,128,128),true) ;
00537 d->waitFrames(onsetTime);
00538 d->clearScreen() ;
00539 }
00540 }
00541
00542
00543 void showMask(int frames, string alphabet="0123456789"){
00544 Image<PixRGB<byte> > textIm(d->getWidth(),d->getHeight(),ZEROS);
00545 PixRGB<byte> bgcolor = PixRGB<byte>(128,128,128);
00546 PixRGB<byte> txtcolor = PixRGB<byte>(0,0,0);
00547 textIm.clear(bgcolor);
00548 for(int i = 0 ; i < 200 ; i++)
00549 writeText(textIm, Point2D<int>((int)random()%(d->getWidth()),(int)random()%(d->getHeight())),alphabet.substr(random()%(int)alphabet.size(),1).c_str(),txtcolor,bgcolor);
00550 SDL_Surface *surf = d->makeBlittableSurface(textIm , true);
00551 SDL_Rect offs ; offs.x = 0 ; offs.y = 0 ;
00552 d->displaySDLSurfacePatch(surf , &offs , NULL , -2 , false ,true ) ;
00553 d->waitFrames(frames) ;
00554 d->clearScreen();
00555 dumpSurface(surf) ;
00556 }
00557
00558 string get0213x(string is){
00559 string sst = ascSort(is);
00560 string tail= "";
00561 if(is.size()>4) tail = sst.substr(4,sst.size()-4);
00562 string rSt= sst.substr(0,1)+sst.substr(2,1)+sst.substr(1,1)+sst.substr(3,1) +tail;
00563 return rSt ;
00564 }
00565
00566 string get3120x(string is){
00567 string sst = ascSort(is);
00568 string tail= "";
00569 if(is.size()>4) tail = sst.substr(4,sst.size()-4);
00570 string rSt= sst.substr(3,1)+sst.substr(1,1)+sst.substr(2,1)+sst.substr(0,1) +tail;
00571 return rSt ;
00572 }
00573
00574 string get3021x(string is){
00575 string sst = ascSort(is);
00576 string tail= "";
00577 if(is.size()>4) tail = sst.substr(4,sst.size()-4);
00578 string rSt= sst.substr(3,1)+sst.substr(0,1)+sst.substr(2,1)+sst.substr(1,1) +tail;
00579 return rSt ;
00580 }
00581
00582 string get1203x(string is){
00583 string sst = ascSort(is);
00584 string tail= "";
00585 if(is.size()>4) tail = sst.substr(4,sst.size()-4);
00586 string rSt= sst.substr(1,1)+sst.substr(2,1)+sst.substr(0,1)+sst.substr(3,1) +tail;
00587 return rSt ;
00588 }
00589
00590 string get1032x(string is){
00591 string sst = ascSort(is);
00592 string tail= "";
00593 if(is.size()>4) tail = sst.substr(4,sst.size()-4);
00594 string rSt= sst.substr(1,1)+sst.substr(0,1)+sst.substr(3,1)+sst.substr(2,1) +tail;
00595 return rSt ;
00596 }
00597
00598 string get2301x(string is){
00599 string sst = ascSort(is);
00600 string tail= "";
00601 if(is.size()>4) tail = sst.substr(4,sst.size()-4);
00602 string rSt= sst.substr(2,1)+sst.substr(3,1)+sst.substr(0,1)+sst.substr(1,1) +tail;
00603 return rSt ;
00604 }
00605
00606
00607 vector<int> spatial_memory_task(int onsetTime, int isd , int dir , int ma=30 ,int Ma=120){
00608
00609 int w = d->getWidth();
00610 int h = d->getHeight();
00611 int neg = rand()%(Ma-ma) +ma ;
00612 int pos = rand()%(Ma-ma) +ma ;
00613
00614 if(dir==0) {
00615 d->displayRedDotFixation(w/2+pos,h/2);
00616 d->waitFrames(onsetTime);
00617 d->clearScreen();
00618 d->waitFrames(isd);
00619 d->displayRedDotFixation(w/2-neg,h/2);
00620 d->waitFrames(onsetTime);
00621 d->clearScreen();
00622 }
00623 if(dir==1) {
00624 d->displayRedDotFixation(w/2,h/2+pos);
00625 d->waitFrames(onsetTime);
00626 d->clearScreen();
00627 d->waitFrames(isd);
00628 d->displayRedDotFixation(w/2,h/2-neg);
00629 d->waitFrames(onsetTime);
00630 d->clearScreen();
00631 }
00632 vector<int> locations;
00633 locations.push_back(neg);
00634 locations.push_back(pos);
00635 return locations ;
00636 }
00637
00638 int spatial_memory_retrival(vector<int> dotsVector,int dir ,int ma=30 , int Ma=120 ,int ds=30 ){
00639
00640 int w = d->getWidth();
00641 int h = d->getHeight();
00642 int change = rand()%2;
00643 int neg = dotsVector.at(0); int pos = dotsVector.at(1);
00644 switch( change ){
00645 case 0 : d->pushEvent("same target");break;
00646 case 1 : d->pushEvent("target changed");break;
00647 }
00648 if(change == 1){
00649 int chDir = rand()%2;
00650 int c=0;
00651 if(chDir==0){
00652 c =((rand()%2 -0.5)/0.5 );
00653 if( neg+ ds > Ma ) c = -1 ;
00654 if(neg -ds < ma ) c=+1 ;
00655 neg = neg + c*ds ;
00656 }
00657 if(chDir==1){
00658 c =((rand()%2 -0.5)/0.5 );
00659 if( pos+ ds > Ma ) c = -1 ;
00660 if(pos -ds < ma ) c=+1 ;
00661 pos = pos + c*ds ;
00662 }
00663 }
00664
00665 d->pushEvent("for retrieval dots showed at negative side :"+ stringify(neg)+" positive side:" + stringify(pos));
00666 if(dir == 0){
00667 d->displayRedDotFixation(w/2+pos,h/2);
00668 d->displayRedDotFixation(w/2-neg,h/2);
00669 }
00670 if(dir == 1){
00671 d->displayRedDotFixation(w/2,h/2+pos);
00672 d->displayRedDotFixation(w/2,h/2-neg);
00673 }
00674 d->waitFrames(30);
00675 d->clearScreen();
00676 string ans = getDigitSequenceFromSubject("yn-",1);
00677 int res = 0 ;
00678 if(change==0 && ans.compare("y")==0) res=1;
00679 if(change==1 && ans.compare("n")==0) res=1;
00680 return res ;
00681 }
00682
00683 int playTone(Mix_Music* tone ){
00684 if(Mix_PlayMusic(tone,0)==-1){return -1;}
00685 while(Mix_PlayingMusic()==1){} ;
00686 return 0 ;
00687 }
00688
00689
00690
00691
00692 std::string getUsageComment(){
00693
00694 string com = string("\nlist of arguments : \n");
00695
00696 com += "\nlogfile=[logfilename.psy] {default = psycho-sm-or.psy}\n" ;
00697 com += "\nmemo=[a_string_without_white_space]\n";
00698 com += "\nstring-size=[>0](the size of counter string){default=4} \n";
00699 com += "\nsubject=[subject_name] \n" ;
00700 com += "\nnum-of-trials=[>1] (number of trials ) {default=10}\n";
00701 com += "\nalphabet=[a string of characters](a string of characters){default=abcdefghijklmnopqrstuvwxyz}\n";
00702 com += "\nmode=[1,2,3](1 for spatial memory task 2 for single counter task, 2 for concurrent task){default=1}\n";
00703 com += "\nsingle-dot-onset=[>1](number of frames that the single dot should be presented){default=16}\n";
00704 com += "\ndots_ISI=[>1](number of frames between dots presentations){default=16}\n";
00705 com += "\ndots-radius=[>1](the radius for circle of dots in pixel){default=100}\n";
00706 com += "\ndots-min-radius=[>0](minimum distance of dots from center){default=32}\n";
00707 com += "\ndots-max-radius=[>0] (maximum distance of dots from center){default=158}\n";
00708 com += "\nspatial-delay=[>0](number of frames for spatial memory task ){default=180}\n";
00709 com += "\n spatial-counter-ISI=[>1](numer of frames between last dot presentation and start of counter task){default=16}\n";
00710 com += "\n counter-length=[>1](total lenght of counter experiment in frames){default=300}\n";
00711 com += "\n counter-spatial-query-ISI=[>1](the delay between end of counter trail and start of spatial memory query in number of frames){default=16}\n";
00712 com += "\n spatial-query-length=[>1](the total length for showing the spatial memory test in number of frames){default=60}\n";
00713 com += "\n spatial-query-counter-query-ISI=[>1](number of frames between the unspeeded spatial memory query and showing the counter query){default=30}\n";
00714 com += "\n counter-query-length=[>1](number of frames for presenting the counter query){default=60}\n";
00715 com += "\n cue-onset-frames=[>1](){default=3}\n";;
00716 com += "\nsound-dir=[path to wav files directory]{default=..}\n";
00717 com += "\ntone1=[a valid file name](name of wav file without extension for tone 1){default=sin}\n";
00718 com += "\ntone2=[a valid file name](name of wav file without extension for tone 2){default=square}\n";
00719 com += "\ndot-shift=[>1](amount of shift in dots position in pixel)[default=16]\n";
00720 com +="\nsorting-delay=[>1](the delay for sorting in number of frames){default=360}\n";
00721 return com ;
00722 }
00723
00724 extern "C" int main(const int argc, char** argv)
00725 {
00726
00727 MYLOGVERB = LOG_INFO;
00728
00729 argMap["experiment"]="spatial-memory-test";
00730 argMap["logfile"]="psycho-sm.psy" ;
00731 argMap["string-size"]="5" ;
00732 argMap["num-of-trials"]="5";
00733 argMap["subject"]="" ;
00734 argMap["memo"]="" ;
00735 argMap["single-dot-onset"]="16" ;
00736 argMap["dots-ISI"]="16";
00737 argMap["spatial-delay"]="180";
00738 argMap["spatial-counter-ISI"]="16";
00739 argMap["counter-length"]="300";
00740 argMap["counter-spatial-query-ISI"]="16";
00741 argMap["spatial-query-length"]="60";
00742 argMap["spatial-query-counter-query-ISI"]="30";
00743 argMap["counter-query-length"]="60";
00744 argMap["alphabet"]="0123456789";
00745 argMap["mode"]="0" ;
00746 argMap["cue-onset-frames"] = "3" ;
00747 argMap["sound-dir"]="..";
00748 argMap["tone1"]="sine";
00749 argMap["tone2"]="square";
00750 argMap["cue-file"]="cue1";
00751 argMap["min-tone-wait"]="50";
00752 argMap["max-tone-wait"]="80";
00753 argMap["dots-min-radius"]="32";
00754 argMap["dots-max-radius"]="158";
00755 argMap["dot-shift"] = "32";
00756 argMap["sorting-delay"]="300";
00757 manager.addSubComponent(d);
00758 nub::soft_ref<EventLog> el(new EventLog(manager));
00759 manager.addSubComponent(el);
00760 d->setEventLog(el);
00761 nub::soft_ref<EyeTrackerConfigurator>
00762 etc(new EyeTrackerConfigurator(manager));
00763 manager.addSubComponent(etc);
00764
00765 if (manager.parseCommandLine(argc, argv,
00766 "at least one argument needed", 1, -1)==false){
00767 cout<<getUsageComment()<<endl;
00768 return(1);
00769 }
00770
00771 for(uint i = 0 ; i < manager.numExtraArgs() ; i++){
00772 addArgument(manager.getExtraArg(i),std::string("=")) ;
00773 }
00774
00775 manager.setOptionValString(&OPT_EventLogFileName, argMap["logfile"]);
00776
00777
00778
00779
00780
00781
00782
00783 manager.start();
00784 for(map<string,string>::iterator it= argMap.begin(); it!= argMap.end() ; ++it) d->pushEvent("arg:"+ it->first+" value:"+it->second ) ;
00785
00786 d->clearScreen();
00787 d->displayISCANcalib();
00788 d->waitForMouseClick();
00789 d->displayText("Here the experiment starts! click to start!");
00790 d->waitForMouseClick();
00791 d->clearScreen();
00792
00793
00794 string masterString=argMap["alphabet"];
00795
00796 int mode = atoi(argMap["mode"].c_str());
00797 int numOfTests = atoi(argMap["num-of-trials"].c_str()) ;
00798 int stringSize = atoi(argMap["string-size"].c_str());
00799 int dots_ISI = atoi(argMap["dots-ISI"].c_str()) ;
00800 int dot_onset = atoi(argMap["single-dot-onset"].c_str());
00801 int dots_min_radius = atoi(argMap["dots-min-radius"].c_str());
00802 int dots_max_radius = atoi(argMap["dots-max-radius"].c_str());
00803 int delayForSorting = atoi(argMap["sorting-delay"].c_str());
00804
00805
00806
00807
00808 int dot_max_change = atoi(argMap["dot-shift"].c_str());
00809 vector<int> orientation_task_Vector;
00810 for( int i = 0 ; i< numOfTests ; i++ ){
00811 orientation_task_Vector.push_back(0);
00812 orientation_task_Vector.push_back(1);
00813
00814
00815 }
00816
00817 scramble(orientation_task_Vector);
00818
00819
00820
00821 d->clearScreen();
00822
00823 cout<< stringify(d->getWidth())<<" x "<<stringify(d->getHeight())<<endl;
00824
00825 Mix_Music* tone1 = NULL;
00826 Mix_Music* tone2 = NULL;
00827 map<int,Mix_Music*> audio_map ;
00828 map<string,int> charmap ;
00829 map<int,string> charinvmap ;
00830
00831 if( Mix_OpenAudio( 22050, MIX_DEFAULT_FORMAT, 2, 4096 ) == -1 ){
00832 LINFO( "did not open the mix-audio") ;
00833 return -1 ;
00834 }
00835
00836 for(uint i = 0; i < masterString.size() ; i++){
00837 string str = argMap["sound-dir"]+"/"+masterString.substr(i,1)+".wav";
00838 audio_map[i]=Mix_LoadMUS(str.c_str());
00839 charmap[masterString.substr(i,1)]=i;
00840 charinvmap[i]=masterString.substr(i,1) ;
00841 }
00842
00843 for( uint i=10;i<100 ;i++ ){
00844 charmap[stringify(i)]=i;
00845 charinvmap[i]=stringify(i);
00846 }
00847
00848
00849 string tmpstr = argMap["sound-dir"]+"/"+argMap["tone1"]+".wav";
00850 tone1 = Mix_LoadMUS(tmpstr.c_str());
00851 tmpstr = argMap["sound-dir"]+"/"+argMap["tone2"]+".wav";
00852 tone2 = Mix_LoadMUS(tmpstr.c_str());
00853
00854 int cr = numOfTests ;
00855 d->showCursor(true);
00856 d->displayText("click one of the mouse buttons to start!");
00857 d->waitForMouseClick() ;
00858 d->showCursor(false);
00859
00860 map<int,int> correctSPMMap;correctSPMMap[0]=0;correctSPMMap[1]=0;correctSPMMap[2]=0;correctSPMMap[3]=0;
00861 map<int,int> incorrectSPMMap;incorrectSPMMap[0]=0;incorrectSPMMap[1]=0;incorrectSPMMap[2]=0;incorrectSPMMap[3]=0;
00862 cr=0;
00863 while( cr < 2*numOfTests ){
00864 string inStr = getARandomString(stringSize,argMap["alphabet"]);
00865
00866 string testString="" ;
00867 int flp = rand()%6;
00868 switch( flp ){
00869 case 0 : testString = get0213x(ascSort(inStr)); break;
00870 case 1 : testString = get3120x(ascSort(inStr)); break;
00871 case 2 : testString = get3021x(ascSort(inStr)); break;
00872 case 3 : testString = get1203x(ascSort(inStr)); break;
00873 case 4 : testString = get1032x(ascSort(inStr)); break;
00874 case 5 : testString = get2301x(ascSort(inStr)); break;
00875 }
00876 d->showCursor(false);
00877 d->clearScreen() ;
00878 d->clearScreen() ;
00879 d->displayFixationBlink();
00880 d->pushEvent("**************************************") ;
00881 d->pushEvent("initial string :" + testString);
00882 for( int i = 0 ; i < stringSize ; i++ ){
00883 playTone(audio_map[charmap[testString.substr(i,1)]]);
00884 d->waitFrames(5);
00885 }
00886
00887
00888 showMask(4,"abcdefghijklmnopqrstuvwxyz");
00889 d->waitFrames(30);
00890 d->displayFixation();
00891 d->waitFrames(10);
00892 d->clearScreen() ;
00893 d->pushEvent("presentation orientation: " + stringify((int)(orientation_task_Vector.at(cr)%2)));
00894 vector<int> dotsVector = spatial_memory_task(dot_onset,dots_ISI,(int)(orientation_task_Vector.at(cr)%2),dots_min_radius,dots_max_radius);
00895 d->pushEvent("dots showed at negative:"+ stringify(dotsVector.at(0))+" positive:" + stringify(dotsVector.at(1)));
00896
00897 d->displayFixation();
00898 d->waitFrames(15);
00899 int currentTask=mode;
00900
00901
00902
00903
00904
00905
00906 if(currentTask==0){
00907 d->pushEvent("task : memorization");
00908 playTone(tone1);
00909 }
00910 if(currentTask==1){
00911 d->pushEvent("task : sorting");
00912 playTone(tone1);
00913 }
00914 d->waitFrames(delayForSorting);
00915 playTone(tone2);
00916 d->waitFrames(30);
00917
00918 int spMemAns = spatial_memory_retrival(dotsVector,(int)(orientation_task_Vector.at(cr)%2),dots_min_radius,dots_max_radius,dot_max_change);
00919 switch( spMemAns ){
00920 case 0: incorrectSPMMap[orientation_task_Vector.at(cr)]= incorrectSPMMap[orientation_task_Vector.at(cr)]+1;d->pushEvent("incorrect spatial memory answer");break;
00921 case 1: correctSPMMap[orientation_task_Vector.at(cr)]= correctSPMMap[orientation_task_Vector.at(cr)]+1;d->pushEvent("correct spatial memory answer");break;
00922 }
00923
00924 string ans1 = getDigitSequenceFromSubject(argMap["alphabet"],stringSize,"");
00925 d->pushEvent("string answer: "+ans1);
00926 if(mode==0){
00927 if(ans1.compare(testString)==0){
00928 d->pushEvent("correct string recall");
00929 d->displayText(":)");
00930 d->waitFrames(15);
00931 }else{
00932 d->pushEvent("incorrect string recall");
00933 d->displayText(":(");
00934 d->waitFrames(15);
00935 }
00936 }
00937
00938 if(mode==1){
00939 if(ans1.compare(ascSort(testString))==0){
00940 d->pushEvent("correct string sorting");
00941 d->displayText(":)");
00942 d->waitFrames(15);
00943 }else{
00944 d->pushEvent("incorrect string sorting");
00945 d->displayText(":(");
00946 d->waitFrames(15);
00947 }
00948 }
00949
00950
00951 cr++;
00952 }
00953
00954 d->pushEvent("horizontal, memory correct:"+stringify(correctSPMMap[0]));
00955 d->pushEvent("vertical, memory correct:"+stringify(correctSPMMap[1]));
00956 d->pushEvent("horizontal, memory incorrect:"+stringify(incorrectSPMMap[0]));
00957 d->pushEvent("vertical, memory incorrect:"+stringify(incorrectSPMMap[1]));
00958
00959 d->displayText("Experiment complete. Thank you!");
00960 d->waitForMouseClick();
00961
00962
00963 manager.stop();
00964
00965
00966
00967 return 0;
00968 }
00969
00970 #endif // INVT_HAVE_LIBSDL_IMAGE
00971