2 个不稳定版本

0.2.2 2022年4月30日
0.1.3 2022年4月26日
0.1.0 2022年4月25日

#175 in 可视化

GPL-3.0 许可协议

240KB
581

Easy print multiple functions

tgraph

⚠️ tgraph 目前处于活跃开发阶段,因此接口和文档都处于非常初级的阶段

Plain-simple Rust crate 提供基于函数的终端绘图。它提供了一个通过传递 Rust 闭包/函数来绘制函数图的接口,也允许你在同一个图中绘制多个函数。

路线图

  • 绘制单个函数的图
  • 绘制多个函数的图
  • 自定义函数显示 (目前只支持颜色和字符,更多功能即将推出)
  • 可选限制图的高度
  • 交互式图表:移动和缩放
  • 绘制负值
  • 记录展示 tgraph 的终端
  • 更多想法即将推出!请在 问题标签 中提出你的想法!

用法

要绘制函数,使用表示图的包装器。有两种类型的图:单个函数图 (Graph) 和多个函数图 (MultiGraph)。虽然你可以直接使用 MultiGraph,但对于单个函数,建议使用 Graph,因为 MultiGraph 会添加一些对于单个函数不必要的代码。

这两个结构体提供了相同的接口。为了创建一个图(这里为了简单起见使用 Graph,对于 MultiGraph 请参见文档),您可以使用以下代码创建图:Graph::new(f, width: u32, height: Option<u32>),其中 f 是函数/闭包(下文将进一步解释)和 height 如果传递 None 则自动设置,或者您也可以使用 Graph::new_screen(f, height: Option<u32>),它会获取屏幕的宽度。如果您想使用选项自定义图,可以分别调用 Graph::with_optionsGraph::with_options_screen,并将 GraphOptions 结构体作为最后一个参数传递(更多内容请参见图自定义部分)。

可以绘制的函数限制为实现了 tgraph::AsF64 特性的类型,这允许函数的参数从 f64 创建,并将函数的结果转换为 f64,因为屏幕绘制是像素级的。您可以对此特性实现您想要的任何类型,这意味着如果您在表示人的结构体上实现了 tgraph::AsF64,那么这个结构体就可以作为图的一部分绘制。

为了编写图函数,提供了一个 func! 宏,它提供了一个简单且直接的语法来创建函数实例,并在 MultiGraph 中更直观地使用函数(由于具有相同类型的函数/闭包有不同的签名,因此您必须添加 as fn(X) -> Y,其中 XY 分别是输入和输出的类型)。

要绘制图,只需要在 GraphMultiGraph 上调用 .draw() 即可,这将把图绘制到执行二进制文件的终端上。另一个选项是打印实例,因此如果 graph 是您的 GraphMultiGraph 实例,那么 println!("{}", graph) 也会将图打印到屏幕上(注意,调试打印不会,只会显示打印)。

图自定义

要自定义图形的打印方式,可以使用与 GraphMultiGraphOptions 一起使用的 GraphOptions,它是一个简单的元组结构体,包含一个 Vec<GraphOptions>,其中每个 GraphOption 都与传递的函数向量中相同位置的函数相关联,用于 MultiGraph。从现在开始,将解释 GraphOptions,因为 MultiGraphOptions 目前仅封装了之前的结构。

要自定义图形颜色,使用 GraphOptions.color 字段,它包含一个包装结构体(tgraph::ColorWrapper)用于 console_engine::Color 枚举,传递一个 console_engine::Color 变体并调用 .into() 以轻松将其转换为包装类型。字符使用 tgraph::Character 枚举来控制,该枚举有几个用于图形表示的预定义字符的变体以及一个表示任何字符的变体,可以通过调用 .into() 在 char 中或手动选择一个变体来使用。最后一个选项是显示或隐藏 y 轴图例,目前仅在 GraphGraphOptions.height_legend 下支持(config 接口将很快改变的原因之一)。

Both GraphOptionsMultiGraph 实现了 Default,因此如果不需要,您不必真正担心配置它。 GraphOptions 还利用 typed_builder crate 提供一个不错的构建器接口(有关更多信息,请查看 typed_builder crate 的文档)。

示例

单函数图形

Graph::with_options_screen(
    func!(|x| 0.005 * (x * x) + 0.1 * x),
    GraphOptions::builder()
        .color(Color::DarkMagenta.into())
        .build(),
)
.draw();

多函数图形

println!(
    "{}",
    MultiGraph::new(
        vec![
            func!(x -> 10f64 -(x/5f64)),
            func!(x -> f64::sin(x/2f64).abs() * 4f64),
            func!(x -> x.ln()),
        ],
        80,
        None,
    )
);

比较这两个示例,您可以看到渲染图形的两种方式以及声明函数的不同方式,使用 func! 宏。

依赖项

~3–12MB
~122K SLoC