public Botsing(float tijd, Deeltje deeltje, Obstakel obstakel, ContentAlignment orientatie)
 {
     Tijd                   = tijd;
     Deeltje                = deeltje;
     Obstakel               = obstakel;
     Orientatie             = orientatie;
     AantalBotsingenDeeltje = deeltje.AantalBotsingen;
 }
        public void BotstMetObstakel(Obstakel obstakel, ContentAlignment orientatie, float tijdBotsing, float huidigeTijd)
        {
            switch (orientatie)
            {
            case ContentAlignment.MiddleLeft:
                Px  = obstakel.X1 - Radius;
                Py += Vy * (tijdBotsing - huidigeTijd);
                Vx  = -Vx;
                break;

            case ContentAlignment.MiddleRight:
                Px  = obstakel.X2 + Radius;
                Py += Vy * (tijdBotsing - huidigeTijd);
                Vx  = -Vx;
                break;

            case ContentAlignment.TopCenter:
                Py  = obstakel.Y1 - Radius;
                Px += Vx * (tijdBotsing - huidigeTijd);
                Vy  = -Vy;
                break;

            case ContentAlignment.BottomCenter:
                Py  = obstakel.Y2 + Radius;
                Px += Vx * (tijdBotsing - huidigeTijd);
                Vy  = -Vy;
                break;

            case ContentAlignment.TopLeft:
                BotstMetHoek(obstakel.HoekLinksBoven, tijdBotsing, huidigeTijd);
                break;

            case ContentAlignment.BottomLeft:
                BotstMetHoek(obstakel.HoekLinksOnder, tijdBotsing, huidigeTijd);
                break;

            case ContentAlignment.TopRight:
                BotstMetHoek(obstakel.HoekRechtsBoven, tijdBotsing, huidigeTijd);
                break;

            case ContentAlignment.BottomRight:
                BotstMetHoek(obstakel.HoekRechtsOnder, tijdBotsing, huidigeTijd);
                break;
            }

            if (Elasticiteit < 1)
            {
                Vx *= Elasticiteit;
                Vy *= Elasticiteit;
            }

            AantalBotsingen++;
        }
Example #3
0
        private void voorspelBotsingen(Deeltje deeltje, Deeltje uitgeslotenDeeltje, Obstakel uitgeslotenObstakel)
        // zojuist geraakte deeltje of obstakel uitsluiten bij voorspelling
        {
            DockStyle wandtype;
            float     dtWand = deeltje.TijdTotWand(out wandtype);

            if (dtWand < 1 << 16) // als deeltje stilstaat niet toevoegen
            {
                minPQ.Invoegen(new Botsing(huidigeTijd + dtWand, deeltje, wandtype));
            }

            foreach (Deeltje overigDeeltje in lijstDeeltjes)
            {
                if (overigDeeltje == deeltje || overigDeeltje == uitgeslotenDeeltje)
                {
                    continue;
                }
                float dt = deeltje.TijdTotAnderDeeltje(overigDeeltje);
                if (dt < dtWand) // tijden na botsing met wand niet relevant
                {
                    minPQ.Invoegen(new Botsing(huidigeTijd + dt, deeltje, overigDeeltje));
                }
            }

            ContentAlignment orientatie;

            foreach (Obstakel obstakel in lijstObstakels)
            {
                if (obstakel == uitgeslotenObstakel)
                {
                    continue;
                }
                float dtObstakel = deeltje.TijdTotObstakel(obstakel, out orientatie);
                if (dtObstakel < dtWand) // tijden na botsing met wand niet relevant
                {
                    minPQ.Invoegen(new Botsing(huidigeTijd + dtObstakel, deeltje, obstakel, orientatie));
                }
            }
        }
        public float TijdTotObstakel(Obstakel obstakel, out ContentAlignment orientatie)
        {
            if (Radius <= obstakel.Permeabiliteit)
            {
                orientatie = ContentAlignment.MiddleCenter;
                return(float.PositiveInfinity);
            }

            // criteria voor Px en Py zijn 1 radius te ruim om ontsnappingen door rekenfouten te voorkomen
            if (Vx > 0 && Px < obstakel.X1) // linker wand
            {
                float dt       = (obstakel.X1 - Radius - Px) / Vx;
                float yBotsing = Py + Vy * dt;
                if (yBotsing < obstakel.Y1)
                {
                    dt = TijdTotHoek(obstakel.HoekLinksBoven);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.TopLeft;
                        return(dt);
                    }
                }
                else if (yBotsing > obstakel.Y2)
                {
                    dt = TijdTotHoek(obstakel.HoekLinksOnder);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.BottomLeft;
                        return(dt);
                    }
                }
                else
                {
                    orientatie = ContentAlignment.MiddleLeft;
                    return(dt);
                }
            }
            else if (Vx < 0 && Px > obstakel.X2) // rechter wand
            {
                float dt       = (obstakel.X2 + Radius - Px) / Vx;
                float yBotsing = Py + Vy * dt;
                if (yBotsing < obstakel.Y1)
                {
                    dt = TijdTotHoek(obstakel.HoekRechtsBoven);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.TopRight;
                        return(dt);
                    }
                }
                else if (yBotsing > obstakel.Y2)
                {
                    dt = TijdTotHoek(obstakel.HoekRechtsOnder);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.BottomRight;
                        return(dt);
                    }
                }
                else
                {
                    orientatie = ContentAlignment.MiddleRight;
                    return(dt);
                }
            }

            if (Vy > 0 && Py < obstakel.Y1) // bovenwand
            {
                float dt       = (obstakel.Y1 - Radius - Py) / Vy;
                float xBotsing = Px + Vx * dt;
                if (xBotsing < obstakel.X1)
                {
                    dt = TijdTotHoek(obstakel.HoekLinksBoven);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.TopLeft;
                        return(dt);
                    }
                }
                else if (xBotsing > obstakel.X2)
                {
                    dt = TijdTotHoek(obstakel.HoekRechtsBoven);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.TopRight;
                        return(dt);
                    }
                }
                else
                {
                    orientatie = ContentAlignment.TopCenter;
                    return(dt);
                }
            }
            else if (Vy < 0 && Py > obstakel.Y2) // onderwand
            {
                float dt       = (obstakel.Y2 + Radius - Py) / Vy;
                float xBotsing = Px + Vx * dt;
                if (xBotsing < obstakel.X1)
                {
                    dt = TijdTotHoek(obstakel.HoekLinksOnder);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.BottomLeft;
                        return(dt);
                    }
                }
                else if (xBotsing > obstakel.X2)
                {
                    dt = TijdTotHoek(obstakel.HoekRechtsOnder);
                    if (dt < float.PositiveInfinity)
                    {
                        orientatie = ContentAlignment.BottomRight;
                        return(dt);
                    }
                }
                else
                {
                    orientatie = ContentAlignment.BottomCenter;
                    return(dt);
                }
            }

            orientatie = ContentAlignment.MiddleCenter;
            return(float.PositiveInfinity);
        }