Newer
Older
# Bevy Remote Events
Magically send and receive events to an arbitrary remote server. Websockets under the hood; web & desktop support
## Description
This repository contains a plugin for the [Bevy](https://bevyengine.org/) game engine. This plugin allows games to easily define
events that can be sent and received from some arbitary websocket server.
This library is quite immature; many features still need to be added for it to be considered "complete".
- [x] WS Connection from desktop
- [x] WS Connection from wasm
- [x] Frame independent event buffering
- [x] User initiated disconnect on desktop
- [x] User initiated disconnect on wasm
- [x] Handle remote disconnect
- [ ] Emit events for non-user-initiated lifecycle events
- [ ] Correctly track status of underlying connection
- [ ] Automatic reconnection
- [x] Map received events to user defined types
- [x] Send events of a user defined type
`remote_events` is not currently available on Cargo; instead, you need to use a Git dependency. Add the following to your project's `Cargo.toml` file:
remote_events = { git = "https://lab.lcr.gr/microhacks/micro-bevy-remote-events", branch = "trunk" }
You need to define two event types; one for events you expect to send to the remote server, and one for events you expect to receive. Typically this will be an `enum` type.
These types need to implement `ToSocketMessage` and `FromSocketMessage` respectively.
`remote_events` expects every received event to be mapped to a type within your project; this might require a custom `None` type added to your event `enum` (see below).
A client will only be created when you emit a `SocketControlEvent::Connect(String)` event containing the URL of the remote host to connect to.
The `Desktop` target can only handle insecure websocket connections (`ws://`, not `wss://`).
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
```rust
use remote_events::events::{FromSocketMessage, SocketControlEvent, ToSocketMessage};
use serde::{Serialize, Deserialize};
use serde_json::from_string;
#[derive(Default, Clone, Debug, Deserialize)]
pub enum ReceivedEvents {
PlayerJoined {
player_id: String,
},
PlayerHasClicked {
player_id: String,
},
SetPlayerClickCount {
player_id: String,
amount: usize,
},
#[default]
// Catch and handle invalid data as part of our events
InvalidEvent,
}
impl FromSocketMessage for ReceivedEvents {
// Our server sends string encoded JSON values
fn from_text(value: String) -> Self {
serde_json::from_str(&value)
.unwrap_or_default()
}
// Our server only sends text values, assume binary is just encoded text
fn from_binary(value: Vec<u8>) -> Self {
Self::from_text(String::from_utf8(value).unwrap_or(String::new()))
}
}
pub fn connect_to_server(mut events: EventWriter<SocketControlEvent>) {
events.send(SocketControlEvent::Connect(String::from("ws://localhost:3000")));
}
#[derive(Default, Clone, Debug, Serialize)]
pub enum SentEvents {
ButtonClicked,
SpendClicks {
amount: usize,
},
}
impl ToSocketMessage for ReceivedEvents {
fn to_text(&self) -> String {
serde_json::to_string(&self).unwrap()
}
}
pub fn main() {
App::new()
// .. Other plugins ..
.add_plugin(
RemoteEventPlugin::<SentEvents, ReceivedEvents>::new()
);
}