TapestryEngine

A 2D Platformer Game Engine
Log | Files | Refs

eb1e7241d09c46a3b901ad5e8f95f4320c6f5d76.svn-base (7680B)


      1 #include "ActorCollision.h"
      2 
      3 bool SpatialMonitor::PartitionCells(int worldH, int worldW)
      4 {
      5 	int cellW = (worldW / CELLS_X);
      6 	int cellH = (worldH / CELLS_Y);
      7 
      8 	for (int i = 0; i < CELLS_Y; i++)
      9 	{
     10 		for (int j = 0; j < CELLS_X; j++)
     11 		{
     12 			Cell new_cell;
     13 			new_cell.GetCellRect()->w = cellW;
     14 			new_cell.GetCellRect()->h = cellH;
     15 			new_cell.GetCellRect()->x = cellW * j;
     16 			new_cell.GetCellRect()->y = cellH * i;
     17 
     18 			mCells[i*CELLS_X + j] = new_cell;
     19 
     20 		}
     21 	}
     22 	return true;
     23 }
     24 
     25 bool SpatialMonitor::LogActor(int id)
     26 {
     27 	//mActors[mActorCount] = &act;
     28 	//mActors.Insert(act.GetHandle(), &act);
     29 	//act.SetSpatID(mActorCount);
     30 	UpdateActorCell(id);
     31 	return true;
     32 }
     33 
     34 bool SpatialMonitor::ClearActorCell(int id)
     35 {
     36 	if ((id == 7) | (id == 8))
     37 	{
     38 		gCons->ConsPrintf("seal updates cell\n");
     39 	}
     40 	if (id == 9)
     41 	{
     42 		gCons->ConsPrintf("player updates cell\n");
     43 	}
     44 	
     45 	if (GetActorCell(id) != -1)
     46 	{
     47 		//mCells[GetActorCell(id)].GetActorTree()->Search(id)->Delete();
     48 		mCells[GetActorCell(id)].GetActorTree()->DeleteNode(id);
     49 		return true;
     50 	}
     51 	return false;
     52 }
     53 
     54 
     55 int SpatialMonitor::UpdateActorCell(int id)
     56 {
     57 	//if (id == 7)
     58 	//{
     59 	//	gCons->ConsPrintf("seal updates cell\n");
     60 	//}
     61 	Actor* act = (mAHM->GetActorAddress(id));
     62 	for (int i = 0; i < CELL_COUNT; i++)
     63 	{
     64 		if (DetectCenterPointIntersect( mCells[i].GetCellRect(),  act->GetPosition() ) )
     65 		{
     66 			//gCons->ConsPrintf("Actor entering cell %i\n", i);
     67 			
     68 			if (i != act->GetSpatCell())
     69 			{
     70 				mCells[i].GetActorTree()->Insert(id, NULL);
     71 				ClearActorCell(id); 
     72 				act->SetSpatCell(i);
     73 			}
     74 
     75 			return i;
     76 		}
     77 	}
     78 	gCons->ConsPrintf("Could not find Actor cell\n");
     79 	return -1;
     80 }
     81 
     82 int SpatialMonitor::GetAdjacentCells(int cellnum, Cell* cells[9])
     83 {
     84 	cells[0] = GetCell((cellnum - CELLS_X - 1));
     85 	cells[1] = GetCell((cellnum - CELLS_X));
     86 	cells[2] = GetCell((cellnum - CELLS_X + 1));
     87 
     88 	cells[3] = GetCell((cellnum - 1));
     89 	cells[4] = GetCell((cellnum));
     90 	cells[5] = GetCell((cellnum + 1));
     91 	
     92 	cells[6] = GetCell((cellnum + CELLS_X - 1));
     93 	cells[7] = GetCell((cellnum + CELLS_X));
     94 	cells[8] = GetCell((cellnum + CELLS_X + 1));
     95 
     96 	return 0;
     97 }
     98 
     99 //bool SpatialMonitor::GetActorsInCell(int cellnum) //uneeded now. Use Cell.GetActorTree()
    100 //{
    101 //	for (int i = 0; i < MAX_ACTORS; i++) //this is very bad. Basically defeats the function of cells by check each actor
    102 //	{
    103 //		if (mActorCells[i] == cellnum)
    104 //		{
    105 //			//gCons->ConsPrintf("Actor %i is in adjacent cell\n", i);
    106 //			mAdjacentActorIDs[mAdjacentActorCount] = i;
    107 //			mAdjacentActorCount++;
    108 //		}
    109 //	}
    110 //	return true;
    111 //}
    112 
    113 //bool SpatialMonitor::GetAdjacentActors(int cellnum)
    114 //{
    115 //	mAdjacentActorCount = 0;
    116 //	mAdjacentActorIDs[MAX_ACTORS] = { 0 };
    117 //
    118 //	int cells[9];
    119 //	GetAdjacentCells(cellnum, cells);
    120 //
    121 //	for (int i = 0; i < 9; i++)
    122 //	{
    123 //		GetActorsInCell(cells[i]);
    124 //		//gDiagDraw->LogDiagRect(mCells[cells[i]]);
    125 //	}
    126 //	return true;
    127 //}
    128 
    129 bool SpatialMonitor::DetectActorCollision(int id1, int id2)
    130 {
    131 	if (id1 != id2)
    132 	{	
    133 		//gDiagDraw->LogDiagRect(*mActors[id2]->GetPosition());
    134 		return DetectRectIntersect(mAHM->GetActorAddress(id1)->GetPosition(), mAHM->GetActorAddress(id2)->GetPosition());
    135 	}
    136 	else
    137 	{
    138 		//gCons->ConsPrintf("Attempted to check actor collision with itself\n");
    139 		return false;
    140 	}
    141 }
    142 
    143 bool SpatialMonitor::DetectRectSensors(SDL_Rect* sensor, int DetectorID, int foreignID)
    144 {
    145 	if (DetectorID != foreignID)
    146 	{
    147 		//gDiagDraw->LogDiagRect(*sensor);
    148 		//gDiagDraw->LogDiagRect(*mActors[foreignID]->GetPosition());
    149 		return DetectRectIntersect(sensor, mAHM->GetActorAddress(foreignID)->GetPosition());
    150 	}
    151 	else
    152 	{
    153 		//gCons->ConsPrintf("Attempted to check actor collision with itself\n");
    154 		return false;
    155 	}
    156 }
    157 
    158 bool SpatialMonitor::HandleCollisions(int CallerID)
    159 {
    160 
    161 	int CallerCell = GetActorCell(CallerID);
    162 	
    163 	Cell* AdjecentCellIndex[9];
    164 	GetAdjacentCells(CallerCell, AdjecentCellIndex);
    165 
    166 	for (int i = 0; i < 9; i++)
    167 	{	
    168 		if (AdjecentCellIndex[i] != NULL)
    169 		{
    170 			int array_size = AdjecentCellIndex[i]->GetActorTree()->Size();
    171 			if (array_size != -1)
    172 			{
    173 				//Node** ActorTreeArray = NULL;
    174 				Node** ActorTreeArray = new Node*[array_size];
    175 				ActorTreeArray = (AdjecentCellIndex[i]->GetActorTree())->Dump();
    176 				for (int j = 0; j < (array_size); j++)
    177 				{
    178 					if (ActorTreeArray[j] == (Node*)(0xcdcdcdcd))
    179 					{
    180 						gCons->ConsPrintf("uninitialized memory\n");
    181 						AdjecentCellIndex[i]->GetActorTree()->Dump();
    182 					}
    183 					assert(j <= array_size);
    184 					//gCons->ConsPrintf("index: %i, item: %i\n", j, ActorTreeArray[j]->GetItem());	
    185 					int size = sizeof(ActorTreeArray);
    186 
    187 					if (ActorTreeArray[j] == NULL)
    188 					{
    189 						gCons->ConsPrintf("Error: invalid index into actor tree, Cell: %i", i);
    190 					}
    191 					if (DetectActorCollision(CallerID, ActorTreeArray[j]->GetItem()) == true)
    192 					{
    193 						mAHM->GetActorAddress(CallerID)->EventProcess(Event(ACTOR_COLLISION, ActorTreeArray[j]->GetItem()));
    194 					}
    195 				}
    196 			}
    197 			else
    198 			{
    199 				//gCons->ConsPrintf("Cell is empty/n");
    200 			}
    201 		}
    202 		else
    203 		{
    204 			//Cell does not exist. do nothing
    205 		}
    206 	}
    207 
    208 	return true;
    209 }
    210 
    211 bool SpatialMonitor::HandleRectSensors(SDL_Rect* sensor, int CallerID, SensorType SeType)
    212 {
    213 	
    214 	int CallerCell = GetActorCell(CallerID);
    215 
    216 	Cell* AdjecentCellIndex[9];
    217 	GetAdjacentCells(CallerCell, AdjecentCellIndex);
    218 
    219 	for (int i = 0; i < 9; i++)
    220 	{
    221 		if (AdjecentCellIndex[i] != NULL)
    222 		{
    223 			int array_size = AdjecentCellIndex[i]->GetActorTree()->Size();
    224 			if (array_size != -1)
    225 			{
    226 				//Node** ActorTreeArray = NULL;
    227 				Node** ActorTreeArray = new Node*[array_size];
    228 				ActorTreeArray = (AdjecentCellIndex[i]->GetActorTree())->Dump();
    229 				for (int j = 0; j < (array_size); j++)
    230 				{
    231 					assert(j <= array_size);
    232 					//gCons->ConsPrintf("index: %i, item: %i\n", j, ActorTreeArray[j]->GetItem());
    233 
    234 					if (ActorTreeArray[j] == NULL)
    235 					{
    236 						gCons->ConsPrintf("Error: invalid index into actor tree, Cell: %i", i);
    237 					}
    238 					if (DetectRectSensors(sensor, CallerID, ActorTreeArray[j]->GetItem()) == true)
    239 					{
    240 						mAHM->GetActorAddress(CallerID)->EventProcess(Event(SENSOR_COLLISION, SeType, ActorTreeArray[j]->GetItem())); //Used to pass actor* now passed ID number. receiver functions need to be updated
    241 					}
    242 				}
    243 			}
    244 			else
    245 			{
    246 				//gCons->ConsPrintf("Cell is empty/n");
    247 			}
    248 		}
    249 		else
    250 		{
    251 			//Cell does not exist. do nothing
    252 		}
    253 	}
    254 	return true;
    255 }
    256 
    257 bool SpatialMonitor::TestBlockers(SDL_Rect* sensor, int CallerID)
    258 {	
    259 	int CallerCell = GetActorCell(CallerID);
    260 
    261 	Cell* AdjecentCellIndex[9];
    262 	GetAdjacentCells(CallerCell, AdjecentCellIndex);
    263 
    264 	for (int i = 0; i < 9; i++)
    265 	{
    266 		if (AdjecentCellIndex[i] != NULL)
    267 		{
    268 			Node** ActorTreeArray = ((AdjecentCellIndex[i]->GetActorTree())->Dump());
    269 			if (ActorTreeArray != NULL)
    270 			{
    271 				for (int j = 0; j < (AdjecentCellIndex[i]->GetActorTree())->Size(); j++)
    272 				{
    273 					if (DetectRectSensors(sensor, CallerID, ActorTreeArray[j]->GetItem()) == true)
    274 					{
    275 						if (mAHM->GetActorAddress(ActorTreeArray[j]->GetItem())->IsBlocking() == true)
    276 						{
    277 							return true;
    278 						}
    279 					}
    280 				}
    281 			}
    282 			else
    283 			{
    284 				//gCons->ConsPrintf("Cell is empty/n");
    285 			}
    286 		}
    287 		else
    288 		{
    289 			//Cell does not exist. do nothing
    290 		}
    291 	}
    292 	return false;
    293 }
    294 
    295 bool SpatialMonitor::EventProcess(Event eve)
    296 {
    297 	switch (*eve.GetEventType())
    298 	{
    299 	case MOVED_THIS_FRAME:
    300 		UpdateActorCell(eve.GetEventData()->i);
    301 		HandleCollisions(eve.GetEventData()->i);
    302 		return true;
    303 		break;
    304 	case CHECK_RECT_SENSOR:
    305 		HandleRectSensors(eve.GetEventData()->sd.sensor, eve.GetEventData()->sd.id, eve.GetEventData()->sd.st);
    306 		return true;
    307 		break;
    308 	case CHECK_BLOCKERS:
    309 		return TestBlockers(eve.GetEventData()->sd.sensor, eve.GetEventData()->sd.id);
    310 		break;
    311 	default:
    312 		gCons->ConsPrintf("Spatial Monitor Received Invalid Event Type\n");
    313 		return false;
    314 		break;
    315 	}
    316 }