Ил-2 Штурмовик: Битва за Британию. Скрипты. Скрипты для чайников. Часть 2 - Загрузка подмиссий — различия между версиями

Материал из АвиаВики
Перейти к: навигация, поиск
(Загрузка подмиссий (автор FG28_Kodiak))
 
(не показано 12 промежуточных версии ещё одного участника)
Строка 1: Строка 1:
 
:'''Автор:''' FG28_Kodiak
 
:'''Автор:''' FG28_Kodiak
 
:'''Ссылка:''' [http://translate.googleusercontent.com/translate_c?hl=en&rurl=translate.google.com&sl=de&tl=en&twu=1&u=http://forum.sturmovik.de/index.php/topic,711.0.html%3FPHPSESSID%3Dac198c6ea43133020cb39e5f138fa85a&usg=ALkJrhjWaTqAGdjIJwlZI8dXorwpqDztTg Перейти (перевод Google)]
 
:'''Ссылка:''' [http://translate.googleusercontent.com/translate_c?hl=en&rurl=translate.google.com&sl=de&tl=en&twu=1&u=http://forum.sturmovik.de/index.php/topic,711.0.html%3FPHPSESSID%3Dac198c6ea43133020cb39e5f138fa85a&usg=ALkJrhjWaTqAGdjIJwlZI8dXorwpqDztTg Перейти (перевод Google)]
 +
Скачать оригиналы миссий:
 
:[http://forum.sturmovik.de/index.php?action=dlattach;topic=711.0;attach=216 Samples.zip]
 
:[http://forum.sturmovik.de/index.php?action=dlattach;topic=711.0;attach=216 Samples.zip]
 +
Скачать примеры с Sukhoi.ru:
 +
:[http://www.sukhoi.ru/forum/attachment.php?attachmentid=142291&d=1317991544 Samples.zip]
 +
  
 
Как мы узнали из предыдущего урока загруженные из под-миссий объекты игнорируются триггерами миссии-хоста (триггеры основной миссии не знают о под-миссиях и их объектах). Этого можно избежать используя триггеры в самих под-миссиях.  
 
Как мы узнали из предыдущего урока загруженные из под-миссий объекты игнорируются триггерами миссии-хоста (триггеры основной миссии не знают о под-миссиях и их объектах). Этого можно избежать используя триггеры в самих под-миссиях.  
Строка 15: Строка 19:
  
 
Используйте разные имена триггеров, чтобы избежать ошибок в дальнейшем.
 
Используйте разные имена триггеров, чтобы избежать ошибок в дальнейшем.
Also you can '''gpGetTrigger("Triggername")''' mitübergeben no mission number.  
+
Вы можете обращаться к триггеру без указания номера миссии при помощи '''gpGetTrigger("Triggername")'''.  
  
Теперь у нас есть три под-миссии, в каждой из которых стоит триггер на уничтожение создаваемых этой под-миссией объектов.
+
Теперь у нас есть три под-миссии, в каждой из которых стоит триггер на уничтожение создаваемых этой под-миссией объектов. Далее объединим эти триггеры в одно условие, чтобы иметь возможность оценить результаты атаки. Можно задать несколько условий используя логические И/ИЛИ, однако мы сделаем более удобный вариант. За успешную атаку будет засчитывать очки и по их количеству потом подводится общий итог.
An alternative is here simply the number of triggered win (or fail) to trigger count, and then simply compare it to a number which represents the number of necessary sub-goals.  
+
Пусть количество необходимых выполненных заданий будет равно 2, третью миссиию можно провалить. Также введем переменную, которая будет определять выполнили ли мы все задание (если 2 из 3-х - задание выполнено).
Also still would be a useful variable to specify whether the mission has been successful or has been lost. This variable could then query later, for example if you want the mission will be considered only after a successful landing.  
+
  
So we come to the code:
 
  
 
  using System;  
 
  using System;  
Строка 85: Строка 87:
  
  
'''enum MissionCondition {Neutral, Success, Failure}''' enum enumerated type identifies a missionary here named condition, in the curly brackets are the states can assume the mission condition. Here stands for Neutral mission is still in the balance, the mission is successful for Success and Failure, of course, is for mission failed. Behind the brace is not a semicolon.  
+
'''enum MissionCondition {Neutral, Success, Failure} ''' -перечисление состояний статуса выполнения миссии (''Нейтрально, Успех, Провал''). Точка с запятой в конце не ставится.
  
'''MissionCondition AktuelleMissionCondition = MissionCondition.Neutral;''' Initializes a condition variable current mission by mission-type condition with the value neutral.
+
'''MissionCondition AktuelleMissionCondition = MissionCondition.Neutral;''' - инициализация переменной состояния текщей миссии со значением ''Нейтрально''.
const int NeededForMissionSuccess = 2; Contains the successful mission for the necessary trigger number in the example once set to 2, was also the number as a constant (const) is defined, it would change the variable later, you would get an error message.
+
WinConditionCounter int = 0; This is our "Trigger counter" it is increased when calling a "WinTriggers" by one. At the beginning of its value was set to 0.
+
The declarations are just made in the entire class mission valid, ie they can be addressed by each method and modified up to the constant.  
+
  
server private void message (string msg)
+
'''const int NeededForMissionSuccess = 2;''' - константа, в которой мы задаем кол-во успешно завершенных миссий, для выполнения задания по штурмовке.
{
+
GamePlay.gpLogServer (null, msg, new object [] {msg});
+
}
+
  
Here I have introduced something new. I have a method which strings programmed into the chat bar (or in the console or in the server log if enabled) as output.  
+
'''int WinConditionCounter = 0;''' - задаем начальное значение (ноль) счетчика успешно выполненных миссий. Увеличивается на единицу с каждым выполнением под-миссий.
You can simply use the method in which one example
+
message server ("example text");
+
fits in the program code.  
+
  
Simple example:
+
private void serverMessage (string msg)
 +
{
 +
    GamePlay.gpLogServer (null, msg, new object [] {msg});
 +
}
  
using System;
+
Ниже команда, которая позволяет выводить на экран сообщения сервера, в том числе и в лог сервера (если это разрашено):
using maddox.game;
+
using maddox.game.world;
+
  
 +
serverMessage ("Пример текста. Я сервер. Баню читеров и таранщиков");
  
public class Mission : maddox.game.AMission
+
Пример вывода на экран сообщения сервера:
{
+
private void serverMessage (string msg)
+
{
+
GamePlay.gpLogServer (null, msg, new object [] {msg});
+
}
+
  
public override void OnBattleStarted()  
+
Simple example:
{  
+
using System;
base.OnBattleStarted();  
+
using maddox.game;
 +
using maddox.game.world;
 +
public class Mission : maddox.game.AMission
 +
{
 +
private void serverMessage (string msg)
 +
{
 +
GamePlay.gpLogServer (null, msg, new object [] {msg});
 +
}
 +
public override void OnBattleStarted()  
 +
{  
 +
base.OnBattleStarted();  
 +
serverMessage("Этот текст выводится после начала миссии.");
 +
}
 +
}
  
serverMessage("Dieser Text wird zum Beginn der Mission ausgegeben");
 
}
 
}
 
  
 +
Вот как это выглядит:
  
 
[[Файл:Sfdp2-4.jpg|800px]]
 
[[Файл:Sfdp2-4.jpg|800px]]
  
message server has a transfer value is a string and passes it to the method of gpLogserver IGamePlay class.
+
Формат команды '''serverMessage(string msg)''', строка передается в метод gpLogserver класса IGamePlay '''(перевод неточен!)'''. Рассмотрим этот метод подробней:
GamePlay.gpLogServer (null, msg, new object [] {msg});
+
 
Let us take a closer look
+
'''void gpLogServer(maddox.game.Player[] to, string msg, object[] args)''' имеет три передаваемых параметра:
gpLogServer has three transfer parameters:
+
 
void gpLogServer (maddox.game.Player [] to, string format, object [] args)  
+
*'''maddox.game.Player[] to''' - массив игроков, которым отправляется сообщение. Если равно null - отправляется всем. 
and indeed, with the first parameter (maddox.game.Player [] to) specify the addressee of the message, which may consist of any player (zero) or even a particular player.  
+
*'''string msg''' - текстовое сообщение формата ''string''.  
The second parameter contains the message to be output as a string ("string").  
+
*'''object[] parms''' - с помощью этого параметра вы можете передавать в строку различные параметры. Они помещаются в строку в фигурные скобки '''{n}''' с указанием индекса массива ''n'': {0}, {1}, {2}.  
With the help of the third parameter you can even pass variables that are in the string {0}, {1} ... Can add {n}. Where {0}, the first variable, {1} the second, {n} the n-th variable (depending on number) refers. In the first example above, I use the following call (as a debugging aid in OnTrigger):  
+
''Пример 1:''
GamePlay.gpLogServer (null, "OnTrigger ({0} | {1} | {2}) has been thrown", new object [] {mission number, short name, active});  
+
GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2}) wurde ausgelost", new object [] {missionNumber, shortName, active});
The example is when the trigger from the WinCondition2 Submission 2 was released, following in the chat bar:  
+
''На экран выводится:''
 +
OnTrigger (2 | WinCondition2 | True) wurde ausgelöst
 +
 
 +
''Пример 2:''
 +
GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2}) wurde ausgelöst", new object [] {missionNumber, shortName, active});
 +
 
 +
 
 +
Ниже пример при срабатывании триггера WinCondition2 из второй подмиссии:
  
 
[[Файл:Sfdp2-5.jpg|800px]]
 
[[Файл:Sfdp2-5.jpg|800px]]
  
After this brief slide back to the topic:
 
  
Let's go to OnBattleStarted (), this remains to previous versions of the past in much the same lesson is issued only with the help of server-message a short explanatory text.
+
Теперь нам нужно после начала основной миссии отправить пилоту задание в виде сообщения сервера, для этого понадобиться поместить следующую команду в рассмотренный нами ранее метод '''OnBattleStarted()''':
server message ("\ nZerstören it at least three vehicles from two groups \ n \ n");
+
\ N is a control sequence and provides for a line break.
+
  
[[Файл:Sfdp2-6.jpg|800px]]
+
serverMessage ("\nZerstören sie jeweils mindestens 3 Fahrzeuge aus zwei Gruppen\n\n");
 +
,где символ \n является символом переноса строки. Мы его используем здесь, чтобы наше сообщение было более заметно в списке команд сервера:
  
 +
[[Файл:Sfdp2-6.jpg|800px]]
  
The biggest changes took place in OnTrigger.
+
Наиболее значительные изменения произошли в методе '''OnTrigger''':
  
public override void OnTrigger(int missionNumber, string shortName, bool active)  
+
public override void OnTrigger(int missionNumber, string shortName, bool active)  
{
+
{
     base.OnTrigger(missionNumber, shortName, active);  
+
     base.OnTrigger(missionNumber, shortName, active);        
         
+
     GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2})  wurde ausgelöst", new object [] {missionNumber, shortName, active}); //Nur für Testzwecke, löschen oder auskommentieren wenn Endfassung  
     GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2})  wurde ausgelöst", new object [] {missionNumber, shortName, active}); //Nur für Testzwecke, löschen oder auskommentieren wenn Endfassung
