From d608f1749f26279772cfde92d8224c46d0c6e556 Mon Sep 17 00:00:00 2001 From: omagdy7 Date: Tue, 6 Sep 2022 20:40:09 +0200 Subject: Made that you could quit whilist animating --- .gitignore | 2 + Cargo.lock | 321 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Cargo.toml | 11 +++ src/main.rs | 164 +++++++++++++++++++++++++++++++ 4 files changed, 498 insertions(+) create mode 100644 .gitignore create mode 100644 Cargo.lock create mode 100644 Cargo.toml create mode 100644 src/main.rs diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..81cf465 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +/target +/.vscode diff --git a/Cargo.lock b/Cargo.lock new file mode 100644 index 0000000..3c28701 --- /dev/null +++ b/Cargo.lock @@ -0,0 +1,321 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "atty" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8" +dependencies = [ + "hermit-abi", + "libc", + "winapi", +] + +[[package]] +name = "autocfg" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" + +[[package]] +name = "bitflags" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" + +[[package]] +name = "cfg-if" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" + +[[package]] +name = "colored" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b3616f750b84d8f0de8a58bda93e08e2a81ad3f523089b05f1dffecab48c6cbd" +dependencies = [ + "atty", + "lazy_static", + "winapi", +] + +[[package]] +name = "crossterm" +version = "0.25.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e64e6c0fbe2c17357405f7c758c1ef960fce08bdfb2c03d88d2a18d7e09c4b67" +dependencies = [ + "bitflags", + "crossterm_winapi", + "libc", + "mio", + "parking_lot", + "signal-hook", + "signal-hook-mio", + "winapi", +] + +[[package]] +name = "crossterm_winapi" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2ae1b35a484aa10e07fe0638d02301c5ad24de82d310ccbd2f3693da5f09bf1c" +dependencies = [ + "winapi", +] + +[[package]] +name = "getrandom" +version = "0.2.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4eb1a864a501629691edf6c15a593b7a51eebaa1e8468e9ddc623de7c9b58ec6" +dependencies = [ + "cfg-if", + "libc", + "wasi", +] + +[[package]] +name = "gof-rs" +version = "0.1.0" +dependencies = [ + "colored", + "crossterm", + "rand", +] + +[[package]] +name = "hermit-abi" +version = "0.1.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33" +dependencies = [ + "libc", +] + +[[package]] +name = "lazy_static" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" + +[[package]] +name = "libc" +version = "0.2.132" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8371e4e5341c3a96db127eb2465ac681ced4c433e01dd0e938adbef26ba93ba5" + +[[package]] +name = "lock_api" +version = "0.4.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9f80bf5aacaf25cbfc8210d1cfb718f2bf3b11c4c54e5afe36c236853a8ec390" +dependencies = [ + "autocfg", + "scopeguard", +] + +[[package]] +name = "log" +version = "0.4.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "abb12e687cfb44aa40f41fc3978ef76448f9b6038cad6aef4259d3c095a2382e" +dependencies = [ + "cfg-if", +] + +[[package]] +name = "mio" +version = "0.8.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57ee1c23c7c63b0c9250c339ffdc69255f110b298b901b9f6c82547b7b87caaf" +dependencies = [ + "libc", + "log", + "wasi", + "windows-sys", +] + +[[package]] +name = "parking_lot" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" +dependencies = [ + "lock_api", + "parking_lot_core", +] + +[[package]] +name = "parking_lot_core" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09a279cbf25cb0757810394fbc1e359949b59e348145c643a939a525692e6929" +dependencies = [ + "cfg-if", + "libc", + "redox_syscall", + "smallvec", + "windows-sys", +] + +[[package]] +name = "ppv-lite86" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eb9f9e6e233e5c4a35559a617bf40a4ec447db2e84c20b55a6f83167b7e57872" + +[[package]] +name = "rand" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" +dependencies = [ + "libc", + "rand_chacha", + "rand_core", +] + +[[package]] +name = "rand_chacha" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" +dependencies = [ + "ppv-lite86", + "rand_core", +] + +[[package]] +name = "rand_core" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d34f1408f55294453790c48b2f1ebbb1c5b4b7563eb1f418bcfcfdbb06ebb4e7" +dependencies = [ + "getrandom", +] + +[[package]] +name = "redox_syscall" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb5a58c1855b4b6819d59012155603f0b22ad30cad752600aadfcb695265519a" +dependencies = [ + "bitflags", +] + +[[package]] +name = "scopeguard" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" + +[[package]] +name = "signal-hook" +version = "0.3.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a253b5e89e2698464fc26b545c9edceb338e18a89effeeecfea192c3025be29d" +dependencies = [ + "libc", + "signal-hook-registry", +] + +[[package]] +name = "signal-hook-mio" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "29ad2e15f37ec9a6cc544097b78a1ec90001e9f71b81338ca39f430adaca99af" +dependencies = [ + "libc", + "mio", + "signal-hook", +] + +[[package]] +name = "signal-hook-registry" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e51e73328dc4ac0c7ccbda3a494dfa03df1de2f46018127f60c693f2648455b0" +dependencies = [ + "libc", +] + +[[package]] +name = "smallvec" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2fd0db749597d91ff862fd1d55ea87f7855a744a8425a64695b6fca237d1dad1" + +[[package]] +name = "wasi" +version = "0.11.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" + +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + +[[package]] +name = "windows-sys" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2" +dependencies = [ + "windows_aarch64_msvc", + "windows_i686_gnu", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_msvc", +] + +[[package]] +name = "windows_aarch64_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47" + +[[package]] +name = "windows_i686_gnu" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6" + +[[package]] +name = "windows_i686_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680" diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000..3e36dcb --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,11 @@ +[package] +name = "gof-rs" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +colored = "2.0.0" +crossterm = "0.25.0" +rand = "0.8.5" diff --git a/src/main.rs b/src/main.rs new file mode 100644 index 0000000..3e20d50 --- /dev/null +++ b/src/main.rs @@ -0,0 +1,164 @@ +#![allow(unused_imports, unused_variables, unused_mut)] + +use colored::Colorize; +use crossterm::cursor::{Hide, MoveTo, Show}; +use crossterm::event::{Event, KeyCode, KeyEvent, poll}; +use crossterm::style::Stylize; +use crossterm::terminal::*; +use crossterm::{event, terminal, ExecutableCommand, QueueableCommand}; +use rand::{thread_rng, Rng}; +use std::io::{self, Write}; +use std::thread::sleep; +use std::time::Duration; + +type Gen = Vec>; + +#[derive(Clone, Copy, Debug)] +enum Cell { + Alive, + Dead, +} + +fn render_gen(stdout: &mut io::Stdout, gen: &Gen) { + for i in 0..gen.len() { + for j in 0..gen[0].len() { + stdout.queue(MoveTo(i as u16, j as u16)).unwrap(); + match gen[i][j] { + // Cell::Alive => print!("😎"), + // Cell::Alive => print!("🦀"), + Cell::Alive => print!("{}", "X".color("blue")), + Cell::Dead => print!("{}", "-".color("red")), + } + stdout.flush().unwrap(); + } + } +} + +fn new_gen() -> Gen { + let cells = vec![Cell::Dead, Cell::Dead, Cell::Alive, Cell::Dead, Cell::Alive]; + let rows: u16 = terminal::size().unwrap().1; + let cols: u16 = terminal::size().unwrap().0; + let mut colums: Vec> = Vec::new(); + for _ in 0..cols { + let mut col: Vec = Vec::new(); + for _ in 0..rows { + let rand = thread_rng().gen_range(0..10); + col.push(cells[rand % 5]); + } + colums.push(col); + } + colums +} + +fn is_valid_idx(i: i32, j: i32, m: i32, n: i32) -> bool { + i >= 0 && i < m && j >= 0 && j < n +} + +fn get_alive(x: i32, y: i32, cur_gen: &Gen) -> i32 { + let mut alive_cnt: i32 = 0; + + let m: i32 = cur_gen.len() as i32; + let n: i32 = cur_gen[0].len() as i32; + let dx: [i8; 8] = [0, 1, 0, -1, 1, -1, -1, 1]; + let dy: [i8; 8] = [1, 0, -1, 0, 1, -1, 1, -1]; + + for i in 0..8 { + let nx: i32 = x as i32 + dx[i] as i32; + let ny: i32 = y as i32 + dy[i] as i32; + if is_valid_idx(nx, ny, m, n) { + let cur_cell = cur_gen[nx as usize][ny as usize]; + match cur_cell { + Cell::Alive => alive_cnt += 1, + Cell::Dead => (), + } + } + } + + alive_cnt +} + +fn next_gen(cur_gen: &mut Gen) -> Gen { + let m: i32 = cur_gen.len() as i32; + let n: i32 = cur_gen[0].len() as i32; + let mut nxt_gen: Gen = Gen::new(); + for _ in 0..m { + let mut col: Vec = Vec::new(); + for _ in 0..n { + col.push(Cell::Dead); + } + nxt_gen.push(col); + } + + for i in 0..m { + for j in 0..n { + let alive = get_alive(i, j, cur_gen); + + match cur_gen[i as usize][j as usize] { + Cell::Alive => { + if alive == 2 || alive == 3 { + nxt_gen[i as usize][j as usize] = Cell::Alive; + } else { + nxt_gen[i as usize][j as usize] = Cell::Dead; + } + } + Cell::Dead => { + if alive == 3 { + nxt_gen[i as usize][j as usize] = Cell::Alive; + } + } + } + } + } + *cur_gen = nxt_gen.clone(); + nxt_gen +} + +fn main() { + let mut stdout = io::stdout(); + let mut frame: Gen = new_gen(); + let mut nxt; + + terminal::enable_raw_mode().unwrap(); + stdout.execute(EnterAlternateScreen).unwrap(); + stdout.execute(Hide).unwrap(); + + 'gameloop: loop { + while event::poll(Duration::default()).unwrap() { + if let Event::Key(key_event) = event::read().unwrap() { + match key_event.code { + KeyCode::Esc | KeyCode::Char('q') => { + break 'gameloop; + } + KeyCode::Char('s') => { + frame = new_gen(); + render_gen(&mut stdout, &frame) + } + + KeyCode::Char('n') => { + nxt = next_gen(&mut frame); + render_gen(&mut stdout, &nxt) + } + KeyCode::Char('a') => + 'animate: loop { + nxt = next_gen(&mut frame); + render_gen(&mut stdout, &nxt); + sleep(Duration::from_millis(16)); + if(poll(Duration::from_millis(1))).unwrap() { + if let Event::Key(k) = event::read().unwrap() { + match k.code { + KeyCode::Char('q') => break 'animate, + _ => {} + } + } + } else {} + }, + _ => {} + } + } + } + } + + stdout.execute(Show).unwrap(); + stdout.execute(LeaveAlternateScreen).unwrap(); + terminal::disable_raw_mode().unwrap(); +} -- cgit v1.2.3