fix(tahuantinsuyu): crash al abrir modal + simplificación de anillos
- Crash fix (panic en gpui entity_map.rs:138 / double_lease): `render_chart_form` hacía `cx.entity().read(cx)` mientras estaba dentro del `render()` del tree — la entity ya estaba leased como `&mut self` y un read concurrente disparaba el double_lease_panic. Se cambió la firma para recibir `picker_open` y `city_atlas` como parámetros desde `render_modal` (que sí tiene `&self`). - Simplificación de anillos: el carril de planetas se acerca (bodies 0.60·r / bodies_inner 0.57·r) — antes 0.05 de separación, ahora 0.03, se ve como "carril" en lugar de dos anillos sueltos. El stroke visible del círculo de aspectos se elimina — `radii.aspects` queda solo como punto de anclaje para las líneas. El `bodies_inner` cambia a stroke plano más sutil (no 3D) para no competir con `bodies`. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
@@ -1533,15 +1533,19 @@ impl Radii {
|
|||||||
houses_outer: r * 0.78,
|
houses_outer: r * 0.78,
|
||||||
houses_inner: r * 0.66,
|
houses_inner: r * 0.66,
|
||||||
midpoints: r * 0.62,
|
midpoints: r * 0.62,
|
||||||
bodies: r * 0.58,
|
bodies: r * 0.60,
|
||||||
bodies_inner: r * 0.53,
|
// bodies_inner cerca de bodies — los dos anillos juntos
|
||||||
// aspects pegado al cinturón de cuerpos pero adentro:
|
// forman un "carril" estrecho que delimita la franja de
|
||||||
// las líneas entran al "círculo de aspectos" justo bajo
|
// planetas, no dos líneas separadas que confunden.
|
||||||
// los glyphs en lugar de cruzar el centro.
|
bodies_inner: r * 0.57,
|
||||||
aspects: r * 0.49,
|
// aspects justo bajo el carril de cuerpos. Las líneas
|
||||||
progression: r * 0.43,
|
// de aspecto entran a este radio, pero el círculo en sí
|
||||||
solar_arc: r * 0.36,
|
// no se pinta — son las líneas las que importan, no
|
||||||
composite: r * 0.28,
|
// un anillo extra que sume ruido.
|
||||||
|
aspects: r * 0.54,
|
||||||
|
progression: r * 0.46,
|
||||||
|
solar_arc: r * 0.38,
|
||||||
|
composite: r * 0.30,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1690,20 +1694,22 @@ fn paint_wheel(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// 2.5. Cinturón de planetas + círculo de aspectos. El cinturón
|
// 2.5. Carril de planetas. `bodies` + `bodies_inner` muy juntos
|
||||||
// (bodies + bodies_inner) marca la franja donde viven los
|
// delimitan la franja estrecha donde viven los glyphs natales.
|
||||||
// glyphs natales. El círculo de aspectos queda apenas más
|
// El círculo de aspectos NO se pinta — `radii.aspects` solo
|
||||||
// adentro — las líneas de aspecto se anclan ahí, no en el
|
// existe como punto donde se anclan las líneas; un stroke ahí
|
||||||
// centro, así "conectan" cuerpos cercanos a su anillo en lugar
|
// sería un anillo extra que confunde sin aportar.
|
||||||
// de cruzar toda la rueda.
|
|
||||||
if show(LayerKind::Bodies) {
|
if show(LayerKind::Bodies) {
|
||||||
let belt_color = with_alpha(palette.dial_ring, 0.55);
|
let belt_color = with_alpha(palette.dial_ring, 0.55);
|
||||||
stroke_circle_3d(window, cx, cy, radii.bodies, 1.0, belt_color, theme);
|
stroke_circle_3d(window, cx, cy, radii.bodies, 0.9, belt_color, theme);
|
||||||
stroke_circle_3d(window, cx, cy, radii.bodies_inner, 0.9, belt_color, theme);
|
stroke_circle(
|
||||||
}
|
window,
|
||||||
if show(LayerKind::Aspects) {
|
cx,
|
||||||
let aspect_ring_color = with_alpha(palette.dial_ring, 0.45);
|
cy,
|
||||||
stroke_circle_3d(window, cx, cy, radii.aspects, 0.9, aspect_ring_color, theme);
|
radii.bodies_inner,
|
||||||
|
0.6,
|
||||||
|
with_alpha(palette.dial_ring, 0.35),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 3. Aspectos. Cada module_id usa su par de radios — natal-natal
|
// 3. Aspectos. Cada module_id usa su par de radios — natal-natal
|
||||||
|
|||||||
@@ -1370,12 +1370,24 @@ impl TahuantinsuyuTree {
|
|||||||
input.clone(),
|
input.clone(),
|
||||||
"Enter = crear — Escape = cancelar",
|
"Enter = crear — Escape = cancelar",
|
||||||
),
|
),
|
||||||
Modal::CreateChart { form, error, .. } => {
|
Modal::CreateChart { form, error, .. } => render_chart_form(
|
||||||
render_chart_form(theme, "Nueva carta natal", form, error.clone(), cx)
|
theme,
|
||||||
}
|
"Nueva carta natal",
|
||||||
Modal::EditChart { form, error, .. } => {
|
form,
|
||||||
render_chart_form(theme, "Editar carta natal", form, error.clone(), cx)
|
error.clone(),
|
||||||
}
|
self.city_picker_open,
|
||||||
|
&self.city_atlas,
|
||||||
|
cx,
|
||||||
|
),
|
||||||
|
Modal::EditChart { form, error, .. } => render_chart_form(
|
||||||
|
theme,
|
||||||
|
"Editar carta natal",
|
||||||
|
form,
|
||||||
|
error.clone(),
|
||||||
|
self.city_picker_open,
|
||||||
|
&self.city_atlas,
|
||||||
|
cx,
|
||||||
|
),
|
||||||
};
|
};
|
||||||
|
|
||||||
div()
|
div()
|
||||||
@@ -1454,6 +1466,12 @@ fn render_chart_form(
|
|||||||
title: &str,
|
title: &str,
|
||||||
form: &ChartForm,
|
form: &ChartForm,
|
||||||
error: Option<SharedString>,
|
error: Option<SharedString>,
|
||||||
|
// Datos del tree que el form necesita renderizar — recibidos por
|
||||||
|
// parámetro porque esta función se llama desde `render()` y la
|
||||||
|
// entity del tree ya está leased; un `cx.entity().read(cx)`
|
||||||
|
// adentro causa double_lease_panic en gpui.
|
||||||
|
picker_open: bool,
|
||||||
|
city_atlas: &[CityPreset],
|
||||||
cx: &mut Context<'_, TahuantinsuyuTree>,
|
cx: &mut Context<'_, TahuantinsuyuTree>,
|
||||||
) -> gpui::Div {
|
) -> gpui::Div {
|
||||||
let labeled = |label: &'static str, input: Entity<TextInput>| -> gpui::Div {
|
let labeled = |label: &'static str, input: Entity<TextInput>| -> gpui::Div {
|
||||||
@@ -1526,10 +1544,6 @@ fn render_chart_form(
|
|||||||
|
|
||||||
// Header del form: title + botón "Ciudad rápida" con dropdown
|
// Header del form: title + botón "Ciudad rápida" con dropdown
|
||||||
// que autocompleta place/lat/lon/tz al elegir un preset.
|
// que autocompleta place/lat/lon/tz al elegir un preset.
|
||||||
let (picker_open, atlas_snapshot) = {
|
|
||||||
let me = cx.entity().read(cx);
|
|
||||||
(me.city_picker_open, me.city_atlas.clone())
|
|
||||||
};
|
|
||||||
let city_btn = div()
|
let city_btn = div()
|
||||||
.id("tts-form-city-btn")
|
.id("tts-form-city-btn")
|
||||||
.px(px(10.0))
|
.px(px(10.0))
|
||||||
@@ -1580,7 +1594,7 @@ fn render_chart_form(
|
|||||||
.flex()
|
.flex()
|
||||||
.flex_col()
|
.flex_col()
|
||||||
.overflow_y_scroll();
|
.overflow_y_scroll();
|
||||||
for preset in atlas_snapshot.iter().cloned() {
|
for preset in city_atlas.iter().cloned() {
|
||||||
let row_id: SharedString =
|
let row_id: SharedString =
|
||||||
SharedString::from(format!("tts-city-{}", preset.name));
|
SharedString::from(format!("tts-city-{}", preset.name));
|
||||||
let label = preset.name.clone();
|
let label = preset.name.clone();
|
||||||
|
|||||||
Reference in New Issue
Block a user