Ejemplo n.º 1
0
        private void OnUpdate()
        {
            if (_queue.Count == 0 || (_task != null && _task.Enabled))
            {
                return;
            }

            // TODO: add delay when processing the requests to reduce perf impact (eg. 0.2s before actual rendering)

            // Setup pipeline
            if (_atlases == null)
            {
                _atlases = new List <Atlas>(4);
            }
            if (_output == null)
            {
                _output = GPUDevice.Instance.CreateTexture("CameraCutMedia.Output");
                var desc = GPUTextureDescription.New2D(Width, Height, PixelFormat.R8G8B8A8_UNorm);
                _output.Init(ref desc);
            }
            if (_task == null)
            {
                _task        = Object.New <SceneRenderTask>();
                _task.Output = _output;
                _task.Begin += OnBegin;
                _task.End   += OnEnd;
            }

            // Kick off the rendering
            _task.Enabled = true;
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Synchronizes size of the back buffer with the size of the control.
        /// </summary>
        public void SyncBackbufferSize()
        {
            float scale  = ResolutionScale * Platform.DpiScale;
            int   width  = Mathf.CeilToInt(Width * scale);
            int   height = Mathf.CeilToInt(Height * scale);

            if (_backBuffer == null || _backBuffer.Width == width && _backBuffer.Height == height)
            {
                return;
            }
            if (width < 1 || height < 1)
            {
                _backBuffer.ReleaseGPU();
                Object.Destroy(ref _backBufferOld);
                return;
            }

            // Cache old backbuffer to remove flickering effect
            if (_backBufferOld == null && _backBuffer.IsAllocated)
            {
                _backBufferOld = _backBuffer;
                _backBuffer    = GPUDevice.Instance.CreateTexture();
            }

            // Set timeout to remove old buffer
            _oldBackbufferLiveTimeLeft = 3;

            // Resize backbuffer
            var desc = GPUTextureDescription.New2D(width, height, BackBufferFormat);

            _backBuffer.Init(ref desc);
            _task.Output = _backBuffer;
        }
Ejemplo n.º 3
0
        public static GPUTexture CreateOutputTexture(Vector2 size)
        {
            var texture     = GPUDevice.CreateTexture();
            var description = GPUTextureDescription.New2D((int)size.X, (int)size.Y, PixelFormat.R8G8B8A8_UNorm);

            texture.Init(ref description);

            return(texture);
        }
Ejemplo n.º 4
0
        /// <inheritdoc />
        public override void Render(GPUContext context, SceneRenderTask task, GPUTexture input, GPUTexture output)
        {
            if (Viewport == null)
            {
                throw new NullReferenceException();
            }

            Profiler.BeginEventGPU("Editor Primitives");

            // Check if use MSAA
            var format = output.Format;

            GPUDevice.GetFeatures(format, out var formatSupport);
            bool enableMsaa = formatSupport.MSAALevelMax >= MSAALevel.X4 && Editor.Instance.Options.Options.Visual.EnableMSAAForDebugDraw;

            // Prepare
            var msaaLevel = enableMsaa ? MSAALevel.X4 : MSAALevel.None;
            var width     = output.Width;
            var height    = output.Height;
            var desc      = GPUTextureDescription.New2D(width, height, format, GPUTextureFlags.RenderTarget | GPUTextureFlags.ShaderResource, 1, 1, msaaLevel);
            var target    = RenderTargetPool.Get(ref desc);

            desc = GPUTextureDescription.New2D(width, height, PixelFormat.D24_UNorm_S8_UInt, GPUTextureFlags.DepthStencil, 1, 1, msaaLevel);
            var targetDepth = RenderTargetPool.Get(ref desc);

            // Copy frame and clear depth
            context.Draw(target, input);
            context.ClearDepth(targetDepth);

            // Draw gizmos and other editor primitives (collect draw calls only)
            _drawCallsCollector.Clear();
            for (int i = 0; i < Viewport.Gizmos.Count; i++)
            {
                Viewport.Gizmos[i].Draw(_drawCallsCollector);
            }
            Viewport.DrawEditorPrimitives(context, task, target, targetDepth, _drawCallsCollector);

            // Draw gizmos (actual drawing)
            _drawCallsCollector.ExecuteDrawCalls(context, task, target, DrawPass.GBuffer);
            _drawCallsCollector.ExecuteDrawCalls(context, task, target, DrawPass.Forward);

            // Resolve MSAA texture
            if (enableMsaa)
            {
                context.ResolveMultisample(target, output);
            }
            else
            {
                context.Draw(output, target);
            }

            // Cleanup
            RenderTargetPool.Release(targetDepth);
            RenderTargetPool.Release(target);

            Profiler.EndEventGPU();
        }
        public override void Initialize()
        {
            _output     = GPUDevice.CreateTexture();
            _cachedSize = SizeGetter();
            var description = GPUTextureDescription.New2D(_cachedSize.X, _cachedSize.Y, PixelFormat.R8G8B8A8_UNorm);

            _output.Init(ref description);
            _outputPromise.SetResult(_output);

            Task.Render  = OnRender;
            Task.Enabled = true;
        }
Ejemplo n.º 6
0
        /// <inheritdoc />
        public override void OnInit()
        {
            // Create cache folder
            if (!Directory.Exists(_cacheFolder))
            {
                Directory.CreateDirectory(_cacheFolder);
            }

            // Find atlases in a Editor cache directory
            var files   = Directory.GetFiles(_cacheFolder, "cache_*.flax", SearchOption.TopDirectoryOnly);
            int atlases = 0;

            for (int i = 0; i < files.Length; i++)
            {
                // Load asset
                var asset = FlaxEngine.Content.LoadAsync(files[i]);
                if (asset == null)
                {
                    continue;
                }

                // Validate type
                if (asset is PreviewsCache atlas)
                {
                    // Cache atlas
                    atlases++;
                    _cache.Add(atlas);
                }
                else
                {
                    // Skip asset
                    Editor.LogWarning(string.Format("Asset \'{0}\' is inside Editor\'s private directory for Assets Thumbnails Cache. Please move it.", asset.Path));
                }
            }
            Editor.Log(string.Format("Previews cache count: {0} (capacity for {1} icons)", atlases, atlases * PreviewsCache.AssetIconsPerAtlas));

            // Prepare at least one atlas
            if (_cache.Count == 0)
            {
                GetValidAtlas();
            }

            // Create render task but disabled for now
            _output = GPUDevice.Instance.CreateTexture("ThumbnailsOutput");
            var desc = GPUTextureDescription.New2D(PreviewsCache.AssetIconSize, PreviewsCache.AssetIconSize, PreviewsCache.AssetIconsAtlasFormat);

            _output.Init(ref desc);
            _task         = Object.New <RenderTask>();
            _task.Order   = 50; // Render this task later
            _task.Enabled = false;
            _task.Render += OnRender;
        }
Ejemplo n.º 7
0
            private void StartRendering()
            {
                if (_isRendering)
                {
                    return;
                }

                var editor = Editor.Instance;

                // Check if save the asset before rendering
                if (_window.IsEdited)
                {
                    var result = MessageBox.Show("Save scene animation asset to file before rendering?", "Save?", MessageBoxButtons.YesNoCancel, MessageBoxIcon.Question);
                    if (result == DialogResult.Yes)
                    {
                        _window.Save();
                    }
                    else if (result != DialogResult.No)
                    {
                        return;
                    }
                }

                // Update UI
                _isRendering             = true;
                _presenter.Panel.Enabled = false;
                _presenter.BuildLayoutOnUpdate();

                // Start rendering
                Editor.Log("Starting scene animation rendering " + _options.Animation);
                _dt     = 1.0f / _options.FrameRate;
                _player = new SceneAnimationPlayer
                {
                    Animation          = _options.Animation,
                    HideFlags          = HideFlags.FullyHidden,
                    RestoreStateOnStop = true,
                    PlayOnStart        = false,
                    RandomStartTime    = false,
                    StartTime          = _options.StartTime,
                    UpdateMode         = SceneAnimationPlayer.UpdateModes.Manual,
                };
                FlaxEngine.Scripting.Update += Tick;
                _wasGamePaused  = Time.GamePaused;
                Time.GamePaused = false;
                Time.SetFixedDeltaTime(true, _dt);
                Time.UpdateFPS = Time.DrawFPS = _options.FrameRate;
                if (!Editor.IsPlayMode)
                {
                    Time.PhysicsFPS = 0;
                }
                Level.SpawnActor(_player);
                var gameWin    = editor.Windows.GameWin;
                var resolution = _options.GetResolution();

                gameWin.Viewport.CustomResolution = resolution;
                gameWin.Viewport.BackgroundColor  = Color.Black;
                gameWin.Viewport.KeepAspectRatio  = true;
                gameWin.Viewport.Task.PostRender += OnPostRender;
                if (!gameWin.Visible)
                {
                    gameWin.Show();
                }
                else if (!gameWin.IsFocused)
                {
                    gameWin.Focus();
                }
                _gameWindow     = gameWin;
                _warmUpTimeLeft = _options.WarmUpTime;
                _animationFrame = 0;
                var stagingTextureDesc = GPUTextureDescription.New2D(resolution.X, resolution.Y, gameWin.Viewport.Task.Output.Format, GPUTextureFlags.None);

                stagingTextureDesc.Usage = GPUResourceUsage.StagingReadback;
                for (int i = 0; i < _stagingTextures.Length; i++)
                {
                    _stagingTextures[i].Texture = new GPUTexture();
                    _stagingTextures[i].Texture.Init(ref stagingTextureDesc);
                    _stagingTextures[i].AnimationFrame = -1;
                    _stagingTextures[i].TaskFrame      = -1;
                }
                _player.Play();
                if (!_player.IsPlaying)
                {
                    Editor.LogError("Scene Animation Player failed to start playing.");
                    CancelRendering();
                    return;
                }
                if (_warmUpTimeLeft > 0.0f)
                {
                    // Start warmup time
                    _player.Tick(0.0f);
                    _player.Pause();
                    _state = States.Warmup;
                }
                else
                {
                    // Render first frame
                    _state = States.Render;
                }
                if (!Editor.IsPlayMode)
                {
                    _editorState = new RenderEditorState(editor, this);
                    editor.StateMachine.AddState(_editorState);
                    editor.StateMachine.GoToState(_editorState);
                }
                _progress = new RenderProgress();
                editor.ProgressReporting.RegisterHandler(_progress);
                _progress.Start();
            }
Ejemplo n.º 8
0
        /// <inheritdoc />
        public override void Render(GPUContext context, ref RenderContext renderContext, GPUTexture input, GPUTexture output)
        {
            if (Viewport == null)
            {
                throw new NullReferenceException();
            }

            Profiler.BeginEventGPU("Editor Primitives");

            // Check if use MSAA
            var  format         = output.Format;
            var  formatFeatures = GPUDevice.Instance.GetFormatFeatures(format);
            bool enableMsaa     = formatFeatures.MSAALevelMax >= MSAALevel.X4 && Editor.Instance.Options.Options.Visual.EnableMSAAForDebugDraw;

            // Prepare
            var msaaLevel = enableMsaa ? MSAALevel.X4 : MSAALevel.None;
            var width     = output.Width;
            var height    = output.Height;
            var desc      = GPUTextureDescription.New2D(width, height, format, GPUTextureFlags.RenderTarget | GPUTextureFlags.ShaderResource, 1, 1, msaaLevel);
            var target    = RenderTargetPool.Get(ref desc);

            desc = GPUTextureDescription.New2D(width, height, PixelFormat.D24_UNorm_S8_UInt, GPUTextureFlags.DepthStencil, 1, 1, msaaLevel);
            var targetDepth = RenderTargetPool.Get(ref desc);

            // Copy frame and clear depth
            context.Draw(target, input);
            context.ClearDepth(targetDepth.View());
            context.SetViewport(width, height);
            context.SetRenderTarget(targetDepth.View(), target.View());

            // Draw gizmos and other editor primitives
            var renderList = RenderList.GetFromPool();
            var prevList   = renderContext.List;

            renderContext.List = renderList;
            for (int i = 0; i < Viewport.Gizmos.Count; i++)
            {
                Viewport.Gizmos[i].Draw(ref renderContext);
            }
            Viewport.DrawEditorPrimitives(context, ref renderContext, target, targetDepth);

            // Sort draw calls
            renderList.SortDrawCalls(ref renderContext, false, DrawCallsListType.GBuffer);
            renderList.SortDrawCalls(ref renderContext, false, DrawCallsListType.GBufferNoDecals);
            renderList.SortDrawCalls(ref renderContext, true, DrawCallsListType.Forward);

            // Perform the rendering
            renderContext.View.Pass = DrawPass.GBuffer;
            renderList.ExecuteDrawCalls(ref renderContext, DrawCallsListType.GBuffer);
            renderList.ExecuteDrawCalls(ref renderContext, DrawCallsListType.GBufferNoDecals);
            renderContext.View.Pass = DrawPass.Forward;
            renderList.ExecuteDrawCalls(ref renderContext, DrawCallsListType.Forward);

            // Resolve MSAA texture
            if (enableMsaa)
            {
                context.ResolveMultisample(target, output);
            }
            else
            {
                context.Draw(output, target);
            }

            // Cleanup
            RenderTargetPool.Release(targetDepth);
            RenderTargetPool.Release(target);
            RenderList.ReturnToPool(renderList);
            renderContext.List = prevList;

            Profiler.EndEventGPU();
        }
Ejemplo n.º 9
0
        public override void Initialize()
        {
            StringBuilder         sb    = new StringBuilder(512);
            ETrackedPropertyError error = ETrackedPropertyError.TrackedProp_Success;
            uint ret = _vrSystem.GetStringTrackedDeviceProperty(
                OVR.k_unTrackedDeviceIndex_Hmd,
                ETrackedDeviceProperty.Prop_TrackingSystemName_String,
                sb,
                512u,
                ref error);

            if (error != ETrackedPropertyError.TrackedProp_Success)
            {
                _deviceName = "<Unknown OpenVR Device>";
            }
            else
            {
                _deviceName = sb.ToString();
            }

            uint eyeWidth  = 0;
            uint eyeHeight = 0;

            _vrSystem.GetRecommendedRenderTargetSize(ref eyeWidth, ref eyeHeight);

            _leftEyeGT = GPUDevice.CreateTexture();
            var descLeftEye = GPUTextureDescription.New2D((int)eyeWidth, (int)eyeHeight, 1, PixelFormat.R8G8B8A8_UNorm, msaaLevel: _options.EyeRenderTargetSampleCount);

            _leftEyeGT.Init(ref descLeftEye);

            _rightEyeGT = GPUDevice.CreateTexture();
            var descRightEye = GPUTextureDescription.New2D((int)eyeWidth, (int)eyeHeight, 1, PixelFormat.R8G8B8A8_UNorm, msaaLevel: _options.EyeRenderTargetSampleCount);

            _rightEyeGT.Init(ref descRightEye);

            Matrix eyeToHeadLeft = ToSysMatrix(_vrSystem.GetEyeToHeadTransform(EVREye.Eye_Left));

            Matrix.Invert(ref eyeToHeadLeft, out _headToEyeLeft);

            Matrix eyeToHeadRight = ToSysMatrix(_vrSystem.GetEyeToHeadTransform(EVREye.Eye_Right));

            Matrix.Invert(ref eyeToHeadRight, out _headToEyeRight);

            // Default RH matrices

            /*_projLeft = ToSysMatrix(_vrSystem.GetProjectionMatrix(EVREye.Eye_Left, 0.1f, 10000f));
             * _projRight = ToSysMatrix(_vrSystem.GetProjectionMatrix(EVREye.Eye_Right, 0.1f, 10000f));*/

            // Build LH projection matrices (https://github.com/ValveSoftware/openvr/wiki/IVRSystem::GetProjectionRaw)
            float pLeft   = 0;
            float pRight  = 0;
            float pTop    = 0;
            float pBottom = 0;

            // Default values
            float zNear = 0.1f;
            float zFar  = 20000f;

            _vrSystem.GetProjectionRaw(EVREye.Eye_Left, ref pLeft, ref pRight, ref pTop, ref pBottom);
            _projLeft = Matrix.PerspectiveOffCenter(pLeft * zNear, pRight * zNear, pBottom * zNear * -1f, pTop * zNear * -1f, zNear, zFar);

            _vrSystem.GetProjectionRaw(EVREye.Eye_Right, ref pLeft, ref pRight, ref pTop, ref pBottom);
            _projRight = Matrix.PerspectiveOffCenter(pLeft * zNear, pRight * zNear, pBottom * zNear * -1f, pTop * zNear * -1f, zNear, zFar);
        }