Issue 0008:
- types.yaml: stash ParsedTypes en g_app.parsed_types tras parsear (lo
consume el Inspector para resolver schemas por type_ref).
- load_input: tras load, llama views_inspector_clear_draft + _refresh_caches.
- switch_to_project: limpia draft y parsed_types antes de cargar nuevo.
- render(): seleccion → load_draft (si single sel y no dirty), Save →
entity_update + reload_graph + relocaliza node_idx por sql_id +
re-load draft + reselecciona en viewport, Discard → re-load draft.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- examples/types.yaml: principal_field + fields para Person, Email,
Domain, Phone, Org, IBAN, Account, Document, Address, Url, Table.
44 fields totales. Documentacion del formato en cabecera.
- project_manager.cpp: seed con fields para los tipos basicos (fallback
cuando no se encuentra examples/types.yaml).
- main.cpp:
- Log de carga incluye conteo de schemas y total de fields.
- --test-types-yaml <path>: smoke test que carga, serializa a temp y
recarga. Compara entidades/relaciones/fields field-a-field. Salida
PASS/FAIL con exit code 0/1. Permite verificar round-trip sin
framework de tests.
Verificado: examples/types.yaml round-trip estable (11 entities, 44
fields, 6 relations).
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- types_registry.cpp::apply_types_yaml: tras aplicar el yaml, sobreescribe
shape de cada tipo: 'Table' → SHAPE_SQUARE, todo lo demas → SHAPE_CIRCLE.
Convencion fija — ediciones futuras del Type Editor (issue 0007) o del
yaml no rompen la regla.
- examples/types.yaml + project_manager.cpp seed: quitar campo `shape`,
añadir tipo Table (cuadrado) y relacion CONTAINS_ROW (preview de 0010).
- main.cpp run_force_step: damping=0.7, max_velocity=8 explicitos para
evitar que el grafo "explote" al cargar grafos pequenos.
- AppState repulsion: 1500 → 800 (lo mismo, aplicado al force layout).
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
main.cpp:
- Forward decl + switch_to_project: cierra layout_store, libera grafo,
aplica nuevos paths, vuelve a cargar.
- apply_project_paths: deriva operations.db/types.yaml/graph_explorer.db
del slug y los expone a g_app.active_project.
- main: arg --project <slug>; modo legacy si --input/positional dado;
modo proyecto si no — migra layout legacy, decide target via
arg/last_active/'default', crea si no existe, abre BDs y carga.
- render(): handler want_switch_project + monta views_new_project_modal.
views.h: AppState gana active_project, want_switch_project,
switch_project_target, show_new_project_modal, new_project_buf,
new_project_error, project_list_cache, project_recent_cache.
views.cpp:
- Toolbar: boton 'Project: <slug>' con popup (New/Recent/Open/Reveal).
Refresca caches al abrir el menu.
- views_new_project_modal: input slug + validacion + creacion + switch.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Bug fixes
- ImGui ID conflict en menu Change type: dedup tipos del grafo +
defaults; PushID/PopID por entrada.
- Dockspace ya no tapa la toolbar: se posiciona 44 px por debajo, asi
las ventanas dockeadas al borde superior quedan bajo la barra de
filtros, no detras.
- Hover radius proporcional al tamaño visual del nodo: query espacial
amplio (24/zoom) + filtro fino por (radio_visual + 2 px) / zoom. El
tooltip solo se dispara si el raton esta efectivamente sobre el nodo.
Layout
- Default layout = grid (en vez de force) para que los grafos cargados
se distribuyan ordenadamente al abrir.
- Boton "Reset layout" en la toolbar: limpia NF_PINNED en todos los
nodos, resetea velocidades y reaplica el layout activo.
- Nodos recien creados (add_node, duplicate) caen en un anillo poisson
alrededor del centro de la vista, no en el origen. Posicion
determinista por user_data para que el mismo nodo no salte entre
reloads.
Notes (markdown)
- Panel "Note" (dockeable) abierto con doble click sobre un nodo.
- entity_get_notes / entity_set_notes en entity_ops sobre la columna
`notes` de operations.db (ya existente en el schema).
- Ctrl+S guarda. Cabecera muestra entity, type, id.
- Dockspace host (PassthruCentralNode) bajo la toolbar para que las
ventanas Viewport/Legend/Inspector/Stats puedan dockearse dentro de la
app principal.
- Toolbar: input "Add node" con auto-deteccion de tipo (text/email/
ip_address/url/domain/phone). Insert en operations.db + reload.
- Context menu (right-click sobre nodo): Change type, Duplicate, Delete,
submenu "Run enricher" (placeholder hasta issues 0001-0003).
- Inspector: vecinos ahora muestran etiqueta de relacion ("-> employs",
"<- owns") usando rel_types[].name como label de arista.
- Default relation label k_default_relation_name="RELATED_TO" para
relaciones creadas sin nombre semantico explicito.
- Indice EntityIndex (FNV1a hash -> sql id) reconstruido tras cada load
para resolver mutaciones desde el grafo en memoria.
Issues planteadas para iteraciones siguientes:
- 0001: chat con Claude sobre el grafo (HTTP + tool-use)
- 0002: enricher GLiNER+GLiREL desde nodo texto
- 0003: enricher web (fetch URL/dominio + extract text)
- 0004: vista tabla por tipo de entidad