Esempio n. 1
0
 static private void GetMovingWindow(IRasterDigitalElevationModel dem, double[][] window, int x, int y)
 {
     for (int xi = -1; xi <= 1; xi++)
     {
         for (int yi = -1; yi <= 1; yi++)
         {
             window[xi + 1][yi + 1] = dem.GetElevationForDataPoint(x + xi, y + yi);
         }
     }
 }
Esempio n. 2
0
        public virtual void CopyElevationPointsFrom(IRasterDigitalElevationModel dem)
        {
            if (dem == null)
            {
                throw new ArgumentNullException("dem");
            }

            if (LatResolution != dem.LatResolution || LonResolution != dem.LonResolution)
            {
                throw new ArgumentException("The two DEM's have incompatibile resolutions.");
            }

            // cell absolute position
            int cellLonAbs = dem.LonOffset * dem.LonResolution;
            int cellLatAbs = dem.LatOffset * dem.LatResolution;

            // first find the place to copy to and extent

            // initialize the copying rectangle to the cell's extent
            int west, south, east, north;

            west  = cellLonAbs;
            south = cellLatAbs;
            east  = west + dem.LonResolution - 1;
            north = south + dem.LatResolution - 1;

            // now intersect it with the destination extent
            if (LonOffset > west)
            {
                west = LonOffset;
            }
            if (LatOffset > south)
            {
                south = LatOffset;
            }
            if (LonOffset + LonLength - 1 < east)
            {
                east = LonOffset + LonLength - 1;
            }
            if (LatOffset + LatLength - 1 < north)
            {
                north = LatOffset + LatLength - 1;
            }

            for (int xx = west; xx <= east; xx++)
            {
                for (int yy = south; yy <= north; yy++)
                {
                    double elevation = dem.GetElevationForDataPoint(xx - cellLonAbs, yy - cellLatAbs);
                    SetElevationForDataPoint(xx - LonOffset, yy - LatOffset, elevation);
                }
            }
        }
Esempio n. 3
0
        private Polyline ConstructIsohypseSegment(IRasterDigitalElevationModel dem, IsohypseMovements isohypseMovements)
        {
            Polyline polyline = new Polyline();

            polyline.IsClosed = isohypseMovements.IsClosed;

            int x = isohypseMovements.StartingX;
            int y = isohypseMovements.StartingY;

            bool checkedOrientation = false;
            bool shouldBeReversed   = false;

            foreach (IsohypseMovement movement in isohypseMovements.Movements)
            {
                int dx1 = 0, dx2 = 0, dy1 = 0, dy2 = 0;

                switch (movement)
                {
                case IsohypseMovement.East:
                    x++;
                    dx1 = dx2 = x;
                    dy1 = y;
                    dy2 = y + 1;
                    break;

                case IsohypseMovement.North:
                    dx1 = x;
                    dx2 = x + 1;
                    dy1 = dy2 = y;
                    y--;
                    break;

                case IsohypseMovement.South:
                    y++;
                    dx1 = x + 1;
                    dx2 = x;
                    dy1 = dy2 = y;
                    break;

                case IsohypseMovement.West:
                    dx1 = dx2 = x;
                    dy1 = y + 1;
                    dy2 = y;
                    x--;
                    break;
                }

                double elevation1 = dem.GetElevationForDataPoint(dx1, dy1);
                double elevation2 = dem.GetElevationForDataPoint(dx2, dy2);

                // check the orientation of the isohypse
                if (false == checkedOrientation)
                {
                    // the right-side elevation should be higher
                    if (elevation2 < elevation1)
                    {
                        shouldBeReversed = true;
                    }
                }

                double factor = (isohypseMovements.IsohypseElevation - elevation1) / (elevation2 - elevation1);
                double ix, iy;
                ix = (factor * (dx2 - dx1) + dx1);
                iy = (factor * (dy2 - dy1) + dy1);
                GeoPosition     geoPos         = dem.GetGeoPosition(ix, iy);
                Point3 <double> isohypseVertex = new Point3 <double> (geoPos.Longitude, geoPos.Latitude, isohypseMovements.IsohypseElevation);

                polyline.AddVertex(isohypseVertex);
            }

            // now reverse the polyline if needed
            if (shouldBeReversed)
            {
                polyline.Reverse();
            }

            return(polyline);
        }
