圆弧与曲线¶
本节覆盖圆弧家族(Arc、扇形、圆环)、贝塞尔曲线与曲线箭头。所有圆弧都继承 TipableVMobject,因此也能像直线一样挂箭头尖。
Arc¶
Arc(radius=1.0, start_angle=0, angle=1.5707963267948966, num_components=9, arc_center=array([0., 0., 0.]), **kwargs) 官方文档 ↗
Arc 是按圆心、半径与角度生成的一段圆弧,是所有圆弧图形的基石。
name |
type |
default |
desc |
|---|---|---|---|
|
float | None |
1.0 |
半径;None 时由其它参数决定 |
|
float |
0 |
起始角(弧度) |
|
float |
PI / 2 |
圆弧张角(弧度) |
|
int |
9 |
组成圆弧的贝塞尔曲线段数 |
|
Point3DLike |
[0, 0, 0] |
圆心位置 |
Arc(radius=2, start_angle=PI / 6, angle=PI * 2 / 3)
常见坑:arc_center 只在构造时生效;之后 move_to / shift 改变的是包围盒位置,get_arc_center() 仍是几何圆心——以圆心为基准做动画时用 arc.get_arc_center() 而不是 ORIGIN。
ArcBetweenPoints¶
ArcBetweenPoints(start, end, angle=1.5707963267948966, radius=None, **kwargs) 官方文档 ↗
ArcBetweenPoints 生成经过指定起点、终点的圆弧,弯曲程度由圆心角 angle 或 radius 控制。
name |
type |
default |
desc |
|---|---|---|---|
|
Point3DLike |
— |
起点 |
|
Point3DLike |
— |
终点 |
|
float |
PI / 2 |
圆心角;决定弯曲程度 |
|
float | None |
None |
半径;传入时优先于 angle 计算圆心 |
常见坑:当 start 与 end 距离固定时,angle 越大弧越“鼓”;angle=PI 恰好是半圆,更大的角会让圆心跑到起终点连线的另一侧。
AnnularSector¶
AnnularSector(inner_radius=1, outer_radius=2, angle=1.5707963267948966, start_angle=0, fill_opacity=1, stroke_width=0, color=ManimColor('#FFFFFF'), **kwargs) 官方文档 ↗
AnnularSector(环形扇区)是内外两个同心圆弧夹出的填充区域,Sector 是它的特例(内半径为 0)。
name |
type |
default |
desc |
|---|---|---|---|
|
float |
1 |
内半径 |
|
float |
2 |
外半径 |
|
float |
PI / 2 |
张角(弧度) |
|
float |
0 |
起始角 |
|
float |
1 |
填充不透明度 |
|
float |
0 |
描边宽度(默认不描边) |
Sector¶
Sector(radius=1, **kwargs) 官方文档 ↗
Sector 是从圆心切出的实心扇形,继承 AnnularSector(inner_radius=0)。
name |
type |
default |
desc |
|---|---|---|---|
|
float |
1 |
扇形半径 |
|
float |
PI / 2 |
张角(弧度),经 kwargs 传入 |
|
float |
0 |
起始角,经 kwargs 传入 |
Sector(radius=2, angle=PI / 3, start_angle=PI / 6)
Annulus¶
Annulus(inner_radius=1, outer_radius=2, fill_opacity=1, stroke_width=0, color=ManimColor('#FFFFFF'), mark_paths_closed=False, **kwargs) 官方文档 ↗
Annulus(圆环)是两个同心圆之间的区域,继承 Circle。
name |
type |
default |
desc |
|---|---|---|---|
|
float |
1 |
内半径 |
|
float |
2 |
外半径 |
|
float |
1 |
填充不透明度 |
|
float |
0 |
描边宽度 |
|
bool |
False |
是否把路径标记为闭合 |
常见坑:Annulus 的填充区域依赖 fill_opacity,默认描边为 0,直接 Create 会看到“空心圆盘外框”而不是圆环——记得保留填充或加描边。
AnnotationDot¶
AnnotationDot(radius=0.10400000000000001, stroke_width=5, stroke_color=ManimColor('#FFFFFF'), fill_color=ManimColor('#58C4DD'), **kwargs) 官方文档 ↗
AnnotationDot 是 3Blue1Brown 风格的注释圆点:青色填充、白色粗描边,继承 Dot。
name |
type |
default |
desc |
|---|---|---|---|
|
float |
0.104 |
圆点半径 |
|
float |
5 |
白色描边宽度 |
|
ParsableManimColor |
WHITE |
描边颜色 |
|
ParsableManimColor |
#58C4DD |
填充颜色(品牌青) |
CubicBezier¶
CubicBezier(start_anchor, start_handle, end_handle, end_anchor, **kwargs) 官方文档 ↗
CubicBezier 用四个控制点生成一段三次贝塞尔曲线:起点锚点、起点手柄、终点手柄、终点锚点。
name |
type |
default |
desc |
|---|---|---|---|
|
Point3DLike |
— |
曲线起点 |
|
Point3DLike |
— |
起点方向手柄 |
|
Point3DLike |
— |
终点方向手柄 |
|
Point3DLike |
— |
曲线终点 |
CubicBezier(LEFT * 2, LEFT * 2 + UP, RIGHT * 2 + DOWN, RIGHT * 2)
常见坑:手柄离锚点越远曲线越“拗”;多段平滑曲线请用多段 CubicBezier 或 VMobject 的 start_new_path,不要把多段硬拼成一个 CubicBezier。
CurvedArrow¶
CurvedArrow(start_point, end_point, **kwargs) 官方文档 ↗
CurvedArrow 是带箭头尖的 ArcBetweenPoints,箭头画在终点切线方向上。
name |
type |
default |
desc |
|---|---|---|---|
|
Point3DLike |
— |
起点 |
|
Point3DLike |
— |
终点 |
|
float |
PI / 2 |
圆心角(kwargs) |
|
type[ArrowTip] |
ArrowTriangleFilledTip |
箭头尖形状 |
Arc、Sector、AnnularSector、Annulus 同框;下方是 CubicBezier 与 CurvedArrow / CurvedDoubleArrow。曲线箭头用 Create 入场,因为 GrowArrow 依赖 scale_tips,对圆弧系不适用。
查看源码 arcs_showcase.py
"""ArcsShowcase: Arc / ArcBetweenPoints / Sector / AnnularSector / Annulus / CubicBezier / CurvedArrow / CurvedDoubleArrow."""
from manim import *
class ArcsShowcase(Scene):
def construct(self):
arc = Arc(radius=1.2, start_angle=PI / 6, angle=PI * 0.75, color=BLUE)
sector = Sector(radius=1.0, angle=PI / 3, color=GREEN).shift(LEFT * 3.5 + DOWN * 0.5)
annular = AnnularSector(inner_radius=0.6, outer_radius=1.1, angle=PI * 0.9, color=YELLOW)
annular.shift(RIGHT * 3.5 + DOWN * 0.5)
annulus = Annulus(inner_radius=0.5, outer_radius=0.9, color=RED).shift(RIGHT * 0.2 + UP * 0.3)
self.play(Create(arc), Create(sector), Create(annular), FadeIn(annulus))
bez = CubicBezier(
LEFT * 5 + DOWN * 2.5,
LEFT * 3.5 + DOWN * 0.5,
LEFT * 2 + DOWN * 3.5,
LEFT * 0.5 + DOWN * 2,
color=PURPLE,
)
curved = CurvedArrow(ORIGIN + DOWN * 2.5, RIGHT * 2.5 + DOWN * 2.5, color=ORANGE)
dcurved = CurvedDoubleArrow(RIGHT * 3 + DOWN * 3, RIGHT * 5.5 + DOWN * 1.5, color=PINK)
self.play(Create(bez), Create(curved), Create(dcurved))
self.wait(1)
CurvedDoubleArrow¶
CurvedDoubleArrow(start_point, end_point, **kwargs) 官方文档 ↗
两端都带箭头尖的曲线箭头,继承 CurvedArrow。
name |
type |
default |
desc |
|---|---|---|---|
|
type[ArrowTip] |
ArrowTriangleFilledTip |
起点箭头尖 |
|
type[ArrowTip] |
ArrowTriangleFilledTip |
终点箭头尖 |
TipableVMobject¶
TipableVMobject(tip_length=0.35, normal_vector=array([0., 0., 1.]), tip_style=None, **kwargs) 官方文档 ↗
TipableVMobject 是 Line 与 Arc 共同的基类,提供“可挂箭头尖”的机制:tip_length、normal_vector、tip_style 三个构造参数与 add_tip()、get_tip() 等方法。CurvedArrow 就是在 ArcBetweenPoints 构造后调用 self.add_tip() 实现的。
name |
type |
default |
desc |
|---|---|---|---|
|
float |
0.35 |
箭头尖默认长度 |
|
Vector3DLike |
[0, 0, 1] |
箭头尖法向量(决定朝向) |
|
dict | None |
None |
箭头尖默认样式字典 |
arc = Arc(angle=PI, tip_style={"fill_opacity": 0.5})
arc.add_tip(tip_shape=StealthTip, tip_length=0.5)
常见错误与建议¶
常见错误
圆弧族的 angle 一律是弧度。传角度制数值(如 90)会得到绕很多圈的乱弧;用 90 * DEGREES 转换。
提示
num_components 控制圆弧的贝zier 分段数:需要让圆弧与直线 Transform 时提高分段数能让变形更平滑,代价是略慢的构造速度。
自测¶
✏️ 练习
画一段从 LEFT*2 到 RIGHT*2、向上鼓起的半圆弧,并把箭头尖装在起点(朝左)。
✅ 参考答案
半圆对应圆心角 PI;箭头尖装在起点用 add_tip(at_start=True):
arc = ArcBetweenPoints(LEFT * 2, RIGHT * 2, angle=PI)
arc.add_tip(at_start=True)
下一步¶
有了基础图形,下一节介绍如何用布尔运算(并、交、差、异或)组合出复杂的填充形状。