/*
	Line path search routine(s)
	Made by Ismo Horppu on 1996 - 1997
*/

#include <stdlib.h>
#include "ailhead.h"
#include <dpmi.h>
#include <go32.h>
#include <stdio.h>
#include "ct2egen.h"
#include "ct2egrx.h"

extern int CheckMove (int x, int y, int z);

/*
	returns how many pixels we can walk from (x1,y1) to specified
	direction
*/
int SeekLine (signed int x1, signed int y1, signed int xs, signed int ys)
{
	signed int ex, ey;
	BYTE value;
	int range = 0;
	int sx, sy;

	ex = x1 << 6;
	ey = y1 << 6;

	while (1){
		sx = (signed int) ex >> 6;
		sy = (signed int) ey >> 6;
		if (sx == targetx && sy == targety) return -1;
	
	/*	value = Map[(ex + xs) >> 6][(ey + ys) >> 6][curz];
		if (BlockFlags[value] != Walkable) return range;	// blocked ?*/
		value = CheckMove ((ex + xs) >> 6, (ey + ys) >> 6, curz);
		if (value != 1) return range;
		if (((ex + xs) >> 6) > MapWidth - 1) return range;
		if (((ex + xs) >> 6) < 1) return range;
		if (((ey + ys) >> 6) > MapHeight - 1) return range;
		if (((ey + ys) >> 6) < 1) return range;
		ex += xs;
		ey += ys;
		range++;
	}
}

/*
	returns if we can move from (x1,y1) towards (x2, y2)
*/
int SeekLine2 (signed int x1, signed int y1, signed int x2, signed int y2)
{
	signed int ex, ey, xs, ys, xr, yr;
	int xd, yd;

	BYTE value;
	int c, yc;


	ex = x1 << 6;
	ey = y1 << 6;

	xr = abs (x2 - x1);

	xd = 0;
	if (x2 > x1) xd = 1;
	if (x2 < x1) xd = -1;

	yd = 0;
	if (y2 > y1) yd = 1;
	if (y2 < y1) yd = -1;

	yr = abs (y2 - y1);

	if (xr == yr){
		xs = 64 * xd;
		ys = 64 * yd;
		c = xr;
	}

	else if (xr > yr){
		xs = 64 * xd;
		ys = yr * 64 / xr * yd;
		c = xr;
	}

	else if (xr < yr){
		ys = 64 * yd;
		xs = xr * 64 / yr * xd;
		c = yr;
	}

	gxs = xs;
	gys = ys;
	grange = c;

	for (yc = 0; yc < c; yc++){
		if (((ex >> 6) == targetx) && ((ey >> 6) == targety)) return 0;
		/*value = Map[(ex + xs) >> 6][(ey + ys) >> 6][curz];
		if (BlockFlags[value] != Walkable) return -1;	// blocked ?*/
		value = CheckMove ((ex + xs) >> 6, (ey + ys) >> 6, curz);
		if (value != 1) return - 1;
		ex += xs;
		ey += ys;
	}

	return 0;
}

/*
	returns how many pixels we can move from (x1,y1) towards (x2,y2)
*/
int SeekLine3 (signed int x1, signed int y1, signed int x2, signed int y2)
{
	signed int ex, ey, xs, ys, xr, yr;
	BYTE value;
	int c, yc;
	int xd, yd;

	ex = x1 << 6;
	ey = y1 << 6;

	xr = abs (x2 - x1);
	yr = abs (y2 - y1);

	xd = 0;
	if (x2 > x1) xd = 1;
	if (x2 < x1) xd = -1;

	yd = 0;
	if (y2 > y1) yd = 1;
	if (y2 < y1) yd = -1;

	if (xr == yr){
		xs = 64 * xd;
		ys = 64 * yd;
		c = xr;
	}

	else if (xr > yr){
		xs = 64 * xd;
		ys = yr * 64 / xr * yd;
		c = xr;
	}

	else if (xr < yr){
		ys = 64 * yd;
		xs = xr * 64 / yr * xd;
		c = yr;
	}

	gxs = xs;
	gys = ys;
	grange = c;

	ex += xs;
	ey += ys;
	c--;

	for (yc = 0; yc < c; yc++){
		value = CheckMove ((ex >> 6), (ey >> 6), curz);
		if (value != 1) return yc;
		/*
		value = Map[(ex >> 6)][(ey >> 6)][curz];
		if (BlockFlags[value] != Walkable) return yc;	// blocked ?*/
		ex += xs;
		ey += ys;
	}

	return yc;
}

/*
	calculates xstep (multiplied by 64) from (x,y) to (targetx, targety)
*/
int GetXS (int x, int y)
{
	int xr, yr;

	xr = abs (targetx - x);
	yr = abs (targety - y);

	if (xr > yr) return 64 * sign[targetx > x];
	else if (xr < yr) return (xr * 64 / yr) * sign[targetx > x];
	else if (xr == yr) return 64;
	return 0;
}

/*
	calculates ystep (multiplied by 64) from (x,y) to (targetx, targety)
*/
int GetYS (int x, int y)
{
	int xr, yr;

	xr = abs (targetx - x);
	yr = abs (targety - y);

	if (yr > xr) return 64 * sign[targety > y];
	else if (yr < xr) return (yr * 64 / xr) * sign[targety > y];
	else if (yr == xr) return 64;
	return 0;
}