Esempio n. 4
0
        public void Isoplete(IRasterDigitalElevationModel dem, double elevationStep, NewIsohypseCallback callback)
        {
            DigitalElevationModelStatistics statistics = dem.CalculateStatistics();

            double minElevation = Math.Floor(statistics.MinElevation / elevationStep) * elevationStep;
            double maxElevation = Math.Floor(statistics.MaxElevation / elevationStep) * elevationStep;

            //if (visualizer != null)
            //{
            //    GeoPosition geoPosMin = dem.GetGeoPosition (0, 0, false);
            //    GeoPosition geoPosMax = dem.GetGeoPosition (dem.LonLength, dem.LatLength, false);

            //    visualizer.Initialize (geoPosMin.Longitude, geoPosMin.Latitude,
            //        geoPosMax.Longitude, geoPosMax.Latitude);
            //}

            Array2 <byte>             flags     = new Array2 <byte> (dem.LonLength - 1, dem.LatLength - 1);
            Array2 <IsohypseMovement> movements = new Array2 <IsohypseMovement> (dem.LonLength - 1, dem.LatLength - 1);

            int[,] adjacentCells = new int[, ] {
                { 0, 0 }, { 1, 0 }, { 1, 1 }, { 0, 1 }
            };

            // foreach elevation step
            for (double isoElev = minElevation; isoElev <= maxElevation; isoElev += elevationStep)
            {
                activityLogger.Log(ActivityLogLevel.Normal, String.Format(System.Globalization.CultureInfo.InvariantCulture,
                                                                          "Analyzing elevation {0}", isoElev));

                //if (visualizer != null)
                //{
                //    GeoPosition geoPosMin = dem.GetGeoPosition (0, 0, false);
                //    GeoPosition geoPosMax = dem.GetGeoPosition (dem.LongLength, dem.LatLength, false);

                //    visualizer.Initialize (geoPosMin.Longitude, geoPosMin.Latitude,
                //        geoPosMax.Longitude, geoPosMax.Latitude);

                //    for (int x = 0; x < dem.LongLength; x++)
                //    {
                //        for (int y = 0; y < dem.LatLength; y++)
                //        {
                //            int elevation = dem.GetElevation (x, y);
                //            GeoPosition geoPos = dem.GetGeoPosition (x, y);

                //            string color = elevation >= isoElev ? "orange" : "yellow";

                //            visualizer.DrawPoint (color, geoPos.Longitude, geoPos.Latitude);
                //            visualizer.DrawText ("pink", geoPos.Longitude, geoPos.Latitude, elevation.ToString ());
                //        }
                //    }
                //}

                Isohypse isohypse = new Isohypse(isoElev);

                flags.Initialize(0);
                movements.Initialize(0);

                for (int x = 0; x < dem.LonLength - 1; x++)
                {
                    for (int y = 0; y < dem.LatLength - 1; y++)
                    {
                        byte cellCharacteristic = 0;

                        for (int i = 0; i < adjacentCells.GetLength(0); i++)
                        {
                            double adjacentCellElev = dem.GetElevationForDataPoint(x + adjacentCells[i, 0], y + adjacentCells[i, 1]);
                            if (adjacentCellElev >= isoElev)
                            {
                                cellCharacteristic++;
                                flags.SetValue((byte)(flags.GetValue(x, y) | (byte)(1 << i)), x, y);
                            }
                        }

                        // skip cells which are definitively not along the isohypse
                        if (cellCharacteristic == 0 || cellCharacteristic == 4)
                        {
                            continue;
                        }

                        if (cellCharacteristic == 2)
                        {
                            int maskedFlags = flags.GetValue(x, y) & 0x9;
                            if (maskedFlags == 0 || maskedFlags == 0x9)
                            {
                                movements.SetValue(IsohypseMovement.North | IsohypseMovement.South, x, y);
                            }
                            else
                            {
                                maskedFlags = flags.GetValue(x, y) & 0x3;
                                if (maskedFlags == 0 || maskedFlags == 0x3)
                                {
                                    movements.SetValue(IsohypseMovement.West | IsohypseMovement.East, x, y);
                                }

                                else
                                {
                                    movements.SetValue(
                                        IsohypseMovement.West | IsohypseMovement.East | IsohypseMovement.North | IsohypseMovement.South,
                                        x, y);
                                }
                            }
                        }
                        else
                        {
                            int maskedFlags = flags.GetValue(x, y) & 0x3;
                            if (maskedFlags != 0 && maskedFlags != 0x3)
                            {
                                movements.SetValue(movements.GetValue(x, y) | IsohypseMovement.North, x, y);
                            }

                            maskedFlags = flags.GetValue(x, y) & 0x6;
                            if (maskedFlags != 0 && maskedFlags != 0x6)
                            {
                                movements.SetValue(movements.GetValue(x, y) | IsohypseMovement.East, x, y);
                            }

                            maskedFlags = flags.GetValue(x, y) & 0xc;
                            if (maskedFlags != 0 && maskedFlags != 0xc)
                            {
                                movements.SetValue(movements.GetValue(x, y) | IsohypseMovement.South, x, y);
                            }

                            maskedFlags = flags.GetValue(x, y) & 0x9;
                            if (maskedFlags != 0 && maskedFlags != 0x9)
                            {
                                movements.SetValue(movements.GetValue(x, y) | IsohypseMovement.West, x, y);
                            }
                        }

                        //if (visualizer != null)
                        //{
                        //    if (cellCharacteristic > 0 && cellCharacteristic < 4)
                        //    {
                        //        GeoPosition geoPos = dem.GetGeoPosition (x + 0.5, y + 0.5);

                        //        if (movements.GetValue (x, y)
                        //            == (IsohypseMovement.West | IsohypseMovement.East | IsohypseMovement.North | IsohypseMovement.South))
                        //            visualizer.DrawText ("blue", geoPos.Longitude, geoPos.Latitude,
                        //                "X");

                        //        //visualizer.DrawText ("blue", geoPos.Longitude, geoPos.Latitude,
                        //        //    cellCharacteristic == 2 ? "K" : "T");

                        //        //List<Point2> points = new List<Point2> ();

                        //        //if ((movements[x, y] & IsohypseMovement.North) != 0)
                        //        //    points.Add (new Point2 (0.5, 0));
                        //        //if ((movements[x, y] & IsohypseMovement.East) != 0)
                        //        //    points.Add (new Point2 (1, 0.5));
                        //        //if ((movements[x, y] & IsohypseMovement.South) != 0)
                        //        //    points.Add (new Point2 (0.5, 1));
                        //        //if ((movements[x, y] & IsohypseMovement.West) != 0)
                        //        //    points.Add (new Point2 (0, 0.5));

                        //        //List<GeoPosition> geoPoints = new List<GeoPosition> ();

                        //        //foreach (Point2 point in points)
                        //        //    geoPoints.Add (dem.GetGeoPosition (x + point.X, y + point.Y));

                        //        //visualizer.DrawLine ("black", geoPoints[0].Longitude, geoPoints[0].Latitude,
                        //        //    geoPoints[1].Longitude, geoPoints[1].Latitude);

                        //        //if (geoPoints.Count > 2)
                        //        //    visualizer.DrawLine ("black", geoPoints[2].Longitude, geoPoints[2].Latitude,
                        //        //        geoPoints[3].Longitude, geoPoints[3].Latitude);
                        //    }
                        //}
                    }
                }

                for (int x = 0; x < dem.LonLength - 1; x++)
                {
                    for (int y = 0; y < dem.LatLength - 1; y++)
                    {
                        if (movements.GetValue(x, y) != IsohypseMovement.None)
                        {
                            IsohypseMovements isohypseMovements = ExtractIsohypseMovements(dem, isoElev, movements, flags, x, y);

                            Polyline isohypseSegment = ConstructIsohypseSegment(dem, isohypseMovements);

                            isohypseSegment.RemoveDuplicateVertices();

                            isohypse.AddSegment(isohypseSegment);

                            activityLogger.Log(ActivityLogLevel.Verbose, String.Format(System.Globalization.CultureInfo.InvariantCulture,
                                                                                       "Found segment with {0} vertices", isohypseSegment.VerticesCount));
                        }
                    }
                }

                if (isohypse.Segments.Count > 0)
                {
                    callback(isohypse);
                }

                //isoColl.AddIsohypse (isohypse);
            }
        }
        static public IList <PointOfInterest> FindPeaks(IRasterDigitalElevationModel dem, int howMany)
        {
            IList <PointOfInterest> peaks = new List <PointOfInterest> ();

            Point2 <int>[] neighbourPoints = { new Point2 <int> (-1, 0), new Point2 <int> (1, 0), new Point2 <int> (0, -1),
                                               new Point2 <int> (0, 1) };

            for (int x = 1; x < dem.LonLength - 1; x++)
            {
                for (int y = 1; y < dem.LatLength - 1; y++)
                {
                    double elevation = dem.GetElevationForDataPoint(x, y);

                    // first check if it is a peak
                    bool isPeak = true;
                    for (int i = 0; i < neighbourPoints.Length; i++)
                    {
                        if (elevation <= dem.GetElevationForDataPoint((int)(x + neighbourPoints[i].X), (int)(y + neighbourPoints[i].Y)))
                        {
                            isPeak = false;
                            break;
                        }
                    }

                    if (isPeak)
                    {
                        for (int i = 0; i < peaks.Count + 1; i++)
                        {
                            bool addPeak = false;

                            if (i == peaks.Count)
                            {
                                addPeak = true;
                            }
                            else
                            {
                                PointOfInterest peak = peaks[i] as PointOfInterest;

                                if (elevation > peak.Position.Elevation)
                                {
                                    addPeak = true;
                                }
                            }

                            if (addPeak)
                            {
                                PointOfInterest newPeak = new PointOfInterest(dem.GetGeoPosition(x, y),
                                                                              String.Format(System.Globalization.CultureInfo.InvariantCulture, "Peak {0}", elevation));
                                peaks.Insert(i, newPeak);
                                if (peaks.Count > howMany)
                                {
                                    peaks.RemoveAt(peaks.Count - 1);
                                }
                                break;
                            }
                        }
                    }
                }
            }

            return(peaks);
        }
