Introduction: IMBUCARE BOX

IMBUCARE BOX es un proyecto que se ha desarrollado en conjunto por estudiantes de la Universidad Autónoma de Occidente para la asignatura Arquitectura de Sistemas Multimedia.

El juego consta de tres actividades:

1. Introducir una sola figura en una sola caja, esta actividad es para que el niño se familiarice con el juguete y entienda su dinámica. Para esta actividad es necesario que el sensor infrarrojo detecte la figura al ser introducida dentro de la caja.

2. Se tendrá una figura de diferentes colores, que deben ser introducidas en una sola caja. Para esto es necesario que el sensor de color reconozca el color de la figura que ha entrado y valide si es el correcto o no, según especificaciones de la profesora hacia el niño.

3. Habrán 3 cajas con diferentes tapas, en donde el niño tendrá a disposición todas las figuras elaboradas, ya sean de la misma forma o del mismo color. Por ejemplo, pueden haber 2 cuadrados, uno rojo y otro azul, así puede darse con las demás figuras y con otros colores. La profesora deberá darle pistas al niño sobre cual figura va en cada caja. Por ejemplo, en la caja 1 va el círculo verde, en la caja 2 va el cuadrado rojo, etcétera.

El objetivo del proyecto es fomentar el aprendizaje de los niños por medio de juegos didácticos. Ademas, la implementación de uso de tecnologías para la identificación y el registro de las actividades realizadas por cada usuario.

MATERIALES A UTILIZAR



Step 1: Realización De Los Planos De La Caja.

En este proceso se usó el software ILLUSTRATOR para la realización de los planos de la caja con las siguientes medidas:

Cada juego es una caja con dos orificios, en la parte frontal un orificio circular de 8 cm de diámetro por el cual se saca la figura y uno superior (dependiente de la figura) por la cual se inserta. La cara frontal (donde esta el orificio circular de 8 cm) se puede retirar para que la mano de un adulto pueda sacar la figura; esta cara que esta anclada con imanes de neodimio que la sujetan fuertemente. La cara superior donde se encuentra la figura geométrica también es desmontable (mismo mecanismo de cierre magnético) y las diferentes figuras se puede intercambiar.

Realizaremos:3 cajas de Imbucare con 6 caras superiores intercambiables:

  1. Prisma triangular.
  2. Cubo.
  3. Prisma cuadrangular
  4. Esfera pequeña
  5. Esfera grande
  6. Moneda.

Step 2: Construcción De La Caja.

1. Para la realización de la caja se crearon planos en Illustrator (se puede utilizar programas de modelado 3D o de dibujo que exporten en formatos PDF). De una caja de 5 lados, sin tapa superior (2 lados de 15x15 cm y 3 lados de 10x15cm); igualmente 6 diferentes tapas superiores de 15x15cm con agujeros de figuras (triangulo, cuadrado, prisma, moneda, etc … ) que podrán ser intercambiables.

2. Dichos planos deben contener todas las agujeros, figuras y detalles que se deseen para la Caja Imbucare. Luego se llevarán a una impresora láser que hará todo el proceso de cortado. (NOTA: Los detalles circulares deben tener más puntos de anclaje para ser reconocidos por la impresora)

3. Al tener c/u de los lados de la caja (4 laterales), 1 de los lados de 10x15cm debe tener un agujero de 6cm de diámetro en el centro y finalmente 6 tapas de 15x15cm como se muestran en el plano de impresión láser.

4. Los lados (NO DEBEN PEGARSE NI LA TAPA SUPERIOR, NI EL LATERAL CON AGUJERO DE 6 CM) se unirán con Colbon o Pegante para Madera, y se dejará reposar hasta que se pegue completamente 2 horas. Verificar que todos los lados quedaron bien sujetos.

5. Con un taladro con una broca muy fina, abrir 3 agujeros en la parte superior y en el frente destapados de la caja (mínimo 3 agujeros por lado), de una profundidad de 0.5 cm, ahí irán los imanes. Teniendo mucha precaución de no romper el lado de madera.

6. Para las tapas superiores intercambiables deben abrirse 3 huecos por debajo de la misma, y para la tapa frontal con agujero, se deben abrir 3 huecos al lado izquierdo y derecho de la madera.

