/* * Search.vala * * Widget for searching feed items */ namespace RSSuper { using Gtk; /** * Search - Widget for searching feed items */ public class Search : WidgetBase { private SearchService search_service; private Entry search_entry; private Button search_button; private Label status_label; private ListView results_view; private ListStore results_store; private ScrolledWindow scrolled_window; public Search(SearchService search_service) { this.search_service = search_service; set_orientation(Orientation.VERTICAL); set_spacing(12); set_margin(20); var title_label = new Label("Search"); title_label.add_css_class("heading"); append(title_label); var search_box = new Box(Orientation.HORIZONTAL, 6); search_box.set_hexpand(true); search_entry = new Entry(); search_entry.set_placeholder_text("Search feeds..."); search_entry.set_hexpand(true); search_entry.activate += on_search; search_box.append(search_entry); search_button = new Button.with_label("Search"); search_button.clicked += on_search; search_box.append(search_button); append(search_box); status_label = new Label(null); status_label.set_xalign(0); status_label.set_wrap(true); append(status_label); scrolled_window = new ScrolledWindow(); scrolled_window.set_hexpand(true); scrolled_window.set_vexpand(true); results_store = new ListStore(1, typeof(string)); results_view = new ListView(results_store); var factory = SignalListItemFactory.new(); factory.setup += on_setup; factory.bind += on_bind; factory.unset += on_unset; results_view.set_factory(factory); scrolled_window.set_child(results_view); append(scrolled_window); } public override void initialize() { // Initialize with default state } protected override void update_from_state() { // Update from state if needed } private void on_search() { var query = search_entry.get_text(); if (query.is_empty()) { status_label.set_text("Please enter a search query"); return; } search_button.set_sensitive(false); status_label.set_text("Searching..."); search_service.search(query, (state) => { if (state.is_success()) { var results = state.get_data() as SearchResult[]; update_results(results); status_label.set_text($"Found {results.length} results"); } else if (state.is_error()) { status_label.set_text($"Error: {state.get_message()}"); } search_button.set_sensitive(true); }); } private void on_setup(ListItem item) { var label = new Label(null); label.set_xalign(0); label.set_wrap(true); label.set_max_width_chars(80); item.set_child(label); } private void on_bind(ListItem item) { var label = item.get_child() as Label; var result = item.get_item() as SearchResult; if (result != null) { label.set_text(result.title); } } private void on_unset(ListItem item) { item.set_child(null); } private void update_results(SearchResult[] results) { results_store.splice(0, results_store.get_n_items(), results); } } }