Studying trigonometry using Aisoy1 and Scratch

April 25, 2014

Hello, Aisoy aficionados. Today we are going to create an application to study trigonometry using our Aisoy1 and the Scratch application.

The Aisoy’s template has the initial appearance and configuration pictured below. It displays the scene and a central sprite that represents our bot. We will be able to develop simple applications that interact with Aisoy1 using this app.

The leftmost panel contains program constructs we can use to instruct the bot. These constructs include variable declarations, conditional statements, loop blocks, and so forth. selecting each option (Motion, Control, Looks, Sensing, Sound, Operators, Pen, Variables) will display the construct options within that categorical scope.

Now we can create our own application. We are going to use the bot’s accelerometer sensor to trigger our application and indicate the current angle of inclination of the bot.

As we tilt the bot, it will form a logical triangle where the bot represents the hypotenuse, the surface on which it sits represents one leg of the right triangle and the effective height of the bot represents the other side of the right triangle. The bot silhouette in the display will indicate the inclination dynamically.

To create this program we must understand how information is provided when the robot is tilted. As the robot is tilted, discrete values will be reflected by the variable “bot1.position”. The sensor will return one of these values:

0: the inclination is between 90º and 67.5º (where 90º represents an upright bot)

1: the inclination is between 67.5º and 45º

2: the inclination is between 45º and 22.5º

3: the inclination is between 22.5º and 0º (where 0º represents a bot lying horizontally)

4: the bot is upside down

So our code will be designed to handle these 5 possible readings. In each case, we will draw a line to represent the inclined state of the bot.

For this first case (bot1.position = 0), we will draw a vertical line. The following code will do this:

As you can see, the first step is to recognize that the value “0” is received from the bot’s  accelerometer. We will have different programming sequences for each possible bot1.position value. We will use the “posX” variables to make sure we only run the code appropriate for the current position (inclination). For example, if the bot1.position is 0, we will set the Scratch variable “pos1” to 1 and “pos2” through “pos5” to 0.

Then we will place the center of the sprite at the position where x = 100 and y = -50 and configure our drawing parameters. We will clear the previous drawing and set the pen with color of black and width of 2 pixels.

At the beginning of the program, we have initialized the hypotenuse variable to 100 to represents 100 units or pixels. We initialized the "hipotenuseP" variable to 24 to represent theh height of the bot (24 cm).

The following code will display a message in a dialogue balloon with text passed as parameters. The “join” function allows us to build a text string out of text variables and static text. This step allows us to show the height of the robot.

Now we have all the logic necessary to draw the vertical line that represents the orientation of the bot.

This “repeat” loop draws the vertical line. It will be repeated 100 times due to the value of the hypotenuse variable. The first blue instruction indicates a direction of 0º (to draw upward), while next blue step drives a movement of 1 unit (or pixel).

The “if” conditional block located inside the loop check the case that “bot1.position” is something other than 0. If it is not 0, we abort this script because program should draw a different triangle. It is very possible that the position of the robot changes during the execution of this drawing routine and this conditional checks for that situation. If we didn’t exit this routine, we could have multiple routines drawing triangles simultaneously which would be inaccurate. So we would exit the current routine if it no longer corresponds to the bot’s current orientation.

We should change the current sprite image to another to take care of this job. We will choose a very simple sprite: a brightly colored square made with the Scratch sprite editor.

If you launch the program and the bot is standing upright on its base, this result will be displayed in the Scratch screen:

Now let's add another sprite. This sprite will be the bot silhouette to indicate what we are drawing.

We can see that now we have two sprites, one of them made ​​the dynamic triangle drawing as well as the bot silhouette.

Now we will establish the structures that display the inclination of the bot according to the accelerometer readings received.

Notice that we place the center of the sprite at (-100, 0) to avoid overlapping the triangle and lines we are drawing. The other instructions will rotate the sprite to the correct angle.

So the result will display like this:

Let's see how we can draw the resulting triangle when the bot is not completely upright ( "bot1.position" has the value 1, 2, 3 or 4). We will describe the procedure for the case when the value of the variable is 1.  We will focus on the “Trigon” sprite:

The first portion of code is the same as when “bot1.position” has the value 0.

However, we introduce the value of the angle we want to draw here (57° in this case; the average between 67.5° and 45°) in the variable "angle", which allow us to perform trigonometric calculations for different measures of the two cathetus (the two sides of triangle adjacent to the right angle).

