ReportLab (python)を使用して PDF にグラデーション塗りつぶしを作成することは可能ですか?
3 に答える
ReportLab は PDF グラデーションをサポートするようになりました。
勾配サポートのパッチは、 2012 年 8 月 6 日に Peter Johnson によってReportLab メーリング リストに投稿され、翌日ソースに追加されました。ReportLab 2.6 のリリース ノートには何も見つかりませんが、2012 年 10 月 1 日にリリースされたので、そこにあると思われます。それは間違いなく2.7に存在します。
複数のストップを持つ線形グラデーションと放射状グラデーションの両方を指定できます。ドキュメントでグラデーションという用語を検索しても、何も見つかりません。ただし、パッチの最初のバージョンのメッセージには、ReportLab ソースのいくつかのテストの基礎となる例がいくつか含まれています。これに基づいて、簡単なデモ スクリプトを作成しました。
from reportlab.pdfgen.canvas import Canvas
from reportlab.lib.colors import red, yellow, green
from reportlab.lib.units import mm
c = Canvas("gradient.pdf")
# Linear gradient with the endpoints extending over the page.
c.linearGradient(105*mm, 200*mm, 180*mm, 100*mm, (red, yellow))
c.drawString(5*mm, 290*mm, "c.linearGradient(105*mm, 200*mm, 180*mm, 100*mm, (red, yellow))")
c.line(105*mm, 200*mm, 180*mm, 100*mm)
c.showPage()
# Linear gradient constrained within the endpoints.
c.linearGradient(105*mm, 200*mm, 180*mm, 100*mm, (red, yellow), extend=False)
c.drawString(5*mm, 290*mm, "c.linearGradient(105*mm, 200*mm, 180*mm, 100*mm, (red, yellow), extend=False)")
c.line(105*mm, 200*mm, 180*mm, 100*mm)
c.showPage()
# Linear gradient with multiple stops.
c.linearGradient(105*mm, 200*mm, 180*mm, 100*mm, (red, yellow, green), (0, 0.8, 1), extend=False)
c.drawString(5*mm, 290*mm, "c.linearGradient(105*mm, 200*mm, 180*mm, 100*mm, (red, yellow, green), (0, 0.8, 1), extend=False)")
c.line(105*mm, 200*mm, 180*mm, 100*mm)
c.line(141*mm, 102*mm, 189*mm, 138*mm)
c.showPage()
# Radial gradient with the endpoint extending over the page.
c.radialGradient(105*mm, 200*mm, 60*mm, (red, yellow))
c.drawString(5*mm, 290*mm, "c.radialGradient(105*mm, 200*mm, 60*mm, (red, yellow))")
c.circle(105*mm, 200*mm, 60*mm)
c.showPage()
# Radial gradient constrained within the circle.
c.radialGradient(105*mm, 200*mm, 60*mm, (red, yellow), extend=False)
c.drawString(5*mm, 290*mm, "c.radialGradient(105*mm, 200*mm, 60*mm, (red, yellow), extend=False)")
c.circle(105*mm, 200*mm, 60*mm)
c.showPage()
# Radial gradient with multiple stops.
c.radialGradient(105*mm, 200*mm, 60*mm, (red, yellow, green), (0, 0.8, 1))
c.drawString(5*mm, 290*mm, "c.radialGradient(105*mm, 200*mm, 60*mm, (red, yellow, green), (0, 0.8, 1))")
c.circle(105*mm, 200*mm, 48*mm)
c.circle(105*mm, 200*mm, 60*mm)
c.showPage()
c.save()
これにより、さまざまなグラデーションに加えて、グラデーション メソッドの呼び出しと、エンドポイントとストップがどこにあるかを示す線/円を含む 6 つのページが出力されます。
[私の答えはもはや正しくありません。グラデーションは Reportlab で利用できるようになりました。詳細については、このページの他の回答を参照してください。]
この質問を復活させて申し訳ありませんが、偶然出くわしましたが、正しく回答されていませんでした。
答えはノーです。現在、ReportLab の現在のバージョンはグラデーションをサポートしていません。ただし、グラデーションは PDF でサポートされています。ReportLab の Canvas クラスを見ると、そのメソッドの多くが、基礎となる PDF コード生成の比較的小さなラッパーであることがわかります。RL でグラデーションにアクセスするには、Canvas クラスを拡張し、正しい PDF コードを生成するためのメソッドを追加する必要があります。これは実行可能ですが、明らかに簡単ではありません。つまり、PDF 仕様をよく読む必要があります。
2 つの選択肢があります。最初にグラデーションをラスター イメージとして生成し、それを使用します。次に、一連の四角形全体を異なる色で描画してグラデーションを生成します。
start_color = (1,0,0)
end_color = (0,1,0)
for i in range(100):
p = i * 0.01
canvas.setFillColorRGB(*[start_color[i]*(1.0-p)+end_color[i]*p for i in range(3)])
canvas.rect(i, 0, 2, 100)
例えば。残念ながら、グラデーションを滑らかにするには多くの長方形が必要であり、これにより PDF が大きくなり、レンダリングが遅くなる可能性があります。ラスター アプローチの方が適しています。
最後に、PyCairo の使用を検討してください。これにより、多くのグラフィック要素のサポートが向上し、PDF または PNG にレンダリングできます。ただし、レポートラボのより高度な構造 (ページ レイアウトなど) はありません。
単色ではなくグラデーションで四角形 (または他のパス) を塗りつぶしたいですか?
問題ない。クリッピングを使用して、グラデーションをパスにバインド/制限します。グラデーションを設定する前に、クリップ パスを設定することを忘れないでください。saveState()
(そして、 /の中にラップしてrestoreState()
、後でクリップとグラデーションをリセットします。)
c = canvas.Canvas (filename)
#c.translate (8*cm, 8*cm) # use this to move the rectangle
p = c.beginPath()
p.rect (0,0 , 5*cm,5*cm)
c.clipPath (p, stroke=0)
c.linearGradient (0,0 , 5*cm, 5*cm , (red, yellow))
extend
放射状グラデーションの場合は、キーワード パラメータをに設定するだけで十分な場合がありますFalse
。