public override void Project(IRasterDataProvider srcRaster, FilePrjSettings prjSettings, ISpatialReference dstSpatialRef, Action <int, string> progressCallback, double weight, float zoom) { ISpatialReference srcSpatialRef = srcRaster.SpatialRef; _projectionTransform = ProjectionTransformFactory.GetProjectionTransform(srcSpatialRef, dstSpatialRef); ArgsCheck(srcRaster, prjSettings, dstSpatialRef); ReadySession(srcRaster, prjSettings, dstSpatialRef, progressCallback); if (prjSettings.OutEnvelope == null || prjSettings.OutEnvelope == PrjEnvelope.Empty) { PrjEnvelope dstEnvelope = null; float srcResolutionX = srcRaster.ResolutionX; float srcResolutionY = srcRaster.ResolutionY; double srcLeftTopX = srcRaster.CoordEnvelope.MinX; double srcLeftTopY = srcRaster.CoordEnvelope.MaxY; int srcWidth = srcRaster.Width; int srcHeight = srcRaster.Height; Size srcSize = new Size(srcWidth, srcHeight); int wSample = 1; int hSample = 1; if (srcWidth > 1000) { wSample = srcWidth / 1000; } if (srcHeight > 1000) { hSample = srcHeight / 1000; } double[] xs = new double[(srcWidth / wSample) * (srcHeight / hSample)]; double[] ys = new double[(srcWidth / wSample) * (srcHeight / hSample)]; int index = 0;//非真实的索引号,采样后的 for (int rowInx = 0; rowInx <= (srcHeight - hSample); rowInx += hSample) { for (int colInx = 0; colInx <= (srcWidth - wSample); colInx += wSample) { xs[index] = srcLeftTopX + colInx * srcResolutionX; ys[index] = srcLeftTopY - rowInx * srcResolutionY; index++; } } _rasterProjector.ComputeDstEnvelope(srcSpatialRef, xs, ys, srcSize, dstSpatialRef, out dstEnvelope, null); prjSettings.OutEnvelope = dstEnvelope; } GC.Collect(); ProjectToLDF(srcRaster, prjSettings, dstSpatialRef, progressCallback, weight, zoom); }
private void TestProj() { Stopwatch stopwatch = new Stopwatch(); stopwatch.Start(); Size srSize = Size.Empty; Double[] lats = null; Double[] longs = null; using (IRasterDataProvider srcPrd = GeoDataDriver.Open(@"D:\masData\FY3A_VIRRX_GBAL_L1_20110322_0525_1000M_MS.HDF") as IRasterDataProvider) { using (IBandProvider srcbandpro = srcPrd.BandProvider as IBandProvider) { srSize = new System.Drawing.Size(srcPrd.Width, srcPrd.Height); lats = new Double[srcPrd.Width * srcPrd.Height]; longs = new Double[srcPrd.Width * srcPrd.Height]; using (IRasterBand latBand = srcbandpro.GetBands("Latitude")[0]) { using (IRasterBand lonsBand = srcbandpro.GetBands("Longitude")[0]) { unsafe { fixed(Double *ptrLat = lats) { fixed(Double *ptrLong = longs) { IntPtr bufferPtrLat = new IntPtr(ptrLat); IntPtr bufferPtrLong = new IntPtr(ptrLong); latBand.Read(0, 0, srcPrd.Width, srcPrd.Height, bufferPtrLat, enumDataType.Double, srcPrd.Width, srcPrd.Height); lonsBand.Read(0, 0, srcPrd.Width, srcPrd.Height, bufferPtrLong, enumDataType.Double, srcPrd.Width, srcPrd.Height); } } } } } stopwatch.Stop(); WriteLine("读取经纬度{0}ms", stopwatch.ElapsedMilliseconds); stopwatch.Restart(); IRasterProjector raster = new RasterProjector(); PrjEnvelope destEnvelope; Action <int, string> progressCallback = new Action <int, string>(OutProgress); //progressCallback = null; //测试不用进度条的情况 ISpatialReference srcSpatialRef = SpatialReferenceFactory.GetSpatialReferenceByPrjFile("WGS 1984.prj"); ISpatialReference dstSpatialRef = SpatialReferenceFactory.GetSpatialReferenceByPrjFile("ChinaBoundary.prj"); raster.ComputeDstEnvelope(srcSpatialRef, longs, lats, srSize, dstSpatialRef, out destEnvelope, progressCallback); stopwatch.Stop(); WriteLine("计算范围{0}ms", stopwatch.ElapsedMilliseconds); WriteLine("范围{0}", destEnvelope.ToString()); Size dstSize = new Size((int)(destEnvelope.Width / 0.01), (int)(destEnvelope.Height / 0.01)); UInt16[] dstRowLookUpTable = new UInt16[dstSize.Width * dstSize.Height]; UInt16[] dstColLookUpTable = new UInt16[dstSize.Width * dstSize.Height]; raster.ComputeIndexMapTable(srcSpatialRef, longs, lats, srSize, dstSpatialRef, dstSize, destEnvelope, out dstRowLookUpTable, out dstColLookUpTable, progressCallback); stopwatch.Stop(); WriteLine("计算投影查找表{0}ms", stopwatch.ElapsedMilliseconds); stopwatch.Restart(); int srcBandCount = srcPrd.BandCount; using (IRasterDataDriver drv = GeoDataDriver.GetDriverByName("LDF") as IRasterDataDriver) { string proj4 = dstSpatialRef.ToProj4String(); using (IRasterDataProvider prdWriter = drv.Create(@"d:\Myproj4LutX.ldf", dstSize.Width, dstSize.Height, srcBandCount, enumDataType.UInt16, "INTERLEAVE=BSQ", "VERSION=LDF", "SPATIALREF=" + proj4) as IRasterDataProvider) { UInt16[] dstData = new UInt16[dstSize.Width * dstSize.Height]; UInt16[] srcData = new UInt16[srSize.Width * srSize.Height]; //int perProgress = 0; //int curProgress = 0; for (int i = 0; i < srcBandCount; i++) { using (IRasterBand latBand = srcPrd.GetRasterBand(i + 1)) { unsafe { fixed(UInt16 *ptr = srcData) { IntPtr bufferptr = new IntPtr(ptr); latBand.Read(0, 0, srSize.Width, srSize.Height, bufferptr, enumDataType.UInt16, srSize.Width, srSize.Height); } } } //stopwatch.Stop(); //WriteLine("读取一个通道{0}ms,通道索引{1}", stopwatch.ElapsedMilliseconds, i + 1); //stopwatch.Restart(); raster.Project <UInt16>(srcData, srSize, dstRowLookUpTable, dstColLookUpTable, dstSize, dstData, 0, progressCallback); //stopwatch.Stop(); //WriteLine("投影一个通道{0}ms,通道索引{1}", stopwatch.ElapsedMilliseconds, i + 1); //stopwatch.Restart(); using (IRasterBand band = prdWriter.GetRasterBand(i + 1)) { unsafe { fixed(UInt16 *ptr = dstData) { IntPtr bufferPtr = new IntPtr(ptr); band.Write(0, 0, band.Width, band.Height, bufferPtr, enumDataType.UInt16, band.Width, band.Height); } } } //curProgress = (i+1) * 100 / srcBandCount; //if (progressCallback != null && curProgress > perProgress) //{ // progressCallback(curProgress, ""); // perProgress = curProgress; //} //stopwatch.Stop(); //WriteLine("写出一个通道{0}ms", stopwatch.ElapsedMilliseconds); //stopwatch.Restart(); } } } stopwatch.Stop(); WriteLine("投影完所有通道{0}ms", stopwatch.ElapsedMilliseconds); stopwatch.Restart(); } } }