通过python以编程方式将蓝牙设备绑定到rfcomm [英] Bind Bluetooth device programmatically to rfcomm via python in

查看:233
本文介绍了通过python以编程方式将蓝牙设备绑定到rfcomm的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我用 python 编写了一个脚本,用于在我的 M5Stack Stick C(如 raduino)和树莓派之间进行串行通信.一切正常.我可以发送X"、Y"或Z"从树莓派到棍子,他会将值(G-Force)回复给 raspi!到目前为止一切顺利

i wrote a script in python for serial communication between my M5Stack Stick C (like raduino) and the raspberry pi. all work fine. i can send "X","Y" or "Z" from raspberry py to the stick and he will reply the value (G-Force) back to the raspi! so far so good

代码:

关于刺耳的 Python:

Python on raspy:

import serial
import time
import threading


ser = serial.Serial('/dev/rfcomm5') #init serial port
input_line = []#init input char array

def process_data(_data):
    #called every time a sream is terminated by \n 
    #and the command string is ready to use
    command = convert(_data)
    print(command)
    
def convert(s):   #convert the char list in a string
    
    new = "" #init string to append all chars from char array
    
    for x in s:     # traverse in the string  
        new += str(x)  
  
    return new    # return string  
    
def processIncomingByte(inByte):#adding incoming chars to input_line
    
    global input_line# globalize the input_line
    
    if(inByte == '\n'):#if \n is incoming, end the chararray and release process data method
        process_data(input_line)
        input_line = []#reset input_line for next incoming string
    elif(inByte == '\r'):
        pass
        
    else:#put all incoming chars in input_line 
        input_line.append(inByte)
        

while True:
    while(ser.in_waiting > 0):#while some data is waiting to read....
        processIncomingByte(ser.read())#.... process bytes whit method
    ser.write(b'X\n')
    time.sleep(0.5)

在脚本工作之前,我必须手动将 m5Stak Stick-C 绑定到 Blueman到/dev/Rfcomm5.它在 GUI 或控制台上工作得很好....

before the script work, i have to manually bind the m5Stak Stick-C over Blueman to /dev/Rfcomm5. it work just fine over GUI or Console....

但现在我想通过python将棒连接到rfcomm5(仅通过知道MAC地址,稍后将在配置文件中找到...)我开始调查一下,但我研究得越多,我就越困惑!!我通过套接字和服务器-客户端方法阅读了一些内容.通过一个单独的脚本等等......我测试了这段代码:

but now i would like to connect the stick via python to rfcomm5 (just by know the MAC adress, will be found in a config file later on...) i startet to investigate a bit, but the more i research the more confused i am!! i read some stuff over sockets and server-client aproaches. over a seperated script and so on.... i tested this code:

from bluetooth import *

target_name = "M5-Stick-C"
target_address = None
nearby_devices = discover_devices()

for address in nearby_devices:
    if (target_name == lookup_name( address )):
        target_address = address
        break
if (target_address is not None):
    print ("found target bluetooth device with address ", target_address)
else:
    print ("could not find target bluetooth device nearby")

它确实找到了设备(只是测试)!但我真的需要制作第二个脚本/进程来连接到我的脚本吗?

and indeed it found the device (just testing)! but do i realy need to make a second script/process to connect to from my script?

M5stack Stick-C 是服务器吗?(我也这么认为)

is the the M5stack Stick-C the server? (i think so)

我对所有这些东西都很困惑.我编码了很多,但从来没有丝毫套接字,服务器客户端的东西.基本上通信(服务器/客户端?)有效.我只需要通过 macadress 将我在第二个脚本中找到的设备连接到 rfcomm5(或任何 rfcomm).我需要蓝牙插座吗?就像在这个例子中https://gist.github.com/kevindoran/5428612

im so confused about all that stuff. i coded a lot, but never whit sockets, server-client stuff. basically the communication (server/client?) works. i just need to connect the device i found in the second script via macadress to rfcomm5 (or whatever rfcomm). do i need a bluetooth socket? like in this example https://gist.github.com/kevindoran/5428612

rfcomm 不是套接字还是我错了?

