mirror of
https://github.com/coding-horror/basic-computer-games.git
synced 2025-12-23 07:29:02 -08:00
implemented taking damage and dying
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
use crate::model::{Galaxy, Pos, SectorStatus, COURSES};
|
||||
use crate::model::{Galaxy, Pos, SectorStatus, COURSES, Quadrant};
|
||||
|
||||
pub fn short_range_scan(model: &Galaxy) {
|
||||
let quadrant = &model.quadrants[model.enterprise.quadrant.as_index()];
|
||||
@@ -35,7 +35,7 @@ pub fn short_range_scan(model: &Galaxy) {
|
||||
}
|
||||
|
||||
pub fn move_enterprise(course: u8, warp_speed: f32, galaxy: &mut Galaxy) {
|
||||
|
||||
|
||||
let end = find_end_quadrant_sector(galaxy.enterprise.quadrant, galaxy.enterprise.sector, course, warp_speed);
|
||||
|
||||
if end.hit_edge {
|
||||
|
||||
@@ -2,6 +2,8 @@ use std::{io::{stdin, stdout, Write}, process::exit, str::FromStr};
|
||||
|
||||
use model::Galaxy;
|
||||
|
||||
use crate::model::Condition;
|
||||
|
||||
mod model;
|
||||
mod commands;
|
||||
|
||||
@@ -10,7 +12,7 @@ fn main() {
|
||||
.expect("Error setting Ctrl-C handler");
|
||||
|
||||
let mut galaxy = Galaxy::generate_new();
|
||||
// init options, starting state and notes
|
||||
// todo: init options, starting state and notes
|
||||
commands::short_range_scan(&galaxy);
|
||||
|
||||
loop {
|
||||
@@ -19,6 +21,14 @@ fn main() {
|
||||
"NAV" => gather_dir_and_speed_then_move(&mut galaxy),
|
||||
_ => print_command_help()
|
||||
}
|
||||
|
||||
if galaxy.enterprise.condition == Condition::Destroyed { // todo: also check if stranded
|
||||
println!("Is is stardate {}.
|
||||
There were {} Klingon battle cruisers left at
|
||||
the end of your mission.
|
||||
", galaxy.stardate, galaxy.remaining_klingons());
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -37,6 +47,21 @@ fn gather_dir_and_speed_then_move(galaxy: &mut Galaxy) {
|
||||
return;
|
||||
}
|
||||
|
||||
let quadrant = &mut galaxy.quadrants[galaxy.enterprise.quadrant.as_index()];
|
||||
for k in 0..quadrant.klingons.len() {
|
||||
let new_sector = quadrant.find_empty_sector();
|
||||
quadrant.klingons[k].sector = new_sector;
|
||||
}
|
||||
|
||||
// todo: check if enterprise is protected by a starbase
|
||||
|
||||
for k in 0..quadrant.klingons.len() {
|
||||
quadrant.klingons[k].fire_on(&mut galaxy.enterprise);
|
||||
}
|
||||
|
||||
if galaxy.enterprise.condition == Condition::Destroyed {
|
||||
return;
|
||||
}
|
||||
commands::move_enterprise(course.unwrap(), speed.unwrap(), galaxy);
|
||||
}
|
||||
|
||||
|
||||
@@ -15,7 +15,21 @@ pub struct Quadrant {
|
||||
}
|
||||
|
||||
pub struct Klingon {
|
||||
pub sector: Pos
|
||||
pub sector: Pos,
|
||||
energy: f32
|
||||
}
|
||||
|
||||
impl Klingon {
|
||||
pub fn fire_on(&mut self, enterprise: &mut Enterprise) {
|
||||
let mut rng = rand::thread_rng();
|
||||
let attack_strength = rng.gen::<f32>();
|
||||
let dist_to_enterprise = self.sector.abs_diff(enterprise.sector) as f32;
|
||||
let hit_strength = self.energy * (2.0 + attack_strength) / dist_to_enterprise;
|
||||
|
||||
self.energy /= 3.0 + attack_strength;
|
||||
|
||||
enterprise.take_hit(self.sector, hit_strength as u16);
|
||||
}
|
||||
}
|
||||
|
||||
pub struct Enterprise {
|
||||
@@ -26,10 +40,30 @@ pub struct Enterprise {
|
||||
pub total_energy: u16,
|
||||
pub shields: u16,
|
||||
}
|
||||
impl Enterprise {
|
||||
fn take_hit(&mut self, sector: Pos, hit_strength: u16) {
|
||||
if self.condition == Condition::Destroyed {
|
||||
return;
|
||||
}
|
||||
|
||||
println!("{hit_strength} unit hit on Enterprise from sector {sector}");
|
||||
|
||||
#[derive(Debug)]
|
||||
// absorb into shields
|
||||
|
||||
if self.shields <= 0 {
|
||||
println!("The Enterprise has been destroyed. The Federation will be conquered.");
|
||||
self.condition = Condition::Destroyed;
|
||||
}
|
||||
|
||||
// report shields
|
||||
// take damage if strength is greater than 20
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(PartialEq, Debug)]
|
||||
pub enum Condition {
|
||||
Green, Yellow, Red
|
||||
Green, Yellow, Red,
|
||||
Destroyed,
|
||||
}
|
||||
|
||||
#[derive(PartialEq, Clone, Copy, Debug)]
|
||||
@@ -39,6 +73,10 @@ impl Pos {
|
||||
pub fn as_index(&self) -> usize {
|
||||
(self.0 * 8 + self.1).into()
|
||||
}
|
||||
|
||||
fn abs_diff(&self, other: Pos) -> u8 {
|
||||
self.0.abs_diff(other.0) + self.1.abs_diff(other.1)
|
||||
}
|
||||
}
|
||||
|
||||
impl Mul<u8> for Pos {
|
||||
@@ -128,7 +166,7 @@ impl Galaxy {
|
||||
_ => 0
|
||||
};
|
||||
for _ in 0..klingon_count {
|
||||
quadrant.klingons.push(Klingon { sector: quadrant.find_empty_sector() });
|
||||
quadrant.klingons.push(Klingon { sector: quadrant.find_empty_sector(), energy: rng.gen_range(100..=300) as f32 });
|
||||
}
|
||||
|
||||
result.push(quadrant);
|
||||
@@ -162,7 +200,7 @@ impl Quadrant {
|
||||
klingons.into_iter().find(|k| &k.sector == sector).is_some()
|
||||
}
|
||||
|
||||
fn find_empty_sector(&self) -> Pos {
|
||||
pub fn find_empty_sector(&self) -> Pos {
|
||||
let mut rng = rand::thread_rng();
|
||||
loop {
|
||||
let pos = Pos(rng.gen_range(0..8), rng.gen_range(0..8));
|
||||
@@ -171,4 +209,4 @@ impl Quadrant {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,6 +2,11 @@
|
||||
|
||||
Started after movement and display of stats was finished (no energy management or collision detection or anything).
|
||||
|
||||
- [ ] stop before hitting an object
|
||||
- [x] klingon movement
|
||||
- [x] klingon firing, game over etc
|
||||
- [ ] remove energy on move
|
||||
- [ ] klingon movement
|
||||
- [ ] shields
|
||||
- [ ] stranded...
|
||||
- [ ] stop before hitting an object
|
||||
- when moving across a sector, the enterprise should stop before it runs into something
|
||||
- the current move is a jump, which makes this problematic. would need to rewrite it
|
||||
|
||||
Reference in New Issue
Block a user