start render other
This commit is contained in:
parent
8f606543f5
commit
1b5b7c9e77
8 changed files with 193 additions and 80 deletions
|
|
@ -3,6 +3,9 @@
|
||||||
lib,
|
lib,
|
||||||
...
|
...
|
||||||
}: rec {
|
}: rec {
|
||||||
|
env.RUST_LOG = "jong=trace";
|
||||||
|
env.RUST_BACKTRACE = "1";
|
||||||
|
|
||||||
# https://devenv.sh/processes/
|
# https://devenv.sh/processes/
|
||||||
processes.lspmux.exec = "lspmux server";
|
processes.lspmux.exec = "lspmux server";
|
||||||
processes.spacetimedb_start.exec = "spacetime start";
|
processes.spacetimedb_start.exec = "spacetime start";
|
||||||
|
|
@ -44,8 +47,6 @@
|
||||||
wayland
|
wayland
|
||||||
];
|
];
|
||||||
env.LD_LIBRARY_PATH = lib.makeLibraryPath packages;
|
env.LD_LIBRARY_PATH = lib.makeLibraryPath packages;
|
||||||
env.RUST_LOG = "jong=trace";
|
|
||||||
# env.RUST_BACKTRACE = "full";
|
|
||||||
|
|
||||||
# https://devenv.sh/languages/
|
# https://devenv.sh/languages/
|
||||||
languages.rust = {
|
languages.rust = {
|
||||||
|
|
|
||||||
|
|
@ -125,10 +125,41 @@ impl<'ctx> BotIdUnique<'ctx> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Access to the `config_id` unique index on the table `bot`,
|
||||||
|
/// which allows point queries on the field of the same name
|
||||||
|
/// via the [`BotConfigIdUnique::find`] method.
|
||||||
|
///
|
||||||
|
/// Users are encouraged not to explicitly reference this type,
|
||||||
|
/// but to directly chain method calls,
|
||||||
|
/// like `ctx.db.bot().config_id().find(...)`.
|
||||||
|
pub struct BotConfigIdUnique<'ctx> {
|
||||||
|
imp: __sdk::UniqueConstraintHandle<Bot, u32>,
|
||||||
|
phantom: std::marker::PhantomData<&'ctx super::RemoteTables>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'ctx> BotTableHandle<'ctx> {
|
||||||
|
/// Get a handle on the `config_id` unique index on the table `bot`.
|
||||||
|
pub fn config_id(&self) -> BotConfigIdUnique<'ctx> {
|
||||||
|
BotConfigIdUnique {
|
||||||
|
imp: self.imp.get_unique_constraint::<u32>("config_id"),
|
||||||
|
phantom: std::marker::PhantomData,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'ctx> BotConfigIdUnique<'ctx> {
|
||||||
|
/// Find the subscribed row whose `config_id` column value is equal to `col_val`,
|
||||||
|
/// if such a row is present in the client cache.
|
||||||
|
pub fn find(&self, col_val: &u32) -> Option<Bot> {
|
||||||
|
self.imp.find(col_val)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
pub(super) fn register_table(client_cache: &mut __sdk::ClientCache<super::RemoteModule>) {
|
pub(super) fn register_table(client_cache: &mut __sdk::ClientCache<super::RemoteModule>) {
|
||||||
let _table = client_cache.get_or_make_table::<Bot>("bot");
|
let _table = client_cache.get_or_make_table::<Bot>("bot");
|
||||||
_table.add_unique_constraint::<u32>("id", |row| &row.id);
|
_table.add_unique_constraint::<u32>("id", |row| &row.id);
|
||||||
|
_table.add_unique_constraint::<u32>("config_id", |row| &row.config_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
|
|
|
||||||
|
|
@ -40,6 +40,7 @@ impl __sdk::__query_builder::HasCols for Bot {
|
||||||
///
|
///
|
||||||
/// Provides typed access to indexed columns for query building.
|
/// Provides typed access to indexed columns for query building.
|
||||||
pub struct BotIxCols {
|
pub struct BotIxCols {
|
||||||
|
pub config_id: __sdk::__query_builder::IxCol<Bot, u32>,
|
||||||
pub id: __sdk::__query_builder::IxCol<Bot, u32>,
|
pub id: __sdk::__query_builder::IxCol<Bot, u32>,
|
||||||
pub lobby_id: __sdk::__query_builder::IxCol<Bot, u32>,
|
pub lobby_id: __sdk::__query_builder::IxCol<Bot, u32>,
|
||||||
}
|
}
|
||||||
|
|
@ -48,6 +49,7 @@ impl __sdk::__query_builder::HasIxCols for Bot {
|
||||||
type IxCols = BotIxCols;
|
type IxCols = BotIxCols;
|
||||||
fn ix_cols(table_name: &'static str) -> Self::IxCols {
|
fn ix_cols(table_name: &'static str) -> Self::IxCols {
|
||||||
BotIxCols {
|
BotIxCols {
|
||||||
|
config_id: __sdk::__query_builder::IxCol::new(table_name, "config_id"),
|
||||||
id: __sdk::__query_builder::IxCol::new(table_name, "id"),
|
id: __sdk::__query_builder::IxCol::new(table_name, "id"),
|
||||||
lobby_id: __sdk::__query_builder::IxCol::new(table_name, "lobby_id"),
|
lobby_id: __sdk::__query_builder::IxCol::new(table_name, "lobby_id"),
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -72,6 +72,7 @@ pub struct Bot {
|
||||||
#[index(btree)]
|
#[index(btree)]
|
||||||
pub lobby_id: u32,
|
pub lobby_id: u32,
|
||||||
|
|
||||||
|
#[unique]
|
||||||
pub config_id: u32,
|
pub config_id: u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -149,6 +150,9 @@ fn view_closed_hands(ctx: &ViewContext) -> Vec<HandView> {
|
||||||
.players
|
.players
|
||||||
.iter()
|
.iter()
|
||||||
.filter_map(|id| {
|
.filter_map(|id| {
|
||||||
|
if *id == this_player.config_id {
|
||||||
|
None
|
||||||
|
} else {
|
||||||
ctx.db
|
ctx.db
|
||||||
.player_hand()
|
.player_hand()
|
||||||
.player_id()
|
.player_id()
|
||||||
|
|
@ -157,8 +161,10 @@ fn view_closed_hands(ctx: &ViewContext) -> Vec<HandView> {
|
||||||
player_id: hand.player_id,
|
player_id: hand.player_id,
|
||||||
hand_length: hand.hand.len() as u8,
|
hand_length: hand.hand.len() as u8,
|
||||||
pond: hand.pond,
|
pond: hand.pond,
|
||||||
drawn: hand.turn_state == TurnState::Tsumo && hand.working_tile.is_some(),
|
drawn: hand.turn_state == TurnState::Tsumo
|
||||||
|
&& hand.working_tile.is_some(),
|
||||||
})
|
})
|
||||||
|
}
|
||||||
})
|
})
|
||||||
.collect()
|
.collect()
|
||||||
} else {
|
} else {
|
||||||
|
|
|
||||||
|
|
@ -64,8 +64,8 @@ impl Plugin for Riichi {
|
||||||
(
|
(
|
||||||
on_view_hand_insert,
|
on_view_hand_insert,
|
||||||
on_view_hand_update,
|
on_view_hand_update,
|
||||||
// on_view_closed_insert,
|
on_view_closed_insert,
|
||||||
// on_view_closed_update,
|
on_view_closed_update,
|
||||||
)
|
)
|
||||||
.after(on_player_config_insert_update)
|
.after(on_player_config_insert_update)
|
||||||
.run_if(in_state(GameState::Play).or(in_state(GameState::Deal))),
|
.run_if(in_state(GameState::Play).or(in_state(GameState::Deal))),
|
||||||
|
|
@ -315,66 +315,86 @@ fn sync_open_hand(
|
||||||
next_turnstate.set(player_hand.turn_state.into());
|
next_turnstate.set(player_hand.turn_state.into());
|
||||||
}
|
}
|
||||||
|
|
||||||
// fn on_view_closed_insert(
|
fn on_view_closed_insert(
|
||||||
// mut messages: ReadInsertMessage<jong_db::HandView>,
|
mut messages: ReadInsertMessage<jong_db::HandView>,
|
||||||
// mut commands: Commands,
|
mut commands: Commands,
|
||||||
// tiles: Query<(Entity, &TileId)>,
|
players: Populated<(Entity, &Player, Option<&Children>)>,
|
||||||
// hands: Query<(Entity, &Hand)>,
|
tiles: Query<(Entity, &TileId)>,
|
||||||
// ponds: Query<(Entity, &Pond)>,
|
hands: Query<(Entity, &Hand)>,
|
||||||
// ) {
|
ponds: Query<(Entity, &Pond)>,
|
||||||
// for msg in messages.read() {
|
) {
|
||||||
// sync_closed_hand(&mut commands, tiles, hands, ponds, &msg.row);
|
for msg in messages.read() {
|
||||||
// }
|
trace!("on_view_closed_insert");
|
||||||
// }
|
sync_closed_hand(&mut commands, &players, tiles, hands, ponds, &msg.row);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// fn on_view_closed_update(
|
fn on_view_closed_update(
|
||||||
// mut messages: ReadUpdateMessage<jong_db::HandView>,
|
mut messages: ReadUpdateMessage<jong_db::HandView>,
|
||||||
// mut commands: Commands,
|
mut commands: Commands,
|
||||||
// tiles: Query<(Entity, &TileId)>,
|
players: Populated<(Entity, &Player, Option<&Children>)>,
|
||||||
// hands: Query<(Entity, &Hand)>,
|
tiles: Query<(Entity, &TileId)>,
|
||||||
// ponds: Query<(Entity, &Pond)>,
|
hands: Query<(Entity, &Hand)>,
|
||||||
// ) {
|
ponds: Query<(Entity, &Pond)>,
|
||||||
// for msg in messages.read() {
|
) {
|
||||||
// sync_closed_hand(&mut commands, tiles, hands, ponds, &msg.new);
|
for msg in messages.read() {
|
||||||
// }
|
trace!("on_view_closed_update");
|
||||||
// }
|
sync_closed_hand(&mut commands, &players, tiles, hands, ponds, &msg.new);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// fn sync_closed_hand(
|
fn sync_closed_hand(
|
||||||
// commands: &mut Commands,
|
commands: &mut Commands,
|
||||||
// tiles: Query<(Entity, &TileId)>,
|
players: &Populated<(Entity, &Player, Option<&Children>)>,
|
||||||
// hands: Query<(Entity, &Hand)>,
|
tiles: Query<(Entity, &TileId)>,
|
||||||
// ponds: Query<(Entity, &Pond)>,
|
hands: Query<(Entity, &Hand)>,
|
||||||
// hand_view: &HandView,
|
ponds: Query<(Entity, &Pond)>,
|
||||||
// ) {
|
hand_view: &HandView,
|
||||||
// let player_id = hand_view.player_id;
|
) {
|
||||||
// let hand_ent = hands
|
let player_id = hand_view.player_id;
|
||||||
// .iter()
|
|
||||||
// .find_map(|(e, h)| (h.player_id == player_id).then_some(e))
|
|
||||||
// .unwrap_or_else(|| commands.spawn(Hand { player_id }).id());
|
|
||||||
// let pond_ent = ponds
|
|
||||||
// .iter()
|
|
||||||
// .find_map(|(e, p)| (p.player_id == player_id).then_some(e))
|
|
||||||
// .unwrap_or_else(|| commands.spawn(Pond { player_id }).id());
|
|
||||||
|
|
||||||
// let pond: Vec<Entity> = hand_view
|
let (player_ent, player_children) = players
|
||||||
// .pond
|
.iter()
|
||||||
// .iter()
|
.find_map(|(e, p, c)| (p.id == player_id).then_some((e, c)))
|
||||||
// .map(|dbt| {
|
.unwrap();
|
||||||
// tiles
|
|
||||||
// .iter()
|
|
||||||
// .find_map(|(e, i)| (i.0 == dbt.id).then_some(e))
|
|
||||||
// .unwrap_or_else(|| commands.spawn((Tile::from(&dbt.tile), TileId(dbt.id))).id())
|
|
||||||
// })
|
|
||||||
// .collect();
|
|
||||||
|
|
||||||
// commands.entity(hand_ent).insert(Closed {
|
let hand_ent = hands
|
||||||
// length: hand_view.hand_length,
|
.iter()
|
||||||
// });
|
.find_map(|(e, _)| player_children.is_some_and(|c| c.contains(&e)).then_some(e))
|
||||||
// commands.entity(pond_ent).replace_children(&pond);
|
.unwrap_or_else(|| {
|
||||||
|
let id = commands.spawn(Hand).id();
|
||||||
|
commands.entity(player_ent).add_child(id);
|
||||||
|
id
|
||||||
|
});
|
||||||
|
let pond_ent = ponds
|
||||||
|
.iter()
|
||||||
|
.find_map(|(e, _)| player_children.is_some_and(|c| c.contains(&e)).then_some(e))
|
||||||
|
.unwrap_or_else(|| {
|
||||||
|
let id = commands.spawn(Pond).id();
|
||||||
|
commands.entity(player_ent).add_child(id);
|
||||||
|
id
|
||||||
|
});
|
||||||
|
|
||||||
// if hand_view.drawn {
|
let pond: Vec<Entity> = hand_view
|
||||||
// commands.spawn(Drawn);
|
.pond
|
||||||
// } else {
|
.iter()
|
||||||
// // TODO clear Drawn from auto-discarded tile
|
.map(|dbt| {
|
||||||
// }
|
tiles
|
||||||
// }
|
.iter()
|
||||||
|
.find_map(|(e, i)| (i.0 == dbt.id).then_some(e))
|
||||||
|
.unwrap_or_else(|| commands.spawn((Tile::from(&dbt.tile), TileId(dbt.id))).id())
|
||||||
|
})
|
||||||
|
.collect();
|
||||||
|
|
||||||
|
commands.entity(hand_ent).insert(Closed {
|
||||||
|
length: hand_view.hand_length,
|
||||||
|
});
|
||||||
|
commands.entity(pond_ent).replace_children(&pond);
|
||||||
|
|
||||||
|
if hand_view.drawn {
|
||||||
|
let id = commands.spawn(Drawn).id();
|
||||||
|
commands.entity(player_ent).add_child(id);
|
||||||
|
} else {
|
||||||
|
// TODO clear Drawn from auto-discarded tile
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,3 @@
|
||||||
#![allow(unused)]
|
|
||||||
|
|
||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
use bevy::{app::ScheduleRunnerPlugin, prelude::*, state::app::StatesPlugin};
|
use bevy::{app::ScheduleRunnerPlugin, prelude::*, state::app::StatesPlugin};
|
||||||
|
|
@ -84,7 +82,7 @@ impl Plugin for TuiPlugin {
|
||||||
.add_systems(
|
.add_systems(
|
||||||
Update,
|
Update,
|
||||||
(
|
(
|
||||||
(render::render_main_hand, render::render_main_pond)
|
(render::render_main_hand, render::render_main_pond, render::render_other_hands)
|
||||||
.run_if(in_state(GameState::Play).or(in_state(GameState::Deal))),
|
.run_if(in_state(GameState::Play).or(in_state(GameState::Deal))),
|
||||||
render::render,
|
render::render,
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -7,9 +7,9 @@ use tui_logger::TuiWidgetEvent;
|
||||||
|
|
||||||
use jong::SpacetimeDB;
|
use jong::SpacetimeDB;
|
||||||
use jong_db::{
|
use jong_db::{
|
||||||
LobbyTableAccess, UserTableAccess, botQueryTableAccess,
|
LobbyTableAccess, UserTableAccess, botQueryTableAccess, join_or_create_lobby,
|
||||||
join_or_create_lobby, lobbyQueryTableAccess, player_clockQueryTableAccess,
|
lobbyQueryTableAccess, player_clockQueryTableAccess, player_configQueryTableAccess,
|
||||||
player_configQueryTableAccess, view_closed_handsQueryTableAccess, view_handQueryTableAccess,
|
view_closed_handsQueryTableAccess, view_handQueryTableAccess,
|
||||||
};
|
};
|
||||||
use jong_types::GameState;
|
use jong_types::GameState;
|
||||||
|
|
||||||
|
|
@ -78,6 +78,14 @@ pub(crate) fn keyboard(
|
||||||
.player_config()
|
.player_config()
|
||||||
.r#where(|pc| pc.id.eq(user.config_id))
|
.r#where(|pc| pc.id.eq(user.config_id))
|
||||||
})
|
})
|
||||||
|
.add_query(|q| {
|
||||||
|
q.from
|
||||||
|
.bot()
|
||||||
|
.r#where(|b| b.lobby_id.eq(lobby_id))
|
||||||
|
.right_semijoin(q.from.player_config(), |b, pc| {
|
||||||
|
b.config_id.eq(pc.id)
|
||||||
|
})
|
||||||
|
})
|
||||||
.add_query(|q| {
|
.add_query(|q| {
|
||||||
q.from
|
q.from
|
||||||
.player_clock()
|
.player_clock()
|
||||||
|
|
|
||||||
|
|
@ -7,7 +7,7 @@ use ratatui::style::{Color, Modifier, Style, Stylize};
|
||||||
use ratatui::text::{Line, Span, Text};
|
use ratatui::text::{Line, Span, Text};
|
||||||
use ratatui::widgets::{Block, Borders, Clear, Paragraph};
|
use ratatui::widgets::{Block, Borders, Clear, Paragraph};
|
||||||
|
|
||||||
use jong::riichi::player::*;
|
use jong::riichi::{Lobby, player::*};
|
||||||
use jong_types::*;
|
use jong_types::*;
|
||||||
|
|
||||||
use crate::tui::input::Hovered;
|
use crate::tui::input::Hovered;
|
||||||
|
|
@ -291,4 +291,51 @@ pub(crate) fn render_main_pond(
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn render_other_hands() {}
|
pub(crate) fn render_other_hands(
|
||||||
|
mut tui: ResMut<RatatuiContext>,
|
||||||
|
layouts: Res<HandLayouts>,
|
||||||
|
|
||||||
|
lobby: Res<Lobby>,
|
||||||
|
|
||||||
|
main_player: Single<&Player, With<MainPlayer>>,
|
||||||
|
players: Query<(&Player, &Children), Without<MainPlayer>>,
|
||||||
|
hands: Query<(Entity, &Closed)>,
|
||||||
|
ponds: Query<(Entity, &Children), With<Pond>>,
|
||||||
|
drawn: Option<Single<Entity, With<Drawn>>>,
|
||||||
|
) {
|
||||||
|
let mut frame = tui.get_frame();
|
||||||
|
|
||||||
|
let main_idx = lobby
|
||||||
|
.players
|
||||||
|
.iter()
|
||||||
|
.position(|id| *id == main_player.id)
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let mut player_it = lobby.players.iter().copied().cycle().skip(main_idx + 1);
|
||||||
|
|
||||||
|
let right_id = player_it.next().unwrap();
|
||||||
|
let top_id = player_it.next().unwrap();
|
||||||
|
let left_id = player_it.next().unwrap();
|
||||||
|
|
||||||
|
{
|
||||||
|
let children = players
|
||||||
|
.iter()
|
||||||
|
.find_map(|(p, c)| (p.id == right_id).then_some(c))
|
||||||
|
.unwrap();
|
||||||
|
let hand = hands
|
||||||
|
.iter()
|
||||||
|
.find_map(|(e, h)| children.contains(&e).then_some(h))
|
||||||
|
.unwrap();
|
||||||
|
// let pond = ponds
|
||||||
|
// .iter()
|
||||||
|
// .find_map(|(e, c)| children.contains(&e).then_some(c))
|
||||||
|
// .unwrap();
|
||||||
|
let drawn = drawn.is_some_and(|e| children.contains(&*e));
|
||||||
|
|
||||||
|
// let hand_draw_meld = Layout::vertical([
|
||||||
|
// Constraint::()
|
||||||
|
// ])
|
||||||
|
}
|
||||||
|
{}
|
||||||
|
{}
|
||||||
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue