rationals, for the sake of 16-bit-int platforms such as Palm. Thanks
to James H.
git-svn-id: svn://svn.tartarus.org/sgt/puzzles@6114
cda61777-01e9-0310-a592-
d414129be87e
* Points are stored using rational coordinates, with the same
* denominator for both coordinates.
*/
* Points are stored using rational coordinates, with the same
* denominator for both coordinates.
*/
} point;
typedef struct edge {
} point;
typedef struct edge {
*/
static int cross(point a1, point a2, point b1, point b2)
{
*/
static int cross(point a1, point a2, point b1, point b2)
{
- int b1x, b1y, b2x, b2y, px, py, d1, d2, d3;
+ long b1x, b1y, b2x, b2y, px, py, d1, d2, d3;
/*
* The condition for crossing is that b1 and b2 are on opposite
/*
* The condition for crossing is that b1 and b2 are on opposite
*/
static void make_circle(point *pts, int n, int w)
{
*/
static void make_circle(point *pts, int n, int w)
{
/*
* First, decide on a denominator. Although in principle it
/*
* First, decide on a denominator. Although in principle it
for (i = 0; i < n; i++) {
double angle = i * 2 * PI / n;
double x = r * sin(angle), y = - r * cos(angle);
for (i = 0; i < n; i++) {
double angle = i * 2 * PI / n;
double x = r * sin(angle), y = - r * cos(angle);
- pts[i].x = (int)(c + x + 0.5);
- pts[i].y = (int)(c + y + 0.5);
+ pts[i].x = (long)(c + x + 0.5);
+ pts[i].y = (long)(c + y + 0.5);
static char *new_game_desc(game_params *params, random_state *rs,
char **aux, int interactive)
{
static char *new_game_desc(game_params *params, random_state *rs,
char **aux, int interactive)
{
- int n = params->n;
- int w, h, i, j, k, m;
+ int n = params->n, i;
+ long w, h, j, k, m;
tree234 *edges, *vertices;
edge *e, *e2;
vertex *v, *vs, *vlist;
tree234 *edges, *vertices;
edge *e, *e2;
vertex *v, *vs, *vlist;
* Choose n points from this grid.
*/
pts = snewn(n, point);
* Choose n points from this grid.
*/
pts = snewn(n, point);
+ tmp = snewn(w*h, long);
for (i = 0; i < w*h; i++)
tmp[i] = i;
shuffle(tmp, w*h, sizeof(*tmp), rs);
for (i = 0; i < w*h; i++)
tmp[i] = i;
shuffle(tmp, w*h, sizeof(*tmp), rs);
* they come out with at least one crossed line when arranged
* in a circle (so that the puzzle isn't immediately solved!).
*/
* they come out with at least one crossed line when arranged
* in a circle (so that the puzzle isn't immediately solved!).
*/
for (i = 0; i < n; i++)
tmp[i] = i;
pts2 = snewn(n, point);
for (i = 0; i < n; i++)
tmp[i] = i;
pts2 = snewn(n, point);
}
pts2[j].x += pts2[j].d / 2;
pts2[j].y += pts2[j].d / 2;
}
pts2[j].x += pts2[j].d / 2;
pts2[j].y += pts2[j].d / 2;
- auxlen += sprintf(buf, ";P%d:%d,%d/%d", i,
+ auxlen += sprintf(buf, ";P%d:%ld,%ld/%ld", i,
pts2[j].x, pts2[j].y, pts2[j].d);
}
k = 0;
auxstr = snewn(auxlen, char);
auxstr[k++] = 'S';
for (i = 0; i < n; i++)
pts2[j].x, pts2[j].y, pts2[j].d);
}
k = 0;
auxstr = snewn(auxlen, char);
auxstr[k++] = 'S';
for (i = 0; i < n; i++)
- k += sprintf(auxstr+k, ";P%d:%d,%d/%d", i,
+ k += sprintf(auxstr+k, ";P%d:%ld,%ld/%ld", i,
pts2[i].x, pts2[i].y, pts2[i].d);
assert(k < auxlen);
*aux = auxstr;
pts2[i].x, pts2[i].y, pts2[i].d);
assert(k < auxlen);
*aux = auxstr;
}
struct game_drawstate {
}
struct game_drawstate {
};
static char *interpret_move(game_state *state, game_ui *ui, game_drawstate *ds,
};
static char *interpret_move(game_state *state, game_ui *ui, game_drawstate *ds,
int n = state->params.n;
if (button == LEFT_BUTTON) {
int n = state->params.n;
if (button == LEFT_BUTTON) {
+ int i, best;
+ long bestd;
/*
* Begin drag. We drag the vertex _nearest_ to the pointer,
/*
* Begin drag. We drag the vertex _nearest_ to the pointer,
bestd = 0;
for (i = 0; i < n; i++) {
bestd = 0;
for (i = 0; i < n; i++) {
- int px = state->pts[i].x * ds->tilesize / state->pts[i].d;
- int py = state->pts[i].y * ds->tilesize / state->pts[i].d;
- int dx = px - x;
- int dy = py - y;
- int d = dx*dx + dy*dy;
+ long px = state->pts[i].x * ds->tilesize / state->pts[i].d;
+ long py = state->pts[i].y * ds->tilesize / state->pts[i].d;
+ long dx = px - x;
+ long dy = py - y;
+ long d = dx*dx + dy*dy;
if (best == -1 || bestd > d) {
best = i;
if (best == -1 || bestd > d) {
best = i;
* First, see if we're within range. The user can cancel a
* drag by dragging the point right off the window.
*/
* First, see if we're within range. The user can cancel a
* drag by dragging the point right off the window.
*/
- if (ui->newpoint.x < 0 || ui->newpoint.x >= state->w*ui->newpoint.d ||
- ui->newpoint.y < 0 || ui->newpoint.y >= state->h*ui->newpoint.d)
+ if (ui->newpoint.x < 0 ||
+ ui->newpoint.x >= (long)state->w*ui->newpoint.d ||
+ ui->newpoint.y < 0 ||
+ ui->newpoint.y >= (long)state->h*ui->newpoint.d)
return "";
/*
* We aren't cancelling the drag. Construct a move string
* indicating where this point is going to.
*/
return "";
/*
* We aren't cancelling the drag. Construct a move string
* indicating where this point is going to.
*/
- sprintf(buf, "P%d:%d,%d/%d", p,
+ sprintf(buf, "P%d:%ld,%ld/%ld", p,
ui->newpoint.x, ui->newpoint.y, ui->newpoint.d);
ui->just_dragged = TRUE;
return dupstr(buf);
ui->newpoint.x, ui->newpoint.y, ui->newpoint.d);
ui->just_dragged = TRUE;
return dupstr(buf);
static game_state *execute_move(game_state *state, char *move)
{
int n = state->params.n;
static game_state *execute_move(game_state *state, char *move)
{
int n = state->params.n;
+ int p, k;
+ long x, y, d;
game_state *ret = dup_game(state);
ret->just_solved = FALSE;
game_state *ret = dup_game(state);
ret->just_solved = FALSE;
ret->cheated = ret->just_solved = TRUE;
}
if (*move == 'P' &&
ret->cheated = ret->just_solved = TRUE;
}
if (*move == 'P' &&
- sscanf(move+1, "%d:%d,%d/%d%n", &p, &x, &y, &d, &k) == 4 &&
+ sscanf(move+1, "%d:%ld,%ld/%ld%n", &p, &x, &y, &d, &k) == 4 &&
p >= 0 && p < n && d > 0) {
ret->pts[p].x = x;
ret->pts[p].y = y;
p >= 0 && p < n && d > 0) {
ret->pts[p].x = x;
ret->pts[p].y = y;
for (i = 0; (e = index234(state->graph->edges, i)) != NULL; i++) {
point p1, p2;
for (i = 0; (e = index234(state->graph->edges, i)) != NULL; i++) {
point p1, p2;
p1 = state->pts[e->a];
p2 = state->pts[e->b];
p1 = state->pts[e->a];
p2 = state->pts[e->b];
int thisc = (j == 0 ? COL_POINT :
j == 1 ? COL_NEIGHBOUR : COL_DRAGPOINT);
for (i = 0; i < state->params.n; i++) {
int thisc = (j == 0 ? COL_POINT :
j == 1 ? COL_NEIGHBOUR : COL_DRAGPOINT);
for (i = 0; i < state->params.n; i++) {
point p = state->pts[i];
if (ui->dragpoint == i) {
point p = state->pts[i];
if (ui->dragpoint == i) {