Now we will draw the triangle. In this case we begin by drawing the hypotenuse (remember that "hypotenuse Bis", "next cathetus Bis" and "opposite cathetus Bis" variables are used to display messages indicating centimeters). The other variables are used for internal calculations.

In the next step we display a message indicating the hypotenuse in centimeters while the program is drawing it.

Then we create a loop to draw the hypotenuse. The procedure is the same as drawing the line, except that the angle is different. In this case,we have done a subtraction between the angle and  90º, because in Scratch, the 0° and 180° endpoints are in positioned vertically rather than horizontally.

Once we have drawn the hypotenuse, is the time to draw the opposite cathetus (the side opposite the angle of inclination):

The height of the opposite side is calculated using the sine function. Knowing that "sin a = height of opposite cathetus / hypotenuse", we can solve for "opposite cathetus” using “hypotenuse * sin a". We store the relevant values in variables for the internal calculation and displaying  messages.

The next step is to display the message with the value of the opposite cathetus height and draw it following the previous processes. But in this case, the direction of the "virtual pen" will be 180 (down).

Time to next cathetus:

The side of the right triangle adjacent to the angle of inclination is the “next cathetus”. The next cathetus is proportional to the cosine of the angle. So the procedure is the similar to the previous but uses the cosine function. Well, the code for the value 1 of “bot1.position” ends here.

Let's see the result of our work:

The procedure for programming the other cases provided by the bot position would be similar,  changing the angle appropriately in each particular case. You can see the source code here.

Saludos Aisoy aficionados. Vamos a centrarnos en explicar cómo podemos crear un ejemplo sencillo de aprendizaje trigonométrico gracias al uso de nuestro robot Aisoy1. Para ello emplearemos el entorno de desarrollo y programación Scratch, bajo la plantilla ofrecida por Aisoy para tal cometido.

Dicha plantilla proporcionada presenta este aspecto inicial, donde se puede observar que en el escenario contamos con un sprite central que respresenta nuestro robot. Gracias a esta plantilla y las posibilidades que nos ofrecen todos sus bloques de programación seremos capaces de interactuar con el bot Aisoy1 y realizar diversas aplicaciones del modo más sencillo y amigable posible.

El área situada más a la izquierda nos proporciona los diferentes bloques en los cuales se catalogan las acciones que podremos indicarle al bot, así como todas y cada una de las sentencias que determinarán nuestro “script” o programa funcional. Cada una de las opciones (Motion, Control, Looks, Sensing, Sound, Operators, Pen, Variables) desplegará las diferentes posibilidades que ofrece dentro del ámbito que describen.

Una vez tenemos claro todo lo anterior, ya somos capaces de disponernos a crear nuestra aplicación de interacción con el robot. En este caso, vamos a aprovechar las funcionalidades que ofrece en cuanto al sensor de acelerómetro para determinar diferentes parámetros trigonométricos y dibujar dinámicamente a partir de la información aportada.

Lo que se pretende con este ejemplo es dibujar el triángulo que definiría el bot respecto al eje horizontal ó “x”, teniendo en cuenta que la hipotenusa representaría al mismo. Esto se hará dinámicamente conforme lo inclinemos. Además, mostraremos la silueta del bot en el mismo escenario, el cual adoptará y representará la inclinación que esté adoptando en cada momento concreto.

Para ello debemos tener claro qué información aporta el robot para detectar el momento de inclinación. Esto se consigue gracias a que el mismo emite valores discretos por medio de la variable “bot1.position”. Los valores que puede adoptar esta variable son los siguientes:

-0: la inclinación se sitúa entre los 90º y los 67.5º (considerando que el bot se encuentra a 90º si se encuentra erguido).

-1: inclinación entre los 67.5º y los 45º.

-2: inclinación entre los 45º y 22.5º.

-3: inclinación entre los 22.5º y 0º (0º indica que el bot se encuentra acostado sobre la horizontal).

-4: el bot se encuentra boca abajo.

Por lo tanto, debemos realizar el dibujado dependiendo de estos 5 valores. Para el primero de ellos, y puesto que el bot forma una línea recta con la horizontal, lo que representaremos será eso mismo, una línea vertical. El siguiente código realizaría esto mismo:

