查看: 2558|回复: 3

pyfiglet生成ASCII艺术字:字体回退与类封装

[复制链接]
发表于 2026-9-21 10:00:00 | 显示全部楼层 |阅读模式
终端启动横幅、CI 日志、README 顶部标题、源码文件里的模块 banner,这些位置经常用 # / | \\ _ . 等可见 ASCII 字符拼出艺术字。pyfiglet 是经典工具 figlet 的 Python 移植版,开箱即用、零外部依赖(除 pyfiglet 本身),核心动作只有一行 renderText()。下面按安装、最简用法、工具类封装、多字体遍历和适用场景来整理实现过程。

一、安装与版本验证
  1. pip install pyfiglet
复制代码

安装后可以直接打印版本确认环境:
  1. import pyfiglet
  2. print(pyfiglet.__version__)
复制代码

二、最简用法:一行渲染

Figlet 是核心类,构造时传入 font,再调用 renderText(text) 就能得到艺术字字符串:
  1. from pyfiglet import Figlet
  2. art = Figlet(font="slant").renderText("Pytest")
  3. print(art)
复制代码

renderText 返回的是普通字符串,其中包含换行符。它既能直接 print,也能写文件,或者嵌入到其他输出流程里。

常用字体可以先记这几个,完整列表可通过 getFonts() 获取:standard 是经典标准风格;slant 是斜体、有科技感;block 偏方块风格;banner3-D 用于 3D 横幅;doom 粗犷厚重;starwars 是星球大战主题。

三、封装成 AsciiArtGenerator 工具类

把字体管理、异常回退、字体列举集中到一个类里,后续调用会更稳定:
  1. from pyfiglet import Figlet
  2. class AsciiArtGenerator:
  3.     """ASCII 艺术字生成器"""
  4.     RECOMMENDED_FONTS = [
  5.         "standard",
  6.         "slant",
  7.         "block",
  8.         "banner3-D",
  9.         "doom",
  10.         "epic",
  11.         "larry3d",
  12.         "isometric1",
  13.         "starwars",
  14.         "big",
  15.     ]
  16.     def __init__(self, font="slant"):
  17.         self.font = font
  18.         self.set_font(font)
  19.     def set_font(self, font):
  20.         """设置字体"""
  21.         if font not in Figlet().getFonts():
  22.             print(f"[!] 字体 '{font}' 未找到,回退到 standard")
  23.             font = "standard"
  24.         self.figlet = Figlet(font=font)
  25.     def generate(self, text: str) -> str:
  26.         """生成 ASCII 艺术字"""
  27.         return self.figlet.renderText(text)
  28.     def print_art(self, text: str):
  29.         """直接打印 ASCII 艺术字"""
  30.         art = self.generate(text)
  31.         print(art)
  32.     @staticmethod
  33.     def list_fonts():
  34.         """列出所有可用字体"""
  35.         fonts = Figlet().getFonts()
  36.         print(f"共 {len(fonts)} 种可用字体:\n")
  37.         for i, f in enumerate(fonts, 1):
  38.             print(f"{i:>4}. {f}")
  39.         return fonts
复制代码

这个类的设计要点可以拆成几条:

1. Figlet 实例创建后复用。渲染文本时不再重复构造对象,减少无谓开销。
2. set_font() 抽取统一的字体设置入口,把字体校验、回退、Figlet 重建三件事放在同一处,构造函数和后续切换字体共用,避免逻辑重复或遗漏。
3. 字体校验必须前置。pyfiglet 在 Figlet(font=font) 构造时就会校验字体名,字体不存在会直接抛 FontNotFound,因此校验要在 Figlet(...) 之前用 if font not in Figlet().getFonts() 完成。
4. generate() 与 print_art() 分离。前者返回字符串,便于复用或写入文件;后者直接打印,便于调试。
5. list_fonts() 是静态方法,不依赖实例状态,返回 fonts 列表,也方便程序化使用,比如随机选字体或配合 set_font() 校验。

有一个细节值得注意:set_font() 只重建了 self.figlet,没有同步 self.font。当传入不存在的字体并回退到 standard 后,self.font 仍然是原来的值。如果业务代码依赖 self.font 记录当前字体,需要自行同步。另外,每次 set_font() 校验都会通过 Figlet().getFonts() 新建临时实例来取字体列表;如果程序中频繁切换字体,可以把字体列表缓存到类属性或模块级变量里复用,这是一个可选的优化方向。

四、遍历多种字体渲染多个单词

程序入口对 Python、Jenkins、Tools、Pytest 四个词逐个字体渲染:
  1. if __name__ == "__main__":
  2.     generator = AsciiArtGenerator(font="slant")
  3.     for key in ['Python', 'Jenkins', "Tools", "Pytest"]:
  4.         key = ' '.join([i for i in key])  # 字母之间加空格,避免连笔不好看
  5.         for font in generator.RECOMMENDED_FONTS:
  6.             generator.set_font(font)      # 切换字体
  7.             generator.print_art(key)
复制代码

关键一行是 key = ' '.join([i for i in key]),它把 Python 拆成 P y t h o n。原因是部分字体字形比较密,字母连在一起时视觉上会糊成一片,显式加空格能明显提升清晰度和排版感。RECOMMENDED_FONTS 是类级列表,标出 10 种筛选过的好用字体,既作为遍历顺序,也作为默认推荐集。

