! Copyright by Rick Dague,
[email protected]
constant ndead 101;
constant sdead 102;
constant nspass 103;
constant nsbreak 104;
constant edead 105;
constant wdead 106;
constant ewpass 107;
constant ewbreak 108;
constant endcmap 109;
global cmapi = 0;
global cmap_first = 0;
class corner(cmap_alloc)
with
short_name [ i j;
i = cmap_linest(cmapi); j = cmap->cmapi;
if(i <= 100 && j <= 50) {
print (string)cmap_ew-->(i - 51)," & ",(string)cmap_ns-->(j - 1);
} else {
if(i <= 100) print (string)cmap_ew-->(i - 51)," St.";
else print (string)cmap_ns-->(j - 1)," Ave.";
}
rtrue;
],
before [ i;
Go:
i = cmap_cango(noun);
if(i ~= 0) { cmapi = i; playerto(cmap_find()); rtrue; }
],
description [ ; print "On a city street. "; cmap_prexits(); ],
cant_go [ ; cmap_prexits(); ],
nxtcnr 0,
has;
[ cmap_find j i x st;
if(j == 0) j = cmapi;
x = cmap_first;
for(i = 0: i <= j: ++i) {
switch(cmap->i) {
1 to 50,edead,wdead,ewpass:
if(st == nsbreak) break;
if(i == j) return x;
x = x.nxtcnr;
ewbreak: ;
default: st = cmap->i;
}
}
cmapi = j;
cmap_err(0,"not a valid corner");
];
[ cmap_prexits dir dir1 ct;
objectloop(dir in compass)
if(cmap_cango(dir)) {
if(++ct > 1) {
if(ct == 2) print "Exits are "; else print ", ";
print (directionname)dir1;
}
dir1 = dir;
}
if(ct == 1) print "An exit is "; else print " and ";
print (directionname)dir1,".^";
];
[ cmap_err b s;
if(b == 0) {
print "error in cmap->",cmapi," == ",cmap->cmapi,": ",(string)s;
new_line; quit;
}
];
[ cmap_linest i x;
do { x = (cmap->--i)&$7f;
} until(50 < x && x <= nsbreak);
return x;
];
[ cmap_cango dir x st i;
x = cmap->cmapi;
st = cmap_linest(cmapi);
if(dir == n_obj) {
if(st == ndead || x > nsbreak) rfalse;
i = cmapi;
do { if(i == 0) rfalse;
} until(cmap->--i == x);
if(cmap_linest(i) == nsbreak or sdead) rfalse;
}
if(dir == s_obj) {
if(st == sdead || x > nsbreak) rfalse;
i = cmapi;
do { if(cmap->++i == endcmap) rfalse;
} until(cmap->i == x);
if(cmap_linest(i) == nsbreak or ndead) rfalse;
}
if(dir == e_obj) {
i = cmapi + 1;
if(x == edead || st > 100) rfalse;
x = cmap->i;
if(x == endcmap or wdead or ewbreak || (50 < x && x <= nsbreak))
rfalse;
}
if(dir == w_obj) {
i = cmapi - 1;
if(x == wdead || st > 100 || cmap->i == st or edead or ewbreak)
rfalse;
}
return i;
];
[ cmap_check x i st n s e w;
cmapi = 0;
cmap_err(51 <= cmap->0 && cmap->0 <= nsbreak,
"cmap->0 must be an east-west number or ndead, sdead, nspass");
for(cmapi = 0: : ++cmapi) {
x = cmap->cmapi;
cmap_err(1 <= x && x <= endcmap,"cmap value out of range");
if(x == endcmap) break;
if(51 <= x && x <= nsbreak) {
st = x;
for(i = cmapi + 1: cmap->i ~= endcmap: ++i)
cmap_err(cmap->i ~= x,"duplicated east-west row");
} else cmap_err(x <= 50 || st <= 100,"edead, wdead, ewpass and
ewbreak can only be used with an east-west row");
}
for(cmapi = 0: : ++cmapi) {
x = cmap->cmapi;
if(x == endcmap) break;
if(51 <= x && x <= nsbreak) st = x;
else {
if(x ~= ewbreak && st ~= nsbreak) {
n = cmap_cango(n_obj); s = cmap_cango(s_obj);
e = cmap_cango(e_obj); w = cmap_cango(w_obj);
switch(x) {
edead: cmap_err(w ~= 0,"need west exit");
wdead: cmap_err(e ~= 0,"need east exit");
ewpass: cmap_err(w ~= 0 && e ~= 0,"need both east and west exits");
default:
switch(st) {
ndead: cmap_err(n ~= 0,"need north exit");
sdead: cmap_err(s ~= 0,"need south exit");
nspass: cmap_err(n ~= 0 && s ~= 0,"need both north and south exits");
default: cmap_err((n ~= 0 || s ~= 0) && (e ~= 0 || w ~= 0),
"need both (north or south) and (east or west) exits");
}
}
}
}
}
cmap_first = 0;
];
[ cmap_create i b x st top first;
for(i = 0: : ++i) {
switch(cmap->i) {
endcmap: jump DONE;
1 to 50,edead,wdead,ewpass:
if(st == nsbreak) break;
if(b ~= 0) { ++b; break; }
x = corner.create();
if(x == 0) { ++b; break; }
jump INSERT;
ewbreak: ;
128 to 255:
cmap->i = cmap->i - 128;
x = cmap_first;
cmap_first = cmap_first.nxtcnr;
INSERT; if(top ~= 0) top.nxtcnr = x; else first = x;
top = x;
default: st = x;
}
}
DONE;
if(b ~= 0) {
print "error in cmap: need to set cmap_alloc to ",cmap_alloc + b;
new_line; quit;
}
cmap_first = first;
];
[ cmap_static cnr i x;
cmapi = i;
x = cmap->i;
cmap_err(x < 128,"a static already assigned");
for(i = cmap_first: i ~= 0: i = i.nxtcnr)
if(i == cnr) {
print "error in cmap: ",(name)cnr," re static-ed";
new_line; quit;
}
if(x < 51) cmap_err(cmap_linest(cmapi) ~= nsbreak,"not a valid corner");
else cmap_err(x ~= ewbreak,"not a valid corner");
cmap->cmapi = x + 128;
cnr.nxtcnr = cmap_first;
x = cnr;
for(i = 0: i < cmapi: ++i)
if(cmap->i >= 128) x = x.nxtcnr;
if(x == cnr) cmap_first = x;
else { cnr.nxtcnr = x.nxtcnr; x.nxtcnr = cnr; }
];