見出し画像

BVE Trainsim5のシナリオ(路線や車両)をつくるには

寄稿者:わっきー

ごあいさつ

こんにちは、Like A Lakeサーバー所有者のわっきーです。
BVE Trainsimまわりでは主に京阪電車シナリオの作者として認識されてるっぽいです。
しかし最近は、サイトの管理は丸投げだし、人のたくさん集まるところには相変わらずめんどくさがって行かないし、そもそもメタバースなる全然別分野での創作に浮気している散々な状況だし、総じてBVEを遊び始めてから24年経つのに9割以上浮気しておりBVEを語るのは大変おそれ多いんですが
【「今あるもの」「今残っているもの」を活用して新しい価値あるものをつくる】という営みがここ最近トレンドになっているな、
と感じておりまして、たまの遊びでさわったのをきっかけに思い出してこの筆をとっております。

「BVEで遊んでいて楽しいと思い、自分の作品を作りたいが何をしたらいいのかわからない」「作品が永遠に完成しない」「設計図は頭の中にあるけどどうやって形にしたらいいか雲をつかむようで途方に暮れている」「雲をつかむよう、というか思いっきり雲をつかんだかのようにプロジェクトが自然消滅した」といった辛酸をなめてきた方々が歩みを進めて理想を現実にする一助となれば幸いです。

わっきーは、社会活動家・システムエンジニア・コンサルタント。SF・歴史・メカを嗜む。尊敬する人物は新渡戸稲造、マハトマ・ガンディー、マーガレット・サッチャー。

わっきーのプロフィール

BVE Trainsimは、PCでプレイ可能なフリーソフトの鉄道運転シミュレーターです。リアルな操作や風景を体験でき、実際の路線や列車を再現したデータ(シナリオ)をカスタムで追加できることから、人気が上がっています。

BVE Trainsimとは

京阪電車は、大阪市から京都市、さらに大津市(滋賀県)を結ぶ私鉄路線の通称です(関西では「おけいはん」という愛称で親しまれています)。
明治期の「電鉄ブーム」中に開業し、都市間路線、通勤通学路線の姿を経て平成期以降は観光路線の色合いが強まっており、最近(平成末期から令和)では、従来からある鉄道の枠にとらわれない独自の社会活動「ビオスタイル プロジェクト」に力を注ぎ、これからの時代のライフスタイル提案と諸商品・サービス提供事業の展開を拡大しています。
沿線には多くの世界遺産がありユニークな列車が頻繁に運行されています。

執筆時点で京阪電車と「ビオスタイル プロジェクト」は切り離せない状況のため説明が少々長くなりすみません。

京阪電車とは

メタバースは、インターネット上の仮想世界です。アバター(ユーザーキャラクター)を通じて他のユーザーと遊んだり働いたり様々な活動ができます。次の時代にインターネット空間の主流の「場」となる可能性があるとして、投資家や実業家、開発者から注目を集めています。

メタバースとは

1.そもそも「BVE Trainsim5のシナリオ」の実体は具体的に何か?

BVE Trainsim基本ソフトウェアがシナリオファイルを読んでごちょごちょ動く、その読む部分です(禅問答みたいですみません)。

基本ソフトウェアがシナリオファイルを読んでごちょごちょ動いた様子(イメージ)

しばらく読むのがしんどいところが続きますがご容赦ください。

  • シナリオファイル

BveTs Scenario 2.00:utf-8

Title = 休B1201A(201X.9) Ver.0.3.15
Author = wackey
Route = wackey.KeihanMainLine\Operations\B1201A\MapRoot_holiday.010101.txt
RouteTitle = 京阪本線・鴨東線
Vehicle = wackey.Keihan_Vehicle\Keihan8000_1989\Keihan8051_B1201A.txt
VehicleTitle = 京阪8000系(1989-,8両)
Image = wackey.KeihanMainLine\Operations\B1201A\scenario_BA_8000.JPG
Comment = 区間:出町柳-樟葉,最高運転速度110km/h,京阪式ATS(初代)

呪文の意味はだいたい以下のようになります。
基本ソフトウェア上での表示これにして、マップロードして、車両ロードして

マップは、線路や駅、信号、勾配、カーブ、オブジェクトの配置などを記述したテキストファイルです。

BVEのマップとは

車両は、性能データ、運転台データ、保安装置プラグイン、走行音などのサウンドが含まれるデータセットです。

BVEの車両とは

運転台は、列車先頭にあり運転士が列車を操作する場所です。操縦席、速度を調整するマスターコントローラー(マスコン)、ブレーキハンドル、計器類(速度計や圧力計など)、警笛スイッチ、モニタ装置などが配置されており運転に使用されます。

運転台とは

保安装置は、列車の安全運行を確保するための装置やシステムです。信号を超過すると自動的にブレーキを作動させるATS(自動列車停止装置)や、列車の速度を監視して制御するATC(自動列車制御装置)などがあり、BVEではDLL形式プラグインファイルとして制作されます。BVE保安装置プラグインの制作にはプログラミング技能が必要です。

保安装置とは
  • マップ(シナリオファイルから呼び出される)の例

BveTs Map 2.01

	Structure.Load('Structures_dev.txt');
	Sound.Load('Sounds.txt');
	Sound3D.Load('Sounds3d.txt');
	Signal.Load('Signals.csv');

Signal.SpeedLimit(0,25,45,75);

Light.Ambient(1,1,1);
Light.Diffuse(1,1,1);
Light.Direction(90,0);

Adhesion.Change(0.342, 0, 0.00643);

Gauge.Set(1435);
Track['down'].Gauge(1435);
Track['up'].Gauge(1435);
Curve.SetFunction(1);

	//先行列車、乗客、天候
//	include 'Map_Trains_h01.txt';
//	include 'Map_People_h01.txt';
	Station.Load('map_StationList_dev_h01.csv');
	include 'Map_Weather_h01.txt';

	include 'MapStations_dev.txt';
	include '../../Data/Map2017/M41323_Signal.txt';
	include '../../Data/Map2017/M41323_Sign.txt';

	include '../../Data/Map2017/M41323_Illuminance.txt';
	include '../../Data/Map2017/M41323_RunSound.txt';
	include '../../Data/Map2017/M41323_DrawDistance.txt';

	include '../../Data/Map2017/M41323_Limit.txt';

	include '../../Data/Map2017/M00_41323_S01_OT12_Hamaotsu.txt';
	include '../../Data/Map2017/M00_41323_S01_OT12Track_Hamaotsu.txt';
	include '../../Data/Map2017/M00_41323_S02.txt';
	include '../../Data/Map2017/M00_41323_S02_Track.txt';
	include '../../Data/Map2017/M00_41323_S03_OT32_Shinomiya.txt';
	include '../../Data/Map2017/M00_41323_S03_OT32Track_Shinomiya.txt';
	include '../../Data/Map2017/M00_41323_S04.txt';
	include '../../Data/Map2017/M00_41323_S04_Track.txt';
	include '../../Data/Map2017/M00_41323_S05_T08_Misasagi.txt';
	include '../../Data/Map2017/M00_41323_S05_T08Track_Misasagi.txt';

呪文の意味はだいたい以下のようになります。
基本データロード、ロード、ロード、早く読まないとエラー吐いてしまうリストからロード、路線の基本設定、状況別のマップ状況ロード、信号と保安装置のデータをロード、分岐器を境界にしてエリア別にマップをロード、仕上がってきたら書き換える頻度が非常に低くなる線形データをロード

鉄道における信号は、線路上の信号機や車内信号、軌道回路、運行管理システムが連携し、列車間隔の調整や進行許可、速度制限などを指示するもので、BVEプレイにおける最重要の情報です。
システム構造は路線により大きく異なるためプレイ前に予習すると円滑に進められるかもしれません。
自動閉塞式(線路を閉塞区間に分割し列車の位置管理を行う。JR東海道線など)、無線式列車制御システム(都市内輸送で運行効率向上と安全確保を両立する場合。集中管理のCBTCあるいは分散管理のATACSが路線特性に適した方式で用いられる。日本国外に導入例が多い。国内ではCBTCが東京メトロ丸ノ内線で導入されている)、自動列車制御装置(新幹線や地下鉄など地上信号機の目視が困難な場合)などの方式があります。複数方式併用の場合もあります。

鉄道の信号について

分岐器は列車の通る線路を切り替える装置です。
BVEでは分岐器ごとに区間を分割してマップを管理すると開発上便利です。
includeを使用してデータを再利用したり発着番線を分けたりすることができます。

鉄道の分岐器について

include先の事例 線形データ
(下りなので基準座標からキロ程を引いてBVE内Z座標として設定している)

BVEの座標表現方法は、進行方向の距離(Z軸)に基づき、そこに曲線や分岐、オブジェクトの配置を設定する(X軸が左右方向、Y軸が上下方向)というものです。シナリオ開発中の慣例をもとに、本稿では進行方向の距離を指して「BVE内Z座標」と呼びます。

BVEの座標表現方法について
BveTs Map 2.01
$KSS = 11750;

$KSS-5650;	Gradient.BeginTransition();
$KSS-5605;	Gradient.BeginConst(5.0);
$KSS-5460;	Gradient.BeginTransition();
$KSS-5450;	Gradient.End();

$KSS-5440-10;	Curve.BeginTransition();
$KSS-5440;	Curve.BeginCircular(-2000, 0);
$KSS-5425;	Curve.BeginTransition();
$KSS-5425+10;	Curve.End();

$KSS-5430;	Gradient.BeginTransition();
$KSS-5420;	Gradient.BeginConst(5.0);
$KSS-5340;	Gradient.BeginTransition();
$KSS-5330;	Gradient.End();
	
$KSS-5310;	Gradient.BeginTransition();
$KSS-5295;	Gradient.BeginConst(-6.3);
$KSS-5205;	Gradient.BeginTransition();
$KSS-5195;	Gradient.BeginConst(-10.0);

//Station OT31

$KSS-5105;	Gradient.BeginTransition();
$KSS-5095;	Gradient.BeginConst(-13.8);
$KSS-5005;	Gradient.BeginTransition();
$KSS-4975;	Gradient.BeginConst(-31.3);
$KSS-4940;	Gradient.BeginTransition();
$KSS-4890;	Gradient.End();

$KSS-4900-30;	Curve.BeginTransition();
$KSS-4900;	Curve.BeginCircular(-402.33+1.7, 107);
$KSS-4825;	Curve.BeginTransition();
$KSS-4825+30;	Curve.End();

$KSS-4885;	Gradient.BeginTransition();
$KSS-4850;	Gradient.BeginConst(-22.2);
	
$KSS-4760-30;	Curve.BeginTransition();
$KSS-4760;	Curve.BeginCircular(160.93+1.8, 107);
$KSS-4650;	Curve.BeginCircular(100.58+1.8, 107);
$KSS-4630;	Curve.BeginTransition();
$KSS-4620;	Curve.End();
$KSS-4610;	Curve.BeginTransition();

$KSS-4605;	Gradient.BeginTransition();
$KSS-4595;	Gradient.BeginConst(-17.3);

$KSS-4585;	Curve.BeginCircular(-80+7.2+1.8, 0);
$KSS-4558;	Curve.BeginTransition();	Track['up'].Position(+3.2,0, 0,0);
$KSS-4558+35;	Curve.End();

呪文の意味は以下のようになります。
様式バージョンセット、基準座標セット、分岐器の終点から開始、勾配、カーブ、目印コメント、勾配、カーブ、・・・、分岐器の手前でデータ終了

勾配は線路の傾斜を示すものです。列車の運転は勾配に大きな影響を受けることがあり、BVEでも注意が必要です。通常はパーミル単位(1パーミルとは1000m進むごとに1m高さが変わること)で表され線路のそばに標識が設置されることが多いです。
勾配の変化する箇所において線路は一定曲率半径の縦カーブとなります(標準で縦曲線半径3,000mのケースが在来線クラスでは多い)。

勾配とは

鉄道のカーブは一定の曲率半径で設置され、場合により列車の速度を抑制する必要があります。カーブが急であったり高速通過用設備が無い場合は低い速度で通過することを余儀なくされます。カーブと直線を滑らかに接続するためトランジションカーブ(緩和曲線)が設けられる場合が多いです。
カーブの曲率半径により軌道中心間隔が拡大しますが、初めてのシナリオ制作では扱わないことを推奨します(「まずは1作品仕上げる」ことを優先して)。拡大量は「定数/R+定数×C(R:曲率半径、C:カント量)」などの式があります。カント量とはカーブで列車を安定させるため左右の線路に設ける高低差です。

