mirror of
https://github.com/zoriya/Quadtree.git
synced 2025-12-06 06:36:09 +00:00
Returning ids that collide
This commit is contained in:
4
Makefile
4
Makefile
@@ -10,7 +10,9 @@ SRC = src/quadtree.c \
|
|||||||
src/qt_collide.c \
|
src/qt_collide.c \
|
||||||
src/qt_destroy.c \
|
src/qt_destroy.c \
|
||||||
src/qt_layer.c \
|
src/qt_layer.c \
|
||||||
src/utility/calloc.c
|
src/qt_position_overlap.c \
|
||||||
|
src/utility/calloc.c \
|
||||||
|
src/array.c
|
||||||
|
|
||||||
OBJ = $(SRC:%.c=%.o)
|
OBJ = $(SRC:%.c=%.o)
|
||||||
|
|
||||||
|
|||||||
11
include/array.h
Normal file
11
include/array.h
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
/*
|
||||||
|
** EPITECH PROJECT, 2020
|
||||||
|
** Twac
|
||||||
|
** File description:
|
||||||
|
** array
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
void arr_add(int *arr, int n);
|
||||||
|
int arr_len(int *arr);
|
||||||
@@ -10,6 +10,7 @@
|
|||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
|
|
||||||
#define MAXCOL 1024
|
#define MAXCOL 1024
|
||||||
|
#define MAX_ENTITY 20
|
||||||
|
|
||||||
typedef struct quadtree quadtree;
|
typedef struct quadtree quadtree;
|
||||||
|
|
||||||
@@ -34,6 +35,7 @@ typedef struct qt_collision
|
|||||||
float distance_right;
|
float distance_right;
|
||||||
float distance_top;
|
float distance_top;
|
||||||
float distance_down;
|
float distance_down;
|
||||||
|
int *collide_with;
|
||||||
} qt_collision;
|
} qt_collision;
|
||||||
|
|
||||||
struct quadtree
|
struct quadtree
|
||||||
@@ -50,7 +52,3 @@ bool qt_collide(qt_intrect r1, qt_intrect r2);
|
|||||||
qt_object *qt_getobj(quadtree *tree, int id);
|
qt_object *qt_getobj(quadtree *tree, int id);
|
||||||
int qt_update(quadtree *tree, qt_object obj);
|
int qt_update(quadtree *tree, qt_object obj);
|
||||||
void qt_destroy(quadtree *tree);
|
void qt_destroy(quadtree *tree);
|
||||||
|
|
||||||
|
|
||||||
#define CAN_BE_SEEN 0b10
|
|
||||||
#define CAN_SEE 0b01
|
|
||||||
@@ -7,10 +7,24 @@
|
|||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#include "quadtree.h"
|
||||||
|
#include <stddef.h>
|
||||||
|
|
||||||
void *my_calloc(int capacity, int size);
|
void *my_calloc(int capacity, int size);
|
||||||
|
|
||||||
quadtree *qt_split(quadtree *tree);
|
quadtree *qt_split(quadtree *tree);
|
||||||
|
|
||||||
|
bool collision_overlapx(qt_intrect r1, qt_intrect r2);
|
||||||
|
bool collision_overlapy(qt_intrect r1, qt_intrect r2);
|
||||||
|
|
||||||
bool collision_can_see(int l1, int l2);
|
bool collision_can_see(int l1, int l2);
|
||||||
|
|
||||||
#define MIN(x, y) ((x) < (y) ? (x) : (y))
|
#define MIN(x, y) ((x) < (y) ? (x) : (y))
|
||||||
#define MAX(x, y) ((x) < (y) ? (y) : (x))
|
#define MAX(x, y) ((x) < (y) ? (y) : (x))
|
||||||
|
|
||||||
|
#define CAN_BE_SEEN 0b10
|
||||||
|
#define CAN_SEE 0b01
|
||||||
|
|
||||||
|
#define TREEOBJ_AT(x) (&((qt_object *)tree->objects)[i])
|
||||||
|
|
||||||
|
#define COLLISION_MAX ((qt_collision){MAXCOL, MAXCOL, MAXCOL, MAXCOL, NULL})
|
||||||
27
src/array.c
Normal file
27
src/array.c
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
/*
|
||||||
|
** EPITECH PROJECT, 2020
|
||||||
|
** Twac
|
||||||
|
** File description:
|
||||||
|
** array
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "quadtree.h"
|
||||||
|
|
||||||
|
int arr_len(int *arr)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
|
||||||
|
while (arr[i] != -1)
|
||||||
|
i++;
|
||||||
|
return (i);
|
||||||
|
}
|
||||||
|
|
||||||
|
void arr_add(int *arr, int n)
|
||||||
|
{
|
||||||
|
int new = arr_len(arr);
|
||||||
|
|
||||||
|
if (new + 1 > MAX_ENTITY)
|
||||||
|
return;
|
||||||
|
arr[new] = n;
|
||||||
|
arr[new + 1] = -1;
|
||||||
|
}
|
||||||
@@ -7,86 +7,73 @@
|
|||||||
|
|
||||||
#include "quadtree.h"
|
#include "quadtree.h"
|
||||||
#include "quadtree_internal.h"
|
#include "quadtree_internal.h"
|
||||||
|
#include "array.h"
|
||||||
|
|
||||||
//X1 is on the line or X2 is on the line or both X are on each side of the map
|
qt_collision check_collisions(qt_object *obj1, qt_object *obj2, int *colwith)
|
||||||
bool collision_overlapx(qt_intrect r1, qt_intrect r2)
|
|
||||||
{
|
{
|
||||||
if (r1.x > r2.x && r1.x < r2.x + r2.w)
|
qt_intrect r1 = obj1->rect;
|
||||||
return (true);
|
qt_intrect r2 = obj2->rect;
|
||||||
if (r1.x + r1.w > r2.x && r1.x + r1.w < r2.x + r2.w)
|
qt_collision col = COLLISION_MAX;
|
||||||
return (true);
|
|
||||||
if (r1.x < r2.x && r1.x + r1.w > r2.x + r2.w)
|
|
||||||
return (true);
|
|
||||||
if (r1.x == r2.x)
|
|
||||||
return (true);
|
|
||||||
return (false);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool collision_overlapy(qt_intrect r1, qt_intrect r2)
|
|
||||||
{
|
|
||||||
if (r1.y - r1.h < r2.y && r1.y - r1.h > r2.y - r2.h)
|
|
||||||
return (true);
|
|
||||||
if (r1.y < r2.y && r1.y - r1.h > r2.y - r2.h)
|
|
||||||
return (true);
|
|
||||||
if (r1.y < r2.y && r1.y > r2.y - r2.h)
|
|
||||||
return (true);
|
|
||||||
if (r1.y == r2.y)
|
|
||||||
return (true);
|
|
||||||
return (false);
|
|
||||||
}
|
|
||||||
|
|
||||||
qt_collision collision_complete(qt_collision col, qt_intrect r1, qt_intrect r2)
|
|
||||||
{
|
|
||||||
if (collision_overlapy(r1, r2)) {
|
if (collision_overlapy(r1, r2)) {
|
||||||
if (r1.x <= r2.x)
|
if (r1.x <= r2.x)
|
||||||
col.distance_right = MIN(col.distance_right, r2.x - (r1.x + r1.w));
|
col.distance_right = r2.x - (r1.x + r1.w);
|
||||||
if (r2.x <= r1.x)
|
if (r2.x <= r1.x)
|
||||||
col.distance_left = MIN(col.distance_left, r1.x - (r2.x + r2.w));
|
col.distance_left = r1.x - (r2.x + r2.w);
|
||||||
}
|
}
|
||||||
if (collision_overlapx(r1, r2)) {
|
if (collision_overlapx(r1, r2)) {
|
||||||
if (r1.y >= r2.y)
|
if (r1.y >= r2.y)
|
||||||
col.distance_down = MIN(col.distance_down, r1.y - r2.y - r1.h);
|
col.distance_down = r1.y - r2.y - r1.h;
|
||||||
if (r2.y >= r1.y)
|
if (r2.y >= r1.y)
|
||||||
col.distance_top = MIN(col.distance_top, r2.y - r1.y - r2.h);
|
col.distance_top = r2.y - r1.y - r2.h;
|
||||||
}
|
}
|
||||||
col.distance_down = MAX(0, col.distance_down);
|
if (col.distance_right == 0 || col.distance_down == 0 ||
|
||||||
col.distance_top = MAX(0, col.distance_top);
|
col.distance_left == 0 || col.distance_right == 0)
|
||||||
col.distance_left = MAX(0, col.distance_left);
|
arr_add(colwith, obj2->id);
|
||||||
col.distance_right = MAX(0, col.distance_right);
|
|
||||||
return (col);
|
return (col);
|
||||||
}
|
}
|
||||||
|
|
||||||
qt_collision collision_get_real_info(quadtree *tree, int id, qt_collision col)
|
qt_collision sum_col(qt_collision col1, qt_collision col2)
|
||||||
|
{
|
||||||
|
col1.distance_down = MAX(0, MIN(col1.distance_down, col2.distance_down));
|
||||||
|
col1.distance_top = MAX(0, MIN(col1.distance_top, col2.distance_top));
|
||||||
|
col1.distance_left = MAX(0, MIN(col1.distance_left, col2.distance_left));
|
||||||
|
col1.distance_right = MAX(0, MIN(col1.distance_right, col2.distance_right));
|
||||||
|
return (col1);
|
||||||
|
}
|
||||||
|
|
||||||
|
qt_collision collrec(quadtree *tree, int id, qt_collision col, int *collidewith)
|
||||||
{
|
{
|
||||||
qt_object *obj;
|
qt_object *obj;
|
||||||
qt_object *tmp;
|
qt_object *tmp;
|
||||||
int cap = tree->capacity;
|
|
||||||
quadtree *child;
|
quadtree *child;
|
||||||
|
|
||||||
if (tree->capacity == -1) {
|
if (tree->capacity == -1) {
|
||||||
for (int i = 0; i < 4; i++) {
|
for (int i = 0; i < 4; i++) {
|
||||||
child = &((quadtree *)tree->objects)[i];
|
child = &((quadtree *)tree->objects)[i];
|
||||||
col = collision_get_real_info(child, id, col);
|
col = collrec(child, id, col, collidewith);
|
||||||
}
|
}
|
||||||
return (col);
|
return (col);
|
||||||
}
|
}
|
||||||
obj = qt_getobj(tree, id);
|
obj = qt_getobj(tree, id);
|
||||||
if (!obj)
|
if (!obj)
|
||||||
return (col);
|
return (col);
|
||||||
for (int i = 0; i < cap && ((qt_object *)tree->objects)[i].id != -1; i++) {
|
for (int i = 0; i < tree->capacity && TREEOBJ_AT(i)->id != -1; i++) {
|
||||||
tmp = &((qt_object *)tree->objects)[i];
|
tmp = TREEOBJ_AT(i);
|
||||||
if (tmp->id == id || !collision_can_see(obj->layer, tmp->layer)) {
|
if (tmp->id == id || !collision_can_see(obj->layer, tmp->layer))
|
||||||
if (tmp->id != id)
|
|
||||||
printf("%d (id %d) VS %d (id %d)\n", obj->layer, id, tmp->layer, tmp->id);
|
|
||||||
continue;
|
continue;
|
||||||
}
|
col = sum_col(col, check_collisions(obj, tmp, collidewith));
|
||||||
col = collision_complete(col, obj->rect, tmp->rect);
|
|
||||||
}
|
}
|
||||||
return (col);
|
return (col);
|
||||||
}
|
}
|
||||||
|
|
||||||
qt_collision collision_get_info(quadtree *tree, int id)
|
qt_collision collision_get_info(quadtree *tree, int id)
|
||||||
{
|
{
|
||||||
qt_collision col = (qt_collision){MAXCOL, MAXCOL, MAXCOL, MAXCOL};
|
qt_collision col = COLLISION_MAX;
|
||||||
return (collision_get_real_info(tree, id, col));
|
static int collidewith[MAX_ENTITY + 1];
|
||||||
|
|
||||||
|
collidewith[0] = -1;
|
||||||
|
col = collrec(tree, id, col, collidewith);
|
||||||
|
col.collide_with = collidewith;
|
||||||
|
return (col);
|
||||||
}
|
}
|
||||||
@@ -5,7 +5,7 @@
|
|||||||
** qt_layer
|
** qt_layer
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "quadtree.h"
|
#include "quadtree_internal.h"
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
|
|
||||||
bool collision_can_see(int l1, int l2)
|
bool collision_can_see(int l1, int l2)
|
||||||
|
|||||||
35
src/qt_position_overlap.c
Normal file
35
src/qt_position_overlap.c
Normal file
@@ -0,0 +1,35 @@
|
|||||||
|
/*
|
||||||
|
** EPITECH PROJECT, 2020
|
||||||
|
** Twac
|
||||||
|
** File description:
|
||||||
|
** qt_position_overlap
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "quadtree.h"
|
||||||
|
|
||||||
|
//X1 is on the line or X2 is on the line or both X are on each side of the map
|
||||||
|
bool collision_overlapx(qt_intrect r1, qt_intrect r2)
|
||||||
|
{
|
||||||
|
if (r1.x > r2.x && r1.x < r2.x + r2.w)
|
||||||
|
return (true);
|
||||||
|
if (r1.x + r1.w > r2.x && r1.x + r1.w < r2.x + r2.w)
|
||||||
|
return (true);
|
||||||
|
if (r1.x < r2.x && r1.x + r1.w > r2.x + r2.w)
|
||||||
|
return (true);
|
||||||
|
if (r1.x == r2.x)
|
||||||
|
return (true);
|
||||||
|
return (false);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool collision_overlapy(qt_intrect r1, qt_intrect r2)
|
||||||
|
{
|
||||||
|
if (r1.y - r1.h < r2.y && r1.y - r1.h > r2.y - r2.h)
|
||||||
|
return (true);
|
||||||
|
if (r1.y < r2.y && r1.y - r1.h > r2.y - r2.h)
|
||||||
|
return (true);
|
||||||
|
if (r1.y < r2.y && r1.y > r2.y - r2.h)
|
||||||
|
return (true);
|
||||||
|
if (r1.y == r2.y)
|
||||||
|
return (true);
|
||||||
|
return (false);
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user