7. Verifica las posiciones como pusiste los primeros imanes, ya que la polaridad debe coincidir para que las tapas superiores y la tapa frontal puedan quedar adheridas con la caja base y no haya ninguna repelencia entre las polaridades. Ya con los agujeros y las polaridades correctas, se procede a pegar con SuperBonder cada uno de los imanes en c/u de esos agujeros encajándolos y haciendo presión hasta que se adhieran a la madera.

8. Finalmente se procede a pintar la caja base, la tapa frontal y las tapas superiores del color que desees. Se deben cubrir también los imanes.

9. Para realizar las tablas separadoras y el soporte de batería, se deben cortar dos pedazos en una cortadora, que queden a la altura de la caja base, y se busca hacer una forma de “L” con las tablas recortadas. Para el soporte de la batería, se realizan dos cortes (soporte y pared) que sostendrán la batería, de 4x5cm para que el separador actué como pared que cierra el soporte de la batería

10. Con un taladro se realizan 1 hueco de 3x1cm en la tabla separadora y un agujero de 1cm de diámetro en el soporte de la batería donde pasaran los cables y el sensor de proximidad.

11. Para los huecos de los botones y los pulsadores se utilizó igualmente un taladro para realizar agujeros de 0.5x0.5cm en la parte trasera de la caja base, igualmente 1 agujero de 2x3cm para la entrada de USB del Arduino y 2 agujeros de 0.5cm de diámetro en un lateral.

12. Para el encaje del sensor RFID, se utilizó una broca escariador que no perfore completamente la tapa trasera y se realizará un enmarcado de 6x4cm en donde casara el sensor.

13. Finalmente se realizó en una cortadora manual, una tapa superior que quedara a ras con la altura de la caja base para que se puedan tapar la parte de circuitos y la batería

Step 3: Preparación De Los Materiales

Para comenzar con el montaje es necesario sacar todos los materiales de su empaque, entender todas sus partes y características, y posteriormente realizar las modificaciones necesarias para la adaptación con el proyecto. Para esto, se necesita soldar todos los materiales para que las conexiones sean seguras y los cables mejoren la conexión, haciéndola más organizada.

Se procede a calentar el pin del elemento, y el cable con el cautín, juntandolos para después aplicar el estaño. Se debe esperar hasta que los elementos se enfríen y poder así retirar la presión. Este proceso dura unos segundos.

En las imágenes se muestran los elementos listos para realizar el montaje.

Step 4: Realizar Montaje De Prueba

Se aconseja realizar conexiones de prueba antes de empezar con el montaje en las cajas para asegurar que todas las soldaduras y los componentes están en buen estado.

Para realizar este paso se realizó el montaje prueba en la protoboard, y se conectó los diferentes pines de los elementos al arduino mediante esta.

En la imagen se pueden ver las conexiones de los distintos elementos listados.

Después, se procede a implementar el código. Para cargar el código en el arduino conectado, presionar en la opción superior izquierda, con símbolo de flecha. En la parte inferior debe decir "Subido".

En el código mostrado a continuación se sigue la definición de los variables en los pines conectados, siguiendo el esquema de la figura. Además, las actividades y los procesos están definidos como métodos, para sólo ser llamados en el void setup, o void loop, donde sea necesario.

Las librerias usadas son las siguientes: SoftwareSerial, SPI sensor library, MFRC522 RFID library.

#include SoftwareSerial.h

#include SPI.h

#include MFRC522.h

int sensorIR = 4;

int valorIR;

int red = 0, green = 0, blue;

boolean estadoact1 = false;

boolean estadopet = false;

boolean estadotarj = false;

String identificador_usuario = "";

//Led que avisa si esta bien o mal

int redPin = A3;//red pin

int greenPin = A4;//green pin

int bluePin = A5;//blue pin

//Led que avisa el color a introducir

int redPin2 = A0;//red pin

int greenPin2 = A1;//green pin

int bluePin2 = A2;//blue pin

//Pulsador del led que cambia los colores

int botonSelect = 3;

//Determina el color que se debe introducir

// 0= Rojo, 1=Verde, 2=Azul

int pinLed = 0;

int S2 =7; //sensor de color s2 al pin 7

int S3 = 8;//sensor de color s3 al pin 8

int outPin = 6;//sensor de color out al pin 4

int rColorStrength;

int gColorStrength;

