diff --git a/Cargo.lock b/Cargo.lock index 6167fcaf8..92fa74b54 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -243,6 +243,20 @@ name = "bytemuck" version = "1.7.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "72957246c41db82b8ef88a5486143830adeb8227ef9837740bdec67724cf2c5b" +dependencies = [ + "bytemuck_derive", +] + +[[package]] +name = "bytemuck_derive" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e215f8c2f9f79cb53c8335e687ffd07d5bfcb6fe5fc80723762d0be46e7cc54" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] [[package]] name = "byteorder" @@ -928,6 +942,7 @@ checksum = "e78d4f1cc4ae33bbfc157ed5d5a5ef3bc29227303d595861deb238fcec4e9457" name = "emath" version = "0.14.0" dependencies = [ + "bytemuck", "mint", "serde", ] @@ -973,6 +988,7 @@ dependencies = [ "ab_glyph", "ahash", "atomic_refcell", + "bytemuck", "cint", "emath", "nohash-hasher", diff --git a/egui-winit/Cargo.toml b/egui-winit/Cargo.toml index eaf2b5823..dd1910f12 100644 --- a/egui-winit/Cargo.toml +++ b/egui-winit/Cargo.toml @@ -46,3 +46,6 @@ links = ["webbrowser"] screen_reader = ["tts"] serialize = ["egui/serialize", "serde"] + +# implement bytemuck on most types. +convert_bytemuck = ["egui/convert_bytemuck"] diff --git a/egui/Cargo.toml b/egui/Cargo.toml index 24f0811dd..9883931ca 100644 --- a/egui/Cargo.toml +++ b/egui/Cargo.toml @@ -53,6 +53,9 @@ persistence = ["serde", "epaint/serialize", "ron"] # implement serde on most types. serialize = ["serde", "epaint/serialize"] +# implement bytemuck on most types. +convert_bytemuck = ["epaint/convert_bytemuck"] + # multi_threaded is only needed if you plan to use the same egui::Context # from multiple threads. It comes with a minor performance impact. single_threaded = ["epaint/single_threaded"] diff --git a/emath/Cargo.toml b/emath/Cargo.toml index 77ad3391e..7cfe6c754 100644 --- a/emath/Cargo.toml +++ b/emath/Cargo.toml @@ -26,6 +26,7 @@ all-features = true # Add compatability with https://github.com/kvark/mint mint = { version = "0.5.6", optional = true } serde = { version = "1", features = ["derive"], optional = true } +bytemuck = { version = "1.7.2", features = ["derive"], optional = true } [features] default = [] diff --git a/emath/src/pos2.rs b/emath/src/pos2.rs index f30d3f4ed..460a40b00 100644 --- a/emath/src/pos2.rs +++ b/emath/src/pos2.rs @@ -8,8 +8,10 @@ use crate::*; /// /// Mathematically this is known as a "point", but the term position was chosen so not to /// conflict with the unit (one point = X physical pixels). +#[repr(C)] #[derive(Clone, Copy, Default, PartialEq)] #[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] +#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))] pub struct Pos2 { pub x: f32, pub y: f32, diff --git a/emath/src/rect.rs b/emath/src/rect.rs index 5cf7520c0..aec425021 100644 --- a/emath/src/rect.rs +++ b/emath/src/rect.rs @@ -6,8 +6,10 @@ use crate::*; /// A rectangular region of space. /// /// Normally given in points, e.g. logical pixels. +#[repr(C)] #[derive(Clone, Copy, Eq, PartialEq)] #[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] +#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))] pub struct Rect { pub min: Pos2, pub max: Pos2, diff --git a/emath/src/rect_transform.rs b/emath/src/rect_transform.rs index 28292def7..6b5c9d092 100644 --- a/emath/src/rect_transform.rs +++ b/emath/src/rect_transform.rs @@ -3,7 +3,10 @@ use crate::*; /// Linearly transforms positions from one [`Rect`] to another. /// /// `RectTransform` stores the rectangles, and therefore supports clamping and culling. +#[repr(C)] #[derive(Clone, Copy, Debug, PartialEq)] +#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] +#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))] pub struct RectTransform { from: Rect, to: Rect, diff --git a/emath/src/rot2.rs b/emath/src/rot2.rs index 5da3ce9c0..9cdcd145f 100644 --- a/emath/src/rot2.rs +++ b/emath/src/rot2.rs @@ -13,7 +13,10 @@ use super::Vec2; // /// Normally a `Rot2` is normalized (unit-length). /// If not, it will also scale vectors. +#[repr(C)] #[derive(Clone, Copy, PartialEq)] +#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] +#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))] pub struct Rot2 { /// angle.sin() s: f32, diff --git a/emath/src/vec2.rs b/emath/src/vec2.rs index 066eb8581..2a8595bc5 100644 --- a/emath/src/vec2.rs +++ b/emath/src/vec2.rs @@ -6,8 +6,10 @@ use std::ops::{Add, AddAssign, Div, Mul, MulAssign, Neg, Sub, SubAssign}; /// emath represents positions using [`crate::Pos2`]. /// /// Normally the units are points (logical pixels). +#[repr(C)] #[derive(Clone, Copy, Default, PartialEq)] #[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] +#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))] pub struct Vec2 { pub x: f32, pub y: f32, diff --git a/epaint/Cargo.toml b/epaint/Cargo.toml index bf0268545..7b0a4bb33 100644 --- a/epaint/Cargo.toml +++ b/epaint/Cargo.toml @@ -34,6 +34,7 @@ cint = { version = "^0.2.2", optional = true } nohash-hasher = "0.2" parking_lot = { version = "0.11", optional = true } # Using parking_lot over std::sync::Mutex gives 50% speedups in some real-world scenarios. serde = { version = "1", features = ["derive"], optional = true } +bytemuck = { version = "1.7.2", features = ["derive"], optional = true } [features] default = ["default_fonts", "multi_threaded"] @@ -53,6 +54,9 @@ mint = ["emath/mint"] # implement serde on most types. serialize = ["serde", "emath/serde"] +# implement bytemuck on most types. +convert_bytemuck = ["bytemuck", "emath/bytemuck"] + single_threaded = ["atomic_refcell"] # Only needed if you plan to use the same fonts from multiple threads. diff --git a/epaint/src/color.rs b/epaint/src/color.rs index df840eea1..47374ca96 100644 --- a/epaint/src/color.rs +++ b/epaint/src/color.rs @@ -13,8 +13,10 @@ /// /// Internally this uses 0-255 gamma space `sRGBA` color with premultiplied alpha. /// Alpha channel is in linear space. +#[repr(C)] #[derive(Clone, Copy, Debug, Default, Eq, Hash, PartialEq)] #[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] +#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))] pub struct Color32(pub(crate) [u8; 4]); impl std::ops::Index for Color32 { diff --git a/epaint/src/mesh.rs b/epaint/src/mesh.rs index bb947e8c9..8218a9cef 100644 --- a/epaint/src/mesh.rs +++ b/epaint/src/mesh.rs @@ -7,6 +7,7 @@ use emath::*; #[repr(C)] #[derive(Clone, Copy, Debug, Default, PartialEq)] #[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] +#[cfg_attr(feature = "bytemuck", derive(bytemuck::Pod, bytemuck::Zeroable))] pub struct Vertex { /// Logical pixel coordinates (points). /// (0,0) is the top left corner of the screen.