Skip to content

Utils Geometria

Alessandro Bria edited this page Sep 30, 2026 · 1 revision

utils — Geometria e collisioni

Le classi di geometryUtils.h sono nel namespace agp e sono condivise da core e giochi. Conviene chiarire unità di misura, origine e verso degli assi prima di usarle per movimento, rendering o collisioni.

Quale tipo usare

Tipo Uso e convenzione
Vec2Df / PointF Vettore o punto a coordinate float: posizioni, velocità, direzioni.
Point Coordinate intere, utili per pixel e indici di griglia.
RectF / AABB Rettangolo allineato agli assi, con pos, size e yUp.
RectI Rettangolo intero, usato per i ritagli nelle spritesheet.
RotatedRectF / OBB Rettangolo descritto da centro, dimensioni e angolo.
LineF Segmento descritto dagli estremi start ed end.

I nomi accoppiati nella tabella sono alias dello stesso tipo. Per moto e normalizzazione usa le versioni float: con tipi interi divisioni e risultati perdono la parte frazionaria.

Rettangoli e asse Y

yUp = false (default) yUp = true
Y cresce Verso il basso Verso l’alto
Rect::pos indica Angolo in alto a sinistra Angolo in basso a sinistra
top() pos.y pos.y + size.y
bottom() pos.y + size.y pos.y

Mantieni la stessa convenzione fra geometrie confrontate. Cambiare yUp cambia l’interpretazione del rettangolo: non converte le coordinate. Anche dir2vec(), perp() e le rotazioni devono ricevere il verso corretto.

Il costruttore con quattro numeri riceve posizione e dimensioni; quello con due vettori riceve due estremi, dai quali calcola la dimensione:

agp::RectF a(10, 20, 4, 2, false);
agp::RectF b(agp::PointF(10, 20), agp::PointF(14, 22), false);
// a e b descrivono lo stesso rettangolo

Le geometrie non incorporano una scala pixel/metri. Un RectI sorgente dello sprite è in pixel; un RectF di gioco è normalmente in unità di scena. toSDL() e toSDLf() copiano/convertono i valori: per camera e trasformazione verso lo schermo usa la View del core.

Tre accortezze essenziali

  • Normalizzazione e segmenti: prima di v.norm() controlla v.mag2() > 0. Prima di calcolare distanze da un segmento, verifica line.isValid(). Queste operazioni dividono per la lunghezza; il vettore nullo e gli estremi coincidenti vanno gestiti dal chiamante.
  • Angoli: RotatedRectF::angle e Vec2D::rot() usano radianti e verso antiorario. Nel JSON dei livelli rotRect.angle è invece in gradi: la conversione è eseguita da LevelData.
  • Rettangolo ruotato: toRect() restituisce posizione e dimensioni senza applicare l’angolo. Per ottenere l’AABB che contiene realmente il rettangolo ruotato usa boundingRect(); per la forma effettiva usa vertices().

Collisioni: cosa restituiscono le funzioni

collisionUtils.h offre test geometrici e informazioni di contatto. Lo spostamento degli oggetti, lo sliding e le regole di gameplay restano alle classi del gioco.

Test Quando usarlo
Rect::intersects(), checkCollisionAABB() Sovrapposizione fra rettangoli allineati; il secondo fornisce anche asse e profondità.
checkCollisionSAT() Poligoni convessi, compresi i vertici di un OBB. L’overload con assi già calcolati richiede assi unitari.
DynamicRectVsRect() Collisione continua di un’AABB lungo lo spostamento del passo.

Per DynamicRectVsRect(), il parametro chiamato source_vel deve contenere lo spostamento del passo, quindi normalmente velocity * dt. contact_time esprime la frazione dello spostamento alla quale avviene il contatto, circa nell’intervallo 0–1, con la tolleranza numerica prevista dal test.

Il solo contatto dei bordi non è trattato allo stesso modo da tutte le funzioni: Rect::intersects() e l’overload SAT che calcola gli assi richiedono una sovrapposizione positiva; SAT con assi espliciti ammette anche profondità zero. Inoltre Rect::contains(punto) esclude i punti sul bordo. Scegli il test coerente con il comportamento cercato.

Riferimenti

Clone this wiki locally