forked from koniifer/ableos
Merge branch 'master' of ssh://git.ablecorp.us:20/able/ableos
This commit is contained in:
commit
0404fdd41f
3
.vscode/settings.json
vendored
3
.vscode/settings.json
vendored
|
@ -1,5 +1,8 @@
|
||||||
{
|
{
|
||||||
"files.associations": {
|
"files.associations": {
|
||||||
"stddef.h": "c"
|
"stddef.h": "c"
|
||||||
|
},
|
||||||
|
"settings": {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -41,7 +41,7 @@ lliw = "0.2.0"
|
||||||
# qoi_rs = "*"
|
# qoi_rs = "*"
|
||||||
spin = "0.5.2"
|
spin = "0.5.2"
|
||||||
vga = "*"
|
vga = "*"
|
||||||
log= "*"
|
log = "*"
|
||||||
pretty-hex = "0.2.1"
|
pretty-hex = "0.2.1"
|
||||||
unicode-width = "0.1.7"
|
unicode-width = "0.1.7"
|
||||||
picorand = "*"
|
picorand = "*"
|
||||||
|
|
|
@ -1 +1 @@
|
||||||
nightly
|
nightly-2022-01-04
|
||||||
|
|
|
@ -18,14 +18,17 @@
|
||||||
#![feature(exclusive_range_pattern)]
|
#![feature(exclusive_range_pattern)]
|
||||||
#![feature(slice_pattern)]
|
#![feature(slice_pattern)]
|
||||||
|
|
||||||
|
/// Contains architecture specific code for aarch64.
|
||||||
#[cfg(target_arch = "aarch64")]
|
#[cfg(target_arch = "aarch64")]
|
||||||
#[path = "arch/aarch64/mod.rs"]
|
#[path = "arch/aarch64/mod.rs"]
|
||||||
pub mod arch;
|
pub mod arch;
|
||||||
|
|
||||||
|
/// Contains architecture specific code for x86_64.
|
||||||
#[cfg(target_arch = "x86_64")]
|
#[cfg(target_arch = "x86_64")]
|
||||||
#[path = "arch/x86_64/mod.rs"]
|
#[path = "arch/x86_64/mod.rs"]
|
||||||
pub mod arch;
|
pub mod arch;
|
||||||
|
|
||||||
|
/// Contains architecture specific code for riscv64.
|
||||||
#[cfg(target_arch = "riscv64")]
|
#[cfg(target_arch = "riscv64")]
|
||||||
#[path = "arch/riscv/mod.rs"]
|
#[path = "arch/riscv/mod.rs"]
|
||||||
pub mod arch;
|
pub mod arch;
|
||||||
|
|
|
@ -3,11 +3,11 @@ use shadeable::pixel_format::Rgba64;
|
||||||
use crate::SCREEN_BUFFER;
|
use crate::SCREEN_BUFFER;
|
||||||
|
|
||||||
use {
|
use {
|
||||||
ab_glyph::{Font, FontRef, Glyph},
|
ab_glyph::{Font, FontRef, Glyph},
|
||||||
vga::{
|
vga::{
|
||||||
colors::Color16,
|
colors::Color16,
|
||||||
writers::{Graphics640x480x16, GraphicsWriter},
|
writers::{Graphics640x480x16, GraphicsWriter},
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
lazy_static::lazy_static! {
|
lazy_static::lazy_static! {
|
||||||
|
@ -20,6 +20,10 @@ lazy_static::lazy_static! {
|
||||||
pub static ref VGAE_BUFF_OFFSET_Y: spin::Mutex<u8> = spin::Mutex::new(0);
|
pub static ref VGAE_BUFF_OFFSET_Y: spin::Mutex<u8> = spin::Mutex::new(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const FONT_SCALE: f32 = 1.6;
|
||||||
|
const GLYPH_HEIGHT: f32 = 18.0;
|
||||||
|
const GLYPH_WIDTH: f32 = 10.0;
|
||||||
|
|
||||||
/// Draw a glyph on the screen at the given position
|
/// Draw a glyph on the screen at the given position
|
||||||
///
|
///
|
||||||
/// # Arguments
|
/// # Arguments
|
||||||
|
@ -27,79 +31,86 @@ lazy_static::lazy_static! {
|
||||||
/// * `y` - the y position of the glyph
|
/// * `y` - the y position of the glyph
|
||||||
/// * `glyph` - the glyph to draw
|
/// * `glyph` - the glyph to draw
|
||||||
/// * `color` - the color of the glyph
|
/// * `color` - the color of the glyph
|
||||||
pub fn draw_char(x: u8, y: u8, character: char, color: Rgba64) {
|
pub fn draw_char(mut x: u32, mut y: u32, character: char, color: Rgba64) {
|
||||||
// let mode = *VGAE.lock();
|
// let mode = *VGAE.lock();
|
||||||
let mut mode = SCREEN_BUFFER.lock();
|
let mut mode = SCREEN_BUFFER.lock();
|
||||||
|
|
||||||
let font = FontRef::try_from_slice(include_bytes!(
|
let basic_multingual_plane = FontRef::try_from_slice(include_bytes!(
|
||||||
"../../ableos/assets/fonts/unifont-14.0.01.ttf"
|
"../../ableos/assets/fonts/unifont-14.0.01.ttf"
|
||||||
))
|
))
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
let font2 = FontRef::try_from_slice(include_bytes!(
|
let supplementary_multilingual_plane = FontRef::try_from_slice(include_bytes!(
|
||||||
"../../ableos/assets/fonts/unifont_upper-14.0.01.ttf"
|
"../../ableos/assets/fonts/unifont_upper-14.0.01.ttf"
|
||||||
))
|
))
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
let mut has_char = false;
|
// let mut has_char = false;
|
||||||
for x in font.codepoint_ids() {
|
// for x in font.codepoint_ids() {
|
||||||
if x.1 == character {
|
// if x.1 == character {
|
||||||
has_char = true;
|
// has_char = true;
|
||||||
break;
|
// break;
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
|
|
||||||
let used_font;
|
let is_in_basic_multilingual_plane = character as u32 <= 0xffff;
|
||||||
match has_char {
|
|
||||||
true => used_font = font,
|
|
||||||
false => used_font = font2,
|
|
||||||
}
|
|
||||||
|
|
||||||
let font_scale = 1.6;
|
let plane = match is_in_basic_multilingual_plane {
|
||||||
|
true => basic_multingual_plane,
|
||||||
|
false => supplementary_multilingual_plane,
|
||||||
|
};
|
||||||
|
|
||||||
match character {
|
match character {
|
||||||
'\n' => {}
|
'\n' => {}
|
||||||
_ => {
|
_ => {
|
||||||
let mut q_glyph: Glyph = used_font.glyph_id(character).with_scale_and_position(
|
let q_glyph: Glyph = plane.glyph_id(character).with_scale_and_position(
|
||||||
20.0 * font_scale,
|
20.0 * FONT_SCALE,
|
||||||
ab_glyph::point(10.0 * font_scale, 18.0 * font_scale),
|
ab_glyph::point(GLYPH_WIDTH * FONT_SCALE, GLYPH_HEIGHT * FONT_SCALE),
|
||||||
);
|
);
|
||||||
|
|
||||||
if let Some(q) = used_font.outline_glyph(q_glyph) {
|
// elf: I don't know if GLYPH_HEIGHT is in the right units here. I'm just guessing.
|
||||||
q.draw(|x, y, c| {
|
if x as usize > mode.size.x {
|
||||||
if c > 0.015 {
|
x = 0;
|
||||||
let corner = q.px_bounds().min;
|
y += (GLYPH_HEIGHT * FONT_SCALE) as u32;
|
||||||
mode.set_pixel(
|
}
|
||||||
x as usize + corner.x as usize,
|
|
||||||
y as usize + corner.y as usize,
|
if let Some(q) = plane.outline_glyph(q_glyph) {
|
||||||
color,
|
q.draw(|gx, gy, c| {
|
||||||
);
|
if c > 0.015 {
|
||||||
}
|
let corner = q.px_bounds().min;
|
||||||
});
|
mode.set_pixel(
|
||||||
}
|
gx as usize + corner.x as usize + x as usize,
|
||||||
}
|
gy as usize + corner.y as usize + y as usize,
|
||||||
}
|
color,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Converts a number to ... i forgor 💀
|
||||||
pub fn num_to_vga16(num: u8) -> Color16 {
|
pub fn num_to_vga16(num: u8) -> Color16 {
|
||||||
use Color16::*;
|
use Color16::*;
|
||||||
match num {
|
match num {
|
||||||
0 => Black,
|
0 => Black,
|
||||||
1 => Blue,
|
1 => Blue,
|
||||||
2 => Green,
|
2 => Green,
|
||||||
3 => Cyan,
|
3 => Cyan,
|
||||||
4 => Red,
|
4 => Red,
|
||||||
5 => Magenta,
|
5 => Magenta,
|
||||||
6 => Brown,
|
6 => Brown,
|
||||||
7 => LightGrey,
|
7 => LightGrey,
|
||||||
8 => DarkGrey,
|
8 => DarkGrey,
|
||||||
9 => LightBlue,
|
9 => LightBlue,
|
||||||
10 => LightGreen,
|
10 => LightGreen,
|
||||||
11 => LightCyan,
|
11 => LightCyan,
|
||||||
12 => LightRed,
|
12 => LightRed,
|
||||||
13 => Pink,
|
13 => Pink,
|
||||||
14 => Yellow,
|
14 => Yellow,
|
||||||
15 => White,
|
15 => White,
|
||||||
// NOTE: Leasve the in
|
// NOTE: Leasve the in
|
||||||
_ => Color16::Pink,
|
_ => Color16::Pink,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,46 +4,46 @@ use clap::Parser;
|
||||||
#[clap(version = clap::crate_version!(), author = clap::crate_authors!("\n"))]
|
#[clap(version = clap::crate_version!(), author = clap::crate_authors!("\n"))]
|
||||||
/// Hello Remember this is a feature
|
/// Hello Remember this is a feature
|
||||||
enum Command {
|
enum Command {
|
||||||
Run {
|
Run {
|
||||||
#[clap(long, short)]
|
#[clap(long, short)]
|
||||||
debug: bool,
|
debug: bool,
|
||||||
|
|
||||||
#[clap(long, short, arg_enum)]
|
#[clap(long, short, arg_enum)]
|
||||||
machine: Option<MachineType>,
|
machine: Option<MachineType>,
|
||||||
},
|
},
|
||||||
|
|
||||||
Doc {
|
Doc {
|
||||||
#[clap(long, short, arg_enum)]
|
#[clap(long, short, arg_enum)]
|
||||||
machine: Option<MachineType>,
|
machine: Option<MachineType>,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(clap::ArgEnum, Debug, Clone)]
|
#[derive(clap::ArgEnum, Debug, Clone)]
|
||||||
enum MachineType {
|
enum MachineType {
|
||||||
X86,
|
X86,
|
||||||
RISCV,
|
RISCV,
|
||||||
ARM,
|
ARM,
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() -> anyhow::Result<()> {
|
fn main() -> anyhow::Result<()> {
|
||||||
let args = Command::parse();
|
let args = Command::parse();
|
||||||
|
|
||||||
match args {
|
match args {
|
||||||
Command::Run { debug, machine } => {
|
Command::Run { debug, machine } => {
|
||||||
let _dir = xshell::pushd("./ableos");
|
let _dir = xshell::pushd("./ableos");
|
||||||
|
|
||||||
let _debug_log: &[&str] = match debug {
|
let _debug_log: &[&str] = match debug {
|
||||||
true => &["-D", "debug.log"],
|
true => &["-D", "debug.log"],
|
||||||
false => &[],
|
false => &[],
|
||||||
};
|
};
|
||||||
match machine.unwrap_or(MachineType::X86) {
|
match machine.unwrap_or(MachineType::X86) {
|
||||||
MachineType::X86 => {
|
MachineType::X86 => {
|
||||||
xshell::cmd!("cargo run --release").run()?;
|
xshell::cmd!("cargo run --release").run()?;
|
||||||
}
|
}
|
||||||
MachineType::ARM => {
|
MachineType::ARM => {
|
||||||
xshell::cmd!("cargo build --release --target=json_targets/aarch64-ableos.json")
|
xshell::cmd!("cargo build --release --target=json_targets/aarch64-ableos.json")
|
||||||
.run()?;
|
.run()?;
|
||||||
#[rustfmt::skip]
|
#[rustfmt::skip]
|
||||||
xshell::cmd!(
|
xshell::cmd!(
|
||||||
"qemu-system-aarch64
|
"qemu-system-aarch64
|
||||||
-machine virt
|
-machine virt
|
||||||
|
@ -53,11 +53,10 @@ fn main() -> anyhow::Result<()> {
|
||||||
-device virtio-keyboard
|
-device virtio-keyboard
|
||||||
"
|
"
|
||||||
).run()?;
|
).run()?;
|
||||||
}
|
}
|
||||||
MachineType::RISCV => {
|
MachineType::RISCV => {
|
||||||
xshell::cmd!("cargo build --release --target=riscv64gc-unknown-none-elf")
|
xshell::cmd!("cargo build --release --target=riscv64gc-unknown-none-elf").run()?;
|
||||||
.run()?;
|
#[rustfmt::skip]
|
||||||
#[rustfmt::skip]
|
|
||||||
xshell::cmd!(
|
xshell::cmd!(
|
||||||
"qemu-system-riscv64
|
"qemu-system-riscv64
|
||||||
-machine virt
|
-machine virt
|
||||||
|
@ -67,27 +66,26 @@ fn main() -> anyhow::Result<()> {
|
||||||
-bios src/arch/riscv/firmwear/opensbi-riscv64-generic-fw_jump.bin
|
-bios src/arch/riscv/firmwear/opensbi-riscv64-generic-fw_jump.bin
|
||||||
-kernel target/riscv64gc-unknown-none-elf/release/ableos"
|
-kernel target/riscv64gc-unknown-none-elf/release/ableos"
|
||||||
).run()?;
|
).run()?;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Command::Doc { machine } => {
|
Command::Doc { machine } => {
|
||||||
let _dir = xshell::pushd("./ableos");
|
let _dir = xshell::pushd("./ableos");
|
||||||
|
|
||||||
match machine.unwrap_or(MachineType::X86) {
|
match machine.unwrap_or(MachineType::X86) {
|
||||||
MachineType::X86 => {
|
MachineType::X86 => {
|
||||||
xshell::cmd!("cargo doc --open").run()?;
|
xshell::cmd!("cargo doc --open").run()?;
|
||||||
}
|
|
||||||
MachineType::ARM => {
|
|
||||||
xshell::cmd!("cargo doc --open --target=json_targets/aarch64-ableos.json")
|
|
||||||
.run()?;
|
|
||||||
}
|
|
||||||
MachineType::RISCV => {
|
|
||||||
xshell::cmd!("cargo doc --open --target=riscv64gc-unknown-none-elf").run()?;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
MachineType::ARM => {
|
||||||
}
|
xshell::cmd!("cargo doc --open --target=json_targets/aarch64-ableos.json").run()?;
|
||||||
|
}
|
||||||
|
MachineType::RISCV => {
|
||||||
|
xshell::cmd!("cargo doc --open --target=riscv64gc-unknown-none-elf").run()?;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,218 +1,162 @@
|
||||||
#![feature(exclusive_range_pattern)]
|
|
||||||
use log::*;
|
|
||||||
use rhai::INT;
|
|
||||||
use vga::colors::Color16;
|
use vga::colors::Color16;
|
||||||
pub type Rgba64 = u64;
|
pub type Rgba64 = u64;
|
||||||
|
|
||||||
pub fn get_r(rgba: Rgba64) -> u8 {
|
pub fn get_r(rgba: Rgba64) -> u8 {
|
||||||
let x: u64 = rgba;
|
(rgba & 0xff_00_00_00 >> 0o30) as u8
|
||||||
|
|
||||||
let y = x >> 24;
|
|
||||||
|
|
||||||
return (y & 0xff).try_into().unwrap();
|
|
||||||
}
|
}
|
||||||
pub fn get_g(rgba: Rgba64) -> u8 {
|
pub fn get_g(rgba: Rgba64) -> u8 {
|
||||||
let x: u64 = rgba;
|
(rgba & 0xff_00_00 >> 0o20) as u8
|
||||||
|
|
||||||
let y = x >> 16;
|
|
||||||
|
|
||||||
return (y & 0xff).try_into().unwrap();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_b(rgba: Rgba64) -> u8 {
|
pub fn get_b(rgba: Rgba64) -> u8 {
|
||||||
let x: u64 = rgba;
|
(rgba & 0xff_00 >> 0o10) as u8
|
||||||
|
|
||||||
let y = x >> (24 - 16);
|
|
||||||
|
|
||||||
return (y & 0xff).try_into().unwrap();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_a(rgba: Rgba64) -> u8 {
|
pub fn get_a(rgba: Rgba64) -> u8 {
|
||||||
let x = rgba;
|
(rgba & 0xff) as u8
|
||||||
|
|
||||||
let y = x >> (24 - 16 - 8);
|
|
||||||
|
|
||||||
return (y & 0xff).try_into().unwrap();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_r(rgba: Rgba64, r: u8) -> Rgba64 {
|
pub fn set_r(rgba: Rgba64, r: u8) -> Rgba64 {
|
||||||
let z = (r as Rgba64) << 24;
|
rgba & 0xffffffff_00_ff_ff_ff | (r as Rgba64) << 0o30
|
||||||
let y = rgba & 0xffffff;
|
|
||||||
return z | y;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_g(rgba: Rgba64, g: u8) -> Rgba64 {
|
pub fn set_g(rgba: Rgba64, g: u8) -> Rgba64 {
|
||||||
let z = (g as Rgba64) << 16;
|
rgba & 0xffffffff_ff_00_ff_ff | (g as Rgba64) << 0o20
|
||||||
let y = rgba & 0xffffff;
|
|
||||||
return z | y;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_b(rgba: Rgba64, b: u8) -> Rgba64 {
|
pub fn set_b(rgba: Rgba64, b: u8) -> Rgba64 {
|
||||||
let z = (b as Rgba64) << 26 - 16;
|
rgba & 0xffffffff_ff_ff_00_ff | (b as Rgba64) << 0o10
|
||||||
let y = rgba & 0xffffff;
|
|
||||||
return z | y;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_a(rgba: Rgba64, a: u8) -> Rgba64 {
|
pub fn set_a(rgba: Rgba64, a: u8) -> Rgba64 {
|
||||||
let z = (a as Rgba64) << 8;
|
rgba & 0xffffffff_ff_ff_ff_00 | (a as Rgba64)
|
||||||
let y = rgba & 0xffffff;
|
|
||||||
return z | y;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn rgba_div(a: Rgba64, b: Rgba64) -> Rgba64 {
|
pub fn rgba_div(a: Rgba64, b: Rgba64) -> Rgba64 {
|
||||||
let mut fin: Rgba64 = 0;
|
set_r(0, get_r(a) / get_r(b))
|
||||||
|
| set_g(0, get_g(a) / get_g(b))
|
||||||
// println!("{}", fin);
|
| set_g(0, get_b(a) / get_b(b))
|
||||||
fin |= set_r(fin, get_r(a) / get_r(b));
|
| set_g(0, get_a(a) / get_a(b))
|
||||||
// println!("{}", fin);
|
|
||||||
|
|
||||||
fin |= set_g(fin, get_g(a) / get_g(b));
|
|
||||||
/*
|
|
||||||
|
|
||||||
get_b(a) / get_b(b);
|
|
||||||
|
|
||||||
get_a(a) / get_a(b);
|
|
||||||
*/
|
|
||||||
|
|
||||||
return fin;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn new_rgba64(r: u8, g: u8, b: u8, a: u8) -> Rgba64 {
|
pub fn new_rgba64(r: u8, g: u8, b: u8, a: u8) -> Rgba64 {
|
||||||
let mut x = 0;
|
set_r(0, r) | set_g(0, g) | set_b(0, b) | set_a(0, a)
|
||||||
|
}
|
||||||
|
|
||||||
x |= set_r(x, r);
|
enum ChannelValue {
|
||||||
x |= set_g(x, g);
|
Dark,
|
||||||
x |= set_b(x, b);
|
Low,
|
||||||
x |= set_a(x, a);
|
Mid,
|
||||||
|
High,
|
||||||
|
}
|
||||||
|
|
||||||
x
|
impl From<u8> for ChannelValue {
|
||||||
|
fn from(b: u8) -> Self {
|
||||||
|
use ChannelValue::*;
|
||||||
|
match b {
|
||||||
|
0x00..=0x3f => Dark,
|
||||||
|
0x40..=0x7f => Low,
|
||||||
|
0x80..=0xbf => Mid,
|
||||||
|
0xc0..=0xff => High,
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn into_vga_16(rgba_64: Rgba64) -> Color16 {
|
pub fn into_vga_16(rgba_64: Rgba64) -> Color16 {
|
||||||
let mut fourbit: u8 = 0;
|
use ChannelValue::*;
|
||||||
fourbit |= match get_r(rgba_64) {
|
use Color16::*;
|
||||||
85..=170 => 0b0100,
|
match (
|
||||||
171..=255 => 0b1100,
|
get_r(rgba_64).into(),
|
||||||
_ => 0,
|
get_g(rgba_64).into(),
|
||||||
};
|
get_b(rgba_64).into(),
|
||||||
fourbit |= match get_g(rgba_64) {
|
) {
|
||||||
85..=170 => 0b0010,
|
(Dark, Dark, Dark) => Black,
|
||||||
171..=255 => 0b1010,
|
(Dark, Dark, Low) => Black,
|
||||||
_ => 0,
|
(Dark, Dark, Mid) => Blue,
|
||||||
};
|
(Dark, Dark, High) => Blue,
|
||||||
fourbit |= match get_b(rgba_64) {
|
(Dark, Low, Dark) => Black,
|
||||||
85..=170 => 0b0001,
|
(Dark, Low, Low) => Black,
|
||||||
171..=255 => 0b1001,
|
(Dark, Low, Mid) => Blue,
|
||||||
_ => 0,
|
(Dark, Low, High) => Blue,
|
||||||
};
|
(Dark, Mid, Dark) => Green,
|
||||||
|
(Dark, Mid, Low) => Green,
|
||||||
// trace!("{}", fourbit);
|
(Dark, Mid, Mid) => Cyan,
|
||||||
|
(Dark, Mid, High) => Cyan,
|
||||||
use Color16::*;
|
(Dark, High, Dark) => Green,
|
||||||
match fourbit {
|
(Dark, High, Low) => Green,
|
||||||
0 => Black,
|
(Dark, High, Mid) => Green,
|
||||||
1 => Blue,
|
(Dark, High, High) => Cyan,
|
||||||
2 => Green,
|
(Low, Dark, Dark) => Black,
|
||||||
3 => Cyan,
|
(Low, Dark, Low) => Black,
|
||||||
4 => Red,
|
(Low, Dark, Mid) => Blue,
|
||||||
5 => Magenta,
|
(Low, Dark, High) => Blue,
|
||||||
6 => Brown,
|
(Low, Low, Dark) => Black,
|
||||||
7 => LightGrey,
|
(Low, Low, Low) => DarkGrey,
|
||||||
8 => DarkGrey,
|
(Low, Low, Mid) => LightGrey,
|
||||||
9 => LightBlue,
|
(Low, Low, High) => Blue,
|
||||||
10 => LightGreen,
|
(Low, Mid, Dark) => DarkGrey,
|
||||||
11 => LightCyan,
|
(Low, Mid, Low) => LightGrey,
|
||||||
12 => LightRed,
|
(Low, Mid, Mid) => Cyan,
|
||||||
13 => Pink,
|
(Low, Mid, High) => Cyan,
|
||||||
14 => Yellow,
|
(Low, High, Dark) => Green,
|
||||||
15 => White,
|
(Low, High, Low) => Green,
|
||||||
_ => Green,
|
(Low, High, Mid) => Cyan,
|
||||||
}
|
(Low, High, High) => Cyan,
|
||||||
|
(Mid, Dark, Dark) => Red,
|
||||||
|
(Mid, Dark, Low) => Red,
|
||||||
|
(Mid, Dark, Mid) => Magenta,
|
||||||
|
(Mid, Dark, High) => Magenta,
|
||||||
|
(Mid, Low, Dark) => Brown,
|
||||||
|
(Mid, Low, Low) => Red,
|
||||||
|
(Mid, Low, Mid) => DarkGrey,
|
||||||
|
(Mid, Low, High) => LightBlue,
|
||||||
|
(Mid, Mid, Dark) => Brown,
|
||||||
|
(Mid, Mid, Low) => Brown,
|
||||||
|
(Mid, Mid, Mid) => LightGrey,
|
||||||
|
(Mid, Mid, High) => LightBlue,
|
||||||
|
(Mid, High, Dark) => Green,
|
||||||
|
(Mid, High, Low) => Green,
|
||||||
|
(Mid, High, Mid) => LightGreen,
|
||||||
|
(Mid, High, High) => LightCyan,
|
||||||
|
(High, Dark, Dark) => Red,
|
||||||
|
(High, Dark, _) => Magenta,
|
||||||
|
(High, Low, Dark) => Red,
|
||||||
|
(High, Low, Low) => LightRed,
|
||||||
|
(High, Low, Mid) => Pink,
|
||||||
|
(High, Low, High) => Magenta,
|
||||||
|
(High, Mid, Dark) => Yellow,
|
||||||
|
(High, Mid, Low) => Yellow,
|
||||||
|
(High, Mid, Mid) => LightRed,
|
||||||
|
(High, Mid, High) => Pink,
|
||||||
|
(High, High, Dark) => Yellow,
|
||||||
|
(High, High, Low) => White,
|
||||||
|
(High, High, Mid) => White,
|
||||||
|
(High, High, High) => White,
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn from_vga_16(color: Color16) -> Rgba64 {
|
pub fn from_vga_16(color: Color16) -> Rgba64 {
|
||||||
use Color16::*;
|
use Color16::*;
|
||||||
match color {
|
match color {
|
||||||
Black => new_rgba64(0, 0, 0, 0),
|
Black => new_rgba64(0, 0, 0, 0),
|
||||||
DarkGrey => new_rgba64(105, 105, 105, 0),
|
DarkGrey => new_rgba64(105, 105, 105, 0),
|
||||||
LightGrey => new_rgba64(211, 211, 211, 0),
|
LightGrey => new_rgba64(211, 211, 211, 0),
|
||||||
//
|
//
|
||||||
Blue => new_rgba64(0, 0, 255, 0),
|
Blue => new_rgba64(0, 0, 0xff, 0),
|
||||||
Green => new_rgba64(0, 255, 0, 0),
|
Green => new_rgba64(0, 0xff, 0, 0),
|
||||||
Red => new_rgba64(255, 0, 0, 0),
|
Red => new_rgba64(0xff, 0, 0, 0),
|
||||||
//
|
//
|
||||||
Yellow => new_rgba64(255, 255, 0, 0),
|
Yellow => new_rgba64(0xff, 0xff, 0, 0),
|
||||||
Cyan => new_rgba64(0, 255, 255, 0),
|
Cyan => new_rgba64(0, 0xff, 0xff, 0),
|
||||||
Magenta => new_rgba64(255, 0, 255, 0),
|
Magenta => new_rgba64(0xff, 0, 0xff, 0),
|
||||||
|
|
||||||
Brown => new_rgba64(165, 42, 42, 0),
|
Brown => new_rgba64(165, 42, 42, 0),
|
||||||
Pink => new_rgba64(255, 105, 180, 0),
|
Pink => new_rgba64(0xff, 105, 180, 0),
|
||||||
White => new_rgba64(255, 255, 255, 0),
|
White => new_rgba64(0xff, 0xff, 0xff, 0),
|
||||||
|
|
||||||
LightBlue => new_rgba64(173, 216, 230, 0),
|
LightBlue => new_rgba64(173, 216, 230, 0),
|
||||||
LightGreen => new_rgba64(144, 238, 144, 0),
|
LightGreen => new_rgba64(144, 238, 144, 0),
|
||||||
LightCyan => new_rgba64(88, 100, 100, 0),
|
LightCyan => new_rgba64(88, 100, 100, 0),
|
||||||
LightRed => new_rgba64(255, 204, 203, 0),
|
LightRed => new_rgba64(0xff, 204, 203, 0),
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
use libm::sqrt;
|
|
||||||
|
|
||||||
fn euclideand(c1: (u8, u8, u8), c2: (u8, u8, u8)) -> u8 {
|
|
||||||
let (r1, g1, b1) = c1;
|
|
||||||
let (r2, g2, b2) = c2;
|
|
||||||
let (rd, gd, bd) = (r2 - r1, g2 - g1, b2 - b1);
|
|
||||||
sqrt((rd * rd + gd * gd + bd * bd) as f64) as u8
|
|
||||||
}
|
|
||||||
pub fn get_color16(c: Rgba64) -> Color16 {
|
|
||||||
let r = get_r(c);
|
|
||||||
let g = get_g(c);
|
|
||||||
let b = get_b(c);
|
|
||||||
|
|
||||||
let c = (r, g, b);
|
|
||||||
let palette: [(u8, u8, u8); 16] = [
|
|
||||||
(0, 0, 0),
|
|
||||||
(105, 105, 105),
|
|
||||||
(211, 211, 211),
|
|
||||||
(0, 0, 255),
|
|
||||||
(0, 255, 0),
|
|
||||||
(255, 0, 0),
|
|
||||||
(255, 255, 0),
|
|
||||||
(0, 255, 255),
|
|
||||||
(255, 0, 255),
|
|
||||||
(165, 42, 42),
|
|
||||||
(255, 105, 180),
|
|
||||||
(255, 255, 255),
|
|
||||||
(173, 216, 230),
|
|
||||||
(144, 238, 144),
|
|
||||||
(88, 100, 100),
|
|
||||||
(255, 204, 203),
|
|
||||||
];
|
|
||||||
let mut minc = euclideand(c, palette[0]);
|
|
||||||
let mut retval = 0;
|
|
||||||
for i in 1..16 {
|
|
||||||
let eucd = euclideand(c, palette[i]);
|
|
||||||
if eucd < minc {
|
|
||||||
retval = i;
|
|
||||||
minc = eucd
|
|
||||||
}
|
|
||||||
}
|
|
||||||
use Color16::*;
|
|
||||||
match retval {
|
|
||||||
0 => Black,
|
|
||||||
1 => Blue,
|
|
||||||
2 => Green,
|
|
||||||
3 => Cyan,
|
|
||||||
4 => Red,
|
|
||||||
5 => Magenta,
|
|
||||||
6 => Brown,
|
|
||||||
7 => LightGrey,
|
|
||||||
8 => DarkGrey,
|
|
||||||
9 => LightBlue,
|
|
||||||
10 => LightGreen,
|
|
||||||
11 => LightCyan,
|
|
||||||
12 => LightRed,
|
|
||||||
13 => Pink,
|
|
||||||
14 => Yellow,
|
|
||||||
15 => White,
|
|
||||||
_ => Green,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue