Sanal gerçeklik web'e geliyor

Sizi sürükleyici deneyimlere hazırlayacak bazı temel bilgiler: sanal gerçeklik, artırılmış gerçeklik ve bu ikisi arasındaki her şey.

Joe Medley
Joe Medley

Etkileyici deneyimler Chrome 79'da web'de yerini aldı. WebXR Device API, sanal gerçekliğin getirdiği sanal gerçekliği getirirken artırılmış gerçeklik desteği Chrome 81'de sunulmaya başlandı. GamePad API'deki güncellemeyle birlikte kontrollerin gelişmiş kullanımı VR da olacak. Firefox Reality, Oculus Tarayıcı, Edge ve Magic Leap'in Helio tarayıcısı gibi başka tarayıcılar da yakında bu özellikleri desteklemeye başlayacak.

Bu makale, web'de bir serinin başlangıcıdır. Bu taksit, temel bir WebXR uygulamasının kurulumunun yanı sıra XR oturumuna girme ve oturumdan çıkma konularını kapsamaktadır. Sonraki makalelerde çerçeve döngüsü (WebXR deneyiminin çalışma alanı), artırılmış gerçekliğin özellikleri ve AR oturumundaki yüzeyleri algılama aracı olan WebXR Hit Test API ele alınacaktır. Aksi belirtilmedikçe, bu ve sonraki makalelerde ele aldığımız her şey hem AR hem de VR için eşit derecede geçerlidir.

Gerçekçi web nedir?

Üç boyutlu deneyimleri (artırılmış gerçeklik ve sanal gerçeklik) tanımlamak için iki terim kullansak da, birçok kişi bu deneyimleri tam gerçeklikten tamamen sanala kadar bir yelpazede düşünüyor. Ancak bu iki terimin arasında içine dalmak var. XR'deki "X", sürükleyici deneyimler aralığındaki herhangi bir şeyi temsil eden bir tür cebirsel değişken olarak bu düşünmeyi yansıtmayı amaçlamaktadır.

Eksiksiz gerçeklikten tamamıyla etkileyicine kadar farklı görsel deneyimleri gösteren bir grafik.
Etkileyici deneyim yelpazesi

Etkileyici deneyimlere örnek olarak aşağıdakiler verilebilir:

  • Oyunlar
  • 360° videolar
  • Üç boyutlu bir ortamda sunulan geleneksel 2D (veya 3D) videolar
  • Ev satın alma
  • Satın almadan önce evinizdeki ürünleri görüntüleme
  • Etkileyici sanat
  • Henüz kimsenin aklına gelmeyen harika bir şey

Kavramlar ve kullanım

WebXR Device API'nin kullanımıyla ilgili bazı temel bilgileri açıklayacağım. Sağladığımdan daha fazla derinliğe ihtiyacınız varsa Immersive Web Working Group'un WebXR örneklerine veya MDN'nin büyüyen referans materyallerine göz atın. WebXR Device API'nin önceki sürümleri hakkında bilginiz varsa bu bilgilerin tamamına göz atmalısınız. Değişiklikler yapıldı.

Bu makaledeki kod, Immersive Web Working Group'un temel örneğine (demo, source) dayanmaktadır ancak daha anlaşılır ve sade olması için düzenlenmiştir.

WebXR spesifikasyonu oluşturma sürecinin bir parçası da, kullanıcıları korumak amacıyla güvenlik ve gizlilik önlemlerini geliştirmektir. Sonuç olarak, uygulamalar belirli gereksinimlere uymalıdır. Bir web sayfasının veya uygulamanın, görüntüleyenden hassas bir şey isteyebilmesi için etkin ve odaklanmış olması gerekir. Web sayfaları veya uygulamalar HTTPS üzerinden sunulmalıdır. API'nin kendisi, sensörlerden ve kameralardan elde edilen ve çalışması için gereken bilgileri koruyacak şekilde tasarlanmıştır.

Oturum iste

XR oturumuna girmek için kullanıcı hareketi gerekir. Özellik algılamayı kullanarak XRSystem için test yapın (navigator.xr üzerinden) ve XRSystem.isSessionSupported() numaralı telefonu arayın. Chrome 79 ve 80 sürümlerinde XRSystem nesnesinin XR olarak adlandırıldığını unutmayın.