Esempio n. 6
0
        static private double CalculateNeighbours(IRasterDigitalElevationModel dem, MissingElevation me)
        {
            double interpolatedElevation = 0;

            me.MissingNeighbours = 0;

            if (me.Lng > 0)
            {
                double elevation = dem.GetElevationForDataPoint(me.Lng - 1, me.Lat);
                if (elevation == Int16.MinValue)
                {
                    me.MissingNeighbours++;
                }
                else
                {
                    interpolatedElevation += elevation;
                }
            }
            else
            {
                me.MissingNeighbours++;
            }

            if (me.Lng < dem.LonLength - 1)
            {
                double elevation = dem.GetElevationForDataPoint(me.Lng + 1, me.Lat);
                if (elevation == Int16.MinValue)
                {
                    me.MissingNeighbours++;
                }
                else
                {
                    interpolatedElevation += elevation;
                }
            }
            else
            {
                me.MissingNeighbours++;
            }

            if (me.Lat > 0)
            {
                double elevation = dem.GetElevationForDataPoint(me.Lng, me.Lat - 1);
                if (elevation == Int16.MinValue)
                {
                    me.MissingNeighbours++;
                }
                else
                {
                    interpolatedElevation += elevation;
                }
            }
            else
            {
                me.MissingNeighbours++;
            }

            if (me.Lat < dem.LatLength - 1)
            {
                double elevation = dem.GetElevationForDataPoint(me.Lng, me.Lat + 1);
                if (elevation == Int16.MinValue)
                {
                    me.MissingNeighbours++;
                }
                else
                {
                    interpolatedElevation += elevation;
                }
            }
            else
            {
                me.MissingNeighbours++;
            }

            if (me.MissingNeighbours < 4)
            {
                interpolatedElevation /= (4 - me.MissingNeighbours);
            }
            else
            {
                interpolatedElevation = 0;
            }

            return(interpolatedElevation);
        }
