2017-09-14 125 views
-2

我在過去幾年中編寫了自己的3D遊戲引擎,並希望將其用於遊戲。地形對象碰撞檢測

我迷迷糊糊accros以下問題:

我在遊戲的多面,但講起一個單一的平面。當然,飛機不能潛入地面並在地形下飛行。因此,我需要實施一些能夠檢測飛機/噴氣機與我的地面之間的碰撞的東西。

給出的信息如下:

  1. 網格地形[2-維陣列;在根據X專賣店高度,z座標]
  2. 擊中格我的飛機(它的動作與我的飛機,所以邊界等等都已經計算和給予)

所以對hitboxes的: 我雖然約使用哪種方法。表現最好的一個似乎是不同半徑的簡單球體。

關於地面:從圖形上看,地面被細分爲三角形: enter image description here

所以我現在需要的是最佳的類型擊中格的(球體,AABB,...),並且根據最有效的計算。

我的嘗試是讓每個周圍的三角形,並計算從那一個到我的hitbox球體的每個中心的距離。如果距離小於半徑,則它已成功檢測到碰撞。但是當我在我的飛機上有多達10/20個球體並且需要檢查100個三角形時,這需要很長時間。

另一個嘗試是從每個hitbox球體獲得與地面的垂直距離。這需要更少的計算,但靠近陡峭的表面時會失敗。

我將非常高興,如果有人願意幫助我實現平面/地形碰撞檢測:)

+0

回答這個問題會非常廣泛。您應該閱讀[Octree](https://en.wikipedia.org/wiki/Octree) - 另請參閱[用於高效碰撞檢測的最佳算法](https:// stackoverflow。com/questions/7107231/best-algorithm-for-efficient-collision-detection-objects-objects)和[八叉樹中的邊界框](https://gamedev.stackexchange.com/questions/25626/bounding-boxes-in- octrees) – Rabbid76

+0

渲染的飛機,你可以在着色器中做到這一點。我假設在對象之前渲染地形,所以一旦你試圖在平面下面渲染平面片段(測試前一次傳遞的預存深度紋理),就會發生碰撞,因此可以將平面ID輸出到某些1D紋理輸出或其他任何東西。這種方式是完美的像素,甚至可以提供命中的位置。 – Spektre

+0

爲了提高我的着色器速度,我預先計算了每個頂點的高度。所以沒有「深度紋理」。我也可能在從我的身高地圖上閱讀後更改頂點位置。 – Luecx

回答

0
  1. 渲染地形的有效版本

    可能是你可以嘗試liner depth buffer以提高精確度。

  2. 讀取深度紋理

    可以使用glReadPixelsGL_DEPTH_COMPONENTGL_FLOAT。這將複製深度緩衝區到CPU側存儲器。所以,現在你也可以做CPU側或鑑於對地有關的任何計算碰撞......

  3. 使用深度緩衝紋理

    所以將它複製回GPUglTexImage2D。我知道這是慢的(但最有可能快得多,那麼你當前的計算碰撞。如果你不使用英特爾高清顯卡你可以代替#2,#3使用FBO深度將直接渲染深度緩衝區質感。但英特爾並不可靠(或全部)工作。

  4. 現在GLSL

    片段着色器裏呈現你的對象(關閉屏幕)只是比較深度渲染位置(附紋理)如果波紋管在某處輸出碰撞,如果在計算着色器中完成,則可以將結果存儲在某個紋理中。或者你可以使用一些附件或FBO爲此。

    如果你不能使用FBO你可以渲染到具有顏色編碼衝突的「屏幕」。然後用glReadPixels讀取它並掃描它以處理你在CPU端有什麼碰撞邏輯...

    不要在此通道中寫入深度緩衝區!也不要使用CULL_FACE,因爲這可能會遺漏物體背面的某​​些碰撞。

  5. 現在渲染的對象正常

    的情況下,你不#4渲染或你編碼碰撞,你需要重寫/渲染的東西屏幕緩衝區。否則,這一步是不需要的。但是在碰撞檢測之後渲染是很好的,因爲在發生碰撞的情況下,最有可能改變對象位置/方向/網格,並且已經渲染的對象可能阻礙了改變的對象。

[注意事項]

複製圖像CPU之間GPU慢所以用FBO如果可以的話,而不是渲染到紋理。

如果你不熟悉多通道渲染看到一些質量檢查的靈感:

這隻在視圖...但你可以做到這碰撞渲染過程(每個對象)。渲染相機設置爲從上到下(birdseye)查看並僅覆蓋對象周圍的區域......此外,您不需要太大的分辨率,因此它應該相對較快...因此,您可以將屏幕分割爲方形區域(使用glViewport)在單幀中測試更多對象以儘可能地減少同步時間的減速(使用更少的glReadPixel調用)。此外,您不需要任何頂點顏色或紋理。