···11use eframe::egui;
2233+use crate::types::{Filaments, Index};
44+35/// The `Filaments Visualizer`, which is an instance of `eframe`, which uses `egui`
44-#[derive(Default)]
56pub struct FilViz {
66- /// example for now
77- text: String,
77+ filaments: Filaments,
88}
991010impl FilViz {
1111 /// Create a new instance of the `FiLViz`
1212- const fn new(_cc: &eframe::CreationContext<'_>) -> Self {
1212+ fn new(_cc: &eframe::CreationContext<'_>, idx: &Index) -> Self {
1313 // Customize egui here with cc.egui_ctx.set_fonts and cc.egui_ctx.set_global_style.
1414 // Restore app state using cc.storage (requires the "persistence" feature).
1515 // Use the cc.gl (a glow::Context) to create graphics shaders and buffers that you can use
1616 // for e.g. egui::PaintCallback.
1717 Self {
1818- text: String::new(),
1818+ filaments: Filaments::from(idx),
1919 }
2020 }
21212222 /// Create and run the `FilViz`.
2323- pub fn run() -> color_eyre::Result<()> {
2323+ pub fn run(idx: &Index) -> color_eyre::Result<()> {
2424 let native_options = eframe::NativeOptions::default();
2525 eframe::run_native(
2626 "Filaments Visualizer",
2727 native_options,
2828- Box::new(|cc| Ok(Box::new(Self::new(cc)))),
2828+ Box::new(|cc| Ok(Box::new(Self::new(cc, idx)))),
2929 )?;
30303131 Ok(())
3232 }
3333}
34343535+type L = egui_graphs::LayoutForceDirected<egui_graphs::FruchtermanReingoldWithCenterGravity>;
3636+type S = egui_graphs::FruchtermanReingoldWithCenterGravityState;
3737+3538impl eframe::App for FilViz {
3639 fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
3740 egui::CentralPanel::default().show_inside(ui, |ui| {
3838- ui.heading("Hello World!");
3939- ui.text_edit_singleline(&mut self.text);
4141+ let g = &mut self.filaments.graph;
4242+4343+ let mut view = egui_graphs::GraphView::<_, _, _, _, _, _, S, L>::new(g);
4444+4545+ ui.add(&mut view);
40464147 // credits!
4248 ui.with_layout(egui::Layout::bottom_up(egui::Align::LEFT), |ui| {
+3-1
src/main.rs
···5252 let tui_handle = std::thread::spawn({
5353 // arc stuff
5454 let tui_rt = rt.clone();
5555+ let kh = kh.clone();
55565657 // closure to run the tui
5758 move || -> color_eyre::Result<()> {
···6970 if args.visualizer {
7071 // enter the guard so egui_async works properly
7172 let _rt_guard = rt.enter();
7272- FilViz::run()?;
7373+ let index = rt.block_on(async { kh.read().await.index.clone() });
7474+ FilViz::run(&index)?;
7375 }
74767577 // join on the tui
+33-12
src/types/filaments.rs
···11#![expect(dead_code)]
22use std::{cmp::max, collections::HashMap};
3344+use eframe::emath;
45use egui_graphs::{
56 Graph,
67 petgraph::{Directed, graph::NodeIndex, prelude::StableGraph},
···1617const GRAPH_MIN_EDGES: usize = GRAPH_MIN_NODES * 3;
17181819pub struct Filaments {
1919- graph: ZkGraph,
2020+ pub graph: ZkGraph,
2021 /// simple conversions
2122 zid_to_gid: HashMap<ZettelId, NodeIndex>,
2223}
23242424-// pub type FilamentsHandle = Arc<RwLock>
2525-//
2626-2727-// impl Filaments {
2828-// pub fn construct() -> Result<Self> {}
2929-// }
3030-3125impl From<&Index> for Filaments {
3226 fn from(value: &Index) -> Self {
3327 let number_of_zettels = value.zods().len();
34283535- let mut _graph: ZkGraph = ZkGraph::from(&StableGraph::with_capacity(
2929+ let mut zid_to_gid = HashMap::new();
3030+3131+ let mut graph: ZkGraph = ZkGraph::from(&StableGraph::with_capacity(
3632 max(number_of_zettels * 2, GRAPH_MIN_EDGES),
3733 max(number_of_zettels * 3, GRAPH_MIN_EDGES),
3834 ));
39354040- #[expect(clippy::for_kv_map)]
4141- for (_id, _zod) in value.zods() {}
3636+ for (zid, zod) in value.zods() {
3737+ let node_idx = graph.add_node_custom(zid.clone(), |node| {
3838+ node.set_label(zod.fm.title.clone());
3939+ let disp = node.display_mut();
4040+ disp.radius = 100.0;
4141+4242+ // randomize position
4343+ let x = rand::random_range(0.0..=100.0);
4444+ let y = rand::random_range(0.0..=100.0);
4545+ node.set_location(emath::Pos2 { x, y });
4646+ });
4747+4848+ let _ = zid_to_gid.insert(zid.clone(), node_idx);
4949+ }
42504343- todo!()
5151+ for (_, links) in value.outgoing_links.clone() {
5252+ for link in links {
5353+ let start = zid_to_gid
5454+ .get(&link.source)
5555+ .expect("Invariant broken, must exist in here if its in the index");
5656+ let end = zid_to_gid
5757+ .get(&link.dest)
5858+ .expect("Invariant broken, must exist in here if its in the index");
5959+6060+ let _ = graph.add_edge(*start, *end, link);
6161+ }
6262+ }
6363+6464+ Self { graph, zid_to_gid }
4465 }
4566}
-1
src/types/mod.rs
···2222pub use link::Link;
23232424mod filaments;
2525-#[expect(unused_imports)]
2625pub use filaments::Filaments;
27262827mod index;