New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
telemetry.position() not working. #176
Comments
Can you takeoff from QGC? And can you takeoff from MAVSDK? I assume you are using HITL? Could you try with udp and SITL? |
I need to look into this at some point. It has now come up several times. |
Always from python? |
Maybe, not sure. |
I had the same problem earlier, maybe that can help, though I used actual board and GPS device, not simulation. |
Doesn't that mean that it needs a GPS fix? Which makes sense to me: before the drone knows its GPS position, it cannot send it. Or am I missing something? |
Thanks, this may solve my problem. I did use a GPS device and I put it outside the window before, QGC show fixed gps data, SDK show fixtype change but does not have position data. I will take it out and test later. |
@JonasVautherin that is not the case I think. I just tested it again inside, getting these results:
and the code is stuck at getting data from When I tested outside earlier, the only difference was that in health also the last check (home position) was True (and it was also indicated by the gps device with the corresponding beeping), and after that position data were streamed correctly. @skymaze I'm happy it is solved! |
Ok I think I'll need @julianoes insights regarding this "home" thing 🤔 |
I looked into this bug. I think something is wrong with the version at pypi.org I've run into a similar bug when using async for position in drone.telemetry.position():
print(position) In my case, the values returned from I run into the bug when I install version 0.7.0 at https://pypi.org/project/mavsdk/. Specifically, when I use the version provided by To avoid the bug, I can tell pip to install I'm using Ubuntu 18.04, and here is how I set up my build environment: git clone https://github.com/PX4/Firmware.git --recursive
cd Firmware
bash ./Tools/setup/ubuntu.sh
sudo apt install --yes software-properties-common
sudo add-apt-repository --yes ppa:deadsnakes/ppa
sudo apt update
sudo apt install --yes python3.8 python3.8-venv python3.8-doc python3.8-dev binutils From there I create a python 3.8 venv and I use pip to install |
@murphym18: thanks for the report! So I just tried to
mkdir /tmp/test-mavsdk
cd /tmp/test-mavsdk
python3 -m venv venv
source ./venv/bin/activate
pip install mavsdk Then still from this venv, run: async for position in drone.telemetry.position():
print(position) And make the drone takeoff (in SITL that can be just |
Did you try against SITL over UDP? The issue mentions serial, and nobody above mentioned trying with SITL. It would be helpful to know.Yup I used UDP. Here is the system address: You mention using 0.7.0 from github, which may mean that it's a clean install. Would you mind trying in a venv?I've been using virtual environments exclusively (created using
But at your suggestion, I made a new venv, with async for position in drone.telemetry.position():
print(position) When I entered Given that behavior, I rechecked my program (the one that uses It might be helpful to see how I launch more than one drone. So the remainder of this post covers that. For each drone, I start a new """A mavsdk_server launcher
The module starts a mavsdk_server for the given system address. It also stop the server's process at exit.
Example:
>>> from _mavsdk_backend import start_mavsdk_server
>>> from mavsdk import System
>>> sys_addr = "udp://:14540"
>>> backend_host, backend_port = start_mavsdk_server(system_address=sys_addr)
>>> drone = System(mavsdk_server_address=backend_host, port=backend_port)
>>> # in an async function
>>> await drone.connect(system_address=sys_addr)
"""
import atexit
import os
import subprocess
import sys
import threading
from importlib.resources import path
from mavsdk import bin
_next_port = 50051
_servers = []
_lock = threading.Lock()
def start_mavsdk_server(system_address):
with _lock:
if len(_servers) < 1:
atexit.register(_cleanup)
mavsdk_port = _get_port()
_mavsdk(system_address, mavsdk_port)
return 'localhost', mavsdk_port
def _get_port():
global _next_port
port = _next_port
_next_port = _next_port + 1
return port
def _mavsdk(system_address, port):
with path(bin, 'mavsdk_server') as backend:
exec_cmd = [os.fspath(backend), "-p", str(port), system_address]
p = subprocess.Popen(exec_cmd,
shell=False,
stdout=subprocess.DEVNULL,
stderr=subprocess.DEVNULL)
_servers.append(p)
def _cleanup():
with _lock:
for mavsdk_process in _servers:
mavsdk_process.kill() In another module I use the async def _get_instance(system_address, mavsdk_server_host, mavsdk_server_port, uav_id, message_callback):
drone = System(mavsdk_server_host, mavsdk_server_port)
await drone.connect(system_address)
async for state in drone.core.connection_state():
if state.is_connected:
log.info(f"Drone discovered with UUID: {state.uuid}")
if uav_id is None:
uav_id = state.uuid
break
px4 = Px4Drone(drone, uav_id, message_callback)
return px4
def get_instance(system_address="udp://:14540", uav_id=None, message_callback=noop):
mavsdk_server_address, mavsdk_server_port = start_mavsdk_server(system_address)
fut = asyncio.run_coroutine_threadsafe(
_get_instance(system_address, mavsdk_server_address, mavsdk_server_port, uav_id, message_callback), loop)
return fut.result() And async def _position(self):
async for position in self.drone.telemetry.position():
self.log.debug(f"position: {position}")
self.position = position After takeoff, when I look at the logs, I can see the position value as 0.007000000216066837. This is the case even though jmavsim shows the drone in the air: Here is a screenshot: |
Very nice, @murphym18 👍 😊. This raises 2 questions on my side:
Because it works with one drone, but not with multiple drones, it suggests that maybe they conflict with each other in some way. Having a separate MAVLink port and a separate |
where does the embedded mavsdk_server executable come from?As far as I know,
And there is a compilation error saying something like the compiler isn't found. Here is a gist with all the output In fact, it takes a long time to compile and I was wondering if there was a way to make the compiler use more than one thread. 😆 I see def get_instance(system_address="udp://:14540". I assume that you create multiple SITL instances, and each of them is on another port. So system_address is not always "udp://:14540", but rather "udp://:14540" for the first drone, "udp://:14541" for the next one, etc. Is that correct?Yes, that is correct. In the scenario screenshotted above, I call the function with But I just noticed that the first port was Thank you by the way. When I get more time, I was hoping to make a pull request to add a multi-drone example in response to #102 |
That would surprise me. Nothing in MAVSDK-Python says how I don't really get what One thing that's missing in MAVSDK-Python is that we just discard the output of |
Is there an upper limit to the number of I got for sensor_function, sensor_name in [
(self.drone.core.connection_state, 'connection_state'),
(self.drone.telemetry.armed, 'armed_state'),
(self.drone.telemetry.attitude_euler, 'attitude'),
(self.drone.telemetry.battery, 'battery'),
(self.drone.telemetry.flight_mode, 'flight_mode'),
(self.drone.telemetry.gps_info, 'gps_info'),
(self.drone.telemetry.health, 'health'),
(self.drone.telemetry.in_air, 'in_air'),
(self.drone.telemetry.position, 'position'),
(self.drone.telemetry.status_text, 'status_text'),
(self.drone.telemetry.velocity_ned, 'velocity'),
]:
self.log.debug(f"{sensor_name} sensor starting")
asyncio.create_task(self._read_sensor(sensor_function, sensor_name)) I wonder if that's too many. With one drone, it seems to work fine. But if I try to control two or more drones within the same process (using the same event loop), I find the problem where the position does not change. I can separate each drone into its own process as a workaround. Here are a few more details.
It almost looks like I'm receiving the positions very slowly. But I can't be sure. I might try running a simulation for a few hours to see if the position catches up. |
One limitation is that for one Could it be what you are experiencing? |
Closing as there was no more answer. Please comment again or answer if the issue persists. |
mavsdk Version: 0.6.1-1-g409a253
mavsdk_server Version: arm64 v0.24.0
I'm using jetson nano and pixhawk 4.
Steps to reproduce:
1.change example/telemetry.py to use serial port
2.run python3 telemetry.py
Expected Behavior:
show all telemetry in example
Actual Behavior:
only show gps info, in air and battery, position not show. However I can see position info in QGroundControl.
The text was updated successfully, but these errors were encountered: