Wednesday, March 29, 2017

Room with a View – HoloLens, Unity3D y Blender


Este blog fue posteado originalmente en Room with a View – HoloLens, Unity3D and Blender.





Desde el mes pasado más o menos he estado iluminándome con un impresionante curso de Blender…y aunque tenía algo de experiencia adquirida tras haber leído varios libros…nada podía traerme al punto en el que estoy como este curso…así que…sin nada más que decir…este curso es altamente recomendado 🙂

Entonces…uno de los retos was crear algo utilizándo solamente primitivos…esto significa…cubos, esferas, conos y demás…nada complicado…no modificadores…no experiencia previa…así que finalmente hice esto…


Era un buen comienzo…pero sabía que necesitaba algo más…además de utilizar texturas claro está 🙂 Se veía bastante simple…así que el siguiente paso era hacerlo más interesánte visualmente…y terminé haciendo esto…


Ahora…se ve bastante interesánte, no? Todo creado a mano en Blender -;)

Así que…el siguiente paso era determinar que hacer con esto…se veía muy bonito como para simplemente dejarlo descanzándo en mi disco duro…así que empecé a pensar y luego recordé que la Holographic Academy tiene un interesánte demo llamado Origami...en este demo tienes que seleccionar una pelota de origami que se va a resbalar por un avión de papel y luego chocar con un ventilador que va a explotar y este a la vez va a abrir un hueco en el piso donde un impresionante mundo subterráneo puede ser visto…realmente impresionante si me lo preguntan…entonces…tenía una idea 🙂 Por que no tener un cuadro del d-shop que explota cuando es seleccionado y luego abre un hueco en la pared donde el cuarto que diseñe en Blender puede ser visto?…eso para mi sonaba como una demo impresionánte…así que eso es exactamente lo que hice 😉

Aquí está el video para que lo disfruten…espero que les guste 🙂




Al inicio pensé que iba a ser mucho trabajo…pero no lo fué tanto realmente…aquí hay algunos puntos importantes…

* Encerré el cuarto en una caja negra con un agujero para que pueda ser visto por adentro…

* En Unity3D simplemente utilizé un Unlit shader…como el color negro es procesado como invisible en HoloLens, tener el modelo en una caja negra que no esta iluminada da la impresión de que es invisible…por lo tanto…se ve como un hueco en la pared…

* Utilicé spatial mapping para poder ajustar el cuadro y el cuarto en la pared…para que no aparezca volando en el espacio pero más bien como si hubiera un cuarto dentro de la pared…

* Cuando importé el modelo de Blender a Unity3D la primera vez…ninguna de mis texturas estaba disponible…lo cual me pareció muy extraño…puesto que estaban ahí y estaban realmente asignadas…resulta que necesitaba escoger cada parte del modelo y hacer un…para que el shader sepa como implementar la textura…

* Al principio hice pruebas con el emulador…el cual es muy bueno…pero realmente no implementa la misma unidad de medida que se utiliza en el dispositivo físico…así que mientras que se vería bien en el emulador…se veía muy lejos en el HoloLens…así que necesité hacer muchas pruebas para poder tenerlo en la posición correcta…

* Para filmar el video, al inicio intenté utilizándo Camtasia…pero por supuesto…el rendering no era lo que yo estaba esperándo…una cosa es verlo por el HoloLens y otra cosa es verlo por la laptop…así que en vez de eso hice una grabación del Live Streaming en el mismo HoloLens…y ese era el truco…

Como pueden imaginarse…esto trae un nuevo mundo de posibilidades y demos…

Ahora es su turno de mostrárnos…que es lo que ustedes pueden hacer 😉

Saludos,

Blag.
Development Culture.

Wednesday, February 15, 2017

SAP d-shop’s Virtual House – Un viaje de los físico a lo Virtual


Este post fué posteado originalmente en SAP d-shop’s Virtual House – A journey from Physical to Virtual.





Hace algún tiempo…nuestro buenos amigos del SAP d-shop Newtown Square (Llamados John Astill y companía) construyeron una Casa IoT para SAP Insurance. Esta pequeña casa (Por cierto, hecha y pintada a mano) utiliza un Arduino Nano, varios sensores y luces LED…y…lo cual es impresionante dicho sea de paso…una lavadora impresa en 3D con un sensor de agua…y por supuesto…estaba y está…habilitada para IoT.




Pensamos que era impresionate…así que tenemos una en nuestro propio SAP d-shop en Silicon Valley y se ha convertido en pieza clave de todos nuestros tours por el d-shop.

Luego…un tiempo después, nuestro amigos de HCP Marketing (Llamados Joe Binkley y compañía) e Intel construyeron un Edificio Inteligente. Un edificio muy bonito…controlado por Amazon Alexa que utiliza un Intel Galileo, algunos Arduinos así como también servos (motores), luces, un panel solar y hasta un ventilador…nuevamente todo esto…habilitado para IoT…pero como se deben haber imaginado ya…controlado por voz…así que puedes enviar el elevador de arriba para abaja…abrir o cerrar las puertas e inclusive enviar todo el edificio en modo de emergencia…afortunadamente…lo hemos mantenido en el d-shop por bastante tiempo y eso otro de nuestros demos con factor “wow” cada vez que alguien viene a visitarnos…




Tener ambos disponibles…poco a poco se fué enciendo la llama de la innovación y la creatividad…por que no construir una Casa Virtual que pueda ser utilizada con el Oculus Rift y que es controlada por Alexa?