int bColorStrength;

unsigned int pulseWidth;

boolean estadoact2 = false;

boolean estadoact3 = false;

int boton1 = 9;

int boton2 = 10;

int boton3= 11;

int estadoact = 0;

#define SS_PIN 53

#define RST_PIN 5

MFRC522 mfrc522(SS_PIN, RST_PIN); // Create MFRC522 instance.

void setup() {

Serial.begin(9600);

SPI.begin(); // Initiate SPI bus

mfrc522.PCD_Init(); // Initiate MFRC522

Serial.println();

Serial1.begin(9600);

pinMode(sensorIR,INPUT);

pinMode(redPin, OUTPUT);

pinMode(greenPin, OUTPUT);

pinMode(bluePin, OUTPUT);

pinMode(redPin2, OUTPUT);

pinMode(greenPin2, OUTPUT);

pinMode(bluePin2, OUTPUT);

pinMode(botonSelect, INPUT);

pinMode(S2, OUTPUT);

pinMode(S3, OUTPUT);

pinMode(outPin, INPUT);

pinMode(boton1, INPUT);

pinMode(boton2, INPUT);

pinMode(boton3, INPUT);

setColor2(255, 255, 255);

reset();

connectWiFi();

Serial.println("Aproxime la tarjeta al lector...");

setColor(255, 255, 255);

}

void reset() {

Serial.println("////------------------/////-------------");

Serial.println("Reiniciando Modulo");

Serial1.println("AT+RST");

while (!Serial1.find("OK") ) {

Serial.print(".");

delay(1000);

}

delay(1000);

Serial.println(".");

char c = Serial1.read();

Serial.print(c);

Serial.println("Modulo Reiniciado");

}

void connectWiFi() {

Serial.println("////------------------/////-------------");

Serial.println("Cambio de modo");

Serial1.println("AT+CWMODE=3");

while (!Serial1.find("OK")) {

Serial.print(".");

delay(1000);

}

delay(5000);

Serial.println(".");

char c = Serial1.read();

Serial.println(c);

Serial.println("////------------------/////-------------");

Serial.println("Conectando a WiFi");

// Serial1.println("AT+CWJAP=\"WiFi-UAO\",\"\"");

Serial1.println("AT+CWJAP=\"385189313291\",\"122633381899\"");

while (!Serial1.find("OK")) {

delay(500);

}

delay(6000);

Serial.println(".");

c = Serial1.read();

Serial.println(c);

Serial.println("Modulo conectado");

Serial1.println("AT+CIPMUX=1");

while (!Serial1.find("OK")) {

Serial.print(".");

delay(500);

}

Serial1.println("AT+CIFSR");

while (!Serial1.find("OK")) {

Serial.print(".");

delay(500);

}

Serial.println("////------------------/////-------------");

}

void enviarpeticion1(){

Serial.println("Conectando a UAO");

//Serial1.println("AT+CIPSTART=4,\"TCP\",\"montessori-andresayala-alejoayala2104669036.codeanyapp.com\",80");

Serial1.println("AT+CIPSTART=4,\"TCP\",\"montessori-luismigon.c9users.io\",80");

while (!Serial1.find("OK")) {

Serial.print(".");

delay(500);

}

Serial.println("Conexion a UAO Establecida");

String server = "montessori-luismigon.c9users.io";

String datos = "\"juego\":\"Imbucare Box\",\r\n \"identificador_usuario\": \"" + identificador_usuario + "\",\r\n \"fecha\": \"3.4.2017.07.00.00\",\r\n \"actividad\": \"Actividad 1: Mismo color varias figuras\"";

String postRequest = "POST /activity HTTP/1.1\r\n";

postRequest = postRequest + "Host: " + server + "\r\n";

postRequest = postRequest + "Content-Type: application/json\r\n" ;

postRequest = postRequest + "Content-Length: " + datos.length() + "\r\n";

postRequest = postRequest + "\r\n" + datos;

String sendCmd = "AT+CIPSEND=4,";

sendCmd.concat(postRequest.length());

Serial.println(sendCmd);

Serial1.println(sendCmd);

while (!Serial1.find(">")) {

Serial.print(".");

delay(500);

}

Serial.println("Enviando Peticion");

Serial.println(postRequest);

Serial1.println(postRequest);

while (!Serial1.find("SEND OK")) {

Serial.print(".");

delay(500);

}

Serial.println("Peticion Enviada");

while (Serial1.available()) {

char ch = Serial1.read();

Serial.print(ch);

}

Serial1.println("AT+CIPCLOSE=4");

Serial.println("Conexion Cerrada");

estadoact = 0;

}

