< Summary

Class:Imagini.EventManager
Assembly:Imagini.Core
File(s):/home/razer/vscode-projects/project-grove/imagini/Imagini.Core/EventManager.cs
Covered lines:40
Uncovered lines:8
Coverable lines:48
Total lines:146
Line coverage:83.3% (40 of 48)
Covered branches:34
Total branches:38
Branch coverage:89.4% (34 of 38)

Metrics

MethodCyclomatic complexity NPath complexity Sequence coverage Branch coverage
.cctor()1020%100%
CreateQueueFor(...)20100%50%
DeleteQueueFor(...)10100%100%
Poll(...)28081.25%96.42%
Push(...)2075%50%
Pump()10100%100%
PushTo(...)20100%100%
PushToCurrent(...)20100%50%
PushToGlobal(...)10100%100%
.ctor()10100%100%
Enqueue(...)10100%100%
ProcessNext(...)10100%100%
ProcessAll(...)20100%100%

File(s)

/home/razer/vscode-projects/project-grove/imagini/Imagini.Core/EventManager.cs

#LineLine coverage
 1using System;
 2using System.Collections.Generic;
 3using System.Runtime.CompilerServices;
 4using System.Runtime.InteropServices;
 5
 6using static SDL2.SDL_error;
 7using static SDL2.SDL_events;
 8using static SDL2.SDL_video;
 9
 10namespace Imagini
 11{
 12    /// <summary>
 13    /// Represents an event manager.
 14    /// </summary>
 15    public static class EventManager
 16    {
 17        private const uint GLOBAL_QUEUE_ID = 0;
 18
 119        static EventManager() => Lifecycle.TryInitialize();
 020        private static Dictionary<uint, EventQueue> _queues =
 021            new Dictionary<uint, EventQueue>() {
 022                { GLOBAL_QUEUE_ID, new EventQueue() }
 023            };
 24
 25        internal static EventQueue CreateQueueFor(Window window)
 26        {
 6927            var id = window.ID;
 6928            if (_queues.ContainsKey(id)) return _queues[id];
 6929            var queue = new EventQueue();
 6930            _queues.Add(id, queue);
 6931            return queue;
 32        }
 33
 34        internal static void DeleteQueueFor(Window window) =>
 6935            _queues.Remove(window.ID);
 36
 10237        internal static EventQueue GlobalQueue => _queues[GLOBAL_QUEUE_ID];
 38
 39        /// <summary>
 40        /// Gathers all available events and distributes them to the
 41        /// corresponding queues.
 42        /// </summary>
 43        /// <param name="suppressGlobalProcessing">
 44        /// If true, global event queue will not be processed after calling this method.
 45        /// </param>
 46        public unsafe static void Poll(bool suppressGlobalProcessing = false)
 47        {
 44048            while (SDL_PollEvent(out SDL_Event @event) != 0)
 49            {
 33850                byte* data = (byte*)&@event;
 33851                switch ((SDL_EventType)@event.type)
 52                {
 53                    // uint32 type, uint32 timestamp, uint32 windowID
 54                    case SDL_EventType.SDL_WINDOWEVENT:
 55                    case SDL_EventType.SDL_KEYDOWN:
 56                    case SDL_EventType.SDL_KEYUP:
 57                    case SDL_EventType.SDL_TEXTEDITING:
 58                    case SDL_EventType.SDL_TEXTINPUT:
 59                    case SDL_EventType.SDL_MOUSEMOTION:
 60                    case SDL_EventType.SDL_MOUSEBUTTONDOWN:
 61                    case SDL_EventType.SDL_MOUSEBUTTONUP:
 62                    case SDL_EventType.SDL_MOUSEWHEEL:
 63                    case SDL_EventType.SDL_USEREVENT:
 32064                        var windowID = (uint)*(data + 8);
 32065                        PushTo(windowID, @event);
 32066                        break;
 67                    case SDL_EventType.SDL_JOYAXISMOTION:
 68                    case SDL_EventType.SDL_JOYBALLMOTION:
 69                    case SDL_EventType.SDL_JOYHATMOTION:
 70                    case SDL_EventType.SDL_JOYBUTTONDOWN:
 71                    case SDL_EventType.SDL_JOYBUTTONUP:
 72                    case SDL_EventType.SDL_CONTROLLERAXISMOTION:
 73                    case SDL_EventType.SDL_CONTROLLERBUTTONDOWN:
 74                    case SDL_EventType.SDL_CONTROLLERBUTTONUP:
 75                    case SDL_EventType.SDL_FINGERDOWN:
 76                    case SDL_EventType.SDL_FINGERUP:
 77                    case SDL_EventType.SDL_FINGERMOTION:
 78                    case SDL_EventType.SDL_DOLLARGESTURE:
 79                    case SDL_EventType.SDL_DOLLARRECORD:
 80                    case SDL_EventType.SDL_MULTIGESTURE:
 1181                        PushToCurrent(@event);
 1182                        break;
 83                    case SDL_EventType.SDL_DROPFILE:
 084                        windowID = (uint)*(data + 8 + IntPtr.Size);
 085                        PushTo(windowID, @event);
 086                        break;
 87                    default:
 788                        PushToGlobal(@event);
 789                        break;
 90                }
 91            }
 10292            if (!suppressGlobalProcessing)
 10193                GlobalQueue.ProcessAll(Events.Global);
 10294        }
 95
 96        /// <summary>
 97        /// Pushes an event onto the poll queue.
 98        /// </summary>
 99        public static void Push(CommonEventArgs e)
 100        {
 26101            var _e = e.AsEvent();
 26102            if (SDL_PushEvent(ref _e) < 0)
 0103                throw new ImaginiException($"Unable to push event: {SDL_GetError()}");
 26104        }
 105
 106        /// <summary>
 107        /// Updates the event queue and internal input device state.
 108        /// </summary>
 6109        public static void Pump() => SDL_PumpEvents();
 110
 111        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 112        private static void PushTo(uint windowId, SDL_Event @event)
 113        {
 331114            if (_queues.ContainsKey(windowId))
 82115                _queues[windowId].Enqueue(@event);
 331116        }
 117
 118        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 119        private static void PushToCurrent(SDL_Event @event)
 120        {
 11121            var current = Window.Current;
 11122            if (current == null) return;
 11123            PushTo(current.ID, @event);
 11124        }
 125
 126        [MethodImpl(MethodImplOptions.AggressiveInlining)]
 127        private static void PushToGlobal(SDL_Event @event) =>
 7128            _queues[GLOBAL_QUEUE_ID].Enqueue(@event);
 129
 130        internal class EventQueue
 131        {
 70132            private Queue<SDL_Event> _events = new Queue<SDL_Event>(32);
 4133            public IReadOnlyCollection<SDL_Event> Events => _events;
 134
 89135            internal void Enqueue(SDL_Event @event) => _events.Enqueue(@event);
 136
 76137            public void ProcessNext(Events events) => events.Process(_events.Dequeue());
 138
 139            public void ProcessAll(Events events)
 140            {
 276141                while (_events.Count > 0)
 76142                    ProcessNext(events);
 200143            }
 144        }
 145    }
 146}