Re: Dynamic Script Usage
PostPosted: 12 Apr 2013, 05:19
@Ben: Please be more specific in error's description. What is exactly happening, do you get an error message, or houses aren't blocked/unlocked?
Talk about Knights and Merchants!
https://knightsandmerchants.net:443/forum/
https://knightsandmerchants.net:443/forum/viewtopic.php?t=1489
procedure OnMissionStart;
var I, P: Integer;
begin
for P := 0 to 5 do
if States.PlayerEnabled(P) then
begin
for I := 0 to 28 do
Actions.HouseAllow(P, I, False);
Actions.HouseAllow(P, 11, True);
Actions.HouseAllow(P, 13, True);
end;
end;
procedure OnHouseBuilt(aHouse: Integer);
begin
if States.HouseType(aHouse) = 11 then
Actions.HouseAllow(States.HouseOwner(aHouse), 13, True);
if States.HouseType(aHouse) = 14 then
Actions.HouseAllow(States.HouseOwner(aHouse), 9, True);
end;
I thought that this was what was happening, so I actually tried switching everything to False, but it still didn't work.
I must have overlooked something. I'll go try again.
Don't switch everything to false, swap true with false and false with true.
Also note that the example I gave you wasn't complete, you need to customise what happens in OnHouseBuilt so building the school allows the inn, etc. You also need to allow everything when they build the sawmill to make it use the "normal" unlock order after that.
Also, if I just wanted to disable just two buildings, and not, say 9-27, could I just do two IDs instead of a range?
var
Message0Sent: Boolean;
Attack1Started, Attack2Started, Attack3Started, Attack4Started, Attack5Started, Attack6Started: Boolean;
Attack1Defeated, Attack2Defeated, Attack3Defeated, Attack4Defeated, Attack5Defeated, Attack6Defeated: array [0..3] of Boolean;
procedure ShowMsgToPlayers(aMsg: Integer);
begin
Actions.ShowMsg(0, aMsg);
Actions.ShowMsg(1, aMsg);
Actions.ShowMsg(2, aMsg);
Actions.ShowMsg(3, aMsg);
end;
procedure CheckAttack1Defeated(aPlayer: Integer);
begin
if (States.ArmyCount(aPlayer + 4) = 0) and (Attack1Defeated[aPlayer] = false) and (States.GameTime > 2400) then
begin
Actions.GiveWares(aPlayer, 1, 50);
Actions.GiveWares(aPlayer, 2, 15);
Actions.GiveWares(aPlayer, 7, 15);
Actions.ShowMsg(aPlayer, 2);
Attack1Defeated[aPlayer] := True;
//Actions.SetOverlayText(0; 1; 2; 3, States.TextFormatted(30, [States.PlayerColorText(aPlayer), States.PlayerName(aPlayer)]));
end;
end;
procedure CheckAttack2Defeated(aPlayer: Integer);
begin
if (States.ArmyCount(aPlayer + 4) = 0) and (Attack2Defeated[aPlayer] = false) and (States.GameTime > 6600) then
begin
Actions.GiveWares(aPlayer, 1, 40);
Actions.GiveWares(aPlayer, 2, 15);
Actions.GiveWares(aPlayer, 7, 15);
Actions.ShowMsg(aPlayer, 4);
Attack2Defeated[aPlayer] := True;
end;
end;
procedure CheckAttack3Defeated(aPlayer: Integer);
begin
if (States.ArmyCount(aPlayer + 4) = 0) and (Attack3Defeated[aPlayer] = false) and (States.GameTime > 9600) then
begin
Actions.GiveWares(aPlayer, 1, 50);
Actions.GiveWares(aPlayer, 2, 20);
Actions.GiveWares(aPlayer, 7, 20);
Actions.ShowMsg(aPlayer, 6);
Attack3Defeated[aPlayer] := True;
end;
end;
procedure CheckAttack4Defeated(aPlayer: Integer);
begin
if (States.ArmyCount(aPlayer + 4) = 0) and (Attack4Defeated[aPlayer] = false) and (States.GameTime > 13800) then
begin
Actions.GiveWares(aPlayer, 1, 50);
Actions.GiveWares(aPlayer, 2, 15);
Actions.GiveWares(aPlayer, 7, 10);
Actions.ShowMsg(aPlayer, 8);
Attack4Defeated[aPlayer] := True;
end;
end;
procedure CheckAttack5Defeated(aPlayer: Integer);
begin
if (States.ArmyCount(aPlayer + 4) = 0) and (Attack5Defeated[aPlayer] = false) and (States.GameTime > 16800) then
begin
Actions.GiveWares(aPlayer, 1, 35);
Actions.GiveWares(aPlayer, 2, 10);
Actions.GiveWares(aPlayer, 7, 5);
Actions.GiveWares(aPlayer, 18, 10);
Actions.ShowMsg(aPlayer, 10);
Attack5Defeated[aPlayer] := True;
end;
end;
procedure CheckAttack6Defeated(aPlayer: Integer);
begin
if (States.ArmyCount(aPlayer + 4) = 0) and (Attack6Defeated[aPlayer] = false) and (States.GameTime > 19800) then
begin
Actions.GiveWares(aPlayer, 1, 30);
Actions.GiveWares(aPlayer, 7, 10);
Actions.ShowMsg(aPlayer, 12);
Attack6Defeated[aPlayer] := True;
end;
end;
begin
if (States.GameTime = 50) and not Message0Sent then
begin
ShowMsgToPlayers(0);
//Actions.ShowCountdown(0, 2350);
//Actions.ShowCountdown(1, 2350);
//Actions.ShowCountdown(2, 2350);
//Actions.ShowCountdown(3, 2350);
Message0Sent := true;
end;
//attack wave 1
if (States.GameTime = 2400) and not Attack1Started then
begin
Actions.GiveGroup(4, 14, 68, 78, 5, 15, 1);
Actions.GiveGroup(5, 14, 122, 78, 3, 15, 1);
Actions.GiveGroup(6, 14, 68, 112, 7, 15, 1);
Actions.GiveGroup(7, 14, 122, 112, 1, 15, 1);
ShowMsgToPlayers(1);
//Actions.ShowCountdown(0, 4200);
//Actions.ShowCountdown(1, 4200);
//Actions.ShowCountdown(2, 4200);
//Actions.ShowCountdown(3, 4200);
Attack1Started := true;
end;
CheckAttack1Defeated(0);
CheckAttack1Defeated(1);
CheckAttack1Defeated(2);
CheckAttack1Defeated(3);
//Attack wave 2
if (States.GameTime = 6600) and (Attack2Started = false) then
begin
Actions.GiveGroup(4, 19, 68, 78, 5, 20, 1);
Actions.GiveGroup(5, 19, 122, 78, 3, 20, 1);
Actions.GiveGroup(6, 19, 68, 112, 7, 20, 1);
Actions.GiveGroup(7, 19, 122, 112, 1, 20, 1);
ShowMsgToPlayers(3);
//Actions.ShowCountdown(0, 3000);
//Actions.ShowCountdown(1, 3000);
//Actions.ShowCountdown(2, 3000);
//Actions.ShowCountdown(3, 3000);
Attack2Started := true;
end;
CheckAttack2Defeated(0);
CheckAttack2Defeated(1);
CheckAttack2Defeated(2);
CheckAttack2Defeated(3);
//Attack wave 3
if (States.GameTime = 9600) and (Attack3Started = false) then
begin
Actions.GiveGroup(4, 20, 68, 78, 5, 25, 1);
Actions.GiveGroup(5, 20, 122, 78, 3, 25, 1);
Actions.GiveGroup(6, 20, 68, 112, 7, 25, 1);
Actions.GiveGroup(7, 20, 122, 112, 1, 25, 1);
ShowMsgToPlayers(5);
//Actions.ShowCountdown(0, 3000);
//Actions.ShowCountdown(1, 3000);
//Actions.ShowCountdown(2, 3000);
//Actions.ShowCountdown(3, 3000);
Attack3Started := true;
end;
CheckAttack3Defeated(0);
CheckAttack3Defeated(1);
CheckAttack3Defeated(2);
CheckAttack3Defeated(3);
//Attack wave 4
if (States.GameTime = 12600) and (Attack4Started = false) then
begin
Actions.GiveGroup(4, 14, 68, 78, 5, 60, 5);
Actions.GiveGroup(5, 14, 122, 78, 3, 60, 5);
Actions.GiveGroup(6, 14, 68, 112, 7, 60, 5);
Actions.GiveGroup(7, 14, 122, 112, 1, 60, 5);
Actions.GiveGroup(4, 15, 70, 80, 5, 20, 2);
Actions.GiveGroup(5, 15, 124, 80, 3, 20, 2);
Actions.GiveGroup(6, 15, 70, 114, 7, 20, 2);
Actions.GiveGroup(7, 15, 124, 114, 1, 20, 2);
ShowMsgToPlayers(7);
//Actions.ShowCountdown(0, 3000);
//Actions.ShowCountdown(1, 3000);
//Actions.ShowCountdown(2, 3000);
//Actions.ShowCountdown(3, 3000);
Attack4Started := true;
end;
CheckAttack4Defeated(0);
CheckAttack4Defeated(1);
CheckAttack4Defeated(2);
CheckAttack4Defeated(3);
//Attack wave 5
if (States.GameTime = 15600) and (Attack5Started = false) then
begin
Actions.GiveGroup(4, 21, 68, 78, 5, 20, 1);
Actions.GiveGroup(5, 21, 122, 78, 3, 20, 1);
Actions.GiveGroup(6, 21, 68, 112, 7, 20, 1);
Actions.GiveGroup(7, 21, 122, 112, 1, 20, 1);
ShowMsgToPlayers(9);
//Actions.ShowCountdown(0, 3000);
//Actions.ShowCountdown(1, 3000);
//Actions.ShowCountdown(2, 3000);
//Actions.ShowCountdown(3, 3000);
Attack5Started := true;
end;
CheckAttack6Defeated(0);
CheckAttack6Defeated(1);
CheckAttack6Defeated(2);
CheckAttack6Defeated(3);
//Attack wave 6
if (States.GameTime = 18600) and (Attack6Started = false) then
begin
Actions.GiveGroup(4, 16, 68, 78, 5, 50, 3);
Actions.GiveGroup(5, 16, 122, 78, 3, 50, 3);
Actions.GiveGroup(6, 16, 68, 112, 7, 50, 3);
Actions.GiveGroup(7, 16, 122, 112, 1, 50, 3);
ShowMsgToPlayers(11);
//Actions.ShowCountdown(0, 3000);
//Actions.ShowCountdown(1, 3000);
//Actions.ShowCountdown(2, 3000);
//Actions.ShowCountdown(3, 3000);
Attack6Started := true;
end;
CheckAttack6Defeated(0);
CheckAttack6Defeated(1);
CheckAttack6Defeated(2);
CheckAttack6Defeated(3);
end.
I'm having troubles too. This error occurs: [Error] (8:26): Type mismatch
I'm using the exact same script as before, when it worked just fine. What's changed?
Also, can't it just ignore the scripts that aren't working? Currently nothing works if there's just one tiny mistake; that's pretty annoying, I can't do a thing right now.
Would be nice to actually have a tool that'd check script's integrity without running the map again and again just to see what was the mistake.
Sado and I were trying to figure out if we could use the OnTick even to run after more than just 1 tick. For example, say I wanted a unit to be created after 1000 ticks. How would I do this?
procedure OnTick;
begin
//Every tick we should set the text overlaid on the screen for player 0
Actions.SetOverlayText(0, 'Current tick: '+IntToStr(States.GameTime));
if States.GameTime = 100 then //After 10 seconds
begin
Actions.ShowMsg(...); //Show a message
Actions.GiveWares(...); //Give the player some wares
end;
if States.GameTime = 1000 then //After 100 seconds
Actions.GiveUnit(...); //Give the player a unit
end;