鉄道のカーブについて
  • 車両(シナリオファイルから呼び出される)

Bvets Vehicle 0.03
PerformanceCurve = notch\notch.txt
Parameters = parameters82.txt
Panel = panel82.cfg
Sound = sound82.cfg
Ats = ATSKeihan800.dll
MotorNoise = motornoise\motornoise.txt

呪文の意味はだいたい以下のようになります。
様式バージョンセット、ノッチ曲線ロード、車両パラメータロード、運転台データロード、サウンド設定ロード、保安装置プラグインロード、モーター音設定ロード

ノッチ曲線は電車のモーター特性を示したデータです。
技術文献では「電流-引張力」「電流-ブレーキ力」「速度(または回転数)-電流」の曲線が制御状態ごとに表されることが多く、BVE車両データで適用するには電動車1両あたりの「速度-引張力」「速度-電流」曲線に変換する必要があります(表計算ソフトを活用することが多いです)。

ノッチ曲線とは

例としてパラメータファイル

Bvets Vehicle Parameters 2.01
FirstCar = M

[Cab]
BrakeNotchCount = 10
PowerNotchCount = 5
AtsCancelNotch = 1
MotorBrakeNotch = 2
ReverserText = 後,切,前
BrakeText = 弛,8°,16°,24°,32°,40°,48°,56°,64°,72°,抜取,非常
PowerText = OFF,P1,P2,P3,P4,P5

[SMEE]
MaximumPressure = 440000
BpInitialPressure = 490000
PressureRates = 0, 0, 0.02, 0.23, 0.37, 0.51, 0.62, 0.73, 0.84, 0.95, 1,1
LeverDelay = 0.5

[LockoutValve]
MaximumPressure = 420000
RegenerationLimit = 25

[Compressor]
UpperPressure = 750000
LowerPressure = 650000
CompressionSpeed = 1600

[Bc]
ApplyStart = 30000
ApplyStop = 10000
ReleaseStart = 30000
ReleaseStop = 10000
ApplySpeed = 500
ReleaseSpeed = 300

[Brake]
PistonArea = 0.45
ShoeFriction = 0.28, 0.01, 0.035

[Sap]
ApplySpeed = 360
ReleaseSpeed = 360
VolumeRatio = 25
[Bp]
ApplySpeed = 150
ReleaseSpeed = 300

[MainCircuit]
RegenerationLimit = 1
RegenerationStartLimit = 25
PowerNotchDelay = 0.5
BrakeNotchDelay = 0.5
ReverserDelay = 0.5

[Dynamics]
MotorcarWeight = 33625
MotorcarCount = 4
TrailerWeight = 26667
TrailerCount = 3
CarLength = 18.8

[ViewPoint]
X = -0.7
Y = 2.4
Z = -1.05

呪文の意味はだいたい以下のようになります。
先頭M車にセット(グリップ挙動のシミュレーションに影響)、ハンドル設定(各段の設定)、電磁直通ブレーキ(ブレーキシステムの一つ)のパラメータ設定、主制御装置の設定(応答特性)、力学パラメータ設定、視点座標設定

ほんとはまだまだあるんですが、既に情報が洪水しまくってると思うのでこの辺にしときます。やべぇよ・・・やべぇよ・・・

基本ソフトウェアがシナリオファイルを読んでごちょごちょ動くと、以下のようになるということです。

基本ソフトウェアがシナリオファイルを読んでごちょごちょ動いた様子(イメージ)

以上「そもそも「BVE Trainsim5のシナリオ」の実体は具体的に何か?」でした。


2.シナリオ制作のゴール設定

「要件定義」と一般に呼ばれます。
同人作品としてなら、ほどほどに煮詰まったらそれで設定完了として次のステップに移行してもいいのではないかと思います。

車両
狭義の「BVEシナリオ」と言えるかも(これ一つで運転曲線が新しくできますので)。

イメージ

特急車のイメージ
通勤車のイメージ

路線
言っちゃなんですが極論盆栽と同じ要領です。グリーンマットでも運転シミュレータとして成立します。某関西大手私鉄京〇〇津線みたいなのは盆栽の敷居を上げすぎているから参考にしてはいけません。内房線Ver.2.00(2020/09/23)などがゴールイメージを描く参考として理想的だと思います。

事業者により規格が異なるので注意が必要です。某関西大手私鉄の京〇電車みたいな特殊事例はBVEの仕様通りに作ると全然コレジャナイものになってしまうので、工夫しないと満足できる品質に仕上がらないかもしれません(複線間隔が他の路線で見られない寸法になっている、デッドマン厳しい、扉扱いは車掌ではなく運転士主導だからここで既にBVEの仕様からはみ出してる、カントえっぐ、特注構造物多すぎ、保安装置も他で例を見ないから流用できない、そもそも一駅間を除いて緩和曲線も縦曲線もない直線部分がほぼ無いとかなんなんだよ、など無数のエラーを吐いている)。

よくわからなかったらいったん一般的な設定を採用して仕上げてしまい、あとで実は違うことがわかってから対処してもよいのではないでしょうか。シナリオ制作もう一回遊べるドン!

線路に近い部分は高品質のテクスチャを用い、線路から離れたところは粗めに表現する
(慣れていないとこれでも作りこみすぎの領域。架線の配線とか信号ケーブルまで再現したり架線柱を一本一本現地モデルで作ったり…このシーンだと奥の方で上に道路が交差していることを表現できていれば十分ではないだろうか)
プレイ中に見えない部分の描写を省略している(応用編)

走って止まってなんかそれっぽかったらもうそれでいいんじゃないでしょうか。
どんな解像度の高いシナリオもフィクションなのですから。


作品を完成させた経験が浅ければ以下は次回作以降の課題としてもよいと思います。

パッケージ
共有することに意義を感じているなら一番意識を向けるのはここです。どれほど高級で精巧な作品でも触れられないならそれは無いも同然と受け取り沈黙する方もいらっしゃいます。「具体的にどの体験を提供するかデザイン」とも言えます。
プレイヤーの手数を最小化して目的を果たすことを意識するとよいのではないでしょうか。

京阪京津線シナリオはリリース当初、プレイヤーさんに来訪してもらうことをゴールにしていたため"その障害になる要素を可能な限り排除する"ことを意識しました。例えば、SNSにログインするのが面倒であることと同様にZIPを展開してカットアンドペーストの面倒はプレイヤーさんに意識させないようにするためインストーラを採用しました。(ただ、リリース後にドイツ語環境の方から「インストーラ無理、多分日本語環境で作られたから不具合出てる」と問い合わせいただいたので修正対応が必要でした。ウムラウトとかもあるしまあ多少はね?インストーラ検討の際はそういうこともあるのをお含み頂いてご判断ください)

XRマーケットでのポジショニング
広く知られたいならこれを徹底的に絞り込みましょう。BVEを知らない人にもBVEを知らないままBVEを楽しんでもらい活動の場を広げていきましょう。
各地で開催される運転会などはターゲットのひとつと言えるでしょう。
BVEを活用して地域価値向上への取り組みのひとつとして展開することも考えられます(地域価値向上への鉄道の活用は1.生活特化…えちぜん鉄道など、2.生活+観光…ひたちなか海浜鉄道など、3.観光特化…大井川鐵道など、4.経営力特化…伊予鉄道など といったように分類され、特に2・3に運転体験は刺さりやすい傾向があると推測される)。

この点考察すると、京阪電車のシナリオはどれだけ細かく作りこんだとしても「SANZEN-HIROBA」にかなわないという課題が浮上します。

「SANZEN-HIROBA」にできなくてBVEにできることはないのでしょうか?
いや、あります。
「無料」「どこでも」「誰でも」「簡易的に」
BVEは作品と人の組み合わせでどんどん可能性が広がるものです。
SteamやApp Storeなどいろんなサイトがありますがうまく棲み分けできたらいいですね。
※1 BVE基本ソフトウェアはスマホ対応できませんが、そこはターゲットの絞り込み要素としましょう 他にもできないことを挙げていくとターゲットの絞り込み解像度が上がっていきます
※2 本稿は"BVEシナリオを利用したあらゆる手段による収益化を否定する主張"をするつもりはございません

執筆時点で、BVE基本ソフトウェアが登場した当時と比較してインターネット普及の結果、電子情報の過剰供給が続き「一般の人々へのストレス過多」「誤解や偏見の拡散」「個人毎の情報消費偏り」「時間不足問題」「他者との比較による自己肯定感低下が過走」「ネガティブ情報への過剰反応」「表面的・断片的な理解で無意識に満足し知的劣化のネガティブループに陥る」といった現象が地球規模で生じており、これらに対処するには「地球規模での露出を前提としたシナリオ設計」「徹底的なローカル特化」のいずれかまたは両方に取り組むのが有効であると仮説を立てています(実を結ぶには非常に長い時間がかかるため最初のうちは目指しているものの形になっていない状況でもいいと思います)。
私の作品例では「地球規模で各個人好きな走り方ができるJR琵琶湖線シナリオ」「徹底的なローカル特化の京阪電車シナリオ」があります(無粋になるから作品に触れている時にそういう説明が出てくることは無いようにしていますが)。

インターネットの普及による商品やコンテンツの活動展開様式変化についての考察

話が少しふくらんでしまいました。
本稿では例として以下のようなゴール設定を行うことにします。

  • 車両は汎用的な系列を選択

  • 路線は特定の状況(日常の昼、季節は秋)を想定してシーンを埋める

  • 自分で遊んで楽しいシナリオに仕上げる

  • シナリオの外のことはシナリオが完成してから進める、と割り切る

BVEシナリオ作りたいのはいいけど、結局あなたがしたかったのは何でしたか?という問いにある程度方向性を持っておけば道を違える危険は避けやすいです、というお話。

開かれた理想 - 作品現物 = 話題性(良くも悪くも)

私が勝手に作った方程式
多分誰か先人が思いついてるだろうけどソース取ってくる時間なかった

以上「シナリオ制作のゴール設定」でした。


3.必要な準備

どうしてBVEシナリオ制作はとんでもなく多大な労力を要するのか。
その答えが本章と次章「4.制作中の基本操作」にあります。
そして手を付ける前の準備で制作能率は大きく変わります。
まあその制作能率ってのはぶっちゃけふたを開けてみないと評価できないので、必要最低限揃ったらさっさと制作に着手しちゃって、残りは後追いでそろえるのが良いと思います。

3-1.取材道具

  • スマートフォン …素材写真、サウンドレコーダー、動画撮影、車両性能ロガーなどこれ一つでそれなりにできます。ただしそれぞれの機能に特化した別道具に性能は格段に劣ります。(執筆時現在)型落ちの中古で十分。これのために残業や副業を増やすくらいなら制作時間に回して手持ちの道具で作れる品質で「足るを知る」方がはるかにQOL高いのでは。

執筆時点で一番安い機種を引いてみたらこれがでてきましたが、これで十分です(動画投稿サイトにアップロードされているデータで品質を確認しました)。予算面で困難があるならこれより5年前の機種でも電池劣化に注意すれば役割を全うすることが期待できます。

もっと上位の機種をお持ちであれば、スペック相応にお使いいただけます。

  • カメラ …スマホで満足なら不要。ミラーレス一眼と広角レンズ(収納性重視)・望遠レンズ(35mm換算200mm以上)各1本など。非常に古い機種を中古で入手した場合でもスマートフォンでは絶対到達できない品質の素材が量産されます。バッテリーの入手性・持続時間・運用(自分の体力と相談)に注意し、電源難民にならないようにだけ。セットアップ次第で動画撮影も完結する。

RAW撮影できて最安のものを探したら例えば以下のような機種。中古で15,000円くらい。

RAW撮影はカメラのセンサーが捉えたデータを、加工せずにそのまま保存する撮影方法です。JPEGで保存する際の劣化を避けられますが専用ソフトでの現像が必要でファイルサイズが大きい(撮影時の保存に何秒かかかる)ことに注意が必要です。ファイルサイズは機種により異なりますが入門機の1200万画素1枚で約15MBなど。カメラのセンサー自体にも微弱なノイズがあるためISO感度を下げて十分な受光量を確保して撮影しましょう(やむを得ずISO感度400以上になる場合はJPEG)。

