I have problem about Dronekit on Python
My project about receive GPS Location from Android application
and Launch drone flying to that Position, Everything work fine but problem is Drone can takeoff but drone didn't go to that Location(Testing 10+ times work only 1 time)
Here is my code (I think problem is GlobalRelative)
# Import DroneKit-Python
from dronekit import connect, VehicleMode, LocationGlobalRelative
import time
import urllib2
import simplejson
import json
import requests
#Wait for json data
response = urllib2.urlopen("http://localhost:3000/posts")
data = simplejson.load(response)
print(data)
json_string = data[0]["Information"]
gps = json.loads(json_string)
x=gps['lat']
y=gps['lon']
r = requests.delete('http://localhost:3000/posts/1')
# Connect to the Vehicle.
print("Connecting")
vehicle = connect('com4', wait_ready=False, baud=57600)#; vehicle.wait_ready(True, timeout=300)
print("Connected")
# Get some vehicle attributes (state)
print "Get some vehicle attribute values:"
print " GPS: %s" % vehicle.gps_0
print " Battery: %s" % vehicle.battery
print " Last Heartbeat: %s" % vehicle.last_heartbeat
print " Is Armable?: %s" % vehicle.is_armable
print " System status: %s" % vehicle.system_status.state
print " Mode: %s" % vehicle.mode.name # settable
# Takeoff Function
def arm_and_takeoff(tgt_altitude):
print("Arming motors")
# while not vehicle.is_armable:
# time.sleep(1)
vehicle.mode = VehicleMode("GUIDED")
vehicle.armed = True
print("Takeoff")
vehicle.simple_takeoff(tgt_altitude)
# wait reach tgt_altitude
while True:
altitude = vehicle.location.global_relative_frame.alt
if altitude >= tgt_altitude -1:
print("Altitude Reached")
break
time.sleep(1)
# Main
arm_and_takeoff(10)
# Speed
vehicle.airspeed = 7
# Go to wp
wp1 = LocationGlobalRelative(x, y, 10)
# Close vehicle object before exiting script
vehicle.mode = VehicleMode("RTL")
vehicle.close()
print("Completed")
Alternative, If I can't fix this problem I want to use MissionPlanner( I test on it , and it work) But I want to wait for GPS Location from Phone, and Launch the mission( every thing must automatic ) I have no idea how to bypass MissionPlanner
The line: wp1 = LocationGlobalRelative(x, y, 10) only assign wp1 variable with a location coordinate. You can use vehicle.simple_goto(wp1). simple_goto is a built in function in dronekit to command the vehicle to specific coordinate you can read more about it here http://python.dronekit.io/automodule.html?highlight=simple_goto#dronekit.Vehicle.simple_goto
Related
I am using Python to build a script for a program to be ran by Artisan-Scope roasting software. The program already works with my device (the Phidgets 1045_1B) but I need to do more filtering on the temperature readings. I would like the program to sample at 32ms and organize those 30 samples per second in ascending order. I would then like the lowest 10 samples to be average and returned to Artisan software to be graphed.
This is what I have so far but I need help figuring out how to organize the samples and average them before giving one temperature reading to Artisan.
import sys
import time
import traceback
from Phidget22.Devices.TemperatureSensor import *
from Phidget22.PhidgetException import *
from Phidget22.Phidget import *
from Phidget22.Net import *
try:
from PhidgetHelperFunctions import *
except ImportError:
sys.stderr.write("\nCould not find PhidgetHelperFunctions. Either add PhdiegtHelperFunctions.py to your project folder "
"or remove the import from your project.")
sys.stderr.write("\nPress ENTER to end program.")
readin = sys.stdin.readline()
sys.exit()
def onAttachHandler(self):
ph = self
try:
#If you are unsure how to use more than one Phidget channel with this event, we recommend going to
#www.phidgets.com/docs/Using_Multiple_Phidgets for information
print("\nAttach Event:")
channelClassName = ph.getChannelClassName()
serialNumber = ph.getDeviceSerialNumber()
channel = ph.getChannel()
ph.setDataInterval(32)
ph.setTemperatureChangeTrigger(0)
except PhidgetException as e:
print("\nError in Attach Event:")
DisplayError(e)
traceback.print_exc()
return
def onDetachHandler(self):
ph = self
try:
except PhidgetException as e:
print("\nError in Detach Event:")
DisplayError(e)
traceback.print_exc()
return
def onErrorHandler(self, errorCode, errorString):
sys.stderr.write("[Phidget Error Event] -> " + errorString + " (" + str(errorCode) + ")\n")
"""
* Outputs the TemperatureSensor's most recently reported temperature.
* Fired when a TemperatureSensor channel with onTemperatureChangeHandler registered meets DataInterval and ChangeTrigger criteria
*
* #param self The TemperatureSensor channel that fired the TemperatureChange event
* #param temperature The reported temperature from the TemperatureSensor channel
"""
def onTemperatureChangeHandler(self, temperature):
#If you are unsure how to use more than one Phidget channel with this event, we recommend going to
#www.phidgets.com/docs/Using_Multiple_Phidgets for information
print("[Temperature Event] -> Temperature: " + str(temperature))
"""
* Prints descriptions of how events related to this class work
"""
def PrintEventDescriptions():
print("\n--------------------\n"
"\n | Temperature change events will call their associated function every time new temperature data is received from the device.\n"
" | The rate of these events can be set by adjusting the DataInterval for the channel.\n"
" | Press ENTER once you have read this message.")
readin = sys.stdin.readline(1)
print("\n--------------------")
"""
* Creates, configures, and opens a TemperatureSensor channel.
* Displays Temperature events for 10 seconds
* Closes out TemperatureSensor channel
*
* #return 0 if the program exits successfully, 1 if it exits with errors.
"""
def main():
try:
ch = TemperatureSensor()
ch.setOnAttachHandler(onAttachHandler)
ch.setDeviceSerialNumber(424909)
ch.setChannel(0)
ch.openWaitForAttachment(5000)
ch.setTemperatureChangeTrigger(0)
ch.setOnDetachHandler(onDetachHandler)
ch.setOnErrorHandler(onErrorHandler)
#This call may be harmlessly removed
PrintEventDescriptions()
ch.setOnTemperatureChangeHandler(onTemperatureChangeHandler)
try:
ch.openWaitForAttachment(5000)
except PhidgetException as e:
PrintOpenErrorMessage(e, ch)
raise EndProgramSignal("Program Terminated: Open Failed")
time.sleep(1)
return 0
except PhidgetException as e:
sys.stderr.write("\nExiting with error(s)...")
DisplayError(e)
traceback.print_exc()
print("Cleaning up...")
ch.close()
return 1
except EndProgramSignal as e:
print(e)
print("Cleaning up...")
ch.close()
return 1
except RuntimeError as e:
sys.stderr.write("Runtime Error: \n\t" + e)
traceback.print_exc()
return 1
finally:
print("Press ENTER to end program.")
readin = sys.stdin.readline()
main()
The first thing that you need is some kind of buffer to hold recorded values until you have enough of them to process them. You can for instance use a python list::
# in onAttachHandler:
# init buffer
global buffer
buffer = []
In onTemperatureChangeHandler, store the values in the buffer. Once the buffer is full, calculate your average, then pass that value on.
# in onTEmperatureChangeHandler
global buffer
buffer.append(temperature)
if len(buffer) > 30:
buffer.sort()
mean_temperature = sum(buffer[:10]) / 10.0
buffer = []
# Do something with mean_temperature here
That said, global variables as used here are considered bad style for good reasons. The code should be improved by defining a class, which has the buffer and all the handlers as attributes. There are plenty of Python tutorials about this.
I have a piece of Python Code running as a service that pulls weather data via API.
The code itself runs perfectly fine when everything is hunky dory, ie the network, but I have noticed that sometimes the WiFi on the Pi that is pulling the API data will drop and then the python codes seems to stop.
I have a small line of code providing the most basic of logs, but I would like to improve upon it greatly. The log code just provides me with the datetime.now so I can see when the last time the code ran was.
#!/usr/bin/python3
#import modules
import cymysql
from time import sleep
from urllib.request import urlopen
import json
import datetime
#set MySQl Variables
host = "localhost"
user = "xxx"
password = "xxx"
schema = "xxx"
#connect to MySQL DB
db = cymysql.connect(host, user, password, schema)
curs = db.cursor()
#set api key for DarkSky API
apikey="xxx"
# Latitude & longitude
lati="-26.20227"
longi="28.04363"
# Add units=si to get it in sensible ISO units.
url="https://api.forecast.io/forecast/"+apikey+"/"+lati+","+longi+"?units=si"
#begin infinite loop
while True:
#convert API reading to json and readable array 'weather'
meteo=urlopen(url).read()
meteo = meteo.decode('utf-8')
weather = json.loads(meteo)
#set variables for current weather
cTemp = (weather['currently']['temperature'])
cCond = (weather['currently']['summary'])
cRain1 = (weather['currently']['precipProbability'])
cRain2 = cRain1*100
cIcon = (weather['currently']['icon'])
oaSum = (weather['daily']['summary'])
#print variables - for testing purposes
#print (cTemp)
#print (cCond)
#print (cRain2)
#print (cIcon)
#print (oaSum)
#extract daily data from 'weather' array
daily = (weather['daily']['data'])
#create new arrays for daily variables
listHigh = []
listLow = []
listCond = []
listRain = []
listIcon = []
#set daily variables
for i in daily:
listHigh.append(i['temperatureHigh'])
for i in range(0,len(listHigh)):
high1 = listHigh[0]
high2 = listHigh[1]
high3 = listHigh[2]
high4 = listHigh[3]
high5 = listHigh[4]
high6 = listHigh[5]
high7 = listHigh[6]
high8 = listHigh[7]
for o in daily:
listLow.append(o['temperatureLow'])
for o in range(0,len(listLow)):
low1 = listLow[0]
low2 = listLow[1]
low3 = listLow[2]
low4 = listLow[3]
low5 = listLow[4]
low6 = listLow[5]
low7 = listLow[6]
low8 = listLow[7]
for p in daily:
listCond.append(p['summary'])
for p in range(0,len(listCond)):
cond1 = listCond[0]
cond2 = listCond[1]
cond3 = listCond[2]
cond4 = listCond[3]
cond5 = listCond[4]
cond6 = listCond[5]
cond7 = listCond[6]
cond8 = listCond[7]
for m in daily:
listRain.append(m['precipProbability'])
for m in range(0,len(listRain)):
rain1 = listRain[0]
rain2 = listRain[1]
rain3 = listRain[2]
rain4 = listRain[3]
rain5 = listRain[4]
rain6 = listRain[5]
rain7 = listRain[6]
rain8 = listRain[7]
#convert rain chance to readable percentage
prain1 = rain1*100
prain2 = rain2*100
prain3 = rain3*100
prain4 = rain4*100
prain5 = rain5*100
prain6 = rain6*100
prain7 = rain7*100
prain8 = rain8*100
for l in daily:
listIcon.append(l['icon'])
for l in range (0,len(listIcon)):
icon1 = listIcon[0]
icon2 = listIcon[1]
icon3 = listIcon[2]
icon4 = listIcon[3]
icon5 = listIcon[4]
icon6 = listIcon[5]
icon7 = listIcon[6]
icon8 = listIcon[7]
#print daily variables - for testing purposes
#print (high1)
#print (low1)
#print (cond1)
#print (prain1)
#print (icon1)
#print (high2)
#print (low2)
#print (cond2)
#print (prain2)
#print (icon2)
#update data in DataBase
try:
sql_update_query = """UPDATE weather SET current_temp = %s, cur$
varis = (cTemp, cCond, cRain2, cIcon, high1, low1, cond1, prain$
curs.execute(sql_update_query, varis)
db.commit()
except db.Error as error:
print("Error: {}".format(error))
db.rollback()
#write date to log file
with open ("/home/pi/CoRo/Projects/WeatherMan/weatherlog.txt", mode="w") as file:
file.write('Last Data was pulled at: %s' %(datetime.datetime.now()))
#set loop to sleep for 10 minutes and go again
sleep(600)
I understand that the Database Code is snipped, but it is just the variables being put in to the database, which I can see works.
However if the network disconnects, the code stops and the database is left with the last polled API data.
How would I restart the python code if the API get fails?
Thanks in advance,
You could rewrite the portion of your code that pulls the weather data as a function or separate module. This would allow you to call it only when the network connection is working. Some pseudo code below:
if network_connection:
pull_weather_data()
else:
do_something()
do_something() could be an effort to reconnect to the network, such as resetting your network adapter.
You could determine the state of the network connection by trying to ping your router or an external IP like one of Google's DNS server (8.8.8.8 or 8.8.4.4).
To avoid nested loops you could use the continue clause. For example:
while True:
if network_connection:
pull_weather_data()
else:
reset_network_connection()
time.sleep(180) # Sleep for 3 minutes.
continue
The continue will send the interpreter back to the start of the while loop. From there it will check the network connection and either pull data or reset the network connection and sleep for another 3 minutes.
Using Quernons answer above the code has been edited as follows:
#!/usr/bin/python3
#import modules
import os
import cymysql
from time import sleep
from urllib.request import urlopen
import json
import datetime
#set MySQl Variables
host = "localhost"
user = "xxx"
password = "xxx"
schema = "xxx"
#connect to MySQL DB
db = cymysql.connect(host, user, password, schema)
curs = db.cursor()
#set api key for DarkSky API
apikey="xxx"
# Latitude & longitude
lati="-26.20227"
longi="28.04363"
# Add units=si to get it in sensible ISO units not stupid Fahreneheit.
url="https://api.forecast.io/forecast/"+apikey+"/"+lati+","+longi+"?units=si"
#begin infinite loop
while True:
#function to check if there is an internet connection
def check_ping():
hostname = "8.8.8.8"
response = os.system("ping -c 1 " + hostname)
#and then check the response...
if response == 0:
pingstatus = 0
else:
pingstatus = 1
return pingstatus
networkstatus = check_ping()
#print check_ping() - for testing purposes
#print (networkstatus)
#function to pull weather data from API
def get_weather():
#insert weather data here with no changes
if networkstatus == 0:
get_weather()
else:
print ("Resetting Network Adapters")
dwnnw = 'ifconfig wlan0 down'
upnw = 'ifconfig wlan0 up'
os.system(dwnnw)
os.system(upnw)
sleep(180)
continue
I am developing GPS(global sat bu-353s4 USB-type) and raspberry pi 3b based project. In which I want to fetch GPS latitude and longitude data, according to that data I want to play some video files and also want to keep track of last played video name. all this process should be in while loop means in an infinite loop.
I have developed logic for that, the problem I am facing is that whenever video playback is complete it will again fetch GPS data and go to specific folder select video file and play video, in between two video playback the screen gets blank I want continuous video play. I am using OMXplayer to open video.I know it can be solved using the multitasking /multithreading concept but don't know how to implement it in Python.
this is my code :
# class to define background process thread
class Asyncfun(threading.Thread):
def __init__(self, text):
threading.Thread.__init__(self)
self.text = text
def run(self):
os.system(self.text)
print "play finished "
def Main():
try:
while True:
# get the GPS latitude longitude data using another gpsdatafetching file
stdn = gps2.latlong()
lat1 = round(float(stdn[0]),5)
long1 = round(float(stdn[1]),5)
ID = gps_geotest3.test1(lat1,long1)# get the areaid according to current latitudeand longitude
print "id is :", ID
if ID == None:
ID = 17
print "lat long is in this areaId : ",ID
location = '/home/pi/files/'
counter = 0 #keep a count of all files found
mp4files = [] #list to store all csv files found at location
lastplayedindex = 0
areaID = str(ID)
location += areaID
#print "file path is: ",location
for file in os.listdir(location):
if file.endswith(".mp4"):
#print "mp4 file found:\t", file
mp4files.append(str(file))
counter = counter+1
#get the lastplayedindex_aeraid file name
indexfilename='lastplayedindex_'
indexfilename +=areaID
indexfilename += '.txt'
#get the index number from lastplayedindex_aeraid file
with open(indexfilename,'rb') as input_file:
for line in input_file:
lastplayedindex = line
path = "/home/pi/files/"
omxcmd = "omxplayer --display=5 "
print "lastplayed index: ",lastplayedindex
if int(lastplayedindex)< (counter-1) : #compare with total filecount in folder
newlastindex=int(lastplayedindex)+1
vfile = mp4files[newlastindex] #videofile name
omxcmd += (location +'/') #append filelocation
omxcmd += vfile # append filename
#omxcmd is command to open videofile using OMXplayer
#play videofile iin backgroundprocess while sending acknowledgment to webserver about that file
background = Asyncfun(omxcmd)
background.start()
# code to update lastplayed index in local file
counter = 0
#to send acknowledgment to server about which video played last
print "sending acknowledgment to server.."
payload2 = {'DeviceMasterId': '30', 'Fk_Area_ID': areaID,'FileName':vfile}
R = requests.post('url to my website', params = payload2)
if R.status_code != 200:
print "Error:", R.status_code
else :
print "acknowledgment sent successfully."
background.join()
except (KeyboardInterrupt, SystemExit): #when you press ctrl+c
gpsp.running = False
gpsp.join()
scope.__del__()
if __name__ == '__main__':
Main()
I am trying to import the snmpSessionBaseClass python module in a script I am running, but I do not have the module installed and I can't seem to find where to download it. Does anyone know the pip or yum command to download and install this module? Thanks!
import netsnmp
sys.path.insert(1, os.path.join(sys.path[0], os.pardir))
from snmpSessionBaseClass import add_common_options, get_common_options, verify_host, get_data
from pynag.Plugins import PluginHelper,ok,critical
The following code needs to be added to a file called snmpSessionBaseClass.py and that file needs to be placed in a directory that is in pythons path.
#!/usr/bin/env python
# Copyright (C) 2016 rsmuc <rsmuc#mailbox.org>
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with health_monitoring_plugins. If not, see <http://www.gnu.org/licenses/>.
import pynag
import netsnmp
import os
import sys
dev_null = os.open(os.devnull, os.O_WRONLY)
tmp_stdout = os.dup(sys.stdout.fileno())
def dev_null_wrapper(func, *a, **kwargs):
"""
Temporarily swap stdout with /dev/null, and execute given function while stdout goes to /dev/null.
This is useful because netsnmp writes to stdout and disturbes Icinga result in some cases.
"""
os.dup2(dev_null, sys.stdout.fileno())
return_object = func(*a, **kwargs)
sys.stdout.flush()
os.dup2(tmp_stdout, sys.stdout.fileno())
return return_object
def add_common_options(helper):
# Define the common command line parameters
helper.parser.add_option('-H', help="Hostname or ip address", dest="hostname")
helper.parser.add_option('-C', '--community', dest='community', help='SNMP community of the SNMP service on target host.', default='public')
helper.parser.add_option('-V', '--snmpversion', dest='version', help='SNMP version. (1 or 2)', default=2, type='int')
def get_common_options(helper):
# get the common options
host = helper.options.hostname
version = helper.options.version
community = helper.options.community
return host, version, community
def verify_host(host, helper):
if host == "" or host is None:
helper.exit(summary="Hostname must be specified"
, exit_code=pynag.Plugins.unknown
, perfdata='')
netsnmp_session = dev_null_wrapper(netsnmp.Session,
DestHost=helper.options.hostname,
Community=helper.options.community,
Version=helper.options.version)
try:
# Works around lacking error handling in netsnmp package.
if netsnmp_session.sess_ptr == 0:
helper.exit(summary="SNMP connection failed"
, exit_code=pynag.Plugins.unknown
, perfdata='')
except ValueError as error:
helper.exit(summary=str(error)
, exit_code=pynag.Plugins.unknown
, perfdata='')
# make a snmp get, if it fails (or returns nothing) exit the plugin
def get_data(session, oid, helper, empty_allowed=False):
var = netsnmp.Varbind(oid)
varl = netsnmp.VarList(var)
data = session.get(varl)
value = data[0]
if value is None:
helper.exit(summary="snmpget failed - no data for host "
+ session.DestHost + " OID: " +oid
, exit_code=pynag.Plugins.unknown
, perfdata='')
if not empty_allowed and not value:
helper.exit(summary="snmpget failed - no data for host "
+ session.DestHost + " OID: " +oid
, exit_code=pynag.Plugins.unknown
, perfdata='')
return value
# make a snmp get, but do not exit the plugin, if it returns nothing
# be careful! This funciton does not exit the plugin, if snmp get fails!
def attempt_get_data(session, oid):
var = netsnmp.Varbind(oid)
varl = netsnmp.VarList(var)
data = session.get(varl)
value = data[0]
return value
# make a snmp walk, if it fails (or returns nothing) exit the plugin
def walk_data(session, oid, helper):
tag = []
var = netsnmp.Varbind(oid)
varl = netsnmp.VarList(var)
data = list(session.walk(varl))
if len(data) == 0:
helper.exit(summary="snmpwalk failed - no data for host " + session.DestHost
+ " OID: " +oid
, exit_code=pynag.Plugins.unknown
, perfdata='')
for x in range(0, len(data)):
tag.append(varl[x].tag)
return data, tag
# make a snmp walk, but do not exit the plugin, if it returns nothing
# be careful! This function does not exit the plugin, if snmp walk fails!
def attempt_walk_data(session, oid):
tag = []
var = netsnmp.Varbind(oid)
varl = netsnmp.VarList(var)
data = list(session.walk(varl))
for x in range(0, len(data)):
tag.append(varl[x].tag)
return data, tag
def state_summary(value, name, state_list, helper, ok_value = 'ok', info = None):
"""
Always add the status to the long output, and if the status is not ok (or ok_value),
we show it in the summary and set the status to critical
"""
# translate the value (integer) we receive to a human readable value (e.g. ok, critical etc.) with the given state_list
state_value = state_list[int(value)]
summary_output = ''
long_output = ''
if not info:
info = ''
if state_value != ok_value:
summary_output += ('%s status: %s %s ' % (name, state_value, info))
helper.status(pynag.Plugins.critical)
long_output += ('%s status: %s %s\n' % (name, state_value, info))
return (summary_output, long_output)
def add_output(summary_output, long_output, helper):
"""
if the summary output is empty, we don't add it as summary, otherwise we would have empty spaces (e.g.: '. . . . .') in our summary report
"""
if summary_output != '':
helper.add_summary(summary_output)
helper.add_long_output(long_output)
So I'm making an application using a GPS module, Python and a MySQL database.
So I have written some code, to try to capture the data from the GPS and store it in the database. I'm using a plugin called "pynmea2" to parse some of the data (longitude and latitude). However, I need more data then that, so, I already tried ALOT different things, but my program keeps crashing the whole time. Could someone help me out with this?
Most of the time I get all the data from the Serial connection, but I want to be able to strip data from it. So example of what I get:[b'$GPGGA,093512.000,,,,,0,3,,,M,,M,,*47\r\n', b'$GPGLL,,,,,093512.000,V,N*76\r\n', b'$GPGSA,A,1,,,,,,,,,,,,,,,*1E\r\n', b'$GPGSV,3,1,11,15,72,214,,24,52,276,,13,48,141,,17,31,093,29*70\r\n', b'$GPGSV,3,2,11,18,28,292,,28,27,049,25,19,24,120,24,12,23,211,13*7E\r\n', b'$GPGSV,3
Well, it's not that simple to extract data from it,but it works out just fine with the pynmea2 library (only library I'm allowed to use.
So, I need the speed, the latitude and longitude for now, but the speed is bothering me now. It gives ValueError: could not convert string to float: "22*49\\r\\n'"
alot of times because I don't do a proper way of finding the data and then "parsing" it.
Here is my code I'm currently using;
from model.GPSParser import GPSParser
from model.DB import DB
import serial
import time
import datetime
import pynmea2
#########################################
# This is the main code to setup the
# serial connection with the GPS module.
# it needs to be OR runt as root OR as
# pi with all the root rights.
#########################################
port = "/dev/ttyAMA0"
ser = serial.Serial(port, 9600, timeout=0)
#########################################
# These are all the global variables
# to be used. All defined and set to
# zero or their standard 'Null' value.
#########################################
lat = 0.0
lon = 0.0
cur_speed = 0.0
while True:
try:
# Get the data from the serial monitor.
data = str(ser.readlines()).lstrip("b'")[:-3]
# print(data)
#########################################
# Find the speed, to check if we're
# standing still or not. Save it in a
# #var speed
#########################################
if data.find('$GPVTG') != -1:
cur_speed = data.split(",")[7]
#########################################
# Get the Latitude and Longitude
#########################################
if data.find('$GPGGA') != -1:
print(data)
# Check whether the data strings are empty or not.
if GPSParser.parseLatitude(data) != "" and GPSParser.parseLongitude(data) != "":
lat = GPSParser.parseLatitude(data)
lon = GPSParser.parseLongitude(data)
# Debug printing
# print("Latitude: " + GPSParser.parseLatitude(data))
# print("Longitude: " + GPSParser.parseLongitude(data))
# print("Speed: " + cur_speed)
#########################################
# Insert the coordinates into the database
# Be sure to check of we are really driving
# So when the speed is higher then 5 km/u
# Store everything into the database.
#########################################
if float(cur_speed) > 5.0:
db = DB()
db.insertCoordinates(lat, lon, datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S"))
# Wait a bit to not overload the Serial port
time.sleep(0.5)
############################################################
# The error handling
############################################################
except serial.serialutil.SerialException:
ser.close()
port = "/dev/ttyAMA0"
ser = serial.Serial(port, 9600, timeout=0)
continue
except pynmea2.ParseError:
# print("Error on parsing object, continuing...")
continue
except BlockingIOError:
# print("Blocking I/O error, continuing...")
continue
except TypeError:
# print("Type error, continuing...")
continue
except IndexError:
# print("To catch an error...")
continue
except KeyboardInterrupt:
print("\nProgram stopped.")
exit()
So the import from model doesn't do much, only the database connection and the "gps parser" is only the pynmea that parses a string of data and then returns it.
So what I want is something like:
It gets all the data it pulses once per second,
it then splits it all into chucks where it starts with the $GP variable, then I can search for the second variable part, for example VTG or GGA. And then I can use that string to make conversions to the right value to extract the speed, latitude, longitude and other data if needed.
Hope you guys can understand me well and can help me out.
Not sure if that solves your problem, but pynmea2 has speed attributes, defined in talker.py.
import pynmea2
for i, line in enumerate(open('/tmp/nmea.txt').readlines()):
# parsing via pynmea
msg = pynmea2.parse(line.strip())
if msg.sentence_type == 'VTG':
print ('parsing line %s with pynmea:' % i, float(msg.spd_over_grnd_kmph))
# parsing via manually
if line.startswith('$GPVTG'):
cur_speed = line.split(",")[7]
print ('parsing line %s manually:' % i, float(cur_speed))
Returns:
parsing line 1 with pynmea: 91.626
parsing line 1 manually: 91.626
parsing line 10 with pynmea: 90.842
parsing line 10 manually: 90.842
parsing line 19 with pynmea: 89.676
parsing line 19 manually: 89.676