Simple Arduino XY Plotter

11,896

59

41

Posted in TechnologyArduino

Introduction: Simple Arduino XY Plotter

About: Músico, matemático, computación, ciencia... insolente y subversivo, pero siempre propositivo

En este instructable aprenderemos a construir un sencillo plotter XY, es decir, con dos servos controlaremos movimientos XY en un plano.

Para hacerlo, debemos entender un poco de la ley de cosenos, el manejo de entradas seriales al Arduino, y el manejo de servos.

El resultado es un plotter que funciona, pero que definitivamente tiene mucho espacio para mejorarlo, calibrarlo y hacerlo que funcione un poco mejor.

Step 1: Materiales

Ocupamos:

  1. Arduino UNO
  2. Breadboard
  3. 2 x servo motores
  4. cables
  5. 3 x paletas de helado
  6. Tiras de plástico

Step 2: Ensamblado

Vamos a utilizar las paletas de helado para poder armar los "brazos" del plotter. Como se muestra en la fotos simplemente se utilizan para pegar un servo al otro, amarrándolos con tiras de plástico. Luego se pueden acomodar los brazos para que ambos queden en posición 0 (o 180)

Step 3: Conexiones

Las conexiones son sencillas. Conectamos 5V y GND ald "+" y "-" del breadboard, para poder alimentar de poder los dos servos.

Los servos, se conectan al "+" y "-" del breadboard. En la foto se ven como cables rojos, cada motor necesita conectarse. Luego, el cable anaranjado, se conecta a los pines 7 y 8. El del pin 7 será nuestro servo1 que va en la base y el pin 8 será nuestro servo2.

Step 4: Ley De Cosenos

En trigonometría, la ley del coseno (fórmula o regla del coseno), establece una relación entre los lados de un triángulo, y uno de sus ángulos. Es una generalización del teorema de Pitágoras, ya que se aplica a cualquier triángulo. Cuando trabajamos con servos y cualquier tipo de brazo robótico, esta fórmula es extremadamente útil, ya que podemos calcular cualquier ángulo, conociendo simplemente los catetos, y es este precisamente el problema que enfrentamos.

La fórmula se muestra en la foto de forma gráfica. Adicionalmente, hay otra foto que lo compara con el brazo con dos servos que acabamos de armar. Queremos mover el brazo a una posición, simplemente al darle las coordenadas x,y. Es decir, dado un punto (x,y), queremos calcular cual será el ángulo que ambos motores deben tener.

En otras palabras. Si tenemos un triángulo con catetos a,b y c con sus ángulos opuestos A,B,C, Resolviendo para un ángulo A, cuyo cateto opuesto es a, tenemos:

cos A =( b^2 + c^2 - a^2 )/(2*b*c)

El símbolo "^" lo utilizo acá como "elevado a". Conocemos todos los catetos. En este caso, digamos que b y c son las paletas de helado, cuyo tamaño conocemos. El cateto a es el que que va desde el origen, hasta el punto al que queremos llegar. Muy fácil de calcular, pues si el origen es (0,0), y queremos medir la distancia a (x,y), entonces sabemos que a^2 = x^2 + y^2, por el teorema de Pitágoras.

Todas estas fórmulas se programan casi de forma directa en el código del Arduino. Pasemos ahora al código

Step 5: Código

El código acá es bastante sencillo. Lo primero es que cargamos la librería math.h. Esta incluye varias funciones trigonométricas, incluyendo acos y atan, que vamos a utilizar. Luego en el setup() simplemente asignamos el pin al servo (si quiere aprender más sobre el servo puedes seguir este instructable).

El ćodigo tiene dos elementos importantes:

  1. conexión serial
  2. funciones de movimiento y ley de cosenos

Lectura del puerto serial

En la líneas 29 a 30 del código:

if (Serial.available() > 0){
posX = Serial.parseInt();
posY = Serial.parseInt();
}

Por el puerto serial, vamos a enviar al Arduino las coordenadas como pares x,y separados por coma. La función parseInt(), permite leer del puerto serial cana elemento separado por coma. Al ejecutarlo por primera vez, lee el primero, hasta la coma, al ejecutarlo la segunda, lee inmediatamente después de la coma el siguiente y así. En este caso, leemos una primera vez y almacenamos en la variable global posX, y la segunda en posY, así entonces utilizamos luego en la línea 38, la función para calcular los ángulos y mover los servos.

Funciones

Creamos tres funciones importantes (acá hay un instructable sobre funciones). La primera que llamamos getAngle():

float getAngle(float a, float b, float c) {
return acos((square(b) + square(c) - square(a)) / (2 * b * c));
}

Que es simplemente la fórmula que explicamos en el paso anterior para calcular el ángulo usando la ley de cosenos.

La siguiente función es:

void armTo(float x, float y) {
float h = sqrt(square(x) + square(y));
//calculates angles based on desired point
float a1 = (getAngle(ARMLENGTH, ARMLENGTH, h) + atan2(y, x));
float a2 = (getAngle(h, ARMLENGTH, ARMLENGTH));
moveServo(a1, a2);
}