+
   
+
 
     if (AktuelleMissionCondition == MissionCondition.Neutral)
 
     if (AktuelleMissionCondition == MissionCondition.Neutral)
 
     {
 
     {
Строка 174: Строка 179:
 
             GamePlay.gpGetTrigger(shortName).Enable = false;
 
             GamePlay.gpGetTrigger(shortName).Enable = false;
 
           }
 
           }
 
+
           serverMessage ("Anzahl erledigter Teilziele: " + WinConditionCounter.ToString()); // Für Testzwecke.            
           serverMessage ("Anzahl erledigter Teilziele: " + WinConditionCounter.ToString()); // Für Testzwecke.
+
             
+
 
         if (WinConditionCounter >= NeededForMissionSuccess)
 
         if (WinConditionCounter >= NeededForMissionSuccess)
 
         {
 
         {
Строка 184: Строка 187:
 
             GamePlay.gpGetTrigger("FailCondition1").Enable = false;
 
             GamePlay.gpGetTrigger("FailCondition1").Enable = false;
 
           }
 
           }
 
 
           if ("FailCondition1".Equals(shortName) && active)  
 
           if ("FailCondition1".Equals(shortName) && active)  
 
         {  
 
         {  
Строка 193: Строка 195:
 
           }
 
           }
 
     }
 
     }
}  
+
}  
  
