1
0
mirror of https://github.com/dschmenk/PLASMA.git synced 2024-11-08 06:09:15 +00:00

Fix some compiler bugs for Rogue combat updates

This commit is contained in:
David Schmenk 2014-12-25 19:54:48 -08:00
parent 79ccb3f676
commit 69b5666afc
6 changed files with 300 additions and 170 deletions

View File

@ -11,6 +11,7 @@ ROD = ROD\#FE1000
SIEVE = SIEVE\#FE1000
ROGUE = ROGUE\#FE1000
ROGUEMAP= ROGUEMAP\#FE1000
ROGUECOMBAT= ROGUECOMBAT\#FE1000
HELLO = HELLO\#FE1000
HGR1 = HGR1\#FE1000
HGR1TEST= HGR1TEST\#FE1000
@ -36,7 +37,7 @@ TXTTYPE = .TXT
#SYSTYPE = \#FF2000
#TXTTYPE = \#040000
all: $(PLASM) $(PLVM) $(PLVM01) $(PLVM02) $(PLVM03) $(CMD) $(PROFILE) $(ED) $(SB) $(ROD) $(SIEVE) $(ROGUE) $(ROGUEMAP) $(HGR1)
all: $(PLASM) $(PLVM) $(PLVM01) $(PLVM02) $(PLVM03) $(CMD) $(PROFILE) $(ED) $(SB) $(ROD) $(SIEVE) $(ROGUE) $(ROGUEMAP) $(ROGUECOMBAT) $(HGR1)
clean:
-rm *FE1000 *FF2000 $(PLASM) $(PLVM) $(PLVM01) $(PLVM02) $(PLVM03)
@ -105,6 +106,10 @@ $(ROGUE): samplesrc/rogue.pla $(PLVM02) $(PLASM)
./$(PLASM) -AM < samplesrc/rogue.pla > samplesrc/rogue.a
acme --setpc 4094 -o $(ROGUE) samplesrc/rogue.a
$(ROGUECOMBAT): samplesrc/rogue.combat.pla $(PLVM02) $(PLASM)
./$(PLASM) -AM < samplesrc/rogue.combat.pla > samplesrc/rogue.combat.a
acme --setpc 4094 -o $(ROGUECOMBAT) samplesrc/rogue.combat.a
$(ROGUEMAP): samplesrc/rogue.map.pla $(PLVM02) $(PLASM)
./$(PLASM) -AM < samplesrc/rogue.map.pla > samplesrc/rogue.map.a
acme --setpc 4094 -o $(ROGUEMAP) samplesrc/rogue.map.a

View File

