Konuyu Oyla:
  • Derecelendirme: 0/5 - 0 oy
  • 1
  • 2
  • 3
  • 4
  • 5
Hangi işlemleri multithread ile bölebiliriz?
#1
Question 
Herkese merhaba benim ustalara bir sorum olacak. Önce yapmak istediğimi anlatayım.

Yaklaşık 4 gündür ileride kullanmayı düşündüğüm bir özellik üzerine araştırmalar yapıyorum. Sonsuz prosedürel oluşturma ve zeminle oyun içinde oynama. Unreal Engine de bu özellik yok. Voxel Plugin pro ile bunu yapabiliyorsun fiyatı sanırım 3000 TL ye yakın tutuyordu. Bir plugin ile yapılabiliyorsa bir yolu var demek ki dedim ve nasıl yapabilirim araştırmaya başladım. Sonuç olarak procedural mesh component ile gayet güzel yapabildim.

Süreç basitçe şöyle: Birkaç kaç farklı frekanstaki perlin noise üst üste birleştirilip bir zemin yapılabiliyor. Tabi bu çok sıradan görünüyor. Gerçekçi ve daha dramatik dağlar ve zeminler için varyasyon ve biraz daha modifiye bir fonksiyon lazımdı. World creator 2 de her katmanı detaylı incelemeye çalıştım. Gördüm ki küçük detaylar yamaçları daha çok etkileyecek şekilde kodlanmış. Eğimin olmadığı yerler daha düzgün kalıyor. Filtreler de yamaçları daha çok etkiliyor.

Yani bir şekilde perlin noise fonksiyonunda yamaçta olduğunu anlayıp ona göre küçük detayların etkisini değiştirecek bir şekilde modifiye ettim. Şu an oynanıp kurulabilecek genişlikte düz pürüzsüz zeminler de pürüzlü düzensiz yamaçlar elde edebiliyorum.

Kod şu şekilde isteyen varsa:

Alıntı:// Main custom procedural noise function

float AProceduralTerrain::CustomProceduralNoise(const float fx, const float fy, const FNoiseParameters& parameters)
{
float fxLocal = fx;
float fyLocal = fy;
float amplitutude = 0.5f;
float gain = parameters.gain;
float lacunarity = parameters.lacunarity;
float value = 0.5f;
int32 octaves = parameters.octave;

float octave2Height = 0.0f;
float slopeAmplitude = 1.0f;

for (int i = 0; i <octaves; i++)
{

value += FMath:TongueerlinNoise2D(FVector2D(fxLocal, fyLocal))*amplitutude*slopeAmplitude;
fxLocal *= lacunarity;
fyLocal *= lacunarity;
amplitutude *= gain;
if (i == 1)
{
octave2Height = value;
slopeAmplitude = GetSlopeAmplitude(octave2Height, parameters);
slope = octave2Height;
}
}

return value;
}


Bu fonksiyondan çıkan noise değeri -1 ile 1.5 arasında değişebiliyor. Bunu bir maksimum yükseklik değeriyle çarpıp hesaplanan noktanın X, Y koordinatını girince bize bir vertex vermiş oluyor. 

Bu fonksiyonu şöyle çağırıyoruz. Diyelim ki 100 metre * 100 metre bir alan yaratacağız. her vertex arası 1 metre olursa size X = 100, sizeY = 100 oluyor. Her bir nokta için bir hesaplama yapacağız. Bir hesaplamada 10.000 loop eder. Bu 10 bin loop içinde bir de 5-7 tane oktav hesaplayacağız olacak size 50.000-100.000 arası hesaplama.

Bitmedi bir de bu hesaplanan noktaları birbirine bağlayıp triangle yapcağız. Sonra UV hesaplayıp normal ve tanjantlarını hesaplayıp procedural mesh componentte create mesh section deyip bir de bu büyüklükte alan için colision ayarlatacağız. 1 milyona yaklaşıyor hesaplama sayısı.

Peki bu işlem kaç saniye sürüyor derseniz yaklaşık 5-6 saniye kitliyor oyunu. Ayrıca 150*150 ve üzeri büyüklükte iterasyon 1 milyonu geçti deyip hesaplamıyor bile. Başka sorunlar da var LOD ayarlayamamak gibi.

Çıkan sonucun resmi şu şekilde:[img]i9oixr8.png[/img]

Araştırmaya devam edip voxel plugin bunu nasıl yapmış diye anlamaya çalıştım. Multithread ile arka planda yaptığını düşünüyordum. Free versiyonunu indirdim ve ufak chunklara bölünmüş şekide. Her tik bir chunk güncelleniyor gibi. Güncelleme işlemi başka threadda yapılıyor gibi.

Bende 100*100 yerine 20*20 yapayım dedim ve her tick bir chunk hesaplanıp haritaya eklenecekti. Bu sandığımdan hızlı oldu ve her bir hesaplama yaklaşık 2ms tuttu ve fps'e etki bile etmedi. 2-3 saniye içinde 300-400 chunk güncelleyip yaratabildim.

Bir gözlem daha yapmak için sadece hesaplamalar kaç ms tutuyor diye baktım. Tüm o vektör hesaplamaları matematiksel işlemler 1ms tutuyor, 1ms de komponentin yaratılması tutuyor. 

Şimdi sorum şu. Ben bu işlemin neresini, ne kadarını başka threadda yapabilirim? Hiç detaylı bir bilgi bulamadım bununla alakalı. Diğer threadlarla direkt iletişim kuramadığımızı, crash yedirecek riskler olduğunu biliyorum. Ama meraktan bu bu threadlara ramdeki adres bilgilerini aktarabiliyorsak bu threadda referans gönderip değişiklik yapabiliyor muyuz diye baktım. Bazıları evet diyor, bazıları yapmayın diyor. Ama sonunda şunu okudum. Procedural mesh componentte create mesh section fonksiyonu game threadda çağırılmak zorundaymış o yüzden o 1ms her türlü bana mal olacak.

Peki ben bu matematiksel vektör hesaplamalarını başka threadda yapıp sonra game threadda nasıl kullanacağım? Bu konuda hiç tecrubem yok. Neyin ne kadarını yapabilirim aydınlatabilirseniz çok sevinirim.
Ara
Cevapla
#2
Acemi olduğum için çok az bir şeyler anladım ama helal olsun dostum. Mükemmel olmuş.
I make games.
Ara
Cevapla
 


Hızlı Menü:


Konuyu Okuyanlar: 1 Ziyaretçi

Unreal Engine Türkiye

This forum is community driven and supported by voluntary community members. It has nothing to do with Epic Games.

Bu site sadece destek amaçlıdır. Epic Games ile bir ilgisi yoktur.