if (condition == current mission MissionCondition.Neutral) If it were our main query, as long as the mission has not decided yet, can the contents of the query are executed, the mission was successful or unsuccessful, all other trigger events are ignored. If you want to continue to count the events yet, as if the mission had been successful, one can extend the if statement also if ((condition == current mission MissionCondition.Neutral) | | (condition == MissionCondition.Success current mission)) that | is for | OR.  
+
'''if (AktuelleMissionCondition == MissionCondition.Neutral)''' - условие, проверяющее статус миссии после вызова триггера. Если "Нейтрально", то выполняется следующий за ним код.
 +
''Примечание:''
 +
== - в условии означает "равно"
 +
|| - "или"
 +
&& - "и"
 +
 +
''Вы можете использовать их для создания нужных вам условий.''
  
if ("WinCondition1." Equals (shortname) & & active)  
+
if ("WinCondition1".Equals(shortName) && active)  
{  
+
{  
WinConditionCounter + +;  
+
    WinConditionCounter++;  
GamePlay.gpGetTrigger (ShortName) Enable = false.;  
+
    GamePlay.gpGetTrigger(shortName).Enable = false;  
}  
+
}
  
The if-statements for the WinCondition Triggers have been adjusted, and that is registered in the trigger is invoked by WinConditionCounter is increased by one (this is + + so to speak, the abbreviation of WinConditionCounter WinConditionCounter = + 1). This is repeated for all of our WinTrigger.  
+
'''WinConditionCounter++;''' - упрощение формулы, означает прибавить к переменной '''WinConditionCounter''' единицу, тоесть мы получили счетчик при помощи которого будем определять сколько успешных атак провел пилот. Можно записать по другому, на результат это не повлияет, только сделает код более громоздким:
  
To save on copying and pasting the if statement and not repeat it at every trigger newcomers need to, we can exploit the WinCondition - triggers were simply numbered. And with
+
if ("WinCondition1".Equals(shortName) && active)
 +
{
 +
    WinConditionCounter = WinConditionCounter + 1;
 +
    GamePlay.gpGetTrigger(shortName).Enable = false;
 +
}
  
if (shortName.Substring (0, 12). Equals ("WinCondition") & & active)
+
Чтобы не копировать постоянно названия и не прописывать имена триггеров в скрипте миссии-хоста при добавлении новых ("WinCondition1", "WinCondition2", "WinCondition3" ... "WinCondition'''''n'''''"), мы можем использовать такой код:
{
+
WinConditionCounter + +;
+
GamePlay.gpGetTrigger (ShortName) Enable = false.;
+
}
+
  
