def construct(self): title = TextMobject("(A few) Fathers of Calculus") title.to_edge(UP) self.add(title) men = Mobject() for name in self.names: image = ImageMobject(name, invert=False) image.scale_to_fit_height(self.picture_height) title = TextMobject(name) title.scale(0.8) title.next_to(image, DOWN) image.add(title) men.add(image) men.arrange_submobjects(RIGHT, aligned_edge=UP) men.shift(DOWN) discover_brace = Brace(Mobject(*men[:3]), UP) discover = discover_brace.get_text("Discovered it") VGroup(discover_brace, discover).highlight(BLUE) rigor_brace = Brace(Mobject(*men[3:]), UP) rigor = rigor_brace.get_text("Made it rigorous") rigor.shift(0.1 * DOWN) VGroup(rigor_brace, rigor).highlight(YELLOW) for man in men: self.play(FadeIn(man)) self.play(GrowFromCenter(discover_brace), Write(discover, run_time=1)) self.play(GrowFromCenter(rigor_brace), Write(rigor, run_time=1)) self.dither()
def construct(self): words = TextMobject("Order 2 Pseudo-Hilbert Curve") words.to_edge(UP, buff=0.3) words.highlight(GREEN) grid2 = Grid(2, 2) grid4 = Grid(4, 4, point_thickness=2) # order_1_curve = HilbertCurve(order = 1) # squaggle_curve = order_1_curve.copy().apply_function( # lambda (x, y, z) : (x + np.cos(3*y), y + np.sin(3*x), z) # ) # squaggle_curve.show() mini_curves = [ HilbertCurve(order=1).scale(0.5).shift(1.5 * vect) for vect in [LEFT + DOWN, LEFT + UP, RIGHT + UP, RIGHT + DOWN] ] last_curve = mini_curves[0] naive_curve = Mobject(last_curve) for mini_curve in mini_curves[1:]: line = Line(last_curve.points[-1], mini_curve.points[0]) naive_curve.add(line, mini_curve) last_curve = mini_curve naive_curve.ingest_sub_mobjects() naive_curve.gradient_highlight(RED, GREEN) order_2_curve = HilbertCurve(order=2) self.add(words, grid2) self.dither() self.play(ShowCreation(grid4)) self.play(*[ShowCreation(mini_curve) for mini_curve in mini_curves]) self.dither() self.play(ShowCreation(naive_curve, run_time=5)) self.remove(*mini_curves) self.dither() self.play(Transform(naive_curve, order_2_curve)) self.dither()
def construct(self, order): start_color, end_color = RED, GREEN curve = HilbertCurve(order = order) line = Line(5*LEFT, 5*RIGHT) for mob in curve, line: mob.gradient_highlight(start_color, end_color) freq_line = get_freq_line() freq_line.replace(line, stretch = True) unit = 6./(2**order) #sidelength of pixel up = unit*UP right = unit*RIGHT lower_left = 3*(LEFT+DOWN) squares = Mobject(*[ Square( side_length = unit, color = WHITE ).shift(x*right+y*up) for x, y in it.product(range(2**order), range(2**order)) ]) squares.center() targets = Mobject() for square in squares.submobjects: center = square.get_center() distances = np.apply_along_axis( lambda p : np.linalg.norm(p-center), 1, curve.points ) index_along_curve = np.argmin(distances) fraction_along_curve = index_along_curve/float(curve.get_num_points()) target = square.copy().center().scale(0.8/(2**order)) line_index = int(fraction_along_curve*line.get_num_points()) target.shift(line.points[line_index]) targets.add(target) self.add(squares) self.play(ShowCreation( curve, run_time = 5, rate_func = None )) self.dither() self.play( Transform(curve, line), Transform(squares, targets), run_time = 3 ) self.dither() self.play(ShowCreation(freq_line)) self.dither()
def construct(self): words = TextMobject("Order 2 Pseudo-Hilbert Curve") words.to_edge(UP, buff = 0.3) words.highlight(GREEN) grid2 = Grid(2, 2) grid4 = Grid(4, 4, stroke_width = 2) # order_1_curve = HilbertCurve(order = 1) # squaggle_curve = order_1_curve.copy().apply_function( # lambda (x, y, z) : (x + np.cos(3*y), y + np.sin(3*x), z) # ) # squaggle_curve.show() mini_curves = [ HilbertCurve(order = 1).scale(0.5).shift(1.5*vect) for vect in [ LEFT+DOWN, LEFT+UP, RIGHT+UP, RIGHT+DOWN ] ] last_curve = mini_curves[0] naive_curve = Mobject(last_curve) for mini_curve in mini_curves[1:]: line = Line(last_curve.points[-1], mini_curve.points[0]) naive_curve.add(line, mini_curve) last_curve = mini_curve naive_curve.ingest_submobjects() naive_curve.gradient_highlight(RED, GREEN) order_2_curve = HilbertCurve(order = 2) self.add(words, grid2) self.dither() self.play(ShowCreation(grid4)) self.play(*[ ShowCreation(mini_curve) for mini_curve in mini_curves ]) self.dither() self.play(ShowCreation(naive_curve, run_time = 5)) self.remove(*mini_curves) self.dither() self.play(Transform(naive_curve, order_2_curve)) self.dither()
def construct(self): self.remove(self.get_primary_pi_creature()) NUM_CONES = 7 NUM_VISIBLE_CONES = 6 INDICATOR_RADIUS = 0.5 OPACITY_FOR_UNIT_INTENSITY = 1.0 self.number_line = NumberLine( x_min=0, color=WHITE, number_at_center=1.6, stroke_width=1, numbers_with_elongated_ticks=range(1, 5), numbers_to_show=range(1, 5), unit_size=2, tick_frequency=0.2, line_to_number_buff=LARGE_BUFF, label_direction=UP, ) self.number_line.label_direction = DOWN #self.number_line.shift(3*UP) self.number_line_labels = self.number_line.get_number_mobjects() self.add(self.number_line, self.number_line_labels) self.wait() origin_point = self.number_line.number_to_point(0) self.default_pi_creature_class = Randolph randy = self.get_primary_pi_creature() randy.scale(0.5) randy.flip() right_pupil = randy.pupils[1] randy.next_to(origin_point, LEFT, buff=0, submobject_to_align=right_pupil) randy_copy = randy.copy() randy_copy.target = randy.copy().shift(DOWN) bubble = ThoughtBubble(direction=RIGHT, width=4, height=3, file_name="Bubbles_thought.svg") bubble.next_to(randy, LEFT + UP) bubble.set_fill(color=BLACK, opacity=1) self.play( randy.change, "wave_2", ShowCreation(bubble), ) euler_sum = TexMobject("1", "+", "{1\over 4}", "+", "{1\over 9}", "+", "{1\over 16}", "+", "{1\over 25}", "+", "\cdots", " ") # the last entry is a dummy element which makes looping easier # used just for putting the fractions into the light indicators intensities = np.array([1. / (n + 1)**2 for n in range(NUM_CONES)]) opacities = intensities * OPACITY_FOR_UNIT_INTENSITY # repeat: # fade in lighthouse # switch on / fade in ambient light # show creation / write light indicator # move indicator onto origin # while morphing and dimming # move indicator into thought bubble # while indicators already inside shift to the back # and while term appears in the series below point = self.number_line.number_to_point(1) v = point - self.number_line.number_to_point(0) light_source = LightSource() light_source.move_source_to(point) #light_source.ambient_light.move_source_to(point) #light_source.lighthouse.move_to(point) self.play(FadeIn(light_source.lighthouse)) self.play(SwitchOn(light_source.ambient_light)) # create an indicator that will move along the number line indicator = LightIndicator( color=LIGHT_COLOR, radius=INDICATOR_RADIUS, opacity_for_unit_intensity=OPACITY_FOR_UNIT_INTENSITY, show_reading=False) indicator_reading = euler_sum[0] indicator_reading.scale_to_fit_height(0.5 * indicator.get_height()) indicator_reading.move_to(indicator.get_center()) indicator.add(indicator_reading) indicator.tex_reading = indicator_reading # the TeX reading is too bright at full intensity indicator.tex_reading.set_fill(color=BLACK) indicator.foreground.set_fill(None, opacities[0]) indicator.move_to(point) indicator.set_intensity(intensities[0]) self.play(FadeIn(indicator)) self.add_foreground_mobject(indicator) collection_point = np.array([-6., 2., 0.]) left_shift = 0.2 * LEFT collected_indicators = Mobject() for i in range(2, NUM_VISIBLE_CONES + 1): previous_point = self.number_line.number_to_point(i - 1) point = self.number_line.number_to_point(i) v = point - previous_point #print v # Create and position the target indicator (next on number line). indicator_target = indicator.deepcopy() indicator_target.shift(v) # Here we make a copy that will move into the thought bubble. bubble_indicator = indicator.deepcopy() # And its target bubble_indicator_target = bubble_indicator.deepcopy() bubble_indicator_target.set_intensity(intensities[i - 2]) # give the target the appropriate reading euler_sum[2 * i - 4].move_to(bubble_indicator_target) bubble_indicator_target.remove(bubble_indicator_target.tex_reading) bubble_indicator_target.tex_reading = euler_sum[2 * i - 4].copy() bubble_indicator_target.add(bubble_indicator_target.tex_reading) # center it in the indicator if bubble_indicator_target.tex_reading.get_tex_string() != "1": bubble_indicator_target.tex_reading.scale_to_fit_height( 0.8 * indicator.get_height()) # the target is less bright, possibly switch to a white text color if bubble_indicator_target.intensity < 0.7: bubble_indicator.tex_reading.set_fill(color=WHITE) # position the target in the thought bubble bubble_indicator_target.move_to(collection_point) self.add_foreground_mobject(bubble_indicator) self.wait() self.play( Transform(bubble_indicator, bubble_indicator_target), collected_indicators.shift, left_shift, ) collected_indicators.add(bubble_indicator) new_light = light_source.deepcopy() w = new_light.get_source_point() new_light.move_source_to(w + (i - 2) * v) w2 = new_light.get_source_point() self.add(new_light.lighthouse) self.play( Transform(indicator, indicator_target), new_light.lighthouse.shift, v, ) new_light.move_source_to(w + (i - 1) * v) new_light.lighthouse.move_to(w + (i - 1) * v) self.play(SwitchOn(new_light.ambient_light), ) # quickly switch on off-screen light cones for i in range(NUM_VISIBLE_CONES, NUM_CONES): indicator_start_time = 0.5 * ( i + 1 ) * FAST_SWITCH_ON_RUN_TIME / light_source.ambient_light.radius * self.number_line.unit_size indicator_stop_time = indicator_start_time + FAST_INDICATOR_UPDATE_TIME indicator_rate_func = squish_rate_func( #smooth, 0.8, 0.9) smooth, indicator_start_time, indicator_stop_time) ls = LightSource() point = point = self.number_line.number_to_point(i) ls.move_source_to(point) self.play( SwitchOn(ls.ambient_light, run_time=FAST_SWITCH_ON_RUN_TIME), ) # and morph indicator stack into limit value sum_indicator = LightIndicator( color=LIGHT_COLOR, radius=INDICATOR_RADIUS, opacity_for_unit_intensity=OPACITY_FOR_UNIT_INTENSITY, show_reading=False) sum_indicator.set_intensity(intensities[0] * np.pi**2 / 6) sum_indicator_reading = TexMobject("{\pi^2 \over 6}") sum_indicator_reading.set_fill(color=BLACK) sum_indicator_reading.scale_to_fit_height(0.8 * sum_indicator.get_height()) sum_indicator.add(sum_indicator_reading) sum_indicator.move_to(collection_point) self.play(Transform(collected_indicators, sum_indicator)) self.wait()
def construct(self): glass = Region(lambda x, y : y < 0, color = BLUE_E) self.generate_start_and_end_points() left = self.start_point[0]*RIGHT right = self.end_point[0]*RIGHT start_x = interpolate(left, right, 0.2) end_x = interpolate(left, right, 1.0) left_line = Line(self.start_point, left, color = RED_D) right_line = Line(self.end_point, right, color = RED_D) h_1, h_2 = map(TexMobject, ["h_1", "h_2"]) h_1.next_to(left_line, LEFT) h_2.next_to(right_line, RIGHT) point_a = Dot(self.start_point) point_b = Dot(self.end_point) A = TextMobject("A").next_to(point_a, UP) B = TextMobject("B").next_to(point_b, DOWN) x = start_x left_brace = Brace(Mobject(Point(left), Point(x))) right_brace = Brace(Mobject(Point(x), Point(right)), UP) x_mob = TexMobject("x") x_mob.next_to(left_brace, DOWN) w_minus_x = TexMobject("w-x") w_minus_x.next_to(right_brace, UP) top_line = Line(self.start_point, x) bottom_line = Line(x, self.end_point) top_dist = TexMobject("\\sqrt{h_1^2+x^2}") top_dist.scale(0.5) a = 0.3 n = top_line.get_num_points() point = top_line.points[int(a*n)] top_dist.next_to(Point(point), RIGHT, buff = 0.3) bottom_dist = TexMobject("\\sqrt{h_2^2+(w-x)^2}") bottom_dist.scale(0.5) n = bottom_line.get_num_points() point = bottom_line.points[int((1-a)*n)] bottom_dist.next_to(Point(point), LEFT, buff = 1) end_top_line = Line(self.start_point, end_x) end_bottom_line = Line(end_x, self.end_point) end_brace = Brace(Mobject(Point(left), Point(end_x))) end_x_mob = TexMobject("x").next_to(end_brace, DOWN) axes = Mobject( NumberLine(), NumberLine().rotate(np.pi/2).shift(7*LEFT) ) graph = FunctionGraph( lambda x : 0.4*(x+1)*(x-3)+4, x_min = -2, x_max = 4 ) graph.highlight(YELLOW) Mobject(axes, graph).scale(0.2).to_corner(UP+RIGHT, buff = 1) axes.add(TexMobject("x", size = "\\small").next_to(axes, RIGHT)) axes.add(TextMobject("Travel time", size = "\\small").next_to( axes, UP )) new_graph = graph.copy() midpoint = new_graph.points[new_graph.get_num_points()/2] new_graph.filter_out(lambda p : p[0] < midpoint[0]) new_graph.reverse_points() pairs_for_end_transform = [ (mob, mob.copy()) for mob in top_line, bottom_line, left_brace, x_mob ] self.add(glass, point_a, point_b, A, B) line = Mobject(top_line, bottom_line).ingest_submobjects() self.play(ShowCreation(line)) self.wait() self.play( GrowFromCenter(left_brace), GrowFromCenter(x_mob) ) self.play( GrowFromCenter(right_brace), GrowFromCenter(w_minus_x) ) self.play(ShowCreation(left_line), ShimmerIn(h_1)) self.play(ShowCreation(right_line), GrowFromCenter(h_2)) self.play(ShimmerIn(top_dist)) self.play(GrowFromCenter(bottom_dist)) self.wait(3) self.clear() self.add(glass, point_a, point_b, A, B, top_line, bottom_line, left_brace, x_mob) self.play(ShowCreation(axes)) kwargs = { "run_time" : 4, } self.play(*[ Transform(*pair, **kwargs) for pair in [ (top_line, end_top_line), (bottom_line, end_bottom_line), (left_brace, end_brace), (x_mob, end_x_mob) ] ]+[ShowCreation(graph, **kwargs)]) self.wait() self.show_derivatives(graph) line = self.show_derivatives(new_graph) self.add(line) self.play(*[ Transform(*pair, rate_func = lambda x : 0.3*smooth(x)) for pair in pairs_for_end_transform ]) self.wait()
def construct(self): glass = Region(lambda x, y : y < 0, color = BLUE_E) self.generate_start_and_end_points() left = self.start_point[0]*RIGHT right = self.end_point[0]*RIGHT start_x = interpolate(left, right, 0.2) end_x = interpolate(left, right, 1.0) left_line = Line(self.start_point, left, color = RED_D) right_line = Line(self.end_point, right, color = RED_D) h_1, h_2 = map(TexMobject, ["h_1", "h_2"]) h_1.next_to(left_line, LEFT) h_2.next_to(right_line, RIGHT) point_a = Dot(self.start_point) point_b = Dot(self.end_point) A = TextMobject("A").next_to(point_a, UP) B = TextMobject("B").next_to(point_b, DOWN) x = start_x left_brace = Brace(Mobject(Point(left), Point(x))) right_brace = Brace(Mobject(Point(x), Point(right)), UP) x_mob = TexMobject("x") x_mob.next_to(left_brace, DOWN) w_minus_x = TexMobject("w-x") w_minus_x.next_to(right_brace, UP) top_line = Line(self.start_point, x) bottom_line = Line(x, self.end_point) top_dist = TexMobject("\\sqrt{h_1^2+x^2}") top_dist.scale(0.5) a = 0.3 n = top_line.get_num_points() point = top_line.points[int(a*n)] top_dist.next_to(Point(point), RIGHT, buff = 0.3) bottom_dist = TexMobject("\\sqrt{h_2^2+(w-x)^2}") bottom_dist.scale(0.5) n = bottom_line.get_num_points() point = bottom_line.points[int((1-a)*n)] bottom_dist.next_to(Point(point), LEFT, buff = 1) end_top_line = Line(self.start_point, end_x) end_bottom_line = Line(end_x, self.end_point) end_brace = Brace(Mobject(Point(left), Point(end_x))) end_x_mob = TexMobject("x").next_to(end_brace, DOWN) axes = Mobject( NumberLine(), NumberLine().rotate(np.pi/2).shift(7*LEFT) ) graph = FunctionGraph( lambda x : 0.4*(x+1)*(x-3)+4, x_min = -2, x_max = 4 ) graph.highlight(YELLOW) Mobject(axes, graph).scale(0.2).to_corner(UP+RIGHT, buff = 1) axes.add(TexMobject("x", size = "\\small").next_to(axes, RIGHT)) axes.add(TextMobject("Travel time", size = "\\small").next_to( axes, UP )) new_graph = graph.copy() midpoint = new_graph.points[new_graph.get_num_points()/2] new_graph.filter_out(lambda p : p[0] < midpoint[0]) new_graph.reverse_points() pairs_for_end_transform = [ (mob, mob.copy()) for mob in top_line, bottom_line, left_brace, x_mob ] self.add(glass, point_a, point_b, A, B) line = Mobject(top_line, bottom_line).ingest_submobjects() self.play(ShowCreation(line)) self.dither() self.play( GrowFromCenter(left_brace), GrowFromCenter(x_mob) ) self.play( GrowFromCenter(right_brace), GrowFromCenter(w_minus_x) ) self.play(ShowCreation(left_line), ShimmerIn(h_1)) self.play(ShowCreation(right_line), GrowFromCenter(h_2)) self.play(ShimmerIn(top_dist)) self.play(GrowFromCenter(bottom_dist)) self.dither(3) self.clear() self.add(glass, point_a, point_b, A, B, top_line, bottom_line, left_brace, x_mob) self.play(ShowCreation(axes)) kwargs = { "run_time" : 4, } self.play(*[ Transform(*pair, **kwargs) for pair in [ (top_line, end_top_line), (bottom_line, end_bottom_line), (left_brace, end_brace), (x_mob, end_x_mob) ] ]+[ShowCreation(graph, **kwargs)]) self.dither() self.show_derivatives(graph) line = self.show_derivatives(new_graph) self.add(line) self.play(*[ Transform(*pair, rate_func = lambda x : 0.3*smooth(x)) for pair in pairs_for_end_transform ]) self.dither()