• Lunes 18 de Noviembre de 2024, 04:41

Autor Tema:  Comunicación Bluetooth GPS  (Leído 1641 veces)

shacklebolt

  • Nuevo Miembro
  • *
  • Mensajes: 6
    • Ver Perfil
Comunicación Bluetooth GPS
« en: Lunes 3 de Mayo de 2010, 13:01 »
0
Tengo una aplicación que debe recoger datos en tiempo real de un gps (Receptor GPS Gtop G33 NMEA-0183) a desarrollar en Visual Studio 2008. Uso un objeto serialPort para comunicarme mediante el puerto COM4 (Bluetooth) con el GPS.

Bien, mi objetivo es cada un cierto tiempo determinado conocer las coordenadas enviadas ACTUALES.

Para ello uso el evento serialPort1_DataReceived, en él leo una linea del puerto utilizando el método "serialPort1.ReadLine()" e identifico si se trata de una sentencia GGA, ya que es la sentencia en la cuál se me indica la latitud y longitud, y guardo estos datos en una variable del programa Coord, estructura creada por mí para representar una coordenada con latitud y longitud.

Pues como he dicho cada cierto tiempo voy añadiendo a una "lista de coordenadas" la variable Coord (utilizando un timer), que por lo que alcanzo a entender sería la última coordenada leída por el GPS.

Pues el problema está que no me añade en la ruta el ÚLTIMO elemento, me explico:

Yo empiezo una ruta, activo el GPS y abro el puerto del serialPort, y empiezo a tomar datos cada 4 segundos. Acabo la ruta, cierro el puerto e imprimo en un documento .xml los datos de la lista de coordenadas. Pues en esa lista no me recoge ni la cuarta parte de puntos de esa ruta!!

me recoge un montón de puntos del sitio inicial y luego muy poco a poco va siguiendo la ruta y se para a menos de la mitad...

el problema está claro que está a la hora de añadir datos a la lista de ruta, es como si la variable nuevopunto tuviera memoria y me fuera añadiendo a la ruta TODOS los puntos recogidos por el GPS y no el último como quiero yo añadir. No encuentro ninguna explicación a esto.

Aquí el código del evento "Datos recibidos por el GPS"
Código: C#
  1. private void serialPort1_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
  2.         {
  3.              string aux1 = "";
  4.                 if (serialPort1.IsOpen == true)
  5.                 {
  6.                     string aux = serialPort1.ReadLine();
  7.                     // Detectamos que es una trama GGA
  8.                     foreach (char c in aux)
  9.                     {
  10.                         if (c != ',')
  11.                         {
  12.                             aux1 += c.ToString();
  13.                         }
  14.                         else
  15.                         {
  16.                             break;
  17.                         }
  18.                     }
  19.                     if (aux1 == "$GPGGA") // Esto nos indica que se trata de una trama GGA
  20.                     {
  21.                            TrataGGA(aux);  // Aquí desmenuzo la trama obteniendo la longitud y latitud actuales y la guardo en una variable global coordenada
  22.                     }
  23.                 }
  24.         }
  25.  
  26. private void TrataGGA(string trama)
  27.         {
  28.             sexagesimal lat_new = new sexagesimal(g1, m1, s1);  // sexagesimal es una clase con dos enteros y un double (grados, minutos y segundos)
  29.             sexagesimal lon_new = new sexagesimal(g2, m2, s2);
  30.             nuevopunto = new Coord(lat_new, lon_new);  // aqui sobreescribo la variable "Coord nuevopunto"
  31.        }
  32.  
  33.  

Aquí el código del evento del timer.

Código: C#
  1. private void timer1_Tick(object sender, EventArgs e)
  2.         {
  3.             ruta.Add(nuevopunto);  // nuevopunto es una variable Coord y ruta una List<Coord>
  4.             // Se supone que nuevopunto tendría recogido el último valor latitud y longitud pero no es así...
  5.         }
  6.  

Y aquí los eventos de los botones:
Código: C#
  1.  
  2. private void button1_Click(object sender, EventArgs e)  // Aquí el botón que empieza la ruta
  3.         {
  4.             if (serialPort1.IsOpen == false)
  5.             {
  6.                 serialPort1.Open();
  7.                 timer1.Interval=Convert.ToInt32(textBox1.Text)*1000;  // Capturo de un textBox los segundos de intervalo de recogida de cada punto
  8.                 timer1.Enabled = true;  // Activo el timer.
  9.                 MessageBox.Show("Puerto Abierto", "Operación iniciada");
  10.             }
  11.         }
  12.  
  13.         private void button2_Click(object sender, EventArgs e)
  14.         {
  15.             if (serialPort1.IsOpen == true)
  16.             {
  17.                 serialPort1.Close();
  18.                 timer1.Enabled = false;
  19.                 MessageBox.Show("Puerto Cerrado", "Operación finalizada");
  20.             }
  21.             GuardaXml();  // Aquí vuelvo los datos de la estructura ruta en un documento xml
  22.         }
  23.  
  24.  

Bueno espero no haberme extendido demasiado gracias de antemano por las respuestas.

shacklebolt

  • Nuevo Miembro
  • *
  • Mensajes: 6
    • Ver Perfil
Re: Comunicación Bluetooth GPS
« Respuesta #1 en: Lunes 3 de Mayo de 2010, 13:40 »
0
He estado haciendo pruebas y creo que el problema está en la comunicación. Me parece que recojo los datos muy poco a poco en comparación a como me los envía el GPS.

Hay alguna manera de que sólo recoja los últimos datos que me envía el GPS y no recoger uno a uno todos los datos? ya que de esta manera se ralentiza mucho la aplicación a la hora de representar dichos datos.

shacklebolt

  • Nuevo Miembro
  • *
  • Mensajes: 6
    • Ver Perfil
Re: Comunicación Bluetooth GPS
« Respuesta #2 en: Lunes 3 de Mayo de 2010, 23:58 »
0
Bueno por si alguien le interesa esto en adelante encontré yo mismo la solución.

El tema estaba en el método de lectura, he modificado el evento DataReceived del serialPort y lo dejé de esta manera.

Código: C#
  1.  
  2. private void serialPort1_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
  3.         {
  4.             /*El método ReadExisting() devuelve un string con todo lo que hay en el buffer de entrada y
  5.             Datos_Recibidos es una variable global string que como veis se sobreescribe cada vez que ocurre el evento.
  6.              Además limité el tamaño del buffer de lectura de serialPort a 128 bytes para que sólo estuvieran más o menos la últimas tramas.*/
  7.             Datos_Recibidos = serialPort1.ReadExisting();
  8.         }
  9.  
  10.  

y luego ya en el evento timer es cuando trato los datos_recibidos y miro si se trata de una sentencia GGA y muestro los datos.

Código: C#
  1.  
  2. private void timer1_Tick(object sender, EventArgs e)
  3.         {
  4.             string aux1 = "";
  5.             foreach (char c in Datos_Recibidos)
  6.             {
  7.                 if (c != ',')
  8.                 {
  9.                     aux1 += c.ToString();
  10.                 }
  11.                 else
  12.                 {
  13.                     break;
  14.                 }
  15.             }
  16.             if (aux1 == "$GPGGA")
  17.             {
  18.                TrataGGA(Datos_Recibidos);  // En este método saco latitud y longitud y lo muestro.
  19.             }
  20.         }
  21.  
  22.  

Bueno pues la verdad que no soy capaz de entender al 100% como envia las sentencias el GPS por el puerto serie COM4 pero el caso es que de esta manera sí que obtengo los últimos datos enviados.