No es un trabajo sencillo…pero de hecho que amamos los retos…y gracias a nuestra experiencia previa con Unity3D and Alexa working together ya sabiamos por donde empezar…



La arquitectura es bastante simple… El servidor Heroku no es más que un servidor de Eco, así que va a repetir todo lo que le pasemos como una respuesta JSON. Nuestra aplicación en Unity constantemente revisa el servidor Heroku para determinar si algún mensaje al que deba responder. Por supuesto, para que este trabaje como se quiere, necesitamos crear un skill en Amazon Alexa solo para poder actualizar el servidor. Así que, cuando decimos “open door”, entonces Alexa va a enviar un comando al servidor Heroku y este en respuesta va a generar un mensaje “open door” en JSON. Nuestra aplicación en Unity va a leer la respuesta generada por el servidor Heroku, y actuar correctamente abriendo la puerta…por supuesto, no queremos que esto siga pasándo una vez que ya se ejecutó el comando…así que luego de que Unity executa la acción va a enviar un mensaje nulo al servidor Heroku, así que la próxima vez el mensaje JSON va a ser también nulo y Unity simplemente va a esperar por el próximo comando válido.

Si quieren echar un pequeño vistazo a como se ve la Casa Virtual…aquí hay un par de imagenes…pero no se olviden de ver el video, J Así tendrán la experiencia completa -;)





Ahora…este proyecto comenzó como un “Project in a Box” (para uso interno solamente…disculpen por eso) lo cual significa…que todo el código fuente y la explicación de como construirlo desde cero debería ser proporcionada…pero…pero por razones obvias…eso no pasó L Así que en vez de eso…lo convertimos en un “Product in a Box” lo cual significa que (Disculpen nuevamente…solo empleados) pueden descargar la aplicación compilada y simplemente modificar el archivo de configuración para tenerlo funcionando por su cuenta J El código fuente no está siendo proporcionado pero obviamente con un simpático email pueden conseguirlo -;)

Consigánlo aquí

Ahora…que tengo toda su atención…por favor vean el video J Es un bonito viaje que parte la Casa IoT a la Casa Virtual pasándo por el Edificio Inteligente…



Ahora…se preguntarán por los modelos 3D Models utilizados para la Casa Virtual…como pueden ver en una de las images, la mayoría de ellos fueron descargados pero algunos de ellos fueron diseñados por nosotros J utilizándo Blender…Como el Amazon Echo, el Robot impreso en 3D y los llaveros con nombre, el Amazon Echo y obviamente la casa en sí J Para algunas otras cosas como las mesas y las plantas…esos fueron importados a Blender y “pintados a mano” puesto que la texturas no estaban disponibles.

Ahora…algo que pensamos que es realmente importante…es listar todos los problemas y lecciones que aprendimos mientras desarrollamos esta aplicación…

