Skip to content

Commit

Permalink
feat: configurable time (#86)
Browse files Browse the repository at this point in the history
fixes #19
  • Loading branch information
Erb3 authored Jun 21, 2024
1 parent 66449ac commit 646edb0
Show file tree
Hide file tree
Showing 8 changed files with 82 additions and 46 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -62,3 +62,4 @@ Here are some resources to get you started with Socketioxide:
- [Posio](https://github.com/abrenaut/posio) by [Abrenaut](https://github.com/abrenaut)
- [JSON of cities](https://github.com/abrenaut/posio/blob/master/game/data/cities.json) by [Abrenaut](https://github.com/abrenaut)
- [Leaflet.js](https://leafletjs.com/)
- [Carto maps](https://carto.com/)
10 changes: 6 additions & 4 deletions frontend/game.js
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@ const distanceLine = L.polyline([], { color: "red" });
const distancePopup = L.popup();
const otherPlayerMarkers = [];
let canMoveMarker = false;
let guessingTime = 5;

map.on("click", (e) => {
if (!canMoveMarker) return;
Expand All @@ -77,7 +78,7 @@ socket.on("newTarget", (data) => {

targetElement.innerHTML = `${data.name}, ${data.country}`;
progressElement.style.width = "100%";
progressElement.style.transitionDuration = "5s";
progressElement.style.transitionDuration = guessingTime + "s";
canMoveMarker = true;
mapElement.classList.remove("cursor-grab");
map.setZoom(3);
Expand Down Expand Up @@ -125,12 +126,13 @@ socket.on("solution", (data) => {
mapElement.classList.add("cursor-grab");
});

socket.on("join-response", () => {
console.log("Connected!");
socket.on("game-metadata", (data) => {
console.log("Connected to game!", data);
guessingTime = data.guess_time;
});

socket.on("kick", (data) => {
console.log(data);
console.log("Kicked!", data);
location.href = "/?message=" + data.message;
});

Expand Down
9 changes: 9 additions & 0 deletions src/cli.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,15 @@ pub struct Cli {
/// Optional logging level to use. Default is info
#[arg(short, long, env = "SVEIO_LOGGING_LEVEL")]
pub logging: Option<LoggingLevel>,

/// Optional amount of seconds to allow guessing. Default is 7s
#[arg(long, env = "SVEIO_GUESS_TIME")]
pub guess_time: Option<u64>,

/// Optional amount of seconds where players can see where the others
/// guessed. Default is 3s
#[arg(long, env = "SVEIO_SHOWCASE_TIME")]
pub showcase_time: Option<u64>,
}

pub fn get_settings() -> Cli {
Expand Down
89 changes: 51 additions & 38 deletions src/game.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,12 @@ use socketioxide::extract::{Data, SocketRef, State};
use socketioxide::SocketIo;
use std::sync::Arc;
use std::time::Duration;
use tokio::time;
use tracing::{debug, info};

#[derive(Clone)]
pub struct GameOptions {
pub datasource: datasource::Datasource,
pub guess_time: u64,
pub showcase_time: u64,
}

pub fn on_connect(socket: SocketRef) {
Expand Down Expand Up @@ -53,7 +54,16 @@ pub fn on_connect(socket: SocketRef) {
.insert_player(socket.id, state::Player::new(data.username.clone()))
.await;

socket.emit("join-response", "").unwrap();
socket
.emit(
"game-metadata",
packets::GameMetadataMessage {
guess_time: state.options.guess_time,
showcase_time: state.options.showcase_time,
},
)
.unwrap();

socket.join("PRIMARY").unwrap();

info!(
Expand All @@ -79,45 +89,16 @@ pub fn on_connect(socket: SocketRef) {
}

pub async fn game_loop(opts: GameOptions, io: Arc<SocketIo>, state: state::GameState) {
let mut interval = time::interval(Duration::from_secs(5));
let mut last_city: Option<datasource::City> = None;
let guessing_time = Duration::from_secs(opts.guess_time);
let showcase_time = Duration::from_secs(opts.showcase_time);
let mut last_city: Option<datasource::City>;
let mut index = 0;
let datasource = datasource::new().await;

loop {
interval.tick().await;

if let Some(city) = last_city {
let target = Location::new(city.latitude, city.longitude);

for guess in state.get_guesses().await {
let packet = guess.1;
let distance =
target.distance_to(&geoutils::Location::new(packet.lat, packet.long));
let points = utils::calculate_score(distance.unwrap().meters() / 1000.0);

if let Some(existing_player) = state.get_player(guess.0).await {
let mut p = existing_player.to_owned();
p.score += points;
state.insert_player(guess.0, p).await;
}
}

let solution = packets::SolutionPacket {
location: city,
guesses: state.get_guesses().await,
leaderboard: state.get_players().await,
};

io.to("PRIMARY")
.emit("solution", solution)
.expect("Unable to broadcast solution");
}

interval.tick().await;

let city: &datasource::City = opts.datasource.cities.get(index).unwrap();
let city: &datasource::City = datasource.cities.get(index).unwrap();
index += 1;
if index == opts.datasource.cities.len() - 1 {
if index == datasource.cities.len() - 1 {
index = 0;
}

Expand Down Expand Up @@ -145,5 +126,37 @@ pub async fn game_loop(opts: GameOptions, io: Arc<SocketIo>, state: state::GameS
}
}
}

tokio::time::sleep(guessing_time).await;

if let Some(city) = last_city {
debug!("Announcing solutions");
let target = Location::new(city.latitude, city.longitude);

for guess in state.get_guesses().await {
let packet = guess.1;
let distance =
target.distance_to(&geoutils::Location::new(packet.lat, packet.long));
let points = utils::calculate_score(distance.unwrap().meters() / 1000.0);

if let Some(existing_player) = state.get_player(guess.0).await {
let mut p = existing_player.to_owned();
p.score += points;
state.insert_player(guess.0, p).await;
}
}

let solution = packets::SolutionPacket {
location: city,
guesses: state.get_guesses().await,
leaderboard: state.get_players().await,
};

io.to("PRIMARY")
.emit("solution", solution)
.expect("Unable to broadcast solution");
}

tokio::time::sleep(showcase_time).await;
}
}
6 changes: 4 additions & 2 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,8 @@ async fn main() -> Result<(), Box<dyn std::error::Error>> {

server::create_server(server::ServerOptions {
game: game::GameOptions {
datasource: datasource::new().await,
guess_time: settings.guess_time.unwrap_or(7),
showcase_time: settings.showcase_time.unwrap_or(3),
},
port: Some(settings.port.unwrap_or(8085)),
})
Expand All @@ -40,7 +41,8 @@ async fn main() -> shuttle_axum::ShuttleAxum {

Ok(server::create_server(server::ServerOptions {
game: game::GameOptions {
datasource: datasource::new().await,
guess_time: 7,
showcase_time: 3,
},
port: None,
})
Expand Down
6 changes: 6 additions & 0 deletions src/packets.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,12 @@ pub struct JoinMessage {
pub username: String,
}

#[derive(Serialize, Debug)]
pub struct GameMetadataMessage {
pub guess_time: u64,
pub showcase_time: u64,
}

#[derive(Serialize, Debug)]
pub struct DisconnectPacket {
pub message: String,
Expand Down
2 changes: 1 addition & 1 deletion src/server.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ pub struct ServerOptions {
}

pub async fn create_server(opts: ServerOptions) -> Option<axum::Router> {
let socketio_state = state::GameState::new();
let socketio_state = state::GameState::new(opts.game.clone());

let (socketio_layer, io) = SocketIoBuilder::new()
.with_state(socketio_state.clone())
Expand Down
5 changes: 4 additions & 1 deletion src/state.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
use crate::game::GameOptions;
use crate::packets;
use chrono::Utc;
use serde::{Deserialize, Serialize};
Expand Down Expand Up @@ -36,13 +37,15 @@ pub type PlayerMap = HashMap<Sid, Player>;
pub struct GameState {
guesses: Arc<RwLock<GuessMap>>,
players: Arc<RwLock<PlayerMap>>,
pub options: GameOptions,
}

impl GameState {
pub fn new() -> GameState {
pub fn new(options: GameOptions) -> GameState {
GameState {
guesses: Arc::new(RwLock::new(GuessMap::new())),
players: Arc::new(RwLock::new(PlayerMap::new())),
options,
}
}

Expand Down

0 comments on commit 646edb0

Please sign in to comment.