サンプル:速度計#
速度計#

スプライトによる速度計のサンプルです。
画像の作成、リソースの登録、スクリプト作成など一連の流れを解説します。
サンプルダウンロード#
ダウンロード後、レイアウトファイルを鉄道模型シミュレーターNXで読み込んでください。スターターの部品のみで利用できます。運転ボタンで実行できます。
制作手順#
テクスチャー作成#
Photoshopなどで、画像を作成します。透明部分は、PNG形式で透明出力してください。 テクスチャー画像は、ハードウェアの互換性から2^nサイズが適切です。(256,512,1024ピクセルなど)
速度計は、メーターパネルと針で構成しています。メータパネルの中央は、カバーがあります。針は、カバーの下を回転します。このため、針の半分程度を透明にしています。

リソース登録#
速度計は、運転している列車に対して表示するため、編成の リソースに画像を登録します。
編成部品を選択、リソースの「リソースの管理」ボタンをクリックします。

「リソース管理」画面になったら、リソース追加ボタンを押します。

作成したテクスチャー画像(PNG形式画像)を選択します。リソースに登録されます。IDが設定されるので、メモしてください。(作例ではID = 1)

スクリプト記述#
次にスクリプトを記述します。
編成部品のスクリプトにあるスクリプトエディタボタンを押します。

下記のコードを記述します。

コード#
#OBJID=18
import vrmapi
global sprite
def vrmevent_18(obj,ev,param):
global sprite
if ev == 'init':
#spriteオブジェクトの生成
sprite = vrmapi.LAYOUT().CreateSprite()
#編成のリソースからテクスチャ読み込み
sprite.LoadTrainTexture(obj.GetID(), 1)
#フレームイベントを有効化
obj.SetEventFrame()
elif ev == 'broadcast':
dummy = 1
elif ev == 'timer':
dummy = 1
elif ev == 'time':
dummy = 1
elif ev == 'after':
dummy = 1
elif ev == 'frame':
#ベース
x0=16
y0=32
sprite.SetUV(0,0,240,240)
sprite.SetPos(x0,y0,x0+240,y0,x0,y0+240,x0+240,y0+240)
sprite.SetSprite()
#針
#速度を取得
vol=obj.GetVoltage()
#20km/h以下はスケールが異なる
if vol < (20.0/120.0):
vol=vol/(20.0/120.0)*26.0-202.0
else:
vol=(vol-(20/120.0))*240.0+2.0-180.0
#針のテクスチャー範囲
sprite.SetUV(164,252,164+92,252+4)
#回転中心は針テクスチャーの座標上
sprite.SetRotate(0,2,vol)
#メーターの中心に移動
sprite.SetTranslate(x0+120,y0+120)
sprite.SetSprite()
サンプルの編成部品は、ID=18です。コードを再利用する場合は、イベントハンドラーの関数名をのぞいて再利用してください。IDと関数名がことなると機能しません。
コード解説#
スプライトオブジェクトを格納する変数#
スプライトオブジェクトは、生成後もPythonで利用するため、オブジェクトを変数に保存しておきます。 サンプルでは、変数を維持するためにグローバル変数にしています。objに格納されているインスタンスに対して、GetDict()を実行して、ディクショナリに保存するなど適切な手段を利用してください。
global sprite
def vrmevent_18(obj,ev,param):
global sprite
スプライトオブジェクトとテクスチャー#
部品の生成時に呼び出される'init'イベントで、スプライトオブジェクトの生成と、テクスチャーの読み込みを行います。
スプライトオブジェクトは、レイアウトから生成します。
LoadTrainTexture()で編成リソースから読み込みます。
スプライトは、毎フレーム、生成するため、フレームイベントを有効にします。
if ev == 'init':
#spriteオブジェクトの生成
sprite = vrmapi.LAYOUT().CreateSprite()
#編成のリソースからテクスチャ読み込み
sprite.LoadTrainTexture(obj.GetID(), 1)
#フレームイベントを有効化
obj.SetEventFrame()
フレームイベントでは、メーターパネルと針のスプライトを登録します。
スプライトは、「座標設定」+「SetSprite()」で1枚、登録できます。
メーターパネルは、(0,0)-(239,239)の範囲です。SetUV()は、大きさに+1を加算した240を設定します。
SetPos()は、画面上の表示座標を指定します。座標は、順序があります。SetPos()の解説を参照してください。
x0、y0は、画面上のパネル表示の基準座標です。
elif ev == 'frame':
#ベース
x0=16
y0=32
sprite.SetUV(0,0,240,240)
sprite.SetPos(x0,y0,x0+240,y0,x0,y0+240,x0+240,y0+240)
sprite.SetSprite()
針は、速度に合わせて回転表示します。
角度を針の表示位置は、次のようになります。
針を0度で表示すると、写真のようになります。

針を-180度で表示すると、写真のようになります。

このタイプの速度計は、20km/h以下がすこし異なるため、計算を分ける必要があります。 vol変数に受け取った電圧を20km/hでわけて、それぞれの角度を計算します。
針のテクスチャー範囲は、SetUV()で設定します。
回転は、SetRotate()で設定します。このとき、回転中心の座標指定に注意が必要です。座標は、針の範囲内座標で指定します。
回転の結果を、SetTranslate()でメーターパネルの中心に移動します。
最後に針をSetSprite()で登録します。
#針
#速度を取得
vol=obj.GetVoltage()
#20km/h以下はスケールが異なる
if vol < (20.0/120.0):
vol=vol/(20.0/120.0)*26.0-202.0
else:
vol=(vol-(20/120.0))*240.0+2.0-180.0
#針のテクスチャー範囲
sprite.SetUV(164,252,164+92,252+4)
#回転中心は針テクスチャーの座標上
sprite.SetRotate(0,2,vol)
#メーターの中心に移動
sprite.SetTranslate(x0+120,y0+120)
sprite.SetSprite()