shortName.Substring (0, 12). Equals ("WinCondition"). Substring (0, 12) ensures that only the first 12 letters of the trigger name to be observed (Actually, had also passed the first three so shortName.Substring (0, 3 )), thus making the inside of each instruction executed when the trigger is the beginning WinCondition.  
+
if (shortName.Substring(0, 12).Equals("WinCondition") && active)
 +
{
 +
    WinConditionCounter++;
 +
    GamePlay.gpGetTrigger(shortName).Enable = false; 
 +
}
  
server message ("Number of completed sub-goals:" + WinConditionCounter.ToString ()) / / For testing purposes only.  
+
'''shortName.Substring(0, 12).Equals("WinCondition")'''. позволяет учитывать только первые 12 символов названия триггеров. Т.е. мы можем добавлять сколь угодно подмиссий с именами типа "WinCondition'''''n'''''" и не портить при этом код главного скрипта.
serves as a control output for debugging purposes, I have deliberately chosen this form, I would be able to write
+
GamePlay.gpLogServer (null, "number of completed sub-goals: {0}", new object [] {} WinConditionCounter);
+
As already mentioned, you can spend with server message ("...") a string. WinConditionCounter but is to be of type int (integer) and must therefore first in a string (String) converted, plus there is the ToString () method that will do this for us.  
+
  
