コード例 #1
0
        public static void CheckMapPoints(CommandEventArgs e)
        {
            try
            {
                if (e.ArgString != null && e.ArgString.Length > 0)
                {
                    Point2D  px    = Point2D.Parse(e.ArgString);
                    SeaChart chart = new SeaChart(1, px);

                    chart.AddWorldPin(px.X, px.Y);

                    bool[] failTest = new bool[10];
                    if (CheckMap(chart, failTest) == false)
                    {
                        e.Mobile.SendMessage("Failed map test");
                    }
                    else
                    {
                        e.Mobile.SendMessage("Passed map test");
                    }

                    for (int ix = m_Locations.GetLowerBound(0); ix <= m_Locations.GetUpperBound(0); ix++)
                    {
                        for (int jx = m_Locations.GetLowerBound(1); jx <= m_Locations.GetUpperBound(1); jx++)
                        {
                            for (int mx = 0; mx < m_Locations[ix, jx].Length; mx++)
                            {
                                if ((Point2D)m_Locations[ix, jx][mx] == px)
                                {
                                    e.Mobile.SendMessage("Database contains the point {0}", px);

                                    ValidDistance(150,
                                                  (Point2D)m_Locations[ix, jx][mx],
                                                  (Point2D)m_Locations[ix, jx][mx + 1]);

                                    return;
                                }
                            }
                        }
                    }

                    e.Mobile.SendMessage("Database does not contain the point {0}", px);
                }
                else
                {
                    e.Mobile.Target = new MapTarget();
                    e.Mobile.SendMessage("Check which map?");
                }
            }
            catch (Exception ex)
            {
                e.Mobile.SendMessage("Usage: [checkMapPoints {0}", new Point2D(123, 456));
                LogHelper.LogException(ex);
            }
        }
コード例 #2
0
        private static bool ValidBounds(SeaChart smallMap, int x, int y)
        {
            try
            {
                int MapX = 0, MapY = 0;
                smallMap.ConvertToMap(x, y, out MapX, out MapY);

                int saveX = MapX, saveY = MapY;
                smallMap.Validate(ref MapX, ref MapY);

                // it's a good point if validate didn't try to correct it
                return(saveX == MapX && saveY == MapY);
            }
            catch
            {                   // Some maps come up with a bounds width of zero, and ConvertToMap bombs
                return(false);
            }
        }
コード例 #3
0
        public static bool CheckMap(SeaChart map, bool[] FailTest)
        {
            if (map == null || map.Pins == null || map.Pins.Count == 0)
            {
                return(false);
            }

            bool failure = false;

            for (int ix = 0; map.Pins != null && ix < map.Pins.Count; ix++)
            {
                int WorldX = 0, WorldY = 0;
                map.ConvertToWorld(((Point2D)map.Pins[ix]).X, ((Point2D)map.Pins[ix]).Y,
                                   out WorldX, out WorldY);

                if (!Utility.BritWrap[0].Contains(new Point2D(WorldX, WorldY)) && !Utility.BritWrap[1].Contains(new Point2D(WorldX, WorldY)))
                {
                    failure     = true;
                    FailTest[0] = true;
                }

                if (!ValidBounds(map, WorldX, WorldY))
                {
                    failure     = true;
                    FailTest[1] = true;
                }

                if (!ValidWater(WorldX, WorldY))
                {
                    failure     = true;
                    FailTest[2] = true;
                }
            }

            return(!failure);
        }
コード例 #4
0
            protected override void OnTarget(Mobile from, object targ)
            {
                if (targ is SeaChart)
                {
                    bool     failure = false;
                    SeaChart map     = (targ as SeaChart);
                    for (int ix = 0; map.Pins != null && ix < map.Pins.Count; ix++)
                    {
                        bool[] FailTest = new bool[10];

                        int WorldX = 0, WorldY = 0;
                        map.ConvertToWorld(((Point2D)map.Pins[ix]).X, ((Point2D)map.Pins[ix]).Y,
                                           out WorldX, out WorldY);

                        if (!Utility.BritWrap[0].Contains(new Point2D(WorldX, WorldY)) && !Utility.BritWrap[1].Contains(new Point2D(WorldX, WorldY)))
                        {
                            failure     = true;
                            FailTest[0] = true;
                        }

                        if (!ValidBounds(map, WorldX, WorldY))
                        {
                            failure     = true;
                            FailTest[1] = true;
                        }

                        if (!ValidWater(WorldX, WorldY))
                        {
                            failure     = true;
                            FailTest[2] = true;
                        }

                        if (failure == true)
                        {
                            from.SendMessage("-- Pin {0} {1}", ix + 1, new Point2D(WorldX, WorldY));

                            if (FailTest[0] == true)
                            {
                                from.SendMessage("    No rects contain point {0}", (Point2D)map.Pins[ix]);
                            }

                            if (FailTest[1] == true)
                            {
                                from.SendMessage("    This point fails the validity check");
                            }

                            if (FailTest[2] == true)
                            {
                                from.SendMessage("    This point fails the wet tile check");
                            }

                            from.SendMessage("    Failed: map width({0})X({1}), map height({2})Y({3})",
                                             map.Width, ((Point2D)map.Pins[ix]).X,
                                             map.Height, ((Point2D)map.Pins[ix]).Y);

                            from.SendMessage("-- failed");
                        }
                    }

                    if (failure == false)
                    {
                        from.SendMessage("Success");
                    }
                }
                else
                {
                    from.SendMessage("The is not a SeaChart.");
                }
                return;
            }
