From 36081213afcd95ca6942481544a772b38ec4d3b2 Mon Sep 17 00:00:00 2001 From: Ian Jackson Date: Fri, 27 Nov 2020 01:28:22 +0000 Subject: [PATCH] layout wip and also a todo Signed-off-by: Ian Jackson --- src/accounts.rs | 1 + src/api.rs | 4 ++++ src/bin/daemon-otter.rs | 9 ++++++--- src/bin/otter.rs | 21 ++++++++++++++++++++- src/cmdlistener.rs | 12 ++++++++++-- src/commands.rs | 1 + src/gamestate.rs | 1 + src/session.rs | 11 ++++++++--- 8 files changed, 51 insertions(+), 9 deletions(-) diff --git a/src/accounts.rs b/src/accounts.rs index 4c4743d5..789d019b 100644 --- a/src/accounts.rs +++ b/src/accounts.rs @@ -55,6 +55,7 @@ pub struct AccountRecord { pub nick: String, pub timezone: String, pub access: AccessRecord, + pub layout: PresentationLayout, } #[derive(Clone,Debug,Hash,Ord,PartialOrd,Eq,PartialEq)] diff --git a/src/api.rs b/src/api.rs index 64632f31..44dddf9d 100644 --- a/src/api.rs +++ b/src/api.rs @@ -36,6 +36,10 @@ impl PresentationLayout { } } +impl Default for PresentationLayout { + fn default() -> Self { PL::Portrait } +} + pub struct AbbrevPresentationLayout(pub PresentationLayout); impl<'r> FromParam<'r> for AbbrevPresentationLayout { diff --git a/src/bin/daemon-otter.rs b/src/bin/daemon-otter.rs index ab337ef4..78da71be 100644 --- a/src/bin/daemon-otter.rs +++ b/src/bin/daemon-otter.rs @@ -63,19 +63,22 @@ struct LoadingRenderContext<'r> { #[get("/")] #[throws(OE)] fn loading_p(ptoken: WholeQueryString) -> Template { - loading(PresentationLayout::Portrait, ptoken)? + loading(None, ptoken)? } // xxx also do p, make it an account/player property #[get("/")] #[throws(OE)] fn loading_l(layout: AbbrevPresentationLayout, ptoken: WholeQueryString) -> Template { - loading(layout.0, ptoken)? + loading(Some(layout.0), ptoken)? } #[throws(OE)] -fn loading(layout: PresentationLayout, ptoken: WholeQueryString) -> Template { +fn loading(layout: Option, ptoken: WholeQueryString) + -> Template +{ if let Some(ptoken) = ptoken.0 { + // xxx do something sensible if token mangled let c = LoadingRenderContext { ptoken: RawTokenVal::from_str(ptoken), layout, diff --git a/src/bin/otter.rs b/src/bin/otter.rs index c6967712..bebb70a9 100644 --- a/src/bin/otter.rs +++ b/src/bin/otter.rs @@ -21,6 +21,7 @@ type MR = MgmtResponse; type MGI = MgmtGameInstruction; type MGR = MgmtGameResponse; type TP = TablePermission; +type PL = PresentationLayout; use argparse::action::ParseResult::Parsed; @@ -65,6 +66,7 @@ struct MainOpts { account: AccountName, nick: Option, timezone: Option, + layout: Option, access: Option, socket_path: String, verbose: i32, @@ -255,6 +257,7 @@ fn main() { socket_path: Option, nick: Option, timezone: Option, + layout: Option, access: Option, verbose: i32, config_filename: Option, @@ -290,6 +293,20 @@ fn main() { StoreOption, "display times in timezone TZ (Olson timezone name) \ (default is to use server's default timezone)"); + let mut layout = ap.refer(&mut rma.layout); + layout.add_option( + &["--layout-portrait"], + StoreConst(Some(PL::Portrait)), + "set account to display in portrait (by default)"); + layout.add_option( + &["--layout-landscape"], + StoreConst(Some(PL::Landscape)), + "set account to display in landscape (by default)"); + layout.add_option( + &["--layout-default"], + StoreConst(None), + "do not modify default layout"); + let mut access = ap.refer(&mut rma.access); access.add_option(&["--url-on-stdout"], @@ -330,7 +347,7 @@ fn main() { }, &|RawMainArgs { account, nick, timezone, access, socket_path, verbose, config_filename, superuser, - subcommand, subargs, spec_dir, + subcommand, subargs, spec_dir, layout, }|{ let config = Thunk::,String),APE>,_>::new( move ||{ @@ -381,6 +398,7 @@ fn main() { access, nick, timezone, + layout, socket_path, verbose, superuser, @@ -456,6 +474,7 @@ impl Conn { account: ma.account.clone(), nick: wantup.u(&ma.nick), timezone: wantup.u(&ma.timezone), + layout: wantup.u(&ma.layout), access: wantup.u(&ma.access).map(Into::into), }; diff --git a/src/cmdlistener.rs b/src/cmdlistener.rs index 20acfe2f..691e238f 100644 --- a/src/cmdlistener.rs +++ b/src/cmdlistener.rs @@ -82,22 +82,28 @@ fn execute(cs: &mut CommandStream, cmd: MgmtCommand) -> MgmtResponse { Fine }, - CreateAccount(AccountDetails { account, nick, timezone, access }) => { + CreateAccount(AccountDetails { + account, nick, timezone, access, layout + }) => { let mut ag = AccountsGuard::lock(); let auth = authorise_for_account(cs, &ag, &account)?; let access = cs.accountrecord_from_spec(access)? .unwrap_or_else(|| AccessRecord::new_unset()); let nick = nick.unwrap_or_else(|| account.to_string()); let account = account.to_owned().into(); + let layout = layout.unwrap_or_default(); let record = AccountRecord { account, nick, access, timezone: timezone.unwrap_or_default(), + layout, }; ag.insert_entry(record, auth)?; Fine } - UpdateAccount(AccountDetails { account, nick, timezone, access }) => { + UpdateAccount(AccountDetails { + account, nick, timezone, access, layout + }) => { let mut ag = AccountsGuard::lock(); let mut games = games_lock(); let auth = authorise_for_account(cs, &ag, &account)?; @@ -108,6 +114,7 @@ fn execute(cs: &mut CommandStream, cmd: MgmtCommand) -> MgmtResponse { } update_from(nick, &mut record.nick ); update_from(timezone, &mut record.timezone); + update_from(layout, &mut record.layout ); /* if let Some(new_timezone) = timezone { let ipr = ig.iplayers.byid_mut(player)?; @@ -321,6 +328,7 @@ fn execute_game_insn<'cs, 'igr, 'ig : 'igr>( let tz = tz_from_str(&timezone); let gpl = GPlayerState { nick: nick.to_string(), + layout: arecord.layout, }; let ipl = IPlayerState { acctid, diff --git a/src/commands.rs b/src/commands.rs index 04778024..1e08f922 100644 --- a/src/commands.rs +++ b/src/commands.rs @@ -44,6 +44,7 @@ pub struct AccountDetails { pub account: AccountName, pub nick: Option, pub timezone: Option, + pub layout: Option, #[serde(flatten)] pub access: Option>, // pub invite: Acl, todo diff --git a/src/gamestate.rs b/src/gamestate.rs index b9395a4b..b4edba3a 100644 --- a/src/gamestate.rs +++ b/src/gamestate.rs @@ -52,6 +52,7 @@ pub struct GameState { #[derive(Debug,Serialize,Deserialize,Clone)] pub struct GPlayerState { pub nick: String, + pub layout: PresentationLayout, } #[derive(Debug,Serialize,Deserialize)] diff --git a/src/session.rs b/src/session.rs index f42babbb..73e6dbec 100644 --- a/src/session.rs +++ b/src/session.rs @@ -56,12 +56,12 @@ struct SessionForm { ptoken : RawToken, } #[post("/_/session/", format="json", data="
")] -fn session(form : Json, layout: PresentationLayout) +fn session(form : Json, layout: Option) -> Result { // make session in this game, log a message to other players let iad = lookup_token(form.ptoken.borrow())?; let player = iad.ident; - let (c, client) = { + let (c, client, layout) = { let mut ig = iad.gref.lock()?; let cl = Client { player, lastseen: Instant::now() }; let client = ig.clients.insert(cl); @@ -72,6 +72,7 @@ fn session(form : Json, layout: PresentationLayout) acctid: iad.acctid, }; let ctoken = record_token(&mut ig, ciad)?; + ig.save_game_later(); // in case we changed anything eg gpl.layout let ig = &mut *ig; let mut uses = vec![]; @@ -101,6 +102,10 @@ fn session(form : Json, layout: PresentationLayout) let gpl = ig.gs.players.byid_mut(player)?; let pr = ig.iplayers.byid(player)?; let tz = &pr.ipl.tz; + if let Some(layout) = layout { + gpl.layout = layout; + } + let layout = gpl.layout; let mut pieces : Vec<_> = ig.gs.pieces.iter().collect(); pieces.sort_by_key(|(_,pr)| &pr.zlevel); @@ -196,7 +201,7 @@ fn session(form : Json, layout: PresentationLayout) }).map_err(|e| InternalError::JSONEncode(e))?, }; trace!("SessionRenderContext {:?}", &src); - (src, client) + (src, client, layout) }; info!("rendering /_/session for {:?} {:?} {:?} {:?} {:?}", &player, client, &c.nick, &c.ctoken, -- 2.30.2