Problemas y Lecciones Aprendidas:

  • Como este es un Product in a Box y no un Project in a Box, no vamos a incluir el código fuente de la aplicación, pero lo que vamos a hacer en vez de eso es contarles los problemas y lecciones que aprendimos del desarrollo de este proyecto.
  • Unity utiliza el .NET Framework 3.5, el cual ya está deprecado por el .NET 4.0 así que muchas cosas no van a funcionar simplemente porque no han sido implementadas…y por qué es esto? Bueno…Unity utiliza Mono (que es .NET para Linux) y yo pienso que lo utilizán para mantener uniformidad entre todas las plataformas. Mientras Mono continue en .NET 3.5, lo más seguro es que Unity tampoco va a actualizase.
  • Cuando cargamos escenas, la iluminación puede quedar hecha un desastre…así que empiezas en el nivel uno…te mueves al nivel dos y de pronto parece que fuera de noche…la solución es simple…escogemos “Window à Lighting à Lightmaps”, desmarcamos el “Auto” checkbox y presionamos “Build” para hacer un bake a luz nuevamente.
  • Los Coroutines son simplemente asombrosos. Normalmente, no puedes hacer que tu aplicación duerma o espere…pero utilizándo Coroutines de hecho que puedes…Coroutines son como threads o hilos.
  • Cuando utlizamos luces, debemos asegurarnos de apagarlas cuando el personaje no está en el cuarto, porque esto nos va a ahorrar un poco de procesamiento gráfico y porque aunque sea virtualmente…tenemos que preocuparnos por el medio ambiente…
  • Unity no tiene una función o propiedad de wrap (salto de línea automático) para textos en 3D…lo cual es problemático especialmente si queremos hacer un muro de Twitter…así que la única opción es programar uno desde cero…aunque no es tan complicado…simplemente tomamos el texto, lo dividimos por espacio en un array…concatenamos cada palabra revisándo primero si la longitud de la cadena es menor que nuestro tope  (que puede ser el máximo número de caracteres que entran en nuestro muro), si la cadena es mayor que el tope, simplemente agregamos un retorno de carro (“\n”) antes de hacer la concatenación.
  • A medida que la aplicación crece puedes tener la necesidad de duplicar assets, lo cual es perfectamente normal y no agrega mucho poder extra de procesamiento (Especialmente si crean un Prefab y utilizan ese prefab), pero no se olviden de asignar un nombre único, de otra manera van a tener un dolor de cabeza si la aplicación necesita interactuar con esos assets.
  • Algunas veces vamos a tener que descargar modelos 3D de internet…otras veces vamos a crearlos utilizándo Blender…pero no hay que olvidar que muchas veces una simple esfera, cubo o algún otro objeto primitivo de Unity puede funcionar perfectamente utilizándo simplemente una imagen como textura.
  • Cuando creamos nuestro skill con Alexa…debemos asegurárnos de no cometer ningún error ortográfico…de otra manera se van a golpear la cabeza pensándo porque Alexa no está haciendo lo que le hemos pedido que haga…
  • Cuando probamos nuestra aplicación Debug.log() y Print() se volverán tus mejores amigos…nada mejor que un valor impreso o un mensaje para darse cuenta que es lo está funcionando mal.
  • Cuando movemos un objeto, debemos asegurárnos de guardar la posición original  y luego agregar el nuevo valor al valor que tenemos guardado. De lo contrario, algo puede provocar que los valores resulten errados…teniendo guardados los valores originales, podemos evitar tener que calcular los valores originales nuevamente y simplemente retornar al valor original para que todo encaje un su lugar.
  • Cuando utilizámos Texo en 3D nos daremos cuenta de que aún cuando coloquemos un objeto en frente del textp…este se mantendrá siempre visible…lo cual obviamente no es muy bonito…así que temos dos opciones…crear un shader para ocultarlo…o la manera más simple…hacer el objeto que está en frente...transparente. Esto no es algo perfecto para cualquier solución pero por lo menos funcionará.
  • El mayor problema al que nos podemos enfrentar cuando hacemos que Unity y Alexa conversen, es que cuando le digamos a Alexa que prenda las luces, ella responderá “La luz está prendida”…pero si le decimos lo mismo una segunda vez su respuesta debería ser “La luz ya está prendida” …para hacer esto…deberíamos utilizar una Base de Datos o algo parecido para almacenar la información…y cuando cerramos la aplicación, deberíamos limpiar los estados…si bien esto se puede hacer…es bastante trabajo, y que pasa si la aplicación colapsa de improviso? Deberíamos resetear los estados manualmente? No es lo ideal…
  • Esto nos lleva al punto de utilizar el elevador…podemos abrir la puerta o enviarlo a cualquiera de los pisos…en línes generales…eso es bastante sencillo…cada piso es una escena, así que necesitamos estar en el primer piso para poder enviar el elevador al segundo o tercer piso…pero…que pasa si estamos afuera del elevador? Estamos en el primer piso…pedimos el tercer piso…y luego abrimos la puerta…a medida que el personaje se mueve junto con el elevador…cuando abrimos la puerta todo se va a ver mal…solución? Simplemente utilizamos un cubo que no tenga un mesh renderer, así que es invisible…asignámos un collider con “is trigger” habilitado…y validamos que el personaje está interactuándo con el cubo para poder hacer que el elevador se mueva…de esa manera, así aunque pidamos el tercer piso y Alexa confirme que el elevador se está moviendo hacia arriba…nada va a pasar…cuando abrimos la puerta…podemos asumir que el elevador subió o bajó hasta tu piso para que podamos entrar…solo una ilusión…pero funciona…
  • Alexa no tiene una opción para retrazar el re-prompt (cuando pregunta si queremos hacer algo más), así que cuando exploramos la Casa Virtual ella nos preguntará “What else can I do for you?” y si no le respondemos nada, el skill simplemente se irá a dormir…así que tendremos que despertarla nuevamente…eso es algo un poco triste debido a la naturaleza de la aplicación…pero no hay nada que podamos hacer a menos que Amazon proponga una solución para que el re-prompt espere más tiempo…
  • Como todo el Alexa-Unity3D depende de Heroku…podemos esperar algunos retrazos o comandos dados por Alexa que no van a ser replicados necesariamente en el mundo virtual…puede ser un problema con la conexión a Internet o simplemente un problema con Heroku …

Como mencioné al inicio…el entorno se ve afectado por el clima…si está soleado…veremos un cielo claro y soleado…si está lloviendo veremos cielo oscuro y húmedo…y esto involucra utilizar un Skybox…aunque no un Skybox común y corriendo…y a propósito de esto, que es un Skybox? Bueno…simplemente…es un cubo que cubre todo el entorno y tiene diferentes images para simular el cielo…el problema es que un Skybox regular solo nos permite asignar 6 lados…lo cual por supuesto no es óptimo…necesitamos un Skybox de 12 lados…para que así podamos asignar images de cielo soleado e imágenes de cielo oscuro…de esa manera cuando revisamos el clime podemos modificar la luminosidad y esto va a afectar al Skybox puesto que va a utilizar uno u otro brindándonos el efecto de que está reflejando el clima que hace afuera…
Greetings,

Blag.
Development Culture.

Tuesday, February 14, 2017

LED es mi nuevo Hello World - Tiempo de Prolog

Como lo prometí...aquí está mi aplicación de Números LED escrita en Prolog...me tomó bastante tiempo...bastante investigación...muchos dolores de cabeza...así que espero que les guste...aun soy un completo novato en Prolog...así que...no hay ningún tipo de garantía -;)

LEDNumbers.pl

number(0,[[' _  '],['| | '],['|_| ']]).
number(1,[['  '],['| '],['| ']]).
number(2,[[' _  '],[' _| '],['|_  ']]).
number(3,[['_  '],['_| '],['_| ']]).
number(4,[['    '],['|_| '],['  | ']]).
number(5,[[' _  '],['|_  '],[' _| ']]).
number(6,[[' _  '],['|_  '],['|_| ']]).
number(7,[['_   '],[' |  '],[' |  ']]).
number(8,[[' _  '],['|_| '],['|_| ']]).
number(9,[[' _  '],['|_| '],[' _| ']]).