RAW撮影とは
RAW撮影のNG事例。上:RAW 下:JPEG ISO感度400
明るさが揃ってなくてすみませんが、センサノイズが乗ったRAWは品質の高いJPEGでの劣化と大差ない素材でありながらファイルサイズが約3倍になり道具のスペックを引き出しきれない結果になります。ISO感度を最低値に固定する、絞りを開く、画素数を低く設定してセンサ面積当たりの受光量を大きくする、光量の豊富な夏の昼間に撮影するといった対策で改善できます。

標識の撮影などに強力な望遠はEマウントだと例えば以下のような機種。35mm換算80-300mm、中古で15,000円くらい。

コンパクトデジカメは原理的に画像品質を追求できない(センサーサイズが小さいため屋根の下で十分な受光量が得られない)のでミラーレス一眼を使えない場合の妥協点くらいで。ミラーレス一眼より安価ですから乗り換えまでのつなぎとして輝くことはあります。

例えば以下のような機種は非常に厳しい環境下での撮影に耐えますが、そんな環境のところに鉄道は走っておりませんし、最安値のミラーレス一眼に画像品質は及びません。登山や水泳もされている方が兼用される分には良いと思います。

無論、上を見ればキリがありません。お好みでセットを組みましょう。

  • ビデオカメラ …スマホで満足なら不要。アクションカメラの一番安い機種でスマートフォンの上位互換として機能する。一眼レフカメラよりも手ぶれに強く、コマ送りなどの際に鮮明なデータが得られます。

例えばこんな感じです。

  • ICレコーダー …スマホで満足なら不要。フロート録音、ガンマイク、バイノーラルマイクのセットが理想。ICレコーダー自体20年くらい進化し続けてもう来るところまで来ちゃってる感じなのでPCM録音さえできればスマートフォンの上位互換として機能する。

フロート録音は、音声データを浮動小数点数(符号&指数&仮数 例:114.514は浮動小数点数で+符号0.114514仮数×10^3指数となる)で記録することにより音声レベルの上限を実質的に無くして一般的なPCM録音より高い精度のデータが得られる録音方法です。執筆時点で多く流通しているフロート録音可能機材は32bitフロートなので仮数の精度だけで見れば24bitPCM録音と同等ですが、指数表現が入ることによりPCM録音では原理的に扱えない非常に小さな音の波形を捉えることができ、PCM録音より格段に高い精度を実現しています。風切り音やマイクへの誤接触による大レベルサウンド発生時も(素材としては意味はありませんが)クリッピング(音割れ)が起きにくい点も優れています。
特に、地下区間の急カーブと地上の高規格軌道を併せ持つ路線においては、地下区間の急カーブで非常に大きな音(カーブ内側より外側の方が同じ車輪回転数で長いレール延長を走り、通常は車輪踏面の傾斜で輪軸を自己操舵してスムーズにカーブを通過するが、曲率半径が一定以下の急カーブではカーブ内外のレール延長差が大きすぎることで輪軸自己操舵してなお車輪走行延長とレール走行延長とに差が生じることで”ゴゴゴゴゴ”みたいな摩擦音が生じ、トンネルに反響して大きな音となる)が発生しながら地上では高速走行しても収録される音量が小さい「大音量と小音量を同時に扱う状況」が生じますが、クリッピング回避しつつ有効な素材を多く取り込むにあたりフロート録音は非常に強力です。例えば京阪本線(北浜-天満橋と東福寺-七条で急カーブかつ天満橋-樟葉が高規格で静かな走行音)や東急東横線・みなとみらい線(渋谷-代官山と横浜-馬車道で急カーブかつ中目黒-日吉が高規格で静かな走行音)などはフロート録音で格段に取材効率が変わります。

フロート録音とは

例えばこんな感じです。

MP3形式のみ対応でPCM録音できない、ステレオ対応していない機種はBVEシナリオ制作には向いていません。

MP3は画像でのJPEGと同様圧縮劣化が生じます。
例えば一般的なネット配信で採用される128kbpsの場合、約15kHzより高い音がカットされます。全く使えないわけではありませんが、聴覚が鋭い方だと圧縮ノイズが気になって制作が窮屈かもしれません。
(ただし、一般的な人は20代後半から聴力が低下し始め10kHz程度の高音も聞き取りにくくなりますので、128kbpsMP3の劣化は問題にならない場合もあります。実際市場での標準規格になっている=商業的に成功していますから・・・。そして、BVEシナリオ作者も人間である以上いずれは加齢による聴力低下が避けられないことも忘れてはならないでしょう)

MP3形式を扱う場合の注意点

マイクは(入手できれば)データシートを確認して特性をうまく活かしましょう。
-20dBで感度1/10、-10dBで感度約1/3です(指数関数)。以下の例では横と後ろの音はだいたい1/3くらいになり高周波数サウンドは1/10くらいになりそう、みたいに読み取れます。マスコンハンドル操作音、コンプレッサー動作音などの素材確保が捗りそうです。

  • 距離計 …あると取材解像度が爆上がりする。ゴルフ用・建築用各1台あれば理想。一番安い機種で十分。

  • 加速度ロガー …上級者向け。速度計目視手書きメモで十分。好みによりRaspberry Pi等活用(アプリを自作してお手持ちのスマホに放り込んでもOK)。

3-2.PCインターフェース

PC本体は最低動作環境の性能で十分です。動作試験一号機も兼用できるので(リリース前にボリュームゾーン環境での試験データもあればなお良い)。たぶん最終的にCPUがボトルネックになるでしょうが、Ryzen 3相当以上であれば問題ないでしょう。メーカー製品の中にメモリが少なすぎる罠がたまにありますが、そういう製品は売れ筋から外れていくので油断しなければハマらないと思います(新製品が頻繁に登場し旧モデルの製品ページがすぐ消えるので具体例は出しにくいです。ご容赦ください)。
理想を言えば3画面以上。2画面までなら簡単にできますが3画面以上は本稿執筆時点で(BVEシナリオ制作入門者のボリュームゾーンは中高生と想定して)かなり高額の出費となります。その出費をするよりはとにかく作品を出してステップアップ目指した方が得策だと思います。
もし実現できた場合どうなるかですが、
「タスク管理」「編集」「資料表示」「シナリオビューワ」を開けている状況を想定して
「編集」「シナリオビューワ」を別画面にするだけで格段に能率が上がりますし
「編集」「資料表示」「シナリオビューワ」それぞれ別画面でほとんどストレスを感じません(個人の感想です)し、
そこからさらに4画面あればタスク管理も常時見やすく資料を2画面出してさらに能率向上という運用もできます。
Xを開けて時間浪費する罠には注意しましょう。

キーボードは人間工学系の製品が理想ですが、高価で手が届かない場合でもキーストロークが深い有線フルキーボードで十分です。(ノートPCなどでみられる一部のキーが特殊キーで呼び出され圧縮配置されているものだと能率が非常に悪いので外付けしてでも避けるべき)

「薄型キーボード」と称している製品はキーストロークが浅いのでBVEシナリオ制作には向いていません。

マウスやタッチパッドよりトラックボールの方が圧倒的に高能率です。一番安い中古のでいいからトラックボールを使いましょう。初めてさわる場合でもまあ2週間もあれば慣れます。もしかすると一番コスパがいい投資先かもしれないです。(あれっこの話は某艦〇れ界隈でも聞いた気がするでち)

3-3.BVE基本ソフトウェア最新版

開発環境であり実行環境でもあるものとして基本ソフトウェアをインストールします。
作品を共有する際、動作環境の明示に必要なのでバージョンと公開日を控えましょう。
例:「BVE基本ソフトウェアバージョン:5.8.7554.391 公開日:2020/09/23」

3-4.シナリオ制作支援ツール

必要なものを導入し、お好みによりデスクトップショートカットなどで呼び出しやすくしましょう。

3-5.エディタ

いくつか選択肢があります。

  • VSCode

メリット:機能が充実している・カスタマイズしやすい・バージョン管理システムに対応している・BVE制作支援ツール対応
デメリット:以前よりだいぶマシになったがまれにバグり散らして対処不能な状況が生じることがある まあMSだし

  • Notepad++

メリット:動作が軽い・BVE制作支援ツールを当てるだけで見やすく編集時の指向ノイズが少ない
デメリット:ファイルサイズが大きくなると動作が重くなる(10000行以上のマップファイルを編集していたら「早くリリースまでこぎつけないとまずい・・・」とひしひし感じていました)

  • お好みのテキストエディタ

文字コード指定保存できるなら制作に利用可能です。

3-6.(推奨)表計算ソフト

MS Excelがよく使われるようです。
座標計算、性能計算いろいろできます。

3-7.画像編集・加工ソフト

選択肢はたくさんありますが使い慣れたソフトを選びましょう。
シナリオの規模により何万回も開くこともあるので・・・

  • GIMP

  • Photoshop

最先端の機能はPhotoshopでなければ利用できませんが、GIMPでも十分作品完成までこぎつけられます。
軽いから、操作に熟練していて高能率だから、と他のお好みのソフトを使い続けても(必要な機能が揃っているなら)大丈夫です。

3-8.サウンド編集ソフト

お好みで。

  • Sazanami

  • Adobe Audition CC

3-9.3Dモデリングソフト

  • Metasequoia

  • Blender

3-10.ファイル内検索

WindowsOS標準機能でもフリーソフトでもお好みで。
「あの構文書いたのどこだっけ??」は結構な頻度で発生します。

ソフトウェアが揃ったらすぐに呼び出せるようWindowsタスクバーに配置するのもいいかもしれません。必要なソフトは後からでも増やせますし全然使わないものはいったん外すこともできます。

ここはお好みで

3-11.バージョン管理システム

お好みで。
あれば保安度が高くなりますがなくても作品は完成します。
BVEシナリオ制作能率向上と親和性が高いのはGitですが、完成品をユーザフレンドリーなフォーマットに整えるにはSVNの方が円滑です。
なお昨今のアプリ多様化の流れで分野横断的にGitが選ばれやすい状況となっており、今後も続くと予想されます。

  • Git

  • SVN

3-12.必要な科目の再履修

シナリオの表現範囲に応じて頭にインストールしましょう。
慣れないうちは全部取らずに今得意なところだけで一作品ずつ仕上げ、それから増やしていった方がいいと思います。

  • 英語:エラー発生時にある程度自力で対処できる程度

  • 物理:力学・電磁気学・波動(サウンド編集に必要)

  • 公民:倫理・社会のルール(取材からシナリオ共有までの作法)

  • 数学:集合と論理・三角関数・微分・図形・データ分析・確率あたりで。制作中特に障壁となりやすい分野である。制作中につまづいてから再履修してもよい。

  • プログラミング:ATSEx(おーとまさん)を活用する場合適宜(プログラミングが苦手な場合もBVEをきっかけに挑戦するのはとても素晴らしいと思います)

以上「必要な準備」でした。


4.制作中の基本操作

頭にインストールしましょう。

4-1.エディタとビューワの切り替え

左手で「Alt」+「Tab」を押している間リストが表示されるので「Tab」を押して移動、離すと切り替え。
「VSCode」or「Notepad++」⇔「BVE」切り替え等で頻繁に使います。

4-2.とてもよく使うショートカットキー

  • エディタ内検索:「Ctrl」+「F」

  • 切り取り:「Ctrl」+「X」 ※Z座標移動で非常によく使います

  • コピー:「Ctrl」+「C」

  • 貼り付け:「Ctrl」+「V」

  • 一手戻す:「Ctrl」+「Z」

  • 戻しすぎたのをやり直す:「Ctrl」+「Y」

  • 全部選択状態にする:「Ctrl」+「A」

  • 複数選択:「Shift」+「→」「↓」「←」「↑」

  • 上書き保存:「Ctrl」+「S」

4-3.バージョン管理

GitやSVNを活用しているならそれらのシステムの操作方法に従います。
Like A Lake制作チームではSVNを使っていますが、個人制作の場合は(メジャー,マイナー,パッチ)のバージョン番号とコミットメッセージつけて「BunBackup」等ソフトで自動バックアップ組んでおけばだいたい事足りるのではないでしょうか。
とりあえず何かしらのトラブルで何千時間かけたシナリオがパーという事態を避けれたらそれでいいと思います。

