イベントのMOD制作¶
イベント型¶
| 型 | 対象 |
|---|---|
event |
ゲーム全体(グローバルイベント) |
country_event |
帝国全体 |
planet_event |
惑星 |
fleet_event |
艦隊 |
ship_event |
艦船 |
pop_faction_event |
派閥 |
pop_group_event |
POP単位。4.0以降、旧pop_event。 |
observer_event |
観察者。開発用で、observeコマンドで観察者モードへ入ります。 |
system_event |
星系(galactic_object)。3.0以降。 |
starbase_event |
星系基地。3.0以降。 |
leader_event |
リーダー。3.0以降。 |
espionage_operation_event |
諜報作戦。3.0以降。 |
first_contact_event |
ファーストコンタクト。3.0以降。 |
situation_event |
状況。3.3以降。 |
agreement_event |
従属国契約。3.4以降。 |
基本挙動¶
名前空間とイベントID¶
イベントファイルの先頭には名前空間を置きます。技術的には使用前に読み込まれればどこでも構いませんが、先頭以外は推奨しません。名前空間はファイル内のイベントを識別する基礎です。たとえばon_action_events.txtの先頭付近にnamespace = actionがあり、イベントIDはその名前空間、ピリオド、一意の数値で構成されます。
namespace = action
country_event = {
id = action.8
hide_window = yes
is_triggered_only = yes
trigger = {
is_country_type = default
from = { is_country_type = default }
NOT = { has_communications = from }
is_hostile = from
}
immediate = {
establish_communications = from
fromfrom = {
conquer = root
set_controller = root
}
}
}
ゲーム内の他の場所はaction.8で呼び出します。1ファイルに複数の名前空間を置けます。名前空間は長くでき、100文字まで動作確認されています。数字も含められます(バニラのparagon_2など)。IDのピリオド後は数字だけにし、文字を入れるとnamespace.0として認識されます。先頭の0は切り捨てられ、.003と.3は同一です。
100文字の動作確認について、原文はStellaris Modding DenのDiscord投稿を根拠として挙げています。
実行¶
既定では、すべてのイベントが毎日(場合によっては毎tick)すべての対象オブジェクトに対してトリガーを検査し、成立したオブジェクトのスコープで実行されます。非常に高負荷なので、通常は次のいずれかを使います。
is_triggered_only = yes— 常時ポーリングから除外し、別の場所から呼びます。mean_time_to_happen— 検査間隔を広げます。
fire_only_once = yesもありますが、実行まではポーリングし続け、1回実行後にだけ除去されます。2.1.2以降、2回目の発火を条件側でも除外しないとエラーログが出ます。
条件¶
trigger内の条件が偽ならイベントは発生しません。次はapoc.1の例です。
trigger = {
owner = { NOT = { has_country_flag = encountered_first_gateway } }
from = {
has_star_flag = abandoned_gateway
any_system_megastructure = { is_megastructure_type = gateway_ruined }
}
}
事前トリガー¶
完全な条件より先に検査する高速な真偽判定で、対象を早期除外して性能を改善します。省略した項目は無視され、惑星、POP、星系、星系基地、リーダーで使えます。通常トリガーとは名前が似ていてもコードを共有せず、独立した仕組みです。ゲーム内資料は000_added_pre_triggers_to_planet_events.txtを参照してください。
惑星:
pre_triggers = {
has_owner = yes # 惑星に所有者がいるか
is_homeworld = no # 所有者の母星か
original_owner = yes # 最初の所有者が今も所有しているか
has_ground_combat = no # 惑星で地上戦が進行中か
is_capital = no # 所属帝国の首都惑星か
is_occupied_flag = no # 惑星が占領されているか
is_ai = no # 惑星の所有者がAI操作か、人間の操作か
}
is_ai以外には通常トリガーの対応物があります。旧版では惑星スコープのis_aiが機能しませんでしたが、3.3のスクリプト刷新で修正されたと思われます。
職業のPOP(common/pop_jobs/000_pretriggers.txt参照):
possible_pre_triggers = {
has_owner = yes # POPのいる惑星に所有者がいるか
is_enslaved = no # POPが奴隷化されているか
is_being_purged = no # POPが浄化中か
is_being_assimilated = no # POPが同化中か
has_planet = yes # POPが惑星にいるか
is_sapient = yes # POPに知性があるか
is_robotic = yes # POPがロボットか(4.0以降)
}
is_roboticは4.0以降です。派閥のcan_join_pre_triggersも同じ項目を受け付けます。
- 星系:
has_owner(所有者のいる星系基地があるか)、is_capital(所有者の首都が星系内にあるか)、is_occupied_flag(全惑星を含め、所有者以外に完全占領されているか)。 - 星系基地:
has_owner(所有者がいるか)、is_occupied_flag(支配者が所有者と異なるか)。 - リーダー:
has_owner、is_idle(リーダーが任務に割り当てられているかを判定)。
これら以外の構文(コメントを除く)を事前トリガーブロックへ書くとエラーになります。
表示¶
既定ではイベントウィンドウが出るため、少なくとも1つの選択肢と表示文章が必要です。hide_window = yesで非表示にでき、実績判定やプレイヤーへ知らせない処理イベントに使います。
コード実行¶
主な処理はimmediate内の効果文へ置き、多くのイベントは全処理をこのブロックへ収めます。ifも使えます。次はcolony.events.txtの例です。
immediate = {
if = {
limit = {
event_target:subterranean_nation = {
NOT = { has_country_flag = tech_request_approved }
}
}
create_army = {
name = "NAME_Invading_Horde"
owner = event_target:subterranean_nation
species = event_target:subterranean_species
type = "industrial_army"
leader = last_created_leader
}
}
}
表示イベントには最低1つの選択肢が必要で、各選択肢も効果を持てます。イベント実行時のスコープは呼出し方に強く依存します。
平均発生時間¶
mean_time_to_happen(MTTH)は、他の条件成立後に平均で指定期間だけ遅らせます。実際の日数には大きなばらつきがあります。内部での遅延の正確な実装は不明ですが、他のトリガーと同様に定期的に検査されると考えられます。
mean_time_to_happen = { months = 5 }
mean_time_to_happen = { days = 15 }
単位はdays、months、yearsです。条件付き補正をいくつでも加えられ、計時開始後にも影響するようです。単純なMTTHは各スコープで指定期間中に50%の確率で呼ばれ、その時点でトリガーを検査します。しかしMTTHへ補正を付けると各スコープで毎日条件を検査し、著しく高負荷になります。
MTTHは非推奨傾向
性能が悪いためバニラではMTTHを減らし、ランダム遅延付きのイベント呼出しへ移行しています。
他イベントからの呼出し¶
実行中イベントから任意のオブジェクトへイベントを呼び、そのオブジェクトのスコープで実行できます。実際の呼出しまで1tick以上遅れる場合があります。
random_galaxy_planet = {
planet_event = { id = my_planet_event.1 }
}
country_event = { id = crisis.2000 days = 200 random = 100 }は200~300日遅延します。実行時に条件を満たさなければ発生しません。遅延イベントの条件はキュー投入時ではなく実行直前だけ検査します。
3.0以降はscopes = { from = fromfrom }で呼出しスコープを上書きできます。ただしローカルイベントターゲットは呼出し先で正しくスコープされません。
On Action¶
常時ポーリング以外で最も一般的な呼出し方法です。バニラの登録はcommon/on_actions/00_on_actions.txtにあります。MODは固有名のファイルをcommon/on_actionsへ追加でき、バニラのイベントに加えて呼ばれます。MOD制作のガイドラインにも従ってください。
月次・年次の低頻度ポーリングから、地上侵攻終了、調査完了、星系進入などの出来事まであります。登録イベントはis_triggered_only = yesにし、同じ出来事へ多数登録された候補から各トリガーで実際に呼ぶものを絞ります。ランダムイベントは出来事のたびに確率判定し、追加トリガーにより表面上の確率よりさらに稀になることがあります。
これは多くの高水準言語のGUI環境でイベントを登録する仕組みに相当します。効果フィールドを持つアノマリー、布告、政策、外交アクションなどからも直接イベントを呼べます。布告なら、有効化するたびに呼ばれます。
3.0以降はスクリプトから独自On Actionを発火できます。
fire_on_action = {
on_action = <string>
scopes = { from = X fromfrom = Y }
}
fire_on_action自体が1スコープとして数えられるようで、イベントターゲット以外はprevを1つ追加します。発火元はfrom = prev、その前はfrom = prevprevです。fromfrom以上へローカルイベントターゲットを指定すると、呼出しイベントで正しくスコープされません。この制約はグローバルイベントターゲットには適用されません。
条件付き説明¶
planet_event = {
id = colony.182
title = "colony.182.name"
desc = {
trigger = { owner = { NOT = { has_authority = auth_machine_intelligence } } }
text = colony.182.desc
}
desc = {
trigger = { owner = { has_authority = auth_machine_intelligence } }
text = colony.182.desc.mach
}
}
複数の条件が成立すると1つをランダム表示し、1つも成立しない場合は最初の説明を表示します。3.0以降、複数のdesc自体もランダムに1つ選ばれます。条件付きと静的説明を併用できます。
desc = {
trigger = { owner = { NOT = { has_authority = auth_machine_intelligence } } }
text = colony.182.desc
}
desc = colony.182.desc.mach
1つのdescへ、条件に応じて複数の文章断片を連結する動的ローカライズも作れます。
desc = {
trigger = {
text = colony.182.desc.top
success_text = {
text = colony.182.desc.multiplayer
is_multiplayer = yes
}
fail_text = {
text = colony.182.desc.singleplayer
is_multiplayer = yes
}
# 追加条件
text = colony.182.desc.bottom
# 追加条件
}
}
これを複数のdescエントリとも組み合わせられます。
選択肢¶
すべての表示イベントには最低1つのoptionが必要です。afterは選択肢と同じ階層へ置き、どの選択肢を選んでもその後に実行されます。Javaなどの例外処理におけるfinallyに似ています。
| フィールド | 説明 |
|---|---|
name |
表示名。事実上唯一の必須値で、通常はローカライズキー。翻訳済みの既定文字列も多数利用できます。条件付きの複数nameも使えます。 |
trigger |
選択肢を表示する条件。偽なら表示も選択もできません。 |
exclusive_trigger |
成立すると他の全選択肢を無効化します。2.0以降。 |
default_hide_option = yes |
名前と異なり隠しません。「キャンセル」キーを押した際の既定選択肢にします。 |
icon |
任意のアイコンスプライト。 |
sound |
選択時に鳴らす任意の音声ファイル。 |
allow |
選択可能条件。偽でも表示でき、特定条件で解禁される選択肢を見せられます。ウィンドウを最初に開いたときだけ検査し、その後の進行では更新しません。 |
tag |
event_window_type = leader_recruitの帝国イベントで、解雇/雇用ボタンを示します。3.8以降。 |
hide_option_if_not_allowed |
同じリーダー雇用画面で、許可されない選択肢を隠します。3.10以降。 |
条件付き名称:
option = {
name = { trigger = { <display_triggers> } text = <localization_string> }
name = { trigger = { <display_triggers> } text = <localization_string> }
...
}
効果文は選択肢本体へ直接置きます。ゲームは効果からツールチップを自動生成します。custom_tooltipは追加説明、hidden_effectは中の効果に基づく自動ツールチップを抑止します。tooltip内の効果は実行せず、ツールチップだけ生成します。
option = {
name = "xxx"
custom_tooltip = "yyy"
hidden_effect = {
# 選択時に実行する効果
}
}
ai_chanceは利用可能な選択肢間でAIの半ランダム選択を重み付けします。次は天上戦争イベントの例です。
ai_chance = {
factor = 100
modifier = {
factor = 0
OR = {
has_valid_civic = civic_hive_devouring_swarm
has_valid_civic = civic_fanatic_purifiers
has_valid_civic = civic_machine_terminator
}
# is_homicidal = yesでも同等
}
}
外交イベント(diplomatic = yes)では次も使えます。
response_text— 応答文キー。is_dialog_onlyなしでは文章とOKボタンを表示し、afterを即座に実行してOKを待ちません。is_dialog_only— 文章応答だけを開く任意の真偽値です。ボタン効果は実行してもイベントを閉じないためafterは実行しません。response_text必須で、省略するとゲームはエラーを出してイベントを終了します。custom_gui— 指定GUIでイベント外観を変更します。選択肢内でもその選択肢のGUIを変更できます。インターフェースのMOD制作のカスタムウィンドウも参照してください。custom_gui_option— 全ボタンを指定GUIへ変更します。選択肢内では使えず、各選択肢のcustom_guiで上書きできます。
推奨事項¶
他のゲームファイルは後勝ちですが、eventsは最初に読み込まれた定義だけが有効です。ファイル全体を上書きせずバニライベントだけを置換するには、UTF-8順でバニラより先になるファイル名が必要です。通常は!!vanilla_override_event.txtのように先頭へ感嘆符を付けます。
発火方法¶
hide_windowとis_triggered_onlyが最も一般的で、両方を持つイベントも多数あります。ポーリングにランダム性を加える設定としてMTTHもよく使われます。常時ポーリングは巨大なCPU負荷になりうるため、必要最小限にします。推奨は次の方法です。
- すぐ偽になる安価な条件を持つ門番イベントだけをポーリングする。
- On Actionからイベント列を開始する。
- On Actionから門番イベントを呼ぶ。
イベント連鎖・スコープ・実行順¶
バニラではイベントを長く連鎖させる例が多く、正しい実行順・スコープ設定に必要と考えられます。特に、非表示イベントが実際の準備処理を行い、表示イベントを呼ぶ形が非常に一般的です。immediateの変更も内部キャッシュを越えて反映されるまで、次イベントの呼出しまで待つ必要がある可能性を示します。
表示イベント例¶
1.6.2版の旧「機械の反乱」の例です。このイベントは現在削除されています。
country_event = {
id = crisis.2192
title = crisis.2192.name
desc = crisis.2192.desc
picture = GFX_evt_robot_assembly_plant
show_sound = event_laboratory_sound
location = root
is_triggered_only = yes
immediate = { set_country_flag = robots_pacified }
option = {
name = crisis.2192.a
custom_tooltip = crisis.2192.a.tooltip
hidden_effect = { set_country_flag = ai_perfect_servants }
}
option = {
name = crisis.2192.b
hidden_effect = {
country_event = { id = crisis.2000 days = 400 random = 400 }
}
}
}
非表示イベント例¶
1.8.3のプレスリン危機テストイベントです。
原文には「銀河規模の大量絶滅や食欲不振を引き起こすかもしれない」という警告があります。hide_windowはプレイヤーへ知らせず起動処理を行うために必要です。trigger = { always = no }については「呼ばれたときだけ発生させると思われる」と原文は説明しています。グローバルフラグは危機発生をゲームへ知らせるために設定します。
country_event = {
id = crisis.199
hide_window = yes
trigger = { always = no }
immediate = {
set_global_flag = prethoryn_invasion_happened
set_global_flag = prethoryn_transmission
begin_event_chain = { event_chain = "coming_storm_chain" target = ROOT }
random_rim_system = {
set_star_flag = swarm_invasion_target_1
save_event_target_as = prethoryn_invasion_system
}
create_point_of_interest = {
id = coming_storm_poi.1
name = "coming_storm_poi_1_poi"
desc = "coming_storm_poi_1_poi_desc"
event_chain = "coming_storm_chain"
location = event_target:prethoryn_invasion_system
}
country_event = { id = crisis.17 days = 10 }
}
}
全パラメータ例¶
次の一覧はイベント本体で利用する全主要フィールドをまとめたものです。
| フィールド | 説明 |
|---|---|
id |
名前空間と一致する一意ID。 |
title |
タイトルのローカライズキー。 |
desc |
説明キー。複数ならランダム。ブロック形式でtext、trigger、exclusive_triggerを使えます。trigger内ではcustom_tooltipと同様にtext、success_text、fail_textやswitchを使えます。textは任意の文章、success_textは条件成立時の文章(複数を連結可)、fail_textは不成立時の文章を表示します。exclusive_trigger成立時は他の説明をすべて無効化します(2.1以降)。 |
picture |
interface/xxx.gfxで定義したイベント画像。条件付きブロックではpicture、trigger、exclusive_triggerを使います。画像一覧はイベント画像。 |
location |
プレイヤーが移動できる関連オブジェクトのスコープ。 |
show_sound |
表示時に鳴らすsound/xxx.assetの音声名。 |
hide_window |
非表示処理イベント。タイトル・説明・選択肢が不要。 |
diplomatic |
外交通信風の表示。ファーストコンタクトなど。 |
custom_gui / custom_gui_option |
外交イベント本体/全選択肢ボタンのGUI。 |
picture_event_data |
外交イベント画像のデータで、ほとんどの項目は任意です。portraitは動くポートレートで、帝国・リーダー・種族スコープを受け付けます。planet_backgroundは窓の向こうの惑星背景、graphical_cultureはその都市の画像種別、city_levelは都市規模(背景惑星を首都らしく見せる場合など)を指定します。roomは静止背景で、静止画像またはスコープを受け付けます。 |
major / major_trigger |
major = yesで他帝国にも表示し、major_triggerで対象国を絞る旧機能。たとえばhas_ethic = ethic_materialistなら全物質主義国へ表示します。3.8で削除された可能性があります。 |
auto_select |
自動選択。 |
force_open |
外交イベントを強制表示。 |
auto_opens |
ポップアップ抑制中でも強制表示。 |
fire_only_once |
1ゲームに1回だけ発生。 |
trackable |
イベント上部の自動追跡ボタンを有効化。location必須。 |
is_triggered_only |
自動発火せず、別イベントかOn Actionからのみ呼ぶ。 |
mean_time_to_happen |
平均発生時間と条件付きmodifier。指定期間に平均して発生するよう、日ごとの確率を計算します。例のyears = 100にfactor = 0.1を適用すると平均10年です。monthsやdaysも指定できます。 |
trigger |
発生条件。On Actionや遅延イベントのように呼出し時点で条件を保証できない場合にも使います。 |
immediate |
発火直後の効果。競合防止フラグ、プレイヤーが選択を遅らせては困る効果(調査船の船長を死亡させるなど)、非表示イベントの全処理を置きます。 |
option |
表示イベントに最低1つ必要。複数可。 |
abort_trigger |
真になると選択肢効果を実行せずイベントを消します。ゲーム停止中は評価しません。 |
abort_effect |
中断条件成立時の効果。 |
after |
選択後の効果。hidden_effectに入れない限り、全選択肢へ共通ツールチップを生成します。 |
country_event = {
id = example.1
title = example.1.name
desc = example.1.desc
desc = {
text = example.1.desc.conditional
trigger = {
text = example.1.desc.conditional
success_text = { text = example.1.success <conditions> }
fail_text = { text = example.1.failure <conditions> }
}
exclusive_trigger = { <conditions> }
}
picture = GFX_evt_exploding_ship
picture = {
picture = GFX_evt_exploding_ship
trigger = { <conditions> }
exclusive_trigger = { <conditions> }
}
location = from
show_sound = event_ship_explosion
hide_window = yes
diplomatic = yes
custom_gui = "enclave_caravaneer_window"
custom_gui_option = "enclave_caravaneer_option"
picture_event_data = {
portrait = event_target:contact_empire
planet_background = event_target:contact_empire
graphical_culture = event_target:contact_empire
city_level = event_target:contact_empire
room = event_target:contact_empire.ruler
}
auto_select = yes
force_open = yes
auto_opens = yes
fire_only_once = yes
trackable = yes
is_triggered_only = yes
mean_time_to_happen = {
years = 100
modifier = { factor = 0.1 <conditions> }
}
trigger = { <conditions> }
immediate = { <effects> }
option = {
name = example.1.a
custom_gui = "enclave_curator_option"
trigger = { <conditions> }
exclusive_trigger = { <conditions> }
allow = { <conditions> }
custom_tooltip = example.1.a.tooltip
tooltip = { <effects_for_tooltip_only> }
hidden_effect = { <effects> }
}
abort_trigger = { <conditions> }
abort_effect = { <effects> }
after = { <effects> }
}
is_triggered_onlyもMTTHもない場合、条件成立中は毎日発生します。銀河全体への意図しない連続実行を防ぐため、必ず発火方式を指定してください。
イベント継承¶
3.4以降はbase = <event_id>で別イベントの性質を継承できます。desc_clear、option_clear、picture_clear、show_sound_clearで個別の継承項目を消し、挙動を再利用しながらフレーバーだけ変更できます。飛び地勢力のスクリプトなどで数千行を削減しました。基礎イベントは継承側より先に定義する必要があります。
原文の参考資料は開発日記第253回(2022年5月5日)です。
空イベントボックスの不具合¶
タイトル・文章・画像がなく、OKボタンだけのイベントが毎日画面を埋め、プレイ不能になることがあります。通常はMOD入り環境で起こります。
原因¶
破損したイベントファイルの読込みです。波括弧の位置が誤っているか、必要な括弧がないと、その後のイベントは存在だけ残り、タイトル、説明、毎日全オブジェクトで発火するのを防ぐ設定などが読み取られず空洞化します。多くはゲーム版間の構文変更へ未対応のMOD、または更新ファイルがローカルへ届いていないことが原因です。
対処¶
debugtooltipコンソールコマンドを有効にし、OKボタンへカーソルを合わせてイベントIDを確認します。- IDの名前空間などから原因MODを特定します。
- MODが古ければ無効化して更新を待ちます。公開版は新しいのにローカルだけ古ければ、購読解除・再購読で再取得します。
原文は、古い構文をMODフォルダ全体で修正する外部Pythonツールとして、FirePrince作のStellarisModpackUtilityのmodupdater.pyも紹介しています。
出典: Stellaris Wiki — Event modding(原文更新日: 2025年12月17日、版ID 112649)
翻訳日: 2026年9月18日 / 対応バージョン: 3.6
本ページは原文Wiki(CC BY-SA 3.0)の内容を翻訳した非公式ファン翻訳です。