Esempio n. 7
0
        public IRasterDigitalElevationModel Process(IRasterDigitalElevationModel input)
        {
            // clone data
            IRasterDigitalElevationModel output = input.Clone() as IRasterDigitalElevationModel;

            SortedList <MissingElevation, Point2 <double> > missingElevations = new SortedList <MissingElevation, Point2 <double> > ();

            // find all missing elevations
            for (int x = 0; x < output.LonLength; x++)
            {
                for (int y = 0; y < output.LatLength; y++)
                {
                    double elevation = output.GetElevationForDataPoint(x, y);
                    if (elevation == double.MinValue)
                    {
                        MissingElevation me = new MissingElevation();
                        me.Lng = x;
                        me.Lat = y;

                        // now calculate missing neighbours count
                        CalculateNeighbours(output, me);

                        // now add it to the list
                        missingElevations.Add(me, new Point2 <double> (me.Lng, me.Lat));
                    }
                }
            }

            int startingMissingElevations = missingElevations.Count;

            // while there are missing elevations
            while (missingElevations.Count > 0)
            {
                // use first missing elevation
                MissingElevation me = missingElevations.Keys[0];

                // based on the neighbouring non-missing data, calculate interpolated elevation
                double interpolatedElevation = CalculateNeighbours(output, me);

                // enter this elevation into the output ElevationData
                output.SetElevationForDataPoint(me.Lng, me.Lat, interpolatedElevation);

                // remove this elevation from missing elevation list
                missingElevations.Remove(me);

                // for each neighbour which is also missing elevation:
                // decrease the missingNeighbours counter
                // and reposition the neighbour in the missing elevations list

                Point2 <double>[] neighbourPoints = { new Point2 <double> (me.Lng - 1, me.Lat),
                                                      new Point2 <double> (me.Lng + 1, me.Lat),new Point2 <double> (me.Lng,  me.Lat - 1),
                                                      new Point2 <double> (me.Lng,     me.Lat + 1) };
                for (int i = 0; i < 4; i++)
                {
                    Point2 <double> p = neighbourPoints[i];
                    if (missingElevations.ContainsValue(p))
                    {
                        MissingElevation me2 = missingElevations.Keys[missingElevations.IndexOfValue(p)];
                        missingElevations.Remove(me2);
                        me2.MissingNeighbours--;
                        missingElevations.Add(me2, p);
                    }
                }
            }

            return(output);
        }