Skip to content

Instantly share code, notes, and snippets.

@uwezi
Last active July 29, 2024 16:27
Show Gist options
  • Save uwezi/bbcdac3eff9583b41d3519a900a2a7db to your computer and use it in GitHub Desktop.
Save uwezi/bbcdac3eff9583b41d3519a900a2a7db to your computer and use it in GitHub Desktop.
[blocks and roller] Showing two blocks on the slopes of a triangle. #manim #geometry #physics
# https://www.reddit.com/r/manim/comments/1b0mkad/help_making_an_animation_for_a_physics_explainer/
class blocks(Scene):
def construct(self):
height = 5
tri = Polygon(
[-height*np.tan(30*DEGREES),-3,0],
[height*np.tan(60*DEGREES),-3,0],
[0,height-3,0]
)
tri.shift(-tri.get_center()[0]*RIGHT)
self.add(tri)
shift = ValueTracker(0)
left_block = Rectangle(
width=1,
height=1,
)
left_block.shift(tri.get_vertices()[0]-left_block.get_critical_point(DL))
left_block.rotate(60*DEGREES, about_point=tri.get_vertices()[0])
def left_block_updater(mobj):
mobj.shift(
tri.get_vertices()[0]
+shift.get_value()*np.array([np.cos(60*DEGREES),np.sin(60*DEGREES),0])
-mobj.get_vertices()[2]
)
left_block.add_updater(left_block_updater, call_updater=True)
right_block = Rectangle(
width=2,
height=1,
)
right_block.shift(tri.get_vertices()[2]-right_block.get_critical_point(DL))
right_block.rotate(-30*DEGREES, about_point=tri.get_vertices()[2])
def right_block_updater(mobj):
mobj.shift(
tri.get_vertices()[2]
+shift.get_value()*np.array([np.cos(30*DEGREES),-np.sin(30*DEGREES),0])
-mobj.get_vertices()[2]
)
right_block.add_updater(right_block_updater, call_updater=True)
roler_dist = 0.35 # from apex
roler_axis = tri.get_vertices()[2]+roler_dist*np.array([-np.sin(15*DEGREES),np.cos(15*DEGREES),0])
roler_radius = 0.5-roler_dist/np.sqrt(2)
roler = always_redraw(lambda:
VGroup(
Circle(radius=roler_radius).shift(roler_axis),
*[Line(roler_axis, roler_axis+roler_radius*RIGHT).rotate(2*PI/5*i-shift.get_value()/(PI*roler_radius), about_point=roler_axis) for i in range(5)]
).set_color(RED)
)
rope_left = always_redraw(lambda:
Line(
roler[0].point_at_angle(150*DEGREES),
0.5*(left_block.get_vertices()[3]+left_block.get_vertices()[0]),
color=YELLOW
)
)
rope_right = always_redraw(lambda:
Line(
roler[0].point_at_angle(60*DEGREES),
0.5*(right_block.get_vertices()[1]+right_block.get_vertices()[2]),
color=YELLOW
)
)
rope_on_roler = Arc(
radius=roler_radius,
start_angle=60*DEGREES,
angle=90*DEGREES,
color=YELLOW
).shift(roler_axis)
self.add(left_block, right_block, roler, rope_left, rope_right, rope_on_roler)
self.play(shift.animate.set_value(4), run_time=4, rate_func=rate_functions.linear)
self.play(shift.animate.set_value(0), run_time=4, rate_func=rate_functions.there_and_back)
self.wait()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment