Last active
February 21, 2018 16:31
-
-
Save rbnpi/6b33d412b4e0c1caa0ad7e4eef6a7363 to your computer and use it in GitHub Desktop.
Sonic Pi Simon musical game with TouchOSC interface vidoe of program running at https://youtu.be/XIm8z8ht8IU
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?xml version="1.0" encoding="UTF-8"?><layout version="16" mode="0" orientation="horizontal"><tabpage name="dG91Y2g=" scalef="0.0" scalet="1.0" li_t="" li_c="gray" li_s="14" li_o="false" li_b="false" la_t="" la_c="gray" la_s="14" la_o="false" la_b="false" ><control name="cHVzaA==" x="57" y="145" w="200" h="200" color="gray" scalef="0.0" scalet="1.0" type="multipush" number_x="2" number_y="2" local_off="true" ></control><control name="c2NvcmU=" x="68" y="105" w="80" h="25" color="red" type="labelh" text="" size="14" background="true" outline="false" ></control><control name="aGlzY29yZQ==" x="160" y="106" w="80" h="25" color="red" type="labelh" text="" size="14" background="true" outline="false" ></control><control name="bGFiZWwz" x="40" y="47" w="239" h="24" color="yellow" type="labelh" text="U29uaWMgUGkgU2ltb24gR2FtZQ==" size="22" background="true" outline="false" ></control><control name="bGFiZWw0" x="69" y="78" w="80" h="25" color="red" type="labelh" text="U2NvcmU=" size="14" background="true" outline="false" ></control><control name="bGFiZWw1" x="159" y="76" w="80" h="25" color="green" type="labelh" text="SGktU2NvcmU=" size="14" background="true" outline="false" ></control><control name="bGFiZWw3" x="60" y="149" w="95" h="95" color="green" type="labelh" text="" size="14" background="true" outline="true" ></control><control name="bGFiZWw4" x="158" y="246" w="95" h="95" color="yellow" type="labelh" text="" size="14" background="true" outline="true" ></control><control name="bGFiZWw5" x="61" y="246" w="95" h="95" color="blue" type="labelh" text="" size="14" background="true" outline="true" ></control><control name="bGFiZWwxMA==" x="158" y="149" w="95" h="95" color="red" type="labelh" text="" size="14" background="true" outline="true" ></control><control name="bGVkZw==" x="61" y="150" w="93" h="93" color="green" scalef="0.0" scalet="1.0" type="led" ></control><control name="bGVkeQ==" x="159" y="247" w="93" h="93" color="yellow" scalef="0.0" scalet="1.0" type="led" ></control><control name="bGVkYg==" x="62" y="247" w="93" h="93" color="blue" scalef="0.0" scalet="1.0" type="led" ></control><control name="bGVkcg==" x="159" y="150" w="93" h="93" color="red" scalef="0.0" scalet="1.0" type="led" ></control><control name="bGFiZWwxMQ==" x="64" y="390" w="185" h="25" color="red" type="labelh" text="YnkgUm9iaW4gTmV3bWFu" size="14" background="true" outline="false" ></control><control name="dHVybg==" x="65" y="356" w="181" h="25" color="blue" type="labelh" text="" size="14" background="true" outline="true" ></control></tabpage></layout> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#Game of Simon for Sonic Pi with TouchOSC interface | |
#by Robin Newman, February 2018 | |
use_osc '192.168.1.240',9000 #address of TouchOSC device. Adjust to suit your setup | |
use_real_time | |
use_debug false | |
use_osc_logging false | |
osc "/touch/score",0 #intialise scores on TouchOSC device | |
osc "/touch/hiscore",0 | |
sleep 0.2 | |
set :button,"" #set up initial time state values | |
set :pattern,[] | |
set :score,0 | |
set :hiscore,0 | |
set :currentstep,0 | |
use_random_seed(Time.now.nsec) #set random seed for new game | |
define :ledon do |s| #function to flash "led" on TouchOSC device and play note | |
use_real_time | |
case s | |
when "g" | |
osc "/touch/ledg",1 | |
play :e3,release: 0.3 | |
when "r" | |
osc "/touch/ledr",1 | |
play :cs4,release: 0.3 | |
when "b" | |
osc "/touch/ledb",1 | |
play :e4,release: 0.3 | |
when "y" | |
osc "/touch/ledy",1 | |
play :a4,release: 0.3 | |
end | |
sleep 0.3 | |
osc "/touch/ledg",0 #turn all TouchOSC leds off | |
osc "/touch/ledr",0 | |
osc "/touch/ledb",0 | |
osc "/touch/ledy",0 | |
sleep 0.01 | |
end | |
define :flashall do |d| | |
osc "/touch/ledg",1 #turn all TouchOSC leds on | |
osc "/touch/ledr",1 | |
osc "/touch/ledb",1 | |
osc "/touch/ledy",1 | |
sleep d | |
osc "/touch/ledg",0 #turn all TouchOSC leds off | |
osc "/touch/ledr",0 | |
osc "/touch/ledb",0 | |
osc "/touch/ledy",0 | |
sleep d if d<0.1 | |
end | |
define :decodebutton do |address| #extracts wild card info from address /osc/touch/push/*/* | |
#uses undocumented function getevent | |
#getevent("/osc/touch/push/*/*") will return output like: | |
#<SonicPi::CueEvent:[[1519217795.274847, 0, #<SonicPi::ThreadId [-1]>, 0, 0.0, 60.0], "/osc/touch/push/2/2", [1.0]] | |
#from which the substitutes for the wildcard * can be extracted using the strign functions below | |
s= get_event(address).to_s.split(",")[6][address.length-1..-2].split("/") | |
column=s[0].to_i | |
row=s[1].to_i | |
res= "g" if column==1 and row==1 | |
res= "b" if column==1 and row==2 | |
res= "r" if column==2 and row==1 | |
res= "y" if column==2 and row==2 | |
return res | |
end | |
define :getbutton do | |
use_real_time | |
b = sync "/osc/touch/push/*/*" | |
if b[0]==1 #pushed | |
pushed=decodebutton("/osc/touch/push/*/*") | |
set :button, pushed | |
puts "Pushed",pushed | |
if get(:inputmode) #check if button input mode | |
p=get(:pattern)#get current pattern | |
c=get(:currentstep) #get step in pattern | |
ledon pushed #flash led for pushed button | |
sleep 0.2 | |
if pushed== p[c] #check if correct button pushed | |
c+=1 #increase step pointer | |
if c == p.length #see if reached end of pattern ie winning state | |
sc=get(:score) #et current score | |
hsc=get(:hiscore) ##get current hi-score | |
set :score,sc+1 ##increase score by one and store | |
hsc=sc+1 if sc+1 > hsc #increase hi-score if necessary | |
set :hiscore,hsc | |
puts "Your score is",sc+1 #publish scores on screen and touch device | |
puts "Hi-score is",hsc | |
osc "/touch/score",sc+1 | |
osc "/touch/hiscore",hsc | |
set :currentstep,0 #reset step for next run | |
sample :perc_till #sound winning cash register | |
puts "well done" | |
flashall 0.5 | |
use_random_seed(Time.now.nsec) #set random seed for new game | |
sleep 0.5 | |
set :inputmode,false #disable input mode | |
else | |
set :currentstep, c #not end of pattern so bump pointer | |
end | |
else | |
set :pattern,[] #reset time state variables | |
set :currentstep,0 | |
set :score,0 | |
sample :misc_crow #play loosing crow sound | |
puts "you made a mistake" | |
3.times do | |
flashall 0.025 | |
end | |
osc "/touch/score",0 #reset user score | |
osc "/touch/hiscore",get(:hiscore) | |
use_random_seed(Time.now.nsec) #set random seed for new game | |
sleep 1 | |
set :inputmode,false #disable input mode | |
end | |
end | |
end | |
end | |
define :displayturn do #function updates label to display tunr information | |
if get(:inputmode) #if input mode set "YOur Turn" | |
osc "/touch/turn","Your Turn" | |
else #otherwise set "Computer Turn" | |
osc "/touch/turn","Computer Turn" | |
end | |
sleep 0.2 | |
end | |
live_loop :game do #main game loop | |
use_real_time | |
set :inputmode,false #start with input mode false (ie computers turn) | |
if get(:inputmode) == false | |
displayturn #update turn indfo | |
p=get(:pattern) #get current pattern | |
set :pattern, p+ [["g","r","b","y"].choose]#add new random choice | |
p=get(:pattern) | |
puts "pattern set to ",p #display current pattern on screen | |
p.length.times do |x| #output pattern data as led flashes and sounds | |
ledon p[x] | |
sleep 0.3 | |
end | |
set :inputmode,true #set input mode true (ie uaser's turn) | |
displayturn #update turn info | |
until get(:inputmode)==false #wait for input to complete | |
getbutton #get input from user | |
sleep 0.05 | |
end | |
end | |
#gets here when get(:inputmode) is true | |
#Time delay not necessary, as always delay waiting for input sync | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
This version works on Sonic Pi 3 and a TouchOSC program running on an iPad, iPhone or Android device on the same local WiFi network. To make the TouchOSC program, download index.xml and zip/compress it naming the resultant file simon.touchosc This can then be loaded to your TouchOSC device from the free TouchOSC editor running on a Mac or Windows PC. You need to enable OSC on the TouchOSC device, set its host address to the address of the computer running Sonic Pi (version 3 or later) and set the outgoing port to 4559. Set the incoming port to 9000. The address in line 3 of the SimonTouchOSC>rb file running on Sonic Pi should point to the Local IP address of the device running TouchOSC.
To play the game, when you run the SimonTouchOSC program on Sonic Pi it will play a note and flash one of the four LED circles on the TouchOSC device. You should respond by pressing this same circle. You will hear a "cash register" sound if successful and a "crow" sound otherwise. If successful, the computer will play two tones, and you respond likewise. The aim is to achieve the maximum sequence without making a mistake. The TouchOSC device will display your current score and the hi-score obtained in the session. It also indicates when it your turn and when it is the computer's turn to play.