[ カスタム関数組込フレンドリ構造とは? ]

プログラムに新しい機能を追加する場合、それを動かすための関数を定義して、プログラム内部のしかるべき個所にその関数の実行命令を書くことになる。
A02SL-Expertのような多機能プログラムは、そういった関数を多数、内部に記述してあるのだが、さらなる機能追加を目指して次々と関数を増やしてゆくとファイル容量が際限なく増えて無駄である。また、ユーザーが表現したい鉄道シーンには、おぱく堂の想定外のものもあろう。そういった問題を解消する唯一の方法は、内部にあらゆる関数を用意しておくことではなく、そのシーンに必要な関数を、必要な時だけ別途に組込むことである。
但し、上級ユーザー向けの A02SL-Expertといえども、通常ではこの方法は難しすぎる。
そこで、プログラム側に「改造準備工事」というべきものを施しておき、ユーザー側がプログラム本体を改造することなく、機能追加できるようにしたのが、ここでいう「カスタム関数組込フレンドリ構造」なのである。

具体的に言うと……。
いくつかの「何も実行しない関数」を定義してあり、内部のしかるべき個所にすでに実行命令を書き込んである。
JavaScriptには「同じ名前の変数や関数が複数定義されている場合、後の行で定義したものが有効となる」というルールがある。この「何も実行しない関数」をパラメータ設定より前の行で定義してあるので、パラメータ設定後の位置で再定義する=書き換えることで、何かを実行する関数として使えるようになるわけである。


[ 使える関数の実際 ]

「何も実行しない関数」として定義してあるものは、全部で40(+2)ある。
そのうち、27の関数が直接、鉄道シーンに関係する。その内訳は、通常の処理と並行して実行する「分類1」が 26、通常を処理を行わず別個に実行する「分類2」が 1つある。
それ以外に、画面上でのマウス操作に反応するものが 6つ。タッチ操作に反応するものが 4つ(+2)。キー操作に反応するものが 1つ、ページのアンロード時に実行するものが 1つある。

概略図

・関数1:exfuncPreset()
画像の読込みや配置などの鉄道シーン開始前の処理の最後に実行される関数。
指定では表示されてしまうものを隠しておく、指定では座標を動かせない「背景」と「前景」の位置を変えてしまう、などといった場合に使う。

・関数2:exfuncRun()
電車走行キットでは 1/10秒(1/20秒設定も可能だが)毎に列車座標をずらすことで鉄道を走らせている。
この 1/10秒毎に並行して実行したい処理のために使う。画面内を移動する別の乗り物や、画面内をスクロールするメッセージを動かす場合に使う。
なお、この関数の動作は、最初の列車が動きだすと同時に開始。
v3.1から、シーン表示と同時に動作開始を可能にするパラメータ exfuncRunQuickStart を追加した。

* exfuncPreset() と exfuncRun() に関しては、A02SL-Expert 以外にも搭載したプログラムあり。使用方法は同じ。といっても、2009年 7月時点で対応しているプログラムは、SA40SL v1.1-のみ。

・関数3:exfuncStationStopR()
・関数4:exfuncStationStopL()
列車が駅に停止した時に実行される関数。Rは右行列車、Lは左行列車用。

・関数5:exfuncStationStartR()
・関数6:exfuncStationStartL()
列車が駅から発車した時に実行される関数。Rは右行列車、Lは左行列車用。

・関数7:exfuncRightChange()
・関数8:exfuncLeftChange()
列車が画面外のある地点に到達すると、次の編成と画像を入れ換えて、画面外反対側にある出発地点から再出発する。
この編成を切り替える時点で、並行して実行される関数。Rightは、右行列車が右端に達して、次の編成が左端に戻る段階。Leftは、左行列車が左端に達して、次の編成が右端に戻る段階。

……分類1に属する関数のうち、以下は A02SL-Expert v2.4以降必須。

・関数9:exfuncDoorOpenRcomplete()
・関数10:exfuncDoorOpenLcomplete()
駅停車した列車のドアが開いた時に実行される関数。Rは右行列車、Lは左行列車用。
スムーズドアの場合は、ドアが完全に開ききった時に実行。
・関数11:exfuncDoorOpenRstart()
・関数12:exfuncDoorOpenLstart()
スムーズドア専用。ドアが開き始めた時に実行される関数。

・関数13:exfuncDoorCloseRcomplete()
・関数14:exfuncDoorCloseLcomplete()
駅停車した列車のドアが閉じた時に実行される関数。Rは右行列車、Lは左行列車用。
スムーズドアの場合は、ドアが完全に閉じた時に実行。
・関数15:exfuncDoorCloseRstart()
・関数16:exfuncDoorCloseLstart()
スムーズドア専用。ドアが閉じ始めた時に実行される関数。

ドア関連のカスタム関数は、スムーズドア特殊設定、ドア2度開閉、ドア一部閉、といった設定との併用では正常に動作しない可能性あり。

・関数17:exfuncCrossCloseStart()
・関数18:exfuncCrossCloseComplete()
・関数19:exfuncCrossOpenStart()
・関数20:exfuncCrossOpenComplete()
踏切動作に連動する関数。
上から順に、17= 警報機が成り始めた時に実行。18= 遮断機が完全に閉った時に実行。19= 列車が通過し踏切が開き始めた時に実行。20= 遮断機が完全に開いた時に実行。
なお、遮断機のない踏切やウィグワグの場合は、18 と 20のみ有効。

・関数21:exfuncSigGreenR()
・関数22:exfuncSigGreenL()
信号が進行現示(青)になった時に実行される関数。Rは右行列車、Lは左行列車用。
・関数23:exfuncSigYellowR()
・関数24:exfuncSigYellowL()
信号が注意現示(黄)になった時に実行される関数。Rは右行列車、Lは左行列車用。
・関数25:exfuncSigRedR()
・関数26:exfuncSigRedL()
信号が停止現示(赤)になった時に実行される関数。Rは右行列車、Lは左行列車用。
なお、青・黄・赤の三色のみ。それ以外の中間現示に対応した関数なし。

……以上の26が分類1に属する関数。

・関数27:exfuncSpecial()
事前準備が終わった後、通常の鉄道走行プログラムを起動せず、別のプログラムを動かす。
鉄道走行プログラムを使わないというのは、A02SL-Expert自身を否定するような話でもあるのだが、それゆえに A02SL-Expertでは絶対に不可能なシーンも可能にしてしまえる。F01のような正面画走行や、GA30SLのような往復自動運転ができるのも、この「何でもあり」的な関数があるゆえだ。
なお、イントロ表現もこれを使う。イントロの場合は表現が終わった段階で、通常の鉄道走行プログラムを起動させるような処理を書くことになる。

分類2の処理をタイマー処理する場合には注意が必要。
タイマー名は extraFunction2Timer でなければならず、またインターバルタイマーではなく通常のタイマーでなければならない。さらに、タイマーを動作させているか否かを、extraFunction2TimerOn という変数に true/false で指定しておかねばならない。

……以上が鉄道シーンに関連する関数。以下は画面上でのマウス操作関連。

