miércoles, 7 de julio de 2010

Sun tracking mini edition

Oh hi!, ayer miré al "motor paso a paso", el me miró a mi y coincidiendo que yo llevaba un panel solar en mis manos, se me ocurrió una idea absurda con la que unir ambas cosas. Nada más y nada menos que un super inutil buscador del sol, como los lindos girasoles que hay en los campos.

Lo que más me costó fué ingeniarmelas para poner el panel en el motor, pero al final di con la solución gracias a la parte de goma que tienen los bolis estos caros. he aki una foto de lo bien que encaja.



El motor y las demás piezas las he encajado en un carton para que no se muevan, que sinó, vaya fiesta.

En cuanto al control del motor, he seguido el mismo esquema que en el post anterior.



He tenido que hacerme unas funciones nuevas específicas para girar el motor una cantidad determinada de grados.

La energia del motor la saco de la salida de 5v del arduino, pero tambien se podría meter una fuente externa, o si pusieramos mas paneles , alimentarse a si mismo y al arduino.

En cuanto a la placa solar, he conectado el cable positifo la entrada analogica 0 y la otra a tierra, y así puedo leer la cantidad de energia que pilla la plaquita.

Una vez montado todo esto, gracias a un superelavorado algoritmo , XD , podremos hacer que el panel gire hacia donde haya más luz. Increíble xD

Aki el algoritmo para el arduino


int motorPin1 = 8;
int motorPin2 = 9;
int motorPin3 = 10;
int motorPin4 = 11;

int angle = 90;
float val = 0;

int step = 0;

void derecha(int delayTime,float angulos){
//96 pasos de 3,75 grados son 360 grados
if (angulos + angle > 180) return;
angle = angle + angulos;
angulos = angulos / 3,75;
for (int i=0; i < angulos ; i++) {
digitalWrite(motorPin1, step==0?HIGH:LOW);
digitalWrite(motorPin2, step==1?HIGH:LOW);
digitalWrite(motorPin3, step==2?HIGH:LOW);
digitalWrite(motorPin4, step==3?HIGH:LOW);
delay(delayTime);
step = (step+1)%4;
}
}

void izquierda(int delayTime,float angulos){
//96 pasos de 3,75 grados son 360 grados
if (angle - angulos < 0) return;
angle = angle - angulos;
angulos = angulos / 3,75;
for (int i=0; i < angulos ; i++) {
digitalWrite(motorPin4, step==0?HIGH:LOW);
digitalWrite(motorPin3, step==1?HIGH:LOW);
digitalWrite(motorPin2, step==2?HIGH:LOW);
digitalWrite(motorPin1, step==3?HIGH:LOW);
delay(delayTime);
step = (step+1)%4;
}
}

void buscabusca(){
float der = 0;
float izk = 0;
float now = 0;
int last = 0;

val = analogRead(0); // lee el valor de tensión del pin
val = val * 6 / 1300;
Serial.println(val);
for(;;) {
now = analogRead(0);
if (last > 0){
derecha(55,5);
der = analogRead(0);
Serial.print("der");
Serial.println(der);
if (abs(der - now)<3) delay(1000);
if (der > now) last = 1;
else last = 0;
} else {
izquierda(55,5);
izk = analogRead(0);
Serial.print("izk");
Serial.println(izk);
if (abs(izk- now)<3) delay(1000);
if (izk > now) last = 0;
else last = 1;
}
}
}

void setup() {
pinMode(motorPin1, OUTPUT);
pinMode(motorPin2, OUTPUT);
pinMode(motorPin3, OUTPUT);
pinMode(motorPin4, OUTPUT);

Serial.begin(9600); // Inicialización del modulo Serial.

}

void loop() {
buscabusca();
}



Como vemos , la lectura del panel, se hace por el pin analogico 0 , y los pines digitales 8,9,10,11 los usamos para mover el estepper.

El programa muestra por el puerto serie información sobre lo leido , por si hay ke debugear. XD

Subiría un video de como se mueve pero ya mejor ke lo averigue cada uno.

Aunque si tuviera que poner un video pondría uno que he visto por youtube que se parece bastante a esto pero en mayor escala xDD


domingo, 4 de julio de 2010

Motor paso a paso con arduino

Esta tarde he desmontao un scanner viejo que tenía por ahi y me he encontrado dentro con esto:


Tachaaann!! que coño es esto? verdad?

pues ya me sonaban un poco asi de oidas lo de los stepper motor , o en castellano, motores paso a paso (PaP).

