Compare commits

..

2 commits

Author SHA1 Message Date
Tao Tien
3143e5964b 2026-02-15 06:08:54 -08:00
Tao Tien
042975e561 begin jiang 2026-02-14 18:07:33 -08:00
7 changed files with 135 additions and 16 deletions

14
Cargo.lock generated
View file

@ -3337,6 +3337,12 @@ dependencies = [
"byteorder",
]
[[package]]
name = "hashbag"
version = "0.1.13"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7040a10f52cba493ddb09926e15d10a9d8a28043708a405931fe4c6f19fac064"
[[package]]
name = "hashbrown"
version = "0.12.3"
@ -3710,6 +3716,14 @@ version = "1.0.17"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "92ecc6618181def0457392ccd0ee51198e065e016d1d527a7ac1b6dc7c1f09d2"
[[package]]
name = "jiang"
version = "0.1.0"
dependencies = [
"hashbag",
"jong-types",
]
[[package]]
name = "jni"
version = "0.21.1"

View file

@ -1,6 +1,6 @@
[workspace]
resolver = "3"
members = ["jong", "jong-types", "spacetimedb"]
members = ["jiang","jong", "jong-types", "spacetimedb"]
[workspace.dependencies]
jong = { version = "0.1.0", path = "jong" }

8
jiang/Cargo.toml Normal file
View file

@ -0,0 +1,8 @@
[package]
name = "jiang"
version = "0.1.0"
edition = "2024"
[dependencies]
hashbag = "0.1.13"
jong-types.workspace = true

62
jiang/src/lib.rs Normal file
View file

@ -0,0 +1,62 @@
use std::collections::HashMap;
use hashbag::HashBag;
use jong_types::*;
// pub fn check_valid() {}
pub enum Meldable {
Chii(Tile, Tile),
Pon,
Kan,
}
pub fn find_meldables(hand: &[Tile], dealt: Tile) -> Vec<Meldable> {
let counts = hand.iter().fold(HashMap::new(), |mut m, t| {
let e = m.entry(t).or_insert(0);
*e += 1;
m
});
let mut calls = vec![];
// find pon & kan
if let Some(&count) = counts.get(&dealt) {
if count == 3 {
calls.push(Meldable::Kan)
} else if count == 2 {
calls.push(Meldable::Pon)
}
}
// find chii
if let Some(next_outer) = dealt.next_rank() {
if let Some(next_inner) = next_outer.next_rank()
&& counts.contains_key(&next_outer)
&& counts.contains_key(&next_inner)
{
calls.push(Meldable::Chii(next_outer, next_inner));
}
if let Some(prev_inner) = next_outer.prev_rank()
&& counts.contains_key(&next_outer)
&& counts.contains_key(&prev_inner)
{
calls.push(Meldable::Chii(next_outer, prev_inner));
}
}
if let Some(prev_outer) = dealt.prev_rank()
&& let Some(prev_inner) = prev_outer.prev_rank()
&& counts.contains_key(&prev_outer)
&& counts.contains_key(&prev_inner)
{
calls.push(Meldable::Chii(prev_outer, prev_inner));
}
calls
}
pub fn check_ron(hand: &[Tile], melds: &[&[Tile]]) {
let bag: HashBag<Tile> = HashBag::from_iter(hand.iter().cloned());
}

View file

@ -4,7 +4,7 @@ mod derive_alias {
Eq = ::core::cmp::PartialEq, ::core::cmp::Eq;
Ord = ..Eq, ::core::cmp::PartialOrd, ::core::cmp::PartialEq, ::core::cmp::Ord;
Base = ::core::fmt::Debug, ..Copy, ..Ord;
Base = ::core::fmt::Debug, ..Copy, ..Ord, ::core::hash::Hash;
}
}
use derive_aliases::derive;
@ -13,7 +13,7 @@ use bevy::prelude::*;
use spacetimedb::SpacetimeType;
use strum::{EnumCount, FromRepr};
#[derive(..Base, Hash, Default, FromRepr)]
#[derive(..Base, Default, FromRepr)]
#[derive(States, SpacetimeType)]
pub enum GameState {
#[default]
@ -41,18 +41,6 @@ pub enum Suit {
Dragon(Dragon),
}
impl Suit {
pub fn rank(&self) -> Option<Rank> {
match self {
Suit::Man(rank) => Some(*rank),
Suit::Pin(rank) => Some(*rank),
Suit::Sou(rank) => Some(*rank),
// Suit::Wind(wind) | Suit::Dragon(dragon) => None,
_ => None,
}
}
}
#[derive(
..Base,
Deref,
@ -63,6 +51,49 @@ pub struct Rank {
pub number: u8,
}
impl Tile {
pub fn next_rank(self) -> Option<Self> {
match self.suit {
Suit::Man(rank) if rank.number < 9 => Some(Tile {
suit: Suit::Man(Rank {
number: rank.number + 1,
}),
}),
Suit::Pin(rank) if rank.number < 9 => Some(Tile {
suit: Suit::Pin(Rank {
number: rank.number + 1,
}),
}),
Suit::Sou(rank) if rank.number < 9 => Some(Tile {
suit: Suit::Sou(Rank {
number: rank.number + 1,
}),
}),
_ => None,
}
}
pub fn prev_rank(self) -> Option<Self> {
match self.suit {
Suit::Man(rank) if rank.number > 1 => Some(Tile {
suit: Suit::Man(Rank {
number: rank.number - 1,
}),
}),
Suit::Pin(rank) if rank.number > 1 => Some(Tile {
suit: Suit::Pin(Rank {
number: rank.number - 1,
}),
}),
Suit::Sou(rank) if rank.number > 1 => Some(Tile {
suit: Suit::Sou(Rank {
number: rank.number - 1,
}),
}),
_ => None,
}
}
}
#[derive(
..Base,
FromRepr,

View file

@ -227,7 +227,9 @@ fn on_lobby_insert_update(
}
stdb::TurnState::Menzen => todo!(),
stdb::TurnState::RiichiKan => todo!(),
stdb::TurnState::Discard => todo!(),
stdb::TurnState::Discard => {
// TODO check if can call reducer here maybe?
}
stdb::TurnState::RonChiiPonKan => todo!(),
stdb::TurnState::End => todo!(),
}

View file

@ -4,6 +4,7 @@ use spacetimedb::{SpacetimeType, table};
use super::DbTile;
// FIXME this shant be public, use views
// TODO split up tables so we aren't sending this over the wire every update, or is differencial handled already
#[table(name = player, public)]
#[derive(Debug)]
pub struct Player {
@ -26,6 +27,7 @@ pub struct Player {
pub pond: Vec<DbTile>,
pub drawn_tile: Option<DbTile>,
pub actionable: Option<()>,
}
#[table(name = bot)]