・関数28:exfuncMouseDown()
・関数29:exfuncMouseMove()
・関数30:exfuncMouseUp()
画面上でのマウスクリックやドラッグに反応する関数。Netscape4では動かない。
元々画面クリックで走行シーン番号を表示する機能が付いているので、そこにこれらの関数をかましただけ。なお、マウスの座標を mouseXposmouseYpos という変数に拾うようにしてある。ただし、この座標には注意が必要。詳細後述 → 見本 No.8 の解説参照。

……以下は v2.9で追加したキー操作関連。

・関数31:exfuncKeyPress()
・関数32:exfuncKeyUp()
キー操作に反応する関数。キーを押した時と、離した時の2種類のみ。それぞれのキーに割り当てられたキー番号(キーコード)を keyNum という変数に拾うようにしてある。但し、キー操作に反応するのは、走行シーンのあるフレームなりウィンドウなりがアクティブになっている時のみ。しかも半角英数モード時のみ、という制約がある。

[ キーコード表 ]
大文字 A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90
小文字 a b c d e f g h i j k l m n o p q r s t u v w x y z
97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122
数字等 0 1 2 3 4 5 6 7 8 9 空白 - + * keyPress でのコード。keyDown や keyUp では数値が異なるものもある。
* これ以外のキーを使う場合は、各自、キーコードを調べられたし。
48 49 50 51 52 53 51 55 56 57 32 45 43

……以下は v3.6で追加した、その他の関数。

・関数33:exfuncOnUnload()
ファイルがアンロードされた時に実行される関数。
走行シーンを別のものに切り替えた時、あるいはフレームごと別のページに移動してしまった時に処理する。他ファイルに干渉するようなスクリプト(親ファイルに干渉してフレームサイズを変える、他フレームのファイルに干渉して画像を変える等)のあるシーンでは、アンロード時に元に戻さねばならない。そのためには必須だが、そういう用途以外にはまず必要がないと思われる。
* 実は v3.3 の時点で組込んであり、隠し関数となっていた。

……以下は v4.2で追加したタッチ操作関連。

・関数34:exfuncTouchDown()
・関数35:exfuncTouchMove()
・関数36:exfuncTouchUp()
・関数37:exfuncTouchCancel()
スマートフォンやタブレットは、クリックはマウス同様に扱えるが、ドラッグ等ではマウスイベントとは別にタッチイベントを拾う必要がある。タッチ座標を touchXpostouchYpos という変数に拾うようにしてある。あとは、マウスと同じように扱えばよい。
* マウスにはないのが、タッチをキャンセルした時の関数。タッチ中にスマートフォン本体を縦から横に向きを変えたりして、画面側の座標系が変わってしまった時に発生するタッチイベントに連動する。ほぼ、タッチを離した時と同じように処理すれば問題はなさそうだ。

……以下は v4.4で追加したダブルクリック等操作関連。

・関数38:exfuncMouseDbl()
・関数39:exfuncMouseDouble()
・関数40:exfuncMouseTriple()
ダブルクリックと、トリプルクリックに反応する関数。
* ダブルクリックには2種類ある。
* onDblClick のイベントハンドラに連動するのが、exfuncMouseDbl()。こちらはタップ非対応。
* 一定時間内の連続マウスダウンからダブルやトリプルを判定するのが、exfuncMouseDouble() と exfuncMouseTriple()。タップ対応だが、シングルタップでダブルクリック関数を実行してしまう等、現状では問題がある。
・関数41:exfuncTouchDouble()
・関数42:exfuncTouchTriple()
* マウスとタッチを別々に処理する場合用の、ダブルタップ、トリプルタップに対応する関数も一応組み込んでみた。だが、上記の問題があるため、正式な追加とはしていない。


[ カスタム関数を書くための基本情報 ]

カスタム関数を書く、といっても通常は、既にプログラム本体内部で定義してある基本動作関数の実行命令を組み合わせるだけだ。解析すれば分かる事だが、解析するのは面倒だろうから、基本関数についての情報を書いておく。

・layerMoveX( オブジェクト名 , X座標 )
・layerMoveY( オブジェクト名 , Y座標 )
これを実行することで、背景でも列車でも何でも好きな位置に移動させられる。

・layerShow( オブジェクト名 )
・layerHide( オブジェクト名 )
オブジェクトを表示したり隠したりする。上のオブジェクト移動で画面外に出してしまっても同じ効果だが、出し忘れや消し忘れに注意。

・layerChange( オブジェクト名 , HTML文字列 )
オブジェクトの中身を入れ替える。
色々なことに使える。たとえば見本の手動ボタンのように、本来はただの画像表示用のオブジェクトをアンカー化するなどの技にも応用できる。

・startEngine()
分類2の関数から、通常の鉄道走行プログラムを起動する際に書くべき命令。
すでに鉄道走行プログラムが動いている状態で再度命令してしまったりすると動作がおかしくなるので、一度だけしか命令しないよう配慮が必要。

……といったところが使える基本関数。

他にも以下のような基本関数も使えるが、いくつか問題がある。

・layerZindex( オブジェクト名 , 重ね順番号 )
オブジェクトの重ね順を変更する関数。
ただ、A02SL-Expert本体が行う「パラメータ設定にあわせた重ね順変更処理」との兼ね合いが難しい。重ね順番号管理について簡単には説明できないので、ユーザー自身に細部まで内部解析してもらう必要がある。2つのオブジェクトが同じ番号に重ならないように正確に割り振るのは大変で、おぱく堂自身、これで幾つか失敗している…。見本では「手動ボタン」や「画面に表示される文字の変更」等で使用。

・imgChange( 画像ID , 画像ファイル名(パス), オブジェクト名(レイヤ名) )
ありふれた画像入れ換え関数。
何が問題かといえば画像ID。これを付番する個所にはカスタム関数が関与できない(関与できるようにするのはややこしすぎる)ため、どのIDにアクセスしていいかは、かなり詳細に内部解析しないと分からないし、解析したところでどうにもならない場合もある。それよりも、使いやすいIDに付番した画像指定を別途に作っておいて、既存のオブジェクトの中身をそれと入れ換えてしまう方が手っ取り早い。見本でも、正面画でこの方法を使っている。
* なお、画像処理なのに引数にレイヤオブジェクト名を指定しなければいけないのは、Netscape4対策。IEなどのブラウザでは画像が属するレイヤオブジェクト名を飛ばしてダイレクトに画像にアクセスできる。たとえば「大阪府」を抜かして直接「大阪市」と書いても郵便が届くようなものだ。それに対して、Netscape4では「大阪府・大阪市」という風に完全な指定をしないとアクセスできないわけだ。

……A02SL-Expert v4.4〜、以下の transform 関数が使える。

