My partner Laura Ciporen tried to address this question for our midterm project.
In spaces such as a museum, people will readily interact with kiosks. Their mere presence seems to invite interaction. This predisposition to kiosks was exploited to solve the anonymous interaction issue. Two people could be enticed to interact with the kiosk first, and the kiosk makes the connection between the individuals. The kiosk is the social lubricant that moves the users to the state of interaction (with each other) that is desired.
When we initially came up with the idea, we were very focused on the enticement phase, getting the users attention. We decided to use a looping movie that used the words "come play" which was satisfactory for prototyping. Flashing lights, noises, flags, etc... could also be used to attract attention.
After the user notices the kiosk, and walks nearer, the kiosk is to invite the user to do something. In this case, it is an invitation to move right or left.
Moving right or left would produce a video instructing the user to either "Wave their hands in the air" or "Do the Funky Chicken". Silly? Perhaps, but the goal was to produce an observable output from the user. The funky chicken is unmistakable.
The two kiosks can be set up anywhere. When two people have been enticed by the kiosks and they are being used simulatneously...the outputs swtich. Kiosk A's output is shown on the screen of B and vice versa. A game of "simon sez" occurs A is telling B what to do, as B does A.
The two users have just interacted with one another.
It is at this point that the interaction that requires two individuals can begin.
Sensors.

The kiosks are activated by proximity, so at first we thought about using an array of ranging sensors to drive the interactions. After further research though, laser and pressure sensors were deemed the most cost effective and practical for the prototype. The lasers were attached to external power sources so that we didn't have to worry about the batteries. One strange note. The batteries added up to 4.5V but when I used a voltage regulator and resistors to bring the current down to that value. The lasers were to dim. They were strung together in parallel at 5V.

