It should show the images not being stretched out, I am unsure why this happens. This is specifically only about mode 3
main.rs
use graphics::{blend_colors, set_pixel_value};
const WIDTH: usize = 900;
const HEIGHT: usize = 900;
struct Image {
width: usize,
height: usize,
buffer: Vec<u32>,
}
impl Image {
fn load(filename: &str) -> Image {
let image =
lodepng::decode32_file(&filename).expect(&format!("Couldn't load {}", &filename));
Image {
width: image.width,
height: image.height,
buffer: image
.buffer
.iter()
.map(|color| {
return u32::from_le_bytes([color.b, color.g, color.r, color.a]);
})
.collect(),
}
}
}
fn main() {
let image1 = Image::load("mainframe1.png");
let image2 = Image::load("mainframe2.png");
let mut window = minifb::Window::new(
"Rotating images",
WIDTH as usize,
HEIGHT as usize,
minifb::WindowOptions {
resize: false,
topmost: true,
borderless: true,
none: true,
transparency: true,
scale: minifb::Scale::X1,
..minifb::WindowOptions::default()
},
)
.expect("Unable to create window");
// The output buffer that we'll render the output image to
let mut buffer = vec![0u32; (WIDTH * HEIGHT) as usize];
// The current rotation in radians (0..2*Pi)
let mut rotation: f32 = 0.0;
// Offsets
let x_offset = WIDTH as f32 / 2 as f32;
let y_offset = HEIGHT as f32 / 2 as f32;
// Whether we are just drawing a single image (0), rotating a single image (1),
// or rotating two superimposed images in different directions (2).
let mut mode = 3;
let mut fps_time = std::time::Instant::now();
let mut fps_count = 0;
while window.is_open() && !window.is_key_down(minifb::Key::Escape) {
rotation += 0.01;
if window.is_key_pressed(minifb::Key::Space, minifb::KeyRepeat::No) {
mode = (mode + 1) % 3;
}
// Draw!
// To prevent code duplication, you may want to move your code from
// your `modes` answers into a function or a method of `Image`.
if mode == 0 {
window.update_with_buffer(&image1.buffer, image1.width, image1.height).unwrap();
} else if mode == 1 {
let mut buffer: Vec<u32> = image1.buffer.to_vec();
let brightness: f32 = 0.25;
for pixel in buffer.iter_mut() {
let [blue, green, red, alpha] = pixel.to_ne_bytes();
*pixel = u32::from_ne_bytes([
set_pixel_value(brightness, blue),
set_pixel_value(brightness, green),
set_pixel_value(brightness, red),
alpha,
]);
}
window.update_with_buffer(&buffer, image1.width, image1.height).unwrap();
} else if mode == 2 {
let brightness: f32 = 0.5;
for y in 0..HEIGHT {
for x in 0..WIDTH {
// for positive integers, the euclidean remainder is the same as the `%` operator
let color_1 = get_color(&image1, y, x);
let color_2 = get_color(&image2, y, x);
// Blend two colors use whatever formula you wants
let final_color = blend_colors(color_1, color_2, brightness);
buffer[y * WIDTH + x] = final_color;
}
}
} else if mode == 3 {
// TODO: Offset and rotate image 1
for x in 0..HEIGHT {
for y in 0..WIDTH {
let translated_x = x as f32 - x_offset as f32;
let translated_y = y as f32 - y_offset as f32;
let rotated_x = translated_x * rotation.cos() + translated_y * rotation.sin();
let rotated_y = translated_x * rotation.sin() - translated_y * rotation.cos();
let color = get_color(&image1, rotated_y as usize, rotated_x as usize);
buffer[y * WIDTH + x] = color;
}
}
} else if mode == 4 {
let brightness = 0.5;
for x in 0..HEIGHT {
for y in 0..WIDTH {
let translated_x = x as f32 - x_offset as f32;
let translated_y = y as f32 - y_offset as f32;
let rotated_x = translated_x * rotation.cos() + translated_y * rotation.sin();
let rotated_y = translated_x * rotation.sin() - translated_y * rotation.cos();
let color_1 = get_color(&image1, y, x);
let color_2 = get_color(&image2, y, x);
let final_color = blend_colors(color_1, color_2, brightness);
buffer[rotated_y as usize * WIDTH + rotated_x as usize] = final_color;
}
}
// TODO: Everything together!
// Offset and rotate two superimposed images in opposite directions
} else {
// Optimized
// For optimization code can be combined here instead of the deduplication
// in the name of speed
}
// Show the buffer in the window
if ![0, 1].contains(&mode) {
window.update_with_buffer(&buffer, WIDTH as usize, HEIGHT as usize).unwrap();
}
// Display the FPS rate 3 times per second
let now = std::time::Instant::now();
let duration = (now - fps_time).as_secs_f32();
fps_count += 1;
if duration >= 0.33 {
println!("{} fps", (fps_count as f32 / duration).round() as u32);
fps_time = now;
fps_count = 0;
}
}
}
fn get_color(image: &Image, y: usize, x: usize) -> u32 {
let x1 = x.rem_euclid(image.width);
let y1 = y.rem_euclid(image.height);
let color = image.buffer[y1 * image.width + x1];
color
}
lib.rs
pub fn blend_colors(mut color_1: u32, mut color_2: u32, brightness: f32) -> u32 {
color_1 = set_all_pixels_to_value(brightness, color_1);
let [blue_color_1, green_color_1, red_color_1, alpha_color_1] = color_1.to_ne_bytes();
color_2 = set_all_pixels_to_value(brightness, color_2);
let [blue_color_2, green_color_2, red_color_2, alpha_color_2] = color_2.to_ne_bytes();
let final_color = u32::from_ne_bytes([
((blue_color_1 as u16 + blue_color_2 as u16) / 2) as u8,
((green_color_1 as u16 + green_color_2 as u16) / 2) as u8,
((red_color_1 as u16 + red_color_2 as u16) / 2) as u8,
((alpha_color_1 as u16 + alpha_color_2 as u16) / 2) as u8,
]);
final_color
}
pub fn set_pixel_value(factor: f32, pixel_color: u8) -> u8 {
let pixel_color = (pixel_color as f32 * factor) as u8;
pixel_color
}
pub fn set_all_pixels_to_value(factor: f32, pixel: u32) -> u32 {
for value in pixel.to_ne_bytes() {
set_pixel_value(factor, value);
}
pixel
}



