diff options
Diffstat (limited to 'server/src/server.rs')
-rw-r--r-- | server/src/server.rs | 127 |
1 files changed, 72 insertions, 55 deletions
diff --git a/server/src/server.rs b/server/src/server.rs index 9928ac90..9b90d6b3 100644 --- a/server/src/server.rs +++ b/server/src/server.rs @@ -28,8 +28,8 @@ use hurrycurry_client_lib::{Game, Involvement, Item, Player, Tile}; use hurrycurry_protocol::{ glam::{IVec2, Vec2}, movement::MovementBase, - Gamedata, ItemLocation, Menu, MessageTimeout, PacketC, PacketS, PlayerClass, PlayerID, Score, - TileIndex, + Gamedata, Hand, ItemLocation, Menu, MessageTimeout, PacketC, PacketS, PlayerClass, PlayerID, + Score, TileIndex, }; use log::{info, warn}; use rand::random; @@ -163,26 +163,29 @@ impl GameServerExt for Game { character: player.character, name: player.name.clone(), }); - if let Some(item) = &player.item { - out.push(PacketC::SetItem { - location: ItemLocation::Player(id), - item: Some(item.kind), - }); - if let Some(Involvement { - player, - position, - speed, - warn, - .. - }) = item.active - { - out.push(PacketC::SetProgress { + for (i, item) in player.items.iter().enumerate() { + let hand = Hand::from_index(i); + if let Some(item) = &item { + out.push(PacketC::SetItem { + location: ItemLocation::Player(id, hand), + item: Some(item.kind), + }); + if let Some(Involvement { player, - item: ItemLocation::Player(id), position, speed, warn, - }); + .. + }) = item.active + { + out.push(PacketC::SetProgress { + player, + item: ItemLocation::Player(id, hand), + position, + speed, + warn, + }); + } } } if let Some((message, timeout)) = &player.communicate_persist { @@ -252,7 +255,7 @@ impl GameServerExt for Game { self.players.insert( id, Player { - item: None, + items: [const { None }; 2], character, class, movement: MovementBase::new(position), @@ -399,15 +402,18 @@ impl Server { self.game.players_spatial_index.remove_entry(player); - if let Some(item) = p.item { - let pos = p.movement.position.floor().as_ivec2(); - if let Some(tile) = self.game.tiles.get_mut(&pos) { - if tile.item.is_none() { - self.packet_out.push_back(PacketC::SetItem { - location: ItemLocation::Tile(pos), - item: Some(item.kind), - }); - tile.item = Some(item); + // TODO if holding two, one is destroyed + for item in p.items { + if let Some(item) = item { + let pos = p.movement.position.floor().as_ivec2(); + if let Some(tile) = self.game.tiles.get_mut(&pos) { + if tile.item.is_none() { + self.packet_out.push_back(PacketC::SetItem { + location: ItemLocation::Tile(pos), + item: Some(item.kind), + }); + tile.item = Some(item); + } } } } @@ -445,7 +451,7 @@ impl Server { } } } - PacketS::Interact { pos, player } => { + PacketS::Interact { pos, player, hand } => { for e in &mut self.entities { if e.interact( EntityContext { @@ -473,7 +479,9 @@ impl Server { .get_mut(&pid) .ok_or(tre!("s.error.no_player"))?; - let (pos, edge) = match (pos, player.interacting) { + let pos = pos.map(|p| (p, hand)); + + let ((pos, hand), edge) = match (pos, player.interacting) { (None, None) => return Ok(()), // this is silent because of auto release (None, Some(pos)) => (pos, false), (Some(pos), None) => (pos, true), @@ -493,7 +501,7 @@ impl Server { // No going back from here on - player.interacting = if edge { Some(pos) } else { None }; + player.interacting = if edge { Some((pos, hand)) } else { None }; let other_pid = if !self.game.data.is_tile_interactable(tile.kind) { self.game @@ -524,10 +532,10 @@ impl Server { edge, None, Some(pid), - &mut this.item, - ItemLocation::Player(base_pid), - &mut other.item, - ItemLocation::Player(pid), + &mut this.items[hand.index()], + ItemLocation::Player(base_pid, hand), + &mut other.items[hand.index()], + ItemLocation::Player(pid, hand), &mut self.game.score, &mut self.score_changed, false, @@ -547,8 +555,8 @@ impl Server { Some(pid), &mut tile.item, ItemLocation::Tile(pos), - &mut player.item, - ItemLocation::Player(pid), + &mut player.items[hand.index()], + ItemLocation::Player(pid, hand), &mut self.game.score, &mut self.score_changed, false, @@ -588,14 +596,14 @@ impl Server { timeout, }); } - PacketS::ReplaceHand { item, player } => { + PacketS::ReplaceHand { item, player, hand } => { let pdata = self.game.players.get_mut(&player).ok_or(tre!(""))?; - pdata.item = item.map(|i| Item { + pdata.items[hand.index()] = item.map(|i| Item { kind: i, active: None, }); self.packet_out.push_back(PacketC::SetItem { - location: ItemLocation::Player(player), + location: ItemLocation::Player(player, hand), item, }) } @@ -661,17 +669,19 @@ impl Server { rot: player.movement.rotation, }); - tick_slot( - dt, - &self.game.data, - &self.gamedata_index, - None, - &mut player.item, - ItemLocation::Player(pid), - &mut self.game.score, - &mut self.score_changed, - &mut self.packet_out, - ); + for (i, item) in player.items.iter_mut().enumerate() { + tick_slot( + dt, + &self.game.data, + &self.gamedata_index, + None, + item, + ItemLocation::Player(pid, Hand::from_index(i)), + &mut self.game.score, + &mut self.score_changed, + &mut self.packet_out, + ); + } } let mut players_auto_release = Vec::new(); @@ -682,20 +692,27 @@ impl Server { player.communicate_persist = None; } } - if let Some(pos) = player.interacting { + if let Some((pos, hand)) = player.interacting { if let Some(tile) = self.game.tiles.get(&pos) { if let Some(item) = &tile.item { if let Some(involvement) = &item.active { if involvement.position >= 1. { - players_auto_release.push(*pid); + players_auto_release.push((*pid, hand)); } } } } } } - for player in players_auto_release.drain(..) { - let _ = self.packet_in(PacketS::Interact { pos: None, player }, &mut vec![]); + for (player, hand) in players_auto_release.drain(..) { + let _ = self.packet_in( + PacketS::Interact { + pos: None, + player, + hand, + }, + &mut vec![], + ); } let mut load_map = None; |