working with new login page, IOS is still a bit weird but it should just be HTML work
This commit is contained in:
10 files changed
+375
-187
No files matched your search
@@ -0,0 +1,66 @@
|
||||
use std::str::FromStr;
|
||||
|
||||
use thiserror::Error;
|
||||
|
||||
#[derive(Error, Debug)]
|
||||
pub enum CfgError {
|
||||
#[error("Unknown client type: '{0}'")]
|
||||
UnkownClientType(String),
|
||||
#[error("Missing cookie: '{0}'")]
|
||||
MissingCookie(String),
|
||||
#[error("Invalid cookie value: '{0}'")]
|
||||
InvalidCookie(String),
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
pub enum ClientType {
|
||||
Host,
|
||||
Player,
|
||||
}
|
||||
|
||||
impl FromStr for ClientType {
|
||||
type Err = CfgError;
|
||||
|
||||
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
||||
match s {
|
||||
"host" => Ok(Self::Host),
|
||||
"player" => Ok(Self::Player),
|
||||
_ => Err(CfgError::UnkownClientType(s.to_string())),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub struct Cfg {
|
||||
pub token: String,
|
||||
pub username: String,
|
||||
pub user_id: u64,
|
||||
pub game_code: String,
|
||||
pub client_type: ClientType,
|
||||
}
|
||||
|
||||
impl Cfg {
|
||||
pub fn load_from_cookies() -> Result<Self, CfgError> {
|
||||
let client_type = wasm_cookies::get_raw("play_of_the_game/client_type")
|
||||
.ok_or(CfgError::MissingCookie("client_type".to_string()))?;
|
||||
let token = wasm_cookies::get_raw("play_of_the_game/token")
|
||||
.ok_or(CfgError::MissingCookie("token".to_string()))?;
|
||||
let user_id = wasm_cookies::get_raw("play_of_the_game/user_id")
|
||||
.ok_or(CfgError::MissingCookie("user_id".to_string()))?
|
||||
.parse()
|
||||
.map_err(|_| CfgError::InvalidCookie("user_id".to_string()))?;
|
||||
let game_id = wasm_cookies::get_raw("play_of_the_game/game_code")
|
||||
.ok_or(CfgError::MissingCookie("game_id".to_string()))?;
|
||||
let username = wasm_cookies::get_raw("play_of_the_game/username")
|
||||
.ok_or(CfgError::MissingCookie("username".to_string()))?;
|
||||
|
||||
let client_type: ClientType = ClientType::from_str(&client_type)?;
|
||||
|
||||
Ok(Self {
|
||||
token,
|
||||
username,
|
||||
user_id,
|
||||
game_code: game_id,
|
||||
client_type,
|
||||
})
|
||||
}
|
||||
}
|
||||
+11
-3
@@ -2,22 +2,30 @@ use ewebsock::WsEvent;
|
||||
use macroquad::prelude::{error, info};
|
||||
use serde::{Serialize, de::DeserializeOwned};
|
||||
|
||||
use crate::cfg::{Cfg, ClientType};
|
||||
|
||||
pub struct Context {
|
||||
pub sender: ewebsock::WsSender,
|
||||
pub reciever: ewebsock::WsReceiver,
|
||||
pub token: String,
|
||||
pub username: String,
|
||||
pub user_id: u64,
|
||||
pub game_code: String,
|
||||
pub client_type: ClientType,
|
||||
}
|
||||
|
||||
impl Context {
|
||||
pub fn new(url: &str) -> Context {
|
||||
pub fn new(url: &str, cfg: Cfg) -> Context {
|
||||
let (sender, reciever) = ewebsock::connect(url, ewebsock::Options::default()).unwrap();
|
||||
|
||||
Self {
|
||||
sender,
|
||||
reciever,
|
||||
token: String::new(),
|
||||
username: String::new(),
|
||||
token: cfg.token,
|
||||
username: cfg.username,
|
||||
game_code: cfg.game_code,
|
||||
user_id: cfg.user_id,
|
||||
client_type: cfg.client_type,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -2,131 +2,77 @@ use crate::StateTransition;
|
||||
use crate::context::Context;
|
||||
use crate::font::FontSize;
|
||||
use crate::screen::Screen;
|
||||
use crate::ui_scaling::window_width;
|
||||
use macroquad::hash;
|
||||
use macroquad::ui::widgets::Window;
|
||||
use macroquad::{prelude::*, ui::root_ui};
|
||||
use macroquad::prelude::*;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Debug, Serialize)]
|
||||
pub struct JoinMessage {
|
||||
pub game_code: String,
|
||||
pub user_id: u64,
|
||||
pub token: String,
|
||||
}
|
||||
|
||||
#[derive(Debug, Serialize)]
|
||||
#[serde(tag = "type")]
|
||||
pub enum NewUserClientMessages {
|
||||
Register { game_code: String, username: String },
|
||||
CreateRoom { game_code: String, username: String },
|
||||
JoinAsPlayer(JoinMessage),
|
||||
JoinAsHost(JoinMessage),
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize)]
|
||||
#[serde(tag = "type")]
|
||||
pub enum NewUserServerMessages {
|
||||
RegisterResponse { username: String, token: String },
|
||||
HostRegisterResponse { username: String, token: String },
|
||||
RegisterResponse,
|
||||
HostRegisterResponse,
|
||||
}
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct LoginScreen {
|
||||
new_username: String,
|
||||
new_room_code: String,
|
||||
sent_join: bool,
|
||||
sent_host: bool,
|
||||
retry_count: usize,
|
||||
error_msg: bool,
|
||||
}
|
||||
|
||||
impl Screen for LoginScreen {
|
||||
fn handle_frame(&mut self, ctx: &mut Context) {
|
||||
clear_background(BEIGE);
|
||||
|
||||
let group_size = Vec2::new(window_width(), screen_height() * 0.05);
|
||||
let window_size = Vec2::new(window_width(), screen_height() * 0.4);
|
||||
|
||||
let mut pressed_join = false;
|
||||
let mut pressed_host = false;
|
||||
|
||||
Window::new(
|
||||
hash!("Window"),
|
||||
Vec2::new(
|
||||
screen_width() * 0.5 - window_size.x * 0.5,
|
||||
screen_height() * 0.5 - window_size.x * 0.5,
|
||||
),
|
||||
window_size,
|
||||
)
|
||||
.movable(false)
|
||||
.ui(&mut root_ui(), |ui| {
|
||||
ui.group(hash!("User Group"), group_size, |ui| {
|
||||
ui.input_text(hash!("Username In"), "Username", &mut self.new_username);
|
||||
});
|
||||
ui.group(hash!("Room Group"), group_size, |ui| {
|
||||
ui.input_text(hash!("Room Code In"), "Room Code", &mut self.new_room_code);
|
||||
});
|
||||
ui.group(hash!("Join Group"), group_size, |ui| {
|
||||
let dim = FontSize::Large.measure("Join");
|
||||
if ui.button(
|
||||
Vec2::new(group_size.x * 0.50, 0.0) - Vec2::new(dim.width * 0.5, 0.0),
|
||||
"Join",
|
||||
) {
|
||||
info!(
|
||||
"User pressed joined with name={} room_code={}",
|
||||
self.new_username, self.new_room_code
|
||||
);
|
||||
|
||||
pressed_join = true;
|
||||
}
|
||||
});
|
||||
ui.group(hash!("Host Group"), group_size, |ui| {
|
||||
let dim = FontSize::Large.measure("Host Game");
|
||||
if ui.button(
|
||||
Vec2::new(group_size.x * 0.50, 0.0) - Vec2::new(dim.width * 0.5, 0.0),
|
||||
"Host Game",
|
||||
) {
|
||||
info!(
|
||||
"User pressed host with name={} room_code={}",
|
||||
self.new_username, self.new_room_code
|
||||
);
|
||||
|
||||
pressed_host = true;
|
||||
}
|
||||
});
|
||||
|
||||
if self.error_msg {
|
||||
ui.group(hash!("Error Group"), group_size, |ui| {
|
||||
ui.label(Vec2::new(0.0, 0.0), "Failed to join game, try again...");
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
if pressed_join {
|
||||
ctx.send_msg(&NewUserClientMessages::Register {
|
||||
game_code: self.new_room_code.clone(),
|
||||
username: self.new_username.clone(),
|
||||
});
|
||||
draw_text(
|
||||
"Starting up...",
|
||||
screen_width() * 0.5,
|
||||
screen_height() * 0.5,
|
||||
FontSize::Large.size() as f32,
|
||||
BLACK,
|
||||
);
|
||||
|
||||
if !self.sent_join {
|
||||
self.sent_join = true;
|
||||
}
|
||||
|
||||
if pressed_host {
|
||||
ctx.send_msg(&NewUserClientMessages::CreateRoom {
|
||||
game_code: self.new_room_code.clone(),
|
||||
username: self.new_username.clone(),
|
||||
});
|
||||
let join_msg = JoinMessage {
|
||||
game_code: ctx.game_code.clone(),
|
||||
user_id: ctx.user_id,
|
||||
token: ctx.token.clone(),
|
||||
};
|
||||
|
||||
self.sent_host = true;
|
||||
let msg = match ctx.client_type {
|
||||
crate::cfg::ClientType::Host => NewUserClientMessages::JoinAsHost(join_msg),
|
||||
crate::cfg::ClientType::Player => NewUserClientMessages::JoinAsPlayer(join_msg),
|
||||
};
|
||||
|
||||
info!("Sending join request...");
|
||||
ctx.send_msg(&msg);
|
||||
}
|
||||
}
|
||||
|
||||
fn handle_messages(&mut self, ctx: &mut Context) -> Option<StateTransition> {
|
||||
if self.sent_join || self.sent_host {
|
||||
if self.sent_join {
|
||||
let msg = ctx.recv_msg();
|
||||
|
||||
if let Some(msg) = msg {
|
||||
match msg {
|
||||
NewUserServerMessages::RegisterResponse { username, token } => {
|
||||
ctx.username = username;
|
||||
ctx.token = token;
|
||||
NewUserServerMessages::RegisterResponse => {
|
||||
return Some(StateTransition::JoinAsPlayer);
|
||||
}
|
||||
NewUserServerMessages::HostRegisterResponse { username, token } => {
|
||||
ctx.username = username;
|
||||
ctx.token = token;
|
||||
NewUserServerMessages::HostRegisterResponse => {
|
||||
return Some(StateTransition::JoinAsHost);
|
||||
}
|
||||
}
|
||||
@@ -134,11 +80,10 @@ impl Screen for LoginScreen {
|
||||
|
||||
self.retry_count += 1;
|
||||
|
||||
if self.retry_count > get_fps() as usize * 5 {
|
||||
if self.retry_count > (get_fps() as usize * 100) {
|
||||
warn!("Join failed, try again...");
|
||||
self.retry_count = 0;
|
||||
self.sent_join = false;
|
||||
self.error_msg = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+24
-1
@@ -1,3 +1,4 @@
|
||||
use cfg::Cfg;
|
||||
use context::Context;
|
||||
use font::FontSize;
|
||||
use host_screen::HostScreen;
|
||||
@@ -9,6 +10,7 @@ use macroquad::{
|
||||
use player_screen::PlayerScreen;
|
||||
use screen::Screen;
|
||||
|
||||
mod cfg;
|
||||
mod context;
|
||||
mod font;
|
||||
mod host_screen;
|
||||
@@ -96,9 +98,30 @@ pub fn default_skin() -> Skin {
|
||||
}
|
||||
}
|
||||
|
||||
fn get_ws_url() -> String {
|
||||
let location = web_sys::window()
|
||||
.unwrap()
|
||||
.document()
|
||||
.unwrap()
|
||||
.location()
|
||||
.unwrap();
|
||||
|
||||
let protocol = if location.protocol().unwrap() == "https" {
|
||||
"wss"
|
||||
} else {
|
||||
"ws"
|
||||
};
|
||||
|
||||
format!("{}://{}/ws", protocol, location.host().unwrap())
|
||||
}
|
||||
|
||||
mod modname {}
|
||||
|
||||
#[macroquad::main("Play of the Game")]
|
||||
async fn main() {
|
||||
let mut context = Context::new("ws://127.0.0.1:8080/ws");
|
||||
let cfg = Cfg::load_from_cookies().unwrap();
|
||||
|
||||
let mut context = Context::new(&get_ws_url(), cfg);
|
||||
|
||||
let mut state = State::Init;
|
||||
state.transition_state(StateTransition::Init);
|
||||
|
||||
Reference in new issue
Block a user