Esempio n. 1
0
        private void UpdateViewInternal()
        {
            if (HeadlessMode)
            {
                SpaceTime.ClearChanges();
                return;
            }

            if (SpaceTime.AddedElements.Count == 0 && SpaceTime.ChangedElements.Count == 0 && SpaceTime.RemovedElements.Count == 0)
            {
                return;
            }
            resetHandle.Reset();
            Application.InvokeNextCycle(() =>
            {
                foreach (var e in SpaceTime.AddedElements)
                {
                    var renderer = thingBinder.Bind(e, SpaceTime);
                    renderers.Add(e, renderer);
                    this.Controls.Add(renderer);
                    SizeAndLocate(renderer);
                    OnBind.Fire(e);
                    renderer.OnRender();
                }

                foreach (var e in SpaceTime.ChangedElements)
                {
                    SizeAndLocate(renderers[e]);
                    renderers[e].OnRender();
                }

                foreach (var e in SpaceTime.RemovedElements)
                {
                    var renderer = renderers[e];
                    renderers.Remove(e);
                    Controls.Remove(renderer);
                }

                if (resizedSinceLastRender)
                {
                    foreach (var r in renderers.Values)
                    {
                        SizeAndLocate(r);
                    }
                }
                Application.Paint();
                resetHandle.Set();
            });

            resetHandle.WaitOne();
            resizedSinceLastRender = false;
            SpaceTime.ClearChanges();
            AfterUpdate.Fire();
        }
Esempio n. 2
0
        private void UpdateViewInternal(bool force)
        {
            foreach (var element in SpaceTime.AddedElements)
            {
                Application.QueueAction(() =>
                {
                    var renderer = thingBinder.Bind(element, SpaceTime);
                    renderers.Add(element, renderer);
                    this.Controls.Add(renderer);
                    SizeAndLocate(renderer);
                    renderer.OnRender();
                });
            }

            foreach (var t in SpaceTime.ChangedElements)
            {
                Application.QueueAction(() =>
                {
                    var renderer = renderers[t];
                    SizeAndLocate(renderer);
                    renderer.OnRender();
                });
            }

            foreach (var t in SpaceTime.RemovedElements)
            {
                Application.QueueAction(() =>
                {
                    var renderer = renderers[t];
                    renderers.Remove(t);
                    Controls.Remove(renderer);
                });
            }

            if (force || resizedSinceLastRender)
            {
                foreach (var renderer in renderers.Values)
                {
                    Application.QueueAction(() =>
                    {
                        SizeAndLocate(renderer);
                    });
                }
            }

            resizedSinceLastRender = false;
            SpaceTime.ClearChanges();
            Application.Paint();
        }
Esempio n. 3
0
        public SpacetimePanel(int w, int h, SpaceTime time = null)
        {
            this.Width  = w;
            this.Height = h;
            Background  = ConsoleColor.White;
            renderers   = new Dictionary <SpacialElement, SpacialElementRenderer>();
            thingBinder = new SpacialElementBinder();

            this.SpaceTime = time ?? new SpaceTime(w, h, increment: TimeSpan.FromSeconds(.05));
            this.SpaceTime.QueueAction(() =>
            {
                RealTimeViewing = new RealTimeViewingFunction(this.SpaceTime)
                {
                    Enabled = true
                };
                this.SpaceTime.ChangeTrackingEnabled = true;
                this.SpaceTime.AfterTick.SubscribeForLifetime(() => UpdateView(false), this.LifetimeManager);

                RealTimeViewing.Behind.SubscribeForLifetime((isBehind) =>
                {
                    Application?.QueueAction(() =>
                    {
                        Background = isBehind ? ConsoleColor.DarkYellow : ConsoleColor.White;
                    });
                }, LifetimeManager);
            });

            this.AddedToVisualTree.SubscribeForLifetime(() =>
            {
                LifetimeManager.Manage(Application.SetInterval(() =>
                {
                    RealTimeViewing?.Evaluate();
                }, TimeSpan.FromSeconds(.1)));
            }, this.LifetimeManager);

            this.SpaceTime.UnhandledException.SubscribeForLifetime((ex) =>
            {
                Application?.QueueAction(() =>
                {
                    throw new AggregateException(ex);
                });
            }, this.LifetimeManager);

            this.SubscribeForLifetime(nameof(Bounds), () => { resizedSinceLastRender = false; }, this.LifetimeManager);
        }
Esempio n. 4
0
        public SpaceTimePanel(int w, int h, SpaceTime time = null)
        {
            this.Width  = w;
            this.Height = h;
            Background  = ConsoleColor.White;
            renderers   = new Dictionary <SpacialElement, SpacialElementRenderer>();
            thingBinder = new SpacialElementBinder();
            resetHandle = new AutoResetEvent(false);

            this.SpaceTime = time;
            if (this.SpaceTime == null)
            {
                this.SpaceTime = new SpaceTime(w, h, increment: TimeSpan.FromSeconds(.05));
                this.OnDisposed(() =>
                {
                    if (this.SpaceTime.IsRunning)
                    {
                        this.SpaceTime.Stop();
                    }
                    this.SpaceTime = null;
                });
            }

            this.SpaceTime.Invoke(() =>
            {
                RealTimeViewing = new RealTimeViewingFunction(this.SpaceTime)
                {
                    Enabled = true
                };
                this.SpaceTime.EndOfCycle.SubscribeForLifetime(() => UpdateViewInternal(), this);
            });

            this.AddedToVisualTree.SubscribeForLifetime(() =>
            {
                this.OnDisposed(() => resetHandle.Set());
            }, this);


            this.SubscribeForLifetime(nameof(Bounds), () => { resizedSinceLastRender = false; }, this);
        }
