alchemistarkの日記

やったことのメモ

Entityについて解説したい 6

ではEntPropについてお話するよ

InputはEntityに命令するもの、KeyValueはEntityの設定
EntPropはメモリの読み書き*1

一番面倒だけど出来ることも多い

GetEntProp系は読み出し、SetEntProp系は書き込み
EntPropも型ごとに関数がある String、Float、Vector、Ent
EntityIndexを扱う時はDecimalじゃなくてEntを使う
関連関数多すぎるのでAPIページ貼るのは省略してSetEntPropのみで

SetEntProp · entity · SourceMod Scripting API Reference
最後2つの要素は省略可。一番最後のはプロパティが配列の場合のみ使う

そもそもEntityというかEntPropを初めて見かけるのって
恐らく無敵化するにはどうするか調べてるときじゃないかなって思う*2

SetEntProp(client, Prop_Data, "m_takedamage", 1);

最初これ見た時の感想、m_takedamageってなんやねんだったんだけど僕だけかな
ググっても出てこないし、何だこれはってなった SourceModのページにNetProps一覧とか置いてあるんだけどその中にもm_takedamageって無いんですけど!?

答えから言います m_takedamageはdatamapにあります。
とりあえずdatamapとはなんぞやは置いておいて*3
コンソールにfind sm_dumpと入力してください。

f:id:alchemistark:20180212000624p:plain

えっと、分かるものだけ説明します。

sm_dump_datamaps datamap.txt
とかするとdatamapの一覧が保存されます。
開くと大量のプロパティ名だかメモリ名だかが出てきます。

// Dump of all datamaps for "tf" as at 2018/02/11
//
//
// Flag Details:
//
// Global: This field is masked for global entity save/restore
// Save: This field is saved to disk
// Key: This field can be requested and written to by string name at load time
// Input: This field can be written to by string name at run time, and a function called
// Output: This field propogates it's value to all targets whenever it changes
// FunctionTable: This is a table entry for a member function pointer
// Ptr: This field is a pointer, not an embedded object
// Override: The field is an override for one in a base class (only used by prediction system for now)
//

CBaseEntity - _ballplayertoucher
- m_iClassname (Offset 92) (Save|Key)(4 Bytes) - classname
- m_iGlobalname (Offset 96) (Global|Save|Key)(4 Bytes) - globalname
- m_iParent (Offset 100) (Save|Key)(4 Bytes) - parentname
- m_iHammerID (Offset 104) (Save|Key)(4 Bytes) - hammerid
- m_flSpeed (Offset 108) (Save|Key)(4 Bytes) - speed
- m_nRenderFX (Offset 112) (Save|Key)(1 Bytes) - renderfx
- m_nRenderMode (Offset 113) (Save|Key)(1 Bytes) - rendermode
- m_flPrevAnimTime (Offset 136) (Save)(4 Bytes)
- m_flAnimTime (Offset 140) (Save)(4 Bytes)
- m_flSimulationTime (Offset 144) (Save)(4 Bytes)
- m_nLastThinkTick (Offset 152) (Save)(4 Bytes)
- m_nNextThinkTick (Offset 208) (Save|Key)(4 Bytes) - nextthink
- m_fEffects (Offset 212) (Save|Key)(4 Bytes) - effects
- m_clrRender (Offset 132) (Save|Key)(4 Bytes) - rendercolor
- m_nModelIndex (Offset 114) (Global|Save|Key)(2 Bytes) - modelindex

……

右側にclassnameだとかhammeridだか書いてあるものは、プロパティ名に関連付けられています。
なのでそこを変更すると対応するプロパティの値も変わります。

1行目のCBaseEntity - _ballplayertoucherってのはEntityのClass名
この種類のEntityはこのプロパティ(メモリ?)を持ってますよって感じ
例えばteam_round_timerで検索してみると

CTeamRoundTimer - team_round_timer

ってのが引っかかるので、これより下がteam_round_timerにEntPropする時に使えるもの一覧になります
型はm_の次の1文字2文字で型の頭文字付いてるのでそれで 絶対じゃないけど

んでdatamapに対してGetやSetをする場合、Prop_Dataを指定します。

SetEntProp(client, Prop_Data, "m_takedamage", 1);

再掲。


次。netprop。
ネットワーク化可能なうんたらって多分コレの事だとは思うんだけど…

ぶっちゃけコレも同じ。
一度ファイルに保存します。
中身はこんな感じ

CBaseDoor (type DT_BaseDoor)
 Table: baseclass (offset 0) (type DT_BaseEntity)
  Table: AnimTimeMustBeFirst (offset 0) (type DT_AnimTimeMustBeFirst)
   Member: m_flAnimTime (offset 140) (type integer) (bits 8) (Unsigned|ChangesOften)
  Member: m_flSimulationTime (offset 144) (type integer) (bits 8) (Unsigned|ChangesOften)
  Member: m_vecOrigin (offset 792) (type vector) (bits 0) (ChangesOften|CoordMP)
  Member: m_ubInterpolationFrame (offset 148) (type integer) (bits 2) (Unsigned)
  Member: m_nModelIndex (offset 114) (type integer) (bits 13) ()
  Table: m_Collision (offset 348) (type DT_CollisionProperty)
   Member: m_vecMinsPreScaled (offset 8) (type vector) (bits 0) (NoScale)
   Member: m_vecMaxsPreScaled (offset 20) (type vector) (bits 0) (NoScale)

使い方も似たようなもん。ただ、Prop_DataがProp_Sendになります。

ちょっと待ってCBaseDoor (type DT_BaseDoor)って何って思った人が出てくると思う
それを調べるにはclasslistを見る必要があるので
sm_dump_classesしてください。
中身はこちら。

// Dump of all classes for "tf" as at 2017/12/06
//

CBaseEntity - _ballplayertoucher
CFireSmoke - _firesmoke
CPlasma - _plasma
CBaseEntity - ai_ally_speech_manager
CBaseEntity - ai_battle_line
CBaseEntity - ai_changehintgroup

…中略…

CBaseEntity - func_croc
CBaseDoor - func_door
CBaseDoor - func_door_rotating
CFunc_Dust - func_dustcloud

CBaseDoorありました。func_doorとfunc_door_rotaingですね。
尚、さらに下の方に行くとfunc_waterもCBaseDoorなのが分かります。
このように似たようなEntityは同じプロパティを持っていたりします。
NetProp使う時は一旦classlistからEntity名検索して該当のクラスを探してください。

tempentity propsってなんですかぼくはしりません

とりあえずここまで説明したInput、KeyValue、EntPropでEntityの操作は大体できると思います。
InputやKeyValueで操作できる内容ならなるべくそちらの方がいいかもしれません。
InputやKeyValueにもよるのですが、1つのInputやKeyValueの操作で、複数のPropが変更されている事があるようです。
その場合、変更が必要なPropが全て分かっているのなら良いのですが、そうでなくPropの設定変更が不足していた場合想定外の動作をする可能性があります。
デバッグ繰り返して問題なければ大丈夫だと思いますが…

6回に渡って長文書きましたが、日本語怪しすぎて読めないとは思いますが
入門者の助けになれば幸いです。
良いプラグイン開発を

*1:だと僕は思ってる

*2:偏見

*3:自分も分かってない