Grade control

But all this is to leave the entire area leveled at 0, and if you want to give it a slope, let’s say 0.5x1000?

Nice job

1 Like

Working on adding slope. Any thoughts on how to do that? If you pick a rectangle, do you edit the four corners? Do you pick a side to slope to? Do you pick an anchor point and pull or push that point? The later is my best guess, grab a point and reslope the surrounding points to a given slope, that would be adjustable. Would like to have any thoughts.

1 Like

My cousin uses a basic grade controller from Deere. The way it works is you pick a point, a direction and a slope and it makes an infinite plane that it tries to grade to. Perhaps a point, direction slope and bounding box would be desirable for a GUI implementation? Something to think about is how big the blade is. If you are trying to make a dimple the size of a kitchen table with a 40 foot blade, you aren’t going to succeed very well. So perhaps blade size could affect a “smoothing” parameter?

Just 5 cents from a guy who’s taking a stab in the dark :slight_smile:
Cheers

1 Like

I would like a mode like to put some reference pts (where the slopes changes) with a desired elevation and then make a calculation like it does in my opengrade3D in OpenGL.designer.cs line 474 to 1004

the more pts you put the more planes it would calculate.
Something like the blue pts in this field.
Maybe with an selectable elevation option before putting the point like -copy the actual elevation or put this elevation(with a box)
og3d pts
here is the code
for each design pt you search the closest blue pt on each side an make an average. Or maybe make something similar with only the 3 closest pts.
Note that you would have to change the minDistSE,SW… from 900 to a bigger value. 900 is 30 meter away (30x30)

 int closestPointMap = 0;
                        int closestPointMapSE = -1;
                        int closestPointMapSW = -1;
                        int closestPointMapNE = -1;
                        int closestPointMapNW = -1;

                        
                        minDistMap = 1000;
                        double minDistSE = 900;
                        double minDistSW = 900;
                        double minDistNE = 900;
                        double minDistNW = 900;

                        //find the closest point to current fix
                        for (int t = 0; t < ptCount; t++)
                        {
                            double distMap = ((h - ct.ptList[t].easting) * (h - ct.ptList[t].easting))
                                            + ((i - ct.ptList[t].northing) * (i - ct.ptList[t].northing));
                            if (distMap < minDistMap)
                            {
                                minDistMap = distMap;
                                closestPointMap = t;       
                            }

                            //Search closest point South West
                            if (h >= ct.ptList[t].easting && i >= ct.ptList[t].northing)
                            {
                                //double distMapSW = ((h - ct.ptList[t].easting) * (h - ct.ptList[t].easting))
                                //            + ((i - ct.ptList[t].northing) * (i - ct.ptList[t].northing));
                                if (distMap < minDistSW)
                                {
                                    minDistSW = distMap;
                                    closestPointMapSW = t;
                                }
                            }

                            //Search closest point South East
                            if (h <= ct.ptList[t].easting && i >= ct.ptList[t].northing)
                            {
                                //double distMapSE = ((h - ct.ptList[t].easting) * (h - ct.ptList[t].easting))
                                //            + ((i - ct.ptList[t].northing) * (i - ct.ptList[t].northing));
                                if (distMap < minDistSE)
                                {
                                    minDistSE = distMap;
                                    closestPointMapSE = t;
                                }
                            }

                            //Search closest point North West
                            if (h >= ct.ptList[t].easting && i <= ct.ptList[t].northing)
                            {
                                //double distMapNW = ((h - ct.ptList[t].easting) * (h - ct.ptList[t].easting))
                                //            + ((i - ct.ptList[t].northing) * (i - ct.ptList[t].northing));
                                if (distMap < minDistNW)
                                {
                                    minDistNW = distMap;
                                    closestPointMapNW = t;
                                }
                            }

                            //Search closest point North East
                            if (h <= ct.ptList[t].easting && i <= ct.ptList[t].northing)
                            {
                                //double distMapNE = ((h - ct.ptList[t].easting) * (h - ct.ptList[t].easting))
                                //            + ((i - ct.ptList[t].northing) * (i - ct.ptList[t].northing));
                                if (distMap < minDistNE)
                                {
                                    minDistNE = distMap;
                                    closestPointMapNE = t;
                                }
                            }
                        }

                        if (minDistMap < minDistMapDist)
                        {
                            
                            double cutFillMap = 0;
                            //double avgAltitude = 0;
                            //double avgCutAltitude = 0;
                            
                            //here calculate the closest point on each line

                            distanceFromNline = 1000;
                            distanceFromSline = 1000;
                            distanceFromEline = 1000;
                            distanceFromWline = 1000;

                            double NoLineAverageAlt = 0;
                            double NoLineAverageCutAlt = 0;
                            double NoLineCount = 0;
                            double NoLineCutCount = 0;

                            //Calculate the North line
                            if (minDistNE < 900 && minDistNW < 900)
                            {
                                double dxN = ct.ptList[closestPointMapNE].easting - ct.ptList[closestPointMapNW].easting;
                                double dyN = ct.ptList[closestPointMapNE].northing - ct.ptList[closestPointMapNW].northing;

                                //how far from Line is fix
                                distanceFromNline = ((dyN * pn.easting) - (dxN * pn.northing) + (ct.ptList[closestPointMapNE].easting
                                            * ct.ptList[closestPointMapNW].northing) - (ct.ptList[closestPointMapNE].northing * ct.ptList[closestPointMapNW].easting))
                                            / Math.Sqrt((dyN * dyN) + (dxN * dxN));

                                //absolute the distance
                                distanceFromNline = Math.Abs(distanceFromNline);


                                //calc point onLine closest to current blade position
                                double UN = (((pn.easting - ct.ptList[closestPointMapNW].easting) * dxN)
                                        + ((pn.northing - ct.ptList[closestPointMapNW].northing) * dyN))
                                        / ((dxN * dxN) + (dyN * dyN));

                                //point on line closest to blade center
                                eastingNpt = ct.ptList[closestPointMapNW].easting + (UN * dxN);
                                northingNpt = ct.ptList[closestPointMapNW].northing + (UN * dyN);

                                //calc altitude for that point
                                altitudeNpt = ct.ptList[closestPointMapNW].altitude + (UN * (ct.ptList[closestPointMapNE].altitude - ct.ptList[closestPointMapNW].altitude));
                                if (ct.ptList[closestPointMapNE].cutAltitude > 0 && ct.ptList[closestPointMapNW].cutAltitude > 0)
                                {
                                    cutAltNpt = ct.ptList[closestPointMapNW].cutAltitude + (UN * (ct.ptList[closestPointMapNE].cutAltitude - ct.ptList[closestPointMapNW].cutAltitude));
                                    NoLineAverageCutAlt += cutAltNpt;
                                    NoLineCutCount++;
                                }
                                else cutAltNpt = -1;

                                NoLineAverageAlt += altitudeNpt;
                                NoLineCount++;
                            }

                            //Calculate the South line
                            if (minDistSE < 900 && minDistSW < 900)
                            {
                                double dxS = ct.ptList[closestPointMapSE].easting - ct.ptList[closestPointMapSW].easting;
                                double dyS = ct.ptList[closestPointMapSE].northing - ct.ptList[closestPointMapSW].northing;

                                //how far from Line is fix
                                distanceFromSline = ((dyS * pn.easting) - (dxS * pn.northing) + (ct.ptList[closestPointMapSE].easting
                                            * ct.ptList[closestPointMapSW].northing) - (ct.ptList[closestPointMapSE].northing * ct.ptList[closestPointMapSW].easting))
                                            / Math.Sqrt((dyS * dyS) + (dxS * dxS));

                                //absolute the distance
                                distanceFromSline = Math.Abs(distanceFromSline);


                                //calc point onLine closest to current blade position
                                double US = (((pn.easting - ct.ptList[closestPointMapSW].easting) * dxS)
                                        + ((pn.northing - ct.ptList[closestPointMapSW].northing) * dyS))
                                        / ((dxS * dxS) + (dyS * dyS));

                                //point on line closest to blade center
                                eastingSpt = ct.ptList[closestPointMapSW].easting + (US * dxS);
                                northingSpt = ct.ptList[closestPointMapSW].northing + (US * dyS);

                                //calc altitude for that point
                                altitudeSpt = ct.ptList[closestPointMapSW].altitude + (US * (ct.ptList[closestPointMapSE].altitude - ct.ptList[closestPointMapSW].altitude));
                                if (ct.ptList[closestPointMapSE].cutAltitude > 0 && ct.ptList[closestPointMapSW].cutAltitude > 0)
                                {
                                    cutAltSpt = ct.ptList[closestPointMapSW].cutAltitude + (US * (ct.ptList[closestPointMapSE].cutAltitude - ct.ptList[closestPointMapSW].cutAltitude));
                                    NoLineAverageCutAlt += cutAltSpt;
                                    NoLineCutCount++;
                                }
                                else cutAltSpt = -1;

                                NoLineAverageAlt += altitudeSpt;
                                NoLineCount++;
                            }

                            //Calculate the West line
                            if (minDistSW < 900 && minDistNW < 900)
                            {
                                double dxW = ct.ptList[closestPointMapNW].easting - ct.ptList[closestPointMapSW].easting;
                                double dyW = ct.ptList[closestPointMapNW].northing - ct.ptList[closestPointMapSW].northing;

                                //how far from Line is fix
                                distanceFromWline = ((dyW * pn.easting) - (dxW * pn.northing) + (ct.ptList[closestPointMapNW].easting
                                            * ct.ptList[closestPointMapSW].northing) - (ct.ptList[closestPointMapNW].northing * ct.ptList[closestPointMapSW].easting))
                                            / Math.Sqrt((dyW * dyW) + (dxW * dxW));

                                //absolute the distance
                                distanceFromWline = Math.Abs(distanceFromWline);


                                //calc point onLine closest to current blade position
                                double UW = (((pn.easting - ct.ptList[closestPointMapSW].easting) * dxW)
                                        + ((pn.northing - ct.ptList[closestPointMapSW].northing) * dyW))
                                        / ((dxW * dxW) + (dyW * dyW));

                                //point on line closest to blade center
                                eastingWpt = ct.ptList[closestPointMapSW].easting + (UW * dxW);
                                northingWpt = ct.ptList[closestPointMapSW].northing + (UW * dyW);

                                //calc altitude for that point
                                altitudeWpt = ct.ptList[closestPointMapSW].altitude + (UW * (ct.ptList[closestPointMapNW].altitude - ct.ptList[closestPointMapSW].altitude));
                                if (ct.ptList[closestPointMapNW].cutAltitude > 0 && ct.ptList[closestPointMapSW].cutAltitude > 0)
                                {
                                    cutAltWpt = ct.ptList[closestPointMapSW].cutAltitude + (UW * (ct.ptList[closestPointMapNW].cutAltitude - ct.ptList[closestPointMapSW].cutAltitude));
                                    NoLineAverageCutAlt += cutAltWpt;
                                    NoLineCutCount++;
                                }
                                else cutAltWpt = -1;

                                NoLineAverageAlt += altitudeWpt;
                                NoLineCount++;
                            }

                            //Calculate the East line
                            if (minDistSE < 900 && minDistNE < 900)
                            {
                                double dxE = ct.ptList[closestPointMapNE].easting - ct.ptList[closestPointMapSE].easting;
                                double dyE = ct.ptList[closestPointMapNE].northing - ct.ptList[closestPointMapSE].northing;

                                //how far from Line is fix
                                distanceFromEline = ((dyE * pn.easting) - (dxE * pn.northing) + (ct.ptList[closestPointMapNE].easting
                                            * ct.ptList[closestPointMapSE].northing) - (ct.ptList[closestPointMapNE].northing * ct.ptList[closestPointMapSE].easting))
                                            / Math.Sqrt((dyE * dyE) + (dxE * dxE));

                                //absolute the distance
                                distanceFromEline = Math.Abs(distanceFromEline);


                                //calc point onLine closest to current blade position
                                double UE = (((pn.easting - ct.ptList[closestPointMapSE].easting) * dxE)
                                        + ((pn.northing - ct.ptList[closestPointMapSE].northing) * dyE))
                                        / ((dxE * dxE) + (dyE * dyE));

                                //point on line closest to blade center
                                eastingEpt = ct.ptList[closestPointMapSE].easting + (UE * dxE);
                                northingEpt = ct.ptList[closestPointMapSE].northing + (UE * dyE);

                                //calc altitude for that point
                                altitudeEpt = ct.ptList[closestPointMapSE].altitude + (UE * (ct.ptList[closestPointMapNE].altitude - ct.ptList[closestPointMapSE].altitude));
                                if (ct.ptList[closestPointMapNE].cutAltitude > 0 && ct.ptList[closestPointMapSE].cutAltitude > 0)
                                {
                                    cutAltEpt = ct.ptList[closestPointMapSE].cutAltitude + (UE * (ct.ptList[closestPointMapNE].cutAltitude - ct.ptList[closestPointMapSE].cutAltitude));
                                    NoLineAverageCutAlt += cutAltEpt;
                                    NoLineCutCount++;
                                }
                                else
                                    cutAltEpt = -1;

                                NoLineAverageAlt += altitudeEpt;
                                NoLineCount++;
                            }

                            // Give a value to the lines witout values
                            if (NoLineCount > 0)
                            {
                                NoLineAverageAlt = NoLineAverageAlt / NoLineCount;
                                if (NoLineCutCount > 0)
                                    NoLineAverageCutAlt = NoLineAverageCutAlt / NoLineCutCount;
                                else NoLineAverageCutAlt = -1;

                                if (distanceFromNline == 1000)
                                {
                                    altitudeNpt = NoLineAverageAlt;
                                    cutAltNpt = NoLineAverageCutAlt;
                                }

                                if (distanceFromSline == 1000)
                                {
                                    altitudeSpt = NoLineAverageAlt;
                                    cutAltSpt = NoLineAverageCutAlt;
                                }

                                if (distanceFromWline == 1000)
                                {
                                    altitudeWpt = NoLineAverageAlt;
                                    cutAltWpt = NoLineAverageCutAlt;
                                }

                                if (distanceFromEline == 1000)
                                {
                                    altitudeEpt = NoLineAverageAlt;
                                    cutAltEpt = NoLineAverageCutAlt;
                                }
                            }

                            // check if the blade is close from a line
                            double mindistFromLine = distanceFromNline;
                            double eastingLine = eastingNpt;
                            double northingLine = northingNpt;
                            double altitudeLine = altitudeNpt;
                            double cutAltLine = cutAltNpt;

                            if (distanceFromSline < mindistFromLine)
                            {
                                mindistFromLine = distanceFromSline;
                                eastingLine = eastingSpt;
                                northingLine = northingSpt;
                                altitudeLine = altitudeSpt;
                                cutAltLine = cutAltSpt;
                            }

                            if (distanceFromEline < mindistFromLine)
                            {
                                mindistFromLine = distanceFromEline;
                                eastingLine = eastingEpt;
                                northingLine = northingEpt;
                                altitudeLine = altitudeEpt;
                                cutAltLine = cutAltEpt;
                            }

                            if (distanceFromWline < mindistFromLine)
                            {
                                mindistFromLine = distanceFromWline;
                                eastingLine = eastingWpt;
                                northingLine = northingWpt;
                                altitudeLine = altitudeWpt;
                                cutAltLine = cutAltWpt;
                            }


                            // Calulate the closest point alitude and cutAltitude

                            //double cutFillMap;
                            double avgAltitude = -1;
                            double avgCutAltitude = -1;

                            

                            // if the pt is near the closest pt or No Average is selected or there is only one survey pt
                            int nbrofPt = 4;
                            if (minDistNE == 900) nbrofPt--;
                            if (minDistNW == 900) nbrofPt--;
                            if (minDistSE == 900) nbrofPt--;
                            if (minDistSW == 900) nbrofPt--;

                            if (minDist < 1 | nbrofPt < 2)
                            {
                                // if the closest point is under the center of the blade
                                avgAltitude = ct.ptList[closestPointMap].altitude;
                                avgCutAltitude = ct.ptList[closestPointMap].cutAltitude;
                            }
                            else if (mindistFromLine < 1)
                            // if the blade is near a line
                            {
                                avgAltitude = altitudeLine;
                                avgCutAltitude = cutAltLine;

                                
                            }
                            else
                            {
                                if (distanceFromEline < 1000 | distanceFromNline < 1000 | distanceFromSline < 1000 | distanceFromWline < 1000)
                                {
                                    //if there is a line on at least one side
                                    double sumofCloseDist = 1 / distanceFromNline + 1 / distanceFromSline + 1 / distanceFromEline + 1 / distanceFromWline;

                                    avgAltitude = ((altitudeNpt / distanceFromNline) + (altitudeSpt / distanceFromSline) +
                                    (altitudeEpt / distanceFromEline) + (altitudeWpt / distanceFromWline)) / sumofCloseDist;

                                    if (cutAltNpt == -1 | cutAltSpt == -1 | cutAltWpt == -1 | cutAltEpt == -1)
                                    {
                                        avgCutAltitude = ct.ptList[closestPointMap].cutAltitude;
                                    }
                                    else
                                    {
                                        avgCutAltitude = (cutAltNpt / distanceFromNline + cutAltSpt / distanceFromSline +
                                    cutAltEpt / distanceFromEline + cutAltWpt / distanceFromWline) / sumofCloseDist;

                                    }
                                }
                                else
                                // if there are no lines but 2 pt build the diag
                                {
                                    double eastingDiaPt;
                                    double northingDiaPt;

                                    //Calculate the diag line SE to NW
                                    if (minDistSE < 900 && minDistNW < 900)
                                    {
                                        double dx = ct.ptList[closestPointMapNW].easting - ct.ptList[closestPointMapSE].easting;
                                        double dy = ct.ptList[closestPointMapNW].northing - ct.ptList[closestPointMapSE].northing;

                                        //how far from Line is fix
                                        //double distanceFromline = ((dy * pn.easting) - (dx * pn.northing) + (ct.ptList[closestPointMapNW].easting
                                        //            * ct.ptList[closestPointMapSE].northing) - (ct.ptList[closestPointMapNW].northing * ct.ptList[closestPointMapSE].easting))
                                        //            / Math.Sqrt((dy * dy) + (dx * dx));

                                        //absolute the distance
                                        //distanceFromline = Math.Abs(distanceFromline);


                                        //calc point onLine closest to current blade position
                                        double U = (((pn.easting - ct.ptList[closestPointMapSE].easting) * dx)
                                                + ((pn.northing - ct.ptList[closestPointMapSE].northing) * dy))
                                                / ((dx * dx) + (dy * dy));

                                        //point on line closest to blade center
                                        eastingDiaPt = ct.ptList[closestPointMapSE].easting + (U * dx);
                                        northingDiaPt = ct.ptList[closestPointMapSE].northing + (U * dy);

                                        //calc altitude for that point
                                        avgAltitude = ct.ptList[closestPointMapSE].altitude + (U * (ct.ptList[closestPointMapNW].altitude - ct.ptList[closestPointMapSE].altitude));
                                        if (ct.ptList[closestPointMapNW].cutAltitude > 0 && ct.ptList[closestPointMapSE].cutAltitude > 0)
                                        {
                                            avgCutAltitude = ct.ptList[closestPointMapSE].cutAltitude + (U * (ct.ptList[closestPointMapNW].cutAltitude - ct.ptList[closestPointMapSE].cutAltitude));
                                        }
                                        else
                                            avgCutAltitude = -1;                                        
                                    }
                                    //Calculate the diag line SW to NE
                                    else if (minDistSW < 900 && minDistNE < 900)
                                    {
                                        double dx = ct.ptList[closestPointMapNE].easting - ct.ptList[closestPointMapSW].easting;
                                        double dy = ct.ptList[closestPointMapNE].northing - ct.ptList[closestPointMapSW].northing;

                                        //how far from Line is fix
                                        //double distanceFromline = ((dy * pn.easting) - (dx * pn.northing) + (ct.ptList[closestPointMapNE].easting
                                        //            * ct.ptList[closestPointMapSW].northing) - (ct.ptList[closestPointMapNE].northing * ct.ptList[closestPointMapSW].easting))
                                        //            / Math.Sqrt((dy * dy) + (dx * dx));

                                        //absolute the distance
                                        //distanceFromline = Math.Abs(distanceFromline);


                                        //calc point onLine closest to current blade position
                                        double U = (((pn.easting - ct.ptList[closestPointMapSW].easting) * dx)
                                                + ((pn.northing - ct.ptList[closestPointMapSW].northing) * dy))
                                                / ((dx * dx) + (dy * dy));

                                        //point on line closest to blade center
                                        eastingDiaPt = ct.ptList[closestPointMapSW].easting + (U * dx);
                                        northingDiaPt = ct.ptList[closestPointMapSW].northing + (U * dy);

                                        //calc altitude for that point
                                        avgAltitude = ct.ptList[closestPointMapSW].altitude + (U * (ct.ptList[closestPointMapNE].altitude - ct.ptList[closestPointMapSW].altitude));
                                        if (ct.ptList[closestPointMapNE].cutAltitude > 0 && ct.ptList[closestPointMapSW].cutAltitude > 0)
                                        {
                                            avgCutAltitude = ct.ptList[closestPointMapSW].cutAltitude + (U * (ct.ptList[closestPointMapNE].cutAltitude - ct.ptList[closestPointMapSW].cutAltitude));
                                        }
                                        else
                                            avgCutAltitude = -1;                                        
                                    }

                                }
                            }

                            if (avgCutAltitude < 1) cutFillMap = 9999;
                            else cutFillMap = avgCutAltitude - avgAltitude;

                            mapListPt point = new mapListPt(h, i, drawPtWidth, avgAltitude, avgCutAltitude,
                                cutFillMap, ct.ptList[closestPointMap].lastPassAltitude);
                            ct.mapList.Add(point);
1 Like

Thought a few times about just take the dimples or bumps out. If a point is the size of the kitchen table, and nothing inside of a blade width is within a tolerance, adjust that point’s cut/fill height. Should be able to pass the whole list through a smoothing routine. Number of passes would smooth it further and further. Using @Pat reference points as no touch anchors is a real possibility. Now, for a typical site, we cannot manipulate the boundary grade without building a retaining wall. In other words drastic change of grade is not allowed next to the neighbor’s property. So, perhaps by default the boundary would be anchored, click on or off.

1 Like

Look at a linear programming solution. Try reading carefully the academic paper “Land Forming Design By Linear Programming” written by “Sowell, Shih and Kriz”. It contains everything you need.

Good luck.

2 Likes

I think this is how it should work. Using a reference plane, you could give it the desired inclination and direction.

1 Like

A lot of interesting info here!
ezigrade algorithms basis.

From this page:
Water always flows to the edge of the job:
This is a field onto itself with the GIS community; and there are a lot of different academic papers in the literature. To access these resources you can google “Depression Filling” which shows the depth of this subject. It is also common in the literature to pass a low pass filter over the surface first (ie smoothing off ridges and filling valleys etc) before running the algorithm. We have based our work on these existing algorithms.

There are a couple of existing GIS software solutions that can perform this operation. For example “WhiteBox GAT” and ESRI “Arc GIS”. However obviously we prefer that you use Ezigrade as we create an output directly that you can use on your favorite grading machine.

1 Like

Added a smoothing function. May not be by the paper, but it sets the current point to the average of the points around it. The more you click it, the smoother it becomes. This is two shots of @Pat 's hole one before and one after smoothing.

image

image

This is in profile:

image

Building a pad:

image

And it’s smoothed profile.

image

Then added a reset to survey button, and built a loop to run the smooth 100 times. Took about 15 secs including redrawing the map.

image

It’s profile west to east. The grade difference across the property is minimal. Note how straight the line overlays it.

image

2 Likes

Again, not by the paper. But thanks to @Pat, if you select a few points across the center of the field and set them to what you want and ignore them during the 100 loop, this is what you get. Also tried several points around the field, it works.

image

image

You grab a set of points and hold it at an elevation, it will form the rest to match. Bad words for a farmer, but this is a pond in the middle of @Pat’s field.

image

And you can just get dumb and build your own pyramid.

image

2 Likes

Yeah there is a big pond in the center!
@KentStuff So can you take this field and putt one pt in the green center to make it 15 or 20 cm higher and then run the loop to smooth it? Elevating the center a bit?
This is real nice work!
image

here is what i have done with optisurface so far
Water can exit everywhere except the red S1 zone.
optiheight
opticutfill
It’s a powerful software! Just cost some $$$ :frowning_face: :wink:

3 Likes

Yes, but like you said, you need to grab a couple of points and set what you want them. They can all be set individually. I set one point up 10 meters and made a nice giant termite mound.

The best thing that was done was the reset button. Edit, make a mess, reset, make a new mess.

Now I need to put a slider bar that controls how smooth. 1 to 100 loops. Running the 100 loops twice almost makes a flat field at the average elevation on your field.

3 Likes

@Pat,

I grew up in the roofing industry and we had to taper roofs to shed the water to all sides. So we would find the hip/ridge/valley points and slope square with the edge of the roof. Using that same concept, I set a series of reference points down the ridges and hips of your land and then ran the smooth. I did not tie the boundaries so they adjusted slightly as well. Here is the reference map:

image

Here is the smoothed gradient map.

image

Here’s the profile:

image

Here’s another through your low spot:

image

Here is the design file: See what it looks like in optisurface.

Survey.agd.txt (54.4 KB)

This is it right at the low spot in Opengrade3d wit the cut and fill visuals turned on.

image

3 Likes

I did some surveys today with OpenGrade3D and AOG. I think something is wrong with my AOG survey.
Here is a survey with AOG (white pts) over the field.kml from the field made this spring with AOG 4.3.10.
AOGsurvey
I will have to check the code.

@nut Did you survey some fields and checked if the seem to be correct?
I think these from Opengrade are OK. just change the .ags to .txt to open in googleEarth.

I will now invest some $ to build the .agd file to see if the boundary fit when going back to the field.

1 Like

It looks just reverse of the twist that I found in the ABLine conversion. I’m unsure if I picked up all the small adjustments that are built into the lat/long to easting northing calcs.

1 Like

Yeah there is a convergence angle to calculate in AOG, not in OpenGrade. I think I read something about it on the forum some months ago. I think this is the reason we had to restart our fields on one update?

So my AOG should now work, will test soon.

@KentStuff I think your ABline conversion will need an update
here is what i found: (search for DecDeg2UTM)

string[] fix = item.Split(',');
                                        double.TryParse(fix[0], NumberStyles.Float, CultureInfo.InvariantCulture, out lonK);
                                        double.TryParse(fix[1], NumberStyles.Float, CultureInfo.InvariantCulture, out latK);
                                        double[] xy = mf.pn.DecDeg2UTM(latK, lonK);

                                        //match new fix to current position
                                        easting = xy[0] - mf.pn.utmEast;
                                        northing = xy[1] - mf.pn.utmNorth;

                                        double east = easting;
                                        double nort = northing;

                                        //fix the azimuth error
                                        easting = (Math.Cos(-mf.pn.convergenceAngle) * east) - (Math.Sin(-mf.pn.convergenceAngle) * nort);
                                        northing = (Math.Sin(-mf.pn.convergenceAngle) * east) + (Math.Cos(-mf.pn.convergenceAngle) * nort);

                                        //add the point to boundary
                                        vec3 bndPt = new vec3(easting, northing, 0);
                                        mf.bnd.bndArr[i].bndLine.Add(bndPt);
1 Like

Thanks, I could not see all of the code in your post on the phone. But tracked the same information and found the same problem. Convergence. @BrianTee_Admin sent me to school on this a while back. I guess I need to repeat that class as well.

2 Likes

Made a field test today with two optisurface design files and the boundary and elevations seem to be fine. Didn’t grade, way to wet here.
I released a new OpenGrade3D (again) v1.0.5.
So now I’m pretty sure the loop survey-design-grade is working.
Next step will be grading and find the right settings for the valve!

1 Like

I added the convergence info back into opengrade. I don’t know if it makes any difference. I’d need to export a few coordinates and compare them. Now if you are recording lat and long from the gps or simulator, then using that data (lat and long), I don’t see why there would be any difference. However, imported gps or output a gps based on a calculated easting/northing, may be off. Again, I don’t know. I’ll have to set up a test. Any thoughts?

1 Like

yeah
I only import and export lat/long so it’s fine for opengrade.
The difference is that the files with easting/northing are not compatible between AOG and opengrade.

From what i understand, opengrade make no convergence at all, meaning that the northing at the field’s 0 northing is not corrected to line up with true north. It doesn’t affect precision at all, the internal coordinates are just not the same than AOG.

I think all import/export should be only made with Lat/Long keeping easting/northing for internal use.
I’m not planning to implement convergence correction unless someone proves me its utility.

@KentStuff The lat/long conversion is used in the survey boundary since it’s a half toolwidth away from antenna, then the other pts use the gps position directly. In importing all pts passe trough the converter, obliviously.
In AOG all survey pts pass trough the converter because of roll compensation.

2 Likes