Skip to content
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

update trouble api #4

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 5 additions & 6 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -32,16 +32,15 @@ embassy-time = { version = "^0.3.0", default-features = false, features = [
] }

# nrf52833 dependencies
microbit-bsp = { git = "https://github.com/jamessizeland/microbit-bsp.git", branch = "trouble", features = [
"trouble",
] }
# microbit-bsp = { path = "../microbit-bsp", features = ["trouble"] }
# microbit-bsp = { git = "https://github.com/jamessizeland/microbit-bsp.git", branch = "trouble", features = [
# "trouble",
# ] }
microbit-bsp = { path = "../microbit-bsp", features = ["trouble"] }

# BLE dependencies
bt-hci = { version = "0.1.1", default-features = false, features = ["defmt"] }
trouble-host = { git = "https://github.com/embassy-rs/trouble.git", features = [
"defmt",
], branch = "main" }
], rev = "07fa452e836f07a302596edb6a61e060d242e4ea" }
static_cell = "2.1.0"

[profile.release]
Expand Down
2 changes: 1 addition & 1 deletion src/ble/advertiser.rs
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ impl<'d, C: Controller> AdvertiserBuilder<'d, C> {
impl<'d, C: Controller> Advertiser<'d, C> {
/// Advertise and connect to a device with the given name
pub async fn advertise(&mut self) -> Result<Connection<'d>, BleHostError<C::Error>> {
let mut advertiser = self
let advertiser = self
.peripheral
.advertise(
&Default::default(),
Expand Down
83 changes: 35 additions & 48 deletions src/ble/gatt.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,9 @@
use super::advertiser::{Advertiser, AdvertiserBuilder};
use super::hid::*;
use super::{ble_task, mpsl_task, BleResources};
use super::{hid::*, BleServer};
use super::{stick::*, BleController};
use defmt::info;
use defmt::{info, warn};
use embassy_executor::Spawner;
use embassy_futures::select::select;
use embassy_futures::select::Either;
use microbit_bsp::ble::{MultiprotocolServiceLayer, SoftdeviceError};
use static_cell::StaticCell;
use trouble_host::prelude::*;
Expand All @@ -14,26 +12,19 @@ use trouble_host::types::gatt_traits::GattValue;
/// Allow a central to decide which player this controller belongs to
#[gatt_service(uuid = "8f701cf1-b1df-42a1-bb5f-6a1028c793b0")]
pub struct Player {
#[characteristic(uuid = "e3d1afe4-b414-44e3-be54-0ea26c394eba", read, write, on_write = on_write)]
#[characteristic(uuid = "e3d1afe4-b414-44e3-be54-0ea26c394eba", read, write)]
index: u8,
}

fn on_write(_: &Connection<'_>, value: &[u8]) -> Result<(), ()> {
if let Ok(index) = u8::from_gatt(value) {
info!("Player index set to {:?}", index);
};
Ok(())
}

#[gatt_server(attribute_data_size = 100)]
pub struct Server {
#[gatt_server]
pub struct BleServer {
// pub bas: BatteryService,
pub hid: ButtonService,
pub stick: StickService,
pub player: Player,
}

impl Server<'static, 'static, BleController> {
impl BleServer<'static> {
pub fn start_gatt(
name: &'static str,
spawner: Spawner,
Expand All @@ -50,19 +41,16 @@ impl Server<'static, 'static, BleController> {
static RESOURCES: StaticCell<BleResources> = StaticCell::new();
RESOURCES.init(BleResources::new(PacketQos::None))
};
let (stack, peripheral, _, runner) = trouble_host::new(controller, resources)
let (_, peripheral, _, runner) = trouble_host::new(controller, resources)
.set_random_address(address)
.build();
let server = {
static SERVER: StaticCell<BleServer<'_>> = StaticCell::new();
SERVER.init(
Server::new_with_config(
stack,
GapConfig::Peripheral(PeripheralConfig {
name,
appearance: &appearance::GAMEPAD,
}),
)
BleServer::new_with_config(GapConfig::Peripheral(PeripheralConfig {
name,
appearance: &appearance::human_interface_device::GAMEPAD,
}))
.expect("Error creating Gatt Server"),
)
};
Expand All @@ -75,34 +63,33 @@ impl Server<'static, 'static, BleController> {

/// A BLE GATT server
pub async fn gatt_server_task(server: &BleServer<'_>, conn: &Connection<'_>) {
let index = server.player.index;
loop {
if let Either::First(event) = select(conn.next(), server.run()).await {
match event {
ConnectionEvent::Disconnected { reason } => {
info!("[gatt] Disconnected: {:?}", reason);
break;
}
ConnectionEvent::Gatt { event, .. } => match event {
GattEvent::Read { value_handle } => {
if value_handle == server.player.index.handle {
let value = server.get(&server.player.index);
info!(
"[gatt] Read Event to Player Index Characteristic: {:?}",
value
);
}
match conn.next().await {
ConnectionEvent::Disconnected { reason } => {
info!("[gatt] disconnected: {:?}", reason);
break;
}
ConnectionEvent::Gatt { data } => match data.process(server).await {
Ok(Some(GattEvent::Read(event))) => {
if event.handle() == index.handle {
let value = server.get(&index);
info!("[gatt] Read Event to index Characteristic: {:?}", value);
}
GattEvent::Write { value_handle } => {
if value_handle == server.player.index.handle {
let value = server.get(&server.player.index);
info!(
"[gatt] Write Event to Player Index Characteristic: {:?}",
value
);
}
}
Ok(Some(GattEvent::Write(event))) => {
if event.handle() == index.handle {
info!(
"[gatt] Write Event to index Characteristic: {:?}",
event.data()
);
}
},
}
}
Ok(_) => {}
Err(e) => {
warn!("[gatt] error processing event: {:?}", e);
}
},
}
}
info!("Gatt server task finished");
Expand Down
6 changes: 2 additions & 4 deletions src/ble/hid.rs
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ pub async fn notify_button_state(
loop {
button.input.wait_for_low().await;
info!("button {} pressed", button.name);
server.notify(&button.ble_handle, connection, &true).await?;
button.ble_handle.notify(server, connection, &true).await?;
display
.display(
DisplayFrame::Letter(button.name),
Expand All @@ -55,9 +55,7 @@ pub async fn notify_button_state(
Timer::after(debounce).await;
button.input.wait_for_high().await;
info!("button {} released", button.name);
server
.notify(&button.ble_handle, connection, &false)
.await?;
button.ble_handle.notify(server, connection, &false).await?;
Timer::after(debounce).await;
}
}
Expand Down
3 changes: 1 addition & 2 deletions src/ble/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ pub mod gatt;
pub mod hid;
pub mod stick;

pub use gatt::BleServer;
use microbit_bsp::ble::{MultiprotocolServiceLayer, SoftdeviceController};
use trouble_host::prelude::*;

Expand All @@ -15,8 +16,6 @@ const CONNECTIONS_MAX: usize = 1;
/// Max number of L2CAP channels.
const L2CAP_CHANNELS_MAX: usize = 2; // Signal + att

pub type BleServer<'d> = gatt::Server<'d, 'd, SoftdeviceController<'d>>;

pub type BleController = SoftdeviceController<'static>;

pub type BleResources =
Expand Down
7 changes: 4 additions & 3 deletions src/ble/stick.rs
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ impl Axis {
let new = -((new_raw - self.offset) / self.divider) as i8; // invert the value
if new != self.old {
self.old = new;
Some(new as i8)
Some(new)
} else {
None
}
Expand All @@ -73,16 +73,17 @@ pub async fn analog_stick_task(
let divider = 623;
let mut x_axis = Axis::new(offset, divider);
let mut y_axis = Axis::new(offset, divider);
let stick = &server.stick;
loop {
// read adc values for x and y, and if they have changed by a certain amount, notify
// we are reducing the number of analogue stick levels to a range of -2 to 2
saadc.sample(&mut buf).await;
// display the x and y values on the led matrix
if let Some(x) = x_axis.changed(buf[0]) {
server.notify(&server.stick.x, conn, &x).await?;
stick.x.notify(server, conn, &x).await?;
}
if let Some(y) = y_axis.changed(buf[1]) {
server.notify(&server.stick.y, conn, &y).await?;
stick.y.notify(server, conn, &y).await?;
}
if !(x_axis.old == 0 && y_axis.old == 0) {
// only display if the stick is not centered
Expand Down
4 changes: 2 additions & 2 deletions src/io/display/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ impl AsyncDisplay {

#[allow(unused)]
pub enum DisplayFrame {
DisplayFrame(Frame<5, 5>),
Custom(Frame<5, 5>),
/// Display a single pixel at the given coordinates, where (0,0) is the center of the display.
Coord {
x: i8,
Expand All @@ -89,7 +89,7 @@ pub enum DisplayFrame {
impl DisplayFrame {
fn to_frame(&self) -> Frame<5, 5> {
match self {
DisplayFrame::DisplayFrame(frame) => frame.clone(),
DisplayFrame::Custom(frame) => *frame,
DisplayFrame::Heart => bitmap::HEART,
DisplayFrame::Smile => bitmap::SMILE,
DisplayFrame::Sad => bitmap::SAD,
Expand Down