private void TryCreateDefaultArgs(AbstractWarpDataset srcRaster, FY3_VIRR_PrjSettings prjSettings,
                                          ref SpatialReference dstSpatialRef)
        {
            if (dstSpatialRef == null)
            {
                dstSpatialRef = _srcSpatialRef;
            }
            if (string.IsNullOrWhiteSpace(prjSettings.OutFormat))
            {
                prjSettings.OutFormat = "LDF";
            }
            if (dstSpatialRef.IsGeographic() == 1)
            {
                _srcImgResolution = 0.01F;
            }
            else
            {
                _srcImgResolution = 1000f;
            }

            if (prjSettings.OutResolutionX <= 0 || prjSettings.OutResolutionY <= 0)
            {
                if (dstSpatialRef.IsGeographic() == 1)
                {
                    prjSettings.OutResolutionX = 0.01F;
                    prjSettings.OutResolutionY = 0.01F;
                }
                else
                {
                    prjSettings.OutResolutionX = 1000F;
                    prjSettings.OutResolutionY = 1000F;
                }
            }

            if (prjSettings.OutBandNos == null || prjSettings.OutBandNos.Length == 0)
            {
                _prjBands = PrjBand.VIRR_1000_Orbit;
            }
            else
            {
                List <PrjBand> bands    = new List <PrjBand>();
                PrjBand[]      defbands = PrjBand.VIRR_1000_Orbit;
                foreach (int bandNo in prjSettings.OutBandNos)
                {
                    bands.Add(defbands[bandNo - 1]);
                }

                _prjBands = bands.ToArray();
            }
        }
        public override AbstractWarpDataset Project(AbstractWarpDataset srcRaster, FilePrjSettings prjSettings,
                                                    AbstractWarpDataset dstRaster, int beginBandIndex, Action <int, string> progressCallback)
        {
            if (srcRaster == null)
            {
                throw new ArgumentNullException("srcRaster");
            }
            if (prjSettings == null)
            {
                throw new ArgumentNullException("prjSettings");
            }
            if (dstRaster == null && prjSettings.OutPathAndFileName == null)
            {
                throw new ArgumentNullException("dstRaster");
            }
            try
            {
                FY3_VIRR_PrjSettings fy3prjSettings = prjSettings as FY3_VIRR_PrjSettings;
                SpatialReference     dstSpatialRef  = (dstRaster.SpatialRef);
                TryCreateDefaultArgs(srcRaster, fy3prjSettings, ref dstSpatialRef);
                DoSession(srcRaster, dstSpatialRef, fy3prjSettings, progressCallback);
                if (prjSettings.OutEnvelope == null || prjSettings.OutEnvelope == PrjEnvelope.Empty)
                {
                    prjSettings.OutEnvelope = _maxPrjEnvelope;
                }
                //if (dstSpatialRef.IsGeographic()==1 && (prjSettings.OutEnvelope.MaxY > 80 || prjSettings.OutEnvelope.MaxY < -80))
                //    throw new Exception(string.Format("高纬度数据[>80],不适合投影为等经纬度数据[{0}]", _maxPrjEnvelope));

                ProjectToLDF(srcRaster, dstRaster, 0, progressCallback);
                return(dstRaster);
            }
            catch
            {
                EndSession();
                TryDeleteCurCatch();
                throw;
            }
            finally
            {
                EndSession();
                if (prjSettings.IsClearPrjCache)
                {
                    TryDeleteCurCatch();
                }
            }
        }
        private Band[] TryCreateRasterDataBands(AbstractWarpDataset srcRaster, FY3_VIRR_PrjSettings prjSettings, Action <int, string> progressCallback)
        {
            List <Band> rasterBands = new List <Band>();

            for (int i = 0; i < _prjBands.Length; i++)
            {
                if (progressCallback != null)
                {
                    progressCallback(_readyProgress++, "准备第" + i + "个输入数据通道");
                }
                PrjBand bandMap  = _prjBands[i];
                Band[]  latBands = srcRaster.GetBands(bandMap.DataSetName);
                Band    band     = latBands[bandMap.DataSetIndex];
                rasterBands.Add(band);
            }
            return(rasterBands.ToArray());
        }
        private void DoSession(AbstractWarpDataset srcRaster, SpatialReference dstSpatialRef,
                               FY3_VIRR_PrjSettings prjSettings, Action <int, string> progressCallback)
        {
            if (_curSession == null || _curSession != srcRaster || _isBeginSession)
            {
                _srcLocationSize = new Size(srcRaster.Width, srcRaster.Height);
                if (progressCallback != null)
                {
                    progressCallback(_readyProgress++, "VIRR读取及预处理经纬度数据集");
                }
                ReadyLocations(srcRaster, dstSpatialRef, _srcLocationSize, out _xs, out _ys, out _maxPrjEnvelope,
                               progressCallback);
                if (progressCallback != null)
                {
                    progressCallback(_readyProgress++, "准备其他参数");
                }
                if (prjSettings.IsRadRef || prjSettings.IsRad)
                {
                    ReadyRadiationArgs(srcRaster);
                }
                if (prjSettings.IsSolarZenith && prjSettings.IsRadRef)
                {
                    _solarZenithCacheFilename = GetSolarZenithCacheFilename(srcRaster.fileName); //太阳天顶角数据
                    if (!File.Exists(_solarZenithCacheFilename))
                    {
                        ReadySolarZenithArgsToFile(srcRaster);
                    }
                    else
                    {
                        _solarZenithCacheRaster = WarpDataset.Open(_solarZenithCacheFilename);
                    }
                    if (prjSettings.IsSensorZenith)
                    {
                        ReadySensorZenith(srcRaster);
                    }
                }

                _rasterDataBands = TryCreateRasterDataBands(srcRaster, prjSettings, progressCallback);
                _isBeginSession  = false;
            }
        }
        private void ReadyArgs(AbstractWarpDataset srcRaster, FilePrjSettings prjSettings,
                               SpatialReference dstSpatialRef, Action <int, string> progressCallback)
        {
            if (srcRaster == null)
            {
                throw new ArgumentNullException("srcRaster");
            }
            if (prjSettings == null)
            {
                throw new ArgumentNullException("prjSettings");
            }
            _readyProgress = 0;
            _prjSettings   = prjSettings as FY3_VIRR_PrjSettings;
            _dstSpatialRef = dstSpatialRef;
            MemoryHelper.MemoryNeed(200, 1536); //剩余200MB,已使用1.2GB
            if (progressCallback != null)
            {
                progressCallback(_readyProgress++, "准备相关参数");
            }
            TryCreateDefaultArgs(srcRaster, _prjSettings, ref dstSpatialRef);
            //这里去除的是读取轨道数据时候的左右像元个数。
            _left  = 4;
            _right = 4;
            TrySetLeftRightInvalidPixel(_prjSettings.ExtArgs);
            DoSession(srcRaster, dstSpatialRef, _prjSettings, progressCallback);
            if (prjSettings.OutEnvelope == null || prjSettings.OutEnvelope == PrjEnvelope.Empty)
            {
                prjSettings.OutEnvelope = _maxPrjEnvelope;
                _orbitBlock             = new Block
                {
                    xBegin = 0, yBegin = 0, xEnd = srcRaster.Width - 1, yEnd = srcRaster.Height - 1
                };
            }
            else
            {
                GetEnvelope(_xs, _ys, srcRaster.Width, srcRaster.Height, _prjSettings.OutEnvelope, out _orbitBlock);
                if (_orbitBlock == null || _orbitBlock.Width <= 0 || _orbitBlock.Height <= 0)
                {
                    throw new Exception("数据不在目标区间内");
                }
                float invalidPresent = (_orbitBlock.Width * _orbitBlock.Height * 1.0F) /
                                       (srcRaster.Width * srcRaster.Height);
                if (invalidPresent < 0.0001f)
                {
                    throw new Exception("数据占轨道数据比例太小,有效率" + invalidPresent * 100 + "%");
                }
                if (invalidPresent > 0.60)
                {
                    _orbitBlock = new Block
                    {
                        xBegin = 0, yBegin = 0, xEnd = srcRaster.Width - 1, yEnd = srcRaster.Height - 1
                    }
                }
                ;
            }

            //if (dstSpatialRef.IsGeographic()==1 && (prjSettings.OutEnvelope.MaxY > 80 || prjSettings.OutEnvelope.MaxY < -80))
            //    throw new Exception(string.Format("高纬度数据,不适合投影为等经纬度数据[{0}]", _maxPrjEnvelope));
            _dstSpatialRef = dstSpatialRef;
            _dstEnvelope   = _prjSettings.OutEnvelope;
            if (!_dstEnvelope.IntersectsWith(_maxPrjEnvelope))
            {
                throw new Exception("数据不在目标区间内");
            }
            _outResolutionX = _prjSettings.OutResolutionX;
            _outResolutionY = _prjSettings.OutResolutionY;
            _outFormat      = _prjSettings.OutFormat;
            _outfilename    = _prjSettings.OutPathAndFileName;
            _dstProj4       = _dstSpatialRef.ExportToProj4();
            _dstBandCount   = _prjBands.Length;
            _dstSize        = _prjSettings.OutSize;
            _isRadRef       = _prjSettings.IsRadRef;
            _isSolarZenith  = _prjSettings.IsSolarZenith;
            _isSensorZenith = _prjSettings.IsSensorZenith;
            _isRad          = _prjSettings.IsRad;
        }
 private void DoSession(AbstractWarpDataset srcRaster, AbstractWarpDataset geoRaster, SpatialReference dstSpatialRef, FY3_VIRR_PrjSettings prjSettings, Action <int, string> progressCallback)
 {
     if (_curSession == null || _curSession != srcRaster || _isBeginSession)
     {
         if (progressCallback != null)
         {
             progressCallback(_readyProgress++, "读取及预处理经纬度数据集");
         }
         ReadyLocations(_geoDataProvider, SpatialReferenceFactory.CreateSpatialReference(4326), dstSpatialRef, out _srcLocationSize, out _xs, out _ys, out _maxPrjEnvelope, progressCallback);
         if (progressCallback != null)
         {
             progressCallback(_readyProgress++, "准备其他参数");
         }
         if (prjSettings.IsRadRef || prjSettings.IsRad)
         {
             ReadyRadiationArgs(srcRaster);
         }
         if (prjSettings.IsSolarZenith && prjSettings.IsRadRef)
         {
             _solarZenithCacheFilename = GetSolarZenithCacheFilename(geoRaster.fileName);    //太阳天顶角数据
             if (!File.Exists(_solarZenithCacheFilename))
             {
                 ReadySolarZenithArgsToFile(geoRaster);
             }
             else
             {
                 var ds = Gdal.OpenShared(_solarZenithCacheFilename, Access.GA_ReadOnly);
                 _solarZenithCacheRaster = new WarpDataset(ds, _solarZenithCacheFilename);
             }
             if (prjSettings.IsSensorZenith)
             {
                 ReadySensorZenith(geoRaster);
             }
         }
         _rasterDataBands = TryCreateRasterDataBands(srcRaster, prjSettings, progressCallback);
         _isBeginSession  = false;
     }
 }