Search code examples
manim

Color MObject with inner arc


I am using manim community where I created an MObject by using Line and ArcBetweenPoints. When I try to fill the MObject, the object is colored between by the start and end point of the larger arc. Is there a way to color this MObject correctly?

Please take a look at the code below to visualize the problem. By uncommenting the line with 'set_fill' you see how the object is filled incorrectly.

%%manim -qm -v WARNING MobjectExample
    g1 = [-1.5, 0, 0]
    g2 = [0, -1.5, 0]
    g3 = [1.5, 0, 0]
    g7 = [0.5, 0, 0]
    g8 = [0, -0.5, 0]
    g9 = [-0.5, 0, 0]
    
    class MobjectExample(Scene):
        def construct(self):
            g = ArcBetweenPoints(start=g1, end=g2, stroke_color=BLUE) \
                .append_points(ArcBetweenPoints(start=g2, end=g3).points) \
                .append_points(ArcBetweenPoints(start=g8, end=g7).points) \
                .append_points(ArcBetweenPoints(start=g9, end=g8).points)\
                .append_points(Line(g1, g9).points)\
                .append_points(Line(g3, g7).points)
            # Please uncomment the next line to color the object
            # g.set_fill(BLUE, opacity=1)
            self.play(Create(g))
            self.wait(2)
     

Solution

  • The way you are using append_points has a weird effect on the mobject, in the sense that not one continuous path is drawn, but multiple ones that form some sort of group. You can fix this by using append_vectorized_mobject instead, which takes care of correctly merging different paths together. And: when you concatenate mobject points like that you have to make sure that the points actually describe a continuous path; the endpoint of the n-th subpath has to be the start point of the (n+1)-th.

    Try this:

    class MobjectExample(Scene):
        def construct(self):
            g = ArcBetweenPoints(start=g1, end=g2, stroke_color=BLUE)
            g.append_vectorized_mobject(ArcBetweenPoints(start=g2, end=g3))
            g.append_vectorized_mobject(Line(g3, g7))
            g.append_vectorized_mobject(ArcBetweenPoints(start=g7, end=g8, angle=-TAU/4))
            g.append_vectorized_mobject(ArcBetweenPoints(start=g8, end=g9, angle=-TAU/4))
            g.append_vectorized_mobject(Line(g9, g1))
            g.set_fill(BLUE, opacity=1)
            self.play(Create(g))
            self.wait(2)