He investigado por ahi los tipos de motores y resulta que estos tipos de motores funcionan como si tuvieran 4 imanes dentro, uno a sus 12 otro a las 3 , 6 y 9, osea, norte sur este y oeste. Entonces dependiendo de el iman que esté encendido es un paso u otro.

Por ejemplo, para darle una vuelta a este motor, tendríamos que encender el motor del norte, solo, luego el del este solo, luego el del sur solo y por ultimo el del oeste solo, y norte again.

voy a robar unas imagenes explicativas que me han gustao xDD









y si queremos girar en sentido opuesto pues imagina, los enciendes en el otro sentido.

También se puede hacer los giros en lugar de en 4 pasos, en 8 encendiendo tambien 2 imanes a la vez, lo cual hace que se quede en medio del A y B por ejemplo

Bueno lo básico ya está claro, si tienes más interés en los motores puedes verlo en este link:
http://www.x-robotics.com/motorizacion.htm

Seguimos, el tema es que una vez desmontado, te vienen 5 cables y no tienes ni idea de para que es cada uno xDD

En mi caso me venían 4 seguidos y uno separado, usando la lógica, el separado es para meterle los voltios y los otros cuatro son para controlar los cuatro imanes ke lleva. Así que si hay ke controlar cosas, que mejor que el multiusos chip ULN2003 que también nos había servido para el ambilight casero.

He usado las primeras 4 patillas del chip para los cuatro cables de control y están conectadas a los pines 8, 9, 10,11. El de voltaje no va enchufado al chip, pero lo enchufaremos más tarde directamente a los 12v de una fuente.



Como se vé los colores amarillo, negro, naranja y marron son de control y el rojo es el del voltaje.
según la especificación del motor el motor se le supone ke va con 24v, pero con 12v o incluso con 5 a mi me ha ido a la misma velocidad...




Para terminar de hacer la gracia , he puesto el motor donde estaba y ahora manejo el carrusel del scaner con el arduino xDDD, la verdad esque me esperaba poder ponerle más velocidad, pero es lento de cojones... aunque bastante potente.


Ah!, por último el código del arduino para hacer maravillas con este motor xDD

PD: mi motor en concreto tiene un giro de 3 grados por cambio de fase

Step Angle
3.75º/step

eso pone en la DATASHEET xDD

osea que por ejemplo para dar una vuelta entera deberemos cambiar de fase unas 360 / 3,75 = inicio, ejecutar, calc y nos dá un resultadod de 96 cambios

en el codigo voy a hacer dos funciones, una que de una vuelta pa un lao y otra ke haga exactamente lo contrario.




int motorPin1 = 8;
int motorPin2 = 9;
int motorPin3 = 10;
int motorPin4 = 11;

int step = 0;

// Up Down Left Right


void derecha(int delayTime,int vueltas){
//96 pasos de 3,75 grados son 360 grados

vueltas = vueltas * 96;
for (int i=0; i < vueltas ; i++) {
digitalWrite(motorPin1, step==0?HIGH:LOW);
digitalWrite(motorPin2, step==1?HIGH:LOW);
digitalWrite(motorPin3, step==2?HIGH:LOW);
digitalWrite(motorPin4, step==3?HIGH:LOW);
delay(delayTime);
step = (step+1)%4;
}

}

void izquierda(int delayTime,int vueltas){
//96 pasos de 3,75 grados son 360 grados

vueltas = vueltas * 96;
for (int i=0; i < vueltas ; i++) {
digitalWrite(motorPin4, step==0?HIGH:LOW);
digitalWrite(motorPin3, step==1?HIGH:LOW);
digitalWrite(motorPin2, step==2?HIGH:LOW);
digitalWrite(motorPin1, step==3?HIGH:LOW);
delay(delayTime);
step = (step+1)%4;
}

}


void setup() {
pinMode(motorPin1, OUTPUT);
pinMode(motorPin2, OUTPUT);
pinMode(motorPin3, OUTPUT);
pinMode(motorPin4, OUTPUT);
}

void loop() {
derecha(2,1);
izquierda(2,1);
derecha(3,1);
izquierda(3,1);
derecha(4,1);
izquierda(4,1);
derecha(5,1);
izquierda(5,1);
}



Y este codigo hace una vuelta pa un lao y otra pa otro xDD lo mas rápido posible, ya que si le metes un delay de 1 se vuelve loco y no se mueve xDDD

OJO! Las funciones se llaman up down left y right, pero no significa que el up sea pa arriba y right sea derecha, tendría que cambiar los nombres, para hacer funciones para girar 90 grados, osea 6 cambios seguidos.

Ah están hechas las funciones de los pasos diagonales, si hicieramos los 4 pasos solo con diagonales el motor sería mas powerfull ya que el motor gira con la fuerza de dos imanes por paso.


Fuentes:
http://www.mitsumi.co.jp/latest/Catalog/compo/motor/m42sp4_e.html
http://www.x-robotics.com/motorizacion.htm
http://www.arduino.cc/en/Tutorial/StepperUnipolar


Ambilight casero para PC

Holas, aquí va el segundo tema util que hacer con arduino. En este caso montaremos un ambilight casero con las tiras de leds RGB del IKEA. Personalmente no recomiendo comprarlas, no porque sean malas, todo lo contrario, funcionan perfectamente, pero son un pelin caras para mi gusto.

Hay otra alternativa en Dealextreme, más económica, y servirá perfectamente.

Hardware

Las tiras de leds que tengo son así:


Cada tira tiene 4 conectores, uno para cada canal R, G y B (Rojo, Verde y Azul) y un cuarto por donde le entran los 12v que pide.

Tenemos que fijarnos si hay alguna leyenda por las tiras donde lo indique ya que en mi caso, el orden está cambiado y es RBG en lugar de RGB, la W será de power.



En cuanto al circuito necesario para que funcione la cosa, aquí pongo un esquema hecho a mano para que quede clara la cosa.



Como se puede apreciar, usamos un chip ULN2003 para controlar la potencia que pasa por los distintos canales.

Este chip soporta bien los 12v pero está limitado a 0.5A de salida, así que asegurate que las tiras de leds no consumen más de eso si no quieres salir ardiendo XDD

El resto es simplemente conectar a las salidas PWM de arduino por un lado y por el otro a las tiras de leds.

Los 12v se los meteremos a ambas tiras directamente por su pin.

Las X marcadas significa que no se usan.

Una vez montado en una placa prototipo o en un proto shield (como es mi caso) nos quedará algo como esto



El interruptor y las resistencias y tal podeis ignorarlas porque no son parte de esto, solo son para poder resetear el arduino con el shiel montado



Software

En cuanto a la parte de programar el arduino, debemos cargar el siguiente programa:

// This sketch translates Boblight commands to control RGB LEDs via PWM.
// Implements LTBL serial protocol (http://blogger.xs4all.nl/loosen/articles/420470.aspx)
// 2009-11-27 (c) Szymon Kobalczyk (http://geekswithblogs.net/kobush/)
// http://opensource.org/licenses/mit-license.php

#define DEBUG 0 // set to 1 to send debug to SoftSerial (2,4)

#define checkByte1 0x55
#define checkByte2 0xAA

int ledPin = 13; // debug led

#define channelCount 6
word channels[channelCount]; // holds current color values
int channelPins[channelCount] = { 6, 3, 5, 11, 9, 10 }; // PWM pins to control LED strips (2x RGB)

#if DEBUG
#include
int rxPin = 2;
int txPin = 4;
NewSoftSerial xSerial(rxPin, txPin);
#endif

void setup() {
digitalWrite(ledPin, HIGH); // say we're alive

Serial.begin(9600); // open serial

#if DEBUG
xSerial.begin(57600);
xSerial.print("[boblight] ");
#endif

for (int i =0; i < channelCount; i++)
{
channels[i] = 0; // reset all channels
pinMode(channelPins[i], OUTPUT); // setup channel pin
}
setLight();

#if DEBUG
xSerial.println("Setup finished.");
#endif

digitalWrite(ledPin, LOW);
}

void loop()
{
// continuously looks to the serial port
// if there is data it processes it
pollSerialPort();
}

void setLight() {
word val;
byte high, low;
for (int i=0; i < channelCount; i++)
{
val = channels[i];
high = val >> 8;
//low = val & 0xFF;
analogWrite(channelPins[i], high);

#if DEBUG
xSerial.print(channelPins[i]);
xSerial.print(":");
xSerial.print(high, DEC);
xSerial.print(" ");
#endif
}
#if DEBUG
xSerial.println();
#endif
}

// process incoming data
void pollSerialPort() {
int data;
if (Serial.available() >= 4) { // if at least 4 bytes are in the buffer
data = Serial.read();
echo(data);
if (data == checkByte1) { // check first prefix byte 0x55
data = Serial.read();
echo(data);
if (data == checkByte2) { // check second prefix byte 0xAA
digitalWrite(ledPin, LOW); // signal prefix recognized
data = Serial.read();
if (data < 127)
readChannels(data);
else
readCommand(data);

return;
}
}
// error
digitalWrite(ledPin, HIGH); // signal unrecognized sequence
}
}

void echo(int data) {
#if DEBUG
xSerial.print((byte)data, HEX);
xSerial.print(" ");
#endif
}

