aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore1
-rw-r--r--Cargo.lock213
-rw-r--r--Cargo.toml9
-rw-r--r--LICENSE21
-rw-r--r--README.md3
-rw-r--r--src/bin/1-1-walker.rs87
-rw-r--r--src/bin/1-2-vector-math.rs51
-rw-r--r--src/bin/1-3-random-vec.rs97
-rw-r--r--src/bin/1-5-1-mover.rs134
-rw-r--r--src/bin/1-5-normalize.rs107
-rw-r--r--src/bin/1-6-mover-mouse.rs122
-rw-r--r--src/bin/2-1-gravity-wind.rs127
-rw-r--r--src/bin/2-2-mass-accel.rs160
-rw-r--r--src/bin/2-3-friction.rs194
-rw-r--r--src/bin/2-4-drag.rs193
-rw-r--r--src/bin/2-5-grav-attraction-point.rs182
-rw-r--r--src/bin/2-5-grav-attraction.rs171
-rw-r--r--src/bin/2-6-mutual-attraction.rs252
-rw-r--r--src/bin/3-1-angles-and-rotation.rs120
-rw-r--r--src/bin/3-2-0-angular-motion.rs163
-rw-r--r--src/bin/3-2-1-grav-rot.rs224
-rw-r--r--src/bin/3-3-angles-and-vectors.rs231
-rw-r--r--src/bin/3-4-polar-cords.rs129
-rw-r--r--src/bin/3-5-harmonic-motion.rs144
-rw-r--r--src/bin/cos-sin.rs89
-rw-r--r--src/bin/transparency-test-a.rs63
-rw-r--r--src/bin/walker-levy-flight.rs135
27 files changed, 3422 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..ea8c4bf
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+/target
diff --git a/Cargo.lock b/Cargo.lock
new file mode 100644
index 0000000..270cf8e
--- /dev/null
+++ b/Cargo.lock
@@ -0,0 +1,213 @@
+# This file is automatically @generated by Cargo.
+# It is not intended for manual editing.
+version = 4
+
+[[package]]
+name = "bitflags"
+version = "1.3.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
+
+[[package]]
+name = "bitflags"
+version = "2.9.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "1b8e56985ec62d17e9c1001dc89c88ecd7dc08e47eba5ec7c29c7b5eeecde967"
+
+[[package]]
+name = "c_vec"
+version = "2.0.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "fdd7a427adc0135366d99db65b36dae9237130997e560ed61118041fb72be6e8"
+
+[[package]]
+name = "cfg-if"
+version = "1.0.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "9555578bc9e57714c812a1f84e4fc5b4d21fcb063490c624de019f7464c91268"
+
+[[package]]
+name = "getrandom"
+version = "0.3.3"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "26145e563e54f2cadc477553f1ec5ee650b00862f0a58bcd12cbdc5f0ea2d2f4"
+dependencies = [
+ "cfg-if",
+ "libc",
+ "r-efi",
+ "wasi",
+]
+
+[[package]]
+name = "lazy_static"
+version = "1.5.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "bbd2bcb4c963f2ddae06a2efc7e9f3591312473c50c6685e1f298068316e66fe"
+
+[[package]]
+name = "libc"
+version = "0.2.174"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "1171693293099992e19cddea4e8b849964e9846f4acee11b3948bcc337be8776"
+
+[[package]]
+name = "libm"
+version = "0.2.15"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "f9fbbcab51052fe104eb5e5d351cf728d30a5be1fe14d9be8a3b097481fb97de"
+
+[[package]]
+name = "ppv-lite86"
+version = "0.2.21"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9"
+dependencies = [
+ "zerocopy",
+]
+
+[[package]]
+name = "proc-macro2"
+version = "1.0.95"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "02b3e5e68a3a1a02aad3ec490a98007cbc13c37cbe84a3cd7b8e406d76e7f778"
+dependencies = [
+ "unicode-ident",
+]
+
+[[package]]
+name = "quote"
+version = "1.0.40"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "1885c039570dc00dcb4ff087a89e185fd56bae234ddc7f056a945bf36467248d"
+dependencies = [
+ "proc-macro2",
+]
+
+[[package]]
+name = "r-efi"
+version = "5.3.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "69cdb34c158ceb288df11e18b4bd39de994f6657d83847bdffdbd7f346754b0f"
+
+[[package]]
+name = "rand"
+version = "0.9.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "9fbfd9d094a40bf3ae768db9361049ace4c0e04a4fd6b359518bd7b73a73dd97"
+dependencies = [
+ "rand_chacha",
+ "rand_core",
+]
+
+[[package]]
+name = "rand_chacha"
+version = "0.9.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb"
+dependencies = [
+ "ppv-lite86",
+ "rand_core",
+]
+
+[[package]]
+name = "rand_core"
+version = "0.9.3"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "99d9a13982dcf210057a8a78572b2217b667c3beacbf3a0d8b454f6f82837d38"
+dependencies = [
+ "getrandom",
+]
+
+[[package]]
+name = "sdl2"
+version = "0.37.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "3b498da7d14d1ad6c839729bd4ad6fc11d90a57583605f3b4df2cd709a9cd380"
+dependencies = [
+ "bitflags 1.3.2",
+ "c_vec",
+ "lazy_static",
+ "libc",
+ "sdl2-sys",
+]
+
+[[package]]
+name = "sdl2-sys"
+version = "0.37.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "951deab27af08ed9c6068b7b0d05a93c91f0a8eb16b6b816a5e73452a43521d3"
+dependencies = [
+ "cfg-if",
+ "libc",
+ "version-compare",
+]
+
+[[package]]
+name = "syn"
+version = "2.0.103"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "e4307e30089d6fd6aff212f2da3a1f9e32f3223b1f010fb09b7c95f90f3ca1e8"
+dependencies = [
+ "proc-macro2",
+ "quote",
+ "unicode-ident",
+]
+
+[[package]]
+name = "unicode-ident"
+version = "1.0.18"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "5a5f39404a5da50712a4c1eecf25e90dd62b613502b7e925fd4e4d19b5c96512"
+
+[[package]]
+name = "vectors"
+version = "0.1.0"
+dependencies = [
+ "libm",
+ "rand",
+ "sdl2",
+]
+
+[[package]]
+name = "version-compare"
+version = "0.1.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "579a42fc0b8e0c63b76519a339be31bed574929511fa53c1a3acae26eb258f29"
+
+[[package]]
+name = "wasi"
+version = "0.14.2+wasi-0.2.4"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "9683f9a5a998d873c0d21fcbe3c083009670149a8fab228644b8bd36b2c48cb3"
+dependencies = [
+ "wit-bindgen-rt",
+]
+
+[[package]]
+name = "wit-bindgen-rt"
+version = "0.39.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "6f42320e61fe2cfd34354ecb597f86f413484a798ba44a8ca1165c58d42da6c1"
+dependencies = [
+ "bitflags 2.9.1",
+]
+
+[[package]]
+name = "zerocopy"
+version = "0.8.26"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "1039dd0d3c310cf05de012d8a39ff557cb0d23087fd44cad61df08fc31907a2f"
+dependencies = [
+ "zerocopy-derive",
+]
+
+[[package]]
+name = "zerocopy-derive"
+version = "0.8.26"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "9ecf5b4cc5364572d7f4c329661bcc82724222973f2cab6f050a4e5c22f75181"
+dependencies = [
+ "proc-macro2",
+ "quote",
+ "syn",
+]
diff --git a/Cargo.toml b/Cargo.toml
new file mode 100644
index 0000000..9b4de71
--- /dev/null
+++ b/Cargo.toml
@@ -0,0 +1,9 @@
+[package]
+name = "vectors"
+version = "0.1.0"
+edition = "2024"
+
+[dependencies]
+libm = "0.2.15"
+rand = "0.9.1"
+sdl2 = { version = "0.37.0", features = ["gfx"] }
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..d54d7cc
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,21 @@
+MIT License
+
+Copyright (c) 2025 iceyrazor
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..65d869b
--- /dev/null
+++ b/README.md
@@ -0,0 +1,3 @@
+# The Nature Of Code Vectors
+
+Me following [The Nature Of Code](https://www.youtube.com/playlist?list=PLRqwX-V7Uu6ZV4yEcW3uDwOgGXKUUsPOM) vectors 1.7 to 3.5 with Rust SDL2
diff --git a/src/bin/1-1-walker.rs b/src/bin/1-1-walker.rs
new file mode 100644
index 0000000..9c78ca0
--- /dev/null
+++ b/src/bin/1-1-walker.rs
@@ -0,0 +1,87 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use std::time::Duration;
+
+use rand::Rng;
+
+struct ObjectG{
+ x: i32,
+ y: i32,
+ screen_width: i32,
+ screen_height: i32,
+}
+
+impl ObjectG{
+ fn walk(&mut self) {
+ let mut rng = rand::rng();
+ self.x = self.x + rng.random_range(-1..2);
+ self.y = self.y + rng.random_range(-1..2);
+
+ if self.x < 0 { self.x = 0 }
+ if self.y < 0 { self.y = 0 }
+ if self.x > self.screen_width { self.x = self.screen_width }
+ if self.y > self.screen_height{ self.y = self.screen_height }
+ }
+}
+
+fn draw(canvas: &mut sdl2::render::WindowCanvas, obj: &mut ObjectG){
+ //canvas.set_draw_color(Color::RGB(0,0,0));
+ //
+ //canvas.clear();
+
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ obj.walk();
+ canvas.fill_rect(Rect::new(obj.x, obj.y, 5, 5)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("walker", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj = ObjectG{
+ x: width as i32 /2,
+ y: height as i32 /2,
+ screen_width: width as i32,
+ screen_height: height as i32,
+ };
+
+ draw(&mut canvas, &mut obj);
+
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ 'running: loop {
+ draw(&mut canvas, &mut obj);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/1-2-vector-math.rs b/src/bin/1-2-vector-math.rs
new file mode 100644
index 0000000..22f91a8
--- /dev/null
+++ b/src/bin/1-2-vector-math.rs
@@ -0,0 +1,51 @@
+// this is just me making a add vec func where
+// it retains the order for add or subtracting
+// and vec1 and vec2 can be different sizes
+fn add_vec(vec1: &Vec<i32>, vec2: &Vec<i32>) -> Vec<i32> {
+ //return vec![vec1[0]+vec2[0],vec1[1]+vec2[1]];
+ let mut len=vec1.len();
+ let mut sumvec: Vec<i32> = vec1.to_vec();
+ let addvec: Vec<i32> = vec2.to_vec();
+ if vec1.len() < vec2.len() {
+ len = vec2.len();
+ }
+
+ for i in 0..len {
+ if let Some(_) = vec2.get(i) {
+ if let Some(_) = vec1.get(i) {
+ sumvec[i] = sumvec[i] + addvec[i]
+ } else {
+ sumvec.push(vec2[i])
+ }
+ }
+ }
+
+ return sumvec;
+}
+
+fn sub_vec(vec1: &Vec<i32>, vec2: &Vec<i32>) -> Vec<i32> {
+ let mut len=vec1.len();
+ let mut sumvec: Vec<i32> = vec1.to_vec();
+ let addvec: Vec<i32> = vec2.to_vec();
+ if vec1.len() < vec2.len() {
+ len = vec2.len();
+ }
+
+ for i in 0..len {
+ if let Some(_) = vec2.get(i) {
+ if let Some(_) = vec1.get(i) {
+ sumvec[i] = sumvec[i] - addvec[i]
+ } else {
+ sumvec.push(vec2[i])
+ }
+ }
+ }
+
+ return sumvec;
+}
+
+fn main() {
+ println!("{:?}", add_vec(&vec![2,4, -1, 4, 10], &vec![1,-1,-4]));
+ println!("{:?}", add_vec(&vec![1,1], &vec![1,-1,-4,3]));
+ println!("{:?}", sub_vec(&vec![2, -1], &vec![1,1,-4]));
+}
diff --git a/src/bin/1-3-random-vec.rs b/src/bin/1-3-random-vec.rs
new file mode 100644
index 0000000..474ccd6
--- /dev/null
+++ b/src/bin/1-3-random-vec.rs
@@ -0,0 +1,97 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Point};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+use rand::Rng;
+
+struct ObjectG{
+ x: i32,
+ y: i32,
+ screen_width: i32,
+ screen_height: i32,
+ points: Vec<Point>,
+}
+
+impl ObjectG{
+ fn walk(&mut self) {
+ let mut rng = rand::rng();
+
+ let rand: f64 = rng.random_range(-100.0..100.0);
+ let rand_len: f64 = rng.random_range(0.2..1.2);
+ let x = (rand_len * (rand.cos() * 100.0)) as i32 + self.screen_width / 2;
+ let y = (rand_len * (rand.sin() * 100.0)) as i32 + self.screen_height / 2;
+ self.points.push(Point::new(x,y));
+
+ if self.x < 0 { self.x = 0 }
+ if self.y < 0 { self.y = 0 }
+ if self.x > self.screen_width { self.x = self.screen_width }
+ if self.y > self.screen_height{ self.y = self.screen_height }
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj: &mut ObjectG){
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+ canvas.set_draw_color(Color::RGB(150,50,255));
+
+ obj.walk();
+ //canvas.fill_rect(Rect::new(obj.x, obj.y, 1, 1));
+ for i in &obj.points {
+ canvas.draw_line(Point::new(obj.screen_width/2,obj.screen_height/2), *i).err();
+ }
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("random-vec", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+
+
+ let mut obj = ObjectG{
+ x: width as i32 /2,
+ y: height as i32 /2,
+ screen_width: width as i32,
+ screen_height: height as i32,
+ points: Vec::new(),
+ };
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+ draw(&mut canvas, &mut obj);
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ 'running: loop {
+ draw(&mut canvas, &mut obj);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 120));
+ }
+}
diff --git a/src/bin/1-5-1-mover.rs b/src/bin/1-5-1-mover.rs
new file mode 100644
index 0000000..ab26e85
--- /dev/null
+++ b/src/bin/1-5-1-mover.rs
@@ -0,0 +1,134 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+use rand::Rng;
+
+fn distance(x: f64,y: f64,x2: f64,y2: f64) -> f64 {
+ ((x2 - x).powi(2) + (y2 - y).powi(2)).sqrt()
+}
+
+fn norm_limit(x: &f64,y: &f64, limit: &f64) -> Vec<f64>{
+ let mag: f64 = distance(0.0, 0.0, *x, *y);
+ let mut rx: f64 = *x;
+ let mut ry: f64 = *y;
+ if mag >= *limit{
+ rx = *x / mag;
+ ry = *y / mag;
+ }
+
+ return vec![rx,ry]
+}
+
+
+struct ObjectG{
+ screen_width: i32,
+ screen_height: i32,
+ x: f64,
+ y: f64,
+ vx: f64,
+ vy: f64,
+ acc_x: f64,
+ acc_y: f64,
+}
+
+impl ObjectG{
+ fn walk(&mut self) {
+ //let norm: Vec<i32> = normalize(&self.vx,&self.vy,x,y, &(self.screen_width/2), &(self.screen_height/2));
+
+
+ //self.vx = self.vx + self.screen_width/2;
+ //self.vy = self.vy + self.screen_height/2;
+ let mut rng = rand::rng();
+ self.acc_x = rng.random_range(-1.01..1.01);
+ self.acc_y = rng.random_range(-1.01..1.01);
+
+ self.vx = self.vx + self.acc_x;
+ self.vy = self.vy + self.acc_y;
+
+ let livec: Vec<f64> = norm_limit(&self.vx, &self.vy, &2.0);
+ self.vx = livec[0];
+ self.vy = livec[1];
+
+ self.x = self.x + self.vx;
+ self.y = self.y + self.vy;
+
+ if self.x < 0.0 { self.x = 0.0 }
+ if self.y < 0.0 { self.y = 0.0 }
+ if self.x > self.screen_width as f64 { self.x = self.screen_width as f64 }
+ if self.y > self.screen_height as f64 { self.y = self.screen_height as f64 }
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj: &mut ObjectG){
+
+ //putRectRGB(renderer,i*boxsize,j*boxsize,boxsize-1,150,50,255);
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+ canvas.set_draw_color(Color::RGB(150,50,255));
+
+ obj.walk();
+ canvas.fill_rect(Rect::new(obj.x as i32, obj.y as i32, 8, 8)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("mover", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+
+ let mut rng = rand::rng();
+ let sx = rng.random_range(-1.0..2.0);
+ let sy = rng.random_range(-1.0..2.0);
+
+
+ let mut obj = ObjectG{
+ screen_width: width as i32,
+ screen_height: height as i32,
+ x: width as f64 /2.0,
+ y: height as f64 /2.0,
+ vx: sx,
+ vy: sy,
+ acc_x: 0.0,
+ acc_y: 0.0,
+ };
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj);
+ 'running: loop {
+ draw(&mut canvas, &mut obj);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 120));
+ }
+}
diff --git a/src/bin/1-5-normalize.rs b/src/bin/1-5-normalize.rs
new file mode 100644
index 0000000..e7c50b5
--- /dev/null
+++ b/src/bin/1-5-normalize.rs
@@ -0,0 +1,107 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+struct ObjectG{
+ x: i32,
+ y: i32,
+ screen_width: i32,
+ screen_height: i32,
+ vx: i32,
+ vy: i32,
+}
+
+fn distance(x: f64,y: f64,x2: f64,y2: f64) -> f64 {
+ ((x2 - x).powi(2) + (y2 - y).powi(2)).sqrt()
+}
+
+impl ObjectG{
+ fn walk(&mut self, x: &i32, y: &i32) {
+ self.vx = x - self.x;
+ self.vy = y - self.y;
+
+ // normalize is vec / mag
+ // this normalize is a bit more complicated because of me using screen / 2
+ // normally you use the first 2 of distance at 0,0
+
+ //get the distance
+ let mag: f64 = distance((self.screen_width/2) as f64, (self.screen_height/2) as f64,*x as f64,*y as f64);
+ //normalize
+ self.vx = ((self.vx as f64 / mag ) * 50.0) as i32;
+ self.vy = ((self.vy as f64 / mag ) * 50.0) as i32;
+
+ self.vx = self.vx + self.screen_width/2;
+ self.vy = self.vy + self.screen_height/2;
+
+ if self.x < 0 { self.x = 0 }
+ if self.y < 0 { self.y = 0 }
+ if self.x > self.screen_width { self.x = self.screen_width }
+ if self.y > self.screen_height{ self.y = self.screen_height }
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj: &mut ObjectG, mx: &i32, my: &i32){
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+ canvas.set_draw_color(Color::RGB(150,50,255));
+
+ obj.walk(mx,my);
+ canvas.fill_rect(Rect::new(obj.vx, obj.vy, 8, 8)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("normalize", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+
+
+ let mut obj = ObjectG{
+ x: width as i32 /2,
+ y: height as i32 /2,
+ screen_width: width as i32,
+ screen_height: height as i32,
+ vx: 0,
+ vy: 0,
+ };
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj, &0, &0);
+ 'running: loop {
+ let state = event_pump.mouse_state();
+ draw(&mut canvas, &mut obj, &state.x(), &state.y());
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 120));
+ }
+}
diff --git a/src/bin/1-6-mover-mouse.rs b/src/bin/1-6-mover-mouse.rs
new file mode 100644
index 0000000..caed6a8
--- /dev/null
+++ b/src/bin/1-6-mover-mouse.rs
@@ -0,0 +1,122 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+fn distance(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = distance(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+fn norm_limit(x: &f64,y: &f64, limit: &f64) -> Vec<f64>{
+ let mag: f64 = distance(*x, *y);
+ let mut rx: f64 = *x;
+ let mut ry: f64 = *y;
+ if mag >= *limit{
+ rx = (*x / mag) * *limit;
+ ry = (*y / mag) * *limit;
+ }
+
+ return vec![rx,ry]
+}
+
+
+struct ObjectG{
+ x: f64,
+ y: f64,
+ vx: f64,
+ vy: f64,
+ acc_x: f64,
+ acc_y: f64,
+}
+
+impl ObjectG{
+ fn walk(&mut self, x: &i32, y: &i32) {
+ self.acc_x = *x as f64 - self.x;
+ self.acc_y = *y as f64 - self.y;
+
+ let smag: Vec<f64> = set_mag(&self.acc_x,&self.acc_y,&1.0);
+ self.acc_x = smag[0];
+ self.acc_y = smag[1];
+
+ self.vx = self.vx + self.acc_x;
+ self.vy = self.vy + self.acc_y;
+
+ let vel_lim: Vec<f64> = norm_limit(&self.vx, &self.vy, &5.0);
+ self.vx = vel_lim[0];
+ self.vy = vel_lim[1];
+
+ self.x = self.x + self.vx;
+ self.y = self.y + self.vy;
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj: &mut ObjectG, mx: &i32, my: &i32){
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+ canvas.set_draw_color(Color::RGB(150,50,255));
+
+ obj.walk(mx,my);
+ canvas.fill_rect(Rect::new(obj.x as i32, obj.y as i32, 8, 8)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("mover-mouse", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+
+ let mut obj = ObjectG{
+ x: width as f64 /2.0,
+ y: height as f64 /2.0,
+ vx: 0.0,
+ vy: 0.0,
+ acc_x: 0.0,
+ acc_y: 0.0,
+ };
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj, &0, &0);
+ 'running: loop {
+ let state = event_pump.mouse_state();
+ draw(&mut canvas, &mut obj, &state.x(), &state.y());
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/2-1-gravity-wind.rs b/src/bin/2-1-gravity-wind.rs
new file mode 100644
index 0000000..309c07a
--- /dev/null
+++ b/src/bin/2-1-gravity-wind.rs
@@ -0,0 +1,127 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+struct ObjectG{
+ screen_width: i32,
+ screen_height: i32,
+ x: f64,
+ y: f64,
+ vx: f64,
+ vy: f64,
+ acc_x: f64,
+ acc_y: f64,
+ size: i32,
+}
+
+impl ObjectG{
+ fn apply_force(&mut self, for_x: &f64, for_y: &f64){
+ self.acc_x = self.acc_x + *for_x;
+ self.acc_y = self.acc_y + *for_y;
+ }
+
+ fn edges(&mut self){
+ if self.y >= (self.screen_height-self.size) as f64 {
+ self.y = (self.screen_height-self.size) as f64;
+ self.vy = self.vy * -1.0;
+ }
+
+ if self.x >= (self.screen_width-self.size) as f64 {
+ self.x = (self.screen_width-self.size) as f64;
+ self.vx = self.vx * -1.0;
+ } else if self.x <= self.size as f64 {
+ self.x = self.size as f64;
+ self.vx = self.vx * -1.0;
+ }
+ }
+
+ fn walk(&mut self) {
+ self.vx = self.vx + self.acc_x;
+ self.vy = self.vy + self.acc_y;
+
+ self.x = self.x + self.vx;
+ self.y = self.y + self.vy;
+
+ self.acc_x = 0.0;
+ self.acc_y = 0.0;
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj: &mut ObjectG, g_button: &bool){
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+ canvas.set_draw_color(Color::RGB(150,50,255));
+
+ //gravity
+ obj.apply_force(&0.0, &0.2);
+
+ if *g_button==true {
+ //wind
+ obj.apply_force(&0.1, &0.0);
+ }
+
+ obj.edges();
+ obj.walk();
+
+ canvas.fill_rect(Rect::new(obj.x as i32 - obj.size, obj.y as i32 - obj.size, (obj.size*2) as u32, (obj.size*2) as u32)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("gravity-wind", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+
+ let mut obj = ObjectG{
+ screen_width: width as i32,
+ screen_height: height as i32,
+ x: width as f64 /2.0,
+ y: height as f64 /2.0,
+ vx: 0.0,
+ vy: 0.0,
+ acc_x: 0.0,
+ acc_y: 0.0,
+ size: 10,
+ };
+
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj, &false);
+ 'running: loop {
+ let mut g_button = false;
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ Event::KeyDown { keycode: Some(Keycode::G), .. } => {
+ g_button = !g_button;
+ },
+ _ => {}
+ }
+ }
+ draw(&mut canvas, &mut obj, &g_button);
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/2-2-mass-accel.rs b/src/bin/2-2-mass-accel.rs
new file mode 100644
index 0000000..73bdd8c
--- /dev/null
+++ b/src/bin/2-2-mass-accel.rs
@@ -0,0 +1,160 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+struct ObjectG{
+ screen_width: i32,
+ screen_height: i32,
+ x: f64,
+ y: f64,
+ vx: f64,
+ vy: f64,
+ acc_x: f64,
+ acc_y: f64,
+ size: i32,
+ mass: f64,
+}
+
+impl ObjectG{
+ fn apply_force(&mut self, for_x: &f64, for_y: &f64){
+ let for_x: f64 = *for_x / self.mass;
+ let for_y: f64 = *for_y / self.mass;
+
+ self.acc_x = self.acc_x + for_x;
+ self.acc_y = self.acc_y + for_y;
+ }
+
+ fn edges(&mut self){
+ if self.y >= (self.screen_height-self.size) as f64 {
+ self.y = (self.screen_height-self.size) as f64;
+ self.vy = self.vy * -1.0;
+ }
+
+ if self.x >= (self.screen_width-self.size) as f64 {
+ self.x = (self.screen_width-self.size) as f64;
+ self.vx = self.vx * -1.0;
+ } else if self.x <= self.size as f64 {
+ self.x = self.size as f64;
+ self.vx = self.vx * -1.0;
+ }
+ }
+
+ fn walk(&mut self) {
+ self.vx = self.vx + self.acc_x;
+ self.vy = self.vy + self.acc_y;
+
+ self.x = self.x + self.vx;
+ self.y = self.y + self.vy;
+
+ self.acc_x = 0.0;
+ self.acc_y = 0.0;
+ }
+
+ fn show(&mut self, canvas: &mut WindowCanvas){
+ canvas.fill_rect(Rect::new(self.x as i32 - self.size, self.y as i32 - self.size, (self.size*2) as u32, (self.size*2) as u32)).err();
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj: &mut ObjectG, obj2: &mut ObjectG, g_button: &bool){
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ //gravity
+ let grav = 0.2;
+ obj.apply_force(&0.0, &(grav * obj.mass));
+ obj2.apply_force(&0.0, &(grav * obj2.mass));
+
+ if *g_button==true {
+ //wind
+ obj.apply_force(&0.1, &0.0);
+ obj2.apply_force(&0.1, &0.0);
+ }
+
+ obj.edges();
+ obj.walk();
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ obj.show(canvas);
+
+ obj2.edges();
+ obj2.walk();
+ canvas.set_draw_color(Color::RGB(255,50,150));
+ obj2.show(canvas);
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("mass-accel", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+
+ let mut obj = ObjectG{
+ screen_width: width as i32,
+ screen_height: height as i32,
+ x: width as f64 /2.0 + 80.0,
+ y: height as f64 /2.0,
+ vx: 0.0,
+ vy: 0.0,
+ acc_x: 0.0,
+ acc_y: 0.0,
+ size: 10,
+ mass: 2.0,
+ };
+
+ obj.size = (obj.mass.sqrt() * 10.0) as i32;
+
+ let mut obj2 = ObjectG{
+ screen_width: width as i32,
+ screen_height: height as i32,
+ x: width as f64 /2.0 - 80.0,
+ y: height as f64 /2.0,
+ vx: 0.0,
+ vy: 0.0,
+ acc_x: 0.0,
+ acc_y: 0.0,
+ size: 10,
+ mass: 4.0,
+ };
+
+ obj2.size = (obj2.mass.sqrt() * 10.0) as i32;
+
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj, &mut obj2, &false);
+ 'running: loop {
+ let mut g_button = false;
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ Event::KeyDown { keycode: Some(Keycode::G), .. } => {
+ g_button = !g_button;
+ },
+ _ => {}
+ }
+ }
+ draw(&mut canvas, &mut obj, &mut obj2, &g_button);
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/2-3-friction.rs b/src/bin/2-3-friction.rs
new file mode 100644
index 0000000..02fcb13
--- /dev/null
+++ b/src/bin/2-3-friction.rs
@@ -0,0 +1,194 @@
+extern crate sdl2;
+
+use rand::Rng;
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn normalize(x: &f64,y: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = *x / getmag;
+ let ry = *y / getmag;
+
+ return vec![rx,ry]
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+struct ObjectG{
+ screen_width: i32,
+ screen_height: i32,
+ x: f64,
+ y: f64,
+ vx: f64,
+ vy: f64,
+ acc_x: f64,
+ acc_y: f64,
+ size: i32,
+ mass: f64,
+}
+
+impl ObjectG{
+ fn apply_force(&mut self, for_x: &f64, for_y: &f64){
+ let for_x: f64 = *for_x / self.mass;
+ let for_y: f64 = *for_y / self.mass;
+
+ self.acc_x = self.acc_x + for_x;
+ self.acc_y = self.acc_y + for_y;
+ }
+
+ fn friction(&mut self){
+ let diff = self.screen_height - (self.y as i32 + self.size);
+ if diff < 1 {
+ //self.vx = self.vx * 0.95;
+ //self.vy = self.vy * 0.95;
+
+ let friction = normalize(&self.vx, &self.vy);
+ let friction = vec![friction[0] * -1.0, friction[1] * -1.0];
+
+ let mu = 0.05;
+ let normal = self.mass;
+
+ let force = set_mag(&friction[0], &friction[1], &(mu * normal));
+
+ self.apply_force(&force[0], &force[1]);
+ }
+ }
+
+ fn edges(&mut self){
+ if self.y >= (self.screen_height-self.size) as f64 {
+ self.y = (self.screen_height-self.size) as f64;
+ self.vy = self.vy * -1.0;
+ }
+
+ if self.x >= (self.screen_width-self.size) as f64 {
+ self.x = (self.screen_width-self.size) as f64;
+ self.vx = self.vx * -1.0;
+ } else if self.x <= self.size as f64 {
+ self.x = self.size as f64;
+ self.vx = self.vx * -1.0;
+ }
+ }
+
+ fn walk(&mut self) {
+ self.vx = self.vx + self.acc_x;
+ self.vy = self.vy + self.acc_y;
+
+ self.x = self.x + self.vx;
+ self.y = self.y + self.vy;
+
+ self.acc_x = 0.0;
+ self.acc_y = 0.0;
+ }
+
+ fn show(&mut self, canvas: &mut WindowCanvas){
+ canvas.set_draw_color(Color::RGBA(150,50,255,100));
+ canvas.fill_rect(Rect::new(self.x as i32 - self.size, self.y as i32 - self.size, (self.size*2) as u32, (self.size*2) as u32)).err();
+ canvas.set_draw_color(Color::RGBA(150,50,255,255));
+ canvas.draw_rect(Rect::new(self.x as i32 - self.size, self.y as i32 - self.size, (self.size*2) as u32, (self.size*2) as u32)).err();
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, g_button: &bool){
+
+ canvas.set_draw_color(Color::RGBA(0,0,0,255));
+ canvas.clear();
+
+
+ //gravity
+ let grav = 8.2;
+ for obj in obj_arr{
+ obj.apply_force(&0.0, &(grav * obj.mass));
+
+ if *g_button==true {
+ //wind
+ obj.apply_force(&0.1, &0.0);
+ }
+
+ obj.friction();
+
+ obj.walk();
+ obj.edges();
+ obj.show(canvas);
+ }
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("friction", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ for _ in 0..10{
+ let mut rng = rand::rng();
+
+ let mut obj = ObjectG{
+ screen_width: width as i32,
+ screen_height: height as i32,
+ x: width as f64 /2.0,
+ y: height as f64 /2.0,
+ vx: rng.random_range(-10.0..10.0),
+ vy: rng.random_range(-10.0..10.0),
+ acc_x: 0.0,
+ acc_y: 0.0,
+ size: 0,
+ mass: rng.random_range(2.0..8.0),
+ };
+
+ obj.size = (obj.mass.sqrt() * 10.0) as i32;
+
+ obj_arr.push(obj);
+ }
+
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr, &false);
+ 'running: loop {
+ let mut g_button = false;
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ Event::KeyDown { keycode: Some(Keycode::G), .. } => {
+ g_button = !g_button;
+ },
+ _ => {}
+ }
+ }
+ draw(&mut canvas, &mut obj_arr, &g_button);
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/2-4-drag.rs b/src/bin/2-4-drag.rs
new file mode 100644
index 0000000..be6e692
--- /dev/null
+++ b/src/bin/2-4-drag.rs
@@ -0,0 +1,193 @@
+extern crate sdl2;
+
+use rand::Rng;
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn normalize(x: &f64,y: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = *x / getmag;
+ let ry = *y / getmag;
+
+ return vec![rx,ry]
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+struct ObjectG{
+ screen_width: i32,
+ screen_height: i32,
+ x: f64,
+ y: f64,
+ vx: f64,
+ vy: f64,
+ acc_x: f64,
+ acc_y: f64,
+ size: i32,
+ mass: f64,
+}
+
+const DRAG_C: f64 = 0.3;
+
+impl ObjectG{
+ fn apply_force(&mut self, for_x: &f64, for_y: &f64){
+ let for_x: f64 = *for_x / self.mass;
+ let for_y: f64 = *for_y / self.mass;
+
+ self.acc_x = self.acc_x + for_x;
+ self.acc_y = self.acc_y + for_y;
+ }
+
+ fn drag(&mut self){
+ let drag = normalize(&self.vx, &self.vy);
+ let drag = vec![drag[0] * -1.0, drag[1] * -1.0];
+
+ let speed = magnitude(self.vx, self.vy);
+
+ let drag = set_mag(&drag[0], &drag[1], &(DRAG_C * speed * speed));
+
+ self.apply_force(&drag[0], &drag[1]);
+ }
+
+ fn edges(&mut self){
+ if self.y >= (self.screen_height-self.size) as f64 {
+ self.y = (self.screen_height-self.size) as f64;
+ self.vy = self.vy * -1.0;
+ }
+
+ if self.x >= (self.screen_width-self.size) as f64 {
+ self.x = (self.screen_width-self.size) as f64;
+ self.vx = self.vx * -1.0;
+ } else if self.x <= self.size as f64 {
+ self.x = self.size as f64;
+ self.vx = self.vx * -1.0;
+ }
+ }
+
+ fn walk(&mut self) {
+ self.vx = self.vx + self.acc_x;
+ self.vy = self.vy + self.acc_y;
+
+ self.x = self.x + self.vx;
+ self.y = self.y + self.vy;
+
+ self.acc_x = 0.0;
+ self.acc_y = 0.0;
+ }
+
+ fn show(&mut self, canvas: &mut WindowCanvas){
+ canvas.set_draw_color(Color::RGBA(150,50,255,100));
+ canvas.fill_rect(Rect::new(self.x as i32 - self.size, self.y as i32 - self.size, (self.size*2) as u32, (self.size*2) as u32)).err();
+ canvas.set_draw_color(Color::RGBA(150,50,255,255));
+ canvas.draw_rect(Rect::new(self.x as i32 - self.size, self.y as i32 - self.size, (self.size*2) as u32, (self.size*2) as u32)).err();
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, g_button: &bool){
+
+ canvas.set_draw_color(Color::RGBA(0,0,0,255));
+ canvas.clear();
+
+ canvas.set_draw_color(Color::RGBA(255,255,255,50));
+ canvas.fill_rect(Rect::new(0,obj_arr[0].screen_height/2,obj_arr[0].screen_width as u32,(obj_arr[0].screen_height/2) as u32)).err();
+
+ //gravity
+ let grav = 0.2;
+ for obj in obj_arr{
+ obj.apply_force(&0.0, &(grav * obj.mass));
+
+ if *g_button==true {
+ //wind
+ obj.apply_force(&0.1, &0.0);
+ }
+
+ if obj.y > (obj.screen_height / 2) as f64 {
+ obj.drag();
+ }
+
+ obj.walk();
+ obj.edges();
+ obj.show(canvas);
+ }
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("drag", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ for _ in 0..10{
+ let mut rng = rand::rng();
+
+ let mut obj = ObjectG{
+ screen_width: width as i32,
+ screen_height: height as i32,
+ x: rng.random_range(10.0..width as f64),
+ y: 20.0,
+ vx: 0.0,
+ vy: 1.0,
+ acc_x: 0.0,
+ acc_y: 0.0,
+ size: 0,
+ mass: rng.random_range(1.0..8.0),
+ };
+
+ obj.size = (obj.mass.sqrt() * 10.0) as i32;
+
+ obj_arr.push(obj);
+ }
+
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr, &false);
+ 'running: loop {
+ let mut g_button = false;
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ Event::KeyDown { keycode: Some(Keycode::G), .. } => {
+ g_button = !g_button;
+ },
+ _ => {}
+ }
+ }
+ draw(&mut canvas, &mut obj_arr, &g_button);
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/2-5-grav-attraction-point.rs b/src/bin/2-5-grav-attraction-point.rs
new file mode 100644
index 0000000..cf310aa
--- /dev/null
+++ b/src/bin/2-5-grav-attraction-point.rs
@@ -0,0 +1,182 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+use rand::Rng;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+//i know i can use sdl points but i wanna make my own thing.
+//plus this is more independant.
+struct Point{
+ x: f64,
+ y: f64,
+}
+impl Point{
+ fn add(&mut self, addvec: &Point){
+ self.x = self.x + addvec.x;
+ self.y = self.y + addvec.y;
+ }
+
+ fn sub(&mut self, subvec: &Point){
+ self.x = self.x - subvec.x;
+ self.y = self.y - subvec.y;
+ }
+
+ fn set_mag(&mut self, mag: &f64) {
+ let smag = set_mag(&self.x, &self.y, &mag);
+ self.x = smag[0];
+ self.y = smag[1];
+ }
+}
+
+struct ObjectG{
+ pos: Point,
+ vel: Point,
+ acc: Point,
+ size: i32,
+ mass: f64,
+}
+
+impl ObjectG{
+ fn apply_force(&mut self, force: &Point){
+ let force = Point { x: force.x / self.mass, y: force.y / self.mass };
+
+ self.acc.add(&force);
+ }
+
+ fn walk(&mut self) {
+ self.vel.add(&self.acc);
+
+ self.pos.add(&self.vel);
+
+ self.acc=Point{x:0.0, y:0.0}
+ }
+}
+
+struct Attractor{
+ pos: Point,
+ size: i32,
+ mass: f64,
+}
+
+impl Attractor{
+ fn attract(&mut self, obj: &mut ObjectG){
+ let mut force = Point{x: self.pos.x, y: self.pos.y};
+ force.sub(&obj.pos);
+
+ let dist = magnitude(force.x, force.y);
+ let mut dist = dist * dist;
+
+ if dist < 100.0 { dist = 100.0 }
+ if dist > 1000.0 { dist = 1000.0 }
+
+ let g = 5.0;
+
+ let strength = g * (self.mass * obj.mass) / dist;
+
+ force.set_mag(&strength);
+
+ obj.apply_force(&force);
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, atr: &mut Attractor){
+ canvas.set_draw_color(Color::RGBA(0,0,0,50));
+ canvas.fill_rect(Rect::new(0,0,600,600)).err();
+ //canvas.clear();
+
+ for obj in obj_arr{
+ obj.walk();
+ canvas.set_draw_color(Color::RGBA(150,50,255,150));
+ canvas.fill_rect(Rect::new(obj.pos.x as i32 - obj.size, obj.pos.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ canvas.draw_rect(Rect::new(obj.pos.x as i32 - obj.size, obj.pos.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ atr.attract(obj);
+ }
+
+ canvas.set_draw_color(Color::RGB(255,50,150));
+ canvas.fill_rect(Rect::new(atr.pos.x as i32 - atr.size, atr.pos.y as i32 - atr.size, (atr.size * 2) as u32, (atr.size * 2) as u32)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=600;
+ let height: u32=600;
+
+ let window = video_subsystem.window("grav-attraction-point", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ for _ in 0..10{
+ let mut rng = rand::rng();
+ let mut obj = ObjectG{
+ pos: Point { x: rng.random_range(6.0..width as f64 -1.0), y: rng.random_range(6.0..width as f64 -1.0)},
+ vel: Point { x: rng.random_range(-11.0..10.0), y: rng.random_range(-11.0..10.0)},
+ acc: Point { x: 0.0, y: 0.0 },
+ size: 0,
+ mass: rng.random_range(50.0..150.0),
+ };
+ obj.size = (obj.mass.sqrt() * 2.0) as i32;
+ obj_arr.push(obj);
+ }
+
+ let mut atr = Attractor{
+ pos: Point{x: width as f64 /2.0, y: height as f64 /2.0},
+ size: 0,
+ mass: 100.0,
+ };
+
+ atr.size = (atr.mass.sqrt() * 2.0) as i32;
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ 'running: loop {
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/2-5-grav-attraction.rs b/src/bin/2-5-grav-attraction.rs
new file mode 100644
index 0000000..d7fc2f5
--- /dev/null
+++ b/src/bin/2-5-grav-attraction.rs
@@ -0,0 +1,171 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+use rand::Rng;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+struct ObjectG{
+ x: f64,
+ y: f64,
+ vx: f64,
+ vy: f64,
+ acc_x: f64,
+ acc_y: f64,
+ size: i32,
+ mass: f64,
+}
+
+impl ObjectG{
+ fn apply_force(&mut self, force_x: &f64, force_y: &f64){
+ let fx = force_x / self.mass;
+ let fy = force_y / self.mass;
+
+ self.acc_x = self.acc_x + fx;
+ self.acc_y = self.acc_y + fy;
+ }
+
+ fn walk(&mut self) {
+ self.vx = self.vx + self.acc_x;
+ self.vy = self.vy + self.acc_y;
+
+ self.x = self.x + self.vx;
+ self.y = self.y + self.vy;
+
+ self.acc_x = 0.0;
+ self.acc_y = 0.0;
+ }
+}
+
+struct Attractor{
+ x: f64,
+ y: f64,
+ size: i32,
+ mass: f64,
+}
+
+impl Attractor{
+ fn attract(&mut self, obj: &mut ObjectG){
+ let force_x = self.x - obj.x;
+ let force_y = self.y - obj.y;
+
+ let dist = magnitude(force_x, force_y);
+ let mut dist = dist * dist;
+
+ if dist < 100.0 { dist = 100.0 }
+ if dist > 1000.0 { dist = 1000.0 }
+
+ let g = 5.0;
+
+ let strength = g * (self.mass * obj.mass) / dist;
+
+ let force = set_mag(&force_x, &force_y, &strength);
+
+ obj.apply_force(&force[0], &force[1]);
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, atr: &mut Attractor){
+ canvas.set_draw_color(Color::RGBA(0,0,0,50));
+ canvas.fill_rect(Rect::new(0,0,600,600)).err();
+ //canvas.clear();
+
+ for obj in obj_arr{
+ obj.walk();
+ canvas.set_draw_color(Color::RGBA(150,50,255,150));
+ canvas.fill_rect(Rect::new(obj.x as i32 - obj.size, obj.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ canvas.draw_rect(Rect::new(obj.x as i32 - obj.size, obj.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ atr.attract(obj);
+ }
+
+ canvas.set_draw_color(Color::RGB(255,50,150));
+ canvas.fill_rect(Rect::new(atr.x as i32 - atr.size, atr.y as i32 - atr.size, (atr.size * 2) as u32, (atr.size * 2) as u32)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=600;
+ let height: u32=600;
+
+ let window = video_subsystem.window("grav-attraction", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ for _ in 0..10{
+ let mut rng = rand::rng();
+ let mut obj = ObjectG{
+ x: rng.random_range(6.0..width as f64 -1.0),
+ y: rng.random_range(6.0..height as f64 -1.0),
+ vx: rng.random_range(-11.0..10.0),
+ vy: rng.random_range(-11.0..10.0),
+ acc_x: 0.0,
+ acc_y: 0.0,
+ size: 0,
+ mass: rng.random_range(50.0..150.0),
+ };
+ obj.size = (obj.mass.sqrt() * 2.0) as i32;
+ obj_arr.push(obj);
+ }
+
+ let mut atr = Attractor{
+ x: width as f64 /2.0,
+ y: height as f64 /2.0,
+ size: 0,
+ mass: 100.0,
+ };
+
+ atr.size = (atr.mass.sqrt() * 2.0) as i32;
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ 'running: loop {
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/2-6-mutual-attraction.rs b/src/bin/2-6-mutual-attraction.rs
new file mode 100644
index 0000000..0daba25
--- /dev/null
+++ b/src/bin/2-6-mutual-attraction.rs
@@ -0,0 +1,252 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+use rand::Rng;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+//i know i can use sdl points but i wanna make my own thing.
+//plus this is more independant.
+#[derive(Clone)]
+struct Point{
+ x: f64,
+ y: f64,
+}
+impl Point{
+ fn add(&mut self, addvec: &Point){
+ self.x = self.x + addvec.x;
+ self.y = self.y + addvec.y;
+ }
+
+ fn sub(&mut self, subvec: &Point){
+ self.x = self.x - subvec.x;
+ self.y = self.y - subvec.y;
+ }
+
+ fn set_mag(&mut self, mag: &f64) {
+ let smag = set_mag(&self.x, &self.y, &mag);
+ self.x = smag[0];
+ self.y = smag[1];
+ }
+
+ fn rotate(&mut self, angle: &f64){
+ let cos_theta = angle.cos();
+ let sin_theta = angle.sin();
+
+ let x = self.x * cos_theta - self.y * sin_theta;
+ let y = self.x * sin_theta + self.y * cos_theta;
+
+ self.x = x;
+ self.y = y;
+ }
+}
+
+struct ObjectG{
+ pos: Point,
+ vel: Point,
+ acc: Point,
+ size: i32,
+ mass: f64,
+}
+
+impl ObjectG{
+ fn new(x: f64, y: f64, vx: f64, vy: f64, mass: f64) -> Self{
+ Self {
+ pos: Point{x: x, y: y},
+ vel: Point { x: vx, y: vy},
+ acc: Point { x: 0.0, y: 0.0},
+ size: (mass.sqrt() * 2.0) as i32,
+ mass: mass,
+ }
+ }
+
+ fn apply_force(&mut self, force: &Point){
+ let force = Point { x: force.x / self.mass, y: force.y / self.mass };
+
+ self.acc.add(&force);
+ }
+
+ fn walk(&mut self) {
+ self.vel.add(&self.acc);
+
+ self.pos.add(&self.vel);
+
+ self.acc=Point{x:0.0, y:0.0}
+ }
+
+ fn attract(&mut self, obj: &mut ObjectG){
+ let mut force = Point{x: self.pos.x, y: self.pos.y};
+ force.sub(&obj.pos);
+
+ let dist = magnitude(force.x, force.y);
+ let mut dist = dist * dist;
+
+ if dist < 100.0 { dist = 100.0 }
+ if dist > 1000.0 { dist = 1000.0 }
+
+ let g = 0.5;
+
+ let strength = g * (self.mass * obj.mass) / dist;
+
+ force.set_mag(&strength);
+
+ obj.apply_force(&force);
+ }
+
+ fn show(&mut self, canvas: &mut WindowCanvas){
+ canvas.set_draw_color(Color::RGBA(150,50,255,150));
+ canvas.fill_rect(Rect::new(self.pos.x as i32 - self.size, self.pos.y as i32 - self.size, (self.size * 2) as u32, (self.size * 2) as u32)).err();
+
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ canvas.draw_rect(Rect::new(self.pos.x as i32 - self.size, self.pos.y as i32 - self.size, (self.size * 2) as u32, (self.size * 2) as u32)).err();
+ }
+}
+
+//ngl these 2 are chatgpt.
+fn get_pair_mut<T>(slice: &mut [T], i: usize, j: usize) -> Option<(&mut T, &mut T)> {
+ if i == j || i >= slice.len() || j >= slice.len() {
+ return None;
+ }
+
+ if i < j {
+ let (left, right) = slice.split_at_mut(j);
+ Some((&mut left[i], &mut right[0]))
+ } else {
+ let (left, right) = slice.split_at_mut(i);
+ Some((&mut right[0], &mut left[j]))
+ }
+}
+
+fn attract_all(obj_arr: &mut [ObjectG]) {
+ let len = obj_arr.len();
+
+ for i in 0..len {
+ for j in (i + 1)..len {
+ let (a, b) = get_pair_mut(obj_arr, i, j).unwrap();
+ a.attract(b);
+ b.attract(a);
+ }
+ }
+}
+
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, sun: &mut ObjectG){
+ canvas.set_draw_color(Color::RGBA(0,0,0,80));
+ canvas.fill_rect(Rect::new(0,0,800,800)).err();
+ //canvas.clear();
+
+ attract_all(obj_arr);
+
+ for obj in obj_arr{
+ obj.walk();
+ sun.attract(obj);
+ obj.show(canvas);
+ }
+
+ canvas.set_draw_color(Color::RGBA(255,50,100,100));
+ canvas.fill_rect(Rect::new(sun.pos.x as i32 - sun.size, sun.pos.y as i32 - sun.size, (sun.size * 2) as u32, (sun.size * 2) as u32)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=800;
+ let height: u32=800;
+
+ let window = video_subsystem.window("mutual-attraction", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ for _ in 0..250{
+ let mut rng = rand::rng();
+ let mut pos = Point{x: rng.random_range(-1.0..1.0), y: rng.random_range(-1.0..1.0)};
+ let mut vel = pos.clone();
+ vel.set_mag(&rng.random_range(5.0..15.0));
+ pos.set_mag(&rng.random_range(200.0..300.0));
+ vel.rotate(&(3.14192/2.0));
+
+ pos.add(&Point { x: width as f64 /2.0, y: height as f64 /2.0 });
+
+ //let vel = Point{ x:rng.random_range(-1.0..1.0), y: rng.random_range(-1.0..1.0)};
+
+ let m = rng.random_range(5.0..15.0);
+
+ let obj = ObjectG::new(pos.x,pos.y,vel.x,vel.y,m);
+ obj_arr.push(obj);
+ }
+
+ /*
+ let obj = ObjectG::new(300.0, 200.0, 0.0, 5.0, 10.0);
+
+ obj_arr.push(obj);
+
+ let obj2 = ObjectG::new(100.0,200.0,0.0,-5.0,10.0);
+
+ obj_arr.push(obj2);
+
+ let obj3 = ObjectG::new(200.0,300.0,-5.0,-0.0,10.0);
+
+ obj_arr.push(obj3);
+
+ let obj4 = ObjectG::new(200.0,100.0,5.0,-0.0,10.0);
+
+ obj_arr.push(obj4);
+ */
+
+ let mut sun = ObjectG::new(width as f64 /2.0, height as f64 /2.0,0.0,0.0,500.0);
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr, &mut sun);
+ 'running: loop {
+ draw(&mut canvas, &mut obj_arr, &mut sun);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 30));
+ }
+}
+
+
+// optimizations
+
+// barnes hut simulation
+// quad tree
diff --git a/src/bin/3-1-angles-and-rotation.rs b/src/bin/3-1-angles-and-rotation.rs
new file mode 100644
index 0000000..b4ee718
--- /dev/null
+++ b/src/bin/3-1-angles-and-rotation.rs
@@ -0,0 +1,120 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Point, Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+
+struct PointG{
+ x: f64,
+ y: f64,
+}
+impl PointG{
+ fn rotate(&mut self, angle: &f64){
+ let cos_theta = angle.cos();
+ let sin_theta = angle.sin();
+
+ let x = self.x * cos_theta - self.y * sin_theta;
+ let y = self.x * sin_theta + self.y * cos_theta;
+
+ self.x = x;
+ self.y = y;
+ }
+}
+
+struct ObjectG{
+ pos: PointG,
+ screen_size: PointG,
+}
+
+impl ObjectG{
+ fn new(x: f64, y: f64, sw: f64, sh: f64) -> Self{
+ Self {
+ pos: PointG{x: x, y: y},
+ screen_size: PointG { x: sw, y: sh },
+ }
+ }
+}
+
+fn draw_line(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, a: &usize, b: &usize){
+ let pos = PointG{x: obj_arr[*a].pos.x + obj_arr[*a].screen_size.x / 2.0, y: obj_arr[*a].pos.y + obj_arr[*a].screen_size.y / 2.0};
+ let pos2 = PointG{x: obj_arr[*b].pos.x + obj_arr[*b].screen_size.x / 2.0, y: obj_arr[*b].pos.y + obj_arr[*b].screen_size.y / 2.0};
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ canvas.draw_line(Point::new(pos.x as i32,pos.y as i32), Point::new(pos2.x as i32,pos2.y as i32)).err();
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>){
+ canvas.set_draw_color(Color::RGBA(0,0,0,80));
+ canvas.fill_rect(Rect::new(0,0,800,800)).err();
+ canvas.clear();
+
+ draw_line(canvas, obj_arr, &0, &1);
+ draw_line(canvas, obj_arr, &1, &2);
+ draw_line(canvas, obj_arr, &2, &3);
+ draw_line(canvas, obj_arr, &3, &0);
+
+
+ for obj in obj_arr{
+ obj.pos.rotate(&0.05);
+ }
+
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("angles-and-rot", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ let obj = ObjectG::new(128.0,64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ let obj = ObjectG::new(-128.0,64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ let obj = ObjectG::new(-128.0,-64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ let obj = ObjectG::new(128.0,-64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr);
+ 'running: loop {
+ draw(&mut canvas, &mut obj_arr);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 30));
+ }
+}
diff --git a/src/bin/3-2-0-angular-motion.rs b/src/bin/3-2-0-angular-motion.rs
new file mode 100644
index 0000000..21ce6ca
--- /dev/null
+++ b/src/bin/3-2-0-angular-motion.rs
@@ -0,0 +1,163 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Point, Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+
+struct PointG{
+ x: f64,
+ y: f64,
+ start_x: f64,
+ start_y: f64,
+ mx: f64,
+ my: f64,
+}
+impl PointG{
+ fn new(x: f64, y: f64) -> Self {
+ Self{
+ x: x,
+ y: y,
+ start_x: x,
+ start_y: y,
+ mx: 0.0,
+ my: 0.0,
+ }
+ }
+
+ fn set_angle(&mut self, angle: &f64){
+ let angle = angle % (3.14192 * 2.0);
+ let cos_theta = angle.cos();
+ let sin_theta = angle.sin();
+
+ let x = self.start_x * cos_theta - self.start_y * sin_theta;
+ let y = self.start_x * sin_theta + self.start_y * cos_theta;
+
+ self.x = x;
+ self.y = y;
+ }
+}
+
+struct ObjectG{
+ pos: PointG,
+ screen_size: PointG,
+ ang: f64,
+ a_vel: f64,
+ a_acc: f64,
+}
+
+impl ObjectG{
+ fn new(x: f64, y: f64, sw: f64, sh: f64) -> Self{
+ Self {
+ pos: PointG::new(x,y),
+ screen_size: PointG::new(sw,sh),
+ ang: 0.0,
+ a_vel: 0.0,
+ a_acc: 0.001,
+ }
+ }
+
+ fn update(&mut self){
+ let map = ((self.pos.mx / self.screen_size.x) - 0.5) / 0.5 / 10.0;
+ if self.a_vel > 0.2 { self.a_vel = 0.2 }
+ if self.a_vel < -0.2 { self.a_vel = -0.2 }
+ self.a_acc = map;
+ self.ang = self.ang + self.a_vel;
+ self.a_vel = self.a_vel + self.a_acc;
+
+ self.pos.set_angle(&self.ang);
+ }
+}
+
+fn draw_line(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, a: &usize, b: &usize){
+ let pos = PointG::new(obj_arr[*a].pos.x + obj_arr[*a].screen_size.x / 2.0, obj_arr[*a].pos.y + obj_arr[*a].screen_size.y / 2.0);
+ let pos2 = PointG::new(obj_arr[*b].pos.x + obj_arr[*b].screen_size.x / 2.0, obj_arr[*b].pos.y + obj_arr[*b].screen_size.y / 2.0);
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ canvas.draw_line(Point::new(pos.x as i32,pos.y as i32), Point::new(pos2.x as i32,pos2.y as i32)).err();
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>){
+ canvas.set_draw_color(Color::RGBA(0,0,0,80));
+ canvas.fill_rect(Rect::new(0,0,800,800)).err();
+ canvas.clear();
+
+ draw_line(canvas, obj_arr, &0, &1);
+ draw_line(canvas, obj_arr, &1, &2);
+ draw_line(canvas, obj_arr, &2, &3);
+ draw_line(canvas, obj_arr, &3, &0);
+
+
+ for obj in obj_arr{
+ obj.update();
+ }
+
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("angular-motion", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ let obj = ObjectG::new(128.0,64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ let obj = ObjectG::new(-128.0,64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ let obj = ObjectG::new(-128.0,-64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ let obj = ObjectG::new(128.0,-64.0,width as f64, height as f64);
+ obj_arr.push(obj);
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr);
+ 'running: loop {
+ draw(&mut canvas, &mut obj_arr);
+ let state = event_pump.mouse_state();
+ for obj in &mut obj_arr{
+ obj.pos.mx=state.x() as f64;
+ obj.pos.my=state.y() as f64;
+ }
+ //draw(&mut canvas, &mut obj, &state.x(), &state.y());
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 30));
+ }
+}
+
+// *~challenges
+// when you click you grab the rect and then rotate it
+// releasing it at a velocity will maintain its velocity
diff --git a/src/bin/3-2-1-grav-rot.rs b/src/bin/3-2-1-grav-rot.rs
new file mode 100644
index 0000000..e8e1388
--- /dev/null
+++ b/src/bin/3-2-1-grav-rot.rs
@@ -0,0 +1,224 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Point, Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+use rand::Rng;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+//i know i can use sdl points but i wanna make my own thing.
+//plus this is more independant.
+struct PointG{
+ x: f64,
+ y: f64,
+ start_x: f64,
+ start_y: f64,
+}
+impl PointG{
+ fn new(x: &f64, y: &f64)->Self{
+ Self{
+ x: *x,
+ y: *y,
+ start_x: *x,
+ start_y: *y,
+ }
+ }
+
+ fn add(&mut self, addvec: &PointG){
+ self.x = self.x + addvec.x;
+ self.y = self.y + addvec.y;
+ }
+
+ fn sub(&mut self, subvec: &PointG){
+ self.x = self.x - subvec.x;
+ self.y = self.y - subvec.y;
+ }
+
+ fn set_mag(&mut self, mag: &f64) {
+ let smag = set_mag(&self.x, &self.y, &mag);
+ self.x = smag[0];
+ self.y = smag[1];
+ }
+
+ fn set_angle(&mut self, angle: &f64){
+ let angle = angle % (3.14192 * 2.0);
+ let cos_theta = angle.cos();
+ let sin_theta = angle.sin();
+
+ let x = self.start_x * cos_theta - self.start_y * sin_theta;
+ let y = self.start_x * sin_theta + self.start_y * cos_theta;
+
+ self.x = x;
+ self.y = y;
+ }
+}
+
+struct ObjectG{
+ pos: PointG,
+ vel: PointG,
+ acc: PointG,
+ size: i32,
+ mass: f64,
+ ang: f64,
+ a_vel: f64,
+ a_acc: f64,
+ line_end: PointG,
+}
+
+impl ObjectG{
+ fn apply_force(&mut self, force: &PointG){
+ let force = PointG::new( &(force.x / self.mass), &(force.y / self.mass) );
+
+ self.acc.add(&force);
+ }
+
+ fn walk(&mut self) {
+ self.vel.add(&self.acc);
+ self.pos.add(&self.vel);
+
+ self.a_acc = self.acc.x / 50.0;
+
+ self.a_vel = self.a_vel + self.a_acc;
+ self.ang = self.ang + self.a_vel;
+
+ self.acc=PointG::new(&0.0, &0.0);
+ }
+}
+
+struct Attractor{
+ pos: PointG,
+ size: i32,
+ mass: f64,
+}
+
+impl Attractor{
+ fn attract(&mut self, obj: &mut ObjectG){
+ let mut force = PointG::new(&self.pos.x, &self.pos.y);
+ force.sub(&obj.pos);
+
+ let dist = magnitude(force.x, force.y);
+ let mut dist = dist * dist;
+
+ if dist < 100.0 { dist = 100.0 }
+ if dist > 1000.0 { dist = 1000.0 }
+
+ let g = 5.0;
+
+ let strength = g * (self.mass * obj.mass) / dist;
+
+ force.set_mag(&strength);
+
+ obj.apply_force(&force);
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, atr: &mut Attractor){
+ canvas.set_draw_color(Color::RGBA(0,0,0,50));
+ canvas.fill_rect(Rect::new(0,0,600,600)).err();
+ //canvas.clear();
+
+ for obj in obj_arr{
+ obj.walk();
+ canvas.set_draw_color(Color::RGBA(150,50,255,150));
+ canvas.fill_rect(Rect::new(obj.pos.x as i32 - obj.size, obj.pos.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ canvas.draw_rect(Rect::new(obj.pos.x as i32 - obj.size, obj.pos.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ obj.line_end.set_angle(&obj.ang);
+
+ canvas.set_draw_color(Color::RGB(255,80,150));
+ canvas.draw_line(Point::new(obj.pos.x as i32,obj.pos.y as i32),Point::new((obj.pos.x + obj.line_end.x) as i32, (obj.pos.y + obj.line_end.y) as i32)).err();
+
+ atr.attract(obj);
+ }
+
+ canvas.set_draw_color(Color::RGB(255,50,150));
+ canvas.fill_rect(Rect::new(atr.pos.x as i32 - atr.size, atr.pos.y as i32 - atr.size, (atr.size * 2) as u32, (atr.size * 2) as u32)).err();
+
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=600;
+ let height: u32=600;
+
+ let window = video_subsystem.window("grav-attraction-point", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ for _ in 0..10{
+ let mut rng = rand::rng();
+ let mut obj = ObjectG{
+ pos: PointG::new( &rng.random_range(6.0..width as f64 -1.0), &rng.random_range(6.0..width as f64 -1.0)),
+ vel: PointG::new( &rng.random_range(-11.0..10.0), &rng.random_range(-11.0..10.0)),
+ acc: PointG::new( &0.0, &0.0 ),
+ size: 0,
+ mass: rng.random_range(50.0..150.0),
+ ang: 0.0,
+ a_vel: 0.02,
+ a_acc: 0.0,
+ line_end: PointG::new(&0.0,&0.0),
+ };
+ obj.size = (obj.mass.sqrt() * 2.0) as i32;
+ obj.line_end = PointG::new(&(obj.size as f64),&0.0);
+ obj_arr.push(obj);
+ }
+
+ let mut atr = Attractor{
+ pos: PointG::new(&(width as f64 /2.0), &(height as f64 /2.0)),
+ size: 0,
+ mass: 100.0,
+ };
+
+ atr.size = (atr.mass.sqrt() * 2.0) as i32;
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ 'running: loop {
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 30));
+ }
+}
diff --git a/src/bin/3-3-angles-and-vectors.rs b/src/bin/3-3-angles-and-vectors.rs
new file mode 100644
index 0000000..531b891
--- /dev/null
+++ b/src/bin/3-3-angles-and-vectors.rs
@@ -0,0 +1,231 @@
+extern crate sdl2;
+
+use libm::atan2;
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Point, Rect};
+use sdl2::render::WindowCanvas;
+use std::time::Duration;
+
+use rand::Rng;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+//i know i can use sdl points but i wanna make my own thing.
+//plus this is more independant.
+struct PointG{
+ x: f64,
+ y: f64,
+ start_x: f64,
+ start_y: f64,
+}
+impl PointG{
+ fn new(x: &f64, y: &f64)->Self{
+ Self{
+ x: *x,
+ y: *y,
+ start_x: *x,
+ start_y: *y,
+ }
+ }
+
+ fn add(&mut self, addvec: &PointG){
+ self.x = self.x + addvec.x;
+ self.y = self.y + addvec.y;
+ }
+
+ fn sub(&mut self, subvec: &PointG){
+ self.x = self.x - subvec.x;
+ self.y = self.y - subvec.y;
+ }
+
+ fn set_mag(&mut self, mag: &f64) {
+ let smag = set_mag(&self.x, &self.y, &mag);
+ self.x = smag[0];
+ self.y = smag[1];
+ }
+
+ fn set_angle(&mut self, angle: &f64){
+ let angle = angle % (3.14192 * 2.0);
+ let cos_theta = angle.cos();
+ let sin_theta = angle.sin();
+
+ let x = self.start_x * cos_theta - self.start_y * sin_theta;
+ let y = self.start_x * sin_theta + self.start_y * cos_theta;
+
+ self.x = x;
+ self.y = y;
+ }
+
+ fn heading(&mut self) -> f64{
+ let angle = atan2(self.y, self.x);
+ angle
+ }
+}
+
+struct ObjectG{
+ pos: PointG,
+ vel: PointG,
+ acc: PointG,
+ size: i32,
+ mass: f64,
+ ang: f64,
+ line_end: PointG,
+}
+
+impl ObjectG{
+ fn apply_force(&mut self, force: &PointG){
+ let force = PointG::new( &(force.x / self.mass), &(force.y / self.mass) );
+
+ self.acc.add(&force);
+ }
+
+ fn walk(&mut self) {
+ self.vel.add(&self.acc);
+ self.pos.add(&self.vel);
+
+ //self.a_acc = self.acc.x / 50.0;
+
+ //self.a_vel = self.a_vel + self.a_acc;
+ //self.ang = self.ang + self.a_vel;
+
+ self.acc=PointG::new(&0.0, &0.0);
+ }
+}
+
+struct Attractor{
+ pos: PointG,
+ size: i32,
+ mass: f64,
+}
+
+impl Attractor{
+ fn attract(&mut self, obj: &mut ObjectG){
+ let mut force = PointG::new(&self.pos.x, &self.pos.y);
+ force.sub(&obj.pos);
+
+ let dist = magnitude(force.x, force.y);
+ let mut dist = dist * dist;
+
+ if dist < 100.0 { dist = 100.0 }
+ if dist > 1000.0 { dist = 1000.0 }
+
+ let g = 5.0;
+
+ let strength = g * (self.mass * obj.mass) / dist;
+
+ force.set_mag(&strength);
+
+ obj.apply_force(&force);
+ }
+}
+
+fn draw(canvas: &mut WindowCanvas, obj_arr: &mut Vec<ObjectG>, atr: &mut Attractor){
+ canvas.set_draw_color(Color::RGBA(0,0,0,50));
+ canvas.fill_rect(Rect::new(0,0,600,600)).err();
+ canvas.clear();
+
+ for obj in obj_arr{
+ obj.walk();
+ canvas.set_draw_color(Color::RGBA(150,50,255,150));
+ canvas.fill_rect(Rect::new(obj.pos.x as i32 - obj.size, obj.pos.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ canvas.draw_rect(Rect::new(obj.pos.x as i32 - obj.size, obj.pos.y as i32 - obj.size, (obj.size * 2) as u32, (obj.size * 2) as u32)).err();
+
+ obj.ang = obj.vel.heading();
+ obj.line_end.set_angle(&obj.ang);
+
+ canvas.set_draw_color(Color::RGB(255,80,0));
+ canvas.draw_line(Point::new(obj.pos.x as i32,obj.pos.y as i32),Point::new((obj.pos.x + obj.line_end.x) as i32, (obj.pos.y + obj.line_end.y) as i32)).err();
+
+ atr.attract(obj);
+ }
+
+ canvas.set_draw_color(Color::RGB(255,50,150));
+ canvas.fill_rect(Rect::new(atr.pos.x as i32 - atr.size, atr.pos.y as i32 - atr.size, (atr.size * 2) as u32, (atr.size * 2) as u32)).err();
+
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=600;
+ let height: u32=600;
+
+ let window = video_subsystem.window("grav-attraction-point", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj_arr: Vec<ObjectG> = Vec::new();
+
+ for _ in 0..10{
+ let mut rng = rand::rng();
+ let mut obj = ObjectG{
+ pos: PointG::new( &rng.random_range(6.0..width as f64 -1.0), &rng.random_range(6.0..width as f64 -1.0)),
+ vel: PointG::new( &rng.random_range(-11.0..10.0), &rng.random_range(-11.0..10.0)),
+ acc: PointG::new( &0.0, &0.0 ),
+ size: 0,
+ mass: rng.random_range(50.0..150.0),
+ ang: 0.0,
+ line_end: PointG::new(&0.0,&0.0),
+ };
+ obj.size = (obj.mass.sqrt() * 2.0) as i32;
+ obj.line_end = PointG::new(&(obj.size as f64),&0.0);
+ obj_arr.push(obj);
+ }
+
+ let mut atr = Attractor{
+ pos: PointG::new(&(width as f64 /2.0), &(height as f64 /2.0)),
+ size: 0,
+ mass: 100.0,
+ };
+
+ atr.size = (atr.mass.sqrt() * 2.0) as i32;
+
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ 'running: loop {
+ draw(&mut canvas, &mut obj_arr, &mut atr);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 30));
+ }
+}
+
+
+// *~challenges
+// force a object forward based on its angle
diff --git a/src/bin/3-4-polar-cords.rs b/src/bin/3-4-polar-cords.rs
new file mode 100644
index 0000000..1c89f8a
--- /dev/null
+++ b/src/bin/3-4-polar-cords.rs
@@ -0,0 +1,129 @@
+extern crate sdl2;
+
+use sdl2::gfx::primitives::DrawRenderer;
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use std::time::Duration;
+use std::f64::consts::PI;
+
+use rand::{rng, Rng};
+
+struct PointG{
+ x: f64,
+ y: f64,
+}
+
+impl PointG{
+ fn new(x: &f64, y: &f64) -> Self{
+ Self{
+ x: *x,
+ y: *y,
+ }
+ }
+}
+
+struct ObjectG{
+ pos: PointG,
+ mouse: PointG,
+ ang: f64,
+ r: f64,
+}
+
+impl ObjectG{
+ fn new(x: &f64, y: &f64) -> Self{
+ Self{
+ pos: PointG::new(x,y),
+ //ang: -3.14192 / 4.0,
+ mouse: PointG::new(&0.0,&0.0),
+ ang: 0.0,
+ r: 150.0,
+ }
+ }
+}
+
+fn draw_circle(canvas: &mut sdl2::render::WindowCanvas, obj: &mut ObjectG){
+ let mut i = 0.0;
+ let mut inc = 0.1;
+ //let mut inc = (obj.mouse.x / PI)/30.0;
+ if inc < 0.01 { inc = 0.01 }
+ let mut vx: Vec<i16> = Vec::new();
+ let mut vy: Vec<i16> = Vec::new();
+
+ while i < (PI*2.0) {
+ obj.ang = i;
+ let r1 = obj.r + rng().random_range(-10.0..10.0);
+ obj.pos.x = r1 * obj.ang.cos();
+ obj.pos.y = r1 * obj.ang.sin();
+ //let nx = obj.r * (obj.ang - inc).cos();
+ //let ny = obj.r * (obj.ang - inc).sin();
+ //canvas.fill_rect(Rect::new(obj.pos.x as i32 + 200, obj.pos.y as i32 + 200, 5, 5)).err();
+ //canvas.draw_line(Point::new((obj.pos.x + 200.0) as i32, (obj.pos.y + 200.0) as i32),Point::new((nx as i32) + 200, (ny as i32) + 200)).err();
+ vx.push((obj.pos.x + 200.0) as i16);
+ vy.push((obj.pos.y + 200.0) as i16);
+ i = i + inc;
+ }
+
+ canvas.polygon(&vx, &vy, Color::RGB(150,50,255)).err();
+}
+
+fn draw(canvas: &mut sdl2::render::WindowCanvas, obj: &mut ObjectG){
+ canvas.set_draw_color(Color::RGBA(0,0,0,50));
+ canvas.clear();
+
+ draw_circle(canvas, obj);
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("polar-cords", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj = ObjectG::new(&0.0, &0.0);
+
+ canvas.set_draw_color(Color::RGBA(0,0,0,0));
+ canvas.fill_rect(Rect::new(0,0,width,height)).err();
+
+ draw(&mut canvas, &mut obj);
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ 'running: loop {
+ let state = event_pump.mouse_state();
+ obj.mouse.x = state.x() as f64;
+ obj.mouse.y = state.y() as f64;
+ draw(&mut canvas, &mut obj);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 30));
+ }
+}
+
+
+// *~challenges
+// make some shapes and shit.
+// perlin noise???
diff --git a/src/bin/3-5-harmonic-motion.rs b/src/bin/3-5-harmonic-motion.rs
new file mode 100644
index 0000000..28fa6b7
--- /dev/null
+++ b/src/bin/3-5-harmonic-motion.rs
@@ -0,0 +1,144 @@
+extern crate sdl2;
+
+use sdl2::gfx::primitives::DrawRenderer;
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use std::time::Duration;
+use std::f64::consts::PI;
+
+use rand::{rng, Rng};
+
+struct PointG{
+ x: f64,
+ y: f64,
+}
+
+impl PointG{
+ fn new(x: &f64, y: &f64) -> Self{
+ Self{
+ x: *x,
+ y: *y,
+ }
+ }
+}
+
+struct ObjectG{
+ pos: PointG,
+ mouse: PointG,
+ ang: f64,
+ a_vel: f64,
+ r: f64,
+}
+
+impl ObjectG{
+ fn new(x: &f64, y: &f64) -> Self{
+ Self{
+ pos: PointG::new(x,y),
+ mouse: PointG::new(&0.0,&0.0),
+ ang: 0.0,
+ a_vel: 0.1,
+ r: 150.0,
+ }
+ }
+}
+
+fn draw_circle(canvas: &mut sdl2::render::WindowCanvas, obj: &mut ObjectG){
+ let mut i = 0.0;
+ let mut inc = 0.1;
+ //let mut inc = (obj.mouse.x / PI)/30.0;
+ if inc < 0.01 { inc = 0.01 }
+ let mut vx: Vec<i16> = Vec::new();
+ let mut vy: Vec<i16> = Vec::new();
+
+ while i < (PI*2.0) {
+ obj.ang = i;
+ let r1 = obj.r + rng().random_range(-10.0..10.0);
+ obj.pos.x = r1 * obj.ang.cos();
+ obj.pos.y = r1 * obj.ang.sin();
+ //let nx = obj.r * (obj.ang - inc).cos();
+ //let ny = obj.r * (obj.ang - inc).sin();
+ //canvas.fill_rect(Rect::new(obj.pos.x as i32 + 200, obj.pos.y as i32 + 200, 5, 5)).err();
+ //canvas.draw_line(Point::new((obj.pos.x + 200.0) as i32, (obj.pos.y + 200.0) as i32),Point::new((nx as i32) + 200, (ny as i32) + 200)).err();
+ vx.push((obj.pos.x + 200.0) as i16);
+ vy.push((obj.pos.y + 200.0) as i16);
+ i = i + inc;
+ }
+
+ canvas.polygon(&vx, &vy, Color::RGB(150,50,255)).err();
+}
+
+fn draw(canvas: &mut sdl2::render::WindowCanvas, obj: &mut ObjectG){
+ canvas.set_draw_color(Color::RGBA(0,0,0,50));
+ //canvas.fill_rect(Rect::new(0,0,400,400)).err();
+ //canvas.rectangle(0, 0, 400, 400, Color::RGB(0,50,0)).err();
+ canvas.clear();
+
+
+ //obj.r = (obj.ang.sin() + 1.0) * 100.0;
+ //canvas.filled_circle(200, 200, (obj.r) as i16, Color::RGBA(150,50,255,254)).err();
+
+ obj.pos.y = obj.ang.sin() * 200.0;
+ canvas.filled_circle(200, (obj.pos.y + 200.0) as i16, 16 , Color::RGBA(150,50,255,254)).err();
+ canvas.line(200, 200, 200, (obj.pos.y + 200.0) as i16, Color::RGBA(150,50,255,254)).err();
+
+ //let inc = (PI * 2.0) / 60.0;
+
+ obj.ang = obj.ang + obj.a_vel;
+
+ //obj.a_vel = obj.a_vel + 0.0001;
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("harmonic-motion", width, height)
+ .position_centered()
+ .opengl()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj = ObjectG::new(&0.0, &0.0);
+
+ canvas.set_draw_color(Color::RGBA(0,0,0,0));
+ canvas.fill_rect(Rect::new(0,0,width,height)).err();
+
+ draw(&mut canvas, &mut obj);
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ 'running: loop {
+ let state = event_pump.mouse_state();
+ obj.mouse.x = state.x() as f64;
+ obj.mouse.y = state.y() as f64;
+ draw(&mut canvas, &mut obj);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
+
+
+// *~challenges
+// x and y ocillation
diff --git a/src/bin/cos-sin.rs b/src/bin/cos-sin.rs
new file mode 100644
index 0000000..6cf2c52
--- /dev/null
+++ b/src/bin/cos-sin.rs
@@ -0,0 +1,89 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use std::time::Duration;
+
+struct ObjectG{
+ x: i32,
+ y: i32,
+ screen_width: i32,
+ screen_height: i32,
+ frame: i32,
+}
+
+impl ObjectG{
+ fn walk(&mut self) {
+ self.frame = self.frame + 1;
+
+ let speed = 50.0;
+ self.x = (((self.frame as f64) / speed).sin() * (self.screen_width as f64) / 2.1) as i32 + (self.screen_width / 2);
+ self.y = (((self.frame as f64) / speed).cos() * (self.screen_height as f64) / 2.1) as i32 + (self.screen_height / 2);
+
+ if self.x < 0 { self.x = 0 }
+ if self.y < 0 { self.y = 0 }
+ if self.x > self.screen_width { self.x = self.screen_width }
+ if self.y > self.screen_height{ self.y = self.screen_height }
+ }
+}
+
+fn draw(canvas: &mut sdl2::render::WindowCanvas, obj: &mut ObjectG){
+ canvas.set_draw_color(Color::RGB(0,0,0));
+ canvas.clear();
+
+ //putRectRGB(renderer,i*boxsize,j*boxsize,boxsize-1,150,50,255);
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ obj.walk();
+ canvas.fill_rect(Rect::new(obj.x-5/2, obj.y-5/2, 5, 5)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("cos-sin", width, height)
+ .position_centered()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+
+
+ let mut obj = ObjectG{
+ x: width as i32 /2,
+ y: height as i32 /2,
+ screen_width: width as i32,
+ screen_height: height as i32,
+ frame: 0,
+ };
+
+ draw(&mut canvas, &mut obj);
+
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ 'running: loop {
+ draw(&mut canvas, &mut obj);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+ // The rest of the game loop goes here...
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}
diff --git a/src/bin/transparency-test-a.rs b/src/bin/transparency-test-a.rs
new file mode 100644
index 0000000..c6be75c
--- /dev/null
+++ b/src/bin/transparency-test-a.rs
@@ -0,0 +1,63 @@
+extern crate sdl2;
+
+//use sdl2::gfx::primitives::DrawRenderer;
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Rect};
+use std::time::Duration;
+
+fn draw(canvas: &mut sdl2::render::WindowCanvas){
+ canvas.set_draw_color(Color::RGBA(200,0,0,50));
+ canvas.fill_rect(Rect::new(200,200,100,100)).err();
+ //canvas.clear();
+
+ canvas.set_draw_color(Color::RGBA(200,0,0,255));
+ canvas.fill_rect(Rect::new(100,100,50,50)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let mut window = video_subsystem.window("transparency-test-a", width, height)
+ .opengl()
+ .position_centered()
+ .build()
+ .unwrap();
+
+ window.set_opacity(0.5).expect("cant set opa :<");
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ canvas.set_draw_color(Color::RGBA(0,0,0,0));
+ canvas.fill_rect(Rect::new(0,0,width,height)).err();
+
+ draw(&mut canvas);
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ 'running: loop {
+ draw(&mut canvas);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 30));
+ }
+}
diff --git a/src/bin/walker-levy-flight.rs b/src/bin/walker-levy-flight.rs
new file mode 100644
index 0000000..b5c0093
--- /dev/null
+++ b/src/bin/walker-levy-flight.rs
@@ -0,0 +1,135 @@
+extern crate sdl2;
+
+use sdl2::pixels::Color;
+use sdl2::event::Event;
+use sdl2::keyboard::Keycode;
+use sdl2::rect::{Point, Rect};
+use std::time::Duration;
+
+use rand::Rng;
+
+fn magnitude(x: f64,y: f64) -> f64 {
+ ((x).powi(2) + (y).powi(2)).sqrt()
+}
+
+fn set_mag(x: &f64,y: &f64, mag: &f64) -> Vec<f64>{
+ let getmag: f64 = magnitude(*x, *y);
+ let rx = (*x / getmag) * mag;
+ let ry = (*y / getmag) * mag;
+
+ return vec![rx,ry]
+}
+
+#[derive(Clone)]
+struct PointG{
+ x: f64,
+ y: f64,
+}
+impl PointG{
+ fn add(&mut self, addvec: &PointG){
+ self.x = self.x + addvec.x;
+ self.y = self.y + addvec.y;
+ }
+
+ fn mul(&mut self, mult: &f64){
+ self.x = self.x * mult;
+ self.y = self.y * mult;
+ }
+
+ fn set_mag(&mut self, mag: &f64) {
+ let smag = set_mag(&self.x, &self.y, &mag);
+ self.x = smag[0];
+ self.y = smag[1];
+ }
+}
+
+struct ObjectG{
+ pos: PointG,
+ prev: PointG,
+ screen_width: i32,
+ screen_height: i32,
+}
+
+impl ObjectG{
+ fn walk(&mut self) {
+ let mut rng = rand::rng();
+ self.prev = self.pos.clone();
+
+ let mut step = PointG{x: rng.random_range(-1.0..1.0), y: rng.random_range(-1.0..1.0)};
+
+ let r = rng.random_range(0.0..100.0);
+ if r < 1.0 {
+ step.mul(&rng.random_range(25.0..100.0));
+ } else {
+ step.set_mag(&2.0);
+ }
+
+ self.pos.add(&step);
+
+ if self.pos.x < 0.0 { self.pos.x = 0.0 }
+ if self.pos.y < 0.0 { self.pos.y = 0.0 }
+ if self.pos.x > self.screen_width as f64{ self.pos.x = self.screen_width as f64}
+ if self.pos.y > self.screen_height as f64{ self.pos.y = self.screen_height as f64}
+ }
+}
+
+fn draw(canvas: &mut sdl2::render::WindowCanvas, obj: &mut ObjectG){
+
+ canvas.set_draw_color(Color::RGBA(0,0,0,20));
+ //canvas.clear();
+ canvas.fill_rect(Rect::new(0,0,obj.screen_width as u32,obj.screen_height as u32)).err();
+
+ canvas.set_draw_color(Color::RGB(150,50,255));
+ obj.walk();
+ canvas.fill_rect(Rect::new(obj.pos.x as i32, obj.pos.y as i32, 5, 5)).err();
+ canvas.draw_line(Point::new(obj.pos.x as i32, obj.pos.y as i32),Point::new(obj.prev.x as i32, obj.prev.y as i32)).err();
+
+ canvas.present();
+}
+
+
+
+fn main() {
+ let sdl2_context = sdl2::init().unwrap();
+ let video_subsystem = sdl2_context.video().unwrap();
+
+
+ let width: u32=400;
+ let height: u32=400;
+
+ let window = video_subsystem.window("walker-levy-flight", width, height)
+ .position_centered()
+ .opengl()
+ .build()
+ .unwrap();
+
+ let mut canvas = window.into_canvas().build().unwrap();
+ canvas.default_pixel_format();
+ canvas.set_blend_mode(sdl2::render::BlendMode::Blend);
+
+ let mut obj = ObjectG{
+ pos: PointG{x: width as f64/2.0,y: height as f64 /2.0},
+ prev: PointG{x: width as f64/2.0,y: height as f64 /2.0},
+ screen_width: width as i32,
+ screen_height: height as i32,
+ };
+
+ draw(&mut canvas, &mut obj);
+
+
+ let mut event_pump = sdl2_context.event_pump().unwrap();
+ 'running: loop {
+ draw(&mut canvas, &mut obj);
+ for event in event_pump.poll_iter() {
+ match event {
+ Event::Quit {..} |
+ Event::KeyDown { keycode: Some(Keycode::Escape), .. } => {
+ break 'running
+ },
+ _ => {}
+ }
+ }
+
+ ::std::thread::sleep(Duration::new(0, 1_000_000_000u32 / 60));
+ }
+}