mirror of
https://github.com/emilk/egui.git
synced 2026-09-01 22:30:03 -04:00
Color emojis 🦀
This commit is contained in:
@@ -4,7 +4,7 @@ use std::sync::Arc;
|
|||||||
use emath::{GuiRounding as _, Vec2, vec2};
|
use emath::{GuiRounding as _, Vec2, vec2};
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
TextureAtlas,
|
ColorImage, TextureAtlas,
|
||||||
mutex::{Mutex, RwLock},
|
mutex::{Mutex, RwLock},
|
||||||
text::FontTweak,
|
text::FontTweak,
|
||||||
};
|
};
|
||||||
@@ -261,6 +261,49 @@ impl FontImpl {
|
|||||||
self.ascent
|
self.ascent
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn allocate_custom_glyph(&self, c: char, image: ColorImage) -> GlyphInfo {
|
||||||
|
let glyph_pos = {
|
||||||
|
let atlas = &mut self.atlas.lock();
|
||||||
|
let (glyph_pos, atlas_image) = atlas.allocate((image.width(), image.height()));
|
||||||
|
|
||||||
|
for x in 0..image.width() {
|
||||||
|
for y in 0..image.height() {
|
||||||
|
let px = glyph_pos.0 + x;
|
||||||
|
let py = glyph_pos.1 + y;
|
||||||
|
atlas_image[(px, py)] = image[(x, y)];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
glyph_pos
|
||||||
|
};
|
||||||
|
|
||||||
|
let glyph_width = image.width();
|
||||||
|
let glyph_height = image.height();
|
||||||
|
|
||||||
|
let offset = vec2(0.0, -self.height_in_points / 1.3);
|
||||||
|
|
||||||
|
let height = self.height_in_points;
|
||||||
|
let width = height * (glyph_width as f32 / glyph_height as f32);
|
||||||
|
|
||||||
|
let uv_rect = UvRect {
|
||||||
|
offset,
|
||||||
|
size: vec2(width, height),
|
||||||
|
min: [glyph_pos.0 as u16, glyph_pos.1 as u16],
|
||||||
|
max: [
|
||||||
|
(glyph_pos.0 + glyph_width) as u16,
|
||||||
|
(glyph_pos.1 + glyph_height) as u16,
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
|
let advance_width = width;
|
||||||
|
|
||||||
|
GlyphInfo {
|
||||||
|
id: ab_glyph::GlyphId(0),
|
||||||
|
advance_width: advance_width as f32,
|
||||||
|
uv_rect,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn allocate_glyph(&self, glyph_id: ab_glyph::GlyphId) -> GlyphInfo {
|
fn allocate_glyph(&self, glyph_id: ab_glyph::GlyphId) -> GlyphInfo {
|
||||||
assert!(glyph_id.0 != 0, "Can't allocate glyph for id 0");
|
assert!(glyph_id.0 != 0, "Can't allocate glyph for id 0");
|
||||||
use ab_glyph::{Font as _, ScaleFont as _};
|
use ab_glyph::{Font as _, ScaleFont as _};
|
||||||
@@ -386,6 +429,16 @@ impl Font {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn allocate_custom_glyph(&mut self, c: char, image: ColorImage) -> GlyphInfo {
|
||||||
|
if let Some(font_impl) = self.fonts.first() {
|
||||||
|
let glyph_info = font_impl.allocate_custom_glyph(c, image);
|
||||||
|
self.glyph_info_cache.insert(c, (0, glyph_info));
|
||||||
|
glyph_info
|
||||||
|
} else {
|
||||||
|
GlyphInfo::default()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub fn preload_common_characters(&mut self) {
|
pub fn preload_common_characters(&mut self) {
|
||||||
// Preload the printable ASCII characters [32, 126] (which excludes control codes):
|
// Preload the printable ASCII characters [32, 126] (which excludes control codes):
|
||||||
const FIRST_ASCII: usize = 32; // 32 == space
|
const FIRST_ASCII: usize = 32; // 32 == space
|
||||||
|
|||||||
@@ -2,6 +2,10 @@
|
|||||||
#![allow(rustdoc::missing_crate_level_docs)] // it's an example
|
#![allow(rustdoc::missing_crate_level_docs)] // it's an example
|
||||||
|
|
||||||
use eframe::egui;
|
use eframe::egui;
|
||||||
|
use eframe::egui::{
|
||||||
|
Color32, ColorImage, FontFamily, FontId, FontSelection, RichText, TextEdit,
|
||||||
|
global_theme_preference_switch, include_image,
|
||||||
|
};
|
||||||
|
|
||||||
fn main() -> eframe::Result {
|
fn main() -> eframe::Result {
|
||||||
env_logger::init(); // Log to stderr (if you run with `RUST_LOG=debug`).
|
env_logger::init(); // Log to stderr (if you run with `RUST_LOG=debug`).
|
||||||
@@ -26,10 +30,14 @@ struct MyApp {
|
|||||||
age: u32,
|
age: u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn font_id() -> FontId {
|
||||||
|
FontId::new(30.0, FontFamily::Proportional)
|
||||||
|
}
|
||||||
|
|
||||||
impl Default for MyApp {
|
impl Default for MyApp {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self {
|
Self {
|
||||||
name: "Arthur".to_owned(),
|
name: "Ferris :crab:".to_owned(),
|
||||||
age: 42,
|
age: 42,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -38,21 +46,28 @@ impl Default for MyApp {
|
|||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show(ctx, |ui| {
|
||||||
ui.heading("My egui Application");
|
global_theme_preference_switch(ui);
|
||||||
ui.horizontal(|ui| {
|
|
||||||
let name_label = ui.label("Your name: ");
|
|
||||||
ui.text_edit_singleline(&mut self.name)
|
|
||||||
.labelled_by(name_label.id);
|
|
||||||
});
|
|
||||||
ui.add(egui::Slider::new(&mut self.age, 0..=120).text("age"));
|
|
||||||
if ui.button("Increment").clicked() {
|
|
||||||
self.age += 1;
|
|
||||||
}
|
|
||||||
ui.label(format!("Hello '{}', age {}", self.name, self.age));
|
|
||||||
|
|
||||||
ui.image(egui::include_image!(
|
ctx.fonts(|f| {
|
||||||
"../../../crates/egui/assets/ferris.png"
|
let mut fonts = f.lock();
|
||||||
));
|
let font = fonts.fonts.font(&font_id());
|
||||||
|
if !font.has_glyph('🦀') {
|
||||||
|
let image = include_bytes!("../../../crates/egui/assets/ferris.png");
|
||||||
|
|
||||||
|
let image = egui_extras::image::load_image_bytes(image).unwrap();
|
||||||
|
|
||||||
|
font.allocate_custom_glyph('🦀', image);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
TextEdit::singleline(&mut self.name)
|
||||||
|
.font(FontSelection::FontId(font_id()))
|
||||||
|
.text_color(Color32::WHITE)
|
||||||
|
.show(ui);
|
||||||
|
|
||||||
|
self.name = self.name.replace(":crab:", "🦀");
|
||||||
|
|
||||||
|
ui.label(RichText::new(&self.name).font(font_id()).strong());
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user