void readChannels(int startChannel) {
int numChannels = Serial.read();

// wait for all data to come in (expecting 2 bytes per channel)
while (Serial.available() < numChannels * 2)
delay(10);

#if DEBUG
xSerial.print("SET: ");
// xSerial.print("Reading channels ");
// xSerial.print(startChannel, DEC);
// xSerial.print(" ");
// xSerial.print(numChannels, DEC);
#endif

byte high, low;
word val;
for (int i = 0; i < numChannels; i++)
{
high = Serial.read(); // echo(high);
low = Serial.read(); // echo(low);
val = word(high, low);

if (startChannel+i < channelCount)
channels[startChannel+i] = val;

#if DEBUG
xSerial.print(high, DEC);
xSerial.print(" ");
#endif
}

#if DEBUG
xSerial.println();
#endif

// apply changes
setLight();
}

void readCommand(int command) {
int numBytes = Serial.read();

#if DEBUG
xSerial.print("Reading command ");
xSerial.print(command, HEX);
xSerial.print(" ");
xSerial.print(numBytes, DEC);
#endif

if (command == 0x81) // request current values
{
requestValues();
}
else if (command == 0x83) // open light
{
setLight();
}
else if (command == 0x84) // close light
{
for (int i =0; i channels[i] = 0; // reset all channels
}
setLight();
}

#if DEBUG
xSerial.println();
#endif
}

void requestValues()
{
int startChannel = Serial.read();
int numChannels = Serial.read();

#if DEBUG
xSerial.print(" request current values ");
xSerial.print(startChannel, DEC);
xSerial.print(" ");
xSerial.print(numChannels, DEC);
#endif
Serial.print(checkByte1, BYTE);
Serial.print(checkByte2, BYTE);

if (startChannel >= channelCount || numChannels <=0)
{
// no data to send
Serial.print(0, BYTE);
Serial.print(0, BYTE);
}
else
{
numChannels = min(channelCount - startChannel, numChannels);
Serial.print(startChannel, BYTE);
Serial.print(numChannels, BYTE);

byte high, low;
word val;
for (int i=startChannel; i < startChannel + numChannels; i++)
{
val = channels[i];
high = val >> 8;
low = val & 0xFF;
Serial.print(high, BYTE);
Serial.print(low, BYTE);
}
}
}


Eso por parte de arduino.

Por otra parte debemos configurar un programa llamado boblight en el pc, que es el que se encarga de mirar los colores que hay en la pantalla e indicarle al arduino por el puerto serie cuales debe mostrar por las tiras de colores izquierda y derecha.
El programa consta de 2 ejecutables, uno rojo y otro verde, hay ke ejecutar el rojo y luego el verde.

El punto interesante aquí es el fichero de configuración boblight.conf. En este fichero deberemos configurar lo siguiente:


[device]
name ambilight
type LTBL
output "com11"
rate 9600
channels 6
interval 10000
Como vemos, yo lo tengo configurado para que se comunique con el arduino por el com11, este habrá que cambiarlo al que uses. Puedes saber cual usas desde el compilador de arduino, Tools > Serial port.

En cuanto al resto de fichero, podemos trastearlo también un poquito para que nuestro ambilight tenga unos colores más parecidos a los de la pantalla, por ejemplo:


[color]
name red
rgb FF0000
gamma 1.0
adjust 1.0
blacklevel 0.0


En este texto configuramos tanto el color Rojo como sus intensidades, a veces puede ser que la tira de leds se vea demasiado rojizo y podemos ajustarlo bajandole el adjust, 1.0 = 100% de potencia, así si le keremos bajar un poco ponemos 0.8 o así

Otro punto interesante son los dos últimos trozos


[light]
name left
color red ambilight 1
color green ambilight 2
color blue ambilight 3
hscan 0 50
vscan 12 88

[light]
name right
color red ambilight 4
color green ambilight 5
color blue ambilight 6
hscan 50 100
vscan 12 88


hscan es el la superficie horizontal que vamos a tomar referencia para esa tira de colores, y la vscan es la superficie vertical. En el caso de la primera luz, estamos tomando del 0% al 50% de la pantalla en horizontal, y del 12% al 88% en vertical ( el vertical está recortado para que no tome en cuenta las barras negras de las películas).

Una vez montado todo, cualquier cosa que tengas en la pantalla estará representado por el ambishield, aunque sea el propio escritorio.

Link de mi boblight aqui.
http://www.megaupload.com/?d=7A8RMLFX

Os porngo un video robado de otra persona para que veais como queda.

sábado, 3 de julio de 2010

Enfriando la fonera

