Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow accessing ghost vectors in :class:.LinearTransformationScene #3435

Merged
merged 12 commits into from
Nov 19, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 15 additions & 3 deletions manim/scene/vector_space_scene.py
Original file line number Diff line number Diff line change
Expand Up @@ -572,7 +572,7 @@ def __init__(self, **kwargs):
self,
show_coordinates=True,
leave_ghost_vectors=True,
*kwargs
**kwargs
)

def construct(self):
Expand Down Expand Up @@ -616,6 +616,8 @@ def __init__(
},
}

self.ghost_vectors = VGroup()

self.foreground_plane_kwargs = {
"x_range": np.array([-config["frame_width"], config["frame_width"], 1.0]),
"y_range": np.array([-config["frame_width"], config["frame_width"], 1.0]),
Expand Down Expand Up @@ -741,6 +743,13 @@ def add_moving_mobject(
mobject.target = target_mobject
self.add_special_mobjects(self.moving_mobjects, mobject)

def get_ghost_vectors(self) -> VGroup:
"""
Returns all ghost vectors ever added to ``self``. Each element is a ``VGroup`` of
two ghost vectors.
"""
return self.ghost_vectors

def get_unit_square(
self, color: str = YELLOW, opacity: float = 0.3, stroke_width: float = 3
):
Expand Down Expand Up @@ -996,8 +1005,11 @@ def get_piece_movement(self, pieces: list | tuple | np.ndarray):
"""
start = VGroup(*pieces)
target = VGroup(*(mob.target for mob in pieces))
if self.leave_ghost_vectors:
self.add(start.copy().fade(0.7))
# don't add empty VGroups
if self.leave_ghost_vectors and start.submobjects:
# start.copy() gives a VGroup of Vectors
self.ghost_vectors.add(start.copy().fade(0.7))
self.add(self.ghost_vectors[-1])
return Transform(start, target, lag_ratio=0)

def get_moving_mobject_movement(self, func: Callable[[np.ndarray], np.ndarray]):
Expand Down
24 changes: 24 additions & 0 deletions tests/test_linear_transformation_scene.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
from manim import RIGHT, UP, LinearTransformationScene, Vector, VGroup

__module_test__ = "vector_space_scene"


def test_ghost_vectors_len_and_types():
scene = LinearTransformationScene()
scene.leave_ghost_vectors = True

# prepare vectors (they require a vmobject as their target)
v1, v2 = Vector(RIGHT), Vector(RIGHT)
v1.target, v2.target = Vector(UP), Vector(UP)

# ghost_vector addition is in this method
scene.get_piece_movement((v1, v2))

ghosts = scene.get_ghost_vectors()
assert len(ghosts) == 1
# check if there are two vectors in the ghost vector VGroup
assert len(ghosts[0]) == 2

# check types of ghost vectors
assert isinstance(ghosts, VGroup) and isinstance(ghosts[0], VGroup)
assert all(isinstance(x, Vector) for x in ghosts[0])