@ -0,0 +1,208 @@
import STDLIB
predef syscall, call, memset, getc, putc, puts, putln
predef memset, memcpy
predef heapmark, heapallocallign, heapalloc, heaprelease, heapavail
byte MACHID
end
import ROGUEMAP
predef puti, toupper, moveplayer
word rnd, getkb, home, gotoxy, tone
end
struc t_pos
byte xpos
byte ypos
end
//
// Player
//
struc t_player
byte[t_pos]
byte angle
byte lamp
byte fov
byte skill
byte health
byte energy
word oil
byte gold
byte key
byte[32] name[32]
end
//
// Other monsters
//
struc t_other
byte[t_pos]
byte kind
byte tileid
byte life
byte power
word prev_other
word next_other
end
//
// ASCII Enemy Art
//
byte[] ascii_thief
byte = " "
byte = " "
byte = " ____ "
byte = " /o_o\\\\ "
byte = "| \\ = // "
byte = "T /###|\\\\ "
byte = "@==###||| "
byte = " xxx@// "
byte = " #|#|\\\\ "
byte = " #|#| \\\\"
byte[] ascii_ogre
byte = " :^; "
byte = " @ }\"{ "
byte = " # /'\\ "
byte = " ##=<#>=##"
byte = " ===== #"
byte = " \\===/ ?"
byte = " ===== :"
byte = " ()^() :"
byte = " () () *"
byte = " {{} {}} "
byte[] ascii_zombie
byte = " \\\\/ "
byte = " {o|0} "
byte = " { ^ } "
byte = " ### "
byte = " /:\\ "
byte = " /%%%%%\\ "
byte = "|%%%//%%|\\"
byte = "|%%%\\%%%||"
byte = "|%%//%%%/|"
byte = "<===|@___/"
byte[] ascii_rogue
byte = " | "
byte = " T "
byte = " \\ () "
byte = " \\^ "
byte = " #\\_] "
byte = " # ] "
byte = " /\\ "
byte = " / \\ "
byte = " / / "
byte = " = = "
word ascii_entity = @ascii_thief, @ascii_ogre, @ascii_zombie, @ascii_rogue
//
// Monster types
//
byte thief = "Thief", 5
byte ogre = "Ogre", 15
byte zombie = "Zombie", 25
byte rogue = "Rogue", 50
export word entity = @thief, @ogre, @zombie, @rogue
export word entities = 0
//
// Combat status strings
//
byte skillstr = "Skill :"
byte healthstr = "Health :"
byte energystr = "Energy :"
byte powerstr = "Power :"
byte lifestr = "Life :"
byte fightstr = "F)ight or R)un?"
//
// Combat Return 1 if running away, 0 if end of fight
//
def win
tone(30, 15)
tone(5, 15)
tone(5, 15)
tone(30, 5)
end
export def fight(player, enemy)
word p_atck, e_atck
repeat
home()
gotoxy(0, 0)
puts(player+name)
gotoxy(1, 2)
puts(@skillstr); puti(player->skill)
gotoxy(1, 3)
puts(@healthstr); puti(player->health)
gotoxy(1, 4)
puts(@energystr); puti(player->energy)
gotoxy(20, 0)
puts(entity[enemy->kind])
gotoxy(21, 2)
puts(@powerstr); puti(enemy->power)
gotoxy(21, 3)
puts(@lifestr); puti(enemy->life)
for e_atck = 0 to 9
gotoxy(20, 10 + e_atck)
puts(ascii_entity[enemy->kind] + e_atck * 11)
next
gotoxy(12, 8); puts(@fightstr)
if toupper(getkb()) == 'R'
return 1
else
//
// Turn player in random direction
//
player->angle = rnd() & 7
//
// Calculate attack (with a little random variation)
//
p_atck = player->skill + player->energy / 10 - enemy->power / 25 + (rnd() & 7)
e_atck = enemy->power - player->skill / 5 - player->energy / 20 + (rnd() & 7)
if enemy->life > p_atck
enemy->life = enemy->life - p_atck
else
win
enemy->life = 0
p_atck = player->skill + enemy->power / 3
if p_atck > 100 // Limit skill
p_atck = 100
fin
player->skill = p_atck
//
// Unlink dead enemy from entities list
//
if enemy == entities
entities = enemy=>next_other
fin
if enemy=>next_other
enemy=>next_other=>prev_other = enemy=>prev_other
fin
if enemy=>prev_other
enemy=>prev_other=>next_other = enemy=>next_other
fin
fin
if player->health > e_atck
player->health = player->health - e_atck
else
player->energy = 0
player->health = 0
fin
if player->energy >= 4
player->energy = player->energy - 4
fin
fin
until player->health == 0 or enemy->life == 0
return 0
end
done

View File

@ -216,7 +216,7 @@ end
def a2tone(duration, delay)
byte i
while duration
^SPEAKER
for i = 0 to delay
@ -227,8 +227,8 @@ end
def a3tone(duration, pitch)
byte env
env = ^ENV_REG
env = ^ENV_REG
^ENV_REG = env | $C0
a2tone(duration, pitch)
^ENV_REG = env
@ -240,7 +240,7 @@ end
def dev_status(devnum, code, list)
byte params[5]
params.0 = 3
params.1 = devnum
params.2 = code
@ -284,6 +284,23 @@ def a2gotoxy(x, y)
return call($FB5B, y + ^$22, 0, 0, 0)
end
export def puti(i)
if i < 0; putc('-'); i = -i; fin
if i < 10
putc(i + '0')
else
puti(i / 10)
putc(i % 10 + '0')
fin
end
export def toupper(c)
if c >= 'a' and c <= 'z'
c = c - $20
fin
return c
end
//
// Load map
//
@ -308,7 +325,7 @@ end
export def setmaptile(xmap, ymap, tile)
word imap
imap = (ymap << 5) + xmap + 1
map[imap] = tile
if ^(viewmap + imap) <> $A0
@ -332,7 +349,7 @@ end
export def lighttorches
word imap, tmap
byte xmap, ymap, xt, yt
for ymap = 1 to maprows - 2
for xmap = 2 to mapcols - 2
imap = (ymap << 5) + xmap
@ -345,7 +362,7 @@ export def lighttorches
next
fin
next
next
next
end
//

View File

