diff --git a/Cargo.toml b/Cargo.toml index b62c9ac..07df551 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -4,4 +4,8 @@ default-members = ["src/redrop"] resolver = "2" [profile.release] -opt-level = 2 # fast and small wasm +opt-level = "z" +codegen-units = 1 +lto = "fat" +panic = "abort" +strip = "symbols" diff --git a/README.md b/README.md index e5a2d6f..0c15f02 100644 --- a/README.md +++ b/README.md @@ -26,11 +26,9 @@ ProjectM (Milkdrop) Music Visualization in Rust. ### ReDrop App -- [ ] Search Preset: - - [ ] Search Categories - - [ ] Hide Empty Categories -- [ ] Grid Layout: auto calcul columns -- [ ] Show Flat Preset: Align text to the left +- [X] Filter Preset / Hide Empty Categories +- [X] Grid Layout: Responsive +- [X] Show Flat Preset: Align text to the left - [ ] Change preset time interval on nBar (4 beat) 160 bpm, 32 bar -> 48s [4 / ( (160 / 60) ) * 32] - [ ] Set Window default size (persistence !?) diff --git a/projectM-4.dll b/projectM-4.dll deleted file mode 100644 index d3ce0b7..0000000 Binary files a/projectM-4.dll and /dev/null differ diff --git a/redrop.exe b/redrop.exe deleted file mode 100644 index e720890..0000000 Binary files a/redrop.exe and /dev/null differ diff --git a/redrop_player.exe b/redrop_player.exe deleted file mode 100644 index c435c32..0000000 Binary files a/redrop_player.exe and /dev/null differ diff --git a/src/common/src/preset.rs b/src/common/src/preset.rs index 3ea035f..0e3daed 100644 --- a/src/common/src/preset.rs +++ b/src/common/src/preset.rs @@ -9,6 +9,7 @@ pub struct Preset { pub img: Option, } +#[derive(Debug, Clone)] pub enum Node { PresetId(usize), InnerNode(BTreeMap), @@ -50,7 +51,7 @@ impl Presets { path: path.clone(), img: if img.exists() { Some(img) } else { None }, }; - node.insert(name, Node::PresetId(preset_id)); + node.insert(name.to_lowercase(), Node::PresetId(preset_id)); self.lists.push(preset); } } @@ -59,7 +60,26 @@ impl Presets { println!("Error: Check `presets path` in config ! ({})", e); } } - node } } + +pub fn filter_presets_tree(query: &str, node: &BTreeMap) -> BTreeMap { + let mut filtered_node = BTreeMap::new(); + for (name, node) in node { + match node { + Node::PresetId(_) => { + if name.contains(query.to_lowercase().as_str()) { + filtered_node.insert(name.clone(), node.clone()); + } + } + Node::InnerNode(inner_node) => { + let filtered_inner = filter_presets_tree(query, inner_node); + if !filtered_inner.is_empty() { + filtered_node.insert(name.clone(), Node::InnerNode(filtered_inner)); + } + } + } + } + filtered_node +} diff --git a/src/player/Cargo.toml b/src/player/Cargo.toml index 6cbee83..43f994c 100644 --- a/src/player/Cargo.toml +++ b/src/player/Cargo.toml @@ -7,14 +7,14 @@ edition = "2021" [dependencies] common = { path = "../common" } -libc = "*" +# libc = "*" projectm = "2.0.1-alpha" egui = "0.27.2" eframe = { version = "0.27.2", default-features = false, features = [ - "accesskit", + # "accesskit", "default_fonts", "glow", ] } log = "0.4" env_logger = "0.11.3" -ipc-channel = "0.18.1" \ No newline at end of file +ipc-channel = "0.18.1" diff --git a/src/redrop/Cargo.toml b/src/redrop/Cargo.toml index 349060a..f9b97f0 100644 --- a/src/redrop/Cargo.toml +++ b/src/redrop/Cargo.toml @@ -7,18 +7,18 @@ edition = "2021" common = { path = "../common" } egui = "0.27.2" eframe = { version = "0.27.2", default-features = false, features = [ - "accesskit", + # "accesskit", "default_fonts", "glow", ] } -egui_extras = { version = "0.27.2", features = ["all_loaders"] } +egui_extras = { version = "0.27.2", features = ["file", "image"] } image = { version = "0.24", features = [ "jpeg", - "png", + # "png ] } # The version needs to be same as the version used by `egui_extra`. (Not working with 0.25.x) log = "0.4" env_logger = "0.11.3" serde = { version = "1.0.203", features = ["derive"] } ipc-channel = "0.18.1" rand = "0.8.5" -rfd = "0.14.1" \ No newline at end of file +rfd = "0.14.1" diff --git a/src/redrop/src/main.rs b/src/redrop/src/main.rs index 7cfd57b..4ab8d82 100644 --- a/src/redrop/src/main.rs +++ b/src/redrop/src/main.rs @@ -1,5 +1,6 @@ use eframe::egui; +use std::collections::BTreeMap; use std::path::Path; use crate::ipc_message::{IpcExchange, Message}; @@ -34,6 +35,7 @@ struct ReDropApp { config_draft: config::Config, show_config: bool, presets: preset::Presets, + filtered_presets_tree: BTreeMap, smooth: bool, preset_search_query: String, player_app: Option, @@ -48,6 +50,7 @@ impl ReDropApp { slf.config_draft = slf.config.clone(); slf.presets .update_presets_lists_and_tree(Path::new(&slf.config.presets_path)); + slf.filtered_presets_tree = slf.presets.tree.clone(); let (ipc_server, server_name) = IpcOneShotServer::::new().unwrap(); diff --git a/src/redrop/src/main_ui.rs b/src/redrop/src/main_ui.rs index 0e18d39..ee48cd0 100644 --- a/src/redrop/src/main_ui.rs +++ b/src/redrop/src/main_ui.rs @@ -1,11 +1,18 @@ use crate::ReDropApp; use common::ipc_message::Message; +use common::preset::filter_presets_tree; impl ReDropApp { pub fn show_main_ui(&mut self, ctx: &egui::Context) { egui::TopBottomPanel::top("top_panel").show(ctx, |ui| { ui.horizontal(|ui| { - ui.text_edit_singleline(&mut self.preset_search_query); + if ui + .add(egui::TextEdit::singleline(&mut self.preset_search_query)) + .changed() + { + self.filtered_presets_tree = + filter_presets_tree(&self.preset_search_query, &self.presets.tree); + } if ui.button("Config").clicked() { self.show_config = true; } @@ -68,11 +75,9 @@ impl ReDropApp { // self.show_presets_into_flat_tree(ui, &self.presets.tree); let option_grid = true; // TODO: Option in config [ReDrop] if option_grid { - self.show_presets_into_tree_grid(ui, &self.presets.tree); - // TODO: Move presets_tree in the fn + self.show_presets_into_tree_grid(ui, &self.filtered_presets_tree); } else { - self.show_presets_into_flat_tree(ui, &self.presets.tree); - // TODO: Move presets_tree in the fn + self.show_presets_into_flat_tree(ui, &self.filtered_presets_tree); } }); }); diff --git a/src/redrop/src/presets_ui.rs b/src/redrop/src/presets_ui.rs index 66898d2..03467ed 100644 --- a/src/redrop/src/presets_ui.rs +++ b/src/redrop/src/presets_ui.rs @@ -8,25 +8,20 @@ impl ReDropApp { ui: &mut egui::Ui, node: &BTreeMap, ) { - const MAX_PRESETS_PER_ROW: usize = 8; // TODO: Autosize with ui.available_width() / preset_width - egui::Grid::new("preset_grid") - .num_columns(MAX_PRESETS_PER_ROW) + .num_columns(1) + .spacing([4., 4.]) .show(ui, |ui| { let mut preset_count = 0; + let max_preset_per_row = (ui.available_width() / 68.) as usize; // Preset width = 64. + 4. (spacing) for (name, node) in node { match node { preset::Node::PresetId(preset_id) => { - if self.presets.lists[*preset_id] - .name - .contains(&self.preset_search_query) - { - self.show_preset(ui, preset_id); - preset_count += 1; - if preset_count >= MAX_PRESETS_PER_ROW { - ui.end_row(); - preset_count = 0; - } + self.show_preset(ui, preset_id); + preset_count += 1; + if preset_count >= max_preset_per_row { + ui.end_row(); + preset_count = 0; } } preset::Node::InnerNode(inner_node) => { @@ -41,7 +36,6 @@ impl ReDropApp { } fn show_preset(&self, ui: &mut egui::Ui, preset_id: &usize) { - // TODO: Add image button into a Grid (Responsive ?) let preset = &self.presets.lists[*preset_id]; if let Some(img_path) = &preset.img { let file_path = "file://".to_owned() + img_path.to_str().unwrap(); @@ -82,12 +76,7 @@ impl ReDropApp { for (name, node) in node { match node { preset::Node::PresetId(preset_id) => { - if self.presets.lists[*preset_id] - .name - .contains(&self.preset_search_query) - { - self.show_preset_flat(ui, preset_id); - } + self.show_preset_flat(ui, preset_id); } preset::Node::InnerNode(inner_node) => { egui::CollapsingHeader::new(name).show(ui, |ui| { @@ -101,10 +90,7 @@ impl ReDropApp { fn show_preset_flat(&self, ui: &mut egui::Ui, preset_id: &usize) { let preset = &self.presets.lists[*preset_id]; if ui - .add_sized( - [ui.available_width(), 0.], - egui::Button::new(&preset.name).wrap(true), // TODO: Text to left - ) // TODO Fix: Button size "overflow" if name is too long / This can be a problem with grid.. + .add(egui::Button::new(&preset.name).wrap(true).frame(false)) .clicked() { self.send_load_preset_file(preset.id, self.smooth)