Sadistic Statistics
SADISTIC STATISTICS
What is it for?
Sadistic Statistics script is a general purpose script for showing in-game statistics. By "general purpose" I mean that it's not tied to one map, you should be able to copy it over to another map with ease. (How-to - see below). It's going to have as many useful features for mapmakers and players as possible.
- for building and fighting maps alike. If your map has a complicated script already (like Bonus), you will likely need a programmer to join two scripts - copying this script to a special map will break it.
- show number of weapons in barracks to teammates before peacetime
- show spam/deaths/kills/killpoints statistics to teammates, or to all players (you can choose what you prefer in the script file)
- show game time - including countdown until the end of peacetime
- building order script. Now you don't need a separate script for it, simply choose the building order you want (default, koczis, or To style) in the script file.
- you can easily edit the colors for the script for some customization
How do the (kill/army) points work?
You get more points for killing/having more powerful units:
How to copy the script to a new map?
- Open the map in Map Editor and save a copy of the map as "MapName S"
- Go to "Remake folder\MapsMP\MapName S\"
- Paste the script file (you can find it with the "Shadow Realm S" map in the attachment below) and change its name to "MapName S.script". WARNING - see below if such file already exists!
- Edit script settings. Open the script file and make needed changes:
- MAP_TYPE = 0; change 0 to 1 if this is a fighting map.
- BUILD_ORDER = 0; change to 0 for default, 1 for koczis and 2 for To building order. When in doubt, change to 0.
- STATS_FOR_ALL = 0; change to 1 if you want everyone to see the kill statistics. If you want people to see only teammates stats, leave it at 0.
-If it's a building order script (it usually starts with "script by Ben modified by sado"), simply set proper building order above. Maps with koczis building script (Golden Cliffs, Shadow Realm, New Horizon) - set BUILD_ORDER to 1.
-If it's a very long and complicated script, like Bonus for example; or if this is a special map - don't use the script, it won't work and the map will be broken. You will need programming skills to combine my script with the one the map uses.
Screenshots:
![Image](https://i.imgur.com/aSBaIyC.jpg)
Code:
- Code:
const MAP_TYPE = 0; BUILD_ORDER = 0; TOWER_LIMIT = 0; //doesn't work yet STATS_FOR_ALL = 0; BARRACKS_STATS_AFTER_PT=1; BARRACKS_STATS_TIME=600; //time in ticks to show the barracks stats after peacetime INTERFACE_COLOR = 'aaaaaa'; INTERFACE_COLOR2 = '88ff88'; SHIELD_COLOR = '3377ff'; ARMOR_COLOR = 'ffffb3'; MELEE_COLOR = '5522bb'; ANTIHORSE_COLOR = '003366'; SHOOTERS_COLOR = 'ff3377'; HR_COLOR = 'a3aaff'; STAT_COLOR = 'ff6600'; var BarracksList, Equipped, Lost, Defeated, DefeatedPoints: array [0..7] of Integer; var BuildOrderH: Integer; procedure UpdateOverlay(Gametime, Player: Integer); var Time,P,B,Sec,Recruits,ArmyPower: Integer; var WareColor: string; begin Time := (States.PeaceTime - Gametime)/10; Actions.OverlayTextSet(Player,'[$'+INTERFACE_COLOR+']Time: '); if (States.PeaceTime > 0) and (States.PeaceTime > Gametime) then begin Actions.OverlayTextAppend(Player, IntToStr(Time /60) +':'); Sec := Time mod 60; if (Sec < 10) then Actions.OverlayTextAppend(Player, '0'+IntToStr(Sec)) else Actions.OverlayTextAppend(Player, IntToStr(Sec)); end else begin Actions.OverlayTextAppend(Player, IntToStr(Gametime /600) +':'); Sec := ((Gametime)/10) mod 60; if (Sec < 10) then Actions.OverlayTextAppend(Player, '0'+IntToStr(Sec)) else Actions.OverlayTextAppend(Player, IntToStr(Sec)); end; if (BARRACKS_STATS_AFTER_PT=1) or ((MAP_TYPE=0) and (States.PeaceTime + BARRACKS_STATS_TIME > Gametime)) or ((MAP_TYPE=0) and (States.PeaceTime = 0) and (BARRACKS_STATS_TIME > Gametime)) then begin Actions.OverlayTextAppend(Player,'|'); for B := 16 to 26 do begin case B of 16,17: WareColor := SHIELD_COLOR; 18,19: WareColor := ARMOR_COLOR; 20,21: WareColor := MELEE_COLOR; 22,23: WareColor := ANTIHORSE_COLOR; 24,25: WareColor := SHOOTERS_COLOR; 26: WareColor := HR_COLOR; end; if (B = 21) then Actions.OverlayTextAppend(Player,'|'); Actions.OverlayTextAppend(Player,'[$'+WareColor+']'+ States.WareTypeName(B) + ', '); end; //Actions.OverlayTextAppend(Player,'[$'+HR_COLOR+']'+ States.WareTypeName(26) + ', '); Actions.OverlayTextAppend(Player,'[$'+HR_COLOR+']'+ States.UnitTypeName(13) + ' '); for P := 0 to States.LocationCount-1 do begin if States.PlayerEnabled(P) and States.PlayerEnabled(Player) then begin if States.PlayerAllianceCheck(Player, P) or (Player = P) then begin if (BarracksList[P] = -1) then begin Actions.OverlayTextAppend(Player,'|[$' + States.PlayerColorText(P) + ']' + States.PlayerName(P) + ' [$'+INTERFACE_COLOR+']has no barracks yet'); end else begin Actions.OverlayTextAppend(Player,'|[$' + States.PlayerColorText(P) + ']' + States.PlayerName(P) + ': '); for B := 16 to 26 do begin case B of 16,17: WareColor := SHIELD_COLOR; 18,19: WareColor := ARMOR_COLOR; 20,21: WareColor := MELEE_COLOR; 22,23: WareColor := ANTIHORSE_COLOR; 24,25: WareColor := SHOOTERS_COLOR; 26: WareColor := HR_COLOR; end; Actions.OverlayTextAppend(Player,'[$'+WareColor+']'+IntToStr(States.HouseResourceAmount(BarracksList[P],B)) + ' '); end; //Actions.OverlayTextAppend(Player,'[$'+HR_COLOR+']'+IntToStr(States.HouseResourceAmount(BarracksList[P],26)) + ' '); Recruits := States.StatUnitTypeCount(P, 13) - States.StatHouseTypeCount(P,17); Actions.OverlayTextAppend(Player,'[$'+HR_COLOR+']'+ IntToStr(Recruits) + ' '); end; end; end; end; end; if ((MAP_TYPE=0) and (States.PeaceTime < Gametime)) or (States.PeaceTime = 0) then begin Actions.OverlayTextAppend(Player,'||[$'+INTERFACE_COLOR+']Kill statistics: ' ); for P := 0 to States.LocationCount-1 do begin if States.PlayerEnabled(P) and States.PlayerEnabled(Player) then begin if States.PlayerAllianceCheck(Player, P) or (Player = P) or (STATS_FOR_ALL=1) then begin Actions.OverlayTextAppend(Player,'|[$' + States.PlayerColorText(P) + ']' + States.PlayerName(P) +': [$'+STAT_COLOR+']'+ IntToStr(Equipped[P]) + '[$'+INTERFACE_COLOR+'] trained, [$'+STAT_COLOR+']' + IntToStr(Lost[P]) + '[$'+INTERFACE_COLOR+'] deaths, [$'+STAT_COLOR+']' + IntToStr(Defeated[P]) + '[$'+INTERFACE_COLOR+'] kills, [$'+STAT_COLOR+']' + IntToStr(DefeatedPoints[P]) + '[$'+INTERFACE_COLOR+'] kill points, '); ArmyPower := States.StatUnitMultipleTypesCount(P, [14,24,25,19,27,17]) + States.StatUnitMultipleTypesCount(P, [15,20,21,18])*2 + States.StatUnitMultipleTypesCount(P, [16,22,23,26])*3; Actions.OverlayTextAppend(Player, '[$'+INTERFACE_COLOR2+']army points: '+IntToStr(ArmyPower)); end; end; end; end; end; function GetUnitPoints(aUnitType: Integer): Integer; var Points: Integer; begin case aUnitType of 14,24,25,19,27,17: Points := 1; //militia,rebel,rogue,lance,vaga,bow 15,20,21,18: Points := 2; //axe,pike,scout,xbow 16,22,23,26: Points := 3; //sword,knight,barb,warr else Points := 0; end; Result := Points; Exit; end; procedure OnUnitDied(aUnit, aKiller: Integer); begin if (aKiller <> -1) then begin Inc(Lost[States.UnitOwner(aUnit)]); Inc(Defeated[aKiller]); DefeatedPoints[aKiller] := DefeatedPoints[aKiller] + GetUnitPoints(States.UnitType(aUnit)); end; end; procedure OnWarriorEquipped(aUnit,aGroup: Integer); begin Inc(Equipped[States.UnitOwner(aUnit)]); end; procedure OnMissionStart; var P,K: Integer; var Houses: array of Integer; begin BuildOrderH := BUILD_ORDER; for P := 0 to States.LocationCount-1 do if States.PlayerEnabled(P) and (MAP_TYPE=0) then begin case BuildOrderH of 1: begin Actions.HouseAllow(P, 27, False); //inn Actions.HouseAllow(P, 14, False); //quarry Actions.HouseAllow(P, 9, False); //cutter //DEBUG //Actions.HouseUnlock(P, 19); //Actions.HouseUnlock(P, 21); end; 2: begin Actions.HouseUnlock(P, 27); Actions.HouseUnlock(P, 14); Actions.HouseUnlock(P, 9); end; end; BarracksList[P] := -1; //States.ClosestHouse(P, 0,0,21); Houses := States.PlayerGetAllHouses(P); for K := 0 to Length(Houses)-1 do begin //Actions.Log('type K='+IntToStr(States.HouseType(Houses[K]))); if States.HouseType(Houses[K])=21 then BarracksList[P] := Houses[K]; //only one barracks per player on start is assumed, but who cares... end; end; end; procedure OnHouseBuilt(aHouse: Integer); begin if States.HouseType(aHouse) = 21 then BarracksList[States.HouseOwner(aHouse)] := aHouse; if (BuildOrderH = 1) then begin if States.HouseType(aHouse) = 13 then //unlock inn after school Actions.HouseAllow(States.HouseOwner(aHouse), 27, True); if States.HouseType(aHouse) = 27 then //unlock quarry Actions.HouseAllow(States.HouseOwner(aHouse), 14, True); if States.HouseType(aHouse) = 14 then //unlock cutter Actions.HouseAllow(States.HouseOwner(aHouse), 9, True); end; end; procedure OnTick; var P: Integer; begin for P := 0 to States.LocationCount-1 do if (States.GameTime + P*2) mod 10 = 0 then UpdateOverlay(States.GameTime, P); end;