・layerSetOrigin( X座標, Y座標, オブジェクト名 ) - transform の原点座標を指定。
・layerRotate( 回転角度, オブジェクト名 ) - transform rotate。ただし単位は「度」のみ。
・layerSkew( X歪み Y歪み, オブジェクト名 ) - transform skew。ただし単位は「度」のみ。
・layerScale( X比率, Y比率, オブジェクト名 ) - transform scale。
勾配表現に有効な transform も、関数ひとつで設定できるようにした。
* 本来の transform 指定は単純だが、過去互換を考慮してベンダープレフィクスを含めて記述しようとすると面倒。ということで、簡単に設定可能な関数を組み込んだ。
* といっても、歪みと比率は使う場面はないかも。
* IE8以前では動作しない。


よく使うであろうオブジェクト名も記しておく。

'haikei':背景
'backObject':線路奥追加配置物
'midObject':上下線間追加配置物
'foreObject':線路手前追加配置物
'zenkei':前景
'extraObject':最前追加配置物
'spareObject':超前追加配置物(v3.7〜)

'denshaAmado':右行・半透明窓 *
'dourinA':右行・動輪
'denshaA':右行・列車本体
'kemuriA':右行・煙
'denshaAdoor':右行用スムーズドア

'denshaBmado':左行・半透明窓 *
'dourinB':左行・動輪
'denshaB':左行・列車本体
'kemuriB':左行・煙
'denshaBdoor':左行用スムーズドア

なにやら日本語と英語が混乱しているが、どうせ自分しか使わないからと思って適当な命名をしてしまったのが、こんなところで恥ずかしい感じになってしまったのは予定外。
* 右行左行を「R・L」ではなく、「A・B」にしてあるのは、単に「shift」+「L」(大文字のL)という文字キーが個人的に打ちにくいから。ユーザー設定用のパラメータでは「R・L」を使うが、ユーザーの目に触れない内部パラメータは「A・B」にしておいた方が楽なのだ。
ただし、半透明窓オブジェクト*のみ、if(glassShow){ } の中で扱わねばならない。そうしないと、半透明窓が指定されていない場合にエラーになるし、指定されている場合でも半透明窓非対応の Netscape4で必ずエラーとなってしまう。
* glassShowという変数は、パラメータ設定より後に定義されるもの。よって、これを使う場合、必ず関数定義の内側にて使用すること。外側で使うと定義されていない変数を使ったことになりエラーとなる。

分類1では通常の走行プログラムも動いているので、風景はともかく車輛にからむ関数を組み込むとエラーの原因になりやすい。さらに、車輛や風景以外に、鉄道構造物等のオブジェクトもある。自らオブジェクト名を調べてもらえば、これらを対象とした関数も書けるわけだが、車輛以上に難しい問題がある。
実際問題として、風景でないものであっても、風景オブジェクトを利用して表現した方が問題が出にくいであろう。

詳細は見本用の外部スクリプトファイルでの実例を参照されたし。


[ 見本について ]

No. 1 (外部スクリプトファイル名:specialIButton.js)

手動発車ボタン。
A02SL-Expertはオートスタート専用なのだが、鉄道走行関数を起動しない分類2の仕様を応用したもの。走行画面は透明画像が最前面を覆っている。よって重ね順変更関数を使ってボタンを最前面に出す処理が必要となる。また、画面内のオブジェクトは風景シーン用であるため、ボタンとして機能させるためオブジェクトの中身を入れ換える処理も使う。
* なお、この見本ではボタン最前面化の z-index を 90 としているが、v2.7で追加したカスタム・オブジェクトを使用した場合や、v3.0で追加した手動操作を選択した場合は、90 では最前面化できなくなる。注意されたし。

No. 2 (外部スクリプトファイル名:specialIntro.js)

単純なイントロ関数。
イントロ画像を最手前に表示した後で、分類2の関数で位置をずらし、画面外に出たところで通常の鉄道シーンを起動。イントロ画像は一枚の画像にアニメの全コマが描いてあって、表示位置をずらすことで画像を切替えているように見せている。複数の画像を入れ替える方法もあるが、それには前述の画像IDの問題を解決するための工夫と事前読込のスクリプトの追加記述が必要となり面倒。よって、一つの画像の位置ずらしという方法を使っているわけだ。

No. 3 (外部スクリプトファイル名:specialJoke.js)

タイムカウントにより細かな制御が可能なイントロ関数。
基本はNo.2のイントロと同じだが、タイマー動作毎にカウントし、そのカウント数値を元に動作処理しているので、コマ(フレーム)毎に切替えタイミングを変えられる。見本はほぼ同じ間隔で動作させているため、この方法ならではの表現例には必ずしもなっていない…。

No. 4 (外部スクリプトファイル名:specialScroll.js)

メッセージスクロール付。
分類1の 1/10秒毎動作の関数で、最手前にある文字画像を上方向に移動させているだけ。

No. 5 (外部スクリプトファイル名:specialUFO.js)

鉄道以外の乗り物追加。
基本はNo.4のメッセージスクロールと同じだが、こちらは横方向に移動させている。なお、見本は UFO なので、縦方向にもゆれるような処理を追加。画面外でオブジェクトを入れ替える処理を追加すれば複数編成も可だが、その場合、事前読込スクリプトの追加が必要となる。

No. 6 (外部スクリプトファイル名:specialStation.js)

駅停止時イベント。
分類1の駅停止時関数と駅発車時関数の使用例。ただし、右行左行で同じオブジェクトを対象としている単純なプログラムのため、右行左行が決して同時には停車しない疑似単線設定用。改良すれば複線でも使えるか。

No. 7 (外部スクリプトファイル名:specialDirection.js)

走行方向表示。
分類1の編成切替え時関数の使用例。ただし、右行左行で同じオブジェクトを対象としている単純なプログラムのため、これまた疑似単線設定用。

No. 8 (外部スクリプトファイル名:specialMouse.js)

画面上でマウスをクリック+ドラッグした場合に反応する例。
* 鉄道シーンそのものとは無関係な機能であり、使い道はそれほどはないと思う。マウスクリックするとシーンの説明を出すとか、画像作者のクレジットを表示するとか、そのぐらいにしか使えないかも…。
* 以前は「使い道がない」等と書いたが、v2.9のパノラマ手動や、v3.0の手動運転機能の追加あたりから、けっこう重要な機能と化した。
これには注意が必要。マウス座標は「ページ(フレーム)左上端からの座標」を拾うのに対して、オブジェクト配置関数は「鉄道シーン左上端からの座標」に配置する。上の見本は、130px高指定の鉄道シーンを、100px高のフレームに表示している。つまり、鉄道シーン上端がフレームに対して -30pxの位置にある。よって、Y軸方向の指定にこの30px差を組み込んでおかないと正しい位置に表示されない事になる。
なお、Netscape4でのエラー回避方法があれこれ試しても見つからなかったため、マウス反応がらみは Netscape4では動かないようにしてしまった。関数の実行そのものが Netscape4回避になっているので、カスタム関数側で Netscape4対応化はできない。
* A02SL-Expert v4.2以降、マウス反応の他にタッチ反応関数を追加したが、v4.3以降は、タッチ操作でマウス関数を動かすことが可能になった。よって、v4.3以降ならば、関数を書き換えることなく、このシーンはタッチ操作できるようになる。

No. 9 (外部スクリプトファイル名:specialFace.js)

