2016-06-27 9 views
1

Ich implementiere einen Blickalgorithmus für ein VR-Projekt in Unity3D. Bisher habe ich hier Physics.Raycast gefunden und die BoxCollider2D-Komponente mit jedem Button-Objekt hinzugefügt, um festzustellen, ob der Benutzer es betrachtet. Ich möchte Raycast vermeiden, weil es teuer ist und Leistungsprobleme verursachen kann, da ich eine sehr komplexe UI-Struktur habe.Alternative von Raycast für UI-Elemente in Unity3D

Ich habe versucht, Cursor Lock verwenden, aber leider ist es nicht für mobile Plattform.

Ich habe auch versucht Zentrum des Kameraansichtsfensters von

Camera.main.ViewportToWorldPoint(new Vector3(0.5f,0.5f,Camera.main.nearClipPlane));

erschaffene Welt Punkt zu überprüfen, ob rect von Button-Objekt enthält Es funktioniert gut, wenn das Objekt der Schaltfläche rect als Mittelzentrum verankert ist verwandeln. Aber funktioniert nicht, wenn es andere Einstellungen hat oder wenn die Taste ein wenig gekippt ist (in der Welt-Raum-Leinwand). Und ich bin nicht sehr vertraut damit, wie die Rect-Transformation funktioniert und wie sie ihre exakte Position im Weltall findet.

Kennt jemand die Lösung? Oder gibt es einen anderen Weg, dies zu tun?

Alle Arten von Hilfe wird sehr geschätzt.

+1

Ich weiß nicht, ob Sie Oculus tun oder nicht, aber das ist eine gute sowieso lesen https://developer.oculus.com/blog/unitys-ui-system -in-vr/ –

+0

Ich habe das Beispielprojekt von Unity überprüft und es ist in der BaseRaycaster-Klasse von Event System implementiert. –

Antwort

0

Ich erkannte das Problem, es waren andere Werte in der Z-Achse verursacht Problem. Lösung nach funktioniert ohne Physics.Raycast mit:

void Update() 
{ 
    pos = Camera.main.ViewportToWorldPoint(new Vector3(0.5f,0.5f,Vector3.Distance(transform.position,Camera.main.transform.position))); 
    _rect = new Rect(pos.x-size,pos.y-size,size,size); 

    _rect2 = new Rect(transform.position.x-rt.rect.width/2,transform.position.y-rt.rect.height/2,rt.rect.width,rt.rect.height); 

    Hit = _rect2.Overlaps(_rect); 

    if(Hit) 
    { 
     if (!isEntered) 
     { 
      _button.OnPointerEnter(new PointerEventData(EventSystem.current)); 
     } 
     isEntered = true; 

     timeElapsed += Time.deltaTime; 
     if(timeElapsed >= 3) // autoclick after 3 sec. 
     { 
      timeElapsed = 0; 
      _button.onClick.Invoke(); 
      isEntered = false; 
     } 
    } 
    else 
    { 
     timeElapsed = 0; 
     if (isEntered) 
     { 
      _button.OnPointerExit(new PointerEventData(EventSystem.current)); 
     } 
     isEntered = false; 

    } 
}