Files
rigid-body/tools.py

85 lines
2.4 KiB
Python

import pygame as pg
from queue import Queue
from functools import reduce
from collider.types import CircleCollider, ConvexCollider, BaseCollider, ColliderContact
from transform import Transform
def _debug(fn):
def wrapper(self: 'Debug', *args, **kwargs):
if not self.enabled: return
fn(self, *args, **kwargs)
return wrapper
class Debug:
def __init__(self, enabled=False):
self.enabled = enabled
self._screen = None
self._debug_queue = Queue()
def debug(self):
while not self._debug_queue.empty():
self._debug_queue.get()()
@_debug
def draw_contact(self, contact: ColliderContact) -> None:
def _draw_lines():
if len(contact.points) > 1:
pg.draw.lines(
self._screen,
(255,0,255),
False,
points=contact.points,
width=1
)
for point in contact.points:
pg.draw.circle(
self._screen,
(255,0,255),
point,
1
)
if len(contact.points) > 0:
pg.draw.circle(
self._screen,
(255,0,255),
contact.points[0],
2
)
base = reduce(lambda a,b: a+b,contact.points) / len(contact.points)
pg.draw.line(
self._screen,
(255,255,0),
base,
base+(contact.normal*15)
)
self._debug_queue.put(_draw_lines)
@_debug
def draw_collider(self, collider: BaseCollider, t: Transform):
def _draw_collider():
if isinstance(collider, ConvexCollider):
h = collider.hull(t)
pg.draw.lines(
self._screen,
color=(0,255,255),
points=[v for v in h.vertices()],
closed=True
)
if isinstance(collider, CircleCollider):
pg.draw.circle(
self._screen,
color=(0,255,255),
center=t.position,
radius=collider.radius,
width=1
)
self._debug_queue.put(_draw_collider)
debug = Debug()