Aşağıdaki örnekte, 'immersive-vr' oturum türünde bir sanal gerçeklik oturumu istediğimi belirtmiştim. Diğer oturum türleri 'immersive-ar' ve 'inline''dir. Satır içi oturum, HTML içerisinde içerik sunmak için kullanılır ve genellikle teaser içeriği için kullanılır. Immersive AR Session örneği bunu göstermektedir. Bunu sonraki bir makalede açıklayacağım.

Sanal gerçeklik oturumlarının desteklendiğini öğrendikten sonra, kullanıcı hareketi kazanmamı sağlayan bir düğmeyi etkinleştiriyorum.

if (navigator.xr) {
  const supported = await navigator.xr.isSessionSupported('immersive-vr');
  if (supported) {
    xrButton.addEventListener('click', onButtonClicked);
    xrButton.textContent = 'Enter VR';
    xrButton.enabled = supported; // supported is Boolean
  }
}

Düğmeyi etkinleştirdikten sonra, bir tıklama etkinliğini bekleyip oturum isteğinde bulunuyorum.

let xrSession = null;
function onButtonClicked() {
  if (!xrSession) {
    navigator.xr.requestSession('immersive-vr')
    .then((session) => {
      xrSession = session;
      xrButton.textContent = 'Exit XR';
      onSessionStarted(xrSession);
    });
  } else {
    xrSession.end();
  }
}

Bu koddaki nesne hiyerarşisine dikkat edin. navigator konumundan xr konumuna, XRSession örneğine taşınır. API'nin önceki sürümlerinde, bir komut dosyasının oturum isteğinde bulunmadan önce cihaz isteğinde bulunması gerekiyordu. Artık cihaz dolaylı yoldan ediniliyor.

Bir oturum girin

Bir oturum aldıktan sonra, oturumu başlatmam ve girmem gerekir. Ama önce birkaç şey kurmam gerekiyor. Bir oturumda onend etkinlik işleyicisinin olması gerekir. Böylece, kullanıcı çıkış yaptığında uygulama veya web sayfası sıfırlanabilir.

Ayrıca, sahnemi çizmek için bir <canvas> öğesine de ihtiyacım olacak. XR uyumlu bir WebGLRenderingContext veya WebGL2RenderingContext olmalıdır. Tüm çizim, bunlar veya Three.js gibi WebGL tabanlı bir çerçeve kullanılarak yapılır.

Artık çizim yapabileceğim bir yer olduğuna göre, bu yerden çizim yapmak için bir içerik kaynağına ihtiyacım var. Bunun için XRWebGLLayer örneği oluşturuyorum. XRSession.updateRenderState() yöntemini çağırarak tuval ile ilişkilendiriyorum.

Bir oturuma girdiğimde, her şeyin sanal gerçeklikte nerede olduğunu belirlemenin bir yolunu bulmam gerekiyor. Referans alanına ihtiyacım var. 'local-floor' referans alanı, başlangıç noktasının görüntüleyicinin yakınında olduğu ve y ekseninin taban seviyesinde 0 olduğu ve hareket etmesi beklenmeyen bir yerdir. Başka referans alanı türleri de vardır, ancak bu burada girebileceğimden daha karmaşık bir konudur. Referans alanını bir değişkene kaydediyorum, çünkü ekrana çizim yaparken buna ihtiyacım var.

function onSessionStarted(xrSession) {
  xrSession.addEventListener('end', onSessionEnded);

  let canvas = document.createElement('canvas');
  webGLRenContext = canvas.getContext('webgl', { xrCompatible: true });

  xrSession.updateRenderState({
    baseLayer: new XRWebGLLayer(xrSession, webGLRenContext)
  });

  xrSession.requestReferenceSpace('local-floor')
  .then((refSpace) => {
    xrRefSpace = refSpace;
    xrSession.requestAnimationFrame(onXRFrame);
  });
}

Bir referans alanı aldıktan sonra XRSession.requestAnimationFrame() numarasını aradım. Bu, sanal içerik sunmanın başlangıcıdır ve bu işlem çerçeve döngüsünde gerçekleştirilir.

Kare döngüsü çalıştırma