void enviarpeticion2(){

Serial.println("Conectando a UAO");

//Serial1.println("AT+CIPSTART=4,\"TCP\",\"www.uao.edu.co\",80");

Serial1.println("AT+CIPSTART=4,\"TCP\",\"montessori-luismigon.c9users.io\",80");

while (!Serial1.find("OK")) {

Serial.print(".");

delay(500);

}

Serial.println("Conexion a UAO Establecida");

String server = "montessori-luismigon.c9users.io";

String datos = "\"juego\":\"Imbucare Box\",\r\n \"identificador_usuario\": \"" + identificador_usuario + "\",\r\n \"fecha\": \"3.4.2017.07.00.00\",\r\n \"actividad\": \"Actividad 2: Misma figura diferentes formas\"";

String postRequest = "POST /game HTTP/1.1\r\n";

postRequest = postRequest + "Host: " + server + "\r\n";

postRequest = postRequest + "Content-Type: application/json\r\n" ;

postRequest = postRequest + "Content-Length: " + datos.length() + "\r\n";

postRequest = postRequest + "\r\n" + datos;

String sendCmd = "AT+CIPSEND=4,";

sendCmd.concat(postRequest.length());

Serial.println(sendCmd);

Serial1.println(sendCmd);

while (!Serial1.find(">")) {

Serial.print(".");

delay(500);

}

Serial.println("Enviando Peticion");

Serial.println(postRequest);

Serial1.println(postRequest);

while (!Serial1.find("SEND OK")) {

Serial.print(".");

delay(500);

}

Serial.println("Peticion Enviada");

while (Serial1.available()) {

char ch = Serial1.read();

Serial.print(ch);

}

Serial1.println("AT+CIPCLOSE=4");

Serial.println("Conexion Cerrada");

estadoact = 0;

pinLed = 0;

}

void enviarpeticion3(){

Serial.println("Conectando a UAO");

//Serial1.println("AT+CIPSTART=4,\"TCP\",\"www.uao.edu.co\",80");

Serial1.println("AT+CIPSTART=4,\"TCP\",\"montessori-luismigon.c9users.io\",80");

while (!Serial1.find("OK")) {

Serial.print(".");

delay(500);

}

Serial.println("Conexion a UAO Establecida");

String server = "montessori-luismigon.c9users.io";

String datos = "\"juego\":\"Imbucare Box\",\r\n \"identificador_usuario\": \"" + identificador_usuario + "\",\r\n \"fecha\": \"3.4.2017.07.00.00\",\r\n \"actividad\": \"Actvidad 3: Diferentes figuras y diferentes formas\"";

String postRequest = "POST /game HTTP/1.1\r\n";

postRequest = postRequest + "Host: " + server + "\r\n";

postRequest = postRequest + "Content-Type: application/json\r\n" ;

postRequest = postRequest + "Content-Length: " + datos.length() + "\r\n";

postRequest = postRequest + "\r\n" + datos;

String sendCmd = "AT+CIPSEND=4,";

sendCmd.concat(postRequest.length());

Serial.println(sendCmd);

Serial1.println(sendCmd);

while (!Serial1.find(">")) {

Serial.print(".");

delay(500);

}

Serial.println("Enviando Peticion");

Serial.println(postRequest);

Serial1.println(postRequest);

while (!Serial1.find("SEND OK")) {

Serial.print(".");

delay(500);

}

Serial.println("Peticion Enviada");

while (Serial1.available()) {

char ch = Serial1.read();

Serial.print(ch);

}

Serial1.println("AT+CIPCLOSE=4");

Serial.println("Conexion Cerrada");

estadoact = 0;

pinLed = 0;

}

void actividad1(){

setColor(0, 0, 0);

setColor2(255, 255, 255);

valorIR = digitalRead(sensorIR);

Serial.println(valorIR);

// Serial.print("Sin deteccion\r\n");

delay(500);

if(!valorIR == 1){

setColor(255, 0, 255);

estadoact1 = true;

// Serial.print("Deteccion\r\n");

}

delay(500);

}

