Exemplo n.º 1
0
        private static void redraw_scene(EglSurface surface)
        {
            // Start with a clear screen
            GL.Clear(ClearBufferMask.ColorBufferBit);
            GlDumpError();

            // Draw first (front) face:
            // Bind texture surface to current vertices
            GL.BindTexture(TextureTarget.Texture2D, tex[0]);
            GlDumpError();

            // Need to rotate textures - do this by rotating each cube face
            GL.Rotatef(270.0f, 0.0f, 0.0f, 1.0f); // front face normal along z axis
            GlDumpError();

            // draw first 4 vertices
            GL.DrawArrays(PrimitiveType.TriangleStrip, 0, 4);
            GlDumpError();

            // same pattern for other 5 faces - rotation chosen to make image orientation 'nice'
            GL.BindTexture(TextureTarget.Texture2D, tex[1]);
            GlDumpError();
            GL.Rotatef(90.0f, 0.0f, 0.0f, 1.0f); // back face normal along z axis
            GlDumpError();
            GL.DrawArrays(PrimitiveType.TriangleStrip, 4, 4);
            GlDumpError();

            GL.BindTexture(TextureTarget.Texture2D, tex[2]);
            GlDumpError();
            GL.Rotatef(90.0f, 1.0f, 0.0f, 0.0f); // left face normal along x axis
            GlDumpError();
            GL.DrawArrays(PrimitiveType.TriangleStrip, 8, 4);
            GlDumpError();

            GL.BindTexture(TextureTarget.Texture2D, tex[3]);
            GlDumpError();
            GL.Rotatef(90.0f, 1.0f, 0.0f, 0.0f); // right face normal along x axis
            GlDumpError();
            GL.DrawArrays(PrimitiveType.TriangleStrip, 12, 4);
            GlDumpError();

            GL.BindTexture(TextureTarget.Texture2D, tex[4]);
            GlDumpError();
            GL.Rotatef(270.0f, 0.0f, 1.0f, 0.0f); // top face normal along y axis
            GlDumpError();
            GL.DrawArrays(PrimitiveType.TriangleStrip, 16, 4);
            GlDumpError();

            GL.BindTexture(TextureTarget.Texture2D, tex[5]);
            GlDumpError();
            GL.Rotatef(90.0f, 0.0f, 1.0f, 0.0f); // bottom face normal along y axis
            GlDumpError();
            GL.DrawArrays(PrimitiveType.TriangleStrip, 20, 4);
            GlDumpError();

            surface.SwapBuffers();
        }
Exemplo n.º 2
0
        void Init(DrmCard card, DrmResources resources, DrmConnector connector, DrmModeInfo modeInfo)
        {
            FbDestroyDelegate = FbDestroyCallback;
            _card             = card;
            uint GetCrtc()
            {
                if (resources.Encoders.TryGetValue(connector.EncoderId, out var encoder))
                {
                    // Not sure why that should work
                    return(encoder.Encoder.crtc_id);
                }
                else
                {
                    foreach (var encId in connector.EncoderIds)
                    {
                        if (resources.Encoders.TryGetValue(encId, out encoder) &&
                            encoder.PossibleCrtcs.Count > 0)
                        {
                            return(encoder.PossibleCrtcs.First().crtc_id);
                        }
                    }

                    throw new InvalidOperationException("Unable to find CRTC matching the desired mode");
                }
            }

            _crtcId = GetCrtc();
            var device = gbm_create_device(card.Fd);

            _gbmTargetSurface = gbm_surface_create(device, modeInfo.Resolution.Width, modeInfo.Resolution.Height,
                                                   GbmColorFormats.GBM_FORMAT_XRGB8888, GbmBoFlags.GBM_BO_USE_SCANOUT | GbmBoFlags.GBM_BO_USE_RENDERING);
            if (_gbmTargetSurface == null)
            {
                throw new InvalidOperationException("Unable to create GBM surface");
            }



            _eglDisplay = new EglDisplay(new EglInterface(eglGetProcAddress), 0x31D7, device, null);
            _eglSurface = _eglDisplay.CreateWindowSurface(_gbmTargetSurface);


            EglContext CreateContext(EglContext share)
            {
                var offSurf = gbm_surface_create(device, 1, 1, GbmColorFormats.GBM_FORMAT_XRGB8888,
                                                 GbmBoFlags.GBM_BO_USE_RENDERING);

                if (offSurf == null)
                {
                    throw new InvalidOperationException("Unable to create 1x1 sized GBM surface");
                }
                return(_eglDisplay.CreateContext(share, _eglDisplay.CreateWindowSurface(offSurf)));
            }

            _immediateContext = CreateContext(null);
            _deferredContext  = CreateContext(_immediateContext);

            _immediateContext.MakeCurrent(_eglSurface);
            _eglDisplay.GlInterface.ClearColor(0, 0, 0, 0);
            _eglDisplay.GlInterface.Clear(GlConsts.GL_COLOR_BUFFER_BIT | GlConsts.GL_STENCIL_BUFFER_BIT);
            _eglSurface.SwapBuffers();
            var bo          = gbm_surface_lock_front_buffer(_gbmTargetSurface);
            var fbId        = GetFbIdForBo(bo);
            var connectorId = connector.Id;
            var mode        = modeInfo.Mode;


            var res = drmModeSetCrtc(_card.Fd, _crtcId, fbId, 0, 0, &connectorId, 1, &mode);

            if (res != 0)
            {
                throw new Win32Exception(res, "drmModeSetCrtc failed");
            }

            _mode      = mode;
            _currentBo = bo;

            // Go trough two cycles of buffer swapping (there are render artifacts otherwise)
            for (var c = 0; c < 2; c++)
            {
                using (CreateGlRenderTarget().BeginDraw())
                {
                    _eglDisplay.GlInterface.ClearColor(0, 0, 0, 0);
                    _eglDisplay.GlInterface.Clear(GlConsts.GL_COLOR_BUFFER_BIT | GlConsts.GL_STENCIL_BUFFER_BIT);
                }
            }
        }