Hatena::Groupragnarok

Seak's Notes RSSフィード

2006-03-15 (Wed)

ジュピロス遺跡

ホムンクルスAI変更点メモ 03:26

ちょっといじってみました。

きゃらめるのメンバーから「逃げ回るホム」というアイデアが出たので、一つ実装してみようと思います。言われてみれば確かに、ホムが攻撃されて困っていたので、ホムが逃げてくれれば便利です。

ってこんちきしょー!ホムが座ってる間だけホムが自由に動けるように指定しようと思ったのに!

ホムンクルス人工知能スクリプトマニュアルより引用します。

4-2 GetV (V_MOTION, id) に対する返り値

  • MOTION_STAND = 0 : 立っている動作
  • MOTION_MOVE = 1 : 移動中の動作
  • MOTION_ATTACK = 2 : 攻撃中の動作
  • MOTION_DEAD = 3 : 死んだ動作
  • MOTION_ATTACK2 = 9 : 攻撃する動作

見ての通り、「座っている動作」が取得できません。なめんなーーー!!しょうがないから立ってる間だけ自由に動けるようにします。しょぼーーん。

そんなわけで、コードは以下の通りです。

あ、ちなみに、ローカル変数で、グローバル変数で、引数で表現しようかと思います。え?やけに丁寧だって?そりゃそうです。自分のためにやってますから。

なお、はてなキーワードリンクなっちゃっていますが、面倒なので主要な部分以外は対策していません。code要素の中身はリンクしないとか、できないものでしょうか。


function  OnIDLE_ST ()
  -- (中略) --
  local distance = GetDistanceFromOwner(MyID)
  -- 2006-03-16追記 主人が立っていたら、どこででも待機する。 座ってたらって条件が取れん…。
  if ( MOTION_STAND ~= GetV(V_MOTION, GetV(V_OWNER, MyID)) ) then
    if ( distance > STOP_DISTANCE or distance == -1) then    -- MYOWNER_OUTSIGNT_IN
      MyState = FOLLOW_ST
      TraceAI ("IDLE_ST -> FOLLOW_ST")
      return;
    end
  end
end

移動中以外は追わなくても良さそうな気がしますが、遠くで戦ってるときに寄ってきてくれなくなるかもしれないので、こんな感じで。

STOP_DISTANCEは、僕が定義した定数です。初めは9にしていましたが、広すぎるので5にしました。ついでに、ケミのIDもよく使いそうなので定義しました。

ちなみにここ、not eqallを!=と書いていました。Luaでは~=が正しいです。


STOP_DISTANCE  = 5  -- 主人から離れていても停止している距離
MyOWNER	= GetV(V_OWNER,MyID)	-- 主人のID

あと、ケミを追いかけてるときの条件です。


function  OnFOLLOW_ST ()
  -- (中略) --
  elseif (GetV(V_MOTION,MyID) == MOTION_STAND) then
    MoveToOwner (MyID)
    TraceAI ("FOLLOW_ST -> FOLLOW_ST")
    return;
  -- 2006-03-16 追記 移動中にも目的地指定
  elseif (GetV(V_MOTION,MyID) == MOTION_MOVE) then
    local x,y = GetOwnerPosition(MyID)
    Move (MyID,x,y)
    return
  end
end

元のプログラムでは、ケミの位置を取得して、移動して、目的地に着いたら改めて取得して……ということを繰り返しています。

ホムを連れて歩くと気付くと思いますが、これだと、ホムが目的地に着いた瞬間に立ち止まってしまうため、少しずつホムが遅れるようになってしまいます。

そこで、移動中もケミを追い続けるよう、追記しました。MoveToOwner()を使っていないのは、MoveToOwner()は、どうもケミとずれた場所を目的地にするらしく、移動中に指定するとホムがフラフラと揺れまくるためです。

副作用として、ケミと同一のセルを目的地とするため、ケミが立ち止まったときに、一度ケミと重なろうとして弾かれるという動作が入ります。

デフォルトでこのような動作になっていないのは、移動中も目的地を更新すると、ホムの位置更新パケットが大量に飛ぶためではないかと思います。

次に、アクティブのホムの動作を変更しました。


-------------------------------------------
 --  先攻型 GetMyEnemy
-------------------------------------------
function  GetMyEnemyB (myid)
  -- (中略) --
  for i,v in ipairs(actors) do
    if (v ~= owner and v ~= myid) then
      if (1 == IsMonster(v))  then
        if (3 >= GetDistance2 (MyOwner, v)) then -- 2006-03-16追記 アクティブ反応の範囲を3セル以内に限定
          enemys[index] = v
          index = index+1
        end
      end
    end
  end
  -- (後略) --

いじったのは、Mob選定の部分です。

もともとのプログラムでは、視野範囲にいるすべてのモンスターをターゲットとして選択するようになっていました。これではあまりにやばいので、ケミから3セル以内にいるMobだけを攻撃するようにしました。

さらに、リーフも羊もこっちを使うようにしてしまったので、僕の羊は、羊のくせにアクティブです。


