VPN1513 Smart Mode with Arduino Mega 2560
dchapma6
Posts: 4
Hi - I have seen many articles on trying to get Smart Mode working. I have connected a 1n914 diode between Tx & Rx pointing toward Tx with Rx connected to SIO. I am using the Serial3 port on the Mega 2560 and I can see my !GPSn command echoed back but no response from the SIO port. If I pull /RAW low, I see the streams of raw data coming out of SIO so that half works. I see reference to a level problem trying to drive the commands into the SIO port. If I need a level shifter, what do I use and how do I mux Rx & Tx in that case? Help or pointing to a reference would help. Thanks. Dean
Comments
Are you attempting to use the diode for the voltage drop? Do you have a schematic?
My understanding is that the Arduino is a 5V part and that the VPN1513 is 3.3V - data returning from the GPS unit to the arduino, if passing through a diode, might not be high enough voltage to register - try a 1K inline resistor instead from the SIO to Rx on GPS and have the Tx to SIO be a simple wire. (Assuming you aren't trying to share the same pin for Rx and Tx)
Is your 'echo' really coming back from the GPS unit or is your terminal program echoing? (Need to ensure serial coms are correctly configured)
Sample code (Arduino 1.0):
Try that.
-- Gordon
The VPN1513 is a 5V part (actually 4.5 to 12V; it has its own 3.3V regulator for the onboard Propeller and GPS receiver). There is a 1K resistor inline with SIO, so another is not needed. Because the Arduino does not have open collector I/O, and the VPN1513 has a single pin for Tx and Rx, some simple half-duplex steering is needed to connect to the two serial pins. Thus the resistor and diode, as shown in the previous illustration.
-- Gordon
Dean
Dean
I was debating on whether or not I should start a new thread or not. I decided to post here, in hopes that Dean or Gordon are subscribed to this thread already and can provide help.
I have a VPN1513 GPS module hooked up to a Mega. I did the same thing Dean mentioned, I have Rx going to pin 11, Tx to pin 10, and I omitted the resistor. I can get everything working very well, but I am unable to figure out how to code my Arduino to pull the heading. I think I got the speed working, but the same code I used for speed doesn't seem to be working for heading.
This is driving me nuts and I can't find any VPN1513 smart mode code ANYWHERE for the Arduino, except this thread. (Thanks Gordon!!!)
I have Lat/Long, speed, validity, and number of sats working. Whatever I'm doing with my heading code seems to cause a buffer overflow or something.
Here is what I'm working with, I apologize if I should have started a new thread, but I think this is related. Can someone explain to me how the GPS module returns the speed and heading? It says 2 bytes. A byte can only be like 255 maximum, so I guess it has to use some sort of Most Significant Bit and Least Significant Bit or something like that to return the full value of speed/heading. I can't see to figure it out. Can you go into explaining a little bit about how it works, along with a code example?
Here are parts of my code pertinent to what I'm trying to do.....pieces of it are what Gordon posted.
I'm also wondering if I'm doing the speed correctly too. It seems to work, but I wonder if I go over 255 mph if that would cause a problem. I don't expect to go that fast ever, but I do want to learn how to code this correctly. Also, is it safe to assume the GPS module will only return a valid heading if you are in motion? That's why I have a little check to make sure speed is > 5.
I didn't look closely at your code but assuming that part is correct, if you're getting what looks like invalid data it could very well be the GPS isn't giving valid data. You really have to be moving for the GPS to deliver useful heading information, and even then, it's often off by several degrees. The 5 MPH you state may not be enough, or it could be sufficient but only after an accumulation of data. If you need accurate heading info you need a digital compass.
(On edit: I see a logic error in your code. You need to put all of your heading code inside the if block for >5 MPH.The way you have it all of the code after the if test runs, regardless of whether the if test is true or false. )
-- Gordon
With this, I'm just looking for a rudimentary 'compass', like you have in your car. So ideally I will just have the LCD display N/E/W/S based on the GPS heading. It doesn't have to be super accurate, or anything like that.
I should note that I'm fairly new at programming, so my question probably yields a really basic answer on how to code this.
I guess my question is, what does the GetHead parameter return? The document says 2 bytes are returned, Heading (Word). It says it is in tenths of degrees.
So AFAIK, a heading can be between 0 and 360 degrees. If you're talking tenths of degrees, what data should GetHead return if you are traveling 359.9 degrees?
Would the first byte be 255? Second byte would be what? You can't express a number higher than 255 in a byte, so I'm not understanding how even do a tenth of a degree via bytes.
if I was traveling 359.0 degrees, I would guess the first byte is 255, second byte is 104. You add the two together to get 359?
For GetHead, how many times should I be calling gps.read()? Would I call it only twice because it returns 2 bytes?
I keep looking at how you did the Lat/Long code in this thread, and I don't understand what you're doing with the minsD portion of your code. I'm so confused now
Not a very fitting avitar for these forums. You might want to consider changing it, (before the moderators do).
Don't worry why the lat/long code uses two separate several variables for returning minutes. That's simply reflects the way GPS's bundle up their data, in a format usually shown as ddmm.mmmm. The set of four m's needs to be represented by a value larger than 255, hence the need to retrieve it as two separate bytes, then combine the value into a variable type that can hold a value larger than 255.
To get heading, with is returned as two bytes, you read it twice. The code you have should be close. You've said only that the code "doesn't seem to be working for heading" but haven't elaborated what that means. How is it not working? Is there no data? Is there data but it's random? Is there data but it's always off?
If the docs say it's in tenths of degrees, the number returned will be more like 0 to 3599 (no decimal point). You can divide by 10 to get 0-359. And no, you don't add them together. You must shift the bits of the first byte as shown. Again, the code you already posted should be pretty close:
Heading = gps.read()<<8;
Heading += gps.read();
It would be helpful if you could be more specific about what the code is doing, even if it's wrong.
-- Gordon
Thanks again for the help, and for looking over my code. After much testing, I realized that the output from the GPS went wonky whenever I was stopped. When I was moving, the heading displayed correctly.
I kept thinking about it, and an hour later realized my problem. With that Speed loop, it worked great....except I was calling the sendGps(gpsType, 2) function before I checked if the Speed was > 5. So if I was moving, the two gps.read() would execute. But if I was stopped, they would not execute, and it would leave the GPS serial outputs hanging.
Anyway, here is the corrected code, I moved the sendGps(gpsType, 2) into the loop. This works great, displays last known heading if not moving. The negative heading check in the code below could be eliminated...I had that in there because of all the other problems I had with that bug
This is LAB just test communication and code 、Connected Line can normal run.but this's can'n work.
I do not know where my question.Imagine asking everyone what the problem is?
Thanks.