Commit | Line | Data |
---|---|---|
c17769db KS |
1 | enum GlyphEdge { |
2 | Left, | |
3 | Top, | |
4 | Right, | |
5 | Bottom, | |
6 | None | |
7 | } | |
8 | ||
9 | impl GlyphEdge { | |
10 | fn get(x: usize, y: usize, size: usize) -> Self { | |
11 | if y == 0 { | |
12 | GlyphEdge::Bottom | |
13 | } else if y == size - 1 { | |
14 | GlyphEdge::Top | |
15 | } else if x == 0 { | |
16 | GlyphEdge::Left | |
17 | } else if x == size - 1 { | |
18 | GlyphEdge::Right | |
19 | } else { | |
20 | GlyphEdge::None | |
21 | } | |
22 | } | |
23 | } | |
24 | ||
25 | enum GlyphDir { | |
26 | Left, | |
27 | Up, | |
28 | Right, | |
29 | Down, | |
30 | None | |
31 | } | |
32 | ||
33 | impl GlyphDir { | |
34 | fn get(edge0: GlyphEdge, edge1: GlyphEdge) -> Self { | |
35 | match (edge0, edge1) { | |
36 | (GlyphEdge::Left, GlyphEdge::Right) | | |
37 | (GlyphEdge::Right, GlyphEdge::Left) => GlyphDir::Up, | |
38 | (GlyphEdge::Top, GlyphEdge::Bottom) | | |
39 | (GlyphEdge::Bottom, GlyphEdge::Top) => GlyphDir::Right, | |
40 | (GlyphEdge::Bottom, _) | | |
41 | (_, GlyphEdge::Bottom) => GlyphDir::Up, | |
42 | (GlyphEdge::Top, _) | | |
43 | (_, GlyphEdge::Top) => GlyphDir::Down, | |
44 | (GlyphEdge::Left, _) | | |
45 | (_, GlyphEdge::Left) => GlyphDir::Left, | |
46 | (GlyphEdge::Right, _) | | |
47 | (_, GlyphEdge::Right) => GlyphDir::Right, | |
48 | _ => GlyphDir::None, | |
49 | } | |
50 | } | |
51 | } | |
52 | ||
53 | const XVEC4: [usize; 16] = [0, 1, 2, 3, 3, 3, 3, 2, 1, 0, 0, 0, 1, 2, 2, 1]; | |
54 | const YVEC4: [usize; 16] = [0, 0, 0, 0, 1, 2, 3, 3, 3, 3, 2, 1, 1, 1, 2, 2]; | |
55 | const XVEC8: [usize; 16] = [0, 2, 5, 7, 7, 7, 7, 7, 7, 5, 2, 0, 0, 0, 0, 0]; | |
56 | const YVEC8: [usize; 16] = [0, 0, 0, 0, 1, 3, 4, 6, 7, 7, 7, 7, 6, 4, 3, 1]; | |
57 | ||
58 | fn make_glyphs_47(glyphs4: &mut [[u8; 16]; 256], glyphs8: &mut [[u8; 64]; 256]) { | |
59 | for (n, glyph) in glyphs4.iter_mut().enumerate() { | |
60 | let i = n >> 4; | |
61 | let j = n & 0xF; | |
62 | make_glyph_47(glyph, XVEC4[i], YVEC4[i], XVEC4[j], YVEC4[j], 4); | |
63 | } | |
64 | for (n, glyph) in glyphs8.iter_mut().enumerate() { | |
65 | let i = n >> 4; | |
66 | let j = n & 0xF; | |
67 | make_glyph_47(glyph, XVEC8[i], YVEC8[i], XVEC8[j], YVEC8[j], 8); | |
68 | } | |
69 | } | |
70 | fn make_glyph_47(dst: &mut [u8], xi: usize, yi: usize, xj: usize, yj: usize, size: usize) { | |
71 | let edge0 = GlyphEdge::get(xi, yi, size); | |
72 | let edge1 = GlyphEdge::get(xj, yj, size); | |
73 | let dir = GlyphDir::get(edge0, edge1); | |
74 | let npoints = if xi > xj { xi - xj } else { xj - xi }.max(if yi > yj { yi - yj } else { yj - yi }); | |
75 | for ipoint in 0..=npoints { | |
76 | let (p0, p1) = if npoints > 0 { | |
77 | (interpolate(xi, xj, ipoint, npoints), | |
78 | interpolate(yi, yj, ipoint, npoints)) | |
79 | } else { | |
80 | (xi, yi) | |
81 | }; | |
82 | let off = p0 + p1 * size; | |
83 | match dir { | |
84 | GlyphDir::Up => { | |
85 | for i in 0..=p1 { | |
86 | dst[off - i * size] = 1; | |
87 | } | |
88 | }, | |
89 | GlyphDir::Down => { | |
90 | for i in 0..size-p1 { | |
91 | dst[off + i * size] = 1; | |
92 | } | |
93 | }, | |
94 | GlyphDir::Left => { | |
95 | for i in 0..=p0 { | |
96 | dst[off - i] = 1; | |
97 | } | |
98 | }, | |
99 | GlyphDir::Right => { | |
100 | for i in 0..size-p0 { | |
101 | dst[off + i] = 1; | |
102 | } | |
103 | }, | |
104 | _ => {}, | |
105 | }; | |
106 | } | |
107 | } | |
108 | fn interpolate(a: usize, b: usize, pos1: usize, range: usize) -> usize { | |
109 | (a * pos1 + b * (range - pos1) + range / 2) / range | |
110 | } | |
111 | ||
112 | mod v1; | |
113 | pub use v1::get_decoder_video_v1; | |
114 | mod v2; | |
115 | pub use v2::get_decoder_video_v2; | |
116 | ||
117 | mod iact; | |
118 | pub use iact::get_decoder_iact; | |
119 | mod vima; | |
120 | pub use vima::get_decoder_vima; |