function	GetMyEnemy (myid)
	local result = 0

	local type = GetV (V_HOMUNTYPE,myid)
	if (type == LIF or type == LIF_H or type == AMISTR or type == AMISTR_H or type == LIF2 or type == LIF_H2 or type == AMISTR2 or type == AMISTR_H2) then
		-- 2006-03-16変更 すべてのホムンクルスアクティブresult = GetMyEnemyB (myid)
	elseif (type == FILIR or type == FILIR_H or type == VANILMIRTH or type == VANILMIRTH_H or type == FILIR2 or type == FILIR_H2 or type == VANILMIRTH2 or type == VANILMIRTH_H2) then
		result = GetMyEnemyB (myid)
	end
	return result
end

やばいです。全変数に手打ちでタグを振っていくのは、想像以上にだるいです。もしかしたら、飽きてやめるかもしれません。

それはともかく、この関数、もともとはこんな意味でした。「リーフやアミストルならノンアクティブ、バニルミルトやフィーリルならアクティブを選択せよ」って感じだったのです。しかしこの書き換えによって、「リーフやアミストルならアクティブ、バニルミルトやフィーリルでもアクティブを選択せよ」……つまり、とにかくアクティブってことです。省略してもいいんですが、ノンアクティブに戻せなくなると困るかもしれないので残しています。

あと、もう1ヶ所です。


function	GetOwnerEnemy (myid)
	-- (中略) --
				if (IsMonster(v) == 1) then
					enemys[index] = v
					index = index+1
				else
					local motion = GetV(V_MOTION,v)	-- 2006-03-16 モーション取得対象を修正
 -- (後略) --

主人の敵を判別する部分で、if (IsMonster())という条件文のelseの部分を変更しました。つまり、主人の敵のうち、モンスターじゃないやつに関する記述です。

ホムンクルスで対人戦なんてまずやらないでしょうからどうでもいい部分なのですが、なぜか対象を表すvではなく、ループの回数を数えるのに使われているiが使われていたので、修正しました。

レーサースレの話題 17:14

なんかGvレポについての話題が出ています。

僕は、自分のブログに何を書こうと、自分の勝手だと思っています。それが嫌なら見に来なければいいからです。ギルドメンバーならともかく、匿名の誰かに内容について口出しされる筋合いはありません。もちろん、参考になる意見であれば参考にします。どんな意見を参考にして、どんな意見を無視するのかも、すべて僕の勝手です。

レポートと銘打っていますが、僕のレポートの中身は、ちゃんとしたレポートにはなり得ていません。レポートと言うなら、検証可能な客観的事実を提示した上で、その事実を分かりやすく解説し、自分なりの、他からの流用でない考察や議論をした上で、結論を明確に示すべきです。しかし、僕のレポートはそんな厳格なことは一切考えていません。レポートと言っているのに中身がレポートでないと言われても、知ったことではありません。それが嫌なら見に来ないでください。

また、僕はGvでの感想をいろいろと書いていますが、僕個人の感想はきわめて主観的なものであり、レポートには適しません。しかしながら、僕はこの感想が重要であると思っており、今後も書いていくつもりです。

まとめると、こういうことです。俺は俺のためにやってるんだ、ガタガタ言うならくんなということです。

ホムンクルスに関するアイデア 15:29

いくつかおもしろいものが出されています。

アクティブスキルをまったく違う命令として使う

例えばキャッスリングの場合、レベル5までありますが、消費SPが変わらない上成功率が下がるだけなので、レベル5を取得してしまえば、レベル4以下を使うことはありません。そのため、レベル4以下のキャッスリングをまったく違う命令(通常攻撃など)に割り当ててしまおうというアイデアです。

弱点としては、汎用AIには使えない(キャッスリングは羊のみのスキルだから)という問題がありますが、自分だけが使うなら関係ありません。いいアイデアですね。

君さえ側に居ればいい

どんなときでも主人の後ろについてきます。常にそばにいてくれます。

え?何?

それって戦わないだけ?ペットと同じ?

そんな夢のないことを言うなよ。

ホムかわいいよホム 14:08

というわけで、ホムンクルス特集です。生体研究所?何それ。あんな、入ったら即死するようなダンジョンに興味はありません。

ジュピロスもおもしろかったんですが、とりあえず置いときます。

それで、ホムンクルスです。ついに来ましたね。

戦闘能力はノビ並みだと言われていましたが、僕の羊くんの場合、レベル16の時点でHPが1800以上あります。これって、騎士よりHP倍率高いんじゃね?って感じです。たぶん、後半に伸びないんだと思いますが。ただ、高いのはHPだけで、あとはDefが55くらいあるだけで、他のステータスは軒並み低いです。ただ、ASPDが138らしいんですが、どう見てももっと速いです。気のせいでしょうか。

さて、ホム最大の利点は、たぶん経験値にあると思います。

