epezent/implot

GitHub: epezent/implot

ImPlot 是一款为 Dear ImGui 打造的即时模式 C++ 绘图库,旨在提供高性能的实时数据可视化和交互式图表功能。

Stars: 6024 | Forks: 664

# ImPlot ImPlot 是一个为 [Dear ImGui](https://github.com/ocornut/imgui) 打造的即时模式、GPU 加速绘图库。它旨在提供一流的 API,让 ImGui 粉丝爱不释手。ImPlot 非常适合实时可视化程序数据或创建交互式图表,并且只需极少代码即可集成。就像 ImGui 一样,它不会给最终用户带来 GUI 状态管理的负担,避免使用 STL 容器和 C++ 头文件,并且除了 ImGui 本身之外没有外部依赖。 ## 功能 - GPU 加速渲染 - 多种图表类型: - 线图 - 阴影图 - 散点图 - 垂直/水平/堆叠条形图 - 垂直/水平误差条 - 茎叶图 - 阶梯图 - 饼图 - 热力图 - 1D/2D 直方图 - 图像 - 以及更多即将推出的类型 - 在单个图表上混合/匹配多个绘图项 - 可配置的坐标轴范围和缩放(线性/对数) - 子图 - 时间格式的 x 轴(美国格式或 ISO 8601) - 可逆和可锁定的坐标轴 - 多个 x 轴和 y 轴 - 用于缩放、平移、框选和自动拟合数据的控件 - 用于创建持久查询范围的控件(参见演示) - 多种图表样式选项:10 种标记类型、可调标记大小、线宽、轮廓颜色、填充颜色等 - 16 种内置配色图,并支持用户添加的配色图 - 可选的图表标题、轴标签和网格标签 - 可选且可配置的图例,带有切换按钮以快速显示/隐藏绘图项 - 基于当前 ImGui 主题的默认样式,或完全自定义的图表样式 - 可自定义的数据获取器和数据步长(就像 ImGui:PlotLine 一样) - 接受 float、double 以及 8、16、32 和 64 位有符号/无符号整数类型的数据 - 以及更多!(参见公告 [2022](https://github.com/epezent/implot/discussions/370)/[2021](https://github.com/epezent/implot/issues/168)/[2020](https://github.com/epezent/implot/issues/48)) ## 用法 该 API 的使用方式就像任何其他 ImGui `BeginX`/`EndX` 对一样。首先,使用 `ImPlot::BeginPlot()` 开始一个新图表。接下来,使用提供的 `PlotX` 函数(例如 `PlotLine()`、`PlotBars()`、`PlotScatter()` 等)绘制任意数量的项目。最后,调用 `ImPlot::EndPlot()` 进行收尾。就是这样! ``` int bar_data[11] = ...; float x_data[1000] = ...; float y_data[1000] = ...; ImGui::Begin("My Window"); if (ImPlot::BeginPlot("My Plot")) { ImPlot::PlotBars("My Bar Plot", bar_data, 11); ImPlot::PlotLine("My Line Plot", x_data, y_data, 1000); ... ImPlot::EndPlot(); } ImGui::End(); ``` ![用法](https://static.pigsec.cn/wp-content/uploads/repos/2026/04/50cfccf471170433.png) 当然,ImPlot 还能做更多事情…… ## 演示 可以在 `implot_demo.cpp` 中找到 ImPlot 功能的综合示例。将此文件添加到您的源代码中,并在更新循环的某处调用 `ImPlot::ShowDemoWindow()`。我们鼓励您在需要实现各种图表类型时将此文件作为参考。演示会随着新图表类型和功能的添加而不断更新,因此请在每个版本发布后回来看看! 演示的在线版本托管在[这里](https://pthom.github.io/imgui_explorer/?lib=implot)。您可以查看图表以及生成它们的源代码。请注意,此演示可能并不总是最新的,并且性能不如桌面版实现,但它应该能让您大致了解 ImPlot 的可能性。特别感谢 [pthom](https://github.com/pthom) 创建并托管了它! 需要更长代码和/或第三方库的更复杂演示可以在单独的仓库中找到:[implot_demos](https://github.com/epezent/implot_demos)。在这里,您将看到高级信号处理和 ImPlot 的实际应用。如果您有新演示的想法,请阅读该仓库的 `Contributing` 部分! ## 集成 0. 如果您尚未设置 [ImGui](https://github.com/ocornut/imgui) 环境,请先设置。 1. 将 `implot.h`、`implot_internal.h`、`implot.cpp`、`implot_items.cpp` 以及可选的 `implot_demo.cpp` 添加到您的源代码中。或者,您可以使用 [vcpkg](https://github.com/microsoft/vcpkg/tree/master/ports/implot) 获取 ImPlot。 2. 在创建和销毁 `ImGuiContext` 的地方创建和销毁 `ImPlotContext`: ``` ImGui::CreateContext(); ImPlot::CreateContext(); ... ImPlot::DestroyContext(); ImGui::DestroyContext(); ``` 您应该可以开始了! ## 使用 vcpkg 安装 ImPlot 您可以使用 [vcpkg](https://github.com/Microsoft/vcpkg) 依赖管理器下载并安装 ImPlot: ``` git clone https://github.com/Microsoft/vcpkg.git cd vcpkg ./bootstrap-vcpkg.sh ./vcpkg integrate install ./vcpkg install implot ``` vcpkg 中的 ImPlot 端口由 Microsoft 团队成员和社区贡献者保持最新。如果版本过时,请在 vcpkg 仓库上[创建 issue 或 pull request](https://github.com/Microsoft/vcpkg)。 ## 极其重要的说明 Dear ImGui 默认使用 **16 位索引**,因此像 `ImPlot::PlotHeatmap()` 这样的高密度 ImPlot 小部件可能会在 `ImDrawList` 中生成过多的顶点,这会导致断言失败,并导致数据截断和/或视觉故障。因此,**强烈**建议您选择以下任一方式: - **选项 1:** 在您的 ImGui [`imconfig.h`](https://github.com/ocornut/imgui/blob/master/imconfig.h#L89) 文件中取消注释 `#define ImDrawIdx unsigned int` 以启用 32 位索引。 - **选项 2:** 如果必须使用 16 位索引,请在您的渲染器中处理 `ImGuiBackendFlags_RendererHasVtxOffset` 标志。许多默认的 ImGui 渲染后端已经支持 `ImGuiBackendFlags_RendererHasVtxOffset`。有关更多信息,请参阅[此 issue](https://github.com/ocornut/imgui/issues/2591)。 ## 常见问题 **Q: 为什么?** A: ImGui 是快速原型设计和开发的极其强大的工具,但仅提供有限的数据可视化机制。二维图表无处不在,对几乎任何应用程序都有用。能够实时可视化您的数据将使您对应用程序有更深入的了解和更好的理解。 **Q: ImPlot 是适合我的绘图库吗?** A: 如果您希望生成出版质量的图表和/或将图表导出到文件,ImPlot **不是**适合您的库!ImPlot 专为以实时速度和高度交互性绘制应用程序数据而设计。ImPlot 尽最大努力创建漂亮的图表(确实有很多样式选项可用),但它始终优先考虑功能而非形式。 **Q: 文档在哪里?** A: API 在 `implot.h` 中有详细注释,`implot_demo.cpp` 中的演示应该足以让您入门。此外,请查看 [implot_demos](https://github.com/epezent/implot_demos) 仓库。 **Q: ImPlot 适合绘制大型数据集吗?** A: 是的,在合理范围内。您可以毫无问题地绘制数万到数十万个点,但不要指望数百万个点能带来如丝般顺滑的体验。也就是说,如果需要,您可以通过告诉 ImPlot 以更大的间隔跨步数据来对超大型数据集进行下采样。也可以尝试实验性的 `backends` 分支,该分支旨在提供 GPU 加速支持。 **Q: 我可以绘制哪些数据类型?** A: ImPlot 绘图函数接受大多数标量类型: `float`、`double`、`int8`、`uint8`、`int16`、`uint16`、`int32`、`uint32`、`int64`、`uint64`。使用内置的跨步功能(参见 `implot.h` 中的文档),可以轻松将自定义结构体或类(例如 `Vector2f` 或类似类型)的数组传递给 ImPlot 函数,并且许多绘图器提供接受数据生成回调的 "getter" 重载。您可以通过在编译时定义 `IMPLOT_CUSTOM_NUMERIC_TYPES` 来完全自定义接受的类型列表:请参阅 `implot_items.cpp` 中的文档。 **Q: 可以修改图表样式吗?** A: 是的。有三种默认样式可用,以及一种尝试匹配您 ImGui 样式的自动样式。您也可以定义任何自定义样式。绘图项通常根据当前配色图为您设置样式,但也可以单独自定义。 **Q: ImPlot 支持非线性轴缩放吗?时间格式?** A: 是的。开箱即用地提供了对数缩放和对称对数缩放,您也可以定义自定义轴缩放。开箱即用地提供了具有微秒精度的时间缩放。 **Q: ImPlot 支持多个 y 轴吗?x 轴?** A: 是的。最多可以启用三个 x 轴和三个 y 轴。 **Q: ImPlot 支持 [插入图表类型] 吗?** A: 也许。请查看演示、图库或公告([2020](https://github.com/epezent/implot/issues/48)/[2021](https://github.com/epezent/implot/issues/168)/[2022](https://github.com/epezent/implot/discussions/370))以查看是否显示了您想要的图表类型。如果没有,请考虑提交 issue,或者更好的是,提交 PR! **Q: ImPlot 支持 3D 图表吗?** A: ImPlot 的实验性扩展 [ImPlot3D](https://github.com/brenocq/implot3d) 提供了类似的 API,用于绘制和交互 3D 数据。 **Q: ImPlot 提供分析工具吗?** A: 不完全是,但它确实让您能够查询图表子范围,您可以使用它随心所欲地处理数据。 **Q: 可以将图表导出/保存为图像吗?** A: 目前不能。如果您需要捕获图表,请使用操作系统的屏幕捕获机制。ImPlot 不适合渲染出版质量的图表;它仅旨在用作可视化工具。为此目的,请使用 MATLAB 或 matplotlib 对数据进行后处理。 **Q: 为什么我的图表线条显示锯齿?** A: 您可能需要启用 `ImGuiStyle::AntiAliasedLinesUseTex`(或者可能是 `ImGuiStyle:AntiAliasedLines`)。如果这些设置已启用,则必须确保您的后端支持基于纹理的抗锯齿(即使用双线性采样)。大多数默认的 ImGui 后端开箱即支持此功能。在[这里](https://github.com/ocornut/imgui/issues/3245)了解更多信息。或者,如果您的硬件支持,您可以在应用程序级别启用 MSAA(4x 应该就足够了)。 **Q: 我可以将 ImPlot 编译为动态库吗?** A: 像 ImGui 一样,建议您将 ImPlot 编译并链接为*静态*库或直接作为源代码的一部分。但是,如果您必须将 ImPlot 和 ImGui 编译为单独的 DLL,请确保使用 `ImPlot::SetImGuiContext(ImGuiContext* ctx)` 设置当前的 *ImGui* 上下文。这可以确保全局 ImGui 变量在 DLL 边界之间正确共享。 **Q: ImPlot 可以与其他语言/绑定一起使用吗?** A: 是的,您可以将生成的 C 绑定 [cimplot](https://github.com/cimgui/cimplot) 与大多数高级语言一起使用。[DearPyGui](https://github.com/hoffstadt/DearPyGui) 提供了 Python 包装器,以及其他功能。[DearImGui/DearImPlot](https://github.com/aybe/DearImGui) 提供 .NET 绑定。[imgui-java](https://github.com/SpaiR/imgui-java) 提供 Java 绑定。[ImPlot.jl](https://github.com/wsphillips/ImPlot.jl) 提供 Julia 绑定。Rust 绑定 [implot-rs](https://github.com/4bb4/implot-rs) 目前正在开发中。可以在[这里](https://github.com/pthom/implot_demo) 找到使用 Emscripten 的示例。
标签:C++, Dear ImGui, GUI开发, K线图, 交互式图表, 即时模式, 图表库, 实时数据, 开源库, 折线图, 搜索引擎爬虫, 散点图, 数据擦除, 数据渲染, 柱状图, 热力图, 直方图, 绘图, 错误条形图, 饼图