remove ncep from awips2-builds

Former-commit-id: 9b99b3a881 [formerly d9437337a6]
Former-commit-id: 5665ee6f11
This commit is contained in:
AWIPS User 2015-04-23 03:59:57 -06:00
parent 4f28f24f15
commit f4dde8dc1d
6719 changed files with 0 additions and 1362322 deletions

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.edex.ncep.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,425 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.edex.ncep.feature"
label="EDEX NCEP Feature"
version="1.0.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<plugin
id="edu.wisc.ssec.mcidas"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.airmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.atcf"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.aww"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.convsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ffg"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.idft"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.intlsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncscat"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.nonconvsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.tcm"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.wcp"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.log"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.airmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.atcf"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.convsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ffg"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.idft"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.intlsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.mcidas"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.mosaic"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ncgrib"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ncscat"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.nonconvsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.tcm"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.wcp"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.mcidas"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncpafm"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncscd"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.nctaf"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncuair"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.sgwh"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.sgwhv"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ssha"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.stormtrack"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.common"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.sgwh"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.sgwhv"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ssha"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.stormtrack"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.uengine"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.log4j.config"
download-size="0"
install-size="0"
version="0.0.0"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.solarimage"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.solarimage"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ntrans"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.geomag"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.geomag"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.pgen"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.pgen"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.gpd"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.gpd"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.gempak"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.gempak"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.airep"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.pirep"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.airep"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.pirep"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
</feature>

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.edex.ncep.nco.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,73 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.edex.ncep.nco.feature"
label="EDEX NCEP National Centers Feature"
version="1.0.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<requires>
<import feature="com.raytheon.uf.edex.ncep.feature" version="1.0.0.qualifier"/>
</requires>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.aww"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.nctext"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ncpafm"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ncscd"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.nctaf"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ncuair"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.ntrans"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
</feature>

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.viz.aviation.advisory.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,54 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.viz.aviation.advisory.feature"
label="Aviation Advisory Feature"
version="1.14.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<plugin
id="com.raytheon.uf.viz.aviation.advisory"
download-size="0"
install-size="0"
version="0.0.0"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.airmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.convsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.intlsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.nonconvsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
</feature>

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.viz.ncep.core.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,95 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.viz.ncep.core.feature"
label="NCEP Viz Core Feature"
version="1.0.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<requires>
<import feature="com.raytheon.uf.viz.cots.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.common.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.viz.text.feature" version="1.0.0.qualifier"/>
</requires>
<plugin
id="gov.noaa.nws.ncep.viz.common"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.localization"
download-size="0"
install-size="0"
version="0.0.0"/>
<plugin
id="gov.noaa.nws.ncep.common"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.common"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.gempak.parameters"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.log"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.log4j.config"
download-size="0"
install-size="0"
version="0.0.0"/>
<plugin
id="gov.noaa.nws.ncep.viz.ui.display"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.gempak.parameters.core"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.staticdata"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
</feature>

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.viz.ncep.dataplugins.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,206 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.viz.ncep.dataplugins.feature"
label="NCEP Dataplugins Feature"
version="1.0.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<requires>
<import feature="com.raytheon.uf.viz.cots.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.ncep.core.feature" version="1.0.0.qualifier"/>
</requires>
<plugin
id="gov.nasa.gsfc.fits"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.edex.plugin.mosaic"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="edu.wisc.ssec.mcidas"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.mcidas"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.atcf"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.aww"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.sgwh"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.sgwhv"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ffg"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.idft"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncscat"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.tcm"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.wcp"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncuair"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncscd"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ncpafm"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.nctaf"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.stormtrack"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.solarimage"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.geomag"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.ntrans"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.pgen"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.gpd"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.airep"
download-size="0"
install-size="0"
version="0.0.0"/>
<plugin
id="gov.noaa.nws.ncep.common.dataplugin.pirep"
download-size="0"
install-size="0"
version="0.0.0"/>
<plugin
id="com.raytheon.uf.common.remote.script"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
</feature>

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.viz.ncep.displays.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,317 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.viz.ncep.displays.feature"
label="NCEP Displays Feature"
version="1.0.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<requires>
<import feature="com.raytheon.uf.viz.common.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.d2d.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.ncep.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.dataplugins.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.ncep.dataplugins.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.viz.satellite.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.viz.radar.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.viz.grib.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.viz.text.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.cots.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.aviation.advisory.feature" version="1.14.0.qualifier"/>
</requires>
<plugin
id="gov.noaa.nws.ncep.gempak.parameterConversionLibrary"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.ui.nctextui"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.ui.pgen"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.cloudHeight"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.gempak"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.overlays"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.resourceManager"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.airmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.atcf"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.convsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.ffg"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.hrcn"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.idft"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.intlsig"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.lightning"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.mosaic"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.ncgrid"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.ncscat"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.nonconvsigmet"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.pgen"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.plotdata"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.satellite"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.stormtrack"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.wcp"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.tools"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.ui.seek"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.ui.locator"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.aww"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.resources"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.wavesat"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.ncradar"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.common.staticdata"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.staticdataprovider"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.gempak.nativelib"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.gempak.nativelib.linux64"
os="linux"
arch="x86_64"
download-size="0"
install-size="0"
version="0.0.0"
fragment="true"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.solarimage"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.ntrans"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.ui.remotescript"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rsc.timeseries"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
<plugin
id="gov.noaa.nws.ncep.viz.rtkp"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
</feature>

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.viz.ncep.nsharp.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,64 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.viz.ncep.nsharp.feature"
label="NCEP NSharp Feature"
version="1.0.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<requires>
<import feature="com.raytheon.uf.viz.cots.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.common.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.ncep.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.sounding.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.displays.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.ncep.displays.feature" version="1.0.0.qualifier"/>
</requires>
<plugin
id="gov.noaa.nws.ncep.ui.nsharp"
download-size="0"
install-size="0"
version="0.0.0"
unpack="true"/>
<plugin
id="gov.noaa.nws.ncep.ui.nsharp.linux64"
os="linux"
arch="x86_64"
download-size="0"
install-size="0"
version="0.0.0"
fragment="true"/>
<plugin
id="gov.noaa.nws.ncep.ui.nsharp.win32"
os="win32"
arch="x86"
download-size="0"
install-size="0"
version="0.0.0"
fragment="true"/>
<plugin
id="gov.noaa.nws.ncep.ui.nsharp.win64"
os="win32"
arch="x86_64"
download-size="0"
install-size="0"
version="0.0.0"
fragment="true"/>
</feature>

View file

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>com.raytheon.uf.viz.ncep.perspective.feature</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.pde.FeatureBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.FeatureNature</nature>
</natures>
</projectDescription>

View file

@ -1 +0,0 @@
bin.includes = feature.xml

View file

@ -1,35 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<feature
id="com.raytheon.uf.viz.ncep.perspective.feature"
label="NCEP Perspective Feature"
version="1.0.0.qualifier"
provider-name="RAYTHEON">
<description url="http://www.example.com/description">
[Enter Feature Description here.]
</description>
<copyright url="http://www.example.com/copyright">
[Enter Copyright Description here.]
</copyright>
<license url="http://www.example.com/license">
[Enter License Description here.]
</license>
<requires>
<import feature="com.raytheon.uf.viz.cots.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.common.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.uf.viz.ncep.core.feature" version="1.0.0.qualifier"/>
<import feature="com.raytheon.viz.satellite.feature" version="1.0.0.qualifier"/>
</requires>
<plugin
id="gov.noaa.nws.ncep.viz.ui.perspectives"
download-size="0"
install-size="0"
version="0.0.0"
unpack="false"/>
</feature>

View file

@ -1,7 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<classpath>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.6"/>
<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
<classpathentry kind="src" path="src"/>
<classpathentry kind="output" path="bin"/>
</classpath>

View file

@ -1,28 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>edu.wisc.ssec.mcidas</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.jdt.core.javabuilder</name>
<arguments>
</arguments>
</buildCommand>
<buildCommand>
<name>org.eclipse.pde.ManifestBuilder</name>
<arguments>
</arguments>
</buildCommand>
<buildCommand>
<name>org.eclipse.pde.SchemaBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.PluginNature</nature>
<nature>org.eclipse.jdt.core.javanature</nature>
</natures>
</projectDescription>

View file

@ -1,7 +0,0 @@
Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: Mcidas Plug-in
Bundle-SymbolicName: edu.wisc.ssec.mcidas
Bundle-Version: 1.0.0.qualifier
Bundle-RequiredExecutionEnvironment: JavaSE-1.6
Export-Package: edu.wisc.ssec.mcidas

View file

@ -1,4 +0,0 @@
source.. = src/
output.. = bin/
bin.includes = META-INF/,\
.

View file

@ -1,465 +0,0 @@
//
// ABISnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* The ABISnav class creates the ability to navigate ABIS
* image data. It is a math copy of the McIDAS nvxabis.dlm
* code.
*
* When used with AreaFile class, set up like this:
*
* <pre><code>
* AreaFile af;
* try {
* af = new AreaFile("/home/user/mcidas/data/AREA0001");
* } catch (AreaFileException e) {
* System.out.println(e);
* return;
* }
* int[] dir;
* try { dir=af.getDir();
* } catch (AreaFileException e){
* System.out.println(e);
* return;
* }
* int[] nav;
* try { nav=af.getNav();
* } catch (AreaFileException e){
* System.out.println(e);
* return;
* }
* try {
* ABISnav ng = new ABISnav(nav); // XXXXnav is the specific implementation
* } catch (IllegalArgumentException excp) {
* System.out.println(excp);
* return;
* }
* ng.setImageStart(dir[5], dir[6]);
* ng.setRes(dir[11], dir[12]);
* ng.setStart(1,1);
* ......................
* </code></pre>
*
* @author Don Murray
*
*/
public class ABISnav extends AREAnav {
/** some constants */
int itype, lpsi2;
/** some more constants */
double h, re, a, rp, pi, cdr, crd, deltax, deltay, rflon;
/** params */
int[] ioff = new int[3];
/** satellite subpoint */
double sublon;
/** nstepfullres and nstep */
double nstepfullres, nstep;
/**
* Set up for the real math work. Must pass in the int array
* of the ABIS nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a ABIS type.
*/
public ABISnav(int[] iparms) throws IllegalArgumentException {
this(1, iparms);
}
/**
* Set up for the real math work. Must pass in the int array
* of the ABIS nav 'codicil'.
* @deprecated Since ifunc must be 1, replaced with #ABISnav(int[] iparms).
* If ifunc != 1, ifunc is set to 1.
*
* @param ifunc the function to do (always 1 for now)
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a ABIS type.
*/
public ABISnav(int ifunc, int[] iparms) throws IllegalArgumentException {
// Only type 1 supported
if (ifunc != 1) ifunc = 1;
// This is not used. Left over from nvxabis.dlm code for Cartesian
// transformations
if (ifunc != 1) {
if (iparms[0] == XY) itype = 1;
if (iparms[0] == LL) itype = 2;
return;
}
itype = 1;
if (iparms[0] != ABIS)
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
if (ifunc == 1) { // these should probably be made class variables
for (int i = 0; i < 3; i++) {
ioff[i] = iparms[3 + i];
}
re = 6378.155;
h = 42164 - re;
a = 1. / 297.;
rp = re / (1. + a);
pi = 3.141592653;
cdr = pi / 180.;
crd = 180. / pi;
lpsi2 = 1;
double angle=17.76;
nstep = 5535.;
nstepfullres = 22141.;
if (iparms[7] != 0 && iparms[8] != 0 && iparms[10] != 0) {
nstep = (double)iparms[7];
nstepfullres = (double)iparms[8];
angle = ((double)iparms[10])/10000.;
}
deltax = angle / nstep;
deltay = angle / nstep;
rflon = 0.0;
sublon = McIDASUtil.mcPackedIntegerToDouble(iparms[6]);
}
}
/**
* converts from satellite coordinates to latitude/longitude
*
* @param linele array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon array of lat/lon pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele) {
int number = linele[0].length;
double[][] latlon = new double[2][number];
// transform line/pixel to geographic coordinates:
double imglinele[][] = areaCoordToImageCoord(linele);
double xlin, xele, xele2, xlin2, x, y, xr, yr, rs, tanx, tany, val1, val2,
yk;
double vmu, cosrf, sinrf, xt, yt, zt, teta, xfi, xla, ylat, ylon;
for (int point = 0; point < number; point++) {
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xele2 = xele / 4.;
xlin2 = xlin / 4.;
x = (nstep / 2.) - xele2;
y = ((nstepfullres - xlin)/4.) - ioff[2] - ioff[1] + ioff[0];
xr = x;
yr = y;
x = xr * lpsi2 * deltax * cdr;
y = yr * lpsi2 * deltay * cdr;
rs = re + h;
tanx = Math.tan(x);
tany = Math.tan(y);
val1 = 1. + tanx * tanx;
val2 = 1. + (tany * tany) * ((1. + a) * (1. + a));
yk = rs / re;
if ((val1 * val2) > ((yk * yk) / (yk * yk - 1))) {
latlon[indexLat][point] = Double.NaN;
latlon[indexLon][point] = Double.NaN;
continue;
}
vmu = (rs -
(re *
(Math.sqrt((yk * yk) -
(yk * yk - 1) * val1 * val2)))) / (val1 * val2);
cosrf = Math.cos(rflon * cdr);
sinrf = Math.sin(rflon * cdr);
xt = (rs * cosrf) + (vmu * (tanx * sinrf - cosrf));
yt = (rs * sinrf) - (vmu * (tanx * cosrf + sinrf));
zt = vmu * tany / Math.cos(x);
teta = Math.asin(zt / rp);
xfi = (Math.atan(((Math.tan(teta)) * re) / rp)) * crd;
xla = -Math.atan(yt / xt) * crd;
//
//-- CHANGE LONGITUDE FOR CORRECT SUBPOINT
//
xla = xla + sublon;
//if (itype == 1) {
ylat = xfi;
ylon = xla;
//call nllxyz(ylat,ylon,xfi,xla,z)
//}
latlon[indexLat][point] = ylat;
latlon[indexLon][point] = -ylon; // McIDAS uses west positive
}
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon) {
int number = latlon[0].length;
double[][] linele = new double[2][number];
// transform line/pixel to geographic coordinates:
double x1, y1, xfi, xla, rom, y, r1, r2, rs, reph, rpph, coslo, sinlo,
teta, xt, yt;
double zt, px, py, xr, yr;
for (int point = 0; point < number; point++) {
x1 = latlon[indexLat][point];
y1 = latlon[indexLon][point]; // seems to want east postitive
/* not used.
if(itype == 1) {
x=vfi;
y=vla;
//call nxyzll(x,y,z,x1,y1)
y1=-y1;
}
*/
//
//-- CORRECT FOR SUBLON
//
y1 = y1 + sublon;
xfi = x1 * cdr;
xla = y1 * cdr;
rom = (re * rp) /
Math.sqrt(rp * rp * Math.cos(xfi) * Math.cos(xfi) +
re * re * Math.sin(xfi) * Math.sin(xfi));
y = Math.sqrt(h * h + rom * rom -
2 * h * rom * Math.cos(xfi) * Math.cos(xla));
r1 = y * y + rom * rom;
r2 = h * h;
if (r1 > r2) {
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
continue;
}
rs = re + h;
reph = re;
rpph = rp;
coslo = Math.cos(rflon * cdr);
sinlo = Math.sin(rflon * cdr);
teta = Math.atan((rpph / reph) * Math.tan(xfi));
xt = reph * Math.cos(teta) * Math.cos(xla);
yt = reph * Math.cos(teta) * Math.sin(xla);
zt = rpph * Math.sin(teta);
px = Math.atan((coslo * (yt - rs * sinlo) -
(xt - rs * coslo) * sinlo) / (sinlo *
(yt - rs * sinlo) + (xt - rs * coslo) * coslo));
py = Math.atan(zt *
((Math.tan(px) * sinlo - coslo) / (xt - rs * coslo)) *
Math.cos(px));
px = px * crd;
py = py * crd;
xr = px / (deltax * lpsi2);
yr = py / (deltay * lpsi2);
xr = (nstep / 2.) - xr;
yr = yr + ioff[2] + ioff[1] - ioff[0];
xr = xr * 4;
yr = nstepfullres - yr * 4;
linele[indexLine][point] = yr;
linele[indexEle][point] = xr;
}
return imageCoordToAreaCoord(linele, linele);
}
/**
* converts from satellite coordinates to latitude/longitude
*
* @param linele array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon array of lat/lon pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele) {
int number = linele[0].length;
float[][] latlon = new float[2][number];
// transform line/pixel to geographic coordinates:
float imglinele[][] = areaCoordToImageCoord(linele);
double xlin, xele, xele2, xlin2, x, y, xr, yr, rs, tanx, tany, val1, val2,
yk;
double vmu, cosrf, sinrf, xt, yt, zt, teta, xfi, xla, ylat, ylon;
for (int point = 0; point < number; point++) {
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xele2 = xele / 4.;
xlin2 = xlin / 4.;
x = (nstep / 2.) - xele2;
y = ((nstepfullres - xlin)/4.) - ioff[2] - ioff[1] + ioff[0];
xr = x;
yr = y;
x = xr * lpsi2 * deltax * cdr;
y = yr * lpsi2 * deltay * cdr;
rs = re + h;
tanx = Math.tan(x);
tany = Math.tan(y);
val1 = 1. + tanx * tanx;
val2 = 1. + (tany * tany) * ((1. + a) * (1. + a));
yk = rs / re;
if ((val1 * val2) > ((yk * yk) / (yk * yk - 1))) {
latlon[indexLat][point] = Float.NaN;
latlon[indexLon][point] = Float.NaN;
continue;
}
vmu = (rs -
(re *
(Math.sqrt((yk * yk) -
(yk * yk - 1) * val1 * val2)))) / (val1 * val2);
cosrf = Math.cos(rflon * cdr);
sinrf = Math.sin(rflon * cdr);
xt = (rs * cosrf) + (vmu * (tanx * sinrf - cosrf));
yt = (rs * sinrf) - (vmu * (tanx * cosrf + sinrf));
zt = vmu * tany / Math.cos(x);
teta = Math.asin(zt / rp);
xfi = (Math.atan(((Math.tan(teta)) * re) / rp)) * crd;
xla = -Math.atan(yt / xt) * crd;
//
//-- CHANGE LONGITUDE FOR CORRECT SUBPOINT
//
xla = xla + sublon;
//if (itype == 1) {
ylat = xfi;
ylon = xla;
//call nllxyz(ylat,ylon,xfi,xla,z)
//}
latlon[indexLat][point] = (float)ylat;
latlon[indexLon][point] = (float)-ylon; // McIDAS uses west positive
}
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon) {
int number = latlon[0].length;
float[][] linele = new float[2][number];
// transform line/pixel to geographic coordinates:
double x1, y1, xfi, xla, rom, y, r1, r2, rs, reph, rpph, coslo, sinlo,
teta, xt, yt;
double zt, px, py, xr, yr;
for (int point = 0; point < number; point++) {
x1 = latlon[indexLat][point];
y1 = latlon[indexLon][point]; // seems to want east postitive
/* not used.
if(itype == 1) {
x=vfi;
y=vla;
//call nxyzll(x,y,z,x1,y1)
y1=-y1;
}
*/
//
//-- CORRECT FOR SUBLON
//
y1 = y1 + sublon;
xfi = x1 * cdr;
xla = y1 * cdr;
rom = (re * rp) /
Math.sqrt(rp * rp * Math.cos(xfi) * Math.cos(xfi) +
re * re * Math.sin(xfi) * Math.sin(xfi));
y = Math.sqrt(h * h + rom * rom -
2 * h * rom * Math.cos(xfi) * Math.cos(xla));
r1 = y * y + rom * rom;
r2 = h * h;
if (r1 > r2) {
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
continue;
}
rs = re + h;
reph = re;
rpph = rp;
coslo = Math.cos(rflon * cdr);
sinlo = Math.sin(rflon * cdr);
teta = Math.atan((rpph / reph) * Math.tan(xfi));
xt = reph * Math.cos(teta) * Math.cos(xla);
yt = reph * Math.cos(teta) * Math.sin(xla);
zt = rpph * Math.sin(teta);
px = Math.atan((coslo * (yt - rs * sinlo) -
(xt - rs * coslo) * sinlo) / (sinlo *
(yt - rs * sinlo) + (xt - rs * coslo) * coslo));
py = Math.atan(zt *
((Math.tan(px) * sinlo - coslo) / (xt - rs * coslo)) *
Math.cos(px));
px = px * crd;
py = py * crd;
xr = px / (deltax * lpsi2);
yr = py / (deltay * lpsi2);
xr = (nstep / 2.) - xr;
yr = yr + ioff[2] + ioff[1] - ioff[0];
xr = xr * 4;
yr = nstepfullres - yr * 4;
linele[indexLine][point] = (float)yr;
linele[indexEle][point] = (float)xr;
}
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,742 +0,0 @@
//
// AREAnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* The AREAnav is the superclass for AREA file navigation modules.
* When used with AreaFile class, set up like this:
*
* <pre><code>
* AreaFile af;
* try {
* af = new AreaFile("/home/user/mcidas/data/AREA0001");
* } catch (AreaFileException e) {
* System.out.println(e);
* return;
* }
* int[] dir;
* try { dir=af.getDir();
* } catch (AreaFileException e){
* System.out.println(e);
* return;
* }
* int[] nav;
* try { nav=af.getNav();
* } catch (AreaFileException e){
* System.out.println(e);
* return;
* }
* try {
* AREAnav ng = new XXXXnav(nav); // XXXXnav is the specific implementation
* } catch (IllegalArgumentException excp) {
* System.out.println(excp);
* return;
* }
* ng.setImageStart(dir[5], dir[6]);
* ng.setRes(dir[11], dir[12]);
* ng.setStart(0,0);
* ng.setMag(1,1);
* ......................
* </code></pre>
*
* By convention, latitudes are positive North (negative South), and
* longitudes are positive East (negative West).
*
* @author Tom Whittaker/Don Murray
*
*/
public abstract class AREAnav
implements java.io.Serializable
{
static final long serialVersionUID = 2334637524537406773L;
/** Constant for radians to degrees conversion */
public final static double RADIANS_TO_DEGREES = 180./Math.PI;
/** Constant for degrees to radians conversion */
public final static double DEGREES_TO_RADIANS = Math.PI/180.;
/** Code value in AREA files used to designate DMSP navigation */
public static final int DMSP = 0x444D5250;
/** Code value in AREA files used to designate GMSX (GMS) navigation */
public static final int GMSX = 0x474D5358;
/** Code value in AREA files used to designate GOES (GOES D-H) navigation */
public static final int GOES = 0x474F4553;
/** Code value in AREA files used to designate GEOS navigation */
public static final int GEOS = 0x47454F53;
/** Code value in AREA files used to designate GVAR (GOES I-M) navigation */
public static final int GVAR = 0x47564152;
/** Code value in AREA files used to designate MOLL (Mollweide)
navigation */
public static final int MOLL = 0x4D4F4C4C;
/** Code value in AREA files used to designate MSAT (Meteosat)
navigation */
public static final int MSAT = 0x4D534154;
/** Code value in AREA files used to designate MSGT navigation */
public static final int MSGT = 0x4D534754;
/** Code value in AREA files used to designate MSG navigation */
public static final int MSG = 0x4D534720;
/** Code value in AREA files used to designate POES navigation */
public static final int POES = 0x5449524F;
/** Code value in AREA files used to designate RADR (radar) navigation */
public static final int RADR = 0x52414452;
/** Code value in AREA files used to designate RECT (rectilinear)
navigation */
public static final int RECT = 0x52454354;
/** Code value in AREA files used to designate PS (polar stereographic)
navigation */
public static final int PS = 0x50532020;
/** Code value in AREA files used to designate MERC (mercator) navigation */
public static final int MERC = 0x4D455243;
/** Code value in AREA files used to designate TANC (tangent cone)
navigation */
public static final int TANC = 0x54414E43;
/** Code value in AREA files used to designate SIN (sinusoidal cone)
navigation */
public static final int SIN = 0x53494E20;
/** Code value in AREA files used to designate LAMB (lambert conformal)
navigation */
public static final int LAMB = 0x4C414D42;
/** Code value in AREA files used to designate Lat/Lon */
public static final int LALO = 0x4C414C4F;
/** Code value in AREA files used to designate Lat/Lon */
public static final int KALP = 0x4B414C50;
/** Code value in AREA files used to designate ABIS */
public static final int ABIS = 0x41424953;
/** Code value for specifying Latitude/Longitude transformations */
public static final int LL = 123;
/** Code value for specifying Cartesian (X/Y) transformations */
public static final int XY = 234;
/** "Line" index in line/element array */
public final int indexLine=1;
/** "Element" index in line/element array */
public final int indexEle=0;
/** "Latitude" index in latitude/longitude array */
public final int indexLat=0;
/** "Longitude" index in latitude/longitude array */
public final int indexLon=1;
private boolean isLineFlipped = false;
private float lineOffset = 0.0f;
// the following are ancillary info set by the set/get
// public methods Res, Mag, and Start
private float resLine = 1.f;
private float resElement = 1.f;
private float magLine = 1.f;
private float magElement = 1.f;
private float startLine = 0.f;
private float startElement = 0.f;
private float startImageLine = 0.f;
private float startImageElement = 0.f;
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public abstract double[][] toLatLon(double[][] linele);
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public abstract double[][] toLinEle(double[][] latlon);
/** converts from satellite coordinates to latitude/longitude.
* This implementation converts the input array to doubles
* and calls the double signature of {@link toLatLon(double[][])}.
* Subclasses should implement a real float version for better
* performance.
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele) {
return doubleToFloat(toLatLon(floatToDouble(linele)));
}
/**
* toLinEle converts lat/long to satellite line/element
* This implementation converts the input array to doubles
* and calls the double signature of {@link toLineEle(double[][])}.
* Subclasses should implement a real float version for better
* performance.
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon) {
return doubleToFloat(toLinEle(floatToDouble(latlon)));
}
/**
* Define the resolution of the image.
* values range from 1 (highest) to n (lowest). Note
* that when an image is blown down during display, this
* value is changed in the frame object to reflect this
* (rather than changing the magnification).
*
* @param resLine is the resolution in the 'line' direction.
* This value is always > 0.
*
* @param resElement is the resolution in the 'element'
* direction. The value is always >0.
*
*/
public void setRes(int resLine, int resElement)
{
this.resLine = (float)resLine;
this.resElement = (float)resElement;
}
/**
* Define the resolution of the image.
* values range from 1 (highest) to n (lowest). Note
* that when an image is blown down during display, this
* value is changed in the frame object to reflect this
* (rather than changing the magnification).
*
* @param resLine is the resolution in the 'line' direction.
* This value is always > 0.
*
* @param resElement is the resolution in the 'element'
* direction. The value is always >0.
*
*/
public void setRes(float resLine, float resElement)
{
this.resLine = resLine;
this.resElement = resElement;
}
/**
* define the magnification factor (in case an image
* was blown up when displayed). This value is always > 0.
*
* @param magLine is the (line) magnification factor that might have
* been used when the image was displayed.
*
* @param magElment is the (element) magnification factor
* that might have been used when the image was displayed.
*
*/
public void setMag(int magLine, int magElement)
{
this.magLine = (float)magLine;
this.magElement = (float)magElement;
}
/** define the magnification factor (in case an image
* was blown up when displayed). This value is always > 0.
*
* @param magLine is the (line) magnification factor that might have
* been used when the image was displayed.
*
* @param magElment is the (element) magnification factor
* that might have been used when the image was displayed.
*
*/
public void setMag(float magLine, float magElement)
{
this.magLine = magLine;
this.magElement = magElement;
}
/** define the starting line and element of another
* coordinate system -- usually a TV (note that the TV
* coordinates start at (1,1).
*
* @param startLine the starting line number in another
* coordinate system
*
* @param startElement the starting element number in another
* coordinate system
*
*/
public void setStart(int startLine, int startElement)
{
this.startLine = (float)startLine;
this.startElement = (float)startElement;
}
/** define the coordinate in the [0][0] position of the image.
*
* @param startImageLine redefines the starting image line number
* (may be different than the signal indicated)
*
* @param startImageElement redefines the starting image element number
* (may be different than the signal indicated)
*
*/
public void setImageStart(int startImageLine, int startImageElement)
{
this.startImageLine = (float)startImageLine;
this.startImageElement = (float)startImageElement;
}
/**
* specify whether the line coordinates are inverted and the line
* offset.
*
* @param line ending line number
*
*/
public void setFlipLineCoordinates(int line)
{
isLineFlipped = true;
lineOffset = (float) line;
}
/**
* Determine if navigation is using flipped coordinates
*
* @return true if using flipped line coordinates, otherwise false
*/
public boolean isFlippedLineCoordinates()
{
return isLineFlipped;
}
/** Get the lat,lon of the subpoint if available
*
* @return double[2] {lat, lon}
*
*/
public double[] getSubpoint() {
return new double[] {Double.NaN, Double.NaN};
}
/**
* Get the line offset for flipped coordinates
*
* @return line offset
*/
public double getLineOffset()
{
return (double) lineOffset;
}
/**
* Converts line/element array values from AREA (file) to Image
* coordinates. Creates new array instead of mucking with input.
*
* @param linele input line/element array in AREA coordinates
* @return array in Image coordinates
*/
public double[][] areaCoordToImageCoord(double[][] linele)
{
return areaCoordToImageCoord(linele, null);
}
/**
* Converts line/element array values from AREA (file) to Image
* coordinates. Creates new array if newvals is null.
*
* @param linele input line/element array in AREA coordinates
* @param newvals return array - create a new array if null
* @return array in Image coordinates
*/
public double[][] areaCoordToImageCoord(double[][] linele, double[][] newvals)
{
if (newvals == null) newvals = new double[2][linele[0].length];
double line;
for (int i = 0; i < linele[0].length; i++)
{
if (linele[indexLine][i] == linele[indexLine][i]) {
// account for flipped coordinates
line = isLineFlipped ? lineOffset - linele[indexLine][i]
: linele[indexLine][i];
newvals[indexLine][i] =
startImageLine + (resLine * (line - startLine)) / magLine;
}
if (linele[indexEle][i] == linele[indexEle][i]) {
newvals[indexEle][i] =
startImageElement + (resElement * (linele[indexEle][i] -
startElement))/magElement;
}
}
return newvals;
}
/**
* Converts line/element array values from Image to AREA (File)
* coordinates. Creates new array instead of mucking with input.
*
* @param linele input line/element array Image coordinates
* @return array in AREA coordinates
*/
public double[][] imageCoordToAreaCoord(double[][] linele)
{
return imageCoordToAreaCoord(linele, null);
}
/**
* Converts line/element array values from Image to AREA (File)
* coordinates. Creates new array if newvals is null.
*
* @param linele input line/element array Image coordinates
* @param newvals return array - create a new array if null
* @return array in AREA coordinates
*/
public double[][] imageCoordToAreaCoord(double[][] linele, double[][] newvals)
{
if (newvals == null) newvals = new double[2][linele[0].length];
for (int i = 0; i < linele[0].length; i++)
{
if (linele[indexLine][i] == linele[indexLine][i]) {
newvals[indexLine][i] = startLine +
( magLine * (linele[indexLine][i] -
startImageLine)) / resLine;
// account for flipped coordinates
if (isLineFlipped) newvals[indexLine][i] =
lineOffset - newvals[indexLine][i];
}
if (linele[indexEle][i] == linele[indexEle][i]) {
newvals[indexEle][i] = startElement +
( magElement * (linele[indexEle][i] -
startImageElement)) / resElement;
}
}
return newvals;
}
/**
* Converts line/element array values from AREA (file) to Image
* coordinates. Creates new array instead of mucking with input.
*
* @param linele input line/element array in AREA coordinates
* @return array in Image coordinates
*/
public float[][] areaCoordToImageCoord(float[][] linele)
{
return areaCoordToImageCoord(linele, null);
}
/**
* Converts line/element array values from AREA (file) to Image
* coordinates. Creates new array if newvals is null.
*
* @param linele input line/element array in AREA coordinates
* @param newvals return array - create a new array if null
* @return array in Image coordinates
*/
public float[][] areaCoordToImageCoord(float[][] linele, float[][] newvals)
{
if (newvals == null) newvals = new float[2][linele[0].length];
float line;
for (int i = 0; i < linele[0].length; i++)
{
// account for flipped coordinates
if (linele[indexLine][i] == linele[indexLine][i]) {
line = isLineFlipped ? lineOffset - linele[indexLine][i]
: linele[indexLine][i];
newvals[indexLine][i] =
startImageLine + (resLine * (line - startLine)) / magLine;
}
if (linele[indexEle][i] == linele[indexEle][i]) {
newvals[indexEle][i] =
startImageElement + (resElement * (linele[indexEle][i] -
startElement))/magElement;
}
}
return newvals;
}
/**
* Converts line/element array values from Image to AREA (File)
* coordinates. Creates new array instead of mucking with input.
*
* @param linele input line/element array Image coordinates
* @return array in AREA coordinates
*/
public float[][] imageCoordToAreaCoord(float[][] linele)
{
return imageCoordToAreaCoord(linele, null);
}
/**
* Converts line/element array values from Image to AREA (File)
* coordinates. Creates new array if newvals is null.
*
* @param linele input line/element array Image coordinates
* @param newvals return array - create a new array if null
* @return array in AREA coordinates
*/
public float[][] imageCoordToAreaCoord(float[][] linele, float[][] newvals)
{
if (newvals == null) newvals = new float[2][linele[0].length];
for (int i = 0; i < linele[0].length; i++)
{
if (linele[indexLine][i] == linele[indexLine][i]) {
newvals[indexLine][i] = startLine +
( magLine * (linele[indexLine][i] -
startImageLine)) / resLine;
// account for flipped coordinates
if (isLineFlipped) newvals[indexLine][i] =
lineOffset - newvals[indexLine][i];
}
if (linele[indexEle][i] == linele[indexEle][i]) {
newvals[indexEle][i] = startElement +
( magElement * (linele[indexEle][i] -
startImageElement)) / resElement;
}
}
return newvals;
}
/**
* Return an AREAnav based on the input nav block.
* @param navBlock block to use
* @return corresponding navigation routine.
*/
public static AREAnav makeAreaNav(int[] navBlock) throws McIDASException {
return (makeAreaNav(navBlock, null) );
}
public static AREAnav makeAreaNav(int[] navBlock, int[] auxBlock)
throws McIDASException {
AREAnav anav = null;
//System.out.println("nav = " + McIDASUtil.intBitsToString(navBlock[0]));
try
{
switch (navBlock[0]) {
case GVAR:
anav = new GVARnav(navBlock);
break;
case MOLL:
anav = new MOLLnav(navBlock);
break;
case MSAT:
anav = new MSATnav(navBlock);
break;
case MSG :
anav = new MSGnav(navBlock);
break;
case MSGT:
anav = new MSGTnav(navBlock);
break;
case RADR:
anav = new RADRnav(navBlock);
break;
case RECT:
anav = new RECTnav(navBlock);
break;
case GMSX:
anav = new GMSXnav(navBlock);
break;
case GOES:
anav = new GOESnav(navBlock);
break;
case GEOS:
anav = new GEOSnav(navBlock);
break;
case PS:
anav = new PSnav(navBlock);
break;
case MERC:
anav = new MERCnav(navBlock);
break;
case LAMB:
anav = new LAMBnav(navBlock);
break;
case TANC:
anav = new TANCnav(navBlock);
break;
case SIN:
anav = new SINUnav(navBlock);
break;
case LALO:
//SAG anav = new LALOnav(navBlock, auxBlock);
break;
case KALP:
anav = new KALPnav(navBlock);
break;
case ABIS:
anav = new ABISnav(navBlock);
break;
default:
throw new McIDASException(
"makeAreaNav: Unknown navigation type" + navBlock[0]);
}
}
catch (IllegalArgumentException excp)
{
throw new McIDASException( "Wrong nav block passed to AREAnav module");
}
return anav;
}
/**
* Determines whether or not the <code>Object</code> in question is
* the same as this <code>AREAnav</code>. Right now, this returns
* false until we can figure out when two navigations are equal.
* Subclasses could override if desired.
*
* @param obj the AREAnav in question
*/
public boolean equals(Object obj)
{
// return false; WLH 13 April 2000, this broke visad.data.mcidas.TestArea
if (obj instanceof AREAnav)
{
// this should really be done in the subclasses, but that will
// have to wait for another day.
AREAnav nav = (AREAnav) obj;
return (resLine == nav.resLine &&
resElement == nav.resElement &&
magLine == nav.magLine &&
magElement == nav.magElement &&
startLine == nav.startLine &&
startElement == nav.startElement &&
startImageLine == nav.startImageLine &&
startImageElement == nav.startImageElement &&
isLineFlipped == nav.isLineFlipped &&
lineOffset == nav.lineOffset);
}
else
{
return false;
}
}
/**
* Return a <code>String</code> representation of this nav module
* @return wordy string.
*/
public String toString() {
String className = getClass().getName();
int lastDot = className.lastIndexOf('.');
className = className.substring(lastDot+1);
return className.substring(0,className.indexOf("nav"));
}
/**
* See if we can approximate by a spline. Subclasses can override
* @return true
*/
public boolean canApproximateWithSpline() {
return true;
}
/**
* Convert arrays of floats to doubles
* @param value arrays of floats
* @return value converted to arrays of doubles
*/
public static double[][] floatToDouble(float[][] value) {
if (value == null) return null;
double[][] val = new double[value.length][];
for (int i=0; i<value.length; i++) {
if (value[i] == null) {
val[i] = null;
}
else {
val[i] = new double[value[i].length];
for (int j=0; j<value[i].length; j++) {
val[i][j] = value[i][j];
}
}
}
return val;
}
/**
* Convert arrays of floats to doubles
* @param value arrays of floats
* @return value converted to arrays of doubles
*/
public static float[][] doubleToFloat(double[][] value) {
if (value == null) return null;
float[][] val = new float[value.length][];
for (int i=0; i<value.length; i++) {
if (value[i] == null) {
val[i] = null;
}
else {
val[i] = new float[value[i].length];
for (int j=0; j<value[i].length; j++) {
val[i][j] = (float) value[i][j];
}
}
}
return val;
}
}

View file

@ -1,384 +0,0 @@
//
// AncillaryData.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
import java.lang.String;
/**
* AncillaryData creates an object providing access to image
* parameters needed to do conversion from McIDAS area format
* to some other image format.
*
* @version 1.6 6 Aug 1999
* @author Tommy Jasmin, SSEC
*/
public class AncillaryData {
private static final int DIR_SIZE = 64;
private int numLines = 0;
private int numElems = 0;
private int firstImageLine = 0;
private int firstImageElem = 0;
private int lineResolution = 0;
private int elemResolution = 0;
private int imageDate = 0;
private int imageTime = 0;
private int creationDate = 0;
private int creationTime = 0;
private int bandCount = 0;
private int sensorId = 0;
private int status = 0;
private int version = 0;
private int dataWidth = 0;
private int numBands = 0;
private int prefixSize = 0;
private int projectNum = 0;
private int bandMap = 0;
private int calType = 0;
private int navOffset = 0;
private int calOffset = 0;
private int datOffset = 0;
private boolean swapWords = false;
/**
*
* constructor
*
* @param dis data input stream
*
*/
public AncillaryData (
DataInputStream dis
)
throws IOException
{
int [] directory;
int i;
// read in what corresponds to the McIDAS area directory
directory = new int[DIR_SIZE];
for (i = 0; i < DIR_SIZE; i++) {
directory[i] = dis.readInt();
}
// byte swap if necessary
if (directory[1] > 255) {
ConversionUtility.swap(directory,0,19);
// word 20 may contain characters -- if small integer, swap it...
if ((directory[20] & 0xffff) == 0) {
ConversionUtility.swap(directory,20,20);
}
ConversionUtility.swap(directory,21,23);
// words 24-31 contain memo field
ConversionUtility.swap(directory,32, 50);
// words 51-2 contain cal info
ConversionUtility.swap(directory,53,55);
// word 56 contains original source type (ascii)
ConversionUtility.swap(directory,57,63);
swapWords = true;
}
// now load the class fields with the appropriate data
numLines = directory[AreaFile.AD_NUMLINES];
numElems = directory[AreaFile.AD_NUMELEMS];
firstImageLine = directory[AreaFile.AD_STLINE];
firstImageElem = directory[AreaFile.AD_STELEM];
lineResolution = directory[AreaFile.AD_LINERES];
elemResolution = directory[AreaFile.AD_ELEMRES];
imageDate = directory[AreaFile.AD_IMGDATE];
imageTime = directory[AreaFile.AD_IMGTIME];
bandCount = directory[AreaFile.AD_NUMBANDS];
sensorId = directory[AreaFile.AD_SENSORID];
creationDate = directory[AreaFile.AD_CRDATE];
creationTime = directory[AreaFile.AD_CRTIME];
status = directory[AreaFile.AD_STATUS];
version = directory[AreaFile.AD_VERSION];
dataWidth = directory[AreaFile.AD_DATAWIDTH];
numBands = directory[AreaFile.AD_NUMBANDS];
prefixSize = directory[AreaFile.AD_PFXSIZE];
projectNum = directory[AreaFile.AD_PROJNUM];
bandMap = directory[AreaFile.AD_BANDMAP];
calType = directory[AreaFile.AD_CALTYPE];
navOffset = directory[AreaFile.AD_NAVOFFSET];
calOffset = directory[AreaFile.AD_CALOFFSET];
datOffset = directory[AreaFile.AD_DATAOFFSET];
}
public int getCalType() {
char [] calBuf = new char[4];
calBuf[0] = (char) ((calType >> 24) & 0xFF);
calBuf[1] = (char) ((calType >> 16) & 0xFF);
calBuf[2] = (char) ((calType >> 8) & 0xFF);
calBuf[3] = (char) ((calType) & 0xFF);
if (String.valueOf(calBuf).equals("RAW ")) {
System.out.println("determined input cal type is RAW");
return Calibrator.CAL_RAW;
} else if (String.valueOf(calBuf).equals("BRIT")) {
System.out.println("determined input cal type is BRIT");
return Calibrator.CAL_BRIT;
} else if (String.valueOf(calBuf).equals("TEMP")) {
System.out.println("determined input cal type is TEMP");
return Calibrator.CAL_TEMP;
} else if (String.valueOf(calBuf).equals("RAD ")) {
System.out.println("determined input cal type is RAD");
return Calibrator.CAL_RAD;
} else if (String.valueOf(calBuf).equals("ALB")) {
System.out.println("determined input cal type is ALB");
return Calibrator.CAL_ALB;
}
return Calibrator.CAL_NONE;
}
/**
*
* return sensor id
*
*/
public int getSensorId() {
return sensorId;
}
/**
*
* return number of elements
*
*/
public int getNumElements() {
return numElems;
}
/**
*
* return number of lines
*
*/
public int getNumLines() {
return numLines;
}
/**
*
* return starting image line
*
*/
public int getStartLine() {
return firstImageLine;
}
/**
*
* return starting image element
*
*/
public int getStartElem() {
return firstImageElem;
}
/**
*
* return line resolution
*
*/
public int getLineRes() {
return lineResolution;
}
/**
*
* return element resolution
*
*/
public int getElemRes() {
return elemResolution;
}
/**
*
* return image date
*
*/
public int getImageDate() {
return imageDate;
}
/**
*
* return image time
*
*/
public int getImageTime() {
return imageTime;
}
/**
*
* return image creation date
*
*/
public int getCreationDate() {
return creationDate;
}
/**
*
* return image creation time
*
*/
public int getCreationTime() {
return creationTime;
}
/**
*
* return image status field
*
*/
public int getStatus() {
return status;
}
/**
*
* return file format version number
*
*/
public int getVersion() {
return version;
}
/**
*
* return number of bytes per pixel
*
*/
public int getDataWidth() {
return dataWidth;
}
/**
*
* return number of bands/channels in image
*
*/
public int getNumBands() {
return numBands;
}
/**
*
* return size in bytes of line prefix
*
*/
public int getPrefixSize() {
return prefixSize;
}
/**
*
* return project number associated with image
*
*/
public int getProjectNum() {
return projectNum;
}
/**
*
* return 32 bit band map
*
*/
public int getBandMap() {
return bandMap;
}
/**
*
* return offset in bytes to navigation data
*
*/
public int getNavOffset() {
return navOffset;
}
/**
*
* return offset in bytes to calibration data
*
*/
public int getCalOffset() {
return calOffset;
}
/**
*
* return offset in bytes to image data
*
*/
public int getDataOffset() {
return datOffset;
}
/**
*
* return flag indicating certain fields were byte flipped
*
*/
public boolean isSwapped() {
return swapWords;
}
}

View file

@ -1,600 +0,0 @@
//
// AreaDirectory.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.text.FieldPosition;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.TimeZone;
import java.util.Vector;
/**
* AreaDirectory interface for the metadata of McIDAS 'area' file format
* image data.
*
* @author Don Murray
*
*/
public class AreaDirectory implements java.io.Serializable
{
static final long serialVersionUID = -3662123383682335190L;
private int[] dir = new int[AreaFile.AD_DIRSIZE]; // single directory
private Date nominalTime; // time of the image
private Date startTime; // start time of the image
private int[] bands; // array of the band numbers
private double centerLatitude;
private double centerLongitude;
private double centerLatitudeResolution;
private double centerLongitudeResolution;
private Vector[] calInfo = null;
private String calType, srcType, srcTypeOrig;
private String calTypeUnit = null;
private int calTypeScaleFactor = 1;
private String memo;
private String[] sensors = {"Derived Data",
"Test Patterns",
"Graphics",
"Miscellaneous",
"PDUS Meteosat visible",
"PDUS Meteosat infrared",
"PDUS Meteosat water vapor",
"Radar",
"Miscellaneous Aircraft Data",
"Raw Meteosat",
"Composite image",
"Topography image",
"GMS visible",
"GMS infrared",
"ATS 6 visible",
"ATS 6 infrared",
"SMS-1 visible",
"SMS-1 infrared",
"SMS-2 visible",
"SMS-2 infrared",
"GOES-1 visible",
"GOES-1 infrared",
"GOES-2 visible",
"GOES-2 infrared",
"GOES-3 visible",
"GOES-3 infrared",
"GOES-4 visible (VAS)",
"GOES-4 infrared and water vapor (VAS)",
"GOES-5 visible (VAS)",
"GOES-5 infrared and water vapor (VAS)",
"GOES-6 visible",
"GOES-6 infrared",
"GOES-7 visible, Block 1 supplemental data",
"GOES-7 infrared",
"FY-2B",
"FY-2C",
"FY-2D",
"FY-2E",
"FY-2F",
"FY-2G",
"FY-2H",
"TIROS-N (POES)",
"NOAA-6",
"NOAA-7",
"NOAA-8",
"NOAA-9",
"Venus",
"Voyager 1",
"Voyager 2",
"Galileo",
"Hubble space telescope",
"MSG-1",
"MSG-2",
"MSG-3",
"Meteosat-3",
"Meteosat-4",
"Meteosat-5",
"Meteosat-6",
"Meteosat-7",
"",
"NOAA-10",
"NOAA-11",
"NOAA-12",
"NOAA-13",
"NOAA-14",
"NOAA-15",
"NOAA-16",
"NOAA-17",
"NOAA-18",
"NOAA-19",
"GOES 8 imager", // 70
"GOES 8 sounder",
"GOES 9 imager",
"GOES 9 sounder",
"GOES 10 imager",
"GOES 10 sounder",
"GOES 11 imager",
"GOES 11 sounder",
"GOES 12 imager",
"GOES 12 sounder",
"ERBE",
"",
"GMS-4",
"GMS-5",
"GMS-6",
"GMS-7",
"GMS-8",
"DMSP F-8",
"DMSP F-9",
"DMSP F-10",
"DMSP F-11",
"DMSP F-12",
"DMSP F-13",
"DMSP F-14",
"DMSP F-15", // 94
"FY-1B",
"FY-1C",
"FY-1D",
"",
"",
"",
"TERRA L1B", // 101
"TERRA CLD",
"TERRA GEO",
"TERRA-AER",
"",
"TERRA TOP",
"TERRA ATM",
"TERRA GUE",
"TERRA RET",
"",
"AQUA L1B", // 111
"AQUA CLD",
"AQUA GEO",
"AQUA AER",
"",
"AQUA TOP",
"AQUA ATM",
"AQUA GUE",
"AQUA RET",
"", // 120
"", "", "", "", "", "", "", "","", "", // 130
"", "", "", "", "", "", "", "","", "", // 140
"", "", "", "", "", "", "", "","", "", // 150
"", "", "", "", "", "", "", "","",
"TERRA NDVI", // 160
"TERRA CREF",
"", "", "", "", "", "", "","",
"AQUA NDVI", // 170
"AQUA CREF",
"", "", "", "", "", "", "","",
"GOES 13 imager", // 180
"GOES 13 sounder",
"GOES 14 imager",
"GOES 14 sounder",
"GOES 15 imager",
"GOES 15 sounder",
"GOES 16 imager",
"GOES 16 sounder",
"", // 188
"","", // 190
"","","","",
"DMSP F-16", // 195
"DMSP F-17",
"","","", // 199
"AIRS L1B", // 200
"","","","","","","","","",
"AMSR-E L1B", // 210
"AMSR-E RAIN",
"","","","","","","","","", // 220
"","","","","","","","","",
"Kalpana-1", // 230
"","","","","","","","","",
"MetOp-A", // 240
"MetOp-B",
"MetOp-C",
""};
/**
* Create an AreaDirectory from the raw block of data of
* an AreaFile. Byte-flipping will be handled.
*
* @param dirblock the integer block
*
* @exception AreaFileException not a valid directory
*/
public AreaDirectory(int[] dirblock)
throws AreaFileException
{
centerLatitude = Double.NaN;
centerLongitude = Double.NaN;
centerLatitudeResolution = Double.NaN;
centerLongitudeResolution = Double.NaN;
if (dirblock.length != AreaFile.AD_DIRSIZE)
throw new AreaFileException("Directory is not the right size");
dir = dirblock;
// see if the directory needs to be byte-flipped
if (dir[AreaFile.AD_VERSION] != AreaFile.VERSION_NUMBER)
{
McIDASUtil.flip(dir,0,19);
// check again to make sure we got the right type of file
if (dir[AreaFile.AD_VERSION] != AreaFile.VERSION_NUMBER)
throw new AreaFileException(
"Invalid version number - probably not an AREA file");
// word 20 may contain characters -- if small int, flip it
if ( (dir[20] & 0xffff) == 0) McIDASUtil.flip(dir,20,20);
McIDASUtil.flip(dir,21,23);
// words 24-31 contain memo field
McIDASUtil.flip(dir,32,50);
// words 51-2 contain cal info
McIDASUtil.flip(dir,53,55);
// word 56 contains original source type (ascii)
McIDASUtil.flip(dir,57,63);
}
/* Debug
for (int i = 0; i < AreaFile.AD_DIRSIZE; i++)
{
System.out.println("dir[" + i +"] = " + dir[i]);
}
*/
// Pull out some of the important information
nominalTime = new Date(1000* McIDASUtil.mcDayTimeToSecs(
dir[AreaFile.AD_IMGDATE],
dir[AreaFile.AD_IMGTIME]));
if (dir[AreaFile.AD_STARTDATE] == 0 &&
dir[AreaFile.AD_STARTTIME] == 0)
startTime = nominalTime;
else
startTime = new Date( 1000*
McIDASUtil.mcDayTimeToSecs(
dir[AreaFile.AD_STARTDATE],
dir[AreaFile.AD_STARTTIME]));
// create the bands array. Might be more bits set than bands, though cuz of the AVHRR band 3a/b thingy
int numbands = dir[AreaFile.AD_NUMBANDS];
bands = new int[numbands];
int j = 0;
for (int i=0; i<64; i++) { // band bits in two consequtive words
int bandmask = 1 << ( i%32 );
if ( (bandmask & dir[AreaFile.AD_BANDMAP + (i/32) ]) == bandmask) {
bands[j] = i+1 ;
j++;
if (j >= numbands) break; // done, one way or the other...
}
}
// get memo field
int[] memoArray = new int[8];
System.arraycopy(dir, 24, memoArray, 0, memoArray.length);
memo = McIDASUtil.intBitsToString(memoArray);
calType = McIDASUtil.intBitsToString(dir[AreaFile.AD_CALTYPE]).trim();
srcType = McIDASUtil.intBitsToString(dir[AreaFile.AD_SRCTYPE]).trim();
srcTypeOrig = (dir[AreaFile.AD_SRCTYPEORIG] == 0)
? srcType
: McIDASUtil.intBitsToString(dir[AreaFile.AD_SRCTYPEORIG]).trim();
calTypeUnit =
(dir[AreaFile.AD_CALTYPEUNIT] == 0 ||
dir[AreaFile.AD_CALTYPEUNIT] == McIDASUtil.MCMISSING)
? null
: McIDASUtil.intBitsToString(dir[AreaFile.AD_CALTYPEUNIT]).trim();
//System.out.println("AD.calTypeUnit = >"+calTypeUnit+"<");
if (calTypeUnit != null && calTypeUnit.equals("")) calTypeUnit = null;
calTypeScaleFactor =
(dir[AreaFile.AD_CALTYPESCALE] == 0 ||
dir[AreaFile.AD_CALTYPESCALE] == McIDASUtil.MCMISSING)
? 1 : dir[AreaFile.AD_CALTYPESCALE];
}
/**
* Create an AreaDirectory from another AreaDirectory object.
*
* @param directory the source AreaDirectory
*
* @exception AreaFileException not a valid directory
*/
public AreaDirectory(AreaDirectory directory)
throws AreaFileException
{
this(directory.getDirectoryBlock());
}
/**
* Return a specific value from the directory
*
* @param pointer part of the directory you want returned.
* Use AreaFile static fields as pointers.
*
* @exception AreaFileException invalid pointer
*/
public int getValue(int pointer)
throws AreaFileException
{
if (pointer < 0 || pointer > AreaFile.AD_DIRSIZE)
throw new AreaFileException("Invalid pointer " + pointer);
return dir[pointer];
}
/**
* Get the raw directory block
*
* @return integer array of the raw directory values
*/
public int[] getDirectoryBlock()
{
return dir;
}
/**
* returns the nominal time of the image
*
* @return the nominal time as a Date
*/
public Date getNominalTime()
{
return nominalTime;
}
/**
* returns the nominal time of the image
*
* @return the nominal time as a Date
*/
public Date getStartTime()
{
return startTime;
}
/**
* returns the number of bands in the image
*
* @return number of bands
*/
public int getNumberOfBands()
{
return dir[AreaFile.AD_NUMBANDS];
}
/**
* returns the number of lines in the image
*
* @return line number
*/
public int getLines()
{
return dir[AreaFile.AD_NUMLINES];
}
/**
* returns the number of elements in the image
*
* @return number of elements
*/
public int getElements()
{
return dir[AreaFile.AD_NUMELEMS];
}
/**
* set the band calibration info (Vector)
* array order is identical to bands array, each Vector
* element is a pair of String values: first, the code value and
* second the descriptive name.
*
* @param the list of calibration parameters
*/
public void setCalInfo(Vector[] v) {
calInfo = v;
}
/** get the valid band calibration information
*
* @return array of Vectors of Strings of calibration info
*/
public Vector[] getCalInfo() {
return calInfo;
}
/**
* returns the bands in each of the images
*
* @return a array of bands
*/
public int[] getBands()
{
return bands;
}
/**
* Returns memo field of the directory
*
* @return string representing the memo
*/
public String getMemoField()
{
return memo;
}
/**
* Returns the sensor type
*
* @return string representing the sensor type
*/
public String getSensorType()
{
return sensors[dir[AreaFile.AD_SENSORID]];
}
public int getSensorID() {
return dir[AreaFile.AD_SENSORID];
}
/**
* Returns the source type
*
* @return string representing the cal type
*/
public String getSourceType()
{
String r = srcType;
if (r.equalsIgnoreCase("VISR")) r=srcTypeOrig;
return r;
}
/**
* Returns the calibration type
*
* @return string representing the cal type
*/
public String getCalibrationType()
{
return calType;
}
/** get Latutide at center of image
*
* @return value of latitude; if not available, return Double.NaN
*/
public double getCenterLatitude() {
return centerLatitude;
}
/** set Latitude at center of image
*
* @param value of latitude at center point of image
*/
public void setCenterLatitude(double lat) {
centerLatitude = lat;
}
/** get longitude at center of image
*
* @return value of longitude; if not available, return Double.NaN.
*/
public double getCenterLongitude() {
return centerLongitude;
}
/** set Longitude at center of image
*
* @param value of Longitude at center point of image
*/
public void setCenterLongitude(double lon) {
centerLongitude = lon;
}
/** get Latutide-wise resolution at center of image
*
* @return value of resolution (usually in KM) . If not available,
* value is Double.NaN.
*/
public double getCenterLatitudeResolution() {
return centerLatitudeResolution;
}
/** set Latitude-wise resolution at center of image
*
* @param value of latitude-wise resolution at center point of image
*/
public void setCenterLatitudeResolution(double res) {
centerLatitudeResolution = res;
}
/** get longitude-wise resolution at center of image
*
* @return value of longitude-wise resolution (usually in KM)
* return Double.NaN if not available.
*/
public double getCenterLongitudeResolution() {
return centerLongitudeResolution;
}
/** set Longitude-wise resolution at center of image
*
* @param value of Longitude-wise resolution at center point of image
*/
public void setCenterLongitudeResolution(double res) {
centerLongitudeResolution = res;
}
/**
* Get the string representing the calibration unit
*
* @return name of calibration unit
*/
public String getCalibrationUnitName() {
return calTypeUnit;
}
/**
* Get the scaling factor of the values for this calibration type
*
* @return scaling factor
*/
public int getCalibrationScaleFactor() {
return calTypeScaleFactor;
}
/**
* Check the equality of the object in question with this.
* @param o object in question
*/
public boolean equals(Object o) {
if (!(o instanceof AreaDirectory)) return false;
AreaDirectory that = (AreaDirectory) o;
return (this == that ||
java.util.Arrays.equals(
getDirectoryBlock(), that.getDirectoryBlock()));
}
/**
* Prints out a formatted listing of the directory info
*/
public String toString()
{
StringBuffer buf = new StringBuffer();
SimpleDateFormat sdf = new SimpleDateFormat();
sdf.setTimeZone(TimeZone.getTimeZone("GMT"));
sdf.applyPattern("yyyy-MMM-dd HH:mm:ss");
buf.append(" ");
buf.append(sdf.format(nominalTime,
new StringBuffer(), new FieldPosition(0)).toString());
buf.append(" ");
buf.append(Integer.toString(getLines()));
buf.append(" ");
buf.append(Integer.toString(getElements()));
buf.append(" ");
//buf.append(" "+bands.length);
for (int i = 0; i < bands.length; i++) buf.append(bands[i]);
return buf.toString();
}
}

View file

@ -1,516 +0,0 @@
//
// AreaDirectoryList.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import edu.wisc.ssec.mcidas.adde.AddeURLConnection;
import java.applet.Applet;
import java.io.BufferedInputStream;
import java.io.DataInputStream;
import java.io.EOFException;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.text.FieldPosition;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.TimeZone;
import java.util.ArrayList;
import java.util.StringTokenizer;
import java.util.Vector;
/**
* AreaDirectoryList interface for McIDAS 'area' file format image data.
* Provides access to a list of one or more AreaDirectoy objects.
*
* @author Don Murray
*
*/
public class AreaDirectoryList
{
private static boolean debug = false;
// load protocol for ADDE URLs
// See java.net.URL for explanation of URL handling
static
{
try
{
String handlers = System.getProperty("java.protocol.handler.pkgs");
String newProperty = null;
if (handlers == null)
newProperty = "edu.wisc.ssec.mcidas";
else if (handlers.indexOf("edu.wisc.ssec.mcidas") < 0)
newProperty = "edu.wisc.ssec.mcidas | " + handlers;
if (newProperty != null) // was set above
System.setProperty("java.protocol.handler.pkgs", newProperty);
}
catch (Exception e)
{
System.out.println(
"Unable to set System Property: java.protocol.handler.pkgs");
}
}
private boolean flipwords = false;
private DataInputStream inputStream; // input stream
private int status=0; // read status
private URLConnection urlc; // URL connection
private boolean isADDE = false; // true if ADDE request
private int[] dir; // single directory
private Date[] nominalTimes; // array of dates
private int[] bands; // array of bands
private int[] lines; // array of lines
private int[] elements; // array of elements
private ArrayList dirs; // list of directories
private int numDirs = 0; // number of directories
/**
* creates an AreaDirectory object that allows reading
* of McIDAS 'area' file format image data. allows reading
* either from a disk file, or a server via ADDE.
*
* @param imageSource the file name or ADDE URL to read from
*
* @exception AreaFileException if file cannot be opened
*
*/
public AreaDirectoryList(String imageSource)
throws AreaFileException
{
// try as a disk file first
try
{
inputStream =
new DataInputStream (
new BufferedInputStream(
new FileInputStream(imageSource), 2048));
}
catch (IOException eIO)
{
// if opening as a file failed, try as a URL
URL url;
try
{
url = new URL(imageSource);
urlc = url.openConnection();
InputStream is = urlc.getInputStream();
inputStream =
new DataInputStream(
new BufferedInputStream(is));
}
catch (Exception e)
{
throw new AreaFileException("Error opening AreaFile: " + e);
}
if (url.getProtocol().equalsIgnoreCase("adde")) isADDE = true;
}
readDirectory();
}
/**
* creates an AreaDirectory object that allows reading
* of the directory of McIDAS 'area' files from a URL
*
* @param URL - the URL to go after
*
* @exception AreaFileException if file cannot be opened
*
*/
public AreaDirectoryList(URL url)
throws AreaFileException
{
try
{
inputStream =
new DataInputStream(
new BufferedInputStream(url.openStream()));
}
catch (IOException e)
{
throw new AreaFileException("Error opening URL for AreaFile:"+e);
}
readDirectory();
}
/**
* Read the directory information for an area file or area directory
* record.
*
* @exception AreaFileException if there is a problem reading
* any portion of the metadata.
*
*/
private void readDirectory() throws AreaFileException {
double resolutionLat = Double.NaN;
double resolutionLon = Double.NaN;
double centerLat = Double.NaN;
double centerLon = Double.NaN;
int band = 0;
String calname = " ", caldesc = " ";
dirs = new ArrayList();
int numBytes =
(isADDE)
? ((AddeURLConnection) urlc).getInitialRecordSize()
: AreaFile.AD_DIRSIZE;
while (numBytes > 0) {
try {
dir = new int[AreaFile.AD_DIRSIZE];
// skip first int which is dataset area number if ADDE request
if (isADDE) {
int areaNumber = inputStream.readInt();
if (debug) System.out.println("Area number = " + areaNumber);
}
for (int i=0; i < AreaFile.AD_DIRSIZE; i++) {
dir[i] = inputStream.readInt();
}
if (!isADDE) dir[0] = 0;
// see if the directory needs to be byte-flipped
if (dir[AreaFile.AD_VERSION] > 255 || flipwords) {
flipwords = true;
McIDASUtil.flip(dir,0,19);
// word 20 may contain characters -- if small int, flip it
if ( (dir[20] & 0xffff) == 0) McIDASUtil.flip(dir,20,20);
McIDASUtil.flip(dir,21,23);
// words 24-31 contain memo field
McIDASUtil.flip(dir,32,50);
// words 51-2 contain cal info
McIDASUtil.flip(dir,53,55);
// word 56 contains original source type (ascii)
McIDASUtil.flip(dir,57,63);
}
if (debug) {
for (int i = 0; i < AreaFile.AD_DIRSIZE; i++)
{
System.out.println("dir[" + i +"] = " + dir[i]);
}
}
AreaDirectory ad = new AreaDirectory(dir);
int[] bands = ad.getBands();
int numBands = ad.getNumberOfBands();
// make a Vector to hold the band calibration info (if available)
Vector [] calInfo = new Vector[numBands];
for (int k=0; k<numBands; k++) {
calInfo[k] = new Vector();
}
if (!isADDE) {
numBytes = 0;
} else {
// last word in trailer is the number of bytes for the
// next record so we need to read that
/*
int skipBytesCount = numBytes - AreaFile.AD_DIRSIZE*4 - 4;
inputStream.skipBytes(skipBytesCount);
*/
/* */
int numCards = dir[AreaFile.AD_DIRSIZE -1];
if (debug) System.out.println("Number of comment cards = " + numCards);
for (int i = 0; i < numCards; i++)
{
byte[] card = new byte[80];
int count = 0;
boolean prevBlank = true;
for (int j = 0; j < 80; j++) {
byte b = inputStream.readByte();
if (b == ' ') {
if (!prevBlank) {
card[count++] = b;
prevBlank = false;
}
prevBlank = true;
} else {
card[count++] = b;
prevBlank = false;
}
}
String cd = new String(card,0,count).trim();
if (debug) System.out.println("card["+i+"] = " + cd);
if (cd.indexOf("Center latitude") > -1) {
int m = cd.indexOf("=");
if (m > 0) {
centerLat = Double.valueOf(
cd.substring(m+1).trim()).doubleValue();
} else {
centerLat = Double.NaN;
}
} else if (cd.indexOf("Center longitude") > -1) {
int m = cd.indexOf("=");
if (m > 0) {
centerLon = - Double.valueOf(
cd.substring(m+1).trim()).doubleValue();
} else {
centerLon = Double.NaN;
}
} else if (cd.indexOf("Computed Latitude") > -1) {
int m = cd.indexOf("=");
if (m > 0) {
resolutionLat = Double.valueOf(
cd.substring(m+1).trim()).doubleValue();
} else {
resolutionLat = Double.NaN;
}
} else if (cd.indexOf("Computed Longitude") > -1) {
int m = cd.indexOf("=");
if (m > 0) {
resolutionLon = Double.valueOf(
cd.substring(m+1).trim()).doubleValue();
} else {
resolutionLon = Double.NaN;
}
} else if (cd.indexOf("Valid calibration unit") > -1) {
int m = cd.indexOf("=");
if (m > 0) {
String cdd = cd.replace('"',' ');
StringTokenizer st = new StringTokenizer(cdd," ");
int n = st.countTokens();
band = 0;
calname = " ";
caldesc = " ";
boolean gotit = false;
for (int k=0; k<n; k++) {
if (st.nextToken().trim().equals("band")) {
gotit = true;
break;
}
}
if (gotit) {
band = Integer.parseInt(st.nextToken().trim());
st.nextToken(); // skip = sign
calname = st.nextToken();
caldesc = calname;
if (st.hasMoreTokens()) {
StringBuffer buf = new StringBuffer();
while (st.hasMoreTokens()) {
buf.append(st.nextToken());
buf.append(" ");
}
caldesc = buf.toString().trim();
}
for (int k=0; k<numBands; k++) {
if (band == bands[k]) {
calInfo[k].addElement(calname);
calInfo[k].addElement(caldesc);
}
}
}
}
}
}
ad.setCenterLatitude(centerLat);
ad.setCenterLongitude(centerLon);
ad.setCenterLatitudeResolution(resolutionLat);
ad.setCenterLongitudeResolution(resolutionLon);
ad.setCalInfo(calInfo);
/* */
numBytes = inputStream.readInt();
if (debug) System.out.println("Bytes in next record = " + numBytes);
}
dirs.add(ad);
}
catch (IOException e) {
status = -1;
throw new AreaFileException(
"Error reading Area directory:" + e);
}
status = 1;
numDirs++;
}
}
/** returns the directory blocks for the requested images,
* sorted into an array of AreaDirectories by time and
* then bands as the second dimenison, if multiple directories
* with the same ADDE position number are returned.
*/
public AreaDirectory[][] getSortedDirs() throws AreaFileException {
if (status <= 0 || dirs.size() <= 0) {
throw new AreaFileException( "Error reading directory information");
}
// first gather up the positions and nominal times
Date[] dtg = new Date[numDirs];
int[] pos = new int[numDirs];
int[] insitu = new int[numDirs];
ArrayList al = new ArrayList();
ArrayList alt = null;
for (int i=0; i<numDirs; i++) {
AreaDirectory ad = (AreaDirectory) dirs.get(i);
dtg[i] = ad.getNominalTime();
pos[i] = ad.getValue(0);
insitu[i] = i;
}
Date ddd = null;
// now sort the values by date
for (int i=0; i<numDirs; i++) {
int swap = i;
for (int k=i+1; k<numDirs; k++) {
if (dtg[swap].compareTo(dtg[k]) > 0) swap = k;
}
if (swap != i) {
Date dtgt = dtg[i];
dtg[i] = dtg[swap];
dtg[swap] = dtgt;
int intt = pos[i];
pos[i] = pos[swap];
pos[swap] = intt;
intt = insitu[i];
insitu[i] = insitu[swap];
insitu[swap] = intt;
}
// look to see if date-time has changed
if ( (ddd == null) || (ddd.compareTo(dtg[i]) != 0)) {
if (ddd != null) al.add(alt); // add the previous one if there
ddd = dtg[i];
alt = new ArrayList();
}
alt.add(dirs.get(insitu[i]) ); // copy the AreaDirectory entry over
}
// catch the very last one...
if (alt != null && alt.size() > 0) al.add(alt);
int num = al.size();
if (num == 0) return null;
// now make an array of AreaDirectory objects for return...
AreaDirectory[][] ada = new AreaDirectory[num][];
for (int i=0; i<num; i++) {
alt = (ArrayList) al.get(i);
int knum = alt.size();
ada[i] = new AreaDirectory[knum];
for (int k=0; k<knum; k++) {
ada[i][k] = (AreaDirectory)alt.get(k);
}
}
return ada;
}
/**
* returns the directory blocks for the requested images.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A> for information on the parameters
* for each value.
*
* @return a ArrayList of AreaDirectorys
*
* @exception AreaFileException if there was a problem
* reading the directory
*
*/
public ArrayList getDirs()
throws AreaFileException
{
if (status <= 0 || dirs.size() <= 0)
{
throw new AreaFileException(
"Error reading directory information");
}
return dirs;
}
/**
* Prints out a formatted listing of the directory info
*/
public String toString()
{
if (status <=0 || numDirs <= 0)
{
return new String("No directory information available");
}
StringBuffer sb = new StringBuffer();
sb.append(" Date Time Lin Ele Bands \n");
sb.append(" ------- ------- --- --- --------\n");
for (int i = 0; i < dirs.size(); i++)
{
sb.append( ((AreaDirectory) dirs.get(i)).toString());
sb.append("\n");
}
return sb.toString();
}
public static void main(String[] args)
throws Exception
{
if (args.length == 0)
{
System.out.println("Must supply a path or ADDE request to images");
System.exit(1);
}
AreaDirectoryList adl = new AreaDirectoryList(args[0]);
System.out.println(adl.toString());
// print out test of getSortedDirs()
AreaDirectory[][] ada = adl.getSortedDirs();
for (int i=0; i<ada.length; i++) {
Date dd = ada[i][0].getNominalTime();
System.out.print(dd+" ");
for (int k=0; k<ada[i].length; k++) {
int[] bands = ada[i][k].getBands();
for (int b=0; b<bands.length; b++) {
System.out.print(" "+bands[b]);
}
}
System.out.println(" ");
}
}
}

View file

@ -1,51 +0,0 @@
//
// AreaFileException.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* AreaFileException class is to handle exceptions when dealing
* with McIDAS 'area' files.
*
* @author Tom Whittaker SSEC
*/
public class AreaFileException extends McIDASException {
/**
* Constructs an AreaFileException with no specified detail message.
*/
public AreaFileException() {super(); }
/**
* Constructs an AreaFileException with the specified detail message.
*
* @param s the detail message.
*/
public AreaFileException(String s) {super(s); }
}

View file

@ -1,456 +0,0 @@
//
// AreaFileFactory.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.net.MalformedURLException;
import java.net.URISyntaxException;
import java.net.URL;
import edu.wisc.ssec.mcidas.adde.AddeURLException;
/**
* Utility class for creating <code>AreaFile</code> instances. This class
* handles subsetting local files using urls whereas the <code>AreaFile</code>
* constructors do not.
*
* <p>No instances of this class can be created.</p>
* @version $Id: AreaFileFactory.java,v 1.8 2009-07-01 12:51:04 donm Exp $
* @author Bruce Flynn, SSEC
*/
public final class AreaFileFactory {
/** No-op constructor preventing instatiation of this class. */
private AreaFileFactory() {}
/**
* String to calibration int.
* @param cal calibration type string
*
* @return calibration type integer, Calibrator.CAL_NONE if unknown
*/
public final static int calStrToInt(String cal) {
int ret = Calibrator.CAL_NONE;
String calType = cal.trim();
if (calType.equalsIgnoreCase("temp")) ret = Calibrator.CAL_TEMP;
else if (calType.equalsIgnoreCase("brit")) ret = Calibrator.CAL_BRIT;
else if (calType.equalsIgnoreCase("rad")) ret = Calibrator.CAL_RAD;
else if (calType.equalsIgnoreCase("raw")) ret = Calibrator.CAL_RAW;
else if (calType.equalsIgnoreCase("refl")) ret = Calibrator.CAL_ALB;
return ret;
}
/**
* Calibration int to string.
* @param cal calibration type
*
* @return calibration type string, raw if unknown
*/
public final static String calIntToStr(int cal) {
String ret = "raw";
switch (cal) {
case Calibrator.CAL_ALB:
ret = "refl";
break;
case Calibrator.CAL_BRIT:
ret = "brit";
break;
case Calibrator.CAL_RAD:
ret = "rad";
break;
case Calibrator.CAL_RAW:
ret = "raw";
break;
case Calibrator.CAL_TEMP:
ret = "temp";
break;
}
return ret;
}
/**
* Construct a url query string for subsetting a local file.
* @param sl starting line number.
* @param nl number of lines.
* @param lm line magnification.
* @param se starting element.
* @param ne number of elements.
* @param em element magnification.
* @param b band number.
* @return &quot;?band=B&amp;linele=SL SE&amp;size=NL NE&amp;mag=LM EM&quot;
*/
public final static String makeLocalQuery(int sl, int nl, int lm, int se,
int ne, int em, int b) {
return "?band=" + b + "&linele=" + sl + " " + se + "&size=" + nl + " " +
ne + "&mag=" + lm + " " + em;
}
/**
* Construct a url query string for subsetting a local file.
* @param sl starting line number.
* @param nl number of lines.
* @param lm line magnification.
* @param se starting element.
* @param ne number of elements.
* @param em element magnification.
* @param b band number.
* @param c calibration type
* @return &quot;?band=B&amp;linele=SL SE&amp;size=NL NE&amp;mag=LM EM&quot&unit=C;
*/
public final static String makeLocalQuery(int sl, int nl, int lm, int se,
int ne, int em, int b, int c) {
String ct = calIntToStr(c);
return "?band=" + b + "&linele=" + sl + " " + se + "&size=" + nl + " " +
ne + "&mag=" + lm + " " + em + "&unit=" + ct;
}
/**
* Construct a url query string for subsetting a local file.
* @param sl starting line number.
* @param nl number of lines.
* @param lm line magnification.
* @param se starting element.
* @param ne number of elements.
* @param em element magnification.
* @param b band number.
* @param c calibration type as a string
* @return &quot;?band=B&amp;linele=SL SE&amp;size=NL NE&amp;mag=LM EM&quot&unit=C;
*/
public final static String makeLocalQuery(int sl, int nl, int lm, int se,
int ne, int em, int b, String c) {
return "?band=" + b + "&linele=" + sl + " " + se + "&size=" + nl + " " +
ne + "&mag=" + lm + " " + em + "&unit=" + c;
}
/**
* Construct a {@link java.net.URL} for subsetting a local file.
* @param fpath canonical path to an area file.
* @param sl starting line number.
* @param nl number of lines.
* @param lm line magnification.
* @param se starting element.
* @param ne number of elements.
* @param em element magnification.
* @param b band number.
* @param u calibration unit
* @return a string of the format <code>&quot;file://FPATH?band=B&amp;
* linele=SL SE&amp;size=NL NE&amp;mag=LM EM&quot;&unit=U</code>
*
* @throws MalformedURLException bad URL specification
*/
public final static URL makeLocalSubsetURL(String fpath, int sl, int nl,
int lm, int se, int ne, int em,
int b, String u)
throws MalformedURLException {
String surl = "file://" + fpath +
makeLocalQuery(sl, nl, lm, se, ne, em, b, u);
URL url = null;
try {
url = new URL(surl);
}
catch (MalformedURLException e) {
// this cannot occur because the protocol is hardcoded to a known one
}
return url;
}
/**
* Create an initialized <code>AreaFile</code> instance. First, an attempt is
* made to create a <code>URL</code> from <code>src</code>, if an error
* occurrs, meaning <code>src</code> is not a valid url, <code>src</code> is
* interpreted as a file path.
* @param src A relative or canonical path to a local file as a string or a
* string representation of a url appropriate for creating an
* <code>AreaFile</code> instance. For more information on urls appropriate
* for creating <code>AreaFile</code> instances see
* {@link #getAreaFileInstance(URL)}.
* <p>URLs containing encoded characters in their query strings will be decoded
* before parsing.
* </p>
* @return an initialized, possibly subsetted, instance
* @throws AreaFileException on any error constructing the instance.
* @throws AddeURLException If the source is a URL and the query string is
* not formatted correctly.
*/
public static final AreaFile getAreaFileInstance(final String src)
throws AreaFileException, AddeURLException {
// handle the special "pop up a gui" case for adde://image?
if (src.startsWith("adde://") &&
(src.endsWith("image?") || src.endsWith("imagedata?"))) {
return new AreaFile(src);
}
// Try to create an instance as a URL first. If a valid URL instance cannot
// be created lets try 'src' as a filename.
// NOTE: it's important to make sure the AreaFile and AddeURL exceptions
// are propagated from constructor or factory method.
AreaFile af = null;
URL url = null;
try {
url = new URL(src);
af = getAreaFileInstance(url);
}
catch (MalformedURLException e) {
af = new AreaFile(src);
}
return af;
}
/**
* Create an initialized <code>AreaFile</code> instance.
*
* <p>A url appropriate for creating an instance will have a protocol of
* either <code>adde</code> for remote ADDE data or <code>file</code> for
* files on the local disk. Information on consructing ADDE urls can be found
* in the {@link edu.wisc.ssec.mcidas.adde.AddeURLConnection} class.</p>
*
* <p>A local file url may either be a standard file url such as
* file:///&lt;absolute file path&gt; or it may specify subsetting
* information. If specifying subsetting information, the url can contain the
* following parameters from the ADDE image data url specification with the
* specified defaults:
* <pre>
* NAME DEFAULT
* linele - 0 0 a Must be used with size.
* NOTE: only type 'a' is supported at this time
* size - 0 0 Must be used with linele.
* mag - 1 1 Only with linele and size, but not required.
* band - 1 Can be used separately, not required.
* unit - RAW Calibration type
* </pre>
* A file url might look like:
* <pre>
* file://&lt;abs file path&gt;?linele=10 10&amp;band=3&amp;mag=-2 -4&amp;size=500 500&unit=BRIT
* </pre>
* </p>
* <p>URLs containing encoded characters in their query strings will be decoded
* before parsing.
* </p>
* @param url - the url as described above
* @return an initialized, possibly subsetted, instance
* @throws AreaFileException on any error constructing the instance.
* @throws AddeURLException if the query string is not a valid ADDE query
* stirng.
*/
public static final AreaFile getAreaFileInstance(final URL url)
throws AddeURLException, AreaFileException {
// it's a local file, investigate further
if (url.getProtocol().equalsIgnoreCase("file")) {
AreaFile af = null;
if (url.getQuery() == null) {
af = new AreaFile(url);
}
else {
// open w/o query string
af = new AreaFile(url.toString().split("\\?")[0]);
}
// is it a local url with subsetting
String query = url.getQuery();
if (query != null && query.contains("%")) {
try {
query = url.toURI().getQuery(); // URI queries are decoded
}
catch (URISyntaxException e) {
throw new AddeURLException(e.getMessage());
}
}
if (query != null) {
final String whtspc = "(\\s)+";
int startLine = 0;
int numLines = af.getAreaDirectory().getLines();
int lineMag = 1;
int startElem = 0;
int numEles = af.getAreaDirectory().getElements();
int eleMag = 1;
int band = -1;
int calType = Calibrator.CAL_NONE;
boolean linele = false;
boolean size = false;
boolean mag = false;
int availableLines = numLines;
int availableEles = numEles;
// parse query string
String[] props = query.split("&");
for (int i = 0; i < props.length; i++) {
String[] kv = props[i].split("=");
if (kv[0].equalsIgnoreCase("mag")) {
lineMag = Integer.parseInt(kv[1].split(whtspc)[0]);
eleMag = Integer.parseInt(kv[1].split(whtspc)[1]);
mag = true;
}
if (kv[0].equalsIgnoreCase("size")) {
numLines = Integer.parseInt(kv[1].split(whtspc)[0]);
numEles = Integer.parseInt(kv[1].split(whtspc)[1]);
size = true;
}
if (kv[0].equalsIgnoreCase("band")) {
int bandIdx = -1;
int[] bands = af.getAreaDirectory().getBands();
if (band == -1) {
bandIdx = 0;
}
else {
for (int j = 0; i < bands.length; j++) {
if (bands[j] == band) {
bandIdx = j;
}
}
}
band = bands[bandIdx];
}
if (kv[0].equalsIgnoreCase("linele")) {
String[] vals = kv[1].split(whtspc);
startLine = Integer.parseInt(vals[0]);
startElem = Integer.parseInt(vals[1]);
if (vals.length >= 3 && !vals[2].equalsIgnoreCase("a")) {
throw new AddeURLException("Image and earth types are not currenly supported");
}
availableLines -= startLine;
availableEles -= startElem;
linele = true;
}
if (kv[0].equalsIgnoreCase("unit")) {
calType = calStrToInt(kv[1]);
switch (calType) {
case Calibrator.CAL_ALB:
case Calibrator.CAL_BRIT:
case Calibrator.CAL_RAD:
case Calibrator.CAL_TEMP:
case Calibrator.CAL_RAW:
case Calibrator.CAL_NONE:
break;
default:
throw new AreaFileException("Unsupported calibration type: " +
kv[1]);
}
}
}
if (mag) {
availableLines = availableLines / (Math.abs(lineMag) == 0
? 1
: Math.abs(lineMag));
availableEles = availableEles / (Math.abs(eleMag) == 0
? 1
: Math.abs(eleMag));
if (size) {
numLines = Math.min(availableLines, numLines);
numEles = Math.min(availableEles, numEles);
}
else {
numLines = availableLines;
numEles = availableEles;
}
}
// recreate with new parameters
af = new AreaFile(url.getPath(), startLine, numLines, lineMag,
startElem, numEles, eleMag, band);
af.setCalType(calType);
}
return af;
}
else {
return new AreaFile(url);
}
}
/**
* See {@link AreaFile#AreaFile(String, int, int, int, int, int, int, int)}
*
* @param fpath the path to the file
* @param startLine the starting image line
* @param numLines the total number of lines to return
* @param lineMag the line magnification. Valid values are &gt;= -1. -1, 0, and
* 1 are all taken to be full line resolution, 2 is every
* other line, 3 every third, etc...
* @param startElem the starting image element
* @param numEles the total number of elements to return
* @param eleMag the element magnification. Valid values are &gt;= -1. -1, 0, and 1
* are all taken to be full element resolution, 2 is every
* other element, 3 every third, etc...
* @param band the 1-based band number for the subset, which must be present
* in the directory blocks band map or -1 for the first band
*
* @return
*
* @throws AreaFileException
*/
public final static AreaFile getAreaFileInstance(String fpath,
int startLine, int numLines, int lineMag, int startElem,
int numEles, int eleMag, int band)
throws AreaFileException {
return new AreaFile(fpath, startLine, numLines, lineMag, startElem,
numEles, eleMag, band);
}
/**
* Copy an area file from one place to another
* @param source source file or ADDE url
* @param outputFile name of the output file
* @throws AreaFileException on any error constructing the instance.
* @throws AddeURLException If the source is a URL and the query string is
* not formatted correctly.
*/
public static void copyAreaFile(String source, String outputFile)
throws AddeURLException, AreaFileException {
copyAreaFile(source, outputFile, false);
}
/**
* Copy an area file from one place to another
* @param source source file or ADDE url
* @param outputFile name of the output file
* @param verbose true to print out status messages
* @throws AreaFileException on any error constructing the instance.
* @throws AddeURLException If the source is a URL and the query string is
* not formatted correctly.
*/
public static void copyAreaFile(String source, String outputFile,
boolean verbose)
throws AddeURLException, AreaFileException {
AreaFile area = getAreaFileInstance(source);
area.save(outputFile, verbose);
}
}

View file

@ -1,86 +0,0 @@
//
// Calibrator.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* interface for creating Calibrator classes.
*
* @version 1.2 16 Nov 1998
* @author Tommy Jasmin, SSEC
*/
public interface Calibrator {
public static final int CAL_NONE = -1;
public static final int CAL_MIN = 1;
public static final int CAL_RAW = 1;
public static final int CAL_RAD = 2;
public static final int CAL_ALB = 3;
public static final int CAL_TEMP = 4;
public static final int CAL_BRIT = 5;
public static final int CAL_MAX = 5;
/** Meteosat Second Generation imager. */
public static final int SENSOR_MSG_IMGR = 51;
/** GOES 8 imager. */
public static final int SENSOR_GOES8_IMGR = 70;
/** GOES 8 sounder. */
public static final int SENSOR_GOES8_SNDR = 71;
/** GOES 9 imager. */
public static final int SENSOR_GOES9_IMGR = 72;
/** GOES 9 sounder. */
public static final int SENSOR_GOES9_SNDR = 73;
/** GOES 10 imager. */
public static final int SENSOR_GOES10_IMGR = 74;
/** GOES 10 sounder. */
public static final int SENSOR_GOES10_SNDR = 75;
/** GOES 12 imager. */
public static final int SENSOR_GOES12_IMGR = 78;
/** GOES 12 sounder. */
public static final int SENSOR_GOES12_SNDR = 79;
/** GOES 13 imager. */
public static final int SENSOR_GOES13_IMGR = 180;
/** GOES 13 sounder. */
public static final int SENSOR_GOES13_SNDR = 181;
public int setCalType (
int calType
);
public float[] calibrate (
float[] inputData,
int band,
int calTypeOut
);
public float calibrate (
float inputPixel,
int band,
int calTypeOut
);
}

View file

@ -1,168 +0,0 @@
//
// CalibratorDefault.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
/**
* CalibratorDefault creates a Calibrator object designed to
* act in the absence of a Calibrator for a particular sensor.
* In other words, if a sensor is not supported yet, just pass
* the input value on as the calibrated value.
*
* @version 1.2 6 Aug 1999
* @author Tommy Jasmin, SSEC
*/
public class CalibratorDefault implements Calibrator {
// public static final int CAL_NONE = -1;
// public static final int CAL_MIN = 1;
// public static final int CAL_RAW = 1;
// public static final int CAL_RAD = 2;
// public static final int CAL_ALB = 3;
// public static final int CAL_TEMP = 4;
// public static final int CAL_BRIT = 5;
// public static final int CAL_MAX = 5;
// var to store current cal type
protected static int curCalType = 0;
/**
*
* constructor - does nothing for default calibrator
*
* @param dis data input stream
* @param ad AncillaryData object
*
*/
public CalibratorDefault(DataInputStream dis, AncillaryData ad)
throws IOException
{
return;
}
/**
*
* set calibration type of current (input) data
*
* @param calType one of the types defined in Calibrator interface
*
*/
public int setCalType(int calType) {
if ((calType < Calibrator.CAL_MIN) || (calType > Calibrator.CAL_MAX)) {
return -1;
}
curCalType = calType;
return 0;
}
/**
*
* calibrate data buffer to specified units.
*
* @param inputData input data buffer
* @param band channel/band number
* @param calTypeOut units to convert input buffer to
*
*/
public float[] calibrate (
float[] inputData,
int band,
int calTypeOut
)
{
// create the output data buffer
float[] outputData = new float[inputData.length];
// just call the other calibrate routine for each data point
for (int i = 0; i < inputData.length; i++) {
outputData[i] = calibrate(inputData[i], band, calTypeOut);
}
// return the calibrated buffer
return outputData;
}
/**
*
* calibrate single value to specified units.
*
* @param inputPixel input data value
* @param band channel/band number
* @param calTypeOut units to convert input buffer to
*
*/
public float calibrate (
float inputPixel,
int band,
int calTypeOut
)
{
float outputData = 0.0f;
// validate, then calibrate for each combination starting with cur type
switch (curCalType) {
case CAL_RAW:
outputData = inputPixel;
break;
case CAL_RAD:
outputData = inputPixel;
break;
case CAL_ALB:
outputData = inputPixel;
break;
case CAL_TEMP:
outputData = inputPixel;
break;
case CAL_BRIT:
outputData = inputPixel;
break;
}
return outputData;
}
}

View file

@ -1,51 +0,0 @@
//
// CalibratorException.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* CalibratorException class is to handle exceptions when calibrating data.
*
* @version $Id: CalibratorException.java,v 1.4 2009-03-02 23:34:50 curtis Exp $
* @author Bruce Flynn, SSEC
*/
public class CalibratorException extends McIDASException {
/**
* Constructs an CalibratorException with no specified detail message.
*/
public CalibratorException() {super(); }
/**
* Constructs an CalibratorException with the specified detail message.
*
* @param s the detail message.
*/
public CalibratorException(String s) {super(s); }
}

View file

@ -1,148 +0,0 @@
//
// CalibratorFactory.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Utility class for creating <code>Calibrator</code> instances.
*
* @author Bruce Flynn, SSEC
* @version $Id: CalibratorFactory.java,v 1.7 2009-05-06 18:45:53 rickk Exp $
*/
public final class CalibratorFactory {
/** Disallow instatiantion. */
private CalibratorFactory() {}
/**
* Get an appropriate <code>Calibrator</code> for the sensor id provided.
* This assumes a RAW source data format. See the McIDAS Users Guide
* <a href="http://www.ssec.wisc.edu/mcidas/doc/users_guide/current/app_c-1.html">Appendix C</a>
* for a table of sensor ids.
* @param id Sensor id from the directory block
* @param cal Calibration block used to initialize the <code>Calibrator
* </code>
* @return initialized <code>Calibrator</code> with a source calibration
* type of RAW.
* @throws CalibratorException on an error initializing the object.
*/
public final static Calibrator getCalibrator(final int id, final int[] cal)
throws CalibratorException {
return getCalibrator(id, Calibrator.CAL_RAW, cal);
}
/**
* Get an appropriate <code>Calibrator</code> for the sensor id provided.
* See the McIDAS Users Guide
* <a href="http://www.ssec.wisc.edu/mcidas/doc/users_guide/current/app_c-1.html">Appendix C</a>
* for a table of sensor ids.
* @param id Sensor id from the directory block
* @param srcType the source data type from the directory block
* @param cal Calibration block used to initialize the
* <code>Calibrator</code>
* @return initialized <code>Calibrator</code>.
* @throws CalibratorException on an error initializing the object or if the
* sensor is unknown.
*/
public final static Calibrator getCalibrator(
final int id, final int srcType, final int[] cal)
throws CalibratorException {
Calibrator calibrator = null;
switch (id) {
case Calibrator.SENSOR_MSG_IMGR:
calibrator = new CalibratorMsg(cal);
calibrator.setCalType(srcType);
break;
case Calibrator.SENSOR_GOES8_IMGR:
case Calibrator.SENSOR_GOES8_SNDR:
calibrator = new CalibratorGvarG8(id, cal);
calibrator.setCalType(srcType);
break;
case Calibrator.SENSOR_GOES9_IMGR:
case Calibrator.SENSOR_GOES9_SNDR:
calibrator = new CalibratorGvarG9(id, cal);
calibrator.setCalType(srcType);
break;
case Calibrator.SENSOR_GOES10_IMGR:
case Calibrator.SENSOR_GOES10_SNDR:
calibrator = new CalibratorGvarG10(id, cal);
calibrator.setCalType(srcType);
break;
case Calibrator.SENSOR_GOES12_IMGR:
case Calibrator.SENSOR_GOES12_SNDR:
calibrator = new CalibratorGvarG12(id, cal);
calibrator.setCalType(srcType);
break;
case Calibrator.SENSOR_GOES13_IMGR:
case Calibrator.SENSOR_GOES13_SNDR:
calibrator = new CalibratorGvarG13(id, cal);
calibrator.setCalType(srcType);
break;
default:
throw new CalibratorException(
"Unknown or unimplemented sensor id: " + id
);
}
return calibrator;
}
/**
* Check if there is a <code>Calibrator</code> implemented for a sensor.
*
* @param id Id of the sensor from the McIDAS Users Guide
* <a href="http://www.ssec.wisc.edu/mcidas/doc/users_guide/current/app_c-1.html">Appendix C</a>
* @return True if there is an implemented <code>Calibrator</code>, false
* otherwise.
* @see The McIDAS Users Guide
*/
public final static boolean hasCalibrator(int id) {
switch (id) {
case Calibrator.SENSOR_GOES13_IMGR:
case Calibrator.SENSOR_GOES13_SNDR:
case Calibrator.SENSOR_GOES12_IMGR:
case Calibrator.SENSOR_GOES12_SNDR:
case Calibrator.SENSOR_GOES10_IMGR:
case Calibrator.SENSOR_GOES10_SNDR:
case Calibrator.SENSOR_GOES8_IMGR:
case Calibrator.SENSOR_GOES8_SNDR:
case Calibrator.SENSOR_GOES9_IMGR:
case Calibrator.SENSOR_GOES9_SNDR:
case Calibrator.SENSOR_MSG_IMGR:
return true;
default:
return false;
}
}
}

View file

@ -1,402 +0,0 @@
//
// CalibratorGvar.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
/**
* CalibratorGvar creates a Calibrator object designed specifically
* to deal with GVAR data. Not fully implemented at present - some
* calibrations remain to be done.
*
* @version 1.5 16 Nov 1998
* @author Tommy Jasmin, SSEC
*/
public abstract class CalibratorGvar implements Calibrator {
protected static final int NUM_BANDS_IMAGER = 5;
protected static final int NUM_BANDS_SOUNDER = 18;
protected static final int NUM_VIS_DETECTORS = 8;
protected static final int NUM_IR_DETECTORS = 2;
protected static final int NUM_IR_BANDS = 4;
protected static final int LOOKUP_TABLE_SZ_IMGR = 1024;
protected static final int LOOKUP_TABLE_SZ_SNDR = 32768;
// var to store current cal type
protected static int curCalType = 0;
protected static int index = 0;
protected float [] visBiasCoef = new float [NUM_VIS_DETECTORS];
protected float [] visGain1Coef = new float [NUM_VIS_DETECTORS];
protected float [] visGain2Coef = new float [NUM_VIS_DETECTORS];
protected float visRadToAlb = 0.0f;
protected float [][] irBiasCoef = new float [NUM_IR_DETECTORS][NUM_IR_BANDS];
protected float [][] irGainCoef = new float [NUM_IR_DETECTORS][NUM_IR_BANDS];
protected float [] sBiasCoef = new float [NUM_BANDS_SOUNDER];
protected float [] sGainCoef = new float [NUM_BANDS_SOUNDER];
protected float [][] lookupTable;
// used in calibrator method
private static float gain = 0.0f;
private static float bias = 0.0f;
private static int scale = 1;
private static int bandNum = 0;
private static int sid = 0;
/**
*
* constructor
*
* @param dis data input stream
* @param ad AncillaryData object
* @param calBlock calibration parameters array
*
*/
public CalibratorGvar (
DataInputStream dis,
AncillaryData ad,
int [] calBlock
)
throws IOException
{
this(ad.getSensorId(), calBlock);
}
public CalibratorGvar(final int sensorId, int[] calBlock) {
int calIndex = 0;
sid = sensorId;
// now, correct for satellites starting with G12 (sid = 78)
int irOffset = 2;
if (sid > 77) irOffset = 0;
//System.out.println("xxx sid = "+sid);
if ((sid % 2) == 0) {
// initialize lookup table
lookupTable = new float [NUM_BANDS_IMAGER] [LOOKUP_TABLE_SZ_IMGR];
for (int i = 0; i < NUM_BANDS_IMAGER; i++) {
for (int j = 0; j < LOOKUP_TABLE_SZ_IMGR; j++) {
lookupTable [i][j] = Float.NaN;
}
}
// read in an imager format cal block
for (int i = 0; i < NUM_VIS_DETECTORS; i++) {
visBiasCoef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_VIS_DETECTORS; i++) {
visGain1Coef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_VIS_DETECTORS; i++) {
visGain2Coef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
visRadToAlb = (float) ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
for (int i = 0; i < NUM_IR_BANDS; i++) {
irBiasCoef[0][(i + irOffset) % NUM_IR_BANDS] =
(float) ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_IR_BANDS; i++) {
irBiasCoef[1][(i + irOffset) % NUM_IR_BANDS] =
(float) ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_IR_BANDS; i++) {
irGainCoef[0][(i + irOffset) % NUM_IR_BANDS] =
(float) ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_IR_BANDS; i++) {
irGainCoef[1][(i + irOffset) % NUM_IR_BANDS] =
(float) ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
} else {
// initialize lookup table
lookupTable = new float [NUM_BANDS_SOUNDER + 1] [LOOKUP_TABLE_SZ_SNDR];
for (int i = 0; i < NUM_BANDS_SOUNDER + 1; i++) {
for (int j = 0; j < LOOKUP_TABLE_SZ_SNDR; j++) {
lookupTable [i][j] = Float.NaN;
}
}
// read in a sounder format cal block
for (int i = 0; i < NUM_VIS_DETECTORS / 2; i++) {
visBiasCoef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_VIS_DETECTORS / 2; i++) {
visGain1Coef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_VIS_DETECTORS / 2; i++) {
visGain2Coef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
visRadToAlb = (float) ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
for (int i = 0; i < NUM_BANDS_SOUNDER; i++) {
sBiasCoef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
for (int i = 0; i < NUM_BANDS_SOUNDER; i++) {
sGainCoef[i] = (float)
ConversionUtility.GouldToNative(calBlock[calIndex]);
calIndex++;
}
}
}
/**
*
* set calibration type of current (input) data
*
* @param calType one of the types defined in Calibrator interface
*
*/
public int setCalType(int calType) {
if ((calType < Calibrator.CAL_MIN) || (calType > Calibrator.CAL_MAX)) {
return -1;
}
curCalType = calType;
return 0;
}
/**
*
* calibrate from radiance to temperature
*
* @param inVal input data value
* @param band channel/band number
* @param sId sensor id number
*
*/
public abstract float radToTemp(float inVal, int band, int sId);
/**
*
* calibrate data buffer to specified units.
*
* @param inputData input data buffer
* @param band channel/band number
* @param calTypeOut units to convert input buffer to
*
*/
public float[] calibrate (
float[] inputData,
int band,
int calTypeOut
)
{
// create the output data buffer
float[] outputData = new float[inputData.length];
// just call the other calibrate routine for each data point
for (int i = 0; i < inputData.length; i++) {
outputData[i] = calibrate(inputData[i], band, calTypeOut);
}
// return the calibrated buffer
return outputData;
}
/**
*
* calibrate single value to specified units.
*
* @param inputPixel input data value
* @param band channel/band number
* @param calTypeOut units to convert input buffer to
*
*/
public float calibrate (
float inputPixel,
int band,
int calTypeOut
)
{
float outputData = 0.0f;
//System.out.println("#### input pixel="+inputPixel);
//System.out.println("#### cal band = "+band);
//System.out.println("#### len lookup = "+lookupTable.length+" "+lookupTable[3].length);
// load gain and bias constants based on band requested
if (band != bandNum) {
bandNum = band;
if ((sid % 2) == 0) {
if (band == 1) {
gain = visGain1Coef[0];
bias = visBiasCoef[0];
} else {
gain = irGainCoef[0][band - 2];
bias = irBiasCoef[0][band - 2];
//System.out.println("#### band="+band+" gain="+gain+" bias"+bias);
}
scale = 32;
} else {
if (band == 19) {
gain = visGain1Coef[0];
bias = visBiasCoef[0];
} else {
gain = sGainCoef[band - 1];
bias = sBiasCoef[band - 1];
}
scale = 2;
}
}
// check lookup table first, if there is an entry, use it
if (curCalType == CAL_BRIT) {
// one byte values are signed, so take absolute value for index
index = (int) inputPixel + 128;
} else {
// otherwise scale down the 1K possible 15 bit values to an index
index = (int) inputPixel / scale;
}
//System.out.println("xxx band = "+band+" index = "+index+" scale="+scale+ " inputPixel"+inputPixel);
if (!(Float.isNaN(lookupTable[band - 1][index]))) {
return (lookupTable[band - 1][index]);
}
// validate, then calibrate for each combination starting with cur type
switch (curCalType) {
case CAL_RAW:
outputData = inputPixel;
// if they want raw, just break right away
if (calTypeOut == CAL_RAW) {
break;
}
// convert to radiance
if ((sid % 2) == 0) {
outputData = inputPixel / scale;
}
outputData = (outputData - bias) / gain;
// if they want radiance we are done
if (calTypeOut == CAL_RAD) {
break;
}
// otherwise, convert to temperature
outputData = radToTemp(outputData, band, sid);
// if they want temperature, break here
if (calTypeOut == CAL_TEMP) {
break;
}
// compute brightness from temperature
if (outputData >= 242.0f) {
outputData = Math.max(660 - (int) (outputData * 2), 0);
} else {
outputData = Math.min(418 - (int) outputData, 255);
}
// if they want brightness, break here
if (calTypeOut == CAL_BRIT) {
break;
}
break;
case CAL_RAD:
outputData = inputPixel;
break;
case CAL_ALB:
outputData = inputPixel;
break;
case CAL_TEMP:
outputData = inputPixel;
break;
case CAL_BRIT:
outputData = inputPixel;
break;
}
lookupTable[band - 1][index] = outputData;
return outputData;
}
}

View file

@ -1,208 +0,0 @@
//
// CalibratorGvarG10.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
/**
* CalibratorGvarG10 creates a Calibrator object designed specifically
* to deal with GOES 10 data. Not fully implemented at present - some
* calibrations remain to be done. It provides all the constants
* specific to the GOES 10 imager and sounder sensors.
*
* @version 1.3 6 Aug 1999
* @author Tommy Jasmin, SSEC
*/
public class CalibratorGvarG10 extends CalibratorGvar {
protected static float [] imager10FK1 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder10FK1 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager10FK2 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder10FK2 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager10TC1 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder10TC1 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager10TC2 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder10TC2 = new float[NUM_BANDS_SOUNDER];
// the following static init block sets the class temp/rad constants
static {
imager10FK1[0] = 0.00000E0f;
imager10FK1[1] = 0.19841E6f;
imager10FK1[2] = 0.39086E5f;
imager10FK1[3] = 0.97744E4f;
imager10FK1[4] = 0.68286E4f;
sounder10FK1[0] = 0.37305E4f;
sounder10FK1[1] = 0.40039E4f;
sounder10FK1[2] = 0.43124E4f;
sounder10FK1[3] = 0.46616E4f;
sounder10FK1[4] = 0.49734E4f;
sounder10FK1[5] = 0.58698E4f;
sounder10FK1[6] = 0.68161E4f;
sounder10FK1[7] = 0.89404E4f;
sounder10FK1[8] = 0.12973E5f;
sounder10FK1[9] = 0.28708E5f;
sounder10FK1[10] = 0.34401E5f;
sounder10FK1[11] = 0.43086E5f;
sounder10FK1[12] = 0.12468E6f;
sounder10FK1[13] = 0.12882E6f;
sounder10FK1[14] = 0.13532E6f;
sounder10FK1[15] = 0.16853E6f;
sounder10FK1[16] = 0.18862E6f;
sounder10FK1[17] = 0.22487E6f;
imager10FK2[0] = 0.00000E0f;
imager10FK2[1] = 0.36745E4f;
imager10FK2[2] = 0.21381E4f;
imager10FK2[3] = 0.13470E4f;
imager10FK2[4] = 0.11953E4f;
sounder10FK2[0] = 0.97710E3f;
sounder10FK2[1] = 0.10004E4f;
sounder10FK2[2] = 0.10255E4f;
sounder10FK2[3] = 0.10524E4f;
sounder10FK2[4] = 0.10754E4f;
sounder10FK2[5] = 0.11365E4f;
sounder10FK2[6] = 0.11945E4f;
sounder10FK2[7] = 0.13076E4f;
sounder10FK2[8] = 0.14804E4f;
sounder10FK2[9] = 0.19291E4f;
sounder10FK2[10] = 0.20490E4f;
sounder10FK2[11] = 0.22087E4f;
sounder10FK2[12] = 0.31474E4f;
sounder10FK2[13] = 0.31818E4f;
sounder10FK2[14] = 0.32345E4f;
sounder10FK2[15] = 0.34800E4f;
sounder10FK2[16] = 0.36131E4f;
sounder10FK2[17] = 0.38311E4f;
imager10TC1[0] = 0.00000f;
imager10TC1[1] = 0.62226f;
imager10TC1[2] = 0.61438f;
imager10TC1[3] = 0.27791f;
imager10TC1[4] = 0.21145f;
sounder10TC1[0] = 0.00988f;
sounder10TC1[1] = 0.01196f;
sounder10TC1[2] = 0.01245f;
sounder10TC1[3] = 0.01245f;
sounder10TC1[4] = 0.01366f;
sounder10TC1[5] = 0.04311f;
sounder10TC1[6] = 0.13973f;
sounder10TC1[7] = 0.11707f;
sounder10TC1[8] = 0.03979f;
sounder10TC1[9] = 0.14968f;
sounder10TC1[10] = 0.27603f;
sounder10TC1[11] = 0.13049f;
sounder10TC1[12] = 0.02008f;
sounder10TC1[13] = 0.01834f;
sounder10TC1[14] = 0.02017f;
sounder10TC1[15] = 0.05292f;
sounder10TC1[16] = 0.05330f;
sounder10TC1[17] = 0.28683f;
imager10TC2[0] = 0.00000f;
imager10TC2[1] = 0.99912f;
imager10TC2[2] = 0.99857f;
imager10TC2[3] = 0.99905f;
imager10TC2[4] = 0.99919f;
sounder10TC2[0] = 0.99995f;
sounder10TC2[1] = 0.99994f;
sounder10TC2[2] = 0.99994f;
sounder10TC2[3] = 0.99995f;
sounder10TC2[4] = 0.99994f;
sounder10TC2[5] = 0.99983f;
sounder10TC2[6] = 0.99947f;
sounder10TC2[7] = 0.99959f;
sounder10TC2[8] = 0.99988f;
sounder10TC2[9] = 0.99962f;
sounder10TC2[10] = 0.99933f;
sounder10TC2[11] = 0.99970f;
sounder10TC2[12] = 0.99997f;
sounder10TC2[13] = 0.99997f;
sounder10TC2[14] = 0.99997f;
sounder10TC2[15] = 0.99992f;
sounder10TC2[16] = 0.99992f;
sounder10TC2[17] = 0.99961f;
}
/**
*
* constructor
*
* @param dis data input stream
* @param ad AncillaryData object
* @param calBlock calibration parameters array
*
*/
public CalibratorGvarG10(DataInputStream dis, AncillaryData ad, int [] cb)
throws IOException
{
super(dis, ad, cb);
}
public CalibratorGvarG10(int sensorId, int[] cb) {
super(sensorId, cb);
}
/**
*
* calibrate from radiance to temperature
*
* @param inVal input data value
* @param band channel/band number
* @param sId sensor id number
*
*/
public float radToTemp(float inVal, int band, int sId) {
double expn;
double temp;
float outVal;
if ((sId % 2) == 0) {
expn = (imager10FK1[band - 1] / inVal) + 1.0;
temp = imager10FK2[band - 1] / Math.log(expn);
outVal = (float) ((temp - imager10TC1[band - 1]) / imager10TC2[band - 1]);
} else {
expn = (sounder10FK1[band - 1] / inVal) + 1.0;
temp = sounder10FK2[band - 1] / Math.log(expn);
outVal = (float)
((temp - sounder10TC1[band - 1]) / sounder10TC2[band - 1]);
}
return (outVal);
}
}

View file

@ -1,138 +0,0 @@
//
// CalibratorGvarG12.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
import edu.wisc.ssec.mcidas.AncillaryData;
/**
* CalibratorGvarG12 creates a Calibrator object designed specifically
* to deal with GOES 10 data. Not fully implemented at present - some
* calibrations remain to be done. It provides all the constants
* specific to the GOES 10 imager and sounder sensors.
*
* @version 1.3 6 Aug 1999
* @author Tommy Jasmin, SSEC
*/
public class CalibratorGvarG12 extends CalibratorGvar {
// the following static init block sets the class temp/rad constants
protected static float [] imager12FK1 = {0.f, 0.20096E6f, 0.43702E5f, 0.96859E4f, 0.50471E4f};
protected static float [] sounder12FK1 =
{0.37778E4f, 0.40086E4f, 0.43085E4f,
0.47041E4f, 0.50134E4f, 0.58645E4f,
0.69071E4f, 0.90388E4f, 0.12972E5f,
0.28931E5f, 0.34531E5f, 0.43340E5f,
0.12492E6f, 0.12822E6f, 0.13535E6f,
0.16981E6f, 0.18954E6f, 0.22538E6f};
protected static float [] imager12FK2 = {0.f, 0.36902E4f,0.22191E4f,0.13430E4f,0.10807E4f};
protected static float [] sounder12FK2 =
{0.98121E3f, 0.10008E4f, 0.10252E4f,
0.10556E4f, 0.10783E4f, 0.11361E4f,
0.11998E4f, 0.13124E4f, 0.14803E4f,
0.19340E4f, 0.20516E4f, 0.22130E4f,
0.31494E4f, 0.31769E4f, 0.32347E4f,
0.34888E4f, 0.36189E4f, 0.38340E4f};
protected static float [] imager12TC1 = {0.f, .69703f, 5.08315f, .37554f, .09537f};
protected static float [] sounder12TC1 =
{.01010f, .01252f, .01229f,
.01189f, .01264f, .04189f,
.13474f, .12341f, .03844f,
.15764f, .27420f, .13683f,
.02124f, .01780f, .02037f,
.04933f, .05386f, .28872f};
protected static float [] imager12TC2 = {0.f, .99902f, .98872f, .99872f, .99960f};
protected static float [] sounder12TC2 =
{.99995f, .99994f, .99994f,
.99995f, .99995f, .99983f,
.99949f, .99957f, .99988f,
.99960f, .99934f, .99969f,
.99996f, .99997f, .99997f,
.99993f, .99992f, .99961f};
/**
*
* constructor
*
* @param dis data input stream
* @param ad AncillaryData object
* @param calBlock calibration parameters array
*
*/
public CalibratorGvarG12(DataInputStream dis, AncillaryData ad, int [] cb)
throws IOException
{
super(dis, ad, cb);
}
public CalibratorGvarG12(int sensorId, int[] cb) {
super(sensorId, cb);
}
/**
*
* calibrate from radiance to temperature
*
* @param inVal input data value
* @param band channel/band number
* @param sId sensor id number
*
*/
public float radToTemp(float inVal, int band, int sId) {
double expn;
double temp;
float outVal;
if ((sId % 2) == 0) {
expn = (imager12FK1[band - 1] / inVal) + 1.0;
temp = imager12FK2[band - 1] / Math.log(expn);
outVal = (float) ((temp - imager12TC1[band - 1]) / imager12TC2[band - 1]);
} else {
expn = (sounder12FK1[band - 1] / inVal) + 1.0;
temp = sounder12FK2[band - 1] / Math.log(expn);
outVal = (float)
((temp - sounder12TC1[band - 1]) / sounder12TC2[band - 1]);
}
return (outVal);
}
}

View file

@ -1,140 +0,0 @@
//
// CalibratorGvarG13.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
import edu.wisc.ssec.mcidas.AncillaryData;
/**
* CalibratorGvarG13 creates a Calibrator object designed specifically
* to deal with GOES 13 data. Not fully implemented at present - some
* calibrations remain to be done. It provides all the constants
* specific to the GOES 13 imager and sounder sensors.
*
* @version 1.3 6 Aug 1999
* @author Tommy Jasmin, SSEC
*/
public class CalibratorGvarG13 extends CalibratorGvar {
// the following static init block sets the class temp/rad constants
protected static float [] imager13FK1 = {0.f, 0.20075E6f, 0.42508E5f, 0.98050E4f, 0.50173E4f};
protected static float [] sounder13FK1 =
{0.37330E4f, 0.40351E4f, 0.42661E4f,
0.46920E4f, 0.49953E4f, 0.58021E4f,
0.68338E4f, 0.89420E4f, 0.13042E5f,
0.28772E5f, 0.34368E5f, 0.42901E5f,
0.12513E6f, 0.12812E6f, 0.13482E6f,
0.16892E6f, 0.18938E6f, 0.22608E6f};
protected static float [] imager13FK2 = {0.f, 0.36890E4f, 0.21987E4f, 0.13484E4f, 0.10786E4f};
protected static float [] sounder13FK2 =
{0.97732E3f, 0.10030E4f, 0.10218E4f,
0.10547E4f, 0.10770E4f, 0.11321E4f,
0.11956E4f, 0.13077E4f, 0.14830E4f,
0.19305E4f, 0.20483E4f, 0.22055E4f,
0.31512E4f, 0.31761E4f, 0.32305E4f,
0.34826E4f, 0.36179E4f, 0.38380E4f};
protected static float [] imager13TC1 = {0.f, 1.47950f, 3.96964f, .36350f, .09502f};
protected static float [] sounder13TC1 =
{.00944f, .01022f, .01011f,
.01291f, .01353f, .04272f,
.12493f, .12033f, .03838f,
.15609f, .28000f, .18057f,
.01799f, .01809f, .02012f,
.05092f, .05740f, .29874f};
protected static float [] imager13TC2 = {0.f, .99794f, .99112f, .99876f, .99960f};
protected static float [] sounder13TC2 =
{.99996f, .99995f, .99995f,
.99994f, .99994f, .99983f,
.99952f, .99958f, .99988f,
.99961f, .99932f, .99959f,
.99997f, .99997f, .99997f,
.99992f, .99992f, .99959f};
/**
*
* constructor
*
* @param dis data input stream
* @param ad AncillaryData object
* @param calBlock calibration parameters array
*
*/
public CalibratorGvarG13(DataInputStream dis, AncillaryData ad, int [] cb)
throws IOException
{
super(dis, ad, cb);
}
public CalibratorGvarG13(int sensorId, int[] cb) {
super(sensorId, cb);
}
/**
*
* calibrate from radiance to temperature
*
* @param inVal input data value
* @param band channel/band number
* @param sId sensor id number
*
*/
public float radToTemp(float inVal, int band, int sId) {
double expn;
double temp;
float outVal;
if ((sId % 2) == 0) {
expn = (imager13FK1[band - 1] / inVal) + 1.0;
temp = imager13FK2[band - 1] / Math.log(expn);
outVal = (float) ((temp - imager13TC1[band - 1]) / imager13TC2[band - 1]);
} else {
expn = (sounder13FK1[band - 1] / inVal) + 1.0;
temp = sounder13FK2[band - 1] / Math.log(expn);
outVal = (float)
((temp - sounder13TC1[band - 1]) / sounder13TC2[band - 1]);
}
return (outVal);
}
}

View file

@ -1,208 +0,0 @@
//
// CalibratorGvarG8.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
/**
* CalibratorGvarG8 creates a Calibrator object designed specifically
* to deal with GOES 8 data. Not fully implemented at present - some
* calibrations remain to be done. It provides all the constants
* specific to the GOES 8 imager and sounder sensors.
*
* @version 1.4 6 Aug 1999
* @author Tommy Jasmin, SSEC
*/
public class CalibratorGvarG8 extends CalibratorGvar {
protected static float [] imager8FK1 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder8FK1 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager8FK2 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder8FK2 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager8TC1 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder8TC1 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager8TC2 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder8TC2 = new float[NUM_BANDS_SOUNDER];
// the following static init block sets the class temp/rad constants
static {
imager8FK1[0] = 0.0000000E0f;
imager8FK1[1] = 0.1999862E6f;
imager8FK1[2] = 0.3879239E5f;
imager8FK1[3] = 0.9737930E4f;
imager8FK1[4] = 0.6944640E4f;
sounder8FK1[0] = 0.3756810E4f;
sounder8FK1[1] = 0.4011100E4f;
sounder8FK1[2] = 0.4296870E4f;
sounder8FK1[3] = 0.4681130E4f;
sounder8FK1[4] = 0.4975250E4f;
sounder8FK1[5] = 0.5881410E4f;
sounder8FK1[6] = 0.6787440E4f;
sounder8FK1[7] = 0.8873710E4f;
sounder8FK1[8] = 0.1299794E5f;
sounder8FK1[9] = 0.2862932E5f;
sounder8FK1[10] = 0.3424830E5f;
sounder8FK1[11] = 0.4311430E5f;
sounder8FK1[12] = 0.1242353E6f;
sounder8FK1[13] = 0.1281235E6f;
sounder8FK1[14] = 0.1351482E6f;
sounder8FK1[15] = 0.1691671E6f;
sounder8FK1[16] = 0.1882350E6f;
sounder8FK1[17] = 0.2257944E6f;
imager8FK2[0] = 0.0000000E0f;
imager8FK2[1] = 0.3684270E4f;
imager8FK2[2] = 0.2132720E4f;
imager8FK2[3] = 0.1345370E4f;
imager8FK2[4] = 0.1201990E4f;
sounder8FK2[0] = 0.3765120E4f;
sounder8FK2[1] = 0.3981160E4f;
sounder8FK2[2] = 0.4281880E4f;
sounder8FK2[3] = 0.4678910E4f;
sounder8FK2[4] = 0.4962590E4f;
sounder8FK2[5] = 0.5860420E4f;
sounder8FK2[6] = 0.6770320E4f;
sounder8FK2[7] = 0.8958910E4f;
sounder8FK2[8] = 0.1296593E5f;
sounder8FK2[9] = 0.2839828E5f;
sounder8FK2[10] = 0.3420134E5f;
sounder8FK2[11] = 0.4252514E5f;
sounder8FK2[12] = 0.1240574E6f;
sounder8FK2[13] = 0.1280114E6f;
sounder8FK2[14] = 0.1348497E6f;
sounder8FK2[15] = 0.1678142E6f;
sounder8FK2[16] = 0.1888012E6f;
sounder8FK2[17] = 0.2258565E6f;
imager8TC1[0] = 0.0000000E0f;
imager8TC1[1] = 0.6357000E0f;
imager8TC1[2] = 0.6060000E0f;
imager8TC1[3] = 0.3735000E0f;
imager8TC1[4] = 0.2217000E0f;
sounder8TC1[0] = 0.1230000E-1f;
sounder8TC1[1] = 0.1330000E-1f;
sounder8TC1[2] = 0.1860000E-1f;
sounder8TC1[3] = 0.1500000E-1f;
sounder8TC1[4] = 0.1650000E-1f;
sounder8TC1[5] = 0.4740000E-1f;
sounder8TC1[6] = 0.1318000E0f;
sounder8TC1[7] = 0.1200000E0f;
sounder8TC1[8] = 0.4260000E-1f;
sounder8TC1[9] = 0.1505000E0f;
sounder8TC1[10] = 0.2743000E0f;
sounder8TC1[11] = 0.1447000E0f;
sounder8TC1[12] = 0.2240000E-1f;
sounder8TC1[13] = 0.2200000E-1f;
sounder8TC1[14] = 0.2170000E-1f;
sounder8TC1[15] = 0.5790000E-1f;
sounder8TC1[16] = 0.6230000E-1f;
sounder8TC1[17] = 0.3675000E0f;
imager8TC2[0] = 0.0000000E0f;
imager8TC2[1] = 0.9991000E0f;
imager8TC2[2] = 0.9986000E0f;
imager8TC2[3] = 0.9987000E0f;
imager8TC2[4] = 0.9992000E0f;
sounder8TC2[0] = 0.9999000E0f;
sounder8TC2[1] = 0.9999000E0f;
sounder8TC2[2] = 0.9999000E0f;
sounder8TC2[3] = 0.9999000E0f;
sounder8TC2[4] = 0.9999000E0f;
sounder8TC2[5] = 0.9998000E0f;
sounder8TC2[6] = 0.9995000E0f;
sounder8TC2[7] = 0.9996000E0f;
sounder8TC2[8] = 0.9999000E0f;
sounder8TC2[9] = 0.9996000E0f;
sounder8TC2[10] = 0.9993000E0f;
sounder8TC2[11] = 0.9997000E0f;
sounder8TC2[12] = 0.1000000E1f;
sounder8TC2[13] = 0.1000000E1f;
sounder8TC2[14] = 0.1000000E1f;
sounder8TC2[15] = 0.9999000E0f;
sounder8TC2[16] = 0.9999000E0f;
sounder8TC2[17] = 0.9995000E0f;
}
/**
*
* constructor
*
* @param dis data input stream
* @param ad AncillaryData object
* @param calBlock calibration parameters array
*
*/
public CalibratorGvarG8(DataInputStream dis, AncillaryData ad, int [] cb)
throws IOException
{
super(dis, ad, cb);
}
public CalibratorGvarG8(final int id, final int[] cal) {
super(id, cal);
}
/**
*
* calibrate from radiance to temperature
*
* @param inVal input data value
* @param band channel/band number
* @param sId sensor id number
*
*/
public float radToTemp(float inVal, int band, int sId) {
double expn;
double temp;
float outVal;
if ((sId % 2) == 0) {
expn = (imager8FK1[band - 1] / inVal) + 1.0;
temp = imager8FK2[band - 1] / Math.log(expn);
outVal = (float) ((temp - imager8TC1[band - 1]) / imager8TC2[band - 1]);
} else {
expn = (sounder8FK1[band - 1] / inVal) + 1.0;
temp = sounder8FK2[band - 1] / Math.log(expn);
outVal = (float) ((temp - sounder8TC1[band - 1]) / sounder8TC2[band - 1]);
}
return (outVal);
}
}

View file

@ -1,208 +0,0 @@
//
// CalibratorGvarG9.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.io.DataInputStream;
import java.io.IOException;
import java.lang.String;
/**
* CalibratorGvarG9 creates a Calibrator object designed specifically
* to deal with GOES 9 data. Not fully implemented at present - some
* calibrations remain to be done. It provides all the constants
* specific to the GOES 9 imager and sounder sensors.
*
* @version 1.3 6 Aug 1999
* @author Tommy Jasmin, SSEC
*/
public class CalibratorGvarG9 extends CalibratorGvar {
protected static float [] imager9FK1 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder9FK1 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager9FK2 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder9FK2 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager9TC1 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder9TC1 = new float[NUM_BANDS_SOUNDER];
protected static float [] imager9TC2 = new float[NUM_BANDS_IMAGER];
protected static float [] sounder9TC2 = new float[NUM_BANDS_SOUNDER];
// the following static init block sets the class temp/rad constants
static {
imager9FK1[0] = 0.0000000E0f;
imager9FK1[1] = 0.1988078E6f;
imager9FK1[2] = 0.3873241E5f;
imager9FK1[3] = 0.9717210E4f;
imager9FK1[4] = 0.6899470E4f;
sounder9FK1[0] = 0.3765120E4f;
sounder9FK1[1] = 0.3981160E4f;
sounder9FK1[2] = 0.4281880E4f;
sounder9FK1[3] = 0.4678910E4f;
sounder9FK1[4] = 0.4962590E4f;
sounder9FK1[5] = 0.5860420E4f;
sounder9FK1[6] = 0.6770320E4f;
sounder9FK1[7] = 0.8958910E4f;
sounder9FK1[8] = 0.1296593E5f;
sounder9FK1[9] = 0.2839828E5f;
sounder9FK1[10] = 0.3420134E5f;
sounder9FK1[11] = 0.4252514E5f;
sounder9FK1[12] = 0.1240574E6f;
sounder9FK1[13] = 0.1280114E6f;
sounder9FK1[14] = 0.1348497E6f;
sounder9FK1[15] = 0.1678142E6f;
sounder9FK1[16] = 0.1888012E6f;
sounder9FK1[17] = 0.2258565E6f;
imager9FK2[0] = 0.0000000E0f;
imager9FK2[1] = 0.3677020E4f;
imager9FK2[2] = 0.2131620E4f;
imager9FK2[3] = 0.1344410E4f;
imager9FK2[4] = 0.1199380E4f;
sounder9FK2[0] = 0.9801200E3f;
sounder9FK2[1] = 0.9985200E3f;
sounder9FK2[2] = 0.1023050E4f;
sounder9FK2[3] = 0.1053740E4f;
sounder9FK2[4] = 0.1074620E4f;
sounder9FK2[5] = 0.1135870E4f;
sounder9FK2[6] = 0.1191850E4f;
sounder9FK2[7] = 0.1308490E4f;
sounder9FK2[8] = 0.1480080E4f;
sounder9FK2[9] = 0.1922130E4f;
sounder9FK2[10] = 0.2045030E4f;
sounder9FK2[11] = 0.2199040E4f;
sounder9FK2[12] = 0.3142140E4f;
sounder9FK2[13] = 0.3175180E4f;
sounder9FK2[14] = 0.3230740E4f;
sounder9FK2[15] = 0.3475050E4f;
sounder9FK2[16] = 0.3614260E4f;
sounder9FK2[17] = 0.3836740E4f;
imager9TC1[0] = 0.0000000E0f;
imager9TC1[1] = 0.5864000E0f;
imager9TC1[2] = 0.4841000E0f;
imager9TC1[3] = 0.3622000E0f;
imager9TC1[4] = 0.2014000E0f;
sounder9TC1[0] = 0.9900000E-2f;
sounder9TC1[1] = 0.1190000E-1f;
sounder9TC1[2] = 0.1220000E-1f;
sounder9TC1[3] = 0.1190000E-1f;
sounder9TC1[4] = 0.1350000E-1f;
sounder9TC1[5] = 0.4400000E-1f;
sounder9TC1[6] = 0.1345000E0f;
sounder9TC1[7] = 0.1193000E0f;
sounder9TC1[8] = 0.4070000E-1f;
sounder9TC1[9] = 0.1438000E0f;
sounder9TC1[10] = 0.2762000E0f;
sounder9TC1[11] = 0.1370000E0f;
sounder9TC1[12] = 0.1890000E-1f;
sounder9TC1[13] = 0.1980000E-1f;
sounder9TC1[14] = 0.1910000E-1f;
sounder9TC1[15] = 0.5310000E-1f;
sounder9TC1[16] = 0.6120000E-1f;
sounder9TC1[17] = 0.3042000E0f;
imager9TC2[0] = 0.0000000E0f;
imager9TC2[1] = 0.9992000E0f;
imager9TC2[2] = 0.9989000E0f;
imager9TC2[3] = 0.9988000E0f;
imager9TC2[4] = 0.9992000E0f;
sounder9TC2[0] = 0.1000000E1f;
sounder9TC2[1] = 0.9999000E0f;
sounder9TC2[2] = 0.9999000E0f;
sounder9TC2[3] = 0.9999000E0f;
sounder9TC2[4] = 0.9999000E0f;
sounder9TC2[5] = 0.9998000E0f;
sounder9TC2[6] = 0.9995000E0f;
sounder9TC2[7] = 0.9996000E0f;
sounder9TC2[8] = 0.9999000E0f;
sounder9TC2[9] = 0.9996000E0f;
sounder9TC2[10] = 0.9993000E0f;
sounder9TC2[11] = 0.9997000E0f;
sounder9TC2[12] = 0.1000000E1f;
sounder9TC2[13] = 0.1000000E1f;
sounder9TC2[14] = 0.1000000E1f;
sounder9TC2[15] = 0.9999000E0f;
sounder9TC2[16] = 0.9999000E0f;
sounder9TC2[17] = 0.9996000E0f;
}
/**
*
* constructor
*
* @param dis data input stream
* @param ad AncillaryData object
* @param calBlock calibration parameters array
*
*/
public CalibratorGvarG9(DataInputStream dis, AncillaryData ad, int [] cb)
throws IOException
{
super(dis, ad, cb);
}
public CalibratorGvarG9(final int id, final int[] cal) {
super(id, cal);
}
/**
*
* calibrate from radiance to temperature
*
* @param inVal input data value
* @param band channel/band number
* @param sId sensor id number
*
*/
public float radToTemp(float inVal, int band, int sId) {
double expn;
double temp;
float outVal;
if ((sId % 2) == 0) {
expn = (imager9FK1[band - 1] / inVal) + 1.0;
temp = imager9FK2[band - 1] / Math.log(expn);
outVal = (float) ((temp - imager9TC1[band - 1]) / imager9TC2[band - 1]);
} else {
expn = (sounder9FK1[band - 1] / inVal) + 1.0;
temp = sounder9FK2[band - 1] / Math.log(expn);
outVal = (float) ((temp - sounder9TC1[band - 1]) / sounder9TC2[band - 1]);
}
return (outVal);
}
}

View file

@ -1,440 +0,0 @@
//
// CalibratorMsg.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Calibration routines for the Meteosat Second Generation (MSG) instrument.
* <p>
* At the time this module was written the
* <a href="http://www.ssec.wisc.edu/mcidas/doc/prog_man/2006/">
* McIDAS documentation
* </a> for the <a href="http://www.esa.int/SPECIALS/MSG/">MSG Instrument</a>
* did not reflect that calibration data is now stored by band in the
* calibration block.
* </p>
* <p>
* Current understanding is that an MSG ASCII calibration block should be
* prefixed by the string MSGT followed by the following 6 values for the
* Inverse Planck Funciton corresponding to each band:
* <br/><br/>
* <table border="1" cellpadding="2">
* <tr><th>Name</th><th>Calculation</th><th>Units</th></tr>
* <tr><td><b>C1W3</b></td><td colspan="2">C1 * W^3</td></tr>
* <tr><td></td><td>C1 = 2.0e5 * P * C^2</td><td>radiance/(cm^-1)^3)</td></tr>
* <tr><td></td><td>W = 1.0e2 * (band wave numbers)</td><td>(cm^-1)</td></tr>
* <tr><td><b>C2W</b></td><td colspan="2">C2 * W</td></tr>
* <tr><td></td><td>C2 = P * C / B</td><td>K/(cm^-1)</td></tr>
* <tr><td></td><td>W = 1.0e2 * (band wave numbers)</td><td>(cm^-1)</td></tr>
* <tr><td><b>ALPHA</b></td><td colspan="2">gain adjustment</td></tr>
* <tr><td><b>BETA</b></td><td colspan="2">bias adjustment</td></tr>
* <tr><td><b>GAIN</b></td><td colspan="2">gain</td></tr>
* <tr><td><b>OFFSET</b></td><td colspan="2">offset</td></tr>
* </table>
* <br/>
* Where C = speed of light, P = planck constant, B = Boltzmann constant.
* </p>
* <p>
* Each string value is 17 characters with 10 decimal places (fortran E17.10),
* and should be parseable using <code>Double.parseDouble</code>. After
* converting cal block from ints to a string calibration values for the first
* band, including the header should look like:
* </p>
* <p>
* <i>MSGT 0.0000000000E+00 0.0000000000E+00 0.0000000000E+00 0.0000000000E+00
* 0.2312809974E-01-0.1179533087E+01</i>
* </p>
* @author Bruce Flynn, SSEC
* @version $Id: CalibratorMsg.java,v 1.7 2009-03-02 23:34:50 curtis Exp $
*/
public class CalibratorMsg implements Calibrator {
private static final int C1W3 = 0;
private static final int C2W = 1;
private static final int ALPHA = 2;
private static final int BETA = 3;
private static final int GAIN = 4;
private static final int OFFSET = 5;
/** Size of cal block values (fortran E17.10 format code). */
private static final int FMT_SIZE = 17;
/** Size of a band in the cal block in bytes. */
private static final int BAND_SIZE = 103;
/** Size of the cal block header in bytes. */
private static final int HDR_SIZE = 4;
/** Cal block header string. */
private static final String HEADER = "MSGT";
/** Coefficients for individual bands. */
private final float[] bandCoefs = new float[] {
21.21f,
23.24f,
19.77f,
0f,
0f,
0f,
0f,
0f,
0f,
0f,
0f,
22.39f
};
/** Coefficients used in the inverse planck function. */
private final double[][] planckCoefs;
/** Cal block converted from an int array. */
private byte[] calBytes;
/**
* Current cal type as set by <code>setCalType</code>
*/
private int curCalType = CAL_RAW;
/**
* Construct this object according to the calibration data provided.
* On initalization the calibration array is cloned and all bands available
* are read from the block.
*
* @param cal calibration block from an MSG AREA file.
* @throws CalibratorException on invalid calibration block.
*/
public CalibratorMsg(final int[] cal) throws CalibratorException {
int[] calBlock = (int[]) cal.clone();
// convert int[] to bytes
calBytes = calIntsToBytes(calBlock);
// if the header is incorrect, flip and try again
String msgt = new String(calBytes, 0, 4);
if (!msgt.equals(HEADER)) {
McIDASUtil.flip(calBlock, 0, calBlock.length - 1);
calBytes = calIntsToBytes(calBlock);
msgt = new String(calBytes, 0, 4);
if (!msgt.equals(HEADER)) {
throw new IllegalArgumentException(
"Invalid calibration block header: " + msgt
);
}
}
planckCoefs = getCalCoefs();
}
/**
*
* @param coefs
* @throws CalibratorException
*/
public CalibratorMsg(final double[][] coefs) throws CalibratorException {
planckCoefs = coefs;
}
/**
* Set the input data calibration type.
*
* @param calType calibration type from <code>Calibrator</code>
* @return 0 if calibration type is valid, -1 otherwise.
*/
public int setCalType(int calType) {
if ((calType < Calibrator.CAL_MIN) || (calType > Calibrator.CAL_MAX)) {
return -1;
}
curCalType = calType;
return 0;
}
/**
* Calibrate an array of pixels from the current calibration type according
* to the parameters provided.
*
* @param input pixel array to calibrate.
* @param band channel for which to perform calibration.
* @param calTypeOut Calibration type constant.
* @return calibrated pixel value or <code>Float.NaN</code> if the
* calibration type cannot be performed for the specified band.
*/
public float[] calibrate(final float[] input, final int band,
final int calTypeOut) {
if (calTypeOut == curCalType || calTypeOut == CAL_NONE) { // no-op
return (float[])input.clone();
}
float[] output = new float[input.length];
for (int i = 0; i < input.length; i++) {
output[i] = calibrate(input[i], band, calTypeOut);
}
return output;
}
/**
* Calibrate a pixel from the current calibration type according to the
* parameters provided.
*
* @param inputPixel pixel value to calibrate.
* @param band channel for which to perform calibration.
* @param calTypeOut Calibration type constant.
* @return calibrated pixel value or <code>Float.NaN</code> if the
* calibration type cannot be performed for the specified band.
*/
public float calibrate(
final float inputPixel,
final int band,
final int calTypeOut) {
float pxl;
if (calTypeOut == curCalType || calTypeOut == CAL_NONE) { // no-op
return inputPixel;
}
switch (curCalType) {
case CAL_ALB:
throw new UnsupportedOperationException(
"Calibration from reflectance not implemented"
);
case CAL_TEMP:
throw new UnsupportedOperationException(
"Calibration from temperature not implemented"
);
case CAL_BRIT:
throw new UnsupportedOperationException(
"Calibration from brightness not implemented"
);
case CAL_RAD:
throw new UnsupportedOperationException(
"Calibration from radiance not implemented"
);
case CAL_RAW:
pxl = calibrateFromRaw(inputPixel, band, calTypeOut);
break;
default:
throw new IllegalArgumentException(
"Unknown calibration type"
);
}
return pxl;
}
/**
* Calibrate a pixel from RAW data according to the parameters provided.
*
* @param inputPixel pixel value to calibrate.
* @param band channel for which to perform calibration.
* @param calTypeOut Calibration type constant.
* @return calibrated pixel value, <code>Float.NaN</code> if the
* calibration type cannot be performed for the specified band.
*/
public float calibrateFromRaw(
final float inputPixel,
final int band,
final int calTypeOut) {
if (calTypeOut == CAL_RAW || calTypeOut == CAL_NONE) { // no-op
return inputPixel;
}
double[] coefs = planckCoefs[band - 1];
double pxl = inputPixel * coefs[GAIN] + coefs[OFFSET];
if (pxl < 0) {
pxl = 0.0;
}
// Visible and near-visible (VIS006, VIS008, IR016, HRV)
if (band < 4 || band == 12) {
switch (calTypeOut) {
case CAL_TEMP: // can't do temp
pxl = Double.NaN;
break;
case CAL_RAD: // radiance
break;
case CAL_ALB: // reflectance
pxl = (pxl / bandCoefs[band-1]) * 100.0;
if (pxl < 0) {
pxl = 0.0;
} else if (pxl > 100) {
pxl = 100.0;
}
break;
case CAL_BRIT: // brightness
pxl = (pxl / bandCoefs[band-1]) * 100.0;
if (pxl < 0) {
pxl = 0.0;
} else if (pxl > 100) {
pxl = 100.0;
}
pxl = Math.sqrt(pxl) * 25.5;
break;
default:
throw new IllegalArgumentException(
"Unknown calibration type: " + calTypeOut
);
}
// IR Channel
} else {
switch (calTypeOut) {
case CAL_TEMP: // temperature
if (pxl > 0) {
pxl = (coefs[C2W] / Math.log(1.0 + coefs[C1W3] / pxl)
- coefs[BETA]) / coefs[ALPHA];
}
break;
case CAL_RAD: // radiance
break;
case CAL_ALB: // can't do reflectance
pxl = Double.NaN;
break;
case CAL_BRIT: // brightness
if (pxl > 0) {
pxl = (coefs[C2W] / Math.log(1.0 + coefs[C1W3] / pxl)
- coefs[BETA]) / coefs[ALPHA];
pxl = greyScale(pxl);
} else {
pxl = 255.0;
}
break;
default:
throw new IllegalArgumentException(
"Unsupported calibration type: " + calTypeOut
);
}
}
return (float) pxl;
}
/**
* Convert a brightness temperature to grey scale.
*
* @param val temperature value in kelvin.
* @return brightness value.
*/
private double greyScale(final double val) {
final int tempLim = 242;
final int c1 = 418;
final int c2 = 660;
double ret;
if (val < tempLim) {
ret = Math.min(c1 - val, 255);
} else {
ret = Math.max(c2 - 2 * val, 0);
}
return ret;
}
/**
* Get cal block coefs, converting from bytes to strings.
*
* @return array of cal coefs by band.
* @throws CalibratorExcpetion when unable to parse calibration block.
*/
private double[][] getCalCoefs() throws CalibratorException {
double[][] coefs = new double[12][6];
for (int i = 0; i < coefs.length; i++) {
// add 1 to band size for extra whitespace between bands
final int bandOffset = (i * (BAND_SIZE + 1)) + HDR_SIZE;
String[] strVals = getBandVals(
new String(calBytes, bandOffset, BAND_SIZE)
);
try {
coefs[i][C1W3] = Double.parseDouble(strVals[0]);
coefs[i][C2W] = Double.parseDouble(strVals[1]);
coefs[i][ALPHA] = Double.parseDouble(strVals[2]);
coefs[i][BETA] = Double.parseDouble(strVals[3]);
coefs[i][GAIN] = Double.parseDouble(strVals[4]);
coefs[i][OFFSET] = Double.parseDouble(strVals[5]);
} catch (NumberFormatException e) {
throw new CalibratorException(
"Unable to parse values from calibration block for band "
+ (i + 1)
);
}
}
return coefs;
}
/**
* Split a line corresponding to a single band in the calibration block
* into <code>String</code>s. There are some additional operations
* performed to identify and correct an issue where some signed values
* were not separated by whitespace.
*
* @param line the line as mentioned above.
* @return array where each value is the string representation of a value
* from the cal block corresponding to a band.
*/
private String[] getBandVals(final String line) {
String[] strVals = new String[6];
for (int i = 0, j = 0; i < strVals.length; i++, j += FMT_SIZE) {
strVals[i] = line.substring(j, j + FMT_SIZE);
}
return strVals;
}
/**
* Convert an array of ints to an array of bytes.
*
* @param orig array of ints to convert
* @return array of bytes
*/
private byte[] calIntsToBytes(final int[] orig) {
byte[] bites = new byte[orig.length * 4];
for (int i = 0, j = 0; i < orig.length; i++) {
bites[j++] = (byte) (orig[i] & 0x000000ff);
bites[j++] = (byte) ((orig[i] >> 8) & 0x000000ff);
bites[j++] = (byte) ((orig[i] >> 16) & 0x000000ff);
bites[j++] = (byte) ((orig[i] >> 24) & 0x000000ff);
}
return bites;
}
}

View file

@ -1,224 +0,0 @@
//
// ConversionUtility.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* A collection of methods for doing various conversions.
* <p>
*
* @version 1.3, 16 Nov 98
* @author Tommy Jasmin, SSEC
*/
public class ConversionUtility
{
/**
* Find the distance in km between two points given the lats/lons.
*
* @param lat1 - latitude of first point
* @param lat2 - latitude of second point
* @param lon1 - longitude of first point
* @param lon2 - longitude of second point
* @return - the distance in km between the two input points
*/
public static float LatLonToDistance (
float lat1,
float lon1,
float lat2,
float lon2
)
{
double arcl;
double cplat;
double cplon;
double crlat;
double crlon;
double dist;
double plat;
double plon;
double rlat;
double rlon;
double srlat;
double srlon;
double splat;
double splon;
double xx;
double yy;
double zz;
float r = 6371.0f;
float z = 0.017453292f;
rlat = (double) (lat1) * z;
rlon = (double) (lon1) * z;
plat = (double) (lat2) * z;
plon = (double) (lon2) * z;
crlat = Math.cos(rlat);
crlon = Math.cos(rlon);
srlat = Math.sin(rlat);
srlon = Math.sin(rlon);
cplat = Math.cos(plat);
cplon = Math.cos(plon);
splat = Math.sin(plat);
splon = Math.sin(plon);
xx = (cplat * cplon) - (crlat * crlon);
yy = (cplat * splon) - (crlat * srlon);
zz = splat - srlat;
dist = Math.sqrt((xx * xx) + (yy * yy) + (zz * zz));
arcl = 2.0 * Math.asin(dist / 2.0) * r;
return (float) (arcl);
}
/**
* Convert a latitude or longitude in dddmmss format to floating point.
*
* @param dddmmss - latitude or longitude
* @return - floating point representation of the input parameter.
*/
public static float FloatLatLon (
int dddmmss
)
{
int inVal;
float negVal;
float retVal;
if (dddmmss < 0) {
inVal = -dddmmss;
negVal = -1.0f;
} else {
inVal = dddmmss;
negVal = 1.0f;
}
retVal = (float) (inVal / 10000) +
(float) ((inVal / 100) % 100) / 60.0f +
(float) (inVal % 100) / 3600.0f;
retVal = negVal * retVal;
return (retVal);
}
/**
* Convert a Gould format floating point number to native double format
*
* @param inVal - input Gould value
* @return - the input value converted to double floating point
*/
public static double GouldToNative(int inVal) {
int sign;
int exponent;
float mant;
int byte0;
int byte1;
int byte2;
double dblMant;
double tempVal;
double nativeVal;
/*
* an example conversion:
*
* input value (hex): BE DA 4D 07
* a) convert to binary:
* 1011 1110 1101 1010 0100 1101 0000 0111
* b) sign bit is set, so take twos complement:
* 0100 0001 0010 0101 1011 0010 1111 1001
* c) convert this back to hex: 41 25 B2 F9
* d) mantissa = 2470649
* e) exponent = 65
* f) tempVal = mantissa / 16 exp (70 - 65)
* g) outputVal = tempVal * sign = -2.3561944
*
*/
// set up munging bytes
byte0 = (inVal & 0x000000FF);
byte1 = ((inVal >> 8) & 0x000000FF);
byte2 = ((inVal >> 16) & 0x000000FF);
sign = 1;
if ((inVal & 0x80000000) != 0) {
sign = -1;
inVal = -inVal;
}
exponent = ((inVal & 0x7F000000) >> 24);
if (exponent == 0) {
exponent = 64;
}
// determine the value of the mantissa, load into a double
mant = (float) (byte0 + (byte1 * 256) + (byte2 * 65536));
mant = Math.abs(mant);
dblMant = (double) mant;
// now adjust the mantissa according to the exponent
tempVal = Math.pow((double) 16, (double) (70 - exponent));
nativeVal = dblMant / tempVal;
nativeVal = nativeVal * sign;
return nativeVal;
}
/**
* swap the bytes of an integer array
*
* @param array[] array of integers to be flipped
* @param first starting element of the array
* @param last last element of array to flip
*
*/
public static void swap (int array[], int first, int last)
{
int i, k;
for (i = first; i <= last; i++) {
k = array[i];
array[i] = ( (k >>> 24) & 0xff) | ( (k >>> 8) & 0xff00) |
( (k & 0xff) << 24 ) | ( (k & 0xff00) << 8);
}
}
}

View file

@ -1,252 +0,0 @@
//
// EnhancementTable.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.awt.Color;
import java.io.DataInputStream;
import java.io.FileInputStream;
import java.io.BufferedInputStream;
import java.io.IOException;
import java.io.File;
import java.net.URL;
/**
* Class for reading a McIDAS enhancement table (.ET file). The default
* constructor creates a grey scale enhancement.
*/
public class EnhancementTable
{
private int[][] rgbValues = null;
private DataInputStream dataStream;
/**
* Construct an enhancement table with a grey scale enhancement.
*/
public EnhancementTable()
{
rgbValues = new int[3][256];
for (int i = 0; i < 3; i++)
{
for (int j = 0; j < 256; j++)
{
rgbValues[i][j] = j;
}
}
}
/**
* Construct an enhancement table from a local disk file or
* URL.
*
* @param source source of the enhancement table (path or URL)
*
* @exception McIDASException error finding or reading the source.
*/
public EnhancementTable(String source)
throws McIDASException
{
try
{
dataStream =
new DataInputStream(
new BufferedInputStream(
new FileInputStream(source)));
}
catch (Exception e)
{
try
{
dataStream =
new DataInputStream(
new BufferedInputStream(
new URL(source).openStream()));
}
catch (Exception e2)
{
throw new McIDASException(
"Unable to open enhancement table " + source);
}
}
readRGBValues();
}
/**
* Construct an enhancement table from a file object.
*
* @param file file object representing the enhancement table.
*
* @exception McIDASException error finding or reading the file.
*/
public EnhancementTable(File file)
throws McIDASException
{
try
{
dataStream =
new DataInputStream(
new BufferedInputStream(
new FileInputStream(file)));
}
catch (Exception e)
{
throw new McIDASException(
"Unable to open enhancement table " + file);
}
readRGBValues();
}
/**
* Construct an enhancement table from a remote URL object.
*
* @param url URL representing the enhancement table.
*
* @exception McIDASException error finding or reading the URL.
*/
public EnhancementTable(URL url)
throws McIDASException
{
try
{
dataStream =
new DataInputStream(
new BufferedInputStream(url.openStream()));
}
catch (Exception e)
{
throw new McIDASException(
"Unable to open enhancement table at URL" + url);
}
readRGBValues();
}
/**
* read in the values
*/
private void readRGBValues()
throws McIDASException
{
rgbValues = new int[3][256];
try
{
int reservedWord = dataStream.readInt();
for (int i = 0; i < 3; i++)
{
for (int j = 0; j < 256; j++)
rgbValues[i][j] = dataStream.readInt();
}
}
catch (Exception e)
{
throw new McIDASException("Invalid enhancement table");
}
}
/**
* Retrieve the data values.
*
* @return integer array [3][256] of red, green, blue values or null if
* the table was not initialized correctly. Values
* range from 0-255.
*/
public int[][] getRGBValues()
{
return rgbValues;
}
/**
* Look up a unique (hopefully) RGB value and return the index
*
* @return index value (0-255) or -1 if not found
*
*/
public int getIndex(int red, int green, int blue) {
int inx;
for (inx=0; inx<256; inx++) {
if (rgbValues[0][inx] == red &&
rgbValues[1][inx] == green &&
rgbValues[2][inx] == blue) {
return inx;
}
}
return -1;
}
/**
* Print out a pretty table. Currently lists all values, but will
* eventually print a format like EU TABLE.
*
* @return table of levels, red, green and blue values
*/
public String toString()
{
StringBuffer sb = new StringBuffer();
sb.append(" Brightness Red Green Blue ");
sb.append("\n");
sb.append(" min max min max min max min max");
sb.append("\n");
sb.append(" --- --- --- --- --- --- --- ---");
sb.append("\n");
for (int i = 0; i < 256; i++)
{
sb.append(" " + i + " " +
rgbValues[0][i] + " " +
rgbValues[1][i] + " " +
rgbValues[2][i]);
sb.append("\n");
}
return sb.toString();
}
/**
* Test by running:
* <UL>
* <LI>java edu.wisc.ssec.mcidas.EnhancementTable _OR_
* <LI>java edu.wisc.ssec.mcidas.EnhancementTable <i>enhancement_file</i>.
* </UL>
*/
public static void main(String[] args)
{
try
{
EnhancementTable et =
args.length == 0
? new EnhancementTable()
: new EnhancementTable(args[0]);
System.out.println(et.toString());
}
catch (McIDASException e)
{
System.out.println(e.toString());
}
}
}

View file

@ -1,213 +0,0 @@
//
// GEOSnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/*
This code ported from the original McIDAS code which contains this notice:
C Copyright(c) 2006, Space Science and Engineering Center, UW-Madison
C Refer to "McIDAS Software Acquisition and Distribution Policies"
C in the file mcidas/data/license.txt
C****************************************************************
C AUTHOR : Oscar Alonso Lasheras
C COPYRIGHT GMV S.A. 2006
C PROPERTY OF GMV S.A.; ALL RIGHTS RESERVED
C
C PROJECT : S3GICast
C FILE NAME : nvxgeos.dlm
C LANGUAGE : FORTRAN-77
C TYPE : Funcion auxliar para creacion de navegacion GEOS
C DESCRIPTION : Navega los productos MPEF y OSIS, ademas de los productos
C de los servidores FSDX y SAFN-HDF5 en McIDAS
C
*/
public class GEOSnav extends AREAnav {
private static final long serialVersionUID = 1L;
final int loff, coff, lfac, cfac, plon;
final double PI = 3.1415926535;
final double radpol = 6356.5838;
final double radeq = 6378.1690;
final double X42 = 42164.0;
private boolean isEastPositive = true;
public GEOSnav(int[] iparms) throws IllegalArgumentException {
if (iparms[0] != GEOS)
throw new IllegalArgumentException ("Invald navigation type " + iparms[0]);
loff = iparms[1];
coff = iparms[2];
lfac = iparms[3];
cfac = iparms[4];
plon = iparms[5];
}
/**
* @param latlon lat and lon of points (N and E are positive)
*/
public double[][] toLinEle(double[][] latlon) {
double xlat, xlon, xlin, xele;
double c_lat, cosc_lat, rn, r1, r2, r3, rl;
double x,y;
double lat,lon,splon;
double ad2, bd, cd, delta2, halfsom, r_eq2, r_pol2;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++) {
xlat = latlon[indexLat][point];
xlon = latlon[indexLon][point];
if (!isEastPositive) xlon = -xlon;
// --- Coordinates are computed accroding EUMETSAT's LRIT/HRIT Global Spec
// --- Doc No: CGMS 03
// --- Coordinates are converted to Radians
lat = xlat*PI/180.;
lon = xlon*PI/180.0;
splon = plon/10. * PI/180.0;
// --- Intermediate data
c_lat=Math.atan(0.993243*Math.tan(lat));
cosc_lat=Math.cos(c_lat);
r_pol2= radpol * radpol;
r_eq2 = radeq * radeq;
rl=radpol/(Math.sqrt(1-((r_eq2-r_pol2)/r_eq2)*cosc_lat*cosc_lat));
r1=X42-rl*cosc_lat*Math.cos(lon-splon);
r2=-rl*cosc_lat*Math.sin(lon-splon);
r3=rl*Math.sin(c_lat);
rn=Math.sqrt(r1*r1+r2*r2+r3*r3);
// --- Compute variables useful to check if pixel is visible
ad2 = r1*r1 + r2*r2 + r3*r3*r_eq2 / r_pol2;
bd = X42*r1;
cd = X42*X42 - r_eq2;
delta2 = bd*bd-ad2*cd;
halfsom = bd*rn/ad2;
if ((delta2 >= 0.) && (rn <= halfsom)) {
// ------- Intermediate coordinates
x = Math.atan(-r2/r1);
y = Math.asin(-r3/rn);
x = x * 180./PI;
y = y * 180./PI;
xele = coff/10. + x / Math.pow(2,16) * cfac/10.;
xlin = loff/10. + y / Math.pow(2,16) * lfac/10.;
} else {
xlin=Double.NaN;
xele=Double.NaN;
}
linele[indexLine][point] = xlin;
linele[indexEle][point] = xele;
}
return imageCoordToAreaCoord(linele, linele);
}
public double[][] toLatLon(double[][] linele) {
double xlat, xlon, xlin, xele;
double x,y;
double s1, s2, s3, sxy, sn, sd, sdd;
double aux, aux2;
double cosx, cosy, sinx, siny;
// --- Coordinates are computed accroding EUMETSAT's LRIT/HRIT Global Spec
// --- Doc No: CGMS 03
int number = linele[0].length;
double[][] latlon = new double[2][number];
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++ ) {
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
// --- Intermediate coordinates
x = (xele - coff/10.) * Math.pow(2,16) / (cfac/10.);
y = (xlin - loff/10.) * Math.pow(2,16) / (lfac/10.);
x = x * PI/180.;
y = y * PI/180.;
//c --- Intermediate data
cosx=Math.cos(x);
cosy=Math.cos(y);
sinx=Math.sin(x);
siny=Math.sin(y);
aux=X42*cosx*cosy;
aux2=cosy*cosy+1.006803*siny*siny;
sdd=aux*aux-aux2*1737121856.0;
if (sdd < 0.0) {
xlat=Double.NaN;
xlon=Double.NaN;
} else {
sd=Math.sqrt(sdd);
sn=(aux-sd)/aux2;
s1=X42 - sn*cosx*cosy;
s2=sn*sinx*cosy;
s3= -sn*siny;
sxy=Math.sqrt(s1*s1+s2*s2);
// --- Computation
xlon = Math.atan(s2/s1);
xlon = xlon * 180./PI + plon/10.;
xlat = Math.atan(1.006803*s3/sxy)* 180./PI;
// --- Longitudes in [-180,180]
if(xlon > 180.0) xlon = xlon - 360.;
if(xlon < -180.0) xlon = xlon + 360.;
}
if (!isEastPositive) xlon = -xlon;
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = xlon;
}
return latlon;
}
}

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -1,460 +0,0 @@
//
// GRIDnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* GRIDnav is the class for handling the navigation of McIDAS grids.
* It is basically a Java version of GRDDEF.FOR.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*
*/
public class GRIDnav
implements java.io.Serializable
{
static final long serialVersionUID = 8741895066356394200L;
/** Navigation type for pseudo-mercator grids */
final int PSEUDO_MERCATOR = 1;
/** Navigation type for polar stero or lambert conformal conic grids */
final int PS_OR_LAMBERT_CONIC = 2;
/** Navigation type for equidistant grids */
final int EQUIDISTANT = 3;
/** Navigation type for pseudo-mercator (general case) grids */
final int PSEUDO_MERCATOR_GENERAL = 4;
final int NO_NAV = 5;
/** Navigation type for lambert conformal tangent grids */
final int LAMBERT_CONFORMAL_TANGENT = 6;
final double EARTH_RADIUS = 6371.23;
final double xrad = Math.PI/180.;
/** "Row" index in row/column array */
public final int indexRow=1;
/** "Column" index in row/column array */
public final int indexCol=0;
/** "Latitude" index in latitude/longitude array */
public final int indexLat=0;
/** "Longitude" index in latitude/longitude array */
public final int indexLon=1;
/* Default start for grid calculations in McIDAS is (1,1) */
private int startRow = 1;
private int startColumn = 1;
/* (1,1) is located in the upper left. If lower left, it's flipped */
private boolean isRowFlipped = false;
private double rowOffset = 0.0;
/* common calculation variables */
private int navType;
private double xnr; // number of rows
private double xnc; // number of columns
private double xnrow; // number of rows for calculations
private double xncol; // number of columns for calculations
private boolean wierd = false; // JTYP = 1, navType > 10
/* Merc and pseudo_merc parameters */
private double glamx; // max latitude
private double glomx; // max longitude
private double ginct; // grid increment in latitude
private double gincn; // grid increment in longitude
/* PS and CONF projection parameters */
private double xrowi; // row # of North Pole*10000
private double xcoli; // column # of North Pole* 10000
private double xqlon; // longitude parallel to columns
private double xspace; // column spacing at standard latitude
private double xh; //
private double xfac; //
private double xblat; //
/* Equidistant params */
private double xrot; // rotation angle
private double yspace;
private double xblon;
/**
* Construct a new GRIDnav from a grid directory block
* @param gridDirBlock grid header block
* @throws McIDASException illegal grid header
*/
public GRIDnav(int[] gridDirBlock)
throws McIDASException
{
if (gridDirBlock.length != GridDirectory.DIRSIZE)
throw new McIDASException("Directory is not the right size");
int gridType = gridDirBlock[GridDirectory.NAV_BLOCK_INDEX];
navType = gridType%10;
wierd = gridType/10 == 1;
xnr = gridDirBlock[GridDirectory.ROWS_INDEX];
xnc = gridDirBlock[GridDirectory.COLS_INDEX];
xnrow = xnr;
xncol = xnc;
switch(navType)
{
case PSEUDO_MERCATOR:
case PSEUDO_MERCATOR_GENERAL:
glamx=gridDirBlock[34]/10000.;
glomx=gridDirBlock[35]/10000.;
ginct=gridDirBlock[38]/10000.;
gincn=
(navType == PSEUDO_MERCATOR_GENERAL)
? gridDirBlock[39]/10000. : ginct;
if (wierd) {
double x = xnr;
xnr = xnc;
xnc = x;
}
break;
case PS_OR_LAMBERT_CONIC:
xrowi = gridDirBlock[34]/10000.; // row # of the North pole*10000
xcoli = gridDirBlock[35]/10000.; // col # of the North pole*10000
xspace = gridDirBlock[36]/1000.; // column spacing at standard lat (m)
xqlon = gridDirBlock[37]/10000.; // lon parallel to cols (deg*10000)
double xt1 = gridDirBlock[38]/10000.; // first standard lat
double xt2 = gridDirBlock[39]/10000.; // second standard lat
xh = (xt1 >= 0) ? 1. : -1.;
xt1 =(90.-xh*xt1)*xrad;
xt2 =(90.-xh*xt2)*xrad;
xfac =1.0;
if (xt1 != xt2)
xfac = (Math.log(Math.sin(xt1))-Math.log(Math.sin(xt2)))/
(Math.log(Math.tan(.5*xt1))-Math.log(Math.tan(.5*xt2)));
xfac = 1.0/xfac;
xblat = 6370. * Math.sin(xt1)/
(xspace*xfac*(Math.pow(Math.tan(xt1*.5),xfac)));
if (wierd) {
double x=xnr;
xnr=xnc;
xnc=x;
x=xcoli;
xcoli=xrowi;
xrowi=xnr-x+1.0;
xqlon=xqlon+90.;
}
break;
case EQUIDISTANT:
xrowi = 1.;
xcoli = 1.;
glamx = gridDirBlock[34]/10000.; // lat of (1,1) degrees*10000
glomx = gridDirBlock[35]/10000.; // lon of (1,1) degrees*10000
xrot = -xrad*gridDirBlock[36]/10000.; // clockwise rotation of col 1
xspace = gridDirBlock[37]/1000.; // column spacing
yspace = gridDirBlock[38]/1000.; // row spacing
xblat = EARTH_RADIUS*xrad/yspace;
xblon = EARTH_RADIUS*xrad/xspace;
if (wierd) {
double x = xnr;
xnr = xnc;
xnc = x;
}
break;
case LAMBERT_CONFORMAL_TANGENT:
xrowi = gridDirBlock[34]/10000.; // row # of the North pole*10000
xcoli = gridDirBlock[35]/10000.; // col # of the North pole*10000
xspace = gridDirBlock[36]/1000.; // column spacing at standard lat (m)
xqlon = gridDirBlock[37]/10000.; // lon parallel to cols (deg*10000)
double xtl = gridDirBlock[38]/10000.; // standard lat
xh = (xtl >= 0) ? 1. : -1.;
xtl = (90. - xh * xtl) * xrad;
xfac = Math.cos(xtl);
xblat = EARTH_RADIUS * Math.tan(xtl) /
(xspace * Math.pow(Math.tan(xtl*.5), xfac));
break;
default:
break;
}
}
/**
* converts from grid coordinates (x,y) or (col, row) to latitude/longitude
*
* @param rowcol[][] array of row/col pairs. Where
* rowcol[indexRow][] is a row and
* rowcol[indexCol][] is a column.
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] rowcol)
{
double[][] latlon = new double[2][rowcol[0].length];
double xlat = Double.NaN; // temp variable for lat
double xlon = Double.NaN; // temp variable for lon
double xrlon = 0.;
double xldif, xedif;
double radius;
for (int i = 0; i < rowcol[0].length; i++)
{
// account for flipped coordinates
double xrow = isRowFlipped ? rowOffset - rowcol[indexRow][i] + 1
: rowcol[indexRow][i];
// adjust row/col based on startRow/startCol
xrow = xrow + (startRow - 1);
double xcol = rowcol[indexCol][i] - (startColumn - 1);
if (xrow > xnrow || xrow < 1.0 ||
xcol > xncol || xcol < 1.0) {
xlat = Double.NaN;
xlon = Double.NaN;
} else {
switch (navType)
{
case PSEUDO_MERCATOR:
case PSEUDO_MERCATOR_GENERAL:
if (wierd) {
double x = xrow;
xcol = xrow;
xrow = xnr - x + 1.0;
}
xlat = glamx-((xrow-1.0)*ginct);
xlon = glomx-((xcol-1.0)*gincn);
break;
case EQUIDISTANT:
break;
case PS_OR_LAMBERT_CONIC:
case LAMBERT_CONFORMAL_TANGENT:
xldif = xh * (xrow - xrowi) / xblat;
xedif = (xcoli - xcol) / xblat;
xrlon = 0.;
if( !(xldif == 0 && xedif == 0)) xrlon = Math.atan2( xedif,xldif);
xlon = xrlon / xfac / xrad + xqlon;
if(xlon > 180.) xlon = xlon - 360.;
radius = Math.sqrt( xldif * xldif + xedif * xedif);
if( radius < 1.E-5 ) {
xlat = xh * 90.;
} else {
xlat = xh * (90. - 2. * Math.atan(
Math.exp( Math.log(radius) / xfac)) /xrad);
}
break;
default:
xlat=1.0-(xrow-1.0)/(xnr-1.0);
xlon=1.0-(xcol-1.0)/(xnc-1.0);
break;
}
}
latlon[indexLat][i] = xlat;
latlon[indexLon][i] = -xlon; // convert to east positive
}
return latlon;
}
/**
* toRowCol converts latitude/longitude to grid row/col
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return rowcol[][] array of row/col pairs. Where
* rowcol[indexRow][] is a row and rowcol[indexCol][]
* is an column. These are in 'grid' coordinates
*/
public double[][] toRowCol(double[][] latlon)
{
double[][] rowcol = new double[2][latlon[0].length];
double xrow, xcol, xlat, xlon;
double xrlon, xclat, xrlat;
double glomx1;
double xldif, xedif, xdis, xangl, xange;
for (int i = 0; i < latlon[0].length; i++)
{
xrow = Double.NaN;
xcol = Double.NaN;
xlat = latlon[indexLat][i];
xlon = -latlon[indexLon][i]; // convert to McIDAS (west pos)
switch(navType)
{
case PSEUDO_MERCATOR:
case PSEUDO_MERCATOR_GENERAL:
glomx1 = glomx;
if (glomx < 0 && glomx*xlon < 0)
glomx1 = glomx + 360;
xrow = (glamx-xlat)/ginct + 1.0;
xcol = (glomx1-xlon)/gincn + 1.0;
break;
case EQUIDISTANT:
xrlon = xlon-glomx;
xrlat = xlat-glamx;
xldif = xblat*xrlat;
xedif = xrlon*xblon*Math.cos(xlat*xrad);
xdis = Math.sqrt(xldif*xldif+xedif*xedif);
if( xdis > .001) {
xangl = Math.atan2(xldif,xedif)-90.*xrad;
xange = Math.atan2(xldif,xedif)+90.*xrad;
xldif = xdis*Math.cos(-xrot+xangl);
xedif = xdis*Math.sin(-xrot+xange);
}
xrow = xrowi-xldif;
xcol = xcoli-xedif;
break;
case PS_OR_LAMBERT_CONIC:
case LAMBERT_CONFORMAL_TANGENT:
xrlon = xlon - xqlon;
if(xrlon > 180.) xrlon = xrlon - 360.;
xrlon = xrlon * xfac * xrad;
xclat = (90. - xh * xlat) * xrad * .5;
xrlat = xblat * Math.pow(Math.tan(xclat), xfac);
xrow = xh * xrlat * Math.cos(xrlon) + xrowi;
xcol = -xrlat * Math.sin(xrlon) + xcoli;
break;
default:
xrow = (1.0 - xlat)*(xnr-1.0)+1;
xcol = (1.0 - xlon)*(xnc-1.0)+1;
break;
}
if (xrow > xnrow || xrow < 1.0 ||
xcol > xncol || xcol < 1.0) {
xrow = Double.NaN;
xcol = Double.NaN;
} else {
// account for non (1,1) origin
xrow = xrow - (startRow - 1);
xcol = xcol + (startColumn - 1);
// account for flipped coordinates
if (isRowFlipped) xrow = rowOffset - xrow + 1;
}
rowcol[indexRow][i] = xrow;
rowcol[indexCol][i] = xcol;
}
return rowcol;
}
/**
* Determines whether or not the <code>Object</code> in question is
* the same as this <code>AREAnav</code>. Right now, this returns
* false until we can figure out when two navigations are equal.
* Subclasses could override if desired.
*
* @param obj the AREAnav in question
*/
public boolean equals(Object obj)
{
if (! (obj instanceof GRIDnav)) return false;
GRIDnav that = (GRIDnav) obj;
return (Double.doubleToLongBits(this.xnr) ==
Double.doubleToLongBits(that.xnr) &&
Double.doubleToLongBits(this.xnc) ==
Double.doubleToLongBits(that.xnc) &&
this.navType == that.navType);
}
/**
* define the starting row and column of another coordinate system --
* for example (0,0)
*
* @param startRow the starting row number in another
* coordinate system
*
* @param startColumn the starting column number in another
* coordinate system
*
*/
public void setStart(int startRow, int startColumn)
{
this.startRow = startRow;
this.startColumn = startColumn;
}
/**
* specify whether the row coordinates are inverted and the row
* offset.
*
* @param row ending row number
*
*/
public void setFlipRowCoordinates(int row)
{
isRowFlipped = true;
rowOffset = (double) row;
}
/**
* Determine if navigation is using flipped coordinates. This would
* mean that the start of the coordinate system is in the lower left
* instead of the upper left.
*
* @return true if using flipped row coordinates, otherwise false
*/
public boolean isFlippedRowCoordinates()
{
return isRowFlipped;
}
/**
* Get the row offset for flipped coordinates
*
* @return row offset
*/
public double getRowOffset()
{
return rowOffset;
}
/**
* Get the row index
* @return the row index in the returned arrays
*/
public int getRowIndex() { return indexRow; }
/**
* Get the column index
* @return the column index in the returned arrays
*/
public int getColumnIndex() { return indexCol; }
}

File diff suppressed because it is too large Load diff

View file

@ -1,395 +0,0 @@
//
// GridDirectory.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.util.Date;
/**
* Class for modelling a McIDAS grid header.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public class GridDirectory
{
/** GridDirectory block size */
public static final int DIRSIZE = 64;
/** Grid size (rows*columns) */
private static final int GRIDSIZE_INDEX = 0;
/** number of rows */
public static final int ROWS_INDEX = 1;
/** number of columns */
public static final int COLS_INDEX = 2;
/** ref date */
public static final int REFDATE_INDEX = 3;
/** ref time */
public static final int REFTIME_INDEX = 4;
/** forecast time */
public static final int FTIME_INDEX = 5;
/** param name */
public static final int PARAM_NAME_INDEX = 6;
/** param scale */
public static final int PARAM_SCALE_INDEX = 7;
/** param units */
public static final int PARAM_UNITS_INDEX = 8;
/** level value */
public static final int LEVEL_VALUE_INDEX = 9;
/** level scale */
public static final int LEVEL_SCALE_INDEX = 10;
/** level unit */
public static final int LEVEL_UNITS_INDEX = 11;
/** param type */
public static final int PARAM_TYPE_INDEX = 12;
/** second forecast time (for time diff or average) */
public static final int SECOND_FTIME_INDEX = 13;
/** second level value */
public static final int SECOND_LEVEL_VALUE_INDEX = 14;
/** navigation index */
public static final int NAV_BLOCK_INDEX = 33;
/** navigation length */
public static final int NAV_BLOCK_LENGTH = 8;
/** grid description */
public static final int GRID_DESCR_INDEX = 52;
/** grid description length*/
public static final int GRID_DESCR_LENGTH = 12;
private int[] dir = new int[GridDirectory.DIRSIZE]; // single directory
private String paramName;
private String gridDescription;
private String paramUnitName;
private int forecastHour;
private Date referenceTime;
private Date validTime;
private Date secondTime = null;
private double paramScale;
private double levelValue;
private String levelUnitName;
private double secondLevelValue;
private int rows;
private int columns;
private int paramType;
private int[] navBlock;
private GRIDnav gridNav = null;
/**
* Construct a GridDirectory from the grid directory block.
*
* @param dirblock directory block from the McIDAS grid
*/
public GridDirectory(int[] dirblock)
throws McIDASException
{
if (dirblock.length != DIRSIZE)
throw new McIDASException("Directory is not the right size");
System.arraycopy(
dirblock, 0, dir, 0, DIRSIZE);
// March down the list of parameters
rows = dirblock[ROWS_INDEX];
columns = dirblock[COLS_INDEX];
// date and time values
int refDay = dirblock[REFDATE_INDEX];
int refHMS = dirblock[REFTIME_INDEX];
referenceTime =
new Date(McIDASUtil.mcDayTimeToSecs(refDay, refHMS) * 1000);
forecastHour = dirblock[FTIME_INDEX];
validTime =
new Date( (McIDASUtil.mcDayTimeToSecs(refDay,refHMS)+
(forecastHour * 3600)) * 1000 );
// parameter values
paramName =
McIDASUtil.intBitsToString(dirblock[PARAM_NAME_INDEX]).trim();
paramScale = Math.pow(10., dirblock[PARAM_SCALE_INDEX]);
paramUnitName =
McIDASUtil.intBitsToString(dirblock[PARAM_UNITS_INDEX]).trim();
paramType = dirblock[PARAM_TYPE_INDEX];
// level values
levelValue =
dirblock[LEVEL_VALUE_INDEX] *
Math.pow(10., dirblock[LEVEL_SCALE_INDEX]); // level * scale
levelUnitName =
McIDASUtil.intBitsToString(dirblock[LEVEL_UNITS_INDEX]).trim();
// Special case for character levels
if (Math.abs(levelValue) > 10000 && levelUnitName.equals(""))
{
levelUnitName =
McIDASUtil.intBitsToString(dirblock[LEVEL_VALUE_INDEX]).trim();
levelValue = 999;
}
if (paramType == 4 || paramType == 8) // level difference or average
{
secondLevelValue =
dirblock[SECOND_LEVEL_VALUE_INDEX] *
Math.pow(10., dirblock[LEVEL_SCALE_INDEX]); // 2nd * scale
}
if (paramType == 1 || paramType == 2) // time difference or average
{
secondTime =
new Date( (McIDASUtil.mcDayTimeToSecs(refDay,refHMS)+
((dirblock[SECOND_FTIME_INDEX]/10000) * 3600)) * 1000 );
// NB: second time is 10000*time in hours to make HHMMSS
// so we need to divide it out
}
// make the nav block
navBlock = new int[NAV_BLOCK_LENGTH];
System.arraycopy(
dirblock, NAV_BLOCK_INDEX, navBlock, 0, NAV_BLOCK_LENGTH);
// get the grid description
int[] nameBits = new int[GRID_DESCR_LENGTH];
System.arraycopy(
dirblock, GRID_DESCR_INDEX, nameBits, 0, nameBits.length);
gridDescription =
McIDASUtil.intBitsToString(nameBits).trim();
}
/**
* Get the raw directory block
* @return array of the raw parameters in int form
* @deprecated use getDirectoryBlock
*/
public int[] getDirBlock()
{
return getDirectoryBlock();
}
/**
* Get the raw directory block
* @return array of the raw parameters in int form
*/
public int[] getDirectoryBlock()
{
return dir;
}
/**
* Get the name of the parameter
* @return parameter name
*/
public String getParamName() {
return paramName;
}
/**
* Get the grid description
* @return grid description
*/
public String getGridDescription() {
return gridDescription;
}
/**
* Get the scale of the parameter values
* @return parameter scale (power of 10)
*/
public double getParamScale() {
return paramScale;
}
/**
* Get the unit name of the parameter values
* @return unit name for this parameter
*/
public String getParamUnitName() {
return paramUnitName;
}
/**
* Get the reference time for this parameter
* @return reference time
*/
public Date getReferenceTime() {
return referenceTime;
}
/**
* Get the valid time for this parameter if it is a forecast
* @return valid time
*/
public Date getValidTime() {
return validTime;
}
/**
* Get the forecast hour for this parameter if it is a forecast
* @return forecast hour
*/
public int getForecastHour() {
return forecastHour;
}
/**
* Get the second time for this parameter if it is a time difference
* @return second time (null if only one time associated with this)
*/
public Date getSecondTime() {
return secondTime;
}
/**
* Get the vertical level value.
* @return level By McIDAS conventions, 1013. == mean sea level,
* 0. == tropopause, 1001. == surface. Otherwise,
* value is what is returned.
*/
public double getLevelValue() {
return levelValue;
}
/**
* Get the units of the vertical level.
* @return unit name of the level
*/
public String getLevelUnitName() {
return levelUnitName;
}
/**
* Get the second vertical level value if one exists.
* @return level By McIDAS conventions, 1013. == mean sea level,
* 0. == tropopause, 1001. == surface. Otherwise,
* value is what is returned.
*/
public double getSecondLevelValue() {
return secondLevelValue;
}
/**
* Get the number of rows in the grid
* @return number of rows
*/
public int getRows()
{
return rows;
}
/**
* Get the number of columns in the grid
* @return number of columns
*/
public int getColumns()
{
return columns;
}
/**
* Get the navigation parameters.
* @return array of nav parameters. The first value is the grid type
* and subsequent values provide the parameters for that type.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A> for a description
* @see #getNavType()
*/
public int[] getNavBlock()
{
return navBlock;
}
/**
* Get the navigation
* @return GRIDnav for this grid (may be null)
*/
public GRIDnav getNavigation()
{
if (gridNav == null) {
// make the nav module
try {
gridNav = new GRIDnav(getDirectoryBlock());
} catch (McIDASException excp) {
gridNav = null;
}
}
return gridNav;
}
/**
* Get the navigation type. Type is stored as first element of
* the nav block.
* @return nav type
* <pre>
* types are:
* 1 = pseudo-Mercator
* 2 = Polar Stereographic or Lambert Conformal
* 3 = Equidistant
* 4 = pseudo-Mercator (more general)
* 5 = no navigation
* 6 = Lambert Conformal Tangent Cone
* </pre>
* @see #getNavBlock()
*/
public int getNavType()
{
return navBlock[0];
}
/**
* Check the equality of the object in question with this.
* @param o object in question
*/
public boolean equals(Object o) {
if (!(o instanceof GridDirectory)) return false;
GridDirectory that = (GridDirectory) o;
return (this == that ||
java.util.Arrays.equals(
getDirectoryBlock(), that.getDirectoryBlock()));
}
/**
* String representation of the GridDirectory
* @return human readable string
*/
public String toString()
{
StringBuffer buff = new StringBuffer();
buff.append("Grid Directory:");
buff.append("\n");
buff.append("\tParameter = ");
buff.append(paramName + " [" + paramUnitName + "] (");
buff.append(gridDescription +")");
buff.append("\n");
buff.append("\trefTime: ");
buff.append(referenceTime.toGMTString());
buff.append(" valid: "+validTime.toGMTString());
buff.append("\n");
buff.append("\tsecond Time: ");
buff.append( (secondTime != null) ? secondTime.toGMTString() : "none");
buff.append("\n");
buff.append("\tLevel: ");
buff.append(levelValue+" ["+levelUnitName+"] second: "+secondLevelValue);
buff.append("\n");
buff.append("\tNav Type: ");
buff.append(getNavType());
buff.append(" rows: " + rows);
buff.append(" cols: " + columns);
buff.append("\n");
return buff.toString();
}
}

View file

@ -1,268 +0,0 @@
//
// GridDirectoryList.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import edu.wisc.ssec.mcidas.adde.AddeURLConnection;
import java.io.BufferedInputStream;
import java.io.DataInputStream;
import java.io.IOException;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
/**
* GridDirectoryList interface for McIDAS 'grids'.
* Provides access to a list of one or more GridDirectoy objects.
*
* @author Don Murray
*
*/
public class GridDirectoryList
{
// load protocol for ADDE URLs
// See java.net.URL for explanation of URL handling
static
{
try
{
String handlers = System.getProperty("java.protocol.handler.pkgs");
String newProperty = null;
if (handlers == null)
newProperty = "edu.wisc.ssec.mcidas";
else if (handlers.indexOf("edu.wisc.ssec.mcidas") < 0)
newProperty = "edu.wisc.ssec.mcidas | " + handlers;
if (newProperty != null) // was set above
System.setProperty("java.protocol.handler.pkgs", newProperty);
}
catch (Exception e)
{
System.out.println(
"Unable to set System Property: java.protocol.handler.pkgs");
}
}
private boolean flipwords = false;
private DataInputStream inputStream; // input stream
private int status=-1; // read status
private AddeURLConnection urlc; // URL connection
private ArrayList dirs; // list of directories
private ArrayList fileHeaders; // list of file headers
private int numDirs = 0; // number of directories
private final int HEARTBEAT = 11223344;
/**
* Creates an GridDirectory object that allows reading
* of McIDAS 'grids' from an ADDE server
*
* @param gridSource ADDE URL to read from as a String
*
* @exception McIDASException if file cannot be opened
*
*/
public GridDirectoryList(String gridSource)
throws McIDASException
{
try
{
URL url = new URL(gridSource);
urlc = (AddeURLConnection) url.openConnection();
inputStream =
new DataInputStream(
new BufferedInputStream(urlc.getInputStream()));
}
catch (IOException e)
{
throw new McIDASException("Error opening URL for grids:"+e);
}
readDirectory();
}
/**
* creates an GridDirectory object that allows reading
* of the directory of McIDAS 'grid' files from a URL
*
* @param URL - the URL to go after
*
* @exception McIDASException if file cannot be opened
*
*/
public GridDirectoryList(URL url)
throws McIDASException
{
try
{
urlc = (AddeURLConnection) url.openConnection();
inputStream =
new DataInputStream(
new BufferedInputStream(urlc.getInputStream()));
}
catch (IOException e)
{
throw new McIDASException("Error opening URL for grids:"+e);
}
readDirectory();
}
/**
* Read the directory information for a grid.
*
* @exception McIDASException if there is a problem reading
* any portion of the metadata.
*
*/
private void readDirectory() throws McIDASException
{
if (urlc.getRequestType() != AddeURLConnection.GDIR)
throw new McIDASException("Request must be of GDIR type");
dirs = new ArrayList();
fileHeaders = new ArrayList();
/* See how many bytes there are to read.
From the McIDAS Programmers Manual a request transmits back:
- 4-byte value containing the total number of bytes to transmit
- 4-byte value of zero indicating a new file header is being sent;
this information is repeated for each new file header to transfer
and is sent after all grids from the previous file are transmitted
- 256-byte grid file header; this information is repeated for each
new grid file header to transmit and is sent after the grids from
the previous file are transmitted
- 4-byte value of zero indicating a new grid directory is being sent;
this information is repeated before each grid directory in the file
is sent
- 256-byte grid header; this information is repeated for each grid
in the file being sent
- 4-byte value of 1 indicating no more grid directories in the file
*/
int numBytes = urlc.getInitialRecordSize();
if (numBytes == 0) {
throw new McIDASException("No datasets found");
}
int check;
byte[] header = new byte[256];
// Check for heartbeat
try
{
while (numBytes == 4)
{
check = inputStream.readInt();
if (check != HEARTBEAT)
System.out.println("problem...not heartbeat = "+check);
numBytes = inputStream.readInt();
}
// now we get the file header
while ( (check = inputStream.readInt()) == 0) // new header
{
inputStream.readFully(header,0,256);
String head = new String(header,0,32);
fileHeaders.add(head);
int check2;
// now we get the grid directory
while( (check2 = inputStream.readInt()) == 0)
{
int[] dir = new int[GridDirectory.DIRSIZE];
for (int i=0; i < AreaFile.AD_DIRSIZE; i++)
{
dir[i] = inputStream.readInt();
}
/* Debug
for (int i = 0; i < GridDirectory.DIRSIZE; i++)
System.out.println("dir[" + i +"] = " + dir[i]);
*/
GridDirectory gridDir = new GridDirectory(dir);
System.out.println(gridDir);
dirs.add(gridDir);
}
}
}
catch (IOException e)
{
status = -1;
throw new McIDASException("Error reading grid directory:" + e);
}
status = 1;
numDirs++;
}
/**
* returns the directory blocks for the requested grids.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A> for information on the parameters
* for each value.
*
* @return a ArrayList of GridDirectorys
*
* @exception AreaFileException if there was a problem
* reading the directory
*
*/
public ArrayList getDirs()
throws McIDASException
{
if (status <= 0 || dirs.size() <= 0)
{
throw new McIDASException(
"Error reading directory information");
}
return dirs;
}
/**
* Prints out a formatted listing of the directory info
*/
public String toString()
{
if (status <=0 || numDirs <= 0)
{
return new String("No directory information available");
}
StringBuffer sb = new StringBuffer();
for (int i = 0; i < dirs.size(); i++)
{
sb.append( ((GridDirectory) dirs.get(i)).toString());
sb.append("\n");
}
return sb.toString();
}
public static void main(String[] args)
throws Exception
{
if (args.length == 0)
{
System.out.println("Must supply a ADDE request to grids");
System.exit(1);
}
GridDirectoryList gdl = new GridDirectoryList(args[0]);
//System.out.println(gdl.toString());
}
}

View file

@ -1,440 +0,0 @@
//
// KALPnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.util.*;
import java.io.*;
/**
* The KALPnav class creates the ability to navigate KALP
* image data. It is a math copy of the McIDAS nvxgvar.dlm
* code.
*
* When used with AreaFile class, set up like this:
*
* <pre><code>
* AreaFile af;
* try {
* af = new AreaFile("/home/user/mcidas/data/AREA0001");
* } catch (AreaFileException e) {
* System.out.println(e);
* return;
* }
* int[] dir;
* try { dir=af.getDir();
* } catch (AreaFileException e){
* System.out.println(e);
* return;
* }
* int[] nav;
* try { nav=af.getNav();
* } catch (AreaFileException e){
* System.out.println(e);
* return;
* }
* try {
* GVARnav ng = new GVARnav(nav); // XXXXnav is the specific implementation
* } catch (IllegalArgumentException excp) {
* System.out.println(excp);
* return;
* }
* ng.setImageStart(dir[5], dir[6]);
* ng.setRes(dir[11], dir[12]);
* ng.setMag(1,1);
* ng.setStart(0,0);
* ......................
* </code></pre>
*
* @author Tom Whittaker
*
*/
public class KALPnav extends AREAnav {
private int ic;
private double h, a, rp, re, cdr, crd, lpsi2, deltax, deltay;
private double sublat, sublon, cenlin, cenele, altitude;
private double PI;
private boolean isEastPositive = true;
public KALPnav (int[] iparms) {
this(1, iparms);
}
public KALPnav (int ifunc, int[] iparms) {
if (ifunc != 1) ifunc = 1;
if (iparms[0] != KALP ) {
throw new IllegalArgumentException("Invalid navigation type" + iparms[0]);
}
// H=42150.766-6378.155
altitude = (double)iparms[11] / 10000.0;
h=altitude-6378.155;
re=6378.155;
a=1./297.;
rp=re/(1.+a);
PI=3.141592653;
cdr=PI/180.;
crd=180./PI;
lpsi2=1.0;
// DELTAX=18.03674/1408.
// DELTAY=18.03674/1408.
deltax = (double)iparms[12] / 1000000000.0;
deltax = deltax * crd;
deltay = deltax;
sublat=(double)iparms[10]/10000.;
sublon=(double)iparms[6]/10000.;
// The center line and element are in full res coords *10
// They are used in scan coords, so divide by 40.
cenlin = (double)iparms[13]/40.;
cenele = (double)iparms[14]/40.;
if(iparms[13] == 0) {
cenlin = 704.5;
cenele = 704.5;
}
}
public float[][] toLatLon(float[][] linele) {
double xele2, xlin2, x, y, xr, yr, rs, tanx, tany, val1, val2, yk;
double vmu, cosrf, sinrf, xt, yt, zt, xfi, xla, teta;
int number = linele[0].length;
float[][] latlon = new float[2][number];
float[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point<number; point++) {
xele2 = imglinele[indexEle][point]/4.0;
xlin2 = imglinele[indexLine][point]/4.0;
x = cenele - xele2;
y = cenlin - xlin2;
xr = x;
yr = y;
x=xr*lpsi2*deltax*cdr;
y=yr*lpsi2*deltay*cdr;
rs=re+h;
tanx=Math.tan(x);
tany=Math.tan(y);
val1=1.+tanx*tanx;
val2=1.+(tany*tany)*((1.+a)*(1.+a));
yk=rs/re;
if((val1*val2) > ((yk*yk)/(yk*yk-1.0))) {
latlon[indexLine][point] = Float.NaN;
latlon[indexEle][point] = Float.NaN;
continue;
}
vmu=(rs-(re*(Math.sqrt((yk*yk)-(yk*yk-1)*val1*val2))))/(val1*val2);
cosrf=Math.cos(sublat*cdr);
sinrf=Math.sin(sublat*cdr);
xt=(rs*cosrf)+(vmu*(tanx*sinrf-cosrf));
yt=(rs*sinrf)-(vmu*(tanx*cosrf+sinrf));
zt=vmu*tany/Math.cos(x);
teta=Math.asin(zt/rp);
xfi=(Math.atan(((Math.tan(teta))*re)/rp))*crd;
xla=-Math.atan(yt/xt)*crd;
//--- CHANGE LONGITUDE FOR CORRECT SUBPOINT
xla=xla+sublon;
if (isEastPositive) xla = -xla;
latlon[indexLat][point] = (float) xfi;
latlon[indexLon][point] = (float) xla;
}
return latlon;
}
public float[][] toLinEle(float [][] latlon) {
double x1, y1, xfi, xla, rom, y, r1, r2, rs, reph, rpph;
double coslo, sinlo, teta, xt, yt, zt, px, py, xr, yr ;
int number = latlon[0].length;
float[][] linele = new float[2][number];
for (int point=0; point<number; point++) {
x1 = (double) latlon[indexLat][point];
y1 = (double) latlon[indexLon][point];
if (!isEastPositive) y1 = -y1;
//--- CORRECT FOR SUBLON
y1=y1+sublon;
xfi=x1*cdr;
xla=y1*cdr;
rom=(re*rp)/Math.sqrt(rp*rp*Math.cos(xfi) *
Math.cos(xfi)+re*re*Math.sin(xfi)*Math.sin(xfi));
y=Math.sqrt(h*h+rom*rom-2*h*rom*Math.cos(xfi)*Math.cos(xla));
r1=y*y+rom*rom;
r2=h*h;
if (r1 > r2) {
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
} else {
rs=re+h;
reph=re;
rpph=rp;
coslo=Math.cos(sublat*cdr);
sinlo=Math.sin(sublat*cdr);
teta=Math.atan((rpph/reph)*Math.tan(xfi));
xt=reph*Math.cos(teta)*Math.cos(xla);
yt=reph*Math.cos(teta)*Math.sin(xla);
zt=rpph*Math.sin(teta);
px=Math.atan((coslo*(yt-rs*sinlo)-(xt-rs*coslo)*sinlo)/
(sinlo*(yt-rs*sinlo)+(xt-rs*coslo)*coslo));
py=Math.atan(zt*((Math.tan(px)*sinlo-coslo)/(xt-rs*coslo))*Math.cos(px));
px=px*crd;
py=py*crd;
xr=px/(deltax*lpsi2);
yr=py/(deltay*lpsi2);
xr=cenele-xr;
yr=cenlin-yr;
xr=xr*4.0;
yr=yr*4.0;
linele[indexLine][point] = (float)yr;
linele[indexEle][point] = (float)xr;
}
}
return imageCoordToAreaCoord(linele, linele);
}
public double[][] toLinEle(double [][] latlon) {
double x1, y1, xfi, xla, rom, y, r1, r2, rs, reph, rpph;
double coslo, sinlo, teta, xt, yt, zt, px, py, xr, yr;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point<number; point++) {
x1 = latlon[indexLat][point];
y1 = latlon[indexLon][point];
if (!isEastPositive) y1 = -y1;
//--- CORRECT FOR SUBLON
y1=y1+sublon;
xfi=x1*cdr;
xla=y1*cdr;
rom=(re*rp)/Math.sqrt(rp*rp*Math.cos(xfi) *
Math.cos(xfi)+re*re*Math.sin(xfi)*Math.sin(xfi));
y=Math.sqrt(h*h+rom*rom-2*h*rom*Math.cos(xfi)*Math.cos(xla));
r1=y*y+rom*rom;
r2=h*h;
if (r1 > r2) {
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
continue;
}
rs=re+h;
reph=re;
rpph=rp;
coslo=Math.cos(sublat*cdr);
sinlo=Math.sin(sublat*cdr);
teta=Math.atan((rpph/reph)*Math.tan(xfi));
xt=reph*Math.cos(teta)*Math.cos(xla);
yt=reph*Math.cos(teta)*Math.sin(xla);
zt=rpph*Math.sin(teta);
px=Math.atan((coslo*(yt-rs*sinlo)-(xt-rs*coslo)*sinlo)/
(sinlo*(yt-rs*sinlo)+(xt-rs*coslo)*coslo));
py=Math.atan(zt*((Math.tan(px)*sinlo-coslo)/(xt-rs*coslo))*Math.cos(px));
px=px*crd;
py=py*crd;
xr=px/(deltax*lpsi2);
yr=py/(deltay*lpsi2);
xr=cenele-xr;
yr=cenlin-yr;
xr=xr*4.0;
yr=yr*4.0;
linele[indexLine][point] = yr;
linele[indexEle][point] = xr;
}
return imageCoordToAreaCoord(linele, linele);
}
public double[][] toLatLon(double[][] linele) {
double xele2, xlin2, x, y, xr, yr, rs, tanx, tany, val1, val2, yk;
double vmu, cosrf, sinrf, xt, yt, zt, xfi, xla, teta;
int number = linele[0].length;
double[][] latlon = new double[2][number];
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point<number; point++) {
xele2 = imglinele[indexEle][point]/4.0;
xlin2 = imglinele[indexLine][point]/4.0;
x = cenele - xele2;
y = cenlin - xlin2;
xr = x;
yr = y;
x=xr*lpsi2*deltax*cdr;
y=yr*lpsi2*deltay*cdr;
rs=re+h;
tanx=Math.tan(x);
tany=Math.tan(y);
val1=1.+tanx*tanx;
val2=1.+(tany*tany)*((1.+a)*(1.+a));
yk=rs/re;
if((val1*val2) > ((yk*yk)/(yk*yk-1.0))) {
latlon[indexLine][point] = Float.NaN;
latlon[indexEle][point] = Float.NaN;
continue;
}
vmu=(rs-(re*(Math.sqrt((yk*yk)-(yk*yk-1)*val1*val2))))/(val1*val2);
cosrf=Math.cos(sublat*cdr);
sinrf=Math.sin(sublat*cdr);
xt=(rs*cosrf)+(vmu*(tanx*sinrf-cosrf));
yt=(rs*sinrf)-(vmu*(tanx*cosrf+sinrf));
zt=vmu*tany/Math.cos(x);
teta=Math.asin(zt/rp);
xfi=(Math.atan(((Math.tan(teta))*re)/rp))*crd;
xla=-Math.atan(yt/xt)*crd;
//--- CHANGE LONGITUDE FOR CORRECT SUBPOINT
xla=xla+sublon;
if (isEastPositive) xla = -xla;
latlon[indexLat][point] = xfi;
latlon[indexLon][point] = xla;
}
return latlon;
}
public static void main(String[] args) {
int [] navBlock = new int[800];
int [] dirBlock = new int[64];
DataInputStream dis = null;
KALPnav kalp = null;
String fileName = "KALPAREA";
System.out.println("unit test of class KALP begin...");
if (args.length > 0) fileName = args[0];
// test assumes presence of test area called KALPXAREA
try {
dis = new DataInputStream (
new BufferedInputStream(new FileInputStream(fileName), 2048)
);
} catch (Exception e) {
System.out.println("error creating DataInputStream: " + e);
System.exit(0);
}
// read and discard the directory
System.out.println("reading in, discarding directory words...");
try {
for (int i = 0; i < 64; i++) {
dirBlock[i] = dis.readInt();
}
} catch (IOException e) {
System.out.println("error reading area file directory: " + e);
System.exit(0);
}
// now read in the navigation data
System.out.println("reading in navigation words...");
try {
for (int i = 0; i < navBlock.length; i++) {
navBlock[i] = dis.readInt();
}
} catch (IOException e) {
System.out.println("error reading area file navigation data: " + e);
System.exit(0);
}
if (navBlock[0] != KALP) {
System.out.println("error: not a KALP navigation block.");
System.exit(0);
}
double [][] linEle = new double [2][1];
double [][] latLon = new double [2][1];
System.out.println("creating KALPnav object...");
kalp = new KALPnav(navBlock);
kalp.setImageStart(dirBlock[5], dirBlock[6]);
System.out.println("#### ImageStart set to:"+dirBlock[5]+" "+dirBlock[6]);
kalp.setRes(dirBlock[11], dirBlock[12]);
System.out.println("#### ImageRes set to:"+dirBlock[11]+" "+dirBlock[12]);
kalp.setStart(0,0);
//System.out.println("#### setFlipLineCoord called with "+dirBlock[8]);
//kalp.setFlipLineCoordinates(dirBlock[8]); // invert Y axis coordinates
System.out.println(" test of toLinEle...");
latLon[kalp.indexLat][0] = 11.0f;
latLon[kalp.indexLon][0] = 50.f;
linEle = kalp.toLinEle(latLon);
System.out.println(" answer is: " + linEle[kalp.indexLine][0] +
", " + linEle[kalp.indexEle][0]);
latLon[0][0] = Double.NaN;
latLon = kalp.toLatLon(linEle);
System.out.println("testing inverse of 11N/50E");
System.out.println(" answer is: " + latLon[kalp.indexLat][0] +
", " + latLon[kalp.indexLon][0]);
System.out.println(" another test of toLinEle...");
latLon[kalp.indexLat][0] = -20.0f;
latLon[kalp.indexLon][0] = 100.f;
linEle = kalp.toLinEle(latLon);
System.out.println(" answer is: " + linEle[kalp.indexLine][0] +
", " + linEle[kalp.indexEle][0]);
latLon[0][0] = Double.NaN;
latLon = kalp.toLatLon(linEle);
System.out.println("testing inverse of 20S/100E");
System.out.println(" answer is: " + latLon[kalp.indexLat][0] +
", " + latLon[kalp.indexLon][0]);
System.out.println("unit test of class KALPnav end...");
}
}

View file

@ -1,194 +0,0 @@
//
// LAMBnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for Lambert Conformal (LAMB) type nav. This code was
* modified from the original FORTRAN code (nvxlamb.dlm) on the McIDAS system.
* It only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class LAMBnav extends AREAnav
{
private boolean isEastPositive = true;
int iwest;
int ihem;
double xrow;
double xcol;
double xlat1;
double xlat2;
double xspace;
double xqlon;
double xblat;
double xfac;
double xpole;
/**
* Set up for the real math work. Must pass in the int array
* of the LAMB nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a LAMB type.
*/
public LAMBnav (int[] iparms)
throws IllegalArgumentException
{
if (iparms[0] != LAMB )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
xrow = iparms[1];
xcol = iparms[2];
int ipole = iparms[11];
if (ipole == 0) ipole = 900000;
ihem = 1;
if (ipole < 0) ihem = -1;
xpole = McIDASUtil.integerLatLonToDouble(ipole);
xlat1 = McIDASUtil.integerLatLonToDouble(iparms[3]);
xlat2 = McIDASUtil.integerLatLonToDouble(iparms[4]);
xlat1 = (90. - ihem*xlat1)*DEGREES_TO_RADIANS;
xlat2 = (90. - ihem*xlat2)*DEGREES_TO_RADIANS;
xspace = iparms[5]/1000.;
xqlon = McIDASUtil.integerLatLonToDouble(iparms[6]);
double r = iparms[7]/1000.;
iwest = iparms[10];
if (iwest >= 0) iwest = 1;
xfac = (Math.log(Math.sin(xlat1)) - Math.log(Math.sin(xlat2)))/
(Math.log(Math.tan(.5*xlat1)) - Math.log(Math.tan(.5*xlat2)));
xblat = r * Math.sin(xlat1)/
(xspace*xfac*Math.pow(Math.tan(xlat1*.5), xfac));
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double xldif;
double xedif;
double xlon;
double xlat;
double xrlon, radius;
int number = linele[0].length;
double[][] latlon = new double[2][number];
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xldif = ihem*(imglinele[indexLine][point] - xrow)/xblat;
xedif = -ihem*(imglinele[indexEle][point] - xcol)/xblat;
xrlon = 0;
if (!(xldif == 0 && xedif == 0)) xrlon = Math.atan2(xedif, xldif);
xlon = ihem*xrlon/xfac/DEGREES_TO_RADIANS + xqlon;
xlon = (xlon+900.)%360. - 180.0;
radius = Math.sqrt(xldif*xldif + xedif*xedif);
if (Math.abs(radius) < 1.e-10)
xlat = ihem*90;
else
xlat = ihem*(90. - 2*Math.atan(
Math.exp(Math.log(radius)/xfac))/DEGREES_TO_RADIANS);
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = (iwest == 1) ? -xlon : xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double xlon;
double xlat;
double xrlon, xrlat, xclat;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west positive longitude) coordinates
xlon = (iwest == 1)
? -latlon[indexLon][point]
: latlon[indexLon][point];
xrlon = ihem*(xlon-xqlon);
xrlon = (xrlon+900.)%360. - 180.;
xrlon = xrlon*xfac*DEGREES_TO_RADIANS;
xclat = (90. - ihem*xlat)*DEGREES_TO_RADIANS*.5;
if (xclat == 0.0)
xrlat = 0.0;
else
xrlat = xblat*Math.pow(Math.tan(Math.abs(xclat)), xfac);
linele[indexLine][point] = xrow + ihem*(xrlat*Math.cos(xrlon));
linele[indexEle][point] = xcol - ihem*(xrlat*Math.sin(xrlon));
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,287 +0,0 @@
//
// MERCnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for Mercator (MERC) type nav. This code was modified
* from the original FORTRAN code (nvxmerc.dlm) on the McIDAS system.
* It only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class MERCnav extends AREAnav
{
private boolean isEastPositive = true;
int iwest;
int leftlon;
double xrow;
double xcol;
double xlat1;
double xspace;
double xqlon;
double xblat;
double xblon;
/**
* Set up for the real math work. Must pass in the int array
* of the MERC nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a MERC type.
*/
public MERCnav (int[] iparms)
throws IllegalArgumentException
{
if (iparms[0] != MERC )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
xrow = iparms[1];
xcol = iparms[2];
xlat1 = McIDASUtil.integerLatLonToDouble(iparms[3]);
xspace = iparms[4]/1000.;
xqlon = McIDASUtil.integerLatLonToDouble(iparms[5]);
double r = iparms[6]/1000.;
iwest = iparms[9];
if (iwest >= 0) iwest = 1;
xblat = r * Math.cos(xlat1*DEGREES_TO_RADIANS)/xspace;
xblon = DEGREES_TO_RADIANS*r/xspace;
leftlon = (int) xqlon-180*iwest;
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double xldif;
double xedif;
double xlon;
double xlat;
double xrlat, xrlon;
int number = linele[0].length;
double[][] latlon = new double[2][number];
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xldif = xrow - imglinele[indexLine][point];
xedif = xcol - imglinele[indexEle][point];
xrlon = iwest*xedif/xblon;
xlon = xrlon+xqlon;
xrlat = Math.atan(Math.exp(xldif/xblat));
xlat = (xrlat/DEGREES_TO_RADIANS - 45.)*2.+xlat1;
if (xlon > (360.+leftlon) || xlon < leftlon)
{
latlon[indexLat][point] = Double.NaN;
latlon[indexLon][point] = Double.NaN;
}
else
{
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = (iwest == 1) ? -xlon : xlon;
}
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double xlon;
double xlat;
double xrlon, xrlat;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west positive longitude) coordinates
xlon = (iwest == 1)
? -latlon[indexLon][point]
: latlon[indexLon][point];
xrlon = iwest*(xlon-xqlon);
if (xrlon > 180.) xrlon -= 360.;
if (xrlon < -180.) xrlon += 360.;
if (xlat >= 90.) xlat = 89.99;
if (xlat <= -90.) xlat = -89.99;
xrlat = ((xlat-xlat1)/2 + 45.)*DEGREES_TO_RADIANS;
if (xrlat <= 0.0)
{
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
}
else
{
linele[indexLine][point] =
xrow - xblat*Math.log(Math.tan(xrlat));
linele[indexEle][point] = xcol - xrlon*xblon;
}
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele)
{
double xldif;
double xedif;
double xlon;
double xlat;
double xrlon, xrlat;
int number = linele[0].length;
float[][] latlon = new float[2][number];
// Convert array to Image coordinates for computations
float[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xldif = xrow - imglinele[indexLine][point];
xedif = xcol - imglinele[indexEle][point];
xrlon = iwest*xedif/xblon;
xlon = xrlon+xqlon;
xrlat = Math.atan(Math.exp(xldif/xblat));
xlat = (xrlat/DEGREES_TO_RADIANS - 45.)*2.+xlat1;
if (xlon > (360.+leftlon) || xlon < leftlon)
{
latlon[indexLat][point] = Float.NaN;
latlon[indexLon][point] = Float.NaN;
}
else
{
latlon[indexLat][point] = (float) xlat;
latlon[indexLon][point] = (float) ((iwest == 1) ? -xlon : xlon);
}
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon)
{
double xlon;
double xlat;
double xrlon, xrlat;
int number = latlon[0].length;
float[][] linele = new float[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west positive longitude) coordinates
xlon = (iwest == 1)
? -latlon[indexLon][point]
: latlon[indexLon][point];
xrlon = iwest*(xlon-xqlon);
if (xrlon > 180.) xrlon -= 360.;
if (xrlon < -180.) xrlon += 360.;
if (xlat >= 90.) xlat = 89.99;
if (xlat <= -90.) xlat = -89.99;
xrlat = ((xlat-xlat1)/2 + 45.)*DEGREES_TO_RADIANS;
if (xrlat <= 0.0)
{
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
}
else
{
linele[indexLine][point] = (float)
(xrow - xblat*Math.log(Math.tan(xrlat)));
linele[indexEle][point] = (float) (xcol - xrlon*xblon);
}
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,580 +0,0 @@
//
// MOLLnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for Mollweide (MOLL) type nav. This code was modified
* from the original FORTRAN code (nvxmoll.dlm) on the McIDAS system. It
* only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see edu.wisc.ssec.mcidas.AREAnav
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class MOLLnav extends AREAnav
{
private boolean isEastPositive = true;
private final double EARTH_RADIUS=6378.155; // earth equatorial radius (km)
private double drad;
private double decc;
private double[] tlat = new double[101];
private double[] t = new double[101];
private double[][] coef = new double[4][101];
private double[] lattbl = new double[91];
private double xrow, xcol, rpix, xqlon;
private int itype, ihem, iwest, icord;
private double asq = 40683833.48;
private double bsq = 40410330.18;
private double ab = 40546851.22;
private double ecc = .081992e0;
private double eccsqr = 6.72265e-3;
private int kwest = -1;
private int kcord = 0;
private final int KMPP = 1263358032;
private final int PPMK = 1347439947;
/**
* Set up for the real math work. Must pass in the int array
* of the MOLL nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a MOLL type.
*/
public MOLLnav (int[] iparms)
throws IllegalArgumentException
{
double res;
double x;
int i;
/* No longer needed. Here for consistency with nvxmoll.dlm
if (ifunc != 1)
{
if (iparms[0] == XY ) itype = 1;
if (iparms[0] == LL ) itype = 2;
return;
}
*/
if (iparms[0] != MOLL )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
itype = 2;
xrow = iparms[1];
xcol = iparms[2];
xqlon = iparms[4];
drad = iparms[6]/1000.e0;
double r = drad;
if (iparms[14] == KMPP || iparms[14] == PPMK)
{
res = iparms[3];
rpix = (0.7071*r)/res;
}
else
{
rpix = iparms[3];
}
decc = iparms[7]/1.e6;
iwest = iparms[9];
if (iwest >= 0 ) iwest = 1;
icord = iparms[8];
// set up coefficients;
// CALL LLOPT(DRAD,DECC,IWEST,IPARMS(9))
asq = drad*drad;
ecc = decc;
eccsqr = ecc*ecc;
double dpole = Math.sqrt(asq*(1.e0-eccsqr));
bsq = dpole*dpole;
ab = drad*dpole;
if(iwest < 0) kwest=1;
if(icord < 0) kcord=-1;
for (i = 0; i < tlat.length; i++)
{
x = i/100.;
if (x >= 1.)
{
t[i] = 1.;
tlat[i] = 1.57080/DEGREES_TO_RADIANS;
}
else
{
t[i] = x;
tlat[i] = Math.asin((Math.asin(x)
+x*Math.sqrt(1.0-x*x))/1.57080)/DEGREES_TO_RADIANS;
}
}
// create cubic spline table - from asspl2.for
int n = 100;
int m = n - 1;
double w, z, t1, s, u, v, zs, zq, ws, wq, aa, ba, ca, da;
for (i = 0; i < n; i++)
{
if (i != 0)
t1 = (t[i+1]-t[i-1])/(tlat[i+1]-tlat[i-1]);
else
{
w = (t[1]+t[2])/2.0;
z = (tlat[1]+tlat[2])/2.0;
t1 = (w-t[0])/(z-tlat[0]);
t1 = 2.0*(t[1]-t[0])/(tlat[1]-tlat[0])-t1;
}
if (i != m)
s = (t[i+2]-t[i])/(tlat[i+2]-tlat[i]);
else
{
w = (t[n-1]+t[n-2])/2.0;
z = (tlat[n-1]+tlat[n-2])/2.0;
s = (t[n]-w)/(tlat[n]-z);
s = 2.0*(t[n]-t[n-1])/(tlat[n]-tlat[n-1])-s;
}
u=t[i+1];
v=t[i];
w=(tlat[i+1]+tlat[i])/2.0;
z=(tlat[i+1]-tlat[i])/2.0;
zs=z*z;
zq=z*zs;
ws=w*w;
wq=w*ws;
aa=.5*(u+v)-.25*z*(s-t1);
ba=.75*(u-v)/z-.25*(s+t1);
ca=.25*(s-t1)/z;
da=.25*(s+t1)/zs-.25*(u-v)/zq;
coef[0][i]=aa-ba*w+ca*ws-da*wq;
coef[1][i]=ba-2.0*ca*w+3.0*da*ws;
coef[2][i]=ca-3.0*da*w;
coef[3][i]=da;
}
for (int j = 0; j < 4; j++)
{
coef[j][n] = coef[j][n-1];
}
i = 0;
int j, k;
for (int l = 0; l < 91; l++)
{
u = l;
if (i >= n-1) i=0;
if (u < tlat[i] || u > tlat[i+1])
{
i = 0;
j = n;
do
{
k = (i+j)/2;
if (u < tlat[k]) j=k;
if (u >= tlat[k]) i=k;
} while (j > i+1);
}
lattbl[l] = coef[0][i]+u*(coef[1][i]+u*(coef[2][i]+u*coef[3][i]));
}
}
/**
* Converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double xlin, xele;
double xldif, xedif;
double w;
double xlat, xlon;
double ylat, ylon;
double snlt, cslt, snln, csln, r, tnlt, z;
int number = linele[0].length;
double[][] latlon = new double[2][number];
// Convert from file to Image coordinates for calculations
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xldif = Math.abs(xlin - xrow)/rpix;
xedif = (xcol - xele)/rpix;
// WLH 8 March 2000
// if (xldif > 1.0)
if (xlin != xlin || xele != xele || xldif > 1.0)
{
xlat = Double.NaN;
xlon = Double.NaN;
}
else
{
w = Math.sqrt(1.0 - xldif*xldif);
if (w == 0.0 || Math.abs(xedif/w) > 2.0)
{
xlat = Double.NaN;
xlon = Double.NaN;
}
else
{
xlat = Math.asin((Math.asin(xldif)+
xldif*w)/1.57080)/DEGREES_TO_RADIANS;
if (xlin > xrow) xlat = -xlat;
// Compute angular displacement from std longitude (XQLON)
xlon = -90.*(xedif/w);
xlon = xqlon - xlon;
// Force angles to (-180 < XLON < 180)
if (xlon > 180.) xlon = xlon - 360.;
if (xlon < -180.) xlon = xlon + 360.;
// Convert to cartesian? coordinates
if (itype == 1)
{
// LLCART(YLAT,YLON,XLAT,XLON,Z)
ylat=DEGREES_TO_RADIANS*xlat;
if (kcord >= 0)
ylat = Math.atan2(bsq*Math.sin(ylat),
asq*Math.cos(ylat));
ylon = kwest*DEGREES_TO_RADIANS*xlon;
snlt = Math.sin(ylat);
cslt = Math.cos(ylat);
csln = Math.cos(ylon);
snln = Math.sin(ylon);
tnlt = Math.pow((snlt/cslt),2.0);
r = ab*Math.sqrt((1.0+tnlt)/(bsq+asq*tnlt));
xlat = r*cslt*csln;
xlon = r*cslt*snln;
z = r*snlt;
}
}
}
// transform from McIDAS (west positive longitude) coordinates
if (isEastPositive) xlon = -xlon;
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double x, y, z;
double xlin, xele;
double xlat, xlon;
double flat, t, t2, w, diff_lon, xedif;
int isign, ilat;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west longitude positive) coordinates
xlon = isEastPositive
? - latlon[indexLon][point]
: latlon[indexLon][point];
// WLH 8 March 2000
if (Double.isNaN(xlat) || Double.isNaN(xlon) ||
(Math.abs(xlat) > 90.) ) { // DRM 10 June 2003
xele = Double.NaN;
xlin = Double.NaN;
}
else {
// if in cartesian coords, transform to lat/lon
if (itype == 1)
{
x = xlat;
y = xlon;
// CALL CARTLL(X,Y,Z,XLAT,XLON)
}
isign = -1;
if (xlat < 0.0) isign = 1;
ilat = (int) (Math.abs(xlat));
flat = Math.abs(xlat) - ilat;
t = lattbl[ilat];
if (ilat != 90) t = t + flat*(lattbl[ilat+1] - lattbl[ilat]);
t2 = Math.max(0.0, 1.0-t*t);
w = Math.sqrt(t2);
//** Here we need to handle the problem of computing
//** angular differences across the dateline.
diff_lon = xlon - xqlon;
if (diff_lon < -180.0) diff_lon = diff_lon + 360.;
if (diff_lon > 180.0) diff_lon = diff_lon - 360.;
xedif = w * (diff_lon)/90.;
if (Math.abs(xedif) > 2.0)
{
xele = Double.NaN;
xlin = Double.NaN;
}
else
{
xele = xcol - xedif*rpix;
xlin = isign*t*rpix + xrow;
}
} // end if (xlat == xlat && xlon == xlon)
linele[indexLine][point] = xlin;
linele[indexEle][point] = xele;
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
/**
* Converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele)
{
double xlin, xele;
double xldif, xedif;
double w;
double xlat, xlon;
double ylat, ylon;
double snlt, cslt, snln, csln, r, tnlt, z;
int number = linele[0].length;
float[][] latlon = new float[2][number];
// Convert from file to Image coordinates for calculations
float[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xldif = Math.abs(xlin - xrow)/rpix;
xedif = (xcol - xele)/rpix;
// WLH 8 March 2000
// if (xldif > 1.0)
if (xlin != xlin || xele != xele || xldif > 1.0)
{
xlat = Double.NaN;
xlon = Double.NaN;
}
else
{
w = Math.sqrt(1.0 - xldif*xldif);
if (w == 0.0 || Math.abs(xedif/w) > 2.0)
{
xlat = Double.NaN;
xlon = Double.NaN;
}
else
{
xlat = Math.asin((Math.asin(xldif)+
xldif*w)/1.57080)/DEGREES_TO_RADIANS;
if (xlin > xrow) xlat = -xlat;
// Compute angular displacement from std longitude (XQLON)
xlon = -90.*(xedif/w);
xlon = xqlon - xlon;
// Force angles to (-180 < XLON < 180)
if (xlon > 180.) xlon = xlon - 360.;
if (xlon < -180.) xlon = xlon + 360.;
// Convert to cartesian? coordinates
if (itype == 1)
{
// LLCART(YLAT,YLON,XLAT,XLON,Z)
ylat=DEGREES_TO_RADIANS*xlat;
if (kcord >= 0)
ylat = Math.atan2(bsq*Math.sin(ylat),
asq*Math.cos(ylat));
ylon = kwest*DEGREES_TO_RADIANS*xlon;
snlt = Math.sin(ylat);
cslt = Math.cos(ylat);
csln = Math.cos(ylon);
snln = Math.sin(ylon);
tnlt = Math.pow((snlt/cslt),2.0);
r = ab*Math.sqrt((1.0+tnlt)/(bsq+asq*tnlt));
xlat = r*cslt*csln;
xlon = r*cslt*snln;
z = r*snlt;
}
}
}
// transform from McIDAS (west positive longitude) coordinates
if (isEastPositive) xlon = -xlon;
latlon[indexLat][point] = (float) xlat;
latlon[indexLon][point] = (float) xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon)
{
double x, y, z;
double xlin, xele;
double xlat, xlon;
double flat, t, t2, w, diff_lon, xedif;
int isign, ilat;
int number = latlon[0].length;
float[][] linele = new float[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west longitude positive) coordinates
xlon = isEastPositive
? - latlon[indexLon][point]
: latlon[indexLon][point];
// WLH 8 March 2000
if (Double.isNaN(xlat) || Double.isNaN(xlon) ||
(Math.abs(xlat) > 90.) ) { // DRM 10 June 2003
xele = Double.NaN;
xlin = Double.NaN;
}
else {
// if in cartesian coords, transform to lat/lon
if (itype == 1)
{
x = xlat;
y = xlon;
// CALL CARTLL(X,Y,Z,XLAT,XLON)
}
isign = -1;
if (xlat < 0.0) isign = 1;
ilat = (int) (Math.abs(xlat));
flat = Math.abs(xlat) - ilat;
t = lattbl[ilat];
if (ilat != 90) t = t + flat*(lattbl[ilat+1] - lattbl[ilat]);
t2 = Math.max(0.0, 1.0-t*t);
w = Math.sqrt(t2);
//** Here we need to handle the problem of computing
//** angular differences across the dateline.
diff_lon = xlon - xqlon;
if (diff_lon < -180.0) diff_lon = diff_lon + 360.;
if (diff_lon > 180.0) diff_lon = diff_lon - 360.;
xedif = w * (diff_lon)/90.;
if (Math.abs(xedif) > 2.0)
{
xele = Double.NaN;
xlin = Double.NaN;
}
else
{
xele = xcol - xedif*rpix;
xlin = isign*t*rpix + xrow;
}
} // end if (xlat == xlat && xlon == xlon)
linele[indexLine][point] = (float) xlin;
linele[indexEle][point] = (float) xele;
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,488 +0,0 @@
//
// MSATnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for Meteosat (MSAT) type nav. This code was modified
* from the original FORTRAN code (nvxmsat.dlm) on the McIDAS system. It
* only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class MSATnav extends AREAnav
{
private boolean isEastPositive = true;
final double NOMORB=42164.; // nominal radial distance of satellite (km)
final double EARTH_RADIUS=6378.155; // earth equatorial radius (km)
int itype;
double h;
double a;
double rp;
double lpsi2;
double deltax;
double deltay;
double rflon; // reference longitude;
double sublon;
int[] ioff = new int[3];
/**
* Set up for the real math work. Must pass in the int array
* of the MSAT nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a MSAT type.
*/
public MSATnav (int[] iparms)
throws IllegalArgumentException
{
/* No longer needed. Kept for consistency with nvxmsat.dlm
if (ifunc != 1)
{
if (iparms[0] == XY ) itype = 1;
if (iparms[0] == LL ) itype = 2;
return;
}
*/
if (iparms[0] != MSAT )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
itype = 2;
System.arraycopy(iparms, 3, ioff, 0, 3);
h = (double) NOMORB - EARTH_RADIUS;
a = 1./297.;
rp = EARTH_RADIUS / (1. + a);
lpsi2=1;
deltax=18./2500.;
deltay=18./2500.;
rflon=0.0;
sublon = McIDASUtil.integerLatLonToDouble(iparms[6]);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double xele, xlin;
double ylat, ylon;
double xele2, xlin2;
double xfi, xla, z;
double x, y;
double xr, yr;
double tanx, tany;
double val1, val2;
double yk;
double vmu;
double cosrf, sinrf;
double teta;
double xt, yt, zt;
double rs;
int number = linele[0].length;
double[][] latlon = new double[2][number];
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xele2 = xele/2.;
xlin2 = xlin/2.;
x = 1250.5 - xele2;
y = ioff[2] - (xlin2 + ioff[1] - ioff[0]);
xr = x;
yr = y;
x = xr*lpsi2*deltax*DEGREES_TO_RADIANS;
y = yr*lpsi2*deltay*DEGREES_TO_RADIANS;
rs = EARTH_RADIUS + h;
tanx = Math.tan(x);
tany = Math.tan(y);
val1=1.+tanx*tanx;
val2=1.+(tany*tany)*((1.+a)*(1.+a));
yk=rs/EARTH_RADIUS;
if ((val1*val2) > ((yk*yk)/(yk*yk-1)))
{
latlon[indexLat][point] = Double.NaN;
latlon[indexLon][point] = Double.NaN;
}
else
{
vmu = (rs-(EARTH_RADIUS*(Math.sqrt((yk*yk)-
(yk*yk-1)*val1*val2))))/(val1*val2);
cosrf = Math.cos(rflon*DEGREES_TO_RADIANS);
sinrf = Math.sin(rflon*DEGREES_TO_RADIANS);
xt = (rs*cosrf) + (vmu*(tanx*sinrf - cosrf));
yt = (rs*sinrf) - (vmu*(tanx*cosrf + sinrf));
zt = vmu*tany/Math.cos(x);
teta = Math.asin(zt/rp);
xfi = (Math.atan(((Math.tan(teta))*EARTH_RADIUS)/rp))*
RADIANS_TO_DEGREES;
xla=-Math.atan(yt/xt)*RADIANS_TO_DEGREES;
// change longitude for correct subpoint
xla = xla + sublon;
// see if we have to convert to x, y, z
if (itype == 1)
{
ylat = xfi;
ylon = xla;
// NLLXYZ(YLAT,YLON,XFI,XLA,Z)
}
// put longitude into East Positive (form)
if (isEastPositive) xla = -xla;
latlon[indexLat][point] = xfi;
latlon[indexLon][point] = xla;
} // end lat/lon point calculation
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double x, y, z;
double x1, y1;
double xlat, xlon;
double xfi, xla;
double rom;
double r1, r2;
double coslo, sinlo;
double teta;
double xt, yt, zt;
double px, py;
double rs;
double reph, rpph;
double xr, yr;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
x1 = latlon[indexLat][point];
// expects positive East Longitude.
y1 = isEastPositive
? latlon[indexLon][point]
: -latlon[indexLon][point];
// if in cartesian coords, transform to lat/lon
if (itype == 1)
{
x = latlon[indexLat][point];
y = latlon[indexLon][point];
// NXYZLL(x,y,z,zlat,zlon);
y1 = -y1;
}
// correct for sublon
y1 = y1 + sublon;
xfi = x1*DEGREES_TO_RADIANS;
xla = y1*DEGREES_TO_RADIANS;
rom =
(EARTH_RADIUS*rp)/
Math.sqrt(
rp*rp*Math.cos(xfi)*Math.cos(xfi)+
EARTH_RADIUS*EARTH_RADIUS*Math.sin(xfi)*Math.sin(xfi));
y = Math.sqrt(h*h+rom*rom-2*h*rom*Math.cos(xfi)*Math.cos(xla));
r1 = y*y + rom*rom;
r2 = h*h;
if (r1 > r2) // invalid point
{
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
}
else // calculate line an element
{
rs = EARTH_RADIUS + h;
reph = EARTH_RADIUS;
rpph = rp;
coslo = Math.cos(rflon*DEGREES_TO_RADIANS);
sinlo = Math.sin(rflon*DEGREES_TO_RADIANS);
teta = Math.atan((rpph/reph)*Math.tan(xfi));
xt = reph*Math.cos(teta)*Math.cos(xla);
yt = reph*Math.cos(teta)*Math.sin(xla);
zt = rpph*Math.sin(teta);
px = Math.atan((coslo*(yt-rs*sinlo)-(xt-rs*coslo)*sinlo)/
(sinlo*(yt-rs*sinlo)+(xt-rs*coslo)*coslo));
py = Math.atan(zt*((Math.tan(px)*sinlo-
coslo)/(xt-rs*coslo))*Math.cos(px));
px = px*RADIANS_TO_DEGREES;
py = py*RADIANS_TO_DEGREES;
xr = px/(deltax*lpsi2);
yr = py/(deltay*lpsi2);
xr = 1250.5-xr;
yr = yr + ioff[2] + ioff[1] - ioff[0];
xr = xr*2;
yr = 5000-yr*2;
linele[indexLine][point] = yr;
linele[indexEle][point] = xr;
} // end calculations
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele)
{
double xele, xlin;
double ylat, ylon;
double xele2, xlin2;
double xfi, xla, z;
double x, y;
double xr, yr;
double tanx, tany;
double val1, val2;
double yk;
double vmu;
double cosrf, sinrf;
double teta;
double xt, yt, zt;
double rs;
int number = linele[0].length;
float[][] latlon = new float[2][number];
// Convert array to Image coordinates for computations
float[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xele2 = xele/2.;
xlin2 = xlin/2.;
x = 1250.5 - xele2;
y = ioff[2] - (xlin2 + ioff[1] - ioff[0]);
xr = x;
yr = y;
x = xr*lpsi2*deltax*DEGREES_TO_RADIANS;
y = yr*lpsi2*deltay*DEGREES_TO_RADIANS;
rs = EARTH_RADIUS + h;
tanx = Math.tan(x);
tany = Math.tan(y);
val1=1.+tanx*tanx;
val2=1.+(tany*tany)*((1.+a)*(1.+a));
yk=rs/EARTH_RADIUS;
if ((val1*val2) > ((yk*yk)/(yk*yk-1)))
{
latlon[indexLat][point] = Float.NaN;
latlon[indexLon][point] = Float.NaN;
}
else
{
vmu = (rs-(EARTH_RADIUS*(Math.sqrt((yk*yk)-
(yk*yk-1)*val1*val2))))/(val1*val2);
cosrf = Math.cos(rflon*DEGREES_TO_RADIANS);
sinrf = Math.sin(rflon*DEGREES_TO_RADIANS);
xt = (rs*cosrf) + (vmu*(tanx*sinrf - cosrf));
yt = (rs*sinrf) - (vmu*(tanx*cosrf + sinrf));
zt = vmu*tany/Math.cos(x);
teta = Math.asin(zt/rp);
xfi = (Math.atan(((Math.tan(teta))*EARTH_RADIUS)/rp))*
RADIANS_TO_DEGREES;
xla=-Math.atan(yt/xt)*RADIANS_TO_DEGREES;
// change longitude for correct subpoint
xla = xla + sublon;
// see if we have to convert to x, y, z
if (itype == 1)
{
ylat = xfi;
ylon = xla;
// NLLXYZ(YLAT,YLON,XFI,XLA,Z)
}
// put longitude into East Positive (form)
if (isEastPositive) xla = -xla;
latlon[indexLat][point] = (float) xfi;
latlon[indexLon][point] = (float) xla;
} // end lat/lon point calculation
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon)
{
double x, y, z;
double x1, y1;
double xlat, xlon;
double xfi, xla;
double rom;
double r1, r2;
double coslo, sinlo;
double teta;
double xt, yt, zt;
double px, py;
double rs;
double reph, rpph;
double xr, yr;
int number = latlon[0].length;
float[][] linele = new float[2][number];
for (int point=0; point < number; point++)
{
x1 = latlon[indexLat][point];
// expects positive East Longitude.
y1 = isEastPositive
? latlon[indexLon][point]
: -latlon[indexLon][point];
// if in cartesian coords, transform to lat/lon
if (itype == 1)
{
x = latlon[indexLat][point];
y = latlon[indexLon][point];
// NXYZLL(x,y,z,zlat,zlon);
y1 = -y1;
}
// correct for sublon
y1 = y1 + sublon;
xfi = x1*DEGREES_TO_RADIANS;
xla = y1*DEGREES_TO_RADIANS;
rom =
(EARTH_RADIUS*rp)/
Math.sqrt(
rp*rp*Math.cos(xfi)*Math.cos(xfi)+
EARTH_RADIUS*EARTH_RADIUS*Math.sin(xfi)*Math.sin(xfi));
y = Math.sqrt(h*h+rom*rom-2*h*rom*Math.cos(xfi)*Math.cos(xla));
r1 = y*y + rom*rom;
r2 = h*h;
if (r1 > r2) // invalid point
{
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
}
else // calculate line an element
{
rs = EARTH_RADIUS + h;
reph = EARTH_RADIUS;
rpph = rp;
coslo = Math.cos(rflon*DEGREES_TO_RADIANS);
sinlo = Math.sin(rflon*DEGREES_TO_RADIANS);
teta = Math.atan((rpph/reph)*Math.tan(xfi));
xt = reph*Math.cos(teta)*Math.cos(xla);
yt = reph*Math.cos(teta)*Math.sin(xla);
zt = rpph*Math.sin(teta);
px = Math.atan((coslo*(yt-rs*sinlo)-(xt-rs*coslo)*sinlo)/
(sinlo*(yt-rs*sinlo)+(xt-rs*coslo)*coslo));
py = Math.atan(zt*((Math.tan(px)*sinlo-
coslo)/(xt-rs*coslo))*Math.cos(px));
px = px*RADIANS_TO_DEGREES;
py = py*RADIANS_TO_DEGREES;
xr = px/(deltax*lpsi2);
yr = py/(deltay*lpsi2);
xr = 1250.5-xr;
yr = yr + ioff[2] + ioff[1] - ioff[0];
xr = xr*2;
yr = 5000-yr*2;
linele[indexLine][point] = (float) yr;
linele[indexEle][point] = (float) xr;
} // end calculations
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,427 +0,0 @@
//
// MSGTnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for MSG type nav. This code was modified
* from the original FORTRAN code (nvxmsgt.dlm) on the McIDAS system. It
* only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Tom Whittaker
*/
public final class MSGTnav extends AREAnav
{
private boolean isEastPositive = true;
final double NOMORB=42164.; // nominal radial distance of satellite (km)
final double EARTH_RADIUS=6378.155; // earth equatorial radius (km)
int itype;
double h;
double a;
double rp;
double cdr;
double crd;
double rs, yk;
double deltax;
double deltay;
int LOFF, COFF, LFAC, CFAC;
int[] ioff = new int[3];
boolean first = true;
int count = 0;
double sublon = 0.0;
/**
* Set up for the real math work. Must pass in the int array
* of the MSGT nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a MSGT type.
*/
public MSGTnav (int[] iparms) throws IllegalArgumentException {
if (iparms[0] != MSGT )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
itype = 2;
LOFF = iparms[1];
COFF = iparms[2];
LFAC = iparms[3];
CFAC = iparms[4];
sublon = iparms[5]/10000.;
if (isEastPositive) sublon = -sublon;
h = NOMORB - EARTH_RADIUS;
rs = EARTH_RADIUS + h;
yk = rs/EARTH_RADIUS;
a = 1./297.;
rp = EARTH_RADIUS / (1. + a);
crd = 180. / Math.PI;
cdr = Math.PI / 180.;
deltax = 1.0/(CFAC/1000000.);
deltay = 1.0/(LFAC/1000000.);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele) {
int number = linele[0].length;
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
double[][] latlon = imglinele;
double xlin, xele, xr, yr, tanx, tany, v1, v2;
double vmu, xt, yt, zt, teta, xlat, xlon;
for (int point=0; point < number; point++)
{
if (Double.isNaN(imglinele[indexLine][point]) ||
Double.isNaN(imglinele[indexEle][point])) {
continue;
}
xlin = 11136.0 - imglinele[indexLine][point] + 1.0;
xele = 11136.0 - imglinele[indexEle][point] + 1.0;
xlin = (xlin + 2.0) / 3.0;
xele = (xele + 2.0) / 3.0;
xr = xele - (COFF/10.);
yr = xlin - (LOFF/10.);
xr = xr*deltax*cdr;
yr = yr*deltay*cdr;
tanx = Math.tan(xr);
tany = Math.tan(yr);
v1 = 1. + tanx*tanx;
v2 = 1. + (tany*tany)*((1.+a)*(1.+a));
if (v1*v2 > ((yk*yk)/(yk*yk-1))) {
xlat = Double.NaN;
xlon = Double.NaN;
} else {
vmu = (rs - EARTH_RADIUS*Math.sqrt(yk*yk-(yk*yk-1)*v1*v2))/(v1*v2);
xt = rs - vmu;
yt = - vmu*tanx;
zt = vmu * tany/Math.cos(xr);
teta = Math.asin(zt/rp);
xlat = Math.atan(Math.tan(teta)*EARTH_RADIUS/rp) * crd;
xlon = Math.atan(yt/xt) * crd;
}
// put longitude into East Positive (form)
xlon = xlon + sublon;
if (!isEastPositive) xlon = -xlon;
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon) {
int number = latlon[0].length;
double[][] linele = new double[2][number];
double xfi, xla, rom, y, r1, r2, teta, xt, yt, zt;
double px, py, xr, yr, xele, xlin;
double xlat, xlon;
if (first) {
//System.out.println("#### first time...");
first = false;
}
for (int point=0; point < number; point++)
{
if (Double.isNaN(latlon[indexLat][point]) ||
Double.isNaN(latlon[indexLon][point])) {
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
continue;
}
xlat = latlon[indexLat][point];
// expects positive East Longitude.
xlon = isEastPositive
? latlon[indexLon][point]
: -latlon[indexLon][point];
xlon = xlon - sublon;
xfi = xlat*cdr;
xla = xlon*cdr;
rom = EARTH_RADIUS*rp/Math.sqrt(rp*rp*Math.cos(xfi) *
Math.cos(xfi)+EARTH_RADIUS*EARTH_RADIUS *
Math.sin(xfi)*Math.sin(xfi));
y = Math.sqrt(h*h + rom*rom - 2.*h*rom*Math.cos(xfi)*Math.cos(xla));
r1 = y*y + rom*rom;
r2 = h*h;
if (r1 > r2) {
xlin = Double.NaN;
xele = Double.NaN;
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
} else {
teta = Math.atan((rp/EARTH_RADIUS) * Math.tan(xfi));
xt = EARTH_RADIUS * Math.cos(teta) * Math.cos(xla);
yt = EARTH_RADIUS * Math.cos(teta) * Math.sin(xla);
zt = rp * Math.sin(teta);
px = Math.atan(yt/(xt-rs));
py = Math.atan(-zt/(xt-rs)*Math.cos(px));
px = px*crd;
py = py*crd;
xr = px/deltax;
yr = py/deltay;
xele = (COFF/10.) + xr;
xlin = (LOFF/10.) + yr;
xlin = xlin * 3.0 - 2.0;
xele = xele * 3.0 - 2.0;
linele[indexLine][point] = 11136.0 - xlin + 1.0;
linele[indexEle][point] = 11136.0 - xele + 1.0;
} // end calculations
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele) {
int number = linele[0].length;
// Convert array to Image coordinates for computations
float[][] imglinele = areaCoordToImageCoord(linele);
float[][] latlon = imglinele;
double xlin, xele, xr, yr, tanx, tany, v1, v2;
double vmu, xt, yt, zt, teta, xlat, xlon;
for (int point=0; point < number; point++)
{
if (Float.isNaN(imglinele[indexLine][point]) ||
Float.isNaN(imglinele[indexEle][point])) {
continue;
}
xlin = 11136.0 - imglinele[indexLine][point] + 1.0;
xele = 11136.0 - imglinele[indexEle][point] + 1.0;
xlin = (xlin + 2.0) / 3.0;
xele = (xele + 2.0) / 3.0;
xr = xele - (COFF/10.);
yr = xlin - (LOFF/10.);
xr = xr*deltax*cdr;
yr = yr*deltay*cdr;
tanx = Math.tan(xr);
tany = Math.tan(yr);
v1 = 1. + tanx*tanx;
v2 = 1. + (tany*tany)*((1.+a)*(1.+a));
if (v1*v2 > ((yk*yk)/(yk*yk-1))) {
xlat = Float.NaN;
xlon = Float.NaN;
} else {
vmu = (rs - EARTH_RADIUS*Math.sqrt(yk*yk-(yk*yk-1)*v1*v2))/(v1*v2);
xt = rs - vmu;
yt = - vmu*tanx;
zt = vmu * tany/Math.cos(xr);
teta = Math.asin(zt/rp);
xlat = Math.atan(Math.tan(teta)*EARTH_RADIUS/rp) * crd;
xlon = Math.atan(yt/xt) * crd;
}
// put longitude into East Positive (form)
xlon = xlon + sublon;
if (!isEastPositive) xlon = -xlon;
latlon[indexLat][point] = (float) xlat;
latlon[indexLon][point] = (float) xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon) {
int number = latlon[0].length;
float[][] linele = new float[2][number];
double xfi, xla, rom, y, r1, r2, teta, xt, yt, zt;
double px, py, xr, yr, xele, xlin;
double xlat, xlon;
if (first) {
//System.out.println("#### first time...");
first = false;
}
for (int point=0; point < number; point++)
{
if (Float.isNaN(latlon[indexLat][point]) ||
Float.isNaN(latlon[indexLon][point])) {
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
continue;
}
xlat = latlon[indexLat][point];
// expects positive East Longitude.
xlon = isEastPositive
? latlon[indexLon][point]
: -latlon[indexLon][point];
xlon = xlon - sublon;
xfi = xlat*cdr;
xla = xlon*cdr;
rom = EARTH_RADIUS*rp/Math.sqrt(rp*rp*Math.cos(xfi) *
Math.cos(xfi)+EARTH_RADIUS*EARTH_RADIUS *
Math.sin(xfi)*Math.sin(xfi));
y = Math.sqrt(h*h + rom*rom - 2.*h*rom*Math.cos(xfi)*Math.cos(xla));
r1 = y*y + rom*rom;
r2 = h*h;
if (r1 > r2) {
xlin = Float.NaN;
xele = Float.NaN;
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
} else {
teta = Math.atan((rp/EARTH_RADIUS) * Math.tan(xfi));
xt = EARTH_RADIUS * Math.cos(teta) * Math.cos(xla);
yt = EARTH_RADIUS * Math.cos(teta) * Math.sin(xla);
zt = rp * Math.sin(teta);
px = Math.atan(yt/(xt-rs));
py = Math.atan(-zt/(xt-rs)*Math.cos(px));
px = px*crd;
py = py*crd;
xr = px/deltax;
yr = py/deltay;
xele = (COFF/10.) + xr;
xlin = (LOFF/10.) + yr;
xlin = xlin * 3.0 - 2.0;
xele = xele * 3.0 - 2.0;
linele[indexLine][point] = (float)(11136.0 - xlin + 1.0);
linele[indexEle][point] = (float)(11136.0 - xele + 1.0);
} // end calculations
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,416 +0,0 @@
//
// MSGnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
/*
This code was modified from the original Fortran code on the
McIDAS system. The code in this file is Copyright(C) 2005 by Tom
Whittaker & Don Murray. It is designed to be used with the VisAD system
for interactive analysis and visualization of numerical data.
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for MSG type nav. This code was modified
* from the original FORTRAN code (nvxmsgt.dlm) on the McIDAS system. It
* only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class MSGnav extends AREAnav
{
private boolean isEastPositive = true;
final double NOMORB=42164.; // nominal radial distance of satellite (km)
final double EARTH_RADIUS=6378.169; // earth equatorial radius (km)
int itype;
double h;
double a;
double rp;
double cdr;
double crd;
double rs, yk;
double deltax;
double deltay;
int[] ioff = new int[3];
int count = 0;
double sublon = 0.0;
/**
* Set up for the real math work. Must pass in the int array
* of the MSG nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a MSG type.
*/
public MSGnav (int[] iparms) throws IllegalArgumentException {
if (iparms[0] != MSG )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
itype = 2;
h = NOMORB - EARTH_RADIUS;
rs = EARTH_RADIUS + h;
yk = rs/EARTH_RADIUS;
a = 1./297.;
rp = EARTH_RADIUS / (1. + a);
crd = 180. / Math.PI;
cdr = Math.PI / 180.;
//sublon = McIDASUtil.integerLatLonToDouble(iparms[1]);
sublon = iparms[1]/10000.;
if (isEastPositive) sublon = -sublon;
deltax = 17.832/3712.;
deltay = 17.832/3712.;
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele) {
int number = linele[0].length;
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
double[][] latlon = imglinele;
double xlin, xele, xr, yr, tanx, tany, v1, v2;
double vmu, xt, yt, zt, teta, xlat, xlon;
for (int point=0; point < number; point++)
{
if (Double.isNaN(imglinele[indexLine][point]) ||
Double.isNaN(imglinele[indexEle][point])) {
continue;
}
xlin = 3713. - imglinele[indexLine][point]/3.0;
xele = 3713. - imglinele[indexEle][point]/3.0;
xr = xele - 1856.;
yr = xlin - 1856.;
xr = xr*deltax*cdr;
yr = yr*deltay*cdr;
tanx = Math.tan(xr);
tany = Math.tan(yr);
v1 = 1. + tanx*tanx;
v2 = 1. + (tany*tany)*((1.+a)*(1.+a));
if (yk*yk-(yk*yk-1)*v1*v2 <= 0.0) {
xlat = Double.NaN;
xlon = Double.NaN;
} else {
vmu = (rs - EARTH_RADIUS*Math.sqrt(yk*yk-(yk*yk-1)*v1*v2))/(v1*v2);
xt = rs - vmu;
yt = - vmu*tanx;
zt = vmu * tany/Math.cos(xr);
teta = Math.asin(zt/rp);
xlat = Math.atan(Math.tan(teta)*EARTH_RADIUS/rp) * crd;
xlon = Math.atan(yt/xt) * crd;
}
// put longitude into East Positive (form)
xlon = xlon + sublon;
if (!isEastPositive) xlon = -xlon;
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon) {
int number = latlon[0].length;
double[][] linele = new double[2][number];
double xfi, xla, rom, y, r1, r2, teta, xt, yt, zt;
double px, py, xr, yr, xele, xlin;
double xlat, xlon;
for (int point=0; point < number; point++)
{
if (Double.isNaN(latlon[indexLat][point]) ||
Double.isNaN(latlon[indexLon][point])) {
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
continue;
}
xlat = latlon[indexLat][point];
// expects positive East Longitude.
xlon = isEastPositive
? latlon[indexLon][point]
: -latlon[indexLon][point];
xlon = xlon - sublon;
xfi = xlat*cdr;
xla = xlon*cdr;
rom = EARTH_RADIUS*rp/Math.sqrt(rp*rp*Math.cos(xfi) *
Math.cos(xfi)+EARTH_RADIUS*EARTH_RADIUS *
Math.sin(xfi)*Math.sin(xfi));
y = Math.sqrt(h*h + rom*rom - 2.*h*rom*Math.cos(xfi)*Math.cos(xla));
r1 = y*y + rom*rom;
r2 = h*h;
if (r1 > r2) {
xlin = Double.NaN;
xele = Double.NaN;
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
} else {
teta = Math.atan((rp/EARTH_RADIUS) * Math.tan(xfi));
xt = EARTH_RADIUS * Math.cos(teta) * Math.cos(xla);
yt = EARTH_RADIUS * Math.cos(teta) * Math.sin(xla);
zt = rp * Math.sin(teta);
px = Math.atan(yt/(xt-rs));
py = Math.atan(-zt/(xt-rs)*Math.cos(px));
px = px*crd;
py = py*crd;
xr = px/deltax;
yr = py/deltay;
xele = 1857. - xr;
xlin = 1857. - yr;
xlin = 3713.0 - xlin;
xele = 3713.0 - xele;
xlin = 3. * 3712 - 3. * xlin + 3;
xele = 3. * 3712 - 3. * xele + 3;
linele[indexLine][point] = xlin - 1;
linele[indexEle][point] = xele - 1;
} // end calculations
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele) {
int number = linele[0].length;
// Convert array to Image coordinates for computations
float[][] imglinele = areaCoordToImageCoord(linele);
float[][] latlon = imglinele;
double xlin, xele, xr, yr, tanx, tany, v1, v2;
double vmu, xt, yt, zt, teta, xlat, xlon;
for (int point=0; point < number; point++)
{
if (Float.isNaN(imglinele[indexLine][point]) ||
Float.isNaN(imglinele[indexEle][point])) {
continue;
}
xlin = 3713. - imglinele[indexLine][point]/3.0;
xele = 3713. - imglinele[indexEle][point]/3.0;
xr = xele - 1856.;
yr = xlin - 1856.;
xr = xr*deltax*cdr;
yr = yr*deltay*cdr;
tanx = Math.tan(xr);
tany = Math.tan(yr);
v1 = 1. + tanx*tanx;
v2 = 1. + (tany*tany)*((1.+a)*(1.+a));
if (yk*yk-(yk*yk-1)*v1*v2 <= 0.0) {
xlat = Float.NaN;
xlon = Float.NaN;
} else {
vmu = (rs - EARTH_RADIUS*Math.sqrt(yk*yk-(yk*yk-1)*v1*v2))/(v1*v2);
xt = rs - vmu;
yt = - vmu*tanx;
zt = vmu * tany/Math.cos(xr);
teta = Math.asin(zt/rp);
xlat = Math.atan(Math.tan(teta)*EARTH_RADIUS/rp) * crd;
xlon = Math.atan(yt/xt) * crd;
}
// put longitude into East Positive (form)
xlon = xlon + sublon;
if (!isEastPositive) xlon = -xlon;
latlon[indexLat][point] = (float) xlat;
latlon[indexLon][point] = (float) xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon) {
int number = latlon[0].length;
float[][] linele = new float[2][number];
double xfi, xla, rom, y, r1, r2, teta, xt, yt, zt;
double px, py, xr, yr, xele, xlin;
double xlat, xlon;
for (int point=0; point < number; point++)
{
if (Float.isNaN(latlon[indexLat][point]) ||
Float.isNaN(latlon[indexLon][point])) {
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
continue;
}
xlat = latlon[indexLat][point];
// expects positive East Longitude.
xlon = isEastPositive
? latlon[indexLon][point]
: -latlon[indexLon][point];
xlon = xlon - sublon;
xfi = xlat*cdr;
xla = xlon*cdr;
rom = EARTH_RADIUS*rp/Math.sqrt(rp*rp*Math.cos(xfi) *
Math.cos(xfi)+EARTH_RADIUS*EARTH_RADIUS *
Math.sin(xfi)*Math.sin(xfi));
y = Math.sqrt(h*h + rom*rom - 2.*h*rom*Math.cos(xfi)*Math.cos(xla));
r1 = y*y + rom*rom;
r2 = h*h;
if (r1 > r2) {
xlin = Float.NaN;
xele = Float.NaN;
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
} else {
teta = Math.atan((rp/EARTH_RADIUS) * Math.tan(xfi));
xt = EARTH_RADIUS * Math.cos(teta) * Math.cos(xla);
yt = EARTH_RADIUS * Math.cos(teta) * Math.sin(xla);
zt = rp * Math.sin(teta);
px = Math.atan(yt/(xt-rs));
py = Math.atan(-zt/(xt-rs)*Math.cos(px));
px = px*crd;
py = py*crd;
xr = px/deltax;
yr = py/deltay;
xele = 1857. - xr;
xlin = 1857. - yr;
xlin = 3713.0 - xlin;
xele = 3713.0 - xele;
xlin = 3. * 3712 - 3. * xlin + 3;
xele = 3. * 3712 - 3. * xele + 3;
linele[indexLine][point] = (float) (xlin - 1);
linele[indexEle][point] = (float) (xele - 1);
} // end calculations
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,50 +0,0 @@
//
// McIDASException.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* McIDASException class is to handle exceptions when dealing
* with McIDAS files or data.
*
* @author Don Murray - Unidata
*/
public class McIDASException extends Exception {
/**
* Constructs a McIDASException with no specified detail message.
*/
public McIDASException() {super(); }
/**
* Constructs a McIDASException with the specified detail message.
*
* @param s the detail message.
*/
public McIDASException(String s) {super(s); }
}

View file

@ -1,513 +0,0 @@
//
// McIDASUtil.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.Date;
import java.util.TimeZone;
import java.io.*;
import edu.wisc.ssec.mcidas.AreaFile;
/**
* Class for static McIDAS utility methods. In many cases, these
* methods are the Java equivalents of McIDAS library functions.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray, Unidata
* @author Tom Whittaker, SSEC
*/
public final class McIDASUtil {
/** McIDAS missing value for 4-byte integers */
public static final int MCMISSING = 0x80808080;
/**
* Converts a packed integer (SIGN DDD MM SS) latitude/longitude to double.
* Java version of McIDAS <code>flalo</code> function except returns a
* double instead of a float.
*
* @param value integer containing the packed data
* @return double representation of value
*/
public static double integerLatLonToDouble(int value) {
return mcPackedIntegerToDouble(value);
}
/**
* Converts a double latitude/longitude to a packed integer (SIGN DDD MM SS)
* Java version of McIDAS <code>ilalo</code> function.
*
* @param value double value of lat/lon
*
* @param dvalue
* @return packed integer representation of value
*/
public static int doubleLatLonToInteger(double dvalue) {
return mcDoubleToPackedInteger(dvalue);
}
/**
* Converts a packed integer (SIGN DDD/HH MM SS) latitude/longitude
* or time (hours) to double.
* Java replacements of McIDAS <code>flalo</code> and <code>ftime</code>
* functions except returns a double instead of a float.
*
* @param value integer containing the packed data
* @return double representation of value
*/
public static double mcPackedIntegerToDouble(int value) {
int val = value < 0
? -value
: value;
double dvalue = ((double)(val / 10000) +
((double)((val / 100) % 100)) / 60.0 +
(double)(val % 100) / 3600.0);
return (value < 0)
? -dvalue
: dvalue;
}
/**
* Converts a double latitude/longitude or time (hours) to a
* packed integer (SIGN DDD/HH MM SS). Java replacements of McIDAS
* <code>ilalo</code> and <code>m0itime</code> functions.
*
* @param value double value of lat/lon or time
*
* @param dvalue
* @return packed integer representation of value
*/
public static int mcDoubleToPackedInteger(double dvalue) {
double dval = dvalue < 0
? -dvalue
: dvalue;
int j = (int)(3600.0 * dval + 0.5);
int value = 10000 * (j / 3600) + 100 * ((j / 60) % 60) + j % 60;
return (dvalue < 0.0)
? -value
: value;
}
/**
* Calculate difference in minutes between two dates/times. Java
* version of timdif.for
*
* @param yrday1 Year/day of first time (yyddd or yyyyddd)
* @param hms1 Hours/minutes/seconds of first time (hhmmss).
* @param yrday2 Year/day of second time (yyddd).
* @param hms2 Hours/minutes/seconds of second time (hhmmss).
*
* @return The difference between the two times (time2 - time1),
* in minutes. If the first time is greater than the second,
* the result will be negative.
*/
public static double timdif(int yrday1, int hms1, int yrday2, int hms2) {
long secs1 = mcDayTimeToSecs(yrday1, hms1);
long secs2 = mcDayTimeToSecs(yrday2, hms2);
return (double)(secs2 - secs1) / 60.;
}
/**
* Create a calendar to be used for mcDayTimeToSecs.
* Use this to minimize object creation overhead when calling the method
* many times.
*
* @return A calendar to use for mcDayTimeToSecs.
*/
public static GregorianCalendar makeCalendarForDayTimeToSecs() {
GregorianCalendar cal = new GregorianCalendar();
cal.setTimeZone(TimeZone.getTimeZone("GMT"));
cal.set(Calendar.ERA, GregorianCalendar.AD);
/*
allow us to specify # of days since the year began without having
worry about leap years and seconds since the day began, instead
of in the minute. Saves on some calculations.
*/
cal.setLenient(true);
return cal;
}
/**
*
* Convert day (yyddd or yyyyddd) and time (hhmmss) to seconds since
* the epoch (January 1, 1970, 00:00GMT). Java version of 'mcdaytimetosecs'
* except it returns a long instead of an int.
*
* @param yearday year/day in either yyddd or yyyyddd format.
* Only works for years > 1900.
* @param time time in packed integer format (hhmmss)
*
* @return seconds since the epoch
*
*/
public static long mcDayTimeToSecs(int yearday, int time) {
return mcDayTimeToSecs(yearday, time, null);
}
/**
* Convert day (yyddd or yyyyddd) and time (hhmmss) to seconds since
* the epoch (January 1, 1970, 00:00GMT). Java version of 'mcdaytimetosecs'
* except it returns a long instead of an int.
*
* @param yearday year/day in either yyddd or yyyyddd format.
* Only works for years > 1900.
* @param time time in packed integer format (hhmmss)
* @param cal If non-null then use this calendar to do the formatting.
* else create a new one. Note: The calendar you pass in should be
* one created from makeCalendarForDayTimeToSecs
*
* @return seconds since the epoch
*
*/
public static long mcDayTimeToSecs(int yearday, int time,
GregorianCalendar cal) {
//jeffmc: Add the cal parameter to this method
if (cal == null) {
cal = makeCalendarForDayTimeToSecs();
}
int year = ((yearday / 1000) % 1900) + 1900; // convert to yyyyddd first
int day = yearday % 1000;
double seconds = mcPackedIntegerToDouble(time) * 3600.;
cal.clear();
cal.set(Calendar.DAY_OF_YEAR, day);
cal.set(Calendar.YEAR, year);
int secs = ((int)Math.round(seconds * 1000)) / 1000;
cal.set(Calendar.SECOND, secs);
cal.set(Calendar.MILLISECOND, 0);
//jeffmc: Change:
// return cal.getTime().getTime()/1000;
//to:
return cal.getTimeInMillis() / 1000;
}
/**
* Convert date (yymmdd or yyyymmdd) and hms (hhmmss) to seconds since
* the epoch (January 1, 1970, 00:00GMT).
*
* @param date year/day in yyymmdd format.
* Only works for years > 1900.
* @param time time in packed integer format (hhmmss)
*
* @return seconds since the epoch
*
*/
public static long mcDateHmsToSecs(int date, int time) {
int year = date / 10000;
if (year < 50) {
year = year + 2000;
}
else if (year < 1000) {
year = year + 1900;
}
int month = (date % 10000) / 100;
int day = date % 100;
/**
* jeffmc: Comment these out?
* System.out.println("year = " + year);
* System.out.println("month = " + month);
* System.out.println("day = " + day);
*/
double seconds = mcPackedIntegerToDouble(time) * 3600.;
GregorianCalendar cal = new GregorianCalendar();
cal.clear();
cal.setTimeZone(TimeZone.getTimeZone("GMT"));
cal.set(Calendar.ERA, GregorianCalendar.AD);
cal.set(Calendar.YEAR, year);
cal.set(Calendar.MONTH, month - 1); // stupid Calendar.MONTH is 0 based
cal.set(Calendar.DAY_OF_MONTH, day);
int secs = ((int)Math.round(seconds * 1000)) / 1000;
cal.set(Calendar.SECOND, secs);
cal.set(Calendar.MILLISECOND, 0);
return cal.getTime().getTime() / 1000;
}
/**
* Convert seconds since the epoch (January 1, 1970, 00:00GMT) to
* day (yyyyddd) and time (hhmmss). Java version of
* 'mcsecstodaytime' except it returns an int array instead of pointers
*
* @param secs seconds since the epoch
*
* @return int[2] array with day (yyyyddd) as first element and
* time (hhmmss - packed integer) as second element.
*/
public static int[] mcSecsToDayTime(long secs) {
int[] retvals = new int[2];
GregorianCalendar cal = new GregorianCalendar();
cal.clear();
cal.setTimeZone(TimeZone.getTimeZone("GMT"));
cal.setTime(new Date(secs * 1000));
retvals[0] = (cal.get(cal.YEAR) * 1000) + cal.get(cal.DAY_OF_YEAR);
retvals[1] = (cal.get(cal.HOUR_OF_DAY) * 10000) +
(cal.get(cal.MINUTE) * 100) + cal.get(cal.SECOND);
return retvals;
}
/**
* Convert an HMS integer to a string of form hh:mm:ss.
* @param hms integer hhmmss
* @return string representation
*/
public static String mcHmsToStr(int hms) {
StringBuffer buf = new StringBuffer();
int hours = (int)hms / 10000;
int mins = (int)(hms % 10000) / 100;
int secs = hms % 100;
buf.append(padZero(hours, 2));
buf.append(":");
buf.append(padZero(mins, 2));
buf.append(":");
buf.append(padZero(secs, 2));
return buf.toString();
}
/**
* Left pad the given value with zeros up to the number of digits
*
* @param value The value.
* @param numDigits number of digits
* @return The String represenation of the value, padded with
* leading "0"-s if value &lt; 10E(numDigits-1)
*/
public static String padZero(int value, int numDigits) {
return padLeft(String.valueOf(value), numDigits, "0");
}
/**
* Pad the given string with padString on the left up to the given length.
*
* @param s String to pad
* @param desiredLength ending length
* @param padString String to pad with (e.g, " ")
* @return padded String
*/
public static String padLeft(String s, int desiredLength,
String padString) {
while(s.length() < desiredLength) {
s = padString + s;
}
return s;
}
/**
* Flip the bytes of an integer.
*
* @param val value to swap
*
* @return
*/
public static int swbyt4(int val) {
int[] vals = new int[] {val};
flip(vals, 0, 0);
return vals[0];
}
/**
* Flip the bytes of an integer array. Java version of 'm0swbyt4'.
*
* @param array array of integers to be flipped
* @param first starting element of the array
* @param num number of values to swap
*/
public static void swbyt4(int[] array, int first, int num) {
flip(array, first, first + num - 1);
}
/**
* Flip the bytes of an integer array. Java version of 'm0swbyt4'.
*
* @param array[] array of integers to be flipped
*
* @param array
* @param first starting element of the array
* @param last last element of array to flip
*
*/
public static void flip(int array[], int first, int last) {
int i, k;
for (i = first; i <= last; i++) {
k = array[i];
array[i] = ((k >>> 24) & 0xff) | ((k >>> 8) & 0xff00)
| ((k & 0xff) << 24) | ((k & 0xff00) << 8);
}
}
/**
* convert four consequtive bytes into a (signed) int. This
* is useful in dealing with McIDAS data files.
*
* @param byte[] array of 4 bytes
*
* @param b
* @param off is the offset into the byte array
*
*
* @return
*/
public static int bytesToInteger(byte[] b, int off) {
int k = (b[off] << 24) + ((b[off + 1] << 16) & 0xff0000) +
((b[off + 2] << 8) & 0xff00) + ((b[off + 3] << 0) & 0xff);
return k;
}
/**
* convert consequtive bytes into a (signed) int array. This
* is useful in dealing with McIDAS data files.
*
* @param byte[] array of bytes
*
* @param b
* @param off is the offset into the byte array
* @param num number of integers to create
*
*
* @return
*/
public static int[] bytesToIntegerArray(byte[] b, int off, int num) {
int[] values = new int[num];
for (int i = 0; i < num; i++) {
byte[] bytes = new byte[4];
System.arraycopy(b, i * 4, bytes, 0, 4);
values[i] = bytesToInteger(bytes, 0);
}
return values;
}
/**
* convert signed int to a String representation. This is useful
* in dealing with McIDAS data files. Java version of 'clit'.
*
* @param value - integer representation of a string
*
* @return String representation of the int
*/
public static String intBitsToString(int value) {
byte[] bval = new byte[4];
bval[0] = (byte)((value & 0xff000000) >>> 24);
bval[1] = (byte)((value & 0x00ff0000) >>> 16);
bval[2] = (byte)((value & 0x0000ff00) >>> 8);
bval[3] = (byte)((value & 0x000000ff) >>> 0);
return new String(bval);
}
/**
* convert signed int array to a String representation. This is useful
* in dealing with McIDAS data files. Java version of 'movwc'.
*
* @param values - integer array representation of a string
*
* @return String representation of the int array
*/
public static String intBitsToString(int[] values) {
StringBuffer sb = new StringBuffer();
for (int i = 0; i < values.length; i++)
sb.append(intBitsToString(values[i]));
return sb.toString();
}
/**
* Check to see if the int value is the representation of a
* string or not. Java version of ischar_.c (sort of).
*
* @param value integer representation
* @return true if the int represents a string
*/
public static boolean isChar(int value) {
String valueString = intBitsToString(value);
char[] chars = valueString.toCharArray();
for (int i = 0; i < 4; i++) {
if (!Character.UnicodeBlock.of(chars[i]).equals(
Character.UnicodeBlock.BASIC_LATIN) || Character.isISOControl(
chars[i]))
return false;
}
return true;
}
/**
* Serialize an AreaFile object to disk
*
* @param filename - name of disk file to write to
* @param af
* @return true if no Exception; false otherwise
*/
public static boolean putAreaFile(String filename, AreaFile af) {
try {
OutputStream os = new FileOutputStream(filename);
ObjectOutput oo = new ObjectOutputStream(os);
oo.writeObject(af);
oo.close();
return true;
}
catch (Exception e) {
e.printStackTrace();
return false;
}
}
/**
* De-serialize an AreaFile object from disk
*
* @param filename - name of disk file to read
*
* @return AreaFile if okay; null otherwise
*/
public static AreaFile getAreaFile(String filename) {
try {
InputStream is = new FileInputStream(filename);
ObjectInput oi = new ObjectInputStream(is);
AreaFile af = (AreaFile)oi.readObject();
oi.close();
return af;
}
catch (Exception ei) {
ei.printStackTrace();
return null;
}
}
}

View file

@ -1,185 +0,0 @@
//
// PSnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for Polar Stereographic (PS) type nav. This code was
* modified from the original FORTRAN code (nvxps.dlm) on the McIDAS system.
* It only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class PSnav extends AREAnav
{
private boolean isEastPositive = true;
int iwest;
int ihem;
double xrow;
double xcol;
double xpole;
double xlat1;
double xspace;
double xqlon;
double xblat;
double fac;
/**
* Set up for the real math work. Must pass in the int array
* of the PS nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a RECT type.
*/
public PSnav (int[] iparms)
throws IllegalArgumentException
{
if (iparms[0] != PS )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
xrow = iparms[1];
xcol = iparms[2];
int ipole = iparms[10];
if (ipole == 0) ipole = 900000;
ihem = 1;
if (ipole < 0) ihem = -1;
xpole = McIDASUtil.integerLatLonToDouble(ipole);
xlat1 =
McIDASUtil.integerLatLonToDouble(ipole - iparms[3]) *
DEGREES_TO_RADIANS;
xspace = iparms[4]/1000.;
xqlon = McIDASUtil.integerLatLonToDouble(iparms[5]);
double r = iparms[6]/1000.;
iwest = iparms[9];
if (iwest >= 0) iwest = 1;
xblat = r * Math.sin(xlat1)/(xspace*Math.tan(xlat1*.5));
fac = 1;
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double xldif;
double xedif;
double xlon;
double xlat;
double xrlon, radius;
int number = linele[0].length;
double[][] latlon = new double[2][number];
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xldif = ihem * (imglinele[indexLine][point] - xrow)/xblat;
xedif = (xcol - imglinele[indexEle][point])/xblat;
xrlon = 0;
if (!(xldif == 0. && xedif == 0.))
xrlon = Math.atan2(xedif, xldif);
xlon = iwest * xrlon/DEGREES_TO_RADIANS + xqlon;
if (xlon > 180.) xlon -= 360.;
if (xlon < -180.) xlon += 360.;
radius = Math.sqrt(xldif*xldif + xedif*xedif);
if (Math.abs(radius) < 1.e-10)
xlat = ihem*90;
else
xlat = ihem*(90. - 2*Math.atan(
Math.exp(Math.log(radius/fac)))/DEGREES_TO_RADIANS);
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = (iwest == 1) ? -xlon : xlon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double xlon;
double xlat;
double xrlon, xclat, xrlat;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west positive longitude) coordinates
xlon = (iwest == 1)
? -latlon[indexLon][point]
: latlon[indexLon][point];
xrlon = ihem*(xlon-xqlon);
if (xrlon > 180.) xrlon -= 360.;
if (xrlon < -180.) xrlon += 360.;
xrlon = iwest*xrlon*DEGREES_TO_RADIANS;
xclat = (xpole-xlat)*DEGREES_TO_RADIANS*.5;
xrlat = xblat*Math.tan(xclat);
linele[indexLine][point] = xrlat*Math.cos(xrlon) + xrow;
linele[indexEle][point] = -xrlat*Math.sin(xrlon) + xcol;
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,362 +0,0 @@
//
// RADRnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for Radar (RADR) type nav. This code was modified
* from the original FORTRAN code (nvxradr.dlm) on the McIDAS system. It
* only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class RADRnav extends AREAnav
{
private boolean isEastPositive = true;
final double EARTH_RADIUS=6371.23; // earth equatorial radius (km)
final int MISS = McIDASUtil.MCMISSING;
int itype;
double xrow;
double xcol;
double xlat;
double xlon;
double xrot;
double xblat;
double xblon;
/**
* Set up for the real math work. Must pass in the int array
* of the RADR nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a RADR type.
*/
public RADRnav (int[] iparms)
throws IllegalArgumentException
{
/* No longer needed. Kept for consistency with nvxradr.dlm
if (ifunc != 1)
{
if (iparms[0] == XY ) itype = 1;
if (iparms[0] == LL ) itype = 2;
return;
}
*/
if (iparms[0] != RADR )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
itype = 2;
xrow = iparms[1];
xcol = iparms[2];
xlat = McIDASUtil.integerLatLonToDouble(iparms[3]);
xlon = McIDASUtil.integerLatLonToDouble(iparms[4]);
double xspace = iparms[5]/1000.;
double yspace = xspace;
if (iparms[7] != 0 && iparms[7] != MISS)
yspace = iparms[7]/1000.;
xrot = -DEGREES_TO_RADIANS*iparms[6]/1000.;
xblat = EARTH_RADIUS*DEGREES_TO_RADIANS/xspace;
xblon = EARTH_RADIUS*DEGREES_TO_RADIANS/yspace;
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double xldif;
double xedif;
double xlin;
double xele;
double xdis;
double xangl;
double xange;
double ylat;
double ylon;
int number = linele[0].length;
//double[][] latlon = new double[2][number];
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
double[][] latlon = imglinele;
for (int point=0; point < number; point++)
{
xldif = xrow - imglinele[indexLine][point];
xedif = xcol - imglinele[indexEle][point];
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > 0.001)
{
xangl = Math.atan2(xldif, xedif) - 90.*DEGREES_TO_RADIANS;
xange = Math.atan2(xldif, xedif) + 90.*DEGREES_TO_RADIANS;
xldif = xdis*Math.cos(xrot+xangl);
xedif = xdis*Math.sin(xrot+xange);
}
ylat = xlat + xldif/xblat;
ylon = xlon + xedif/xblon/Math.cos(ylat* DEGREES_TO_RADIANS);
// transform from McIDAS coordinates
if (isEastPositive) ylon = -ylon;
latlon[indexLat][point] = ylat;
latlon[indexLon][point] = ylon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double zlat;
double zlon;
double xrlon;
double xrlat;
double xldif;
double xedif;
double xdis;
double xangl;
double xange;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
if (Double.isNaN(latlon[indexLat][point]) ||
Double.isNaN(latlon[indexLon][point])) {
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
continue;
}
zlat = latlon[indexLat][point];
// transform to McIDAS (west positive longitude) coordinates
zlon = isEastPositive
? -latlon[indexLon][point]
: latlon[indexLon][point];
if (zlon > 180) zlon -= 360;
if (zlon < -180) zlon += 360;
xrlon = zlon - xlon;
xrlat = zlat - xlat;
xldif = xblat*xrlat;
xedif = xrlon*xblon*Math.cos(zlat*DEGREES_TO_RADIANS);
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > .001)
{
xangl = Math.atan2(xldif, xedif)-90*DEGREES_TO_RADIANS;
xange = Math.atan2(xldif, xedif)+90*DEGREES_TO_RADIANS;
xldif = xdis*Math.cos(-xrot+xangl);
xedif = xdis*Math.sin(-xrot+xange);
}
linele[indexLine][point] = xrow - xldif;
linele[indexEle][point] = xcol - xedif;
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele)
{
double xldif;
double xedif;
double xlin;
double xele;
double xdis;
double xangl;
double xange;
double ylat;
double ylon;
int number = linele[0].length;
/*
float[][] latlon = new float[2][number];
float[] lats = latlon[indexLat];
float[] lons = latlon[indexLon];
*/
// Convert array to Image coordinates for computations
float[][] imglinele = areaCoordToImageCoord(linele);
float[][] latlon = imglinele;
float[] lats = latlon[indexLat];
float[] lons = latlon[indexLon];
float[] lines = imglinele[indexLine];
float[] eles = imglinele[indexEle];
for (int point=0; point < number; point++)
{
xldif = xrow - lines[point];
xedif = xcol - eles[point];
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > 0.001)
{
xangl = Math.atan2(xldif, xedif) - 90.*DEGREES_TO_RADIANS;
xange = Math.atan2(xldif, xedif) + 90.*DEGREES_TO_RADIANS;
xldif = xdis*Math.cos(xrot+xangl);
xedif = xdis*Math.sin(xrot+xange);
}
ylat = xlat + xldif/xblat;
ylon = xlon + xedif/xblon/Math.cos(ylat* DEGREES_TO_RADIANS);
// transform from McIDAS coordinates
if (isEastPositive) ylon = -ylon;
lats[point] = (float) ylat;
lons[point] = (float) ylon;
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon)
{
double zlat;
double zlon;
double xrlon;
double xrlat;
double xldif;
double xedif;
double xdis;
double xangl;
double xange;
int number = latlon[0].length;
float[][] linele = new float[2][number];
float[] lines = linele[indexLine];
float[] eles = linele[indexEle];
float[] lats = latlon[indexLat];
float[] lons = latlon[indexLon];
for (int point=0; point < number; point++)
{
if (Float.isNaN(lats[point]) ||
Float.isNaN(lons[point])) {
linele[indexLine][point] = Float.NaN;
linele[indexEle][point] = Float.NaN;
continue;
}
zlat = lats[point];
// transform to McIDAS (west positive longitude) coordinates
zlon = isEastPositive
? -lons[point]
: lons[point];
if (zlon > 180) zlon -= 360;
if (zlon < -180) zlon += 360;
xrlon = zlon - xlon;
xrlat = zlat - xlat;
xldif = xblat*xrlat;
xedif = xrlon*xblon*Math.cos(zlat*DEGREES_TO_RADIANS);
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > .001)
{
xangl = Math.atan2(xldif, xedif)-90*DEGREES_TO_RADIANS;
xange = Math.atan2(xldif, xedif)+90*DEGREES_TO_RADIANS;
xldif = xdis*Math.cos(-xrot+xangl);
xedif = xdis*Math.sin(-xrot+xange);
}
lines[point] = (float) (xrow - xldif);
eles[point] = (float) (xcol - xedif);
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
public boolean equals(Object o)
{
if (!(o instanceof RADRnav)) return false;
RADRnav that = (RADRnav) o;
return (super.equals(o) &&
that.xlat == xlat &&
that.xlon == xlon &&
that.xrow == xrow &&
that.xcol == xcol);
}
}

View file

@ -1,405 +0,0 @@
//
// RECTnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for Radar (RECT) type nav. This code was modified
* from the original FORTRAN code (nvxrect.dlm) on the McIDAS system. It
* only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class RECTnav extends AREAnav
{
private boolean isEastPositive = true;
int itype;
int iwest;
double xrow;
double xcol;
double zslat;
double zslon;
double zdlat;
double zdlon;
//double xlin;
//double xele;
//double xldif;
//double xedif;
//double xlat;
//double xlon;
/**
* Set up for the real math work. Must pass in the int array
* of the RECT nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a RECT type.
*/
public RECTnav (int[] iparms)
throws IllegalArgumentException
{
/* No longer needed. Kept for consistency with nvxrect.dlm
if (ifunc != 1)
{
if (iparms[0] == XY ) itype = 1;
if (iparms[0] == LL ) itype = 2;
return;
}
*/
if (iparms[0] != RECT )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
itype = 2;
xrow = iparms[1];
int ipowlat = iparms[11];
if (ipowlat == 0) ipowlat = 4;
zslat = iparms[2]/Math.pow(10.,ipowlat);
xcol = iparms[3];
int ipowlon = iparms[12];
if (ipowlon == 0) ipowlon = 4;
zslon = iparms[4]/Math.pow(10.,ipowlon);
int ipowdlin = iparms[13];
if (ipowdlin == 0) ipowdlin = 4;
zdlat = iparms[5]/Math.pow(10.,ipowdlin);
int ipowdele = iparms[14];
if (ipowdele == 0) ipowdele = 4;
zdlon = iparms[6]/Math.pow(10.,ipowdele);
int ipowrad = iparms[15];
if (ipowrad == 0) ipowrad = 3;
double drad = iparms[7]/Math.pow(10.,ipowrad);
int ipowecc = iparms[16];
if (ipowecc == 0) ipowecc = 6;
double decc = iparms[8]/Math.pow(10.,ipowecc);
iwest = (iparms[10] >= 0) ? 1 : -1;
if (iwest == 1) isEastPositive = false;
/* Don't know why this was ever here!
xlin = 1;
xele = 1;
xldif = xrow - xlin;
xedif = iwest*(xcol - xele);
xlon = zslon + xedif*zdlon;
xlat = zslat + xldif*zdlat;
zslat = xlat;
zslon = xlon;
xrow = 1;
xcol = 1;
*/
if (xcol == 1) {
zslon=zslon-180.0*iwest;
}
/*
System.out.println("Center line = " + xrow +
"\nCenter elem = " + xcol +
"\n lat = " + zslat +
"\n lon = " + zslon +
"\n zdlat = " + zdlat +
"\n zdlon = " + zdlon +
"\n iwest = " + iwest);
*/
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double xldif;
double xedif;
double xlon;
double xlat;
double xele;
double xlin;
int number = linele[0].length;
double[][] latlon = new double[2][number];
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xldif = xrow - xlin;
if (xcol == 1) {
xedif = iwest * (xele-xcol);
xlon = zslon + 180*iwest-xedif*zdlon;
} else {
xedif = iwest * (xcol-xele);
xlon = zslon + xedif*zdlon;
}
xlat = zslat + xldif*zdlat;
if (xlat > 90. || xlat < -90.)
{
xlat = Double.NaN;
}
if (xlon > (zslon+180) ||
xlon < (zslon-180)) {
xlon = Double.NaN;
}
if (!Double.isNaN(xlon)) {
if (xlon < -180.)
{
xlon = xlon + 360.;
//if (xlon < -180.) xlon = Double.NaN;
}
if (xlon > 180)
{
xlon = xlon - 360.;
//if (xlon > 180.) xlon = Double.NaN;
}
}
if (Double.isNaN(xlat) || Double.isNaN(xlon))
{
latlon[indexLat][point] = Double.NaN;
latlon[indexLon][point] = Double.NaN;
}
else
{
latlon[indexLat][point] = xlat;
latlon[indexLon][point] = (iwest == 1) ? -xlon : xlon;
}
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double xlon;
double xlat;
double xlin;
double xele;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west positive longitude) coordinates
xlon = (iwest == 1)
? -latlon[indexLon][point]
: latlon[indexLon][point];
if (xlon > (zslon+180)) {
xlon = xlon-360;
} else if (xlon < zslon-180) {
xlon = xlon+360;
}
//if (iwest == -1 && xlon < zslon) xlon = xlon +360.;
xlin = xrow - (xlat - zslat)/zdlat;
if (xcol == 1) {
xele = xcol - (xlon - zslon-180*iwest)/(zdlon*iwest);
} else {
xele = xcol - (xlon - zslon)/(zdlon*iwest);
}
linele[indexLine][point] = xlin;
linele[indexEle][point] = xele;
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public float[][] toLatLon(float[][] linele)
{
double xldif;
double xedif;
double xlon;
double xlat;
double xele;
double xlin;
int number = linele[0].length;
float[][] latlon = new float[2][number];
// Convert array to Image coordinates for computations
float[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xldif = xrow - xlin;
if (xcol == 1) {
xedif = iwest * (xele-xcol);
xlon = zslon + 180*iwest-xedif*zdlon;
} else {
xedif = iwest * (xcol-xele);
xlon = zslon + xedif*zdlon;
}
xlat = zslat + xldif*zdlat;
if (xlat > 90. || xlat < -90.)
{
xlat = Double.NaN;
}
if (xlon > (zslon+180) ||
xlon < (zslon-180)) {
xlon = Double.NaN;
}
if (!Double.isNaN(xlon)) {
if (xlon < -180.)
{
xlon = xlon + 360.;
//if (xlon < -180.) xlon = Double.NaN;
}
if (xlon > 180)
{
xlon = xlon - 360.;
//if (xlon > 180.) xlon = Double.NaN;
}
}
if (Double.isNaN(xlat) || Double.isNaN(xlon))
{
latlon[indexLat][point] = Float.NaN;
latlon[indexLon][point] = Float.NaN;
}
else
{
latlon[indexLat][point] = (float) xlat;
latlon[indexLon][point] = (float) ((iwest == 1) ? -xlon : xlon);
}
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* linele[indexLine][] is a line and linele[indexEle][]
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public float[][] toLinEle(float[][] latlon)
{
double xlon;
double xlat;
double xlin;
double xele;
int number = latlon[0].length;
float[][] linele = new float[2][number];
for (int point=0; point < number; point++)
{
xlat = latlon[indexLat][point];
// transform to McIDAS (west positive longitude) coordinates
xlon = (iwest == 1)
? -latlon[indexLon][point]
: latlon[indexLon][point];
if (xlon > (zslon+180)) {
xlon = xlon-360;
} else if (xlon < zslon-180) {
xlon = xlon+360;
}
//if (iwest == -1 && xlon < zslon) xlon = xlon +360.;
xlin = xrow - (xlat - zslat)/zdlat;
if (xcol == 1) {
xele = xcol - (xlon - zslon-180*iwest)/(zdlon*iwest);
} else {
xele = xcol - (xlon - zslon)/(zdlon*iwest);
}
linele[indexLine][point] = (float) xlin;
linele[indexEle][point] = (float) xele;
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,293 +0,0 @@
//
// SINUnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
public final class SINUnav extends AREAnav {
double drad, decc, r;
double xrow, xcol, xlat, xlon;
double xblat, xblon, xspace, yspace;
int itype, iwest;
boolean isEastPositive = true;
public SINUnav(int[] iparms) throws IllegalArgumentException {
if (iparms[0] != SIN )
throw new IllegalArgumentException("Invalid navigation type "+
iparms[0]);
itype = 2;
xrow = iparms[1];
xcol = iparms[2];
xlat = McIDASUtil.integerLatLonToDouble(iparms[3]);
xlon = McIDASUtil.integerLatLonToDouble(iparms[4]);
xspace = iparms[5]/1000.;
yspace = xspace;
drad = iparms[6]/1000.;
r = drad;
decc = iparms[7]/1.e6;
iwest = iparms[9];
if (iwest >= 0) iwest = 1;
xblat = r*DEGREES_TO_RADIANS/xspace;
xblon = DEGREES_TO_RADIANS*r/yspace;
/*
for (int i=0; i<10; i++) {
System.out.println("#### i="+i+" val = "+iparms[i]);
}
*/
}
public double[][] toLatLon(double[][] linele) {
double xlin, xele, xldif, xedif, xdis, ylat, ylon;
int number = linele[0].length;
double[][] latlon = new double[2][number];
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++ ){
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xldif = xrow - xlin;
xedif = xcol - xele;
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > .001) {
double xangl = Math.atan2(xldif, xedif) - 90.*DEGREES_TO_RADIANS;
double xange = Math.atan2(xldif,xedif) + 90.*DEGREES_TO_RADIANS;
xldif = xdis*Math.cos(xangl);
xedif = xdis*Math.sin(xange);
}
ylat = xlat + xldif/xblat;
ylon = iwest * xedif/xblon/Math.cos(ylat*DEGREES_TO_RADIANS);
if (Math.abs(ylon) > 180.0) {
latlon[indexLat][point] = Double.NaN;
latlon[indexLon][point] = Double.NaN;
} else {
ylon = xlon + ylon;
if (ylon < -180.0) {
ylon = ylon + 360.0;
} else if (ylon > 180.0) {
ylon = ylon - 360.0;
}
if (Math.abs(ylat) > 90.0 || Math.abs(ylon) > 180.0) {
latlon[indexLat][point] = Double.NaN;
latlon[indexLon][point] = Double.NaN;
}
if (isEastPositive) ylon = -ylon;
latlon[indexLat][point] = ylat;
latlon[indexLon][point] = ylon;
}
}
return latlon;
}
public double[][] toLinEle(double[][] latlon) {
double xdis, xele, xlin, zlat, zlon, xrlon, xrlat, xldif, xedif;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point<number; point++) {
zlat = latlon[indexLat][point];
zlon = isEastPositive
? -latlon[indexLon][point]
: latlon[indexLon][point];
if (Double.isNaN(zlat) || Double.isNaN(zlon) ||
(Math.abs(zlat) > 90.) ) {
xele = Double.NaN;
xlin = Double.NaN;
} else {
xrlon = iwest*(zlon - xlon);
if (xrlon > 180.) xrlon = xrlon - 360.;
if (xrlon < -180.) xrlon = xrlon + 360.;
xrlat = zlat - xlat;
xldif = xblat*xrlat;
xedif = xrlon*xblon*Math.cos(zlat * DEGREES_TO_RADIANS);
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > .001) {
double xangl = Math.atan2(xldif, xedif) - 90.*DEGREES_TO_RADIANS;
double xange = Math.atan2(xldif, xedif) + 90.*DEGREES_TO_RADIANS;
xldif = xdis * Math.cos(xangl);
xedif = xdis * Math.sin(xange);
}
xlin = xrow - xldif;
xele = xcol - xedif;
}
linele[indexLine][point] = xlin;
linele[indexEle][point] = xele;
}
return imageCoordToAreaCoord(linele, linele);
}
public float[][] toLatLon(float[][] linele) {
double xlin, xele, xldif, xedif, xdis, ylat, ylon;
int number = linele[0].length;
float[][] latlon = new float[2][number];
float[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++ ){
xlin = imglinele[indexLine][point];
xele = imglinele[indexEle][point];
xldif = xrow - xlin;
xedif = xcol - xele;
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > .001) {
double xangl = Math.atan2(xldif, xedif) - 90.*DEGREES_TO_RADIANS;
double xange = Math.atan2(xldif,xedif) + 90.*DEGREES_TO_RADIANS;
xldif = xdis*Math.cos(xangl);
xedif = xdis*Math.sin(xange);
}
ylat = xlat + xldif/xblat;
ylon = iwest * xedif/xblon/Math.cos(ylat*DEGREES_TO_RADIANS);
if (Math.abs(ylon) > 180.0) {
latlon[indexLat][point] = Float.NaN;
latlon[indexLon][point] = Float.NaN;
} else {
ylon = xlon + ylon;
if (ylon < -180.0) {
ylon = ylon + 360.0;
} else if (ylon > 180.0) {
ylon = ylon - 360.0;
}
if (Math.abs(ylat) > 90.0 || Math.abs(ylon) > 180.0) {
latlon[indexLat][point] = Float.NaN;
latlon[indexLon][point] = Float.NaN;
}
if (isEastPositive) ylon = -ylon;
latlon[indexLat][point] = (float) ylat;
latlon[indexLon][point] = (float) ylon;
}
}
return latlon;
}
public float[][] toLinEle(float[][] latlon) {
double xdis, xele, xlin, zlat, zlon, xrlon, xrlat, xldif, xedif;
int number = latlon[0].length;
float[][] linele = new float[2][number];
for (int point=0; point<number; point++) {
zlat = latlon[indexLat][point];
zlon = isEastPositive
? -latlon[indexLon][point]
: latlon[indexLon][point];
if (Double.isNaN(zlat) || Double.isNaN(zlon) ||
(Math.abs(zlat) > 90.) ) {
xele = Double.NaN;
xlin = Float.NaN;
} else {
xrlon = iwest*(zlon - xlon);
if (xrlon > 180.) xrlon = xrlon - 360.;
if (xrlon < -180.) xrlon = xrlon + 360.;
xrlat = zlat - xlat;
xldif = xblat*xrlat;
xedif = xrlon*xblon*Math.cos(zlat * DEGREES_TO_RADIANS);
xdis = Math.sqrt(xldif*xldif + xedif*xedif);
if (xdis > .001) {
double xangl = Math.atan2(xldif, xedif) - 90.*DEGREES_TO_RADIANS;
double xange = Math.atan2(xldif, xedif) + 90.*DEGREES_TO_RADIANS;
xldif = xdis * Math.cos(xangl);
xedif = xdis * Math.sin(xange);
}
xlin = xrow - xldif;
xele = xcol - xedif;
}
linele[indexLine][point] = (float)xlin;
linele[indexEle][point] = (float)xele;
}
return imageCoordToAreaCoord(linele, linele);
}
public static void main(String[] a) {
int[] p = {1397313056, 10000, 10000, 421353,831951,1000,6378388,81992,0,0};
SINUnav sn = new SINUnav(p);
double [][] latlon = new double[2][1];
latlon[0][0] = 43.;
latlon[1][0] = -89.;
System.out.println("#### Doing double");
System.out.println("#### Original latlon="+latlon[0][0]+" "+latlon[1][0]);
double[][] pix = sn.toLinEle(latlon);
System.out.println("#### pix="+pix[0][0]+" "+pix[1][0]);
latlon = sn.toLatLon(pix);
System.out.println("#### latlon="+latlon[0][0]+" "+latlon[1][0]);
System.out.println("#### Now doing float....");
float [][] flatlon = new float[2][1];
flatlon[0][0] = 43.f;
flatlon[1][0] = -89.f;
System.out.println("#### Original flatlon="+flatlon[0][0]+" "+flatlon[1][0]);
float[][] fpix = sn.toLinEle(flatlon);
System.out.println("#### fpix="+fpix[0][0]+" "+fpix[1][0]);
flatlon = sn.toLatLon(fpix);
System.out.println("#### flatlon="+flatlon[0][0]+" "+flatlon[1][0]);
}
}

View file

@ -1,251 +0,0 @@
//
// TANCnav.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas;
/**
* Navigation class for tangent cone (TANC) type nav. This code was
* modified from the original FORTRAN code (nvxtanc.dlm) on the McIDAS system.
* It only supports latitude/longitude to line/element transformations (LL)
* and vice/versa. Transform to 'XYZ' not implemented.
* @see <A HREF="http://www.ssec.wisc.edu/mug/prog_man/prog_man.html">
* McIDAS Programmer's Manual</A>
*
* @author Don Murray
*/
public final class TANCnav extends AREAnav
{
private boolean isEastPositive = true;
int iwest;
int ihem;
double lin0; // image line of pole
double ele0; // image element of pole
double scale; // km per unit image coordinate
double lon0; // standard longitude
double lat0; // standard latitude
double coscl; // cosine of standard colatitude
double tancl; // tangent of standard colatitude
double tancl2; // tangent of standard colatitude/2
double mxtheta; // limit of angle from std. lon on proj surface
private static double Erad = 6371.2; // earth radius
/**
* Set up for the real math work. Must pass in the int array
* of the TANC nav 'codicil'.
*
* @param iparms the nav block from the image file
* @throws IllegalArgumentException
* if the nav block is not a TANC type or the parameters are
* bogus
*/
public TANCnav (int[] iparms)
throws IllegalArgumentException
{
if (iparms[0] != TANC )
throw new IllegalArgumentException("Invalid navigation type" +
iparms[0]);
lin0 = iparms[1]/10000.;
ele0 = iparms[2]/10000.;
scale = iparms[3]/10000.;
lat0 = iparms[4]/10000.;
lon0 = iparms[5]/10000.;
if (scale <= 0 || lat0 <= -90. || lat0 >= 90. ||
lat0 == 0 || lon0 <= -180. || lon0 >= 180.)
throw new IllegalArgumentException("Invalid nav parameters");
lon0 = -lon0 * DEGREES_TO_RADIANS; // convert to radians
double colat0;
if (lat0 < 0)
colat0 = Math.PI/2. + lat0*DEGREES_TO_RADIANS;
else
colat0 = Math.PI/2. - lat0*DEGREES_TO_RADIANS;
coscl = Math.cos(colat0);
tancl = Math.tan(colat0);
tancl2 = Math.tan(colat0/2.);
mxtheta = Math.PI*coscl;
}
/** converts from satellite coordinates to latitude/longitude
*
* @param linele[][] array of line/element pairs. Where
* linele[indexLine][] is a 'line' and
* linele[indexEle][] is an element. These are in
* 'file' coordinates (not "image" coordinates.)
*
* @return latlon[][] array of lat/long pairs. Output array is
* latlon[indexLat][] of latitudes and
* latlon[indexLon][] of longitudes.
*
*/
public double[][] toLatLon(double[][] linele)
{
double d_lin;
double d_ele;
double lon;
double lat;
double radius;
double theta_rh;
int number = linele[0].length;
double[][] latlon = new double[2][number];
// Convert array to Image coordinates for computations
double[][] imglinele = areaCoordToImageCoord(linele);
for (int point=0; point < number; point++)
{
d_lin = imglinele[indexLine][point] - lin0;
d_ele = imglinele[indexEle][point] - ele0;
if ( Math.abs(d_lin) < 0.01 && Math.abs(d_ele) < 0.01)
{
radius = 0.0;
theta_rh = 0.0;
}
else
{
double dx = scale*(d_lin);
double dy = scale*(d_ele);
radius = Math.sqrt(dx*dx + dy*dy);
theta_rh = Math.atan2(dy, dx);
}
// convert theta_rh to angle FROM standard longitude (theta)
// maintaining theta positive from positive x-axis.
double theta;
if (lat0 < 0.)
{
theta = (theta_rh <= 0.)
? Math.PI - Math.abs(theta_rh)
: -1.*(Math.PI - Math.abs(theta_rh));
}
else theta = theta_rh;
// Apply range checking on theta to determine if point is navigable
if (theta <= -mxtheta || theta > mxtheta)
{
latlon[indexLat][point] = Double.NaN;
latlon[indexLon][point] = Double.NaN;
}
else
{
lon = lon0 + theta/coscl;
if (lon <= -Math.PI) lon = lon + 2.*Math.PI;
if (lon > Math.PI) lon = lon - 2.*Math.PI;
double colat =
2.* Math.atan(
tancl2*Math.pow(radius/(Erad*tancl),1./coscl));
// convert to degrees
lon = lon/DEGREES_TO_RADIANS;
lat = 90. - colat/DEGREES_TO_RADIANS;
latlon[indexLat][point] = (lat0 < 0) ? -1*lat : lat;
latlon[indexLon][point] = lon;
}
} // end point for loop
return latlon;
}
/**
* toLinEle converts lat/long to satellite line/element
*
* @param latlon[][] array of lat/long pairs. Where latlon[indexLat][]
* are latitudes and latlon[indexLon][] are longitudes.
*
* @return linele[][] array of line/element pairs. Where
* is an element. These are in 'file' coordinates
* (not "image" coordinates);
*/
public double[][] toLinEle(double[][] latlon)
{
double lon;
double lat;
int number = latlon[0].length;
double[][] linele = new double[2][number];
for (int point=0; point < number; point++)
{
lat = latlon[indexLat][point];
lon = latlon[indexLon][point];
if (lat <= -90. || lat >= 90. || lon <= -360. ||
lon > 360.)
{
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
}
else
{
double colat =
(lat0 < 0)
? Math.PI/2. + DEGREES_TO_RADIANS*lat
: Math.PI/2. - DEGREES_TO_RADIANS*lat;
double in_lon = DEGREES_TO_RADIANS*lon;
// map longitude into range -Pi to Pi
if (in_lon <= -Math.PI) in_lon = in_lon + 2.*Math.PI;
if (in_lon > Math.PI) in_lon = in_lon - 2.*Math.PI;
// Now trap opposite Pole. Though a physically possible latitude,
// tan(colat/2) -> infinity there so it is not navigable
if (colat == Math.PI)
{
linele[indexLine][point] = Double.NaN;
linele[indexEle][point] = Double.NaN;
}
else
{
double radius =
Erad * tancl *
Math.pow(Math.tan(colat/2.)/tancl2, coscl);
double theta = in_lon-lon0;
if (theta <= -Math.PI) theta = theta + 2*Math.PI;
if (theta > Math.PI) theta = theta - 2*Math.PI;
theta = coscl * theta;
// Compute line and element, check for northern or southern
// hemisphere projection cone. Put north pole on top of frame,
// south pole on bottom. Maintain right-handed coordinate system
// by measuring theta positive from the positive x-axis.
if (lat0 < 0) theta = Math.PI + theta;
linele[indexLine][point] =
lin0 + radius*Math.cos(theta)/scale;
linele[indexEle][point] =
ele0 + radius*Math.sin(theta)/scale;
}
}
} // end point loop
// Return in 'File' coordinates
return imageCoordToAreaCoord(linele, linele);
}
}

View file

@ -1,183 +0,0 @@
//
// AddeDatasetURL.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
/**
* A subclass of AddeURL to support queries on datasets.
* <pre>
*
* URLs must all have the following format:
*
* adde://host/request?keyword_1=value_1&amp;keyword_2=value_2
*
* group=&lt;groupname&gt; ADDE dataset group
* descr=&lt;descriptor&gt; ADDE dataset descriptor
* user=&lt;user_id&gt; ADDE user identification
* proj=&lt;proj #&gt; a valid ADDE project number
* trace=&lt;0/1&gt; setting to 1 tells server to write debug
* trace file
* version= ADDE version number, currently 1 except for
* griddata requests
* debug= set to true to watch the printlns stream by
* compress= set to "gzip" if you want to use the GZIP
* compression or "compress" if you want to use
* transfers in Unix compress format (You need to
* have the VisAD package if you want to support
* this.) default = none.
* port= Socket port to connect on. Overridden by
* a port specified in the host
* (e.g., adde.ucar.edu:500)
* </pre>
*/
public class AddeDatasetURL extends AddeURL {
/** Keyword for dataset group */
public static final String KEY_GROUP = "GROUP";
/** Keyword for dataset descriptor */
public static final String KEY_DESCRIPTOR = "DESCRIPTOR";
/**
* Dataset name
*/
private String group = null;
/**
* Dataset name
*/
private String descriptor = null;
/**
* Create an ADDE URL
*/
public AddeDatasetURL() {}
/**
* Create an ADDE Dataset URL from the given spec
* @param host host to send to
* @param requestType type of request (REQ_*)
* @param group ADDE group
*/
public AddeDatasetURL(String host, String requestType, String group) {
this(host, requestType, group, null);
}
/**
* Create an ADDE Dataset URL from the given spec
* @param host host to send to
* @param requestType type of request (REQ_*)
* @param group ADDE group
* @param descriptor ADDE descriptor (may be null)
*/
public AddeDatasetURL(String host, String requestType, String group,
String descriptor) {
this(host, requestType, group, descriptor, null);
}
/**
* Create an ADDE URL from the given spec
* @param host host to send to
* @param requestType type of request (REQ_*)
* @param group ADDE group
* @param descriptor ADDE descriptor (may be null)
* @param extraKeys extraKeys string (key/value pairs)
*/
public AddeDatasetURL(String host, String requestType, String group,
String descriptor, String extraKeys) {
super(host, requestType, extraKeys);
this.group = group;
this.descriptor = descriptor;
}
/**
* Make the query portion of the URL (e.g., key1=value1&amp;key2=value2..)
* Subclasses should override.
*
* @return the query portion of the URL
*/
protected String makeQuery() {
StringBuffer buf = new StringBuffer(super.makeQuery());
if (getGroup() != null) appendKeyValue(buf, KEY_GROUP, getGroup());
if (getDescriptor() != null)
appendKeyValue(buf, KEY_DESCRIPTOR, getDescriptor());
return buf.toString();
}
/**
* Get the group for this ADDE URL
* @return the group
*/
public String getGroup() {
return group;
}
/**
* Set the group for this ADDE URL
* @param group the group
*/
public void setGroup(String group) {
this.group = group;
}
/**
* Get the dataset descriptor for this ADDE URL
* @return the dataset descriptor
*/
public String getDescriptor() {
return descriptor;
}
/**
* Set the dataset descriptor for this ADDE URL
* @param desc the dataset descriptor
*/
public void setDescriptor(String desc) {
this.descriptor = desc;
}
/**
* Parse the query string and set the values accordingly, subclasses
* should extend to parse their particular keywords
* @param query query string
*/
protected void parseQuery(String query) {
super.parseQuery(query);
String test = getValue(query, KEY_GROUP);
if (test != null) {
setGroup(test);
}
// should be able to do this, but old URLS have desc
//test = getValue(query, KEY_DESCRIPTOR);
test = getValue(query, "DESC");
if (test != null) {
setDescriptor(test);
}
}
}

View file

@ -1,53 +0,0 @@
//
// AddeException.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import edu.wisc.ssec.mcidas.McIDASException;
/**
* AddeException class is to handle exceptions when dealing
* with ADDE access to data. More general than AddeURLException
*
* @author Don Murray - Unidata
*/
public class AddeException extends McIDASException
{
/**
* Constructs an AddeException with no specified detail message.
*/
public AddeException() {super(); }
/**
* Constructs an AddeException with the specified detail message.
*
* @param s the detail message.
*/
public AddeException(String s) {super(s); }
}

View file

@ -1,356 +0,0 @@
//
// GridDirList.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.*;
import java.lang.*;
import java.util.*;
import java.io.*;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
//SAG import visad.jmet.*;
//SAG import visad.*;
//SAG import visad.data.mcidas.*;
//SAG import visad.data.units.*;
import edu.wisc.ssec.mcidas.*;
import edu.wisc.ssec.mcidas.adde.*;
/**
* AddeGridReader interface for McIDAS ADDE grid data sets. Simulates a
* McIDAS GRDLIST request using an ADDE URL.
*
* <pre>
* URLs must all have the following format:
*
* for directory listing:
*
* adde://host/griddirectory?keyword_1=value_1&amp;keyword_2=value_2
*
* or (for data)
*
* adde://host/griddata?keyword_1=value_1&amp;keyword_2=value_2
*
* there can be any valid combination of the following supported keywords:
*
* group=&lt;groupname&gt; ADDE group name
* descr=&lt;descriptor&gt; ADDE descriptor name
* param=&lt;param list&gt; parameter code list
* time=&lt;model run time&gt; time in hhmmss format
* day=&lt;model run day&gt; day in ccyyddd format
* lev=&lt;level list&gt; list of requested levels (value or SFC, MSL
* or TRO)
* ftime=&lt;forecast time&gt; valid time (hhmmss format) (use with fday)
* fday=&lt;forecast day&gt; forecast day (ccyyddd)
* fhour=&lt;forecast hours&gt; forecast hours (offset from model run time)
* (hhmmss format)
* lat=&lt;min lat&gt; &lt;max lat&gt; latitude bounding box (needs lon specified)
* lon=&lt;min lon&gt; &lt;max lon&gt; longitude bounding box (needs lat specified)
* row=&lt;min row&gt; &lt;max row&gt; row bounding box (needs col specified)
* col=&lt;min col&gt; &lt;max col&gt; column bounding box (needs row specified)
* skip=&lt;row&gt; &lt;col&gt; skip factors for rows and columns (def = 1 1)
* gpro=&lt;pro&gt; grid projection (e.g. TANC)
* src=&lt;s1&gt; ... &lt;s2&gt; list of grid sources (ETA, AVN, etc)
* drange=&lt;btime&gt; &lt;etime&gt; &lt;inc&gt; range of primary days
* that the grid represents (cannot use with
* day=)
* frange=&lt;btime&gt; &lt;etime&gt; &lt;inc&gt; range of forecast times
* that the grid represents (cannot use with
* fhour=, fday= or ftime=)
* trange=&lt;btime&gt; &lt;etime&gt; &lt;inc&gt; range of primary times
* that the grid represents (cannot use with time=)
* num=&lt;max&gt; maximum number of grids (nn) to return (def=1)
*
* the following keywords are required:
*
* group
* descr
*
* an example URL might look like:
* adde://viper/griddirectory?group=rtmodel&amp;descr=eta
* </pre>
*
* @author Tom Whittaker
*
*/
public class AddeGridReader {
// load protocol for ADDE URLs
// See java.net.URL for explanation of URL handling
static {
try
{
String handlers = System.getProperty("java.protocol.handler.pkgs");
String newProperty = null;
if (handlers == null)
newProperty = "edu.wisc.ssec.mcidas";
else if (handlers.indexOf("edu.wisc.ssec.mcidas") < 0)
newProperty = "edu.wisc.ssec.mcidas | " + handlers;
if (newProperty != null) // was set above
System.setProperty("java.protocol.handler.pkgs", newProperty);
}
catch (Exception e)
{
System.out.println(
"Unable to set System Property: java.protocol.handler.pkgs");
}
}
private DataInputStream dis; // input stream
private int status=0; // read status
private URLConnection urlc; // URL connection
private char[] data; // data returned from server
private final int HEARTBEAT = 11223344;
ArrayList fileHeaders, gridHeaders, gridData;
/**
* allows reading of McIDAS grid headers and data
*
*/
public AddeGridReader() {
}
/**
* creates an ArrayList of McIDASGridDirectories
*
* @param request ADDE URL to read from. See class javadoc.
*
* <pre>
* an example URL might look like:
* adde://viper/griddirectory?group=gvar&amp;type=image
* </pre>
*
* @exception AddeURLException if there are no datasets of the particular
* type or there is an error reading data
*
*/
public ArrayList getGridDirectory (String request) throws AddeURLException {
URL url;
gridHeaders = new ArrayList();
fileHeaders = new ArrayList();
try {
url = new URL(request);
urlc = url.openConnection();
InputStream is = urlc.getInputStream();
dis = new DataInputStream(new BufferedInputStream(is));
} catch (AddeURLException ae) {
throw new AddeURLException("Dataset not found: "+ae);
}
catch (Exception e) {
throw new AddeURLException("Error opening connection: " + e);
}
int numBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
if (numBytes == 0) {
status = -1;
throw new AddeURLException("No datasets found");
}
try {
int check;
byte[] header = new byte[256];
while (numBytes == 4) {
check = dis.readInt();
if (check != HEARTBEAT) {
System.out.println("problem...not heartbeat = "+check);
}
numBytes = dis.readInt();
}
//System.out.println("numBytes = "+numBytes);
while ( (check = dis.readInt()) == 0) {
dis.readFully(header,0,256);
String head = new String(header,0,32);
fileHeaders.add(head);
//System.out.println("File Header="+head);
int check2;
while( (check2 = dis.readInt()) == 0) {
dis.readFully(header,0,256);
String name = new String(header,24,4);
//SAG McIDASGridDirectory mg = new McIDASGridDirectory(header);
//System.out.println(mg.toString());
//SAG gridHeaders.add(mg);
}
//System.out.println("check2 = "+check2);
}
//System.out.println("check = "+check);
} catch (Exception re) {System.out.println(re);}
return gridHeaders;
}
public ArrayList getGridHeaders() {
return gridHeaders;
}
public ArrayList getFileHeaders() {
return fileHeaders;
}
/**
* creates an ArrayList of arrays of data, plus an ArrayList
* of grid headers (McIDASGridDirectories) which are then
* available using the getGridHeaders() method.
*
* @param request ADDE URL to read from. See class javadoc.
*
* <pre>
* an example URL might look like:
* adde://viper/griddata?group=abom&amp;descr=grid&amp;parm=T&amp;lev=500
* </pre>
*
* @exception AddeURLException if there are no datasets of the particular
* type or there is an error reading data
*
*/
public ArrayList getGridData (String request) throws AddeURLException {
URL url;
gridHeaders = new ArrayList();
gridData = new ArrayList();
try {
url = new URL(request);
urlc = url.openConnection();
InputStream is = urlc.getInputStream();
dis = new DataInputStream(new BufferedInputStream(is));
} catch (AddeURLException ae) {
throw new AddeURLException("Dataset not found: "+ae);
}
catch (Exception e) {
throw new AddeURLException("Error opening connection: " + e);
}
int numBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
if (numBytes == 0) {
status = -1;
throw new AddeURLException("No datasets found");
}
try {
int check;
byte[] header = new byte[256];
while (numBytes == 4) {
check = dis.readInt();
if (check != HEARTBEAT) {
System.out.println("problem...not heartbeat = "+check);
}
numBytes = dis.readInt();
}
//System.out.println("numBytes = "+numBytes);
int checkBytes = dis.readInt();
if (checkBytes != numBytes) {throw new
AddeURLException("Invalid number of bytes returned for grid.");}
int numGrids = dis.readInt();
//System.out.println("numGrids = "+numGrids);
for (int i=0; i<numGrids; i++) {
/* SAG
dis.readFully(header,0,256);
String name = new String(header,24,4);
McIDASGridDirectory mg = new McIDASGridDirectory(header);
System.out.println(mg.toString());
//SAG CoordinateSystem c = mg.getCoordinateSystem();
gridHeaders.add(mg);
int rows = mg.getRows();
int cols = mg.getColumns();
//System.out.println("# rows & cols = "+rows+" "+cols);
double scale = mg.getParamScale();
//System.out.println("param scale = "+scale+" gridType="+mg.getGridType());
double[] ddata = new double[rows*cols];
int n = 0;
// store such that 0,0 is in lower left corner...
for (int nc=0; nc<cols; nc++) {
for (int nr=0; nr<rows; nr++) {
int temp = dis.readInt();
ddata[(rows-nr-1)*cols + nc] = // check for missing value
(temp == McIDASUtil.MCMISSING)
? Double.NaN
: ( (double) temp) / scale ;
}
}
gridData.add(ddata);
SAG */
check = dis.readInt();
//System.out.println("check after grid = "+check+" point value = "+data[100]);
if (check != 0) break;
}
//System.out.println("check = "+check);
} catch (Exception re) {System.out.println(re);}
return gridData;
}
/** test by running 'java edu.wisc.ssec.mcidas.adde.AddeGridReader' */
public static void main (String[] args)
throws Exception
{
String request =
(args.length == 0)
? "adde://sweetpea.ssec.wisc.edu/grid?group=ABOM&descr=GRIDS&pos=302&num=40&lev=500&proj=6999&user=tomw&"
// ? "adde://sweetpea.ssec.wisc.edu/grid?group=ABOM&descr=GRIDS&pos=302&num=2&proj=6999&user=tomw&"
// ? "adde://noaaport.ssec.wisc.edu/grid?group=NGM&descr=12&num=12&proj=6999&user=tomw&"
// ? "adde://noaaport.ssec.wisc.edu/griddirectory?group=NGM&descr=12&num=15&proj=6999&user=tomw&"
// ? "adde://adde.unidata.ucar.edu/griddirectory?group=rtgrids&descr=ngm&num=all&proj=6999&user=tomw&"
: args[0];
AddeGridReader d = new AddeGridReader();
/*
ArrayList v = d.getGridDirectory(request);
ArrayList vh = d.getFileHeaders();
String s = (String) vh.elementAt(0);
System.out.println("File header = "+s);
for (int i=0; i<v.size(); i++) {
McIDASGridDirectory mg = (McIDASGridDirectory) v.elementAt(i);
System.out.println(mg.toString());
}
*/
ArrayList v = d.getGridData(request);
ArrayList vd = d.getGridHeaders();
}
}

View file

@ -1,672 +0,0 @@
//
// AddeImageURL.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.util.Date;
import edu.wisc.ssec.mcidas.McIDASUtil;
/**
* A class for holding the ADDE URL for an image directory or data request.
*
* <pre>
* URLs must all have the following format:
*
* adde://host/request?keyword_1=value_1&amp;keyword_2=value_2
*
* where request can be one of the following:
*
* imagedata - request for data in AreaFile format (AGET)
* imagedirectory - request for image directory information (ADIR)
*
* There can be any valid combination of the following supported keywords:
*
* group=&lt;groupname&gt; ADDE group name
* descr=&lt;descriptor&gt; ADDE descriptor name
* band=&lt;band&gt; spectral band or channel number
* mag=&lt;lmag&gt; &lt;emag&gt; image magnification, postitive for blowup,
* negative for blowdown (default = 1, emag=lmag)
* (imagedata only)
* latlon=&lt;lat&gt; &lt;lon&gt; lat/lon point to center image on (imagedata only)
* linele=&lt;lin&gt; &lt;ele&gt; &lt;type&gt; line/element to center image on (imagedata only)
* place=&lt;placement&gt; placement of lat/lon or linele points (center
* or upperleft (def=center)) (imagedata only)
* pos=&lt;position&gt; request an absolute or relative ADDE position
* number. May use &lt;start&gt; &lt;end&gt; Default
* for &lt;end&gt; is 0 if start&lt;0, or =start otherwise.
* size=&lt;lines&gt; &lt;elements&gt; size of image to be returned (imagedata only)
* unit=&lt;unit&gt; to specify calibration units other than the
* default
* spac=&lt;bytes&gt; number of bytes per data point, 1, 2, or 4
* (imagedata only)
* doc=&lt;yes/no&gt; specify yes to include line documentation
* with image (def=no)
* nav=&lt;lalo&gt; include the lat-lon navigation info and not the O&A.
* aux=&lt;yes/no&gt; specify yes to include auxilliary information
* with image
* time=&lt;time1&gt; &lt;time2&gt; specify the time range of images to select
* (def=latest image if pos not specified)
* day=&lt;day&gt; specify the day of the images to select
* (def=latest image if pos not specified)
* cal=&lt;cal type&gt; request a specific calibration on the image
* (imagedata only)
* id=&lt;stn id&gt; radar station id
* user=&lt;user_id&gt; ADDE user identification
* proj=&lt;proj #&gt; a valid ADDE project number
* trace=&lt;0/1&gt; setting to 1 tells server to write debug
* trace file
* version= ADDE version number, currently 1 except for
* griddata requests
* debug= set to true to watch the printlns stream by
* compress= set to "gzip" if you want to use the GZIP
* compression or "compress" if you want to use
* transfers in Unix compress format (You need to
* have the VisAD package if you want to support
* this.) default = none.
* port= Socket port to connect on. Overridden by
* a port specified in the host
* (e.g., adde.ucar.edu:500)
* </pre>
*
*/
public class AddeImageURL extends AddeDatasetURL {
/** Keyword for band */
public static final String KEY_BAND = "BAND";
/** Keyword for position */
public static final String KEY_POS = "POS";
/** Keyword for station id */
public static final String KEY_ID = "ID";
/** Keyword for lat/lon request */
public static final String KEY_LATLON = "LATLON";
/** Keyword for lin/ele request */
public static final String KEY_LINEELE = "LINELE";
/** Keyword for location */
public static final String KEY_LOC = "LOC";
/** Keyword for mag */
public static final String KEY_MAG = "MAG";
/** Keyword for number of items */
public static final String KEY_NUM = "NUM";
/** Keyword for place */
public static final String KEY_PLACE = "PLACE";
/** Keyword for size */
public static final String KEY_SIZE = "SIZE";
/** Keyword for spacing */
public static final String KEY_SPAC = "SPAC";
/** Keyword for calibration unit */
public static final String KEY_UNIT = "UNIT";
/** Keyword for navigation type */
public static final String KEY_NAV = "NAV";
/** Keyword for aux request */
public static final String KEY_AUX = "AUX";
/** Keyword for doc request */
public static final String KEY_DOC = "DOC";
/** Keyword for day request */
public static final String KEY_DAY = "DAY";
/** Keyword for time request */
public static final String KEY_TIME = "TIME";
/** number of lines */
private int lines;
/** number of elements */
private int elements;
/** element magnification */
private int emag = 1;
/** line magnification */
private int lmag = 1;
/** default placement value (CENTER, ULEFT) */
private static String DEFAULT_PLACE_VALUE = "ULEFT";
/** default key for location (LATLON, LINELE) */
private static String DEFAULT_LOCATE_KEY = "LINELE";
/** default value for location */
private static String DEFAULT_LOCATE_VALUE = "0 0";
/** default key for location (LATLON, LINELE) */
private String locateKey = DEFAULT_LOCATE_KEY;
/** placement value (CENTER, ULEFT) */
private String placeValue = DEFAULT_PLACE_VALUE;
/** value for location */
private String locateValue = DEFAULT_LOCATE_VALUE;
/** band */
private String band = ALL;
/** band */
private String unit = DEFAULT_VALUE;
/** nav type */
private String navType = DEFAULT_VALUE;
/** aux value */
private String auxValue = YES;
/** doc value */
private String docValue = DEFAULT_VALUE;
/** spacing value */
private int spacing = -1;
/** station id */
private String locationId = null;
/** dataset position */
private int pos = 0;
/** start time */
private Date startDate = null;
/** end time */
private Date endDate = null;
/** time coordinate */
private String timeCoverage = "I";
/** no arg constructor */
public AddeImageURL() {}
/**
* Create an AddeImageURL.
*
* @param host host to send to
* @param requestType type of request (REQ_IMAGEDATA, REQ_IMAGEDIR)
* @param group ADDE group
* @param descriptor ADDE descriptor
*/
public AddeImageURL(String host, String requestType, String group,
String descriptor) {
this(host, requestType, group, descriptor, null);
}
/**
* Create an ADDE Image URL from the given specs.
*
* @param host host to send to
* @param requestType type of request (REQ_IMAGEDATA, REQ_IMAGEDIR)
* @param group ADDE group (may be null)
* @param descriptor ADDE descriptor (may be null)
* @param query query string (key/value pairs)
*/
public AddeImageURL(String host, String requestType, String group,
String descriptor, String query) {
super(host, requestType, group, descriptor, query);
}
/**
* Create an ADDE Image URL from the given spec
* @param host host to send to
* @param requestType type of request (REQ_IMAGEDATA, REQ_IMAGEDIR)
* @param group ADDE group
* @param descriptor ADDE descriptor
* @param locateKey locate key
* @param locateValue locate value
* @param placeValue place value
* @param lines number of lines
* @param elements number of elements
* @param lmag line magnification
* @param emag element magnification
* @param band band
* @param unit calibration unit
* @param spacing data size
*/
public AddeImageURL(String host, String requestType, String group,
String descriptor, String locateKey,
String locateValue, String placeValue, int lines,
int elements, int lmag, int emag, String band,
String unit, int spacing) {
super(host, requestType, group, descriptor);
this.locateKey = locateKey;
this.locateValue = locateValue;
this.placeValue = placeValue;
this.lines = lines;
this.elements = elements;
this.lmag = lmag;
this.emag = emag;
this.band = band;
this.unit = unit;
this.spacing = spacing;
}
/**
* Get the PLACE value
*
* @return the PLACE value
*/
public String getPlaceValue() {
return placeValue;
}
/**
* Get the locate key
*
* @return the locate key
*/
public String getLocateKey() {
return locateKey;
}
/**
* Get the locate value
*
* @return the locate value
*/
public String getLocateValue() {
return locateValue;
}
/**
* Get the number of lines
*
* @return the number of lines
*/
public int getLines() {
return lines;
}
/**
* Get the number of elements
*
* @return the number of elements
*/
public int getElements() {
return elements;
}
/**
* Get the element magnification
*
* @return the element magnification
*/
public int getElementMag() {
return emag;
}
/**
* Get the line magnification
*
* @return the line magnification
*/
public int getLineMag() {
return lmag;
}
/**
* Set the locate key
*
* @param value the locate key
*/
public void setLocateKey(String value) {
locateKey = value;
}
/**
* Set the locate value
*
* @param value the locate value
*/
public void setLocateValue(String value) {
locateValue = value;
}
/**
* Set the place value
*
* @param value the place value
*/
public void setPlaceValue(String value) {
placeValue = value;
}
/**
* Set the number of lines
*
* @param value the number of lines
*/
public void setLines(int value) {
lines = value;
}
/**
* Set the number of elements
*
* @param value the number of elements
*/
public void setElements(int value) {
elements = value;
}
/**
* Set the element magnification
*
* @param value the element magnification
*/
public void setElementMag(int value) {
emag = value;
}
/**
* Set the line magnification
*
* @param value the line magnification
*/
public void setLineMag(int value) {
lmag = value;
}
/**
* Set the data size (SPAC)
*
* @param value the data size
*/
public void setSpacing(int value) {
spacing = value;
}
/**
* Get the data size (SPAC)
*
* @return the data size
*/
public int getSpacing() {
return spacing;
}
/**
* Set the band or band range
*
* @param value the band range or ALL. For REQ_IMAGEDATA, must
* be a single band
*/
public void setBand(String value) {
band = value;
}
/**
* Get the band or band range
*
* @return the band range or ALL.
*/
public String getBand() {
return band;
}
/**
* Set the calibration unit
*
* @param value the calibration unit
*/
public void setUnit(String value) {
unit = value;
}
/**
* Get the calibration unit
*
* @return calibration unit
*/
public String getUnit() {
return unit;
}
/**
* Set the navigation type
*
* @param value the navigation type (X or LALO)
*/
public void setNavType(String value) {
navType = value;
}
/**
* Get the navigation type
*
* @return navigation type (default or LALO)
*/
public String getNavType() {
return navType;
}
/**
* Set the location ID for radar images
*
* @param value the location ID
*/
public void setId(String value) {
locationId = value;
}
/**
* Get the location ID for radar images
*
* @return location ID
*/
public String getId() {
return locationId;
}
/**
* Set the dataset position
*
* @param value the dataset position
*/
public void setDatasetPosition(int value) {
pos = value;
}
/**
* Get the dataset position
*
* @return dataset position
*/
public int getDatasetPosition() {
return pos;
}
/**
* Set the start date for the request
*
* @param value the starting date for the request
*/
public void setStartDate(Date value) {
startDate = value;
}
/**
* Get the start date for the request
*
* @return the start date for the request
*/
public Date getStartDate() {
return startDate;
}
/**
* Set the end date for the request
*
* @param value the ending date for the request
*/
public void setEndDate(Date value) {
endDate = value;
}
/**
* Get the end date for the request
*
* @return the ending date for the request
*/
public Date getEndDate() {
return endDate;
}
/**
* Set the time coverage
*
* @param value the time coverage
*/
public void setTimeCoverage(String value) {
timeCoverage = value;
}
/**
* Set the time coverage
*
* @return the time coverage
*/
public String getTimeCoverage() {
return timeCoverage;
}
/**
* Set the AUX keyword value
*
* @param value the AUX keyword value (YES, NO or DEFAULT_VALUE)
*/
public void setAuxValue(String value) {
auxValue = value;
}
/**
* Get the AUX keyword value
*
* @return the AUX keyword value (YES, NO or DEFAULT_VALUE)
*/
public String getAuxValue() {
return auxValue;
}
/**
* Set the DOC keyword value
*
* @param value the DOC keyword value (YES, NO or DEFAULT_VALUE)
*/
public void setDocValue(String value) {
docValue = value;
}
/**
* Get the DOC keyword value
*
* @return the DOC keyword value (YES, NO or DEFAULT_VALUE)
*/
public String getDocValue() {
return docValue;
}
/**
* Create the ADDE URL
* @return a Adde URL
*/
protected String makeQuery() {
StringBuffer buf = new StringBuffer(super.makeQuery());
if (getRequestType().equals(REQ_IMAGEDATA)) {
appendKeyValue(buf, KEY_BAND, band);
appendKeyValue(buf, getLocateKey(), getLocateValue());
appendKeyValue(buf, KEY_PLACE, getPlaceValue());
appendKeyValue(buf, KEY_SIZE, getLines() + " " + getElements());
appendKeyValue(buf, KEY_UNIT, getUnit());
appendKeyValue(buf, KEY_MAG, getLineMag() + " " + getElementMag());
appendKeyValue(buf, KEY_SPAC, ((getSpacing() == -1)
? DEFAULT_VALUE
: "" + getSpacing()));
appendKeyValue(buf, KEY_NAV, getNavType());
appendKeyValue(buf, KEY_AUX, getAuxValue());
appendKeyValue(buf, KEY_DOC, getDocValue());
}
else {
appendKeyValue(buf, KEY_BAND, ALL);
}
// add in for the radar queries
if (getId() != null) appendKeyValue(buf, KEY_ID, getId());
appendDateOrPosString(buf);
return buf.toString();
}
/**
* Create a DAY/TIME or POS string
* @param buf buffer to append to
*/
protected void appendDateOrPosString(StringBuffer buf) {
if (getStartDate() == null && getEndDate() == null) {
appendKeyValue(buf, KEY_POS, "" + getDatasetPosition());
}
else {
int[] start = null;
if (getStartDate() != null)
start = McIDASUtil.mcSecsToDayTime(getStartDate().getTime() / 1000l);
int[] end = null;
if (getEndDate() != null)
end = McIDASUtil.mcSecsToDayTime(getEndDate().getTime() / 1000l);
StringBuffer day = new StringBuffer();
StringBuffer time = new StringBuffer();
if (start != null) {
day.append("" + start[0]);
time.append(McIDASUtil.mcHmsToStr(start[1]));
}
day.append(" ");
time.append(" ");
if (end != null) {
if (getRequestType().equals(REQ_IMAGEDIR)) day.append("" + end[0]);
time.append("" + McIDASUtil.mcHmsToStr(end[1]));
}
else {
time.append(McIDASUtil.mcHmsToStr(start[1]));
}
time.append(" ");
time.append(getTimeCoverage());
appendKeyValue(buf, KEY_DAY, day.toString().trim());
appendKeyValue(buf, KEY_TIME, time.toString().trim());
}
}
}

View file

@ -1,538 +0,0 @@
//
// AddePointDataReader.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.util.Vector;
import edu.wisc.ssec.mcidas.McIDASUtil;
/**
* AddePointDataReader interface for McIDAS ADDE point data sets. Simulates a
* McIDAS PTLIST output using an ADDE URL if <code>toString() method is used.
*
* Note that units are ignored by this client, default units are used.
*
* <pre>
* URLs must all have the following format
* adde://host/point?keyword_1=value_1&amp;keyword_2=value_2
*
* there can be any valid combination of the following supported keywords:
*
* group=&lt;groupname&gt; ADDE group name
* descr=&lt;descriptor&gt; ADDE descriptor name
* pos=&lt;position&gt; request an absolute or relative ADDE
* position number
* select=&lt;select clause&gt; to specify which data is required
* param=&lt;param list&gt; what parameters to return
* num=&lt;max&gt; maximum number of obs to return
* user=&lt;user_id&gt; ADDE user identification
* proj=&lt;proj #&gt; a valid ADDE project number
* trace=&lt;0/1&gt; setting to 1 tells server to write debug
* trace file (imagedata, imagedirectory)
* version=1 ADDE version number, currently 1
*
* the following keywords are required:
*
* group
* descr
*
* an example URL might look like:
* adde://rtds/point?group=neons&amp;type=metar
* </pre>
*
* @author Don Murray - Unidata and James Kelly - BoM
*
*/
public class AddePointDataReader {
// load protocol for ADDE URLs
// See java.net.URL for explanation of URL handling
static
{
try
{
String handlers = System.getProperty("java.protocol.handler.pkgs");
String newProperty = null;
if (handlers == null)
newProperty = "edu.wisc.ssec.mcidas";
else if (handlers.indexOf("edu.wisc.ssec.mcidas") < 0)
newProperty = "edu.wisc.ssec.mcidas | " + handlers;
if (newProperty != null) // was set above
System.setProperty("java.protocol.handler.pkgs", newProperty);
}
catch (Exception e)
{
System.out.println(
"Unable to set System Property: java.protocol.handler.pkgs");
}
}
/**
* Key for getting data in param order [numParams][numObs]
*/
public static final int PARAM_ORDER = 0;
/**
* Key for getting data in obs order [numObs][numParams]
*/
public static final int OB_ORDER = 1;
/**
* Maximum number of parameters - used as a sanity check
*/
public static final int MAXNUMPARM = 402; // number of parameters
private int status=0; // read status
//private URLConnection urlc; // URL connection
private String[] params; // parameters returned from server
private int[] ScalingFactors; // scaling factors returned from server
private String[] units; // units returned from server
private int[][] iData = null; // data returned from server as array of ints
private int[][] oData = null; // data returned from server as array of ints
private Vector data = null; // holds the obs
private int numParams = 0; // number of parameters
private boolean debug = false; // set to true for debugging
/**
* creates an AddePointDataReader object that allows reading ADDE point
* datasets.
*
* @param request ADDE URL to read from. See class javadoc.
*
* <pre>
* an example URL might look like:
* adde://rtds.ho.bom.gov.au/point?group=neons&amp;descr=metar
* </pre>
*
* @exception AddeException if there are no datasets of the particular
* type or there is an error reading data
*
*/
public AddePointDataReader(String request)
throws AddeException
{
DataInputStream dataInputStream;
URLConnection urlc;
try
{
URL url = new URL(request);
urlc = url.openConnection();
//InputStream is = urlc.getInputStream();
dataInputStream =
new DataInputStream(
new BufferedInputStream(
urlc.getInputStream()));
}
catch (AddeURLException ae)
{
throw new AddeException("No datasets found " + ae);
}
catch (Exception e)
{
throw new AddeException("Error opening connection: " + e);
}
//
// first get number of bytes for Parameter Names
//
int numParamBytes;
if(urlc instanceof AddeURLConnection) {
numParamBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
} else {
try {
numParamBytes = dataInputStream.readInt();
} catch (IOException e) {
throw new AddeException("Error reading data: " + e);
}
}
if (debug) System.out.println("numParamBytes = " + numParamBytes);
if (numParamBytes == 0)
{
status = -1;
throw new AddeException("No data found");
} else if (numParamBytes/4 > MAXNUMPARM)
{
status = -1;
throw new AddeException("Not an ADDE Point Data set");
}
else
{
byte[] bParamNames = new byte[numParamBytes];
numParams = numParamBytes/4;
params = new String[numParams];
try
{
//
// read Parameter names into paramNames
//
dataInputStream.readFully(bParamNames, 0, numParamBytes);
String sParamNames = new String(bParamNames);
if (debug) System.out.println(" sParamNames = " + sParamNames);
for (int i = 0; i < numParams; i++)
params[i] = sParamNames.substring(i*4, (i+1)*4).trim();
}
catch (IOException e)
{
status = -1;
throw new AddeException("Error reading parameters:" + e);
}
}
//
// next get number of bytes for Unit Names
//
try
{
int numUnitBytes = dataInputStream.readInt();
units = new String[numUnitBytes/4];
if (debug) System.out.println("numUnitBytes = " + numUnitBytes);
byte[] bUnitNames = new byte[numUnitBytes];
dataInputStream.readFully(bUnitNames, 0, numUnitBytes);
String sUnitNames = new String(bUnitNames);
if (debug) System.out.println("sUnitNames = " + sUnitNames);
for (int i = 0; i < numUnitBytes/4; i++)
units[i] = sUnitNames.substring(i*4, (i+1)*4).trim();
}
catch (IOException e)
{
status = -1;
throw new AddeException("Error reading units:" + e);
}
//
// next get number of bytes for Scaling Factors
//
try
{
int numScalingBytes = dataInputStream.readInt();
if (debug)
System.out.println("numScalingBytes = " + numScalingBytes);
ScalingFactors = new int[(int)(numScalingBytes/4)];
for (int i=0; i < (int) (numScalingBytes/4); i++) {
ScalingFactors[i] = dataInputStream.readInt();
}
}
catch (IOException e)
{
status = -1;
throw new AddeException("Error reading scaling factors:" + e);
}
//
// next get number of bytes for the actual data
//
data = new Vector();
byte[] bThisUnitName = new byte[4];
try
{
int numDataBytes = dataInputStream.readInt();
while (numDataBytes !=0) {
if (debug) System.out.println(" i, Param, Unit, Value " );
int[] dataArray = new int[numParams];
for (int i=0; i < (int) (numDataBytes/4); i++) {
dataArray[i] = dataInputStream.readInt();
}
data.addElement(dataArray);
numDataBytes = dataInputStream.readInt();
if (debug) System.out.println("numDataBytes = " + numDataBytes);
}
}
catch (IOException e)
{
status = -1;
throw new AddeException("Error reading data:" + e);
}
}
/**
* Return the data sent by the server
*
* @return array of the data. Data is in the format of an integer array
* of unscaled integers as returned from the server in parameter
* order ([numParams][numObs]).
*
* @exception AddeException if there was an error reading data
*/
public int[][] getData()
throws AddeException
{
return getData(PARAM_ORDER);
}
/**
* Return the data sent by the server in a particular order
* (PARAM_ORDER, OB_ORDER).
* @param order order of the data. (PARAM_ORDER, OB_ORDER)
*
* @return array of the data. Data is in the format of an integer array
* of unscaled integers in the specified order
* (PARAM_ORDER = [numParams][numObs],
* OB_ORDER = [numObs][numParams])
*
* @exception AddeException if there was an error reading data
*/
public int[][] getData(int order)
throws AddeException
{
if (status < 0)
throw new AddeException("No data available");
return (order == PARAM_ORDER)
? getParamOrderData()
: getObOrderData();
}
/**
* Get the list of parameters
*
* @return array of the parameter names. The names will be in the same
* order as the array of data values in the <code>getData()</code>
* method.
*
* @exception AddeException if there was an error reading data
*/
public String[] getParams()
throws AddeException
{
if (status < 0)
throw new AddeException("No data available");
return params;
}
/**
* Get the list of units
*
* @return array of the unit names. The names will be in the same
* order as the array of data values in the <code>getData()</code>
* method.
*
* @exception AddeException if there was an error reading data
*/
public String[] getUnits()
throws AddeException
{
if (status < 0)
throw new AddeException("No data available");
return units;
}
/**
* Get the list of scaling factors
*
* @return array of the scaling factors (powers of 10). The scaling
* factors will be in the same order as the array of data
* values in the <code>getData()</code> method.
*
* @exception AddeException if there was an error reading data
*/
public int[] getScales()
throws AddeException
{
if (status < 0)
throw new AddeException("No data available");
return ScalingFactors;
}
/**
* return the number of parameters
*
* @return number of parameters returned from the server
*/
public int getNumParams()
throws AddeException
{
if (status < 0)
throw new AddeException("No data available");
return numParams;
}
/**
* Return an array of data for the particular parameter.
*
* @return array of values for the particular parameter or
* null if an invalid parameter was entered. This
* will return String[] for parameters with units of CHAR,
* float[1][] for an array of non scaled data, and double[1][] for
*/
public Object[] getData(String parameter)
throws AddeException
{
if (status < 0)
throw new AddeException("No data available");
for (int i = 0; i < numParams; i++)
{
if (parameter.equalsIgnoreCase(params[i]))
{
iData = getParamOrderData();
if (units[i].equalsIgnoreCase("CHAR"))
{
String[] vals = new String[iData[i].length];
for (int j = 0; j < iData[i].length; j++)
{
vals[j] = McIDASUtil.intBitsToString(iData[i][j]);
}
return vals;
}
else
if (ScalingFactors[i] != 0)
{
double[][] vals = new double[1][iData[i].length];
for (int j = 0; j < iData[i].length; j++)
{
vals[0][j] = iData[i][j]/Math.pow(10.0,
(double) ScalingFactors[i]);
}
return vals;
}
else
{
float[][] vals = new float[1][iData[i].length];
for (int j = 0; j < iData[i].length; j++)
{
vals[0][j] = (float) iData[i][j];
}
return vals;
}
}
}
return null;
}
/**
* Create an array of data in parameter order [numParams][numobs].
* @return array of data in parameter order
*/
private int[][] getParamOrderData() {
if (iData == null) {
// Convert to in array
iData = new int[numParams][data.size()];
if (debug) {
System.out.println("number of data records = " + data.size());
}
for (int i = 0; i < data.size(); i++)
{
int[] values = (int[]) data.get(i);
for (int j = 0; j < numParams; j++) iData[j][i] = values[j];
}
}
return iData;
}
/**
* Create an array of data in observation order [numObs][numParams].
* @return array of data in obs order
*/
private int[][] getObOrderData() {
if (oData == null) {
// Convert to in array
oData = new int[data.size()][numParams];
if (debug) {
System.out.println("number of data records = " + data.size());
}
for (int i = 0; i < data.size(); i++)
{
oData[i] = (int[]) data.get(i);
}
}
return oData;
}
/**
* Return a formated string of the returned data
*
* @return formatted representation of the data ala McIDAS PTLIST command.
*/
public String toString()
{
if (status < 0)
return new String("No data Available");
StringBuffer buf = new StringBuffer();
for (int i = 0; i < numParams; i++)
{
buf.append(params[i]);
buf.append("[");
buf.append(units[i]);
buf.append("] ");
buf.append("\t");
}
buf.append("\n");
iData = getParamOrderData();
for (int i = 0; i < iData[0].length; i++)
{
for (int j = 0; j < numParams; j++)
{
if (units[j].equalsIgnoreCase("CHAR"))
{
buf.append(McIDASUtil.intBitsToString(iData[j][i]));
}
else
if (ScalingFactors[j] != 0)
{
buf.append( iData[j][i] == McIDASUtil.MCMISSING
? " "
: Double.toString(
iData[j][i]/Math.pow(10.0,
(double) ScalingFactors[j] )));
}
else
{
buf.append( iData[j][i] == McIDASUtil.MCMISSING
? " "
: Integer.toString(iData[j][i]));
}
buf.append("\t");
}
buf.append("\n");
}
return buf.toString();
}
/** test by running 'java edu.wisc.ssec.mcidas.adde.AddePointDataReader' */
public static void main (String[] args)
throws Exception
{
System.out.println("\nData Requested:");
String request =
(args.length == 0)
// ? "adde://servb.ho.bom.gov.au/point?group=neons&descr=metar&num=2&select='id ymml; time 22 24; day 1999317'&parm=id dir spd t[c] td[c] psl&pos=ALL&version=1"
// Unidata server
? "adde://adde.ucar.edu/point?group=rtptsrc&descr=sfchourly&num=2&select='id ypph'&parm=id dir spd t[c] td[c] psl&pos=0&version=1&trace=1"
: args[0];
AddePointDataReader ptlist = new AddePointDataReader(request);
System.out.println(ptlist.toString());
}
}

View file

@ -1,321 +0,0 @@
//
// AddePointURL.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.util.regex.*;
/**
* A class for holding the ADDE URL for an image directory or data request.
* Decode the ADDE request for point data.
*
* If the request contains specific parameters (eg param=t),
* then the class variable binaryData is set to this param string
*
* <pre>
* group=&lt;groupname&gt; ADDE group name
* descr=&lt;descriptor&gt; ADDE descriptor name
* pos=&lt;position&gt; request an absolute or relative ADDE
* position number
* select=&lt;select clause&gt; to specify which data is required
* param=&lt;param list&gt; what parameters to return
* eg param=t[c]
* note that the units [c] are ignored by server
* it is the clients task to convert units
* Note that if "param=" is used,
* binaryData is set to the
* (processed) parameter list
* max=&lt;max&gt; maximum number of obs to return
* trace=&lt;0/1&gt; setting to 1 tells server to write debug
* trace file (imagedata, imagedirectory)
* binaryData=&lt;param list&gt; because an unlimited number of parameters may
* be requested, these must be packaged up at the end
* of the adde request, and this is known as the
* "binary data" part of the request
*
* the following keywords are required:
*
* group
*
* an example URL might look like:
* adde://rtds/point?group=neons&amp;descr=metar
*
* </pre>
*/
public class AddePointURL extends AddeDatasetURL {
/** Keyword for SELECT */
public static final String KEY_SELECT = "SELECT";
/** Keyword for PARAM */
public static final String KEY_PARAM = "PARAM";
/** Keyword for MAX */
public static final String KEY_MAX = "MAX";
/** Keyword for MAX */
public static final String KEY_NUM = "NUM";
/** Keyword for POS */
public static final String KEY_POS = "POS";
/** the select clause */
private String selectClause = "";
/** the parameters */
private String params = "";
/** the max value */
private int max = 1;
/** the max value */
private String pos = DEFAULT_VALUE;
/** no arg constructor */
public AddePointURL() {}
/**
* Create an AddePointURL.
*
* @param host host to send to
* @param requestType type of request (REQ_IMAGEDATA, REQ_IMAGEDIR)
* @param group ADDE group
* @param descriptor ADDE descriptor
*/
public AddePointURL(String host, String requestType, String group,
String descriptor) {
this(host, requestType, group, descriptor, null);
}
/**
* Create an ADDE PointURL from the given specs.
*
* @param host host to send to
* @param requestType type of request (REQ_IMAGEDATA, REQ_IMAGEDIR)
* @param group ADDE group (may be null)
* @param descriptor ADDE descriptor (may be null)
* @param query query string (key/value pairs)
*/
public AddePointURL(String host, String requestType, String group,
String descriptor, String query) {
super(host, requestType, group, descriptor, query);
}
/**
* Create an ADDE Point URL from the given spec
* @param host host to send to
* @param requestType type of request (REQ_IMAGEDATA, REQ_IMAGEDIR)
* @param group ADDE group
* @param descriptor ADDE descriptor
* @param position dataset position (number or ALL)
* @param select select clause
* @param paramList parameter list
* @param maxNum maximum number to return
*/
public AddePointURL(String host, String requestType, String group,
String descriptor, String position, String select,
String paramList, int maxNum) {
super(host, requestType, group, descriptor);
this.pos = position;
this.selectClause = selectClause;
this.params = paramList;
this.max = maxNum;
}
/**
* Get the SELECT value
*
* @return the PLACE value
*/
public String getSelectClause() {
return selectClause;
}
/**
* Set the SELECT clause
*
* @param value the SELECT clause
*/
public void setSelectClause(String value) {
selectClause = value;
}
/**
* Get the PARAM value
*
* @return the PARAM value
*/
public String getParams() {
return params;
}
/**
* Set the PARAM value
*
* @param value the PARAM clause
*/
public void setParams(String value) {
params = value;
}
/**
* Get the MAX value
*
* @return the MAX value
*/
public int getMaxNumber() {
return max;
}
/**
* Set the MAX value
*
* @param value the MAX clause
*/
public void setMaxNumber(int value) {
max = value;
}
/**
* Get the POS value
*
* @return the POS value (number or ALL)
*/
public String getPosition() {
return pos;
}
/**
* Set the POS value
*
* @param value the POS clause (number or ALL)
*/
public void setPosition(String value) {
pos = value;
}
/**
* Create the ADDE URL
* @return a Adde URL
*/
protected String makeQuery() {
StringBuffer buf = new StringBuffer(super.makeQuery());
if (!getSelectClause().equals(""))
appendKeyValue(buf, KEY_SELECT, getSelectClause());
if (!getParams().equals("")) appendKeyValue(buf, KEY_PARAM, getParams());
appendKeyValue(buf, KEY_MAX, String.valueOf(getMaxNumber()));
appendKeyValue(buf, KEY_POS, getPosition());
return buf.toString();
}
/**
* Decode a URL and return an AddePointURL
*
* @param baseURL url to decode
* @return an AddePointURL object (or null)
*/
public static AddePointURL decodeURL(String baseURL) {
Pattern pattern = Pattern.compile("(.*)://(.*)/(.*)\\?(.*)");
Matcher matcher = pattern.matcher(baseURL);
boolean ok = matcher.find();
if (!ok) {
return null;
}
int numGroups = matcher.groupCount();
if (numGroups >= 3) {
String protocol = matcher.group(1);
String requestType = matcher.group(3);
if (!(protocol.equals("adde") &&
requestType.toLowerCase().startsWith("point")))
return null;
AddePointURL apu = new AddePointURL();
apu.setHost(matcher.group(2));
apu.setRequestType(requestType);
if (numGroups > 3) {
String query = matcher.group(4);
apu.parseQuery(query);
}
return apu;
}
return null;
}
/**
* Parse the query string and set the values accordingly, subclasses
* should extend to parse their particular keywords
* @param query query string
*/
protected void parseQuery(String query) {
super.parseQuery(query);
String test = getValue(query, KEY_SELECT);
if (test != null) {
setSelectClause(test);
}
test = getValue(query, KEY_PARAM);
if (test != null) {
setParams(test);
}
test = getValue(query, KEY_POS);
if (test != null) {
setPosition(test);
}
test = getValue(query, KEY_MAX);
if (test != null) {
setMaxNumber(Integer.parseInt(test));
}
// and just in case people are using NUM, convert to max else {
test = getValue(query, KEY_NUM);
if (test != null) {
int num = max;
if (test.equalsIgnoreCase(ALL)) {
num = 99999;
}
else {
try {
num = Integer.parseInt(test);
}
catch (Exception e) {
}
}
setMaxNumber(num);
}
}
/**
* Test the parsing
*
* @param args url to parse
*/
public static void main(String[] args) {
if (args.length > 0) {
AddePointURL url = AddePointURL.decodeURL(args[0]);
System.out.println(url.getURLString());
}
}
}

View file

@ -1,171 +0,0 @@
//
// AddeSatBands.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.util.*;
import java.lang.*;
import java.io.*;
/** Helper class
* to interpret the band information
* from the ADDE SATBANDS file returned by servers
*/
public class AddeSatBands {
String[] c;
public AddeSatBands(String[] cards) {
c = cards;
}
/** given a sensor and a source type, return a list of bands possible
* @param sensor is the satellite sensor ID number
* @param src is the sensor source code
*
* @return String[] of channel words. The array is
* 1-based to match the customary way of numbering channels (bands),
* so element 0 is usually null
*/
public String[] getBandDescr(int sensor, String src) {
if (c == null) return null;
int gotit = -1;
Vector v = new Vector();
for (int i=0; i<c.length; i++) {
if ( ! c[i].startsWith("Sat ")) continue;
StringTokenizer st = new StringTokenizer(c[i]," ");
String temp = st.nextToken(); // throw away the key
int m = st.countTokens();
for (int k=0; k<m; k++) {
int ss = Integer.parseInt(st.nextToken().trim());
if (ss == sensor) {
gotit = i;
break;
}
}
if (gotit != -1) break;
}
if (gotit == -1) return null;
// now look for Source
int gotSrc = -1;
for (int i=gotit; i<c.length; i++) {
if (c[i].startsWith("EndSat")) break;
if ( ! c[i].startsWith("Cal ")) continue;
String srcVal = c[i].substring(4).trim();
if (srcVal.equals(src)) {
gotSrc = i;
break;
}
}
if (gotSrc == -1) return null;
gotSrc++;
for (int i=gotSrc; i<c.length; i++) {
if (c[i].startsWith("C") || c[i].startsWith("S") || c[i].startsWith("E")) break;
if (c[i].startsWith("B") ) continue;
String b = c[i].substring(0,2);
int bi = Integer.parseInt(b.trim());
String d = null;
int ids = c[i].indexOf("DESC="); // look for new file format
if (ids > 0) { // new format
int idsb = c[i].indexOf("'",ids+5);
if (idsb < 2) { // no quoted field
d = c[i].substring(ids+5);
} else {
int idse = c[i].indexOf("'", idsb+1);
d = c[i].substring(idsb+1,idse);
}
} else { // old format
d = c[i].substring(3).trim();
}
if (bi >= v.size()) v.setSize(bi+1);
v.setElementAt(d, bi);
}
int num = v.size();
String[] s = new String[num];
for (int i=0; i<num; i++) {
s[i] = (String) v.elementAt(i);
}
return s;
}
public static void main(String[] a) {
try {
DataInputStream das = new DataInputStream(new FileInputStream("/src/edu/wisc/ssec/mcidas/adde/satband.txt"));
//DataInputStream das = new DataInputStream(new FileInputStream("/src/edu/wisc/ssec/mcidas/adde/SATBAND-new.txt"));
Vector v = new Vector();
while(true) {
String s = das.readLine();
if (s == null) break;
v.addElement(s);
}
das.close();
int num = v.size();
System.out.println("size of input file = "+num);
String sat = "12";
//String src = "MSAT"; // this is an error
String src = "GMS";
if (a != null && a.length > 1) {
sat = a[0];
src = a[1];
}
String[] sv = new String[num];
for (int i=0; i<num; i++) { sv[i] = (String) v.elementAt(i); }
AddeSatBands asb = new AddeSatBands(sv);
String[] f = asb.getBandDescr(Integer.parseInt(sat), src);
System.out.println("return from addesatbands");
if (f == null) {
System.out.println("#### No matches found...!");
} else {
int numb = f.length;
System.out.println("length of return = "+numb);
for (int i=0; i<numb; i++) {
System.out.println("band = value -> "+i+" = "+f[i]);
}
}
} catch (Exception e) {System.out.println(e);}
}
}

View file

@ -1,556 +0,0 @@
//
// AddeServerInfo.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.*;
import java.lang.*;
import java.util.*;
import java.text.*;
import edu.wisc.ssec.mcidas.*;
import edu.wisc.ssec.mcidas.adde.*;
import edu.wisc.ssec.mcidas.adde.ReadTextFile;
import edu.wisc.ssec.mcidas.AreaDirectoryList;
import edu.wisc.ssec.mcidas.AreaDirectory;
import edu.wisc.ssec.mcidas.McIDASException;
/** All things related to ADDE servers, groups and datasets
*
* @author tomw
* @version 0.1
*/
public class AddeServerInfo extends Object {
private String[] serverList;
private String selectedServer = null;
private boolean hasServers = false;
private String dataType = null;
private String[] bandNames;
private boolean hasBandNames = false;
private String[] groupsList;
private String selectedGroup = null;
private boolean hasGroup = false;
private String[] datasetsList;
private String selectedDataset = null;
private boolean hasDataset = false;
private AreaDirectory [][]dirs;
private String[] dirsTimes;
private Vector table, groups;
private String status="OK";
private String userproj = null;
private String DATEFORMAT = "yyyy-MM-dd / HH:mm:ss";
private boolean debug = false;
private boolean priv = false;
private boolean isArchive = false;
private String archiveDate = null;
/** Creates new AddeServerInfo. This collects information about
* ADDE server(s) -- their groups, datasets, and date-times (right
* now only image date-time implemented). This is a helper class
* for anything else that needs to get these information.
*
* The candidate list of ADDE servers should be obtained from a
* yet-to-be-identified "well-known list", and made available
* in this class.
*/
public AddeServerInfo() {
// go find the list of well-known servers ?
this(null);
}
/** The non-default parameter is a list of of ADDE servers
*
* @param l a list of ADDE servers that can be used in lieu
* of automatically obtaining it.
*
*/
public AddeServerInfo(String[] l) {
// well known list of ADDE servers
String[] list = l;
if (list == null) {
list = new String[] {"adde.unidata.ucar.edu","suomi.ssec.wisc.edu",
"motherlode.ucar.edu","uwamrc.ssec.wisc.edu"};
}
serverList = new String[list.length];
for (int i=0; i<list.length; i++) {
serverList[i] = list[i];
}
hasServers = true;
}
/** get a list of servers
*
* @return names of server hosts
*/
public String[] getServerList() {
if (hasServers) {
return serverList;
} else {
return null;
}
}
/** get name of the server that has been selected and for
* which all group and dataset info is currently valid for
*
* @return name of server host
*/
public String getSelectedServer() {
return selectedServer;
}
/** define which server to select, and the type of ADDE data group
* (image, point, grid, text) to get group and descriptor info for
*
* This is the workhorse of the code.
*
* @param s the name of the ADDE server to be selected
* @param type the type of data to select.
*
* @return status code: 0=ok, -1=invalid accounting, -2=didn't get metadata
*
*/
public int setSelectedServer(String s, String type) {
selectedServer = s.trim();
int istatus = 0;
dataType = type.trim();
groups = new Vector();
status = "Failed to get PUBLIC.SRV file from from server "+s+".";
priv = false;
try {
// go get the modified PUBLIC.SRV file from the server...
String req = "adde://"+selectedServer+"/text?file=PUBLIC.SRV";
if (userproj != null) {
String req2 = req+"&"+userproj+"&version=1";
req = req2;
}
if (debug) System.out.println("Req:"+req);
ReadTextFile rtf = new ReadTextFile(req);
if (debug) System.out.println("Status from RTF="+rtf.getStatus());
// see if accounting data is required but not provided...
if (rtf.getStatusCode() == -3) {
return -1;
}
/* do we really want to do this????? */
// if that fails, try to get RESOLV.SRV, but keep it hidden...
if (!rtf.getStatus().equals("OK")) { // try again
req = "adde://"+selectedServer+"/text?file=RESOLV.SRV";
if (userproj != null) {
String req2 = req+"&"+userproj+"&version=1";
req = req2;
}
if (debug) System.out.println("2ndReq:"+req);
priv = true;
rtf = new ReadTextFile(req);
if (debug) System.out.println("Status from 2ndRTF="+rtf.getStatus());
}
table = rtf.getText();
status = "Failed to locate required information on server "+s+".";
// look at each table member and pull out info only
// when the TYPE='dataType'
for (int i=0; i<table.size(); i++) {
String a = (String) table.elementAt(i);
if (debug) System.out.println("Table: "+a);
StringTokenizer st = new StringTokenizer(a,",");
int num = st.countTokens();
String[] tok = new String[num];
String[] val = new String[num];
int indexType = -1;
int indexN1 = -1;
int indexN2 = -1;
int indexC = -1;
// number of items in the record
for (int j=0; j<num; j++) {
String p = st.nextToken();
// simple token=value within each group
int x = p.indexOf("=");
if (x < 0) continue;
tok[j] = p.substring(0,x);
val[j] = p.substring(x+1).trim();
// flags to indicate found needed keys
if (tok[j].equalsIgnoreCase("type")) indexType = j;
if (tok[j].equalsIgnoreCase("N1")) indexN1 = j;
if (tok[j].equalsIgnoreCase("N2")) indexN2 = j;
if (tok[j].equalsIgnoreCase("C")) indexC = j;
}
// skip if: a) no =, b> not TYPE type, c) element missing
if (debug) {
System.out.println("indexType = "+indexType+
" dataType="+dataType+" indexN1,N2,C="+indexN1+" "+
indexN2+" "+indexC);
}
if (indexType < 0) continue;
if (!val[indexType].equalsIgnoreCase(dataType)) continue;
if (indexN1 < 0 || indexN2 < 0) continue;
// If no Comment field, just use N2 (kludge)
if (indexC < 0) indexC = indexN2;
boolean hit = false;
// search to see if this group has been encountered before.
// if so, just append descr; otherwise make a new entry
for (int j=0; j<groups.size(); j++) {
Vector vg = (Vector)groups.elementAt(j);
// element: 0=groupname, 1=Vector of datasets, 2=Vector of descrs
String g = (String)vg.elementAt(0);
if (g.equalsIgnoreCase(val[indexN1])) {
hit = true;
Vector v = (Vector)vg.elementAt(1);
v.addElement(val[indexN2]);
v = (Vector)vg.elementAt(2);
v.addElement(val[indexC]);
}
}
// if needed, make a new entry
if (!hit) {
Vector v = new Vector();
v.addElement(val[indexN1]);
Vector v2 = new Vector();
v2.addElement(val[indexN2]);
Vector v3 = new Vector();
v3.addElement(val[indexC]);
v.addElement(v2);
v.addElement(v3);
groups.addElement(v);
}
}
String reqBand = "adde://"+selectedServer+"/text?file=SATBAND";
if (userproj != null) {
String reqBand2 = reqBand+"&"+userproj+"&version=1";
reqBand = reqBand2;
}
if (debug) System.out.println("ReqBand:"+reqBand);
ReadTextFile rtfBand = new ReadTextFile(reqBand);
if (debug) System.out.println("Status from RTFBand="+rtfBand.getStatus());
Vector vBand = null;
if (rtfBand.getStatus().equals("OK")) {
vBand = rtfBand.getText();
int num = vBand.size();
bandNames = new String[num];
for (int i=0; i<num; i++) {
bandNames[i] = (String) vBand.elementAt(i);
if (debug) System.out.println("band = "+bandNames[i]);
}
hasBandNames = true;
}
status = "ADDE group & dataset information retrieved from server "+s+".";
istatus = 0;
} catch (Exception e) {e.printStackTrace(); return -2;}
return istatus;
}
/** get a list of all groups valid for this server
*
* @return array of group ids
*/
public String[] getGroupList() {
// if private, return no group list...
if (priv) return null;
int num = groups.size();
String[] sg = new String[num];
for (int i=0; i<num; i++) {
Vector v = (Vector)groups.elementAt(i);
sg[i] = (String)v.elementAt(0);
}
status = "List of groups on server "+selectedServer+" obtained.";
return sg;
}
/** get a list of all datasets valid for this server and
* the designated group.
*
* @return array of dataset tags
*
*/
public String[] getDatasetList() {
int num = groups.size();
for (int i=0; i<num; i++) {
Vector v = (Vector)groups.elementAt(i);
String g = (String)v.elementAt(0);
if (g.equalsIgnoreCase(selectedGroup)) {
Vector ds = (Vector)v.elementAt(1);
int numds = ds.size();
String[] sdl = new String[numds];
for (int j=0; j<numds; j++) {
sdl[j] = (String)ds.elementAt(j);
}
status = "Dataset list for server "+selectedServer+
" and group "+selectedGroup+" obtained.";
return sdl;
}
}
status = "Dataset list for server "+selectedServer+
" and group "+selectedGroup+" not found.";
return null;
}
/** get a list of all dataset descriptions for this server and
* the designated group
*
* @return array of dataset descriptors
*
*/
public String[] getDatasetListDescriptions() {
int num = groups.size();
for (int i=0; i<num; i++) {
Vector v = (Vector)groups.elementAt(i);
String g = (String)v.elementAt(0);
if (g.equalsIgnoreCase(selectedGroup)) {
Vector dsd = (Vector)v.elementAt(2);
int numdsd = dsd.size();
String[] sdld = new String[numdsd];
for (int j=0; j<numdsd; j++) {
sdld[j] = (String)dsd.elementAt(j);
}
status = "Dataset list for server "+selectedServer+
" and group "+selectedGroup+" obtained.";
return sdld;
}
}
status = "Dataset list for server "+selectedServer+
" and group "+selectedGroup+" not found.";
return null;
}
/** get the valid date-time list for the selected server/group/dataset.
* Note that you must 'setSelectedGroup()' and 'setSelectedDataset()'
* prior to using this method.
*
* [Also, Don Murray at Unidata wrote the original - thanks!]
*
* @return list of date-times ("yy-MM-dd / hh:mm:ss" format)
* or the string "No data available"
*
*
*/
public String[] getDateTimeList() {
status = "Trying to get date-times for "+selectedGroup+
" from server "+selectedServer;
if (!hasGroup || !hasDataset) return null;
StringBuffer addeCmdBuff =
new StringBuffer("adde://"+selectedServer+
"/imagedir?group=" + selectedGroup);
addeCmdBuff.append("&descr=");
addeCmdBuff.append(selectedDataset);
// if user/proj supplied, then put them in here...
if (userproj != null) addeCmdBuff.append("&"+userproj);
addeCmdBuff.append("&pos=all&version=1");
if (isArchive && archiveDate != null) {
addeCmdBuff.append("&DAY="+archiveDate);
}
if (debug) System.out.println("cmd:"+addeCmdBuff.toString());
String[] times = {"No data available"};
try {
AreaDirectoryList adir =
new AreaDirectoryList(addeCmdBuff.toString());
dirs = adir.getSortedDirs();
int numTimes = dirs.length;
times = new String[numTimes];
SimpleDateFormat sdf = new SimpleDateFormat();
sdf.setTimeZone(TimeZone.getTimeZone("GMT"));
sdf.applyPattern(DATEFORMAT);
for (int i=0; i < numTimes; i++)
{
times[i] =
sdf.format(
dirs[i][0].getNominalTime(),
new StringBuffer(),
new FieldPosition(0)).toString();
}
dirsTimes = times;
}
catch (McIDASException e) {status = "Error getting times";}
return times;
}
/** get the sorted list of AreaDirectory objects
*
*/
public AreaDirectory[][] getAreaDirectories() {
return dirs;
}
/** identify the selected group
*
* @param g the name of the group to select
*/
public void setSelectedGroup(String g) {
selectedGroup = g;
hasGroup = true;
}
/** identify the selected dataset
*
* @param d the name of the dataset/descr to select
*/
public void setSelectedDataset(String d) {
selectedDataset = d;
hasDataset = true;
}
public void setIsArchive(boolean flag) {
isArchive = flag;
}
public boolean getIsArchive() {
return isArchive;
}
public void setArchiveDate(String d) {
archiveDate = d;
}
public String getArchiveDate() {
return archiveDate;
}
/** return the bandNames text
*
* @return array of text of the SATBAND data fetched from selectedServer
*
*/
public String[] getBandNames() {
if (hasBandNames) {
return bandNames;
} else {
return null;
}
}
/**
*/
public String getRequestString(int reqestType) {
return null;
// requestType = static ints IMAGE, DIR, etc
}
/** set the userID and proj number if required for transactions,
* as required by servers that use accounting.
*
* @param up the user/project number request string in
* the form "user=tom&proj=1234"
*
*
*/
public void setUserIDandProjString(String up) {
userproj = up;
return;
}
/** get the status of the last request
*
* @return words describing last transaction
*/
public String getStatus() {
return status;
}
/** for testing purposes. Hope Unidata doesn't mind...
*/
public static void main(String[] args) {
AddeServerInfo asi = new AddeServerInfo();
//asi.setUserIDandProjString("user=tomw&proj=8035");
//asi.setSelectedServer("eastl.ssec.wisc.edu", "image");
int sstat = asi.setSelectedServer("suomi.ssec.wisc.edu", "image");
//asi.setSelectedServer("adde.unidata.ucar.edu", "image");
System.out.println("Status = "+asi.getStatus()+" code="+sstat);
String[] a = asi.getGroupList();
System.out.println("Status = "+asi.getStatus());
for (int i=0; i<a.length; i++) {
System.out.println("group = "+a[i]);
// set the selected group
asi.setSelectedGroup(a[i]);
String[]b = asi.getDatasetList();
String[]c = asi.getDatasetListDescriptions();
for (int k=0; k<b.length; k++) {
System.out.println(" "+b[k]+" == "+c[k]);
if (i==0 && k==0) {
// set the selected Dataset, and fetch its date-time info
asi.setSelectedDataset(b[k]);
String[] dt = asi.getDateTimeList();
for (int m=0; m<dt.length; m++) {
System.out.println("DateTime = "+dt[m]);
}
}
}
}
System.out.println("Status = "+asi.getStatus());
}
}

View file

@ -1,500 +0,0 @@
//
// ReadWxText.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.io.DataInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import java.lang.*;
import java.util.*;
import edu.wisc.ssec.mcidas.McIDASUtil;
/**
* Read text from an ADDE server interface for McIDAS ADDE data sets.
* This class handles file, weather text and obs text requests.
* <P>
* <pre>
* For File Reading:
* URLs must all have the following format
* adde://host/text?file=filename.ext
*
* there can be any valid combination of the following supported keywords:
*
* file - name of text file on ADDE server
*
* the following keywords are required:
*
* file
*
* an example URL might look like:
* adde://viper/text?file=filename.ext
*
* For Weather Text Reading:
* URLs must all have the following format
* adde://host/wxtext?group=group&amp;key1=value1&amp;key2=val2....&amp;keyn=valn
*
* there can be any valid combination of the following supported keywords:
*
* group=&lt;group&gt; weather text group (default= RTWXTEXT)
* prod=&lt;product&gt; predefind product name
* apro=&lt;val1 .. valn&gt; AFOS/AWIPS product headers to match (don't
* use with wmo keyword
* astn=&lt;val1 .. valn&gt; AFOS/AWIPS stations to match
* wmo= &lt;val1 .. valn&gt; WMO product headers to match (don't
* use with apro keyword
* wstn=&lt;val1 .. valn&gt; WMO stations to match
* day=&lt;start end&gt; range of days to search
* dtime=&lt;numhours&gt; maximum number of hours to search back (def=96)
* match=&lt;match strings&gt; list of character match strings to find from text
* num=&lt;num&gt; number of matches to find (def=1)
*
* the following keywords are required:
*
* day (bug causes it not to default to current day)
* one of the selection criteria
*
* an example URL might look like:
* adde://adde.ucar.edu/wxtext?group=rtwxtext&amp;prod=zone_fcst&amp;astn=bou
*
* For Observational Text Reading:
* URLs must all have the following format
* adde://host/obtext?group=group&amp;descr=descr&amp;key1=value1....&amp;keyn=valn
*
* there can be any valid combination of the following supported keywords:
*
* group=&lt;group&gt; weather text group (default= RTWXTEXT)
* descr=&lt;descriptor&gt; weather text subgroup (default=SFCHOURLY)
* id=&lt;id1 id2 ... idn&gt; list of station ids
* co=&lt;co1 co2 ... con&gt; list of countries
* reg=&lt;reg1 reg2..regn&gt; list of regions
* newest=&lt;day hour&gt; most recent time to allow in request
* (def=current time)
* oldest=&lt;day hour&gt; oldest observation time to allow in request
* type=&lt;type&gt; numeric value for the type of ob
* nhours=&lt;numhours&gt; maximum number of hours to search
* num=&lt;num&gt; number of matches to find (def=1)
*
* the following keywords are required:
*
* group
* descr
* id, co, or reg
*
* an example URL might look like:
* adde://adde.ucar.edu/obtext?group=rtwxtext&amp;descr=sfchourly&amp;id=kden&amp;num=2
*
* </pre>
*
* @author Tom Whittaker/Don Murray
*
*/
public class AddeTextReader {
// load protocol for ADDE URLs
// See java.net.URL for explanation of URL handling
static
{
try
{
String handlers = System.getProperty("java.protocol.handler.pkgs");
String newProperty = null;
if (handlers == null)
newProperty = "edu.wisc.ssec.mcidas";
else if (handlers.indexOf("edu.wisc.ssec.mcidas") < 0)
newProperty = "edu.wisc.ssec.mcidas | " + handlers;
if (newProperty != null) // was set above
System.setProperty("java.protocol.handler.pkgs", newProperty);
}
catch (Exception e)
{
System.out.println(
"Unable to set System Property: java.protocol.handler.pkgs");
}
}
private int status=0; // read status
private String statusString = "OK";
private boolean debug = false; // debug
private Vector linesOfText = null;
private URLConnection urlc;
private DataInputStream dis;
private final int HEARTBEAT = 11223344;
private List<WxTextProduct> wxTextProds = new ArrayList<WxTextProduct>();
/**
* Creates an AddeTextReader object that allows reading an ADDE
* text file or weather text
*
* @param request ADDE URL to read from. See class javadoc.
*/
public AddeTextReader(String request) {
try {
URL url = new URL(request);
debug = request.indexOf("debug=true") > 0;
if (debug) System.out.println("Request: "+request);
urlc = url.openConnection();
InputStream is = urlc.getInputStream();
dis = new DataInputStream(is);
}
catch (AddeURLException ae)
{
status = -1;
statusString = "No data found";
String aes = ae.toString();
if (aes.indexOf(" Accounting ") != -1) {
statusString = "No accounting data";
status = -3;
}
if (debug) System.out.println("AddeTextReader Exception:"+aes);
}
catch (Exception e)
{
status = -2;
if (debug) System.out.println("AddeTextReader Exception:"+e);
statusString = "Error opening connection: "+e;
}
linesOfText = new Vector();
if (status == 0) readText(((AddeURLConnection) urlc).getRequestType());
if (linesOfText.size() < 1) statusString = "No data read";
status = linesOfText.size();
}
private void readText(int reqType) {
switch(reqType) {
case AddeURLConnection.TXTG:
readTextFile();
break;
case AddeURLConnection.WTXG:
readWxText();
break;
case AddeURLConnection.OBTG:
readObText();
break;
}
}
private void readTextFile() {
int numBytes;
try {
numBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
if (debug)
System.out.println("ReadTextFile: initial numBytes = " + numBytes);
numBytes = dis.readInt();
while ((numBytes = dis.readInt()) != 0) {
if (debug)
System.out.println("ReadTextFile: numBytes = " + numBytes);
byte[] data = new byte[numBytes];
dis.readFully(data,0,numBytes);
String s = new String(data);
if (debug) System.out.println(s);
linesOfText.addElement(s);
}
} catch (Exception iox) {
statusString = " "+iox;
}
}
private void readWxText() {
int numBytes;
/*
From the McIDAS programmer's ref:
The server sends the client the following information:
o 4-byte value containing the length of the client request
string; this lets users know how their request was expanded
when the PROD keyword is specified the expanded client
request string
o heartbeat value if needed
o 4-byte value containing the total number of bytes of
data for this text block, including the 64-byte header and
the text 64-byte text header
o n bytes of 80-character text, blank padded
The last three pieces of information are repeated until no more
data is found.
*/
try {
numBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
if (debug)
System.out.println("ReadWxText: initial numBytes = " + numBytes);
// Read in the expanded client request string
byte[] expandedRequest = new byte[numBytes];
dis.readFully(expandedRequest,0,numBytes);
String s = new String(expandedRequest);
if (debug)
System.out.println("Server interpreted request as:\n " + s);
// look for heartbeat
while ((numBytes = dis.readInt()) == 4) {
int check = dis.readInt();
if (check != HEARTBEAT) { // must be number of bytes to read
numBytes = check;
break;
}
}
// Now we go read the data
if (debug) System.out.println("numBytes for text = "+numBytes);
wxTextProds = new ArrayList<WxTextProduct>();
while (numBytes != 0) {
// read in the header
byte[] header = new byte[64];
dis.readFully(header,0,64);
WxTextProduct wtp = new WxTextProduct(header);
String head = new String(header);
// note this is not true text so prints as garbage
//if (debug) System.out.println(decodeWxTextHeader(header));
if (debug) System.out.println(wtp);
// read in the text in 80 byte chunks
byte[] text = new byte[numBytes-64];
dis.readFully(text,0,numBytes-64);
int nLines = text.length/80;
if (debug) System.out.println("nLines = " + nLines);
StringBuilder wxText = new StringBuilder();
for (int i = 0; i < nLines; i++)
{
String line = new String(text, i*80, 80);
linesOfText.add(line);
wxText.append(line);
wxText.append("\n");
}
wtp.setText(wxText.toString());
wxTextProds.add(wtp);
// read in next length, but check for heartbeat
while ((numBytes = dis.readInt()) == 4) {
int check = dis.readInt();
if (check != HEARTBEAT) { // must be number of bytes to read
numBytes = check;
break;
}
}
}
} catch (Exception iox) {
statusString = " "+iox;
}
}
private void readObText() {
int numBytes;
/*
From the McIDAS programmer's ref:
Once the data is formatted, the text data can be sent
to the client. The server sends the client the following
information:
o 4-byte value containing the length of the text header,
which is currently 96; when all the data is sent, this
value is reset to zero
o 96-byte text header
o 4-byte value containing the number of bytes of text to be sent
o n bytes of text; 80 characters per line, blank padded
This information should be repeated until no more data is found.
*/
try {
numBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
if (debug)
System.out.println("ReadObText: initial numBytes = " + numBytes);
while( numBytes != 0) {
// Read in the header
byte[] header = new byte[numBytes];
dis.readFully(header,0,numBytes);
String s = new String(header);
if (debug) System.out.println(decodeObsHeader(header));
numBytes = dis.readInt();
// Now we go read the data
if (debug) System.out.println("numBytes for text = "+numBytes);
// read in the data
byte[] text = new byte[numBytes];
dis.readFully(text,0,numBytes);
int nLines = text.length/80;
if (debug) System.out.println("nLines = " + nLines);
for (int i = 0; i < nLines; i++)
{
String line = new String(text, i*80, 80);
linesOfText.add(line);
}
numBytes = dis.readInt();
}
} catch (Exception iox) {
statusString = " "+iox;
}
}
/**
* Get a string representation of the status code
* @return human readable status
*/
public String getStatus() {
return statusString;
}
/**
* Return the status code of the read
* @return status code (>0 == read okay);
*/
public int getStatusCode() {
return status;
}
/**
* Return the number of lines of text that were read.
* @return number of lines.
*/
public int getNumLines() {
return linesOfText.size();
}
/**
* Return the text read from the server. If there was a problem
* the error message is returned.
* @return text from server or error message
*/
public String getText() {
StringBuffer buf = new StringBuffer();
if (getStatusCode() <= 0) {
buf.append(getStatus());
} else {
for (Iterator iter = linesOfText.iterator(); iter.hasNext();) {
buf.append((String) iter.next());
buf.append("\n");
}
}
return buf.toString();
}
public Vector getLinesOfText() {
Vector v = new Vector();
if (getStatusCode() <= 0) {
v.add(getStatus());
} else {
v.addAll(linesOfText);
}
return v;
}
public List<WxTextProduct> getWxTextProducts() {
List<WxTextProduct> retList = new ArrayList<WxTextProduct>();
retList.addAll(wxTextProds);
return retList;
}
/** test by running 'java edu.wisc.ssec.mcidas.adde.AddeTextReader' */
public static void main (String[] args)
throws Exception
{
String request = (args.length == 0)
? "adde://adde.ucar.edu/text?file=PUBLIC.SRV"
: args[0];
AddeTextReader atr = new AddeTextReader(request);
String status = atr.getStatus();
System.out.println("\n" + atr.getText());
}
private String decodeObsHeader(byte[] header) {
StringBuffer buf = new StringBuffer();
int[] values = McIDASUtil.bytesToIntegerArray(header,0,13);
buf.append("Ver = ");
buf.append(values[0]);
buf.append(" ObType = ");
buf.append(values[1]);
buf.append(" ActFlag = ");
buf.append(values[2]);
buf.append(" IDType = ");
buf.append(values[9]);
buf.append("\nStarting at ");
buf.append(values[3]);
buf.append(" ");
buf.append(values[4]);
buf.append(" ");
buf.append(values[5]);
buf.append("\nEnding at ");
buf.append(values[6]);
buf.append(" ");
buf.append(values[7]);
buf.append(" ");
buf.append(values[8]);
return buf.toString();
}
private String decodeWxTextHeader(byte[] header) {
StringBuffer buf = new StringBuffer();
int[] values = McIDASUtil.bytesToIntegerArray(header,0,13);
buf.append("SOU nb location day time WMO WSTN APRO ASTN\n");
buf.append("--- ---- -------- ------- ------ ------- ---- ---- ----\n");
buf.append(McIDASUtil.intBitsToString(values[0]));
buf.append(values[1]);
buf.append(" ");
buf.append(values[2]);
buf.append(" ");
buf.append(values[10]);
buf.append(" ");
buf.append(values[3]);
buf.append(" ");
buf.append(McIDASUtil.intBitsToString(values[4]));
buf.append(values[5]);
buf.append(" ");
buf.append(McIDASUtil.intBitsToString(values[6]));
buf.append(" ");
buf.append(McIDASUtil.intBitsToString(values[7]));
buf.append(" ");
buf.append(McIDASUtil.intBitsToString(values[8]));
return buf.toString();
}
}

View file

@ -1,603 +0,0 @@
//
// AddeURL.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
/**
* A class for holding information about an ADDE URL.
*
* <pre>
*
* URLs must all have the following format:
*
* adde://host/request?keyword_1=value_1&amp;keyword_2=value_2
*
* where request can be one of the following:
*
* datasetinfo - request for data set information (LWPR)
* griddirectory - request for grid directory information (GDIR)
* griddata - request for grid data (GGET)
* imagedata - request for data in AreaFile format (AGET)
* imagedirectory - request for image directory information (ADIR)
* pointdata - request for point data (MDKS)
* textdata - request to read a text file (TXTG)
* wxtext - request to read a weather text file (WTXG)
* obtext - request to read a observation text file (OBTG)
*
* There can be any valid combination of the following supported keywords:
*
* -------for any request
*
* group=&lt;groupname&gt; ADDE group name
* user=&lt;user_id&gt; ADDE user identification
* proj=&lt;proj #&gt; a valid ADDE project number
* trace=&lt;0/1&gt; setting to 1 tells server to write debug
* trace file
* version= ADDE version number, currently 1 except for
* griddata requests
* debug= set to true to watch the printlns stream by
* compress= set to "gzip" if you want to use the GZIP
* compression or "compress" if you want to use
* transfers in Unix compress format (You need to
* have the VisAD package if you want to support
* this.) default = none.
* port= Socket port to connect on. Overridden by
* a port specified in the host
* (e.g., adde.ucar.edu:500)
*
* </pre>
*/
public class AddeURL implements Cloneable {
/** The protocol */
public static final String ADDE_PROTOCOL = "adde";
/** AGET request type */
public final static String REQ_AGET = "aget";
/** ADIR request type */
public final static String REQ_ADIR = "adir";
/** LWPR request type */
public final static String REQ_LWPR = "lwpr";
/** GDIR request type */
public final static String REQ_GDIR = "gdir";
/** GGET request type */
public final static String REQ_GGET = "gget";
/** MDKS request type */
public final static String REQ_MDKS = "mdks";
/** TXTG request type */
public final static String REQ_TXTG = "txtg";
/** WTXG request type */
public final static String REQ_WTXG = "wtxg";
/** OBTG request type */
public final static String REQ_OBTG = "obtg";
/** Image data request type */
public final static String REQ_IMAGEDATA = "imagedata";
/** Image directory request type */
public final static String REQ_IMAGEDIR = "imagedirectory";
/** Data set info request type */
public final static String REQ_DATASETINFO = "datasetinfo";
/** Text request type */
public final static String REQ_TEXT = "text";
/** weather text request type */
public final static String REQ_WXTEXT = "wxtext";
/** obs text request type */
public final static String REQ_OBTEXT = "obtext";
/** Grid data request type */
public final static String REQ_GRIDDATA = "griddata";
/** Grid directory request type */
public final static String REQ_GRIDDIR = "griddir";
/** Point data request type */
public final static String REQ_POINTDATA = "point";
/** Default value for key/value pairs (X) */
public final static String DEFAULT_VALUE = "X";
/** Value for yes */
public final static String YES = "YES";
/** Value for no */
public final static String NO = "NO";
/** Value for ALL */
public final static String ALL = "ALL";
/** Keyword for trace */
public static final String KEY_TRACE = "TRACE";
/** Keyword for debug */
public static final String KEY_DEBUG = "DEBUG";
/** Keyword for port */
public static final String KEY_PORT = "PORT";
/** Keyword for project */
public static final String KEY_PROJ = "PROJ";
/** Keyword for user */
public static final String KEY_USER = "USER";
/** Keyword for compress */
public static final String KEY_COMPRESS = "COMPRESS";
/** Keyword for version */
public static final String KEY_VERSION = "VERSION";
/** Flag for "compress" compression. */
public final static int COMPRESS = 503;
/** Flag for "no compress" compression. */
public final static int NO_COMPRESS = 500;
/** Flag for GZip compression. */
public final static int GZIP = 112;
/** flag for trace on */
public static final int TRACE_ON = 0;
/** flag for trace off */
public static final int TRACE_OFF = 1;
/** the host */
private String host = "localhost";
/** the version */
private String version = "" + AddeURLConnection.VERSION_1;
/** the user id */
private String user = AddeURLConnection.DEFAULT_USER;
/** the project number */
private int project = AddeURLConnection.DEFAULT_PROJ;
/** the trace flag */
private int trace = 0;
/** the extra key/value pairs */
private String extraKeys = null;
/** the compression type */
private int compress = -1; // let port determine compression by default
/** the port */
private int port = AddeURLConnection.DEFAULT_PORT;
/** the request type */
private String requestType = "";
/** the debug type */
private boolean debug = false;
/**
* Create an ADDE URL
*/
public AddeURL() {}
/**
* Create an ADDE URL from the given spec
* @param host host to send to
* @param requestType type of request (REQ_*)
*/
public AddeURL(String host, String requestType) {
this(host, requestType, null);
}
/**
* Create an ADDE URL from the given spec
* @param host host to send to
* @param requestType type of request (REQ_*)
* @param extraKeys extra key/value arguments
*/
public AddeURL(String host, String requestType, String extraKeys) {
this.host = host;
this.requestType = requestType;
this.extraKeys = extraKeys;
}
/**
* Create the ADDE URL as a String
*
* @return an Adde URL
*/
public String getURLString() {
StringBuffer buf = new StringBuffer(ADDE_PROTOCOL);
buf.append("://");
buf.append(host);
buf.append("/");
buf.append(requestType);
buf.append("?");
buf.append(makeQuery());
return buf.toString();
}
/**
* Make the query portion of the URL (e.g., key1=value1&amp;key2=value2..)
* Subclasses should override.
*
* @return the query portion of the URL
*/
protected String makeQuery() {
StringBuffer buf = new StringBuffer();
appendKeyValue(buf, KEY_PORT, "" + getPort());
appendKeyValue(buf, KEY_COMPRESS, getCompressionType());
appendKeyValue(buf, KEY_USER, getUser());
appendKeyValue(buf, KEY_PROJ, "" + getProject());
appendKeyValue(buf, KEY_VERSION, getVersion());
appendKeyValue(buf, KEY_DEBUG, Boolean.toString(getDebug()));
appendKeyValue(buf, KEY_TRACE, "" + getTrace());
if (getExtraKeys() != null) {
if (!getExtraKeys().startsWith("&")) buf.append("&");
buf.append(getExtraKeys());
}
return buf.toString();
}
/**
* Parse the query string and set the values accordingly, subclasses
* should extend to parse their particular keywords
* @param query query string
*/
protected void parseQuery(String query) {
String test = getValue(query, KEY_PORT);
if (test != null) {
setPort(Integer.parseInt(test));
}
test = getValue(query, KEY_COMPRESS);
if (test != null) {
setCompressionFromString(test);
}
test = getValue(query, KEY_USER);
if (test != null) {
setUser(test);
}
test = getValue(query, KEY_PROJ);
if (test != null) {
setProject(Integer.parseInt(test));
}
test = getValue(query, KEY_VERSION);
if (test != null) {
setVersion(test);
}
test = getValue(query, KEY_DEBUG);
if (test != null) {
setDebug(test.equals("true"));
}
test = getValue(query, KEY_TRACE);
if (test != null) {
setTrace(Integer.parseInt(test));
}
}
/**
* Get the value for a particular key.
* @param query the query string
* @param key the key to search
* @return the value or null if it doesn't exist
*/
public String getValue(String query, String key) {
String retVal = null;
int keyIndex = query.indexOf(key);
if (keyIndex < 0) { // try lowercase version;
keyIndex = query.indexOf(key.toLowerCase());
}
if (keyIndex >= 0) {
int equalIndex = query.indexOf("=", keyIndex);
int ampIndex = query.indexOf("&", keyIndex);
retVal = (ampIndex >= 0)
? query.substring(equalIndex+1, ampIndex) // to the amp
: query.substring(equalIndex+1); // to the end
}
return retVal;
}
/**
* A utility method to make a name=value part of the adde request string
*
* @param buf The buffer to append to
* @param name The property name
* @param value The value
*/
protected void appendKeyValue(StringBuffer buf, String name, String value) {
if ((buf.length() == 0) || (buf.charAt(buf.length() - 1) != '?')) {
buf.append("&");
}
buf.append(name);
buf.append("=");
buf.append(value);
}
/**
* Compare two AddeURLs
*
* @param o Object in question
*
* @return true if they are the same object or if all
*/
public boolean equals(Object o) {
if (!(o.getClass().equals(this.getClass()))) {
return false;
}
AddeURL that = (AddeURL)o;
if (this == that) {
return true;
}
return getURLString().equals(that.getURLString());
}
/**
* Get the hashcode for this
*
* @return the hashcode
*/
public int hashCode() {
return getURLString().hashCode();
}
/**
* Get the host for this ADDE URL
* @return the host
*/
public String getHost() {
return host;
}
/**
* Set the host for this ADDE URL
* @param host the host
*/
public void setHost(String host) {
this.host = host;
}
/**
* Get the request type for this ADDE URL
* @return the host
*/
public String getRequestType() {
return requestType;
}
/**
* Set the request type for this ADDE URL
*
* @param requestType the request Type
*/
public void setRequestType(String requestType) {
this.requestType = requestType;
}
/**
* Get the extraKeys string for this ADDE URL
* @return the extraKeys string
*/
public String getExtraKeys() {
return extraKeys;
}
/**
* Set the extraKeys string for this ADDE URL
* @param extraKeys the extraKeys
*/
public void setExtraKeys(String extraKeys) {
this.extraKeys = extraKeys;
}
/**
* Get the project for this ADDE URL
* @return the project
*/
public String getUser() {
return user;
}
/**
* Set the user for this ADDE URL
* @param user the user
*/
public void setUser(String user) {
this.user = user;
}
/**
* Get the project for this ADDE URL
* @return the project
*/
public int getProject() {
return project;
}
/**
* Set the project for this ADDE URL
* @param project the project
*/
public void setProject(int project) {
this.project = project;
}
/**
* Get the version for this ADDE URL
* @return the version
*/
public String getVersion() {
return version;
}
/**
* Set the version this ADDE URL
* @param version the version
*/
public void setVersion(String version) {
this.version = version;
}
/**
* Get the debug value for this ADDE URL
* @return the debug value (true or false)
*/
public boolean getDebug() {
return debug;
}
/**
* Set the debug value this ADDE URL
* @param debug the debug value (true or false);
*/
public void setDebug(boolean debug) {
this.debug = debug;
}
/**
* Get the port for this ADDE URL
* @return the port
*/
public int getPort() {
return port;
}
/**
* Set the port used for this ADDE URL
* @param port the port
*/
public void setPort(int port) {
this.port = port;
}
/**
* Get the compression type for this ADDE URL
* @return the compression type
*/
public int getCompression() {
return compress;
}
/**
* Set the compression type used for this ADDE URL
* @param compress the compression type (GZIP, NO_COMPRESS, COMPRESS)
*/
public void setCompression(int compress) {
this.compress = compress;
}
/**
* Get the trace value used for this ADDE URL
* @return the trace value (TRACE_ON, TRACE_OFF)
*/
public int getTrace() {
return trace;
}
/**
* Set the trace value used for this ADDE URL
* @param trace the trace value (TRACE_ON, TRACE_OFF)
*/
public void setTrace(int trace) {
this.trace = trace;
}
/**
* Get the compression type from the port number if not specified.
*
* @return the compression type as a string
*/
private String getCompressionType() {
String testStr = null;
int valueToCheck = (compress == -1)
? port
: compress;
switch (valueToCheck) {
case NO_COMPRESS: // port == 500
case 1: // port == 1
testStr = "none";
break;
case COMPRESS: // port == 503
case 2: // port == 2
testStr = "compress";
break;
case GZIP: // port == 112
case 3: // port == 3
default:
testStr = "gzip";
break;
}
return testStr;
}
/**
* Set the compression type from a string
*
* @param type the string type
*/
public void setCompressionFromString(String type) {
if (type.equals("gzip") || type.equals("112")) {
setCompression(112);
}
else if (type.equals("compress") || type.equals("503")) {
setCompression(503);
}
else if (type.equals("none") || type.equals("500")) {
setCompression(500);
}
}
/**
* Clones this instance.
*
* <p>This implementation never throws {@link CloneNotSupportException}.</p>
*
* @return A clone of this instance.
* @throws CloneNotSupportedException if cloning isn't supported.
*/
public Object clone() throws CloneNotSupportedException {
Object clone = null;
try {
clone = super.clone();
}
catch (CloneNotSupportedException ex) {
throw new Error("Assertion failure"); // can't happen
}
return clone;
}
}

View file

@ -1,48 +0,0 @@
//
// AddeURLException.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
/**
* AddeURLException class is to handle exceptions when using ADDE URLs.
*
* @author Tommy Jasmin, University of Wisconsin - SSEC
*/
import java.io.IOException;
public class AddeURLException extends IOException {
public AddeURLException() {
super();
}
public AddeURLException(String s) {
super(s);
}
}

View file

@ -1,72 +0,0 @@
//
// AddeURLStreamHandler.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.io.IOException;
import java.net.URL;
import java.net.URLConnection;
import java.net.URLStreamHandler;
/**
* This class defines the openConnection method, which is
* used to create an AddeURLConnection. Note that this
* class is automatically loaded when a URL of this type
* is created, you don't have explicitly create an object.
*
* @author Tommy Jasmin, University of Wisconsin, SSEC
*/
public class AddeURLStreamHandler extends URLStreamHandler
{
/**
*
* returns a reference to a special URLConnection object
* designed to implement the ADDE protocol.
*
* @param url - user specified URL, encodes ADDE request
* @return AddeURLConnection reference.
*/
protected URLConnection openConnection(URL url)
throws IOException
{
return new AddeURLConnection(url);
}
/**
* Returns the default port for a URL parsed by this handler.
* This method is meant to be overidden by handlers with default
* port numbers.
*/
protected int getDefaultPort() {
return AddeURLConnection.DEFAULT_PORT;
}
}

View file

@ -1,62 +0,0 @@
//
// AddeURLStreamHandlerFactory.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.net.URLStreamHandler;
import java.net.URLStreamHandlerFactory;
/**
* This class creates a URLStreamHandler for the ADDE protocol.
* An instance is passed to URL.setURLStreamHandlerFactory when
* an application will be using ADDE URLs.
*
* @author Tommy Jasmin, University of Wisconsin, SSEC
*/
public class AddeURLStreamHandlerFactory
implements URLStreamHandlerFactory
{
/**
*
* Creates URLStreamHandler object - not called directly.
*
* @param protocol - should be "adde"
* @return AddeURLStreamHandler reference.
*/
public URLStreamHandler createURLStreamHandler(String protocol) {
if (protocol.equalsIgnoreCase("adde")) {
return new AddeURLStreamHandler();
} else {
return null;
}
}
}

View file

@ -1,306 +0,0 @@
//
// DataSetInfo.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import java.util.Hashtable;
import java.util.Arrays;
import java.util.Enumeration;
/**
* DataSetInfo interface for McIDAS ADDE data sets. Simulates a
* McIDAS DSINFO request using an ADDE URL.
*
* <pre>
* URLs must all have the following format
* adde://host/datasetinfo?keyword_1=value_1&keyword_2=value_2
*
* there can be any valid combination of the following supported keywords:
*
* group - ADDE group name
* type - ADDE data type. Must be one of the following:
* image, point, grid, text, nav
* the default is the image type.
*
* the following keywords are required:
*
* group
*
* an example URL might look like:
* adde://viper/datasetinfo?group=gvar&type=image
* </pre>
*
* @author Don Murray
*
*/
public class DataSetInfo
{
// load protocol for ADDE URLs
// See java.net.URL for explanation of URL handling
static
{
try
{
String handlers = System.getProperty("java.protocol.handler.pkgs");
String newProperty = null;
if (handlers == null)
newProperty = "edu.wisc.ssec.mcidas";
else if (handlers.indexOf("edu.wisc.ssec.mcidas") < 0)
newProperty = "edu.wisc.ssec.mcidas | " + handlers;
if (newProperty != null) // was set above
System.setProperty("java.protocol.handler.pkgs", newProperty);
}
catch (Exception e)
{
System.out.println(
"Unable to set System Property: java.protocol.handler.pkgs");
}
}
private int status=0; // read status
private char[] data; // data returned from server
private Hashtable descriptorTable;
private boolean debug = false; // debug
/**
* creates a DataSetInfo object that allows reading
*
* @param request ADDE URL to read from. See class javadoc.
*
* <pre>
* an example URL might look like:
* adde://viper/datasetinfo?group=gvar&type=image
* </pre>
*
* @exception AddeURLException if there are no datasets of the particular
* type or there is an error reading data
*
*/
public DataSetInfo(String request)
throws AddeURLException
{
URLConnection urlc;
BufferedReader reader;
debug = debug || request.indexOf("debug=true") >= 0;
try
{
URL url = new URL(request);
urlc = url.openConnection();
reader =
new BufferedReader(
new InputStreamReader(
urlc.getInputStream()));
}
catch (AddeURLException ae)
{
status = -1;
throw new AddeURLException("No datasets found");
}
catch (Exception e)
{
status = -1;
throw new AddeURLException("Error opening connection: " + e);
}
int numBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
if (debug) System.out.println("DataSetInfo: numBytes = " + numBytes);
if (numBytes == 0)
{
status = -1;
throw new AddeURLException("No datasets found");
}
else
{
data = new char[numBytes];
try
{
int start = 0;
while (start < numBytes)
{
int numRead =
reader.read(data, start, (numBytes - start));
if (debug) System.out.println("bytes read = " + numRead);
start += numRead;
}
}
catch (IOException e)
{
status = -1;
throw new AddeURLException("Error reading dataset info:" + e);
}
int numNames = data.length/80;
descriptorTable = new Hashtable(numNames);
if (debug)
System.out.println("Number of descriptors = " + numNames);
for (int i = 0; i < numNames; i++)
{
String temp = new String(data, i*80, 80);
if (debug) System.out.println("Parsing: >"+temp+"<");
if (temp.trim().equals("")) continue;
String descriptor = temp.substring(0,12).trim();
if (debug) System.out.println("Descriptor = " + descriptor);
String comment = descriptor;
int pos = temp.indexOf('"');
if (debug) System.out.println("Found quote at " + pos);
if (pos >= 23)
{
comment = temp.substring(pos + 1).trim();
if (comment.equals("")) comment = descriptor;
}
if (debug) System.out.println("Comment = " + comment);
descriptorTable.put(comment, descriptor);
}
}
}
/**
* Return the data sent by the server
*
* @return array of the data. Data is in the format of a McIDAS DSINFO
* (LWPR) request.
*
* @exception AddeURLException if there was an error reading data
*/
public char[] getData()
throws AddeURLException
{
if (status < 0)
throw new AddeURLException("No data available");
return data;
}
/**
* Return a hashtable of descriptive names and ADDE dataset descriptors
* Descriptive names are the keys. If there is no descriptive name,
* the dataset descriptor is used.
*
* @return hashtable of names/desciptors
*
* @exception AddeURLException if there was an error reading data
*/
public Hashtable getDescriptionTable()
throws AddeURLException
{
if (status < 0)
throw new AddeURLException("No data available");
return descriptorTable;
}
/**
* Return a sorted list of the dataset descriptors
*
* @return sorted list
*
* @exception AddeURLException if there was an error reading data
*/
public String[] getDescriptors()
throws AddeURLException
{
if (status < 0)
throw new AddeURLException("No data available");
String[] list = new String[descriptorTable.size()];
Enumeration elements = descriptorTable.elements();
int i = 0;
while (elements.hasMoreElements())
{
list[i] = (String) elements.nextElement();
i++;
}
Arrays.sort(list);
return list;
}
/**
* Return a formated string of the returned data
*
* @return formatted string representing the data.
*/
public String toString()
{
if (status < 0)
return new String("No data Available");
String header = new String(
"Name NumPos Content\n" +
"------------ ------ --------------------------------------\n");
StringBuffer buf = new StringBuffer(header);
for (int i = 0; i < data.length/80; i++)
{
StringBuffer sb =
new StringBuffer(" ");
String line = new String(data, i*80, 80);
sb.insert(0,line.substring(0,12));
int brange = 0;
int erange = 0;
try {
brange = Integer.parseInt(line.substring(12,18).trim());
} catch (NumberFormatException ne) { brange = 0; }
try {
erange = Integer.parseInt(line.substring(18,23).trim());
} catch (NumberFormatException ne) { erange = 0; }
if (erange == 0) erange = brange;
int numPos = (erange-brange) + 1;
int insertPos = 17;
if (numPos >= 10 && numPos < 100)
insertPos = 16;
else if (numPos >= 100 && numPos < 1000)
insertPos = 15;
else if (numPos > 1000)
insertPos = 14;
sb.insert(insertPos,String.valueOf(numPos));
int pos = line.indexOf('"');
if (pos >= 23) sb.insert(22, line.substring(pos+1));
buf.append(sb.toString().trim());
buf.append("\n");
}
return buf.toString();
}
/** test by running 'java edu.wisc.ssec.mcidas.adde.DataSetInfo' */
public static void main (String[] args)
throws Exception
{
System.out.println("\nDataset Names:\n");
String request = (args.length == 0)
? "adde://adde.unidata.ucar.edu/datasetinfo?group=blizzard&type=image"
: args[0];
DataSetInfo dsinfo = new DataSetInfo(request);
System.out.println(dsinfo.toString());
String[] descriptors = dsinfo.getDescriptors();
System.out.println("Sorted list of Descriptors:");
for (int i = 0; i < descriptors.length; i++)
System.out.println(descriptors[i]);
}
}

View file

@ -1,538 +0,0 @@
//
// GetAreaFile.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.io.*;
import java.util.*;
import java.lang.*;
import java.awt.*;
import java.awt.image.*;
import java.awt.event.*;
import javax.swing.*;
import edu.wisc.ssec.mcidas.*;
import edu.wisc.ssec.mcidas.adde.*;
import edu.wisc.ssec.mcidas.AreaFile;
import edu.wisc.ssec.mcidas.AreaFileException;
/**
* Application to fetch an AREA file and write it as a local file.
*
* It is command-line driven, but can be forced into "gui mode" by
* either using the '-gui' option or specifying the URL 'adde://image?'
* as the source (although in the latter case, you still need to
* the desitnation filename on the command line; whereas with the -gui
* option, a FileChooser is presented to the user).
*
* @author Tom Whittaker, SSEC/CIMSS
*
*/
public class GetAreaFile implements ActionListener {
final String[] paramNames = {"host", "group", "descr", "user", "proj",
"trace", "band","mag","linele","place","pos",
"size","unit","spac","doc","latlon",
"aux","time","day","cal","id" };
String[] flags = {"h","g","d", "k","j","t",
"b","m","l","n","p",
"s","u","z","o","r",
"a","i","y","c","e"};
String[] paramValues;
String[] serverNames;
String paramFile, outputFile;
Properties pars;
boolean verbose;
boolean doGUI=false;
GetAreaGUI gag = null;
String gagRequest = null;
/** AD_DATAOFFSET - byte offset to start of data block */
public static final int AD_DATAOFFSET = 33;
/** AD_NAVOFFSET - byte offset to start of navigation block */
public static final int AD_NAVOFFSET = 34;
/** AD_AUXOFFSET - byte offset to start of auxilliary data section */
public static final int AD_AUXOFFSET = 59;
/** AD_CALOFFSET - byte offset to start of calibration section */
public static final int AD_CALOFFSET = 62;
/** AD_DATAWIDTH - number of bytes per data point */
public static final int AD_DATAWIDTH = 10;
public static void main(String args[] ) {
GetAreaFile gaf = new GetAreaFile(args);
}
public GetAreaFile(String args[]) {
paramFile = "params.properties";
verbose = false;
// if no arguments, emit a "help" message
if (args == null || args.length < 1) {
System.out.println("Usage: java edu.wisc.ssec.mcidas.GetAreaFile [options] output_file");
System.out.println(" Command line [options] are:");
for (int i=0; i<paramNames.length; i++) {
System.out.println(" -"+flags[i]+" = "+paramNames[i]);
}
System.out.println(" -f = parameter save filename (def=params.properties)");
System.out.println(" -v (verbose text output)");
System.out.println(" -gui = use GUI interface (no other options should be used with this)");
System.out.println(" Note: for multi-argument options (like -s), you need to enclose the values in quotes. e.g., -s \"200 200\"");
return;
}
paramValues = new String[paramNames.length];
// first try to get all the command line parameters
outputFile = doArguments(args);
if (outputFile == null) {
System.out.println("No output file specified...");
return;
}
// now go for the properties file
pars = fetchParams(paramFile);
if (doGUI) {
doGUI();
// ug = new UseGUI(this, pars);
} else {
doRequest(pars);
}
}
public void actionPerformed(ActionEvent e) {
System.out.println("got action performed...");
if (!e.getActionCommand().startsWith("adde://")) return;
Object source = e.getSource();
if (source.equals(gag)) {
Properties p = new Properties();
putProp(p,"host",gag.getServer());
putProp(p,"group",gag.getGroup());
putProp(p,"descr",gag.getDescr());
putProp(p,"user",gag.getUserName());
putProp(p,"proj",gag.getProjectNumber());
putProp(p,"trace",null);
putProp(p,"band",gag.getBand());
putProp(p,"mag",gag.getMag());
String ctype = gag.getCoordType();
if (ctype.equals("E")) {
putProp(p,"latlon",gag.getLocationString());
} else if (ctype.equals("I")) {
putProp(p,"linele",gag.getLocationString());
} else if (ctype.equals("S")) {
putProp(p,"id",gag.getLocationString());
}
putProp(p,"time",gag.getTime());
putProp(p,"day",gag.getDay());
putProp(p,"size",gag.getNumLinesEles());
putProp(p,"unit",gag.getUnit());
putProp(p,"doc",gag.getDoc());
gagRequest = e.getActionCommand();
JFileChooser getout = new JFileChooser();
getout.setDialogTitle("Name of AREA file to write into");
int status = getout.showSaveDialog(gag);
if (status == JFileChooser.APPROVE_OPTION) {
File fn = getout.getSelectedFile();
putProp(p,"outfile",fn.toString()); // temporary...
doRequest(p);
} else {
gag.status("File not saved!!!");
}
return;
}
}
void putProp(Properties p, String name, String value) {
if (value == null) return;
if (value.trim().length() < 1) return;
p.put(name,value);
return;
}
private void doGUI() {
String thost, tgroup, tdescr;
String tpos, tday, ttime;
String tlatlon, tlinele;
String tsize, tmag, tspac;
String tband, tunit;
String taux, tcal, tid, tdoc;
String ttrace, tuser, tproj;
gag = new GetAreaGUI("Select File", false);
gag.addActionListener(this);
gag.show();
tuser = pars.getProperty("user");
if (tuser != null) gag.setUserName(tuser);
tproj = pars.getProperty("proj");
if (tproj != null) gag.setProjectNumber(tproj);
tpos = pars.getProperty("pos");
//if (tpos != null) gag.setDatasetPosition(tpos);
tday = pars.getProperty("day");
ttime = pars.getProperty("time");
tlatlon = pars.getProperty("latlon");
tlinele = pars.getProperty("linele");
tid = pars.getProperty("id");
if (tlatlon != null) {
gag.setCoordType("E");
gag.setLocationString(tlatlon);
} else if (tlinele != null) {
gag.setCoordType("I");
gag.setLocationString(tlinele);
} else if (tid != null) {
gag.setCoordType("S");
gag.setLocationString(tid);
}
tsize = pars.getProperty("size");
if (tsize != null) {
gag.setNumLinesEles(tsize);
} else {
gag.setNumLinesEles("480 640");
}
tmag = pars.getProperty("mag");
if (tmag != null) gag.setMag(tmag);
tband = pars.getProperty("band");
if (tband != null) gag.setBand(tband);
tspac = pars.getProperty("spac");
//if (tspac != null) gag.setNumBytes(tspac);
tunit = pars.getProperty("unit");
if (tunit != null) gag.setUnit(tunit);
tcal = pars.getProperty("cal");
//if (tcal != null) gag.setCal(tcal);
tdoc = pars.getProperty("doc");
if (tdoc != null) gag.setDoc(tdoc);
taux = pars.getProperty("aux");
//if (taux != null) gag.setAux(taux);
}
public void doRequest(Properties params) {
String request = makeADDEString(params);
if (gagRequest != null) request = gagRequest;
if (gag != null) outputFile = params.getProperty("outfile");
System.out.println("Request sent: "+request);
if (gag != null) gag.status("Request sent: "+request);
AreaFile af;
try {
af = new AreaFile(request);
} catch (AreaFileException e) {
System.out.println("While getting AreaFile:"+e);
String es = e.toString();
String es2 = es;
int ei = es.lastIndexOf("Exception:");
if (ei > 0) es = es2.substring(ei+11);
if (gag != null) gag.status("Error: "+es);
return;
}
int[] dir;
dir=af.getDir();
if (dir == null) {
System.out.println("No AREA file directory!");
return;
}
if (verbose) {
System.out.println("Length of directory = "+dir.length);
for (int i=0; i<dir.length; i++) {
System.out.println(" index "+i+" = "+dir[i]);
}
}
int[] nav=null;
nav=af.getNav();
if (nav == null) {
System.out.println("No navigation block!");
} else {
if (verbose) System.out.println("Length of nav block = "+nav.length);
}
int[] cal=null;
cal=af.getCal();
if (cal == null) {
System.out.println("No calibration block!");
} else {
if (verbose) System.out.println("Length of cal block = "+cal.length);
}
int[] aux=null;
aux=af.getAux();
if (aux == null) {
System.out.println("No aux block");
} else {
if (verbose) System.out.println("Length of aux block = "+aux.length);
}
int NL=dir[8];
int NE=dir[9];
if (verbose) System.out.println("Start reading data, num points="+(NL*NE));
if (gag != null) gag.status("Start reading data, num points="+(NL*NE));
int[][]data;
try { data = af.getData(0,0,NL,NE); }
catch (AreaFileException e) {System.out.println(e);return;}
if (verbose) System.out.println("Finished reading data");
if (gag != null) gag.status("Finished reading data");
try {
RandomAccessFile raf = new RandomAccessFile(outputFile,"rw");
if (verbose) System.out.println("Dir to word 0");
raf.seek(0);
dir[0] = 0; // make sure this is zero!!
for (int i=0; i<dir.length; i++) raf.writeInt(dir[i]);
if (verbose) System.out.println("Nav to word "+dir[AD_NAVOFFSET]);
if (nav != null && dir[AD_NAVOFFSET] > 0) {
raf.seek(dir[AD_NAVOFFSET]);
for (int i=0; i<nav.length; i++) raf.writeInt(nav[i]);
}
if (verbose) System.out.println("Cal to word "+dir[AD_CALOFFSET]);
if (cal != null && dir[AD_NAVOFFSET] > 0) {
raf.seek(dir[AD_CALOFFSET]);
for (int i=0; i<cal.length; i++) raf.writeInt(cal[i]);
}
if (verbose) System.out.println("Aux to word "+dir[AD_AUXOFFSET]);
if (aux != null && dir[AD_NAVOFFSET] > 0) {
raf.seek(dir[AD_AUXOFFSET]);
for (int i=0; i<aux.length; i++) raf.writeInt(aux[i]);
}
if (verbose) System.out.println("Data to word "+dir[AD_DATAOFFSET]);
if (dir[AD_NAVOFFSET] > 0) {
raf.seek(dir[AD_DATAOFFSET]);
for (int i=0; i<data.length; i++) {
for (int j=0; j<data[i].length; j++) {
if (dir[AD_DATAWIDTH] == 1) {
raf.writeByte(data[i][j]);
} else if (dir[AD_DATAWIDTH] == 2) {
raf.writeShort(data[i][j]);
} else if (dir[AD_DATAWIDTH] == 4) {
raf.writeInt(data[i][j]);
}
}
}
}
raf.close();
} catch (Exception we) {System.out.println(we);}
System.out.println( "Completed. Data saved to: "+outputFile+
" Saving parameters to: "+paramFile);
if (gag != null) gag.status("Completed. Data saved to: "+outputFile+
" Saving parameters to: "+paramFile);
writeParams(paramFile,params);
}
/** make the ADDE request string out of the various parameters
* the host, group and descr are required. Everything else is
* optional. version=1 is appended...
*/
public String makeADDEString(Properties params) {
String host = params.getProperty("host");
if (host == null) return null;
String group = params.getProperty("group");
if (group == null) return null;
String descr = params.getProperty("descr");
if (descr == null) return null;
StringBuffer sb = new StringBuffer("adde://"+host+"/image?");
for (int i=0; i<paramNames.length; i++) {
if (paramNames[i] != "host" && params.getProperty(paramNames[i]) != null) {
sb.append(paramNames[i]+"="+params.getProperty(paramNames[i])+"&");
}
}
sb.append("version=1");
return sb.toString();
}
/** scans the input argument list and if it finds any legitimate
* flags, it replaces the value of the parameter
*/
String doArguments(String[] arg) {
String outfile = arg[arg.length - 1];
// if there is only one parameter, see if it's the '-gui' switch
// instead of the 'outfile' name
if (outfile.equalsIgnoreCase("-gui")) {
doGUI = true;
outfile = " ";
return outfile;
}
for (int k=0; k<arg.length-1; k++) {
String s = arg[k];
if ((s.length()) > 1 && s.startsWith("-")) {
if (s.equalsIgnoreCase("-gui")) {
doGUI = true;
continue;
}
String r = s.substring(1,2);
if (r.equals("f")) {
if (s.length() == 2) {
paramFile = arg[++k];
} else {
paramFile = s.substring(2);
}
} else if (r.equals("v")) {
verbose = true;
} else {
for (int i=0; i<paramNames.length; i++) {
if (r.equals(flags[i])) {
if (s.length() == 2) {
paramValues[i] = arg[++k];
} else {
paramValues[i] = s.substring(2);
}
}
}
}
} else {
System.out.println("Problem with parameter: "+s);
return null;
}
}
return outfile;
}
/** fetch the parameters from the property file
*/
Properties fetchParams(String filename) {
Properties p = new Properties();
try {
InputStream is = new FileInputStream(filename);
p.load(is);
is.close();
} catch (Exception e) {System.out.println(e);}
for (int i=0; i<paramNames.length; i++) {
if (paramValues[i] != null) p.put(paramNames[i], paramValues[i]);
}
//if (outputFile != null && outputFile.length>1) p.put("outfile",outputFile);
return p;
}
/** write the property file back out...
*/
void writeParams(String filename, Properties p) {
try {
OutputStream os = new FileOutputStream(filename);
p.save(os,"GetAreaFile properties");
os.flush();
os.close();
} catch (Exception e) {System.out.println(e);}
}
}
/*
*-g group=<groupname> ADDE group name
*-k user=<user_id> ADDE user identification
*-j proj=<proj #> a valid ADDE project number
*-t trace=<0/1> setting to 1 tells server to write debug
* trace file (imagedata, imagedirectory)
* version=1 ADDE version number, currently 1
*
*-d descr=<descriptor> ADDE descriptor name
*-b band=<band> spectral band or channel number
*-m mag=<lmag> <emag> image magnification, postitive for blowup,
* negative for blowdown (default = 1, emag=lmag)
* (imagedata only)
*-l linele=<lin> <ele> <type> line/element to center image on
*-n place=<placement> placement of lat/lon or linele points (center
* or upperleft (def=center))
*-p pos=<position> request an absolute or relative ADDE position
* number
*-s size=<lines> <elements> size of image to be returned (imagedata only)
*-u unit=<unit> to specify calibration units other than the
* default
*-z spac=<bytes> number of bytes per data point, 1, 2, or 4
* (imagedata only)
*-o doc=<yes/no> specify yes to include line documentation
* with image (def=no)
*-r latlon=<lat> <lon> lat/lon point to center image on
*-a aux=<yes/no> specify yes to include auxilliary information
* with image for calibration purposes
*-i time=<time1> <time2> specify the time range of images to select
* (def=latest image if pos not specified)
*-y day=<day> specify the day of the images to select
* (def=latest image if pos not specified)
*-c cal=<cal type> request a specific calibration on the image
* (imagedata only)
*-i id=<stn id> radar station id
*-h host= ADDE server hostname or IP address
*
*/

View file

@ -1,43 +0,0 @@
//
// Handler.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
/**
* This class defines the openConnection method, which is
* used to create an AddeURLConnection. Note that this
* class is automatically loaded when a URL of this type
* is created, you don't have explicitly create an object.<P>
*
* The class name allows this to work if the system property
* java.protocol.handler.pkgs includes the edu.wisc.ssec.mcidas
* package.
* @see java.net.URL for more information
*
* @author Don Murray, UCAR/Unidata
*/
public class Handler extends AddeURLStreamHandler {}

View file

@ -1,201 +0,0 @@
//
// ReadTextFile.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import java.io.DataInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import java.lang.*;
import java.util.*;
/**
* ReadTextFile interface for McIDAS ADDE data sets.
*
* <pre>
* URLs must all have the following format
* adde://host/text?file=filename.ext
*
* there can be any valid combination of the following supported keywords:
*
* file - name of text file on ADDE server
*
* the following keywords are required:
*
* file
*
* an example URL might look like:
* adde://viper/text?file=filename.ext
* </pre>
*
* @author Tom Whittaker (derived from DataSetInfo by Don Murray)
*
*/
public class ReadTextFile
{
// load protocol for ADDE URLs
// See java.net.URL for explanation of URL handling
static
{
try
{
String handlers = System.getProperty("java.protocol.handler.pkgs");
String newProperty = null;
if (handlers == null)
newProperty = "edu.wisc.ssec.mcidas";
else if (handlers.indexOf("edu.wisc.ssec.mcidas") < 0)
newProperty = "edu.wisc.ssec.mcidas | " + handlers;
if (newProperty != null) // was set above
System.setProperty("java.protocol.handler.pkgs", newProperty);
}
catch (Exception e)
{
System.out.println(
"Unable to set System Property: java.protocol.handler.pkgs");
}
}
private int status=0; // read status
private String statusString = null;
private boolean debug = false; // debug
private Vector linesOfText = null;
private URLConnection urlc;
private DataInputStream dis;
/**
* creates a ReadTextFile object that allows reading an ADDE
* text file or TEXT dataset
*
* @param request ADDE URL to read from. See class javadoc.
*
* <pre>
* an example URL might look like:
* adde://viper/datasetinfo?group=gvar&descr=FILE=RESOLV.SRV
* </pre>
*
* @exception AddeURLException if there are no datasets of the particular
* type or there is an error reading data
*
*/
public ReadTextFile(String request) {
status = 0;
statusString = "OK";
try {
URL url = new URL(request);
if (debug) System.out.println("Request: "+request);
urlc = url.openConnection();
InputStream is = urlc.getInputStream();
dis = new DataInputStream(is);
}
catch (AddeURLException ae)
{
status = -1;
statusString = "No file found";
String aes = ae.toString();
if (aes.indexOf(" Accounting ") != -1) {
statusString = "No accounting data";
status = -3;
}
if (debug) System.out.println("ReadText AF Exception:"+aes);
}
catch (Exception e)
{
status = -2;
if (debug) System.out.println("ReadText Exception:"+e);
statusString = "Error opening connection: "+e;
}
int numBytes;
linesOfText = new Vector();
if (status == 0) {
try {
numBytes = ((AddeURLConnection) urlc).getInitialRecordSize();
if (debug)
System.out.println("ReadTextFile: initial numBytes = " + numBytes);
numBytes = dis.readInt();
while ((numBytes = dis.readInt()) != 0) {
if (debug)
System.out.println("ReadTextFile: numBytes = " + numBytes);
byte[] data = new byte[numBytes];
dis.readFully(data,0,numBytes);
String s = new String(data);
if (debug) System.out.println(s);
linesOfText.addElement(s);
}
} catch (Exception iox) {
statusString = " "+iox;
System.out.println(" "+iox);
}
if (linesOfText.size() < 1) statusString = "No data read";
status = linesOfText.size();
}
}
public String getStatus() {
return statusString;
}
public int getStatusCode() {
return status;
}
public Vector getText() {
return linesOfText;
}
/** test by running 'java edu.wisc.ssec.mcidas.adde.ReadTextFile' */
public static void main (String[] args)
throws Exception
{
String request = (args.length == 0)
? "adde://adde.ucar.edu/text?file=PUBLIC.SRV"
: args[0];
ReadTextFile rtf = new ReadTextFile(request);
String status = rtf.getStatus();
System.out.println("Status = "+status);
if (status.equals("OK")) {
Vector l = rtf.getText();
for (int i=0; i<l.size(); i++) {
System.out.println( (String)l.elementAt(i));
}
}
}
}

View file

@ -1,222 +0,0 @@
//
// WxTextProduct.java
//
/*
This source file is part of the edu.wisc.ssec.mcidas package and is
Copyright (C) 1998 - 2009 by Tom Whittaker, Tommy Jasmin, Tom Rink,
Don Murray, James Kelly, Bill Hibbard, Dave Glowacki, Curtis Rueden
and others.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
package edu.wisc.ssec.mcidas.adde;
import edu.wisc.ssec.mcidas.McIDASUtil;
import java.util.Date;
/**
* Class to hold a weather text product returned from an ADDE server
*/
public class WxTextProduct {
/** soure of the data */
private String source = "";
/** number of bytes */
private int numBytes = 0;
/** location in the file */
private int location = 0;
/** day of report */
private int day = 0;
/** time of report */
private int time = 0;
/** WMO id*/
private String wmo = "";
/** WMO station */
private String wstn = "";
/** AFOS product id */
private String apro = "";
/** AFOS station */
private String astn = "";
/** product text */
private String text = "";
/** date of bulleting */
private Date date = new Date();
/**
* Create a new WxTextProduct from the header info.
*
* @param header the ADDE header
*/
public WxTextProduct(byte[] header) {
int[] values = McIDASUtil.bytesToIntegerArray(header, 0, 13);
source = McIDASUtil.intBitsToString(values[0]);
numBytes = values[1];
location = values[2];
day = values[10];
time = values[3];
String wmoBase = McIDASUtil.intBitsToString(values[4]);
int wmoNum = values[5];
wmo = wmoBase + ((wmoNum < 10)
? "0"
: "") + wmoNum;
wstn = McIDASUtil.intBitsToString(values[6]);
apro = McIDASUtil.intBitsToString(values[7]);
astn = McIDASUtil.intBitsToString(values[8]);
date = new Date(McIDASUtil.mcDayTimeToSecs(day, time) * 1000);
}
/**
* Adde text to the existing text
*
* @param newText
*/
public void addText(String newText) {
text = text + newText;
}
/**
* Set the text of the bulleting
*
* @param newText the text
*/
public void setText(String newText) {
text = newText;
}
/**
* Get the product text
*
* @return the product text
*/
public String getText() {
return text;
}
/**
* Get the source of the product
*
* @return the source of the product
*/
public String getSource() {
return source;
}
/**
* Get the day of the product
*
* @return the day of the product
*/
public int getDay() {
return day;
}
/**
* Get the time of the product
*
* @return the time of the product
*/
public int getTime() {
return time;
}
/**
* Get the wmo id of the product
*
* @return the wmo id of the product
*/
public String getWmo() {
return wmo;
}
/**
* Get the wmo station
*
* @return the wmo station
*/
public String getWstn() {
return wstn;
}
/**
* Get the AFOS product id
*
* @return the AFOS product id
*/
public String getApro() {
return apro;
}
/**
* Get the AFOS station
*
* @return the AFOS station
*/
public String getAstn() {
return astn;
}
/**
* Get the date of the product
*
* @return the date of the product
*/
public Date getDate() {
return date;
}
/**
* Get the string representation of this product
*/
public String toString() {
StringBuffer buf = new StringBuffer();
buf.append("SOU nb location day time WMO WSTN APRO ASTN\n");
buf.append("--- ---- -------- ------- ------ ------- ---- ---- ----\n");
buf.append(source);
buf.append(numBytes);
buf.append(" ");
buf.append(location);
buf.append(" ");
buf.append(day);
buf.append(" ");
buf.append(time);
buf.append(" ");
buf.append(wmo);
buf.append(" ");
buf.append(wstn);
buf.append(" ");
buf.append(apro);
buf.append(" ");
buf.append(astn);
return buf.toString();
}
}

View file

@ -1,7 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<classpath>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.6"/>
<classpathentry kind="con" path="org.eclipse.pde.core.requiredPlugins"/>
<classpathentry exported="true" kind="lib" path="fits.jar" sourcepath="fits_src.jar"/>
<classpathentry kind="output" path="bin"/>
</classpath>

View file

@ -1,28 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>gov.nasa.gsfc.fits</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.jdt.core.javabuilder</name>
<arguments>
</arguments>
</buildCommand>
<buildCommand>
<name>org.eclipse.pde.ManifestBuilder</name>
<arguments>
</arguments>
</buildCommand>
<buildCommand>
<name>org.eclipse.pde.SchemaBuilder</name>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.pde.PluginNature</nature>
<nature>org.eclipse.jdt.core.javanature</nature>
</natures>
</projectDescription>

View file

@ -1,9 +0,0 @@
Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: fits
Bundle-SymbolicName: gov.nasa.gsfc.fits
Bundle-Version: 1.0.0.qualifier
Bundle-ClassPath: fits.jar
Bundle-RequiredExecutionEnvironment: JavaSE-1.6
Export-Package: nom.tam.fits,
nom.tam.util

Some files were not shown because too many files have changed in this diff Show more