ホムの経験値は、俺のものは俺のもの、お前のものも俺のものという、どこかで聞いたような法則によって決定されています。つまり、ケミが殴った分の経験値はケミに入り、ホムが殴った分の経験値は、ホムに入ると同時に、ケミにも入ります。ただ、ジョブ経験値は入りませんけど。そして重要なのは、共闘ボーナスが入るってことです。つまり、ホムを連れて歩いて、ホムが一発でもダメージを入れた時点で経験値が25%まるまる上昇するのです。トレイン狩りだとホムが共闘を入れる隙がありませんが、普通に狩っている限りは、連れて歩くだけで経験値が大幅に上昇するのです。

ところで、ホム4種の特徴を書いていこうと思います。

それぞれのホムについて

フィーリル

たぶん一番人気のです。そして、たぶん戦闘能力も一番高いです。ホムは囲まれによるFlee減少がないため、Flee上昇スキルを使用することによって、どれほど囲まれても避けまくります。また、アクティブスキルは660%という高倍率であり、元のATKが低いとは言え、そこそこの殲滅力を持っています。まあ、ジオの方が強いけどな。

欠点は耐久力のなさでしょう。結構簡単にくたばるようです。もっとも、蘇生すりゃいいだけの話なんですが……。蘇生にSPが60くらい必要なので、そのSPが確保できるなら、ガンガン突撃させて、ガンガン殺して戦えばいいんじゃないかと。

バニルミルト スライム

謎のスライムです。

攻撃、回復、支援とバランスの取れたスキル構成ですが、残念なことに、回復スキルは、やってみないことには誰が回復するか分かりません。敵が回復することもあるようです。

MATKが高く、攻撃スキルもなかなかの威力が期待できるのですが、撃つたびに属性が変わります。効くときは効くでしょうが、効かないときはさっぱりでしょう。

基本能力はかなり高めのようです。

アミストル 羊

なんかやる気なさげな羊です。

キャッスリングは、ホムと主人の場所を入れ替えるおもしろいスキルですが、一体何に使うのかよく分かりません。ああ、あれか。ホムを捨て駒にして、その間に逃げるために使うんですね、きっと。あとは、Def上昇スキルがあります。+10じゃちと微妙っぽいですが。攻撃能力も低いです。

でも、高レベルケミには一番いいホムだと思います。それはなぜか。

僕のケミ特化サーベルで斬りつけた場合、だいたい1発で400程度のダメージが出ます。一番攻撃力の高いフィーリルでも、アクティブスキルを使っても700程度、通常攻撃では、100くらいでしょう。さらにASPDが低いので、殲滅力にはそれほど期待できません。もちろん、製薬ケミなんかの場合には十分でしょうけど、レベルが上がり、狂気POTを飲んでガンガン狩るようなケミには不向きです。

しかし羊の場合、死ににくいという特徴があります。レベル16の時点で1800のHPがありますから、レベル85で4500程度の主人のHPを越えるのもそう遠い日のことではないでしょう。また、VITが高いので、ポーションピッチャーによってかなりのHPが回復します。つまり、共闘を入れるのに一番向いていると思われるのです。

リーフ 幼女

幼女がまずいなら妖精にしますか。でも、幼女ですよね、あれ。

ヒールを持っていますが、赤スリムポーションを消費します。赤スリムポーションは白ポーションより高いので、残念ですが、こいつにヒールさせるくらいなら、自分で自分にポーションを投げましょう。

ただ、緊急回避がおもしろそうです。20秒だけですが、IAペコ騎士並みの速さに加速してくれます。緊急回避って名前ですが、どう考えても索敵に使うのが一番向いてます。

アルケミストたちの間では、観賞用ホムと言われているそうです。

AIについて

ちょっといじってみました。取っつきにくいですが、さかんに情報交換が行われているので、そのうちある程度いじれるようになると思います。

ホム使いが最初にするべきなのは、スライムの性質変更です。スライムデフォルトアクティブなので、初期状態だとガンガン横殴りします。共闘ボーナスが入る上にATKが低いので、経験値は、どちらかと言えば増えるでしょう。しかし、いい気分がする人はそれほどいないでしょうから、こいつは修正すべきです。

あとは、遠くで待機できるように修正をしてみました。そうすると、他人のところに自分のホムを行かせることができて、ちょっとおもしろいんですよね。いつも自分のそばにいるだけではおもしろくないというものです。

あとは、待機状態のときにウロウロする、というような動きを実装してみたいですね。んなことしたらHPの回復が止まりますが。

あと、AI作成用の自分メモです。

おまけ

ペットとホムを一緒に連れて歩いているのですが、ホムが攻撃してもペットがしゃべります。攻撃の処理としては、主人が攻撃してるのと同じような扱いなのかもしれません。だからどうなるってわけでもないのですが。

retroretro2006/03/16 00:29アミストルのキャッスリングはチェスのキャスリングから来ていると思いますよ。
チェスの場合はいくつか条件はありますがキングとルークの位置を一手で変えることが出来ることだったと思います。
まあやっぱり「俺の為に死んでくれ(ぁ」ってことでしょうねw

secseeksecseek2006/03/16 01:48キャスリングなんでしょうね。やっぱり。だから、何か条件があるかと思ったんですが、まったくありませんでした。まあ、つまりは俺のため(ry