以上「制作中の基本操作」でした。


5.シナリオ制作の流れ

大変長らくお待たせいたしました。
「2.シナリオ制作のゴール設定」のゴールまで走り切る時がようやく来ました。

5-1.取材

どうして「3.必要な準備」にこの節が含まれなかったかというと、ここまでの準備が穴だらけの状態では取材時に要点を押さえることが難しいこと、ならびにシナリオ制作中にも再取材を必要とするケースが多々あり制作の営みに組み込まれた概念として解説することがお役に立ちやすいのではないかと考えたためです。

さて取材しに出発する前にマインドセットを。

大前提:
あなたは運送約款が適用される旅客の一人として法的に扱われます。
他のお客様のご旅行やプライバシーにも十分配慮し、駅係員・乗務員等から指示を受けた場合は滞りなく従いましょう。

危険が予想される行動の例:

  • 通行者の多い場所での撮影(衝突による怪我であなたが苦しむことはもちろん、視覚や聴覚に難のある方を巻き込んだ場合重大な事故につながるおそれがあります)

  • 大人数での取材(他のお客様が通行時微妙な気分になるかもしれません)

  • 他の旅客や事業者係員等のプライバシーを侵害する取材(顔だけでなく持ち物の特徴で個人を特定できることも多いです。収音中の声も同様です。私だと目を閉じていても声だけで誰が乗務しているか特定できますし…

  • 不安定な姿勢での取材(列車接近時は思いがけず突風に見舞われる場合があり、転倒・転落など重大な事態を引き起こす恐れがあります)

  • 長い棒の先に取材道具を付けスピーカーに向けて伸ばす(あなたが高圧電撃を受け命の危険にさらされるおそれがあります)

  • 三脚の使用(ホーム上だろうと列車内だろうと原則として公道上のルールが適用されます。家の前の公道で三脚立てられたら困りますよね)

  • フラッシュの使用(威力業務妨害で立件される場合もあります)

  • 非常用経路をふさぐ体勢での取材(取材中に震度7来たらあなた込みで非常に多くの方の命が危険にさらされます)

  • お身体の不自由な方を補助する設備付近での取材(お相手様はあなたが何をしているのかわからないので無防備で衝突し大けがの原因になります)

  • 荷物を散らかす(原則として公道上以下略)

  • 黄色い点字ブロックの以下略(時間がもったいないからこれ以上書かせないでください)。

一度の取材、一本の行程で全ての素材をそろえることは無理です。
誤差やノイズがゼロになる収録方法はありません。
想定している品質への影響が大きくないのであれば、採れた素材を組み合わせて活用しとにかく仕上げてしまいましょう。
どんな解像度の高いシナリオもフィクションなのですから。

  • 路線

    • 配線 …トポロジー、分岐器のクロッシング番数(応用 構造、材質、付帯設備)

    • 曲率半径 …軌道中心線のものか?各線路のものか?入力前に検証

    • 勾配 …標識の中で一番見つけやすいかも。書き取り漏らしが怖かったら望遠写真を撮ることで検証しやすい。

    • 各変曲点のキロ程 …架線柱に番号を付けて各々Z座標を求め、標識との位置関係から求める。慣れないうちは100m精度とかで十分それっぽくできると思います。5m精度でも10km以上のマップ制作に何年もかかるのはざらなので欲張りすぎると危険。

    • 信号機 …対向の信号機座標も記録しましょう。運転時の目印となる場合があります。

    • 速度制限標 …対向の標識も記録しましょう。

    • 停止目標 …対向の標識も記録しましょう。

    • セクション標 …BVEのシステムであまり表現されている例を見ませんが、実際は止まってはいけない箇所であり運転上重要なので記録しましょう。

    • 駅設備 …屋根、昇降機、看板など

    • 構造物 …橋梁、トンネル、留置線など

    • 隣接構造物や建造物の特徴 …線路の上を横切っているものをだいたい網羅していたらなんとかなるんじゃないでしょうか。踏切のキロ程を把握できれば誤差の小さい路線データに仕上げやすいです

    • 自然物 …大きさにより国土地理院データなども活用しましょう

    • 放送 …スピーカーのなるべく正面から指向性マイクを向けて収録。指向性マイクなくても編集ソフトで放送っぽく演出すればよし。車内放送はスピーカー位置を確認して収音しましょう。例えば京阪プレミアムカーでは「10C」「11C」席など。

    • ダイヤ、運用 …対向列車の設定に

線形の書き方例
路線取材データの例
(実際には非常に多くのデータを記録します。
数をこなしていれば本当に必要なものは何か見えてくると思います)
別の取材データ
取材しながらイメージしたシナリオ例
図書館等に活用できる資料があれば積極的に取りに行きましょう(建設誌など)
キロ程がわかるオブジェクトは重宝します
(ただし表記が誤っている場合もあるのであまり神経質にならないようにしましょう
周辺情報と照合してもっともらしい値を推定すればよいです)
セクション標の並び(事業者により様式が異なります)
  • 車両

    • 運転台 …運転台本体、圧力計、各種表示灯、速度計、保安装置表示灯など

    • サウンド …ブレーキ込め緩め、ドア開閉音左右、フランジ音、警笛、分岐器通過音、補助電源作動音、モーター音、ハンドル操作音、定速走行音、空気ばね作動音、コンプレッサー作動音など

      • 場合により車外からの収音が適していることもあります。

      • ジョイント音は運転席または台車直上から可能な限り近い位置から収録しましょう。

      • 主制御装置とモーターは離れたところにあるので同時に収録することが困難です。例えば京都市交10系電車の場合、主電動機は1800形(国際会館寄り1両目)にも搭載されていますがチョッパ制御のサウンドは1700形・1200形(2両目・5両目)でなければ聞こえないでしょう。補助電源は1800形・1600形・1100形(1・3・6両目)コンプレッサーは1800形・1100形(1・6両目)にあります。

    • 性能 …一般的に実車はカタログスペックより余裕を持った性能を持っているので、たくさん実測しましょう。カタログスペック上起動加速度2.8km/h/s?でも実測だと起動から60km/hまで20秒というのはよくあることです。

    • 保安装置 …システム構造、地上子位置、動作仕様など実装に必要な情報を入手しましょう。

運転台についてはカメラ画角とBVE画角のすり合わせが手間なので、
可能な限りBVE画角に近い態勢で取材しましょう
このアングルは下向きすぎでアウトです(計器やランプの素材は取れるかも)
運転台用素材の例(これはやりすぎ BVEは原則停電しません)
ノッチ曲線の例
(引張力=電流の関数、電流=走行速度の関数としてモデルを作り、引張力テーブル・電流テーブル・進段パラメータテーブルに落とし込むことで性能データができます)
ATS-Pの概要(出典:日本信号(株))
地上子の配置がわかる取材データの例

5-2.車両制作

まずは白紙状態の車両を作りましょう

基本ソフトと一緒にインストールしたであろう京成千葉線の京成3500形をコピーし、(この段階では正常に動作しなくていいので)取材で得た素材を上書きします。
全ファイル置き換えできた状態の車両をもって「白紙状態の車両」データとします。(白紙状態の車両は次回作のためのテンプレートとして保存するとよいかもしれません)

こういうところは生成AIでやればいいんじゃないか、と私は思いますが、執筆時点でやってみたら全然使えないデータが出てきました(ファイル構成が間違っている、BVE2とBVE5の書式が入り乱れている、文法に誤りがある、ファイルとパラメータの対応が間違っている)。そのデータを訂正できるスキルがあるなら生成AIを使わなくていいと思います。未来人に希望を託します。

白紙状態の車両から編集を進めていき完成に運びましょう。

  • vehicle.txt

Bvets Vehicle 2.00
PerformanceCurve = notch\notch.txt
Parameters = parameters.txt
Panel = panel6.cfg
Sound = sound.cfg
MotorNoise = motornoise\motornoise.txt
Ats32 = ATS_Kh_2gen_32.dll
Ats64 = ATS_Kh_2gen_64.dll

呪文の意味:性能データロード、車両パラメータロード、運転台データロード、サウンドデータロード、保安装置プラグインロード

  • notch.txt 性能ファイル

[Power]
Params = power\params.csv
Force = power\force.csv
MaxForce = power\force.csv
Current = power\current.csv
MaxCurrent = power\current.csv
NoLoadCurrent = power\current0.csv

[Brake]
Params = brake\params.csv
Force = brake\force.csv
MaxForce = brake\force.csv
Current = brake\current.csv
MaxCurrent = brake\current.csv
NoLoadCurrent = brake\current0.csv

呪文の意味:力行とブレーキにセクションを分ける、進段パラメータロード、空車状態引張力テーブルロード、満車状態引張力テーブルロード、電流テーブルロード
説明がよくわからなかったら京成3500形を開けて考察したらいいと思います。

  • params.csv 進段パラメータファイル

bvets vehicle performance table 0.01
#
BreakerDelay_On,0.5,0.5,0.5,0.5
BreakerDelay_Off,0.5,0.5,0.5,0.5
ResetTime,1,0,0,0
jerkregulation_up,20,20,20,20
jerkregulation_down,20,20,20,20
CurrentReducingTime,0,0,0,0
currentlimitingtime,0,0,0,0
requirednotch_up,2,3,4,5
requirednotch_down,0,1,2,3
stepdelay_up,0,0,0,0
stepdelay_down,0,0,0,0
cutoffcurrent_empty,0,0,0,0
cutoffcurrent_full,0,0,0,0

VVVF車の事例です。界磁位相制御とかの緻密な再現をしようとしたらだいぶ複雑になるので、慣れないうちはVVVF車のような挙動をする設定で近似するのがいいと思います(緻密な再現はリメイク時にすればよいでしょう。そもそも100点の車両データなどこの世にないということに留意して着地点を設定しましょう)。

  • force.csv

bvets vehicle performance table 0.01
#
0,13547,17627,26131,29587
15,13547,17627,26131,29587
48,4234,17627,26131,29587
49,4148,17627,25598,28984
50,4065,17627,25086,28404
55,3695,17627,22806,25822
60,3387,16159,20905,23670
65,3127,14916,19297,21849
70,2903,13850,17919,20289
75,2547,12149,15717,17796
76,2484,11847,15327,17354

引張力=電流の関数、電流=走行速度の関数としてモデルを作り、引張力=走行速度の関数として投射したモデルです。
走行速度の間隔が空いているところは線形補完されます。
特性域(この例だと48km/h以上)は非線形になるのでデータを打つ数が多くなります。

電流=走行速度の関数 でテーブルを作ることで電流テーブル(current.csv)も作成できます。
応過重最大のケースは1人65kg×定員で設定するケースが多いようです。

  • panel.txt

本体とパーツを適宜配置してください。
Layerは手前から降順な点がBVE独特。

配置例
  • sound.txt

対応するサウンドファイルに設定してください。

車両のための保安装置

全部出すと長すぎるので機能面で最低限の部分だけ載せてみました。
約20年前のBVE4での作り方(つまりめっちゃ古い)なので、都度適切なやり方に置き換えてお納めください。

  • Ats.cpp 例示用

クラス定義やインスタンス生成は省略。

// ヘッダ読み込み
#include "stdafx.h"
#include "CVehicle.h"

BOOL APIENTRY DllMain( HANDLE hModule, 
                       DWORD  ul_reason_for_call, 
                       LPVOID lpReserved ){


初期値を入れる。
(中略)

    return true;
}

// 車両クラス初期化と解放
ATS_API void WINAPI Load(void){	pVehicle = new CVehicle;	}
ATS_API void WINAPI Dispose(void){	delete pVehicle;	}

ATS_API void WINAPI atsSetVehicleSpec(ATS_VEHICLESPEC vehicleSpec){	pVehicle->SetVSpec(vehicleSpec);	}
ATS_API void WINAPI atsInitialize(int brake){	pVehicle->Init(brake);	}

// メインループ
ATS_API ATS_HANDLES WINAPI atsElapse(ATS_VEHICLESTATE vehicleState, int *panel, int *sound){

	pVehicle->SetATScond(vehicleState);	// ATSの状態更新
	pVehicle->CSound(sound);	// サウンド処理
	pVehicle->ElapseState(vehicleState);	// 諸状態の更新
	pVehicle->ElapseHandle(&HOutput);	// ハンドル指令の更新
	pVehicle->SetPanel(panel);	// 運転台表示の更新
	return HOutput;//ATS_HANDLES構造体を返します。
}

ATS_API void WINAPI atsSetSignal(int signal){
	信号が変化したら照査パターンを更新するなど。
}

以下略
  • ATSsampleroute.cpp

例としてK-ATSを想定してATSの挙動を制御します。簡略化しています。

ヘッダ読み込み

void CVehicle::SetATScond(ATS_VEHICLESTATE vehicleState){

停止パターン制限速度 = 停止パターン関数(vehicleState.Location);
減速パターン制限速度 = 減速パターン関数(vehicleState.Location);//減速信号や曲線・勾配の制限速度を守るパターン
パターン接近検知速度 = パターン接近検知関数(vehicleState.Location);

フレーム更新時処理(諸状態の条件から外れていれば解除する)

if(vehicleState.Speed > パターン接近検知速度) パターン接近状態に更新(CVehicleメンバ関数に作っておく)
if(vehicleState.Speed > 減速パターン制限速度) ATS減速制御状態に更新
if(vehicleState.Speed > 停止パターン制限速度) ATS停止制御状態に更新

}

実際には減速パターンは信号や曲線、勾配などで複数重ね合わされます。制限速度は全パターンのうち最も低いものが適用されます。
保安装置により地上子通過時にパターン更新する場合がありますが、それはSetBeaconData関数からSetATScond関数にあたるものを呼び出します。

パターン曲線は平方根関数となり、走行位置でのパターン制限速度は以下の式から得られます(走行位置と速度制限開始位置との運動エネルギーの関係式から変形 導出略)。

v_p = sqrt( v_t^2 - 2a(l_c - l_t) - 2g(h_c - h_t) )

v_p:パターン制限速度,v_t:目標速度,a:常用最大ブレーキ減速度,
l_c:現在の走行位置座標,l_t:制限速度が適用される位置座標,h_c & h_t:標高g:重力加速度
sqrt:平方根関数

(簡易実装で勾配を考慮しないならsqrt内3項目は不要です)
常用最大ブレーキ減速度が4.00km/h/sの場合、a=4.00/3.60=1.11m/s/sとなります。
重力加速度は9.80m/s/sが一般的に採用されます。
制限速度が適用される位置座標は残り距離をBeacon.Put構文を介して保安装置プラグインに入力します(信号によるパターンか曲線によるパターンかといった情報も地上子種別や送る値を工夫して渡します)。Beacon.Put構文は信号に干渉せずATSによる減速制御で速度制限を守れるよう配置します。

パターン接近検知については、減速・停止パターン-5km/h以上で検知する場合や半ブレーキ(常用最大の半分のブレーキ力)で所定速度まで減速する状態で検知する場合などがあり、保安装置ごとに異なりますので仕様を確認してください。

保安装置が点制御であれば、常時照査する必要はなく地上子を通過した時にATS状態を更新すればよいです(復帰にはリセットスイッチを実装)。

その他、BVE基本ソフトウェアに実装されていないけれども演出上重要な機能(転動防止ブレーキやドアが開いている時はチャイムを鳴らす機能など)もATSプラグインで実装します。

5-3.路線制作

5-3-1.準備

まずは白紙状態のマップを作りましょう

車両データの初期状態表示試験に使っているマップのコードを以下に示します。

BveTs Map 2.02
0;

実際の制作では以下の感じかなと(路線や演出状況によりパラメータは異なります)

BveTs Map 2.02

	Structure.Load('Structures.csv');
	Sound.Load('Sounds.csv');
	Sound3D.Load('Sounds3D.csv');
	Signal.Load('Signals.csv');
	Station.Load('Stations.csv');

	Section.SetSpeedLimit(0,8,15,20,25,30,35,40,45,50,55,60,65,70,75,80,85,90,95,100,105,110);
	Irregularity.Change( 0.0005, 0.0010, 0.0003, 100, 100, 25 );

	Light.Ambient(0.9375, 0.9375, 0.9375);
	Light.Diffuse(0.125, 0.125, 0.125);
	Light.Direction(75, 225);

	Adhesion.Change(0.234, 0, 0.005478851);
	Fog.Set(0.0004, 0.875, 0.9375, 1);

	Curve.SetGauge(1435/1000);	Curve.SetCenter(1435/2000);	Curve.SetFunction(1);

	Track['Up'].Cant.SetGauge(1435/1000);	Track['Up'].Cant.SetCenter(1435/2000);	Track['Up'].Cant.SetFunction(1);
	Track['Down'].Cant.SetGauge(1435/1000);	Track['Down'].Cantr.SetCenter(1435/2000);	Track['Down'].Cant.SetFunction(1);

白紙状態のマップは次回作のためのテンプレートとして保存するとよいかもしれません。

5-3-2.線形の仮置き

自線、本線、自線から近い順に別線の順で配置しましょう。
架線柱のZ座標推定値ははじめのうちは精度が高くなくてよいのでとにかく出して仮置きに活用しましょう。
この段階ではまだ風景を埋めてはいけません(風景を埋めた後のZ座標修正は作業量が膨大になるため)。

立体交差の事例:
(最初は変曲点の座標に大きな誤差が無ければ十分で、そこから調整していけばいいと思います)

$MLS = 50338;

$MLS-44676; //架線柱

$MLS-44673-75/2;
	Gradient.BeginTransition();
	Track['JRNara_down'].Y.Interpolate(0.6,-4000);
$MLS-44673;
$MLS-44673+75/2;
	Gradient.BeginConst(33.0);
	Track['JRNara_down'].Y.Interpolate(-0.6,0);

$MLS-44669; //ニノ橋踏切+-6.5

$MLS-44650; //府道

$MLS-44640;
	Track['JRNara_down'].X.Interpolate(+15.6,0);

$MLS-44631; //架線柱
$MLS-44586; //架線柱
$MLS-44538; //架線柱
$MLS-44513; //架線柱

$MLS-44510-75;
	Curve.BeginTransition();
	Track['down'].Cant(0);
	Track['up'].Cant(0);
	Track['up'].Position(+3.4,0, 0,0);
	Track['JRNara_down'].X.Interpolate(+22.6,-800);
$MLS-44510-75/2;
	Track['JRNara_down'].X.Interpolate(+27.1,-300);

$MLS-44510;
	Curve.BeginCircular(+201.17+1.9, 148);
	Track['down'].Cant(148);
	Track['up'].Cant(148);
	Track['up'].Position(+3.4+0.21,0, 0,0);
	Track['JRNara_down'].X.Interpolate(+28.1,-220);
$MLS-44510+52;

$MLS-44488; //架線柱
$MLS-44463; //架線柱

$MLS-44460-52;
$MLS-44460;
	Curve.BeginTransition();
	Track['down'].Cant(148);
	Track['up'].Cant(148);
	Track['JRNara_down'].X.Interpolate(+20.1,-200);
$MLS-44460+55/2;
	Track['JRNara_down'].X.Interpolate(+10.3,-800);

$MLS-44460+55;
	Curve.End();
	Track['down'].Cant(0);
	Track['up'].Cant(0);
	Track['up'].Position(+3.4+0.21,0, 0,0);
	Track['JRNara_down'].X.Interpolate(-2.7,1200);

$MLS-44438; //架線柱

$MLS-44435-75/2;
	Gradient.BeginTransition();
	Track['JRNara_down'].Y.Interpolate(-6.3,4000);
$MLS-44435;
$MLS-44435+75/2;
	Gradient.End();
	Track['JRNara_down'].Y.Interpolate(-7.5,0);

$MLS-44408; //架線柱

//奈良線立体交差

$MLS-44373; //架線柱
$MLS-44348; //架線柱

$MLS-44345-75/2;
	Gradient.BeginTransition();
	Track['JRNara_down'].Y.Interpolate(-7.5,4000);
$MLS-44345;
$MLS-44345+75/2;
	Gradient.BeginConst(-33.0);
	Track['JRNara_down'].Y.Interpolate(-6.3,0);

$MLS-44325-75;
	Curve.BeginTransition();
	Track['down'].Cant(0);
	Track['up'].Cant(0);
$MLS-44325-75/2;
	Track['JRNara_down'].X.Interpolate(-22.5,280);
$MLS-44325;
	Curve.BeginCircular(-261.52+1.9, -160);
	Track['down'].Cant(-160);
	Track['up'].Cant(-160);
	Track['up'].Position(+3.46+0.16,0, 0,0);
	Track['JRNara_down'].X.Interpolate(-35.5,300);
$MLS-44325+68;

$MLS-44323; //架線柱
$MLS-44298; //架線柱
$MLS-44273; //架線柱
$MLS-44248; //架線柱
$MLS-44223; //架線柱 変電所接続

$MLS-44220;
	Curve.BeginTransition();
	Track['down'].Cant(-160);
	Track['up'].Cant(-160);
	Track['JRNara_down'].X.Interpolate(-44.0,320);
$MLS-44145-75/2;
	Track['JRNara_down'].X.Interpolate(-38.3,800);
$MLS-44145;
	Curve.End();
	Track['down'].Cant(0);
	Track['up'].Cant(0);
	Track['up'].Position(+3.4+0.16,0, 0,0);
	Track['JRNara_down'].X.Interpolate(-29.0,-1200);

$MLS-44193; //架線柱
$MLS-44163; //架線柱
$MLS-44123; //架線柱

$MLS-44123-75/2;
	Gradient.BeginTransition();
	Track['JRNara_down'].Y.Interpolate(-1.2,-4000);
$MLS-44123;
$MLS-44123+75/2;
	Gradient.End();
	Track['JRNara_down'].Y.Interpolate(0.0,0);

$MLS-44145;
	Curve.BeginTransition();
	Track['down'].Cant(0);
	Track['up'].Cant(0);
$MLS-44123-22/2;
	Track['JRNara_down'].X.Interpolate(-26.1,-380);
$MLS-44123;
	Curve.BeginCircular(+402.34+1.8, 106);
	Track['down'].Cant(106);
	Track['up'].Cant(106);
	Track['up'].Position(+3.4+0.11,0, 0,0);
$MLS-44123+45/2;

$MLS-44083; //架線柱
$MLS-44043; //架線柱

$MLS-44053-45/2;
$MLS-44053;
	Curve.BeginTransition();
	Track['down'].Cant(106);
	Track['up'].Cant(106);
	Track['up'].Position(+3.4+0.11,0, 0,0);
	Track['JRNara_down'].X.Interpolate(-12.8,-400);
$MLS-44053+45/2;
	Track['JRNara_down'].X.Interpolate(-12.1,0);
$MLS-44053+45;
	Curve.End();
	Track['down'].Cant(0);
	Track['up'].Cant(0);
	Track['up'].Position(+3.4,0, 0,0);

$MLS-44013; //架線柱
立体交差の表示例

プレイ中にゆがみが目立たなければ十分だと思います。

立体交差の表示例2 ※この箇所はプレイ中1秒未満で通過して次のシーンに入ります

2面4線島式ホームの駅の事例:

$MLS = 21347;
// PLS=池田秦線連立事業高架切替地点からの調整座標
$PLS = $MLS+135;
// RLS=枚方市駅連立事業高架切替地点からの破差調整座標
$RLS = $PLS-85;
// KLS=牧野駅高架化事業船橋川橋梁地点からの破差調整座標
$KLS = $RLS-42;

//S21:丹波橋1番線

$KLS+39700;
	Track['Tanbabashi3'].Cant.SetGauge(1435/1000);	Track['Tanbabashi3'].Cant.SetCenter(1435/2000);	Track['Tanbabashi3'].Cant.SetFunction(1);
	Track['Tanbabashi4'].Cant.SetGauge(1435/1000);	Track['Tanbabashi4'].Cant.SetCenter(1435/2000);	Track['Tanbabashi4'].Cant.SetFunction(1);

$KLS+39753;
   	Track['Up'].Position(0, 0);
    Track['Up'].X.Interpolate(0, 0);
   	Track['Down'].Position(3.6, 0);
    Track['Down'].X.Interpolate(3.6, 0);

   	Track['Tanbabashi2'].Position(0, 0);
    Track['Tanbabashi2'].X.Interpolate(0, 0);
   	Track['Tanbabashi3'].Position(3.6, 0);
    Track['Tanbabashi3'].X.Interpolate(3.6, 0);
   	Track['Tanbabashi1'].Position(0, 0);
    Track['Tanbabashi1'].X.Interpolate(0, 0);
   	Track['Tanbabashi4'].Position(3.6, 0);
    Track['Tanbabashi4'].X.Interpolate(3.6, 0);

$KLS+39758;
//1番線分岐
    SpeedLimit.Begin(25);
    Curve.Begin(-166.4);
    Track['Tanbabashi1'].X.Interpolate(0, 0);
    Track['Tanbabashi2'].X.Interpolate(0, 166.4);
    Track['Tanbabashi3'].X.Interpolate(3.6, 166.4);
    Track['Tanbabashi4'].X.Interpolate(3.6, 166.4);

$KLS+39758+20;
    SpeedLimit.End();
    Curve.End();
    Track['Tanbabashi1'].X.Interpolate(0, 0);
    Track['Tanbabashi2'].X.Interpolate(1.2, 0);
    Track['Tanbabashi3'].X.Interpolate(3.6+1.2, 0);

$KLS+39773;
//4番線分岐
    Track['Tanbabashi4'].X.Interpolate(4.3, 115);

$KLS+39778;
    Track['Tanbabashi4En'].X.Interpolate(15.3, 0);
$KLS+39773+20;
    Track['Tanbabashi4'].X.Interpolate(8.0, -1000);

$KLS+39788;
    Curve.Begin(1000);
    $Tanbabashi2_X = 2.4;
    Track['Tanbabashi2'].X.Interpolate($Tanbabashi2_X, -1000);
    Track['Tanbabashi3'].X.Interpolate($Tanbabashi2_X+3.6, -1000);
    Track['Tanbabashi4En'].X.Interpolate(16.7, -1000);

$KLS+39788+120;
	Curve.End();
    // この部分はホーム幅が資料から既知なので変数使わない
    Track['Tanbabashi2'].X.Interpolate(9.8, 0);
    Track['Tanbabashi3'].X.Interpolate(9.8+3.6, 0);
    Track['Tanbabashi4'].X.Interpolate(9.8+3.6+10.4, 0);

$KLS+39813-15;
	Gradient.BeginTransition();
$KLS+39813;
$KLS+39813+15;
	Gradient.End();

$KLS+39833;
    Track['Tanbabashi4'].X.Interpolate(19.0, -100);

$KLS+39853;
    Track['Tanbabashi4'].X.Interpolate(22.3, -1000);
    Track['Tanbabashi4En'].X.Interpolate(22.3, 0);

$KLS+39963;
    Curve.Begin(300);
    Track['Tanbabashi2'].X.Interpolate(9.8, -400);
    Track['Tanbabashi3'].X.Interpolate(9.8+3.6, -800);
    Track['Tanbabashi4'].X.Interpolate(9.8+3.6+2.8+7.6, -300);
    Track['Tanbabashi3'].Cant.BeginTransition();

$KLS+39983;
    $Tanbabashi2_X = 9.3;
    Track['Tanbabashi2'].X.Interpolate($Tanbabashi2_X, -900);
    Track['Tanbabashi3'].X.Interpolate($Tanbabashi2_X+3.7, -900);
    Track['Tanbabashi4'].X.Interpolate($Tanbabashi2_X+13.9, -300);

$KLS+40003;
    Track['Tanbabashi4'].X.Interpolate(21.3, -600);

$KLS+40028;
    Curve.Begin(900);
    $Tanbabashi2_X = 5.9;
    Track['Tanbabashi2'].X.Interpolate($Tanbabashi2_X, 900);
    Track['Tanbabashi3'].X.Interpolate($Tanbabashi2_X+4.6, 900);
    Track['Tanbabashi4'].X.Interpolate(17.6, 2000);
    Track['Tanbabashi3'].Cant.Begin(150/1000);

$KLS+40048;
    SpeedLimit.Begin(25);
    Curve.Begin(100);
    // トングレールは内側のみ可動、外側リードレールは基本レールと直結されている
    $Tanbabashi2_X = 3.9;
    Track['Tanbabashi2'].X.Interpolate($Tanbabashi2_X, -200);
    Track['Tanbabashi3'].X.Interpolate($Tanbabashi2_X+5.1, -200);
    Track['Tanbabashi4'].X.Interpolate(14.1, -200);
    Track['Tanbabashi1An'].X.Interpolate(0, -100);

$KLS+40068;
    Curve.Begin(-100);
    $Tanbabashi2_X = 1.0;
    Track['Tanbabashi2'].X.Interpolate($Tanbabashi2_X, 60);
    Track['Tanbabashi3'].X.Interpolate($Tanbabashi2_X+5.7, 60);
    Track['Tanbabashi4'].X.Interpolate($Tanbabashi2_X+8.8, 80);
    Track['Tanbabashi1An'].X.Interpolate(-2.03, 100);

//1番線合流
$KLS+40078;
    SpeedLimit.Begin(65);
    Curve.Begin(600);
    Track['Tanbabashi1'].X.Interpolate(0, 0);
    Track['Tanbabashi2'].X.Interpolate(0, 0);
    Track['Tanbabashi3'].X.Interpolate(5.4, 0);
    Track['Tanbabashi4'].X.Interpolate(5.4+1.6, 166.4);
    Track['Tanbabashi1An'].X.Interpolate(-3.5, 400);
    Track['Tanbabashi4'].Cant.BeginTransition();

$KLS+40088;
    Track['Tanbabashi1An'].X.Interpolate(-4.3, 0);

//4番線合流
$KLS+40098;
    Track['Tanbabashi3'].X.Interpolate(4.3, 400);
    Track['Tanbabashi4'].X.Interpolate(4.3, 0);
    Track['Tanbabashi4'].Cant.Begin(150/1000);

	Curve.BeginTransition();

$KLS+40110-29;
	Gradient.BeginTransition();
$KLS+40110+29;
    Gradient.Begin(28.6);

$KLS+40123;
    Curve.Begin(402+1.8);
   	Track['Tanbabashi2'].Position(0, 0);
    Track['Tanbabashi2'].X.Interpolate(0, 0);
   	Track['Tanbabashi3'].Position(3.6, 0);
    Track['Tanbabashi3'].X.Interpolate(3.6, 0);
   	Track['Tanbabashi1'].Position(0, 0);
    Track['Tanbabashi1'].X.Interpolate(0, 0);
   	Track['Tanbabashi4'].Position(3.6, 0);
    Track['Tanbabashi4'].X.Interpolate(3.6, 0);

	Track['Up'].Position(0, 0);
    Track['Up'].X.Interpolate(0, 0);
   	Track['Down'].Position(3.6, 0);
    Track['Down'].X.Interpolate(3.6, 0);
2面4線島式ホームの駅表示例

大きな駅の事例:

//0m=東京駅から400km地点
$KytStStart = 90000;

(中略)

$KytStStart+23256;
	Curve.BeginTransition();
	Track['kyoto_5'].Position(0,0, 0,0);
	Track['up_in_2'].Position(+9.0,0, 2000,0);
	Track['up_out_1'].Position(+12.8,0, 1000,0);
	Track['storage'].Position(+4.5,0, 1200,0);
	Track['shinkan_u'].Position(-55,8, 500,0);

//高倉通立体交差

$KytStStart+23270;
	Track['5_3'].Position(+2.25,0, -300,0);

$KytStStart+23280;
	Track['kyoto_7'].Position(-8.5,0, 700,0);
//7-8渡り線
	Track['7_8'].Position(-8.5,0, -500,0);
	Track['nara_dw'].Position(-13.0,0, 500,0);
	Track['kyoto_9'].Position(-13.0,0, -500,0);

$KytStStart+23291;
//架線柱

$KytStStart+23300;
	Track['storage'].Position(+4.9,0, 400,0);
	Track['5_3'].Position(+4.9,0, 0,0);
	
$KytStStart+23305;
	Curve.BeginCircular(-400,-45);
	Track['up_in_2'].Position(+9.6,0, 400,0);
	Track['up_out_1'].Position(+13.8,0, 200,0);
	Track['kyoto_7'].Position(-11.8,0, 900,0);
	Track['7_8'].Position(-13.0,0, 400,0);
	Track['kyoto_9'].Position(-17.0,0, 600,0);

$KytStStart+23325;
	Track['nara_dw'].Position(-17.3,0, -500,0);
	Track['up_in_2'].Position(+11.1,0, 500,0);
	Track['storage'].Position(+6.8,0, 800,0);
	Track['kyoto_3'].Position(+6.8,0, 800,0);
	Track['storage_2'].Position(+6.8,0, 160,0);
	//4番線分岐
	Track['kyoto_4'].Position(0,0, 200,0);

$KytStStart+23326;
//架線柱

$KytStStart+23330;
	Curve.BeginTransition();
	//奈良線シーサス
	Track['9_10'].Position(-21.1,0, -300,0);
	Track['10_9'].Position(-24.9,0, 180,0);

$KytStStart+23335;
	Curve.BeginCircular(-800,-45);
	Track['shinkan_u'].Position(-60,8, 600,0);

$KytStStart+23345;
	Track['nara_dw'].Position(-18.5,0, 0,0);
	Track['7_8'].Position(-18.5,0, 0,0);
	Track['kyoto_8'].Position(-18.5,0, 800,0);
	Track['kyoto_9'].Position(-23.0,0, 600,0);

$KytStStart+23350;
	Track['storage_2'].Position(+11.5,0, 500,0);
	Track['up_in_2'].Position(+14.0,0, 200,0);
	Track['kyoto_4'].Position(+2.0,0, -400,0);
	Track['up_out_1'].Position(+22.6,0, 0,0);
	Track['kyoto_1'].Position(+22.4,0, 0,0);
	//0番線分岐
	Track['kyoto_0'].Position(+22.4,0, 300,0);

$KytStStart+23355;
	Track['9_10'].Position(-26.1,0, 150,0);
	Track['10_9'].Position(-26.1,0, -300,0);

$KytStStart+23365;
	Curve.BeginTransition();

$KytStStart+23366;
	Track['kyoto_4'].Position(+3.6,0, 400,0);
//架線柱

$KytStStart+23370;
	Curve.BeginCircular(-400,-45);
	Track['shinkan_u'].Position(-58,8, 400,0);

$KytStStart+23375;
	Track['storage_2'].Position(+18.8,0, 0,0);
	Track['kyoto_3'].Position(+13.8,0, -1500,0);
	Track['up_in_2'].Position(+19.0,0, 300,0);
	Track['kyoto_2'].Position(+18.8,0, 600,0);
	Track['kyoto_0'].Position(+30.4,0, -500,0);
	Track['2_1'].Position(+18.8,0, 200,0);

$KytStStart+23380;
	Track['9_10'].Position(-30.0,0, 0,0);
	Track['10_9'].Position(-26.2,0, 0,0);

$KytStStart+23395;
	Curve.BeginTransition();
	Track['kyoto_4'].Position(+6.6,0, -3000,0);
	Track['kyoto_8'].Position(-22.0,0, 0,0);
	Track['kyoto_9'].Position(-27.0,0, -1000,0);

$KytStStart+23396;
//架線柱

$KytStStart+23400;
	Curve.End();
	Track['kyoto_1'].Position(+34.9,0, -400,0);
	Track['kyoto_0'].Position(+39.4,0, -400,0);
	Track['kyoto_2'].Position(+27.8,0, -260,0);
	Track['2_1'].Position(+29.6,0, -180,0);
	Track['kyoto_7'].Position(-16.1,0, -1000,0);
	//留置線分岐
	Track['kyoto_st_1'].Position(+18.1,0, -400,0);

$KytStStart+23405;
	Curve.BeginTransition();
	Track['kyoto_4'].Position(+8.1,0, -1000,0);

$KytStStart+23426;
//架線柱

$KytStStart+23430;
	Curve.BeginCircular(373,45);
	Track['kyoto_3'].Position(+22.7,0, -500,0);
	Track['kyoto_4'].Position(+11.4,0, -600,0);
	Track['kyoto_8'].Position(-22.5,0, 2000,0);
	Track['kyoto_9'].Position(-28.5,0, 2000,0);
	Track['shinkan_u'].Position(-50,8, -400,0);

$KytStStart+23440;
	Track['kyoto_st_1'].Position(+21.8,0, -800,0);
	Track['kyoto_st_2'].Position(+21.8,0, -300,0);

$KytStStart+23450;
	Track['kyoto_2'].Position(+40.0,0, -400,0);
	Track['2_1'].Position(+45.0,0, 0,0);

$KytStStart+23456;
//架線柱

$KytStStart+23470;
	Track['kyoto_st_2'].Position(+21.5,0, 800,0);
	Track['kyoto_7'].Position(-16.3,0, 0,0);
$KytStStart+23470-5;
	Gradient.BeginTransition();
$KytStStart+23470+5;
	Gradient.End();

$KytStStart+23492;
//架線柱

$KytStStart+23495;
	Curve.BeginTransition();

$KytStStart+23515;
	Curve.End();
	Track['kyoto_4'].Position(+14.9,0, 0,0);
	Track['kyoto_3'].Position(+27.0,0, 0,0);
	Track['kyoto_2'].Position(+44.0,0, 0,0);
	Track['kyoto_1'].Position(+48.5,0, 0,0);
	Track['kyoto_0'].Position(+53.0,0, 0,0);
	Track['kyoto_st_1'].Position(+23.2,0, 0,0);
	Track['kyoto_st_2'].Position(+19.4,0, 0,0);
	Track['shinkan_u'].Position(-45,8, 0,0);
大きな駅の配線表示例

5-3-3.信号・標識の配置

信号機 → 停止標識 → 速度制限標識 → 踏切遮断反応灯 → 架線死区間標識 → 勾配標 → 曲線標 → 距離標(現時点ではまだ正確な座標出なくてよい) → 力行標・惰行標 → その他運転に必要な標識
みたいな順で配置するとよいでしょう。
架線柱とのZ座標位置関係を把握できていれば円滑に進行できます

信号の配置例を以下に示します。
もしかしたら修正するかもしれない事態に備えて修正する構文はひとまとめで配置します。

//4103
$MLS-41760;
Structure['SigPole01'].Put('down', -2.25,0,0.2, 0,0,0, 1,0);
Structure['Signal_4_tie01L'].Put('down', -1.9,+3.5,0, 0,0,0, 1,0);
Signal['Sig_4LED'].Put(1,'down', -1.9,+3.5,0, 0,0,0, 1,0);
Section.BeginNew(0,2,3,4);
Structure['SignalNB_4103'].Put('down', -1.9,+3.5-0.01,0, 0,0,0, 1,0);

$MLS-41449-5;
Structure['MissstartStoperHold02'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['MissstartStopperLoop_5m'].Put('down', 0,0.05,0, 0,0,0, 1,0);
$MLS-41449;
Structure['MissstartStoperHold02'].Put('down', 0,0,0, 0,0,0, 1,0);
$MLS-41449;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-41449+10;
//Beacon.Put(1,1,1);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);

$MLS-41449; //確
Structure['StopAttention_kaku'].Put('down', -2.5,+2.1,-0.4, 0,0,0, 1,0);
Structure['StopAttention_light_on'].Put('down', -2.5,+2.1,-0.4, 0,0,0, 1,0);

$MLS-41263;
//Beacon.Put(2,1,1);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);

$MLS-41265; //通
Structure['StopAttention_p'].Put('down', -2.75,+2.1,-0.4, 0,0,0, 1,0);
Structure['StopAttentionCover'].Put('down', -2.75,+2.1,-0.4, 0,0,0, 1,0);
Structure['StopAttention45'].Put('down', -2.75,+1.4,-0.4, 0,0,0, 1,0);

$MLS-41223-122;
Beacon.Put(0,1,150);	// 30照査
Structure['Beacon09_Lim25'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-4.16, 0,90,0, 1,0);

$MLS-41223-47;
Beacon.Put(0,1,50);	// 20照査
Structure['Beacon09_Lim15'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-2.77, 0,90,0, 1,0);

// 閉塞用
$MLS-41223-9.72;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-41223-6.94;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-41223;
Beacon.Put(0,1,0);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);

//4101
$MLS-41223;
Structure['SigPole01'].Put('down', +5.65,0,0.2, 0,0,0, 1,0);
Structure['Signal_4_tie01R'].Put('down', +5.3,+3.5,0, 0,0,0, 1,0);
Signal['Sig_4LED'].Put(1,'down', +5.3,+3.5,0, 0,0,0, 1,0);
Section.BeginNew(0,2,3,4);
Structure['SignalNB_4101'].Put('down', +5.3,+3.5-0.01,0, 0,0,0, 1,0);

$MLS-40933-122;
Beacon.Put(0,1,150);	// 30照査
Structure['Beacon09_Lim25'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-4.16, 0,90,0, 1,0);

$MLS-40933-47;
Beacon.Put(0,1,50);	// 20照査
Structure['Beacon09_Lim15'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-2.77, 0,90,0, 1,0);

// 閉塞用
$MLS-40933-9.72;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40933-6.94;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40933;
Beacon.Put(0,1,0);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);

