ユーザー定義 Displayable link
Ren'Py の動作をカスタマイズする最も複雑だが最もパワフルな方法はユーザー定義 displayable の使用です。ユーザー定義 displayable は任意の pygame イベントを受け取られ、他の displayable をレンダリングして画面の任意の位置にそれらを配置できます。 このため Ren'Py が提供するツールでは表現できない 2D ゲームを作成するのに最適です。( sprites の章も見てください。大量の同一displayableを扱う高度な方法が述べられています。 )
ユーザー定義 displayable はすべて Python でプログラムされるため、この作成を始める前にある程度のオブジェクト指向 Python プログラミングスキル獲得を勧めます。
例 link
これはユーザー定義 displayable の例です。この displayable は、その中心とマウスポインターとの距離から alpha 値を決めて、その子のレンダリングを変更します。
init python:
import math
class Appearing(renpy.Displayable):
def __init__(self, child, opaque_distance, transparent_distance, **kwargs):
# Pass additional properties on to the renpy.Displayable
# constructor.
super(Appearing, self).__init__(**kwargs)
# The child.
self.child = renpy.displayable(child)
# The distance at which the child will become fully opaque, and
# where it will become fully transparent. The former must be less
# than the latter.
self.opaque_distance = opaque_distance
self.transparent_distance = transparent_distance
# The alpha channel of the child.
self.alpha = 0.0
# The width and height of us, and our child.
self.width = 0
self.height = 0
def render(self, width, height, st, at):
# Create a transform, that can adjust the alpha channel of the
# child.
t = Transform(child=self.child, alpha=self.alpha)
# Create a render from the child.
child_render = renpy.render(t, width, height, st, at)
# Get the size of the child.
self.width, self.height = child_render.get_size()
# Create the render we will return.
render = renpy.Render(self.width, self.height)
# Blit (draw) the child's render to our render.
render.blit(child_render, (0, 0))
# Return the render.
return render
def event(self, ev, x, y, st):
# Compute the distance between the center of this displayable and
# the mouse pointer. The mouse pointer is supplied in x and y,
# relative to the upper-left corner of the displayable.
distance = math.hypot(x - (self.width / 2), y - (self.height / 2))
# Base on the distance, figure out an alpha.
if distance <= self.opaque_distance:
alpha = 1.0
elif distance >= self.transparent_distance:
alpha = 0.0
else:
alpha = 1.0 - 1.0 * (distance - self.opaque_distance) / (self.transparent_distance - self.opaque_distance)
# If the alpha has changed, trigger a redraw event.
if alpha != self.alpha:
self.alpha = alpha
renpy.redraw(self, 0)
# Pass the event to our child.
return self.child.event(ev, x, y, st)
def visit(self):
return [ self.child ]
ユーザー定義 displayable を使用するためにそのインスタンスを作成し、それをスクリーンに追加できます。
screen alpha_magic:
add Appearing("logo.png", 100, 200):
xalign 0.5
yalign 0.5
label start:
show screen alpha_magic
"Can you find the logo?"
return
renpy.Displayable link
ユーザー定義 displayable は renpy.Displayable のサブクラスとして作成されます。ユーザー定義 displayable では render メソッドと、おそらくその他のメソッドも同様に上書きしなければなりません。
displayable オブジェクトは pickle 可能でなければなりません。つまり pickle できないオブジェクトへの参照を含んではいけません。 特に Render オブジェクトはユーザー定義 displayable に保存できません。
displayable クラスのメソッド上書きをして欲しいので、 self パラメーターつきで記載します。
- class renpy.Displayable link
ユーザー定義 displayable の基本クラスです。
- __init__(**properties) link
サブクラスはコンストラクターを上書きし、新しいパラメーターを追加するかもしれません。その場合、以下のようなコードを使用して、すべての未知のキーワード引数をrenpy.Displayable のコンストラクターに渡すべきです。
super(MyDisplayable, self).__init__(**properties)
- render(self, width, height, st, at) link
サブクラスはこれを上書きして
renpy.Render
オブジェクトを返さなければなりません。 render オブジェクトは画面に何が表示されるかを決定します。- width, height
この displayable が利用できるピクセル数での空間です。
- st
秒数での出現時間軸の浮動小数です。出現時間軸はこの displayable が最初に画面に表示されると開始します。
- at
秒数でのアニメーション時間軸の浮動小数です。アニメーション時間軸は同じタグを持つ画像が hide されていない状態で表示されると開始します。 ( displayable がタグなしで表示されるとこれは出現時間軸と同じです。 )
render メソッドはこの displayable が最初に表示されるときに呼び出されます。これはこのオブジェクトの
renpy.redraw()
が呼び出されると、もう一度呼び出されます。
- event(self, ev, x, y, st) link
イベントメソッドを呼び出して pygame イベントをユーザー定義 Displayable に渡せます。イベントメソッドが None ではなく値を返すならその値はそのインタラクションの結果として返されます。イベントメソッドが None を返すと、そのイベントは他の Displayable に渡されます。
None を返す以外でイベントを無視するには
renpy.IgnoreEvent
を投げます。event メソッドは他の displayable にも存在し、ユーザー定義 displayable がそのイベントを渡せるようにします。
- ev
- x, y
displayable の左上に対するイベントの x,y 座標です。これらは pygame イベントオブジェクトで見つけられる位置情報より優先して使用されるはずです。
- st
出現する時間軸の秒数
event は各インタラクションの開始で生成され、
renpy.timeout()
はもう一つのイベントを発生させるために使用できます。
- per_interact(self) link
このメソッドは各インタラクションの開始で呼び出されます。再描画を起こすために使用でき、また、オブジェクトがロールバックに参加するなら、再描画に使用するべきです。
- visit(self) link
displayable が子の displayable を持っていたら、このメソッドを上書きしてそれらの displayable のリストを返すべきです。これはそれらの displayable の per_interact メソッドが呼び出されることを保証し、それらの displayable に使用される画像が予測されるようにもします。
- place(self, dest, x, y, width, height, surf, main=True) link
レンダー(この Displayable のレンダーでなければなりません)をバウンディング領域内に配置し、 その Displayable が配置された場所を与える (x, y) タプルを返します。
- dest
None でなければ算出された座標で surf が dest に貼り付けられます。
- x, y, width, height
バウンディング領域
- surf
配置される Render オブジェクト
- main
これは Render.blit() に渡されます。
renpy.Render link
ユーザー定義 displayable は renpy.Render オブジェクトとともに働きます。 Render オブジェクトはdisplayableの renpy.render()
関数を呼び出すと返されます。ユーザー定義 displayable はその render メソッドから renpy.Render
を呼び出して Render オブジェクトを作成するべきです。
render オブジェクトはサブクラスにすることが意図されていないので、 self パラメーターを省略して記載しています。
- class renpy.Render(width, height) link
新しい Render オブジェクトを作成します。
- width, height
ピクセル数での Render オブジェクトの幅と高さです。
- blit(source, pos, main=True) link
この Render オブジェクトにもう一つの Render オブジェクトを描写します。
- source
描画する Render オブジェクト
- pos
描画する座標。これは対象の Render の左上端に対するピクセル数の座標 (x,y) のタプルです。
- main
キーワード専用パラメーターです。 True なら source がスタイルインスペクターに表示されます。
- place(d, x=0, y=0, width=None, height=None, st=None, at=None, render=None, main=True) link
Displayable d をレンダリングし、 x, y, width, height で定義された矩形に Ren'Py 標準の配置方法で配置します。その Displayabe が配置された場所を与える (x, y) タプルを返します。場所は Displayable.place メソッドを呼び出して算出されます。
- x, y, width, height
配置する長方形です。 width や height が None でなければ、それぞれこの render の幅と高さになります。
- st, at
render に渡される時間です。 None なら、このメソッドを呼び出している render メソッドに渡される時間になります。
- render
None でなければこれが d の代わりに使用されます。
- main
.blit() と同様です。
- canvas() link
canvas オブジェクトを返します。 canvas オブジェクトは pygame.draw の関数に対応し、最初のパラメーター ( surface ) を省略したメソッドを持ちます。
Ren'Py では arc 関数と ellipse 関数は実装されていません。
Canvas オブジェクトはその canvas 下にある pygame Surface を返す get_surface() メソッドも持ちます。
- get_size() link
この Render のサイズを与える (width, height) のタプルを返します。
- subsurface(rect) link
この Render を長方形に切り取って構成される Render を返します。
- rect
(x, y, width, height) のタプル
- zoom(xzoom, yzoom) link
この displayable の子の水平、垂直方向のズームレベルを設定します。 displayable の子のみが拡大され、幅、高さ、 blit 座標は拡大されません。
以下の属性とメソッドはモデルベースのレンダリング有効時のみ使用可能です。
- mesh link
このフィールドはこのレンダーに対してモデルベースのレンダリングを有効にします。 :
True なら :
この Displayable のすべての子がテクスチャにレンダリングされます。
A mesh the size of the first child is associated with this displayable.
モデルはこのレンダーの mesh, shader, uniform, properties で作成されます。
モデル1つのオペレーションで描画されます。
- add_shader(shader) link
これにより、 shader は shader を分離してこのレンダーやその子が描画されるときに使用されるようにします。文字列またはshaderで描画されないようにする "-" で始まる文字列です。
- add_uniform(name, value) link
このレンダーやその子が描画されるときに uniform name を value にします。
- add_property(name, value) link
このレンダーまたはその子の1つが描画されるときに GL プロパティー name を value にします。
ユーソリティー関数とクラス link
- renpy.displayable(d, scope=None) link
これは displayable オブジェクトか文字列の d を受け取ります。文字列なら通常のルールに基づきその文字列を displayable に変換します。
- renpy.end_interaction(value) link
value が None でなければ、即座に現在のインタラクションが終了し、インタラクションは value を返します。 value が None の場合は何もしません。
これは Render 内部とユーザー定義 displayable の event メソッドから呼び出され得ます。
- renpy.is_pixel_opaque(d, width, height, st, at, x, y) link
この Displayable が
renpy.render(d, width, height, st, at)
によりレンダリングされたときに (x, y) でのピクセルが不透明かどうかを返します。
- renpy.load_image(im) link
画像キャッシュを使用して画像マニピュレータ im をロードし、 render を返します。
- renpy.load_rgba(data, size) link
size で指定したサイズのテクスチャーに画像データ bytes をロードし、 render を返します。
- data
RGBA8888 順の画像データを含むバイトオブジェクトであるべきです。
- renpy.load_surface(im) link
画像キャッシュを使用して画像マニピュレータ im をロードし、 pygame Surface を返します。
- renpy.map_event(ev, keysym) link
pygame のイベント ev が keysym にマッチするなら True を返します。
- keysym
以下のうちの 1 つです :
config.keymap
のキーバインディングの名前キーマップのカスタマイズ に記載されているキーシンボル
1 つ以上のキーシンボルのリスト
- renpy.render(d, width, height, /, st, at) link
displayable がレンダリングされ、 renpy.Render オブジェクトが返されます。
- d
レンダリングする displayable
- width, height
displayable がレンダリング可能な幅と高さです。
- st, at
出現時刻とアニメーション時間軸です。
このオブジェクトから返された Render はキャッシュされるので、一度取り出された Render は修正すべきではありません。
- renpy.timeout(seconds) link
event が seconds 秒が経過後に生成されます。これは ユーザー定義 displayable の event メソッドが呼び出されることを保証します。
- renpy.redraw(d, when) link
when 秒が経過後、 Displayable d を(renderメソッドを呼び出して)再描画します。 Displayable がその時間前に再描画される可能性もあります(例えば子の再描画)。その場合、保留中の再描画は破棄されます。
- exception renpy.IgnoreEvent link
これは発生すると Ren'Py にそのイベントを無視させる例外です。イベントのメソッド内でこれを発生させるには次のように記述します。
raise renpy.IgnoreEvent()