notedeck

One damus client to rule them all
git clone git://jb55.com/notedeck
Log | Files | Refs | README | LICENSE

thread.rs (4077B)


      1 use crate::{
      2     actionbar::NoteAction,
      3     imgcache::ImageCache,
      4     muted::MuteFun,
      5     notecache::NoteCache,
      6     notes_holder::{NotesHolder, NotesHolderStorage},
      7     thread::Thread,
      8     ui::note::NoteOptions,
      9     unknowns::UnknownIds,
     10 };
     11 use nostrdb::{Ndb, NoteKey, Transaction};
     12 use tracing::error;
     13 
     14 use super::timeline::TimelineTabView;
     15 
     16 pub struct ThreadView<'a> {
     17     threads: &'a mut NotesHolderStorage<Thread>,
     18     ndb: &'a Ndb,
     19     note_cache: &'a mut NoteCache,
     20     unknown_ids: &'a mut UnknownIds,
     21     img_cache: &'a mut ImageCache,
     22     selected_note_id: &'a [u8; 32],
     23     textmode: bool,
     24     id_source: egui::Id,
     25 }
     26 
     27 impl<'a> ThreadView<'a> {
     28     #[allow(clippy::too_many_arguments)]
     29     pub fn new(
     30         threads: &'a mut NotesHolderStorage<Thread>,
     31         ndb: &'a Ndb,
     32         note_cache: &'a mut NoteCache,
     33         unknown_ids: &'a mut UnknownIds,
     34         img_cache: &'a mut ImageCache,
     35         selected_note_id: &'a [u8; 32],
     36         textmode: bool,
     37     ) -> Self {
     38         let id_source = egui::Id::new("threadscroll_threadview");
     39         ThreadView {
     40             threads,
     41             ndb,
     42             note_cache,
     43             unknown_ids,
     44             img_cache,
     45             selected_note_id,
     46             textmode,
     47             id_source,
     48         }
     49     }
     50 
     51     pub fn id_source(mut self, id: egui::Id) -> Self {
     52         self.id_source = id;
     53         self
     54     }
     55 
     56     pub fn ui(&mut self, ui: &mut egui::Ui, is_muted: &MuteFun) -> Option<NoteAction> {
     57         let txn = Transaction::new(self.ndb).expect("txn");
     58 
     59         let selected_note_key = if let Ok(key) = self
     60             .ndb
     61             .get_notekey_by_id(&txn, self.selected_note_id)
     62             .map(NoteKey::new)
     63         {
     64             key
     65         } else {
     66             // TODO: render 404 ?
     67             return None;
     68         };
     69 
     70         ui.label(
     71             egui::RichText::new("Threads ALPHA! It's not done. Things will be broken.")
     72                 .color(egui::Color32::RED),
     73         );
     74 
     75         egui::ScrollArea::vertical()
     76             .id_salt(self.id_source)
     77             .animated(false)
     78             .auto_shrink([false, false])
     79             .scroll_bar_visibility(egui::scroll_area::ScrollBarVisibility::AlwaysVisible)
     80             .show(ui, |ui| {
     81                 let note = if let Ok(note) = self.ndb.get_note_by_key(&txn, selected_note_key) {
     82                     note
     83                 } else {
     84                     return None;
     85                 };
     86 
     87                 let root_id = {
     88                     let cached_note = self
     89                         .note_cache
     90                         .cached_note_or_insert(selected_note_key, &note);
     91 
     92                     cached_note
     93                         .reply
     94                         .borrow(note.tags())
     95                         .root()
     96                         .map_or_else(|| self.selected_note_id, |nr| nr.id)
     97                 };
     98 
     99                 let thread = self
    100                     .threads
    101                     .notes_holder_mutated(self.ndb, self.note_cache, &txn, root_id, is_muted)
    102                     .get_ptr();
    103 
    104                 // TODO(jb55): skip poll if ThreadResult is fresh?
    105 
    106                 // poll for new notes and insert them into our existing notes
    107                 match thread.poll_notes_into_view(&txn, self.ndb, is_muted) {
    108                     Ok(action) => {
    109                         action.process_action(&txn, self.ndb, self.unknown_ids, self.note_cache)
    110                     }
    111                     Err(err) => error!("{err}"),
    112                 };
    113 
    114                 // This is threadview. We are not the universe view...
    115                 let is_universe = false;
    116                 let mut note_options = NoteOptions::new(is_universe);
    117                 note_options.set_textmode(self.textmode);
    118 
    119                 TimelineTabView::new(
    120                     thread.view(),
    121                     true,
    122                     note_options,
    123                     &txn,
    124                     self.ndb,
    125                     self.note_cache,
    126                     self.img_cache,
    127                 )
    128                 .show(ui)
    129             })
    130             .inner
    131     }
    132 }