Tarayıcıda açık dünya oluşturmak, bölüm 8: Temel yapımızı kaybetmeden entegrasyon
Yazan: Oleg Sidorkin, Cinevva CTO'su ve Kurucu Ortağı
Burada yeni misiniz? Seri rehberine göz atın. Rehber, denemenin ne olduğunu açıklıyor ve tüm bölümlere bağlantılar sunuyor.
Entegrasyon, projelerin karmaşık hâle geldiği aşamadır. Tek başına çalışan parçalarınız vardır. Bunları birbirine bağladığınızda birdenbire her hata, kaynağı her yerde olabilecekmiş gibi görünür.
- ve 14. denemeler, bu tuzağa verdiğimiz yanıttı. 13. denemede temiz bir Three.js WebGPU temel yapısı oluşturduk. Yalnızca bir işleyici, bir sahne, bir kamera ve basit bir ağ model vardı. Arazi, hesaplama veya efekt yoktu. Three.js'in WebGPU arka ucunun doğru şekilde başlatıldığını, işleme döngüsünün kararlı olduğunu ve TSL (Three.js Shading Language) düğüm malzemelerinin beklendiği gibi çalıştığını doğruladık. Ancak bu kontrol noktasını geçtikten sonra katman eklemeye başladık.
13. denemeyi yeni sekmede aç ↗ · Kaynak kodunu görüntüle
- deneme, aşamalı sağlamlaştırma süreciydi. Her seferinde tek bir yetenek ekledik: önce kamera kontrollerini, ardından aydınlatmayı, sonra marching cubes işlem hattında hesaplamayla üretilen ağ modeli ve son olarak GPU çıktısını doğrudan Three.js geometri niteliklerine aktaran tampon bağlantılarını. Her eklemenin ardından önceki katmanın hâlâ doğru davrandığını doğruladık.
14. denemeyi yeni sekmede aç ↗ · Kaynak kodunu görüntüle
Kulağa yavaş geliyor. Tam olarak bir gün boyunca yavaştı ve kısa süre sonra dikiş mantığı ile politika değiştirme karmaşıklaştığında bize birkaç gün kazandırdı.
Bu disiplini haklı çıkaran belirli hata kategorisi, kıl inceliğindeki bozulmalardı. Geometri bozulması gibi görünen ama aslında güncelliğini yitirmiş verilerden kaynaklanan ince parçacıklar. Hesaplama gölgelendiricisi bir tampona N köşe yazıyor, ancak çizim çağrısı hâlâ önceki kareden kalan N+M köşeyi işleyecek şekilde yapılandırılmış oluyordu. Bu fazladan köşeler, eski gönderimden kalan anlamsız veriler içeriyordu. Görsel sonuç, öngörülemez biçimde belirip kaybolan, titreşen ve jilet inceliğinde üçgenlerdi.
Bu tür bir hatayı sezgiyle yenemezsiniz. Son çalışan durum ile mevcut bozuk durum arasında tam olarak neyin değiştiğini bildiğiniz kontrollü farklarla yenebilirsiniz.
WebGPU entegrasyonu bize tampon yaşam döngüsü hakkında da çok şey öğretti. WebGPU'daki GPU tamponları, belirli bir kullanım için eşlendikten sonra değiştirilemez. Marching cubes çıktısı büyüdüğü için bir köşe tamponunu yeniden boyutlandırmanız gerekiyorsa yeni bir tampon oluşturmalı ve bağlamayı güncellemelisiniz. realloc yoktur. Bu yaşam döngüsünü doğru yönetmek ve eski tamponları yürütülmekte olan GPU işleriyle yarışa girmeden yok etmek, WebGL'de bulunmayan açık bariyer yönetimini gerektiriyordu.
- bölümde Transvoxel dikiş çalışmalarına geçiyoruz. Bu bölüm bilinçli olarak bir iskeletle başlıyor. Bu noktaya geldiğimizde, entegrasyonu aceleye getirmenin gizemli sorunlar; kontrollü kurulumun ise hata ayıklanabilir problemler ürettiği dersini tamamen benimsemiştik.
Bu bölümde değinilen teknolojiler
WebGPU. WebGL'in halefi olan ve hesaplama gölgelendiricileri ile dolaylı işleme aracılığıyla tarayıcıda düşük seviyeli GPU erişimi sağlayan teknoloji. WebGPU'nun açık dünyalar açısından kritik iki özelliği şunlardır: hesaplama gölgelendiricileri, arazi üretiminin, bitki örtüsü yerleştirmenin ve ayıklamanın GPU tarafında yapılmasını sağlar; dolaylı işleme ise GPU'nun hesaplama çıktısına göre neyi çizeceğine karar vermesine olanak tanıyarak yoğun sahnelerdeki CPU darboğazlarını ortadan kaldırır. Masaüstünde Chrome, Edge ve Firefox'ta kullanılabilir. Bkz. Performans kilidini açan WebGPU.
Three.js Shading Language (TSL). Ham GLSL/WGSL'nin yerine birleştirilebilir JavaScript ifadeleri kullanan, Three.js'in düğüm tabanlı gölgelendirici sistemi. texture(), positionWorld, smoothstep() ve fog() gibi TSL düğümleri, çalışma zamanında uygun arka uç için (WebGL GLSL veya WebGPU WGSL) derlenen bir gölgelendirici grafiği oluşturur. TSL, malzeme mantığını bir kez yazıp her iki işleyiciyi de hedeflemeyi mümkün kılar. Düğüm grafiği her karede değerlendirilir; dolayısıyla dinamik uniform değişkenler ve koşullu dallanma doğal biçimde çalışır.
WebGPU'da GPU tamponu yaşam döngüsü. WebGPU tamponları belirli kullanım bayraklarıyla (VERTEX, STORAGE, COPY_DST vb.) oluşturulur ve oluşturulduktan sonra yeniden boyutlandırılamaz. Bir marching cubes gönderimi tamponun kapasitesinden daha fazla köşe üretirse yeni bir tampon oluşturmanız, bağlamayı güncellemeniz ve eskisini yok etmeniz gerekir. Yürütülmekte olan bir GPU komutunun hâlâ başvurduğu tamponu yok etmek hatalara neden olur. Açık bariyer yönetimi (device.queue.onSubmittedWorkDone() aracılığıyla), eski tamponun GPU tarafından kullanımı tamamlanmadan yok edilmemesini sağlar. Sürücünün belleği örtük olarak yönettiği WebGL'de böyle bir yaşam döngüsü disiplini yoktur.
Aşamalı sağlamlaştırma. Entegrasyona yönelik bir süreç disiplini: çalıştığı bilinen bir temel yapı oluşturun, her seferinde tek bir yetenek ekleyin ve her eklemeden sonra önceki katmanın hâlâ çalıştığını doğrulayın. Bu yaklaşım bir günlüğüne daha yavaştır, ancak sonraki hata ayıklama çalışmalarında günler kazandırır; çünkü her gerileme belirli ve kontrollü bir değişikliğe kadar izlenebilir. Önce temel yapı, ardından aşamalı ekleme yaklaşımı; riski yönetmek amacıyla sistemlerin belirli bir sırayla entegre edildiği AAA açık dünya geliştirme süreçlerinde yaygındır.
12 bölümün 8. bölümü.
Önceki: Bölüm 7 - Marching cubes ve ilk gerçek mağaralar
Sonraki: Bölüm 9 - Transvoxel bir iskeletle başladı
Seri rehberi: /blog/2026-02-25-open-world-browser-series-guide