馃 Vim-like, Command-line Gemini Client
gemini gemini-protocol tui smolweb vim
at main 82 lines 1.9 kB view raw
1// This file is part of Sydney <https://github.com/gemrest/sydney>. 2// 3// This program is free software: you can redistribute it and/or modify 4// it under the terms of the GNU General Public License as published by 5// the Free Software Foundation, version 3. 6// 7// This program is distributed in the hope that it will be useful, but 8// WITHOUT ANY WARRANTY; without even the implied warranty of 9// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 10// General Public License for more details. 11// 12// You should have received a copy of the GNU General Public License 13// along with this program. If not, see <http://www.gnu.org/licenses/>. 14// 15// Copyright (C) 2022-2022 Fuwn <contact@fuwn.me> 16// SPDX-License-Identifier: GPL-3.0-only 17 18//! <https://github.com/fdehau/tui-rs/blob/master/examples/list.rs> 19 20use ratatui::widgets::ListState; 21 22pub struct StatefulList<T> { 23 pub state: ListState, 24 pub items: Vec<T>, 25 pub selected: usize, 26} 27 28impl<T> StatefulList<T> { 29 pub fn with_items(items: Vec<T>) -> Self { 30 Self { 31 state: ListState::default(), 32 items, 33 selected: 0, 34 } 35 } 36 37 pub fn next(&mut self) { 38 let i = match self.state.selected() { 39 Some(i) => 40 if i >= self.items.len() - 1 { 41 0 42 } else { 43 i + 1 44 }, 45 None => 0, 46 }; 47 48 self.selected = i; 49 50 self.state.select(Some(i)); 51 } 52 53 pub fn previous(&mut self) { 54 let i = match self.state.selected() { 55 Some(i) => 56 if i == 0 { 57 self.items.len() - 1 58 } else { 59 i - 1 60 }, 61 None => 0, 62 }; 63 64 self.selected = i; 65 66 self.state.select(Some(i)); 67 } 68 69 pub fn last(&mut self) { 70 self.state.select(Some(self.items.len() - 1)); 71 72 self.selected = self.items.len() - 1; 73 } 74 75 pub fn first(&mut self) { 76 self.state.select(Some(0)); 77 78 self.selected = 0; 79 } 80 81 pub fn unselect(&mut self) { self.state.select(None); } 82}