R

ReflexKR

Reflex 官方文档

组件工坊:Reflex 组件库 100 例

·

课程概览

布局

·

Box

·

Flex

·

Stack

·

Grid

·

Container

·

Section

·

Center

·

Spacer

·

Separator

·

Card

·

Inset

·

Aspect Ratio

·

Fragment

排版

·

Text

·

Heading

·

Link

·

Code

·

Markdown

·

Blockquote

·

Quote

·

Strong

·

Em

·

Kbd

表单

·

Button

·

Input

·

Text Area

·

Checkbox

·

Switch

·

Radio Group

·

Select

·

Slider

·

Form

·

Upload

数据展示

·

Badge

·

Avatar

·

Icon

·

Callout

·

List

·

Data List

·

Code Block

·

Progress

·

Spinner

·

Scroll Area

·

Moment

展开与切换

·

Tabs

·

Accordion

·

Segmented Control

浮层

·

Tooltip

·

Popover

·

Hover Card

·

Dialog

·

Alert Dialog

·

Drawer

·

Dropdown Menu

·

Context Menu

·

Toast

动态渲染

·

Cond

·

Match

·

Foreach

·

Auto Scroll

媒体

·

Image

·

Audio

·

Video

表格与数据网格

·

Table

·

Data Table

·

Data Editor

图表

·

Area Chart

·

Bar Chart

·

Line Chart

·

Composed Chart

·

Pie Chart

·

Radar Chart

·

Radial Bar Chart

·

Scatter Chart

·

Funnel Chart

·

Treemap

·

Sankey Chart

·

Error Bar

图表部件

·

Axis

·

Cartesian Grid

·

Chart Tooltip

·

Legend

·

Label

·

Reference

·

Brush

其他图表库

·

Plotly

·

Pyplot

HTML 元素

·

HTML

·

HTML Text

·

HTML Layout

·

HTML Forms

·

HTML Media

·

HTML Tables

·

SVG

其他工具

·

Theme

·

Skeleton

·

Clipboard

·

Html Embed

·

Script

·

Memo

组件工坊:Reflex 组件库 100 例
其他图表库

Pyplot

reflex_pyplot.pyplot

官方文档

工坊订单

请把实验室里用的 matplotlib 绘图代码原样搬到网页上,选择产品时图随之切换。

pyplot 是在 Reflex 页面上显示 Matplotlib 图的组件,位于单独的 reflex-pyplot 包中。把用 matplotlib.pyplot 画出的 Figure 传进去,它就会在浏览器中绘制出来,不再需要 Flask 路由或把图片转成 base64 之类的工作。

本页的示例只展示代码。因为本站没有安装 matplotlib 和 reflex-pyplot。要在自己的应用里运行下面的代码,需要先安装这两个包(部分示例还需要 numpy)。

pyplot 是什么

matplotlib.pyplot 是一组让你像用 MATLAB 一样使用 Matplotlib 的函数。plt.plot、plt.scatter、plt.bar 这些调用会一项项往图里添加线条、柱子、文字和图例。在脚本里,最后用 plt.show() 弹出窗口;而在 Reflex 应用里,是把 Figure 传给 pyplot 组件,State 变化时就会重新绘制。

什么时候用 Matplotlib

如果 Jupyter 笔记本、研究脚本或数据管道里已经有 matplotlib 代码,就不必迁移到别的图表库,直接用在 Web 应用里。

  • 数据分析仪表盘:给笔记本原型加上控件后分享
  • 科学报告:包含 LaTeX 文字和精细样式的出版级图表
  • 机器学习监控:学习曲线、混淆矩阵、特征分布
  • 金融分析:时间序列和收益率图
  • 工程工具:仿真结果和传感器数据

柱形、折线、饼图这类常规业务图表更适合用 Reflex 自带的 Recharts 图表(rx.recharts);可缩放、可旋转的交互式图和 3D 图则更适合用 rx.plotly。

安装

安装 reflex-pyplot 时还需要 matplotlib。下面有几个示例还会用到 numpy。

pip install reflex-pyplot
# in a project that uses uv
uv add reflex-pyplot

基本用法

用 from reflex_pyplot import pyplot 导入,把图(Figure)作为第一个子元素传入。它在页面上以图片形式绘制,所以要一并设上 alt(替代文字)、loading、decoding 等图片属性以及 width、height。

import matplotlib.pyplot as plt
import numpy as np
import reflex as rx
from reflex_pyplot import pyplot


def create_contour_plot():
    X, Y = np.meshgrid(np.linspace(-3, 3, 256), np.linspace(-3, 3, 256))
    Z = (1 - X / 2 + X**5 + Y**3) * np.exp(-(X**2) - Y**2)
    levels = np.linspace(Z.min(), Z.max(), 7)

    fig, ax = plt.subplots()
    ax.contourf(X, Y, Z, levels=levels)
    plt.close(fig)
    return fig