//4003
$MLS-40933;
Structure['SigPole01'].Put('down', -2.25,0,0.2, 0,0,0, 1,0);
Structure['Signal_4_tie01L'].Put('down', -1.9,+3.5,0, 0,0,0, 1,0);
Signal['Sig_4LED'].Put(1,'down', -1.9,+3.5,0, 0,0,0, 1,0);
Section.BeginNew(0,2,3,4);
Structure['SignalNB_4003'].Put('down', -1.9,+3.5-0.01,0, 0,0,0, 1,0);

$MLS-40573-122;
Beacon.Put(0,1,150);	// 30照査
Structure['Beacon09_Lim25'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-4.16, 0,90,0, 1,0);

$MLS-40573-47;
Beacon.Put(0,1,50);	// 20照査
Structure['Beacon09_Lim15'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-2.77, 0,90,0, 1,0);

// 閉塞用
$MLS-40573-9.72;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40573-6.94;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40573;
Beacon.Put(0,1,0);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);

//4001
$MLS-40573;
Structure['SigPole01'].Put('down', -2.25,0,0.2, 0,0,0, 1,0);
Structure['Signal_4_tie01L'].Put('down', -1.9,+3.5,0, 0,0,0, 1,0);
Signal['Sig_4LED'].Put(1,'down', -1.9,+3.5,0, 0,0,0, 1,0);
Signal['Dir_4_C'].Put(1,'down', -2.1,+3.0,0.1, 0,0,0, 1,0);
Section.BeginNew(0,2,3,4);
Structure['SignalNB_4001'].Put('down', -2.25,+2.5,0, 0,0,0, 1,0);

