ability to search by property name in inspector

This commit is contained in:
Dmitry Stepanov
2026-09-05 22:49:48 +03:00
parent f29280ef94
commit 39c743e915
4 changed files with 89 additions and 80 deletions
+48 -41
View File
@@ -63,6 +63,7 @@ use crate::{
Editor, Message, WidgetMessage, WrapMode,
};
use fyrox::gui::inspector::InspectorEnvironmentContainer;
use fyrox::gui::searchbar::{SearchBar, SearchBarBuilder, SearchBarMessage};
use std::{any::Any, sync::mpsc::Sender, sync::Arc};
pub mod editors;
@@ -123,6 +124,7 @@ pub struct InspectorPlugin {
pub inspector: Handle<fyrox::gui::inspector::Inspector>,
pub head: Handle<StackPanel>,
pub footer: Handle<UiNode>,
search_bar: Handle<SearchBar>,
warning_text: Handle<Text>,
type_name_text: Handle<Text>,
docs_button: Handle<Button>,
@@ -219,7 +221,7 @@ impl InspectorPlugin {
Only common properties will be editable!";
let head = StackPanelBuilder::new(WidgetBuilder::new()).build(ctx);
let footer = BorderBuilder::new(WidgetBuilder::new().on_row(3))
let footer = BorderBuilder::new(WidgetBuilder::new().on_row(4))
.build(ctx)
.to_base();
let inspector =
@@ -229,55 +231,53 @@ impl InspectorPlugin {
StackPanelBuilder::new(WidgetBuilder::new().with_child(head).with_child(inspector))
.build(ctx);
let warning_text;
let type_name_text;
let docs_button;
let warning_text = TextBuilder::new(
WidgetBuilder::new()
.with_visibility(false)
.with_margin(Thickness::left(4.0))
.with_foreground(ctx.style.property(Style::BRUSH_ERROR))
.on_row(0),
)
.with_wrap(WrapMode::Word)
.with_text(warning_text_str)
.build(ctx);
let search_bar = SearchBarBuilder::new(
WidgetBuilder::new()
.on_row(2)
.with_margin(Thickness::uniform(2.0)),
)
.build(ctx);
let type_name_text = TextBuilder::new(
WidgetBuilder::new()
.with_margin(Thickness::uniform(4.0))
.on_row(0)
.on_column(0),
)
.with_wrap(WrapMode::NoWrap)
.build(ctx);
let docs_button = ImageButtonBuilder::default()
.with_image_color(Color::YELLOW)
.with_width(26.0)
.with_height(26.0)
.on_column(1)
.with_image(load_image!("../../../resources/doc.png"))
.with_tooltip("Open Documentation")
.with_tab_index(Some(0))
.build_button(ctx);
let window = WindowBuilder::new(WidgetBuilder::new().with_name("Inspector"))
.with_title(WindowTitle::text("Inspector"))
.with_tab_label("Inspector")
.with_content(
GridBuilder::new(
WidgetBuilder::new()
.with_child({
warning_text = TextBuilder::new(
WidgetBuilder::new()
.with_visibility(false)
.with_margin(Thickness::left(4.0))
.with_foreground(ctx.style.property(Style::BRUSH_ERROR))
.on_row(0),
)
.with_wrap(WrapMode::Word)
.with_text(warning_text_str)
.build(ctx);
warning_text
})
.with_child(warning_text)
.with_child(search_bar)
.with_child(
GridBuilder::new(
WidgetBuilder::new()
.on_row(1)
.with_child({
type_name_text = TextBuilder::new(
WidgetBuilder::new()
.with_margin(Thickness::uniform(4.0))
.on_row(0)
.on_column(0),
)
.with_wrap(WrapMode::NoWrap)
.build(ctx);
type_name_text
})
.with_child({
docs_button = ImageButtonBuilder::default()
.with_image_color(Color::YELLOW)
.with_width(26.0)
.with_height(26.0)
.on_column(1)
.with_image(load_image!("../../../resources/doc.png"))
.with_tooltip("Open Documentation")
.with_tab_index(Some(0))
.build_button(ctx);
docs_button
}),
.with_child(type_name_text)
.with_child(docs_button),
)
.add_row(Row::auto())
.add_column(Column::stretch())
@@ -285,7 +285,7 @@ impl InspectorPlugin {
.build(ctx),
)
.with_child(
ScrollViewerBuilder::new(WidgetBuilder::new().on_row(2))
ScrollViewerBuilder::new(WidgetBuilder::new().on_row(3))
.with_content(content)
.build(ctx),
)
@@ -293,6 +293,7 @@ impl InspectorPlugin {
)
.add_row(Row::auto())
.add_row(Row::auto())
.add_row(Row::auto())
.add_row(Row::stretch())
.add_row(Row::auto())
.add_column(Column::stretch())
@@ -309,6 +310,7 @@ impl InspectorPlugin {
docs_button,
clipboard: None,
footer,
search_bar,
}
}
@@ -532,6 +534,11 @@ impl EditorPlugin for InspectorPlugin {
_ => (),
}
}
} else if let Some(SearchBarMessage::Text(search_text)) = message.data_from(self.search_bar)
{
let ui = editor.engine.user_interfaces.first();
let filter = search_text.to_lowercase();
ui[self.inspector].apply_filter(&filter, ui);
}
if let Some(InspectorMessage::PropertyChanged(args)) =
+1 -39
View File
@@ -240,44 +240,6 @@ impl SettingsWindow {
ui.send(self.inspector, InspectorMessage::Context(context));
}
fn apply_filter(&self, filter_text: &str, ui: &UserInterface) {
fn apply_recursive(
filter_text: &str,
inspector: Handle<UiNode>,
ui: &UserInterface,
) -> bool {
let inspector = ok_or_return!(ui.try_get_of_type::<Inspector>(inspector), false);
let mut is_any_match = false;
for entry in inspector.context.entries.iter() {
// First look at any inner inspectors, because they could also contain properties
// matching search criteria.
let mut inner_match = false;
let sub_inspector = ui.find_handle(entry.property_editor, &mut |node| {
node.is_or_has_field::<Inspector>()
});
if sub_inspector.is_some() {
inner_match |= apply_recursive(filter_text, sub_inspector, ui);
}
let display_name = entry.property_display_name.to_lowercase();
inner_match |= display_name.contains(filter_text)
|| fuzzy_compare(filter_text, display_name.as_str()) >= 0.5;
ui.send(
entry.property_container,
WidgetMessage::Visibility(inner_match),
);
is_any_match |= inner_match;
}
is_any_match
}
apply_recursive(filter_text, self.inspector.to_base(), ui);
}
pub fn handle_ui_message(
mut self,
message: &UiMessage,
@@ -343,7 +305,7 @@ impl SettingsWindow {
} else if let Some(SearchBarMessage::Text(search_text)) = message.data_from(self.search_bar)
{
let filter = search_text.to_lowercase();
self.apply_filter(&filter, ui);
ui[self.inspector].apply_filter(&filter, ui);
}
if let GraphicsContext::Initialized(ref mut graphics_context) = engine.graphics_context {