def pyplot_simple_example():
    return rx.card(
        pyplot(
            create_contour_plot(),
            alt="Filled contour plot of a two-dimensional function",
            loading="lazy",
            decoding="async",
            width="100%",
            height="400px",
        ),
        bg_color="#ffffff",
        width="100%",
    )

画完图后一定要用 plt.close(fig) 关闭。不关闭的话,服务器会一直占着这张图,内存会不断增加。图的颜色由 Matplotlib 决定,所以为了在深色主题下也显示白色背景,外面包了一层 rx.card(bg_color="#ffffff")。

折线图

最常见的图。和写脚本时一样,用 plt.subplots() 和 ax.plot() 画好,再把图传给 pyplot。

import matplotlib.pyplot as plt
import numpy as np
import reflex as rx
from reflex_pyplot import pyplot


def create_line_plot():
    x = np.linspace(0, 10, 100)
    fig, ax = plt.subplots()
    ax.plot(x, np.sin(x), label="sin(x)")
    ax.plot(x, np.cos(x), label="cos(x)")
    ax.set_xlabel("x")
    ax.set_ylabel("y")
    ax.legend()
    plt.close(fig)
    return fig


def pyplot_line_example():
    return rx.card(
        pyplot(
            create_line_plot(),
            alt="Sine and cosine curves from zero to ten",
            loading="lazy",
            decoding="async",
            width="100%",
            height="400px",
        ),
        bg_color="#ffffff",
        width="100%",
    )

柱形图

除了给 ax.bar() 传入类别和数值之外,做法完全相同。

import matplotlib.pyplot as plt
import reflex as rx
from reflex_pyplot import pyplot


def create_bar_chart():
    fruits = ["apples", "oranges", "bananas", "pears"]
    counts = [23, 17, 35, 29]
    fig, ax = plt.subplots()
    ax.bar(fruits, counts, color="#4e79a7")
    ax.set_ylabel("count")
    ax.set_title("Fruit inventory")
    plt.close(fig)
    return fig


def pyplot_bar_example():
    return rx.card(
        pyplot(
            create_bar_chart(),
            alt="Fruit inventory: apples 23, oranges 17, bananas 35, pears 29",
            loading="lazy",
            decoding="async",
            width="100%",
            height="400px",
        ),
        bg_color="#ffffff",
        width="100%",
    )

结合 State

在随机打点的散点图上,加一个重新打乱的按钮和一个控制点数的滑块。图由 @rx.var 计算值生成,所以 State 值一变就会重新绘制。给事件设了 throttle=500,让它每 0.5 秒最多重绘一次。

Matplotlib 图的颜色不会跟随应用主题。所以浅色图和深色图都画一份,再用 rx.color_mode_cond 显示与当前模式相符的那张。

import random

import matplotlib.pyplot as plt
import numpy as np
import reflex as rx
from matplotlib.figure import Figure
from reflex_pyplot import pyplot


def create_plot(theme: str, plot_data: tuple, scale: list):
    bg_color, text_color = ("#1e1e1e", "white") if theme == "dark" else ("white", "black")
    grid_color = "#555555" if theme == "dark" else "#cccccc"

    fig, ax = plt.subplots(facecolor=bg_color)
    ax.set_facecolor(bg_color)

    for (x, y), color in zip(plot_data, ["#4e79a7", "#f28e2b"]):
        ax.scatter(x, y, c=color, s=scale, label=color, alpha=0.6, edgecolors="none")

    ax.legend(loc="upper right", facecolor=bg_color, edgecolor="none", labelcolor=text_color)
    ax.grid(True, color=grid_color)
    ax.tick_params(colors=text_color)
    for spine in ax.spines.values():
        spine.set_edgecolor(text_color)
    for item in [ax.xaxis.label, ax.yaxis.label, ax.title]:
        item.set_color(text_color)
    plt.close(fig)
    return fig


class PyplotState(rx.State):
    num_points: int = 25
    plot_data: tuple = tuple(np.random.rand(2, 25) for _ in range(2))
    scale: list = [random.uniform(0, 100) for _ in range(25)]

    @rx.event(temporal=True, throttle=500)
    def randomize(self):
        self.plot_data = tuple(np.random.rand(2, self.num_points) for _ in range(2))
        self.scale = [random.uniform(0, 100) for _ in range(self.num_points)]

    @rx.event(temporal=True, throttle=500)
    def set_num_points(self, num_points: list[int | float]):
        self.num_points = int(num_points[0])
        yield PyplotState.randomize()

    @rx.var
    def fig_light(self) -> Figure:
        return create_plot("light", self.plot_data, self.scale)

    @rx.var
    def fig_dark(self) -> Figure:
        return create_plot("dark", self.plot_data, self.scale)