La cual es la que calcula, usando la ley de cosenos, los dos ángulos que ocupamos. Los ángulos los almacenamos en a1 y a2. Noten que a a1, le sumamos atan2(x,y), ese es el ángulo que hay desde la linea del horizonte hasta el punto, que hay que sumarle al ángulo del servo1.

La función moveServo, simplemente mueve los servo motores, convirtiendo los ángulos de radianes a grados que es lo que ocupa la función write() de los servos. esta función se puede mejorar muchísimo, para hacer mover los motores de apoco hacia el ángulo deseado... eso se los dejo de tarea.

Step 6: Funcionando Y Más

Listo. Abra el puerto serial, y desde la línea de comando puede enviar pares ordenados x,y para hacer mover el brazo a ese punto.

Bueno, el brazo no se mueve muy bien y hay bastante que se puede mejorar. Eso se los dejo a ustedes. Algunas cosas que se pueden mejorar:

  1. Imprimir en 3D los brazos (luego publico mi versión)
  2. Mejorar la función moveServo(), para que el movimiento de los servos sea suave
  3. Agregar aceleración y desaceleración a los servos.
  4. Incluir un algoritmo que dibuje algo bonito
  5. Conectar con processing para controlar el brazo desde allí (eso lo publico luego)

Step 7: Conectando Con Processing

Para extender el control del XY plotter, podemos conectarlo con Processing (descargar acá el programa). Adjunto está el código de processing y simplemente lo pueden conectar. Utilicen el código adjunto de Arduino que utiliza serialEvent(), para recibir la información por puerto serial de processing. Acá no explico detalles del código, luego hago un instructable con más detalles.

Share

Recommendations

  • Microcontroller Contest

    Microcontroller Contest
  • Space Challenge

    Space Challenge
  • Science of Cooking

    Science of Cooking
user

We have a be nice policy.
Please be positive and constructive.

Tips

1 Questions

how can i import a picture by bluetooth using processing to the plotter

Well, in this proyect I left that open. One way is to import SVG files into processing and then have processing send every line to Arduino. This is not a simple task, since movements have to be optimized, and perhaps a pen lifter needs to be added. I think the best way is to open an image and trace it by hand in processing... hope this helps

41 Comments

Buenas, no tengo idea de Arduino, pero quiero adentrarme haciendo por ejemplo un Plotter, este me pareció bastante simple, pero no entendí como se le pasan los diseños. Supongo que será con algoritmos de Arduino, pero me pregunto si se podrá enviar diseños vectoriales como con los plotters más avanzados (obviamente el resultado no será el mismo, pero por ejemplo, hacer una letra). Saludos y muchas gracias.

1 reply

Hasta ahora veo este mensaje (un año tarde), bueno lo ideal es que toda la optimización para dibujar un diseño se resuelva en Processing, y que este simplemente mande los comandos a Arduino... Para eso probablemente es mejor usar algo como GRBL. El objetivo de este tutorial es más para enseñar a trabajar con coodenadas cartesianas

Thank Tomas! If someday in future you finished it, please let me know. Best Regards!

Thank Tomas! Install Processing and load your code and it works. Thank you very much! Do you know how to use this device to print the drawing which made by other software such as CAD DXF format ?

1 reply

It could be done with Processing. Haven't had the time to do it!

Hi Tomas, It's a great project! I have built one and tested two servos that both are ok.What is the software that you used to make the drawing? It's very appreciated to received your reply! many thanks!

2 replies

You can also try out this related project https://www.instructables.com/id/Cinem%C3%A1tica-Directa-Con-Arduino/

I'm using processing, you can donwload this sftware for free here https://processing.org/. When you have everything installed, load this code https://github.com/tomasdecamino/ProcessingStuff/blob/master/XY_Plotter/XY_Plotter.pde

Hello again ... got back after some learning , but i still cant get it to work , am having problems with aligning the arms of the servo . I tried working with proccessing in order to help me but am not making anything to work , ok so ill provide a picture and where i align with proccessing : the first image shows the paper in which am tryn to draw . What should i change in the code ? Or if its not the code i should change then what should i change ? am so confused ... and when i thought i was done ... thank you for your time .

20160520_192359.jpg20160520_192412.jpg20160520_192422.jpg20160520_192443.jpg20160520_192711.jpg20160520_192717.jpg

Para el movimiento suave de los servos, recomiendo una librería muy buena llamada : varspeedservo :)

ofrece funciones extra para la velocidad

1 reply

you know devesh kannappan and arjun devesh are same me k.devesh and arjun.t

Do something like this in your arduino,

Servo myservo1, myservo2;

void setup() {

myservo1.attach(6);

myservo2.attach(9);

}

void loop() {

myservo1.write(90);

myservo2.write(0);

}

Then fix the arms, and then load the other code

For that just move servos to 90 and 0 in the setup() code and the put the arms

The base servo, has to be in position 90, the second servo in position 0