コード例 #5
0
        public static void GenMapPoints(CommandEventArgs e)
        {
            try
            {
                e.Mobile.SendMessage("Begin generation.");
                Dolphin  fish = new Dolphin();
                SeaChart tempMap = null;
                double   maxd = 0; double mind = 64; int count = 0; int failedPin = 0;
                int      pinNdx = 0; int pinCollisions = 0; int notInRect = 0; int specialExclusions = 0; int badMap = 0;
                int      wetTileFailure = 0; int badMapBounds = 0; int failMap = 0; int noLand = 0; int minDist = 0;
                SortedList <double, MapNode> list = new SortedList <double, MapNode>();
                for (int ji = 0; ji < Utility.BritWrap.Length; ji++)
                {
                    for (int mx = Utility.BritWrap[ji].Start.X; mx <= (Utility.BritWrap[ji].Start.X + Utility.BritWrap[ji].Width - 1); mx++)
                    {
                        for (int my = Utility.BritWrap[ji].Start.Y; my <= (Utility.BritWrap[ji].Start.Y + Utility.BritWrap[ji].Height - 1); my++)
                        {
                            // are we inside the brit rect?
                            if (Utility.BritWrap[ji].Contains(new Point2D(mx, my)) == false)
                            {                                   // bad point - not in rect
                                notInRect++;
                                continue;
                            }

                            // wet tile rect sanity check - make sure we are surrounded by water (not a puddle)
                            if (PuddleCheck(Utility.BritWrap[ji], new Point2D(mx, my)) == false)
                            {
                                wetTileFailure++;
                                continue;
                            }

                            // exclude special areas (eg. angel island prison, dungeons)
                            if (ValidRegion(mx, my) == false)
                            {
                                specialExclusions++;
                                continue;
                            }

                            // okay, we have what looks like a good map center and first pin
                            // we must have land within 64 tiles
                            Point3D wetLoc = new Point3D(mx, my, Map.Felucca.GetAverageZ(mx, my));
                            Point3D dryLoc = Spawner.GetSpawnPosition(Map.Felucca, wetLoc, 64, false, null);
                            if (wetLoc == dryLoc)
                            {                                   // spawner failed to find a good location
                                noLand++;
                                continue;
                            }

                            // okay, we have a focus point
                            //	now place the remaing N pins with validation

                            // dist2land to old point
                            double dist2land = GetDistance(new Point2D(wetLoc), new Point2D(dryLoc));

                            // level of this map
                            int level = (dist2land < 21) ? 1 : (dist2land < 31) ? 2 : (dist2land < 41) ? 3 : (dist2land < 51) ? 4 : (dist2land < 91) ? 5 : 0;

                            // create a temp map to validate pin locations
                            #region TEMP MAP CREATION & VALIDATION
                            if (tempMap != null)
                            {
                                tempMap.Delete();
                                tempMap = null;
                            }
                            // new level-sized map
                            tempMap = new SeaChart(level, new Point2D(wetLoc));

                            // make sure there is no w/h failure. I think this happens when we are at the map edge
                            if (tempMap.Bounds.Width <= 0 || tempMap.Height <= 0)
                            {
                                badMap++;
                                continue;
                            }
                            // even though our wet-point is in the brit rect, the bounds may not be. Exclude those maps here
                            if (!Utility.BritWrap[ji].Contains(tempMap.Bounds.Start) || !Utility.BritWrap[ji].Contains(tempMap.Bounds.End))
                            {
                                badMapBounds++;
                                continue;
                            }
                            #endregion TEMP MAP CREATION & VALIDATION

                            #region ADD PINS
                            // okay, place the start pin
                            Point2D[] pins = new Point2D[6];
                            pinNdx         = 0;
                            pins[pinNdx++] = new Point2D(wetLoc.X, wetLoc.Y);

                            Point3D newPinLoc;                                          // new pin location
                            Point3D lastPinLoc = wetLoc;                                // last pin location

                            // okay, try to place 6 pins
                            int good = 1;                       // how many pins have we placed?
                            for (int hx = 1; hx < 6; hx++)      // 6 pins
                            {                                   // 100 tries to place a pin
                                for (int retry = 0; retry < 100; retry++)
                                {
                                    // get a new pin location
                                    newPinLoc = Spawner.GetSpawnPosition(Map.Felucca, lastPinLoc, 200, false, false, Spawner.SpawnFlags.SpawnFar, fish);
                                    if (newPinLoc == lastPinLoc)
                                    {
                                        continue;
                                    }

                                    // did we exit the brit rect?
                                    if (Utility.BritWrap[ji].Contains(newPinLoc) == false)
                                    {                                           // bad point - not in rect
                                        notInRect++;
                                        continue;
                                    }

                                    // wet tile rect sanity check - make sure we are surrounded by water (not a puddle)
                                    if (PuddleCheck(Utility.BritWrap[ji], new Point2D(newPinLoc)) == false)
                                    {
                                        wetTileFailure++;
                                        continue;
                                    }

                                    // is this pin in an illegal region?
                                    if (ValidRegion(newPinLoc.X, newPinLoc.Y) == false)
                                    {
                                        specialExclusions++;
                                        continue;
                                    }

                                    // validate that we don't exceed the map bounds
                                    if (ValidBounds(tempMap, newPinLoc.X, newPinLoc.Y) == false)
                                    {
                                        badMap++;
                                        continue;
                                    }

                                    // validate a minmum distance
                                    if (ValidDistance(150, new Point2D(lastPinLoc), new Point2D(newPinLoc)) == false)
                                    {
                                        minDist++;
                                        continue;
                                    }

                                    if (ValidUnique(pins, pinNdx, new Point2D(newPinLoc.X, newPinLoc.Y)) == false)
                                    {
                                        pinCollisions++;
                                        continue;
                                    }

                                    // okay, looks to be a reasonable pin location
                                    pins[pinNdx++] = new Point2D(newPinLoc.X, newPinLoc.Y);
                                    lastPinLoc     = newPinLoc;                                 // make the next pin relative to this pin
                                    good++;
                                    break;
                                }
                            }

                            if (good < 6)
                            {                                   // skip this location as we can't place sufficient pins
                                failedPin++;
                                continue;
                            }
                            #endregion ADD PINS


                            // Create an actual map and run sanity checks on it.
                            //	for some unknown reason, we're still getting like 10% bad maps
                            #region FINAL CHECK
                            for (int rm = 0; rm < pins.Length; rm++)
                            {
                                tempMap.AddWorldPin(pins[rm].X, pins[rm].Y);
                            }
                            bool[] failTest = new bool[10];
                            if (CheckMap(tempMap, failTest) == false)
                            {
                                failMap++;
                                tempMap.ClearPins();
                                continue;
                            }
                            tempMap.ClearPins();
                            #endregion FINAL CHECK

                            // maps processed
                            count++;

                            // give a little feedback since thie process is so slow
                            if (count % 1000 == 0)
                            {
                                Console.Write("{0},", count);
                            }

                            // add to sorted list
                            double key      = Utility.RandomDouble();
                            bool   retrykey = false;
                            while (list.ContainsKey(key))
                            {                                   // feedback for key retries
                                Console.Write(".");
                                key      = Utility.RandomDouble();
                                retrykey = true;
                            }
                            list.Add(key, new MapNode(level, pins));

                            if (retrykey == true)
                            {
                                Console.Write(",");
                            }
                        }
                    }
                }

                // no longer need our test fish
                fish.Delete();

                Console.WriteLine();
                Console.WriteLine("Fill arrays");

                int[] indexes = new int[m_Locations.GetUpperBound(0) + 1]; // column index
                foreach (KeyValuePair <double, MapNode> kvp in list)
                {                                                          // only store the first 500 (m_Locations.GetUpperBound(1)+1) for each level
                    if (indexes[kvp.Value.Level - 1] > m_Locations.GetUpperBound(1))
                    {
                        continue;
                    }

                    m_Locations[kvp.Value.Level - 1, indexes[kvp.Value.Level - 1]] =
                        new Point2D[6] {
                        kvp.Value.Pins[0], kvp.Value.Pins[1], kvp.Value.Pins[2],
                        kvp.Value.Pins[3], kvp.Value.Pins[4], kvp.Value.Pins[5]
                    };

                    indexes[kvp.Value.Level - 1]++;
                }

                Console.WriteLine("Write the data");
                try
                {
                    int    rowx, coly;
                    string filePath = Path.Combine(Core.BaseDirectory, "Data/seatreasure.bin");
                    using (Stream stream = File.Open(filePath, FileMode.Create))
                    {
                        BinaryFormatter bin = new BinaryFormatter();
                        for (rowx = 0; rowx <= m_Locations.GetUpperBound(0); rowx++)
                        {
                            for (coly = 0; coly <= m_Locations.GetUpperBound(1); coly++)
                            {
                                bin.Serialize(stream, m_Locations[rowx, coly]);
                            }
                        }
                    }

                    // read it back
                    using (Stream stream = File.Open(filePath, FileMode.Open))
                    {
                        BinaryFormatter bin = new BinaryFormatter();

                        for (rowx = 0; rowx <= m_Locations.GetUpperBound(0); rowx++)
                        {
                            for (coly = 0; coly <= m_Locations.GetUpperBound(1); coly++)
                            {
                                m_Locations[rowx, coly] = new Point2D[6];
                                m_Locations[rowx, coly] = (Point2D[])bin.Deserialize(stream);
                            }
                        }
                    }
                }
                catch (Exception ex)
                {
                    LogHelper.LogException(ex);
                }

                e.Mobile.SendMessage("Generation complete with {0} maps processed.", count);
                e.Mobile.SendMessage("{0} map locations were skipped for bad pin placement.", failedPin);
                e.Mobile.SendMessage("{0} pin locations were skipped because of pin collisions.", pinCollisions);
                e.Mobile.SendMessage("{0} points were skipped: outside rect.", notInRect);
                e.Mobile.SendMessage("{0} points were skipped: special area.", specialExclusions);
                e.Mobile.SendMessage("{0} maps were skipped: bad width/height.", badMap);
                e.Mobile.SendMessage("{0} pins were skipped: not wet.", wetTileFailure);
                e.Mobile.SendMessage("{0} pins were skipped: min distance.", minDist);
                e.Mobile.SendMessage("{0} maps were skipped: bad map bounds.", badMapBounds);
                e.Mobile.SendMessage("{0} maps were skipped: failed map test.", failMap);
                e.Mobile.SendMessage("{0} maps were skipped: failed dist to land test.", noLand);
                e.Mobile.SendMessage("{0} total maps output.", count - failedPin);
            }
            catch (Exception ex)
            {
                LogHelper.LogException(ex);
            }
        }
