PDA

View Full Version : Advanced failsafe tutorial(for noobs and leet scripters alike)



elementalelf
09-11-2007, 06:27 AM
hey guys, i think i better start giving back alot more to the community to earn the auto-memberizing i got, so i decided to make this tutorial on advanced failsafing.

firstly: this is quite an easy skill to master, its pretty basic coding, and only requires you to think logically, anyone with more then 2 months scar experience will be able to make one of these in under 20 minutes.

ok, onto the tutorial.
ill start off with a basic example of a failsafe:


procedure failsafing;
var counter:integer;
begin
repeat
wait(500);
counter:=counter+1;
until(getcolor(523,235)=244) or (counter=20);
end;

ok, so, breaking this down.

procedure failsafing; //procedure name, everyone knows this
var counter:integer; //declaring the variables, the counter variable should always be a private variable, i.e. inside the script
begin //beginning the procedure
repeat //start of a repeat. note: you only need to use failsafes on repeat/while/for commands
wait(500); //a wait time, this is mainly so it doesnt lag out
counter:=counter+1; //this is to count the number of times it waits
until(getcolor(523,235)=244) or (counter=20); //the failsafe. every time the loop is executed, it'll check if there is color 244(red) at location 523,235. if there is not, it will repeat the loop until the loop is repeated 20 times, as seen by the (counter = 20) command
end; //basic procedure end command


ok, so, we are all up to date on basic failsafes.

after the basics, before the advanced:

the problem with the failsafe above, is that in the event that the counter hits 20, the script will go on to the next part even though it really hasnt completed this part.
if this happens, the script will most likely screw up, as it will try to, say, mine a rock while its sitting in a bank.

so!
we put an if(fail safe is reached)then terminatescript;
which is as easy as it looks just there.

procedure failsafing;
var counter:integer;
begin
repeat
wait(500);
counter:=counter+1;
until(getcolor(523,235)=244) or (counter=20);
if(counter=20)then
terminatescript;
end;

terminatescript is an SRL command that does exactly what it says.
alternativly if you are making a multilogin script, you could use this:

procedure failsafing;
var counter:integer;
begin
repeat
wait(500);
counter:=counter+1;
until(getcolor(523,235)=244) or (counter=20);
if(counter=20)then
players[current].active:=false;
nextplayer;
end;

note: im quite rusty with arrays so im pretty sure i did that wrong, if i did, just post here the correct code and ill fix it up.

what this does is:
if the character failed the failsafe(i.e. did not find color 244 at 523,235) then it will disable that character, then log out and run the script on the next character like normal.
every time its the "failed" characters turn to auto, it will automatically skip to the next one

__________________________________________________ ___________

ADVANCED FAILSAFES!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!

__________________________________________________ ___________

EDIT: i just realised that i made a mistake in my talkguy procedure... ill fix it in a second

ok, enough with the basics.

the idea behind advanced failsafes is that even if the procedure fails, the script will still be able to function without terminating that particular character.
ill give you the example i am working on in my tutorial island runner.

procedure findguy(tehtext1,tehtext2,tehtext3:string);
var clll,countr: integer;
heheheheh: boolean;
begin
writeln('beggining findguy');
repeat
wait(50);
countr:=countr+1;
until(myFindObjectdeformed(lulx,luly,tehtext1,teht ext2,tehtext3,lulbmp,msx1,msy1,msx2,msy2)) or (countr=100);
if(countr=100)then
begin
miniwalk;
findguy(tehtext1,tehtext2,tehtext3);
end else
mouse(lulx,luly,1,1,true);
writeln('found the guy');
repeat
wait(300);
clll := clll + 1;
if (findnpcchattext('tinue')) or (findnpcchattext('cook')) then heheheheh := true;
until (heheheheh = true) or (clll = 10);
if (heheheheh = false)
then
begin
wait(500);
findguy(tehtext1,tehtext2,tehtext3);
end;
cha1:=tehtext1;
cha2:=tehtext2;
cha3:=tehtext3;
end;

procedure talkguy;
var countr:integer;
begin
repeat;
if (clicktocontinue)
then
begin
clicktocontinue;
wait(50);
mmouse(300, 300, 120, 120);
repeat
wait(100);
countr:=countr+1;
until (not(findnpcchattext('ait'))) or (countr=15);
end else
begin
wait(100);
findguy(cha1,cha2,cha3);
talkguy;
exit;
end;
end; //note: this is not the real end of the script, this end; is only here because the rest of the procedure takes up about 100 lines and really doesnt do anything of interest to you guys

put simply:

procedure findguy(tehtext1,tehtext2,tehtext3:string);
var clll,countr: integer;
heheheheh: boolean;

basic stuff here
[/scar]


begin
writeln('beggining findguy');

this is a little trick if your script hangs, to find out exactly where it gets up to

repeat
wait(50);
countr:=countr+1;
until(myFindObjectdeformed(lulx,luly,tehtext1,teht ext2,tehtext3,lulbmp,msx1,msy1,msx2,msy2)) or (countr=100);

basic failsafe.

if(countr=100)then
begin
miniwalk;
findguy(tehtext1,tehtext2,tehtext3);

HERE is the Advanced failsafing.
as you can see, if the failsafe(countr=100) is tripped, then the script will automatically find the place on the minimap where the thing that it wants should be, gets closer to him, and attempts to find him again.
usually this failsafe requires a failsafe of its own, as it to can start an endless loop, unless you have made the procedures good enough to be pretty much 99% accurate