digits(0,[]).
digits(X,[H|T]) :- (X/10 > 0 -> H1 is floor(X/10), H is X mod 10, digits(H1,T)), !.

accRev([],A,A).
accRev([H|T],A,R) :- accRev(T,[H|A],R). 

getDigits(L,R) :- digits(L,Y), accRev(Y, [], R).

show_records([]).
show_records([A|B]) :-
  print_records(A), nl,
  show_records(B).  

print_records([]).
print_records([A|B]) :-
  format('~w',A), 
  print_records(B).

merge([L], L).
merge([H1,H2|T], R) :- maplist(append, H1, H2, H),
    merge([H|T], R), !.

listnum([],[]).
listnum([H1|T1],[R|Y]) :- number(H1,R), listnum(T1,Y).

led(X) :- getDigits(X,Y), listnum(Y,Z), merge(Z,R), show_records(R).

Quieren verlo en acción? Yo también -;)


A seguir aprendiendo -;)

Saludos,

Blag.
Development Culture.

Mi primer post en Prolog

Como siempre...estaba buscando el próximo lenguaje de programación que quieo aprender...y de alguna manera...Prolog se metió en el camino...

Ya había jugado con Programación Lógica en el pasado cuando aprendí Mercury...pero realmente...cuando se trata de lógica...Prolog se gana el premio...

Ustedes sabían que el primer compilador de Erlang se construyó en Prolog? Yo tampoco -:P

Para aprender...Estoy utilizándo SWI-Prolog que parece ser el mejor y más usado...y debo admitirlo...me encanta -;)


Así que...a simple vista...Prolog me recuerda a Mercury obviamente...pero también un poco a Forth...y extrañamente a Haskell en el sentido de que la recursividad es un elemente muy importante...

Como sucede generalmente cuando aprendo un nuevo lenguaje de programación...Empecé con mi aplicación de lista de números Fibonacci...así que aquí está...

fibonacci.pl
fibo(NUM,A,B,[H|T]) :- (NUM > 1 -> H is A + B, X is NUM - 1, 
                        (A =:= 0 -> fibo(X,H,B,T); fibo(X,H,A,T))).
fibo(_,_,_,[]).

fibonacci(NUM,R) :- fibo(NUM,0,1,X), !, append([0,1], X, R).

extensión .pl? Sip...la misma que Perl...pero como pueden ver...no tiene nada que ver como Perl -;)

En fín...aquí está el resultado...


Mi aplicación de Números LED está felizmente terminada y van a poder verla justo después de este blog -;)

Saludos,

Blag.
Development Culture.

Monday, December 05, 2016

LED es mi nuevo Hello World - Tiempo de Rust

Como actualmente estoy aprendiendo Rust, tenía que publica mi aplicación de números LED otra vez -;)

Por favor tomen en cuenta...que..."Estoy aprendiendo Rust"...así que código puede ser flojo, redundante y nada idiomático...pero...suficiente para mostrar el lenguaje y permitirme aprender más -;)

Aquí está el código...

led_numbers.rs
use std::io;
use std::collections::HashMap;

fn main(){
 let mut leds:HashMap<&str, &str> = HashMap::new();

 leds.insert("0", " _  ,| | ,|_| ");
 leds.insert("1", "  ,| ,| ");
 leds.insert("2", " _  , _| ,|_  ");
 leds.insert("3", "_  ,_| ,_| ");
 leds.insert("4", "    ,|_| ,  | "); 
 leds.insert("5", " _  ,|_  , _| ");
 leds.insert("6", " _  ,|_  ,|_| ");
 leds.insert("7", "_   , |  , |  ");
 leds.insert("8", " _  ,|_| ,|_| ");
 leds.insert("9", " _  ,|_| , _| ");

 println!("Enter a number : ");
 let mut input_text = String::new();
 io::stdin().read_line(&mut input_text)
            .expect("failed to read");

 let split = input_text.split("");
 let vec: Vec<&str> = split.collect();
 let count = &vec.len() - 2;
 
 for i in 0..3{
  for j in 0..count{
   match leds.get(&vec[j]){
    Some(led_line) => { 
     let line = led_line.split(",");
     let vec_line: Vec<&str> = line.collect();
     print!("{}",&vec_line[i]);
     },
    None => println!("")
   }
  }
  print!("");
 }
 println!("");
}

Y aquí está el resultado...


Espero que les guste y si pueden mostrarme una manera más Rusty de hacer las cosas...por favor me avisan -:D

Saludos,

Blag.
Development Culture.

Mi primer post en Rust

Nuevamente...estoy aprendiendo un nuevo lenguaje de programación...y esta vez le tocó el turno a Rust.


Rust es muy bueno y tiene características muy interesántes como ownership y borrowing...y la sintáxis me recuerda bastante a OCaml...lo cual me gusta bastante...

Por ahora estoy leyendo la documentación oficial, que está realmente muy bien hecha...así que por supuesto hice mi aplicación de números fibonacci...

fibonacci.rs
use std::io;

fn fib(num: i64, a: i64, b:i64) -> String{
 let mut result: String = "".to_string();
 let sum: i64 = a + b;
 let sum_str: &str = &sum.to_string();
 let a_str: &str = &a.to_string();
 let b_str: &str = &b.to_string();
 if a > 0 && num > 1 {
  result = result + sum_str + " " + &fib((num - 1), (a + b), a);
 }else if a == 0{
  result = "".to_string() + a_str + " " + b_str + " " + 
           sum_str + " " + &fib((num - 1), (a + b), b); 
 }
 result
}