Continue with
+
'''serverMessage ("Количество выполненных заданий: " + WinConditionCounter.ToString()); // Für Testzwecke.''' - служит для отладки скрипта, можно записать и так (чтобы сообщения отправлялись в лог сервера:
  
if (WinConditionCounter> = NeededForMissionSuccess)
+
'''GamePlay.gpLogServer (null, "Количество выполненных заданий: {0}", new object [] {WinConditionCounter});'''
{
+
current mission condition = MissionCondition.Success;
+
GamePlay.gpHUDLogCenter ("goal reached");
+
server message ("final number:" + WinConditionCounter.ToString ()) / / For testing purposes only.
+
GamePlay.gpGetTrigger ("FailCondition1") enable = false.;  
+
}
+
  
This if statement to ask whether WinConditionCounter NeededForMissionSuccess already greater than or equal (that is to win the necessary number of sub-goals) is. If this is the case, the condition variable current mission is set to Success (mission is won) and the message "destination reached" is displayed on the screen. Also, the trigger "FailCondition1" disabled.
+
Так как '''serverMessage ("...")''' является строкой типа '''string''', а '''WinConditionCounter''' целое число типа '''int''' мы должны преобразовать '''WinConditionCounter''' в тип '''string'''. Для этого воспользуемся методом '''ToString()''', который для этого предназначен:
  
if ("FailCondition1." Equals (shortname) & & active)  
+
if (WinConditionCounter >= NeededForMissionSuccess)
{  
+
{
current mission condition = MissionCondition.Failure;  
+
    AktuelleMissionCondition = MissionCondition.Success;
GamePlay.gpHUDLogCenter ("You have exceeded the time");  
+
    GamePlay.gpHUDLogCenter("Вы выполнили задание и уничтожили все цели");
server message ("final number:" + WinConditionCounter.ToString ()) / / For testing purposes only.
+
    serverMessage ("Счет: " + WinConditionCounter.ToString()); // для отладки скрипта
GamePlay.gpGetTrigger (ShortName) Enable = false.;  
+
    GamePlay.gpGetTrigger("FailCondition1").Enable = false;
}  
+
}
  
This query asks if released from the trigger was FailCondition1 & & this is activated.
+
Если счетчик '''WinConditionCounter''' имеет значение равно или больше необходимого кол-ва успешно выполненных заданий, которое задается переменной "NeededForMissionSuccess" статус миссии меняется на "Выполнено" и на экран выводится итоговый счет. Также отключается триггер '''FailCondition1'''/
If the expression is true, the if statement, the message "You have exceeded the time", the variable current mission set to failure condition (the mission is lost. And as so often is also the trigger FailCondition1 disabled.
+
  
 +
if ("FailCondition1." Equals (shortname) & & active)
 +
{
 +
current mission condition = MissionCondition.Failure;
 +
GamePlay.gpHUDLogCenter ("Вы не уложились в норматив, задание не выполнено");
 +
server message ("final number:" + WinConditionCounter.ToString ()) // для отладки скрипта
 +
GamePlay.gpGetTrigger (ShortName) Enable = false.;
 +
}
  
At the conclusion of the entire code again without the test messages and "shortName.Substring (0, 12). Equals (" WinCondition ")"  
+
Если вы не уложились в заданное время, появляется сообщение о неудаче и статус миссии меняет на "Провал".
  
As mission designers need to actually specify only the number of events needed for victory with NeededForMissionSuccess, replace the paths and file names of the missions to be loaded and, if the on-screen messages (or control messages) with your own.  
+
Как создателю миссий, чтобы использовать этот скрипт вам нужно проставить свои пути к файлам, кол-во заданий, которые нужно выполнить для успеха, текстовые сообщения и время выполнения задания.
  
 +
Итоговый код:
  
using System;  
+
using System;
using maddox.game;  
+
using maddox.game;
using maddox.game.world;  
+
using maddox.game.world;
 
+
public class Mission : maddox.game.AMission
public class Mission : maddox.game.AMission  
+
{
{  
+
    enum MissionCondition {Neutral, Success, Failure}
enum MissionCondition {Neutral, Success, Failure}
+
    MissionCondition AktuelleMissionCondition = MissionCondition.Neutral;
 
+
    const int NeededForMissionSuccess = 2;
MissionCondition AktuelleMissionCondition = MissionCondition.Neutral;  
+
    int WinConditionCounter = 0;
const int NeededForMissionSuccess = 2;  
+
    private void serverMessage (string msg)
int WinConditionCounter = 0;  
+
    {
 
+
        GamePlay.gpLogServer (null, msg, new object [] {msg});
 
+
    }
private void serverMessage (string msg)  
+
    public override void OnBattleStarted()
{  
+
    {
GamePlay.gpLogServer (null, msg, new object [] {msg});  
+
        base.OnBattleStarted();
}  
+
        MissionNumberListener = -1;
 
+
        serverMessage ("\nZerstören sie jeweils mindestens 3 Fahrzeuge aus zwei Gruppen\n\n");
public override void OnBattleStarted()  
+
        GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub1.mis");
{  
+
        GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub2.mis");
base.OnBattleStarted();  
+
        GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub3.mis");
MissionNumberListener = -1;  
+
    }
 
+
    public override void OnTrigger(int missionNumber, string shortName, bool active)
serverMessage ("\nZerstören sie jeweils mindestens 3 Fahrzeuge aus zwei Gruppen\n\n");  
+
            {
 
+
    base.OnTrigger(missionNumber, shortName, active);    
GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub1.mis");  
+
    if (AktuelleMissionCondition == MissionCondition.Neutral)
GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub2.mis");  
+
    {
GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub3.mis");  
+
        if (shortName.Substring(0, 12).Equals("WinCondition") && active)  
}
+
            {  
 
+
                WinConditionCounter++;  
public override void OnTrigger(int missionNumber, string shortName, bool active)  
+
                GamePlay.gpGetTrigger(shortName).Enable = false;
{  
+
                }      
base.OnTrigger(missionNumber, shortName, active);  
+
        if (WinConditionCounter >= NeededForMissionSuccess)
+
        {
if (AktuelleMissionCondition == MissionCondition.Neutral)  
+
            AktuelleMissionCondition = MissionCondition.Success;
{  
+
            GamePlay.gpHUDLogCenter("Ziel erreicht");
if (shortName.Substring(0, 12).Equals("WinCondition") && active)  
+
            GamePlay.gpGetTrigger("FailCondition1").Enable = false;
{  
+
        }
WinConditionCounter++;  
+
                    if ("FailCondition1".Equals(shortName) && active)
GamePlay.gpGetTrigger(shortName).Enable = false;  
+
                    {  
}  
+
            AktuelleMissionCondition = MissionCondition.Failure;
+
            GamePlay.gpHUDLogCenter("Sie haben die Zeit überschritten");
if (WinConditionCounter >= NeededForMissionSuccess)  
+
            GamePlay.gpGetTrigger(shortName).Enable = false;
{  
+
                    }
AktuelleMissionCondition = MissionCondition.Success;  
+
                  }
GamePlay.gpHUDLogCenter("Ziel erreicht");  
+
              }
GamePlay.gpGetTrigger("FailCondition1").Enable = false;  
+
}  
}  
+
 
+
if ("FailCondition1".Equals(shortName) && active)  
+
{  
+
AktuelleMissionCondition = MissionCondition.Failure;  
+
GamePlay.gpHUDLogCenter("Sie haben die Zeit überschritten");
+
GamePlay.gpGetTrigger(shortName).Enable = false;
+
}  
+
}  
+
}  
+
}  
+
 
+
Again, I am as always grateful for criticism and suggestions.
+
 
+
Attachment as the training mission, MissionNachladen3.cs contains the first version at the top and bottom of the adjusted MissionNachladen4.cs.
+
 
+
The sample directory to ... \ Documents \ 1C club Soft \ IL-2 Sturmovik cliffs of dover \ missions \ single copy or adapt the paths to the submissions manually.
+
  
  
 +
: ''Для установки миссий-примеров скопируйте их в папку:
 +
..\Documents\1C SoftClub\il-2 sturmovik cliffs of dover\missions\Single
  
 +
----
 +
=== Загрузка подмиссий (автор FG28_Kodiak) ===
 +
Оригинальные темы см. на форуме [http://translate.google.com/translate?hl=en&sl=de&tl=en&u=http%3A%2F%2Fforum.sturmovik.de%2Findex.php%2Fboard%2C17.0.html sturmovik.de](перевод от Google):
  
 +
*[[Ил-2 Штурмовик: Битва за Британию. Скрипты. Скрипты для чайников. Часть 1 - Загрузка подмиссий|Часть 1 - Загрузка подмиссий]]
 +
*[[Ил-2 Штурмовик: Битва за Британию. Скрипты. Скрипты для чайников. Часть 3 - Загрузка подмиссий|Часть 3 - Загрузка подмиссий]]
 +
*[[Ил-2 Штурмовик: Битва за Британию. Скрипты. Скрипты для чайников. Часть 4 - Загрузка подмиссий|Часть 4 - Загрузка подмиссий]]
  
 +
[[Ил-2 Штурмовик: Битва за Британию. Скрипты|Вернуться на страницу "Скрипты"]]
  
 
[[Категория:Ил-2 Штурмовик: Битва за Британию. Скрипты]]
 
[[Категория:Ил-2 Штурмовик: Битва за Британию. Скрипты]]

Текущая версия на 18:28, 6 ноября 2011

Автор: FG28_Kodiak
Ссылка: Перейти (перевод Google)

Скачать оригиналы миссий:

Samples.zip

Скачать примеры с Sukhoi.ru:

Samples.zip


Как мы узнали из предыдущего урока загруженные из под-миссий объекты игнорируются триггерами миссии-хоста (триггеры основной миссии не знают о под-миссиях и их объектах). Этого можно избежать используя триггеры в самих под-миссиях. Создадим по одному триггеру в каждой из наших трех под-миссий:

Sfdp2-1.jpg


Sfdp2-2.jpg


Sfdp2-3.jpg

Используйте разные имена триггеров, чтобы избежать ошибок в дальнейшем. Вы можете обращаться к триггеру без указания номера миссии при помощи gpGetTrigger("Triggername").

Теперь у нас есть три под-миссии, в каждой из которых стоит триггер на уничтожение создаваемых этой под-миссией объектов. Далее объединим эти триггеры в одно условие, чтобы иметь возможность оценить результаты атаки. Можно задать несколько условий используя логические И/ИЛИ, однако мы сделаем более удобный вариант. За успешную атаку будет засчитывать очки и по их количеству потом подводится общий итог. Пусть количество необходимых выполненных заданий будет равно 2, третью миссиию можно провалить. Также введем переменную, которая будет определять выполнили ли мы все задание (если 2 из 3-х - задание выполнено).


using System; 
using maddox.game; 
using maddox.game.world; 
public class Mission : maddox.game.AMission 
{ 
enum MissionCondition {Neutral, Success, Failure}
MissionCondition AktuelleMissionCondition = MissionCondition.Neutral; 
const int NeededForMissionSuccess = 2; 
int WinConditionCounter = 0;
private void serverMessage (string msg) 
{ 
GamePlay.gpLogServer (null, msg, new object [] {msg}); 
}
public override void OnBattleStarted() 
{ 
base.OnBattleStarted(); 
MissionNumberListener = -1; 
serverMessage ("\nZerstören sie jeweils mindestens 3 Fahrzeuge aus zwei Gruppen\n\n");
GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub1.mis"); 
GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub2.mis"); 
GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub3.mis"); 
}
public override void OnTrigger(int missionNumber, string shortName, bool active) 	 	 { 
base.OnTrigger(missionNumber, shortName, active); 	 	 
GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2}) wurde ausgelöst", new object [] {missionNumber, shortName, active}); //Nur für Testzwecke, löschen oder auskommentieren wenn Endfassung 	 	 
if (AktuelleMissionCondition == MissionCondition.Neutral) 
{ 
if ("WinCondition1".Equals(shortName) && active) 
{ 
WinConditionCounter++; 
GamePlay.gpGetTrigger(shortName).Enable = false; 
} 
if ("WinCondition2".Equals(shortName) && active) 
{ 
WinConditionCounter++; 
GamePlay.gpGetTrigger(shortName).Enable = false; 
} 
if ("WinCondition3".Equals(shortName) && active) 
{ 
WinConditionCounter++; 
GamePlay.gpGetTrigger(shortName).Enable = false; 
} 
serverMessage ("Anzahl erledigter Teilziele: " + WinConditionCounter.ToString()); // Für Testzwecke. 	 
if (WinConditionCounter >= NeededForMissionSuccess) 
{ 
AktuelleMissionCondition = MissionCondition.Success; 
GamePlay.gpHUDLogCenter("Ziel erreicht"); 
serverMessage ("Endanzahl: " + WinConditionCounter.ToString()); // Für Testzwecke. 
GamePlay.gpGetTrigger("FailCondition1").Enable = false; 
} 
if ("FailCondition1".Equals(shortName) && active) 
{ 
AktuelleMissionCondition = MissionCondition.Failure; 
GamePlay.gpHUDLogCenter("Sie haben die Zeit überschritten"); 	 	 
serverMessage ("Endanzahl: " + WinConditionCounter.ToString()); // Für Testzwecke. 	 
GamePlay.gpGetTrigger(shortName).Enable = false; 	 
} 
} 
} 
} 


enum MissionCondition {Neutral, Success, Failure} -перечисление состояний статуса выполнения миссии (Нейтрально, Успех, Провал). Точка с запятой в конце не ставится.

MissionCondition AktuelleMissionCondition = MissionCondition.Neutral; - инициализация переменной состояния текщей миссии со значением Нейтрально.

const int NeededForMissionSuccess = 2; - константа, в которой мы задаем кол-во успешно завершенных миссий, для выполнения задания по штурмовке.

int WinConditionCounter = 0; - задаем начальное значение (ноль) счетчика успешно выполненных миссий. Увеличивается на единицу с каждым выполнением под-миссий.

private void serverMessage (string msg)
{
   GamePlay.gpLogServer (null, msg, new object [] {msg});
}

Ниже команда, которая позволяет выводить на экран сообщения сервера, в том числе и в лог сервера (если это разрашено):

serverMessage ("Пример текста. Я сервер. Баню читеров и таранщиков"); 

Пример вывода на экран сообщения сервера:

Simple example: 
using System; 
using maddox.game; 
using maddox.game.world;
public class Mission : maddox.game.AMission 
{ 
private void serverMessage (string msg) 
{ 
GamePlay.gpLogServer (null, msg, new object [] {msg}); 
}
public override void OnBattleStarted() 
{ 
base.OnBattleStarted(); 
serverMessage("Этот текст выводится после начала миссии."); 
} 
} 


Вот как это выглядит:

Sfdp2-4.jpg

Формат команды serverMessage(string msg), строка передается в метод gpLogserver класса IGamePlay (перевод неточен!). Рассмотрим этот метод подробней:

void gpLogServer(maddox.game.Player[] to, string msg, object[] args) имеет три передаваемых параметра:

  • maddox.game.Player[] to - массив игроков, которым отправляется сообщение. Если равно null - отправляется всем.
  • string msg - текстовое сообщение формата string.
  • object[] parms - с помощью этого параметра вы можете передавать в строку различные параметры. Они помещаются в строку в фигурные скобки {n} с указанием индекса массива n: {0}, {1}, {2}.

Пример 1:

GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2})  wurde ausgelost", new object [] {missionNumber, shortName, active});

