AE 遍歷柵格實現柵格重分類(C#實現)


 

下面要講的種重分類方法,網上很多。但是好像 System.Array pSafeArray = pPixelBlock.get_SafeArray(0) as System.Array;這一句一直報下面的錯誤。我還沒有解決。

不過還是將這種方法整理一下,轉載自此。

作者本人的初步的解決方法為:

pSafeArray.GetValue(x, y) 替換為 pPixelBlock.GetVal(0, c_x, r_y)。 同時避免了“System.Array pSafeArray = pPixelBlock.get_SafeArray(0) as System.Array”的異常問題。該問題很有可能為內部調用 MemoryStream 的 set_Capacity 時,在申請新內存時失敗,可能是需要存儲到ViewState中的內容太過龐大,或者可用內存太少。導致嘗試將數據序列化寫入ViewState時內存溢出。

 

 

 

下面為正文

--------------------------

柵格重分類方法很多,在AE中有多種方式可以實現,使用地圖代數(在RasterModel中實現),或者IReclassOp,或者Geoprocessor的方式都可以,甚至可以遍歷柵格來實現,這是最原始的方式,不過也可能是最實用的。這里使用的是最原始的遍歷柵格的方式。

private void reclass(IRaster pRaster, float weight)  
{  
    IRasterProps rasterProps = (IRasterProps)pRaster;  
  
    //設置柵格數據起始點  
    IPnt pBlockSize = new Pnt();  
    pBlockSize.SetCoords(rasterProps.Width, rasterProps.Height);  
  
    //選取整個范圍  
    IPixelBlock pPixelBlock = pRaster.CreatePixelBlock(pBlockSize);  
  
    //左上點坐標  
    IPnt tlp = new Pnt();  
    tlp.SetCoords(0, 0);  
  
    //讀入柵格  
    IRasterBandCollection pRasterBands = pRaster as  IRasterBandCollection;  
    IRasterBand pRasterBand = pRasterBands.Item(0);  
    IRawPixels pRawRixels = pRasterBands.Item(0) as IRawPixels;  
    pRawRixels.Read(tlp, pPixelBlock);  
  
    //將PixBlock的值組成數組  
    System.Array pSafeArray = pPixelBlock.get_SafeArray(0) as System.Array;  
    for (int y = 0; y < rasterProps.Height; y++)  
    {  
        for (int x = 0; x < rasterProps.Width; x++)  
        {  
            //int value = Convert.ToInt32(pSafeArray.GetValue(x, y));  
            Byte value = Convert.ToByte(pSafeArray.GetValue(x, y));  
            if (value != 0)  
                pSafeArray.SetValue((Byte)(value * weight), x, y);  
        }  
    }  
  
    pPixelBlock.set_SafeArray(0, pSafeArray);  
  
    //編輯raster,將更新的值寫入raster中  
    IRasterEdit rasterEdit = pRaster as IRasterEdit;  
    rasterEdit.Write(tlp, pPixelBlock);  
    rasterEdit.Refresh();  
}  

 

改變RasterLayer中DEM的值

public void ChangePixelValue(double xMax, double xMin, double yMax, double yMin,double[,] PixelChanged)
{
    IRaster pRaster = thisRasterLayer.Raster;
    IRaster2 pRaster2 = pRaster as IRaster2;       
      
    //地圖坐標轉換為圖中行列值
    rowMax = pRaster2.ToPixelRow(yMin);
    rowMin = pRaster2.ToPixelRow(yMax);
    columnMin = pRaster2.ToPixelColumn(xMin);
    columnMax = pRaster2.ToPixelColumn(xMax);
      
    int Height = rowMax - rowMin + 1;
    int Width = columnMax - columnMin + 1;
      
    //按照需要的大小建立一個空的PixelBlock3
    IPnt blocksize = new PntClass();
    blocksize.SetCoords(Width, Height);
      
    IPixelBlock3 pPixelBlock3 = pRaster.CreatePixelBlock(blocksize) as IPixelBlock3;
      
    System.Array pixels = (System.Array)pPixelBlock3.get_PixelData(0);
      
    //為新建的PixelBlock賦值
    try
    {
        for (int i = 0; i < Height; i++)
        {
            for (int j = 0; j < Width; j++)
            {
                pixels.SetValue(Convert.ToByte(PixelChanged[i,j]), j, i);
            }
        }
    }
    catch (Exception ex)
    {
        MessageBox.Show(ex.Message);
    }
      
    //把像素值賦予新建的PixelBlock3
    pPixelBlock3.set_PixelData(0, pixels);
      
    //PixelBlock3應在的位置
    blocksize.SetCoords(columnMin, rowMin);
      
    //改變的像素值寫入圖層
    IRasterEdit pRasterEdit = pRaster as IRasterEdit;
    pRasterEdit.Write(blocksize, (IPixelBlock)pPixelBlock3);
    pRasterEdit.Refresh();
      
    System.Runtime.InteropServices.Marshal.ReleaseComObject(pRasterEdit);    
}
View Code

 

及將IRasterLayer存儲起來的方法

public static void SaveRasterLayerTofile(IRasterLayer pRasterLayer, string fileName, string strFileExtension="TIFF")
 {

            IRaster pRaster = pRasterLayer.Raster;
            IRaster2 pRaster2 = pRaster as IRaster2;

            ISaveAs pSaveAs = pRaster2 as ISaveAs;
            pSaveAs.SaveAs(fileName, null, strFileExtension);
}

 

 

 

 
參考文章:
 
 
 
 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM