Gunakan jumlah Minkowski
Cara yang baik untuk menyelesaikan masalah ini adalah dengan mempertimbangkan persimpangan antara garis gerak ( v ) yang diterjemahkan ke titik asal ( v ' ) dan jumlah Minkowski dari A yang diputar 180 derajat pada titik asal ( A' ) dan rintangannya (hanya B dalam kasus ini): A' ⊕ B .
Dalam gambar berikut saya tempat A smack-dab di asal sewenang-wenang sistem koordinat. Ini menyederhanakan pemahaman karena memutar A sebesar 180 derajat menghasilkan A ' , dan v yang diterjemahkan ke asal sama dengan v' .
Jumlah Minkowski adalah persegi panjang hijau, dan titik persimpangan A bergerak dan B stasioner dapat ditemukan dengan melakukan persimpangan garis-AABB . Titik-titik ini ditandai dengan lingkaran biru.
Dalam gambar berikut asal yang berbeda digunakan dan titik persimpangan yang sama ditemukan.
Beberapa AABB bergerak
Untuk membuat karya ini untuk dua AABBs bahwa langkah secara linear selama periode waktu tertentu Anda akan kurangi B 's kecepatan vektor dari A ' vektor kecepatan dan penggunaan yang sebagai segmen garis untuk persimpangan line-AABB.
Kode palsu
def normalize(aabb):
return {x1: min(aabb.x1, aabb.x2), x2: max(aabb.x1, aabb.x2),
y1: min(aabb.y1, aabb.y2), y2: max(aabb.y1, aabb.y2),
def rotate_about_origin(aabb):
return normalize({x1: -aabb.x1, x2: -aabb.x2
y1: -aabb.y1, y2: -aabb.y2})
# given normalized aabb's
def minkowski_sum(aabb1, aabb2):
return {x1: aabb1.x1+aabb2.x1, x2: aabb1.x2+aabb2.x2,
y1: aabb1.y1+aabb2.y1, y2: aabb1.y2+aabb2.y2}
def get_line_segment_from_origin(v):
return {x1: 0, y1: 0, x2: v.x, y2: v.y}
def moving_objects_with_aabb_intersection(object1, object2):
A = object1.get_aabb()
B = object2.get_aabb()
# get A'⊕B
rotated_A = rotate_about_origin(A)
sum_aabb = minkowski_sum(rotated_A, B)
# get v'
total_relative_velocity = vector_subtract(object1.get_relative_velocity(), object2.get_relative_velocity())
line_segment = get_line_segment_from_origin(total_relative_velocity)
# call your favorite line clipping algorithm
return line_aabb_intersection(line_segment, sum_aabb)
Respon tabrakan
Bergantung pada gameplay Anda akan melakukan deteksi tabrakan lebih halus (mungkin AABB mengandung jerat), atau bergerak maju ke fase berikutnya: respon tabrakan.
Ketika ada tabrakan, algoritma garis-AABB-persimpangan akan mengembalikan 1 atau 2 titik persimpangan tergantung pada apakah A mengakhiri gerakannya di dalam B atau melewatinya, masing-masing. (Ini mengabaikan kasus yang merosot di mana A menyerempet B di sepanjang sisinya atau di salah satu sudutnya masing-masing.)
Either way, titik persimpangan pertama sepanjang segmen garis adalah titik tumbukan, Anda akan menerjemahkan ini kembali ke posisi yang benar dalam sistem koordinat dunia (lingkaran biru muda pertama di gambar kedua sepanjang v asli , sebut saja p ) dan kemudian memutuskan (misalnya, untuk tumbukan elastis dengan merefleksikan v sepanjang tumbukan normal pada p ) apa posisi sebenarnya untuk A pada akhir bingkai akan ( Pada +1 ).
Jika ada lebih dari 2 colliders, ini akan menjadi sedikit lebih rumit, karena Anda ingin melakukan deteksi tabrakan untuk bagian kedua, yang direfleksikan, dari v juga.