some changes like horizontal lines ---

This commit is contained in:
deadvey 2025-01-07 21:14:34 +00:00
parent 50c6293eba
commit 7ec6bf1c47
2 changed files with 94 additions and 23 deletions

View File

@ -7,3 +7,4 @@ edition = "2021"
colored = "2.2.0"
regex = "1.11.1"
url = "2.5.4"
termion = "4.0.3"

View File

@ -2,18 +2,19 @@ use std::process::{Command};
use std::io::{stdin,stdout,Write};
use colored::Colorize;
use regex::Regex;
use url::Url;
fn clear_screen() {
Command::new("clear")
.spawn()
.status()
.expect("Failed to clear screen");
//println!("clearing");
}
fn parse_markdown(page_content: String) -> (String, Vec<String>) {
let mut parsed_page_content: String = "".to_string();
let mut hyperlink_number_counter: u64 = 0;
let mut links: Vec<String> = Vec::new();
let (screen_width, screen_height) = termion::terminal_size().unwrap();
for line in page_content.lines() {
let mut parsed_line: String = line.to_string();
@ -27,6 +28,17 @@ fn parse_markdown(page_content: String) -> (String, Vec<String>) {
caps[1].bold().to_string()
}).to_string();
// Horizontal lines
let hr_regex = Regex::new(r"^(\*\*\*)|(---)|(___)$").unwrap();
parsed_line = hr_regex.replace_all(&parsed_line, |_caps: &regex::Captures| {
let mut result: String = "\n".to_string();
for _x in 0..screen_width/2 {
result += "- ";
}
result += "\n";
result
}).to_string();
// Italics
let italic_regex = Regex::new(r"\*(.*?)\*").unwrap();
parsed_line = italic_regex.replace_all(&parsed_line, |caps: &regex::Captures| {
@ -58,17 +70,22 @@ fn parse_markdown(page_content: String) -> (String, Vec<String>) {
}).to_string();
// HyperLink
let hyperlink_regex = Regex::new(r"\[(.*?)\]\((.*?)\)").unwrap();
let hyperlink_regex = Regex::new(r"(.*?)\[(.*?)\]\((.*?)\)").unwrap();
parsed_line = hyperlink_regex.replace_all(&parsed_line, |caps: &regex::Captures| {
let result = format!("{}[{}]", &caps[1].blue().underline(),hyperlink_number_counter);
let url = caps[2].to_string();
links.push(url);
hyperlink_number_counter+=1;
result
// Check if the character before the link is not '!'
if !caps[1].ends_with('!') { // caps[1] is everything before the link
let result = format!("{}{}[{}]", &caps[1], &caps[2].blue().underline(), hyperlink_number_counter);
let url = caps[3].to_string();
links.push(url);
hyperlink_number_counter += 1;
result
} else {
// If it's an image (starts with !), return the link as is
format!("[{}]", &caps[2].green())
}
}).to_string();
parsed_page_content+=&(parsed_line + "\n");
}
@ -116,14 +133,16 @@ fn render_page(host: String, port: String, path: String) -> Vec<String> {
clear_screen();
let mut content = fetch_page(&host, &port, &path);
let mut links = Vec::new();
let (screen_width, screen_height) = termion::terminal_size().unwrap();
(content, links) = parse_markdown(content);
print!("{}: {}\n", host, path);
for _i in 0..format!("{}: {}", host, path).len() {
print!("-");
for _i in 0..screen_width {
print!("");
}
print!("\n\n{}", content);
for _i in 0..format!("{}: {}", host, path).len() {
print!("-");
println!("\n\n{}", content);
for _i in 0..screen_width {
print!("");
}
println!();
for i in 0..links.len() {
@ -146,29 +165,80 @@ fn input() -> String{
return s;
}
fn main() {
println!("Enter a url: ");
let mut host: String = input();
fn parse_url(url: String, previous_host: &String) -> (String, String, String) {
let mut host: String = previous_host.to_string();
let mut port: String = "3477".to_string();
let mut path: String = "/".to_string();
let mttp_regex = Regex::new(r"^mttp:\/\/(.*?)\/(.*?)$").unwrap();
let mttp_regex_no_path = Regex::new(r"^mttp:\/\/(.*?)$").unwrap();
let accept_this_as_mttp = Regex::new(r"^(.*?)$").unwrap();
let path_change = Regex::new(r"^/(.*?)$").unwrap();
if let Some(caps) = mttp_regex.captures(&url) {
host = caps[1].to_string();
port = "3477".to_string();
path = caps[2].to_string();
}
else if let Some(caps) = mttp_regex_no_path.captures(&url) {
host = caps[1].to_string();
port = "3477".to_string();
path = "/".to_string();
}
else if let Some(caps) = path_change.captures(&url) {
println!("path change");
host = previous_host.to_string();
port = "3477".to_string();
path = caps[1].to_string();
}
else if let Some(caps) = accept_this_as_mttp.captures(&url) {
host = caps[1].to_string();
port = "3477".to_string();
path = "/".to_string();
}
println!("{}:{}/{}",host,port,path);
return (host, port, path);
}
fn main() {
clear_screen();
println!("Enter a url: ");
let url = input();
if url == "q" {
std::process::exit(0);
}
let (mut host, mut port, mut path) = parse_url(url, &"example.com".to_string()); // Must pass
// 'previous
// host'
'mainloop: loop {
let links = render_page(host.clone(), port.clone(), path.clone());
println!("{}:{}/{}", host, port, path);
println!("Enter link number to follow, or q to quit");
println!("Enter link number to follow, r to reload this page, h for help, or q to quit");
let link_to_follow = input();
if link_to_follow == "q" {
break 'mainloop;
}
else if link_to_follow == "r" {
continue;
}
else if link_to_follow == "h" {
println!("
Source code: https://git.javalsai.dynv6.net/deadvey/markdown-webbrowser\n
q: quit
h: help
r: reload
");
}
else {
let number: usize = link_to_follow.parse::<usize>().unwrap();
let parsed_url = Url::parse(&links[number]).expect("Invalid URL");
host = parsed_url.host_str().expect("No host found").to_string();
port = parsed_url.port().unwrap_or(3477).to_string();
path = parsed_url.path().to_string();
(host, port, path) = parse_url(links[number].clone(), &host);
println!("{}:{}/{}", host, port, path);
}
}