void actividad2(){

// pinLed = 0;

int estadoselect = digitalRead(botonSelect);

if ( estadoselect == 1) {

pinLed++;

// Para no pasarse de vueltas

if (pinLed > 2) { pinLed=0; }

// Esperamos a que el boton se suelte

while (digitalRead(botonSelect) == HIGH) { }

delay(10); // Esperamos un poquito más...

}

//leer el componente rojo del color

//S2 y S3 deben estar en LOW

digitalWrite(S2, LOW);

digitalWrite(S3, LOW);

pulseWidth = pulseIn(outPin,LOW);

rColorStrength = pulseWidth;

//leer el componente verde del color

//S2 y S3 deben estar HIGH

digitalWrite(S2, HIGH);

digitalWrite(S3, HIGH);

pulseWidth = pulseIn(outPin,LOW);

gColorStrength = pulseWidth;

//leer el componente azul del color

//S2 debe estar en LOW y S3 debe estar HIGH

digitalWrite(S2, LOW);

digitalWrite(S3, HIGH);

pulseWidth = pulseIn(outPin,LOW);

bColorStrength = pulseWidth;

if(pinLed == 0){

setColor2(0, 255, 255); // rojo

//Si el color menor es rojo

if(rColorStrength < bColorStrength && rColorStrength < gColorStrength){

// setColor(0, 255, 255); // rojo

setColor(255, 0, 255); // verde

Serial.print("Color rojo detectado\r\n");

estadoact2 = true;

}

else{

setColor(0, 255, 255);

}

}

if(pinLed == 1){

setColor2(255, 0, 255); // verde

//Si el color menor es verde

if(gColorStrength < bColorStrength && gColorStrength < rColorStrength){

setColor(255, 0, 255); // verde

Serial.print("Color verde detectado\r\n");

estadoact2 = true;

}

else{

setColor(0, 255, 255);

}

}

if(pinLed == 2){

setColor2(255, 255, 0); // azul

//Si el color menor es azul

if(bColorStrength < rColorStrength && bColorStrength < gColorStrength){

// setColor(255, 255, 0); // azul

setColor(255, 0, 255); // verde

Serial.print("Color azul detectado\r\n");

estadoact2 = true;

}

else{

setColor(0, 255, 255);

}

}

delay(100);

}

void actividad3(){

int estadoselect = digitalRead(botonSelect);

if ( estadoselect == 1) {

pinLed++;

// Para no pasarse de vueltas

if (pinLed > 2) { pinLed=0; }

// Esperamos a que el boton se suelte

while (digitalRead(botonSelect) == HIGH) { }

delay(10); // Esperamos un poquito más...

}

//leer el componente rojo del color

//S2 y S3 deben estar en LOW

digitalWrite(S2, LOW);

digitalWrite(S3, LOW);

pulseWidth = pulseIn(outPin,LOW);

rColorStrength = pulseWidth;

//leer el componente verde del color

//S2 y S3 deben estar HIGH

digitalWrite(S2, HIGH);

digitalWrite(S3, HIGH);

pulseWidth = pulseIn(outPin,LOW);

gColorStrength = pulseWidth;

//leer el componente azul del color

//S2 debe estar en LOW y S3 debe estar HIGH

digitalWrite(S2, LOW);

digitalWrite(S3, HIGH);

pulseWidth = pulseIn(outPin,LOW);

bColorStrength = pulseWidth;

if(pinLed == 0){

setColor2(0, 255, 255); // rojo

//Si el color menor es rojo

if(rColorStrength < bColorStrength && rColorStrength < gColorStrength){

// setColor(0, 255, 255); // rojo

setColor(255, 0, 255); // verde

Serial.print("Color rojo detectado\r\n");

estadoact3 = true;

}

else{

setColor(0, 255, 255);

}

}

if(pinLed == 1){

setColor2(255, 0, 255); // verde

//Si el color menor es verde

if(gColorStrength < bColorStrength && gColorStrength < rColorStrength){

setColor(255, 0, 255); // verde

Serial.print("Color verde detectado\r\n");

estadoact3 = true;

}

else{

setColor(0, 255, 255);

}

}

if(pinLed == 2){

setColor2(255, 255, 0); // azul

//Si el color menor es azul

if(bColorStrength < rColorStrength && bColorStrength < gColorStrength){

// setColor(255, 255, 0); // azul

setColor(255, 0, 255); // verde

Serial.print("Color azul detectado\r\n");

estadoact3 = true;

}

else{

setColor(0, 255, 255);

}

}

delay(100);

}

