SourceEngineにおける当たり判定とラグ補完について #1
いずれちゃんとした文書を書きたいけどとりあえず簡単にブログ記事で書いてみる。死ぬまでにはもっとちゃんとした文書で構造化してまとめておく予定。ちなみに推測も多々含まれてるけど偉そうな口調で書く。
Hitboxについて
Hitboxとはなんだろう。これは当たり判定を行うための小さな立方体の集まりであり、これはキャラクターModelのデータに定義されている。たとえば以下のような感じである。
HLMV create hitboxes - Valve Developer Community
(このデータはSourceSDKに付属しているhlmv(Half-Life Model Viewer)で見れるらしい)
これを見ればわかる通り、キャラクターの実際の頭の位置とヒットボックスの位置はずれているため、たとえばこの画像でいえば、この馬の耳の部分を撃っても頭に当たった判定にはならない。
sv_showhitboxesの誤解について
L4Dやその他のSourceEngineゲームでは、コンソールでsv_showhitboxesとやるとhitboxを表示できる。
Hitboxがモデルとずれている?? いやこれはおそらく見た目上のわかりやすさのためにわざとずらして表示しているだけであって、実際のヒットボックスはModelの位置にあると思われる。実際に試してみればわかるが、たとえばこの画像のように後ろにあるHitbox(のようなもの)に発砲したとしてもこのプレイヤーはダメージを受けないし、Modelのほうに発砲すればこのプレイヤーはダメージを受ける。つまり、おそらくsv_showhitboxesが表示している情報は、ヒットボックスの形自体は正しいのだが、位置はずらして表示しているだけだと思う。重なっていたらわかりにくいだろう?
ちなみにTF2ではこのcvarは削除されていて、"この情報はプレイヤーを混乱させるから"という理由で2010年に削除されている。
Removed sv_showhitboxes to avoid players confusing it with the method by which we do hit detection (see http://developer.valvesoftware.com/wiki/Source_Multiplayer_Networking for info)
cl_interpについて
これは、このcvarに設定した時間分だけサーバーよりも遅れた世界に生きることが出来るというもの。たとえばcl_interpが1であれば、1秒だけサーバーよりも遅れて世界を描画します。何それ不利になるだけじゃない? とあなたは思うかもしれない。いやちがうんです。ちがうんですよ。ネットワークというのは残念ながらかなり不安定なものなのでありのままほかのプレイヤーの行動の情報パケットを受け取ったままそのまま表示するとかなりワープしてしまうんです。それを軽減するための仕組み、ラグ補完の仕組みがこのcvarで設定できることです。たとえば1秒間遅れた世界に生きるとすれば、ちょっとした回線の不安定があったとしてプレイヤーの移動情報が一部欠落していたとしても欠落していた部分を推測して補完してあげることができるんです。しかしリアルタイムにすべて表示していたらパケットをロスしたら、ロスしたときの場所がわからない。表示しようがない。だからワープしてしまう。
海外の鯖とかで超ラグいときの話をすると、ありがちなのがいったんすべてのプレイヤーが完全停止したあとに、少したった後突然敵のスピードが超早くなって移動したりするのはこの補完システムが影響しています。パケットを大幅ロスしたせいで元居た位置と現在の位置の間が通常の移動速度ではあり得ないほど離れちゃったので高速にプレイヤーが移動したことにせざるを得ないがゆえに高速移動しちゃったことになっちゃっています。
まあつまり以上の通り、cl_interpと当たり判定自体は全然関係ない概念ってことですね。カクカクさ、ワープをおさえるためにどの程度バッファをもうけるかという設定がcl_interpです。当たり判定用の立方体データはモデルデータにある。ちなみにcl_interpのclはclient、interpは補完という意味です。ラグ補完の調整するためのcvarだったんですねぇ。
ここで力尽きたので次回に続く。cl_interpは実はどっちが先にダメージを与えたか、殺したかに、影響しています。これまたヒットボックスとはまったく無関係とも言えなくなってきました。そういうのを詳しく次回の記事で書きます。