正面画走行。
分類2で、正面画走行プログラム F01同等の処理を組み込んで正面画を走らせている。A02SL-Expert本来の走行関数を起動しないからこそ可能な技だが、強引な技には違いなく、色々と工夫が必要になっている。はっきり言って「カスタム関数組込でこんなこともできますよ」的な見本であって、実際に正面画の鉄道シーンを作るのであれば、専用プログラムである F01を使った方がいいだろうとは思う。
なお、F01同様、ちゃんと動作しない Netscape4 は回避処理してある。

No. 10 (外部スクリプトファイル名:specialIRoundTrip.js)

簡易往復自動運転。
同じく分類2で、往復自動運転プログラム GA30SLから基本的な処理の部分だけ持ってきて組み込んだもの。ドア開閉も中間駅もない、ただ往復するだけの代物。A02SL-Expert本来の駅停車システムでは左右2ケ所の停止位置精度が保てないため、複数停車でも停止位置精度が保てる A07系の駅停車システムを使った関数となっている。
GA30SLにもない走行位置(左出発地点からの走行距離)計も追加。オブジェクトの中身を入れ替える関数で、最前追加配置物をフォームに入れ換えてしまうことで実現。フォームへの色付けは Netscape4でエラーになるのでブラウザ分岐処理で回避するのがポイント。

No. 11 (外部スクリプトファイル名:specialIGradation.js)

半透明グラデーション表現。
24bit-PNGが扱えるブラウザでは半透明という表現は画像側で行う。WindowsIE(v6以前)は 24bit-PNGが正常に表示されないかわりに CSS指定で半透明化可能。この仕様ゆえに、車輛の半透明窓も風景オブジェクトの半透明化もブラウザ別に画像を用意するわけだが、ここでも同じ。ただし A02SL-Expertには、単なる半透明を設定する機能はあるが、半透明グラデーションを設定する機能はない。
そこで、WindowsIEのみ、半透明グラデーションの CSS指定を書き加えた画像タグ指定を用意して、カスタム関数を使って差し換えてしまう。使う関数そのものは非常に簡単なので、CSSでのフィルタ指定の知識さえあれば OK。
なお、白一色なので画像ではなくオブジェクトの色指定でも可能。但し、オブジェクトの中身を入れ替える基本関数は内部に存在するが、オブジェクトまるごと差し換える関数は用意されていない。ゆえに、その方法ではもう少し関数がややこしくなる。JavaScriptの知識があれば可能ではあるが、画像を使う方が楽なのは事実。
例によって、半透明非対応の Netscape4 回避も要する。ブラウザ分岐に使う変数については、jsファイル内に詳しく記述してあるので参照されたし。

WindowsIEも、IE7からは 24bit-PNGが扱える。
電車走行キットとしての IE7の扱いは、既存のIEとの互換を重視して、CSS指定での半透過を選択する構造を維持している。但し、A02SL-Expert v.2.1〜のみ、IE7の扱いをどちらにも選択可能とした。
半透過を使った表現に関して、ドット単位で透明度を設定できる 24bit-PNGの方がはるかに高質な表現が可能である。しかし、PNGには動画がないため、動画GIFすら半透過させてしまえる WindowsIEのCSSフィルタ機能も捨てがたいのだ。こういった 24bit-PNGにしか出来ない事や、CSSフィルタでしか不可能な表現を使ってしまうと、ブラウザ限定になってしまい、パラメータ設定を処理する際にブラウザ分岐を組込む必要が出てくるが、カスタム関数を使うレベルのユーザーには特段難しいことではあるまい。IE7の扱いを A02SL-Expertでのみ選択可能としたのも、このレベルの話になって初めて意味を持つからである。
* CSSによる半透過を最初に実現したのは1997年に採用されたWindowsIEのCSSフィルタ機能だが、後発のブラウザは2008年頃までに CSS opacity 指定を採用。IEも 9に至ってこの機能を採用した。A02SL-Expertも v3.8から、追加風景オブジェクトに限ってこれに対応。古いブラウザを考慮しないのであれば、半透過表現にややこしい問題はなくなる。


……以下、A02SL-Expert v2.4以降必須。

No. 12 (外部スクリプトファイル名:specialFunc12.js)

踏切動作に連動して、メッセージを書いた画像を入れ替える(正確に言えば、画像の位置をずらしているだけ)スクリプト。

No. 13 (外部スクリプトファイル名:specialFunc13.js)

No.12 と同じことを、A03系の二車線踏切で設定したもの。

No. 14 (外部スクリプトファイル名:specialFunc14.js)

信号動作に連動して、信号機正面の画像を入れ替える(正確に言えば、画像の位置をずらしているだけ)スクリプト。

No. 15 (外部スクリプトファイル名:specialFunc15.js)

ドア開閉動作に連動して、画像を入れ替える(正確に言えば、画像の位置をずらしているだけ)スクリプト。これは、通常の2段開閉ドア。なお、見本では動作対象の画像が、左行ドアと右行ドアと同じ。つまり、左行と右行が決して同時には現れない疑似単線設定用。複線で使う場合は、左行と右行で動作対象の画像を別にする必要がある。

No. 16 (外部スクリプトファイル名:specialFunc16.js)

No.15 とほぼ同じことを、スムーズドアで設定したもの。


……以下、A02SL-Expert v2.6以降必須。

No. 17 (外部スクリプトファイル名:specialFunc17.js)

蒸機動輪の空転や滑走を表現。
専用の内部パラメータ(右行=wheelRotationRatioR、左行=wheelRotationRatioL)を、カスタム関数を使って切り替える。どういう条件で切り替えるかはユーザー次第(丸投げとも言う)である。パラメータは1=粘着、0=滑走、1を越えた数値はすべて空転である。なお、空転時は加速がゼロになるようになっている。
なお、このパラメータは重連時、あるいは追加動輪に関しても同時に適用されてしまうため、表現上制約がある。重連などには使いづらい。
ちなみに、この見本は空転や滑走は大げさにしてある。ちょっとヘタな運転ということになってしまうが、リアリティを追求して微妙な表現にとどめると、空転しているのかどうか殆ど分からないシーンになってしまうのも事実。


……以下、A02SL-Expert v2.7以降必須。

No. 18 (外部スクリプトファイル名:specialFunc18.js)

既存の鉄道シーン・オブジェクトの上に、カスタム・オブジェクトを重ねて追加する機能の使用例。
重ねて追加した新規オブジェクトの表示範囲を限定することで、拡張プログラム「A08(地下鉄)」的な明暗切替が可能となる。但し、新規オブジェクトを動かす場合は、カスタム関数を使うしかない。
なお、Netscape4 では新規オブジェクトは表示されない。だが、もはや太古の化石のようなブラウザなので影響はほとんどないだろう。
カスタム・オブジェクト概念図
ここでは、暗側を重ねている。暗列車の動作がカスタム関数となる。また、重ねる側に半透明窓がある場合、画像そのものが半透明の 24bit-PNGは問題ないが、指定で半透明化させる WindowsIE用の画像処理にひと工夫必要。