La primera de las acciones será reconocer que se reciba, a partir del bot, el valor “0” en cuanto a su posición. Puesto que para cada una de las posiciones realizaremos una secuencia distinta de programación, y dado que al ejecutarse una de ellas, es muy fácil que el bot cambie a otra posición y la secuencia actual siga ejecutándose en paralelo, deberemos dejar en ejecución solamente aquella de la posición en que se encuentre en ese mismo momento, abortando el resto de ejecuciones en paralelo. Hacia tal fin están dirigidas las variables “posX”, de modo que tomarán el valor 1 si el valor que emite el robot es “X” ó 0 en caso contrario.

De este modo, si estamos contemplando el caso en que el robot esté emitiendo que el valor de la variable “bot1.position” es 0, deberemos establecer a 1 la variable en scratch pos1 y el resto de “posX” como 0.

A continuación, situaremos el centro del sprite en la posición x=100 e y=-50, y configuraremos los valores de dibujado dinámico para borrar todo lo que hubiera anteriormente respecto a este sprite, y ya situar el dibujado activo, en color negro y con un grosor de 2 puntos.

Además, debemos tener en cuenta que al inicio del programa se han establecido los tamaños de hipotenusa en 100 unidades o píxels para el tratamiento de la misma en cuanto a programación (almacenado en la variable “hypotenuse”), y del valor 24 almacenado en la variable “hipotenuseP”, que nos servirá para mostrar mensajes de acuerdo a la altura real del bot en cm. (24 cm).

Con el siguiente código haremos que el puntero muestre un bocadillo (a modo de diálogo de cómic) el texto pasado como parámetros. La función “join” nos permite combinar varios tipos de variables o texto. Así podremos mostrar un texto aclarativo del tamaño que tiene el robot (hipotenusa para el resto de triángulos a mostrar).

Entonces ya tenemos todo el código relacionado con el dibujado dinámico dispuesto a realizar esa línea recta que determinará la figura del robot.

Con este bucle “repeat” indicamos que la acción situada dentro del bloque se realizará tantas veces como indica la variable indicada como parámetro (repetir tantas veces como indica dicha variable). De este modo, conseguiremos dibujar en cada una de las iteraciones del bucle el dibujado de cada píxel que formará la línea recta que queremos obtener. El código en azul establecerá el sentido del sprite actual en los 0º para dibujar ascendentemente, mientras que el paso siguiente es realizar el movimiento en 1 unidad (o píxel en este caso).

Notemos que el bloque condicional “if” situado dentro del bucle comprobará que, dado el caso en que se esté ejecutando esta porción de código y la última posición detectada no sea la “0”, es decir la propia de éste en concreto, se aborte la ejecución del script. Esto es así debido a que es muy posible que en mitad de su ejecución, la posición del robot cambie e inicie otra de las rutinas de dibujado. Sin embargo, si la actual no ha finalizado, ambas rutinas accederán al control del sprite para hacer el dibujado propio pero de forma simultánea, con lo que el resultado visual será una combinación de ambas y por lo tanto incorrecto. Así, podremos abortar la ejecución en el momento en que la posición actual ya no corresponda con la ejecución del script.

Previamente a la ejecución del script sería conveniente cambiar el disfraz del sprite actual por otro más adecuado a lo que se desea con este trabajo. En este caso hemos escogido un sprite muy simple (cuadrado de color llamativo realizado desde el mismo editor de sprites de scratch) a modo de puntero e indique en todo momento dónde se está “pintando”.

Si lanzamos el programa y el bot se encuentra de pie apoyado sobre su base, el resultado mostrado en la pantalla de scratch será el siguiente:

Ahora vamos añadir otro sprite con la silueta del bot para aclarar qué indican estos trazos que estamos dibujando.

Podemos observar cómo ahora contamos con dos sprites, uno que realizará el dibujado dinámico de triángulos, y otro, con la silueta del bot.

Lo que haremos a continuación será establecer las pautas de este sprite. Lo que queremos hacer es que muestre la inclinación relativa a su homónimo en la realidad de acuerdo a la información recibida. Entonces, basta con mostrar dicho sprite con los grados de inclinación adecuados para cada situación en concreto.

Advirtamos que situamos el centro del sprite en el punto (-100 , 0) para evitar colisionar con el visionado de triángulos y rectas que también se desea mostrar. El resto de instrucciones se centran en dar ángulo al sprite según el valor devuelto de “bot1.position”.

