Official Soldat Forums
Server Talk => Scripting Discussions and Help => Topic started by: mich1103 on July 18, 2010, 08:31:20 am
-
This will be where i'll ask my question !
(i don't have question now ...) :D
I add level and xp in my shop script
how can i detect if Xp is higher to maxXp ?
-
if (xp >= maxxp) then
-
...oh god
i'm usually for helping people, but when the questions are so elementary, i feel like they need to do a bit of research on their own.
mich: how much programming have you done in soldat scripting?
-
@Dark Crusade : Thanks ! ;D
@zyxstand : You're asking me how many script i did ?
-
that's one way of putting it... i'm just asking because your question seemed very basic for a programmer...
-
@zyxstand : I only have 13 years old and im not native english speaker so i learn scripting very slowly ^^
-
@zyxstand : I only have 13 years old and im not native english speaker so i learn scripting very slowly ^^
i started programming when I was 11. what language do you speak (French?).
I recommend that you learn programming in another language first. it's hard to program in soldat without knowing the basics.
Try starting with QBASIC. this can help you get some basic programming skills.
READ THIS (http://www.petesqbsite.com/sections/introduction/intro.shtml) to help you get started. QBASIC is very old, but so simple that you can learn programming easily!
-
I'm not at homw now so i'll learn this language later !
But how can i detect if a player is level 10 and higher ?
like:
Onplayerrespawn
begin
If soldier[ID].level >= 10
then begin GiveBonus(ID,3)
end;
end;
-
First of all understand what an integer is.
-
I got a problem with AppOnIdles
because there is no ID in AppOnIdles my script wont work ...
I want to put this in apponidle to make that if a player is lvl 25 and higher and that at each second he got 2% of life ! How can i do this ?
if soldier[ID].level >=25
then begin
DoDamage(ID,-3);
end;
-
Stop wasting our time here. You don't know the basics of programming. Not even simple stuff like if..else..
As you seem to be struggling with the use of Google here is a little help: Link (http://lmgtfy.com/?q=pascal+tutorial)
Work through a tutorial and if you have questions afterwards you may ask here again.
-
Im learning now !
but its hard cause i dont understand all ... (im French) ...
I think i know the basic now !
@Dark Crusade : you can ask me question if u want !
-
So tell me what this script does: Link (http://darkcrusade.pastebin.com/uJuNkPgt)
-
const
MaxRange = 195;
type
PlayerStats=Record
RugerKills:Byte;
end;
var
Player:Array[1..32] of PlayerStats;
Procedure TriggerRuger(Killer,Victim:Byte); //i don't understand this procedure ...
var
X1,Y1,X2,Y2:Single;
i,j,Team:Byte;
k:Integer;
begin
GetPlayerXY(Victim,X1,Y1);
Team := GetPlayerStat(Victim,'Team');
repeat
j := j + 1;
for i := 1 to 32 do if (GetPlayerStat(i,'Active') = true) AND (GetPlayerStat(i,'Team') <> Team) AND (GetPlayerStat(i,'Alive') = true) then begin
GetPlayerXY(i,X2,Y2);
if (Distance(X1,Y1,X2,Y2) <= MaxRange) then begin
CreateBullet(X2,Y2,0,0,0,5,Killer);
DoDamageBy(i,Killer,20);
k := k + 1;
end;
end;
until(j = Player[Killer].RugerKills);
WriteConsole(Killer,'You''ve hit ' + IntToStr(k) + ' targets.', $FFFFFF);
end;
Procedure OnPlayerKill(Killer,Victim:Byte; Weapon:String); //add 1 ruger kill to player
begin
if (Weapon = 'RUGER') then begin
Player[Killer].RugerKills := Player[Killer].RugerKills + 1;
TriggerRuger(Killer,Victim);
end;
end;
Procedure OnJoinGame(ID,Team:Byte); //put that player did 0 ruger kill
begin
Player[ID].RugerKills := 0;
end;
Procedure ActivateServer(); //write on the server console that the server started !
begin
WriteLn('*** SERVER STARTED ***');
end;
-
Fine, you were able to click on my link and paste the code here..
-
i know the pascal syntax but the problem is with the soldat scripting !
there is no tutorial about wath i want ...
-
Link (http://forums.soldat.pl/index.php?topic=29911.0)
\o/
-
Fine, you were able to click on my link and paste the code here..
lmao
DC, i think we should cease helping people with too basic questions. Give them a link to a tutorial or whatnot, and let them do the rest... even though it's hard to let questions go by (and not share your knowledge), it does waste our time - and we don't even get paid :P
-
I did the script by another way !
did you guys have an idea of skills that i should add to my server ?
-
Derp derp don't think about adding advanced things like skills when you don't understand how Soldat coding works.
@zxy: I always feel the urge to help and I have (right now) enough time to response, so why should I refrain?
-
@ DarkCrusade : i already did some skills (Easy one ^^)
thats how i did the regeneration skills !
Procedure Heal(ID: integer);
begin
if soldier[ID].level >=25
then begin
DoDamage(ID,-3);
end;
end;
Procedure AppOnIdle(Ticks: Integer);
Begin
for i:= 1 to 32 do begin
Heal(i);
If you want you can see my script in action :P
IP:soldat.no-ip.ca PORT: 23098
-
Whenever you access an ID in AppOnIdle (in general when you loop through the player list) you must check whether the ID is active (whether the ID is a player/bot on the server).
if (GetPlayerStat(ID,'Active') = true) then
-
DC, he's probs not gonna understand that. i'll just give him the code. hopefully he can learn from it...
Procedure Heal(ID: integer);
begin
if soldier[ID].level >=25
then begin
DoDamage(ID,-3);
end;
end;
Procedure AppOnIdle(Ticks: Integer);
Begin
for i:= 1 to 32 do if GetPlayerStat(i,'Active') then begin
Heal(i);
Also, I'm not sure if you're aware of this, but a player's health is maximum 150. check to make sure he has less than maximum health before actually healing. (I'm not sure if you can give more than 150 health anyway, in which case it might not matter too much). Also, in realistic mode, max health is 65. good to know.
-
Ok now i understand !
Thanks ;D
-
Normal: 150 (200 by scripting)
Realistic: 65 (never tested)
-
So with this script !
a player got 200 health ?
-
Proximitly.
-
I did a small small kamikaze script but the bullet are too high
The procedure
Procedure Kamikaze(ID: byte);
begin
if soldier[ID].level >= 40
then begin
CreateBullet(GetPlayerStat(ID,'x'), GetPlayerStat(ID,'y') - 500, 0, 0,100, 4, 1);
CreateBullet(GetPlayerStat(ID,'x'), GetPlayerStat(ID,'y') - 500, 1, 1,100, 4, 1);
CreateBullet(GetPlayerStat(ID,'x'), GetPlayerStat(ID,'y') - 500, 2, 2,100, 4, 1);
end;
end;
I dont really know how X and Y work :)
-
Procedure Kamikaze(ID: byte);
var
X, Y: single;
begin
if soldier[ID].level >= 40
then begin
GetPlayerXY(ID, X, Y)
CreateBullet(X, Y - 10, 0, 0,100, 4, 1);
CreateBullet(X, Y - 10, 1, 1,100, 4, 1);
CreateBullet(X, Y - 10, 2, 2,100, 4, 1);
end;
end;
This should spawn all bullets in his ass
-
I did a small procedure for a Nuclear bomb !
procedure Nuke(ID: byte);
begin
if GetPlayerStat(ID,'Human') = False
then begin
DoDamage(ID,4000);
end;
end;
but the server crash when i do /nuke ... :'(
if regExpMatch('^/(nuke)$', Text) then
begin
For i := 1 to 32 do
if soldier[ID].level >= 40 then
begin
if soldier[ID].money >= 50 then
begin
Nuke(i);
writeconsole(0, 'NUCLEAR BOMB !', Color);
end else begin writeconsole(ID, 'You are not lvl 40 + or you dont have enough money.', Color);
end;
end;
end;
-
Whenever you access an ID in AppOnIdle (in general when you loop through the player list) you must check whether the ID is active (whether the ID is a player/bot on the server).
if (GetPlayerStat(ID,'Active') = true) then
-
if regExpMatch('^/(nuke)$', Text) then
begin
if (soldier[ID].level >= 40) and (soldier[ID].money >= 50) then
begin
For i := 1 to 32 do begin
Nuke(i);
WriteConsole(i, 'NUCLEAR BOMB !', Color);
end;
end else begin
writeconsole(ID, 'You are not lvl 40 + or you dont have enough money.', Color);
end;
end;
that should work, remember... first check money/level, next begin your loop
-
Work but i got some error !
-
Whenever you access an ID in AppOnIdle (in general when you loop through the player list) you must check whether the ID is active (whether the ID is a player/bot on the server).
if (GetPlayerStat(ID,'Active') = true) then
-
Already did ;) !
procedure Nuke(ID: byte);
begin
if GetPlayerStat(ID,'Human') = False
then begin
if (GetPlayerStat(ID,'Active') = true)
then begin
DoDamage(ID,4000);
end;
end;
end;
-
What's so hard to understand about "You must check whether the ID is active before you can access any other data"?
-
I got it i got no error now :D
but with the kamikaze part
Procedure Kamikaze(ID: byte);
var
X, Y: single;
begin
if soldier[ID].level >= 40
then begin
GetPlayerXY(ID, X, Y)
CreateBullet(X, Y - 10, 0, 0,120, 4, 1);
CreateBullet(X, Y - 10, 1, 1,120, 2, 1);
CreateBullet(X, Y - 10, 2, 2,120, 9, 1);
end;
end;
The bullet dont do any damage ... !
-
function CreateBullet(X, Y, VelX, VelY, HitM: single; sStyle, Owner: byte): integer;
The owner of these bullets should be the ID. The bulletstyle 4 (M79 bullet).
-
How can i put like that the nuke kill only bot named ZoMbIe ?
-
omg x.X ..... IF GETPLAYERSTAT(ID,'NAME') = 'ZoMbIe'!!! thats hard? -.- // what is your IQ? ^^
-
mich1103 are you even trying to figure out how to do these before you ask? They are fairly simple and anyone with basic knowledge of any kind of programming should be able to figure it out. Maybe use a translator on the descriptions for what each function/procedure does, although it probably wont work 100% it should help you get a basic understanding of what it does.
-
I understand now ! :)
i can put more than 1 getplayerstat
like :
if GetPlayerStat(ID,'Human') = False
then begin
if (GetPlayerStat(ID,'Active') = true)
then begin
if (GetPlayerStat(ID,'name') = 'ZoMbIe')
then begin
So whit that i can put that player need to be alive to be named : Major, then begin ^^ (exemple) :)
-
What's so hard to understand about "You must check whether the ID is active before you can access any other data"?
Anyone noticed how useless this is?
-
Eh he added it, just put in the wrong spot so at least he got half of your message ;). Maybe saying "Move the 'Active' check so its checked before the 'Human' check" would help more. Not everyone is always going to start out as an epic scripter and some people are more dense than others.
-
Telling him 5 times that he needs to check whether the ID is active before he can do anything with the ID should have been enough.
-
Each time i lay a mine i got a error message in the console ...
-
You try to access a variable that doesn't exist.
-
which variable ? ???
-
How can I tell? Did I see the script or something? :P
-
I think i will not put the mine skills in my script (too much trouble)
Or maybe you have another mine script (simple mine script)
The error can crash my server ?
-
Well the error says that its in the AppOnIdle procedure so if you could, post the code for that section unless you don't want to. Considering its when the user types /mine it has something to do with the code for the mine, probably the part where you spawn something to mark the location(if you do that) or the part where you check player locations.
Also DC you're working with someone with extremely horrible english comprehension so obviously there will be issues with communication, you told him 5 times but 5 times the exact same way(fairly rude as well) I was just suggesting trying to tell him in a different, kinder way what to do to see if it worked better.
-
You want i post the AppOnIddle part ? (sorry im not native english speaker ...)
-
Whenever you access an ID in AppOnIdle (in general when you loop through the player list) you must check whether the ID is active (whether the ID is a player/bot on the server).
How is this rude? More information is appreciated!
I made a mine script and gave it to him. It works perfectly so he shouldn't have any issues with it. A few modifications and it's done.
-
Thanks ;D !
I includes it to my script and it work fine !
Now i need some idea for skills ...
-
Look around RPG scripts, you might get some ideas for skills ;)
-
LOOT AMMO !!! ;D
:-\ how can i procede ?
Maybe something like that ?
function Chance(Perc: single): boolean;
begin
result := (strtofloat(inttostr(random(0,101)))/100.0 < perc);
end;
procedure LootAmmo(ID: byte);
begin
ForceWeapon(ID,GetPlayerStat(ID,'primary'),GetPlayerStat(ID,'secondary'),11);
end;
function OnPlayerDamage(Victim,Shooter: Byte;Damage: Integer;Weapon: Byte) : integer
begin
if soldier[ID].level >= 50 then begin
if chance(0.1) then begin
LootAmmo(Shooter);
end;
end;
-
LootAmmoChance = 10;
Procedure LootAmmo(ID:Byte);
var
Amount,MaxAmmo:Byte;
begin
case GetPlayerStat(ID,'Primary') of
1: MaxAmmo := 7;
2: MaxAmmo := 30;
3: MaxAmmo := 40;
4: MaxAmmo := 25;
5: MaxAmmo := 8;
6: MaxAmmo := 4;
7: MaxAmmo := 1;
8: MaxAmmo := 10;
9: MaxAmmo := 50;
10: MaxAmmo := 100;
11: MaxAmmo := 200;
12: MaxAmmo := 1;
13: MaxAmmo := 1;
14: MaxAmmo := 1;
15: MaxAmmo := 150
16: MaxAmmo := 1;
0: MaxAmmo := 12;
255:Exit;
end;
if (MaxAmmo <> 1) then
Amount := MaxAmmo / 10 + Random(2,6)
else
Amount := 0;
ForceWeapon(ID,GetPlayerStat(ID,'Primary'),GetPlayerStat(ID,'Secondary'),Amount);
WriteConsole(ID,'Looted: ' + IntToStr(Amount) + ' ammunition.', $FFFFFF);
end;
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Random(1,101) <= LootAmmoChance) then LootAmmo(Shooter);
end;
Try to figure what I did. I didn't test the code so maybe you must fix it ;)
-
Work but if i loot with the minigun 15 ammo and that i have 100 ammo
i will have 15 ammo instead of 100 ...
-
LootAmmoChance = 10;
Procedure LootAmmo(ID:Byte);
var
Amount,MaxAmmo:Byte;
begin
case GetPlayerStat(ID,'Primary') of
1: MaxAmmo := 7;
2: MaxAmmo := 30;
3: MaxAmmo := 40;
4: MaxAmmo := 25;
5: MaxAmmo := 8;
6: MaxAmmo := 4;
7: MaxAmmo := 1;
8: MaxAmmo := 10;
9: MaxAmmo := 50;
10: MaxAmmo := 100;
11: MaxAmmo := 200;
12: MaxAmmo := 1;
13: MaxAmmo := 1;
14: MaxAmmo := 1;
15: MaxAmmo := 150
16: MaxAmmo := 1;
0: MaxAmmo := 12;
255:Exit;
end;
if (MaxAmmo <> 1) then begin
Amount := MaxAmmo / 10 + Random(2,6) + GetPlayerStat(ID,'Ammo')
if (Amount > MaxAmmo) then
Amount := 0;
end else Amount := 0;
ForceWeapon(ID,GetPlayerStat(ID,'Primary'),GetPlayerStat(ID,'Secondary'),Amount);
WriteConsole(ID,'Looted: ' + IntToStr(Amount) + ' ammunition.', $FFFFFF);
end;
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Random(1,101) <= LootAmmoChance) then LootAmmo(Shooter);
end;
-
Thanks :)
Player are able to spawn a stationary gun !
but it stuck like that
|
|
v
-
Happens to happen. Just add a !rebuild command that places the stationary gun on a new position and crouch. It'll spawn on the ground then ;)
-
i don't understand ...
i just want that the stationary gun i placed correctly the first time ...
-
It just happens. If you want it to be placed correctly the first time just crouch that moment..
-
Im working to do a Fatal hit skills !
here it is !
const
FatalHitChance = 5;
color = $FFFFFF;
procedure FatalHit(ID :byte);
begin
DoDamage(ID,4000);
end;
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Random(1,101) <= FatalHitChance) then
FatalHit(Victim);
WriteConsole(Shooter,'Fatal Hit !',color)
end;
end;
Its okay ? :-\
-
Use DoDamageBy(ID1,ID2,Damage) instead of DoDamage. ID1 is the ID that gets the damage, ID2 the guy who will get the kill.
-
something like that ?
const
FatalHitChance = 5;
color = $FFFFFF;
procedure FatalHit(Victim,Shooter:Byte;);
begin
DoDamageBy(Victim,Shooter,1000)
end;
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Random(1,101) <= FatalHitChance) then
FatalHit(Victim);
WriteConsole(Shooter,'Fatal Hit !',color)
end;
end;
-
const
FatalHitChance = 5;
color = $FFFFFF;
procedure FatalHit(Victim,Shooter:Byte;);
begin
DoDamageBy(Victim,Shooter,1000);
end;
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Random(1,101) <= FatalHitChance) then begin
FatalHit(Victim);
WriteConsole(Shooter,'Fatal Hit !',color)
end;
end;
You forgot a ; and a begin + end
-
Invalide number of parameter ...
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if soldier[shooter].level >= 50 then begin
if (Random(1,101) <= LootAmmoChance) then begin
LootAmmo(Shooter);
end;
end;
if soldier[shooter].level >= 55 then begin
if (Random(1,101) <= FatalHitChance) then begin
FatalHit(Victim);
WriteConsole(Shooter,'Fatal Hit !',colorr);
end;
end;
end;
-
Change FatalHit(Victim) to FatalHit(Victim,Shooter) ...
-
The script passs !
But there is alot of DAMN laggg ... :(
Like randomly sometime it say Fatal it and i got killed and that apear has i kill my self :P/
-
I put this line at the beginning of the function (but after "Result := Damage"):
if (Victim = Shooter) then Exit;
If the two IDs are the same the function gets cancelled so FatalHit cannot trigger.
Correct function:
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Victim = Shooter) then Exit;
if soldier[shooter].level >= 50 then
if (Random(1,101) <= LootAmmoChance) then
LootAmmo(Shooter);
if soldier[shooter].level >= 55 then
if (Random(1,101) <= FatalHitChance) then begin
FatalHit(Victim,Shooter);
WriteConsole(Shooter,'Fatal Hit !',colorr);
end;
end;
-
I want to give onflagscore 10% of mapXp i can ? ???
-
Soldier[ID].EP := Soldier[ID].EP + (MapXP * 10 / 100);
CheckLevelUp(ID);
First line: Increase the EP
Second: Check whether the player has enough EP for the next level
-
+ (MapXP * 10 / 100); lol
-
It's just to give him a basic idea of what percentage is all about >_>
-
also, you might have to use DIV instead of / if .ep is an integer
-
So i decide to put my server in the sevrer 2.7.0 !
and now my shop script wont pass but it pass on 2.6.5 ....
shop -> [Error] (103:118): Invalid number of parameters
-
yes, scripting for server version 2.7.0 has changed. i encourage you to look up the Changelog (http://enesce.com/help/html/Changelog.html) on enesce's website and read through ALL the changes. this is essential for a scripter!
as to your question, as you can read in the changelog, drawtext has been modified:
- Added BigTextID parameter to DrawText (after ID)
This will allow you to have multiple drawtext events up and not overwrite standard messages.
essentially, there's a new parameter, BigTextID, that you need to specify. And since you don't seem to know of all these changes, i also encourage you to read about the new functions that allow you to write/draw in new ways!
- Added InterfaceText function
- Added WorldText function
- Added InterfaceImage function
- Added WorldImage function
you might want to use InterfaceText, as they get their own writing slots on the screen (for instance: when you cap a flag, and get killed immediately after, the kill-message will replace the cap-message, which you might not like - you'd run into the same problem with DrawText. Using InterfaceText, you can manipulate your own writing "slots" so that it doesn't get overwritten by immediately-following messages)
-
Thanks !
But soldat 1.5.1 will be realesed soon ?
or i can wait to transfer my server ?
-
But soldat 1.5.1 will be realesed soon ?
HAHAHAHAH *wipes tear*
stick with 2.6.5 for now
-
So i can wait ?
-
You can and you must.
-
How many time before it will be released ?
-
Who knows..
-
EnEsCe ;D
-
i doubt it.
-
How can i do a shield skills !
like your invincible for 20 second !
-
here's the basic pseudo code
function OnPlayerDamage(Victim,Shooter: Byte;Damage: Integer;Weapon: Byte) : integer;
if (Victim is invincible) Result := 0 else Result := Damage
someone confirm this: i'm not sure if this works with m79/law/nade instant kill - i guess u can check it out!
-
If you want real invincibility you must set the result to -9999. I'm not sure whether you use some other stuff in OnPlayerDamage, if that's so you must exit after you've set the result to the new value.
Example:
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Soldier[Victim].Godmode) then begin
Result := -99999;
Exit;
end;
// Other stuff here
end:
-
But for the timer of 20 second ?
-
type
Stats=Record
GodTime:Integer;
end;
var
Soldier: Array[1..32] of Stats;
Procedure OnJoinGame(ID,Team:Byte);
begin
Soldier[ID].GodTime := -1;
end;
Function OnPlayerCommand(ID:Byte; Text:String):Boolean;
begin
if (LowerCase(Copy(Text,1,4)) = '/god') then begin
Soldier[ID].GodTime := 20;
WriteConsole(ID,'You are invincible for 20 seconds!',$FFFFFF);
end;
Result := false;
end;
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage;
if (Soldier[Victim].GodTime <> -1) then begin
Result := -99999;
Exit;
end;
// Other stuff here
end;
Procedure AppOnIdle(Ticks:Integer);
var
i:Byte;
begin
for i := 1 to 32 do if (GetPlayerStat(i,'Active') = true) then
if (Solder[i].GodTime <> -1) then begin
Solder[i].GodTime := Soldier[i].GodTime - 1;
if (Soldier[i].GodTime = 0) then begin
Soldier[i].GodTime := -1;
WriteConsole(i,'You are mortal again..',$CC0000);
end;
end;
-
And for the command i do it like that ?
if regExpMatch('^/(god|shield)$', Text) then
begin
if (soldier[ID].level >= 60) then begin
soldier[ID].GodTime :=20;
WriteConsole(ID,'You are invincible for 20 seconds!',$FFFFFF);
end else begin
writeconsole(ID, 'You are not lvl 60 +', Color);
end;
Result := false;
end;
end;
-
Yes.
Also you'll love to use this:
Function LowerCase(Input:String):String;
Returns the input string in lowercase. Example:
Input = 'fOoBAR'
Result = 'foobar'
-
What it is supposed to do ?
From: July 26, 2010, 11:13:21 am
- shop -> [Error] (736:1): 'BEGIN' expected
-
If the error is 'BEGIN' expected then you have an 'END' too much and viceversa.
-
i think you want to take out the "end" on line 726
also, perhaps you should nest all your "If Text = 'lol' then begin" with else lines so that it doesn't have to check it against every possible command and will stop as soon as the first one has been reached. Also, your code is very crowded. Any chance you can break it up into multiple parts??
-
i need a cooldown of 2 min ... for the god script !
-
Just add another timer for the cooldown.. you should be able to do that, and if you need help you can still ask ;)
-
I've tried but 'I FAILED' :'(
-
So show me what you tried? And please not the whole script
-
Here it is ! ;D
//here is wath i added in the script
type tsoldier = record
godcooldown:integer;
//i added this onplayerdamage
if soldier[Victim].godcooldown = 0 then begin
if (Soldier[Victim].GodTime <> -1) then begin
Result := -99999;
Exit;
//i added this onjoingame
soldier[ID].godcooldown := 0;
//i added this in AppOnIddle
if (Soldier[i].godcooldown := 100) then begin
Soldier[i].godcooldown := Soldier[i].godcooldown - 1;
if (Soldier[i].godcooldown = 0) then begin
Soldier[i].godcooldown := -1;
WriteConsole(i,'Shield can now be casted !',$CC0000);
-
your apponidle seems wrong - here's kinda what it should look like:
here's conceptually what needs to happen:
When god-shield is casted, set cooldown to 100 (or however many seconds you want). Then in apponidle, do this for every player:
if soldier[i].godcooldown > 0 then begin
soldier[i].godcooldown := soldier[i].godcooldown - 1;
if soldier[i].godcooldown = 0 then draw(shield ready);
end;
this will keep counting down until 0 is reached (your code seems to only count down ONCE, when godcooldown = 100. This means it'll stay at 99).
this will also display the message when shield is ready.
then when the player wants to use god-shield, you have to do a check to make sure cooldown = 0
Anyway, i haven't actually given you the actual script, only the concept. Try at it one more time and let us know if you got it or still need help ;)
-
Something like that ?
-
you're making huge errors in your onplayerdamage
when using if then begin, you must use END to mark the end of the code to be executed given the condition.
in your code, you leave out the END line until the end of your procedure, which is wrong.
i'm not gonna bother correcting it, i'll just give you the code:
function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage
if (Victim = Shooter) then Exit;
if (Soldier[Victim].GodTime > 0) then begin // 0 means god-mode
Result := 0;
end else begin
if (soldier[shooter].level >= 55) and (Random(1,101) <= FatalHitChance) then begin
FatalHit(Victim,Shooter);
WriteConsole(Shooter,'Fatal Hit !',colorr);
end;
// i put loot ammo here, so that you can't loot from someone in god-mode
if (soldier[shooter].level >= 50) and (Random(1,101) <= LootAmmoChance) then LootAmmo(Shooter);
end;
end;
// this is in your apponidle:
for i:= 1 to 32 do if GetPlayerStat(i,'Active') then begin
if (Soldier[i].GodTime > 0) then begin
Soldier[i].GodTime := Soldier[i].GodTime - 1;
if (Soldier[i].GodTime = 0) then WriteConsole(i,'You are mortal again..',$CC0000);
end else begin
if (Soldier[i].godcooldown > 0) then begin // cooldown doesn't start until god-mode is over
Soldier[i].godcooldown := Soldier[i].godcooldown - 1;
if (Soldier[i].godcooldown = 0) then WriteConsole(i,'God shield is ready to cast !',$CC0000);
end;
end;
end;
// this goes in your OnPlayerCommand
if regExpMatch('^/(god|shield)$', Text) then begin
if (soldier[ID].level >= 60) then begin
if (soldier[ID].godcooldown = 0) then begin
soldier[ID].GodTime := 20;
soldier[ID].godcooldown := 120;
WriteConsole(ID,'You are invincible for 20 seconds!',$FFFFFF);
end else WriteConsole(ID, 'God shield not ready. ' + inttostr(soldier[ID].godcooldown) + ' seconds remaining', Color);
end else WriteConsole(ID, 'You are not lvl 60 + Or you have too wait until the spell is ready', Color);
end;
-
So i've tried /god after i use it ! and it was always staying at 118 second ...
and i got this erro in the console : (AppOnIdle): Out of range
-
Should work better ;)
function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
begin
Result := Damage
if (Victim = Shooter) then Exit;
if (Soldier[Victim].GodTime > 0) then begin // 0 means god-mode
Result := -99999;
Exit;
end;
if (soldier[shooter].level >= 55) and (Random(1,101) <= FatalHitChance) then begin
FatalHit(Victim,Shooter);
WriteConsole(Shooter,'Fatal Hit !',colorr);
end;
if (soldier[shooter].level >= 50) and (Random(1,101) <= LootAmmoChance) then LootAmmo(Shooter);
end;
// AppOnIdle part
for i:= 1 to 32 do if GetPlayerStat(i,'Active') then begin
if (Soldier[i].GodTime > 0) then begin
Soldier[i].GodTime := Soldier[i].GodTime - 1;
if (Soldier[i].GodTime = 0) then WriteConsole(i,'You are mortal again..',$CC0000);
if (Soldier[i].godcooldown > 0) then begin // cooldown doesn't start until god-mode is over
Soldier[i].godcooldown := Soldier[i].godcooldown - 1;
if (Soldier[i].godcooldown = 0) then WriteConsole(i,'God shield is ready to cast !',$CC0000);
end;
end;
end;
// this goes in your OnPlayerCommand
if regExpMatch('^/(god|shield)$', Text) then begin
if (soldier[ID].level >= 60) then begin
if (soldier[ID].godcooldown = 0) then begin
soldier[ID].GodTime := 20;
soldier[ID].godcooldown := 120;
WriteConsole(ID,'You are invincible for 20 seconds!',$FFFFFF);
end else WriteConsole(ID, 'God shield not ready. ' + inttostr(soldier[ID].godcooldown) + ' seconds remaining', Color);
end else WriteConsole(ID, 'You are not lvl 60 + Or you have too wait until the spell is ready', Color);
end;
-
Same thing ... >:(
Maybe its a error due to AppOnIdle ...
Procedure AppOnIdle(Ticks: Integer);
Var N,i, K: Byte;
X, Y, Dista: Single;
Begin
CheckMines();
for i:= 1 to 32 do if GetPlayerStat(i,'Active') then begin
if (Soldier[i].GodTime > 0) then begin
Soldier[i].GodTime := Soldier[i].GodTime - 1;
if (Soldier[i].GodTime = 0) then WriteConsole(i,'You are mortal again..',$CC0000);
if (Soldier[i].godcooldown > 0) then begin // cooldown doesn't start until god-mode is over
Soldier[i].godcooldown := Soldier[i].godcooldown - 1;
if (Soldier[i].godcooldown = 0) then WriteConsole(i,'God shield is ready to cast !',$CC0000);
AllDraw(i);
Heal(i);
end;
end;
end;
For N := 1 To maxpsg Do Begin
if sgd[n] = True Then Begin
CreateBullet(sgx[n],sgy[n],0,0,0,5,sgo[n]);
For K := 1 To 32 Do Begin
GetPlayerXy(K,X,Y);
if GetPlayerStat(K,'Team') <> sgt[n] Then if GetPlayerStat(K,'Alive') = True Then if RayCast(sgx[n],sgy[n],x,y,dista,psgrang) = True Then if dista <= psgrang Then Begin
x := ((x-sgx[n]) / dista)*psgspee;
y := ((y-sgy[n]) / dista)*psgspee;
CreateBullet(sgx[n],sgy[n],x,y,psgpowa,psgtype,sgo[n]); sga[n]:=sga[n]-1;
if sga[n] = 0 Then Begin
sgd[n] := false;
Writeconsole(sgo[n],'One of your sentry guns ran out of ammo.',$0000FF00);
end;
Break;
end;
end;
end;
end;
end;
-
why are your indentions so weird? note how mine and darkcrusader's work: when there's a BEGIN, the next lines will be indented. the END gets UNindented and stays like that until there's another begin. if there is a BEGIN inside a BEGIN, then you have to indent your code more.
what i want you to do is use that indentation format and look at your code - this should help you figure it out better. If you don't figure it out, show us your code with proper indentations so we can help you better!
-
Mich, you will need to understand how imporant indentations are. Without them your code appears to be scary and (reasonably) unreadable. Hence you will have problems finding simple errors like the error with the redundant 'END'.
Annotation: I don't get why people always call me Dark Crusader when it's meant to be Dark Crusade as I already use it.
-
Guys can you explain with simple word i under syand only 50% of what u said ...
-
Without indentations:
Procedure ClusterSpawnTrigger();
var
Team,Heal:Boolean;
i,ii:Byte;
begin
if (not ClusterInitialized) then Exit;
if (ClusterSpecTeam = 0) then Team := false;
if (ClusterRegen > 0) then Heal := false;
for i := 1 to ClusterRegions do if (ClusterSpawnX[i] <> 0) AND (ClusterSpawnY[i] <> 0) then
for ii := 1 to HighestPlayerID() do if (GetPlayerStat(ii,'Active') = true) then
if (GetPlayerStat(ii,'Alive') = true) AND (GetPlayerStat(ii,'Team') <> 5) then
if (Team) then begin
if (GetPlayerStat(ii,'Team') = ClusterSpecTeam) AND (Distance(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),ClusterSpawnX[i],ClusterSpawnY[i]) <= ClusterRange) then begin
if (Heal) then begin
if (GetPlayerStat(ii,'Health') < 150) then
if (GetPlayerStat(ii,'Health') + ClusterRegen <= 150) then
DoDamage(ii,ClusterRegen)
else
DoDamage(ii,GetPlayerStat(ii,'Health') -150);
end else DoDamage(ii,ClusterRegen);
CreateBullet(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),0,0,0,5,ii);
end;
end else if (Distance(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),ClusterSpawnX[i],ClusterSpawnY[i]) <= ClusterRange) then begin
if (Heal) then begin
if (GetPlayerStat(ii,'Health') < 150) then
if (GetPlayerStat(ii,'Health') + ClusterRegen <= 150) then
DoDamage(ii,ClusterRegen)
else
DoDamage(ii,GetPlayerStat(ii,'Health') -150);
end else DoDamage(ii,ClusterRegen);
CreateBullet(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),0,0,0,5,ii);
end;
end;
With correct indentations:
Procedure ClusterSpawnTrigger();
var
Team,Heal:Boolean;
i,ii:Byte;
begin
if (not ClusterInitialized) then Exit;
if (ClusterSpecTeam = 0) then Team := false;
if (ClusterRegen > 0) then Heal := false;
for i := 1 to ClusterRegions do if (ClusterSpawnX[i] <> 0) AND (ClusterSpawnY[i] <> 0) then
for ii := 1 to HighestPlayerID() do if (GetPlayerStat(ii,'Active') = true) then
if (GetPlayerStat(ii,'Alive') = true) AND (GetPlayerStat(ii,'Team') <> 5) then
if (Team) then begin
if (GetPlayerStat(ii,'Team') = ClusterSpecTeam) AND (Distance(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),ClusterSpawnX[i],ClusterSpawnY[i]) <= ClusterRange) then begin
if (Heal) then begin
if (GetPlayerStat(ii,'Health') < 150) then
if (GetPlayerStat(ii,'Health') + ClusterRegen <= 150) then
DoDamage(ii,ClusterRegen)
else
DoDamage(ii,GetPlayerStat(ii,'Health') -150);
end else DoDamage(ii,ClusterRegen);
CreateBullet(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),0,0,0,5,ii);
end;
end else if (Distance(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),ClusterSpawnX[i],ClusterSpawnY[i]) <= ClusterRange) then begin
if (Heal) then begin
if (GetPlayerStat(ii,'Health') < 150) then
if (GetPlayerStat(ii,'Health') + ClusterRegen <= 150) then
DoDamage(ii,ClusterRegen)
else
DoDamage(ii,GetPlayerStat(ii,'Health') -150);
end else DoDamage(ii,ClusterRegen);
CreateBullet(GetPlayerStat(ii,'X'),GetPlayerStat(ii,'Y'),0,0,0,5,ii);
end;
end;
-
Here is what you have (BAD):
for i := 0 to 20 do begin
if y = 3 then begin
if x = 5 then begin
x := x + 1;
if x > 35 then begin
x := x - 1
end;
end;
end;
Here is what you should have (GOOD):
for i := 0 to 20 do begin
if y = 3 then begin
if x = 5 then begin
x := x + 1;
end;
if x > 35 then begin
x := x - 1
end;
end;
end;
notice after the word "BEGIN" every line is moved to the right and when there is "END" every line goes back left.
I think you don't understand what begin and end do. look at this code:
if x > 0 then begin
x := x - 1;
WriteConsole(ID, x);
end;
the phrase "x > 0" at the beginning is called the conditional. the 2 lines "x := x - 1;" and "WriteConsole(ID, x)" will ONLY be executed if the conditional is met. The computer needs to know what code to execute. the words BEGIN and END show beginning and ending of that code. In the example, if the CONDITIONAL is not true, then the computer will not execute the code that's between the BEGIN and END words!
I hope this makes sense to you.
-
@ DC : You've just added some space O.o ...
@ zyxstand : i understand but wath is that code ? (it is in the script ?)
for i := 0 to 20 do begin
if y = 3 then begin
if x = 5 then begin
x := x + 1;
end;
if x > 35 then begin
x := x - 1
end;
end;
end;
-
DarkCrusade and I showed you the code to put it. I'm sure they'll both work. If it doesn't work, attach your file in your next post and tell us what's wrong. The code that you just showed us earlier didn't have that format and it's hard to help you.
-
Mich, this is not only space. This is what makes your code understandable. It is important to use proper "free space", because you can fix your code easier and understand the code after some time has passed.
-
i will put indentitions tomorow !
when i type /god it always stay to 100
-
Maybe you can put the whole code here again so we can check it?
-
Yeah but there is no identation ... :-\
(And i wanna say thanks to you guys who helped me alot :P)
-
aahhhh...
we are asking you to make your put text after a BEGIN line more to the right and then after END put it back left. use the TAB key on your keyboard to move the text to the right. moving text to the right is called indentation. Do this and then show us your code.
-
Here it is !
i did the indentations !
-
you can move your br variable to constants, and make it
br = #13+#10;
should work, less confusion
-
You don't need to use #13+#10, #13#10 works, too.
-
I'll do it later ! now i wanna know why the counter always stay to 100
-
Hey, I think your indentations are still wrong. This is what you have:
if (Soldier[i].GodTime > 0) then begin
Soldier[i].GodTime := Soldier[i].GodTime - 1;
if (Soldier[i].GodTime = 0) then WriteConsole(i,'You are mortal again..',$CC0000);
if (Soldier[i].godcooldown > 0) then begin // cooldown doesn't start until god-mode is over
Soldier[i].godcooldown := Soldier[i].godcooldown - 1;
if (Soldier[i].godcooldown = 0) then WriteConsole(i,'God shield is ready to cast !',$CC0000);
end;
end;
end;
Correct indentation (but still wrong code:
if (Soldier[i].GodTime > 0) then begin
Soldier[i].GodTime := Soldier[i].GodTime - 1;
if (Soldier[i].GodTime = 0) then WriteConsole(i,'You are mortal again..',$CC0000);
if (Soldier[i].godcooldown > 0) then begin // cooldown doesn't start until god-mode is over
Soldier[i].godcooldown := Soldier[i].godcooldown - 1;
if (Soldier[i].godcooldown = 0) then WriteConsole(i,'God shield is ready to cast !',$CC0000);
end;
end;
The problem is, you need to keep GodTime separate from godcooldown. This is the correct code:
if (Soldier[i].GodTime > 0) then begin
Soldier[i].GodTime := Soldier[i].GodTime - 1;
if (Soldier[i].GodTime = 0) then WriteConsole(i,'You are mortal again..',$CC0000);
end;
if (Soldier[i].godcooldown > 0) then begin // cooldown doesn't start until god-mode is over
Soldier[i].godcooldown := Soldier[i].godcooldown - 1;
if (Soldier[i].godcooldown = 0) then WriteConsole(i,'God shield is ready to cast !',$CC0000);
end;
In your way, it only does the cooldown if the player is also in god-mode (which is wrong). notice how the END word i put in mark the end of the if-statement code.
-
Thanks it work ! ;D
OFF TOPIC(500 post w00t)
-
Congrats!
Don't just use the code - try to understand it!
i also like your spongebob quote ;)
-
Congrats!
Don't just use the code - try to understand it!
i also like your spongebob quote ;)
its in left 4 dead 2 !
when coach say Did you say chocolate ?
From: July 27, 2010, 11:23:53 am
So did a new zombie named 'KaMiKaZe ZoMbIe' and i add a script to it !
there is the script :
function OnPlayerDamage(Victim,Shooter: Byte;Damage: Integer;Weapon: Byte) : integer;
var
X, Y: single;
begin
if GetPlayerStat(Victim,'Name') ='KaMiKaZe ZoMbIe'
then begin
GetPlayerXY(Victim, X, Y);
CreateBullet(X, Y - 10, 0, 0,120, 4, Victim);
CreateBullet(X, Y - 10, 1, 1,120, 4, Victim);
CreateBullet(X, Y - 10, 2, 2,120, 4, Victim);
DoDamage(Victim,4000);
end;
end;
When i join the game it spam me up with that |
|
v
-
Learn to use indentations better. Take this as an example:
Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer; Weapon:Byte):Integer;
var
X,Y:Single;
begin
if GetPlayerStat(Victim,'Name') ='KaMiKaZe ZoMbIe' then begin
GetPlayerXY(Victim, X, Y);
CreateBullet(X, Y - 10, 0, 0,120, 4, Victim);
CreateBullet(X, Y - 10, 1, 1,120, 4, Victim);
CreateBullet(X, Y - 10, 2, 2,120, 4, Victim);
DoDamage(Victim,4000);
end;
end;
2.6.5: Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer):Integer;
3.0: Function OnPlayerDamage(Victim,Shooter:Byte; Damage:Integer; Weapon:Byte):Integer;
You use the wrong server version.
-
How can i disable grenade throw for a bot ?
-
open bot file and make:
Grenade_Frequency=1000
that works for me
-
It d'ont work for me ...
they throw grenade ...
-
change difficulty of bots to "Stupid" if you have other
-
currently the bot difficulty is 50 ... i change it to which number ?
-
just go to Options in Soldat and change Difficulty to STUPID (mark first dot)
-
i want to disable grenade throw not ingame for my server !
-
Difficulty=300
is that hard to find in Soldat.ini?
-
Thanks ! ;D
I got a problem with the nuke skills ...
i want to put that if a player type nuke
money[ID] := money[ID]-60;
xp[ID] := xp[ID]+30;
but if i do this it loop 32 time so its like
-60X32 money ....
+30X32 xp ...
Nuke skills procedure !
procedure Nuke(ID: byte);
begin
if GetPlayerStat(ID,'Human') = False
then begin
if (GetPlayerStat(ID,'Active') = true)
then begin
if (GetPlayerStat(ID,'name') = 'ZoMbIe')
then begin
DoDamage(ID,4000);
end;
end;
end;
end;
if regExpMatch('^/(nuke)$', Text) then
begin
if (soldier[ID].level >= 45) and (soldier[ID].money >= 60) then
begin
For i := 1 to 32 do begin
Nuke(i);
WriteConsole(i, 'NUCLEAR BOMB !', Color);
end;
end else begin
writeconsole(ID, 'You are not lvl 45 + or you dont have enough money.', Color);
end;
end;
-
put
money[ID] := money[ID]-60;
xp[ID] := xp[ID]+30;
before loop, this should work, btw why you use nuke only for zombie? change "name = zombie" to "team = 2" ^^ this should kill all players from bravo team, also change position of getplayerstat(id,'active') with getplayerstat(id,'human'), rememer, first check active, then next "if" questions because that making laggs
-
Its only for zombie cause this will hurt boss ...
Come on my server !
i have currentrly 11 skills
soldat://soldat.no-ip.ca:23098
-
i dont have time to play, im still working hard with my script...
-
Ok i understand !
I wanna know if someone have a barble wire script like in last stand ?