![]() |
Under The HoodThe Stuff That Doesn't ShowWelcome to the second part of our biased and opinionated tour of Cyborg scripts. Let's talk for a moment about structure.
|
I've seen three major schemes for organizing the overall code in users' Cyborg.ipt files:
(Okay, this isn't a complete quotation from the Cyborg.ipt file. Here's why.)
ON SIGNON {
TICKS itk =
botHold GLOBAL
timeBase GLOBAL
debugOn GLOBAL
burning GLOBAL
burnInt GLOBAL
burnCt GLOBAL
facM GLOBAL
altM GLOBAL
twinPW GLOBAL
iptPW GLOBAL
iptOn GLOBAL
autoPos GLOBAL
autoX GLOBAL
autoY GLOBAL
"\x3bwirf" iptPW = ; "\x3b" = semicolon
"\x3bzoik" twinPW =
0 FALSE =
FALSE NOT TRUE =
FALSE debugOn =
DATETIME timeBase =
200 burnInt =
FALSE burning =
0 burnCt =
FALSE autoPos =
0 autoX =
0 autoY =
9 facM =
8 altM =
TRUE iptOn =
; end of global variable initializations
|
That block of GLOBAL declarations is then copied to the INCHAT and OUTCHAT handlers, as well as any Macros etc that might use any of these variables.
The itk variable is NOT global, but something I use to keep track of operations inside of the ON SIGNON block, as we'll see below.After the variables come the shared global subroutines/functions:
; ****************************************
; *** Global Subroutines *****************
; ****************************************
; return # of seconds since signon
time GLOBAL
{
timeBase GLOBAL
DATETIME timeBase -
} time DEF
; number of Guests in current room
count_guests GLOBAL
{
NBRROOMUSERS r =
0 result =
0 i =
{
{ result ++ } i ROOMUSER WHONAME "^Guest " GREPSTR IF
i ++
} { i r < } WHILE
result
} count_guests DEF
; return true if named user is in current room
; <name> find_name EXEC
;
find_name GLOBAL
{
seekName =
NBRROOMUSERS r =
{
0 i =
{
{
1 RETURN
} i ROOMUSER WHONAME seekName == IF
i ++
} { i r < } WHILE
} seekName "" == NOT IF
0
} find_name DEF
; return position of named user is in current room, or own pos if
; not found
; <name> find_pos EXEC
;
find_pos GLOBAL
{
seekName =
NBRROOMUSERS r =
{
0 i =
{
{
i ROOMUSER WHOPOS RETURN
} i ROOMUSER WHONAME seekName == IF
i ++
} { i r < } WHILE
} seekName "" == NOT IF
POSX POSY
} find_pos DEF
;
; ...etc.
; There are quite a few functions here, then a wrapup:
;
TICKS itk - ITOA " Ticks for SIGNON exec" & LOGMSG
}
|
which ends the SIGNON block. The itk timer
variable lets me know how long the entire SIGNON block took
to load, in 1/60th of a second "ticks."
Each OUTCHAT etc handler
then needs to have those global functions declared, too, e.g.,
time GLOBAL
time_log GLOBAL
find_name GLOBAL
count_guests GLOBAL
bot_say GLOBAL
auto_pos GLOBAL
leap_to GLOBAL
glide_to GLOBAL
burn_it GLOBAL
aps GLOBAL
n_prop GLOBAL
costume_set GLOBAL
|
My own habit for naming variables and
the like is to use multiple words with different separators
to name
variablesWithCaps and functions_with_underscores.
Iptscrae ignores case, so don't make the mistake of thinking that,
say, "msX" and "MSX" are different variable names.
(Variables and functions used by the
BotBot are automatically scoped correctly)