@ -32,10 +32,16 @@ import ROGUEMAP
const INV_TILE = $3F
const MAP_TILE = $7F
predef puti, toupper
predef loadmap, getmaptile, setmaptile, updtmaptile, lighttorches, drawmap, drawvisentity
word rnd, getkb, home, gotoxy, tone
end
import ROGUECOMBAT
predef fight
word entity, entities
end
const FALSE = 0
const TRUE = not FALSE
@ -46,6 +52,7 @@ word xdir = 0, 1, 1, 1, 0, -1, -1, -1
word ydir = -1, -1, 0, 1, 1, 1, 0, -1
byte vplayer = '^', '\\', '>', '/', 'v', '\\', '<', '/'
byte totaldarkness = 0
//
// Power-ups
//
@ -53,6 +60,7 @@ byte totaldarkness = 0
const TORCH_OIL = 250
const MANA = 50
const RUN_ENERGY = 4
struc t_pos
byte xpos
byte ypos
@ -105,17 +113,6 @@ struc t_other
word next_other
end
//
// Monster types
//
byte thief = "Thief", 5
byte ogre = "Ogre", 15
byte zombie = "Zombie", 25
byte rogue = "Rogue", 50
word entity = @thief, @ogre, @zombie, @rogue
word entities = 0
//
// One line status strings
//
@ -128,17 +125,6 @@ byte oilstr = "Oil:"
byte goldstr = "Gold:"
byte keystr = "Key"
//
// Combat status strings
//
byte skillstr = "Skill :"
byte healthstr = "Health :"
byte energystr = "Energy :"
byte powerstr = "Power :"
byte lifestr = "Life :"
byte fightstr = "F)ight or R)un?"
//
// Messages
//
@ -152,13 +138,6 @@ byte youdiedstr = "You perished inside the catacombs :-("
// Utility functions
//
def toupper(c)
if c >= 'a' and c <= 'z'
c = c - $20
fin
return c
end
def abs(i)
if i < 0
i = -i
@ -177,7 +156,7 @@ end
def fall
byte i
for i = 0 to 10
tone(50, i)
next
@ -185,29 +164,12 @@ end
def groan
byte i
for i = 0 to 5
tone(5, 40 + i)
next
end
def win
tone(30, 15)
tone(5, 15)
tone(5, 15)
tone(30, 5)
end
def puti(i)
if i < 0; putc('-'); i = -i; fin
if i < 10
putc(i + '0')
else
puti(i / 10)
putc(i % 10 + '0')
fin
end
//
// Update status line
//
@ -234,79 +196,36 @@ end
def clearstatus
return memset($07D0, 40, $A0A0)
end
//
// Combat
// Move player, check for obstacles
//
def fight(enemy)
word p_atck, e_atck
repeat
home()
gotoxy(0, 0)
puts(@player.name)
gotoxy(1, 2)
puts(@skillstr); puti(player.skill)
gotoxy(1, 3)
puts(@healthstr); puti(player.health)
gotoxy(1, 4)
puts(@energystr); puti(player.energy)
gotoxy(20, 0)
puts(entity[enemy->kind])
gotoxy(21, 2)
puts(@powerstr); puti(enemy->power)
gotoxy(21, 3)
puts(@lifestr); puti(enemy->life)
gotoxy(12, 8); puts(@fightstr)
if toupper(getkb()) == 'R'
if player.energy > RUN_ENERGY
moveplayer(1)
def moveplayer(dir)
player.xpos = player.xpos + dir * xdir[player.angle]
player.ypos = player.ypos + dir * ydir[player.angle]
when getmaptile(player.xpos, player.ypos) & MAP_TILE
is PIT_TILE
fall
player.energy = 0
player.health = 0
is FLOOR_TILE
is TORCH_TILE
is KEY_TILE
is GOLD_TILE
is FOOD_TILE
if player.energy < 10
player.fov = 0
fin
return moveplayer(1)
else
//
// Turn player in random direction
//
player.angle = rnd() & 7
//
// Calculate attack (with a little random variation)
//
p_atck = player.skill + player.energy / 10 - enemy->power / 25 + (rnd() & 7)
e_atck = enemy->power - player.skill / 5 - player.energy / 20 + (rnd() & 7)
if enemy->life > p_atck
enemy->life = enemy->life - p_atck
else
win
enemy->life = 0
p_atck = player.skill + enemy->power / 3
if p_atck > 100 // Limit skill
p_atck = 100
fin
player.skill = p_atck
//
// Unlink dead enemy from entities list
//
if enemy == entities
entities = enemy=>next_other
fin
if enemy=>next_other
enemy=>next_other=>prev_other = enemy=>prev_other
fin
if enemy=>prev_other
enemy=>prev_other=>next_other = enemy=>next_other
fin
if player.energy
player.energy = player.energy - 1
fin
if player.health > e_atck
player.health = player.health - e_atck
else
player.energy = 0
player.health = 0
fin
if player.energy >= 4
player.energy = player.energy - 4
fin
fin
until player.health == 0 or enemy->life == 0
break
otherwise
player.xpos = player.xpos - dir * xdir[player.angle]
player.ypos = player.ypos - dir * ydir[player.angle]
ouch
wend
end
//
@ -316,7 +235,7 @@ end
def findentities
word newother
byte xmap, ymap, what
for ymap = 1 to maprows - 2
for xmap = 2 to mapcols - 2
what = 0
@ -350,7 +269,7 @@ def findentities
setmaptile(xmap, ymap, FLOOR_TILE)
wend
next
next
next
end
//
@ -359,7 +278,7 @@ end
def drawentities
word other, xofst, yofst
other = entities
while other
xofst = other->xpos - player.xpos
@ -434,7 +353,7 @@ end
def moveentities(playerisvis)
byte xmove, ymove
word other
other = entities
while other
if playerisvis
@ -464,43 +383,21 @@ def moveentities(playerisvis)
fin
fin
if other->xpos == player.xpos and other->ypos == player.ypos
return fight(other)
if fight(@player, other)
//
// Player trying to run away
//
if player.energy > RUN_ENERGY
moveplayer(1)
fin
return moveplayer(1)
fin
return
fin
other = other=>next_other
loop
end
//
// Move player, check for obstacles
//
def moveplayer(dir)
player.xpos = player.xpos + dir * xdir[player.angle]
player.ypos = player.ypos + dir * ydir[player.angle]
when getmaptile(player.xpos, player.ypos) & MAP_TILE
is PIT_TILE
fall
player.energy = 0
player.health = 0
is FLOOR_TILE
is TORCH_TILE
is KEY_TILE
is GOLD_TILE
is FOOD_TILE
if player.energy < 10
player.fov = 0
fin
if player.energy
player.energy = player.energy - 1
fin
break
otherwise
player.xpos = player.xpos - dir * xdir[player.angle]
player.ypos = player.ypos - dir * ydir[player.angle]
ouch
wend
end
//
// Read player input and do something
//
@ -573,7 +470,7 @@ def play
ouch
break
fin
is DOOR_TILE
is DOOR_TILE
updtmaptile(player.xpos + xdir[player.angle], player.ypos + ydir[player.angle], FLOOR_TILE)
break
is ENTER_TILE
@ -588,12 +485,12 @@ def play
player.key = 1
updtmaptile(player.xpos, player.ypos, FLOOR_TILE)
gotit
break
break
is GOLD_TILE
player.gold = player.gold + 1
updtmaptile(player.xpos, player.ypos, FLOOR_TILE)
gotit
break
break
is TORCH_TILE
player:oil = player:oil + TORCH_OIL
if player:oil > 1000