На экран выводится:

OnTrigger (2 | WinCondition2 | True) wurde ausgelöst

Пример 2:

GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2})  wurde ausgelöst", new object [] {missionNumber, shortName, active});


Ниже пример при срабатывании триггера WinCondition2 из второй подмиссии:

Sfdp2-5.jpg


Теперь нам нужно после начала основной миссии отправить пилоту задание в виде сообщения сервера, для этого понадобиться поместить следующую команду в рассмотренный нами ранее метод OnBattleStarted():

serverMessage ("\nZerstören sie jeweils mindestens 3 Fahrzeuge aus zwei Gruppen\n\n");

,где символ \n является символом переноса строки. Мы его используем здесь, чтобы наше сообщение было более заметно в списке команд сервера:

Sfdp2-6.jpg

Наиболее значительные изменения произошли в методе OnTrigger:

public override void OnTrigger(int missionNumber, string shortName, bool active) 
{
   base.OnTrigger(missionNumber, shortName, active);          
   GamePlay.gpLogServer (null, "OnTrigger({0} | {1} | {2})  wurde ausgelöst", new object []  {missionNumber, shortName, active}); //Nur für Testzwecke, löschen oder auskommentieren wenn Endfassung    
   if (AktuelleMissionCondition == MissionCondition.Neutral)
   {
       if ("WinCondition1".Equals(shortName) && active) 
       { 
           WinConditionCounter++; 
           GamePlay.gpGetTrigger(shortName).Enable = false; 
         }
         if ("WinCondition2".Equals(shortName) && active) 
       { 
           WinConditionCounter++;
           GamePlay.gpGetTrigger(shortName).Enable = false;
         }
         if ("WinCondition3".Equals(shortName) && active) 
       { 
           WinConditionCounter++;
           GamePlay.gpGetTrigger(shortName).Enable = false;
         }
         serverMessage ("Anzahl erledigter Teilziele: " + WinConditionCounter.ToString()); // Für Testzwecke.              
       if (WinConditionCounter >= NeededForMissionSuccess)
       {
           AktuelleMissionCondition = MissionCondition.Success;
           GamePlay.gpHUDLogCenter("Ziel erreicht");
           serverMessage ("Endanzahl: " + WinConditionCounter.ToString()); // Für Testzwecke.
           GamePlay.gpGetTrigger("FailCondition1").Enable = false;
         }
         if ("FailCondition1".Equals(shortName) && active) 
       { 
           AktuelleMissionCondition = MissionCondition.Failure;
           GamePlay.gpHUDLogCenter("Sie haben die Zeit überschritten");      
           serverMessage ("Endanzahl: " + WinConditionCounter.ToString()); // Für Testzwecke.   
           GamePlay.gpGetTrigger(shortName).Enable = false;   
         }
   }
} 

