OBB ve OBB Çarpışma Tespiti


20

Her birinin, bir kutunun geçerli köşelerini bir vektörde saklayan iki adet Sınırlayıcı Kutu Nesneniz olduğunu varsayalım, nesnenin tüm köşeleri ortak bir eksene göre döndürülür ve çevrilir.

İşte benim sorunumu göstermek için bir görüntü:

Sorunun çözümünün açıklanmasına yardımcı olmak için iki OBB'nin herhangi bir bağlantıyla çakışması durumunda nasıl çalışabilirim. Çok kıvrık bir şey lütfen ...

Yanıtlar:


16

Bir OBB dışbükey bir gövdedir. Dışbükey bir gövde, yüzeyinde "çatlak" bulunmayan 3D bir şekildir. Dışbükey gövdedeki her "çarpma" (tepe noktası) dışa doğru çıkıntı yapar , asla içe doğru uzanmaz. Bir düzlemi dışbükey bir gövdeden keserseniz, (sadece bir) dışbükey çokgen elde edersiniz. Dışbükey bir teknenin içindeyseniz ve dışa dönük bir lazer atarsanız, gövdenin yüzeyine sadece bir kez (asla iki kez) yumruk atacaksınız .

Ayırıcı Eksen Teoremi testi, dışbükey gövdelerin çarpışmasını tespit etmek için kullanılabilir. SAT testi basittir. 2D ve 3D olarak çalışır. Aşağıdaki resimler 2B olsa da, 3B'ye de kolayca uygulanabilir.

kavram

SAT ile kullandığınız anahtar kavram budur:

  • İki şekil, yalnızca her iki şeklin her normal eksenine "yansıtıldığında" çakışırsa kesişir .

1D vektörüne bir şeklin "izdüşümü" şuna benzer (buna "ezilme" diyorum)

Kırmızı verts ve eksen içeren bir şekil

resim açıklamasını buraya girin

"Şekli eksene yansıtmak", şeklin üzerindeki her noktadan yalnızca eksene inmek için dikey olarak düşmek anlamına gelir. Bunu, her şeyi toplayan ve onu eksene dik olarak ezen bir el ile noktaları "ezmek" olarak düşünebilirsiniz.

resim açıklamasını buraya girin

Ne kaldı: Eksendeki noktalar

resim açıklamasını buraya girin

SAT diyor ki:

Kesişen 2 dışbükey gövde için, her eksende üst üste binmek zorundadırlar ( her iki şekildeki her normal, kontrol etmemiz gereken bir eksen olarak sayılır).

Şu 2 şekli al:

resim açıklamasını buraya girin

Kesişmediklerini görüyorsunuz, bu yüzden çakışma olmadığını göstermek için birkaç ekseni deneyelim .

Pentagonun en normalini denemek:

resim açıklamasını buraya girin

Bunlar uzantılar. Üst üste biniyorlar.

resim açıklamasını buraya girin

Dikdörtgenin sol tarafını deneyin. Şimdi bu eksende örtüşmüyorlar, bu nedenle KESİNTİSİZ YOK.

resim açıklamasını buraya girin

Algoritma:

Her iki şekil için normal olan her yüz için:

  • Her iki şeklin tüm köşe köşe noktalarının o eksene yansıtılmasının minimum ve maksimum genişliklerini (en büyük ve en küçük değer) bulun
  • Eğer üst üste binmezlerse, kesişme olmaz .

Ve bu gerçekten. SAT çalışmasını sağlayan kod çok kısa ve basittir.

Bir SAT ekseni projeksiyonu nasıl yapılacağını gösteren bazı kodlar:

void SATtest( const Vector3f& axis, const vector<Vector3f>& ptSet, float& minAlong, float& maxAlong )
{
  minAlong=HUGE, maxAlong=-HUGE;
  for( int i = 0 ; i < ptSet.size() ; i++ )
  {
    // just dot it to get the min/max along this axis.
    float dotVal = ptSet[i].dot( axis ) ;
    if( dotVal < minAlong )  minAlong=dotVal;
    if( dotVal > maxAlong )  maxAlong=dotVal;
  }
}

Telefon kodu:

// Shape1 and Shape2 must be CONVEX HULLS
bool intersects( Shape shape1, Shape shape2 )
{
  // Get the normals for one of the shapes,
  for( int i = 0 ; i < shape1.normals.size() ; i++ )
  {
    float shape1Min, shape1Max, shape2Min, shape2Max ;
    SATtest( normals[i], shape1.corners, shape1Min, shape1Max ) ;
    SATtest( normals[i], shape2.corners, shape2Min, shape2Max ) ;
    if( !overlaps( shape1Min, shape1Max, shape2Min, shape2Max ) )
    {
      return 0 ; // NO INTERSECTION
    }

    // otherwise, go on with the next test
  }

  // TEST SHAPE2.normals as well

  // if overlap occurred in ALL AXES, then they do intersect
  return 1 ;
}

