1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190
|
/* $NetBSD: hack.o_init.c,v 1.5 1997/10/19 16:58:37 christos Exp $ */
/*
* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985.
*/
#include <sys/cdefs.h>
#ifndef lint
__RCSID("$NetBSD: hack.o_init.c,v 1.5 1997/10/19 16:58:37 christos Exp $");
#endif /* not lint */
#include <string.h>
#include "hack.h"
#include "extern.h"
#include "def.objects.h"
#include "hack.onames.h" /* for LAST_GEM */
int
letindex(let)
char let;
{
int i = 0;
char ch;
while ((ch = obj_symbols[i++]) != 0)
if (ch == let)
return (i);
return (0);
}
void
init_objects()
{
int i, j, first, last, sum, end;
char let;
const char *tmp;
/*
* init base; if probs given check that they add up to 100, otherwise
* compute probs; shuffle descriptions
*/
end = SIZE(objects);
first = 0;
while (first < end) {
let = objects[first].oc_olet;
last = first + 1;
while (last < end && objects[last].oc_olet == let
&& objects[last].oc_name != NULL)
last++;
i = letindex(let);
if ((!i && let != ILLOBJ_SYM) || bases[i] != 0)
error("initialization error");
bases[i] = first;
if (let == GEM_SYM)
setgemprobs();
check:
sum = 0;
for (j = first; j < last; j++)
sum += objects[j].oc_prob;
if (sum == 0) {
for (j = first; j < last; j++)
objects[j].oc_prob = (100 + j - first) / (last - first);
goto check;
}
if (sum != 100)
error("init-prob error for %c", let);
if (objects[first].oc_descr != NULL && let != TOOL_SYM) {
/* shuffle, also some additional descriptions */
while (last < end && objects[last].oc_olet == let)
last++;
j = last;
while (--j > first) {
i = first + rn2(j + 1 - first);
tmp = objects[j].oc_descr;
objects[j].oc_descr = objects[i].oc_descr;
objects[i].oc_descr = tmp;
}
}
first = last;
}
}
int
probtype(let)
char let;
{
int i = bases[letindex(let)];
int prob = rn2(100);
while ((prob -= objects[i].oc_prob) >= 0)
i++;
if (objects[i].oc_olet != let || !objects[i].oc_name)
panic("probtype(%c) error, i=%d", let, i);
return (i);
}
void
setgemprobs()
{
int j, first;
first = bases[letindex(GEM_SYM)];
for (j = 0; j < 9 - dlevel / 3; j++)
objects[first + j].oc_prob = 0;
first += j;
if (first >= LAST_GEM || first >= SIZE(objects) ||
objects[first].oc_olet != GEM_SYM ||
objects[first].oc_name == NULL)
printf("Not enough gems? - first=%d j=%d LAST_GEM=%d\n",
first, j, LAST_GEM);
for (j = first; j < LAST_GEM; j++)
objects[j].oc_prob = (20 + j - first) / (LAST_GEM - first);
}
void
oinit()
{ /* level dependent initialization */
setgemprobs();
}
void
savenames(fd)
int fd;
{
int i;
unsigned len;
bwrite(fd, (char *) bases, sizeof bases);
bwrite(fd, (char *) objects, sizeof objects);
/*
* as long as we use only one version of Hack/Quest we need not save
* oc_name and oc_descr, but we must save oc_uname for all objects
*/
for (i = 0; i < SIZE(objects); i++) {
if (objects[i].oc_uname) {
len = strlen(objects[i].oc_uname) + 1;
bwrite(fd, (char *) &len, sizeof len);
bwrite(fd, objects[i].oc_uname, len);
}
}
}
void
restnames(fd)
int fd;
{
int i;
unsigned len;
mread(fd, (char *) bases, sizeof bases);
mread(fd, (char *) objects, sizeof objects);
for (i = 0; i < SIZE(objects); i++)
if (objects[i].oc_uname) {
mread(fd, (char *) &len, sizeof len);
objects[i].oc_uname = (char *) alloc(len);
mread(fd, objects[i].oc_uname, len);
}
}
int
dodiscovered()
{ /* free after Robert Viduya */
int i, end;
int ct = 0;
cornline(0, "Discoveries");
end = SIZE(objects);
for (i = 0; i < end; i++) {
if (interesting_to_discover(i)) {
ct++;
cornline(1, typename(i));
}
}
if (ct == 0) {
pline("You haven't discovered anything yet...");
cornline(3, (char *) 0);
} else
cornline(2, (char *) 0);
return (0);
}
int
interesting_to_discover(i)
int i;
{
return (
objects[i].oc_uname != NULL ||
(objects[i].oc_name_known && objects[i].oc_descr != NULL)
);
}
|