Laminar多人 fps 游戲 UDP 協(xié)議
Laminar 是一種應(yīng)用級(jí)傳輸協(xié)議,為快節(jié)奏的 fps 游戲提供基于 UDP 的可配置可靠性和排序保證,且提供輕量級(jí)的界面。
它的靈感來自 Gaffer on Games,功能類似 RakNet, Steam Socket, netcode.io。通過 Rust 寫的低級(jí) UDP 協(xié)議來支持多人游戲聯(lián)網(wǎng)功能(尤其是 FPS 游戲),Laminar 一般用于 Amethyst 游戲引擎,不過沒它也能用。
特性:
- 碎片化
- 不可靠的數(shù)據(jù)包
- 不可靠的排序數(shù)據(jù)包
- 可靠的無序數(shù)據(jù)包
- 可靠有序的數(shù)據(jù)包
- 可靠的排序數(shù)據(jù)包
- Rtt 估算
- 協(xié)議版本監(jiān)控
- 基本連接管理
- Heartbeat
- 基礎(chǔ)的 DoS 緩沖
- 高時(shí)序控制
- 協(xié)議版本控制
- 集成和單元測(cè)試良好
- 可以被多個(gè)線程使用(Sender, Receiver)
協(xié)議
- 握手協(xié)議
- 高級(jí)連接管理
- 密碼密匙體系(Cryptography)
- 擁塞控制
用例:
UDP API - 發(fā)送數(shù)據(jù)
use laminar::{Socket, Packet}; // Creates the socket let mut socket = Socket::bind("127.0.0.1:12345")?; let packet_sender = socket.get_packet_sender(); // Starts the socket, which will start a poll mechanism to receive and send messages. let _thread = thread::spawn(move || socket.start_polling()); // Bytes to sent let bytes = vec![...]; // Creates packets with different reliabilities let unreliable = Packet::unreliable(destination, bytes); let reliable = Packet::reliable_unordered(destination, bytes); // Specifies on which stream and how to order our packets, check out our book and documentation for more information let unreliable = Packet::unreliable_sequenced(destination, bytes, Some(1)); let reliable_sequenced = Packet::reliable_sequenced(destination, bytes, Some(2)); let reliable_ordered = Packet::reliable_ordered(destination, bytes, Some(3)); // Sends the created packets packet_sender.send(unreliable).unwrap(); packet_sender.send(reliable).unwrap(); packet_sender.send(unreliable_sequenced).unwrap(); packet_sender.send(reliable_sequenced).unwrap(); packet_sender.send(reliable_ordered).unwrap();
UDP API - 接收數(shù)據(jù)
use laminar::{SocketEvent, Socket}; // Creates the socket let mut socket = Socket::bind("127.0.0.1:12346")?; let event_receiver = socket.get_event_receiver(); // Starts the socket, which will start a poll mechanism to receive and send messages. let _thread = thread::spawn(move || socket.start_polling()); // Waits until a socket event occurs let result = event_receiver.recv(); match result { Ok(socket_event) => { match socket_event { SocketEvent::Packet(packet) => { let endpoint: SocketAddr = packet.addr(); let received_data: &[u8] = packet.payload(); } SocketEvent::Connect(connect_event) => { /* a client connected */ } SocketEvent::Timeout(timeout_event) => { /* a client timed out */ } SocketEvent::Disconnect(disconnect_event) => { /* a client disconnected */ } } } Err(e) => { println!("Something went wrong when receiving, error: {:?}", e); } }
評(píng)論
圖片
表情