No. 19 (外部スクリプトファイル名:specialFunc19.js)

No.18 と明暗の配置が逆。
重ねる側の列車が一枚画像ではないため、列車画像を連ねたタグを別途生成、および別途事前読込しておき、該当オブジェクトと走行前に入れ替える処理が必要となり、多少面倒。

No. 20 (外部スクリプトファイル名:specialFunc20.js)

明暗切替の応用、鏡面反転。
反転列車画像に半透明窓を使っていないため、処理は No.18より簡単。反転のための走行座標計算が必要なのが、ちょい面倒なだけ。なお、反転走行は A08では不可能。


……以下、A02SL-Expert v2.8以降必須。

No. 21 (外部スクリプトファイル名:specialFunc21.js)

No.18 にパノラマ表示を追加しただけ。カスタム関数的には No.18と同じ。

No. 22 (外部スクリプトファイル名:specialFunc22.js)

パノラマ表示で「単なる左右往復」と「列車先端追尾」以外の動作をさせるためには、カスタム関数が必要。
このシーンは、単線で、列車の走行方向には連動するが、走行位置の追尾はしない。動作そのものは専用関数 panoramaMover() を A02SL-Expert 本体に内臓しているため、カスタム関数では所定位置とのズレ panOffset(正数)の値を求めるだけでよい。

なお、動作比率を設定できるオブジェクト(背景、前景、奥追加配置物、手前追加配置物、最前追加配置物)に関しては、比率=0 と指定した時に panoramaMover() の動作対象から外れるようにしてある。よって、専用動作関数の実行と平行して、カスタム関数で動かすことが可能。

No. 23 (外部スクリプトファイル名:specialFunc23.js)

パノラマ機能を応用して、動的な風景切替をさせる関数。
列車の方向や位置を一切無視して時間で動作させるだけなので簡単。風景位置の移動目標を一定時間毎に変更し、その位置に向かって panOffset の数値を近づけてゆくことで、動的な切替となる。なお目標座標ではなく、直接 panOffset の値を変更すれば、動的ではなく一気に風景を切り替えることになる。

No. 24 (外部スクリプトファイル名:specialFunc24.js)

パノラマをマウスによる手動操作にしたもの。
シーンそのものは No.23と同じなので、全幅 2000pxとなっている。
スライドバーの範囲内でマウスダウンした時のみ動作有効として、マウスの X座標から panOffset の値を設定し panoramaMover() で、画面を動かすのみ。マウスの処理は上記 No.8 の説明を参照されたし。
なお、スライダは、風景用のオブジェクトを邪魔しないようにするため、カスタム・オブジェクトを使っている。

No. 25 (外部スクリプトファイル名:specialFunc25.js)

処理はNo.24 と同じだが、全幅 1600pxのシーンに合わせて変更+スライダの位置を上にしたもの。

No. 26 (外部スクリプトファイル名:specialFunc26.js)

処理はNo.24 と同じだが、全幅 1000pxのシーンに合わせて変更したもの。また、シーンそのものは No.22と同じ。

No. 27 (外部スクリプトファイル名:specialFunc27.js)

パノラマ動作そのものはカスタム関数ではないが、表示位置を示すインジケータ動作がカスタム関数。
panOffset の値を拾って、インジケータ画像の移動距離(この見本では 1/4)を計算して動かすのみ。
なお、インジケータ画像が邪魔なほど大きいのは分かりやすくするため。実際にシーンにインジケータを付ける場合は、列車を邪魔しない程度の大きさの画像が望ましいとは思う。


……以下、A02SL-Expert v2.9以降必須。

No. 28 (外部スクリプトファイル名:specialFunc28.js)

v2.9で追加したキー操作を拾うカスタム関数で、No.26 とほぼ同じパノラマシーンを動かす。
FとGで左へ、HとJで右へ。各々、外側のキーの移動速度が速い。押されたキー番号が keyNum に拾われるので、それに対応したパノラマ表示位置目標を設定。それに向かって panOffset を変化させ風景を移動させるスクリプト。キーを離すと即座に動作停止する。
前述したが、キー操作は、走行フレームアクティブ+半角英数モードでないと反応しない。その辺がいささか不便なところではある。

No. 29 (外部スクリプトファイル名:specialFunc29.js)

v2.9で追加した簡易ズーム機能と、キー操作を拾うカスタム関数を使った例。
F=縮小、G=TB縮尺、H=TK原寸、J=拡大。押されたキー番号が keyNum に拾われるので、それに対応したズーム倍率目標を設定。それに向かって zoomRatio を変化させシーンを拡大縮小させるスクリプト。キーを離すとその縮尺を維持して停止する。
なお、キー関連のカスタム関数は、マウス関連とは異なり Netscape4でも反応する。ただ、ズーム機能が Netscape4 非対応。

No. 30 (外部スクリプトファイル名:specialFunc30.js)

簡易ズーム機能をマウスで操作する。
No.29のシーン+No.24〜26のマウス操作を組み合わせたもの。但し風景設定がズーム対応ということで、100px高設定+100pxフレーム高(他は 130px高設定+100pxフレーム高)になっているため、マウス座標の修正不要。その分だけ設定する時に頭を使わずにすむ。

No. 31 (外部スクリプトファイル名:specialFunc31.js)

簡易ズーム機能をマウスで操作する。
基本は No.30と同じだが、ズーム範囲拡大+マウスを離した時に原寸に戻る処理に変更したもの。
縮小 0.46倍まで可能だが、0.5倍を割ると風景画像が風景サイズに足りなくなる。ちなみに 0.46とは、TK縮尺に対する、アメリカ発の TrainGif規格の標準縮尺の比率。


……以下、A02SL-Expert v3.0以降必須。

No. 32 (外部スクリプトファイル名:specialFunc32.js)

カスタム関数的には No.25と同じ、手動でパノラマ動作をさせる例。
これが何故 v3.0必須かといえば、以前の panoramaMover() には「最初の列車が動き出す前には列車画像をパノラマ動作させられない」という問題があったから。駅停車のないシーンや、手動でなければ何の問題もないのだが、駅+手動パノラマでは、駅から列車が発車する以前にパノラマ動作させることが可能。v3.0 で列車が発車する以前に動作させても問題がないように改良した。

No. 33 (外部スクリプトファイル名:specialFunc33.js)

v3.0 で追加した「手動速度制御(単純走行)」に、各列車解説表示を追加したもの。
手動に設定すると、expCtrlExtra1expCtrlExtra2 の2つの予備オブジェクトを生成する。これはカスタム関数を使わなければ何の表示の役にもたたない陰の存在で、これに layerChange() を使って文字列タグを入れて表示させるのみ。関数としては単純で、この見本はカスタム関数見本というよりも、手動シーン見本として作ったようなもの。
なお、手動運転系の機能はすべて Netscape4に対応していないので、それを回避する処理が必要。

No. 34 (外部スクリプトファイル名:specialFunc34.js)

v3.0 で追加した「手動速度制御(列車固定)」に、走行方向/速度比率表示を追加したもの。
関数の手法としては、上記 No.33と同じ。

