`Code` mobject does not support ligatures
Description of bug / unexpected behavior
I'm working with Code mobject. I was getting started with this https://docs.manim.community/en/stable/reference/manim.mobject.text.code_mobject.Code.html#codefromstring and I found this.
When I add line print("Hello World"), it works fine. But when I add print(1<2) or print("Hello World", 1<2), an error occur.
I'm not sure it happened with other language or not.
from manim import *
class CodeFromString(Scene):
def construct(self):
code = """from manim import Scene, Square
class FadeInSquare(Scene):
def construct(self):
print(1<=2)
s = Square()
self.play(FadeIn(s))
self.play(s.animate.scale(2))
self.wait()
"""
rendered_code = Code(
code=code,
tab_width=4,
background="window",
language="Python",
font="FiraCode Nerd Font",
)
self.play(Create(rendered_code))
Logs
IndexError: list index out of range
And btw, what would be nice if you teach me how to apply fontLigasture when render
I found out that error occur cause manim is not support well for fontLigatures, and code above has <= in code string
Hey, I stumbled over the same issue. At a closer look it seems like this happens in the Text class.
Minimal example:
Using:
-
manim 0.17.3 -
ManimPango 0.4.3 - Fira Code or another font supporting ligatures
from manim import *
Text("==", font="Fira Code", disable_ligatures=True)
Traceback (most recent call last):
File "../bug.py", line 3, in <module>
Text("==", font="Fira Code", disable_ligatures=True)
File "../lib/python3.10/site-packages/manim/mobject/text/text_mobject.py", line 500, in __init__
self.submobjects = [*self._gen_chars()]
File "../lib/python3.10/site-packages/manim/mobject/text/text_mobject.py", line 601, in _gen_chars
chars.add(self.submobjects[submobjects_char_index])
IndexError: list index out of range
This IndexError is caused by a mismatch between the text length and the number of subobjects of the Text which are created from a corresponding svg file.
The underlying issue seems to be in the text2svg conversion. https://github.com/ManimCommunity/ManimPango/blob/main/manimpango/cmanimpango.pyx#L30. Even though manimpango.text2svg is called with disable_liga=True the created svg file is showing ligatures. In fact, setting the flag does not seem to affect the resulting svg at all.
Example text2svg conversion
import manimpango
import pathlib
manimpango.text2svg(
settings=[
manimpango.TextSetting(
color="red",
end=2,
font="Fira Code",
line_num=0,
slant="NORMAL",
start=0,
weight="NORMAL",
)
],
size=10,
line_spacing=13,
disable_liga=True,
file_name=str(pathlib.Path("media/texts/liga_disabled.svg").resolve()),
START_X=30,
START_Y=20,
width=1920,
height=1080,
orig_text="==",
)
manimpango.text2svg(
settings=[
manimpango.TextSetting(
color="red",
end=2,
font="Fira Code",
line_num=0,
slant="NORMAL",
start=0,
weight="NORMAL",
)
],
size=10,
line_spacing=13,
disable_liga=False,
file_name=str(pathlib.Path("media/texts/liga_enabled.svg").resolve()),
START_X=30,
START_Y=20,
width=1920,
height=1080,
orig_text="==",
)
Both create equivalent svgs which use ligatures:
liga_disabled.svg
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="1920pt" height="1080pt" viewBox="0 0 1920 1080" version="1.1">
<defs>
<g>
<symbol overflow="visible" id="glyph0-0">
<path style="stroke:none;" d="M 0.546875 -10.109375 L 7.65625 -10.109375 L 7.65625 0.703125 L 0.546875 0.703125 Z M 6.921875 0 L 6.921875 -9.390625 L 1.296875 -9.390625 L 1.296875 0 Z M 4.203125 -3.53125 C 4.203125 -3.425781 4.164062 -3.34375 4.09375 -3.28125 C 4.019531 -3.226562 3.941406 -3.203125 3.859375 -3.203125 C 3.765625 -3.203125 3.679688 -3.226562 3.609375 -3.28125 C 3.546875 -3.34375 3.515625 -3.425781 3.515625 -3.53125 L 3.515625 -4.671875 C 4.003906 -4.703125 4.332031 -4.796875 4.5 -4.953125 C 4.664062 -5.109375 4.75 -5.367188 4.75 -5.734375 C 4.75 -5.992188 4.695312 -6.210938 4.59375 -6.390625 C 4.488281 -6.578125 4.265625 -6.671875 3.921875 -6.671875 C 3.785156 -6.671875 3.660156 -6.65625 3.546875 -6.625 C 3.441406 -6.601562 3.332031 -6.566406 3.21875 -6.515625 C 3.144531 -6.492188 3.082031 -6.484375 3.03125 -6.484375 C 2.9375 -6.484375 2.859375 -6.515625 2.796875 -6.578125 C 2.734375 -6.640625 2.703125 -6.710938 2.703125 -6.796875 C 2.703125 -6.921875 2.769531 -7.019531 2.90625 -7.09375 C 3.050781 -7.175781 3.222656 -7.234375 3.421875 -7.265625 C 3.617188 -7.304688 3.804688 -7.328125 3.984375 -7.328125 C 4.367188 -7.328125 4.671875 -7.253906 4.890625 -7.109375 C 5.117188 -6.960938 5.273438 -6.769531 5.359375 -6.53125 C 5.453125 -6.289062 5.5 -6.03125 5.5 -5.75 C 5.5 -5.269531 5.394531 -4.898438 5.1875 -4.640625 C 4.988281 -4.378906 4.660156 -4.210938 4.203125 -4.140625 Z M 3.375 -2.328125 C 3.375 -2.460938 3.421875 -2.570312 3.515625 -2.65625 C 3.609375 -2.75 3.722656 -2.796875 3.859375 -2.796875 C 3.992188 -2.796875 4.101562 -2.75 4.1875 -2.65625 C 4.28125 -2.570312 4.328125 -2.460938 4.328125 -2.328125 C 4.328125 -2.179688 4.28125 -2.054688 4.1875 -1.953125 C 4.101562 -1.859375 3.992188 -1.8125 3.859375 -1.8125 C 3.722656 -1.8125 3.609375 -1.859375 3.515625 -1.953125 C 3.421875 -2.054688 3.375 -2.179688 3.375 -2.328125 Z M 3.375 -2.328125 "/>
</symbol>
<symbol overflow="visible" id="glyph0-1">
<path style="stroke:none;" d=""/>
</symbol>
<symbol overflow="visible" id="glyph0-2">
<path style="stroke:none;" d="M 6.765625 -6.046875 L 6.765625 -5.046875 L -6.765625 -5.046875 L -6.765625 -6.046875 Z M 6.765625 -3.453125 L 6.765625 -2.453125 L -6.765625 -2.453125 L -6.765625 -3.453125 Z M 6.765625 -3.453125 "/>
</symbol>
</g>
</defs>
<g id="surface1">
<g style="fill:rgb(100%,0%,0%);fill-opacity:1;">
<use xlink:href="#glyph0-1" x="30" y="32.307617"/>
<use xlink:href="#glyph0-2" x="38" y="32.307617"/>
</g>
</g>
</svg>
liga_enabled.svg
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="1920pt" height="1080pt" viewBox="0 0 1920 1080" version="1.1">
<defs>
<g>
<symbol overflow="visible" id="glyph0-0">
<path style="stroke:none;" d="M 0.546875 -10.109375 L 7.65625 -10.109375 L 7.65625 0.703125 L 0.546875 0.703125 Z M 6.921875 0 L 6.921875 -9.390625 L 1.296875 -9.390625 L 1.296875 0 Z M 4.203125 -3.53125 C 4.203125 -3.425781 4.164062 -3.34375 4.09375 -3.28125 C 4.019531 -3.226562 3.941406 -3.203125 3.859375 -3.203125 C 3.765625 -3.203125 3.679688 -3.226562 3.609375 -3.28125 C 3.546875 -3.34375 3.515625 -3.425781 3.515625 -3.53125 L 3.515625 -4.671875 C 4.003906 -4.703125 4.332031 -4.796875 4.5 -4.953125 C 4.664062 -5.109375 4.75 -5.367188 4.75 -5.734375 C 4.75 -5.992188 4.695312 -6.210938 4.59375 -6.390625 C 4.488281 -6.578125 4.265625 -6.671875 3.921875 -6.671875 C 3.785156 -6.671875 3.660156 -6.65625 3.546875 -6.625 C 3.441406 -6.601562 3.332031 -6.566406 3.21875 -6.515625 C 3.144531 -6.492188 3.082031 -6.484375 3.03125 -6.484375 C 2.9375 -6.484375 2.859375 -6.515625 2.796875 -6.578125 C 2.734375 -6.640625 2.703125 -6.710938 2.703125 -6.796875 C 2.703125 -6.921875 2.769531 -7.019531 2.90625 -7.09375 C 3.050781 -7.175781 3.222656 -7.234375 3.421875 -7.265625 C 3.617188 -7.304688 3.804688 -7.328125 3.984375 -7.328125 C 4.367188 -7.328125 4.671875 -7.253906 4.890625 -7.109375 C 5.117188 -6.960938 5.273438 -6.769531 5.359375 -6.53125 C 5.453125 -6.289062 5.5 -6.03125 5.5 -5.75 C 5.5 -5.269531 5.394531 -4.898438 5.1875 -4.640625 C 4.988281 -4.378906 4.660156 -4.210938 4.203125 -4.140625 Z M 3.375 -2.328125 C 3.375 -2.460938 3.421875 -2.570312 3.515625 -2.65625 C 3.609375 -2.75 3.722656 -2.796875 3.859375 -2.796875 C 3.992188 -2.796875 4.101562 -2.75 4.1875 -2.65625 C 4.28125 -2.570312 4.328125 -2.460938 4.328125 -2.328125 C 4.328125 -2.179688 4.28125 -2.054688 4.1875 -1.953125 C 4.101562 -1.859375 3.992188 -1.8125 3.859375 -1.8125 C 3.722656 -1.8125 3.609375 -1.859375 3.515625 -1.953125 C 3.421875 -2.054688 3.375 -2.179688 3.375 -2.328125 Z M 3.375 -2.328125 "/>
</symbol>
<symbol overflow="visible" id="glyph0-1">
<path style="stroke:none;" d=""/>
</symbol>
<symbol overflow="visible" id="glyph0-2">
<path style="stroke:none;" d="M 6.765625 -6.046875 L 6.765625 -5.046875 L -6.765625 -5.046875 L -6.765625 -6.046875 Z M 6.765625 -3.453125 L 6.765625 -2.453125 L -6.765625 -2.453125 L -6.765625 -3.453125 Z M 6.765625 -3.453125 "/>
</symbol>
</g>
</defs>
<g id="surface6">
<g style="fill:rgb(100%,0%,0%);fill-opacity:1;">
<use xlink:href="#glyph0-1" x="30" y="32.307617"/>
<use xlink:href="#glyph0-2" x="38" y="32.307617"/>
</g>
</g>
</svg>