Равноугольное дрожание видео three.js в гарнитуре Vive

Я рендерю равнопрямоугольное видео на сфере three.js и тестирую производительность Chromium WebVR на VIVE.

Я замечаю, что видео вибрирует и трясется, когда я оглядываюсь в VIVE. Это вызывает у меня головокружение.

Если я заменю видео на изображение, вибрация прекратится. Я тестирую разные видео, каждое видео вибрирует. Так что, возможно, проблема возникает, когда three.js пытается отобразить эти видео на сфере.

Я также проверяю фпс. Это примерно 85~90 кадров в секунду. Выглядит неплохо.

(До этого я тестировал этот же скрипт на мобильном телефоне с помощью WebVR Boilerplate и смотрел видео в Cardboard, все работает нормально. Никакой тряски и вибрации. Fps в районе 50. )

Во время тестирования я случайно выяснил, что если я помещу сферу в пример three.js webvr_vive_sculp.html, вибрация уменьшится. Также фпс снижается до 50~60. Если бы я ограничил fps в своем исходном скрипте, ничего не изменилось бы.

Кто-нибудь сталкивался с этой проблемой?

Вот мой сценарий:

<!DOCTYPE html>
<html lang="en">
    <head>
    <title>360 video in vive</title>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
    <style>

        body {

        background-color: #000000;
        margin: 0px;
        overflow: hidden;
        }

        #info {
            position: absolute;
            top: 0px; width: 100%;
            color: #ffffff;
            padding: 5px;
            font-family:Monospace;
            font-size:13px;
            font-weight: bold;
            text-align:center;
        }

        a {
            color: #ffffff;
        }
    </style>
</head>
<body>

    <div id="container"></div>


    <script src="../build/three.js"></script>
    <script src="js/controls/VRControls.js"></script>
    <script src="js/effects/VREffect.js"></script>
    <script src="js/vr/ViveController.js"></script>
    <script src="js/vr/WebVR.js"></script>


    <script>
        if ( WEBVR.isAvailable() === false ) {

            document.body.appendChild( WEBVR.getMessage() );

        }


        var camera, scene, renderer;
        var effect, controls;
        var video;

        init();
        animate();

        function init() {

            var container, mesh;

            container = document.getElementById( 'container' );


            camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 1, 1100 );
            camera.target = new THREE.Vector3( 0, 0, 0 );

            controls = new THREE.VRControls( camera );
            controls.standing = true;

            scene = new THREE.Scene();

            // 360 video
            video      = document.createElement('video');
            video.autoplay = true;
            video.src    = 'video/8Kevil_3840x1920_hq.webm'; // 'video/Danger in the Room.webm' // 8Kevil_3840x1920_hq
            video.crossOrigin = '';
            videoTexture = new THREE.Texture(video);
            videoTexture.minFilter = THREE.LinearFilter;
            videoTexture.magFilter = THREE.LinearFilter;
            videoTexture.format = THREE.RGBFormat;

            // 360 video sphere   
            var cubeGeometry = new THREE.SphereGeometry(500, 60, 40);
            var sphereMat = new THREE.MeshBasicMaterial({map: videoTexture});
            sphereMat.side = THREE.BackSide;
            var cube = new THREE.Mesh(cubeGeometry, sphereMat);
            scene.add(cube);

            renderer = new THREE.WebGLRenderer();
            renderer.setPixelRatio( window.devicePixelRatio );
            renderer.setSize( window.innerWidth, window.innerHeight );
            container.appendChild( renderer.domElement );



            effect = new THREE.VREffect( renderer );
            if ( WEBVR.isAvailable() === true ) {

                document.body.appendChild( WEBVR.getButton( effect ) );

            }
            window.addEventListener( 'resize', onWindowResize, false );

        }

        function onWindowResize() {

            camera.aspect = window.innerWidth / window.innerHeight;
            camera.updateProjectionMatrix();

            renderer.setSize( window.innerWidth, window.innerHeight );

        }

        function animate() {

            effect.requestAnimationFrame( animate );
            update();

        }

        function update() {
            if( video.readyState === video.HAVE_ENOUGH_DATA ){
                videoTexture.needsUpdate = true;
            }

            controls.update();
            effect.render( scene, camera );

        }

    </script>
</body>



person Claire    schedule 01.03.2017    source источник


Ответы (1)


WebVr сейчас плохо обрабатывает видеотекстуры, если вы приостановите видео, мерцание прекратится, верно?

Вы можете попробовать Firefox по ночам, он немного лучше обрабатывает видеотекстуры и в целом имеет меньшую задержку.

Вы можете проверить это, открыв меню Vive во время опыта и покачав головой, в Chrome вы заметите гораздо большую задержку между производительностью собственного меню Vive и вашим опытом в затемненном фоне.

Попробуйте использоватьvideoTexture.minFilter = THREE.NearestFilter; и videoTexture.maxFilter = THREE.NearestFilter;

Для сферы используйте new THREE.SphereGeometry(500, 720, 4); Я знаю, что это выглядит странно, но таким образом вы получите гораздо более гладкие стежки сверху/снизу сферы.

person Aram Avetisyan    schedule 22.03.2017
comment
Большое спасибо за то, что дали мне эти советы! - person Claire; 23.03.2017