def pyplot_example():
    return rx.vstack(
        rx.card(
            rx.color_mode_cond(
                pyplot(PyplotState.fig_light, alt="Scatter plot of the current randomized points", width="100%", height="100%"),
                pyplot(PyplotState.fig_dark, alt="Scatter plot of the current randomized points", width="100%", height="100%"),
            ),
            rx.hstack(
                rx.button("Randomize", on_click=PyplotState.randomize),
                rx.text("Number of Points:"),
                rx.slider(default_value=25, min=10, max=100, on_value_commit=PyplotState.set_num_points),
                width="100%",
            ),
            width="100%",
        ),
        justify_content="center",
        align_items="center",
        width="100%",
    )

官方文档示例里的滑块写的是 min_=10,但在 Reflex 0.10 的 rx.slider 中,这个名字不会被当成最小值,而是作为 CSS 样式传进去。上面的代码已改成 min=10。另外,这个示例把 numpy 数组存进了 State;在实际应用中,更稳妥的做法是在 State 里放列表这类简单的值,画图时再转成数组。

常见问题

怎样在网页上显示 Matplotlib 图?照常画图,然后把那个 Figure 传给 pyplot 组件即可。不需要 Flask、REST 路由或 base64 转换。

能让 Matplotlib 图变成可交互的吗?可以。在依赖 State 的 rx.var 里画图,再通过按钮、滑块等事件改变 State,图就会自动重绘(见上面的 State 示例)。

需要调用 plt.show() 吗?不需要。plt.show() 是弹出桌面窗口的函数,Web 应用里用不到。返回图对象,再用 plt.close(fig) 关闭即可。

API

pyplot 显示一张 Matplotlib 图。它没有单独定义的属性或事件,只接受所有组件都有的基础事件(on_click、on_mount 等)。

参数取值用途
第一个子元素matplotlib.figure.Figure 或返回它的 State 值要显示的图
alt · loading · decoding字符串图片替代文字、延迟加载、异步解码
width · heightCSS 尺寸图所占的尺寸

完成订单

State 里只放选中的产品名,由计算值画出该产品的柱形图。这段代码同样要在安装了 reflex-pyplot 和 matplotlib 的应用中运行。

import matplotlib.pyplot as plt
import reflex as rx
from matplotlib.figure import Figure
from reflex_pyplot import pyplot

MONTHS = ["Jan", "Feb", "Mar", "Apr", "May", "Jun"]
SALES = {"Chairs": [32, 41, 38, 52, 61, 58], "Tables": [12, 15, 21, 19, 24, 30]}


class PyplotReportState(rx.State):
    product: str = "Chairs"

    @rx.event
    def set_product(self, value: str):
        self.product = value

    @rx.var
    def figure(self) -> Figure:
        fig, ax = plt.subplots(figsize=(6, 3))
        ax.bar(MONTHS, SALES[self.product], color="#4e79a7")
        ax.set_title(f"{self.product} sales")
        ax.set_ylabel("units")
        fig.tight_layout()
        plt.close(fig)
        return fig


def pyplot_report():
    return rx.vstack(
        rx.select(["Chairs", "Tables"], value=PyplotReportState.product, on_change=PyplotReportState.set_product),
        rx.card(
            pyplot(PyplotReportState.figure, alt="Monthly sales of the selected product", width="100%"),
            bg_color="#ffffff",
            width="100%",
        ),
        width="100%",
    )

工坊笔记

  • pip install reflex-pyplot(需要 matplotlib)。from reflex_pyplot import pyplot。

  • 像 pyplot(fig, alt=…, width=…) 这样把 Figure 作为第一个子元素传入。不使用 plt.show()。

  • 画完图后一定要用 plt.close(fig) 关闭。

  • 让 @rx.var 计算值返回 Figure,State 变化时就会重新绘制。

  • 颜色不跟随主题,所以用 color_mode_cond 分别准备浅色图和深色图。

← 上一课

其他图表库 · Plotly

下一课 →

HTML 元素 · HTML

订阅新课时和新课程通知

本课程新增课时或推出后续课程时,我们会发邮件通知你。

收集项目:电子邮箱 · 用途:本课程的新课时和上线通知 · 保存期限:直到你要求删除。不会用于其他用途,也不会提供给他人。回复任意通知邮件,我们会立即删除。

问答

关于本课有任何疑问都可以在这里留言。所有语言版本页面的提问会汇集在一起。

以纯文本显示,不支持链接和格式。

R

ReflexKR

动手学 Python 和 Reflex。所有示例均已在 Reflex 0.10.0 上实际运行验证。

ReflexKR 免费,没有横幅广告。如果对你有帮助,欢迎请我们喝杯咖啡。 ☕ 请我们喝杯咖啡

联盟链接与赞助说明
한국어English日本語简体中文EspañolDeutsch

© 2026 ReflexKR · Since 2026 · CC BY-NC 4.0

Built with Reflex