//第1場内中継
$MLS-40414;
Signal['Sig_Relay'].Put(1,'down', -2.75,+3.5,-0.3, 0,0,0, 1,0);
Structure['SignalNB_RelayArr1'].Put('down', -2.75,+3.5,-0.3, 0,0,0, 1,0);

$MLS-40218-122;
Beacon.Put(0,1,150);	// 30照査
Structure['Beacon09_Lim25'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-4.16, 0,90,0, 1,0);

$MLS-40218-47;
Beacon.Put(0,1,50);	// 20照査
Structure['Beacon09_Lim15'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-2.77, 0,90,0, 1,0);

$MLS-40218-9.72;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40218-6.94;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40218-4.16;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40218;
Beacon.Put(0,1,0);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);

//丹波橋
//第1場内
$MLS-40218;
Structure['SigPole01'].Put('down', -2.25,0,0.2, 0,0,0, 1,0);
Structure['Signal_5_tie01L'].Put('down', -1.9,+3.5,0, 0,0,0, 1,0);
Signal['Sig_5LED'].Put(1,'down', -1.9,+3.5,0, 0,0,0, 1,0);
Section.BeginNew(0,2,3,3,4);
Structure['SignalNB_arr1_03_1L'].Put('down', -1.9,3.5,0, 0,0,0, 1,0);

