Skip to main content

gaming_systems/
gaming_systems.rs

1//! Gaming system examples for the dice-nom library.
2//!
3//! This example demonstrates how to use dice-nom for various tabletop RPG systems,
4//! showing real-world applications of the library's features.
5
6use dice_nom::parse;
7
8fn main() {
9    let mut rng = rand::rng();
10
11    println!("=== D&D 5th Edition Examples ===");
12
13    // Character creation - roll stats
14    println!("Rolling ability scores (4d6, drop lowest):");
15    for ability in ["STR", "DEX", "CON", "INT", "WIS", "CHA"] {
16        if let Ok(generator) = parse("4d6^3") {
17            let result = generator.generate(&mut rng);
18            println!("{}: {}", ability, result);
19        }
20    }
21
22    // Combat rolls
23    println!("\nCombat examples:");
24    let combat_rolls = vec![
25        ("Attack roll (d20+5)", "1d20+5"),
26        ("Damage (longsword)", "1d8+3"),
27        ("Sneak attack", "1d8+3+3d6"),
28        ("Fireball damage", "8d6"),
29        ("Healing potion", "2d4+2"),
30    ];
31
32    for (description, expr) in combat_rolls {
33        if let Ok(generator) = parse(expr) {
34            let result = generator.generate(&mut rng);
35            println!("{}: {}", description, result);
36        }
37    }
38
39    // Advantage/Disadvantage
40    println!("\nAdvantage and Disadvantage:");
41    let adv_dis_rolls = vec![
42        ("Attack with Advantage", "1d20ADV+5"),
43        ("Stealth with Disadvantage", "1d20DIS+2"),
44    ];
45
46    for (description, expr) in adv_dis_rolls {
47        if let Ok(generator) = parse(expr) {
48            let result = generator.generate(&mut rng);
49            println!("{}: {}", description, result);
50        }
51    }
52
53    println!("\n=== Call of Cthulhu  ===");
54
55    // Character creation - roll stats
56    println!("Generate statistics:");
57    let character_stats = vec![
58        ("STR (Strength)", "3d6x5"),
59        ("CON (Constitution)", "3d6x5"),
60        ("SIZ (Size)", "2d6+6x5"),
61        ("DEX (Dexterity)", "3d6x5"),
62        ("APP (Appearance)", "3d6x5"),
63        ("INT (Intelligence)", "2d6+6x5"),
64        ("POW (Power)", "3d6x5"),
65        ("EDU (Education)", "2d6+6x5"),
66        ("Luck", "3d6x5"),
67    ];
68
69    for (description, expr) in character_stats {
70        if let Ok(generator) = parse(expr) {
71            let result = generator.generate(&mut rng);
72            println!("{}: {}", description, result);
73        }
74    }
75
76    println!("\n=== World of Darkness Examples ===");
77
78    // Success counting system
79    let wod_rolls = vec![
80        ("Dexterity + Athletics (6 dice)", "6d10[6]"),
81        ("Manipulation + Subterfuge (4 dice)", "4d10[6]"),
82        ("Intelligence + Academics (7 dice)", "7d10[6]"),
83    ];
84
85    for (description, expr) in wod_rolls {
86        if let Ok(generator) = parse(expr) {
87            let result = generator.generate(&mut rng);
88            println!("{}: {} successes", description, result.lhs.hits());
89        }
90    }
91
92    println!("\n=== Shadowrun Examples ===");
93
94    // Edge cases and exploding dice
95    let shadowrun_rolls = vec![
96        ("Firearms skill test", "8d6[5]"),
97        ("Edge-enhanced roll", "8d6**[5]"),
98        ("Damage resistance", "6d6[5]"),
99    ];
100
101    for (description, expr) in shadowrun_rolls {
102        if let Ok(generator) = parse(expr) {
103            let result = generator.generate(&mut rng);
104            println!("{}: {} hits", description, result.lhs.hits());
105        }
106    }
107
108    println!("\n=== GURPS Examples ===");
109
110    // 3d6 roll-under system
111    let gurps_rolls = vec![
112        ("Skill check vs 12", "3d6 <= 12"),
113        ("Attribute check vs 14", "3d6 <= 14"),
114        ("Hard skill check vs 10", "3d6 <= 10"),
115    ];
116
117    for (description, expr) in gurps_rolls {
118        if let Ok(generator) = parse(expr) {
119            let result = generator.generate(&mut rng);
120            let success = result.sum() == 1;
121            println!(
122                "{}: {} ({})",
123                description,
124                result.lhs.sum(),
125                if success { "Success" } else { "Failure" }
126            );
127        }
128    }
129
130    println!("\n=== Fate/Fudge Examples ===");
131
132    // Fudge dice simulation using d3 (1=-, 2=blank, 3=+)
133    println!("Fate dice (simulated with d3s where 1=-, 2=0, 3=+):");
134    for i in 1..=3 {
135        if let Ok(generator) = parse("4d3--2") {
136            let result = generator.generate(&mut rng);
137            let fate_result = result.sum();
138            println!(
139                "Roll {}: {} ({})",
140                i,
141                result,
142                match fate_result {
143                    -4..=-3 => "Terrible",
144                    -2..=-1 => "Poor",
145                    0 => "Mediocre",
146                    1..=2 => "Good",
147                    3..=4 => "Great",
148                    _ => "Exceptional",
149                }
150            );
151        }
152    }
153
154    println!("\n=== Savage Worlds Examples ===");
155
156    // Exploding dice and Aces
157    let savage_worlds_rolls = vec![
158        ("Fighting with d8", "1d8!"),
159        ("Shooting with d10", "1d10!"),
160        ("Wild die + trait", "1d6! + 1d8!"),
161        ("Damage with d6+2", "1d6!+2"),
162    ];
163
164    for (description, expr) in savage_worlds_rolls {
165        if let Ok(generator) = parse(expr) {
166            let result = generator.generate(&mut rng);
167            let total = result.sum();
168            println!(
169                "{}: {} ({})",
170                description,
171                result,
172                if total >= 4 { "Success" } else { "Failure" }
173            );
174        }
175    }
176}