isnt the rfcomm the socket or am i wrong?

推荐答案

在通信过程中使用了许多层,根据您进入该堆栈的位置将取决于您需要执行什么编码.另一个复杂因素是 BlueZ(Linux 上的蓝牙堆栈)最近改变了它的工作方式,在互联网上留下了许多过时的信息,很容易让人们感到困惑.

There are a number of layers that are used in the communication process and depending where you tap into that stack will depend what coding you need to do. The other complication is that BlueZ (the Bluetooth stack on linux) changed how it works over recent times leaving a lot of out of date information on the internet and easy for people to get confused.

有两个蓝牙设备,他们需要建立配对.这通常是一次性配置步骤.这可以使用 Blueman 等工具或使用 bluetoothctl 在命令行上完成.在 RPi 和 M5Stack Stick 之间建立配对后,您就不需要再次发现附近的设备了.如果您告诉脚本要连接到哪个设备,您的脚本应该能够连接.

With two Bluetooth devices, they need to establish a pairng. This is typically a one off provisioning step. This can be done with tools like Blueman or on the command line with bluetoothctl. Once you have a pairing established between your RPi and the M5Stack Stick, you shouldn't need to discover nearby devices again. Your script should just be able to connect if you tell it which device to connect to.

M5Stack 棒被宣传为具有串行端口配置文件 (SPP).这是在 rfcomm 之上的一层.

The M5Stack stick is advertising as having a Serial Port Profile (SPP). This is a layer on top of rfcomm.

有一篇关于如何使用标准 Python3 安装完成此类连接的博客文章:http://blog.kevindoran.co/bluetooth-programming-with-python-3/

There is a blog post about how this type of connection can be done with the standard Python3 installation: http://blog.kevindoran.co/bluetooth-programming-with-python-3/

我的期望是您只需在 RPi 上执行 client.py,因为 M5Stack Stick 是服务器.您需要知道它的地址以及要连接的端口.可能是端口号上的一些试验和错误(1 和 3 似乎很常见).

My expectation is that you will only have to do the client.py on your RPi as the M5Stack Stick is the server. You will need to know its address and which port to connect on. Might be some trial and error on the port number (1 and 3 seem to be common).

我发现对 SPP 有帮助的另一个库是 bluedot 因为它抽象了一些样板代码:https://bluedot.readthedocs.io/en/latest/btcommapi.html#bluetoothclient

Another library that I find helpful for SPP, is bluedot as it abstracts away some of the boilerplate code: https://bluedot.readthedocs.io/en/latest/btcommapi.html#bluetoothclient

所以总而言之,我的建议是使用标准的 Python Socket 库或 Bluedot.这将允许您在代码中指定要连接的设备的地址,底层库将负责建立连接和设置串行端口(只要您已经将两个设备配对).

So in summary, my recommendation is to use the standard Python Socket library or Bluedot. This will allow you to specify the address of the device you wish to connect to in your code and the underlying libraries will take care of making the connection and setting up the serial port (as long as you have already paired the two devices).

上面使用 Bluedot 的示例

Example of what the above might look like with Bluedot

from bluedot.btcomm import BluetoothClient
from signal import pause
from time import sleep

# Callback to handle data
def data_received(data):
    print(data)
    sleep(0.5)
    c.send("X\n")

# Make connection and establish serial connection
c = BluetoothClient("M5-Stick-C", data_received)
# Send initial requests
c.send("X\n")

# Cause the process to sleep until data received
pause()

使用 Python 套接字库的示例:

Example using the Python socket library:

import socket
from time import sleep

# Device specific information
m5stick_addr = 'xx:xx:xx:xx:xx:xx'
port = 5 # This needs to match M5Stick setting

# Establish connection and setup serial communication
s = socket.socket(socket.AF_BLUETOOTH, socket.SOCK_STREAM, socket.BTPROTO_RFCOMM)
s.connect((m5stick_addr, port))

# Send and receive data
while True:
    s.sendall(b'X\n')
    data = s.recv(1024)
    print(data)
    sleep(0.5)
s.close()

这篇关于通过python以编程方式将蓝牙设备绑定到rfcomm的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