1use png::{BitDepth, ColorType};
2use wasm_bindgen::prelude::*;
3
4use libmosh::{MoshCore, generate_palette};
5
6pub mod utils;
7
8#[wasm_bindgen]
9#[derive(Default)]
10pub struct Core(MoshCore);
11
12#[wasm_bindgen]
13impl Core {
14 pub fn ansi(&self) -> bool {
15 self.0.options.ansi
16 }
17 pub fn min_rate(&self) -> u16 {
18 self.0.options.min_rate
19 }
20
21 pub fn max_rate(&self) -> u16 {
22 self.0.options.max_rate
23 }
24
25 pub fn pixelation(&self) -> u8 {
26 self.0.options.pixelation
27 }
28
29 pub fn line_shift(&self) -> f64 {
30 self.0.options.line_shift
31 }
32
33 pub fn reverse(&self) -> f64 {
34 self.0.options.reverse
35 }
36
37 pub fn flip(&self) -> f64 {
38 self.0.options.flip
39 }
40
41 pub fn channel_swap(&self) -> f64 {
42 self.0.options.channel_swap
43 }
44
45 pub fn channel_shift(&self) -> f64 {
46 self.0.options.channel_shift
47 }
48
49 pub fn seed(&self) -> u64 {
50 self.0.options.seed
51 }
52
53 pub fn set_ansi(&mut self, value: bool) {
54 self.0.options.ansi = value;
55 }
56
57 pub fn set_min_rate(&mut self, value: u16) {
58 self.0.options.min_rate = value;
59 }
60
61 pub fn set_max_rate(&mut self, value: u16) {
62 self.0.options.max_rate = value;
63 }
64
65 pub fn set_pixelation(&mut self, value: u8) {
66 self.0.options.pixelation = value;
67 }
68
69 pub fn set_line_shift(&mut self, value: f64) {
70 self.0.options.line_shift = value;
71 }
72
73 pub fn set_reverse(&mut self, value: f64) {
74 self.0.options.reverse = value;
75 }
76
77 pub fn set_flip(&mut self, value: f64) {
78 self.0.options.flip = value;
79 }
80
81 pub fn set_channel_swap(&mut self, value: f64) {
82 self.0.options.channel_swap = value;
83 }
84
85 pub fn set_channel_shift(&mut self, value: f64) {
86 self.0.options.channel_shift = value;
87 }
88
89 pub fn new_seed(&mut self) {
90 self.0.options.new_seed();
91 }
92
93 #[wasm_bindgen]
98 pub fn pixelmosh(&mut self, image: &[u8]) -> Result<Vec<u8>, JsValue> {
99 let mut output: Vec<u8> = Vec::new();
100
101 self.0
102 .read_image(image)
103 .map_err(|error| JsValue::from(error.to_string()))?;
104
105 self.0
106 .mosh()
107 .map_err(|error| JsValue::from(error.to_string()))?;
108
109 {
110 let mut encoder = png::Encoder::new(&mut output, self.0.data.width, self.0.data.height);
111
112 encoder.set_color(if self.0.options.ansi {
113 ColorType::Indexed
114 } else {
115 self.0.data.color_type
116 });
117
118 encoder.set_depth(if self.0.options.ansi {
119 BitDepth::Eight
120 } else {
121 self.0.data.bit_depth
122 });
123
124 if self.0.options.ansi {
125 encoder.set_palette(crate::generate_palette());
126 };
127
128 let mut writer = encoder
129 .write_header()
130 .map_err(|error| JsValue::from(error.to_string()))?;
131
132 writer
133 .write_image_data(&self.0.data.buf)
134 .map_err(|error| JsValue::from(error.to_string()))?;
135 }
136
137 Ok(output)
138 }
139}