Ayer me decidí a trastear la maravillosa fonera que tenía ahi sin usar, y pensé, voy a tunearla para conectarla al arduino, y así me ahorro tener un wifi y ethernet shield.

La cosa iba bien , estuve buscando información y tal. Hay bastante información de hacer esto por ahí, pero el tema es que tuve que ir tomando cachitos de varios sitios para poder montarlo todo.

Ah , y cuando lo tenía todo montado, me daba cosa tener la fonera encendida más de 1 hora porque las temperaturas que alcanzaba eran tremendas, así que busqué por ahi y tb solucioné el tema de la temperatura.

Pondré los pasos que he seguido para tener la cosa ya montada:

Flashear la fonera

Este paso no tiene mucha complicación ya que solo es seguir un tutorial que hay por ahi para instalarle el dd-wrt

Podeis encontrarlo aki :
http://www.dd-wrt.com/wiki/index.php/LaFonera_Software_Flashing

Como comentario diré , que tardé unas horas largas

Mi fonera en concreto es la vieja, la primer, el modelo 2100, y encima cuando la resetee, llevaba el firmware 0.7.1 r1 por lo tanto me tocó la via facil.

Lo que mola esque ahora que la tengo ya
flasheada, puedo acceder a ella facilmente por el putty (192.168.1.1) y tener un shell ahi a mi disposicion

PD: como dato extra, para acceder por ssh, te puedes rayar bastante, porque el login y pass es simplemente login: root, y contraseñ
a la que tengas configurada en la administración del router.
Digo esto porque yo le cambié la pass a la fonera, yaque las que venían por defecto (root/admin) eran muy evidentes, y le puse (arduino/arduin
o), pues por ssh, aunque el user sea arduino hay ke entrar como root...

Una vez hecho esto, cuando accedo por el navegador al 192.168.1.1 me sale la administración del dd-wrt, y yastá listo. Supongo que pa
ra que el arduino se conecte a internet, deberémos configurar la fonera para ke sea cliente de otra wifi, pero eso ya lo veremos otro dia xD.

Sacar cables

Para que el arduino se conecte con la fonera , irremediablemente deberá estar conectada a esta mediante cables, puesla cosa está bien sencilla.




Abrimos la fonera y buscamos estos pines, sólo necesitaremos 4 de ellos , aunque el de lso 3,3v no se usa para nada pero puede servir xDD.

El Tx y el Rx se conectan al Tx y Rx del arduino, según he leido por ahi, a veces es al reves, el T al T y el R al R o de la otra forma, es cuestión de probar.

Para facilitar la conexión me he pillado un par de cables que ya tenían sus conectores hembra, pero como era demasiado largo he tenido ke doblar las patas como se ve en la imagen para que quepa.


La verdad esque una vez montados los cables, han kedado bastante bien.




A la derecha se puede ver el conector que he hecho para pichar en el arduino, de los otros dos cables solo se necesita enchufar al arduino el de tierra.


Enchufarle un ventilador

Como el problema de temperatura era palpablemente evidente, ponerle un ventilador es necesario si no queremos tener riesgo de incendio... yo lo he montado así

buscamos los 5v de la placa y le soldamos un par de cables ahi para la alimentación del ventilador. Por cierto, el ventilador lo he pillao de 5v, ke los de 12 van muy lentillos aa 5v




Una vez sacados los cables los soldamos con los del ventilador y listo, en mi caso, un dia se me ocurrión la inteligente idea de ponerle un antirobo a la fonera, cosa que no me ha venido bien ahora porque el espacio para el ventilador es escaso, peeeero, cosas del karma, he pillado un ventilador perfecto tanto por espacio como por disposición de este en la fonera, ya que pilla justo encima del minidisipador que tiene XDDD




Si, el recorte del bujero es super cutre, pero da igual, funciona perfectamente

XDD

Tachannn!!!




Ahora sólo queda la parte del arduino ya que la fonera no hay ke tocarle ya nada hardware. lista y en marcha

PD: la fonera está fria. xDD

Fuentes:

http://www.dd-wrt.com/wiki/index.php/LaFonera_Software_Flashing



http://www.dd-wrt.com/wiki/index.php/LaFonera_Hardware_Cooling-System



http://www.sherkhan.net/blogs/frikadas/?p=420

viernes, 2 de julio de 2010

Presentación del blog

Hola, este blog, tendrá como misión la recopilación detallada de las diversas chorradas o ingenios que logremos con nuestros arduinos. Somos un grupo de amigos los que iremos publicando entradas aquí e intentaremos que las cosas queden bien detalladas por si en un futuro se nos olvida como hicimos tal y cual... Saludos!