end else
mouse(lulx,luly,1,1,true);
writeln('found the guy');
repeat
wait(300);
clll := clll + 1;
if (findnpcchattext('tinue')) or (findnpcchattext('cook')) then heheheheh := true;
until (heheheheh = true) or (clll = 10);
if (heheheheh = false)
then
begin
wait(500);
findguy(tehtext1,tehtext2,tehtext3);
end;
cha1:=tehtext1;
cha2:=tehtext2;
cha3:=tehtext3;
end;

the rest of the stuff you dont really need to worry about. there is another advanced failsafe in there somewhere in case the script clicks on the guy but the guy moves and the script detects that he isnt talking to him.

The Claw
09-11-2007, 07:30 AM
Pretty nice tutorial, I was thinking of doing something like this :)

For this part:

players[current].active:=false;
nextplayer;

you did get the arrays messed up, its meant to be Players[CurrentPlayer] instead. But you could just do NextPlayer(False), which would automatically set the players status to false.

another way to do failsafes is TimeFromMarks. essentially, they are the same thing as counters, just instead of executions it depends (obviously) on time. you can use them like this:

MarkTime(YourTime);
repeat
Stuff
if MoreStuff then zzzz := True;
until zzzz or TimeFromMark(YourTime) > 60000;

YourTime is an integer. So it repeats everything until it acheives what it wants, or until a minute of trying is up :)

~alex~
09-11-2007, 07:43 AM
Nice tutorial but your standards are awfull >.<

BobboHobbo
09-11-2007, 08:13 AM
Ye good TUT use capital letters for some letters, looks neater.

elementalelf
09-11-2007, 08:42 AM
yes, i realise i have terrible CamelCaps, its a problem i will have to remedy.

TheClaw: ive always shied away from real time orientated scripting. it makes the script alot more unstable if say, the server is lagging badly.

heres a challenge(albiet quite a simple one)
this one is a purely logical challenge, see if you can see whats wrong with this part of the script:

if(countr=100)then
begin
miniwalk;
findguy(tehtext1,tehtext2,tehtext3);

although it will run, something will happen that will screw up the script if 1 line is not put in.

hint: the line that needs to be put in is 5 chars long(thats including the semicolon)

Santa_Clause
09-11-2007, 10:25 AM
You forgot:

Flag;

;)

elementalelf
09-11-2007, 10:58 AM
miniwalk has flag built in :)
findguy has repeat until(findnpcchattext('lick here'));

any other takers?

ZephyrsFury
09-11-2007, 12:38 PM
terminatescript is an SRL command that does exactly what it says.


TerminateScript is a in-built SCAR command. ;) And yea your standards are horrible. Other than that good tut :D.

Santy, what did you do to your avatar?..:rolleyes:.

elementalelf
09-11-2007, 08:24 PM
zephyr: you are right, it is an inbuilt scar command... my bad.

for all those out there... the missing line was exit;

Kik
09-11-2007, 10:19 PM
Yeah, work on standards, but otherwise it's a good tut for people who don't know what failsafing is. Maybe at beginning give a little definition of what failsafes are and why to use 'em?

And you might want to add something about for to do loops, using break and exit, but that's just a suggestion.

Good tutorial.

Santa_Clause
09-13-2007, 03:58 AM
zephyr: you are right, it is an inbuilt scar command... my bad.

for all those out there... the missing line was exit;

You can't really tell what you need to put when you only have 3 lines there.

elementalelf
09-13-2007, 04:21 AM
i have the entire procedure as a whole above it :)

brad734
09-22-2008, 06:09 AM
thanks a million

Tom_Gower
11-07-2008, 09:40 AM
Im having trouble with one certain part of a procedure, with else, its saying i need an identifiyer wtf?
procedure MineCopper;
var
Copper: Boolean;
Tin: Boolean;
begin
if(not(LoggedIn)) then
Exit;
repeat
if(FindColorSpiralTolerance(x, y, CopperColour, MSX1, MSY1,MSX2, MSY2, 3)) or
(FindColorSpiralTolerance(x, y, CopperColour1, MSX1, MSY1,MSX2, MSY2, 3)) then
Copper:= True;
if(Copper = False) then
TerminateScript;
else
begin
MMouse(x, y, 5, 5);
if(IsUpText('ine')) then
begin
Wait(3000);
Mouse(x, y, 2, 2, True);
Wait(3000);
Writeln('Found Copper');
Randoms;
end;
end;
until(invfull);
end;
Any help would be greatly appreciated

SirPa
11-07-2008, 09:52 AM
This should fix it:


if(Copper = False) then
begin
TerminateScript;
end
else


After then's, always use begin and end (learned this myself yesterday ;) )

ZephyrsFury
11-07-2008, 02:04 PM
This should fix it:


if(Copper = False) then
begin
TerminateScript;
end
else


After then's, always use begin and end (learned this myself yesterday ;) )

No not necessarily. The cause of the identifier expected error is the semicolon before the else statement.


if(Copper = False) then
TerminateScript //There can't be a semicolon here
else



Using the begin and end just bypasses the problem. :)

SirPa
11-07-2008, 02:37 PM
Really? AH! SO that's maybe what's wrong with my script then ;) Thanks