if (AktuelleMissionCondition == MissionCondition.Neutral) - условие, проверяющее статус миссии после вызова триггера. Если "Нейтрально", то выполняется следующий за ним код.

Примечание:
== - в условии означает "равно"
|| - "или"
&& - "и"

Вы можете использовать их для создания нужных вам условий.
if ("WinCondition1".Equals(shortName) && active) 
{ 
   WinConditionCounter++; 
   GamePlay.gpGetTrigger(shortName).Enable = false; 
}

WinConditionCounter++; - упрощение формулы, означает прибавить к переменной WinConditionCounter единицу, тоесть мы получили счетчик при помощи которого будем определять сколько успешных атак провел пилот. Можно записать по другому, на результат это не повлияет, только сделает код более громоздким:

if ("WinCondition1".Equals(shortName) && active) 
{ 
   WinConditionCounter = WinConditionCounter + 1; 
   GamePlay.gpGetTrigger(shortName).Enable = false; 
}

Чтобы не копировать постоянно названия и не прописывать имена триггеров в скрипте миссии-хоста при добавлении новых ("WinCondition1", "WinCondition2", "WinCondition3" ... "WinConditionn"), мы можем использовать такой код:

if (shortName.Substring(0, 12).Equals("WinCondition") && active)
{
   WinConditionCounter++;
   GamePlay.gpGetTrigger(shortName).Enable = false;   
}