Structure['Signal_4_tie01R'].Put('down', -2.55,+3.3,0, 0,0,0, 1,0);
Structure['Sig_4LED_0'].Put('down', -2.5,+3.3,0, 0,0,0, 1,0);
Structure['SignalNB_arr1_04_1L'].Put('down', -2.5,+3.3,0, 0,0,0, 1,0);

$MLS-40028-147;
Beacon.Put(0,1,150);	// 30照査
Structure['Beacon09_Lim25'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-4.16, 0,90,0, 1,0);

$MLS-40028-77;
Beacon.Put(0,1,50);	// 20照査
Structure['Beacon09_Lim15'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-2.77, 0,90,0, 1,0);

$MLS-40028-9.72;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40028-6.94;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40028-4.16;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-40028;
Beacon.Put(0,1,0);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);

//第2場内
$MLS-40028;
Structure['SigPole01'].Put('down', +1.95,0,0.2, 0,0,0, 1,0);
Structure['Signal_5_tie01R'].Put('down', +1.6,+3.5,0, 0,0,0, 1,0);
Signal['Sig_5LED'].Put(1,'down', +1.6,+3.5,0, 0,0,0, 1,0);
Section.BeginNew(0,2,2,3,4);
Structure['SignalNB_arr2_03_1L'].Put('down', +1.6,3.5,0, 0,0,0, 1,0);

//$MLS-39833-122;
//Beacon.Put(0,1,150);	// 30照査
//Structure['Beacon09_Lim25'].Put('down', 0,0,0, 0,0,0, 1,0);
//Structure['BeaconBox09'].Put('down', -1.95,0,-4.16, 0,90,0, 1,0);

$MLS-39833-57;
Beacon.Put(0,1,50);	// 20照査
Structure['Beacon09_Lim15'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,-2.77, 0,90,0, 1,0);
Structure['StopLimit15_board'].Put('down', +1.7,0,-2.77, 0,0,0, 1,5);
Structure['StopPosHolder11'].Put('down', +1.7,0,-2.77, 0,0,0, 1,5);

$MLS-39833-9.72;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-39833-6.94;
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);
Structure['BeaconBox09'].Put('down', -1.95,0,0, 0,90,0, 1,0);
$MLS-39833;
Beacon.Put(0,1,0);
Structure['Beacon09'].Put('down', 0,0,0, 0,0,0, 1,0);

//出発
$MLS-39850;
Structure['SigPole01'].Put('down_sub', -2.25,0,0.2, 0,0,0, 1,0);
Structure['Signal_4_tie01L'].Put('down_sub', -1.9,+3.5,0, 0,0,0, 1,0);
Structure['Sig_4_0'].Put('down_sub', -1.9,+3.5,0, 0,0,0, 1,0);
$MLS-39833;
Structure['SigPole01'].Put('down', -2.25,0,0.2, 0,0,0, 1,0);
Structure['Signal_4_tie01L'].Put('down', -1.9,+3.5,0, 0,0,0, 1,0);
Signal['Sig_4'].Put(1,'down', -1.9,+3.5,0, 0,0,0, 1,0);
Section.BeginNew(0,2,3,4);

5-3-4.駅部分の基本オブジェクト配置

駅部分のZ座標範囲を表現する最低限のオブジェクトを配置しましょう。
長すぎるのでコードは省略します。

基本オブジェクト配置例

5-3-5.Z座標調整

プレイに大きな影響が出る誤差(駅間距離が実際より大幅に長い、曲線長が不自然)や画面表示が乱れる場合などがあれば、諸構文のZ座標を最適化しましょう。
キロポストの座標もこの段階で合わせます。高架化工事などの影響でBVE内Z座標とキロポストが合わないのはとてもよくあることですが、この段階ではシナリオがどこからどこまでなのか固まっているはずなので帳尻合わせします。

立体交差地点がもう少し右に寄り、奥の方にある駅がもう少し左に寄るよう調整すれば自然になるはず。架線柱のZ座標推定が済んだ段階なのでCurve構文のZ座標を修正する。この場合急カーブなのでZ座標の修正量はあまり大きくならない。
図面を持っていて表記通りに入力しても合わないケースもあるがその場合図面よりもシーン納まりに寄せる。施工誤差ゼロの構造物などあり得ないのです。
緩和曲線の扱いが面倒なケースはとても多いです。

5-3-6.風景オブジェクトの配置

この段階では多分Z座標が大幅に狂うおそれがないので、じゃんじゃんオブジェクトを配置していきましょう。

駅付近はちょっと濃い目に埋めておくと臨場感が増すかもしれません
地上と地下の切り替え部分は視界が一気に変わるので特注のハリボテなど活用しましょう

5-3-7.(上級者向け)対向列車の配置