void setColor (int red, int green, int blue){

analogWrite(redPin, red);

analogWrite(greenPin, green);

analogWrite(bluePin, blue);

}

void setColor2 (int red, int green, int blue){

analogWrite(redPin2, red);

analogWrite(greenPin2, green);

analogWrite(bluePin2, blue);

}

void leerTarjeta()

{

// Look for new cards

if ( ! mfrc522.PICC_IsNewCardPresent())

{

return;

}

// Select one of the cards

if ( ! mfrc522.PICC_ReadCardSerial())

{

return;

}

//Show UID on serial monitor

Serial.print("UID tag :");

String content= "";

byte letter;

for (byte i = 0; i < mfrc522.uid.size; i++)

{

Serial.print(mfrc522.uid.uidByte[i] < 0x10 ? " 0" : " ");

Serial.print(mfrc522.uid.uidByte[i], HEX);

content.concat(String(mfrc522.uid.uidByte[i] < 0x10 ? " 0" : " "));

content.concat(String(mfrc522.uid.uidByte[i], HEX));

}

Serial.println();

Serial.print("Mensaje : ");

content.toUpperCase();

//D3 30 F1 C5

if (content.substring(1) == "75 7E 00 AB") //change here the UID of the card/cards that you want to give access

{

Serial.println("Acceso autorizado");

Serial.println();

delay(3000);

identificador_usuario = content.substring(1);

estadotarj = true;

setColor(0, 0, 0);

setColor2(0, 0, 0);

Serial.println("Esperando actividad...");

}

else {

Serial.println(" Acceso denegado");

delay(3000);

}

}

void loop() {

while (!estadotarj == true){

leerTarjeta();

}

if (Serial1.available()) {

char c = Serial1.read();

Serial.print(c);

}

if (Serial.available()) {

char c = Serial.read();

Serial1.print(c);

}

if(digitalRead(boton1) == HIGH){

estadoact = 1;

Serial.print("Actividad 1\r\n");

delay(100);

}

if(digitalRead(boton2) == HIGH){

estadoact = 2;

Serial.print("Actividad 2\r\n");

delay(100);

}

if(digitalRead(boton3) == HIGH){

estadoact = 3;

Serial.print("Actividad 3\r\n");

delay(100);

}

if(estadoact == 1 && estadoact1 == false){

actividad1();

if(estadopet == false && estadoact1 == true){

estadopet == true;

enviarpeticion1();

}

}

if(estadoact == 2 && estadoact2 == false){

actividad2();

if(estadopet == false && estadoact2 == true){

estadopet == true;

enviarpeticion2();

}

}

if(estadoact == 3 && estadoact3 == false){

actividad3();

if(estadopet == false && estadoact3 == true){

estadopet == true;

enviarpeticion3();

}

}

if(estadoact1 == true && estadoact2 == true && estadoact3 == true){

estadoact1 = false;

estadoact2 = false;

estadoact3 = false;

}

}

Con el código cargado, se puede acceder a la ventana de serial para ver lo que está pasando mientras se ejecuta el código. Para hacer esto, de clic en el icono superior derecho con forma de lupa en Arduino.

Si las conexiones están realizadas de forma correcta, el programa no debería quedarse esperando la petición al servidor, y los botones deberían responder a las actividades correctas.

En el siguiente link se adjunta el proyecto en Arduino.
Código Imbucare Box

Step 5: Integrar Conexiones a La Caja

Después de tener la certeza de que las conexiones y el código se ejecuta de manera correcta, se procede a soldar los cables de cada elemento a su respectiva ubicación.

Para esto se hizo uso de la plaqueta de circuitos, en donde solamente se conectó las salidas a 3.3V, 5V y GND, para lo demás se hizo uso de cables jumpers para conectar cada pin del elemento al arduino.

Una vez realizado el montaje, se verifica que el programa funcione de manera correcta.

En las imágenes se puede ver el montaje parcial del circuito.