为啥会有这么一个需求呢,后面要是继续写的话会详细说,首先是有一个栅格数据,比如这样的:
我的目标是这样的(矢量),
就是这样,上面的栅格数据像大小是2*2的,直接上代码:
string fileNameRaster = System.IO.Path.GetFileName(rasterPath);
IWorkspaceFactory pWorkspaceFactory = new RasterWorkspaceFactory();
string projectPath = System.IO.Path.GetDirectoryName(rasterPath);
IWorkspace rWorkspace = pWorkspaceFactory.OpenFromFile(projectPath, 0);
IRasterWorkspace pRasterWorkspace = rWorkspace as IRasterWorkspace;
IRasterDataset pRasterDataset = pRasterWorkspace.OpenRasterDataset(fileNameRaster);
IRasterLayer pRasterLayer = new RasterLayerClass();
pRasterLayer.CreateFromDataset(pRasterDataset);
IRaster pRaster = pRasterLayer.Raster;
IRasterProps pRasterProps = (IRasterProps)pRaster;
double xMin = pRasterProps.Extent.XMin;
double xMax = pRasterProps.Extent.XMax;
double yMin = pRasterProps.Extent.YMin;
double yMax = pRasterProps.Extent.YMax;
int dHeight = pRasterProps.Height;//当前栅格数据集的行数
int dWidth = pRasterProps.Width; //当前栅格数据集的列数
int count = dHeight * dWidth;//网格数据的总数
double dX = pRasterProps.MeanCellSize().X; //栅格的宽度
double dY = pRasterProps.MeanCellSize().Y; //栅格的高度
IRaster2 raster2 = pRaster as IRaster2;
object o = Type.Missing;
//这个CreateFeatureClass()方法就是创建一个featureclass,我就不贴代码了,网上很多
IFeatureClass pfeatureClass = CreateFeatureClass(System.IO.Path.GetDirectoryName(rasterPath), System.IO.Path.GetFileNameWithoutExtension(rasterPath));
if (pfeatureClass != null)
{
for (int i = 0; i < dHeight; i++)
{
double x0 = xMin;
double y0 = yMax - dY * i;
for (int j = 0; j < dWidth; j++)
{
IGeometry geo = new PolygonClass();
IPolygon polygon = new PolygonClass();
IGeometryCollection pGeomCol = polygon as IGeometryCollection;
IFeature pfeature = pfeatureClass.CreateFeature();
//xMIN, yMax,
IRing pRing = new RingClass();
IPointCollection pPointMulti = pRing as IPointCollection;
//左上
IPoint pPoint0 = new PointClass();
pPoint0.PutCoords(x0 + dX * j, y0);
pPointMulti.AddPoint(pPoint0, ref o, ref o);
//右上
IPoint pPoint1 = new PointClass();
pPoint1.PutCoords(x0 + dX * (j + 1), y0);
pPointMulti.AddPoint(pPoint1, ref o, ref o);
//右下
IPoint pPoint2 = new PointClass();
pPoint2.PutCoords(x0 + dX * (j + 1), y0 - dY);
pPointMulti.AddPoint(pPoint2, ref o, ref o);
//左下
IPoint pPoint3 = new PointClass();
pPoint3.PutCoords(x0 + dX * j, y0 - dY);
pPointMulti.AddPoint(pPoint3, ref o, ref o);
//关闭的点
IPoint pPoint4 = new PointClass();
pPoint4.PutCoords(x0 + dX * j, y0);
pPointMulti.AddPoint(pPoint4, ref o, ref o);
pRing.Close();
if (!pRing.IsExterior)
{
pRing.ReverseOrientation();
}
pGeomCol.AddGeometry(pRing, ref o, o);
ITopologicalOperator topo = polygon as ITopologicalOperator;
topo.Simplify();
geo = polygon;
int numIndex = pfeature.Fields.FindField("number");
int pixelIndex = pfeature.Fields.FindField("pixelValue");
int num = i * dWidth + j;
pfeature.set_Value(numIndex, num);
//0,列号,行号
// object value = raster2.GetPixelValue(0, j, i);
//pfeature.set_Value(pixelIndex, value);
pfeature.Shape = geo as IPolygon;
pfeature.Store();
}
}
}
大概的实现的思路就是以栅格数据的左上角为顶点,先创建一行的数据,因为像元大小为2,point0-point3就是4个角点,左上,右上,右下,左下,需要注意,第一点跟最后一个点必须是同个点,就是把这个图形包起来(我的理解),所有就有了point4,之后依次遍历,一行遍历之后,开始下一个循环,你的左上角的起始顶点变成了上个图形的左下角的坐标。再次循环就可以了,实现思路就是这样。
PS:网格多了程序很耗时。