運用調査するなどして必要な情報を持っていたら対向列車の配置に挑戦するのもいいでしょう。

この世には対向列車が40本/時のシナリオがあるらしいですが
過労〇レベルの作業量になるのでやめといたほうがいいと思います

5-4.マニュアル

まずは適当に書いてみて、AIに添削させましょう。
手順書の体をなした文章ができているならAIにスライド生成させてもそれなりのものが出てくるかも。
実際の画面とアイコンを用いて視覚的に示しましょう。
もちろん自力でデザインしても全然OK

タイトル:
〇〇線 BVE(フリーの3DCG鉄道運転シミュレータ) 操作手順書
目的:
この手順書は、プレイヤーが〇〇線BVEを正しく操作し円滑なプレイ技能を習得することを目的としています。
キー・マウスの操作方法:
(レバーサー、マスコン、ブレーキ、運転台スイッチの操作説明)
手順:
1.始業準備
(ここに操作を書く)
2.発車手順
(ここに操作を書く)
3.停車手順
(ここに操作を書く)
4.終了手順
(ここに操作を書く)
トラブル時の対応:
(ここにケースと対処法を記載する)

マニュアルひな形サンプル
ペライチで収まるのが理想
プレイヤーさんはあなたほどシナリオのことを知らないし学習するための時間も不足しています

5-5.パッケージング

5-5-1.インストーラ作成

頒布ファイル作成作業用ディレクトリに必要なファイルをコピーし、セキュリティチェックの後、インストールファイルを作成します。

  • ZIP形式の場合はインストール手順書を同梱しましょう。

  • 依存関係(動作に必要な他のBVEデータ 共通ストラクチャなど)を確認し、インストール前に円滑な導入ができるよう示しましょう。

  • ライセンスを明確にしましょう(そうしないと他の方があなたのBVEシナリオの話題に触れることを避けてしまう恐れがあります。ただしライセンスを厳格にしすぎると逆にあなたを縛ることもあるので気を付けましょう)。

  • 事業者により「公共物は公共物として扱ってください」「このデザインの権利は全てわが社に属する」など異なるので、現物所有者の意思表示をよく確認してください(発車メロディーとか非常に面倒なケースが多いです)。契約書は全部読んで理解してから同意しましょうみたいなみっともないことは書きたくないよぉ。

  • インストールテストは必ず複数環境で行いましょう。

5-5-2.共有ページ

  • Bve trainsim 制作・公開ガイドライン」を守りましょう

  • わかりやすいタイトル(BVEを知らない人でも意味が通じる)を掲げましょう

  • スクリーンショット・デモ動画・「今すぐダウンロード」

  • 機能説明

  • システム要件

  • インストール手順

  • サポート

公開したらテストとプロモーション(SNS等宣伝)しましょう。
プレイヤーさんとつながるまでがBVEシナリオ制作です。

完成例ですか?作る時間なかったので、どなたかのプレイ動画をテキトーにご参照いただければ・・・

以上「シナリオ制作の流れ」でした。


6.よくある詰まり方と対処法

だいたいいつも詰まった側も対処法提示する側もだるいなあと思ってるので投げやりな感じになっちゃってますがご容赦頂ければ幸いです。

  • 取材対象までのアクセスが大変

    • ターゲットの沿線に住みましょう。

  • 取材したサウンドデータが乱れている

    • 収音レベルが低すぎる → 機材自体のわずかな電位揺らぎもノイズになり、サウンドの中で無視できない大きさになってしまいます。可能な限り収音レベルは高くしましょう。理想は最大位相約-6dB程度ですが、室内収録ではなく自然環境下での収録においては非常に強い音が入る場合があります。私の音源を適当に開けてみたら最高速度で走行中のジョイント音最大位相約-12dB程度で調整されていました。適切なレベルは機材により異なり、収音テストを多岐にわたる条件下で繰り返し行うことで見出すことができます。まあフロート録音したらはじめから問題起きないんですけどね。

    • 収音レベルが高すぎる → 音量が記録フォーマットからはみ出したことで最大位相に張り付く形で潰れノイズとして聞こえる状態になってしまいます。

    • 音が曇る → MP3録音では普通の人にはわかりにくい高音がカットされるため原理的に避けられない音の曇りが発生します。圧縮率が高ければカットされる音も多くなり劣化が目立つようになります。収音機材の解像度もボトルネックになります。対処法は1.確保できた音源で満足する 2.PCM録音可能な機材を導入する 3.高品質のマイクを導入する 4.フロート録音可能な機材を導入する といったことが挙げられます。

    • 録音設定が不適切 → ノイズカット機能は放送を収録する場合以外むやみに使わない。入力感度自動調整は必ずオフにする。

    • 人の話し声が入っている → プライバシーに関わるのでその音源はお蔵入りして次のカットを収録しましょう。自分はどうなんやと私の記録をひいてみたら100カット/年くらい取ってそこから素材を作ってました。

    • 自分では乱れているのがわからないけれど人に指摘された → 完璧な耳を持つ人など実際にはおらず、認知の個性による場合が非常に多いです(視覚や味覚と同じ)。一方、品質を徹底的に追求した音源に触れたことが無ければわからないこともあります。この話題を突き詰めると某料理マンガの「究極のメニューVS至高のメニュー」みたいなことになりかねないのでほどほどにしたいですが、まあ個人の資金力で入手可能な機材で追求しようとしたらそれだけで一生が終わってしまうので今手持ちの機材でトレーニングされひらめきを得たら次のステップに進まれるのがよいのではないでしょうか。

  • 人が多すぎて取材が難しい

    • 路線によりますが、私の作品モチーフだと一年の中で人が少ないのは1月1日・4月1日・8月15日・12月31日・2月11日、逆に多いのは11月23日・10月1日・4月7日といったように日によって大きく変動します。いろいろ要因はありますが分析して狙いましょう(ただし近年では列車ごとの乗車率平準化がかなり進んでおり、空いている列車はダイヤ改正ごとに運用取りやめとなるケースが多いです。例えば、昔は京阪の終夜運転午前3時~5時で非常に空いている急行がいっぱい走っていましたが、2022-2023終夜運転ダイヤからは種別も本数も需要とかなりマッチしていて空いている急行はゼロになったりしています)。

  • 完成する気がしない

    • 要求品質の設定が高すぎるのかもしれません。まずは完成することが大事なので、できないことはやらない仕様に改めましょう。BVEシナリオ制作はとにかく面倒で最終的に自分との戦いになりがちなので、うまく負けるが勝ちかなと。

  • モチベが維持できない

    • BVEシナリオ制作はアウトプット活動なので、インプットを超えることは無理です。気持ちいいインプットを100倍くらい吸いましょう。てか100倍でも足りないかも。

  • 時間足りない

    • 面倒なことはAIにやらせて時間を作りましょう

  • ファイル名とかの命名ネーミングセンスなさすぎて作ってて萎えるんですがどうしましょう

    • プレイ中見えないから気にしないでください 人を傷つける感じのはアカンけど

  • 作品の質を上げたいけれど何をしたらいいか分からなくてどうしたらいいか困っている

    • 素材の質を上げましょう。素材の品質より上の作品はフィクションに振り切らない限り出せません。素材の質が現時点でそれ以上にできないのであれば、作品をシェアしましょう。それでその作品は0点から50点になり、あとは流れに身をゆだねれば自然と100点に近づいていきます。

  • とにかくわからん。誰か教えて

    • オフ会行くのが手っ取り早いです。「誰か教えて」がイラスト描いている時なら人口が多いから気の合う人とつながって学ぶとか本を買うとかできますが、BVEシナリオ制作は現時点でそれができる状況にありません。ゲームであればデッキを晒せばヒマな人がアドバイスくれる場合もありますがBVEシナリオ制作だとデッキを晒すに相当することの手間が大きすぎて無理筋です。SNSでサーバー土下座して教えを乞うのもお互いどんな人物かよくわかっていないまま話を進めて事故るリスクがあるのでお勧めできない・・・というかぶっちゃけ止めに入りたい。そんな感じです。

  • 前提知識多すぎてどうすればいいかわからないから一つだけ選ぶとしたらどれですか

    • 物理。

以上「よくある詰まり方と対処法」でした。


7.完成後はどうするか

BVEシナリオ制作を一通りやってみた時には既に人生の何割かをベットしたはず。
後生に禍根を残す事態を可能な限り避けるには、一連の活動に意味づけして道を違えぬよう次に進むのが寛容かと存じます。

  • BVEシナリオ制作はあなたと関係者にとって何だったのか?

    • ライフワーク?

      • → 生き様。(制作のやり方・社会貢献・教育・環境活動)

    • ライクワーク?

      • → 快楽として。

    • ライスワーク?

      • → 生活費を得るため。

(私の場合はライフワークとライクワークにまたがっていてややライクワークに寄ってる感じですね)

  • BVEシナリオ制作で何を積み上げられたか?これからの見込みは?

    • 人とのつながり?

    • 技能蓄積?

    • 有形資産?

気持ちを整理して次なる活動に進みましょう。


もちろん「数をこなせば質は後からついてくる」みたいな考え方で本章の課題を後回しにしてさっさと次回作に取り組む、というやり方もいいと思います。
しかし本稿執筆時において、あらゆる分野での創作物・表現者が供給過多どころか飽和を通り越している状況にあると私は認識しており、その状況下ではどんないいものを作って公開しても99%誰にも見向きされないと予想されます。20年以上前私がコミケに初めて参加した時に会場で起こっていたことがリアル日常にもサイバー空間にも飛び出してきたのが今起こっていることだな、と受け取っています。
ゆえに、やりたいことに飛びつくのはいいじゃない、せやかてその後はどうするの?そしてその後は?と問いを提示させていただきました。
私自身もしばらく新作を一般公開していないですが、それは私がBVEを始めた頃に比べて鉄道というもののあり方自体が急激に変化してしまい(例えば京阪間三社競争論など平成中期時点で既に過去のものになっていたにも関わらずそれが続いているかのような喧伝が専門誌でずっと出され多くの人の混乱した反応を招いていて日常的に利用する人達と大きな温度差が生じており2024年現在も拡大し続けていることなど)、その中でどのあたりに落ち着こうかイメージはぼんやりあるんですけれども、前に踏み出して得られることが期待できるものと予想されるリスクとを天秤にかけたら引き伸ばしの答えが出続けていることに因る結果です。これからもっと視野を広く持ち、自分の道を進めるには今どう行動するかしっかり見据えて歩んでいきたいと思います。


おわりに

BVEシナリオをつくるには、と簡単に書き出してはみたものの、簡単とはとても言えませんね。だからこそ書いてみた甲斐がありました。
本稿中では誰にでも必要不可欠とは限らないオプションも提示しましたが、制作中につまづいて抜け出し方が全く見えないケースを数えきれないくらい見てきたのでこれくらい出しといていいのかなと。
意見感想改善案その他文句などがありましたらぜひ「BVEシナリオをつくるにはをつくるには」を出してみてください。

本稿は行き当たりばったりで書いたつもりではなく、じつは本稿で示した手順で制作されたシナリオがあります。それはJR琵琶湖線です(ただし、本稿説明の例には話の通りやすさを重視して別の素材を使用しています)。

10年前から「BVEシナリオをつくるには」は出したいと思っていたのですが、何回も作ってはボツにしては、を繰り返し今にいたります。制作道具紹介は2024年に合わせてアップグレードしましたが、完成にこぎつけるための考え方は変わっていません。そしてBVEが現在のあり方でい続ける限りは「完成させるにはどういう道筋があるかという概念は変わらない」「道具は分野ごとにブレイクスルーがある都度アップグレード」という姿勢が続くでしょう。もし本稿に続編があるとすれば、各章さらにかみくだいた解説をする、アップグレードの解説をする、といったものになると思います。

BVEシナリオをつくるのはすっごい面倒でだるいですが「BVEシナリオをつくるには」をつくるのもまたすっごい面倒でだるいです。しかし一旦着地してみようかと思い、ちょっと走ってみました。
私がBVEシナリオを初めて作った時から今に至るまで俯瞰して、プレイヤーの皆さんのニーズは多様化細分化しており、今後この傾向がさらに加速すると予想されますが、今残っているもの、今あるもの、これから出てくる作品を通して人々が心を寄せ合い、文化が途切れることなく安定的に続いていくことを望みます。