summaryrefslogtreecommitdiffstats
path: root/AIController.cpp
blob: d310fa0a7f4f0c3ca828b2b6531c104285aa09d7 (plain)
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
#include <stdio.h>
#include "AIController.h"
 

AIController::AIController(Player &player, Field& field, int inhibitDelay, int randomThreshold):
	Controller(player), m_field(field), m_inhibitDelay(inhibitDelay), m_randomThreshold(randomThreshold)
{
	m_inhibit = 0;
}

AIController::~AIController(void)
{
}


void AIController::think() {
	Coordinates coord = m_player.getCoordinates();
	VelocityVector velocity = m_player.getVelocity();

	// assume either x or y is null
	int speed = max(abs(velocity.x), abs(velocity.y));
	int sgn_x = velocity.x == 0 ? 0 : (velocity.x > 0 ? 1 : -1);
	int sgn_y = velocity.y == 0 ? 0 : (velocity.y > 0 ? 1 : -1);

	for (int i = 1; i <= m_inhibitDelay*speed+1 ; ++i ) {
		try {
			if (m_field.getCell(Coordinates(coord.x+i*sgn_x, coord.y+i*sgn_y)).getState()) {
				turnRandom();
      }
		} catch (std::out_of_range e) {
			turnRandom();
		}
	}
	if (rand() % 100 <= m_randomThreshold) turnRandom();
	m_inhibit = max(0,m_inhibit-1);
}

void AIController::turnRandom() {
	if (m_inhibit == 0) {
		VelocityVector oldVelocity = m_player.getVelocity();

		VelocityVector leftVelocity = VelocityVector(- oldVelocity.y, oldVelocity.x);
		// right = -left
		int sgn_x = leftVelocity.x == 0 ? 0 : (leftVelocity.x > 0 ? 1 : -1);
		int sgn_y = leftVelocity.y == 0 ? 0 : (leftVelocity.y > 0 ? 1 : -1);

		Coordinates coord = m_player.getCoordinates();

		uint freeSpaceLeft = 1;
		uint freeSpaceRight = 1;

		try {
			while (1) {
				if (m_field.getCell(Coordinates(coord.x+freeSpaceLeft*sgn_x, coord.y+freeSpaceLeft*sgn_y)).getState()) break;
				freeSpaceLeft++;
    	}
		} catch (std::out_of_range e) {}

		try {
			while (1) {
				if (m_field.getCell(Coordinates(coord.x-freeSpaceRight*sgn_x, coord.y-freeSpaceRight*sgn_y)).getState()) break;
				freeSpaceRight++;
    	}
		} catch (std::out_of_range e) {}

		if (max(freeSpaceRight,freeSpaceLeft) > m_inhibitDelay*max(abs(leftVelocity.x),abs(leftVelocity.y))+1) {
			freeSpaceLeft > freeSpaceRight ? m_player.turnLeft() : m_player.turnRight();
			m_inhibit = m_inhibitDelay;
    }
	}
}