fn main(){
 println!("Enter a number : ");
 let mut input_num = String::new();
 io::stdin().read_line(&mut input_num)
            .expect("failed to read");

 let trimmed = input_num.trim();
    match trimmed.parse::() {
        Ok(i) => { let result: String = fib(i, 0, 1); print!("{}", result);}
        Err(..) => println!("Please enter an interger, not {}", trimmed)
    };
}

El código es un poco extenso para mi gusto...pero puede ser simplemente porque no he aprendido lo suficiente de Rust...o porque su sistema de ownership/borrowing sacrifica longitud para agregar seguridad...lo cual es algo realmente muy bueno...

Aquí está el resultado



Por supuesto, mi aplicación de Números LED ya está lista...y está viniendo justo después de este post -;)

Saludos,

Blag.
Development Culture.

Friday, December 02, 2016

Unity3D y Alexa trabajándo juntos

Este post fué posteado originalmente en Unity3D and Alexa working together.


Desde hace tiempo ...Tuve la idea de hacer que Unity3D y Alexa trabajen juntos...sin embargo...otros proyectos me mantuvieron ocupado y me quitaron tiempo para poder trabajar en esto...así que...hace unos días...una conversación con un amigo me hizo recordar que tenía muchas ganas de hacer esto...así que lo hice :)

Al inicio...no estaba exactamente seguro...pero lentamente las ideas se comenzaron a formar en mi mente...que pasaría si Unity leyera un webservice que es actualizado por Alexa? Cuando el comando correcto es interpretado, entonces Unity creará el objeto y problema resuelto...parece sencillo, no? Bueno...en realidad lo es...


Primero lo primero...tenemos que crear un pequeñp servidor web en NodeJS con Heroku...luego...necesitamos instalar Heroku Toolbelt...

Ahora...creamos una carpeta llamada node_alexa y dentro creamos los siguientes archivos...

package.json
{
  "dependencies": {
    "express": "4.13.3"
  },
  "engines": {
    "node": "0.12.7"
  }
}

procfile
web: node index.js
index.js
var express = require('express')
    ,app = express()
    ,last_value;

app.set('port', (process.env.PORT || 5000));

app.get('/', function (req, res) {
  if(req.query.command == ""){
 res.send("{ \"command\":\"" + last_value + "\"}");
  }else{
 if(req.query.command == "empty"){
  last_value = "";
  res.send("{}");
 }else{
  res.send("{ \"command\":\"" + req.query.command + "\"}");
  last_value = req.query.command;
 }
  }
})

app.listen(app.get('port'), function () {
  console.log("Node app is running on port', app.get('port')");
})

Una vez que tenemos esto...nos logeamos en Heroku Toolbelt y escribimos lo siguiente...

Heroku Toolbelt
cd node_alexa
git init .
git add .
git commit -m "Init"
heroku apps:create "yourappname"
git push heroku master
heroku ps:scale = web 0
heroku ps:scale = web 1

El WebService está listo para rockear -:) Deberías poder encontrárlo si vas a "http://yourappname.herokuapp.com/"

Ahora...este simple webservice potenciado por NodeJS nos servirá como un pequeño servidor de Eco...lo cual significa...cualquier cosa que escribamos nos devolverá una respuesta json...por supuesto...si escribimos "empty" entonces la respuesta será un json vacío...así que la idea principal es que podamos guardar el último valor ingresado...si pasamos un comando, este va a ser llamado cuando volvamos a llamar el servicio sin pasar ningún tipo de comando...así que si lo llamamos una vez...podemos llamarlo multiples veces sin interferir con su valor...

Lo siguiente en la lista...será crear nuestra aplicación en Unity...

Creamos una nueva aplicación y la llamamos "WebService" o algo parecido...el nombre del proyecto no importa mucho...

En la ventana de Hierarchy seleccionamos "Main Camera" y cambiamos los detalles del "Tranform" de esta forma...


Ahora, creamos un nuevo "3D Object" -> "Cube" y lo llamamos "Platform" con los siguientes detalles en el "Transform"...


Luego de eso, debemos crear cuatro paredes que van a ir alrededor de la plataforma...así que creamos 4 "3D Object" -> "Cube" y los llamamos "Wall 1", "Wall 2", "Wall 3" y "Wall 4"...





Cuando todo está listo, nuestro workspace debería verse así...


Vamos al tab project y creamos una carpeta llamada "plugins" y después creamos un nuevo archivo C# llamado "SimpleJSON"...dentro copiamos el código fuente que esta aquí...esto nos va a pemitir utlizar SimpleJSON para interpretar el JSON...

Ahora...creamos otra carpeta llamada "Script" y dentro creamos un nuevo archivo C# llamado "MetaCoding"...o cualquier otra cosa...



MetaCoding.cs
using UnityEngine;
using System.Collections;
using System.Net;
using System.IO;
using SimpleJSON;

public class MetaCoding : MonoBehaviour {

    int counter = 1;

    IEnumerator DownloadWebService()
    {
        while (true) { 
            WWW w = new WWW("http://yourapp.herokuapp.com/?command");
            yield return w;

            print("Waiting for webservice\n");

            yield return new WaitForSeconds(1f);

            print("Received webservice\n");
        
            ExtractCommand(w.text);

            print("Extracted information");

            WWW y = new WWW("http://yourapp.herokuapp.com/?command=empty");
            yield return y;

            print("Cleaned webservice");

            yield return new WaitForSeconds(5);
        }
    }