bool overlaps( float min1, float max1, float min2, float max2 )
{
  return isBetweenOrdered( min2, min1, max1 ) || isBetweenOrdered( min1, min2, max2 ) ;
}

inline bool isBetweenOrdered( float val, float lowerBound, float upperBound ) {
  return lowerBound <= val && val <= upperBound ;
}

Hullinator dışbükey tekneler için SAT testini uygular
bobobobo

harika bir açıklama! Teşekkürler. Sana doğrultusunda bir yazım hatası olabilir düşünüyorum: o zaman nerede örnekler vermek geçin çünkü "bu yüzden bir örtüşme olmaz idi göstermek için birkaç eksenleri deneyelim." Do örtüşme. Tekrar teşekkürler!

Testleri normalin tüm çapraz ürünleri için de yapmanıza gerek yok mu? Bu yazı geometriktools.com/Documentation/DynamicCollisionDetection.pdf öyle diyor.
iNFINITEi

Bu özel SAT yönteminin yalnızca 2D'de çalıştığını belirtmek gerekir. 3D'de her yüzün normallerinden daha fazlasını elde etmeniz gerekir. Doğru normlara sahip olduğunuzda, sürecin geri kalanı (proje, karşılaştırma) tamamen aynıdır.
Monica'nın Davası

2D resimlerinizden okların hangi yöne gittiğini söylemek gerçekten zor.
WDUK

7

Ayırıcı Eksen Teoremini mutlaka aramalısınız . Dışbükey nesneler için. Bir kural vardır: "Eğer iki dışbükey nesne kesişmezse, o zaman bu iki nesnenin izdüşümünün kesişmeyeceği bir düzlem vardır".

Wiki'de bazı örnekler bulabilirsiniz . Ama durumunuzdan biraz daha karmaşık.

Sorununuz için daha uygun bir şey burada bulunabilir (iki araba çarpışıyor).


1

Diğer SAT makaleleri.

Bu sitedeki son makale tam kod ile geliyor, ben FLASH olduğunu düşünüyorum, hiçbir fikrim yok, ama ben ilk kez SAT kullanmak zorundayken C ++ dönüştürmek tam 0 sorunları vardı, zor olmamalı aynısını diğer diller için de yapın. Eklemeniz gereken tek şey, her hesaplamada yer değiştirme vektörünün depolanmasıdır (eğer en küçük, tabii ki, SAT hakkında bilgi edinirken bunu anlayacaksınız), bu öğreticideki kod bunu yapmaz, bu yüzden son hesaplanan vektör ile sonuçlanır.

http://rocketmandevelopment.com/tag/separation-axis-theorem/

İyi, eski N-Game öğreticileri. Web'deki en iyi SAT teorisi.

http://www.metanetsoftware.com/technique/tutorialA.html


Kimse gerekli tüm sınıflarla tam çalışma kaynağını yayınlamıyor. Kodunu kendime ait bir demoya taşıdım ama işe yaramıyor. :( Bu benim projem şimdiye kadar kimse bana hata ayıklama yardımcı olabilir harika olurdu link
Joshua Barnett

ne işe yaramaz demek istiyorsun? köşelerinizi nasıl sakladığınıza dikkat edin, onları kartezyen bir koordinat sistemine sahip olduğunuz görüntüde, öğreticide köşeleri centroide göre vektörler olarak saklar (tek yapmanız gereken centroid'i kendi köşelerinizden çıkarmak veya kendi köşelerini değiştirdiği çizgileri kaldırın), kendiniz oluşturabileceğiniz nokta ürünü gibi işlevler, bunlar için bir rehbere ihtiyacınız yoktur, geri kalanı düz olmalıdır, bir kopya yapıştır malzemesi değildir, uygulamayı denemeden önce SAT öğrenin
dreta

Bunu nasıl uyguladım: SAT.as , Shape2D.as , Centroid ile ne demek istiyorsun? (X, y) gibi çokgenin merkezi?
Joshua Barnett

Şu anda orijinal görüntümde ayrıntılı olarak köşeleri döndüren bir getOBB () fonksiyonum var. Bu, şeklin köşe noktalarını, bir açı değişkenini ve bir pozisyon değişkenini içeren bir Vector <b2Vec2> 'den hesaplanır.
Joshua Barnett

evet, merkez, bu adamın çokgenlerini yaratma şekli merkezden ofsetler vermektir, idk AS3, ama gördüğüm kadarıyla, köşelerinizi oldukları gibi yansıttığınızı, nokta ürünü hesaplarken, centroidi köşe noktalarından çıkarmaya çalışın (vektör çıkarma) ), bunun yanında hangi ayırma vektörünün en küçük olduğunu kontrol etmiyorsunuz, sadece hesaplanan
sonuncuyu kaydediyorsunuz
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.