No. 35 (外部スクリプトファイル名:specialFunc35.js)

v3.0 で追加した「手動運転」に、走行距離計/速度計の表示を追加したもの。
計器表示の関数の手法としては、これまた上記 No.33と同じ。
さらに、速度 50km/hを超えると加速度を減少させるような処理も組込んである。加速度比を変更できるように manualAccelRatio という内部パラメータを A02SL-Expert 本体に埋め込んであるので、この数値を速度に応じて変化させるだけでよい。但し、それだけでは減速時にも適用されてしまうので、加速中か減速中かで処理を分岐させる必要はある。

なお、この見本では 24bit-PNG形式の車輌画像を設定してあり、正常に表示できないブラウザで見た時に、警告画像を出す処理も追加してある。
強制的に警告表示
本来は、WindowsIE6以前や Netscape4 といった古いブラウザで見ないとその画面は見られない。だが、確認できないと不便なので、cookieを使ってモードを切り替え、強制的に表示させられるようにしてみた。

No. 36 (外部スクリプトファイル名:specialFunc36.js)

v3.0 で追加した「手動運転」に、停止位置精度の記録を cookieセーブできるようにしたもの。
文字表示の手法は、上記と同じ。ややこしいのは、停止位置の判定と保存。
初期表示位置を停止位置 0 としているが、これは背景の座標も 0 の位置。見本では 3000pxの幅の風景だが、backObject の移動座標 bgrunpos[1] から数値を拾う。但し、これは負数。0〜-3000の範囲となる。停止位置を超えると、見た目には分からないが、風景が 3000px分移動(超過した瞬間、座標 0から -3000に一気に飛ぶ)しているので、それを超過か手前かの判定に使う。

cookieの処理は、セーブ・ロード・消去の3つが必要。
といっても、説明が難しいので詳細は省く。解析するのが面倒なら、ほぼそのままのスクリプトを流用されたし。といっても cookie名の変更ぐらいはやってほしいところではあるが…。
なお、消去用の関数も書いてあるが、画面上からの操作は追加していない。この見本では、フレームを超えて画面外から消去させるしかない。
記録消去
フレームを超えて命令を出す場合は、フレームのチェック等が必須。
なお、cookieを消去するだけなら、No.36 を表示していてもいなくても消去可能。だが、ここでは No.36 表示時にしか消去できないようにしてある。同時に「前回より良い記録が出たか否か」をチェックするためのパラメータをリセットする処理を組込んであるため。

No. 37 (外部スクリプトファイル名:specialFunc37.js)

No.36と同じ手動シーン(但し cookie機能は削除)を自動化した、デモ走行シーン。
自動化といっても直接列車を走らせるのではなく、カスタム関数が操作系を乗っ取る手法。この場合、手動操作に邪魔されると困るので、隠しパラメータ manualCtrlObstructer を exfuncPreset() でtrueに設定して、マウス操作を不能にする。
自動化といっても、P2-N-B5(全加速‐定速‐全制動)の3つしか使わない安直なスクリプトなので、停止位置ジャストはなかなか難しい。


……以下、A02SL-Expert v3.1以降必須。

No. 38 (外部スクリプトファイル名:specialFunc38.js)

降雨表現。
これが何故 v3.1以降かといえば、exfuncRun() は「最初の列車が動き出してから動作開始」という仕様だったため。exfuncSpecial() を使うことで以前のバージョンでも降雨表現は可能ではあったが、面倒だった。v3.1から、exfuncRun()の動作開始タイミングを「シーン表示と同時」に設定可能にするパラメータ exfuncRunQuickStart を追加。
雨の動作そのものは、No. 4 の「メッセージスクロール」と方向が逆なだけで、全く同じ。

No. 39 (外部スクリプトファイル名:specialFunc39.js)

カスタム・オブジェクトのずらし設定の見本。
ここでは、シーン上にフィルムを重ねたような表現だが、右側だけでなく、左側も切れたオブジェクトとして画像上に配置できる。
なお、この見本では 24bit-PNG形式の画像を設定してあり、正常に表示できないブラウザで見た時に、警告画像を出す処理も追加してある。


……以下、A02SL-Expert v3.6以降必須。

No. 40 (外部スクリプトファイル名:specialFunc40.js)- v2.0

フレームサイズを変更する見本。
方法はフレーム設定ファイル(=親ファイル)にアクセスして、フレーム属性を設定しなおすだけ。問題はどうやってアクセスするかだが、やり方は二つある。
ひとつは、タグ名(この場合は「frameset」)と、その番号(何番目の framesetタグなのか。最初は 0 である)でアクセスする方法。もうひとつは ID番号でアクセスする方法で、ここでは後者を使っている。よって、親ファイルに IDを書き込んでおかなければならない。前者を使うのであれば、親ファイルをいじる必要はない。
重要なのは、アンロード時の処理で、ここにカスタム関数が必要となる。
二つの場合を想定しておかねばならない。
ひとつは、別の走行シーンに切り替えられた場合。これは、元のフレームサイズに戻してやること。でないと、別のシーンもそのサイズで表示されてしまう。
もうひとつは、他のサイトに移動したりしてフレームごと消えてしまう場合。こちらは、元のフレームに戻そうとする処理がエラーになる場合がある。だから、親フレームにアクセスできる状態にあるかチェックを入れて処理する必要があるわけだ。
* アンロード時に実行されるカスタム関数は、実は v3.3から隠し関数として存在していたので、サイズを変更するだけなら v3.3以降で可能。但し、v3.5以前には、フレーム高に自動で合わせてしまう機能を解除した場合のバグがあり、このシーンはそれに抵触するので v3.6は必須である。
* 2016年 4月に、モバイルビューア(インラインフレーム)のフレームサイズ変更にも対応した。なお、モバイルビューアを使う場合は、A02SL-Expert v4.11以降必須。


……以下、A02SL-Expert v3.71以降必須。

No. 41 (外部スクリプトファイル名:specialFunc41.js)

