diff --git a/src/ui/app.rs b/src/ui/app.rs index f31a50f..d229435 100644 --- a/src/ui/app.rs +++ b/src/ui/app.rs @@ -214,49 +214,9 @@ mod inspector { match *global_borrow.object_type() { ObjectType::Factory => { - if let (Some(name), Some(object_type)) = ( - global_borrow.name(), - global_borrow.props().get("factory.type.name"), - ) { - let object_type = match object_type.as_str() { - "PipeWire:Interface:Link" => ObjectType::Link, - "PipeWire:Interface:Port" => ObjectType::Port, - "PipeWire:Interface:Node" => ObjectType::Node, - "PipeWire:Interface:Client" => ObjectType::Client, - "PipeWire:Interface:Device" => ObjectType::Device, - "PipeWire:Interface:Registry" => ObjectType::Registry, - "PipeWire:Interface:Profiler" => ObjectType::Profiler, - "PipeWire:Interface:Metadata" => ObjectType::Metadata, - "PipeWire:Interface:Factory" => ObjectType::Factory, - "PipeWire:Interface:Module" => ObjectType::Module, - "PipeWire:Interface:Core" => ObjectType::Core, - "PipeWire:Interface:Endpoint" => ObjectType::Endpoint, - "PipeWire:Interface:EndpointLink" => ObjectType::EndpointLink, - "PipeWire:Interface:EndpointStream" => { - ObjectType::EndpointStream - } - "PipeWire:Interface:ClientSession" => ObjectType::ClientSession, - "PipeWire:Interface:ClientEndpoint" => { - ObjectType::ClientEndpoint - } - "PipeWire:Interface:ClientNode" => ObjectType::ClientNode, - _ => ObjectType::Other(object_type.clone()), - }; - self.object_creator.tool.add_factory( - id, - name, - object_type, - Rc::clone(global), - ); - } - } - ObjectType::Metadata => { - if let Some(name) = global_borrow.name() { - self.metadata_editor - .tool - .add_metadata(id, name, Rc::clone(global)) - } + self.object_creator.tool.add_factory(global); } + ObjectType::Metadata => self.metadata_editor.tool.add_metadata(global), _ => {} } @@ -335,19 +295,9 @@ mod inspector { let Some(metadata) = self.globals.get_global(id) else { return; }; - self.metadata_editor.tool.add_property( - id, - metadata - .borrow() - .name() - .cloned() - .unwrap_or_else(|| format!("Unnamed metadata {id}")), - subject, - key, - type_, - value, - Rc::clone(metadata), - ); + self.metadata_editor + .tool + .add_property(metadata, subject, key, type_, value); } None => { self.metadata_editor.tool.remove_property(id, &key); diff --git a/src/ui/global.rs b/src/ui/global.rs index 5f6aaef..7acf4d7 100644 --- a/src/ui/global.rs +++ b/src/ui/global.rs @@ -440,6 +440,10 @@ impl Global { }); } + pub const fn id(&self) -> u32 { + self.id + } + pub const fn name(&self) -> Option<&String> { self.name.as_ref() } diff --git a/src/ui/metadata_editor.rs b/src/ui/metadata_editor.rs index c9890e2..af5b0f1 100644 --- a/src/ui/metadata_editor.rs +++ b/src/ui/metadata_editor.rs @@ -54,7 +54,6 @@ impl Property { } struct Metadata { - name: String, properties: BTreeMap, user_properties: Vec<(String, Property)>, global: Rc>, @@ -74,30 +73,30 @@ impl Tool for MetadataEditor { } impl MetadataEditor { - pub fn add_metadata(&mut self, id: u32, name: &str, global: Rc>) { + pub fn add_metadata(&mut self, global: &Rc>) { + let id = global.borrow().id(); self.metadatas.entry(id).or_insert(Metadata { - name: name.to_owned(), properties: BTreeMap::new(), user_properties: Vec::new(), - global, + global: Rc::clone(global), }); } pub fn add_property( &mut self, - id: u32, - name: String, + global: &Rc>, subject: u32, key: String, type_: Option, value: String, - global: Rc>, ) { let prop = Property { subject, type_, value, }; + + let id = global.borrow().id(); match self.metadatas.entry(id) { Entry::Occupied(e) => { let properties = &mut e.into_mut().properties; @@ -105,10 +104,9 @@ impl MetadataEditor { } Entry::Vacant(e) => { let metadata = Metadata { - name, properties: BTreeMap::new(), user_properties: Vec::new(), - global, + global: Rc::clone(global), }; e.insert(metadata).properties.insert(key, prop); } @@ -134,7 +132,14 @@ impl MetadataEditor { fn show(&mut self, ui: &mut egui::Ui, sx: &backend::Sender) { for (id, metadata) in &mut self.metadatas { ui.group(|ui| { - ui.heading(&metadata.name); + ui.heading( + metadata + .global + .borrow() + .name() + .map(String::as_str) + .unwrap_or(""), + ); ui.horizontal(|ui| { global_info_button(ui, Some(&metadata.global), sx); @@ -145,7 +150,7 @@ impl MetadataEditor { .ok(); } }); - egui::Grid::new(&metadata.name) + egui::Grid::new(id) .num_columns(2) .striped(true) .show(ui, |ui| { diff --git a/src/ui/object_creator.rs b/src/ui/object_creator.rs index ce06b7f..0f7d115 100644 --- a/src/ui/object_creator.rs +++ b/src/ui/object_creator.rs @@ -29,11 +29,16 @@ use crate::{ }; struct Factory { - name: String, object_type: ObjectType, global: Rc>, } +impl Factory { + fn name(&self) -> String { + self.global.borrow().name().cloned().unwrap_or_default() + } +} + #[derive(Default)] pub struct ObjectCreator { factories: HashMap, @@ -51,21 +56,45 @@ impl Tool for ObjectCreator { } impl ObjectCreator { - pub fn add_factory( - &mut self, - id: u32, - name: &str, - object_type: ObjectType, - global: Rc>, - ) { - self.factories.insert( - id, - Factory { - name: name.to_owned(), - object_type, - global, - }, - ); + pub fn add_factory(&mut self, global: &Rc>) { + let (id, object_type) = { + let global = global.borrow(); + + let object_type = global.props().get("factory.type.name").map(|object_type| { + match object_type.as_str() { + "PipeWire:Interface:Link" => ObjectType::Link, + "PipeWire:Interface:Port" => ObjectType::Port, + "PipeWire:Interface:Node" => ObjectType::Node, + "PipeWire:Interface:Client" => ObjectType::Client, + "PipeWire:Interface:Device" => ObjectType::Device, + "PipeWire:Interface:Registry" => ObjectType::Registry, + "PipeWire:Interface:Profiler" => ObjectType::Profiler, + "PipeWire:Interface:Metadata" => ObjectType::Metadata, + "PipeWire:Interface:Factory" => ObjectType::Factory, + "PipeWire:Interface:Module" => ObjectType::Module, + "PipeWire:Interface:Core" => ObjectType::Core, + "PipeWire:Interface:Endpoint" => ObjectType::Endpoint, + "PipeWire:Interface:EndpointLink" => ObjectType::EndpointLink, + "PipeWire:Interface:EndpointStream" => ObjectType::EndpointStream, + "PipeWire:Interface:ClientSession" => ObjectType::ClientSession, + "PipeWire:Interface:ClientEndpoint" => ObjectType::ClientEndpoint, + "PipeWire:Interface:ClientNode" => ObjectType::ClientNode, + _ => ObjectType::Other(object_type.clone()), + } + }); + + (global.id(), object_type) + }; + + if let Some(object_type) = object_type { + self.factories.insert( + id, + Factory { + object_type, + global: Rc::clone(global), + }, + ); + } } pub fn remove_factory(&mut self, id: u32) { @@ -83,17 +112,20 @@ impl ObjectCreator { None }; + // Store the name here to avoid calling .borrow() every time it's needed + let factory_name = factory.map(Factory::name).unwrap_or_default(); + ui.horizontal(|ui| { let cb = egui::ComboBox::from_label("Factory"); - let cb = if let Some(factory) = factory { - cb.selected_text(&factory.name) + let cb = if factory.is_some() { + cb.selected_text(&factory_name) } else { cb.selected_text("No factory selected") }; cb.show_ui(ui, |ui| { for (id, factory) in &self.factories { - ui.selectable_value(&mut self.selected_factory, Some(*id), &factory.name); + ui.selectable_value(&mut self.selected_factory, Some(*id), factory.name()); } }); @@ -124,7 +156,7 @@ impl ObjectCreator { let factory = factory.unwrap(); sx.send(Request::CreateObject( factory.object_type.clone(), - factory.name.clone(), + factory_name, self.props.list().clone(), )) .ok();