shortName.Substring(0, 12).Equals("WinCondition"). позволяет учитывать только первые 12 символов названия триггеров. Т.е. мы можем добавлять сколь угодно подмиссий с именами типа "WinConditionn" и не портить при этом код главного скрипта.

serverMessage ("Количество выполненных заданий: " + WinConditionCounter.ToString()); // Für Testzwecke. - служит для отладки скрипта, можно записать и так (чтобы сообщения отправлялись в лог сервера:

GamePlay.gpLogServer (null, "Количество выполненных заданий: {0}", new object [] {WinConditionCounter});

Так как serverMessage ("...") является строкой типа string, а WinConditionCounter целое число типа int мы должны преобразовать WinConditionCounter в тип string. Для этого воспользуемся методом ToString(), который для этого предназначен:

if (WinConditionCounter >= NeededForMissionSuccess)
{
   AktuelleMissionCondition = MissionCondition.Success;
   GamePlay.gpHUDLogCenter("Вы выполнили задание и уничтожили все цели");
   serverMessage ("Счет: " + WinConditionCounter.ToString()); // для отладки скрипта
   GamePlay.gpGetTrigger("FailCondition1").Enable = false;
}

Если счетчик WinConditionCounter имеет значение равно или больше необходимого кол-ва успешно выполненных заданий, которое задается переменной "NeededForMissionSuccess" статус миссии меняется на "Выполнено" и на экран выводится итоговый счет. Также отключается триггер FailCondition1/

if ("FailCondition1." Equals (shortname) & & active) 
{ 
current mission condition = MissionCondition.Failure; 
GamePlay.gpHUDLogCenter ("Вы не уложились в норматив, задание не выполнено"); 
server message ("final number:" + WinConditionCounter.ToString ()) // для отладки скрипта 
GamePlay.gpGetTrigger (ShortName) Enable = false.; 
} 

Если вы не уложились в заданное время, появляется сообщение о неудаче и статус миссии меняет на "Провал".

Как создателю миссий, чтобы использовать этот скрипт вам нужно проставить свои пути к файлам, кол-во заданий, которые нужно выполнить для успеха, текстовые сообщения и время выполнения задания.

Итоговый код:

using System;
using maddox.game;
using maddox.game.world;
public class Mission : maddox.game.AMission
{
   enum MissionCondition {Neutral, Success, Failure}
   MissionCondition AktuelleMissionCondition = MissionCondition.Neutral;
   const int NeededForMissionSuccess = 2;
   int WinConditionCounter = 0;
   private void serverMessage (string msg)
   {
       GamePlay.gpLogServer (null, msg, new object [] {msg});
   }
   public override void OnBattleStarted()
   {
       base.OnBattleStarted();
       MissionNumberListener = -1;
       serverMessage ("\nZerstören sie jeweils mindestens 3 Fahrzeuge aus zwei Gruppen\n\n");
       GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub1.mis");
       GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub2.mis");
       GamePlay.gpPostMissionLoad("missions\\Single\\Samples\\TestSubmissions\\MissionNachladen3Sub3.mis");
   }
   public override void OnTrigger(int missionNumber, string shortName, bool active)
           {
   		base.OnTrigger(missionNumber, shortName, active);     		
   		if (AktuelleMissionCondition == MissionCondition.Neutral)
   		{
   		    if (shortName.Substring(0, 12).Equals("WinCondition") && active) 
           { 
               WinConditionCounter++; 
               GamePlay.gpGetTrigger(shortName).Enable = false;
               }    		    
   		    if (WinConditionCounter >= NeededForMissionSuccess)
   		    {
   		        AktuelleMissionCondition = MissionCondition.Success;
   		        GamePlay.gpHUDLogCenter("Ziel erreicht");
   		        GamePlay.gpGetTrigger("FailCondition1").Enable = false;
   		    }
                   if ("FailCondition1".Equals(shortName) && active)
                   { 
       		    AktuelleMissionCondition = MissionCondition.Failure;
       		    GamePlay.gpHUDLogCenter("Sie haben die Zeit überschritten");		
       		    GamePlay.gpGetTrigger(shortName).Enable = false;
                   }
                  }
              }
}   


Для установки миссий-примеров скопируйте их в папку:
..\Documents\1C SoftClub\il-2 sturmovik cliffs of dover\missions\Single

Загрузка подмиссий (автор FG28_Kodiak)

Оригинальные темы см. на форуме sturmovik.de(перевод от Google):

Вернуться на страницу "Скрипты"