Así que, con todo lo realizado anteriormente, podemos visualizar el resultado final de dibujado dinámico y silueta del bot para el caso en que “bot1.position” = 0. Sería el siguiente:

Veamos ahora cómo podemos dibujar el triángulo resultante cuando el ángulo no es recto (como es el caso en que “bot1.position” tome el valor 1 ó 2). Así que para ello, mostraremos el procedimiento para el caso en el que el valor de dicha variable sea 1.

El código del sprite “Aisoy” ha quedado claro cómo procedería. Centrémonos entonces en el del sprite “Trigon”, encargado de realizar el dibujado del triángulo.

La primera porción del código se corresponde tal cual al caso anterior en que “bot1.position” tomaba el valor 0, puesto que se trata de la preparación de variables y del puntero de dibujado. Sin embargo, introducimos en este caso el valor del ángulo que queremos dibujar (57 en este caso, dado que es la media discreta entre 67.5º y 45º y resultaría la representación más fiel de dicho intervalo) en la variable “angle”, lo cual nos permitirá realizar los diferentes cálculos trigonométricos para obtener las medidas de los dos catetos.

Lo que resta entonces es dibujar el triángulo. En este caso se empieza por realizar la hipotenusa (recordemos que las variables “hipotenusaP”, “NextCathetusP” y “OpCathetusP” van dirigidas a la muestra de mensajes, dado que son las que contienen las medidas en centímetros). El resto van destinadas exclusivamente al cálculo interno del programa.

Así que, en primer lugar mostraremos en un bocadillo los cm. que caracterizan la hipotenusa que se va a dibujar, que se mantendrá mientras el programa se encuentre en el bucle que se encarga de pintar el triángulo.

Seguidamente se procederá a realizar el bucle de pintado de la hipotenusa. El procedimento es el mismo que para el dibujado de la recta en el caso en que bot1.position=0, salvo que el ángulo en el que se va a ir realizando el dibujado es distinto ya no es recto. En este caso, se ha realizado una resta del ángulo con 90º, puesto que en Scratch, la referencia a 0º y 180º se sitúa en la vertical en vez de la horizontal.

Una vez dibujada la hipotenusa, el trabajo sigue por abordar el cateto opuesto.

En primer lugar, se calcula el cateto opuesto, gracias a la función del seno. Dado que “ sen a = catetoOpuesto/hipotenusa”, podemos despejar y obtener que “catetoOpuesto = sen a * hipotenusa”. Así conseguimos almacenarlos en las variables correspondientes al cálculo interno y pintado de mensajes.

El siguiente paso es mostrar el mensaje con el valor del cateto y dibujarlo siguiendo el mismo ejemplo que en los casos anteriores, salvo que el ángulo de dirección del “bolígrafo virtual” deberá ser 180º, es decir, hacia abajo.

Solamente nos queda trabajar con el cateto contiguo.

El cateto contiguo tiene relación con el coseno del ángulo. Así que el proceder es el mismo que para el cateto opuesto pero recurriendo a la función coseno. Con este código terminaría la programación dado el caso en que el valor obtenido del bot por la variable “bot1.position” sea 1.

Veamos el resultado de nuestro trabajo:

 El procedimiento para programar los casos del resto de valores proporcionados por el bot en cuanto a su posición sería el mismo, sólo que modificando el ángulo perteneciente al caso en concreto en el que nos encontremos.

Puedes ver el código fuente aquí.




Also in Aisoy Blog

Aisoy welcomes North American Learning Robots, our new official distributor in the US.
Aisoy welcomes North American Learning Robots, our new official distributor in the US.

March 06, 2017

North American Learning Robotics is now the exclusive official distributor of Aisoy products in the US.

Aisoy, is a Spanish manufacturer of emotional educational robots which favor creativity and the development of multiple intelligences in a personalized way is ready to conquer the American market.

Read More

Aisoy wishes you a happy 2017
Aisoy wishes you a happy 2017

December 23, 2016

Every year has 365 days plenty of opportunities for enjoying life, with your family, with your friends, and why not, with a new robot that has come to our life and make us smile.

Read More

Aisoy is highly committed to children's education, particularly to children with special needs

October 29, 2016


New Friends 2016

Aisoy creates emotional robots for changing the way children play and learn. And makes them affordable for everyone. Since the first day, we participate and collaborate with people and initiatives aligned with us.

Read More