コード例 #6
0
        public SeaChart(int level, Point2D location)
        {
            m_level = level;

            double skillValue;                                                                                                  // = from.Skills[SkillName.Cartography].Value;

            switch (level)
            {
            case 5:
                skillValue = 100;
                Name       = "a legendary fishing spot";
                break;

            case 4:
                skillValue = 90;
                Name       = "a fabled fishing spot";
                break;

            case 3:
                skillValue = 50;
                Name       = "a good fishing spot";
                break;

            case 2:
                skillValue = 30;
                Name       = "a decent fishing spot";
                break;

            case 1:
            default:
                skillValue = 20;
                Name       = "a fair fishing spot";
                break;
            }

            int dist = 64 + (int)(skillValue * 10);

            if (dist < 200)
            {
                dist = 200;
            }

            int size = 24 + (int)(skillValue * 3.3);

            if (size < 200)
            {
                size = 200;
            }
            else if (size > 400)
            {
                size = 400;
            }

            SetDisplay(location.X - dist, location.Y - dist, location.X + dist, location.Y + dist, size, size);

            Point2D[] pins = SeaChart.GetPinLocations(level, location);

            // place level + 1 pins
            if (pins != null)
            {
                for (int pinNum = 0; pinNum < pins.Length && pinNum <= level; pinNum++)
                {
                    int mapX, mapY;
                    ConvertToMap(pins[pinNum].X, pins[pinNum].Y, out mapX, out mapY);
                    AddPin(mapX, mapY);
                }
            }
        }
コード例 #7
0
 public SeaChart(int level)
     : this(level, SeaChart.GetRandomLocation(level))
 {
 }