    void ExtractCommand(string json)
    {
        var jsonstring = JSON.Parse(json);
        string command = jsonstring["command"];
        print(command);
        if (command == null) { return;  }
        string[] commands_array = command.Split(" "[0]);
        if(commands_array.Length < 3)
        {
            return;
        }
        if (commands_array[0] == "create")
        {
            CreateObject(commands_array[1], commands_array[2]);
        }
    }

    void CreateObject(string color, string shape)
    {

        string name = "NewObject_" + counter;
        counter += 1;
        GameObject NewObject = new GameObject(name);

        switch (shape)
        {
            case "cube":
                NewObject = GameObject.CreatePrimitive(PrimitiveType.Cube);
                break;
            case "sphere":
                NewObject = GameObject.CreatePrimitive(PrimitiveType.Sphere);
                break;
            case "cylinder":
                NewObject = GameObject.CreatePrimitive(PrimitiveType.Cylinder);
                break;
            case "capsule":
                NewObject = GameObject.CreatePrimitive(PrimitiveType.Capsule);
                break;
        }
        NewObject.transform.position = new Vector3(0, 5, 0);
        NewObject.AddComponent();
        switch (color)
        {
            case "red":
                NewObject.GetComponent().material.color = Color.red;
                break;
            case "yellow":
                NewObject.GetComponent().material.color = Color.yellow;
                break;
            case "green":
                NewObject.GetComponent().material.color = Color.green;
                break;
            case "blue":
                NewObject.GetComponent().material.color = Color.blue;
                break;
            case "black":
                NewObject.GetComponent().material.color = Color.black;
                break;
            case "white":
                NewObject.GetComponent().material.color = Color.white;
                break;
        }
    }

        // Use this for initialization
    void Start () {
        print("Started webservice import...\n");

        StartCoroutine(DownloadWebService());
    }
 
 // Update is called once per frame
 void Update () {
 
 }
}

Una vez que tenemos el código...simplemente debemos adjuntarlo al Main Camera...


El concepto básico para este script es bastante simple...Estamos creándo "DownloadWebService" como un método IEnumerator para poder llamarlo como un Coroutine...y eso nos permite poder poner la función a dormir puesto que necesitamos darle un poco de tiempo entre llamadas a la función...

Este método va a llamar a nuestro WebService en Heroku buscándo un comando "create"...una vez que lo tiene...va a interpretar la respuesta JSON y dividirla en 3...para que podamos tener..."create", "blue" y "sphere"...esto va a llmar a CreateObject que luego va a crear la esfera azul...luego de que ha hecho eso...el coroutine va a continuar y simplemente va a enviar un nuevo comando a nuestro WebService para limpiar el resultado...para hacer que esto funcione de manera correcta...queremos darle un tiempo de 5 segundos después de haber el limpiado el webservice antes de poder llamar a otros comando "create"...

Y esta llamada va a ser hecha por nuestro skill en Alexa...así que basicamente cuando decimos "create blue sphere" en Alexa...ella va a enviar el comando al WebService...va a actualizar el mensaje y nuestra aplicación en Unity va a tomar el mensaje...hacer su trabajo...y luego limpiar el Webservice...luego esperar a que Alexa le provea el siguiente comando...

Así que...para ir finalizándo...necesitamos crear nuestro skill en Alexa...

Primera, vamos a crear una función Lambda...así que nos logeamos aquí...

Por supuesto...yo ya tengo todo configurado...así que vamos a crear una función dummy solamente para mostrárles los pasos...

Debemos hacer click en "Create Lambda Function" y veremos la siguiente pantalla...


Por supuesto hay bastantes...así que escribimos "Color" en el filtro...


Escogemos "alexa-skills-kit-color-expert"


Dejamos todo como está y presionamos "Next"


Escogemos un nombre y descripción...


Escogemos un rol existente si es que tenemos alguno creado anteriormente...de otra forma creamos un nuevo lambda_basic_execution...luego aumentamos el Timeout a 10 segundos y dejamos todo lo demás como está...presionamos "Next"...una ventana de confirmación va a aparecer...así que simplemente presionamos "Create function"...

Vamos a ser presentados con una ventana en donde podemos subir nuestro código fuente (lo cual vamos a hacer un poco más adelánte) y un número ARN...el cual necesitamos para un paso más adelánte...


Esta sección explica como crear el skill en Alexa...así que favor sigan mis pasos...y logeense aquí...


Escogemos "Alexa Skills Kit"...y creamos un nuevo skill...



Escogemos un nombre para nuestro skill y lo más importante...escogemos un "Invocation Name"...que es lo que le vamos a decir a Alexa para que abra nuestra aplicación..algo como..."Alexa, open Sandbox"...presionamos click...

En el tab de Interaction Model tenemos dos ventanas...llenamos esto en "Intent Schema"...

Intent Schema
{
  "intents": [
    {
      "intent": "GetUnityIntent",
      "slots": [
        {
          "name": "color",
          "type": "LITERAL"         
        },
        {
          "name": "shape",
          "type": "LITERAL"
        }
      ]
    },
    {
      "intent": "HelpIntent",
      "slots": []
    }
  ]
}

Estos son basicamente parámetros que podemos usar cuando estamos preguntándole algo a Alexa...

Y debemos llenar esto en "Sample Utterances"...