Esempio n. 5
0
        public static HitPrediction PredictHit(SpaceTime r, SpacialElement Target, List <Type> hitDetectionTypes, List <SpacialElement> hitDetectionExclusions, float dx, float dy)
        {
            if (Math.Abs(dx) <= 1 && Math.Abs(dy) <= 1)
            {
                return(PredictHitInternal(r, Target, hitDetectionTypes, hitDetectionExclusions, dx, dy));
            }

            HitPrediction latestResult = null;

            for (var i = 1; i <= 10; i++)
            {
                var dxP = Approach(0, dx, dx / 10 * i);
                var dyP = Approach(0, dy, dy / 10 * i);
                latestResult = PredictHitInternal(r, Target, hitDetectionTypes, hitDetectionExclusions, dxP, dyP);
                if (latestResult.Type != HitType.None)
                {
                    return(latestResult);
                }
            }

            return(latestResult);
        }
Esempio n. 6
0
        public SpacialElementRenderer Bind(SpacialElement t, SpaceTime spaceTime)
        {
            if (t.Renderer != null)
            {
                t.Renderer.Element = t;
                t.Renderer.OnBind();
                return(t.Renderer);
            }

            Type binding;

            if (Bindings.TryGetValue(t.GetType(), out binding) == false)
            {
                binding = typeof(SpacialElementRenderer);
            }

            SpacialElementRenderer ret = Activator.CreateInstance(binding) as SpacialElementRenderer;

            ret.Element   = t;
            ret.Spacetime = spaceTime;
            ret.OnBind();
            return(ret);
        }
Esempio n. 7
0
        public SpacetimePanel(int w, int h, SpaceTime time = null)
        {
            this.Width     = w;
            this.Height    = h;
            Background     = ConsoleColor.White;
            renderers      = new Dictionary <SpacialElement, SpacialElementRenderer>();
            thingBinder    = new SpacialElementBinder();
            resetHandle    = new AutoResetEvent(false);
            this.SpaceTime = time ?? new SpaceTime(w, h, increment: TimeSpan.FromSeconds(.05));
            this.SpaceTime.QueueAction(() =>
            {
                RealTimeViewing = new RealTimeViewingFunction(this.SpaceTime)
                {
                    Enabled = true
                };
                this.SpaceTime.ChangeTrackingEnabled = true;
                this.SpaceTime.AfterTick.SubscribeForLifetime(() => UpdateViewInternal(), this);
            });

            this.AddedToVisualTree.SubscribeForLifetime(() =>
            {
                this.SpaceTime.Application = this.Application;
                this.OnDisposed(() => resetHandle.Set());
            }, this);

            this.SpaceTime.UnhandledException.SubscribeForLifetime((ex) =>
            {
                resetHandle.Set();
                Application?.QueueAction(() =>
                {
                    throw new AggregateException(ex);
                });
            }, this);

            this.SubscribeForLifetime(nameof(Bounds), () => { resizedSinceLastRender = false; }, this);
        }
Esempio n. 8
0
        public static HitPrediction PredictHit(SpaceTime r, SpacialElement Target, List <Type> hitDetectionTypes, float dx, float dy)
        {
            HitPrediction prediction = new HitPrediction();

            if (dx == 0 && dy == 0)
            {
                prediction.Direction = Direction.None;
                prediction.Type      = HitType.None;
                return(prediction);
            }

            if (dy > 0 && Target.Bottom() + dy >= r.Height)
            {
                prediction.Direction            = Direction.Down;
                prediction.Type                 = HitType.Boundary;
                prediction.BoundsOfItemBeingHit = Rectangular.Create(Target.Left + dx, r.Bounds.Height + dy, 1, 1);
                return(prediction);
            }
            else if (dx < 0 && Target.Left + dx <= 0)
            {
                prediction.Direction            = Direction.Left;
                prediction.Type                 = HitType.Boundary;
                prediction.BoundsOfItemBeingHit = Rectangular.Create(-dx, Target.Top + dy, 1, 1);
                return(prediction);
            }
            else if (dy < 0 && Target.Top + dy <= 0)
            {
                prediction.Direction            = Direction.Up;
                prediction.Type                 = HitType.Boundary;
                prediction.BoundsOfItemBeingHit = Rectangular.Create(Target.Left + dx, -dy, 1, 1);
                return(prediction);
            }
            else if (dx > 0 && Target.Right() + dx >= r.Width)
            {
                prediction.Direction            = Direction.Right;
                prediction.Type                 = HitType.Boundary;
                prediction.BoundsOfItemBeingHit = Rectangular.Create(r.Width + dx, Target.Top + dy, 1, 1);
                return(prediction);
            }

            var testArea = Rectangular.Create(Target.Left + dx, Target.Top + dy, Target.Width, Target.Height);

            var match = (from t in r.Elements
                         where
                         t.IsOneOfThese(hitDetectionTypes) &&
                         Target != t &&
                         testArea.NumberOfPixelsThatOverlap(t) > 0
                         select t).OrderBy(t => t.Center().CalculateDistanceTo(Target.Center()));


            if (match.Count() == 0)
            {
                prediction.Direction = Direction.None;
                prediction.Type      = HitType.None;
            }
            else
            {
                prediction.ElementHit           = match.First();
                prediction.Type                 = HitType.Element;
                prediction.Direction            = testArea.GetHitDirection(match.First().Bounds);
                prediction.BoundsOfItemBeingHit = prediction.ElementHit.Bounds;
            }

            return(prediction);
        }