refresh: stack al día (vello 0.7 / wgpu 27 / parley 0.6) + motor 3D voxel

Re-sincroniza las fuentes desde el monorepo (estaba en vello 0.5/wgpu 24 y con la
estructura vieja de eventloop) y suma el 3D:

- bump del workspace a vello 0.7 / wgpu 27 / parley 0.6, + accesskit 0.24 /
  accesskit_winit 0.33 / vello_hybrid 0.0.9.
- nuevos crates: llimphi-3d (voxels ray-march + mallas en un depth compartido,
  montable dentro de un View 2D vía set_viewport+scissor) y llimphi-voxel
  (world-gen, personajes, director de escenas) + shared/foreign-vox (puente .vox).
- README: sección "Not just 2D — a 3D voxel engine" + GIF (docs/llimphi_voxel.gif).
- excluido modules/allichay (arrastra deps fuera del alcance del front-door).
- cargo check --workspace: verde.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Sergio
2026-06-18 14:40:00 +00:00
parent e74800d9da
commit ccab39f140
202 changed files with 44034 additions and 1811 deletions
+41
View File
@@ -41,6 +41,8 @@ pub struct TimelinePalette {
pub fill: Color,
/// Color del playhead (la barrita vertical en la posición actual).
pub knob: Color,
/// Color de las marcas (bookmarks) pintadas sobre la barra.
pub mark: Color,
/// Alto total del widget en pixels.
pub height: f32,
/// Radio de las esquinas del track.
@@ -60,6 +62,9 @@ impl TimelinePalette {
track: t.bg_button,
fill: t.accent,
knob: t.fg_text,
// Ámbar cálido para que las marcas resalten tanto sobre la pista
// de fondo como sobre el tramo recorrido (accent).
mark: Color::from_rgba8(255, 196, 84, 255),
height: 14.0,
radius: 7.0,
}
@@ -74,6 +79,24 @@ impl TimelinePalette {
/// para ignorar el click). El widget es stateless: redibujá pasando un
/// `progress` nuevo en cada frame y el playhead avanza solo.
pub fn timeline_view<Msg, F>(progress: f32, palette: &TimelinePalette, on_seek: F) -> View<Msg>
where
Msg: 'static,
F: Fn(f32) -> Option<Msg> + Send + Sync + 'static,
{
timeline_view_marked(progress, &[], palette, on_seek)
}
/// Igual que [`timeline_view`] pero pinta además unas **marcas** (bookmarks)
/// en las fracciones `marks` (`0.0..=1.0`): finas barras verticales con el
/// color `palette.mark`, bajo el playhead. Las fracciones fuera de rango se
/// ignoran. El resto del comportamiento (recorrido, playhead, click-to-seek)
/// es idéntico — `timeline_view` es este con `marks` vacío.
pub fn timeline_view_marked<Msg, F>(
progress: f32,
marks: &[f32],
palette: &TimelinePalette,
on_seek: F,
) -> View<Msg>
where
Msg: 'static,
F: Fn(f32) -> Option<Msg> + Send + Sync + 'static,
@@ -81,6 +104,12 @@ where
let p = progress.clamp(0.0, 1.0);
let fill_color = palette.fill;
let knob_color = palette.knob;
let mark_color = palette.mark;
let marks: Vec<f32> = marks
.iter()
.copied()
.filter(|f| f.is_finite() && (0.0..=1.0).contains(f))
.collect();
View::new(Style {
size: Size {
width: percent(1.0_f32),
@@ -105,6 +134,18 @@ where
let fill = Rect::new(x0 as f64, y0 as f64, (x0 + fw) as f64, (y0 + h) as f64);
scene.fill(Fill::NonZero, Affine::IDENTITY, fill_color, None, &fill);
}
// Marcas — finas barras verticales en cada fracción (bajo el playhead).
let mw: f32 = 2.0;
for f in &marks {
let mx = x0 + w * f;
let mark = Rect::new(
(mx - mw * 0.5) as f64,
y0 as f64,
(mx + mw * 0.5) as f64,
(y0 + h) as f64,
);
scene.fill(Fill::NonZero, Affine::IDENTITY, mark_color, None, &mark);
}
// Playhead — fina barra vertical en la posición actual.
let kx = x0 + fw;
let kw: f32 = 3.0;