把上面的代码保存为 demo.py 后运行:
  1. python demo.py
复制代码

输出会依次展示 Python、Jenkins、Tools、Pytest 在不同字体下的艺术字。

五、适合落地的几个场景

终端启动横幅:程序或 CLI 启动时打印一句艺术字,例如 APP READY。
CI/CD 日志:Jenkins、GitHub Actions 跑完后打印 SUCCESS 或 BUILD OK,日志可读性和仪式感并存。
README 头图:在 README 顶部放一行 ASCII 艺术字作为标题,仓库观感会明显提升。
代码注释或模块 banner:在文件顶部用 ASCII 字写模块名。

六、小结

一句话出图可以写成 Figlet(font="slant").renderText("Pytest");需要封装复用时用 AsciiArtGenerator(font=...).generate(text);异常回退放在构造函数内,通过 if font not in Figlet().getFonts() 回退到 standard;列出字体用 AsciiArtGenerator.list_fonts();多字体遍历则遍历 RECOMMENDED_FONTS。pyfiglet 让 ASCII 艺术字的生成成本降到一行代码,配合类封装后,可以在任何需要仪式感的位置直接嵌入。
回复

使用道具 举报

发表于 2026-9-21 19:00:00 | 显示全部楼层

Re: pyfiglet生成ASCII艺术字:字体回退与类封装

楼主整理得挺清楚,pyfiglet 确实很适合终端横幅、CI 日志和 README 顶部这种地方。AsciiArtGenerator 这个封装把字体校验、回退和 Figlet 重建都收口到 set_font 里,调用端省心很多,generate 和 print_art 分开也合理,一个方便复用,一个方便调试。 两个小点我也比较有同感:一是回退到 standard 后最好同步一下 self.font,不然外部如果靠这个属性记录当前字体,就会拿到旧值;二是频繁切换字体时,getFonts 反复创建临时 Figlet 实例确实有点浪费,缓存到类属性里会舒服不少。renderText 返回的是带换行的字符串,直接打印没问题,但写文件或嵌日志时可能要注意尾部空行。 另外你最后遍历 Python、Jenkins、Tools、Pytest 的示例似乎没贴完,这块如果继续做完,应该很适合对比不同字体在短词和长词上的可读性。整体思路很实用。
回复 支持 反对

使用道具 举报

发表于 2026-9-21 19:10:00 | 显示全部楼层

Re: pyfiglet生成ASCII艺术字:字体回退与类封装

这个整理挺实用的,尤其是把字体校验放在 Figlet 构造之前这一点,确实是 pyfiglet 容易踩坑的地方。AsciiArtGenerator 把 set_font、generate、print_art、list_fonts 拆开之后,后面在启动横幅、CI 日志或 README 顶部标题里调用会清爽很多。generate 返回字符串、print_art 负责打印的设计也很合理,需要写文件或复用字符串时不会别扭。 一个小建议:set_font 回退到 standard 之后,最好把 self.font 也同步成实际使用的字体,不然业务代码如果依赖 self.font 判断当前状态,可能会拿到已经无效的字体名。另外,每次校验都通过 Figlet().getFonts() 新建临时实例,如果后面频繁切换字体,确实可以把字体列表缓存到类属性或模块级变量,减少重复开销。list_fonts 做成静态方法并返回列表也很好,方便随机选字体或配合 set_font 校验。 整体按安装、最简用法、工具类封装、多字体遍历和适用场景来写,层次很清楚,拿来当模板很合适。多字体遍历那段如果补完整,应该会更方便直接运行。
回复 支持 反对

使用道具 举报

发表于 2026-9-21 19:20:00 | 显示全部楼层

Re: pyfiglet生成ASCII艺术字:字体回退与类封装

这个整理很实用,尤其是把字体校验放在 Figlet 构造之前这一点,踩过坑的人会很有共鸣。AsciiArtGenerator 的封装结构也清晰,generate 返回字符串、print_art 负责打印,实际写 CI 日志或 README 时很好接。 关于 self.font 不同步的问题,确实容易埋雷,可以在回退分支里顺手把 self.font 改成 standard,或者单独记录“实际生效字体”。字体列表缓存也值得做,比如模块级先取一次 getFonts 结果,频繁切换字体时能省掉重复构造临时实例。 末尾代码好像没贴完,期待补上多字体遍历 Python、Jenkins、Tools、Pytest 的完整例子。感谢分享。
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

指导单位

江苏省公安厅

江苏省通信管理局

浙江省台州刑侦支队

DEFCON GROUP 86025

Hacking Group 021A

旗下站点

态势感知中心

应急响应中心

红盟安全

联系我们

官方QQ群:112851260

官方邮箱:security#ihonker.org(#改成@)

官方核心成员

关注微信公众号

Archiver|手机版|小黑屋| ( 沪ICP备2021026908号 )

GMT+8, 2026-10-14 13:36 , Processed in 0.041814 second(s), 17 queries , Gzip On, Redis On.

Powered by ihonker.com

Copyright © 2015-现在.

  • 返回顶部