- 帖子
- 578
- 积分
- 1235
- 技术
- 170
- 捐助
- 60
- 注册时间
- 2012-8-5
|
[文本处理] bbhlt - 可能是你见过的最强大的论坛代码高亮工具
本帖最后由 bailong360 于 2019-10-31 00:18 编辑
闲来无事写了一个论坛代码高亮工具, 顺便宣传一波 Rust
超好用的包管理 + 强大的宏 + 强大的静态类型系统 + 与 C/C++ 同一级别的运行速度 + 无 GC 下的内存安全 + 函数式 + 究极友好的文档系统 + ...
什么叫现代语言啊? (仰头
这就叫现代语言 (逃
use failure::{format_err, Error};
use std::fmt::Write;
use std::fs::read_to_string;
use std::path::PathBuf;
use structopt::StructOpt;
use syntect::dumps;
use syntect::easy::HighlightLines;
use syntect::highlighting::{Color, Style, ThemeSet};
use syntect::parsing::SyntaxSet;
use syntect::util::LinesWithEndings;
#[derive(StructOpt)]
#[structopt(name = "bbhlt")]
struct Config {
/// 指定代码语言, 不指定则自动推断
#[structopt(short, value_name = "LANG", long)]
pub language: Option<String>,
/// 代码高亮主题
#[structopt(short, value_name = "THEME", long, default_value = "Dracula")]
pub theme: String,
/// 字体大小
#[structopt(short, value_name = "SIZE", long, default_value = "12px")]
pub size: String,
/// 等待高亮的文件
#[structopt(value_name = "FILE", parse(from_os_str))]
pub path: PathBuf,
}
fn init_syntect() -> (SyntaxSet, ThemeSet) {
(
dumps::from_binary(include_bytes!("../assets/syntaxes.bin")),
dumps::from_binary(include_bytes!("../assets/themes.bin")),
)
}
fn rgb_to_hex(c: Color) -> String {
format!("#{:02x}{:02x}{:02x}", c.r, c.g, c.b)
}
fn as_discuz_bbcode(v: &[(Style, &str)]) -> String {
let mut s: String = String::new();
for &(ref style, text) in v.iter() {
write!(
s,
"【color={}]{}【/color]",
rgb_to_hex(style.foreground),
text,
)
.unwrap();
}
s
}
fn run(config: &Config) -> Result<(), Error> {
let (ps, ts) = init_syntect();
let syntax = if let Some(lang) = &config.language {
ps.find_syntax_by_name(lang)
} else {
ps.find_syntax_for_file(config.path.to_str().unwrap())?
};
let syntax = syntax.ok_or_else(|| format_err!("无法确定语言"))?;
let theme = ts.themes.get(&config.theme).ok_or_else(|| format_err!("未找到该主题"))?;
let mut h = HighlightLines::new(syntax, theme);
let mut bg = Color::WHITE;
let code = read_to_string(&config.path)?;
let body = LinesWithEndings::from(&code)
.map(|line| {
let ranges = h.highlight(line, &ps);
bg = ranges[0].0.background;
as_discuz_bbcode(&ranges)
})
.collect::<Vec<_>>()
.join("");
print!(
"【table=100%,{}]【tr]【td]【font=monospace]【size={}]",
rgb_to_hex(bg),
config.size
);
print!("{}", body);
println!("【/size]【/font]【/td]【/tr]【/table]");
Ok(())
}
fn main() {
let config: Config = Config::from_args();
match run(&config) {
Err(e) => eprintln!("ERROR:\n{}", e),
_ => (),
}
}
|
(因为 bbcode 不支持转义,所以我将代码中的部分中括号替换成了全角字符,避免看起来一团糟
链接: https://pan.baidu.com/s/1RqvEkD0Ogz7zRrxgh6NbSg 提取码: bxxj |
-
2
评分人数
-
|