CSS transform を使って、勾配表現をする見本。
カスタム・オブジェクトだけを傾斜させて、手前にある傾斜しない画像と重ねる表現。
No.18〜No.20 の応用。v3.71からカスタム・オブジェクトに CSS 指定を追記できるように改造したので、そこに transform : rotate(-1deg) を書き込んで、左下がり1度の傾斜をつけたもの。
但し、問題あり。
ひとつは、IEでは 9以降が必須だということ。IE8以前を使っている人に対しては不親切なシーンとなる。ちなみに、非対応ブラウザと処理を分岐する必要があるのだが、ここでは IE8以前と Netscape4 だけを除外し、後は全部対応ブラウザと見なしてしまうというザックリとした方法を使っている。
ふたつめは、本来は通常オブジェクトの手前に来るはずのカスタム・オブジェクトが、CSS指定を追記するとなぜか通常オブジェクトの背後に隠れてしまい、肝腎の勾配シーンが見えなくなる、ということ。原因は見つけていないので、根本的な解決策はわからない。ここでは、消せない車輌は走行位置をフレーム外(-100px 下げた)に追いやり、風景がらみのものは全て false にして表示させない手法を使った。傾斜させない手前の画像は spareObject を使用。
ふたつめは、z-index の指定数値では傾斜したカスタム・オブジェクトの背後にあるはずの、通常オブジェクトが手前に表示されてしまうこと。このシーンを作った当時は原因が分からず、この No.41 では、「通常オブジェクトを一切表示させない」という解決策をとった。その後、z-index の順番どおりにならないのは、スタック文脈(stacking context)の問題があると判明。通常オブジェクト(ID="tetsudou")に対して、exfuncPreset() で、明示的に z-index に -1 指定をする = layerZindex('tetsudou',-1) を実行することで解決する。
* 電車走行キットでは、子オブジェクトにのみ z-index 指定が入れてあり、通常オブジェクトやカスタム・オブジェクトといった親レベルのオブジェクトには z-index 指定を入れていない。ややこしいことをしなければ、このまま子オブジェクトの z-index どおりの重ね順で表示されるのだが、カスタム・オブジェクトに transform 指定を入れることで、カスタム・オブジェクトに、親オブジェクトに対して明示的に z-index を指定したのと同じ状況(=重ね順に親子構造が関与する=スタック文脈の発生)になってしまう。この時、明示的に z-index を指定していない親オブジェクトである通常オブジェクトが前面に出てしまうことと、子オブジェクトの z-index が親オブジェクトの内部だけの重ね順になってしまうことが重なり、指定数値が小さくても通常オブジェクトに属するオブジェクトはすべてカスタム・オブジェクトの前に出てしまうのだ。ということで、背後にあるべき通常オブジェクト=親レベルに対して明示的な z-index 指定を入れることで、通常オブジェクトとカスタム・オブジェクトの前後関係が確定するのである。
* ……とか書いても、分かりにくいか。ネット上には、スタック文脈について、もっとわかりやすく解説したページがあるので、検索されたし。
三つ目は、シーン番号表示がどこかに消えてしまうこと。これは……原因不明。なので何の策も講じていない。
他にも問題があったが、最新のブラウザでは発生しないので、原因不明のまま、無視することとする。
* v3.7ではバグが絡むので正常に表示されない。v3.71以降必須。
* こういう関数を書くのに必要になったので、v3.7から isIE9 という IE9以降では true となる変数を用意した。
* この方法は傾斜するものと傾斜しないものを重ねるためのものだが、全てが傾斜していいのなら、電車走行キットすべてで、鉄道オブジェクト(親子構造の親)に CSS 指定を入れれば勾配シーンになる。この方法に、逆方向への回転を追加して傾斜しないオブジェクトを可能にしたのが、後述の No.44 と No.45だ。
なお、ブラウザ限定ということで、正常に表示できないブラウザで見た時に、警告画像を出す処理も追加してある。


……以下、A02SL-Expert v3.8以降必須。

No. 43 (外部スクリプトファイル名:specialFunc43.js)

CSS transform を使って、回転表現をする見本。
カスタム・オブジェクトだけを回転させて、手前にある回転しない画像と重ねる表現。
基本的には、No.41の勾配表現に、角度を動的に変えるスクリプトを追加しただけ。但し、v3.71でこれをやると問題があり(失敗実例は No. 42)、v3.8へのバージョンアップが必要になった。
シーン Clip と回転の関係
電車走行キットプログラムは、設定されたシーン寸法からはみ出た部分を非表示にする処理(Clip)をしているが、CSS の回転設定は、回転した後のシーンを Clip するのではなく、Clip した後のシーンを回転させる。そのため、回転させると欠けが見えてしまう。それを回避する方法として、欠け部分を超手前オブジェクトで隠す(No.41)しかないが、それも限界がある。そこで、Clip 機能そのものを解除してしまうことを可能にしたのが、v3.8だ。シーン外(楽屋裏)が見えてしまうが、フレーム(含インラインフレーム)を使った表現なら問題はない。
小さな問題は、シーン番号表示が指定どおりの座標に配置されないこと。しかも、通常オブジェクト用とカスタム・オブジェクト用のシーン番号(この二つは全く同じ位置に重なるはずの設定なのだが)がズレて、二重に見えてしまう。回避するために、通常オブジェクト用の番号をあらぬ座標に指定し、連動してあらぬ場所に行ってしまったカスタム・オブジェクト用の番号をカスタム関数で移動させた。
* 楽屋裏が見えてしまうのは、シーンを作る過程で確認作業をする上でも便利だったりする。
ちなみに、回転機能に対応していないブラウザで見ても、回転しないだけで何の問題もないため、No.41と異なり、非対応ブラウザで見た時に警告画像を出す処理は入れていない。

No. 44 (外部スクリプトファイル名:specialFunc44.js)

見た目は、No.43と全く同じ。
但し、No.43ではカスタム・オブジェクトを回転させる方法を使ったが、これは通常オブジェクトを回転させたもの。
この場合、全てが回転してしまうので、回転してほしくないものだけ逆回転させて、差し引きゼロにする処理を追加した。また、No.43と同様に Clip を解除するが、こちらは通常オブジェクトの Clipを解除しなければならないので設定時は注意。
問題はこの逆回転。次の No.45 も含めて、この手法では「?」と思うようなトリッキーな動きをする。
ここで使っているシーン画像は、回転する風景画像と回転しない手前画像の寸法が同じなので、画像回転は問題ない。しかし、シーン番号が設定どおりの位置に留まらない。それを防ぐために子オブジェクトの座標を個別に設定すると、今度はうまく回転していたはずの超手前画像があらぬ動きをしてしまう。ということで、ここではシーン番号をはるか遠く画面外に追いやってしまった。

No. 45 (外部スクリプトファイル名:specialFunc45.js)

見た目は、No.41と全く同じ。
但し、No.41ではカスタム・オブジェクトを回転させる方法を使ったが、これは通常オブジェクトを回転させたもの。
これも、No.44 と同じく、回転してほしくないものだけ逆回転させて差し引きゼロにする処理を行っているが、問題が2つ発生。
ひとつは、Clipを解除しているのに画面の一部が欠けた。原因はよく分からないのだが、傾ける画像と傾けない画像のサイズの不一致とか、130pxシーン高と 100pxフレーム高の不一致とか、そのあたりにありそうだ。lowFrameControl=false にして、一旦フレーム高に自動的に合わせる処理をやめて、後にカスタム関数であらためて 30px分のズレを補正することで欠けなくなった。
もうひとつは、逆回転オブジェクトが微妙に位置ズレを起こしたこと。これは、傾ける親オブジェクトだけでなく、逆方向に傾斜させる子オブジェクトにも、いちいち明示的に回転中心を設定することで解消。No.44では逆に子オブジェクトの逆回転はうまくいかなかったので「???」と疑問符だらけだが、原因はさっぱりわからん。現場あわせ的にこういう処理にしているだけ。
* 逆回転時に発生する表示座標の不思議さえ解決すれば、通常オブジェクトを傾斜させる手法の方が楽なんだが……確実性という点では、カスタム・オブジェクトを使う手法に軍配が上がる。


