美文网首页
AE栅格处理:读取、加载、复制、修改属性、创建栅格数据集、保存、

AE栅格处理:读取、加载、复制、修改属性、创建栅格数据集、保存、

作者: 吵吵人 | 来源:发表于2019-03-25 20:40 被阅读0次

    从图层中读取数据

    //读取指定图层,含有landuse字样
    if (axMapControl1.LayerCount > 0)
        for (int i = 0; i < axMapControl1.LayerCount; i++)
            if (axMapControl1.get_Layer(i).Name.Contains("landuse"))
                rasterLayer = (IRasterLayer)axMapControl1.Map.get_Layer(i);
    
    IRaster raster = rasterLayer.Raster;      
    IRaster2 pRaster2 = raster as IRaster2; //IRaster2接口常用于处理栅格
    

    将栅格加载至地图中

        // 是否将最后的结果加载至地图
        DialogResult dr = MessageBox.Show("是否将结果添加至地图?", "提示", MessageBoxButtons.YesNo, MessageBoxIcon.Question);
        if (dr == DialogResult.Yes)
        {
    
            IRasterLayer pRasterLayer;
            pRasterLayer = new RasterLayer();
            pRasterLayer.CreateFromRaster(raster);           
            ILayer pLayer = pRasterLayer as ILayer;
            axMapControl1.AddLayer(pLayer, 0);
            axMapControl1.ActiveView.Refresh();
        }
    

    复制栅格

    注意: 是rasterbandcollection.Item(0).RasterDataset;,不是简单的接口转换,否则会出现错误。

    IRasterBandCollection rasterbandcollection = raster as IRasterBandCollection;
    IRasterDataset rasterdataset = rasterbandcollection.Item(0).RasterDataset;
    
    IWorkspaceFactory rWorkspaceFactory = new RasterWorkspaceFactory();
    IWorkspace rasterWorkspace=rWorkspaceFactory.OpenFromFile(@"E:\GraduationProject\data\数据备份", 0);
    IDataset resultDataset = rasterdataset.Copy("栖霞2005.tif", rasterWorkspace);
    
    MessageBox.Show("栅格复制完毕!");
    

    栅格属性

    //获取栅格属性
    IRasterProps rasterProps = (IRasterProps)raster;    //栅格属性
    int dHeight = rasterProps.Height;           //当前栅格数据集的行数484
    int dWidth = rasterProps.Width;             //当前栅格数据集的列数894
    double dX = rasterProps.MeanCellSize().X;   //栅格的宽度50
    double dY = rasterProps.MeanCellSize().Y;   //栅格的高度50
    IEnvelope extent = rasterProps.Extent;      //当前栅格数据集的范围   
    rasterProps.PixelType = rstPixelType.PT_LONG; //设置栅格像素值类型为PT_LONG型 
    

    提取栅格数据值到二维数组

    private int[,] GetPixelValueToIntArray(IRaster pRaster)
    {
        IRaster2 pRaster2 = pRaster as IRaster2;
        IRasterProps pRasterProps = pRaster as IRasterProps;
    
        int Height = pRasterProps.Height;
        int Width = pRasterProps.Width;
        int[,] PixelValue = new int[Height, Width];
        IRasterCursor pRasterCursor = pRaster2.CreateCursorEx(null); //参数设为null,内部自动设置PixelBlock大小
       
        long blockwidth = 0;
        long blockheight = 0;
                
        try
        {
            do
            {
                int left = (int)pRasterCursor.TopLeft.X;
                int top = (int)pRasterCursor.TopLeft.Y;
    
                IPixelBlock3 pPixelBlock3 = pRasterCursor.PixelBlock as IPixelBlock3;
       
                blockheight = pPixelBlock3.Height;
                blockwidth = pPixelBlock3.Width;
    
                System.Array pixels = (System.Array)pPixelBlock3.get_PixelData(0);
       
                for (int i = 0; i < blockheight; i++)
                    for (int j = 0; j < blockwidth; j++)
                        PixelValue[top + i, left + j] = Convert.ToInt32(pixels.GetValue(j, i));
            }
            while (pRasterCursor.Next() == true);                
        }
        catch(Exception ex)
        {
            MessageBox.Show(ex.Message);
        }
        return PixelValue;
    }
    
    

    修改栅格数据值

    像素块移动修改像素值,可以自定义像素块的大小

    public void ChangeRasterValue(IRaster pRaster, int[,] values)
    {
        IRaster2 pRaster2 = pRaster as IRaster2;
        IRasterProps pRasterProps = pRaster as IRasterProps;
      
        //获取图层的行列值  
        int Height = pRasterProps.Height;
        int Width = pRasterProps.Width;
      
        //定义并初始化数组,用于存储栅格内所有像员像素值
        short[,] PixelValue = new short[Width, Height];
        System.Array pixels;
      
        //数设为null,内部自动设置PixelBlock大小
        IRasterCursor pRasterCursor = pRaster2.CreateCursorEx(null);
      
        //用于存储PixelBlock的长宽
        long blockwidth = 0;
        long blockheight = 0;
      
        IPixelBlock3 pPixelBlock3;
        IRasterEdit pRasterEdit = pRaster2 as IRasterEdit;  //栅格状态编辑
        try
        {
            do
            {
                //获取Cursor的左上角坐标
                int left = (int)pRasterCursor.TopLeft.X;
                int top = (int)pRasterCursor.TopLeft.Y;
      
                pPixelBlock3 = pRasterCursor.PixelBlock as IPixelBlock3;
      
                blockheight = pPixelBlock3.Height;
                blockwidth = pPixelBlock3.Width;
                //pPixelBlock3.Mask(255);
      
                pixels = (System.Array)pPixelBlock3.get_PixelData(0);
      
                //获取该Cursor的PixelBlock中像素的值
                try
                {
                    for (int i = 0; i < blockwidth; i++)
                         for (int j = 0; j < blockheight; j++)
                        {
                            //一定要注意,pixels中的数组排序为[Width,Height]
                            object pvalue = pixels.GetValue(i, j);
                            if (Convert.ToInt32(pvalue) != -9999)  PixelValue.SetValue((short)1, i, j);
                        }
                }
                catch (Exception)
                {
                }
            }
            while (pRasterCursor.Next() == true);
    
            pPixelBlock3.set_PixelData(0, PixelValue);
            pRasterEdit.Write(pRasterCursor.TopLeft, (IPixelBlock)pPixelBlock3);
            pRasterEdit.Refresh();
            System.Runtime.InteropServices.Marshal.ReleaseComObject(pRasterEdit);
        
        }
        catch(Exception ex)
        {
            MessageBox.Show(ex.Message);
        }           
    }
    
    //释放资源
    System.Runtime.InteropServices.Marshal.ReleaseComObject(pRasterEdit);
    

    创建栅格数据集

    之前一直不会如何创建一个栅格,只会备份了栅格数据之后,再修改栅格的值。这种办法让人觉得很不舒服。现在,可以随心所欲的创建了。其实就两步:

    1. CreateRasterDataset 创建一个栅格数据集
    2. 给栅格赋值
      step1:从栅格中创建像素块
      step2:修改像素块的值
      step3:将像素块写入栅格

    ok,大功告成!

            public IRasterDataset CreateFileRasterDataset(string directoryName, string fileName,IRasterProps pros,int[,] data)
            {
                try
                {
                    IRasterDataset rasterDataset = null;
                    IPoint originPoint = new PointClass();
                    originPoint.PutCoords(pros.Extent.XMin, pros.Extent.YMin);   
    
                    // Create the dataset
                    IRasterWorkspace2 rasterWorkspace2 = null;
                    rasterWorkspace2 = this.CreateRasterWorkspace(directoryName);
    
                    //rasterDataset = rasterWorkspace2.CreateRasterDataset(fileName, "TIFF", originPoint, pros.Width, pros.Height, pros.MeanCellSize().X, pros.MeanCellSize().Y, 1, pros.PixelType, new UnknownCoordinateSystemClass(), true);
                    rasterDataset = rasterWorkspace2.CreateRasterDataset(fileName, "TIFF", originPoint, pros.Width, pros.Height, pros.MeanCellSize().X, pros.MeanCellSize().Y, 1, pros.PixelType, pros.SpatialReference, true);
    
    
                    IRasterBandCollection rasterBands = (IRasterBandCollection)rasterDataset;
                    IRasterBand rasterBand;
                    IRasterProps rasterProps;
                    rasterBand = rasterBands.Item(0);
                    rasterProps = (IRasterProps)rasterBand;
                    rasterProps.NoDataValue = this.mNoDataValue;
                    IRaster raster = rasterDataset.CreateDefaultRaster();
    
    
                    //Create a pixel block using the weight and height of the raster dataset. 
                    //If the raster dataset is large, a smaller pixel block should be used. 
                    //Refer to the topic "How to access pixel data using a raster cursor".
                    IPnt blocksize = new PntClass();
                    blocksize.SetCoords(pros.Width, pros.Height);
                    IPixelBlock3 pixelblock = raster.CreatePixelBlock(blocksize)as IPixelBlock3;
    
                    //Populate some pixel values to the pixel block.
                    System.Array pixels;
                    pixels = (System.Array)pixelblock.get_PixelData(0);
                    for (int i = 0; i < pros.Width; i++)
                        for (int j = 0; j < pros.Height; j++)
                            //if (i == j)
                            //    pixels.SetValue(Convert.ToByte(255), i, j);
                            //else
                            pixels.SetValue(Convert.ToByte(data[j, i]), i, j);
    
    
                    ////测试
                    ////Populate some pixel values to the pixel block.
                    //System.Array pixels;
                    //pixels = (System.Array)pixelblock.get_PixelData(0);
                    //for (int i = 0; i < pros.Width; i++)
                    //    for (int j = 0; j < pros.Height; j++)
                    //        pixels.SetValue(Convert.ToByte(255), i, j);
    
                    //for (int i = 200; i < 500; i++)
                    //    for (int j = 100; j <200; j++)
                    //        pixels.SetValue(Convert.ToByte(5), i, j);
    
    
                    pixelblock.set_PixelData(0, (System.Array)pixels);
    
                    //Define the location that the upper left corner of the pixel block is to write.
                    IPnt upperLeft = new PntClass();
                    upperLeft.SetCoords(0, 0);
    
                    //Write the pixel block.
                    IRasterEdit rasterEdit = (IRasterEdit)raster;
                    rasterEdit.Write(upperLeft, (IPixelBlock)pixelblock);
    
                    //Release rasterEdit explicitly.
                    System.Runtime.InteropServices.Marshal.ReleaseComObject(rasterEdit);
    
                    return rasterDataset ;
                }
                catch (Exception ex)
                {
                    System.Diagnostics.Debug.WriteLine(ex.Message);
                    return null;
                }
            }
    
            public IRasterWorkspace2 CreateRasterWorkspace(string pathName)
            {
                // Create RasterWorkspace
                IWorkspaceFactory workspaceFactory = new RasterWorkspaceFactoryClass();
    
                return workspaceFactory.OpenFromFile(pathName, 0) as IRasterWorkspace2;
            }
    

    如果取消掉测试的注释,黑色是其他的图,白色是修改的图


    测试结果

    在给很少量的点创建栅格时,可以先给栅格统一赋值成无值,再设置某些点的栅格值,否则会出现其他区域为0,而不是无值的情况。

    用二维数组更新栅格数据

    整体一次性更新完毕


    public void ChangeRasterValue(IRaster pRaster, int[,] values)
    {
        IRaster2 pRaster2 = pRaster as IRaster2;
        IRasterProps pRasterProps = pRaster as IRasterProps;
                
        int Height = pRasterProps.Height;
        int Width = pRasterProps.Width;
    
        short[,] PixelValue = new short[Width, Height];
    
        Pnt pntSize = new PntClass();
        pntSize.X = pRasterProps.Width;
        pntSize.Y = pRasterProps.Height;
    
        IRasterCursor pRasterCursor = pRaster2.CreateCursorEx(pntSize);
        IRasterEdit pRasterEdit = pRaster2 as IRasterEdit; 
        try
        {
            for (int i = 0; i < Width; i++)
                for (int j = 0; j < Height; j++)
                    PixelValue.SetValue((short)values[j, i],i,j);
    
            IPixelBlock3 pPixelBlock3 = pRasterCursor.PixelBlock as IPixelBlock3;
            System.Array pixels = (System.Array)pPixelBlock3.get_PixelData(0);
            pPixelBlock3.set_PixelData(0, PixelValue);
            pRasterEdit.Write(pRasterCursor.TopLeft, (IPixelBlock)pPixelBlock3);
            pRasterEdit.Refresh();
            System.Runtime.InteropServices.Marshal.ReleaseComObject(pRasterEdit);
            MessageBox.Show("完成遍历!");
        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message);
        }
    } 
    

    保存栅格

    可以用rasterBandCollection.SaveAs(fullPath, rWorkspace, "TIFF");
    亦可以用pRaster2接口转换到ISaveAS接口

    private void SaveRasterToFile(IRaster2 pRaster2)
    {          
        //保存结果
        SaveFileDialog sd = new SaveFileDialog();
        sd.Title = "保存文件";
        sd.InitialDirectory = @"E:\毕设CA项目\TEST\结果\";
        sd.Filter = "栅格数据(*.tif)|(*.tif)";
        try
        {
            if (sd.ShowDialog() == DialogResult.OK)
            {
                string fullPath = sd.FileName;
                int index = fullPath.LastIndexOf("\\");
                string direction = fullPath.Substring(0, index);        //路径,没带//
                string name = fullPath.Substring(index + 1);            //文件名  
    
                IWorkspaceFactory rWorkspaceFactory = new RasterWorkspaceFactory();
                IWorkspace rasterWorkspace = rWorkspaceFactory.OpenFromFile(direction + "\\", 0);
                IRasterBandCollection rasterBandCollection = pRaster2 as IRasterBandCollection;
                rasterBandCollection.SaveAs(fullPath, rasterWorkspace, "TIFF");
            }
        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message.ToString());
        }
    }
    

    结果写入txt文件

    string filename = System.IO.Directory.GetCurrentDirectory() + @"文件名.txt";
    System.IO.FileStream fs = System.IO.File.Create(filename);
    fs.Close();
    System.IO.StreamWriter sw = new System.IO.StreamWriter(filename);
    
    for(int i=0;i<num;i++)
    {
        for(int j=0;j<3;j++)
        {
            if(j<2)
                sw.Write(arr[i, j] + ", ");
            else 
                sw.Write(arr[i, j]);
        }
        sw.Write("\r\n");
    }
    sw.Flush();
    

    弹出窗口自定义保存路径

    //自定义保存路径
    SaveFileDialog sd = new SaveFileDialog();
    sd.Title = "保存文件";
    sd.InitialDirectory = @"E:\GraduationProject\result\";
    try
    {
        if (sd.ShowDialog() == DialogResult.OK)
        {
            fullPath = sd.FileName;
            //int index = fullPath.LastIndexOf("\\");
            //string direction = fullPath.Substring(0, index);        //路径,没带//
            //string name = fullPath.Substring(index + 1);            //文件名  
        }
    }
    catch (Exception ex)
    {
        MessageBox.Show(ex.Message.ToString());
    }
    

    计时器

    //记时开始
    Stopwatch timer = new Stopwatch();
    timer.Start();   
    
    //记时结束
    timer.Stop();
    
    //运行时间
    timer.Elapsed.ToString()
    

    ArcObjects API Reference for .NET:http://resources.arcgis.com/en/help/arcobjects-net/componenthelp/

    相关文章

      网友评论

          本文标题:AE栅格处理:读取、加载、复制、修改属性、创建栅格数据集、保存、

          本文链接:https://www.haomeiwen.com/subject/ztxivqtx.html