Ejemplo n.º 1
0
        public static void AddOpenGl(this IServiceCollection services)
        {
            services.AddSingleton <EglDisplay>(svc =>
            {
                //svc.GetRequiredService<BcmHost>();

                svc.GetRequiredService <ILogger <Program> >().LogDebug("Initializing EglDisplay");
                return(new EglDisplay());
            });
            services.AddSingleton <EglContext>(svc =>
            {
                EglDisplay display = svc.GetRequiredService <EglDisplay>();

                svc.GetRequiredService <ILogger <Program> >().LogDebug("Initializing EglContext");
                return(new EglContext(display));
            });
            services.AddSingleton <EglSurface>(svc =>
            {
                EglDisplay display         = svc.GetRequiredService <EglDisplay>();
                INativeWindow nativeWindow = svc.GetRequiredService <INativeWindow>();

                svc.GetRequiredService <ILogger <Program> >().LogDebug("Initializing EglSurface");
                return(new EglSurface(display, nativeWindow));
            });
            services.AddSingleton <Data>(svc =>
            {
                svc.GetRequiredService <ILogger <Program> >().LogDebug("Initializing Data");
                return(new Data());
            });
        }
Ejemplo 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);
                }
            }
        }
Ejemplo n.º 3
0
        private static int RunApp()
        {
            app.Out.WriteLine("Hello World!");

            int brightnessValue = 100;

            if (brightness.HasValue())
            {
                if (int.TryParse(brightness.Value(), out brightnessValue))
                {
                    if (brightnessValue < 1 || brightnessValue > 100)
                    {
                        app.Error.WriteLine("Brightness value outside allowed values");
                        return(-1);
                    }
                }
                else
                {
                    app.Error.WriteLine("Invalid brightness value");
                    return(-1);
                }
            }

            //long uid = UnixUserInfo.GetRealUserId();
            //if (uid != 0)
            //{
            //    app.Out.WriteLine("You must run this app as root.");
            //    return -1;
            //}

            //ServiceCollection serviceConfig = new ServiceCollection();
            //serviceConfig.AddLogging();
            //serviceConfig.AddOptions();

            //serviceConfig.AddBcm();
            //serviceConfig.AddOpenGl();
            //serviceConfig.AddLedMatrix();

            //using (ServiceProvider services = serviceConfig.BuildServiceProvider())
            //{
            //    services.GetRequiredService<ILoggerFactory>().AddConsole(LogLevel.Information);

            //    return RunApp(services);
            //}

            using (LedMatrixOptions options = new LedMatrixOptions()
            {
                chain_length = 2,
                parallel = 1,
                rows = 64,
                led_rgb_sequence = "RBG",
                pwm_bits = 8,
                show_refresh_rate = 1,
                brightness = brightnessValue,
            })
                using (LedMatrix matrix = new LedMatrix(options.rows, options.chain_length, options.parallel))
                    using (BcmHost host = new BcmHost())
                        using (Resource target = host.Dispman.CreateResource(VC_IMAGE_TYPE_T.VC_IMAGE_RGB888, matrix.CanvasWidth, matrix.CanvasHeight))
                            using (Display display = host.Dispman.DisplayOpenOffscreen(target, DISPMANX_TRANSFORM_T.DISPMANX_NO_ROTATE))
                                //using (Display display = host.Dispman.DisplayOpen(Screen.MAIN_LCD))
                                using (ScopedElement element = ScopedElement.Create(host, display, null, destRect: display.Rectangle, srcRect: Rescale(display.Rectangle)))
                                    using (DispmanWindow window = new DispmanWindow(element, display.Width, display.Height))
                                        using (EglDisplay eglDisp = new EglDisplay())
                                            using (EglContext ctx = new EglContext(eglDisp))
                                                using (EglSurface surface = new EglSurface(eglDisp, window))
                                                    using (Data data = new Data())
                                                    {
                                                        Rectangle rect = display.Rectangle;
                                                        app.Out.WriteLine("Ready to go, screen is {0}x{1}", display.Width, display.Height);
                                                        Stopwatch swatch = Stopwatch.StartNew();

                                                        app.Out.WriteLine("Initializing 3D context");
                                                        ctx.MakeCurrent(surface);

                                                        app.Out.WriteLine("init_ogl");
                                                        init_ogl();
                                                        app.Out.WriteLine("init_model_proj");
                                                        init_model_proj(rect, data);
                                                        app.Out.WriteLine("init_textures");
                                                        init_textures(data);

                                                        app.Out.WriteLine("Initializing buffer");
                                                        //int bufferLength = rect.Width * rect.Height * 3;
                                                        //byte[] buffer = new byte[bufferLength];

                                                        app.Out.WriteLine("Init complete, starting loop");
                                                        //Render loop
                                                        bool run = true;
                                                        Console.CancelKeyPress += (s, e) =>
                                                        {
                                                            if (run)
                                                            {
                                                                run      = false;
                                                                e.Cancel = true;
                                                            }
                                                        };
                                                        Console.TreatControlCAsInput = true;

                                                        int    pitch = Utils.ALIGN_UP(3 * display.Width, 32);
                                                        byte[] image = new byte[pitch * display.Height];
                                                        app.Out.WriteLine("Buffer size: {0}", image.Length);
                                                        while (run)
                                                        {
                                                            if (Console.KeyAvailable)
                                                            {
                                                                var key = Console.ReadKey(true);
                                                                if (key.Key == ConsoleKey.C && key.Modifiers == ConsoleModifiers.Control)
                                                                {
                                                                    run = false;
                                                                    Console.TreatControlCAsInput = false;
                                                                    continue;
                                                                }
                                                                if (key.Key == ConsoleKey.Add || key.Key == ConsoleKey.Subtract)
                                                                {
                                                                    int newB;
                                                                    if (key.Key == ConsoleKey.Add)
                                                                    {
                                                                        newB = Math.Min(options.brightness + 1, 100);
                                                                    }
                                                                    else
                                                                    {
                                                                        newB = Math.Max(options.brightness - 1, 0);
                                                                    }
                                                                    if (options.brightness != newB)
                                                                    {
                                                                        options.brightness = newB;
                                                                        app.Out.WriteLine("New brightness: {0}%", newB);
                                                                        if (!matrix.UpdateOptions(options))
                                                                        {
                                                                            app.Out.WriteLine("Update option failed");
                                                                        }
                                                                    }
                                                                }
                                                            }

                                                            update_model();
                                                            redraw_scene(surface);

                                                            //extract data to buffer
                                                            //target.WriteData(1, buffer, rect);
                                                            target.ReadData(rect, image, pitch);

                                                            //Display image to matrix
                                                            matrix.UpdateCanvas(canvas =>
                                                            {
                                                                for (int x = 0; x < canvas.Width; x++)
                                                                {
                                                                    for (int y = 0; y < canvas.Height; y++)
                                                                    {
                                                                        int baseAddr = (x * canvas.Width + y) * 3;
                                                                        try
                                                                        {
                                                                            byte r = image[baseAddr + 0];
                                                                            byte g = image[baseAddr + 1];
                                                                            byte b = image[baseAddr + 2];
                                                                            canvas.SetPixel(x, y, r, g, b);
                                                                        }
                                                                        catch (IndexOutOfRangeException ex)
                                                                        {
                                                                            app.Out.WriteLine("X={0} Y={1} baseAddre={2} pitch={3}", x, y, baseAddr, pitch);
                                                                            System.Runtime.ExceptionServices.ExceptionDispatchInfo.Capture(ex).Throw();
                                                                        }
                                                                    }
                                                                }
                                                            });
                                                            app.Out.Write(".");
                                                        }

                                                        return(0);
                                                    }
        }