Sandstorm
12-10-2008, 05:19 AM
Functions. Creating them, using them.
Table of Contents:
Introduction.
Creating a function.
Turning a procedure into a function.
Starting from scratch
Using the returned result in a script.
Conclusion.
Introduction:
*Note - I know my standards are a little off, so don't quote me on them.
Functions. For a long while, I had no idea what they were or how they were used. After I learned, I found them to be VERY useful.
Functions have many uses, from returning True/False in a While Do statement, to finding the midpoint of a set of numbers.
A function is basically a procedure that returns a result. This result can be used to do just about anything, as long as the types are the same.
Here's an example of what a Function is:
Function IsLog(InvSpot : integer) : Boolean;
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85;
End;
This is an excerpt from my Firemaking script. What it does is it checks if the number of black dots in a given area is 85. If it is, then it returns true, if not, then it returns false.
The things that really make a function a function, are these two lines, as they are the only two that are unique to functions:
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
Let's break it down now.
Function - Tells the script it's a function, and it can return a value.
IsLog(InvSpot : integer) - Same as a procedure would use. Declares the name and parameters.
: Boolean; - Tells the script the result will be a boolean
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
Result := - Declares what the Result will be. Makes the function return whatever is after this line.
CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; - Counts the number of dots with the color 65536 in the specified area. If it equals 85, then the function returns true. If not, it returns false.
More on this later.
Creating a function.
Creating a function is actually very similar to creating a procedure, with one main difference. A function frees up a variable.
There's two main things you can do to make a Function. Turn a procedure into a function (only if you use a variable to check something later on, in the procedure), and start from scratch.
I'll start with turning a procedure into a function:
Program New;
{.include srl/srl.scar}
Var
I : Boolean;
Procedure IsLog(InvSpot : integer); //Declares it as a Procedure
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
I := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the I, be it true or false.
End;
Begin
SetupSrl;
IsLog(1)
If I Then
WriteLn('It''s a log!');
End.
Let's turn that into the function I posted earlier.
To do that, we need to change a few things:
First of all, we need to let the script know that it's a Function, not a Procedure:
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
I := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
End;
Second, we need to add in the use of Result:
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
End;
Next, we have to remove the variable I, as it isn't used, and instead put IsLog in there:
Program New;
{.include srl/srl.scar}
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
End;
Begin
SetupSrl;
If IsLog(1) Then //Runs the IsLog Function, and checks if there's a log in slot one or not.
WriteLn('It''s a log!');
End.
It looks sleeker, doesn't it? There's also one less global variable in use, and I believe that saves memory.
Now, let's focus on creating a function from scratch.
To start, you want to decide on a name, and what it will return, plus if it has parameters. Let's call it NewFunction, and we'll make it return an integer, and we'll make it have two parameters, X1, and Y1, which will both be integers.
Function NewFunction(X1, Y1 : Integer) : Integer;
Begin
End;
Now, we have to decide what we want it to do. To start, let's make it return the middle of the two parameters.
To do that, we want to tell it that the result equals the middle of the two parameters. The math formula for that is X1 + Y1 / 2 = Result. To implement that into scar, we need to add a variable, because scar is picky about the way it uses math.
For example:
Function NewFunction(X1, Y1 : Integer) : Integer;
Begin
Result := X1 + Y1 / 2;
End;
Will return a different value then this, which is the working function:
Function NewFunction(X1, Y1 : Integer) : Integer;
Var
P : Integer;
Begin
P := X1 + Y1; //Makes P equal X1 + Y1.
Result := P / 2; //Makes the Function return X1 + Y1 / 2.
End;
And there you go. You have a fully working function that will tell you the middle of two integers.
How to use the value of a Function in a script.
Using the result of a function in a script is not all that different then using a Variable, except that you don't have to set the variable every time it needs to be changed, you just call the function again, and it will adjust if it needs to.
Let's use the example function we made in the last section.
Currently, we have this, or something like it (strictly speaking, we don't need to include srl for this to work, but I like to get into the habit of including it):
Program New;
{.include srl/srl.scar}
Function NewFunction(X1, Y1 : Integer) : Integer;
Var
P : Integer;
Begin
P := X1 + Y1; //Makes P equal X1 + Y1.
Result := P / 2; //Makes the Function return X1 + Y1 / 2.
End;
Begin
SetupSrl;
End.
But that isn't enough to get it to return a value!
To do that, we need to call the function, which may sound just like a procedure, but they aren't called in the same way at all.
If we were to use that as a procedure, and have it return the finished product to the variable I, we would need to do this:
NewFunction(10, 20);
WriteLn(IntToStr(I));
But functions don't use a variable that you declare, so you use them like this:
WriteLn(IntToStr(Newfunction(10, 20)));
It does the same thing, but saves some space and saves a variable.
In the end, you should have something like this:
Program New;
{.include srl/srl.scar}
Function NewFunction(X1, Y1 : Integer) : Integer;
Var
P : Integer;
Begin
P := X1 + Y1; //Makes P equal X1 + Y1.
Result := P / 2; //Makes the Function return X1 + Y1 / 2.
End;
Begin
SetupSrl; //Sets up srl, not needed.
WriteLn(IntToStr(Newfunction(10, 20))); //Calls the NewFunction function, and writes in what the result of it is.
End.
Conclusion:
Functions can be used for many different things, from checking if a screen is up, to seeing if it's time to run a procedure. The result can be many different types, from strings and integers, to booleans and variants.
All things considered, my opinion is that Functions are better than Procedure in some cases. I hope you came out of this tutorial having learned something, even if you won't use it in your scripts.
I hope you now know how to create and use a function, as well as change a procedure into a function.
~Sandstorm
P.S. - This was written at 10 at night, so if theres any errors, please point them out :).
Table of Contents:
Introduction.
Creating a function.
Turning a procedure into a function.
Starting from scratch
Using the returned result in a script.
Conclusion.
Introduction:
*Note - I know my standards are a little off, so don't quote me on them.
Functions. For a long while, I had no idea what they were or how they were used. After I learned, I found them to be VERY useful.
Functions have many uses, from returning True/False in a While Do statement, to finding the midpoint of a set of numbers.
A function is basically a procedure that returns a result. This result can be used to do just about anything, as long as the types are the same.
Here's an example of what a Function is:
Function IsLog(InvSpot : integer) : Boolean;
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85;
End;
This is an excerpt from my Firemaking script. What it does is it checks if the number of black dots in a given area is 85. If it is, then it returns true, if not, then it returns false.
The things that really make a function a function, are these two lines, as they are the only two that are unique to functions:
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
Let's break it down now.
Function - Tells the script it's a function, and it can return a value.
IsLog(InvSpot : integer) - Same as a procedure would use. Declares the name and parameters.
: Boolean; - Tells the script the result will be a boolean
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
Result := - Declares what the Result will be. Makes the function return whatever is after this line.
CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; - Counts the number of dots with the color 65536 in the specified area. If it equals 85, then the function returns true. If not, it returns false.
Creating a function.
Creating a function is actually very similar to creating a procedure, with one main difference. A function frees up a variable.
There's two main things you can do to make a Function. Turn a procedure into a function (only if you use a variable to check something later on, in the procedure), and start from scratch.
I'll start with turning a procedure into a function:
Program New;
{.include srl/srl.scar}
Var
I : Boolean;
Procedure IsLog(InvSpot : integer); //Declares it as a Procedure
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
I := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the I, be it true or false.
End;
Begin
SetupSrl;
IsLog(1)
If I Then
WriteLn('It''s a log!');
End.
Let's turn that into the function I posted earlier.
To do that, we need to change a few things:
First of all, we need to let the script know that it's a Function, not a Procedure:
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
I := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
End;
Second, we need to add in the use of Result:
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
End;
Next, we have to remove the variable I, as it isn't used, and instead put IsLog in there:
Program New;
{.include srl/srl.scar}
Function IsLog(InvSpot : integer) : Boolean; //Declares it as a function.
Var
P : Tbox;
Begin
GetInvItemBounds(InvSpot, p);
Result := CountColor(65536, p.x1, p.y1, p.x1+34, p.y1+27) = 85; //Returns the value of the function, be it true or false.
End;
Begin
SetupSrl;
If IsLog(1) Then //Runs the IsLog Function, and checks if there's a log in slot one or not.
WriteLn('It''s a log!');
End.
It looks sleeker, doesn't it? There's also one less global variable in use, and I believe that saves memory.
Now, let's focus on creating a function from scratch.
To start, you want to decide on a name, and what it will return, plus if it has parameters. Let's call it NewFunction, and we'll make it return an integer, and we'll make it have two parameters, X1, and Y1, which will both be integers.
Function NewFunction(X1, Y1 : Integer) : Integer;
Begin
End;
Now, we have to decide what we want it to do. To start, let's make it return the middle of the two parameters.
To do that, we want to tell it that the result equals the middle of the two parameters. The math formula for that is X1 + Y1 / 2 = Result. To implement that into scar, we need to add a variable, because scar is picky about the way it uses math.
For example:
Function NewFunction(X1, Y1 : Integer) : Integer;
Begin
Result := X1 + Y1 / 2;
End;
Will return a different value then this, which is the working function:
Function NewFunction(X1, Y1 : Integer) : Integer;
Var
P : Integer;
Begin
P := X1 + Y1; //Makes P equal X1 + Y1.
Result := P / 2; //Makes the Function return X1 + Y1 / 2.
End;
And there you go. You have a fully working function that will tell you the middle of two integers.
How to use the value of a Function in a script.
Using the result of a function in a script is not all that different then using a Variable, except that you don't have to set the variable every time it needs to be changed, you just call the function again, and it will adjust if it needs to.
Let's use the example function we made in the last section.
Currently, we have this, or something like it (strictly speaking, we don't need to include srl for this to work, but I like to get into the habit of including it):
Program New;
{.include srl/srl.scar}
Function NewFunction(X1, Y1 : Integer) : Integer;
Var
P : Integer;
Begin
P := X1 + Y1; //Makes P equal X1 + Y1.
Result := P / 2; //Makes the Function return X1 + Y1 / 2.
End;
Begin
SetupSrl;
End.
But that isn't enough to get it to return a value!
To do that, we need to call the function, which may sound just like a procedure, but they aren't called in the same way at all.
If we were to use that as a procedure, and have it return the finished product to the variable I, we would need to do this:
NewFunction(10, 20);
WriteLn(IntToStr(I));
But functions don't use a variable that you declare, so you use them like this:
WriteLn(IntToStr(Newfunction(10, 20)));
It does the same thing, but saves some space and saves a variable.
In the end, you should have something like this:
Program New;
{.include srl/srl.scar}
Function NewFunction(X1, Y1 : Integer) : Integer;
Var
P : Integer;
Begin
P := X1 + Y1; //Makes P equal X1 + Y1.
Result := P / 2; //Makes the Function return X1 + Y1 / 2.
End;
Begin
SetupSrl; //Sets up srl, not needed.
WriteLn(IntToStr(Newfunction(10, 20))); //Calls the NewFunction function, and writes in what the result of it is.
End.
Conclusion:
Functions can be used for many different things, from checking if a screen is up, to seeing if it's time to run a procedure. The result can be many different types, from strings and integers, to booleans and variants.
All things considered, my opinion is that Functions are better than Procedure in some cases. I hope you came out of this tutorial having learned something, even if you won't use it in your scripts.
I hope you now know how to create and use a function, as well as change a procedure into a function.
~Sandstorm
P.S. - This was written at 10 at night, so if theres any errors, please point them out :).