Sample Utterances
GetUnityIntent create {red|color} {sphere|shape}
GetUnityIntent create {yellow|color} {sphere|shape}
GetUnityIntent create {green|color} {sphere|shape}
GetUnityIntent create {blue|color} {sphere|shape}
GetUnityIntent create {black|color} {sphere|shape}
GetUnityIntent create {white|color} {sphere|shape}

GetUnityIntent create {red|color} {cube|shape}
GetUnityIntent create {yellow|color} {cube|shape}
GetUnityIntent create {green|color} {cube|shape}
GetUnityIntent create {blue|color} {cube|shape}
GetUnityIntent create {black|color} {cube|shape}
GetUnityIntent create {white|color} {cube|shape}

GetUnityIntent create {red|color} {cylinder|shape}
GetUnityIntent create {yellow|color} {cylinder|shape}
GetUnityIntent create {green|color} {cylinder|shape}
GetUnityIntent create {blue|color} {cylinder|shape}
GetUnityIntent create {black|color} {cylinder|shape}
GetUnityIntent create {white|color} {cylinder|shape}

GetUnityIntent create {red|color} {capsule|shape}
GetUnityIntent create {yellow|color} {capsule|shape}
GetUnityIntent create {green|color} {capsule|shape}
GetUnityIntent create {blue|color} {capsule|shape}
GetUnityIntent create {black|color} {capsule|shape}
GetUnityIntent create {white|color} {capsule|shape}

GetUnityIntent {thank you|color}

Estos son todos los comandos que Alexa puede entender...y sí...podriamos haber utilizado "Custom Slot Types" para hacer el código más corto...pero...he tenido problemas donde no funciona muy bien cuando hay mas de un slot...simplemente presionamos next...


Aquí, escogemos AWS Lambda ARN...y escogemos North America o Europe dependiendo de nuestra locación física...luego en la caja de texto...simplemente copiamos y pegamos el número ARN que recibimos de nuestra función Lambda...

Esto nos va a enviar al tab de "Test"...pero en realidad no queremos eso e inclusive no podemos usarlo...así que debemos regresar al tab "Skill Information" y encontraremos que un nuevo campo ha aparecido...

Este campo será "Application Id"...copiamos este número y continuamos hacia la parte final...

Creamos una carpeta llamada "Unity" y dentro una carpeta llamada "src"...dentro de esa carpeta copiamos el archivo "AlexaSkills.js"

Vamos a utilizar el módulo "request" de NodeJS...así que lo instalamos localmente en la carpeta Unity...

sudo npm install --prefix=~/Unity/src request 

Esto va a crear una carpeta llamada node_module conteniendo al módulo request...

Luego, creamos un nuevo archivo llamado "index.js"


index.js
var request = require("request")
  , AlexaSkill = require('./AlexaSkill')
    , APP_ID     = 'yourappid';

var error = function (err, response, body) {
    console.log('ERROR [%s]', err);
};

var getJsonFromUnity = function(color, shape, callback){

var command = "create " + color + " " + shape;

if(color == "thank you"){
 callback("thank you");
}
else{
var options = { method: 'GET',
  url: 'http://yourapp.herokuapp.com/',
  qs: { command: command },
  headers: 
   { 'postman-token': '230914f7-c478-4f13-32fd-e6593d8db4d1',
     'cache-control': 'no-cache' } };

var error_log = "";

request(options, function (error, response, body) {
 if (!error) {
  error_log = color + " " + shape;
 }else{
  error_log = "There was a mistake";
 }
  callback(error_log);
    });
}
}

var handleUnityRequest = function(intent, session, response){
  getJsonFromUnity(intent.slots.color.value,intent.slots.shape.value, function(data){
 if(data != "thank you"){
 var text = 'The ' + data + ' has been created';
 var reprompt = 'Which shape would you like?';
    response.ask(text, reprompt);
 }else{
  response.tell("You're welcome");
 }
  });
};

var Unity = function(){
  AlexaSkill.call(this, APP_ID);
};

Unity.prototype = Object.create(AlexaSkill.prototype);
Unity.prototype.constructor = Unity;

Unity.prototype.eventHandlers.onSessionStarted = function(sessionStartedRequest, session){
  console.log("onSessionStarted requestId: " + sessionStartedRequest.requestId
      + ", sessionId: " + session.sessionId);
};

Unity.prototype.eventHandlers.onLaunch = function(launchRequest, session, response){
  // This is when they launch the skill but don't specify what they want.

  var output = 'Welcome to Unity. Create any color shape by saying create and providing a color and a shape';

  var reprompt = 'Which shape would you like?';

  response.ask(output, reprompt);

  console.log("onLaunch requestId: " + launchRequest.requestId
      + ", sessionId: " + session.sessionId);
};

Unity.prototype.intentHandlers = {
  GetUnityIntent: function(intent, session, response){
    handleUnityRequest(intent, session, response);
  },

  HelpIntent: function(intent, session, response){
    var speechOutput = 'Create a new colored shape. Which shape would you like?';
    response.ask(speechOutput);
  }
};

exports.handler = function(event, context) {
    var skill = new Unity();
    skill.execute(event, context);
};

El código es bastante simple...principalmente porque la mayoría es un template...simplemente lo copia...cambias un par de cosas y estás listo para continuar...

Basicamente cuando decimos "Alexa, open Unity"...ella va a escuchar nuestros pedidos...así que podemos decir "create green cube"...y va a llamar a nuesto WebService en Heroku y luego esperar por otro comando...si no le hablas nuevamente...te va a invitar a decir algo...si le dices "Thank you" ella va a desactivarse a si misma de una manera muy educada...