The "Come hither" movie would play until the user steps onto the mat (pressure sensor) then right and left movements would be activated using the interruption of a laser's beam on a photo diode.
Here is the whole interaction for one Kiosk.
Construction:
Autopoles with super clamps were used to align lasers and sensors. In a final build however we would use sensors that could register inputs without needing beam breaks for activation. We'd keep it all to one side. of the user.
Code:
Because we did not have ANY working experience with Processing, we decided it would be best for all conditional output from the sensors to be evaluated by the Arduino. Only one value would be sent to processing, allowing a simple Case Switch to be used.
The Arduino Code was written first. We set up the sensors and did a serial.read to make sure the sensors were working and used letters to determine which movie instruction would be passed to Processing.
"d" is "Default", the initial state
"m" means the pressure sensor has been tripped, but the laser beams are intact.
"l" and "r" register the right and left beam breaks.
Here is a sample of the serial output:
ArdyCalling
ArdyCalling
d
d
d
d
d
d
d
d
current reading 918
m
current reading 918
m
current reading 918
m
current reading 918
m
current reading 917
m
current reading 917
m
d
d
d
current reading 915
l
current reading 914
l
current reading 914
l
d
d
d
current reading 694
r
current reading 692
r
current reading 691
r
Arduino
//
//THIS CODE IS FOR THE ARDUINO COMMUNICATING WITH THE COMPUTER IN FRONT OF PERSON B
//
//Arduino is responsible for the management of all sensor data being
//sent to processing. Data will be tranlated to a single variable for
//output to processing.
//*************************
//VARIABLES
//*************************
//initialize pin settings
int proxyA=0; //Pressure Sensor on kiosk A on Analog pin 0 Yellow
int proxyB=1; //Pressure Sensor on kiosk B on Analog pin 1 Purple
int irlA=2; // left photocell on kiosk A on Analog pin 2 Orange
int irrA=3; // right photocell on kiosk A on Analog pin 3 Mauve
int irlB=4; // left photocell on kiosk B on Analog pin 4 Blue
int irrB=5; // right photocell on kiosk B on Analog pin 5 Green
//places to store base light readings for all 4 light sensors
int baseIRLA=0;
int baseIRLB=0;
int baseIRRA=0;
int baseIRRB=0;
//places to store the new light readings from the appropriate pair of light sensors
int newIRL=0;
int newIRR=0;
//initialize pressure reading variables
int pressureReadingA=0;
int pressureReadingB=0;
int basePressureReadingA=0;
int basePressureReadingB=0;
//variables to tell Ardy which sensors and base values to use in comparisons
int currentBaseL=baseIRLB;
int currentBaseR=baseIRRB;
int currentSensorL=irlB;
int currentSensorR=irrB;
//int swapped=0; //for our testing purposes
//int i=-1;
//*************************
//FUNCTIONS
//*************************
void setup()
{
Serial.begin(9600);
pickUpTelephone(); //start talking to processing
//get normal reading for light sensors to have a way to tell if the person is blocking the left or right sides or not
baseIRLA=analogRead(irlA);
baseIRLB=analogRead(irlB);
baseIRRA=analogRead(irrA);
baseIRRB=analogRead(irrB);
basePressureReadingA=analogRead(proxyA);
basePressureReadingB=analogRead(proxyB);
}
//call up Processing to make sure that it is ready to get info
void pickUpTelephone() {
while (Serial.available() <= 0) { Serial.println(666); // send a starting message delay(300); } } void loop() { if (Serial.available() > 0) {
int inByte = Serial.read(); // read the incoming byte from processing
//IF person my person is standing in front of the kiosk
//figure out if the other person is and if so, react to their movements, otherwise react to my person's
pressureReadingB=analogRead(proxyB);
if((pressureReadingB-basePressureReadingB)>60){
// if (Serial.available() > 0) {
// int inByte = Serial.read(); // read the incoming byte from processing
pressureReadingA=analogRead(proxyA); //read pressure sensor for other person
if((pressureReadingA-basePressureReadingA)>60) { //if other person is standing in front of their kiosk...
//read from other person's sensors
currentBaseL=baseIRLA;
currentBaseR=baseIRRA;
currentSensorL=irlA;
currentSensorR=irrA;
}//end if other person is close
else {
//reset left and right sensors and base readings to my person
currentBaseL=baseIRLB;
currentBaseR=baseIRRB;
currentSensorL=irlB;
currentSensorR=irrB;
}//end else if other person isn't close
//see if whichever person we are paying attention to is moving to the left or right or neither
//we are treating the possibility of someone breaking both beams as if they only broke the left one for simplicity's sake
newIRL=analogRead(currentSensorL); //read the left sensor
newIRR=analogRead(currentSensorR); //read the right sensor
if((currentBaseL-newIRL)>20) { //if left is blocked
Serial.println('l', DEC);
// Serial.print("Did we swap? ");
// Serial.println(swapped);
}//end if person broke left beam
else if((currentBaseR-newIRR)>20) { //if right is blocked
Serial.println('r', DEC);
}//end if person broke right beam
else {
Serial.println('m', DEC); //m for middle IE person is close but not breaking either side beam
// Serial.print("Is A broken? ");
// Serial.println(swapped);
}//end default for reacting to person
// }//end if serial available
}//end if my person is close
else {
Serial.println('d', DEC); //tell processing to go back to the default video
// Serial.print("Is A broken? ");
// Serial.println(swapped);
}
}//end if serial available
delay(10);
} //end loop
Processing
import processing.serial.*; // import the Processing serial library
Serial myPort; // The serial port
import processing.video.*;
//initialize movie variables
Movie myComeHitherMovie;
Movie myMiddleMovie;
Movie myLeftMovie;
Movie myRightMovie;
boolean firstContact = false; // Whether we've heard from the microcontroller
int thisIsNotAstring=999999;
//set the window size and which movie variable holds which movie
void setup()
{
size(720, 480);
println(Serial.list());
myPort = new Serial(this, Serial.list()[0], 9600);
// read bytes into a buffer until you get a linefeed (ASCII 10):
myPort.bufferUntil('\n');
myComeHitherMovie = new Movie(this, "comeHither.mov");
myComeHitherMovie.loop();
myMiddleMovie = new Movie(this, "arrow.mov");
myMiddleMovie.loop();
myLeftMovie = new Movie(this, "funkychicken.mov");
myLeftMovie.loop();
myRightMovie = new Movie(this, "waveHand.mov");
myRightMovie.loop();
}
//I'm not sure, but I think this tells the movie to keep looking for the next frame...
void movieEvent(Movie m) {
m.read();
}
//the main loop, which plays a movie depending on which key you press (since I don't have my Ardy here)
//these correspond to the letters Ardy is sending to Processing
void draw()
{
} //end draw
void serialEvent(Serial myPort) {
// read the serial buffer:
String myString = myPort.readStringUntil('\n');
// if you got any bytes other than the linefeed:
if (myString != null) {
myString = trim(myString);
// if you haven't heard from the microncontroller yet, listen:
if (firstContact == false) {
if (myString.equals("666")) {
myPort.clear(); // clear the serial port buffer
firstContact = true; // you've had first contact from the microcontroller
myPort.write('A'); // ask for more
}
}
// if you have heard from the microcontroller, proceed:
else {
// println(myString);
/* if (myString=="d"){
thisIsNotAstring=1;
}//end if d
else if (myString=="m"){
thisIsNotAstring=2;
}//end if m
else if (myString=="l"){
thisIsNotAstring=3;
}//end if l
if (myString=="r"){
thisIsNotAstring=4;
}//end if r
println(thisIsNotAstring); */
thisIsNotAstring=int(myString);
// println(thisIsNotAstring);
switch (thisIsNotAstring){
case 100:
image(myComeHitherMovie, 0, 0);
break;
case 109:
image(myMiddleMovie, 0, 0);
break;
case 108:
image(myLeftMovie, 0, 0);
break;
case 114:
image(myRightMovie, 0, 0);
break;
default:
fill(66,66,0);
ellipse(200, 80, 200, 40);
break;
}//end switch case
myPort.write("A");
}
// when you've parsed the data you have, ask for more:
}
}
This method uses the handshake protocol as described in the second serial lab.
Debugging.
Our two biggest issues were:
A- Getting Processing to recognize the variable we were passing it.
We had to declare the variable as a DEC. So that it could be read in processing. Initially the ASCII value was being read as a string and it wouldn't allow the Case Swtich to work. we tried a ParseInt but it didn't work. Still recognized it as a String. DEC solved the issue.
B- The handshake was not working because we forgot to instruct the Arduino code to pass the "/n" to Processing. It only interating through the loop once. This caused a big headache but with help, we sorted it out.
C- The last bug that remains unresolved is once the inputs swtich. Whichever kiosk is approached first is the one that will drive BOTH outputs, they do not swtich as planned. They do swtich however at the Arduino output level. It is not a circuit issue but a coding one.
This project was interesting because I feel that it does have the ability to promote interaction in a public space. In a final build of the design, the next step of the interaction would need two people to take place. But I could also see an more playful exercise of havving the kiosks in totally seperate locations and making the interactions more varied and complex. A person could be engaging with a person in another location for several minutes before realizing they are playing with someone else as opposed to the computer. Having that person be far away (the further the better) could start a thought provoking dialogue about connections , anonymity and isolation.