aboutsummaryrefslogtreecommitdiff
path: root/src/display/pixelflut.rs
blob: 3a62f8dfecae9e1062cc4c3865bb13c1f050df46 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
use std::io::Write;
use std::net::{TcpStream};

use crate::vec3::Color;
use crate::display::{Display, Pixel};    

pub struct Pixelflut {
    socket: TcpStream,
    x: usize,
    y: usize,
    width: usize,
    height: usize,
    data: Vec<Pixel>,
}

impl Pixelflut {
    pub fn new(addr: &str, x: usize, y: usize, width: usize, height: usize) -> Self {
        let data = vec![
            Pixel {
                color: Color {
                    x: 0.0,
                    y: 0.0,
                    z: 0.0
                },
                sample_count: 0
            };
            width * height
        ];
        let mut ret = Self {
            socket: TcpStream::connect(addr).expect("Could not connect to Pixelflut!"),
            x,
            y,
            width,
            height,
            data,
        };
        ret.maybe_update();
        ret
    }
}

impl Display for Pixelflut {
    fn add_sample(&mut self, x: usize, y: usize, color: crate::vec3::Color) {
        self.data
            .get_mut((y * self.width) + x)
            .unwrap()
            .update(color);
    }

    fn maybe_write(&self, _: &mut impl std::io::prelude::Write) {}

    fn maybe_update(&mut self) {
        for y in 0..self.height {
            for x in 0..self.width {
                let pixel = self.data.get((y * self.width) + x).unwrap();
                let scale = 1.0 / pixel.sample_count as f64;
                let mut r = (pixel.color.x * scale).sqrt();
                let mut g = (pixel.color.y * scale).sqrt();
                let mut b = (pixel.color.z * scale).sqrt();
                self.socket.write(format!("PX {} {} {:02x}{:02x}{:02x}\n",
                                          self.x + x,
                                          self.y + self.height - y,
                                          (256.0 * r.clamp(0.0, 0.999)) as u32,
                                          (256.0 * g.clamp(0.0, 0.999)) as u32,
                                          (256.0 * b.clamp(0.0, 0.999)) as u32).as_bytes());
            }
        }
    }
}