……以下、A02SL-Expert v4.11以降必須。

No. 46 (外部スクリプトファイル名:specialFunc46.js)

スマートフォンで電車走行キットの走行シーンを見るための、モバイルビューア(Mobile Viewer)対応。
このページから見る限り、「通常フレーム」と書いたシーンを蒸機が走るだけだが、モバイルビューアで見ると、PCなのか、スマホ縦長(Portrait)なのか、スマホ横長(Landscape)なのかをチェックする。表示されるデバイスによって走行シーンを変える見本だが、モバイルビューアで見ない限り、その機能は使えない。
* なお、モバイルビューアは HTML5で記述してあり、対応ブラウザか否かの判定を、きわめて安直な方法によっているため、IE10以前が排除されてしまうという問題がある。もっとも、メインターゲットである、スマートフォンでは問題はないため、さほどの問題はないと思われる。
* No.40 同様、フレームサイズ変更の見本でもある。


……以下、A02SL-Expert v4.2以降必須。

No. 47 (外部スクリプトファイル名:specialFunc47.js)

大画面のパソコンでは、フレーム拡張。小画面のスマートフォンでは、フレーム寸法そのままに、タッチ操作で画面スクロール。
大小の両立が難しいので、見せ方そのものを変えてしまおうという話。
* マウス操作の画面スクロールを組み込んでいないので、パソコン上のスマートフォンシミュレータでの確認時は注意。


……以下、A02SL-Expert v4.4以降必須。

No. 48 (外部スクリプトファイル名:specialFunc48.js)

見た目は、No.43 と No.44 と全く同じ。
v4.4- の機能を使って、同じ表現を再現したもの。この No.48 のカスタム関数が一番シンプルになる。
おまけで、トリプルクリックで逆回転になるギミックも追加。
* v4.4- の機能の詳細は、次項 No.49 の解説を参照。

No. 49 (外部スクリプトファイル名:specialFunc49.js)

右行、左行で別々の勾配を表現したシーン。
これを実現するために、v4.4では、カスタムオブジェクトとは別に、走行オブジェクト全体を分割する設定を追加。
通常は ID="tetsudou" の親オブジェクトの下に、車輌や風景の子オブジェクトが配置されている。カスタムオブジェクトの場合、親オブジェクトを分割して、ID="tetsudou2" と ID="tetsudou3" を合わせて3つの親オブジェクトを重ねる仕組みで、tetsudou2 だけを傾斜させて勾配表現を試みていた。
v4.4からは、カスタムオブジェクトを挿入することなく、親オブジェクトをいくつかに分割可能にした。
* ちなみに、設定パラメータは以下のものがある。
stackPartition[1] - 背景と追加配置物(奥)との間で分割(true=分割、false=何もしない)
stackPartition[2] - 右行列車の奥で分割
stackPartition[3] - 右行列車の手前で分割
stackPartition[4] - 右行と左行の間、追加配置物(上下線間)と線路の間で分割
stackPartition[5] - 左行列車の奥で分割
stackPartition[6] - 左行列車の手前で分割
stackPartition[7] - 生成されたカスタム・オブジェクトの手前=追加配置物(超手前)の奥で分割
stackPartition[8] - 追加配置物(超手前)の手前=ほぼ最前面だが、マウス座標を拾う透明オブジェクトより奥
* それぞれ分割時の親要素の ID名は、[1]の場合は "tetsudou_pt1" というように、tetsudou_pt +数字 となる。
親オブジェクト分割
分割した親オブジェクトそれぞれに対して、傾斜指定を入れれば、右行と左行を別の勾配にすることが可能となる。
ただし、No.41の説明でも書いたが、スタック文脈が発生するため、カスタム関数を使って、親オブジェクトの前後重ね順を明示させないといけなくなる。また、疑似複々線のような重ね順を変えて疑似的に表現しているものは、親オブジェクトを超えて順番を変更できないため、表現不能となる。
* スタック文脈の副作用として、シーン番号表示が背後に行ってしまう問題がある。
* v4.4-から、原点座標指定 layerSetOrigin( ) と 回転角度指定 layerRotate( ) が組み込まれたので、勾配表現が、以前よりは簡単になった……はず。
* ちなみに、回転角度指定なので、パーミルでの表現では換算が必要。
 10‰ = 0.5729387°
 22.6‰ = 1.2946642°
 25‰ = 1.432962°
 33.3‰ = 1.9072447°
 40‰ = 2.29061°
 50‰ = 2.8624052°
 66.7‰ = 3.8159762°
 80‰ = 4.5739213°
 90‰ = 5.1427646°
* 正数で右下がり、負数で左下がりとなる。
* No.49 では、換算が面倒なので、右行が +2°、左行が -2°という安易な整数指定。ちなみに、34.9‰ という急勾配である。

さらに、v4.4からは、ダブルクリックとトリプルクリックに反応する関数を用意したので、このシーンもダブルクリックでフレームサイズを拡大縮小する。
* 但し、現状では、シングルタップでダブルクリック関数が動作してしまう等、タッチデバイス向けとしては問題がある。。


……以下、A02SL-Expert v4.5以降必須。

No. 50 (外部スクリプトファイル名:specialFunc50.js)

CSS3による勾配表現と、No. 22のような、パノラマ的画面スクロールを両立させたシーン。
親オブジェクト分割と、パノラマ動作処理の相性が悪いため、別の方法が必要になった。
勾配表現に必要な「分割した親オブジェクト」をまとめて左右動させるためには、親の親、つまり「祖父母レベルのオブジェクト」を追加して、複数の親オブジェクトを一括して扱えるようにするのが最適。それを実現したのが、v4.5。
元々組み込んである panoramaMover() が使えないため、左右動はカスタム関数。
No.50 は、単線の各列車の動きにスクロールを連動させたもの。つまり「A00B - M00B」風の処理。
* 勾配表現プログラム「KA00」添付の風景画像を使っているため、20‰という緩い勾配シーン。
* オブジェクト構造が、親の親、親、子の3世代になっているため、ややこしい。それ以外は、特に複雑な処理をしているわけではなく、特に説明を要することもない。

No. 51 (外部スクリプトファイル名:specialFunc51.js)

No.50 と同じシーンだが、こちらは画面スクロールが列車に連動しない。
その代わり、画面クリックで、スクロールの停止/再開が切り替えられる。
* 画像を「KA00」から流用しただけなので、スクロール停止を示すインジケータ的な表現はない。


[ 使用条件の解釈 ]

プログラム動作部分を改造した場合には「おぱく堂版電車走行キットを○○が××部分の改造をしたものである」と、改造者名○○と改造内容××を明記すること、という使用条件がある。
ユーザー自作のカスタム関数を組み込んだ場合は問題なくこの条件に当てはまるが、ここで用意した関数見本を改造して使った場合はどうなるのか。解釈の難しいところであるが、見本をちょっと改造した程度なら、改造時の条件を適用しなくてもよいことにする。逆に言えば適用してもよい。なにやらグレーゾーンだが、世の中、なんでもかんでも白黒ハッキリしているわけでもないし…。


前頁に戻る