View File

@ -104,7 +104,7 @@ int idlocal_add(char *name, int len, int type, int size)
{
parse_error("local label already defined\n");
return (0);
}
}
name[len] = '\0';
emit_idlocal(name, localsize);
name[len] = c;
@ -135,7 +135,7 @@ int idglobal_add(char *name, int len, int type, int size)
{
parse_error("global label already defined\n");
return (0);
}
}
name[len] = '\0';
name[len] = c;
idglobal_name[globals][0] = len;
@ -274,7 +274,7 @@ char *tag_string(int tag, int type)
{
static char str[16];
char t;
if (type & EXTERN_TYPE)
t = 'X';
else if (type & DEF_TYPE)
@ -371,7 +371,7 @@ void emit_rld(void)
void emit_esd(void)
{
int i;
printf(";\n; EXTERNAL/ENTRY SYMBOL DICTIONARY\n;\n");
for (i = 0; i < globals; i++)
{
@ -632,7 +632,7 @@ void emit_globaladdr(int tag, int offset, int type)
int fixup = fixup_new(tag, type, FIXUP_WORD);
char *taglbl = tag_string(tag, type);
printf("\t%s\t$26\t\t\t; LA\t%s+%d\n", DB, taglbl, offset);
printf("_F%03d%c\t%s\t%s+%d\t\t\n", fixup, LBL, DW, type & EXTERN_TYPE ? "" : taglbl, offset);
printf("_F%03d%c\t%s\t%s+%d\t\t\n", fixup, LBL, DW, type & EXTERN_TYPE ? "0" : taglbl, offset);
}
void emit_indexbyte(void)
{

View File

@ -51,7 +51,7 @@ t_token keywords[] = {
void parse_error(char *errormsg)
{
char *error_carrot = statement;
fprintf(stderr, "\n%4d: %s\n ", lineno, statement);
for (error_carrot = statement; error_carrot != tokenstr; error_carrot++)
putc(*error_carrot == '\t' ? '\t' : ' ', stderr);
@ -220,6 +220,9 @@ t_token scan(void)
case '\'':
*scanpos = '\'';
break;
case '\"':
*scanpos = '\"';
break;
case '\\':
*scanpos = '\\';
break;
@ -233,7 +236,7 @@ t_token scan(void)
for (scanshift = scanpos + 1; *scanshift; scanshift++)
scanshift[0] = scanshift[1];
}
else
// else
scanpos++;
}
if (!*scanpos++)