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
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
//! # Rustvision
//!
//! Simple (and very early) project for interacting with images, vertices, and polygons (and some other stuff related to computer vision).
//!
//! **Note:** This project is in a very early state and the documentation is far from perfect. Feel free to open PRs with improvements!
//!
//! ## Installation
//!
//! Simply add this crate to your `Cargo.toml` (either via `cargo add` or manually).
//!
//! ## Usage
//!
//! The usage of this library is very straight forward. First you need to create a new image.
//!
//! ```rust
//! use rustvision::image::Image;
//!
//! let mut img = Image::new(400, 400);
//! ```
//!
//! ### Rectangle
//!
//! To work with a simple rectangle, you can import and then create one:
//!
//! ```rust
//! use rustvision::{shapes::Rectangle, rgb, vec2};
//!
//! let rect = Rectangle::new(vec2![50.0, 40.0], 100, 70, rgb!(255, 0, 0));
//! ```
//!
//! This will create a new instance of a rectangle at the coordinates x-y-coordinates `(50.0, 40.0)` with a width of 100, a height of 70 and the color red.
//!
//! You will notice the usage of two macros here: `vec2![]` and `rgb!()`. `vec2![]` is a utility macro to create a 2D vector with the specified coordinates, whereas `rgb!()` creates a new RGB color for you. For more information on these have a look at the code (or later documentation).
//!
//! If you want to draw this created rectangle to the image, you can do so by calling `img.draw`:
//!
//! ```rust
//! # use rustvision::{image::Image, shapes::Rectangle, rgb, vec2};
//! # let mut img = Image::new(400, 400);
//! # let rect = Rectangle::new(vec2![50.0, 40.0], 100, 70, rgb!(255, 0, 0));
//! img.draw(&rect);
//! ```
//!
//! This will draw the rectangle to the provided image. To finally save the image to your disk, you can use another utility macro:
//!
//! ```rust, no_run
//! # use rustvision::{image::Image, shapes::Rectangle, rgb, ppm::PNM, vec2, save_pnm_p6};
//! # let mut img = Image::new(400, 400);
//! # let rect = Rectangle::new(vec2![50.0, 40.0], 100, 70, rgb!(255, 0, 0));
//! # img.draw(&rect);
//! save_pnm_p6!("path_to_image.ppm", img);
//! ```
//!
//! The image will be saved in the P6 (binary PPM) representation. If you prefer the ASCII representation (P3), this library provides another utility macro as well.
//!
//! ### Polygons
//!
//! Similar to rectangles, you can create more complex polygons:
//!
//! ```rust
//! use rustvision::{shapes::Polygon, vec2};
//!
//! let mut polygon = Polygon::from_points(vec![
//! vec2![20.0, 250.0],
//! vec2![50.0, 350.0],
//! vec2![80.0, 280.0],
//! vec2![110.0, 350.0],
//! vec2![140.0, 250.0],
//! vec2![110.0, 300.0],
//! vec2![80.0, 250.0],
//! vec2![50.0, 300.0],
//! ]);
//! ```
//!
//! Notice that this "constructor" does not take a color. By default, this polygon will be black. If you want to specify a color, you can do so with the respective method:
//!
//! ```rust
//! # use rustvision::{image::Image, shapes::Polygon, rgb, vec2};
//! # let mut polygon = Polygon::from_points(vec![
//! # vec2![20.0, 250.0],
//! # vec2![50.0, 350.0],
//! # vec2![80.0, 280.0],
//! # vec2![110.0, 350.0],
//! # vec2![140.0, 250.0],
//! # vec2![110.0, 300.0],
//! # vec2![80.0, 250.0],
//! # vec2![50.0, 300.0],
//! # ]);
//! polygon.set_color(rgb!(0, 255, 0));
//! ```
//!
//! This will color the polygon green. Painting this polygon now would result in only the outline being drawn. To fill it, you need to manually set the flag:
//!
//! ```rust
//! # use rustvision::{image::Image, shapes::Polygon, rgb, vec2};
//! # let mut polygon = Polygon::from_points(vec![
//! # vec2![20.0, 250.0],
//! # vec2![50.0, 350.0],
//! # vec2![80.0, 280.0],
//! # vec2![110.0, 350.0],
//! # vec2![140.0, 250.0],
//! # vec2![110.0, 300.0],
//! # vec2![80.0, 250.0],
//! # vec2![50.0, 300.0],
//! # ]);
//! # polygon.set_color(rgb!(0, 255, 0));
//! polygon.set_filled(true);
//! ```
//!
//! Similar to a rectangle, you can draw this polygon to an image:
//!
//! ```rust
//! # use rustvision::{image::Image, shapes::Polygon, rgb, vec2};
//! # let mut polygon = Polygon::from_points(vec![
//! # vec2![20.0, 250.0],
//! # vec2![50.0, 350.0],
//! # vec2![80.0, 280.0],
//! # vec2![110.0, 350.0],
//! # vec2![140.0, 250.0],
//! # vec2![110.0, 300.0],
//! # vec2![80.0, 250.0],
//! # vec2![50.0, 300.0],
//! # ]);
//! # polygon.set_color(rgb!(0, 255, 0));
//! # polygon.set_filled(true);
//! # let mut img = Image::new(400, 400);
//! img.draw(&polygon);
//! ```
//! ## Reading Files
//!
//! You can read files and convert them to the internal image representation by using the `load_image` macro:
//!
//! ```rust, no_run
//! use rustvision::{load_image, save_pnm_p3};
//!
//! let image = load_image!("assets/mona_lisa_small.ppm");
//! ```
//!
//! **Note:** Currently, this library only support images in PPM6 (i.e., binary PPM) representation. Trying to read any other file will lead to a panic!