使用Golang实现蓝牙通信的完整指南
使用Golang实现蓝牙通信的完整指南 大家好,
我是Go语言的新手(几周时间,做过几个项目——其中一些使用了fyne.io),现在又遇到了另一个难题。我是法国人(我知道,人无完人)。
我能看懂英文,但对我来说并不总是那么容易。同样,我的英文表达肯定也不是很好。
我有一个使用Arduino和HC06蓝牙适配器的项目。这个项目目前运行正常。
我用Android(使用App Inventor)制作了一个发送信息的应用程序。
我想把这个应用程序移植到Go语言上,以便在Linux和Windows上运行(甚至可能包括Android)。 但我不确定哪个库最适合我,以及如何在Go代码中发送消息(一个字符串或只是一个字符)。
我看到了Tinygo包(https://pkg.go.dev/tinygo.org/x/bluetooth)。使用它时,我不明白如何进行蓝牙通信。 我测试了扫描器的示例,它可以工作,但之后呢……?
我找不到更多的示例。
如果你能帮助我。
非常感谢。
Jean Pierre。
更多关于使用Golang实现蓝牙通信的完整指南的实战教程也可以访问 https://www.itying.com/category-94-b0.html
这听起来是个有趣的项目。我很喜欢tiny-go。当你提到“有某个地方(但看起来我找不到了)有一个示例……”时,你指的是这个心率监测器客户端吗?它看起来像是连接到一个设备并接收数据。
更多关于使用Golang实现蓝牙通信的完整指南的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html
你好,
感谢您的回答。
这个项目旨在制作一个用于射箭的移动靶。它目前可以工作,但如果我能为PC(Linux和Windows)制作一个遥控器,并且为Android也制作一个(目前Android的遥控器可以工作),也许还能适配Apple设备……因为是用Go(和Fyne)编写的。
我需要更仔细地研究一下心率监测器的示例……并用不同的方式测试。当我第一次看到它时,我没有理解,就像这次第二次阅读一样(而且我还需要多次阅读才能完全理解)。
Jean-Pierre。
嗨,Jean,
这个想法很有趣。我认为你需要了解BLE编程:https://www.bluetooth.com/bluetooth-resources/bluetooth-le-developer-starter-kit/
这个也很有用:https://learn.sparkfun.com/tutorials/bluetooth-basics/all
不过我有些疑问:
- 你打算构建一个GUI应用程序吗?
- 为什么选择Go?
你好,
感谢你的回复和提供的链接。我会尽快阅读这些内容。
我知道我需要了解更多关于蓝牙的知识,但我个人学习编程语言的方法之一是查看示例并研究不同的信息,以理解实现细节。一步一步来。
我过去是一名程序员,但现在从事教育工作,我为协会或出于兴趣编写代码。
所以,我认为应该存在某个地方(但看起来我找不到)一个包含连接以及少量发送和接收消息的示例。
关于你的问题:
- 是的,使用 Fyne.io
- 出于几个原因:这门语言符合我的逻辑思维,我可以用它完成许多我需要的事情,支持交叉编译,它是一门编译型语言,用户只需安装一个可执行程序,我不想学习很多不同的语言(目前就是 Go),等等。
使用Golang实现蓝牙通信的完整指南
对于你的蓝牙通信需求,我推荐使用github.com/go-ble/ble库,它支持Linux、macOS和Windows平台。以下是完整的实现示例:
1. 安装必要的库
go get github.com/go-ble/ble
go get github.com/go-ble/ble/examples/lib/dev
2. 扫描蓝牙设备
package main
import (
"context"
"fmt"
"log"
"time"
"github.com/go-ble/ble"
"github.com/go-ble/ble/examples/lib/dev"
)
func main() {
d, err := dev.NewDevice("default")
if err != nil {
log.Fatalf("无法创建设备: %v", err)
}
ble.SetDefaultDevice(d)
// 扫描蓝牙设备
ctx := ble.WithSigHandler(context.WithTimeout(context.Background(), 30*time.Second))
fmt.Println("开始扫描蓝牙设备...")
err = ble.Scan(ctx, true, func(a ble.Advertisement) {
fmt.Printf("发现设备: %s, 地址: %s, RSSI: %d\n",
a.LocalName(), a.Addr(), a.RSSI())
}, nil)
if err != nil {
log.Fatalf("扫描失败: %v", err)
}
}
3. 连接HC-06蓝牙模块并发送数据
package main
import (
"context"
"fmt"
"log"
"time"
"github.com/go-ble/ble"
"github.com/go-ble/ble/examples/lib/dev"
)
const (
hc06Address = "00:00:00:00:00:00" // 替换为你的HC-06地址
serviceUUID = "00001101-0000-1000-8000-00805F9B34FB" // 标准串口服务UUID
)
func main() {
d, err := dev.NewDevice("default")
if err != nil {
log.Fatalf("无法创建设备: %v", err)
}
ble.SetDefaultDevice(d)
// 连接设备
fmt.Printf("正在连接HC-06: %s\n", hc06Address)
ctx := ble.WithSigHandler(context.WithTimeout(context.Background(), 30*time.Second))
addr := ble.NewAddr(hc06Address)
client, err := ble.Dial(ctx, addr)
if err != nil {
log.Fatalf("连接失败: %v", err)
}
defer client.CancelConnection()
fmt.Println("连接成功!")
// 发现服务
p, err := client.DiscoverProfile(true)
if err != nil {
log.Fatalf("发现服务失败: %v", err)
}
// 查找串口服务
var uartService *ble.Service
for _, s := range p.Services {
if s.UUID.Equal(ble.MustParse(serviceUUID)) {
uartService = s
break
}
}
if uartService == nil {
log.Fatal("未找到串口服务")
}
// 查找特征值(用于发送数据)
var txCharacteristic *ble.Characteristic
for _, c := range uartService.Characteristics {
// 通常TX特征具有以下UUID之一
if c.UUID.Equal(ble.MustParse("00002a00-0000-1000-8000-00805f9b34fb")) ||
c.UUID.Equal(ble.MustParse("0000ffe1-0000-1000-8000-00805f9b34fb")) {
txCharacteristic = c
break
}
}
if txCharacteristic == nil {
log.Fatal("未找到发送特征")
}
// 发送字符串数据
message := "Hello from Go!\n"
fmt.Printf("发送消息: %s", message)
err = client.WriteCharacteristic(txCharacteristic, []byte(message), false)
if err != nil {
log.Fatalf("发送失败: %v", err)
}
fmt.Println("消息发送成功!")
// 保持连接
time.Sleep(2 * time.Second)
}
4. 接收数据示例
// 添加接收数据的函数
func receiveData(client ble.Client, rxUUID string) {
rxCharUUID := ble.MustParse(rxUUID)
// 订阅通知
err := client.Subscribe(rxCharUUID, false, func(req []byte) {
fmt.Printf("收到数据: %s\n", string(req))
})
if err != nil {
log.Printf("订阅失败: %v", err)
return
}
// 持续接收数据
select {}
}
5. 针对HC-06的简化版本
package main
import (
"bufio"
"context"
"fmt"
"log"
"os"
"time"
"github.com/go-ble/ble"
"github.com/go-ble/ble/examples/lib/dev"
)
func main() {
// 初始化蓝牙适配器
d, err := dev.NewDevice("default")
if err != nil {
log.Fatal(err)
}
ble.SetDefaultDevice(d)
// HC-06蓝牙地址(替换为你的设备地址)
hc06Addr := "00:00:00:00:00:00"
// 连接设备
ctx := context.WithTimeout(context.Background(), 30*time.Second)
client, err := ble.Connect(ctx, ble.NewAddr(hc06Addr))
if err != nil {
log.Fatal(err)
}
defer client.Clear()
fmt.Println("已连接到HC-06")
fmt.Println("输入要发送的消息 (输入'quit'退出):")
// 交互式发送消息
scanner := bufio.NewScanner(os.Stdin)
for scanner.Scan() {
text := scanner.Text()
if text == "quit" {
break
}
// 添加换行符
message := text + "\n"
// 发送数据(使用HC-06的标准串口服务)
err := client.WriteCharacteristic(
ble.NewCharacteristic(ble.MustParse("0000ffe1-0000-1000-8000-00805f9b34fb")),
[]byte(message),
false,
)
if err != nil {
log.Printf("发送失败: %v", err)
} else {
fmt.Printf("已发送: %s\n", text)
}
}
}
6. Windows系统注意事项
对于Windows系统,需要安装WinBle驱动:
// Windows专用初始化
func initWindows() {
// Windows需要额外的驱动设置
// 参考: https://github.com/go-ble/ble/tree/master/examples/lib/dev/windows
}
关键点说明:
- HC-06地址:使用Android应用或系统蓝牙设置查找HC-06的MAC地址
- UUID:HC-06通常使用标准串口UUID(00001101-0000-1000-8000-00805F9B34FB)
- 权限:Linux系统需要蓝牙权限(将用户加入
bluetooth组) - 配对:确保HC-06已与计算机配对
这个实现可以让你在Linux和Windows上与HC-06蓝牙模块进行通信,发送字符串或字符数据。

