ErisPulse-Takumi
ErisPulse-Takumi は ccd2s が維持する サードパーティの画像レンダリングモジュール です。takumi-py をベースに、Bot が HTML、ノードツリー、Jinja テンプレート、SVG、アニメーションを画像にレンダリングできるようにします。モジュールには 中英文字体(Noto Sans SC / Roboto / Source Code Pro)が内蔵されており、追加の設定は不要です。
Important
Takumi は ErisPulse フレームワークの組み込み機能ではなく、個別にインストールする必要があります:
epsdk install Takumi
利用シーン:
- データや統計情報をカード画像にレンダリングする
- Markdown / 長文をレイアウトが安定した画像にレンダリングし、プラットフォームのスタイル差異を回避する
- SVG / アニメーションを生成して、動的な視覚効果を実現する
- 中英混排の图文(内蔵フォントで即座に使用可能)
インストールと有効化
epsdk install Takumi
インストール後、モジュールは自動的に読み込まれます。設定ファイルで有効化を確認してください:
[Takumi]
enabled = true
快速上手
モジュールが自動的にロードされた後、モジュールマネージャーから取得するか、sdk のショートカットを使用します。
from ErisPulse import sdk
takumi = sdk.module.get("Takumi")
# 等価な書き方: takumi = sdk.Takumi
HTML のレンダリング
png = takumi.render_html(
"""
<div class="card">
<h1>你好,ErisPulse</h1>
<p>由 Takumi 渲染</p>
</div>
""",
stylesheets=["""
.card {
width: 800px;
padding: 48px;
color: white;
background: #111827;
font-family: "Noto Sans SC";
}
"""],
width=800,
height=None, # 内容に応じて高さを自動調整
lang="zh-CN",
)
ノードツリーのレンダリング
png = takumi.render_node(
{
"type": "text",
"text": "中文和 English 都可直接渲染",
"style": {"fontSize": 48, "color": "#111827"},
},
width=800,
height=None,
lang="zh-CN",
)
png は bytes であり、event.reply(png, method="Image") を使用して送信できます(詳細は レンダリング結果の送信 を参照してください)。
レンダリング API
sdk.Takumi は、下層の takumi_py.Renderer のすべての機能をラップしています。すべてのレンダリング、測定、SVG、アニメーション、テンプレートメソッドは、sdk.Takumi で直接呼び出すことができます。これらのメソッドに対して、モジュールは呼び出し時に自動的に組み込みのフォントフォールバックスタック(takumi.families)を注入します。font_families を手動で渡す必要はありません。明示的に渡した場合は、呼び出し元の設定を尊重します。
メソッド一覧
| カテゴリ | メソッド | 戻り値 | 説明 |
|---|---|---|---|
| 静的レンダリング | render_html(html, ...) |
bytes |
HTML文字列をレンダリング |
render_node(node, ...) |
bytes |
ノードツリー(dict)をレンダリング | |
render_template(name, ctx, ...) |
bytes |
Jinjaテンプレートをレンダリング | |
render_compiled(node, ...) |
bytes |
事前コンパイルされたノードをレンダリング | |
| SVG出力 | render_svg_html(html, ...) |
str |
SVGを出力(HTML入力) |
render_svg_node(node, ...) |
str |
SVGを出力(ノードツリー入力) | |
render_svg_template(name, ctx, ...) |
str |
SVGを出力(テンプレート入力) | |
render_svg_compiled(node, ...) |
str |
SVGを出力(事前コンパイル入力) | |
| アニメーション | render_animation(scenes, ...) |
bytes |
複数フレームアニメーションをエンコード |
render_sequence_at_time(scenes, time_ms, ...) |
bytes |
シーケンスの特定時間のフレームを取得 | |
| 測定 | measure_node(node, ...) |
dict |
ノードツリーのレイアウトを測定 |
measure_html(html, ...) |
dict |
HTMLのレイアウトを測定 | |
measure_compiled(node, ...) |
dict |
事前コンパイルされたノードを測定 | |
| コンパイル | compile_node(node) |
CompiledNode |
ノードツリーをコンパイル |
compile_html(html, ...) |
CompiledNode |
HTMLをコンパイル | |
| フォント | register_font(font) |
list[str] |
自定義フォントを登録し、familyリストを返す |
register_fonts(fonts) |
list[str] |
フォントを一括登録 |
CompiledNodeはresource_urls()メソッドを公開しており、HTTP(S) 画像参照を事前に検出できるため、リソースの事前準備が可能です。
一般的パラメータ
以下のパラメータは、静的レンダリングおよびSVGメソッドに適用されます(アニメーションメソッドには fps などがあります。対応する例を参照してください):
| パラメータ | 型 | デフォルト値 | 説明 |
|---|---|---|---|
stylesheets |
list[str] |
None |
ドキュメントレベルのCSS文字列リスト。インラインの style はHTMLとともに解析されます |
width |
int | None |
1200 |
ビューポートの幅(ピクセル)。None の場合はレイアウトに基づいて推定されます |
height |
int | None |
630 |
画布の高さ(ピクセル)。None の場合は内容に応じて自動的に高さが設定されます(ビューポートと出力形式を参照) |
lang |
str | None |
None |
BCP-47言語タグ(例:zh-CN)。テキスト整形と改行に影響します |
font_families |
list[str] |
自動注入 | フォントフォールバックスタック。便利なメソッドでは組み込みフォントが自動的に注入されます |
format |
str |
"png" |
出力形式(ビューポートと出力形式を参照) |
device_pixel_ratio |
float |
1.0 |
デバイスピクセル比。出力解像度を制御します |
time_ms |
int |
0 |
アニメーションのサンプリング時刻(ミリ秒) |
dithering |
str |
"none" |
ドイジングアルゴリズム:none / ordered-bayer / floyd-steinberg |
quality |
int | None |
None |
有損圧縮の品質 |
lossless |
bool | None |
None |
無損圧縮を行うかどうか |
images |
list |
None |
今回のレンダリングに使用する画像リソース(ImageResource または (src, bytes) タプル) |
keyframes |
Mapping |
None |
構造化されたキーフレーム。@keyframes に記述する必要はありません |
options |
RenderOptions |
— | RenderOptions(...) でパラメータをまとめて渡す。上表のフィールドと一致します |
完全なフィールド定義は takumi_py.RenderOptions を参照してください。
ノードツリーの例
png = takumi.render_node(
{
"type": "container",
"style": {"padding": "32px", "backgroundColor": "#111827"},
"children": [
{"type": "text", "text": "タイトル", "style": {"fontSize": 32, "color": "white"}},
{"type": "text", "text": "本文", "style": {"fontSize": 18, "color": "#9ca3af"}},
],
},
width=800,
height=None,
lang="zh-CN",
)
Jinjaテンプレートの例
png = takumi.render_template(
"card.html.jinja",
{"title": "Takumi", "subtitle": "Jinja to image"},
stylesheets=["""
.card {
width: 800px;
padding: 48px;
color: white;
background: #111827;
}
"""],
width=800,
height=None,
lang="zh-CN",
)
filters={...}を使用してカスタムJinjaフィルターを注入したり、environment=...で完全なjinja2.Environmentを渡すことができます。テンプレートディレクトリと環境設定は、takumi-pyのテンプレートドキュメントを参照してください。
SVG出力の例
svg = takumi.render_svg_html(
'<div class="card">Hello</div>',
stylesheets=[".card { width: 800px; color: black; }"],
width=800,
height=None,
)
アニメーションの例
from takumi_py import AnimationScene
webp = takumi.render_animation(
[
AnimationScene(
{"type": "container", "style": {"width": "100%", "height": "100%", "backgroundColor": "black"}},
duration_ms=100,
),
AnimationScene(
{"type": "container", "style": {"width": "100%", "height": "100%", "backgroundColor": "white"}},
duration_ms=100,
),
],
width=64,
height=64,
fps=20,
format="webp",
)
各フレームは
AnimationScene(node, duration_ms=...)で構成され、duration_msは正数でなければなりません。
ビューポートと出力形式
出力形式
| 場合 | format の値 |
|---|---|
| 静的画像 | png(デフォルト) / jpeg / jpg / webp / ico / raw |
| アニメーション | webp(デフォルト) / apng / gif |
format="raw" は、行優先の RGBA バイトストリームを返し、ピクセル単位でのカスタム処理に使用します。
width と height について
width と height の役割は非対称です:
widthはビューポートの幅であり、テキストとレイアウトはこれに基づいて改行や再レイアウトを行います。具体的な数値(例:800)で固定する必要があります。そうでないと、画布は内容の自然な幅に引き伸ばされ、テキストが改行せず、サイズが制御不能になります。heightは画布の高さで、内容に応じて伸びます。heightのデフォルト値は630です。height=Noneを渡すと、Takumi は内容に応じて画布の高さを自動的に伸ばします(自動ビューポート)。
Tip
**推奨の組み合わせ:width を固定 + height=None**。固定サイズの画布や切り抜き効果が必要な場合にのみ、具体的な height を渡してください。
Note
width / height のいずれかは技術的に None を渡すことで、レイアウトに応じて推定させることも可能です(例:ノードが自身でサイズを宣言している場合)。両方とも渡した場合、出力サイズは確定値になります。
フォント
内蔵フォント
| フォント | family | カテゴリ |
|---|---|---|
| Noto Sans SC | Noto Sans SC |
sans-serif |
| Roboto | Roboto |
sans-serif |
| Roboto Italic | Roboto |
sans-serif(italic) |
| Source Code Pro | Source Code Pro |
monospace |
| Source Code Pro Italic | Source Code Pro |
monospace(italic) |
モジュール属性:
| 属性 | 说明 |
|---|---|
takumi.fonts |
内蔵フォントのファイル名リスト |
takumi.families |
登録済みのフォント family リスト |
自動注入
sdk.Takumi のすべての描画、測定、SVG、アニメーション、テンプレートメソッドは、takumi.families をフォントのフォールバックスタックとして自動的に注入します。直接 takumi.renderer(元のインスタンス)を呼び出す場合、または create_renderer() で作成された独立したインスタンスを使用する場合は、font_families=takumi.families を手動で渡す必要があります。
自定義フォント
from takumi_py import FontResource
families = takumi.renderer.register_font(
FontResource(
font_bytes,
name="MyFont",
weight=400,
style="normal",
generic_family="sans-serif",
)
)
register_font は登録された family 名のリストを返し、後続の描画時に font_families として渡すことができます。
レンダラーアン instance
ネイティブレンダラー
takumi.renderer は、元の takumi_py.Renderer インスタンスです。直接呼び出す場合は、font_families を手動で渡す必要があります:
png = takumi.renderer.render_html(
"<div>你好</div>",
font_families=takumi.families,
lang="zh-CN",
)
独立レンダラー
フォント / 画像 / リソースのキャッシュを分離する必要がある場合(長寿命のプロセス、マルチテナント環境など)、独立した Renderer を作成できます。この場合、内蔵フォントは自動的に登録されます:
renderer = takumi.create_renderer(cache_max_bytes=64 * 1024 * 1024)
png = renderer.render_html(
"<div>独立 Renderer</div>",
font_families=takumi.families,
width=800,
height=None,
lang="zh-CN",
)
create_renderer() は takumi_py.Renderer のコンストラクター引数を受け取ります:
| 引数 | 型 | デフォルト値 | 説明 |
|---|---|---|---|
load_default_fonts |
bool |
False |
takumi-py に付属するフォントをロードするかどうか(内蔵フォントは常にロードされます) |
fonts |
list[FontResource] |
None |
追加で登録するカスタムフォント |
cache_max_bytes |
int | None |
None |
リソースキャッシュの上限(バイト);0 で無効化 |
persistent_images |
list |
None |
永続化する画像リソース |
独立インスタンスはモジュールのプロキシを経由しないため、統一された内蔵フォントのフォールバックスタックを保持するには、
font_families=takumi.familiesを明示的に渡す必要があります。font_familiesを明示的に渡した場合、モジュールは呼び出し元の設定を尊重し、デフォルトのフォールバックスタックを挿入しません。RenderOptions(font_families=...)でも同様です。
レンダリング結果の送信
レンダリングされた画像は bytes 形式で取得でき、イベントの返信として直接送信することができます。
from ErisPulse import sdk
takumi = sdk.Takumi
png = takumi.render_html("<div>hello</div>", lang="zh-CN")
# 方法1:Imageメソッドで返信
await event.reply(png, method="Image")
# 方法2:OneBot12メッセージセグメントで返信
from ErisPulse.Core.Event import MessageBuilder
await event.reply_ob12(
MessageBuilder().image(png).build()
)
画像の異なるプラットフォームへのラッピングはアダプターによって統一的に処理されます。詳しくは MessageBuilderの詳細 および 送信メソッドの規格 を参照してください。
設定
[Takumi]
enabled = true