Çerçeve döngüsü, içeriğin ekrana sürekli olarak çizildiği, kullanıcı aracısı kontrol eden bir sonsuz döngüdür. İçerik, çerçeve adı verilen ayrı bloklar halinde çizilir. Karelerin ardışık olarak hareket etmesi hareket illüzyonu yaratır. VR uygulamalarında saniyedeki kare sayısı 60 ile 144 arasında bir değer olabilir. Android için artırılmış gerçeklik (AR) saniyede 30 kare hızında çalışır. Kodunuz belirli bir kare hızı tahmininde bulunmamalıdır.

Çerçeve döngüsü için temel süreç şu şekildedir:

  1. XRSession.requestAnimationFrame() Hizmetleri İçin Arayın. Buna yanıt olarak, kullanıcı aracısı sizin tarafınızdan tanımlanan XRFrameRequestCallback yöntemini çağırır.
  2. Geri çağırma işlevinizin içinde:
    1. XRSession.requestAnimationFrame() adlı kişiyi tekrar arayın.
    2. İzleyicinin pozunu çekin.
    3. WebGLFramebuffer öğesini XRWebGLLayer ile WebGLRenderingContext arasında aktarın ("bağlayın").
    4. Her XRView nesnesini yineleme yaparak XRWebGLLayer nesnesinden XRViewport öğesini alın ve WebGLRenderingContext öğesine iletin.
    5. Çerçeve arabelleğine bir şey çizin.

Bu makalenin geri kalanında, 1. adım ile 2. adımın bir kısmı olan XRFrameRequestCallback öğesinin kurulumu ve çağrılması açıklanmaktadır. 2. adımın diğer öğeleri 2. bölümde ele alınmıştır.

XRFrameRequestCallback

XRFrameRequestCallback sizin tarafınızdan tanımlanır. İki parametre alır: DOMHighResTimeStamp ve XRFrame örneği. XRFrame nesnesi, ekranda tek bir kare oluşturmak için gereken bilgileri sağlar. DOMHighResTimeStamp bağımsız değişkeni ileride kullanılabilir.

Başka bir işlem yapmadan önce bir sonraki animasyon karesini istiyorum. Daha önce belirtildiği gibi, karelerin zamanlaması temel donanıma dayalı olarak kullanıcı aracısı tarafından belirlenir. Önce bir sonraki kareyi istemek, geri çağırma sırasında bir hata verirse çerçeve döngüsünün devam etmesini sağlar.

function onXRFrame(hrTime, xrFrame) {
  let xrSession = xrFrame.session;
  xrSession.requestAnimationFrame(onXRFrame);
  // Render a frame.
}

Bu noktada görüntüleyen için bir şeyler çizmenin zamanı gelmiştir. Bu 2. bölümde konuştuk. Bu bölüme geçmeden önce size oturumları nasıl sonlandıracağınızı göstereyim.

Oturumu sonlandır

Tam sayfa oturum, XRSession.end() numaralı telefona yapılan bir çağrı aracılığıyla kendi kodunuzla sona erdirme de dahil olmak üzere çeşitli nedenlerle sonlandırılabilir. Diğer nedenler arasında mikrofonlu kulaklığın bağlantısının kesilmesi veya başka bir uygulamanın mikrofonun kontrolünü ele geçirmesi yer alır. Bu nedenle iyi çalışan bir uygulama end etkinliğini izlemelidir. Oturumu ve oturumla ilgili oluşturma nesnelerini silin. Sonlandırılan yoğun içerik oturumu devam ettirilemez. Gerçekçi deneyime yeniden girebilmek için uygulamamın yeni bir oturum başlatması gerekiyor.

Oturum girme bölümünde, kurulum sırasında bir onend etkinlik işleyici eklediğimi hatırlıyorum.

function onSessionStarted(xrSession) {
  xrSession.addEventListener('end', onSessionEnded);
  // More setup…
}

Etkinlik işleyicinin içinde, kullanıcının oturum girmeden önceki durumunu geri yükleyin.

function onSessionEnded(event) {
  xrSession = null;
  xrButton.textContent = 'Enter VR';
}

Sonuç

Web XR veya AR uygulaması yazmak için ihtiyacınız olan her şeyi açıklamadım. Umarım size kodu anlamaya ve denemeye başlamaya yetecek kadar vakit ayırabilmişimdir. Bir sonraki makalede, içeriğin ekrana çizildiği çerçeve döngüsünü açıklayacağım.

Fotoğraf: JESHOOTS.COM Unsplash'ta