gyscos / cursive

A Text User Interface library for the Rust programming language
MIT License
4.32k stars 247 forks source link

[FEATURE] OSC8/Hyperlink Support #802

Open ultrabear opened 2 months ago

ultrabear commented 2 months ago

Is your feature request related to a problem? Please describe. I have a program where I want to render clickable hyperlinks as specified by OSC 8, cursive has no native way to render OSC8, and going around cursive for it is a major hassle and not something advisable.

OSC 8 described

Describe the solution you'd like A way to specify a hyperlink in cursive, potentially the api could look like this (modeled after the with_* Printer methods):

impl Printer {
    /// Wraps the printed text with a hyperlink
    pub fn with_hyperlink<F: FnOnce(&Printer)>(&self, link: &str, f: F);
}

and other related methods like set_hyperlink, though this seems weird to set/unset

Alternatively, OSC8 provides a way to label hyperlinks as the same with the id parameter, so the api could look like this (and set_hyperlink would make more sense):

#[derive(Copy, Clone)]
struct Hyperlink<'a> {
    link: &'a str,
    // this can be a stable hash of the link, or user provided, or just random,
    // whatever works best for cursive
    // OSC8 intends id's to be used for applications where you have
    // hyperlinks split over multiple lines, the id will uniquely 
    // identify separate segments as one link
    // the length of 8 was arbitrarily chosen for demonstration
    id: [u8; 8],
}

impl<'a> Hyperlink<'a> {
    // using rand here as an example, in this way each new Hyperlink is probabilistically distinct
    fn new(link: &'a str) -> Self { Self { link, id: rand::thread_rng().gen() } }
}

impl Printer {
    /// Wraps the printed text with a hyperlink
    pub fn with_hyperlink<F: FnOnce(&Printer)>(&self, link: Hyperlink, f: F);
}

Additional context While cursive View's can be used to replicate a portion of the OSC8 hyperlink behavior, this is an API that modern terminal emulators provide, and it would be cool if cursive could support rendering them

gyscos commented 1 month ago

Hi, and thanks for the report!

Indeed, I didn't know about it but it looks like it would be great to support it!