新機能の「ワークショップ」を使って、今までにない柔軟さでゲームを作成することができます!ワークショップでは、今現在お楽しみいただいている「オーバーウォッチ」のゲーム・モードにさまざまなルールやユニークなプレイ条件を追加する「スクリプト」というものを作成していきます。ヒーローの移動やアビリティの挙動に変更を加える、プレイヤーが受けるダメージや回復量を変化させる、一定の状況下でテキストを表示させるなど、ルールにできることは多岐に渡ります。
地面に触れていると炎上してしまう「モルテン・フロア」など、さまざまなゲーム・モードを作れるようになります!
目次
ワークショップへのアクセス
ワークショップにアクセスするには、[プレイ] > [ゲーム・ブラウザー] > [作成] > [設定] > [ワークショップ]をクリックしてください。
スクリプトを作成する
スクリプトは以下の手順で作成します。
この手順を踏めば、その余地さえあればいくらでもルール、条件、アクションを追加できます。
ルールを追加する
ルールとはスクリプトを構成する部品で、細かくカスタマイズすることができます。各スクリプトには1つ以上のルールが必要です。
ルールには任意のコメントがついていることもあります。また、各ルールは以下のものを含んでいます。
- イベント:ルールが実行されるタイミングを定義します。詳しくは「イベントを選ぶ」をご覧ください。
- 条件:ルールが適用されるために満たす必要がある、さまざまな条件のリストです。任意で設定できます。詳しくは「条件を追加する」をご覧ください。
- アクション:イベントと条件が満たされたときに発生することのリストです。詳しくは「アクションを追加する」をご覧ください。
ルールを追加するには、[ルール追加]をクリックします。
イベントを選ぶ
イベントはルールが実行されるタイミングを定義します。ゲーム内でイベントが発生すると、ルールのインスタンスが作成されます。インスタンスはそれぞれ条件を評価し、他のインスタンスとは無関係にアクションを実行します。
エディターでルールを作成すると、自動的にイベントが追加されます。発生させたいイベントのタイプを指定しましょう。
イベントタイプは以下の手順で指定します。
- イベントの横のドロップダウンをクリックします。
-
以下のいずれかを選択します。
イベントタイプ 説明 進行中 - グローバル ゲームの開始時に、このルールのインスタンスを1つ作成します。このインスタンスはゲームが終わるまで有効です。
- インスタンスはゲーム中ずっと有効なので、条件をパスすることもあれば失敗することもあります。初めて条件をパスした段階でアクションが実行されます。
- 条件リストが失敗した後、もう一度パスすると、アクションの実行を再度試みます。
進行中 - 各プレイヤー 各プレイヤーについて、ゲームへの参加時にこのルールのインスタンスが作られます。このインスタンスはプレイヤーが抜けるか、そのゲームが終わるまで有効です。それぞれのインスタンスは別々に条件とアクションを追跡および実行します。
- インスタンスは該当するプレイヤーがゲームに参加している限り有効なので、条件をパスすることもあれば失敗することもあります。初めて条件をパスした段階でアクションが実行されます。
- 条件リストが失敗した後、もう一度パスすると、アクションの実行を再度試みます。
プレイヤーがキルを獲得 プレイヤーがキルを獲得した時にルールを実行します。このルールのインスタンスは、1人のプレイヤーにつき一度に1つだけ有効になります。
- プレイヤーが誰かを倒した時に条件をチェックします。すべての条件をパスするとアクションが実行されます。1つでも失敗するとアクションは実行されません。
ファイナル・ブロウを獲得 プレイヤーがファイナル・ブロウを獲得した時にルールを実行します。このルールのインスタンスは、1人のプレイヤーにつき一度に1つだけ有効になります。
- プレイヤーが敵にファイナル・ブロウを放った時に条件をチェックします。すべての条件をパスするとアクションが実行されます。1つでも失敗するとアクションは実行されません。
プレイヤーがダメージを与えた プレイヤーがダメージを与えた時にルールを実行します。このルールのインスタンスは、1人のプレイヤーにつき一度に1つだけ有効になります。
- プレイヤーが敵にダメージを与えた時に条件をチェックします。すべての条件をパスするとアクションが実行されます。1つでも失敗するとアクションは実行されません。
プレイヤーがダメージを受けた プレイヤーがダメージを受けた時にルールを実行します。このルールのインスタンスは、1人のプレイヤーにつき一度に1つだけ有効になります。
- プレイヤーが敵からダメージを受けた時に条件をチェックします。すべての条件をパスするとアクションが実行されます。1つでも失敗するとアクションは実行されません。
プレイヤーが倒れた プレイヤーがキルされた時にルールを実行します。このルールのインスタンスは、1人のプレイヤーにつき一度に1つだけ有効になります。
- プレイヤーがキルされた時に条件をチェックします。すべての条件をパスするとアクションが実行されます。1つでも失敗するとアクションは実行されません
-
必要に応じて、このイベントの影響を受けるチームまたはプレイヤーを指定します。以下の選択肢があります。
オプション 説明 すべて すべてのチームにイベントが適用されます。フリー・フォー・オールのゲーム・モードのプレイヤーも同様です チーム1(または現在のチーム名) イベントはこのチームにのみ適用されます チーム2(または現在のチーム名) イベントはこのチームにのみ適用されます オプション 説明 すべて すべてのプレイヤーにイベントが適用されます スロット0〜5 イベントは指定されたスロットのプレイヤーにのみ適用されます。チーム戦では、2人のプレイヤーに1つのスロットが割り当てられていることがあります(各チームから1人ずつ)。 スロット6〜11 イベントは指定されたスロットのプレイヤーにのみ適用されます。フリー・フォー・オールのゲーム・モードでのみ使用します。 特定のヒーロー イベントはそのヒーローとしてスポーンしたプレイヤーにのみ適用されます
条件を追加する
ルールとイベントを設定した後は、任意で1つまたは複数の条件を設定できます。条件とは、ルールに設定されたアクション・リストを実行するためにクリアしなければならない一連の決め事です。イベントタイプが「進行中 - グローバル」または「進行中 - 各プレイヤー」に設定されているルールに属する条件は、満たされているかどうか(Trueかどうか)継続的にチェックされます。それ以外のルールに属する条件は、指定されたイベントが発生するたびにチェックされます。条件が設定されていないルールの場合は、イベントが発生した時点でアクション・リストの実行を試みます。条件は、それぞれ2つの値から成り立っています。これらの値は演算子を用いて比較し、Trueかどうかのチェックを行います。詳しくは「値」をご覧ください。
条件を追加する方法は次の通りです。
- 条件の横の[追加]をクリックします。
- 値の項目を入力します。
- 注意:値そのものに入力すべき内容がある場合(たとえば、「ヒーロー」の値では、使用ヒーローを取得するプレイヤーを指定しなければなりません)、一段下に値に必要な情報を入力するための項目が表示されます。
- 演算子を選びます。使用できる演算子は以下の通りです。
- ==等しい
- != 等しくない
- > より大きい(超過)
- >= 以上
- < より小さい(未満)
- <=以下
こちらの例では、そのゲームのプレイヤーの合計数が生存中のプレイヤーの数と等しいかどうかをチェックします。
- 値:生存プレイヤーの数… 生存しているプレイヤー全員の数をチェックします
- チーム:チーム… チームに参加している全プレイヤーをチェックします
- チーム:すべて… すべてのチームのプレイヤー全員をチェックします
- 演算子: ==… 1つ目の値と2つ目の値が等しいとき、条件がTrueを返します
- 値:生存プレイヤーの数… 生存しているプレイヤー全員の数をチェックします
- チーム:チーム… チームに参加している全プレイヤーをチェックします
- チーム:すべて… すべてのチームのプレイヤー全員をチェックします
その他の例
- フラッグが運ばれている(犠牲者) == False:倒されたプレイヤーがフラッグを持っていないことが条件です
- しゃがんでいる(イベント・プレイヤー) == True:イベントが有効になっているプレイヤーがしゃがんでいることが条件です
- ファイナル・ブロウ数(攻撃者) > 10:攻撃しているプレイヤーがファイナル・ブロウを11回以上達成していることが条件です
アクションを追加する
アクションは、ゲームに変化を起こします。アクションは上から順番に実行されていきます。設定したアクション・リストを実行するには、以下のことが必要です。
- ルールに関連づけられたイベントが発生している
- ルールのすべての条件がTrueを返している(または、条件が設定されていない)
- イベントタイプが「進行中 - グローバル」か「進行中 - 各プレイヤー」の場合、すべての条件を初めてパスしたときに一連のアクションが実行されます。条件リストが失敗した後、もう一度パスすると、アクションの実行を再度試みます。
待機アクション(詳しくは待機アクションをご覧ください)を除いて、すべてのアクションは直ちに実行および完了されます。各アクションは0個以上の「入力」で構成されており、これらはゲームに生じる変化を表現します。入力はそれぞれ「値」を与えられます。値とは断片的な情報、あるいは情報を取得するための指示のことです。詳しくは「値」をご覧ください。
アクションを追加する方法は次の通りです。
- アクションの横の[追加]をクリックします。
- アクションを選択します。アクションとは、ゲームに生じる変化を設定するものです。
- 表示されたそれぞれの入力について、ドロップダウンから値を選択します。
- 注意:一部のアクションはオブジェクトや継続的な動作を作成します。このようなアクションは「再評価」と呼ばれる入力が設定されていることがあります。この入力は、そのアクションの他の入力が「固定」(オブジェクトや継続的な動作が変化しない)であるか「動的」(入力に割り当てられた値が変化すると、オブジェクトや継続的な動作が変化する)であるかを決定します。
アクション
- マッチ時間をポーズする:現在のマッチの時間を一時停止します
- 変更するグローバル変数(T, 追加, 5):グローバル変数「T」が5増加します
- 目視可否を設定(イベント・プレイヤー, 敵):このルールを実行しているプレイヤーは、敵から姿が見えなくなります
再評価の入力を持つアクション
- アイコンを作成(すべてのプレイヤー(すべてのチーム), グローバル変数(P), 注意, 位置):グローバル変数「P」で位置を指定し、その場にいる全員が見ることのできる警告アイコンを作成します。継続的に位置を再評価するため、グローバル変数「P」が後から変化した場合、アイコンは新しい位置に表示されます。
- アイコンを作成(すべてのプレイヤー(すべてのチーム), グローバル変数(P), 注意, なし):グローバル変数「P」で場所を指定し、その場にいる全員が見ることのできる警告アイコンを作成します。再評価を一切行わないので、グローバル変数「P」が後から変化してもアイコンの位置は変わりません。
アクションタイプ
さまざまなアクションを設定できますが、中にはいくつか注意が必要なものがあります。
ループは、一連のアクションをもう一度最初から実行するアクションです。ループするアクションは4種類あります。
- ループ:アクション・リストを必ず再実行します
- ループする条件:アクションの条件の入力が「0」か「False」以外の値を返した場合、アクションを繰り返します。
- 条件が「TRUE」の場合ループ:ルールのすべての条件をその時点でパスしている場合にアクションをリスタートします
- 条件が「FALSE」の場合ループ:ルールのいずれかの条件を失敗している場合にアクションをリスタートします
ループのアクションを実行できるのは、アクション・リストの開始前に待機アクションの実行が確定している場合だけです。
良い例 | 悪い例 |
---|---|
ループ(LOOP)の前に待機(WAIT)アクションがあるので、実行できます。 |
待機をはさまず延々と繰り返してしまうので、実行できません。 |
待機とは、その後に続くアクションを実行する前に時間を経過させるアクションです。待機時間は最短で0.25秒です。
待機アクションの挙動には3つの選択肢があります。
- 条件無視:これを選択していると、条件や他のイベントがアクションの実行を妨げなくなります。
- イベントタイプが「進行中 - グローバル」か「進行中 - 各プレイヤー」の場合、失敗していた条件をパスしても、何も起きません。
- それ以外のイベントタイプの場合、そのタイプのイベントが同じイベント・プレイヤーに発生した時にイベントが無視されます。
- 「FALSE」の場合中止:これを選択していると、条件が失敗するようになった時にアクション・リストの実行が中止されます。
- 「TRUE」の場合リスタート:これを選択していると、以下のいずれかに該当した場合、アクションの実行がリセットされて最初のアクションに戻ります。
- イベントタイプが「進行中 - グローバル」か「進行中 - 各プレイヤー」であり、それまで失敗していた条件がパスするようになった。
- それ以外のイベントタイプであり、同じイベント・プレイヤーにイベントが発生し、かつすべての条件がパスした。
付加情報
ストリングとは、ゲーム内で表示できる一連の文字、数字、記号の列です。
- ストリング:表示されるテキストです。ここに波括弧に囲われた数値を入力すると、対応する入力によって引き出される値がその部分に表示されます。
- {0}:テキストに変換され、{0}を置き換える値。値の種類は問いません。
- {1}:テキストに変換され、{1}を置き換える値。値の種類は問いません。
- {2}:テキストに変換され、{2}を置き換える値。値の種類は問いません。
- ストリング(“ハロー”, NULL, NULL, NULL):「ハロー」というストリングを生成します
- ストリング(“{0} vs {1}”, ヒーロー(アナ), ヒーロー(ファラ), NULL):「アナ vs ファラ」というストリングを生成します
ストリング同士を組み合わせることでで、複雑なストリングを作ることもできます。
- ストリング(”{0} vs {1}”, ヒーロー(アナ), ストリング("{0} & {1}", ヒーロー(ファラ), ヒーロー(ゲンジ), NULL), NULL):「アナ vs ファラ & ゲンジ」というストリング生成します
ストリングは条件に使うことができず、変数に格納することもできません。同じカスタム・ゲームに異なる言語を使うプレイヤーがいると、複雑な処理が必要になってしまうためです。
値とは断片的な情報、あるいはどうやって情報を取得するかという指示です。これは条件の入力、アクション、それ自身とは別の値に与えられます。値は互いに組み合わせることが可能です。
値の種類は非常に多いためここでは紹介を控えますが、ワークショップ・エディターに説明が記載されています。以下は、よく目にすることになる値の例です。
値 | 説明 |
---|---|
数値 | 入力によって指定された範囲の実数を与えます |
ベクトル | 入力によって指定された範囲の3次元の値を与えます。位置や方向を示すときに使用します。 |
チーム | チーム1、チーム2、すべてのチームなど、特定のチームを表します |
ヒーロー | 特定のヒーローを表します |
NULL | プレイヤーまたはエンティティがないことを表します |
TRUE | 「TRUE」の値を返します |
FALSE | 「FALSE」の値を返します |
COMPARE | 自身が表す比較が真か偽かによって、「TRUE」か「FALSE」を返します |
イベント・プレイヤー | ルールのインスタンスを実行しているプレイヤーを返します。該当するプレイヤーがいなければ「NULL」を返します |
攻撃者 | ルールのインスタンスの攻撃者を表します。攻撃者がいなければ「NULL」を返します |
犠牲者 | ルールのインスタンスの犠牲者を表します。犠牲者がいなければ「NULL」を返します |
現在の配列の要素 | 「いずれに対しても『TRUE』」、「すべてに対して『TRUE』」、「フィルタリングされた配列」、「ソートされた配列」の値と一緒に使うことで、現在評価されている値を返します |
値は配列に格納されることがあります。配列とは、複数の値の集合体のことです。
- アクションや値の中には、配列を作成したり編集したりするものがあります。
- たとえば「すべてのプレイヤー」の値は、その時点でゲームにいるすべてのプレイヤーの配列を作ります。
- 「グローバル変数を変更する」アクションか「プレイヤー変数を変更する」アクションの「配列に追加」演算を利用して、自分で配列を構築することも可能です。
- 入力が配列を必要としている時に他の種類の値を受け取った場合、その値は入力のために、要素が1つだけの配列にコピーされます。同様に、他の何らかの値を期待していた入力が配列を受け取った場合には、配列内の最初の値(配列が空の場合は「0」)が使われます。
変数とは値を格納することができ、後から取り出して使うことができる場所です。変数にはストリング以外のどんな値でも格納できます。すべての変数は、数値の「0」から始まります。
スクリプトの変数には、次の2つの種類があります。
- グローバル変数:グローバル変数は、全部で26個(「A」から「Z」まで)あります。それぞれの変数は、別々の値や値の配列を持っています。
- プレイヤー変数:各プレイヤーが、全部で26個(「A」から「Z」まで)の変数を持ちます。それぞれの変数は別々の値や値の配列を持っています。
変数に行える演算は、次の3種類です。
- 設定:「グローバル変数を設定する」と「プレイヤー変数を設定する」は、変数を新しい値に設定し、以前の値と置き換えます。
- 変更:「グローバル変数を変更する」と「プレイヤー変数を変更する」は、特定の算術演算(足し算や掛け算など)や配列演算(追加、削除)を用いて、変数の値を変更します。
- 追跡:「グローバル変数を継続的に追跡」、「プレイヤー変数を継続的に追跡」、「グローバル変数を特定のレートで追跡」、「プレイヤー変数を特定のレートで追跡」は、継続的に、または一定のペースで、少しずつ変数を変更します。
- 追跡の目的は、数値かベクトル(または、数値かベクトルを結果とする値)のいずれかです。
- 目的が数値の場合、変数の値は追跡が始まる前の数字である必要があります。
- 目的がベクトルの場合、変数の値は追跡が始まる前のベクトルである必要があります。
- 目的の再評価が有効になっている場合、追跡は必要に応じて更新され、変更された目的を追跡します。すでに目的に到達したことがある場合でも同様です。再評価について詳しくは、アクションの追加をご覧ください。
- 追跡は「グローバル変数の追跡を中止」と「プレイヤー変数の追跡を中止」のアクションでキャンセルできます。
- 追跡をキャンセルした場合、変数はその時点の値を保ちます。この値は、追跡が始まった時点の値と目的の間のいずれかの値です。
- 追跡の目的は、数値かベクトル(または、数値かベクトルを結果とする値)のいずれかです。
使用例
これでアクションの基本は押さえました。それでは早速、ゲーム・モードを実際に作ってみましょう!追加する必要のあるもの、そしてその理由を、順を追って説明していきます。
まずはモルテン・フロアの作り方を説明していきます。モルテン・フロアでは、ヒーローは地面に接すると炎上し、ダメージを受けます。
- まず初めに、ゲームの舞台となるマップを決めましょう。
- [プレイ] > [ゲーム・ブラウザー] > [作成] > [設定] > [マップ]をクリックします。
- ゲームのテストに使いたいマップを選択し、それ以外のマップをすべて無効にします。
- 次に、ワークショップに入ります。
- [戻る]をクリックします。
- [ワークショップ]をクリックします。
- それではスクリプトを作成していきましょう!最初のルールを追加します。
- [ルール追加]をクリックします。
- 「コメント」に「地上にある場合、燃焼を開始する」と記入します。こうすることで、これが地面に触れているプレイヤーを炎上させるルールであると分かります。
- 次はイベントタイプを変更して、このルールがいつ実行されるかを指定します。
- イベントのドロップダウンの中から、[進行中 - 各プレイヤー]を選択します。これは、ゲーム内のプレイヤー全員について個別にルールが評価されることを表します。
- 他のドロップダウンはデフォルトのままにしておきます。
- ここで条件を1つ追加します。この条件は、ルールを実行するかどうかを決定するものです。ルールを常に実行したいときは、空欄にしておきましょう。
- 条件で[追加]をクリックします。
- 値のドロップダウンで[地上にいる]を選択します。プレイヤーが地面にいると、この値は常にTrueを返します。
- 他のドロップダウンはデフォルトのままにして、[OK]をクリックします。
- イベント・プレイヤーは、「ルールが現在実行されているプレイヤー」を意味します。
- 最後に、アクションを追加します。アクションとは、条件がTrueのときに発生する出来事です。
- 今回は、ヒーローが地面にいると炎上するようにアクションを設定します。
- アクションで[追加]をクリックします。
- アクションのドロップダウンから[ステータスを設定]を選択します。
- ステータスのドロップダウンから[燃焼中]を選択します。
- 期間の数字のスライダーを動かし[10,000]に設定します。
- 他のドロップダウンはデフォルトのままにして、[OK]をクリックします。
- 今回は、ヒーローが地面にいると炎上するようにアクションを設定します。
- では、地面に触れたヒーローが本当に炎上するかどうか、テストしてみましょう!
- [戻る]を2回クリックします。
- ゲーム作成画面で、[開始]をクリックします。
- ヒーローを選択します。
- ゲームに入ると、ヒーローが炎に包まれているはずです。
- Escキーを押して[ワークショップ・エディター]をクリックし、スクリプトの設定を続けます。
- それでは、もう1つルールを追加して、ジャンプ中や空中に浮かんでいる時はヒーローが炎上しないようにします。
- 新しくルールを作ってもいいですが、ここでは先ほど作ったものをコピーしましょう。
- 作成したルールの横の[コピー] をクリックします。
- [ルールをペースト]をクリックします。
- 説明を「地上にない場合、燃焼を停止する」に変更します。こうすることで、空中やジャンプ中に火を消すルールであると分かります。
- すでにあるイベントタイプを残します。
- 次は条件を編集してみましょう。この条件は、ルールを実行するかどうかを決定するものです。
- [地上にいる(イベント・プレイヤー) == True]という既存の条件をクリックします。
- 値のドロップダウンで[False]を選択します。
- 他のドロップダウンは元のままで、[OK]をクリックします。
- 今度はアクションを編集しましょう。地上にいないヒーローの炎上を止めるというアクションを設定します。
- [ステータスを設定(イベント・プレイヤー, NULL, 燃焼中, 10000)]という既存のアクションをクリックします。
- アクションのドロップダウンから[ステータスをクリア]を選択します。
- ステータスのドロップダウンから[燃焼中]を選択します。
- 他のドロップダウンはすべてそのままで、[OK]をクリックします。
- ヒーローが空中にいれば炎上しなくなるかどうか、テストしてみましょう!
- [戻る]を2回クリックします。
- ゲームに入ると、ヒーローが炎に包まれているはずです。この状態でジャンプして、ヒーローの炎上が止まるかどうか確認してみましょう。
- Escキーを押して[ワークショップ・エディター]をクリックし、スクリプトの設定を続けます。
- 最後に、ヒーローが地上にいるときにダメージが発生するように設定しましょう。
- 「地上にある場合、燃焼を開始する」ルールを開きます。
- アクションで[追加]をクリックします。ヒーローが地面に接しているとダメージを受けるというアクションを設定しましょう。
- アクションのドロップダウンから[継続ダメージ]を選択します。
- 期間の数字のスライダーを動かし[9999]に設定します。
- 1秒あたりのダメージで、数字のスライダーを[30]に動かします。
- 他のドロップダウンはデフォルトのままにして、[OK]をクリックします。
- o「地上にない場合、燃焼を停止する」ルールにも手を加えましょう。
- アクションで[追加]をクリックします。ヒーローが地面に接していない時はダメージが止まるアクションを設定しましょう。
- アクションのドロップダウンから[すべての継続ダメージを停止]を選択します。
- ヒーローが地上にいるとダメージを受け、ジャンプ中や空中にいるときはダメージを受けなくなっているでしょうか? テストして確認してみましょう。
- [戻る]を2回クリックします。
- リスポーンエリアから出て、ヒーローがダメージを受け始めるかどうか確認します。
- ジャンプして、ヒーローがダメージを受けなくなるかどうか確認します。
- 大成功です!「オーバーウォッチ」流のダメージ床の完成です!
ここからは「ミラー・デスマッチ」のゲーム・モードを詳しく解説しながら作っていきます。ミラー・デスマッチとは、複数の短いラウンドからなるゲームで、プレイヤー全員が同じヒーローを操作して戦います。1つのラウンドが終了すると、各プレイヤーはそれまでいたのと同じ場所に次のヒーローとなってリスポーンします。次のヒーローは、予め用意したリストからランダムに選ばれます。最後のラウンドが終了した時点で、最もキル数の多いプレイヤーの勝利です。
たとえば、あるマッチでは全員がマクリーとしてスタートし、次のラウンドでファラに切り替わります。別のマッチでは、スタート時はウィドウメイカーですが、次のラウンドでアッシュに切り替わるかもしれません。同じヒーローリストに遭遇することはほとんどないよう、リストを生成することになります。
それでは、ミラー・デスマッチのスクリプトを作ってみましょう!
- [プレイ] > [ゲーム・ブラウザー] > [作成] > [設定] > [ワークショップ]をクリックします。
- 最初に、操作対象になる可能性のあるヒーローのリストを作るルールを設定しましょう。
- このリストはグローバル変数「L」に配列として格納します。
- 配列は、プレイヤーのリスト、ヒーローのリスト、数値のリスト、単一の値など、様々な形をとることができます。値がないケースも存在します(これを「空」の配列といいます)。
- 配列内のそれぞれの値は、0から始まって数字が増えていく固有のインデックス番号をつけられ保存されます。インデックスとその値は、「要素」と呼ばれることもあります。
- 配列の順番は重要です。
[リーパー, ウィンストン, マーシー]は、[マーシー, ウィンストン, リーパー]
とは別の配列となるので注意しましょう。 - 配列にはいろいろなタイプを組み合わせたものを格納する場合があります。たとえば、
[123, リーパー, True, -4.5]
のような配列も作れます。 - 入力が配列を必要としている時に与えられたのが単一の値である場合、入力はその値が構成する要素1つしか入っていない配列を受け取ります。
- 単一の値を必要とする入力に配列が与えられた場合、入力は配列内の最初の値を受け取ります(配列が空の場合は「0」)。
- ルールを追加し、このルールの役割がわかるようにコメントを入力します。
- イベントタイプを[進行中 - グローバル]に設定します。これは、このルールのインスタンスが1つしか実行されないことを示します。
- ルールに条件が設定されていないため、ゲームが始まるとすぐにルールが実行されます。
- 以下の内容のアクションを追加します。
- アクション:グローバル変数を設定する
- 変数:L
- 値:ヒーロー
- ヒーロー:プレイアブルにするヒーロー
- アクション:グローバル変数を設定する
- 操作できるヒーローが1人だけでは退屈なので、もっとヒーローを増やしましょう!以下の内容のアクションを好きなだけ追加してください。
- アクション:グローバル変数を変更する
- 変数:L
- 演算:追加
- 値:ヒーロー
- ヒーロー:プレイアブルにするヒーロー
[0, ファラ, ハンゾー, アナ,...]
のような配列になります。 - アクション:グローバル変数を変更する
- このルールに最後のアクションを追加しましょう。このルールはグローバル変数「L」(ヒーローの配列)のランダム化されたコピーをとり、新たにランダム化された配列を、「0」からゲーム・モードに必要なヒーローの数だけコピーします。そして、このコピーがグローバル変数「L」に格納されます。その結果、元のヒーローリストをランダムにシャッフルしたサブセットが生成されるというわけです。
- 実際の例を見てみましょう。最初のヒーローリストが
[アッシュ, ドゥームフィスト, ハンゾー, マクリー, ファラ, ソルジャー76, ゼニヤッタ, ウィドウメイカー, アナ]
だった場合、ランダム化された配列は[ハンゾー, ファラ, ウィドウメイカー, アナ, アッシュ, ドゥームフィスト, ソルジャー76, ゼニヤッタ, マクリー]
となり、この一部がコピーされるので最終的に[ハンゾー, ファラ, ウィドウメイカー, アナ, アッシュ, ドゥームフィスト]
となる可能性があります。
- 実際の例を見てみましょう。最初のヒーローリストが
- このリストはグローバル変数「L」に配列として格納します。
- 次のルールは、すべてのプレイヤーがいついかなる時も必ず同じヒーローをプレイするというものになります。
- ルールを追加し、このルールの役割がわかるようにコメントを入力します。
- イベントタイプを[進行中 - 各プレイヤー]に設定します。これは、各プレイヤーが自分のルールのインスタンスを実行するという意味です。
- 条件を2つ追加します。これらの条件が両方Trueと返すと、ヒーローが強制的に変わります。
- ラウンド数を指すグローバル変数「R」は、ヒーローリストのヒーローの合計数より小さい数字を設定しましょう。そうでない場合はゲームが終了し、それ以上ヒーローが強制されなくなります。ラウンド数は「0」から始まり、順に数字が増えていきます。したがって、全部で6ラウンドにしたい場合、最後のラウンドの数は「5」となります。グローバル変数「R」を「0」に設定する必要はありません。変数はすべて、デフォルトの値である0から始まるからです。
- 値:グローバル変数
- 変数:R
- 演算子:
- 値:カウント:
- 配列:グローバル変数
- 変数:L
- 配列:グローバル変数
- 値:グローバル変数
- このルールは、任意のプレイヤーが現在操作しているヒーローが、そのラウンド番号で求められるヒーローとは異なっていなければならないかどうかをチェックします。ここでいう任意のプレイヤーは、ルールのインスタンスを現在実行中のプレイヤーを示す特別な値「イベント・プレイヤー」で表されます。現在のラウンドの「求められるヒーロー」は、ヒーローリスト(グローバル変数「L」)の対応するインデックスに保存されているヒーローです。現在のラウンドはグローバル変数「R」に保存されているので、求められるヒーローは「配列内の値」を用いて取得できます。
- 値:ヒーロー:
- プレイヤー:イベント・プレイヤー
- 演算子:!=
- 値:配列内の値
- 配列:グローバル変数
- 変数:L
- インデックス:グローバル変数
- 変数:R
- 配列:グローバル変数
- 値:ヒーロー:
- ラウンド数を指すグローバル変数「R」は、ヒーローリストのヒーローの合計数より小さい数字を設定しましょう。そうでない場合はゲームが終了し、それ以上ヒーローが強制されなくなります。ラウンド数は「0」から始まり、順に数字が増えていきます。したがって、全部で6ラウンドにしたい場合、最後のラウンドの数は「5」となります。グローバル変数「R」を「0」に設定する必要はありません。変数はすべて、デフォルトの値である0から始まるからです。
- これでプレイヤーがヒーローを変更しなければならないことが分かりました。次に、2つの実行されるアクションを追加します。
- 最初のアクションは、求められるヒーローをイベント・プレイヤーに強制します。このアクションの最初の入力は、ヒーローを強制的に変えられるプレイヤーです。2番目の入力はヒーローですので、求められるヒーローを与えます。
- アクション:プレイヤーへのヒーロー強制を開始
- プレイヤー:イベント・プレイヤー
- ヒーロー:配列内の値
- 配列:グローバル変数
- 変数:L
- インデックス:グローバル変数
- 変数:R
- 配列:グローバル変数
- 第2のアクションによって、リストの次のヒーローをプリロード(事前に読み込むこと)します。こうしておくことで、プレイヤーは操作するヒーローが切り替わる時に長く待たされません。プレイするヒーローは全員同じですが、ヒーローのプリロードは各プレイヤーが個別に行います。これは、各プレイヤーがそのヒーローの異なるスキンをプリロードする可能性があるためです。[追加]の値を利用してグローバル変数「R」に「1」を追加することによって、現在のヒーローではなく次のヒーローをプリロードするよう、アクションに対して指示を出します。最終ラウンドでは、配列のグローバル変数「L」の範囲外の配列インデックスが生成されます。この挙動に問題はないので安心してください。なぜなら配列の範囲外の値は、すべて「0」とみなされるからです。ヒーローの入力が必要なアクションは「0」を受け取っても何も起きません。
- アクション:ヒーローをプリロード
- プレイヤー:イベント・プレイヤー
- ヒーロー:配列内の値
- 配列:グローバル変数
- 変数:L
- インデックス:追加
- 値:グローバル変数
- 変数:R
- 値:数値
- 数値:1.00
- 値:グローバル変数
- 配列:グローバル変数
- 最初のアクションは、求められるヒーローをイベント・プレイヤーに強制します。このアクションの最初の入力は、ヒーローを強制的に変えられるプレイヤーです。2番目の入力はヒーローですので、求められるヒーローを与えます。
- 次に作るルールは、まだ初期化されていない場合に、各ラウンドをセットアップするためのものです。
- ルールを追加し、このルールの役割がわかるようにコメントを入力します。
- イベントタイプを[進行中 - グローバル]に設定します。これは、このルールのインスタンスが1つしか実行されないことを示します。
- 次の3つの条件を追加します。ラウンドが始まるには、これらがTrueでなければなりません。
- ゲームが進行中でなければなりません。つまり、「ヒーローを編成しよう」画面とセットアップ時間は発生済み、一方でゲームはまだ終了していないという状況です。
- 値:進行中のゲーム
- 演算子:==
- 値:TRUE
- グローバル変数「I」がFalseでなければなりません。この変数は現在のラウンドが初期化されているかどうかを表すために使われます。グローバル変数「I」が設定されていない場合、値は「0」です。このような比較では、「0」は「FALSE」に相当します。
- 値:グローバル変数
- 変数:I
- 演算子:==
- 値:FALSE
- 値:グローバル変数
- ラウンド数を表すグローバル変数「R」は、ヒーローリストのヒーローの合計数未満でなければなりません。
- 値:グローバル変数
- 変数:R
- 演算子:<
- 値:カウント:
- 配列:グローバル変数
- 変数:L
- 配列:グローバル変数
- 値:グローバル変数
- ゲームが進行中でなければなりません。つまり、「ヒーローを編成しよう」画面とセットアップ時間は発生済み、一方でゲームはまだ終了していないという状況です。
- すべての条件がTrueのときに、ラウンドが初期化されます。これを行うためのアクションを追加します。
- 最初のアクションは、元のゲーム・モードに対し、通常の基準に基づいてマッチを終わらせてはならないことを伝えます。たとえばデスマッチなら、時間切れになったり、誰かがスコア上限に達したりしても、ゲームを終了させないということです。このアクションが実行されると、スクリプトが元のゲーム・モードの標準的な完了条件を再び有効にするか、勝者が明確に宣言されるまで、マッチは終了しなくなります。
- アクション:ゲーム・モードの標準完了を無効化
- 次のアクションは、ゲーム・モードの現在のタイマーをラウンドの長さに設定します。
- アクション:マッチ時間を設定
- 時間:数値
- 数値:60.00
- このアクションはグローバル変数「I」を「TRUE」に設定します。したがって、グローバル変数「I」が「FALSE」に戻されるまで初期化は発生しません。
- アクション:グローバル変数を設定する
- 変数:I
- 値:TRUE
- 最初のアクションは、元のゲーム・モードに対し、通常の基準に基づいてマッチを終わらせてはならないことを伝えます。たとえばデスマッチなら、時間切れになったり、誰かがスコア上限に達したりしても、ゲームを終了させないということです。このアクションが実行されると、スクリプトが元のゲーム・モードの標準的な完了条件を再び有効にするか、勝者が明確に宣言されるまで、マッチは終了しなくなります。
- このルールは、現在のラウンドが時間切れになるのを待ってから次のラウンドに進みます。
- ルールを追加し、このルールの役割がわかるようにコメントを入力します。
- イベントタイプを[進行中 - グローバル]に設定します。これは、このルールのインスタンスが1つしか実行されないことを示します。
- 以下の2つの条件を追加します。ゲームが次のラウンドに進むには、これらがTrueでなければなりません。
- ゲームが進行中でなければなりません。つまり、「ヒーローを編成しよう」画面とセットアップ時間は発生済み、一方でゲームはまだ終了していないという状況です。
- 値:進行中のゲーム
- 演算子:==
- 値:TRUE
- 現在のマッチ時間は0でなければなりません。これはラウンドの時間切れを意味します。
- 値:マッチ時間
- 演算子:==
- 値:数値
- 数値:0.00
- ゲームが進行中でなければなりません。つまり、「ヒーローを編成しよう」画面とセットアップ時間は発生済み、一方でゲームはまだ終了していないという状況です。
- これらの条件がTrueを返し、ラウンドが終了すると、マッチはラウンドの番号を進め、そのラウンドをまだ初期化されていないものとしてマークします。そのためのアクションを2つ追加しましょう。
- このアクションは、マッチが次のラウンドに移行したことを他のルールに知らせます。
- アクション:グローバル変数を変更する
- 変数:R
- 演算:追加
- 値:数値
- 数値:1.00
- このアクションはグローバル変数「I」を「FALSE」に設定し、新しいラウンドを初期化しなければならないことを他のルールに知らせます。
- アクション:グローバル変数を設定する
- 変数:I
- 値:FALSE
- このアクションは、マッチが次のラウンドに移行したことを他のルールに知らせます。
- 最後のルールは、すべてのラウンドがプレイされた段階でマッチを終わらせるためのものです。
- ルールを追加し、このルールの役割がわかるようにコメントを入力します。
- イベントタイプを[進行中 - グローバル]に設定します。これは、このルールのインスタンスが1つしか実行されないことを示します。
- グローバル変数「R」がグローバル変数「L」に含まれる要素の数と同じかどうかをチェックする条件を1つ追加します。同じであれば、ヒーローリストのすべてのヒーローが1ラウンドずつプレイされたということです。この状況になった時に、マッチが終了します。
- 値:グローバル変数
- 変数:R
- 演算子:==
- 値:カウント:
- 配列:グローバル変数
- 変数:L
- 配列:グローバル変数
- 値:グローバル変数
- 条件がTrueを返すと、このアクションが元のゲーム・モードの完了条件を再び有効にします。タイマーが0になっているので、ゲーム・モードがただちにマッチを終了させ、通常のマッチ終了時のフローが始まります。
- アクション:ゲーム・モードの標準完了を有効化
スクリプトをデバッグする
スクリプトを作り終わったら、ワークショップ・インスペクターの出番です。このツールは、作成したスクリプトがゲーム内で実行されているか、またどのアクションや条件が有効になっているかを見られるほか、スクリプトの問題点を確認することが可能です。
ワークショップ・インスペクターは以下の手順で開くことができます。
- 作成したスクリプトで ゲームを開始します。
- Escキーを押します。
- [ワークショップ・インスペクター]を押します。
- [有効化]を押します。この機能はデフォルト状態では有効化されていません。
ワークショップ・インスペクターは以下の内容で構成されています。
- エントリー:エントリーは、今何が起きているかを示します。
- コメント:ルールに関連づけられたコメントを表示します。
- 条件:アクションが実行されるためにパスしなければならない条件の一覧です。
- アクション:実行されたアクションの一覧です。
- タイムライン・スクラバー:タイムライン・スクラバーを左右に動かすと、ゲームの進行を進めたり巻き戻したりすることができます。
スクリプトをシェアする
素晴らしいスクリプトができあがったら、全世界に向けて(またはフレンドだけに)シェアしましょう。シェアは6ヶ月間有効です。あなたが作成したスクリプトは、作成元のプラットフォームにかかわらず、どのプラットフォームでも利用できます。
スクリプトをシェアする手順は次の通りです。
- [プレイ] > [ゲーム・ブラウザー] > [作成] > [設定] > [シェア ] をクリックします。
- [コピー]をクリックします。
- リンクを送りましょう!
スクリプトを開く
シェアされたスクリプトを利用する手順は以下の通りです。
- [プレイ] > [ゲーム・ブラウザー] > [作成] > [設定] > [インポート] をクリックします。 .
- リンクを入力します。
- [OK]をクリックします。
ヒントとポイント
- ワークショップ・インスペクターにキー割り当てを設定しておくと、すぐにアクセスできて便利です。キー割り当てを設定するには、Escキー > [オプション] > [操作設定]をクリックします。[ワークショップ・インスペクターを開く]が表示されるまで下にスクロールして、キー割り当てを行ってください。
- ワークショップ・インスペクターは、何が起きたかだけでなく、何が起きなかった、そしてその理由も教えてくれます!
- 既定の設定のこともお忘れなく!特定の設定がすでに作られているので、新たな解決策を自分で考えなくても、それらを流用することができます。
- イベントが思ったように発生しない場合、イベント・プレイヤーがすでにアクション・リストを実行している可能性があります。そんな時は、自分のルールの待機アクションをチェックしてみましょう。特に条件を無視する設定のルールがある場合は入念に確認したほうがいいでしょう。
- マップ上の特定の場所を選ぶには、「ベクトル」の値を使ってカメラアイコンをクリックします。
- 「スポーンした」の値は、プレイヤーがヒーローをゲーム内に入れた後にロジックを実行したい場合に便利です。
- セットアップと「ヒーローを編成しよう」フェーズの完了後にルールを実行したい場合は、「進行中のゲーム」の値を使うと便利です。
- 変数に値を割り当てて、ワークショップ・インスペクターで確認してみましょう。ゲームプレイ中に値が何を返しているのかを手軽に確認できます。
- 最後に作成されたエフェクトやアイコンは、「最新のエンティティ」の値を使ってプレイヤー変数に保存できます。こうしておけば後からエンティティを参照して破棄できます。
- フィルタリングされた配列を「プレイヤー全員が目標を確保中」や「半径内のプレイヤー」などの値と組み合わせると、特定の基準(死亡、生存、ステータス効果など)を満たしているプレイヤーを簡単にフィルタリングできます。
- 分岐する動作を作るときは、「スキップする条件」アクションを利用するといいでしょう。任意の条件がTrueの場合に、いくつでもアクションをスキップさせることができます。ただし、スキップされるアクションに「中止」アクションを組み込んで、両方の分岐が実行されるのを防がなければならないこともあります。
- ドロップダウンリストで文字をタイプすると、打ち込んだ文字でリストを絞り込むことができます。
- パラメータとして配列を期待している値が配列を受け取らない場合、その値は入力を要素が1つだけの配列として扱います。
- その逆も同じです。単独のデータを期待している値が配列を受け取った場合、その値は配列の0の位置にある要素を使います。
- スクリプトを複数のアクションや条件に分けると、うまくいかないときに原因を突き止めやすくなります。
- アクションや値や入力が何をするものかわからない場合は、PC版ならマウスオーバー、コンソール版では「詳細を見る」を選ぶことで、説明を見ることができます。
- ルールが何をしているのか忘れても思い出せるよう、必ずコメント欄に入力しておくようにしましょう!
- こまめにテストしましょう!