Приветствую. Перейду сразу к вопросу. При начале игровой сессии и до всплытия сообщения на экране "New wave inbound" отсчитывается таймер и начинается непосредственно сама волна. Необходимо увеличить это стартовое время в варьируемых пределах для закупки. Итого: игровая сессия началась, отсчитывается таймер торговца (например, минута), торговец закрывается и начинается 1-ая волна. Возможно, у кого-то уже есть подобный мутатор или способ, как реализовать.
Настройки: Спойлер Код: [TraderTimeChangerMut.SRGameType] BeginningTime=180 BeginningTime - Стартовое время. Код: Спойлер Код: class TraderTimeChangerMut extends Mutator; function PostBeginPlay() { if(SRGameType(Level.Game)==None) Level.ServerTravel("?game=TraderTimeChangerMut.SRGameType", true); } defaultproperties { bAddToServerPackages=True GroupName="KF-TraderTimeChanger" FriendlyName="TraderTimeChangerMut" Description="Changes the trading time" } Код: class SRGameType extends KFGameType config(TraderTimeChangerMut); var config int BeginningTime; function PostBeginPlay() { SaveConfig(); Super.PostBeginPlay(); } State MatchInProgress { function BeginState() { Super.BeginState(); WaveNum = InitialWave; InvasionGameReplicationInfo(GameReplicationInfo).WaveNumber = WaveNum; WaveCountDown = BeginningTime; // Essence. Увеличиваем стартовое время. SetupPickups(); } function Timer() { local Controller C; local bool bOneMessage; local Bot B; Global.Timer(); if ( Level.TimeSeconds > HintTime_1 && bTradingDoorsOpen && bShowHint_2 ) { for ( C = Level.ControllerList; C != None; C = C.NextController ) { if( C.Pawn != none && C.Pawn.Health > 0 ) { KFPlayerController(C).CheckForHint(32); HintTime_2 = Level.TimeSeconds + 11; } } bShowHint_2 = false; } if ( Level.TimeSeconds > HintTime_2 && bTradingDoorsOpen && bShowHint_3 ) { for ( C = Level.ControllerList; C != None; C = C.NextController ) { if( C.Pawn != None && C.Pawn.Health > 0 ) { KFPlayerController(C).CheckForHint(33); } } bShowHint_3 = false; } if ( !bFinalStartup ) { bFinalStartup = true; PlayStartupMessage(); } if ( NeedPlayers() && AddBot() && (RemainingBots > 0) ) RemainingBots--; ElapsedTime++; GameReplicationInfo.ElapsedTime = ElapsedTime; if( !UpdateMonsterCount() ) { EndGame(None,"TimeLimit"); Return; } if( bUpdateViewTargs ) UpdateViews(); if (!bNoBots && !bBotsAdded) { if(KFGameReplicationInfo(GameReplicationInfo) != none) if((NumPlayers + NumBots) < MaxPlayers && KFGameReplicationInfo(GameReplicationInfo).PendingBots > 0 ) { AddBots(1); KFGameReplicationInfo(GameReplicationInfo).PendingBots --; } if (KFGameReplicationInfo(GameReplicationInfo).PendingBots == 0) { bBotsAdded = true; return; } } if( bWaveBossInProgress ) { // Close Trader doors if( bTradingDoorsOpen ) { CloseShops(); TraderProblemLevel = 0; } if( TraderProblemLevel<4 ) { if( BootShopPlayers() ) TraderProblemLevel = 0; else TraderProblemLevel++; } if( !bHasSetViewYet && TotalMaxMonsters<=0 && NumMonsters>0 ) { bHasSetViewYet = True; for ( C = Level.ControllerList; C != None; C = C.NextController ) if ( C.Pawn!=None && KFMonster(C.Pawn)!=None && KFMonster(C.Pawn).MakeGrandEntry() ) { ViewingBoss = KFMonster(C.Pawn); Break; } if( ViewingBoss!=None ) { ViewingBoss.bAlwaysRelevant = True; for ( C = Level.ControllerList; C != None; C = C.NextController ) { if( PlayerController(C)!=None ) { PlayerController(C).SetViewTarget(ViewingBoss); PlayerController(C).ClientSetViewTarget(ViewingBoss); PlayerController(C).bBehindView = True; PlayerController(C).ClientSetBehindView(True); PlayerController(C).ClientSetMusic(BossBattleSong,MTRAN_FastFade); } if ( C.PlayerReplicationInfo!=None && bRespawnOnBoss ) { C.PlayerReplicationInfo.bOutOfLives = false; C.PlayerReplicationInfo.NumLives = 0; if ( (C.Pawn == None) && !C.PlayerReplicationInfo.bOnlySpectator && PlayerController(C)!=None ) C.GotoState('PlayerWaiting'); } } } } else if( ViewingBoss!=None && !ViewingBoss.bShotAnim ) { ViewingBoss = None; for ( C = Level.ControllerList; C != None; C = C.NextController ) if( PlayerController(C)!=None ) { if( C.Pawn==None && !C.PlayerReplicationInfo.bOnlySpectator && bRespawnOnBoss ) C.ServerReStartPlayer(); if( C.Pawn!=None ) { PlayerController(C).SetViewTarget(C.Pawn); PlayerController(C).ClientSetViewTarget(C.Pawn); } else { PlayerController(C).SetViewTarget(C); PlayerController(C).ClientSetViewTarget(C); } PlayerController(C).bBehindView = False; PlayerController(C).ClientSetBehindView(False); } } if( TotalMaxMonsters<=0 || (Level.TimeSeconds>WaveEndTime) ) { // if everyone's spawned and they're all dead if ( NumMonsters <= 0 ) DoWaveEnd(); } else AddBoss(); } else if(bWaveInProgress) { WaveTimeElapsed += 1.0; // Close Trader doors if (bTradingDoorsOpen) { CloseShops(); TraderProblemLevel = 0; } if( TraderProblemLevel<4 ) { if( BootShopPlayers() ) TraderProblemLevel = 0; else TraderProblemLevel++; } if(!MusicPlaying) StartGameMusic(True); if( TotalMaxMonsters<=0 ) { if ( NumMonsters <= 5 /*|| Level.TimeSeconds>WaveEndTime*/ ) { for ( C = Level.ControllerList; C != None; C = C.NextController ) if ( KFMonsterController(C)!=None && KFMonsterController(C).CanKillMeYet() ) { C.Pawn.KilledBy( C.Pawn ); Break; } } // if everyone's spawned and they're all dead if ( NumMonsters <= 0 ) { DoWaveEnd(); } } // all monsters spawned else if ( (Level.TimeSeconds > NextMonsterTime) && (NumMonsters+NextSpawnSquad.Length <= MaxMonsters) ) { WaveEndTime = Level.TimeSeconds+160; if( !bDisableZedSpawning ) { AddSquad(); // Comment this out to prevent zed spawning } if(nextSpawnSquad.length>0) { NextMonsterTime = Level.TimeSeconds + 0.2; } else { NextMonsterTime = Level.TimeSeconds + CalcNextSquadSpawnTime(); } } } else if ( NumMonsters <= 0 ) { if ( WaveNum == FinalWave && !bUseEndGameBoss ) { if( bDebugMoney ) { log("$$$$$$$$$$$$$$$$ Final TotalPossibleMatchMoney = "$TotalPossibleMatchMoney,'Debug'); } EndGame(None,"TimeLimit"); return; } else if( WaveNum == (FinalWave + 1) && bUseEndGameBoss ) { if( bDebugMoney ) { log("$$$$$$$$$$$$$$$$ Final TotalPossibleMatchMoney = "$TotalPossibleMatchMoney,'Debug'); } EndGame(None,"TimeLimit"); return; } WaveCountDown--; if ( !CalmMusicPlaying ) { InitMapWaveCfg(); StartGameMusic(False); } // Open Trader doors if ( !bTradingDoorsOpen ) // Essence. Открываем магазины в начальное время. { OpenShops(); } // Select a shop if one isn't open if ( KFGameReplicationInfo(GameReplicationInfo).CurrentShop == none ) { SelectShop(); } KFGameReplicationInfo(GameReplicationInfo).TimeToNextWave = WaveCountDown; if ( WaveCountDown == 30 ) { for ( C = Level.ControllerList; C != None; C = C.NextController ) { if ( KFPlayerController(C) != None ) { // Have Trader tell players that they've got 30 seconds KFPlayerController(C).ClientLocationalVoiceMessage(C.PlayerReplicationInfo, none, 'TRADER', 4); } } } else if ( WaveCountDown == 10 ) { for ( C = Level.ControllerList; C != None; C = C.NextController ) { if ( KFPlayerController(C) != None ) { // Have Trader tell players that they've got 10 seconds KFPlayerController(C).ClientLocationalVoiceMessage(C.PlayerReplicationInfo, none, 'TRADER', 5); } } } else if ( WaveCountDown == 5 ) { KFGameReplicationInfo(Level.Game.GameReplicationInfo).MaxMonstersOn=false; InvasionGameReplicationInfo(GameReplicationInfo).WaveNumber = WaveNum; } else if ( (WaveCountDown > 0) && (WaveCountDown < 5) ) { if( WaveNum == FinalWave && bUseEndGameBoss ) { BroadcastLocalizedMessage(class'KFMod.WaitingMessage', 3); } else { BroadcastLocalizedMessage(class'KFMod.WaitingMessage', 1); } } else if ( WaveCountDown <= 1 ) { bWaveInProgress = true; KFGameReplicationInfo(GameReplicationInfo).bWaveInProgress = true; // Randomize the ammo pickups again if( WaveNum > 0 ) { SetupPickups(); } if( WaveNum == FinalWave && bUseEndGameBoss ) { StartWaveBoss(); } else { SetupWave(); for ( C = Level.ControllerList; C != none; C = C.NextController ) { if ( PlayerController(C) != none ) { PlayerController(C).LastPlaySpeech = 0; if ( KFPlayerController(C) != none ) { KFPlayerController(C).bHasHeardTraderWelcomeMessage = false; } } if ( Bot(C) != none ) { B = Bot(C); InvasionBot(B).bDamagedMessage = false; B.bInitLifeMessage = false; if ( !bOneMessage && (FRand() < 0.65) ) { bOneMessage = true; if ( (B.Squad.SquadLeader != None) && B.Squad.CloseToLeader(C.Pawn) ) { B.SendMessage(B.Squad.SquadLeader.PlayerReplicationInfo, 'OTHER', B.GetMessageIndex('INPOSITION'), 20, 'TEAM'); B.bInitLifeMessage = false; } } } } } } } } } defaultproperties { BeginningTime=60 GameName="Custom Killing Floor" } Скачать мутатор UPD. Обновлено.
WaveNum - номер волны, а TimeBetweenWaves - время между волнами. Тогда уж WaveCountDown=TimeBetweenWaves; P.S. Не до конца протестировал мутатор, трейдер не доступен, позже пофиксю. UPD. Обновил ссылку.
Ну как-то так можно: Код: Спойлер Код: class Trader0Mut extends Mutator; function MatchStarting() { if(KFGameType(Level.Game)==none) return; TimeRoutine(); OpenShopsRoutine(); Destroy(); } function TimeRoutine() { KFGameType(Level.Game).WaveCountDown=KFGameType(Level.Game).TimeBetweenWaves; } function OpenShopsRoutine() { local int i; local Controller C; local KFGameType KFGT; KFGT=KFGameType(Level.Game); KFGT.bTradingDoorsOpen = True; for(i=0;i<KFGT.ShopList.Length;i++ ) { if(KFGT.ShopList[i].bAlwaysClosed) continue; if(KFGT.ShopList[i].bAlwaysEnabled ) KFGT.ShopList[i].OpenShop(); } if(KFGameReplicationInfo(KFGT.GameReplicationInfo).CurrentShop == none) SelectShopRoutine(); KFGameReplicationInfo(KFGT.GameReplicationInfo).CurrentShop.OpenShop(); for(C=Level.ControllerList;C!=None;C=C.NextController) { if(KFPlayerController(C)!=None) KFPlayerController(C).SetShowPathToTrader(true); } } function SelectShopRoutine() { local array<ShopVolume> TempShopList; local int i; local int SelectedShop; local KFGameType KFGT; KFGT=KFGameType(Level.Game); if(KFGT.ShopList.Length < 1) return; for(i=0;i<KFGT.ShopList.Length;i++ ) { if(KFGT.ShopList[i].bAlwaysClosed) continue; TempShopList[TempShopList.Length] = KFGT.ShopList[i]; } SelectedShop = Rand(TempShopList.Length); if(TempShopList[SelectedShop] != KFGameReplicationInfo(KFGT.GameReplicationInfo).CurrentShop) KFGameReplicationInfo(KFGT.GameReplicationInfo).CurrentShop = TempShopList[SelectedShop]; else if ( SelectedShop + 1 < TempShopList.Length ) KFGameReplicationInfo(KFGT.GameReplicationInfo).CurrentShop = TempShopList[SelectedShop + 1]; else KFGameReplicationInfo(KFGT.GameReplicationInfo).CurrentShop = TempShopList[0]; } defaultproperties { GroupName="KF-Trader0" FriendlyName="Trader0Mut" Description="Trader0Mut" } Ссылка Trader0Mut.Trader0Mut Замечание: Так как мутатор чисто серверный (хоть и серый), то он не повлияет на возможность стим прокачки на классических серверах. Замечание 2: Спойлер Для себя самого) Если буду делать отдельную тему вдруг - надо бы сделать вызов всех функций через таймер небольшой. Чтобы можно было ещё и Pawn'ы сделать "прозрачные" для других Pawn'ов В MatchStarting рано это делать - ещё нет "тел"
Спасибо! Установка времени работает, а вот магазины не открываются( И еще не показывается указатель куда бежать к магазину Помогите пожалуйста подправить
Ну указатель не показывается - эт да Вон у Эссенса выше можешь взять код с указателями - я тупо поленился копипастить много кода) Ну или в KFMod.KFGameType.OpenShops() А магазины открывались - я проверял Ну сейчас ещё разок гляну Upd1. Хм. Действительно не открываются) Очень странно. Ладно, сейчас поправлю Upd2. Поправил - см. исходный пост. Заодно добавил указатель