Y eso es basicamente todo...una vez que Alexa envia el comando al WebServer...nuestra aplicación en Unity va a leerla y actuar como corresponde...creándo cualquier forma y color que le hemos pedido...interesánte, huh?

Pero por supuesto...no me creen, no? No puede ser tan simple...bueno...si y no...es simple...pero saqué todos los puntos complicados para poder proveerles una serie de instruciones claras y consisas...

Así que...así es como se ve cuando ejecutamos la aplicación en Unity...



Y aquí está el video en acción...


Espero que les guste...y mantenganse alertas...porque para mi esto solo fué una prueba de concepto...mi próximo proyecto va a llevar esto al siguiente nivel...

Saludos,

Blag.
Development Culture.

Thursday, December 01, 2016

LED es mi nuevo Hello World - Tiempo de Swift (para Linux)

Me tomó un poco de tiempo escribir este blog...principalmente porque estoy aprendiendo Rust y también porque acabo de teminar mi último demo...cuyo blog publicaré más tarde -;)

Esta versión de mi applicación de Números LED se convierte en la versión de 25 lenguajes de programación...así que...obviamente...es una gran hito para mi -:D Quién sabe? Quizás haga algo interesánte si alcanzo los 50 lenguajes de programación -:D

En fín...como me encanta decir..."Basta de hablar...muestrame el Código Fuente" -;)

LedNumbers.swift
let leds: [Character:String] = [
 "0" : " _  ,| | ,|_| ",
 "1" : "  ,| ,| ",
 "2" : " _  , _| ,|_  ",
 "3" : "_  ,_| ,_| ",
 "4" : "    ,|_| ,  | ",
 "5" : " _  ,|_  , _| ",
 "6" : " _  ,|_  ,|_| ",
 "7" : "_   , |  , |  ",
 "8" : " _  ,|_| ,|_| ",
 "9" : " _  ,|_| , _| "
];

print("Enter a number: ",terminator:"");
let num = readLine(strippingNewline: true);

var line = [String]();
var led = "";

for i in 0...2{
 for character in num!.characters{
  line = String(leds[character]!)!.
                       characters.split(separator: ",").map(String.init);
  print(line[i], terminator:"");
 }
 print("");
}

Y aquí está la imagen del programa haciendo su magia -:)


Saludos,

Blag.
Development Culture.

Monday, November 28, 2016

Mi primer post en Swift (para Linux)


Puesto que Apple liberó de forma muy amable  Swift for Linux...Tenía que aprenderlo-:)

Por supuesto...no está totalmente implementado...así que la mayoría de cosas que hacen a Swift impresionante en IOS no están presenten aún...pero aún así...es impresionante! -:D

Swift es medio functional...así que puedes ver muchas cosas de Haskell y Erlang...pero también imperativo y orientado a objects...así que eso lo convierte en un lenguaje muy interesánte...

Como siempre...aquí está mi pequeña aplicación de números Fibonacci...

fibonacci.swift
func fib(num:Int,a:Int,b:Int) -> String{
 var result: String = "";
 if a > 0 && num > 1{
  result = result + String(a + b) + " " + 
           fib(num: (num - 1), a: (a + b), b: a);
 }else if a == 0{
  result = String(a) + " " + String(b) + " " + 
           String(a + b) + " " + 
           fib(num: (num - 1), a: (a + b), b: b);
 }
 return result;
}

print("Enter a number: ",terminator:"");
let number = Int(readLine(strippingNewline: true)!);

print(fib(num: number!, a: 0, b: 1));

Y aquí está el resultado....


Ya tengo lista mi aplicación de Números LED...así que esperen -;)

Saludos,

Blag.
Development Culture.

Tuesday, November 15, 2016

LED es mi nuevo Hello World - Tiempo de Perl

Como lo prometí...acá está mi LED Numbers a la Perl...y como siempre...por favor tengan en cuenta de que soy un novato en Perl...Yo se que hay maneras más eficientes, cortas y consisas de hacer esta aplicación...pero...que tan bueno es un código introductorio que usa código oscuro y arcano? Yo no quiero que la gente se asuste con Perl...Quiero que la gente diga "Hey...eso no se ve tan dificil...Yo quiero aprender Perl"...

Así que...aquí está...

LedNumbers.pl
#!/usr/bin/perl
use strict;
use warnings;
use diagnostics;

my %leds = (
 0 => ' _  ,| | ,|_| ',
 1 => '  ,| ,| ',
 2 => ' _  , _| ,|_  ',
 3 => '_  ,_| ,_| ',
 4 => '    ,|_| ,  | ',
 5 => ' _  ,|_  , _| ',
 6 => ' _  ,|_  ,|_| ',
 7 => '_   , |  , |  ',
 8 => ' _  ,|_| ,|_| ',
 9 => ' _  ,|_| , _| '
);

print "Enter a number: ";
my $num = <>;
my @numbers = ( $num =~ /\d/g );

for my $i (0 .. 2){
 for my $j (0 .. scalar(@numbers) - 1){
  my @line = split /\,/,$leds{$numbers[$j]};
  print $line[$i];
 }
 print "\n";
}

Y acá está el resultado...


Y para que lo sepan...esta es mi versión numero 23 del código...sip...he escrito mi aplicación de LED Numbers en 24 lenguages hasta el momento -;) Cuál va a ser mi punto de quiebre? Quien sabe...la programación es el límite -;)

Saludos,

Blag.
Development Culture.